OSDN Git Service

* config/mips/mips.md: Complete the unfinished R4000
[pf3gnuchains/gcc-fork.git] / gcc / config / mips / mips.md
1 ;;  Mips.md          Machine Description for MIPS based processors
2 ;;  Copyright (C) 1989, 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
3 ;;  1999, 2000, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
4 ;;  Contributed by   A. Lichnewsky, lich@inria.inria.fr
5 ;;  Changes by       Michael Meissner, meissner@osf.org
6 ;;  64 bit r4000 support by Ian Lance Taylor, ian@cygnus.com, and
7 ;;  Brendan Eich, brendan@microunity.com.
8
9 ;; This file is part of GCC.
10
11 ;; GCC is free software; you can redistribute it and/or modify
12 ;; it under the terms of the GNU General Public License as published by
13 ;; the Free Software Foundation; either version 2, or (at your option)
14 ;; any later version.
15
16 ;; GCC is distributed in the hope that it will be useful,
17 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
18 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19 ;; GNU General Public License for more details.
20
21 ;; You should have received a copy of the GNU General Public License
22 ;; along with GCC; see the file COPYING.  If not, write to
23 ;; the Free Software Foundation, 59 Temple Place - Suite 330,
24 ;; Boston, MA 02111-1307, USA.
25
26 ;; ??? Currently does not have define_function_unit support for the R8000.
27 ;; Must include new entries for fmadd in addition to existing entries.
28
29 (define_constants
30   [(UNSPEC_LOAD_DF_LOW           0)
31    (UNSPEC_LOAD_DF_HIGH          1)
32    (UNSPEC_STORE_DF_HIGH         2)
33    (UNSPEC_GET_FNADDR            3)
34    (UNSPEC_BLOCKAGE              4)
35    (UNSPEC_CPRESTORE             5)
36    (UNSPEC_EH_RECEIVER           6)
37    (UNSPEC_EH_RETURN             7)
38    (UNSPEC_CONSTTABLE_QI         8)
39    (UNSPEC_CONSTTABLE_HI         9)
40    (UNSPEC_CONSTTABLE_SI        10)
41    (UNSPEC_CONSTTABLE_DI        11)
42    (UNSPEC_CONSTTABLE_SF        12)
43    (UNSPEC_CONSTTABLE_DF        13)
44    (UNSPEC_ALIGN_2              14)
45    (UNSPEC_ALIGN_4              15)
46    (UNSPEC_ALIGN_8              16)
47    (UNSPEC_HIGH                 17)
48    (UNSPEC_LWL                  18)
49    (UNSPEC_LWR                  19)
50    (UNSPEC_SWL                  20)
51    (UNSPEC_SWR                  21)
52    (UNSPEC_LDL                  22)
53    (UNSPEC_LDR                  23)
54    (UNSPEC_SDL                  24)
55    (UNSPEC_SDR                  25)
56    (UNSPEC_LOADGP               26)
57    (UNSPEC_LOAD_CALL            27)
58    (UNSPEC_LOAD_GOT             28)
59
60    (UNSPEC_ADDRESS_FIRST        100)
61
62    (FAKE_CALL_REGNO             79)])
63 \f
64 ;; ....................
65 ;;
66 ;;      Attributes
67 ;;
68 ;; ....................
69
70 (define_attr "got" "unset,xgot_high,load"
71   (const_string "unset"))
72
73 ;; For jal instructions, this attribute is DIRECT when the target address
74 ;; is symbolic and INDIRECT when it is a register.
75 (define_attr "jal" "unset,direct,indirect"
76   (const_string "unset"))
77
78 ;; This attribute is YES if the instruction is a jal macro (not a
79 ;; real jal instruction).
80 ;;
81 ;; jal is always a macro in SVR4 PIC since it includes an instruction to
82 ;; restore $gp.  Direct jals are also macros in NewABI PIC since they
83 ;; load the target address into $25.
84 (define_attr "jal_macro" "no,yes"
85   (cond [(eq_attr "jal" "direct")
86          (symbol_ref "TARGET_ABICALLS != 0")
87          (eq_attr "jal" "indirect")
88          (symbol_ref "(TARGET_ABICALLS && !TARGET_NEWABI) != 0")]
89         (const_string "no")))
90
91 ;; Classification of each insn.
92 ;; branch       conditional branch
93 ;; jump         unconditional jump
94 ;; call         unconditional call
95 ;; load         load instruction(s)
96 ;; store        store instruction(s)
97 ;; prefetch     memory prefetch (register + offset)
98 ;; prefetchx    memory indexed prefetch (register + register)
99 ;; move         data movement within same register set
100 ;; condmove     conditional moves
101 ;; xfer         transfer to/from coprocessor
102 ;; hilo         transfer of hi/lo registers
103 ;; arith        integer arithmetic instruction
104 ;; darith       double precision integer arithmetic instructions
105 ;; const        load constant
106 ;; imul         integer multiply
107 ;; imadd        integer multiply-add
108 ;; idiv         integer divide
109 ;; icmp         integer compare
110 ;; fadd         floating point add/subtract
111 ;; fmul         floating point multiply
112 ;; fmadd        floating point multiply-add
113 ;; fdiv         floating point divide
114 ;; fabs         floating point absolute value
115 ;; fneg         floating point negation
116 ;; fcmp         floating point compare
117 ;; fcvt         floating point convert
118 ;; fsqrt        floating point square root
119 ;; frsqrt       floating point reciprocal square root
120 ;; multi        multiword sequence (or user asm statements)
121 ;; nop          no operation
122 (define_attr "type"
123   "unknown,branch,jump,call,load,store,prefetch,prefetchx,move,condmove,xfer,hilo,const,arith,darith,imul,imadd,idiv,icmp,fadd,fmul,fmadd,fdiv,fabs,fneg,fcmp,fcvt,fsqrt,frsqrt,multi,nop"
124   (cond [(eq_attr "jal" "!unset") (const_string "call")
125          (eq_attr "got" "load") (const_string "load")]
126         (const_string "unknown")))
127
128 ;; Main data type used by the insn
129 (define_attr "mode" "unknown,none,QI,HI,SI,DI,SF,DF,FPSW"
130   (const_string "unknown"))
131
132 ;; Is this an extended instruction in mips16 mode?
133 (define_attr "extended_mips16" "no,yes"
134   (const_string "no"))
135
136 ;; Length of instruction in bytes.
137 (define_attr "length" ""
138    (cond [;; Direct branch instructions have a range of [-0x40000,0x3fffc].
139           ;; If a branch is outside this range, we have a choice of two
140           ;; sequences.  For PIC, an out-of-range branch like:
141           ;;
142           ;;    bne     r1,r2,target
143           ;;    dslot
144           ;;
145           ;; becomes the equivalent of:
146           ;;
147           ;;    beq     r1,r2,1f
148           ;;    dslot
149           ;;    la      $at,target
150           ;;    jr      $at
151           ;;    nop
152           ;; 1:
153           ;;
154           ;; where the load address can be up to three instructions long
155           ;; (lw, nop, addiu).
156           ;;
157           ;; The non-PIC case is similar except that we use a direct
158           ;; jump instead of an la/jr pair.  Since the target of this
159           ;; jump is an absolute 28-bit bit address (the other bits
160           ;; coming from the address of the delay slot) this form cannot
161           ;; cross a 256MB boundary.  We could provide the option of
162           ;; using la/jr in this case too, but we do not do so at
163           ;; present.
164           ;;
165           ;; Note that this value does not account for the delay slot
166           ;; instruction, whose length is added separately.  If the RTL
167           ;; pattern has no explicit delay slot, mips_adjust_insn_length
168           ;; will add the length of the implicit nop.
169           (eq_attr "type" "branch")
170           (cond [(lt (abs (minus (match_dup 1) (plus (pc) (const_int 4))))
171                      (const_int 131072))
172                  (const_int 4)
173                  (ne (symbol_ref "flag_pic && ! TARGET_EMBEDDED_PIC")
174                      (const_int 0))
175                  (const_int 24)
176                  ] (const_int 12))
177
178           (eq_attr "got" "load")
179           (const_int 4)
180           (eq_attr "got" "xgot_high")
181           (const_int 8)
182
183           (eq_attr "type" "const")
184           (symbol_ref "mips_const_insns (operands[1]) * 4")
185           (eq_attr "type" "load")
186           (symbol_ref "mips_fetch_insns (operands[1]) * 4")
187           (eq_attr "type" "store")
188           (symbol_ref "mips_fetch_insns (operands[0]) * 4")
189
190           ;; In the worst case, a call macro will take 8 instructions:
191           ;;
192           ;;     lui $25,%call_hi(FOO)
193           ;;     addu $25,$25,$28
194           ;;     lw $25,%call_lo(FOO)($25)
195           ;;     nop
196           ;;     jalr $25
197           ;;     nop
198           ;;     lw $gp,X($sp)
199           ;;     nop
200           (eq_attr "jal_macro" "yes")
201           (const_int 32)
202
203           (and (eq_attr "extended_mips16" "yes")
204                (ne (symbol_ref "TARGET_MIPS16") (const_int 0)))
205           (const_int 8)
206
207           (eq_attr "type" "idiv")
208           (symbol_ref "mips_idiv_insns () * 4")
209           ] (const_int 4)))
210
211 ;; Attribute describing the processor.  This attribute must match exactly
212 ;; with the processor_type enumeration in mips.h.
213 (define_attr "cpu"
214   "default,4kc,5kc,20kc,m4k,r3000,r3900,r6000,r4000,r4100,r4111,r4120,r4300,r4600,r4650,r5000,r5400,r5500,r7000,r8000,r9000,sb1,sr71000"
215   (const (symbol_ref "mips_tune")))
216
217 ;; The type of hardware hazard associated with this instruction.
218 ;; DELAY means that the next instruction cannot read the result
219 ;; of this one.  HILO means that the next two instructions cannot
220 ;; write to HI or LO.
221 (define_attr "hazard" "none,delay,hilo"
222   (cond [(and (eq_attr "type" "load")
223               (ne (symbol_ref "ISA_HAS_LOAD_DELAY") (const_int 0)))
224          (const_string "delay")
225
226          (and (eq_attr "type" "xfer")
227               (ne (symbol_ref "ISA_HAS_XFER_DELAY") (const_int 0)))
228          (const_string "delay")
229
230          (and (eq_attr "type" "fcmp")
231               (ne (symbol_ref "ISA_HAS_FCMP_DELAY") (const_int 0)))
232          (const_string "delay")
233
234          ;; The r4000 multiplication patterns include an mflo instruction.
235          (and (eq_attr "type" "imul")
236               (ne (symbol_ref "TARGET_FIX_R4000") (const_int 0)))
237          (const_string "hilo")
238
239          (and (eq_attr "type" "hilo")
240               (and (eq (symbol_ref "ISA_HAS_HILO_INTERLOCKS") (const_int 0))
241                    (match_operand 1 "hilo_operand" "")))
242          (const_string "hilo")]
243         (const_string "none")))
244
245 ;; Is it a single instruction?
246 (define_attr "single_insn" "no,yes"
247   (symbol_ref "get_attr_length (insn) == (TARGET_MIPS16 ? 2 : 4)"))
248
249 ;; Can the instruction be put into a delay slot?
250 (define_attr "can_delay" "no,yes"
251   (if_then_else (and (eq_attr "type" "!branch,call,jump")
252                      (and (eq_attr "hazard" "none")
253                           (eq_attr "single_insn" "yes")))
254                 (const_string "yes")
255                 (const_string "no")))
256
257 ;; Attribute defining whether or not we can use the branch-likely instructions
258 (define_attr "branch_likely" "no,yes"
259   (const
260    (if_then_else (ne (symbol_ref "GENERATE_BRANCHLIKELY") (const_int 0))
261                  (const_string "yes")
262                  (const_string "no"))))
263
264 ;; Describe a user's asm statement.
265 (define_asm_attributes
266   [(set_attr "type" "multi")])
267 \f
268 ;; .........................
269 ;;
270 ;;      Branch, call and jump delay slots
271 ;;
272 ;; .........................
273
274 (define_delay (and (eq_attr "type" "branch")
275                    (eq (symbol_ref "TARGET_MIPS16") (const_int 0)))
276   [(eq_attr "can_delay" "yes")
277    (nil)
278    (and (eq_attr "branch_likely" "yes")
279         (eq_attr "can_delay" "yes"))])
280
281 (define_delay (eq_attr "type" "jump")
282   [(eq_attr "can_delay" "yes")
283    (nil)
284    (nil)])
285
286 (define_delay (and (eq_attr "type" "call")
287                    (eq_attr "jal_macro" "no"))
288   [(eq_attr "can_delay" "yes")
289    (nil)
290    (nil)])
291 \f
292 ;; .........................
293 ;;
294 ;;      Functional units
295 ;;
296 ;; .........................
297
298 ; (define_function_unit NAME MULTIPLICITY SIMULTANEITY
299 ;                       TEST READY-DELAY ISSUE-DELAY [CONFLICT-LIST])
300
301 ;; Make the default case (PROCESSOR_DEFAULT) handle the worst case
302
303 (define_function_unit "memory" 1 0
304   (and (eq_attr "type" "load")
305        (eq_attr "cpu" "!r3000,r3900,r4600,r4650,r4100,r4120,r4300,r5000"))
306   3 0)
307
308 (define_function_unit "memory" 1 0
309   (and (eq_attr "type" "load")
310        (eq_attr "cpu" "r3000,r3900,r4600,r4650,r4100,r4120,r4300,r5000"))
311   2 0)
312
313 (define_function_unit "memory"   1 0 (eq_attr "type" "store") 1 0)
314
315 (define_function_unit "memory"   1 0 (eq_attr "type" "xfer") 2 0)
316
317 (define_function_unit "imuldiv"  1 0
318   (eq_attr "type" "hilo")
319   1 3)
320
321 (define_function_unit "imuldiv"  1 0
322   (and (eq_attr "type" "imul,imadd")
323        (eq_attr "cpu" "!r3000,r3900,r4000,r4600,r4650,r4100,r4120,r4300,r5000"))
324   17 17)
325
326 ;; On them mips16, we want to stronly discourage a mult from appearing
327 ;; after an mflo, since that requires explicit nop instructions.  We
328 ;; do this by pretending that mflo ties up the function unit for long
329 ;; enough that the scheduler will ignore load stalls and the like when
330 ;; selecting instructions to between the two instructions.
331
332 (define_function_unit "imuldiv" 1 0
333   (and (eq_attr "type" "hilo") (ne (symbol_ref "TARGET_MIPS16") (const_int 0)))
334   1 5)
335
336 (define_function_unit "imuldiv"  1 0
337   (and (eq_attr "type" "imul,imadd") (eq_attr "cpu" "r3000,r3900"))
338   12 12)
339
340 (define_function_unit "imuldiv"  1 0
341   (and (eq_attr "type" "imul,imadd") (eq_attr "cpu" "r4000,r4600"))
342   10 10)
343
344 (define_function_unit "imuldiv"  1 0
345   (and (eq_attr "type" "imul,imadd") (eq_attr "cpu" "r4650"))
346   4 4)
347
348 (define_function_unit "imuldiv"  1 0
349   (and (eq_attr "type" "imul,imadd")
350        (and (eq_attr "mode" "SI") (eq_attr "cpu" "r4100,r4120")))
351   1 1)
352
353 (define_function_unit "imuldiv"  1 0
354   (and (eq_attr "type" "imul,imadd")
355        (and (eq_attr "mode" "DI") (eq_attr "cpu" "r4100,r4120")))
356   4 4)
357
358 (define_function_unit "imuldiv"  1 0
359   (and (eq_attr "type" "imul,imadd")
360        (and (eq_attr "mode" "SI") (eq_attr "cpu" "r4300,r5000")))
361   5 5)
362
363 (define_function_unit "imuldiv"  1 0
364   (and (eq_attr "type" "imul,imadd")
365        (and (eq_attr "mode" "DI") (eq_attr "cpu" "r4300")))
366   8 8)
367
368 (define_function_unit "imuldiv"  1 0
369   (and (eq_attr "type" "imul,imadd")
370        (and (eq_attr "mode" "DI") (eq_attr "cpu" "r5000")))
371   9 9)
372
373 (define_function_unit "imuldiv"  1 0
374   (and (eq_attr "type" "idiv")
375        (eq_attr "cpu" "!r3000,r3900,r4000,r4600,r4650,r4100,r4120,r4300,r5000"))
376   38 38)
377
378 (define_function_unit "imuldiv"  1 0
379   (and (eq_attr "type" "idiv") (eq_attr "cpu" "r3000,r3900"))
380   35 35)
381
382 (define_function_unit "imuldiv"  1 0
383   (and (eq_attr "type" "idiv") (eq_attr "cpu" "r4600"))
384   42 42)
385
386 (define_function_unit "imuldiv"  1 0
387   (and (eq_attr "type" "idiv") (eq_attr "cpu" "r4650"))
388   36 36)
389
390 (define_function_unit "imuldiv"  1 0
391   (and (eq_attr "type" "idiv") (eq_attr "cpu" "r4000"))
392   69 69)
393
394 (define_function_unit "imuldiv" 1 0
395   (and (eq_attr "type" "idiv")
396        (and (eq_attr "mode" "SI") (eq_attr "cpu" "r4100,r4120")))
397   35 35)
398
399 (define_function_unit "imuldiv" 1 0
400   (and (eq_attr "type" "idiv")
401        (and (eq_attr "mode" "DI") (eq_attr "cpu" "r4100,r4120")))
402   67 67)
403
404 (define_function_unit "imuldiv" 1 0
405   (and (eq_attr "type" "idiv")
406        (and (eq_attr "mode" "SI") (eq_attr "cpu" "r4300")))
407   37 37)
408
409 (define_function_unit "imuldiv" 1 0
410   (and (eq_attr "type" "idiv")
411        (and (eq_attr "mode" "DI") (eq_attr "cpu" "r4300")))
412   69 69)
413
414 (define_function_unit "imuldiv" 1 0
415   (and (eq_attr "type" "idiv")
416        (and (eq_attr "mode" "SI") (eq_attr "cpu" "r5000")))
417   36 36)
418
419 (define_function_unit "imuldiv" 1 0
420   (and (eq_attr "type" "idiv")
421        (and (eq_attr "mode" "DI") (eq_attr "cpu" "r5000")))
422   68 68)
423
424 ;; The R4300 does *NOT* have a separate Floating Point Unit, instead
425 ;; the FP hardware is part of the normal ALU circuitry.  This means FP
426 ;; instructions affect the pipe-line, and no functional unit
427 ;; parallelism can occur on R4300 processors.  To force GCC into coding
428 ;; for only a single functional unit, we force the R4300 FP
429 ;; instructions to be processed in the "imuldiv" unit.
430
431 (define_function_unit "adder" 1 1
432   (and (eq_attr "type" "fcmp") (eq_attr "cpu" "!r3000,r3900,r6000,r4300,r5000"))
433   3 0)
434
435 (define_function_unit "adder" 1 1
436   (and (eq_attr "type" "fcmp") (eq_attr "cpu" "r3000,r3900,r6000"))
437   2 0)
438
439 (define_function_unit "adder" 1 1
440   (and (eq_attr "type" "fcmp") (eq_attr "cpu" "r5000"))
441   1 0)
442
443 (define_function_unit "adder" 1 1
444   (and (eq_attr "type" "fadd") (eq_attr "cpu" "!r3000,r3900,r6000,r4300"))
445   4 0)
446
447 (define_function_unit "adder" 1 1
448   (and (eq_attr "type" "fadd") (eq_attr "cpu" "r3000,r3900"))
449   2 0)
450
451 (define_function_unit "adder" 1 1
452   (and (eq_attr "type" "fadd") (eq_attr "cpu" "r6000"))
453   3 0)
454
455 (define_function_unit "adder" 1 1
456   (and (eq_attr "type" "fabs,fneg")
457        (eq_attr "cpu" "!r3000,r3900,r4600,r4650,r4300,r5000"))
458   2 0)
459
460 (define_function_unit "adder" 1 1
461   (and (eq_attr "type" "fabs,fneg") (eq_attr "cpu" "r3000,r3900,r4600,r4650,r5000"))
462   1 0)
463
464 (define_function_unit "mult" 1 1
465   (and (eq_attr "type" "fmul")
466        (and (eq_attr "mode" "SF")
467             (eq_attr "cpu" "!r3000,r3900,r6000,r4600,r4650,r4300,r5000")))
468   7 0)
469
470 (define_function_unit "mult" 1 1
471   (and (eq_attr "type" "fmul")
472        (and (eq_attr "mode" "SF") (eq_attr "cpu" "r3000,r3900,r5000")))
473   4 0)
474
475 (define_function_unit "mult" 1 1
476   (and (eq_attr "type" "fmul")
477        (and (eq_attr "mode" "SF") (eq_attr "cpu" "r6000")))
478   5 0)
479
480 (define_function_unit "mult" 1 1
481   (and (eq_attr "type" "fmul")
482        (and (eq_attr "mode" "SF") (eq_attr "cpu" "r4600,r4650")))
483   8 0)
484
485 (define_function_unit "mult" 1 1
486   (and (eq_attr "type" "fmul")
487        (and (eq_attr "mode" "DF") (eq_attr "cpu" "!r3000,r3900,r6000,r4300,r5000")))
488   8 0)
489
490 (define_function_unit "mult" 1 1
491   (and (eq_attr "type" "fmul")
492        (and (eq_attr "mode" "DF") (eq_attr "cpu" "r3000,r3900,r5000")))
493   5 0)
494
495 (define_function_unit "mult" 1 1
496   (and (eq_attr "type" "fmul")
497        (and (eq_attr "mode" "DF") (eq_attr "cpu" "r6000")))
498   6 0)
499
500 (define_function_unit "divide" 1 1
501   (and (eq_attr "type" "fdiv")
502        (and (eq_attr "mode" "SF")
503             (eq_attr "cpu" "!r3000,r3900,r6000,r4600,r4650,r4300,r5000")))
504   23 0)
505
506 (define_function_unit "divide" 1 1
507   (and (eq_attr "type" "fdiv")
508        (and (eq_attr "mode" "SF") (eq_attr "cpu" "r3000,r3900")))
509   12 0)
510
511 (define_function_unit "divide" 1 1
512   (and (eq_attr "type" "fdiv")
513        (and (eq_attr "mode" "SF") (eq_attr "cpu" "r6000")))
514   15 0)
515
516 (define_function_unit "divide" 1 1
517   (and (eq_attr "type" "fdiv")
518        (and (eq_attr "mode" "SF") (eq_attr "cpu" "r4600,r4650")))
519   32 0)
520
521 (define_function_unit "divide" 1 1
522   (and (eq_attr "type" "fdiv")
523        (and (eq_attr "mode" "SF") (eq_attr "cpu" "r5000")))
524   21 0)
525
526 (define_function_unit "divide" 1 1
527   (and (eq_attr "type" "fdiv")
528        (and (eq_attr "mode" "DF")
529             (eq_attr "cpu" "!r3000,r3900,r6000,r4600,r4650,r4300")))
530   36 0)
531
532 (define_function_unit "divide" 1 1
533   (and (eq_attr "type" "fdiv")
534        (and (eq_attr "mode" "DF") (eq_attr "cpu" "r3000,r3900")))
535   19 0)
536
537 (define_function_unit "divide" 1 1
538   (and (eq_attr "type" "fdiv")
539        (and (eq_attr "mode" "DF") (eq_attr "cpu" "r6000")))
540   16 0)
541
542 (define_function_unit "divide" 1 1
543   (and (eq_attr "type" "fdiv")
544        (and (eq_attr "mode" "DF") (eq_attr "cpu" "r4600,r4650")))
545   61 0)
546
547 ;;; ??? Is this number right?
548 (define_function_unit "divide" 1 1
549   (and (eq_attr "type" "fsqrt,frsqrt")
550        (and (eq_attr "mode" "SF") (eq_attr "cpu" "!r4600,r4650,r4300,r5000")))
551   54 0)
552
553 (define_function_unit "divide" 1 1
554   (and (eq_attr "type" "fsqrt,frsqrt")
555        (and (eq_attr "mode" "SF") (eq_attr "cpu" "r4600,r4650")))
556   31 0)
557
558 (define_function_unit "divide" 1 1
559   (and (eq_attr "type" "fsqrt,frsqrt")
560        (and (eq_attr "mode" "SF") (eq_attr "cpu" "r5000")))
561   21 0)
562
563 ;;; ??? Is this number right?
564 (define_function_unit "divide" 1 1
565   (and (eq_attr "type" "fsqrt,frsqrt")
566        (and (eq_attr "mode" "DF") (eq_attr "cpu" "!r4600,r4650,r4300,r5000")))
567   112 0)
568
569 (define_function_unit "divide" 1 1
570   (and (eq_attr "type" "fsqrt,frsqrt")
571        (and (eq_attr "mode" "DF") (eq_attr "cpu" "r4600,r4650")))
572   60 0)
573
574 (define_function_unit "divide" 1 1
575   (and (eq_attr "type" "fsqrt,frsqrt")
576        (and (eq_attr "mode" "DF") (eq_attr "cpu" "r5000")))
577   36 0)
578
579 ;; R4300 FP instruction classes treated as part of the "imuldiv"
580 ;; functional unit:
581
582 (define_function_unit "imuldiv" 1 0
583   (and (eq_attr "type" "fadd") (eq_attr "cpu" "r4300"))
584   3 3)
585
586 (define_function_unit "imuldiv" 1 0
587   (and (eq_attr "type" "fcmp,fabs,fneg") (eq_attr "cpu" "r4300"))
588   1 1)
589
590 (define_function_unit "imuldiv" 1 0
591   (and (eq_attr "type" "fmul") (and (eq_attr "mode" "SF") (eq_attr "cpu" "r4300")))
592   5 5)
593 (define_function_unit "imuldiv" 1 0
594   (and (eq_attr "type" "fmul") (and (eq_attr "mode" "DF") (eq_attr "cpu" "r4300")))
595   8 8)
596
597 (define_function_unit "imuldiv" 1 0
598   (and (and (eq_attr "type" "fdiv") (eq_attr "type" "fsqrt,frsqrt"))
599        (and (eq_attr "mode" "SF") (eq_attr "cpu" "r4300")))
600   29 29)
601 (define_function_unit "imuldiv" 1 0
602   (and (and (eq_attr "type" "fdiv") (eq_attr "type" "fsqrt,frsqrt"))
603        (and (eq_attr "mode" "DF") (eq_attr "cpu" "r4300")))
604   58 58)
605 \f
606 ;; Include scheduling descriptions.
607
608 (include "5400.md")
609 (include "5500.md")
610 (include "7000.md")
611 (include "9000.md")
612 (include "sr71k.md")
613 \f
614 ;;
615 ;;  ....................
616 ;;
617 ;;      CONDITIONAL TRAPS
618 ;;
619 ;;  ....................
620 ;;
621
622 (define_insn "trap"
623   [(trap_if (const_int 1) (const_int 0))]
624   ""
625 {
626   if (ISA_HAS_COND_TRAP)
627     return "teq\t$0,$0";
628   /* The IRIX 6 O32 assembler requires the first break operand.  */
629   else if (TARGET_MIPS16 || !TARGET_GAS)
630     return "break 0";
631   else
632     return "break";
633 })
634
635 (define_expand "conditional_trap"
636   [(trap_if (match_operator 0 "cmp_op"
637                             [(match_dup 2) (match_dup 3)])
638             (match_operand 1 "const_int_operand" ""))]
639   "ISA_HAS_COND_TRAP"
640 {
641   if (operands[1] == const0_rtx)
642     {
643       mips_gen_conditional_trap (operands);
644       DONE;
645     }
646   else
647     FAIL;
648 })
649
650 (define_insn ""
651   [(trap_if (match_operator 0 "trap_cmp_op"
652                             [(match_operand:SI 1 "reg_or_0_operand" "dJ")
653                              (match_operand:SI 2 "arith_operand" "dI")])
654             (const_int 0))]
655   "ISA_HAS_COND_TRAP"
656   "t%C0\t%z1,%z2")
657
658 (define_insn ""
659   [(trap_if (match_operator 0 "trap_cmp_op"
660                             [(match_operand:DI 1 "reg_or_0_operand" "dJ")
661                              (match_operand:DI 2 "arith_operand" "dI")])
662             (const_int 0))]
663   "TARGET_64BIT && ISA_HAS_COND_TRAP"
664   "t%C0\t%z1,%z2")
665 \f
666 ;;
667 ;;  ....................
668 ;;
669 ;;      ADDITION
670 ;;
671 ;;  ....................
672 ;;
673
674 (define_insn "adddf3"
675   [(set (match_operand:DF 0 "register_operand" "=f")
676         (plus:DF (match_operand:DF 1 "register_operand" "f")
677                  (match_operand:DF 2 "register_operand" "f")))]
678   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
679   "add.d\t%0,%1,%2"
680   [(set_attr "type"     "fadd")
681    (set_attr "mode"     "DF")])
682
683 (define_insn "addsf3"
684   [(set (match_operand:SF 0 "register_operand" "=f")
685         (plus:SF (match_operand:SF 1 "register_operand" "f")
686                  (match_operand:SF 2 "register_operand" "f")))]
687   "TARGET_HARD_FLOAT"
688   "add.s\t%0,%1,%2"
689   [(set_attr "type"     "fadd")
690    (set_attr "mode"     "SF")])
691
692 (define_expand "addsi3"
693   [(set (match_operand:SI 0 "register_operand" "")
694         (plus:SI (match_operand:SI 1 "reg_or_0_operand" "")
695                  (match_operand:SI 2 "arith_operand" "")))]
696   ""
697 {
698   /* If a large stack adjustment was forced into a register, we may be
699      asked to generate rtx such as:
700
701         (set (reg:SI sp) (plus:SI (reg:SI sp) (reg:SI pseudo)))
702
703      but no such instruction is available in mips16.  Handle it by
704      using a temporary.  */
705   if (TARGET_MIPS16
706       && REGNO (operands[0]) == STACK_POINTER_REGNUM
707       && ((GET_CODE (operands[1]) == REG
708            && REGNO (operands[1]) != STACK_POINTER_REGNUM)
709           || GET_CODE (operands[2]) != CONST_INT))
710     {
711       rtx tmp = gen_reg_rtx (SImode);
712
713       emit_move_insn (tmp, operands[1]);
714       emit_insn (gen_addsi3 (tmp, tmp, operands[2]));
715       emit_move_insn (operands[0], tmp);
716       DONE;
717     }
718 })
719
720 (define_insn "addsi3_internal"
721   [(set (match_operand:SI 0 "register_operand" "=d,d")
722         (plus:SI (match_operand:SI 1 "reg_or_0_operand" "dJ,dJ")
723                  (match_operand:SI 2 "arith_operand" "d,Q")))]
724   "!TARGET_MIPS16"
725   "@
726     addu\t%0,%z1,%2
727     addiu\t%0,%z1,%2"
728   [(set_attr "type"     "arith")
729    (set_attr "mode"     "SI")])
730
731 ;; For the mips16, we need to recognize stack pointer additions
732 ;; explicitly, since we don't have a constraint for $sp.  These insns
733 ;; will be generated by the save_restore_insns functions.
734
735 (define_insn ""
736   [(set (reg:SI 29)
737         (plus:SI (reg:SI 29)
738                  (match_operand:SI 0 "small_int" "I")))]
739   "TARGET_MIPS16"
740   "addu\t%$,%$,%0"
741   [(set_attr "type"     "arith")
742    (set_attr "mode"     "SI")
743    (set (attr "length") (if_then_else (match_operand:VOID 0 "m16_simm8_8" "")
744                                       (const_int 4)
745                                       (const_int 8)))])
746
747 (define_insn ""
748   [(set (match_operand:SI 0 "register_operand" "=d")
749         (plus:SI (reg:SI 29)
750                  (match_operand:SI 1 "small_int" "I")))]
751   "TARGET_MIPS16"
752   "addu\t%0,%$,%1"
753   [(set_attr "type"     "arith")
754    (set_attr "mode"     "SI")
755    (set (attr "length") (if_then_else (match_operand:VOID 1 "m16_uimm8_4" "")
756                                       (const_int 4)
757                                       (const_int 8)))])
758
759 (define_insn ""
760   [(set (match_operand:SI 0 "register_operand" "=d,d,d")
761         (plus:SI (match_operand:SI 1 "register_operand" "0,d,d")
762                  (match_operand:SI 2 "arith_operand" "Q,O,d")))]
763   "TARGET_MIPS16
764    && (GET_CODE (operands[1]) != REG
765        || REGNO (operands[1]) >= FIRST_PSEUDO_REGISTER
766        || M16_REG_P (REGNO (operands[1]))
767        || REGNO (operands[1]) == ARG_POINTER_REGNUM
768        || REGNO (operands[1]) == FRAME_POINTER_REGNUM
769        || REGNO (operands[1]) == STACK_POINTER_REGNUM)
770    && (GET_CODE (operands[2]) != REG
771        || REGNO (operands[2]) >= FIRST_PSEUDO_REGISTER
772        || M16_REG_P (REGNO (operands[2]))
773        || REGNO (operands[2]) == ARG_POINTER_REGNUM
774        || REGNO (operands[2]) == FRAME_POINTER_REGNUM
775        || REGNO (operands[2]) == STACK_POINTER_REGNUM)"
776 {
777   if (REGNO (operands[0]) == REGNO (operands[1]))
778     return "addu\t%0,%2";
779   else
780     return "addu\t%0,%1,%2";
781 }
782   [(set_attr "type"     "arith")
783    (set_attr "mode"     "SI")
784    (set_attr_alternative "length"
785                 [(if_then_else (match_operand:VOID 2 "m16_simm8_1" "")
786                                (const_int 4)
787                                (const_int 8))
788                  (if_then_else (match_operand:VOID 2 "m16_simm4_1" "")
789                                (const_int 4)
790                                (const_int 8))
791                  (const_int 4)])])
792
793
794 ;; On the mips16, we can sometimes split an add of a constant which is
795 ;; a 4 byte instruction into two adds which are both 2 byte
796 ;; instructions.  There are two cases: one where we are adding a
797 ;; constant plus a register to another register, and one where we are
798 ;; simply adding a constant to a register.
799
800 (define_split
801   [(set (match_operand:SI 0 "register_operand" "")
802         (plus:SI (match_dup 0)
803                  (match_operand:SI 1 "const_int_operand" "")))]
804   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
805    && GET_CODE (operands[0]) == REG
806    && M16_REG_P (REGNO (operands[0]))
807    && GET_CODE (operands[1]) == CONST_INT
808    && ((INTVAL (operands[1]) > 0x7f
809         && INTVAL (operands[1]) <= 0x7f + 0x7f)
810        || (INTVAL (operands[1]) < - 0x80
811            && INTVAL (operands[1]) >= - 0x80 - 0x80))"
812   [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
813    (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))]
814 {
815   HOST_WIDE_INT val = INTVAL (operands[1]);
816
817   if (val >= 0)
818     {
819       operands[1] = GEN_INT (0x7f);
820       operands[2] = GEN_INT (val - 0x7f);
821     }
822   else
823     {
824       operands[1] = GEN_INT (- 0x80);
825       operands[2] = GEN_INT (val + 0x80);
826     }
827 })
828
829 (define_split
830   [(set (match_operand:SI 0 "register_operand" "")
831         (plus:SI (match_operand:SI 1 "register_operand" "")
832                  (match_operand:SI 2 "const_int_operand" "")))]
833   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
834    && GET_CODE (operands[0]) == REG
835    && M16_REG_P (REGNO (operands[0]))
836    && GET_CODE (operands[1]) == REG
837    && M16_REG_P (REGNO (operands[1]))
838    && REGNO (operands[0]) != REGNO (operands[1])
839    && GET_CODE (operands[2]) == CONST_INT
840    && ((INTVAL (operands[2]) > 0x7
841         && INTVAL (operands[2]) <= 0x7 + 0x7f)
842        || (INTVAL (operands[2]) < - 0x8
843            && INTVAL (operands[2]) >= - 0x8 - 0x80))"
844   [(set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))
845    (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 3)))]
846 {
847   HOST_WIDE_INT val = INTVAL (operands[2]);
848
849   if (val >= 0)
850     {
851       operands[2] = GEN_INT (0x7);
852       operands[3] = GEN_INT (val - 0x7);
853     }
854   else
855     {
856       operands[2] = GEN_INT (- 0x8);
857       operands[3] = GEN_INT (val + 0x8);
858     }
859 })
860
861 (define_expand "adddi3"
862   [(parallel [(set (match_operand:DI 0 "register_operand" "")
863                    (plus:DI (match_operand:DI 1 "register_operand" "")
864                             (match_operand:DI 2 "arith_operand" "")))
865               (clobber (match_dup 3))])]
866   "TARGET_64BIT || (!TARGET_DEBUG_G_MODE && !TARGET_MIPS16)"
867 {
868   /* If a large stack adjustment was forced into a register, we may be
869      asked to generate rtx such as:
870
871         (set (reg:DI sp) (plus:DI (reg:DI sp) (reg:DI pseudo)))
872
873      but no such instruction is available in mips16.  Handle it by
874      using a temporary.  */
875   if (TARGET_MIPS16
876       && REGNO (operands[0]) == STACK_POINTER_REGNUM
877       && ((GET_CODE (operands[1]) == REG
878            && REGNO (operands[1]) != STACK_POINTER_REGNUM)
879           || GET_CODE (operands[2]) != CONST_INT))
880     {
881       rtx tmp = gen_reg_rtx (DImode);
882
883       emit_move_insn (tmp, operands[1]);
884       emit_insn (gen_adddi3 (tmp, tmp, operands[2]));
885       emit_move_insn (operands[0], tmp);
886       DONE;
887     }
888
889   if (TARGET_64BIT)
890     {
891       emit_insn (gen_adddi3_internal_3 (operands[0], operands[1],
892                                         operands[2]));
893       DONE;
894     }
895
896   operands[3] = gen_reg_rtx (SImode);
897 })
898
899 (define_insn "adddi3_internal_1"
900   [(set (match_operand:DI 0 "register_operand" "=d,&d")
901         (plus:DI (match_operand:DI 1 "register_operand" "0,d")
902                  (match_operand:DI 2 "register_operand" "d,d")))
903    (clobber (match_operand:SI 3 "register_operand" "=d,d"))]
904   "!TARGET_64BIT && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16"
905 {
906   return (REGNO (operands[0]) == REGNO (operands[1])
907           && REGNO (operands[0]) == REGNO (operands[2]))
908     ? "srl\t%3,%L0,31\;sll\t%M0,%M0,1\;sll\t%L0,%L1,1\;addu\t%M0,%M0,%3"
909     : "addu\t%L0,%L1,%L2\;sltu\t%3,%L0,%L2\;addu\t%M0,%M1,%M2\;addu\t%M0,%M0,%3";
910 }
911   [(set_attr "type"     "darith")
912    (set_attr "mode"     "DI")
913    (set_attr "length"   "16")])
914
915 (define_split
916   [(set (match_operand:DI 0 "register_operand" "")
917         (plus:DI (match_operand:DI 1 "register_operand" "")
918                  (match_operand:DI 2 "register_operand" "")))
919    (clobber (match_operand:SI 3 "register_operand" ""))]
920   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_64BIT
921    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
922    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
923    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
924    && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))
925    && (REGNO (operands[0]) != REGNO (operands[1])
926        || REGNO (operands[0]) != REGNO (operands[2]))"
927
928   [(set (subreg:SI (match_dup 0) 0)
929         (plus:SI (subreg:SI (match_dup 1) 0)
930                  (subreg:SI (match_dup 2) 0)))
931
932    (set (match_dup 3)
933         (ltu:SI (subreg:SI (match_dup 0) 0)
934                 (subreg:SI (match_dup 2) 0)))
935
936    (set (subreg:SI (match_dup 0) 4)
937         (plus:SI (subreg:SI (match_dup 1) 4)
938                  (subreg:SI (match_dup 2) 4)))
939
940    (set (subreg:SI (match_dup 0) 4)
941         (plus:SI (subreg:SI (match_dup 0) 4)
942                  (match_dup 3)))]
943   "")
944
945 (define_split
946   [(set (match_operand:DI 0 "register_operand" "")
947         (plus:DI (match_operand:DI 1 "register_operand" "")
948                  (match_operand:DI 2 "register_operand" "")))
949    (clobber (match_operand:SI 3 "register_operand" ""))]
950   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_64BIT
951    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
952    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
953    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
954    && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))
955    && (REGNO (operands[0]) != REGNO (operands[1])
956        || REGNO (operands[0]) != REGNO (operands[2]))"
957
958   [(set (subreg:SI (match_dup 0) 4)
959         (plus:SI (subreg:SI (match_dup 1) 4)
960                  (subreg:SI (match_dup 2) 4)))
961
962    (set (match_dup 3)
963         (ltu:SI (subreg:SI (match_dup 0) 4)
964                 (subreg:SI (match_dup 2) 4)))
965
966    (set (subreg:SI (match_dup 0) 0)
967         (plus:SI (subreg:SI (match_dup 1) 0)
968                  (subreg:SI (match_dup 2) 0)))
969
970    (set (subreg:SI (match_dup 0) 0)
971         (plus:SI (subreg:SI (match_dup 0) 0)
972                  (match_dup 3)))]
973   "")
974
975 (define_insn "adddi3_internal_2"
976   [(set (match_operand:DI 0 "register_operand" "=d,d,d")
977         (plus:DI (match_operand:DI 1 "register_operand" "%d,d,d")
978                  (match_operand:DI 2 "small_int" "P,J,N")))
979    (clobber (match_operand:SI 3 "register_operand" "=d,d,d"))]
980   "!TARGET_64BIT && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16"
981   "@
982    addu\t%L0,%L1,%2\;sltu\t%3,%L0,%2\;addu\t%M0,%M1,%3
983    move\t%L0,%L1\;move\t%M0,%M1
984    subu\t%L0,%L1,%n2\;sltu\t%3,%L0,%2\;subu\t%M0,%M1,1\;addu\t%M0,%M0,%3"
985   [(set_attr "type"     "darith")
986    (set_attr "mode"     "DI")
987    (set_attr "length"   "12,8,16")])
988
989 (define_split
990   [(set (match_operand:DI 0 "register_operand" "")
991         (plus:DI (match_operand:DI 1 "register_operand" "")
992                  (match_operand:DI 2 "small_int" "")))
993    (clobber (match_operand:SI 3 "register_operand" ""))]
994   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_64BIT
995    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
996    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
997    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
998    && INTVAL (operands[2]) > 0"
999
1000   [(set (subreg:SI (match_dup 0) 0)
1001         (plus:SI (subreg:SI (match_dup 1) 0)
1002                  (match_dup 2)))
1003
1004    (set (match_dup 3)
1005         (ltu:SI (subreg:SI (match_dup 0) 0)
1006                 (match_dup 2)))
1007
1008    (set (subreg:SI (match_dup 0) 4)
1009         (plus:SI (subreg:SI (match_dup 1) 4)
1010                  (match_dup 3)))]
1011   "")
1012
1013 (define_split
1014   [(set (match_operand:DI 0 "register_operand" "")
1015         (plus:DI (match_operand:DI 1 "register_operand" "")
1016                  (match_operand:DI 2 "small_int" "")))
1017    (clobber (match_operand:SI 3 "register_operand" ""))]
1018   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_64BIT
1019    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
1020    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
1021    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
1022    && INTVAL (operands[2]) > 0"
1023
1024   [(set (subreg:SI (match_dup 0) 4)
1025         (plus:SI (subreg:SI (match_dup 1) 4)
1026                  (match_dup 2)))
1027
1028    (set (match_dup 3)
1029         (ltu:SI (subreg:SI (match_dup 0) 4)
1030                 (match_dup 2)))
1031
1032    (set (subreg:SI (match_dup 0) 0)
1033         (plus:SI (subreg:SI (match_dup 1) 0)
1034                  (match_dup 3)))]
1035   "")
1036
1037 (define_insn "adddi3_internal_3"
1038   [(set (match_operand:DI 0 "register_operand" "=d,d")
1039         (plus:DI (match_operand:DI 1 "reg_or_0_operand" "dJ,dJ")
1040                  (match_operand:DI 2 "arith_operand" "d,Q")))]
1041   "TARGET_64BIT && !TARGET_MIPS16"
1042   "@
1043     daddu\t%0,%z1,%2
1044     daddiu\t%0,%z1,%2"
1045   [(set_attr "type"     "darith")
1046    (set_attr "mode"     "DI")])
1047
1048 ;; For the mips16, we need to recognize stack pointer additions
1049 ;; explicitly, since we don't have a constraint for $sp.  These insns
1050 ;; will be generated by the save_restore_insns functions.
1051
1052 (define_insn ""
1053   [(set (reg:DI 29)
1054         (plus:DI (reg:DI 29)
1055                  (match_operand:DI 0 "small_int" "I")))]
1056   "TARGET_MIPS16 && TARGET_64BIT"
1057   "daddu\t%$,%$,%0"
1058   [(set_attr "type"     "arith")
1059    (set_attr "mode"     "DI")
1060    (set (attr "length") (if_then_else (match_operand:VOID 0 "m16_simm8_8" "")
1061                                       (const_int 4)
1062                                       (const_int 8)))])
1063
1064 (define_insn ""
1065   [(set (match_operand:DI 0 "register_operand" "=d")
1066         (plus:DI (reg:DI 29)
1067                  (match_operand:DI 1 "small_int" "I")))]
1068   "TARGET_MIPS16 && TARGET_64BIT"
1069   "daddu\t%0,%$,%1"
1070   [(set_attr "type"     "arith")
1071    (set_attr "mode"     "DI")
1072    (set (attr "length") (if_then_else (match_operand:VOID 0 "m16_uimm5_4" "")
1073                                       (const_int 4)
1074                                       (const_int 8)))])
1075
1076 (define_insn ""
1077   [(set (match_operand:DI 0 "register_operand" "=d,d,d")
1078         (plus:DI (match_operand:DI 1 "register_operand" "0,d,d")
1079                  (match_operand:DI 2 "arith_operand" "Q,O,d")))]
1080   "TARGET_MIPS16 && TARGET_64BIT
1081    && (GET_CODE (operands[1]) != REG
1082        || REGNO (operands[1]) >= FIRST_PSEUDO_REGISTER
1083        || M16_REG_P (REGNO (operands[1]))
1084        || REGNO (operands[1]) == ARG_POINTER_REGNUM
1085        || REGNO (operands[1]) == FRAME_POINTER_REGNUM
1086        || REGNO (operands[1]) == STACK_POINTER_REGNUM)
1087    && (GET_CODE (operands[2]) != REG
1088        || REGNO (operands[2]) >= FIRST_PSEUDO_REGISTER
1089        || M16_REG_P (REGNO (operands[2]))
1090        || REGNO (operands[2]) == ARG_POINTER_REGNUM
1091        || REGNO (operands[2]) == FRAME_POINTER_REGNUM
1092        || REGNO (operands[2]) == STACK_POINTER_REGNUM)"
1093 {
1094   if (REGNO (operands[0]) == REGNO (operands[1]))
1095     return "daddu\t%0,%2";
1096   else
1097     return "daddu\t%0,%1,%2";
1098 }
1099   [(set_attr "type"     "arith")
1100    (set_attr "mode"     "DI")
1101    (set_attr_alternative "length"
1102                 [(if_then_else (match_operand:VOID 2 "m16_simm5_1" "")
1103                                (const_int 4)
1104                                (const_int 8))
1105                  (if_then_else (match_operand:VOID 2 "m16_simm4_1" "")
1106                                (const_int 4)
1107                                (const_int 8))
1108                  (const_int 4)])])
1109
1110
1111 ;; On the mips16, we can sometimes split an add of a constant which is
1112 ;; a 4 byte instruction into two adds which are both 2 byte
1113 ;; instructions.  There are two cases: one where we are adding a
1114 ;; constant plus a register to another register, and one where we are
1115 ;; simply adding a constant to a register.
1116
1117 (define_split
1118   [(set (match_operand:DI 0 "register_operand" "")
1119         (plus:DI (match_dup 0)
1120                  (match_operand:DI 1 "const_int_operand" "")))]
1121   "TARGET_MIPS16 && TARGET_64BIT && reload_completed && !TARGET_DEBUG_D_MODE
1122    && GET_CODE (operands[0]) == REG
1123    && M16_REG_P (REGNO (operands[0]))
1124    && GET_CODE (operands[1]) == CONST_INT
1125    && ((INTVAL (operands[1]) > 0xf
1126         && INTVAL (operands[1]) <= 0xf + 0xf)
1127        || (INTVAL (operands[1]) < - 0x10
1128            && INTVAL (operands[1]) >= - 0x10 - 0x10))"
1129   [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1)))
1130    (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))]
1131 {
1132   HOST_WIDE_INT val = INTVAL (operands[1]);
1133
1134   if (val >= 0)
1135     {
1136       operands[1] = GEN_INT (0xf);
1137       operands[2] = GEN_INT (val - 0xf);
1138     }
1139   else
1140     {
1141       operands[1] = GEN_INT (- 0x10);
1142       operands[2] = GEN_INT (val + 0x10);
1143     }
1144 })
1145
1146 (define_split
1147   [(set (match_operand:DI 0 "register_operand" "")
1148         (plus:DI (match_operand:DI 1 "register_operand" "")
1149                  (match_operand:DI 2 "const_int_operand" "")))]
1150   "TARGET_MIPS16 && TARGET_64BIT && reload_completed && !TARGET_DEBUG_D_MODE
1151    && GET_CODE (operands[0]) == REG
1152    && M16_REG_P (REGNO (operands[0]))
1153    && GET_CODE (operands[1]) == REG
1154    && M16_REG_P (REGNO (operands[1]))
1155    && REGNO (operands[0]) != REGNO (operands[1])
1156    && GET_CODE (operands[2]) == CONST_INT
1157    && ((INTVAL (operands[2]) > 0x7
1158         && INTVAL (operands[2]) <= 0x7 + 0xf)
1159        || (INTVAL (operands[2]) < - 0x8
1160            && INTVAL (operands[2]) >= - 0x8 - 0x10))"
1161   [(set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))
1162    (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 3)))]
1163 {
1164   HOST_WIDE_INT val = INTVAL (operands[2]);
1165
1166   if (val >= 0)
1167     {
1168       operands[2] = GEN_INT (0x7);
1169       operands[3] = GEN_INT (val - 0x7);
1170     }
1171   else
1172     {
1173       operands[2] = GEN_INT (- 0x8);
1174       operands[3] = GEN_INT (val + 0x8);
1175     }
1176 })
1177
1178 (define_insn "addsi3_internal_2"
1179   [(set (match_operand:DI 0 "register_operand" "=d,d")
1180         (sign_extend:DI (plus:SI (match_operand:SI 1 "reg_or_0_operand" "dJ,dJ")
1181                                  (match_operand:SI 2 "arith_operand" "d,Q"))))]
1182   "TARGET_64BIT && !TARGET_MIPS16"
1183   "@
1184     addu\t%0,%z1,%2
1185     addiu\t%0,%z1,%2"
1186   [(set_attr "type"     "arith")
1187    (set_attr "mode"     "SI")])
1188
1189 (define_insn ""
1190   [(set (match_operand:DI 0 "register_operand" "=d,d,d")
1191         (sign_extend:DI (plus:SI (match_operand:SI 1 "register_operand" "0,d,d")
1192                                  (match_operand:SI 2 "arith_operand" "Q,O,d"))))]
1193   "TARGET_MIPS16 && TARGET_64BIT"
1194 {
1195   if (REGNO (operands[0]) == REGNO (operands[1]))
1196     return "addu\t%0,%2";
1197   else
1198     return "addu\t%0,%1,%2";
1199 }
1200   [(set_attr "type"     "arith")
1201    (set_attr "mode"     "SI")
1202    (set_attr_alternative "length"
1203                 [(if_then_else (match_operand:VOID 2 "m16_simm8_1" "")
1204                                (const_int 4)
1205                                (const_int 8))
1206                  (if_then_else (match_operand:VOID 2 "m16_simm4_1" "")
1207                                (const_int 4)
1208                                (const_int 8))
1209                  (const_int 4)])])
1210 \f
1211 ;;
1212 ;;  ....................
1213 ;;
1214 ;;      SUBTRACTION
1215 ;;
1216 ;;  ....................
1217 ;;
1218
1219 (define_insn "subdf3"
1220   [(set (match_operand:DF 0 "register_operand" "=f")
1221         (minus:DF (match_operand:DF 1 "register_operand" "f")
1222                   (match_operand:DF 2 "register_operand" "f")))]
1223   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
1224   "sub.d\t%0,%1,%2"
1225   [(set_attr "type"     "fadd")
1226    (set_attr "mode"     "DF")])
1227
1228 (define_insn "subsf3"
1229   [(set (match_operand:SF 0 "register_operand" "=f")
1230         (minus:SF (match_operand:SF 1 "register_operand" "f")
1231                   (match_operand:SF 2 "register_operand" "f")))]
1232   "TARGET_HARD_FLOAT"
1233   "sub.s\t%0,%1,%2"
1234   [(set_attr "type"     "fadd")
1235    (set_attr "mode"     "SF")])
1236
1237 (define_expand "subsi3"
1238   [(set (match_operand:SI 0 "register_operand" "")
1239         (minus:SI (match_operand:SI 1 "register_operand" "")
1240                   (match_operand:SI 2 "register_operand" "")))]
1241   ""
1242   "")
1243
1244 (define_insn "subsi3_internal"
1245   [(set (match_operand:SI 0 "register_operand" "=d")
1246         (minus:SI (match_operand:SI 1 "register_operand" "d")
1247                   (match_operand:SI 2 "register_operand" "d")))]
1248   ""
1249   "subu\t%0,%z1,%2"
1250   [(set_attr "type"     "arith")
1251    (set_attr "mode"     "SI")])
1252
1253 (define_expand "subdi3"
1254   [(parallel [(set (match_operand:DI 0 "register_operand" "=d")
1255                    (minus:DI (match_operand:DI 1 "register_operand" "d")
1256                              (match_operand:DI 2 "register_operand" "d")))
1257               (clobber (match_dup 3))])]
1258   "TARGET_64BIT || (!TARGET_DEBUG_G_MODE && !TARGET_MIPS16)"
1259 {
1260   if (TARGET_64BIT)
1261     {
1262       emit_insn (gen_subdi3_internal_3 (operands[0], operands[1],
1263                                         operands[2]));
1264       DONE;
1265     }
1266
1267   operands[3] = gen_reg_rtx (SImode);
1268 })
1269
1270 (define_insn "subdi3_internal"
1271   [(set (match_operand:DI 0 "register_operand" "=d")
1272         (minus:DI (match_operand:DI 1 "register_operand" "d")
1273                   (match_operand:DI 2 "register_operand" "d")))
1274    (clobber (match_operand:SI 3 "register_operand" "=d"))]
1275   "!TARGET_64BIT && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16"
1276   "sltu\t%3,%L1,%L2\;subu\t%L0,%L1,%L2\;subu\t%M0,%M1,%M2\;subu\t%M0,%M0,%3"
1277   [(set_attr "type"     "darith")
1278    (set_attr "mode"     "DI")
1279    (set_attr "length"   "16")])
1280
1281 (define_split
1282   [(set (match_operand:DI 0 "register_operand" "")
1283         (minus:DI (match_operand:DI 1 "register_operand" "")
1284                   (match_operand:DI 2 "register_operand" "")))
1285    (clobber (match_operand:SI 3 "register_operand" ""))]
1286   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_64BIT
1287    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
1288    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
1289    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
1290    && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))"
1291
1292   [(set (match_dup 3)
1293         (ltu:SI (subreg:SI (match_dup 1) 0)
1294                 (subreg:SI (match_dup 2) 0)))
1295
1296    (set (subreg:SI (match_dup 0) 0)
1297         (minus:SI (subreg:SI (match_dup 1) 0)
1298                   (subreg:SI (match_dup 2) 0)))
1299
1300    (set (subreg:SI (match_dup 0) 4)
1301         (minus:SI (subreg:SI (match_dup 1) 4)
1302                   (subreg:SI (match_dup 2) 4)))
1303
1304    (set (subreg:SI (match_dup 0) 4)
1305         (minus:SI (subreg:SI (match_dup 0) 4)
1306                   (match_dup 3)))]
1307   "")
1308
1309 (define_split
1310   [(set (match_operand:DI 0 "register_operand" "")
1311         (minus:DI (match_operand:DI 1 "register_operand" "")
1312                   (match_operand:DI 2 "register_operand" "")))
1313    (clobber (match_operand:SI 3 "register_operand" ""))]
1314   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_64BIT
1315    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
1316    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
1317    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
1318    && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))"
1319
1320   [(set (match_dup 3)
1321         (ltu:SI (subreg:SI (match_dup 1) 4)
1322                 (subreg:SI (match_dup 2) 4)))
1323
1324    (set (subreg:SI (match_dup 0) 4)
1325         (minus:SI (subreg:SI (match_dup 1) 4)
1326                   (subreg:SI (match_dup 2) 4)))
1327
1328    (set (subreg:SI (match_dup 0) 0)
1329         (minus:SI (subreg:SI (match_dup 1) 0)
1330                   (subreg:SI (match_dup 2) 0)))
1331
1332    (set (subreg:SI (match_dup 0) 0)
1333         (minus:SI (subreg:SI (match_dup 0) 0)
1334                   (match_dup 3)))]
1335   "")
1336
1337 (define_insn "subdi3_internal_3"
1338   [(set (match_operand:DI 0 "register_operand" "=d")
1339         (minus:DI (match_operand:DI 1 "register_operand" "d")
1340                   (match_operand:DI 2 "register_operand" "d")))]
1341   "TARGET_64BIT"
1342   "dsubu\t%0,%1,%2"
1343   [(set_attr "type"     "darith")
1344    (set_attr "mode"     "DI")])
1345
1346 (define_insn "subsi3_internal_2"
1347   [(set (match_operand:DI 0 "register_operand" "=d")
1348         (sign_extend:DI
1349             (minus:SI (match_operand:SI 1 "register_operand" "d")
1350                       (match_operand:SI 2 "register_operand" "d"))))]
1351   "TARGET_64BIT"
1352   "subu\t%0,%1,%2"
1353   [(set_attr "type"     "arith")
1354    (set_attr "mode"     "DI")])
1355 \f
1356 ;;
1357 ;;  ....................
1358 ;;
1359 ;;      MULTIPLICATION
1360 ;;
1361 ;;  ....................
1362 ;;
1363
1364 (define_expand "muldf3"
1365   [(set (match_operand:DF 0 "register_operand" "=f")
1366         (mult:DF (match_operand:DF 1 "register_operand" "f")
1367                  (match_operand:DF 2 "register_operand" "f")))]
1368   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
1369   "")
1370
1371 (define_insn "muldf3_internal"
1372   [(set (match_operand:DF 0 "register_operand" "=f")
1373         (mult:DF (match_operand:DF 1 "register_operand" "f")
1374                  (match_operand:DF 2 "register_operand" "f")))]
1375   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_4300_MUL_FIX"
1376   "mul.d\t%0,%1,%2"
1377   [(set_attr "type"     "fmul")
1378    (set_attr "mode"     "DF")])
1379
1380 ;; Early VR4300 silicon has a CPU bug where multiplies with certain
1381 ;; operands may corrupt immediately following multiplies. This is a
1382 ;; simple fix to insert NOPs.
1383
1384 (define_insn "muldf3_r4300"
1385   [(set (match_operand:DF 0 "register_operand" "=f")
1386         (mult:DF (match_operand:DF 1 "register_operand" "f")
1387                  (match_operand:DF 2 "register_operand" "f")))]
1388   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_4300_MUL_FIX"
1389   "mul.d\t%0,%1,%2\;nop"
1390   [(set_attr "type"     "fmul")
1391    (set_attr "mode"     "DF")
1392    (set_attr "length"   "8")])
1393
1394 (define_expand "mulsf3"
1395   [(set (match_operand:SF 0 "register_operand" "=f")
1396         (mult:SF (match_operand:SF 1 "register_operand" "f")
1397                  (match_operand:SF 2 "register_operand" "f")))]
1398   "TARGET_HARD_FLOAT"
1399   "")
1400
1401 (define_insn "mulsf3_internal"
1402   [(set (match_operand:SF 0 "register_operand" "=f")
1403         (mult:SF (match_operand:SF 1 "register_operand" "f")
1404                  (match_operand:SF 2 "register_operand" "f")))]
1405   "TARGET_HARD_FLOAT && !TARGET_4300_MUL_FIX"
1406   "mul.s\t%0,%1,%2"
1407   [(set_attr "type"     "fmul")
1408    (set_attr "mode"     "SF")])
1409
1410 ;; See muldf3_r4300.
1411
1412 (define_insn "mulsf3_r4300"
1413   [(set (match_operand:SF 0 "register_operand" "=f")
1414         (mult:SF (match_operand:SF 1 "register_operand" "f")
1415                  (match_operand:SF 2 "register_operand" "f")))]
1416   "TARGET_HARD_FLOAT && TARGET_4300_MUL_FIX"
1417   "mul.s\t%0,%1,%2\;nop"
1418   [(set_attr "type"     "fmul")
1419    (set_attr "mode"     "SF")
1420    (set_attr "length"   "8")])
1421
1422
1423 ;; The original R4000 has a cpu bug.  If a double-word or a variable
1424 ;; shift executes while an integer multiplication is in progress, the
1425 ;; shift may give an incorrect result.  Avoid this by keeping the mflo
1426 ;; with the mult on the R4000.
1427 ;;
1428 ;; From "MIPS R4000PC/SC Errata, Processor Revision 2.2 and 3.0"
1429 ;; (also valid for MIPS R4000MC processors):
1430 ;;
1431 ;; "16. R4000PC, R4000SC: Please refer to errata 28 for an update to
1432 ;;      this errata description.
1433 ;;      The following code sequence causes the R4000 to incorrectly
1434 ;;      execute the Double Shift Right Arithmetic 32 (dsra32)
1435 ;;      instruction.  If the dsra32 instruction is executed during an
1436 ;;      integer multiply, the dsra32 will only shift by the amount in
1437 ;;      specified in the instruction rather than the amount plus 32
1438 ;;      bits.
1439 ;;      instruction 1:          mult    rs,rt           integer multiply
1440 ;;      instruction 2-12:       dsra32  rd,rt,rs        doubleword shift
1441 ;;                                                      right arithmetic + 32
1442 ;;      Workaround: A dsra32 instruction placed after an integer
1443 ;;      multiply should not be one of the 11 instructions after the
1444 ;;      multiply instruction."
1445 ;;
1446 ;; and:
1447 ;;
1448 ;; "28. R4000PC, R4000SC: The text from errata 16 should be replaced by
1449 ;;      the following description.
1450 ;;      All extended shifts (shift by n+32) and variable shifts (32 and
1451 ;;      64-bit versions) may produce incorrect results under the
1452 ;;      following conditions:
1453 ;;      1) An integer multiply is currently executing
1454 ;;      2) These types of shift instructions are executed immediately
1455 ;;         following an integer divide instruction.
1456 ;;      Workaround:
1457 ;;      1) Make sure no integer multiply is running wihen these
1458 ;;         instruction are executed.  If this cannot be predicted at
1459 ;;         compile time, then insert a "mfhi" to R0 instruction
1460 ;;         immediately after the integer multiply instruction.  This
1461 ;;         will cause the integer multiply to complete before the shift
1462 ;;         is executed.
1463 ;;      2) Separate integer divide and these two classes of shift
1464 ;;         instructions by another instruction or a noop."
1465 ;;
1466 ;; These processors have PRId values of 0x00004220 and 0x00004300,
1467 ;; respectively.
1468
1469 (define_expand "mulsi3"
1470   [(set (match_operand:SI 0 "register_operand" "")
1471         (mult:SI (match_operand:SI 1 "register_operand" "")
1472                  (match_operand:SI 2 "register_operand" "")))]
1473   ""
1474 {
1475   if (GENERATE_MULT3_SI || TARGET_MAD)
1476     emit_insn (gen_mulsi3_mult3 (operands[0], operands[1], operands[2]));
1477   else if (!TARGET_FIX_R4000)
1478     emit_insn (gen_mulsi3_internal (operands[0], operands[1], operands[2]));
1479   else
1480     emit_insn (gen_mulsi3_r4000 (operands[0], operands[1], operands[2]));
1481   DONE;
1482 })
1483
1484 (define_insn "mulsi3_mult3"
1485   [(set (match_operand:SI 0 "register_operand" "=d,l")
1486         (mult:SI (match_operand:SI 1 "register_operand" "d,d")
1487                  (match_operand:SI 2 "register_operand" "d,d")))
1488    (clobber (match_scratch:SI 3 "=h,h"))
1489    (clobber (match_scratch:SI 4 "=l,X"))]
1490   "GENERATE_MULT3_SI
1491    || TARGET_MAD"
1492 {
1493   if (which_alternative == 1)
1494     return "mult\t%1,%2";
1495   if (TARGET_MAD
1496       || TARGET_MIPS5400
1497       || TARGET_MIPS5500
1498       || TARGET_MIPS7000
1499       || TARGET_MIPS9000
1500       || ISA_MIPS32
1501       || ISA_MIPS32R2
1502       || ISA_MIPS64)
1503     return "mul\t%0,%1,%2";
1504   return "mult\t%0,%1,%2";
1505 }
1506   [(set_attr "type"     "imul")
1507    (set_attr "mode"     "SI")])
1508
1509 ;; If a register gets allocated to LO, and we spill to memory, the reload
1510 ;; will include a move from LO to a GPR.  Merge it into the multiplication
1511 ;; if it can set the GPR directly.
1512 ;;
1513 ;; Operand 0: LO
1514 ;; Operand 1: GPR (1st multiplication operand)
1515 ;; Operand 2: GPR (2nd multiplication operand)
1516 ;; Operand 3: HI
1517 ;; Operand 4: GPR (destination)
1518 (define_peephole2
1519   [(parallel
1520        [(set (match_operand:SI 0 "register_operand" "")
1521              (mult:SI (match_operand:SI 1 "register_operand" "")
1522                       (match_operand:SI 2 "register_operand" "")))
1523         (clobber (match_operand:SI 3 "register_operand" ""))
1524         (clobber (scratch:SI))])
1525    (set (match_operand:SI 4 "register_operand" "")
1526         (match_dup 0))]
1527   "GENERATE_MULT3_SI
1528    && true_regnum (operands[0]) == LO_REGNUM
1529    && GP_REG_P (true_regnum (operands[4]))
1530    && peep2_reg_dead_p (2, operands[0])"
1531   [(parallel
1532        [(set (match_dup 4)
1533              (mult:SI (match_dup 1)
1534                       (match_dup 2)))
1535         (clobber (match_dup 3))
1536         (clobber (match_dup 0))])])
1537
1538 (define_insn "mulsi3_internal"
1539   [(set (match_operand:SI 0 "register_operand" "=l")
1540         (mult:SI (match_operand:SI 1 "register_operand" "d")
1541                  (match_operand:SI 2 "register_operand" "d")))
1542    (clobber (match_scratch:SI 3 "=h"))]
1543   "!TARGET_FIX_R4000"
1544   "mult\t%1,%2"
1545   [(set_attr "type"     "imul")
1546    (set_attr "mode"     "SI")])
1547
1548 (define_insn "mulsi3_r4000"
1549   [(set (match_operand:SI 0 "register_operand" "=d")
1550         (mult:SI (match_operand:SI 1 "register_operand" "d")
1551                  (match_operand:SI 2 "register_operand" "d")))
1552    (clobber (match_scratch:SI 3 "=h"))
1553    (clobber (match_scratch:SI 4 "=l"))]
1554   "TARGET_FIX_R4000"
1555   "mult\t%1,%2\;mflo\t%0"
1556   [(set_attr "type"     "imul")
1557    (set_attr "mode"     "SI")
1558    (set_attr "length"   "8")])
1559
1560 ;; Multiply-accumulate patterns
1561
1562 ;; For processors that can copy the output to a general register:
1563 ;;
1564 ;; The all-d alternative is needed because the combiner will find this
1565 ;; pattern and then register alloc/reload will move registers around to
1566 ;; make them fit, and we don't want to trigger unnecessary loads to LO.
1567 ;;
1568 ;; The last alternative should be made slightly less desirable, but adding
1569 ;; "?" to the constraint is too strong, and causes values to be loaded into
1570 ;; LO even when that's more costly.  For now, using "*d" mostly does the
1571 ;; trick.
1572 (define_insn "*mul_acc_si"
1573   [(set (match_operand:SI 0 "register_operand" "=l,*d,*d")
1574         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "d,d,d")
1575                           (match_operand:SI 2 "register_operand" "d,d,d"))
1576                  (match_operand:SI 3 "register_operand" "0,l,*d")))
1577    (clobber (match_scratch:SI 4 "=h,h,h"))
1578    (clobber (match_scratch:SI 5 "=X,3,l"))
1579    (clobber (match_scratch:SI 6 "=X,X,&d"))]
1580   "(TARGET_MIPS3900
1581    || ISA_HAS_MADD_MSUB)
1582    && !TARGET_MIPS16"
1583 {
1584   static const char *const madd[] = { "madd\t%1,%2", "madd\t%0,%1,%2" };
1585   if (which_alternative == 2)
1586     return "#";
1587   if (ISA_HAS_MADD_MSUB && which_alternative != 0)
1588     return "#";
1589   return madd[which_alternative];
1590 }
1591   [(set_attr "type"     "imadd,imadd,multi")
1592    (set_attr "mode"     "SI")
1593    (set_attr "length"   "4,4,8")])
1594
1595 ;; Split the above insn if we failed to get LO allocated.
1596 (define_split
1597   [(set (match_operand:SI 0 "register_operand" "")
1598         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "")
1599                           (match_operand:SI 2 "register_operand" ""))
1600                  (match_operand:SI 3 "register_operand" "")))
1601    (clobber (match_scratch:SI 4 ""))
1602    (clobber (match_scratch:SI 5 ""))
1603    (clobber (match_scratch:SI 6 ""))]
1604   "reload_completed && !TARGET_DEBUG_D_MODE
1605    && GP_REG_P (true_regnum (operands[0]))
1606    && GP_REG_P (true_regnum (operands[3]))"
1607   [(parallel [(set (match_dup 6)
1608                    (mult:SI (match_dup 1) (match_dup 2)))
1609               (clobber (match_dup 4))
1610               (clobber (match_dup 5))])
1611    (set (match_dup 0) (plus:SI (match_dup 6) (match_dup 3)))]
1612   "")
1613
1614 ;; Splitter to copy result of MADD to a general register
1615 (define_split
1616   [(set (match_operand:SI                   0 "register_operand" "")
1617         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "")
1618                           (match_operand:SI 2 "register_operand" ""))
1619                  (match_operand:SI          3 "register_operand" "")))
1620    (clobber (match_scratch:SI               4 ""))
1621    (clobber (match_scratch:SI               5 ""))
1622    (clobber (match_scratch:SI               6 ""))]
1623   "reload_completed && !TARGET_DEBUG_D_MODE
1624    && GP_REG_P (true_regnum (operands[0]))
1625    && true_regnum (operands[3]) == LO_REGNUM"
1626   [(parallel [(set (match_dup 3)
1627                    (plus:SI (mult:SI (match_dup 1) (match_dup 2))
1628                             (match_dup 3)))
1629               (clobber (match_dup 4))
1630               (clobber (match_dup 5))
1631               (clobber (match_dup 6))])
1632    (set (match_dup 0) (match_dup 3))]
1633   "")
1634
1635 (define_insn "*macc"
1636   [(set (match_operand:SI 0 "register_operand" "=l,d")
1637         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "d,d")
1638                           (match_operand:SI 2 "register_operand" "d,d"))
1639                  (match_operand:SI 3 "register_operand" "0,l")))
1640    (clobber (match_scratch:SI 4 "=h,h"))
1641    (clobber (match_scratch:SI 5 "=X,3"))]
1642   "ISA_HAS_MACC"
1643 {
1644   if (which_alternative == 1)
1645     return "macc\t%0,%1,%2";
1646   else if (TARGET_MIPS5500)
1647     return "madd\t%1,%2";
1648   else
1649     return "macc\t%.,%1,%2";
1650 }
1651   [(set_attr "type" "imadd")
1652    (set_attr "mode" "SI")])
1653
1654 ;; Pattern generated by define_peephole2 below
1655 (define_insn "*macc2"
1656   [(set (match_operand:SI 0 "register_operand" "=l")
1657         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "d")
1658                           (match_operand:SI 2 "register_operand" "d"))
1659                  (match_dup 0)))
1660    (set (match_operand:SI 3 "register_operand" "=d")
1661         (plus:SI (mult:SI (match_dup 1)
1662                           (match_dup 2))
1663                  (match_dup 0)))
1664    (clobber (match_scratch:SI 4 "=h"))]
1665   "ISA_HAS_MACC && reload_completed"
1666   "macc\t%3,%1,%2"
1667   [(set_attr "type"     "imadd")
1668    (set_attr "mode"     "SI")])
1669
1670 ;; Convert macc $0,<r1>,<r2> & mflo <r3> into macc <r3>,<r1>,<r2>
1671 ;;
1672 ;; Operand 0: LO
1673 ;; Operand 1: GPR (1st multiplication operand)
1674 ;; Operand 2: GPR (2nd multiplication operand)
1675 ;; Operand 3: HI
1676 ;; Operand 4: GPR (destination)
1677 (define_peephole2
1678   [(parallel
1679        [(set (match_operand:SI 0 "register_operand" "")
1680              (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "")
1681                                (match_operand:SI 2 "register_operand" ""))
1682                       (match_dup 0)))
1683         (clobber (match_operand:SI 3 "register_operand" ""))
1684         (clobber (scratch:SI))])
1685    (set (match_operand:SI 4 "register_operand" "")
1686         (match_dup 0))]
1687   "ISA_HAS_MACC
1688    && true_regnum (operands[0]) == LO_REGNUM
1689    && GP_REG_P (true_regnum (operands[4]))"
1690   [(parallel [(set (match_dup 0)
1691                    (plus:SI (mult:SI (match_dup 1)
1692                                      (match_dup 2))
1693                             (match_dup 0)))
1694               (set (match_dup 4)
1695                    (plus:SI (mult:SI (match_dup 1)
1696                                      (match_dup 2))
1697                             (match_dup 0)))
1698               (clobber (match_dup 3))])]
1699   "")
1700
1701 ;; When we have a three-address multiplication instruction, it should
1702 ;; be faster to do a separate multiply and add, rather than moving
1703 ;; something into LO in order to use a macc instruction.
1704 ;;
1705 ;; This peephole needs a scratch register to cater for the case when one
1706 ;; of the multiplication operands is the same as the destination.
1707 ;;
1708 ;; Operand 0: GPR (scratch)
1709 ;; Operand 1: LO
1710 ;; Operand 2: GPR (addend)
1711 ;; Operand 3: GPR (destination)
1712 ;; Operand 4: GPR (1st multiplication operand)
1713 ;; Operand 5: GPR (2nd multiplication operand)
1714 ;; Operand 6: HI
1715 (define_peephole2
1716   [(match_scratch:SI 0 "d")
1717    (set (match_operand:SI 1 "register_operand" "")
1718         (match_operand:SI 2 "register_operand" ""))
1719    (match_dup 0)
1720    (parallel
1721        [(set (match_operand:SI 3 "register_operand" "")
1722              (plus:SI (mult:SI (match_operand:SI 4 "register_operand" "")
1723                                (match_operand:SI 5 "register_operand" ""))
1724                       (match_dup 1)))
1725         (clobber (match_operand:SI 6 "register_operand" ""))
1726         (clobber (match_dup 1))])]
1727   "ISA_HAS_MACC && GENERATE_MULT3_SI
1728    && true_regnum (operands[1]) == LO_REGNUM
1729    && peep2_reg_dead_p (2, operands[1])
1730    && GP_REG_P (true_regnum (operands[3]))"
1731   [(parallel [(set (match_dup 0)
1732                    (mult:SI (match_dup 4)
1733                             (match_dup 5)))
1734               (clobber (match_dup 6))
1735               (clobber (match_dup 1))])
1736    (set (match_dup 3)
1737         (plus:SI (match_dup 0)
1738                  (match_dup 2)))]
1739   "")
1740
1741 ;; Same as above, except LO is the initial target of the macc.
1742 ;;
1743 ;; Operand 0: GPR (scratch)
1744 ;; Operand 1: LO
1745 ;; Operand 2: GPR (addend)
1746 ;; Operand 3: GPR (1st multiplication operand)
1747 ;; Operand 4: GPR (2nd multiplication operand)
1748 ;; Operand 5: HI
1749 ;; Operand 6: GPR (destination)
1750 (define_peephole2
1751   [(match_scratch:SI 0 "d")
1752    (set (match_operand:SI 1 "register_operand" "")
1753         (match_operand:SI 2 "register_operand" ""))
1754    (match_dup 0)
1755    (parallel
1756        [(set (match_dup 1)
1757              (plus:SI (mult:SI (match_operand:SI 3 "register_operand" "")
1758                                (match_operand:SI 4 "register_operand" ""))
1759                       (match_dup 1)))
1760         (clobber (match_operand:SI 5 "register_operand" ""))
1761         (clobber (scratch:SI))])
1762    (match_dup 0)
1763    (set (match_operand:SI 6 "register_operand" "")
1764         (match_dup 1))]
1765   "ISA_HAS_MACC && GENERATE_MULT3_SI
1766    && true_regnum (operands[1]) == LO_REGNUM
1767    && peep2_reg_dead_p (3, operands[1])
1768    && GP_REG_P (true_regnum (operands[6]))"
1769   [(parallel [(set (match_dup 0)
1770                    (mult:SI (match_dup 3)
1771                             (match_dup 4)))
1772               (clobber (match_dup 5))
1773               (clobber (match_dup 1))])
1774    (set (match_dup 6)
1775         (plus:SI (match_dup 0)
1776                  (match_dup 2)))]
1777   "")
1778
1779 (define_insn "*mul_sub_si"
1780   [(set (match_operand:SI 0 "register_operand" "=l,*d,*d")
1781         (minus:SI (match_operand:SI 1 "register_operand" "0,l,*d")
1782                   (mult:SI (match_operand:SI 2 "register_operand" "d,d,d")
1783                            (match_operand:SI 3 "register_operand" "d,d,d"))))
1784    (clobber (match_scratch:SI 4 "=h,h,h"))
1785    (clobber (match_scratch:SI 5 "=X,1,l"))
1786    (clobber (match_scratch:SI 6 "=X,X,&d"))]
1787   "ISA_HAS_MADD_MSUB"
1788   "@
1789    msub\t%2,%3
1790    #
1791    #"
1792   [(set_attr "type"     "imadd,multi,multi")
1793    (set_attr "mode"     "SI")
1794    (set_attr "length"   "4,8,8")])
1795
1796 ;; Split the above insn if we failed to get LO allocated.
1797 (define_split
1798   [(set (match_operand:SI 0 "register_operand" "")
1799         (minus:SI (match_operand:SI 1 "register_operand" "")
1800                   (mult:SI (match_operand:SI 2 "register_operand" "")
1801                            (match_operand:SI 3 "register_operand" ""))))
1802    (clobber (match_scratch:SI 4 ""))
1803    (clobber (match_scratch:SI 5 ""))
1804    (clobber (match_scratch:SI 6 ""))]
1805   "reload_completed && !TARGET_DEBUG_D_MODE
1806    && GP_REG_P (true_regnum (operands[0]))
1807    && GP_REG_P (true_regnum (operands[1]))"
1808   [(parallel [(set (match_dup 6)
1809                    (mult:SI (match_dup 2) (match_dup 3)))
1810               (clobber (match_dup 4))
1811               (clobber (match_dup 5))])
1812    (set (match_dup 0) (minus:SI (match_dup 1) (match_dup 6)))]
1813   "")
1814
1815 ;; Splitter to copy result of MSUB to a general register
1816 (define_split
1817   [(set (match_operand:SI 0 "register_operand" "")
1818         (minus:SI (match_operand:SI 1 "register_operand" "")
1819                   (mult:SI (match_operand:SI 2 "register_operand" "")
1820                            (match_operand:SI 3 "register_operand" ""))))
1821    (clobber (match_scratch:SI 4 ""))
1822    (clobber (match_scratch:SI 5 ""))
1823    (clobber (match_scratch:SI 6 ""))]
1824   "reload_completed && !TARGET_DEBUG_D_MODE
1825    && GP_REG_P (true_regnum (operands[0]))
1826    && true_regnum (operands[1]) == LO_REGNUM"
1827   [(parallel [(set (match_dup 1)
1828                    (minus:SI (match_dup 1)
1829                              (mult:SI (match_dup 2) (match_dup 3))))
1830               (clobber (match_dup 4))
1831               (clobber (match_dup 5))
1832               (clobber (match_dup 6))])
1833    (set (match_dup 0) (match_dup 1))]
1834   "")
1835
1836 (define_insn "*muls"
1837   [(set (match_operand:SI                  0 "register_operand" "=l,d")
1838         (neg:SI (mult:SI (match_operand:SI 1 "register_operand" "d,d")
1839                          (match_operand:SI 2 "register_operand" "d,d"))))
1840    (clobber (match_scratch:SI              3                    "=h,h"))
1841    (clobber (match_scratch:SI              4                    "=X,l"))]
1842   "ISA_HAS_MULS"
1843   "@
1844    muls\t$0,%1,%2
1845    muls\t%0,%1,%2"
1846   [(set_attr "type"     "imul")
1847    (set_attr "mode"     "SI")])
1848
1849 (define_insn "*msac"
1850   [(set (match_operand:SI 0 "register_operand" "=l,d")
1851         (minus:SI (match_operand:SI 1 "register_operand" "0,l")
1852                   (mult:SI (match_operand:SI 2 "register_operand" "d,d")
1853                            (match_operand:SI 3 "register_operand" "d,d"))))
1854    (clobber (match_scratch:SI 4 "=h,h"))
1855    (clobber (match_scratch:SI 5 "=X,1"))]
1856   "ISA_HAS_MSAC"
1857 {
1858   if (which_alternative == 1)
1859     return "msac\t%0,%2,%3";
1860   else if (TARGET_MIPS5500)
1861     return "msub\t%2,%3";
1862   else
1863     return "msac\t$0,%2,%3";
1864 }
1865   [(set_attr "type"     "imadd")
1866    (set_attr "mode"     "SI")])
1867
1868 (define_expand "muldi3"
1869   [(set (match_operand:DI 0 "register_operand" "")
1870         (mult:DI (match_operand:DI 1 "register_operand" "")
1871                  (match_operand:DI 2 "register_operand" "")))]
1872   "TARGET_64BIT"
1873 {
1874   if (GENERATE_MULT3_DI)
1875     emit_insn (gen_muldi3_mult3 (operands[0], operands[1], operands[2]));
1876   else if (!TARGET_FIX_R4000)
1877     emit_insn (gen_muldi3_internal (operands[0], operands[1], operands[2]));
1878   else
1879     emit_insn (gen_muldi3_r4000 (operands[0], operands[1], operands[2]));
1880   DONE;
1881 })
1882
1883 (define_insn "muldi3_mult3"
1884   [(set (match_operand:DI 0 "register_operand" "=d")
1885         (mult:DI (match_operand:DI 1 "register_operand" "d")
1886                  (match_operand:DI 2 "register_operand" "d")))
1887    (clobber (match_scratch:DI 3 "=h"))
1888    (clobber (match_scratch:DI 4 "=l"))]
1889   "TARGET_64BIT && GENERATE_MULT3_DI"
1890   "dmult\t%0,%1,%2"
1891   [(set_attr "type"     "imul")
1892    (set_attr "mode"     "DI")])
1893
1894 (define_insn "muldi3_internal"
1895   [(set (match_operand:DI 0 "register_operand" "=l")
1896         (mult:DI (match_operand:DI 1 "register_operand" "d")
1897                  (match_operand:DI 2 "register_operand" "d")))
1898    (clobber (match_scratch:DI 3 "=h"))]
1899   "TARGET_64BIT && !TARGET_FIX_R4000"
1900   "dmult\t%1,%2"
1901   [(set_attr "type"     "imul")
1902    (set_attr "mode"     "DI")])
1903
1904 (define_insn "muldi3_r4000"
1905   [(set (match_operand:DI 0 "register_operand" "=d")
1906         (mult:DI (match_operand:DI 1 "register_operand" "d")
1907                  (match_operand:DI 2 "register_operand" "d")))
1908    (clobber (match_scratch:DI 3 "=h"))
1909    (clobber (match_scratch:DI 4 "=l"))]
1910   "TARGET_64BIT && TARGET_FIX_R4000"
1911   "dmult\t%1,%2\;mflo\t%0"
1912   [(set_attr "type"     "imul")
1913    (set_attr "mode"     "DI")
1914    (set_attr "length"   "8")])
1915
1916 ;; ??? We could define a mulditi3 pattern when TARGET_64BIT.
1917
1918 (define_expand "mulsidi3"
1919   [(parallel
1920       [(set (match_operand:DI 0 "register_operand" "")
1921             (mult:DI
1922                (sign_extend:DI (match_operand:SI 1 "register_operand" ""))
1923                (sign_extend:DI (match_operand:SI 2 "register_operand" ""))))
1924        (clobber (scratch:DI))
1925        (clobber (scratch:DI))
1926        (clobber (scratch:DI))])]
1927   "!TARGET_64BIT || !TARGET_FIX_R4000"
1928 {
1929   if (!TARGET_64BIT)
1930     {
1931       if (!TARGET_FIX_R4000)
1932         emit_insn (gen_mulsidi3_32bit_internal (operands[0], operands[1],
1933                                                 operands[2]));
1934       else
1935         emit_insn (gen_mulsidi3_32bit_r4000 (operands[0], operands[1],
1936                                              operands[2]));
1937       DONE;
1938     }
1939 })
1940
1941 (define_insn "mulsidi3_32bit_internal"
1942   [(set (match_operand:DI 0 "register_operand" "=x")
1943         (mult:DI
1944            (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))
1945            (sign_extend:DI (match_operand:SI 2 "register_operand" "d"))))]
1946   "!TARGET_64BIT && !TARGET_FIX_R4000"
1947   "mult\t%1,%2"
1948   [(set_attr "type"     "imul")
1949    (set_attr "mode"     "SI")])
1950
1951 (define_insn "mulsidi3_32bit_r4000"
1952   [(set (match_operand:DI 0 "register_operand" "=d")
1953         (mult:DI
1954            (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))
1955            (sign_extend:DI (match_operand:SI 2 "register_operand" "d"))))
1956    (clobber (match_scratch:DI 3 "=l"))
1957    (clobber (match_scratch:DI 4 "=h"))]
1958   "!TARGET_64BIT && TARGET_FIX_R4000"
1959   "mult\t%1,%2\;mflo\t%L0;mfhi\t%M0"
1960   [(set_attr "type"     "imul")
1961    (set_attr "mode"     "SI")
1962    (set_attr "length"   "12")])
1963
1964 (define_insn_and_split "*mulsidi3_64bit"
1965   [(set (match_operand:DI 0 "register_operand" "=d")
1966         (mult:DI (match_operator:DI 1 "extend_operator"
1967                     [(match_operand:SI 3 "register_operand" "d")])
1968                  (match_operator:DI 2 "extend_operator"
1969                     [(match_operand:SI 4 "register_operand" "d")])))
1970    (clobber (match_scratch:DI 5 "=l"))
1971    (clobber (match_scratch:DI 6 "=h"))
1972    (clobber (match_scratch:DI 7 "=d"))]
1973   "TARGET_64BIT && !TARGET_FIX_R4000
1974    && GET_CODE (operands[1]) == GET_CODE (operands[2])"
1975   "#"
1976   "&& reload_completed"
1977   [(parallel
1978        [(set (match_dup 5)
1979              (sign_extend:DI
1980                 (mult:SI (match_dup 3)
1981                          (match_dup 4))))
1982         (set (match_dup 6)
1983              (ashiftrt:DI
1984                 (mult:DI (match_dup 1)
1985                          (match_dup 2))
1986                 (const_int 32)))])
1987
1988    ;; OP7 <- LO, OP0 <- HI
1989    (set (match_dup 7) (match_dup 5))
1990    (set (match_dup 0) (match_dup 6))
1991
1992    ;; Zero-extend OP7.
1993    (set (match_dup 7)
1994         (ashift:DI (match_dup 7)
1995                    (const_int 32)))
1996    (set (match_dup 7)
1997         (lshiftrt:DI (match_dup 7)
1998                      (const_int 32)))
1999
2000    ;; Shift OP0 into place.
2001    (set (match_dup 0)
2002         (ashift:DI (match_dup 0)
2003                    (const_int 32)))
2004
2005    ;; OR the two halves together
2006    (set (match_dup 0)
2007         (ior:DI (match_dup 0)
2008                 (match_dup 7)))]
2009   ""
2010   [(set_attr "type"     "imul")
2011    (set_attr "mode"     "SI")
2012    (set_attr "length"   "24")])
2013
2014 (define_insn "*mulsidi3_64bit_parts"
2015   [(set (match_operand:DI 0 "register_operand" "=l")
2016         (sign_extend:DI
2017            (mult:SI (match_operand:SI 2 "register_operand" "d")
2018                     (match_operand:SI 3 "register_operand" "d"))))
2019    (set (match_operand:DI 1 "register_operand" "=h")
2020         (ashiftrt:DI
2021            (mult:DI
2022               (match_operator:DI 4 "extend_operator" [(match_dup 2)])
2023               (match_operator:DI 5 "extend_operator" [(match_dup 3)]))
2024            (const_int 32)))]
2025   "TARGET_64BIT && !TARGET_FIX_R4000
2026    && GET_CODE (operands[4]) == GET_CODE (operands[5])"
2027 {
2028   if (GET_CODE (operands[4]) == SIGN_EXTEND)
2029     return "mult\t%2,%3";
2030   else
2031     return "multu\t%2,%3";
2032 }
2033   [(set_attr "type" "imul")
2034    (set_attr "mode" "SI")])
2035
2036 (define_expand "umulsidi3"
2037   [(parallel
2038       [(set (match_operand:DI 0 "register_operand" "")
2039             (mult:DI
2040                (zero_extend:DI (match_operand:SI 1 "register_operand" ""))
2041                (zero_extend:DI (match_operand:SI 2 "register_operand" ""))))
2042        (clobber (scratch:DI))
2043        (clobber (scratch:DI))
2044        (clobber (scratch:DI))])]
2045   "!TARGET_64BIT || !TARGET_FIX_R4000"
2046 {
2047   if (!TARGET_64BIT)
2048     {
2049       if (!TARGET_FIX_R4000)
2050         emit_insn (gen_umulsidi3_32bit_internal (operands[0], operands[1],
2051                                                  operands[2]));
2052       else
2053         emit_insn (gen_umulsidi3_32bit_r4000 (operands[0], operands[1],
2054                                               operands[2]));
2055       DONE;
2056     }
2057 })
2058
2059 (define_insn "umulsidi3_32bit_internal"
2060   [(set (match_operand:DI 0 "register_operand" "=x")
2061         (mult:DI
2062            (zero_extend:DI (match_operand:SI 1 "register_operand" "d"))
2063            (zero_extend:DI (match_operand:SI 2 "register_operand" "d"))))]
2064   "!TARGET_64BIT && !TARGET_FIX_R4000"
2065   "multu\t%1,%2"
2066   [(set_attr "type"     "imul")
2067    (set_attr "mode"     "SI")])
2068
2069 (define_insn "umulsidi3_32bit_r4000"
2070   [(set (match_operand:DI 0 "register_operand" "=d")
2071         (mult:DI
2072            (zero_extend:DI (match_operand:SI 1 "register_operand" "d"))
2073            (zero_extend:DI (match_operand:SI 2 "register_operand" "d"))))
2074    (clobber (match_scratch:DI 3 "=l"))
2075    (clobber (match_scratch:DI 4 "=h"))]
2076   "!TARGET_64BIT && TARGET_FIX_R4000"
2077   "multu\t%1,%2\;mflo\t%L0;mfhi\t%M0"
2078   [(set_attr "type"     "imul")
2079    (set_attr "mode"     "SI")
2080    (set_attr "length"   "12")])
2081
2082 ;; Widening multiply with negation.
2083 (define_insn "*muls_di"
2084   [(set (match_operand:DI 0 "register_operand" "=x")
2085         (neg:DI
2086          (mult:DI
2087           (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))
2088           (sign_extend:DI (match_operand:SI 2 "register_operand" "d")))))]
2089   "!TARGET_64BIT && ISA_HAS_MULS"
2090   "muls\t$0,%1,%2"
2091   [(set_attr "type"     "imul")
2092    (set_attr "length"   "4")
2093    (set_attr "mode"     "SI")])
2094
2095 (define_insn "*umuls_di"
2096   [(set (match_operand:DI 0 "register_operand" "=x")
2097         (neg:DI
2098          (mult:DI
2099           (zero_extend:DI (match_operand:SI 1 "register_operand" "d"))
2100           (zero_extend:DI (match_operand:SI 2 "register_operand" "d")))))]
2101   "!TARGET_64BIT && ISA_HAS_MULS"
2102   "mulsu\t$0,%1,%2"
2103   [(set_attr "type"     "imul")
2104    (set_attr "length"   "4")
2105    (set_attr "mode"     "SI")])
2106
2107 (define_insn "*smsac_di"
2108   [(set (match_operand:DI 0 "register_operand" "=x")
2109         (minus:DI
2110            (match_operand:DI 3 "register_operand" "0")
2111            (mult:DI
2112               (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))
2113               (sign_extend:DI (match_operand:SI 2 "register_operand" "d")))))]
2114   "!TARGET_64BIT && ISA_HAS_MSAC"
2115 {
2116   if (TARGET_MIPS5500)
2117     return "msub\t%1,%2";
2118   else
2119     return "msac\t$0,%1,%2";
2120 }
2121   [(set_attr "type"     "imadd")
2122    (set_attr "length"   "4")
2123    (set_attr "mode"     "SI")])
2124
2125 (define_insn "*umsac_di"
2126   [(set (match_operand:DI 0 "register_operand" "=x")
2127         (minus:DI
2128            (match_operand:DI 3 "register_operand" "0")
2129            (mult:DI
2130               (zero_extend:DI (match_operand:SI 1 "register_operand" "d"))
2131               (zero_extend:DI (match_operand:SI 2 "register_operand" "d")))))]
2132   "!TARGET_64BIT && ISA_HAS_MSAC"
2133 {
2134   if (TARGET_MIPS5500)
2135     return "msubu\t%1,%2";
2136   else
2137     return "msacu\t$0,%1,%2";
2138 }
2139   [(set_attr "type"     "imadd")
2140    (set_attr "length"   "4")
2141    (set_attr "mode"     "SI")])
2142
2143 ;; _highpart patterns
2144 (define_expand "umulsi3_highpart"
2145   [(set (match_operand:SI 0 "register_operand" "")
2146         (truncate:SI
2147          (lshiftrt:DI
2148           (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" ""))
2149                    (zero_extend:DI (match_operand:SI 2 "register_operand" "")))
2150           (const_int 32))))]
2151   "ISA_HAS_MULHI || !TARGET_FIX_R4000"
2152 {
2153   if (ISA_HAS_MULHI)
2154     emit_insn (gen_umulsi3_highpart_mulhi_internal (operands[0], operands[1],
2155                                                     operands[2]));
2156   else
2157     emit_insn (gen_umulsi3_highpart_internal (operands[0], operands[1],
2158                                               operands[2]));
2159   DONE;
2160 })
2161
2162 (define_insn "umulsi3_highpart_internal"
2163   [(set (match_operand:SI 0 "register_operand" "=h")
2164         (truncate:SI
2165          (lshiftrt:DI
2166           (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "d"))
2167                    (zero_extend:DI (match_operand:SI 2 "register_operand" "d")))
2168           (const_int 32))))
2169    (clobber (match_scratch:SI 3 "=l"))]
2170   "!ISA_HAS_MULHI && !TARGET_FIX_R4000"
2171   "multu\t%1,%2"
2172   [(set_attr "type"   "imul")
2173    (set_attr "mode"   "SI")
2174    (set_attr "length" "4")])
2175
2176 (define_insn "umulsi3_highpart_mulhi_internal"
2177   [(set (match_operand:SI 0 "register_operand" "=h,d")
2178         (truncate:SI
2179          (lshiftrt:DI
2180           (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "d,d"))
2181                    (zero_extend:DI (match_operand:SI 2 "register_operand" "d,d")))
2182           (const_int 32))))
2183    (clobber (match_scratch:SI 3 "=l,l"))
2184    (clobber (match_scratch:SI 4 "=X,h"))]
2185   "ISA_HAS_MULHI"
2186   "@
2187    multu\t%1,%2
2188    mulhiu\t%0,%1,%2"
2189   [(set_attr "type"   "imul")
2190    (set_attr "mode"   "SI")
2191    (set_attr "length" "4")])
2192
2193 (define_insn "umulsi3_highpart_neg_mulhi_internal"
2194   [(set (match_operand:SI 0 "register_operand" "=h,d")
2195         (truncate:SI
2196          (lshiftrt:DI
2197           (neg:DI
2198            (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "d,d"))
2199                     (zero_extend:DI (match_operand:SI 2 "register_operand" "d,d"))))
2200           (const_int 32))))
2201    (clobber (match_scratch:SI 3 "=l,l"))
2202    (clobber (match_scratch:SI 4 "=X,h"))]
2203   "ISA_HAS_MULHI"
2204   "@
2205    mulshiu\t%.,%1,%2
2206    mulshiu\t%0,%1,%2"
2207   [(set_attr "type"   "imul")
2208    (set_attr "mode"   "SI")
2209    (set_attr "length" "4")])
2210
2211 (define_expand "smulsi3_highpart"
2212   [(set (match_operand:SI 0 "register_operand" "")
2213         (truncate:SI
2214          (lshiftrt:DI
2215           (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" ""))
2216                    (sign_extend:DI (match_operand:SI 2 "register_operand" "")))
2217          (const_int 32))))]
2218   "ISA_HAS_MULHI || !TARGET_FIX_R4000"
2219 {
2220   if (ISA_HAS_MULHI)
2221     emit_insn (gen_smulsi3_highpart_mulhi_internal (operands[0], operands[1],
2222                                                     operands[2]));
2223   else
2224     emit_insn (gen_smulsi3_highpart_internal (operands[0], operands[1],
2225                                               operands[2]));
2226   DONE;
2227 })
2228
2229 (define_insn "smulsi3_highpart_internal"
2230   [(set (match_operand:SI 0 "register_operand" "=h")
2231         (truncate:SI
2232          (lshiftrt:DI
2233           (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))
2234                    (sign_extend:DI (match_operand:SI 2 "register_operand" "d")))
2235           (const_int 32))))
2236    (clobber (match_scratch:SI 3 "=l"))]
2237   "!ISA_HAS_MULHI && !TARGET_FIX_R4000"
2238   "mult\t%1,%2"
2239   [(set_attr "type"     "imul")
2240    (set_attr "mode"     "SI")
2241    (set_attr "length"   "4")])
2242
2243 (define_insn "smulsi3_highpart_mulhi_internal"
2244   [(set (match_operand:SI 0 "register_operand" "=h,d")
2245         (truncate:SI
2246          (lshiftrt:DI
2247           (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d,d"))
2248                    (sign_extend:DI (match_operand:SI 2 "register_operand" "d,d")))
2249           (const_int 32))))
2250    (clobber (match_scratch:SI 3 "=l,l"))
2251    (clobber (match_scratch:SI 4 "=X,h"))]
2252   "ISA_HAS_MULHI"
2253   "@
2254    mult\t%1,%2
2255    mulhi\t%0,%1,%2"
2256   [(set_attr "type"   "imul")
2257    (set_attr "mode"   "SI")
2258    (set_attr "length" "4")])
2259
2260 (define_insn "smulsi3_highpart_neg_mulhi_internal"
2261   [(set (match_operand:SI 0 "register_operand" "=h,d")
2262         (truncate:SI
2263          (lshiftrt:DI
2264           (neg:DI
2265            (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d,d"))
2266                     (sign_extend:DI (match_operand:SI 2 "register_operand" "d,d"))))
2267           (const_int 32))))
2268    (clobber (match_scratch:SI 3 "=l,l"))
2269    (clobber (match_scratch:SI 4 "=X,h"))]
2270   "ISA_HAS_MULHI"
2271   "@
2272    mulshi\t%.,%1,%2
2273    mulshi\t%0,%1,%2"
2274   [(set_attr "type"   "imul")
2275    (set_attr "mode"   "SI")])
2276
2277 (define_insn "smuldi3_highpart"
2278   [(set (match_operand:DI 0 "register_operand" "=h")
2279         (truncate:DI
2280          (lshiftrt:TI
2281           (mult:TI
2282            (sign_extend:TI (match_operand:DI 1 "register_operand" "d"))
2283            (sign_extend:TI (match_operand:DI 2 "register_operand" "d")))
2284          (const_int 64))))
2285    (clobber (match_scratch:DI 3 "=l"))]
2286   "TARGET_64BIT && !TARGET_FIX_R4000"
2287   "dmult\t%1,%2"
2288   [(set_attr "type"     "imul")
2289    (set_attr "mode"     "DI")])
2290
2291 (define_insn "umuldi3_highpart"
2292   [(set (match_operand:DI 0 "register_operand" "=h")
2293         (truncate:DI
2294          (lshiftrt:TI
2295           (mult:TI
2296            (zero_extend:TI (match_operand:DI 1 "register_operand" "d"))
2297            (zero_extend:TI (match_operand:DI 2 "register_operand" "d")))
2298           (const_int 64))))
2299    (clobber (match_scratch:DI 3 "=l"))]
2300   "TARGET_64BIT && !TARGET_FIX_R4000"
2301   "dmultu\t%1,%2"
2302   [(set_attr "type"     "imul")
2303    (set_attr "mode"     "DI")])
2304
2305
2306 ;; The R4650 supports a 32 bit multiply/ 64 bit accumulate
2307 ;; instruction.  The HI/LO registers are used as a 64 bit accumulator.
2308
2309 (define_insn "madsi"
2310   [(set (match_operand:SI 0 "register_operand" "+l")
2311         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "d")
2312                           (match_operand:SI 2 "register_operand" "d"))
2313                  (match_dup 0)))
2314    (clobber (match_scratch:SI 3 "=h"))]
2315   "TARGET_MAD"
2316   "mad\t%1,%2"
2317   [(set_attr "type"     "imadd")
2318    (set_attr "mode"     "SI")])
2319
2320 (define_insn "*umul_acc_di"
2321   [(set (match_operand:DI 0 "register_operand" "=x")
2322         (plus:DI
2323          (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "d"))
2324                   (zero_extend:DI (match_operand:SI 2 "register_operand" "d")))
2325          (match_operand:DI 3 "register_operand" "0")))]
2326   "(TARGET_MAD || ISA_HAS_MACC)
2327    && !TARGET_64BIT"
2328 {
2329   if (TARGET_MAD)
2330     return "madu\t%1,%2";
2331   else if (TARGET_MIPS5500)
2332     return "maddu\t%1,%2";
2333   else
2334     return "maccu\t%.,%1,%2";
2335 }
2336   [(set_attr "type"   "imadd")
2337    (set_attr "mode"   "SI")])
2338
2339
2340 (define_insn "*smul_acc_di"
2341   [(set (match_operand:DI 0 "register_operand" "=x")
2342         (plus:DI
2343          (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))
2344                   (sign_extend:DI (match_operand:SI 2 "register_operand" "d")))
2345          (match_operand:DI 3 "register_operand" "0")))]
2346   "(TARGET_MAD || ISA_HAS_MACC)
2347    && !TARGET_64BIT"
2348 {
2349   if (TARGET_MAD)
2350     return "mad\t%1,%2";
2351   else if (TARGET_MIPS5500)
2352     return "madd\t%1,%2";
2353   else
2354     return "macc\t%.,%1,%2";
2355 }
2356   [(set_attr "type"   "imadd")
2357    (set_attr "mode"   "SI")])
2358
2359 ;; Floating point multiply accumulate instructions.
2360
2361 (define_insn ""
2362   [(set (match_operand:DF 0 "register_operand" "=f")
2363         (plus:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
2364                           (match_operand:DF 2 "register_operand" "f"))
2365                  (match_operand:DF 3 "register_operand" "f")))]
2366   "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_FUSED_MADD"
2367   "madd.d\t%0,%3,%1,%2"
2368   [(set_attr "type"     "fmadd")
2369    (set_attr "mode"     "DF")])
2370
2371 (define_insn ""
2372   [(set (match_operand:SF 0 "register_operand" "=f")
2373         (plus:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
2374                           (match_operand:SF 2 "register_operand" "f"))
2375                  (match_operand:SF 3 "register_operand" "f")))]
2376   "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_FUSED_MADD"
2377   "madd.s\t%0,%3,%1,%2"
2378   [(set_attr "type"     "fmadd")
2379    (set_attr "mode"     "SF")])
2380
2381 (define_insn ""
2382   [(set (match_operand:DF 0 "register_operand" "=f")
2383         (minus:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
2384                            (match_operand:DF 2 "register_operand" "f"))
2385                   (match_operand:DF 3 "register_operand" "f")))]
2386   "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_FUSED_MADD"
2387   "msub.d\t%0,%3,%1,%2"
2388   [(set_attr "type"     "fmadd")
2389    (set_attr "mode"     "DF")])
2390
2391 (define_insn ""
2392   [(set (match_operand:SF 0 "register_operand" "=f")
2393         (minus:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
2394                            (match_operand:SF 2 "register_operand" "f"))
2395                   (match_operand:SF 3 "register_operand" "f")))]
2396
2397   "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_FUSED_MADD"
2398   "msub.s\t%0,%3,%1,%2"
2399   [(set_attr "type"     "fmadd")
2400    (set_attr "mode"     "SF")])
2401
2402 (define_insn ""
2403   [(set (match_operand:DF 0 "register_operand" "=f")
2404         (neg:DF (plus:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
2405                                   (match_operand:DF 2 "register_operand" "f"))
2406                          (match_operand:DF 3 "register_operand" "f"))))]
2407   "ISA_HAS_NMADD_NMSUB && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_FUSED_MADD"
2408   "nmadd.d\t%0,%3,%1,%2"
2409   [(set_attr "type"     "fmadd")
2410    (set_attr "mode"     "DF")])
2411
2412 (define_insn ""
2413   [(set (match_operand:SF 0 "register_operand" "=f")
2414         (neg:SF (plus:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
2415                                   (match_operand:SF 2 "register_operand" "f"))
2416                          (match_operand:SF 3 "register_operand" "f"))))]
2417   "ISA_HAS_NMADD_NMSUB && TARGET_HARD_FLOAT && TARGET_FUSED_MADD"
2418   "nmadd.s\t%0,%3,%1,%2"
2419   [(set_attr "type"     "fmadd")
2420    (set_attr "mode"     "SF")])
2421
2422 (define_insn ""
2423   [(set (match_operand:DF 0 "register_operand" "=f")
2424         (minus:DF (match_operand:DF 1 "register_operand" "f")
2425                   (mult:DF (match_operand:DF 2 "register_operand" "f")
2426                            (match_operand:DF 3 "register_operand" "f"))))]
2427   "ISA_HAS_NMADD_NMSUB && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_FUSED_MADD"
2428   "nmsub.d\t%0,%1,%2,%3"
2429   [(set_attr "type"     "fmadd")
2430    (set_attr "mode"     "DF")])
2431
2432 (define_insn ""
2433   [(set (match_operand:SF 0 "register_operand" "=f")
2434         (minus:SF (match_operand:SF 1 "register_operand" "f")
2435                   (mult:SF (match_operand:SF 2 "register_operand" "f")
2436                            (match_operand:SF 3 "register_operand" "f"))))]
2437   "ISA_HAS_NMADD_NMSUB && TARGET_HARD_FLOAT && TARGET_FUSED_MADD"
2438   "nmsub.s\t%0,%1,%2,%3"
2439   [(set_attr "type"     "fmadd")
2440    (set_attr "mode"     "SF")])
2441 \f
2442 ;;
2443 ;;  ....................
2444 ;;
2445 ;;      DIVISION and REMAINDER
2446 ;;
2447 ;;  ....................
2448 ;;
2449
2450 (define_expand "divdf3"
2451   [(set (match_operand:DF 0 "register_operand" "")
2452         (div:DF (match_operand:DF 1 "reg_or_const_float_1_operand" "")
2453                 (match_operand:DF 2 "register_operand" "")))]
2454   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
2455 {
2456   if (const_float_1_operand (operands[1], DFmode))
2457     if (!(ISA_HAS_FP4 && flag_unsafe_math_optimizations))
2458       FAIL;
2459 })
2460
2461 ;; This pattern works around the early SB-1 rev2 core "F1" erratum:
2462 ;;
2463 ;; If an mfc1 or dmfc1 happens to access the floating point register
2464 ;; file at the same time a long latency operation (div, sqrt, recip,
2465 ;; sqrt) iterates an intermediate result back through the floating
2466 ;; point register file bypass, then instead returning the correct
2467 ;; register value the mfc1 or dmfc1 operation returns the intermediate
2468 ;; result of the long latency operation.
2469 ;;
2470 ;; The workaround is to insert an unconditional 'mov' from/to the
2471 ;; long latency op destination register.
2472
2473 (define_insn "*divdf3"
2474   [(set (match_operand:DF 0 "register_operand" "=f")
2475         (div:DF (match_operand:DF 1 "register_operand" "f")
2476                 (match_operand:DF 2 "register_operand" "f")))]
2477   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
2478 {
2479   if (TARGET_FIX_SB1)
2480     return "div.d\t%0,%1,%2\;mov.d\t%0,%0";
2481   else
2482     return "div.d\t%0,%1,%2";
2483 }
2484   [(set_attr "type"     "fdiv")
2485    (set_attr "mode"     "DF")
2486    (set (attr "length")
2487         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
2488                       (const_int 8)
2489                       (const_int 4)))])
2490
2491
2492 ;; This pattern works around the early SB-1 rev2 core "F2" erratum:
2493 ;;
2494 ;; In certain cases, div.s and div.ps may have a rounding error
2495 ;; and/or wrong inexact flag.
2496 ;;
2497 ;; Therefore, we only allow div.s if not working around SB-1 rev2
2498 ;; errata, or if working around those errata and a slight loss of
2499 ;; precision is OK (i.e., flag_unsafe_math_optimizations is set).
2500 (define_expand "divsf3"
2501   [(set (match_operand:SF 0 "register_operand" "")
2502         (div:SF (match_operand:SF 1 "reg_or_const_float_1_operand" "")
2503                 (match_operand:SF 2 "register_operand" "")))]
2504   "TARGET_HARD_FLOAT && (!TARGET_FIX_SB1 || flag_unsafe_math_optimizations)"
2505 {
2506   if (const_float_1_operand (operands[1], SFmode))
2507     if (!(ISA_HAS_FP4 && flag_unsafe_math_optimizations))
2508       FAIL;
2509 })
2510
2511 ;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
2512 ;; "divdf3" comment for details).
2513 ;;
2514 ;; This pattern works around the early SB-1 rev2 core "F2" erratum (see
2515 ;; "divsf3" comment for details).
2516 (define_insn "*divsf3"
2517   [(set (match_operand:SF 0 "register_operand" "=f")
2518         (div:SF (match_operand:SF 1 "register_operand" "f")
2519                 (match_operand:SF 2 "register_operand" "f")))]
2520   "TARGET_HARD_FLOAT && (!TARGET_FIX_SB1 || flag_unsafe_math_optimizations)"
2521 {
2522   if (TARGET_FIX_SB1)
2523     return "div.s\t%0,%1,%2\;mov.s\t%0,%0";
2524   else
2525     return "div.s\t%0,%1,%2";
2526 }
2527   [(set_attr "type"     "fdiv")
2528    (set_attr "mode"     "SF")
2529    (set (attr "length")
2530         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
2531                       (const_int 8)
2532                       (const_int 4)))])
2533
2534 ;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
2535 ;; "divdf3" comment for details).
2536 (define_insn ""
2537   [(set (match_operand:DF 0 "register_operand" "=f")
2538         (div:DF (match_operand:DF 1 "const_float_1_operand" "")
2539                 (match_operand:DF 2 "register_operand" "f")))]
2540   "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && flag_unsafe_math_optimizations"
2541 {
2542   if (TARGET_FIX_SB1)
2543     return "recip.d\t%0,%2\;mov.d\t%0,%0";
2544   else
2545     return "recip.d\t%0,%2";
2546 }
2547   [(set_attr "type"     "fdiv")
2548    (set_attr "mode"     "DF")
2549    (set (attr "length")
2550         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
2551                       (const_int 8)
2552                       (const_int 4)))])
2553
2554 ;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
2555 ;; "divdf3" comment for details).
2556 (define_insn ""
2557   [(set (match_operand:SF 0 "register_operand" "=f")
2558         (div:SF (match_operand:SF 1 "const_float_1_operand" "")
2559                 (match_operand:SF 2 "register_operand" "f")))]
2560   "ISA_HAS_FP4 && TARGET_HARD_FLOAT && flag_unsafe_math_optimizations"
2561 {
2562   if (TARGET_FIX_SB1)
2563     return "recip.s\t%0,%2\;mov.s\t%0,%0";
2564   else
2565     return "recip.s\t%0,%2";
2566 }
2567   [(set_attr "type"     "fdiv")
2568    (set_attr "mode"     "SF")
2569    (set (attr "length")
2570         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
2571                       (const_int 8)
2572                       (const_int 4)))])
2573
2574 (define_insn "divmodsi4"
2575   [(set (match_operand:SI 0 "register_operand" "=l")
2576         (div:SI (match_operand:SI 1 "register_operand" "d")
2577                 (match_operand:SI 2 "register_operand" "d")))
2578    (set (match_operand:SI 3 "register_operand" "=h")
2579         (mod:SI (match_dup 1)
2580                 (match_dup 2)))]
2581   ""
2582   { return mips_output_division ("div\t$0,%1,%2", operands); }
2583   [(set_attr "type"     "idiv")
2584    (set_attr "mode"     "SI")])
2585
2586 (define_insn "divmoddi4"
2587   [(set (match_operand:DI 0 "register_operand" "=l")
2588         (div:DI (match_operand:DI 1 "register_operand" "d")
2589                 (match_operand:DI 2 "register_operand" "d")))
2590    (set (match_operand:DI 3 "register_operand" "=h")
2591         (mod:DI (match_dup 1)
2592                 (match_dup 2)))]
2593   "TARGET_64BIT"
2594   { return mips_output_division ("ddiv\t$0,%1,%2", operands); }
2595   [(set_attr "type"     "idiv")
2596    (set_attr "mode"     "DI")])
2597
2598 (define_insn "udivmodsi4"
2599   [(set (match_operand:SI 0 "register_operand" "=l")
2600         (udiv:SI (match_operand:SI 1 "register_operand" "d")
2601                  (match_operand:SI 2 "register_operand" "d")))
2602    (set (match_operand:SI 3 "register_operand" "=h")
2603         (umod:SI (match_dup 1)
2604                  (match_dup 2)))]
2605   ""
2606   { return mips_output_division ("divu\t$0,%1,%2", operands); }
2607   [(set_attr "type"     "idiv")
2608    (set_attr "mode"     "SI")])
2609
2610 (define_insn "udivmoddi4"
2611   [(set (match_operand:DI 0 "register_operand" "=l")
2612         (udiv:DI (match_operand:DI 1 "register_operand" "d")
2613                  (match_operand:DI 2 "register_operand" "d")))
2614    (set (match_operand:DI 3 "register_operand" "=h")
2615         (umod:DI (match_dup 1)
2616                  (match_dup 2)))]
2617   "TARGET_64BIT"
2618   { return mips_output_division ("ddivu\t$0,%1,%2", operands); }
2619   [(set_attr "type"     "idiv")
2620    (set_attr "mode"     "DI")])
2621 \f
2622 ;;
2623 ;;  ....................
2624 ;;
2625 ;;      SQUARE ROOT
2626 ;;
2627 ;;  ....................
2628
2629 ;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
2630 ;; "divdf3" comment for details).
2631 (define_insn "sqrtdf2"
2632   [(set (match_operand:DF 0 "register_operand" "=f")
2633         (sqrt:DF (match_operand:DF 1 "register_operand" "f")))]
2634   "TARGET_HARD_FLOAT && HAVE_SQRT_P() && TARGET_DOUBLE_FLOAT"
2635 {
2636   if (TARGET_FIX_SB1)
2637     return "sqrt.d\t%0,%1\;mov.d\t%0,%0";
2638   else
2639     return "sqrt.d\t%0,%1";
2640 }
2641   [(set_attr "type"     "fsqrt")
2642    (set_attr "mode"     "DF")
2643    (set (attr "length")
2644         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
2645                       (const_int 8)
2646                       (const_int 4)))])
2647
2648 ;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
2649 ;; "divdf3" comment for details).
2650 (define_insn "sqrtsf2"
2651   [(set (match_operand:SF 0 "register_operand" "=f")
2652         (sqrt:SF (match_operand:SF 1 "register_operand" "f")))]
2653   "TARGET_HARD_FLOAT && HAVE_SQRT_P()"
2654 {
2655   if (TARGET_FIX_SB1)
2656     return "sqrt.s\t%0,%1\;mov.s\t%0,%0";
2657   else
2658     return "sqrt.s\t%0,%1";
2659 }
2660   [(set_attr "type"     "fsqrt")
2661    (set_attr "mode"     "SF")
2662    (set (attr "length")
2663         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
2664                       (const_int 8)
2665                       (const_int 4)))])
2666
2667 ;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
2668 ;; "divdf3" comment for details).
2669 (define_insn ""
2670   [(set (match_operand:DF 0 "register_operand" "=f")
2671         (div:DF (match_operand:DF 1 "const_float_1_operand" "")
2672                 (sqrt:DF (match_operand:DF 2 "register_operand" "f"))))]
2673   "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && flag_unsafe_math_optimizations"
2674 {
2675   if (TARGET_FIX_SB1)
2676     return "rsqrt.d\t%0,%2\;mov.d\t%0,%0";
2677   else
2678     return "rsqrt.d\t%0,%2";
2679 }
2680   [(set_attr "type"     "frsqrt")
2681    (set_attr "mode"     "DF")
2682    (set (attr "length")
2683         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
2684                       (const_int 8)
2685                       (const_int 4)))])
2686
2687 ;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
2688 ;; "divdf3" comment for details).
2689 (define_insn ""
2690   [(set (match_operand:SF 0 "register_operand" "=f")
2691         (div:SF (match_operand:SF 1 "const_float_1_operand" "")
2692                 (sqrt:SF (match_operand:SF 2 "register_operand" "f"))))]
2693   "ISA_HAS_FP4 && TARGET_HARD_FLOAT && flag_unsafe_math_optimizations"
2694 {
2695   if (TARGET_FIX_SB1)
2696     return "rsqrt.s\t%0,%2\;mov.s\t%0,%0";
2697   else
2698     return "rsqrt.s\t%0,%2";
2699 }
2700   [(set_attr "type"     "frsqrt")
2701    (set_attr "mode"     "SF")
2702    (set (attr "length")
2703         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
2704                       (const_int 8)
2705                       (const_int 4)))])
2706 \f
2707 ;;
2708 ;;  ....................
2709 ;;
2710 ;;      ABSOLUTE VALUE
2711 ;;
2712 ;;  ....................
2713
2714 ;; Do not use the integer abs macro instruction, since that signals an
2715 ;; exception on -2147483648 (sigh).
2716
2717 (define_insn "abssi2"
2718   [(set (match_operand:SI 0 "register_operand" "=d")
2719         (abs:SI (match_operand:SI 1 "register_operand" "d")))]
2720   "!TARGET_MIPS16"
2721 {
2722   operands[2] = const0_rtx;
2723
2724   if (REGNO (operands[0]) == REGNO (operands[1]))
2725     {
2726       if (GENERATE_BRANCHLIKELY)
2727         return "%(bltzl\t%1,1f\;subu\t%0,%z2,%0\n%~1:%)";
2728       else
2729         return "bgez\t%1,1f%#\;subu\t%0,%z2,%0\n%~1:";
2730     }
2731   else
2732     return "%(bgez\t%1,1f\;move\t%0,%1\;subu\t%0,%z2,%0\n%~1:%)";
2733 }
2734   [(set_attr "type"     "multi")
2735    (set_attr "mode"     "SI")
2736    (set_attr "length"   "12")])
2737
2738 (define_insn "absdi2"
2739   [(set (match_operand:DI 0 "register_operand" "=d")
2740         (abs:DI (match_operand:DI 1 "register_operand" "d")))]
2741   "TARGET_64BIT && !TARGET_MIPS16"
2742 {
2743   unsigned int regno1;
2744   operands[2] = const0_rtx;
2745
2746   if (GET_CODE (operands[1]) == REG)
2747     regno1 = REGNO (operands[1]);
2748   else
2749     regno1 = REGNO (XEXP (operands[1], 0));
2750
2751   if (REGNO (operands[0]) == regno1)
2752     return "%(bltzl\t%1,1f\;dsubu\t%0,%z2,%0\n%~1:%)";
2753   else
2754     return "%(bgez\t%1,1f\;move\t%0,%1\;dsubu\t%0,%z2,%0\n%~1:%)";
2755 }
2756   [(set_attr "type"     "multi")
2757    (set_attr "mode"     "DI")
2758    (set_attr "length"   "12")])
2759
2760 (define_insn "absdf2"
2761   [(set (match_operand:DF 0 "register_operand" "=f")
2762         (abs:DF (match_operand:DF 1 "register_operand" "f")))]
2763   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
2764   "abs.d\t%0,%1"
2765   [(set_attr "type"     "fabs")
2766    (set_attr "mode"     "DF")])
2767
2768 (define_insn "abssf2"
2769   [(set (match_operand:SF 0 "register_operand" "=f")
2770         (abs:SF (match_operand:SF 1 "register_operand" "f")))]
2771   "TARGET_HARD_FLOAT"
2772   "abs.s\t%0,%1"
2773   [(set_attr "type"     "fabs")
2774    (set_attr "mode"     "SF")])
2775 \f
2776 ;;
2777 ;;  ....................
2778 ;;
2779 ;;      FIND FIRST BIT INSTRUCTION
2780 ;;
2781 ;;  ....................
2782 ;;
2783
2784 (define_insn "ffssi2"
2785   [(set (match_operand:SI 0 "register_operand" "=&d")
2786         (ffs:SI (match_operand:SI 1 "register_operand" "d")))
2787    (clobber (match_scratch:SI 2 "=&d"))
2788    (clobber (match_scratch:SI 3 "=&d"))]
2789   "!TARGET_MIPS16"
2790 {
2791   if (optimize && find_reg_note (insn, REG_DEAD, operands[1]))
2792     return "%(\
2793 move\t%0,%.\;\
2794 beq\t%1,%.,2f\n\
2795 %~1:\tand\t%2,%1,0x0001\;\
2796 addu\t%0,%0,1\;\
2797 beq\t%2,%.,1b\;\
2798 srl\t%1,%1,1\n\
2799 %~2:%)";
2800
2801   return "%(\
2802 move\t%0,%.\;\
2803 move\t%3,%1\;\
2804 beq\t%3,%.,2f\n\
2805 %~1:\tand\t%2,%3,0x0001\;\
2806 addu\t%0,%0,1\;\
2807 beq\t%2,%.,1b\;\
2808 srl\t%3,%3,1\n\
2809 %~2:%)";
2810 }
2811   [(set_attr "type"     "multi")
2812    (set_attr "mode"     "SI")
2813    (set_attr "length"   "28")])
2814
2815 (define_insn "ffsdi2"
2816   [(set (match_operand:DI 0 "register_operand" "=&d")
2817         (ffs:DI (match_operand:DI 1 "register_operand" "d")))
2818    (clobber (match_scratch:DI 2 "=&d"))
2819    (clobber (match_scratch:DI 3 "=&d"))]
2820   "TARGET_64BIT && !TARGET_MIPS16"
2821 {
2822   if (optimize && find_reg_note (insn, REG_DEAD, operands[1]))
2823     return "%(\
2824 move\t%0,%.\;\
2825 beq\t%1,%.,2f\n\
2826 %~1:\tand\t%2,%1,0x0001\;\
2827 daddu\t%0,%0,1\;\
2828 beq\t%2,%.,1b\;\
2829 dsrl\t%1,%1,1\n\
2830 %~2:%)";
2831
2832   return "%(\
2833 move\t%0,%.\;\
2834 move\t%3,%1\;\
2835 beq\t%3,%.,2f\n\
2836 %~1:\tand\t%2,%3,0x0001\;\
2837 daddu\t%0,%0,1\;\
2838 beq\t%2,%.,1b\;\
2839 dsrl\t%3,%3,1\n\
2840 %~2:%)";
2841 }
2842   [(set_attr "type"     "multi")
2843    (set_attr "mode"     "DI")
2844    (set_attr "length"   "28")])
2845 \f
2846 ;;
2847 ;;  ...................
2848 ;;
2849 ;;  Count leading zeroes.
2850 ;;
2851 ;;  ...................
2852 ;;
2853
2854 (define_insn "clzsi2"
2855   [(set (match_operand:SI 0 "register_operand" "=d")
2856         (clz:SI (match_operand:SI 1 "register_operand" "d")))]
2857   "ISA_HAS_CLZ_CLO"
2858   "clz\t%0,%1"
2859   [(set_attr "type" "arith")
2860    (set_attr "mode" "SI")])
2861
2862 (define_insn "clzdi2"
2863   [(set (match_operand:DI 0 "register_operand" "=d")
2864         (clz:DI (match_operand:DI 1 "register_operand" "d")))]
2865   "ISA_HAS_DCLZ_DCLO"
2866   "dclz\t%0,%1"
2867   [(set_attr "type" "arith")
2868    (set_attr "mode" "DI")])
2869 \f
2870 ;;
2871 ;;  ....................
2872 ;;
2873 ;;      NEGATION and ONE'S COMPLEMENT
2874 ;;
2875 ;;  ....................
2876
2877 (define_insn "negsi2"
2878   [(set (match_operand:SI 0 "register_operand" "=d")
2879         (neg:SI (match_operand:SI 1 "register_operand" "d")))]
2880   ""
2881 {
2882   if (TARGET_MIPS16)
2883     return "neg\t%0,%1";
2884   else
2885     return "subu\t%0,%.,%1";
2886 }
2887   [(set_attr "type"     "arith")
2888    (set_attr "mode"     "SI")])
2889
2890 (define_expand "negdi2"
2891   [(parallel [(set (match_operand:DI 0 "register_operand" "=d")
2892                    (neg:DI (match_operand:DI 1 "register_operand" "d")))
2893               (clobber (match_dup 2))])]
2894   "(TARGET_64BIT || !TARGET_DEBUG_G_MODE) && !TARGET_MIPS16"
2895 {
2896   if (TARGET_64BIT)
2897     {
2898       emit_insn (gen_negdi2_internal_2 (operands[0], operands[1]));
2899       DONE;
2900     }
2901
2902   operands[2] = gen_reg_rtx (SImode);
2903 })
2904
2905 (define_insn "negdi2_internal"
2906   [(set (match_operand:DI 0 "register_operand" "=d")
2907         (neg:DI (match_operand:DI 1 "register_operand" "d")))
2908    (clobber (match_operand:SI 2 "register_operand" "=d"))]
2909   "! TARGET_64BIT && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16"
2910   "subu\t%L0,%.,%L1\;subu\t%M0,%.,%M1\;sltu\t%2,%.,%L0\;subu\t%M0,%M0,%2"
2911   [(set_attr "type"     "darith")
2912    (set_attr "mode"     "DI")
2913    (set_attr "length"   "16")])
2914
2915 (define_insn "negdi2_internal_2"
2916   [(set (match_operand:DI 0 "register_operand" "=d")
2917         (neg:DI (match_operand:DI 1 "register_operand" "d")))]
2918   "TARGET_64BIT && !TARGET_MIPS16"
2919   "dsubu\t%0,%.,%1"
2920   [(set_attr "type"     "arith")
2921    (set_attr "mode"     "DI")])
2922
2923 (define_insn "negdf2"
2924   [(set (match_operand:DF 0 "register_operand" "=f")
2925         (neg:DF (match_operand:DF 1 "register_operand" "f")))]
2926   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
2927   "neg.d\t%0,%1"
2928   [(set_attr "type"     "fneg")
2929    (set_attr "mode"     "DF")])
2930
2931 (define_insn "negsf2"
2932   [(set (match_operand:SF 0 "register_operand" "=f")
2933         (neg:SF (match_operand:SF 1 "register_operand" "f")))]
2934   "TARGET_HARD_FLOAT"
2935   "neg.s\t%0,%1"
2936   [(set_attr "type"     "fneg")
2937    (set_attr "mode"     "SF")])
2938
2939 (define_insn "one_cmplsi2"
2940   [(set (match_operand:SI 0 "register_operand" "=d")
2941         (not:SI (match_operand:SI 1 "register_operand" "d")))]
2942   ""
2943 {
2944   if (TARGET_MIPS16)
2945     return "not\t%0,%1";
2946   else
2947     return "nor\t%0,%.,%1";
2948 }
2949   [(set_attr "type"     "arith")
2950    (set_attr "mode"     "SI")])
2951
2952 (define_insn "one_cmpldi2"
2953   [(set (match_operand:DI 0 "register_operand" "=d")
2954         (not:DI (match_operand:DI 1 "register_operand" "d")))]
2955   "TARGET_64BIT"
2956 {
2957   if (TARGET_MIPS16)
2958     return "not\t%0,%1";
2959   else
2960     return "nor\t%0,%.,%1";
2961 }
2962   [(set_attr "type"     "darith")
2963    (set_attr "mode"     "DI")])
2964 \f
2965 ;;
2966 ;;  ....................
2967 ;;
2968 ;;      LOGICAL
2969 ;;
2970 ;;  ....................
2971 ;;
2972
2973 ;; Many of these instructions use trivial define_expands, because we
2974 ;; want to use a different set of constraints when TARGET_MIPS16.
2975
2976 (define_expand "andsi3"
2977   [(set (match_operand:SI 0 "register_operand" "=d,d")
2978         (and:SI (match_operand:SI 1 "uns_arith_operand" "%d,d")
2979                 (match_operand:SI 2 "uns_arith_operand" "d,K")))]
2980   ""
2981 {
2982   if (TARGET_MIPS16)
2983     {
2984       operands[1] = force_reg (SImode, operands[1]);
2985       operands[2] = force_reg (SImode, operands[2]);
2986     }
2987 })
2988
2989 (define_insn ""
2990   [(set (match_operand:SI 0 "register_operand" "=d,d")
2991         (and:SI (match_operand:SI 1 "uns_arith_operand" "%d,d")
2992                 (match_operand:SI 2 "uns_arith_operand" "d,K")))]
2993   "!TARGET_MIPS16"
2994   "@
2995    and\t%0,%1,%2
2996    andi\t%0,%1,%x2"
2997   [(set_attr "type"     "arith")
2998    (set_attr "mode"     "SI")])
2999
3000 (define_insn ""
3001   [(set (match_operand:SI 0 "register_operand" "=d")
3002         (and:SI (match_operand:SI 1 "register_operand" "%0")
3003                 (match_operand:SI 2 "register_operand" "d")))]
3004   "TARGET_MIPS16"
3005   "and\t%0,%2"
3006   [(set_attr "type"     "arith")
3007    (set_attr "mode"     "SI")])
3008
3009 (define_expand "anddi3"
3010   [(set (match_operand:DI 0 "register_operand" "")
3011         (and:DI (match_operand:DI 1 "register_operand" "")
3012                 (match_operand:DI 2 "uns_arith_operand" "")))]
3013   "TARGET_64BIT"
3014 {
3015   if (TARGET_MIPS16)
3016     {
3017       operands[1] = force_reg (DImode, operands[1]);
3018       operands[2] = force_reg (DImode, operands[2]);
3019     }
3020 })
3021
3022 (define_insn ""
3023   [(set (match_operand:DI 0 "register_operand" "=d,d")
3024         (and:DI (match_operand:DI 1 "register_operand" "d,d")
3025                 (match_operand:DI 2 "uns_arith_operand" "d,K")))]
3026   "TARGET_64BIT && !TARGET_MIPS16"
3027   "@
3028    and\t%0,%1,%2
3029    andi\t%0,%1,%x2"
3030   [(set_attr "type"     "darith")
3031    (set_attr "mode"     "DI")])
3032
3033 (define_insn ""
3034   [(set (match_operand:DI 0 "register_operand" "=d")
3035         (and:DI (match_operand:DI 1 "register_operand" "0")
3036                 (match_operand:DI 2 "register_operand" "d")))]
3037   "TARGET_64BIT && TARGET_MIPS16"
3038   "and\t%0,%2"
3039   [(set_attr "type"     "darith")
3040    (set_attr "mode"     "DI")])
3041
3042 (define_expand "iorsi3"
3043   [(set (match_operand:SI 0 "register_operand" "=d,d")
3044         (ior:SI (match_operand:SI 1 "uns_arith_operand" "%d,d")
3045                 (match_operand:SI 2 "uns_arith_operand" "d,K")))]
3046   ""
3047 {
3048   if (TARGET_MIPS16)
3049     {
3050       operands[1] = force_reg (SImode, operands[1]);
3051       operands[2] = force_reg (SImode, operands[2]);
3052     }
3053 })
3054
3055 (define_insn ""
3056   [(set (match_operand:SI 0 "register_operand" "=d,d")
3057         (ior:SI (match_operand:SI 1 "uns_arith_operand" "%d,d")
3058                 (match_operand:SI 2 "uns_arith_operand" "d,K")))]
3059   "!TARGET_MIPS16"
3060   "@
3061    or\t%0,%1,%2
3062    ori\t%0,%1,%x2"
3063   [(set_attr "type"     "arith")
3064    (set_attr "mode"     "SI")])
3065
3066 (define_insn ""
3067   [(set (match_operand:SI 0 "register_operand" "=d")
3068         (ior:SI (match_operand:SI 1 "register_operand" "%0")
3069                 (match_operand:SI 2 "register_operand" "d")))]
3070   "TARGET_MIPS16"
3071   "or\t%0,%2"
3072   [(set_attr "type"     "arith")
3073    (set_attr "mode"     "SI")])
3074
3075 (define_expand "iordi3"
3076   [(set (match_operand:DI 0 "register_operand" "")
3077         (ior:DI (match_operand:DI 1 "register_operand" "")
3078                 (match_operand:DI 2 "uns_arith_operand" "")))]
3079   "TARGET_64BIT"
3080 {
3081   if (TARGET_MIPS16)
3082     {
3083       operands[1] = force_reg (DImode, operands[1]);
3084       operands[2] = force_reg (DImode, operands[2]);
3085     }
3086 })
3087
3088 (define_insn ""
3089   [(set (match_operand:DI 0 "register_operand" "=d,d")
3090         (ior:DI (match_operand:DI 1 "register_operand" "d,d")
3091                 (match_operand:DI 2 "uns_arith_operand" "d,K")))]
3092   "TARGET_64BIT && !TARGET_MIPS16"
3093   "@
3094    or\t%0,%1,%2
3095    ori\t%0,%1,%x2"
3096   [(set_attr "type"     "darith")
3097    (set_attr "mode"     "DI")])
3098
3099 (define_insn ""
3100   [(set (match_operand:DI 0 "register_operand" "=d")
3101         (ior:DI (match_operand:DI 1 "register_operand" "0")
3102                 (match_operand:DI 2 "register_operand" "d")))]
3103   "TARGET_64BIT && TARGET_MIPS16"
3104   "or\t%0,%2"
3105   [(set_attr "type"     "darith")
3106    (set_attr "mode"     "DI")])
3107
3108 (define_expand "xorsi3"
3109   [(set (match_operand:SI 0 "register_operand" "=d,d")
3110         (xor:SI (match_operand:SI 1 "uns_arith_operand" "%d,d")
3111                 (match_operand:SI 2 "uns_arith_operand" "d,K")))]
3112   ""
3113   "")
3114
3115 (define_insn ""
3116   [(set (match_operand:SI 0 "register_operand" "=d,d")
3117         (xor:SI (match_operand:SI 1 "uns_arith_operand" "%d,d")
3118                 (match_operand:SI 2 "uns_arith_operand" "d,K")))]
3119   "!TARGET_MIPS16"
3120   "@
3121    xor\t%0,%1,%2
3122    xori\t%0,%1,%x2"
3123   [(set_attr "type"     "arith")
3124    (set_attr "mode"     "SI")])
3125
3126 (define_insn ""
3127   [(set (match_operand:SI 0 "register_operand" "=d,t,t")
3128         (xor:SI (match_operand:SI 1 "uns_arith_operand" "%0,d,d")
3129                 (match_operand:SI 2 "uns_arith_operand" "d,K,d")))]
3130   "TARGET_MIPS16"
3131   "@
3132    xor\t%0,%2
3133    cmpi\t%1,%2
3134    cmp\t%1,%2"
3135   [(set_attr "type"     "arith")
3136    (set_attr "mode"     "SI")
3137    (set_attr_alternative "length"
3138                 [(const_int 4)
3139                  (if_then_else (match_operand:VOID 2 "m16_uimm8_1" "")
3140                                (const_int 4)
3141                                (const_int 8))
3142                  (const_int 4)])])
3143
3144 (define_expand "xordi3"
3145   [(set (match_operand:DI 0 "register_operand" "")
3146         (xor:DI (match_operand:DI 1 "register_operand" "")
3147                 (match_operand:DI 2 "uns_arith_operand" "")))]
3148   "TARGET_64BIT"
3149 {
3150   if (TARGET_MIPS16)
3151     {
3152       operands[1] = force_reg (DImode, operands[1]);
3153       operands[2] = force_reg (DImode, operands[2]);
3154     }
3155 })
3156
3157 (define_insn ""
3158   [(set (match_operand:DI 0 "register_operand" "=d,d")
3159         (xor:DI (match_operand:DI 1 "register_operand" "d,d")
3160                 (match_operand:DI 2 "uns_arith_operand" "d,K")))]
3161   "TARGET_64BIT && !TARGET_MIPS16"
3162   "@
3163    xor\t%0,%1,%2
3164    xori\t%0,%1,%x2"
3165   [(set_attr "type"     "darith")
3166    (set_attr "mode"     "DI")])
3167
3168 (define_insn ""
3169   [(set (match_operand:DI 0 "register_operand" "=d,t,t")
3170         (xor:DI (match_operand:DI 1 "register_operand" "%0,d,d")
3171                 (match_operand:DI 2 "uns_arith_operand" "d,K,d")))]
3172   "TARGET_64BIT && TARGET_MIPS16"
3173   "@
3174    xor\t%0,%2
3175    cmpi\t%1,%2
3176    cmp\t%1,%2"
3177   [(set_attr "type"     "arith")
3178    (set_attr "mode"     "DI")
3179    (set_attr_alternative "length"
3180                 [(const_int 4)
3181                  (if_then_else (match_operand:VOID 2 "m16_uimm8_1" "")
3182                                (const_int 4)
3183                                (const_int 8))
3184                  (const_int 4)])])
3185
3186 (define_insn "*norsi3"
3187   [(set (match_operand:SI 0 "register_operand" "=d")
3188         (and:SI (not:SI (match_operand:SI 1 "register_operand" "d"))
3189                 (not:SI (match_operand:SI 2 "register_operand" "d"))))]
3190   "!TARGET_MIPS16"
3191   "nor\t%0,%z1,%z2"
3192   [(set_attr "type"     "arith")
3193    (set_attr "mode"     "SI")])
3194
3195 (define_insn "*nordi3"
3196   [(set (match_operand:DI 0 "register_operand" "=d")
3197         (and:DI (not:DI (match_operand:DI 1 "register_operand" "d"))
3198                 (not:DI (match_operand:DI 2 "register_operand" "d"))))]
3199   "TARGET_64BIT && !TARGET_MIPS16"
3200   "nor\t%0,%z1,%z2"
3201   [(set_attr "type"     "darith")
3202    (set_attr "mode"     "DI")])
3203 \f
3204 ;;
3205 ;;  ....................
3206 ;;
3207 ;;      TRUNCATION
3208 ;;
3209 ;;  ....................
3210
3211
3212
3213 (define_insn "truncdfsf2"
3214   [(set (match_operand:SF 0 "register_operand" "=f")
3215         (float_truncate:SF (match_operand:DF 1 "register_operand" "f")))]
3216   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
3217   "cvt.s.d\t%0,%1"
3218   [(set_attr "type"     "fcvt")
3219    (set_attr "mode"     "SF")])
3220
3221 ;; Integer truncation patterns.  Truncating SImode values to smaller
3222 ;; modes is a no-op, as it is for most other GCC ports.  Truncating
3223 ;; DImode values to SImode is not a no-op for TARGET_64BIT since we
3224 ;; need to make sure that the lower 32 bits are properly sign-extended
3225 ;; (see TRULY_NOOP_TRUNCATION).  Truncating DImode values into modes
3226 ;; smaller than SImode is equivalent to two separate truncations:
3227 ;;
3228 ;;                        A       B
3229 ;;    DI ---> HI  ==  DI ---> SI ---> HI
3230 ;;    DI ---> QI  ==  DI ---> SI ---> QI
3231 ;;
3232 ;; Step A needs a real instruction but step B does not.
3233
3234 (define_insn "truncdisi2"
3235   [(set (match_operand:SI 0 "nonimmediate_operand" "=d,m")
3236         (truncate:SI (match_operand:DI 1 "register_operand" "d,d")))]
3237   "TARGET_64BIT"
3238   "@
3239     sll\t%0,%1,0
3240     sw\t%1,%0"
3241   [(set_attr "type" "darith,store")
3242    (set_attr "mode" "SI")
3243    (set_attr "extended_mips16" "yes,*")])
3244
3245 (define_insn "truncdihi2"
3246   [(set (match_operand:HI 0 "nonimmediate_operand" "=d,m")
3247         (truncate:HI (match_operand:DI 1 "register_operand" "d,d")))]
3248   "TARGET_64BIT"
3249   "@
3250     sll\t%0,%1,0
3251     sh\t%1,%0"
3252   [(set_attr "type" "darith,store")
3253    (set_attr "mode" "SI")
3254    (set_attr "extended_mips16" "yes,*")])
3255
3256 (define_insn "truncdiqi2"
3257   [(set (match_operand:QI 0 "nonimmediate_operand" "=d,m")
3258         (truncate:QI (match_operand:DI 1 "register_operand" "d,d")))]
3259   "TARGET_64BIT"
3260   "@
3261     sll\t%0,%1,0
3262     sb\t%1,%0"
3263   [(set_attr "type" "darith,store")
3264    (set_attr "mode" "SI")
3265    (set_attr "extended_mips16" "yes,*")])
3266
3267 ;; Combiner patterns to optimize shift/truncate combinations.
3268
3269 (define_insn ""
3270   [(set (match_operand:SI 0 "register_operand" "=d")
3271         (truncate:SI (ashiftrt:DI (match_operand:DI 1 "register_operand" "d")
3272                                   (match_operand:DI 2 "small_int" "I"))))]
3273   "TARGET_64BIT && !TARGET_MIPS16 && INTVAL (operands[2]) >= 32"
3274   "dsra\t%0,%1,%2"
3275   [(set_attr "type" "darith")
3276    (set_attr "mode" "SI")])
3277
3278 (define_insn ""
3279   [(set (match_operand:SI 0 "register_operand" "=d")
3280         (truncate:SI (lshiftrt:DI (match_operand:DI 1 "register_operand" "d")
3281                                   (const_int 32))))]
3282   "TARGET_64BIT && !TARGET_MIPS16"
3283   "dsra\t%0,%1,32"
3284   [(set_attr "type" "darith")
3285    (set_attr "mode" "SI")])
3286
3287
3288 ;; Combiner patterns for truncate/sign_extend combinations.  They use
3289 ;; the shift/truncate patterns above.
3290
3291 (define_insn_and_split ""
3292   [(set (match_operand:SI 0 "register_operand" "=d")
3293         (sign_extend:SI
3294             (truncate:HI (match_operand:DI 1 "register_operand" "d"))))]
3295   "TARGET_64BIT && !TARGET_MIPS16"
3296   "#"
3297   "&& reload_completed"
3298   [(set (match_dup 2)
3299         (ashift:DI (match_dup 1)
3300                    (const_int 48)))
3301    (set (match_dup 0)
3302         (truncate:SI (ashiftrt:DI (match_dup 2)
3303                                   (const_int 48))))]
3304   { operands[2] = gen_lowpart (DImode, operands[0]); })
3305
3306 (define_insn_and_split ""
3307   [(set (match_operand:SI 0 "register_operand" "=d")
3308         (sign_extend:SI
3309             (truncate:QI (match_operand:DI 1 "register_operand" "d"))))]
3310   "TARGET_64BIT && !TARGET_MIPS16"
3311   "#"
3312   "&& reload_completed"
3313   [(set (match_dup 2)
3314         (ashift:DI (match_dup 1)
3315                    (const_int 56)))
3316    (set (match_dup 0)
3317         (truncate:SI (ashiftrt:DI (match_dup 2)
3318                                   (const_int 56))))]
3319   { operands[2] = gen_lowpart (DImode, operands[0]); })
3320
3321
3322 ;; Combiner patterns to optimize truncate/zero_extend combinations.
3323
3324 (define_insn ""
3325   [(set (match_operand:SI 0 "register_operand" "=d")
3326         (zero_extend:SI (truncate:HI
3327                          (match_operand:DI 1 "register_operand" "d"))))]
3328   "TARGET_64BIT && !TARGET_MIPS16"
3329   "andi\t%0,%1,0xffff"
3330   [(set_attr "type"     "darith")
3331    (set_attr "mode"     "SI")])
3332
3333 (define_insn ""
3334   [(set (match_operand:SI 0 "register_operand" "=d")
3335         (zero_extend:SI (truncate:QI
3336                          (match_operand:DI 1 "register_operand" "d"))))]
3337   "TARGET_64BIT && !TARGET_MIPS16"
3338   "andi\t%0,%1,0xff"
3339   [(set_attr "type"     "darith")
3340    (set_attr "mode"     "SI")])
3341
3342 (define_insn ""
3343   [(set (match_operand:HI 0 "register_operand" "=d")
3344         (zero_extend:HI (truncate:QI
3345                          (match_operand:DI 1 "register_operand" "d"))))]
3346   "TARGET_64BIT && !TARGET_MIPS16"
3347   "andi\t%0,%1,0xff"
3348   [(set_attr "type"     "darith")
3349    (set_attr "mode"     "HI")])
3350 \f
3351 ;;
3352 ;;  ....................
3353 ;;
3354 ;;      ZERO EXTENSION
3355 ;;
3356 ;;  ....................
3357
3358 ;; Extension insns.
3359 ;; Those for integer source operand are ordered widest source type first.
3360
3361 (define_insn_and_split "zero_extendsidi2"
3362   [(set (match_operand:DI 0 "register_operand" "=d")
3363         (zero_extend:DI (match_operand:SI 1 "register_operand" "d")))]
3364   "TARGET_64BIT"
3365   "#"
3366   "&& reload_completed"
3367   [(set (match_dup 0)
3368         (ashift:DI (match_dup 1) (const_int 32)))
3369    (set (match_dup 0)
3370         (lshiftrt:DI (match_dup 0) (const_int 32)))]
3371   "operands[1] = gen_lowpart (DImode, operands[1]);"
3372   [(set_attr "type" "arith")
3373    (set_attr "mode" "DI")])
3374
3375 (define_insn "*zero_extendsidi2_mem"
3376   [(set (match_operand:DI 0 "register_operand" "=d")
3377         (zero_extend:DI (match_operand:SI 1 "memory_operand" "W")))]
3378   "TARGET_64BIT"
3379   "lwu\t%0,%1"
3380   [(set_attr "type"     "load")
3381    (set_attr "mode"     "DI")])
3382
3383 (define_expand "zero_extendhisi2"
3384   [(set (match_operand:SI 0 "register_operand" "")
3385         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
3386   ""
3387 {
3388   if (TARGET_MIPS16 && GET_CODE (operands[1]) != MEM)
3389     {
3390       rtx op = gen_lowpart (SImode, operands[1]);
3391       rtx temp = force_reg (SImode, GEN_INT (0xffff));
3392
3393       emit_insn (gen_andsi3 (operands[0], op, temp));
3394       DONE;
3395     }
3396 })
3397
3398 (define_insn ""
3399   [(set (match_operand:SI 0 "register_operand" "=d,d")
3400         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "d,m")))]
3401   "!TARGET_MIPS16"
3402   "@
3403    andi\t%0,%1,0xffff
3404    lhu\t%0,%1"
3405   [(set_attr "type"     "arith,load")
3406    (set_attr "mode"     "SI")
3407    (set_attr "length"   "4,*")])
3408
3409 (define_insn ""
3410   [(set (match_operand:SI 0 "register_operand" "=d")
3411         (zero_extend:SI (match_operand:HI 1 "memory_operand" "m")))]
3412   "TARGET_MIPS16"
3413   "lhu\t%0,%1"
3414   [(set_attr "type"     "load")
3415    (set_attr "mode"     "SI")])
3416
3417 (define_expand "zero_extendhidi2"
3418   [(set (match_operand:DI 0 "register_operand" "")
3419         (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "")))]
3420   "TARGET_64BIT"
3421 {
3422   if (TARGET_MIPS16 && GET_CODE (operands[1]) != MEM)
3423     {
3424       rtx op = gen_lowpart (DImode, operands[1]);
3425       rtx temp = force_reg (DImode, GEN_INT (0xffff));
3426
3427       emit_insn (gen_anddi3 (operands[0], op, temp));
3428       DONE;
3429     }
3430 })
3431
3432 (define_insn ""
3433   [(set (match_operand:DI 0 "register_operand" "=d,d")
3434         (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "d,m")))]
3435   "TARGET_64BIT && !TARGET_MIPS16"
3436   "@
3437    andi\t%0,%1,0xffff
3438    lhu\t%0,%1"
3439   [(set_attr "type"     "arith,load")
3440    (set_attr "mode"     "DI")
3441    (set_attr "length"   "4,*")])
3442
3443 (define_insn ""
3444   [(set (match_operand:DI 0 "register_operand" "=d")
3445         (zero_extend:DI (match_operand:HI 1 "memory_operand" "m")))]
3446   "TARGET_64BIT && TARGET_MIPS16"
3447   "lhu\t%0,%1"
3448   [(set_attr "type"     "load")
3449    (set_attr "mode"     "DI")])
3450
3451 (define_expand "zero_extendqihi2"
3452   [(set (match_operand:HI 0 "register_operand" "")
3453         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))]
3454   ""
3455 {
3456   if (TARGET_MIPS16 && GET_CODE (operands[1]) != MEM)
3457     {
3458       rtx op0 = gen_lowpart (SImode, operands[0]);
3459       rtx op1 = gen_lowpart (SImode, operands[1]);
3460       rtx temp = force_reg (SImode, GEN_INT (0xff));
3461
3462       emit_insn (gen_andsi3 (op0, op1, temp));
3463       DONE;
3464     }
3465 })
3466
3467 (define_insn ""
3468   [(set (match_operand:HI 0 "register_operand" "=d,d")
3469         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "d,m")))]
3470   "!TARGET_MIPS16"
3471   "@
3472    andi\t%0,%1,0x00ff
3473    lbu\t%0,%1"
3474   [(set_attr "type"     "arith,load")
3475    (set_attr "mode"     "HI")
3476    (set_attr "length"   "4,*")])
3477
3478 (define_insn ""
3479   [(set (match_operand:HI 0 "register_operand" "=d")
3480         (zero_extend:HI (match_operand:QI 1 "memory_operand" "m")))]
3481   "TARGET_MIPS16"
3482   "lbu\t%0,%1"
3483   [(set_attr "type"     "load")
3484    (set_attr "mode"     "HI")])
3485
3486 (define_expand "zero_extendqisi2"
3487   [(set (match_operand:SI 0 "register_operand" "")
3488         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))]
3489   ""
3490 {
3491   if (TARGET_MIPS16 && GET_CODE (operands[1]) != MEM)
3492     {
3493       rtx op = gen_lowpart (SImode, operands[1]);
3494       rtx temp = force_reg (SImode, GEN_INT (0xff));
3495
3496       emit_insn (gen_andsi3 (operands[0], op, temp));
3497       DONE;
3498     }
3499 })
3500
3501 (define_insn ""
3502   [(set (match_operand:SI 0 "register_operand" "=d,d")
3503         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "d,m")))]
3504   "!TARGET_MIPS16"
3505   "@
3506    andi\t%0,%1,0x00ff
3507    lbu\t%0,%1"
3508   [(set_attr "type"     "arith,load")
3509    (set_attr "mode"     "SI")
3510    (set_attr "length"   "4,*")])
3511
3512 (define_insn ""
3513   [(set (match_operand:SI 0 "register_operand" "=d")
3514         (zero_extend:SI (match_operand:QI 1 "memory_operand" "m")))]
3515   "TARGET_MIPS16"
3516   "lbu\t%0,%1"
3517   [(set_attr "type"     "load")
3518    (set_attr "mode"     "SI")])
3519
3520 (define_expand "zero_extendqidi2"
3521   [(set (match_operand:DI 0 "register_operand" "")
3522         (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "")))]
3523   "TARGET_64BIT"
3524 {
3525   if (TARGET_MIPS16 && GET_CODE (operands[1]) != MEM)
3526     {
3527       rtx op = gen_lowpart (DImode, operands[1]);
3528       rtx temp = force_reg (DImode, GEN_INT (0xff));
3529
3530       emit_insn (gen_anddi3 (operands[0], op, temp));
3531       DONE;
3532     }
3533 })
3534
3535 (define_insn ""
3536   [(set (match_operand:DI 0 "register_operand" "=d,d")
3537         (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "d,m")))]
3538   "TARGET_64BIT && !TARGET_MIPS16"
3539   "@
3540    andi\t%0,%1,0x00ff
3541    lbu\t%0,%1"
3542   [(set_attr "type"     "arith,load")
3543    (set_attr "mode"     "DI")
3544    (set_attr "length"   "4,*")])
3545
3546 (define_insn ""
3547   [(set (match_operand:DI 0 "register_operand" "=d")
3548         (zero_extend:DI (match_operand:QI 1 "memory_operand" "m")))]
3549   "TARGET_64BIT && TARGET_MIPS16"
3550   "lbu\t%0,%1"
3551   [(set_attr "type"     "load")
3552    (set_attr "mode"     "DI")])
3553 \f
3554 ;;
3555 ;;  ....................
3556 ;;
3557 ;;      SIGN EXTENSION
3558 ;;
3559 ;;  ....................
3560
3561 ;; Extension insns.
3562 ;; Those for integer source operand are ordered widest source type first.
3563
3564 (define_insn "extendsidi2"
3565   [(set (match_operand:DI 0 "register_operand" "=d,d")
3566         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,m")))]
3567   "TARGET_64BIT"
3568   "@
3569    sll\t%0,%1,0
3570    lw\t%0,%1"
3571   [(set_attr "type" "arith,load")
3572    (set_attr "mode" "DI")
3573    (set_attr "extended_mips16" "yes,*")])
3574
3575 ;; These patterns originally accepted general_operands, however, slightly
3576 ;; better code is generated by only accepting register_operands, and then
3577 ;; letting combine generate the lh and lb insns.
3578
3579 ;; These expanders originally put values in registers first. We split
3580 ;; all non-mem patterns after reload.
3581
3582 (define_expand "extendhidi2"
3583   [(set (match_operand:DI 0 "register_operand" "")
3584         (sign_extend:DI (match_operand:HI 1 "nonimmediate_operand" "")))]
3585   "TARGET_64BIT"
3586   "")
3587
3588 (define_insn "*extendhidi2"
3589   [(set (match_operand:DI 0 "register_operand" "=d")
3590         (sign_extend:DI (match_operand:HI 1 "register_operand" "d")))]
3591   "TARGET_64BIT"
3592   "#")
3593
3594 (define_split
3595   [(set (match_operand:DI 0 "register_operand" "")
3596         (sign_extend:DI (match_operand:HI 1 "register_operand" "")))]
3597   "TARGET_64BIT && reload_completed"
3598   [(set (match_dup 0)
3599         (ashift:DI (match_dup 1) (const_int 48)))
3600    (set (match_dup 0)
3601         (ashiftrt:DI (match_dup 0) (const_int 48)))]
3602   "operands[1] = gen_lowpart (DImode, operands[1]);")
3603
3604 (define_insn "*extendhidi2_mem"
3605   [(set (match_operand:DI 0 "register_operand" "=d")
3606         (sign_extend:DI (match_operand:HI 1 "memory_operand" "m")))]
3607   "TARGET_64BIT"
3608   "lh\t%0,%1"
3609   [(set_attr "type"     "load")
3610    (set_attr "mode"     "DI")])
3611
3612 (define_expand "extendhisi2"
3613   [(set (match_operand:SI 0 "register_operand" "")
3614         (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
3615   ""
3616 {
3617   if (ISA_HAS_SEB_SEH)
3618     {
3619       emit_insn (gen_extendhisi2_hw (operands[0],
3620                                      force_reg (HImode, operands[1])));
3621       DONE;
3622     }
3623 })
3624
3625 (define_insn "*extendhisi2"
3626   [(set (match_operand:SI 0 "register_operand" "=d")
3627         (sign_extend:SI (match_operand:HI 1 "register_operand" "d")))]
3628   ""
3629   "#")
3630
3631 (define_split
3632   [(set (match_operand:SI 0 "register_operand" "")
3633         (sign_extend:SI (match_operand:HI 1 "register_operand" "")))]
3634   "reload_completed"
3635   [(set (match_dup 0)
3636         (ashift:SI (match_dup 1) (const_int 16)))
3637    (set (match_dup 0)
3638         (ashiftrt:SI (match_dup 0) (const_int 16)))]
3639   "operands[1] = gen_lowpart (SImode, operands[1]);")
3640
3641 (define_insn "extendhisi2_mem"
3642   [(set (match_operand:SI 0 "register_operand" "=d")
3643         (sign_extend:SI (match_operand:HI 1 "memory_operand" "m")))]
3644   ""
3645   "lh\t%0,%1"
3646   [(set_attr "type"     "load")
3647    (set_attr "mode"     "SI")])
3648
3649 (define_insn "extendhisi2_hw"
3650   [(set (match_operand:SI 0 "register_operand" "=r")
3651         (sign_extend:SI (match_operand:HI 1 "register_operand" "r")))]
3652   "ISA_HAS_SEB_SEH"
3653   "seh\t%0,%1"
3654   [(set_attr "type" "arith")
3655    (set_attr "mode" "SI")])
3656
3657 (define_expand "extendqihi2"
3658   [(set (match_operand:HI 0 "register_operand" "")
3659         (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))]
3660   ""
3661   "")
3662
3663 (define_insn "*extendqihi2"
3664   [(set (match_operand:HI 0 "register_operand" "=d")
3665         (sign_extend:HI (match_operand:QI 1 "register_operand" "d")))]
3666   ""
3667   "#")
3668
3669 (define_split
3670   [(set (match_operand:HI 0 "register_operand" "")
3671         (sign_extend:HI (match_operand:QI 1 "register_operand" "")))]
3672   "reload_completed"
3673   [(set (match_dup 0)
3674         (ashift:SI (match_dup 1) (const_int 24)))
3675    (set (match_dup 0)
3676         (ashiftrt:SI (match_dup 0) (const_int 24)))]
3677   "operands[0] = gen_lowpart (SImode, operands[0]);
3678    operands[1] = gen_lowpart (SImode, operands[1]);")
3679
3680 (define_insn "*extendqihi2_internal_mem"
3681   [(set (match_operand:HI 0 "register_operand" "=d")
3682         (sign_extend:HI (match_operand:QI 1 "memory_operand" "m")))]
3683   ""
3684   "lb\t%0,%1"
3685   [(set_attr "type"     "load")
3686    (set_attr "mode"     "SI")])
3687
3688
3689 (define_expand "extendqisi2"
3690   [(set (match_operand:SI 0 "register_operand" "")
3691         (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))]
3692   ""
3693 {
3694   if (ISA_HAS_SEB_SEH)
3695     {
3696       emit_insn (gen_extendqisi2_hw (operands[0],
3697                                      force_reg (QImode, operands[1])));
3698       DONE;
3699     }
3700 })
3701
3702 (define_insn "*extendqisi2"
3703   [(set (match_operand:SI 0 "register_operand" "=d")
3704         (sign_extend:SI (match_operand:QI 1 "register_operand" "d")))]
3705   ""
3706   "#")
3707
3708 (define_split
3709   [(set (match_operand:SI 0 "register_operand" "")
3710         (sign_extend:SI (match_operand:QI 1 "register_operand" "")))]
3711   "reload_completed"
3712   [(set (match_dup 0)
3713         (ashift:SI (match_dup 1) (const_int 24)))
3714    (set (match_dup 0)
3715         (ashiftrt:SI (match_dup 0) (const_int 24)))]
3716   "operands[1] = gen_lowpart (SImode, operands[1]);")
3717
3718 (define_insn "*extendqisi2_mem"
3719   [(set (match_operand:SI 0 "register_operand" "=d")
3720         (sign_extend:SI (match_operand:QI 1 "memory_operand" "m")))]
3721   ""
3722   "lb\t%0,%1"
3723   [(set_attr "type"     "load")
3724    (set_attr "mode"     "SI")])
3725
3726 (define_insn "extendqisi2_hw"
3727   [(set (match_operand:SI 0 "register_operand" "=r")
3728         (sign_extend:SI (match_operand:QI 1 "register_operand" "r")))]
3729   "ISA_HAS_SEB_SEH"
3730   "seb\t%0,%1"
3731   [(set_attr "type" "arith")
3732    (set_attr "mode" "SI")])
3733
3734 (define_expand "extendqidi2"
3735   [(set (match_operand:DI 0 "register_operand" "")
3736         (sign_extend:DI (match_operand:QI 1 "nonimmediate_operand" "")))]
3737   "TARGET_64BIT"
3738   "")
3739
3740 (define_insn "*extendqidi2"
3741   [(set (match_operand:DI 0 "register_operand" "=d")
3742         (sign_extend:DI (match_operand:QI 1 "register_operand" "d")))]
3743   "TARGET_64BIT"
3744   "#")
3745
3746 (define_split
3747   [(set (match_operand:DI 0 "register_operand" "")
3748         (sign_extend:DI (match_operand:QI 1 "register_operand" "")))]
3749   "TARGET_64BIT && reload_completed"
3750   [(set (match_dup 0)
3751         (ashift:DI (match_dup 1) (const_int 56)))
3752    (set (match_dup 0)
3753         (ashiftrt:DI (match_dup 0) (const_int 56)))]
3754   "operands[1] = gen_lowpart (DImode, operands[1]);")
3755
3756 (define_insn "*extendqidi2_mem"
3757   [(set (match_operand:DI 0 "register_operand" "=d")
3758         (sign_extend:DI (match_operand:QI 1 "memory_operand" "m")))]
3759   "TARGET_64BIT"
3760   "lb\t%0,%1"
3761   [(set_attr "type"     "load")
3762    (set_attr "mode"     "DI")])
3763
3764 (define_insn "extendsfdf2"
3765   [(set (match_operand:DF 0 "register_operand" "=f")
3766         (float_extend:DF (match_operand:SF 1 "register_operand" "f")))]
3767   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
3768   "cvt.d.s\t%0,%1"
3769   [(set_attr "type"     "fcvt")
3770    (set_attr "mode"     "DF")])
3771 \f
3772 ;;
3773 ;;  ....................
3774 ;;
3775 ;;      CONVERSIONS
3776 ;;
3777 ;;  ....................
3778
3779 (define_expand "fix_truncdfsi2"
3780   [(set (match_operand:SI 0 "register_operand" "=f")
3781         (fix:SI (match_operand:DF 1 "register_operand" "f")))]
3782   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
3783 {
3784   if (!ISA_HAS_TRUNC_W)
3785     {
3786       emit_insn (gen_fix_truncdfsi2_macro (operands[0], operands[1]));
3787       DONE;
3788     }
3789 })
3790
3791 (define_insn "fix_truncdfsi2_insn"
3792   [(set (match_operand:SI 0 "register_operand" "=f")
3793         (fix:SI (match_operand:DF 1 "register_operand" "f")))]
3794   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && ISA_HAS_TRUNC_W"
3795   "trunc.w.d %0,%1"
3796   [(set_attr "type"     "fcvt")
3797    (set_attr "mode"     "DF")
3798    (set_attr "length"   "4")])
3799
3800 (define_insn "fix_truncdfsi2_macro"
3801   [(set (match_operand:SI 0 "register_operand" "=f")
3802         (fix:SI (match_operand:DF 1 "register_operand" "f")))
3803    (clobber (match_scratch:DF 2 "=d"))]
3804   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !ISA_HAS_TRUNC_W"
3805 {
3806   if (set_nomacro)
3807     return ".set\tmacro\;trunc.w.d %0,%1,%2\;.set\tnomacro";
3808   else
3809     return "trunc.w.d %0,%1,%2";
3810 }
3811   [(set_attr "type"     "fcvt")
3812    (set_attr "mode"     "DF")
3813    (set_attr "length"   "36")])
3814
3815 (define_expand "fix_truncsfsi2"
3816   [(set (match_operand:SI 0 "register_operand" "=f")
3817         (fix:SI (match_operand:SF 1 "register_operand" "f")))]
3818   "TARGET_HARD_FLOAT"
3819 {
3820   if (!ISA_HAS_TRUNC_W)
3821     {
3822       emit_insn (gen_fix_truncsfsi2_macro (operands[0], operands[1]));
3823       DONE;
3824     }
3825 })
3826
3827 (define_insn "fix_truncsfsi2_insn"
3828   [(set (match_operand:SI 0 "register_operand" "=f")
3829         (fix:SI (match_operand:SF 1 "register_operand" "f")))]
3830   "TARGET_HARD_FLOAT && ISA_HAS_TRUNC_W"
3831   "trunc.w.s %0,%1"
3832   [(set_attr "type"     "fcvt")
3833    (set_attr "mode"     "DF")
3834    (set_attr "length"   "4")])
3835
3836 (define_insn "fix_truncsfsi2_macro"
3837   [(set (match_operand:SI 0 "register_operand" "=f")
3838         (fix:SI (match_operand:SF 1 "register_operand" "f")))
3839    (clobber (match_scratch:SF 2 "=d"))]
3840   "TARGET_HARD_FLOAT && !ISA_HAS_TRUNC_W"
3841 {
3842   if (set_nomacro)
3843     return ".set\tmacro\;trunc.w.s %0,%1,%2\;.set\tnomacro";
3844   else
3845     return "trunc.w.s %0,%1,%2";
3846 }
3847   [(set_attr "type"     "fcvt")
3848    (set_attr "mode"     "DF")
3849    (set_attr "length"   "36")])
3850
3851
3852 (define_insn "fix_truncdfdi2"
3853   [(set (match_operand:DI 0 "register_operand" "=f")
3854         (fix:DI (match_operand:DF 1 "register_operand" "f")))]
3855   "TARGET_HARD_FLOAT && TARGET_FLOAT64 && TARGET_DOUBLE_FLOAT"
3856   "trunc.l.d %0,%1"
3857   [(set_attr "type"     "fcvt")
3858    (set_attr "mode"     "DF")
3859    (set_attr "length"   "4")])
3860
3861
3862 (define_insn "fix_truncsfdi2"
3863   [(set (match_operand:DI 0 "register_operand" "=f")
3864         (fix:DI (match_operand:SF 1 "register_operand" "f")))]
3865   "TARGET_HARD_FLOAT && TARGET_FLOAT64 && TARGET_DOUBLE_FLOAT"
3866   "trunc.l.s %0,%1"
3867   [(set_attr "type"     "fcvt")
3868    (set_attr "mode"     "SF")
3869    (set_attr "length"   "4")])
3870
3871
3872 (define_insn "floatsidf2"
3873   [(set (match_operand:DF 0 "register_operand" "=f")
3874         (float:DF (match_operand:SI 1 "register_operand" "f")))]
3875   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
3876   "cvt.d.w\t%0,%1"
3877   [(set_attr "type"     "fcvt")
3878    (set_attr "mode"     "DF")
3879    (set_attr "length"   "4")])
3880
3881
3882 (define_insn "floatdidf2"
3883   [(set (match_operand:DF 0 "register_operand" "=f")
3884         (float:DF (match_operand:DI 1 "register_operand" "f")))]
3885   "TARGET_HARD_FLOAT && TARGET_FLOAT64 && TARGET_DOUBLE_FLOAT"
3886   "cvt.d.l\t%0,%1"
3887   [(set_attr "type"     "fcvt")
3888    (set_attr "mode"     "DF")
3889    (set_attr "length"   "4")])
3890
3891
3892 (define_insn "floatsisf2"
3893   [(set (match_operand:SF 0 "register_operand" "=f")
3894         (float:SF (match_operand:SI 1 "register_operand" "f")))]
3895   "TARGET_HARD_FLOAT"
3896   "cvt.s.w\t%0,%1"
3897   [(set_attr "type"     "fcvt")
3898    (set_attr "mode"     "SF")
3899    (set_attr "length"   "4")])
3900
3901
3902 (define_insn "floatdisf2"
3903   [(set (match_operand:SF 0 "register_operand" "=f")
3904         (float:SF (match_operand:DI 1 "register_operand" "f")))]
3905   "TARGET_HARD_FLOAT && TARGET_FLOAT64 && TARGET_DOUBLE_FLOAT"
3906   "cvt.s.l\t%0,%1"
3907   [(set_attr "type"     "fcvt")
3908    (set_attr "mode"     "SF")
3909    (set_attr "length"   "4")])
3910
3911
3912 (define_expand "fixuns_truncdfsi2"
3913   [(set (match_operand:SI 0 "register_operand" "")
3914         (unsigned_fix:SI (match_operand:DF 1 "register_operand" "")))]
3915   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
3916 {
3917   rtx reg1 = gen_reg_rtx (DFmode);
3918   rtx reg2 = gen_reg_rtx (DFmode);
3919   rtx reg3 = gen_reg_rtx (SImode);
3920   rtx label1 = gen_label_rtx ();
3921   rtx label2 = gen_label_rtx ();
3922   REAL_VALUE_TYPE offset;
3923
3924   real_2expN (&offset, 31);
3925
3926   if (reg1)                     /* Turn off complaints about unreached code.  */
3927     {
3928       emit_move_insn (reg1, CONST_DOUBLE_FROM_REAL_VALUE (offset, DFmode));
3929       do_pending_stack_adjust ();
3930
3931       emit_insn (gen_cmpdf (operands[1], reg1));
3932       emit_jump_insn (gen_bge (label1));
3933
3934       emit_insn (gen_fix_truncdfsi2 (operands[0], operands[1]));
3935       emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx,
3936                                    gen_rtx_LABEL_REF (VOIDmode, label2)));
3937       emit_barrier ();
3938
3939       emit_label (label1);
3940       emit_move_insn (reg2, gen_rtx_MINUS (DFmode, operands[1], reg1));
3941       emit_move_insn (reg3, GEN_INT (trunc_int_for_mode
3942                                      (BITMASK_HIGH, SImode)));
3943
3944       emit_insn (gen_fix_truncdfsi2 (operands[0], reg2));
3945       emit_insn (gen_iorsi3 (operands[0], operands[0], reg3));
3946
3947       emit_label (label2);
3948
3949       /* Allow REG_NOTES to be set on last insn (labels don't have enough
3950          fields, and can't be used for REG_NOTES anyway).  */
3951       emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
3952       DONE;
3953     }
3954 })
3955
3956
3957 (define_expand "fixuns_truncdfdi2"
3958   [(set (match_operand:DI 0 "register_operand" "")
3959         (unsigned_fix:DI (match_operand:DF 1 "register_operand" "")))]
3960   "TARGET_HARD_FLOAT && TARGET_64BIT && TARGET_DOUBLE_FLOAT"
3961 {
3962   rtx reg1 = gen_reg_rtx (DFmode);
3963   rtx reg2 = gen_reg_rtx (DFmode);
3964   rtx reg3 = gen_reg_rtx (DImode);
3965   rtx label1 = gen_label_rtx ();
3966   rtx label2 = gen_label_rtx ();
3967   REAL_VALUE_TYPE offset;
3968
3969   real_2expN (&offset, 63);
3970
3971   emit_move_insn (reg1, CONST_DOUBLE_FROM_REAL_VALUE (offset, DFmode));
3972   do_pending_stack_adjust ();
3973
3974   emit_insn (gen_cmpdf (operands[1], reg1));
3975   emit_jump_insn (gen_bge (label1));
3976
3977   emit_insn (gen_fix_truncdfdi2 (operands[0], operands[1]));
3978   emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx,
3979                                gen_rtx_LABEL_REF (VOIDmode, label2)));
3980   emit_barrier ();
3981
3982   emit_label (label1);
3983   emit_move_insn (reg2, gen_rtx_MINUS (DFmode, operands[1], reg1));
3984   emit_move_insn (reg3, GEN_INT (BITMASK_HIGH));
3985   emit_insn (gen_ashldi3 (reg3, reg3, GEN_INT (32)));
3986
3987   emit_insn (gen_fix_truncdfdi2 (operands[0], reg2));
3988   emit_insn (gen_iordi3 (operands[0], operands[0], reg3));
3989
3990   emit_label (label2);
3991
3992   /* Allow REG_NOTES to be set on last insn (labels don't have enough
3993      fields, and can't be used for REG_NOTES anyway).  */
3994   emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
3995   DONE;
3996 })
3997
3998
3999 (define_expand "fixuns_truncsfsi2"
4000   [(set (match_operand:SI 0 "register_operand" "")
4001         (unsigned_fix:SI (match_operand:SF 1 "register_operand" "")))]
4002   "TARGET_HARD_FLOAT"
4003 {
4004   rtx reg1 = gen_reg_rtx (SFmode);
4005   rtx reg2 = gen_reg_rtx (SFmode);
4006   rtx reg3 = gen_reg_rtx (SImode);
4007   rtx label1 = gen_label_rtx ();
4008   rtx label2 = gen_label_rtx ();
4009   REAL_VALUE_TYPE offset;
4010
4011   real_2expN (&offset, 31);
4012
4013   emit_move_insn (reg1, CONST_DOUBLE_FROM_REAL_VALUE (offset, SFmode));
4014   do_pending_stack_adjust ();
4015
4016   emit_insn (gen_cmpsf (operands[1], reg1));
4017   emit_jump_insn (gen_bge (label1));
4018
4019   emit_insn (gen_fix_truncsfsi2 (operands[0], operands[1]));
4020   emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx,
4021                                gen_rtx_LABEL_REF (VOIDmode, label2)));
4022   emit_barrier ();
4023
4024   emit_label (label1);
4025   emit_move_insn (reg2, gen_rtx_MINUS (SFmode, operands[1], reg1));
4026   emit_move_insn (reg3, GEN_INT (trunc_int_for_mode
4027                                  (BITMASK_HIGH, SImode)));
4028
4029   emit_insn (gen_fix_truncsfsi2 (operands[0], reg2));
4030   emit_insn (gen_iorsi3 (operands[0], operands[0], reg3));
4031
4032   emit_label (label2);
4033
4034   /* Allow REG_NOTES to be set on last insn (labels don't have enough
4035      fields, and can't be used for REG_NOTES anyway).  */
4036   emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
4037   DONE;
4038 })
4039
4040
4041 (define_expand "fixuns_truncsfdi2"
4042   [(set (match_operand:DI 0 "register_operand" "")
4043         (unsigned_fix:DI (match_operand:SF 1 "register_operand" "")))]
4044   "TARGET_HARD_FLOAT && TARGET_64BIT && TARGET_DOUBLE_FLOAT"
4045 {
4046   rtx reg1 = gen_reg_rtx (SFmode);
4047   rtx reg2 = gen_reg_rtx (SFmode);
4048   rtx reg3 = gen_reg_rtx (DImode);
4049   rtx label1 = gen_label_rtx ();
4050   rtx label2 = gen_label_rtx ();
4051   REAL_VALUE_TYPE offset;
4052
4053   real_2expN (&offset, 63);
4054
4055   emit_move_insn (reg1, CONST_DOUBLE_FROM_REAL_VALUE (offset, SFmode));
4056   do_pending_stack_adjust ();
4057
4058   emit_insn (gen_cmpsf (operands[1], reg1));
4059   emit_jump_insn (gen_bge (label1));
4060
4061   emit_insn (gen_fix_truncsfdi2 (operands[0], operands[1]));
4062   emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx,
4063                                gen_rtx_LABEL_REF (VOIDmode, label2)));
4064   emit_barrier ();
4065
4066   emit_label (label1);
4067   emit_move_insn (reg2, gen_rtx_MINUS (SFmode, operands[1], reg1));
4068   emit_move_insn (reg3, GEN_INT (BITMASK_HIGH));
4069   emit_insn (gen_ashldi3 (reg3, reg3, GEN_INT (32)));
4070
4071   emit_insn (gen_fix_truncsfdi2 (operands[0], reg2));
4072   emit_insn (gen_iordi3 (operands[0], operands[0], reg3));
4073
4074   emit_label (label2);
4075
4076   /* Allow REG_NOTES to be set on last insn (labels don't have enough
4077      fields, and can't be used for REG_NOTES anyway).  */
4078   emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
4079   DONE;
4080 })
4081 \f
4082 ;;
4083 ;;  ....................
4084 ;;
4085 ;;      DATA MOVEMENT
4086 ;;
4087 ;;  ....................
4088
4089 ;; Bit field extract patterns which use lwl/lwr or ldl/ldr.
4090
4091 (define_expand "extv"
4092   [(set (match_operand 0 "register_operand" "")
4093         (sign_extract (match_operand:QI 1 "memory_operand" "")
4094                       (match_operand 2 "immediate_operand" "")
4095                       (match_operand 3 "immediate_operand" "")))]
4096   "!TARGET_MIPS16"
4097 {
4098   if (mips_expand_unaligned_load (operands[0], operands[1],
4099                                   INTVAL (operands[2]),
4100                                   INTVAL (operands[3])))
4101     DONE;
4102   else
4103     FAIL;
4104 })
4105
4106 (define_expand "extzv"
4107   [(set (match_operand 0 "register_operand" "")
4108         (zero_extract (match_operand:QI 1 "memory_operand" "")
4109                       (match_operand 2 "immediate_operand" "")
4110                       (match_operand 3 "immediate_operand" "")))]
4111   "!TARGET_MIPS16"
4112 {
4113   if (mips_expand_unaligned_load (operands[0], operands[1],
4114                                   INTVAL (operands[2]),
4115                                   INTVAL (operands[3])))
4116     DONE;
4117   else
4118     FAIL;
4119 })
4120
4121 (define_expand "insv"
4122   [(set (zero_extract (match_operand:QI 0 "memory_operand" "")
4123                       (match_operand 1 "immediate_operand" "")
4124                       (match_operand 2 "immediate_operand" ""))
4125         (match_operand 3 "reg_or_0_operand" ""))]
4126   "!TARGET_MIPS16"
4127 {
4128   if (mips_expand_unaligned_store (operands[0], operands[3],
4129                                    INTVAL (operands[1]),
4130                                    INTVAL (operands[2])))
4131     DONE;
4132   else
4133     FAIL;
4134 })
4135
4136 ;; Unaligned word moves generated by the bit field patterns.
4137 ;;
4138 ;; As far as the rtl is concerned, both the left-part and right-part
4139 ;; instructions can access the whole field.  However, the real operand
4140 ;; refers to just the first or the last byte (depending on endianness).
4141 ;; We therefore use two memory operands to each instruction, one to
4142 ;; describe the rtl effect and one to use in the assembly output.
4143 ;;
4144 ;; Operands 0 and 1 are the rtl-level target and source respectively.
4145 ;; This allows us to use the standard length calculations for the "load"
4146 ;; and "store" type attributes.
4147
4148 (define_insn "mov_lwl"
4149   [(set (match_operand:SI 0 "register_operand" "=d")
4150         (unspec:SI [(match_operand:BLK 1 "memory_operand" "m")
4151                     (match_operand:QI 2 "memory_operand" "m")]
4152                    UNSPEC_LWL))]
4153   "!TARGET_MIPS16"
4154   "lwl\t%0,%2"
4155   [(set_attr "type" "load")
4156    (set_attr "mode" "SI")
4157    (set_attr "hazard" "none")])
4158
4159 (define_insn "mov_lwr"
4160   [(set (match_operand:SI 0 "register_operand" "=d")
4161         (unspec:SI [(match_operand:BLK 1 "memory_operand" "m")
4162                     (match_operand:QI 2 "memory_operand" "m")
4163                     (match_operand:SI 3 "register_operand" "0")]
4164                    UNSPEC_LWR))]
4165   "!TARGET_MIPS16"
4166   "lwr\t%0,%2"
4167   [(set_attr "type" "load")
4168    (set_attr "mode" "SI")])
4169
4170
4171 (define_insn "mov_swl"
4172   [(set (match_operand:BLK 0 "memory_operand" "=m")
4173         (unspec:BLK [(match_operand:SI 1 "reg_or_0_operand" "dJ")
4174                      (match_operand:QI 2 "memory_operand" "m")]
4175                     UNSPEC_SWL))]
4176   "!TARGET_MIPS16"
4177   "swl\t%z1,%2"
4178   [(set_attr "type" "store")
4179    (set_attr "mode" "SI")])
4180
4181 (define_insn "mov_swr"
4182   [(set (match_operand:BLK 0 "memory_operand" "+m")
4183         (unspec:BLK [(match_operand:SI 1 "reg_or_0_operand" "dJ")
4184                      (match_operand:QI 2 "memory_operand" "m")
4185                      (match_dup 0)]
4186                     UNSPEC_SWR))]
4187   "!TARGET_MIPS16"
4188   "swr\t%z1,%2"
4189   [(set_attr "type" "store")
4190    (set_attr "mode" "SI")])
4191
4192
4193 (define_insn "mov_ldl"
4194   [(set (match_operand:DI 0 "register_operand" "=d")
4195         (unspec:DI [(match_operand:BLK 1 "memory_operand" "m")
4196                     (match_operand:QI 2 "memory_operand" "m")]
4197                    UNSPEC_LDL))]
4198   "TARGET_64BIT && !TARGET_MIPS16"
4199   "ldl\t%0,%2"
4200   [(set_attr "type" "load")
4201    (set_attr "mode" "DI")])
4202
4203 (define_insn "mov_ldr"
4204   [(set (match_operand:DI 0 "register_operand" "=d")
4205         (unspec:DI [(match_operand:BLK 1 "memory_operand" "m")
4206                     (match_operand:QI 2 "memory_operand" "m")
4207                     (match_operand:DI 3 "register_operand" "0")]
4208                    UNSPEC_LDR))]
4209   "TARGET_64BIT && !TARGET_MIPS16"
4210   "ldr\t%0,%2"
4211   [(set_attr "type" "load")
4212    (set_attr "mode" "DI")])
4213
4214
4215 (define_insn "mov_sdl"
4216   [(set (match_operand:BLK 0 "memory_operand" "=m")
4217         (unspec:BLK [(match_operand:DI 1 "reg_or_0_operand" "dJ")
4218                      (match_operand:QI 2 "memory_operand" "m")]
4219                     UNSPEC_SDL))]
4220   "TARGET_64BIT && !TARGET_MIPS16"
4221   "sdl\t%z1,%2"
4222   [(set_attr "type" "store")
4223    (set_attr "mode" "DI")])
4224
4225 (define_insn "mov_sdr"
4226   [(set (match_operand:BLK 0 "memory_operand" "+m")
4227         (unspec:BLK [(match_operand:DI 1 "reg_or_0_operand" "dJ")
4228                      (match_operand:QI 2 "memory_operand" "m")
4229                      (match_dup 0)]
4230                     UNSPEC_SDR))]
4231   "TARGET_64BIT && !TARGET_MIPS16"
4232   "sdr\t%z1,%2"
4233   [(set_attr "type" "store")
4234    (set_attr "mode" "DI")])
4235
4236 ;; Insns to fetch a global symbol from a big GOT.
4237
4238 (define_insn_and_split "*xgot_hisi"
4239   [(set (match_operand:SI 0 "register_operand" "=d")
4240         (high:SI (match_operand:SI 1 "global_got_operand" "")))]
4241   "TARGET_EXPLICIT_RELOCS && TARGET_XGOT"
4242   "#"
4243   "&& reload_completed"
4244   [(set (match_dup 0) (high:SI (match_dup 2)))
4245    (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 3)))]
4246 {
4247   operands[2] = mips_gotoff_global (operands[1]);
4248   operands[3] = pic_offset_table_rtx;
4249 }
4250   [(set_attr "got" "xgot_high")])
4251
4252 (define_insn_and_split "*xgot_losi"
4253   [(set (match_operand:SI 0 "register_operand" "=d")
4254         (lo_sum:SI (match_operand:SI 1 "register_operand" "d")
4255                    (match_operand:SI 2 "global_got_operand" "")))]
4256   "TARGET_EXPLICIT_RELOCS && TARGET_XGOT"
4257   "#"
4258   "&& reload_completed"
4259   [(set (match_dup 0)
4260         (unspec:SI [(match_dup 1) (match_dup 3)] UNSPEC_LOAD_GOT))]
4261   { operands[3] = mips_gotoff_global (operands[2]); }
4262   [(set_attr "got" "load")])
4263
4264 (define_insn_and_split "*xgot_hidi"
4265   [(set (match_operand:DI 0 "register_operand" "=d")
4266         (high:DI (match_operand:DI 1 "global_got_operand" "")))]
4267   "TARGET_EXPLICIT_RELOCS && TARGET_XGOT"
4268   "#"
4269   "&& reload_completed"
4270   [(set (match_dup 0) (high:DI (match_dup 2)))
4271    (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 3)))]
4272 {
4273   operands[2] = mips_gotoff_global (operands[1]);
4274   operands[3] = pic_offset_table_rtx;
4275 }
4276   [(set_attr "got" "xgot_high")])
4277
4278 (define_insn_and_split "*xgot_lodi"
4279   [(set (match_operand:DI 0 "register_operand" "=d")
4280         (lo_sum:DI (match_operand:DI 1 "register_operand" "d")
4281                    (match_operand:DI 2 "global_got_operand" "")))]
4282   "TARGET_EXPLICIT_RELOCS && TARGET_XGOT"
4283   "#"
4284   "&& reload_completed"
4285   [(set (match_dup 0)
4286         (unspec:DI [(match_dup 1) (match_dup 3)] UNSPEC_LOAD_GOT))]
4287   { operands[3] = mips_gotoff_global (operands[2]); }
4288   [(set_attr "got" "load")])
4289
4290 ;; Insns to fetch a global symbol from a normal GOT.
4291
4292 (define_insn_and_split "*got_dispsi"
4293   [(set (match_operand:SI 0 "register_operand" "=d")
4294         (match_operand:SI 1 "global_got_operand" ""))]
4295   "TARGET_EXPLICIT_RELOCS && !TARGET_XGOT"
4296   "#"
4297   "&& reload_completed"
4298   [(set (match_dup 0)
4299         (unspec:SI [(match_dup 2) (match_dup 3)] UNSPEC_LOAD_GOT))]
4300 {
4301   operands[2] = pic_offset_table_rtx;
4302   operands[3] = mips_gotoff_global (operands[1]);
4303 }
4304   [(set_attr "got" "load")])
4305
4306 (define_insn_and_split "*got_dispdi"
4307   [(set (match_operand:DI 0 "register_operand" "=d")
4308         (match_operand:DI 1 "global_got_operand" ""))]
4309   "TARGET_EXPLICIT_RELOCS && !TARGET_XGOT"
4310   "#"
4311   "&& reload_completed"
4312   [(set (match_dup 0)
4313         (unspec:DI [(match_dup 2) (match_dup 3)] UNSPEC_LOAD_GOT))]
4314 {
4315   operands[2] = pic_offset_table_rtx;
4316   operands[3] = mips_gotoff_global (operands[1]);
4317 }
4318   [(set_attr "got" "load")])
4319
4320 ;; Insns for loading the high part of a local symbol.
4321
4322 (define_insn_and_split "*got_pagesi"
4323   [(set (match_operand:SI 0 "register_operand" "=d")
4324         (high:SI (match_operand:SI 1 "local_got_operand" "")))]
4325   "TARGET_EXPLICIT_RELOCS"
4326   "#"
4327   "&& reload_completed"
4328   [(set (match_dup 0)
4329         (unspec:SI [(match_dup 2) (match_dup 3)] UNSPEC_LOAD_GOT))]
4330 {
4331   operands[2] = pic_offset_table_rtx;
4332   operands[3] = mips_gotoff_page (operands[1]);
4333 }
4334   [(set_attr "got" "load")])
4335
4336 (define_insn_and_split "*got_pagedi"
4337   [(set (match_operand:DI 0 "register_operand" "=d")
4338         (high:DI (match_operand:DI 1 "local_got_operand" "")))]
4339   "TARGET_EXPLICIT_RELOCS"
4340   "#"
4341   "&& reload_completed"
4342   [(set (match_dup 0)
4343         (unspec:DI [(match_dup 2) (match_dup 3)] UNSPEC_LOAD_GOT))]
4344 {
4345   operands[2] = pic_offset_table_rtx;
4346   operands[3] = mips_gotoff_page (operands[1]);
4347 }
4348   [(set_attr "got" "load")])
4349
4350 ;; Lower-level instructions for loading an address from the GOT.
4351 ;; We could use MEMs, but an unspec gives more optimization
4352 ;; opportunities.
4353
4354 (define_insn "*load_gotsi"
4355   [(set (match_operand:SI 0 "register_operand" "=d")
4356         (unspec:SI [(match_operand:SI 1 "register_operand" "d")
4357                     (match_operand:SI 2 "immediate_operand" "")]
4358                    UNSPEC_LOAD_GOT))]
4359   "TARGET_ABICALLS"
4360   "lw\t%0,%R2(%1)"
4361   [(set_attr "type" "load")
4362    (set_attr "length" "4")])
4363
4364 (define_insn "*load_gotdi"
4365   [(set (match_operand:DI 0 "register_operand" "=d")
4366         (unspec:DI [(match_operand:DI 1 "register_operand" "d")
4367                     (match_operand:DI 2 "immediate_operand" "")]
4368                    UNSPEC_LOAD_GOT))]
4369   "TARGET_ABICALLS"
4370   "ld\t%0,%R2(%1)"
4371   [(set_attr "type" "load")
4372    (set_attr "length" "4")])
4373
4374 ;; Instructions for adding the low 16 bits of an address to a register.
4375 ;; Operand 2 is the address: print_operand works out which relocation
4376 ;; should be applied.
4377
4378 (define_insn "*lowsi"
4379   [(set (match_operand:SI 0 "register_operand" "=d")
4380         (lo_sum:SI (match_operand:SI 1 "register_operand" "d")
4381                    (match_operand:SI 2 "immediate_operand" "")))]
4382   "!TARGET_MIPS16"
4383   "addiu\t%0,%1,%R2"
4384   [(set_attr "type"     "arith")
4385    (set_attr "mode"     "SI")])
4386
4387 (define_insn "*lowdi"
4388   [(set (match_operand:DI 0 "register_operand" "=d")
4389         (lo_sum:DI (match_operand:DI 1 "register_operand" "d")
4390                    (match_operand:DI 2 "immediate_operand" "")))]
4391   "!TARGET_MIPS16 && TARGET_64BIT"
4392   "daddiu\t%0,%1,%R2"
4393   [(set_attr "type"     "arith")
4394    (set_attr "mode"     "DI")])
4395
4396 (define_insn "*lowsi_mips16"
4397   [(set (match_operand:SI 0 "register_operand" "=d")
4398         (lo_sum:SI (match_operand:SI 1 "register_operand" "0")
4399                    (match_operand:SI 2 "immediate_operand" "")))]
4400   "TARGET_MIPS16"
4401   "addiu\t%0,%R2"
4402   [(set_attr "type"     "arith")
4403    (set_attr "mode"     "SI")
4404    (set_attr "length"   "8")])
4405
4406 (define_insn "*lowdi_mips16"
4407   [(set (match_operand:DI 0 "register_operand" "=d")
4408         (lo_sum:DI (match_operand:DI 1 "register_operand" "0")
4409                    (match_operand:DI 2 "immediate_operand" "")))]
4410   "TARGET_MIPS16 && TARGET_64BIT"
4411   "daddiu\t%0,%R2"
4412   [(set_attr "type"     "arith")
4413    (set_attr "mode"     "DI")
4414    (set_attr "length"   "8")])
4415
4416 ;; 64-bit integer moves
4417
4418 ;; Unlike most other insns, the move insns can't be split with
4419 ;; different predicates, because register spilling and other parts of
4420 ;; the compiler, have memoized the insn number already.
4421
4422 (define_expand "movdi"
4423   [(set (match_operand:DI 0 "nonimmediate_operand" "")
4424         (match_operand:DI 1 "" ""))]
4425   ""
4426 {
4427   if (mips_legitimize_move (DImode, operands[0], operands[1]))
4428     DONE;
4429
4430   /* If we are generating embedded PIC code, and we are referring to a
4431      symbol in the .text section, we must use an offset from the start
4432      of the function.  */
4433   if (TARGET_EMBEDDED_PIC
4434       && (GET_CODE (operands[1]) == LABEL_REF
4435           || (GET_CODE (operands[1]) == SYMBOL_REF
4436               && ! SYMBOL_REF_FLAG (operands[1]))))
4437     {
4438       rtx temp;
4439
4440       temp = embedded_pic_offset (operands[1]);
4441       temp = gen_rtx_PLUS (Pmode, embedded_pic_fnaddr_reg (),
4442                            force_reg (DImode, temp));
4443       emit_move_insn (operands[0], force_reg (DImode, temp));
4444       DONE;
4445     }
4446 })
4447
4448 ;; For mips16, we need a special case to handle storing $31 into
4449 ;; memory, since we don't have a constraint to match $31.  This
4450 ;; instruction can be generated by save_restore_insns.
4451
4452 (define_insn ""
4453   [(set (match_operand:DI 0 "stack_operand" "=m")
4454         (reg:DI 31))]
4455   "TARGET_MIPS16 && TARGET_64BIT"
4456   "sd\t$31,%0"
4457   [(set_attr "type"     "store")
4458    (set_attr "mode"     "DI")])
4459
4460 (define_insn "movdi_internal"
4461   [(set (match_operand:DI 0 "nonimmediate_operand" "=d,d,d,m,*x,*d,*x,*B*C*D,*B*C*D,*d,*m")
4462         (match_operand:DI 1 "general_operand" "d,iF,m,d,J,*x,*d,*d,*m,*B*C*D,*B*C*D"))]
4463   "!TARGET_64BIT && !TARGET_MIPS16
4464    && (register_operand (operands[0], DImode)
4465        || register_operand (operands[1], DImode)
4466        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0)
4467        || operands[1] == CONST0_RTX (DImode))"
4468   { return mips_output_move (operands[0], operands[1]); }
4469   [(set_attr "type"     "move,arith,load,store,hilo,hilo,hilo,xfer,load,xfer,store")
4470    (set_attr "mode"     "DI")
4471    (set_attr "length"   "8,16,*,*,8,8,8,8,*,8,*")])
4472
4473 (define_insn ""
4474   [(set (match_operand:DI 0 "nonimmediate_operand" "=d,y,d,d,d,d,m,*d")
4475         (match_operand:DI 1 "general_operand" "d,d,y,K,N,m,d,*x"))]
4476   "!TARGET_64BIT && TARGET_MIPS16
4477    && (register_operand (operands[0], DImode)
4478        || register_operand (operands[1], DImode))"
4479   { return mips_output_move (operands[0], operands[1]); }
4480   [(set_attr "type"     "move,move,move,arith,arith,load,store,hilo")
4481    (set_attr "mode"     "DI")
4482    (set_attr "length"   "8,8,8,8,12,*,*,8")])
4483
4484 (define_insn "movdi_internal2"
4485   [(set (match_operand:DI 0 "nonimmediate_operand" "=d,d,e,d,m,*f,*f,*f,*d,*m,*x,*d,*x,*B*C*D,*B*C*D,*d,*m")
4486         (match_operand:DI 1 "move_operand" "d,U,T,m,dJ,*f,*d*J,*m,*f,*f,*J,*x,*d,*d,*m,*B*C*D,*B*C*D"))]
4487   "TARGET_64BIT && !TARGET_MIPS16
4488    && (register_operand (operands[0], DImode)
4489        || register_operand (operands[1], DImode)
4490        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0)
4491        || operands[1] == CONST0_RTX (DImode))"
4492   { return mips_output_move (operands[0], operands[1]); }
4493   [(set_attr "type"     "move,const,const,load,store,move,xfer,load,xfer,store,hilo,hilo,hilo,xfer,load,xfer,store")
4494    (set_attr "mode"     "DI")
4495    (set_attr "length"   "4,*,*,*,*,4,4,*,4,*,4,4,4,8,*,8,*")])
4496
4497 (define_insn "*movdi_internal2_mips16"
4498   [(set (match_operand:DI 0 "nonimmediate_operand" "=d,y,d,d,d,d,d,m,*d")
4499         (match_operand:DI 1 "move_operand" "d,d,y,K,N,U,m,d,*x"))]
4500   "TARGET_64BIT && TARGET_MIPS16
4501    && (register_operand (operands[0], DImode)
4502        || register_operand (operands[1], DImode))"
4503   { return mips_output_move (operands[0], operands[1]); }
4504   [(set_attr "type"     "move,move,move,arith,arith,const,load,store,hilo")
4505    (set_attr "mode"     "DI")
4506    (set_attr_alternative "length"
4507                 [(const_int 4)
4508                  (const_int 4)
4509                  (const_int 4)
4510                  (if_then_else (match_operand:VOID 1 "m16_uimm8_1" "")
4511                                (const_int 4)
4512                                (const_int 8))
4513                  (if_then_else (match_operand:VOID 1 "m16_nuimm8_1" "")
4514                                (const_int 8)
4515                                (const_int 12))
4516                  (const_string "*")
4517                  (const_string "*")
4518                  (const_string "*")
4519                  (const_int 4)])])
4520
4521
4522 ;; On the mips16, we can split ld $r,N($r) into an add and a load,
4523 ;; when the original load is a 4 byte instruction but the add and the
4524 ;; load are 2 2 byte instructions.
4525
4526 (define_split
4527   [(set (match_operand:DI 0 "register_operand" "")
4528         (mem:DI (plus:DI (match_dup 0)
4529                          (match_operand:DI 1 "const_int_operand" ""))))]
4530   "TARGET_64BIT && TARGET_MIPS16 && reload_completed
4531    && !TARGET_DEBUG_D_MODE
4532    && GET_CODE (operands[0]) == REG
4533    && M16_REG_P (REGNO (operands[0]))
4534    && GET_CODE (operands[1]) == CONST_INT
4535    && ((INTVAL (operands[1]) < 0
4536         && INTVAL (operands[1]) >= -0x10)
4537        || (INTVAL (operands[1]) >= 32 * 8
4538            && INTVAL (operands[1]) <= 31 * 8 + 0x8)
4539        || (INTVAL (operands[1]) >= 0
4540            && INTVAL (operands[1]) < 32 * 8
4541            && (INTVAL (operands[1]) & 7) != 0))"
4542   [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1)))
4543    (set (match_dup 0) (mem:DI (plus:DI (match_dup 0) (match_dup 2))))]
4544 {
4545   HOST_WIDE_INT val = INTVAL (operands[1]);
4546
4547   if (val < 0)
4548     operands[2] = const0_rtx;
4549   else if (val >= 32 * 8)
4550     {
4551       int off = val & 7;
4552
4553       operands[1] = GEN_INT (0x8 + off);
4554       operands[2] = GEN_INT (val - off - 0x8);
4555     }
4556   else
4557     {
4558       int off = val & 7;
4559
4560       operands[1] = GEN_INT (off);
4561       operands[2] = GEN_INT (val - off);
4562     }
4563 })
4564
4565 ;; 32-bit Integer moves
4566
4567 ;; Unlike most other insns, the move insns can't be split with
4568 ;; different predicates, because register spilling and other parts of
4569 ;; the compiler, have memoized the insn number already.
4570
4571 (define_expand "movsi"
4572   [(set (match_operand:SI 0 "nonimmediate_operand" "")
4573         (match_operand:SI 1 "" ""))]
4574   ""
4575 {
4576   if (mips_legitimize_move (SImode, operands[0], operands[1]))
4577     DONE;
4578
4579   /* If we are generating embedded PIC code, and we are referring to a
4580      symbol in the .text section, we must use an offset from the start
4581      of the function.  */
4582   if (TARGET_EMBEDDED_PIC
4583       && (GET_CODE (operands[1]) == LABEL_REF
4584           || (GET_CODE (operands[1]) == SYMBOL_REF
4585               && ! SYMBOL_REF_FLAG (operands[1]))))
4586     {
4587       rtx temp;
4588
4589       temp = embedded_pic_offset (operands[1]);
4590       temp = gen_rtx_PLUS (Pmode, embedded_pic_fnaddr_reg (),
4591                            force_reg (SImode, temp));
4592       emit_move_insn (operands[0], force_reg (SImode, temp));
4593       DONE;
4594     }
4595 })
4596
4597 ;; We can only store $ra directly into a small sp offset.
4598
4599 (define_insn ""
4600   [(set (match_operand:SI 0 "stack_operand" "=m")
4601         (reg:SI 31))]
4602   "TARGET_MIPS16"
4603   "sw\t$31,%0"
4604   [(set_attr "type"     "store")
4605    (set_attr "mode"     "SI")])
4606
4607 ;; The difference between these two is whether or not ints are allowed
4608 ;; in FP registers (off by default, use -mdebugh to enable).
4609
4610 (define_insn "movsi_internal"
4611   [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,e,d,m,*f,*f,*f,*d,*m,*d,*z,*x,*d,*x,*B*C*D,*B*C*D,*d,*m")
4612         (match_operand:SI 1 "move_operand" "d,U,T,m,dJ,*f,*d*J,*m,*f,*f,*z,*d,J,*x,*d,*d,*m,*B*C*D,*B*C*D"))]
4613   "!TARGET_MIPS16
4614    && (register_operand (operands[0], SImode)
4615        || register_operand (operands[1], SImode)
4616        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0))"
4617   { return mips_output_move (operands[0], operands[1]); }
4618   [(set_attr "type"     "move,const,const,load,store,move,xfer,load,xfer,store,xfer,xfer,hilo,hilo,hilo,xfer,load,xfer,store")
4619    (set_attr "mode"     "SI")
4620    (set_attr "length"   "4,*,*,*,*,4,4,*,4,*,4,4,4,4,4,4,*,4,*")])
4621
4622 (define_insn ""
4623   [(set (match_operand:SI 0 "nonimmediate_operand" "=d,y,d,d,d,d,d,m,*d")
4624         (match_operand:SI 1 "move_operand" "d,d,y,K,N,U,m,d,*x"))]
4625   "TARGET_MIPS16
4626    && (register_operand (operands[0], SImode)
4627        || register_operand (operands[1], SImode))"
4628   { return mips_output_move (operands[0], operands[1]); }
4629   [(set_attr "type"     "move,move,move,arith,arith,const,load,store,hilo")
4630    (set_attr "mode"     "SI")
4631    (set_attr_alternative "length"
4632                 [(const_int 4)
4633                  (const_int 4)
4634                  (const_int 4)
4635                  (if_then_else (match_operand:VOID 1 "m16_uimm8_1" "")
4636                                (const_int 4)
4637                                (const_int 8))
4638                  (if_then_else (match_operand:VOID 1 "m16_nuimm8_1" "")
4639                                (const_int 8)
4640                                (const_int 12))
4641                  (const_string "*")
4642                  (const_string "*")
4643                  (const_string "*")
4644                  (const_int 4)])])
4645
4646 ;; On the mips16, we can split lw $r,N($r) into an add and a load,
4647 ;; when the original load is a 4 byte instruction but the add and the
4648 ;; load are 2 2 byte instructions.
4649
4650 (define_split
4651   [(set (match_operand:SI 0 "register_operand" "")
4652         (mem:SI (plus:SI (match_dup 0)
4653                          (match_operand:SI 1 "const_int_operand" ""))))]
4654   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
4655    && GET_CODE (operands[0]) == REG
4656    && M16_REG_P (REGNO (operands[0]))
4657    && GET_CODE (operands[1]) == CONST_INT
4658    && ((INTVAL (operands[1]) < 0
4659         && INTVAL (operands[1]) >= -0x80)
4660        || (INTVAL (operands[1]) >= 32 * 4
4661            && INTVAL (operands[1]) <= 31 * 4 + 0x7c)
4662        || (INTVAL (operands[1]) >= 0
4663            && INTVAL (operands[1]) < 32 * 4
4664            && (INTVAL (operands[1]) & 3) != 0))"
4665   [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
4666    (set (match_dup 0) (mem:SI (plus:SI (match_dup 0) (match_dup 2))))]
4667 {
4668   HOST_WIDE_INT val = INTVAL (operands[1]);
4669
4670   if (val < 0)
4671     operands[2] = const0_rtx;
4672   else if (val >= 32 * 4)
4673     {
4674       int off = val & 3;
4675
4676       operands[1] = GEN_INT (0x7c + off);
4677       operands[2] = GEN_INT (val - off - 0x7c);
4678     }
4679   else
4680     {
4681       int off = val & 3;
4682
4683       operands[1] = GEN_INT (off);
4684       operands[2] = GEN_INT (val - off);
4685     }
4686 })
4687
4688 ;; On the mips16, we can split a load of certain constants into a load
4689 ;; and an add.  This turns a 4 byte instruction into 2 2 byte
4690 ;; instructions.
4691
4692 (define_split
4693   [(set (match_operand:SI 0 "register_operand" "")
4694         (match_operand:SI 1 "const_int_operand" ""))]
4695   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
4696    && GET_CODE (operands[0]) == REG
4697    && M16_REG_P (REGNO (operands[0]))
4698    && GET_CODE (operands[1]) == CONST_INT
4699    && INTVAL (operands[1]) >= 0x100
4700    && INTVAL (operands[1]) <= 0xff + 0x7f"
4701   [(set (match_dup 0) (match_dup 1))
4702    (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))]
4703 {
4704   int val = INTVAL (operands[1]);
4705
4706   operands[1] = GEN_INT (0xff);
4707   operands[2] = GEN_INT (val - 0xff);
4708 })
4709
4710 ;; On the mips16, we can split a load of a negative constant into a
4711 ;; load and a neg.  That's what mips_output_move will generate anyhow.
4712
4713 (define_split
4714   [(set (match_operand:SI 0 "register_operand" "")
4715         (match_operand:SI 1 "const_int_operand" ""))]
4716   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
4717    && GET_CODE (operands[0]) == REG
4718    && M16_REG_P (REGNO (operands[0]))
4719    && GET_CODE (operands[1]) == CONST_INT
4720    && INTVAL (operands[1]) < 0
4721    && INTVAL (operands[1]) > - 0x8000"
4722   [(set (match_dup 0) (match_dup 1))
4723    (set (match_dup 0) (neg:SI (match_dup 0)))]
4724   { operands[1] = GEN_INT (- INTVAL (operands[1])); })
4725
4726 ;; This insn handles moving CCmode values.  It's really just a
4727 ;; slightly simplified copy of movsi_internal2, with additional cases
4728 ;; to move a condition register to a general register and to move
4729 ;; between the general registers and the floating point registers.
4730
4731 (define_insn "movcc"
4732   [(set (match_operand:CC 0 "nonimmediate_operand" "=d,*d,*d,*m,*d,*f,*f,*f,*m")
4733         (match_operand:CC 1 "general_operand" "z,*d,*m,*d,*f,*d,*f,*m,*f"))]
4734   "ISA_HAS_8CC && TARGET_HARD_FLOAT"
4735   { return mips_output_move (operands[0], operands[1]); }
4736   [(set_attr "type"     "move,move,load,store,xfer,xfer,move,load,store")
4737    (set_attr "mode"     "SI")
4738    (set_attr "length"   "8,4,*,*,4,4,4,*,*")])
4739
4740 ;; Reload condition code registers.  reload_incc and reload_outcc
4741 ;; both handle moves from arbitrary operands into condition code
4742 ;; registers.  reload_incc handles the more common case in which
4743 ;; a source operand is constrained to be in a condition-code
4744 ;; register, but has not been allocated to one.
4745 ;;
4746 ;; Sometimes, such as in movcc, we have a CCmode destination whose
4747 ;; constraints do not include 'z'.  reload_outcc handles the case
4748 ;; when such an operand is allocated to a condition-code register.
4749 ;;
4750 ;; Note that reloads from a condition code register to some
4751 ;; other location can be done using ordinary moves.  Moving
4752 ;; into a GPR takes a single movcc, moving elsewhere takes
4753 ;; two.  We can leave these cases to the generic reload code.
4754 (define_expand "reload_incc"
4755   [(set (match_operand:CC 0 "fcc_register_operand" "=z")
4756         (match_operand:CC 1 "general_operand" ""))
4757    (clobber (match_operand:TF 2 "register_operand" "=&f"))]
4758   "ISA_HAS_8CC && TARGET_HARD_FLOAT"
4759 {
4760   mips_emit_fcc_reload (operands[0], operands[1], operands[2]);
4761   DONE;
4762 })
4763
4764 (define_expand "reload_outcc"
4765   [(set (match_operand:CC 0 "fcc_register_operand" "=z")
4766         (match_operand:CC 1 "register_operand" ""))
4767    (clobber (match_operand:TF 2 "register_operand" "=&f"))]
4768   "ISA_HAS_8CC && TARGET_HARD_FLOAT"
4769 {
4770   mips_emit_fcc_reload (operands[0], operands[1], operands[2]);
4771   DONE;
4772 })
4773
4774 ;; MIPS4 supports loading and storing a floating point register from
4775 ;; the sum of two general registers.  We use two versions for each of
4776 ;; these four instructions: one where the two general registers are
4777 ;; SImode, and one where they are DImode.  This is because general
4778 ;; registers will be in SImode when they hold 32 bit values, but,
4779 ;; since the 32 bit values are always sign extended, the [ls][wd]xc1
4780 ;; instructions will still work correctly.
4781
4782 ;; ??? Perhaps it would be better to support these instructions by
4783 ;; modifying GO_IF_LEGITIMATE_ADDRESS and friends.  However, since
4784 ;; these instructions can only be used to load and store floating
4785 ;; point registers, that would probably cause trouble in reload.
4786
4787 (define_insn ""
4788   [(set (match_operand:SF 0 "register_operand" "=f")
4789         (mem:SF (plus:SI (match_operand:SI 1 "register_operand" "d")
4790                          (match_operand:SI 2 "register_operand" "d"))))]
4791   "ISA_HAS_FP4 && TARGET_HARD_FLOAT"
4792   "lwxc1\t%0,%1(%2)"
4793   [(set_attr "type"     "load")
4794    (set_attr "mode"     "SF")
4795    (set_attr "length"   "4")])
4796
4797 (define_insn ""
4798   [(set (match_operand:SF 0 "register_operand" "=f")
4799         (mem:SF (plus:DI (match_operand:DI 1 "register_operand" "d")
4800                          (match_operand:DI 2 "register_operand" "d"))))]
4801   "ISA_HAS_FP4 && TARGET_HARD_FLOAT"
4802   "lwxc1\t%0,%1(%2)"
4803   [(set_attr "type"     "load")
4804    (set_attr "mode"     "SF")
4805    (set_attr "length"   "4")])
4806
4807 (define_insn ""
4808   [(set (match_operand:DF 0 "register_operand" "=f")
4809         (mem:DF (plus:SI (match_operand:SI 1 "register_operand" "d")
4810                          (match_operand:SI 2 "register_operand" "d"))))]
4811   "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
4812   "ldxc1\t%0,%1(%2)"
4813   [(set_attr "type"     "load")
4814    (set_attr "mode"     "DF")
4815    (set_attr "length"   "4")])
4816
4817 (define_insn ""
4818   [(set (match_operand:DF 0 "register_operand" "=f")
4819         (mem:DF (plus:DI (match_operand:DI 1 "register_operand" "d")
4820                          (match_operand:DI 2 "register_operand" "d"))))]
4821   "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
4822   "ldxc1\t%0,%1(%2)"
4823   [(set_attr "type"     "load")
4824    (set_attr "mode"     "DF")
4825    (set_attr "length"   "4")])
4826
4827 (define_insn ""
4828   [(set (mem:SF (plus:SI (match_operand:SI 1 "register_operand" "d")
4829                          (match_operand:SI 2 "register_operand" "d")))
4830         (match_operand:SF 0 "register_operand" "f"))]
4831   "ISA_HAS_FP4 && TARGET_HARD_FLOAT"
4832   "swxc1\t%0,%1(%2)"
4833   [(set_attr "type"     "store")
4834    (set_attr "mode"     "SF")
4835    (set_attr "length"   "4")])
4836
4837 (define_insn ""
4838   [(set (mem:SF (plus:DI (match_operand:DI 1 "register_operand" "d")
4839                          (match_operand:DI 2 "register_operand" "d")))
4840         (match_operand:SF 0 "register_operand" "f"))]
4841   "ISA_HAS_FP4 && TARGET_HARD_FLOAT"
4842   "swxc1\t%0,%1(%2)"
4843   [(set_attr "type"     "store")
4844    (set_attr "mode"     "SF")
4845    (set_attr "length"   "4")])
4846
4847 (define_insn ""
4848   [(set (mem:DF (plus:SI (match_operand:SI 1 "register_operand" "d")
4849                          (match_operand:SI 2 "register_operand" "d")))
4850         (match_operand:DF 0 "register_operand" "f"))]
4851   "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
4852   "sdxc1\t%0,%1(%2)"
4853   [(set_attr "type"     "store")
4854    (set_attr "mode"     "DF")
4855    (set_attr "length"   "4")])
4856
4857 (define_insn ""
4858   [(set (mem:DF (plus:DI (match_operand:DI 1 "register_operand" "d")
4859                          (match_operand:DI 2 "register_operand" "d")))
4860         (match_operand:DF 0 "register_operand" "f"))]
4861   "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
4862   "sdxc1\t%0,%1(%2)"
4863   [(set_attr "type"     "store")
4864    (set_attr "mode"     "DF")
4865    (set_attr "length"   "4")])
4866
4867 ;; 16-bit Integer moves
4868
4869 ;; Unlike most other insns, the move insns can't be split with
4870 ;; different predicates, because register spilling and other parts of
4871 ;; the compiler, have memoized the insn number already.
4872 ;; Unsigned loads are used because LOAD_EXTEND_OP returns ZERO_EXTEND.
4873
4874 (define_expand "movhi"
4875   [(set (match_operand:HI 0 "nonimmediate_operand" "")
4876         (match_operand:HI 1 "general_operand" ""))]
4877   ""
4878 {
4879   if ((reload_in_progress | reload_completed) == 0
4880       && !register_operand (operands[0], HImode)
4881       && !register_operand (operands[1], HImode)
4882       && (TARGET_MIPS16
4883           || (GET_CODE (operands[1]) != CONST_INT
4884           || INTVAL (operands[1]) != 0)))
4885     {
4886       rtx temp = force_reg (HImode, operands[1]);
4887       emit_move_insn (operands[0], temp);
4888       DONE;
4889     }
4890 })
4891
4892 (define_insn "movhi_internal"
4893   [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d,m,*d,*f,*f,*x,*d")
4894         (match_operand:HI 1 "general_operand"       "d,IK,m,dJ,*f,*d,*f,*d,*x"))]
4895   "!TARGET_MIPS16
4896    && (register_operand (operands[0], HImode)
4897        || register_operand (operands[1], HImode)
4898        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0))"
4899   "@
4900     move\t%0,%1
4901     li\t%0,%1
4902     lhu\t%0,%1
4903     sh\t%z1,%0
4904     mfc1\t%0,%1
4905     mtc1\t%1,%0
4906     mov.s\t%0,%1
4907     mt%0\t%1
4908     mf%1\t%0"
4909   [(set_attr "type"     "move,arith,load,store,xfer,xfer,move,hilo,hilo")
4910    (set_attr "mode"     "HI")
4911    (set_attr "length"   "4,4,*,*,4,4,4,4,4")])
4912
4913 (define_insn ""
4914   [(set (match_operand:HI 0 "nonimmediate_operand" "=d,y,d,d,d,d,m,*d")
4915         (match_operand:HI 1 "general_operand"      "d,d,y,K,N,m,d,*x"))]
4916   "TARGET_MIPS16
4917    && (register_operand (operands[0], HImode)
4918        || register_operand (operands[1], HImode))"
4919   "@
4920     move\t%0,%1
4921     move\t%0,%1
4922     move\t%0,%1
4923     li\t%0,%1
4924     li\t%0,%n1\;neg\t%0
4925     lhu\t%0,%1
4926     sh\t%1,%0
4927     mf%1\t%0"
4928   [(set_attr "type"     "move,move,move,arith,arith,load,store,hilo")
4929    (set_attr "mode"     "HI")
4930    (set_attr_alternative "length"
4931                 [(const_int 4)
4932                  (const_int 4)
4933                  (const_int 4)
4934                  (if_then_else (match_operand:VOID 1 "m16_uimm8_1" "")
4935                                (const_int 4)
4936                                (const_int 8))
4937                  (if_then_else (match_operand:VOID 1 "m16_nuimm8_1" "")
4938                                (const_int 8)
4939                                (const_int 12))
4940                  (const_string "*")
4941                  (const_string "*")
4942                  (const_int 4)])])
4943
4944
4945 ;; On the mips16, we can split lh $r,N($r) into an add and a load,
4946 ;; when the original load is a 4 byte instruction but the add and the
4947 ;; load are 2 2 byte instructions.
4948
4949 (define_split
4950   [(set (match_operand:HI 0 "register_operand" "")
4951         (mem:HI (plus:SI (match_dup 0)
4952                          (match_operand:SI 1 "const_int_operand" ""))))]
4953   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
4954    && GET_CODE (operands[0]) == REG
4955    && M16_REG_P (REGNO (operands[0]))
4956    && GET_CODE (operands[1]) == CONST_INT
4957    && ((INTVAL (operands[1]) < 0
4958         && INTVAL (operands[1]) >= -0x80)
4959        || (INTVAL (operands[1]) >= 32 * 2
4960            && INTVAL (operands[1]) <= 31 * 2 + 0x7e)
4961        || (INTVAL (operands[1]) >= 0
4962            && INTVAL (operands[1]) < 32 * 2
4963            && (INTVAL (operands[1]) & 1) != 0))"
4964   [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
4965    (set (match_dup 0) (mem:HI (plus:SI (match_dup 0) (match_dup 2))))]
4966 {
4967   HOST_WIDE_INT val = INTVAL (operands[1]);
4968
4969   if (val < 0)
4970     operands[2] = const0_rtx;
4971   else if (val >= 32 * 2)
4972     {
4973       int off = val & 1;
4974
4975       operands[1] = GEN_INT (0x7e + off);
4976       operands[2] = GEN_INT (val - off - 0x7e);
4977     }
4978   else
4979     {
4980       int off = val & 1;
4981
4982       operands[1] = GEN_INT (off);
4983       operands[2] = GEN_INT (val - off);
4984     }
4985 })
4986
4987 ;; 8-bit Integer moves
4988
4989 ;; Unlike most other insns, the move insns can't be split with
4990 ;; different predicates, because register spilling and other parts of
4991 ;; the compiler, have memoized the insn number already.
4992 ;; Unsigned loads are used because LOAD_EXTEND_OP returns ZERO_EXTEND.
4993
4994 (define_expand "movqi"
4995   [(set (match_operand:QI 0 "nonimmediate_operand" "")
4996         (match_operand:QI 1 "general_operand" ""))]
4997   ""
4998 {
4999   if ((reload_in_progress | reload_completed) == 0
5000       && !register_operand (operands[0], QImode)
5001       && !register_operand (operands[1], QImode)
5002       && (TARGET_MIPS16
5003           || (GET_CODE (operands[1]) != CONST_INT
5004           || INTVAL (operands[1]) != 0)))
5005     {
5006       rtx temp = force_reg (QImode, operands[1]);
5007       emit_move_insn (operands[0], temp);
5008       DONE;
5009     }
5010 })
5011
5012 (define_insn "movqi_internal"
5013   [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,m,*d,*f,*f,*x,*d")
5014         (match_operand:QI 1 "general_operand"       "d,IK,m,dJ,*f,*d,*f,*d,*x"))]
5015   "!TARGET_MIPS16
5016    && (register_operand (operands[0], QImode)
5017        || register_operand (operands[1], QImode)
5018        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0))"
5019   "@
5020     move\t%0,%1
5021     li\t%0,%1
5022     lbu\t%0,%1
5023     sb\t%z1,%0
5024     mfc1\t%0,%1
5025     mtc1\t%1,%0
5026     mov.s\t%0,%1
5027     mt%0\t%1
5028     mf%1\t%0"
5029   [(set_attr "type"     "move,arith,load,store,xfer,xfer,move,hilo,hilo")
5030    (set_attr "mode"     "QI")
5031    (set_attr "length"   "4,4,*,*,4,4,4,4,4")])
5032
5033 (define_insn ""
5034   [(set (match_operand:QI 0 "nonimmediate_operand" "=d,y,d,d,d,d,m,*d")
5035         (match_operand:QI 1 "general_operand"      "d,d,y,K,N,m,d,*x"))]
5036   "TARGET_MIPS16
5037    && (register_operand (operands[0], QImode)
5038        || register_operand (operands[1], QImode))"
5039   "@
5040     move\t%0,%1
5041     move\t%0,%1
5042     move\t%0,%1
5043     li\t%0,%1
5044     li\t%0,%n1\;neg\t%0
5045     lbu\t%0,%1
5046     sb\t%1,%0
5047     mf%1\t%0"
5048   [(set_attr "type"     "move,move,move,arith,arith,load,store,hilo")
5049    (set_attr "mode"     "QI")
5050    (set_attr "length"   "4,4,4,4,8,*,*,4")])
5051
5052 ;; On the mips16, we can split lb $r,N($r) into an add and a load,
5053 ;; when the original load is a 4 byte instruction but the add and the
5054 ;; load are 2 2 byte instructions.
5055
5056 (define_split
5057   [(set (match_operand:QI 0 "register_operand" "")
5058         (mem:QI (plus:SI (match_dup 0)
5059                          (match_operand:SI 1 "const_int_operand" ""))))]
5060   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
5061    && GET_CODE (operands[0]) == REG
5062    && M16_REG_P (REGNO (operands[0]))
5063    && GET_CODE (operands[1]) == CONST_INT
5064    && ((INTVAL (operands[1]) < 0
5065         && INTVAL (operands[1]) >= -0x80)
5066        || (INTVAL (operands[1]) >= 32
5067            && INTVAL (operands[1]) <= 31 + 0x7f))"
5068   [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
5069    (set (match_dup 0) (mem:QI (plus:SI (match_dup 0) (match_dup 2))))]
5070 {
5071   HOST_WIDE_INT val = INTVAL (operands[1]);
5072
5073   if (val < 0)
5074     operands[2] = const0_rtx;
5075   else
5076     {
5077       operands[1] = GEN_INT (0x7f);
5078       operands[2] = GEN_INT (val - 0x7f);
5079     }
5080 })
5081
5082 ;; 32-bit floating point moves
5083
5084 (define_expand "movsf"
5085   [(set (match_operand:SF 0 "nonimmediate_operand" "")
5086         (match_operand:SF 1 "general_operand" ""))]
5087   ""
5088 {
5089   if ((reload_in_progress | reload_completed) == 0
5090       && !register_operand (operands[0], SFmode)
5091       && !nonmemory_operand (operands[1], SFmode))
5092     operands[1] = force_reg (SFmode, operands[1]);
5093 })
5094
5095 (define_insn "movsf_internal1"
5096   [(set (match_operand:SF 0 "nonimmediate_operand" "=f,f,f,m,*f,*d,*d,*d,*m")
5097         (match_operand:SF 1 "general_operand" "f,G,m,fG,*d,*f,*G*d,*m,*d"))]
5098   "TARGET_HARD_FLOAT
5099    && (register_operand (operands[0], SFmode)
5100        || nonmemory_operand (operands[1], SFmode))"
5101   { return mips_output_move (operands[0], operands[1]); }
5102   [(set_attr "type"     "move,xfer,load,store,xfer,xfer,move,load,store")
5103    (set_attr "mode"     "SF")
5104    (set_attr "length"   "4,4,*,*,4,4,4,*,*")])
5105
5106 (define_insn "movsf_internal2"
5107   [(set (match_operand:SF 0 "nonimmediate_operand" "=d,d,m")
5108         (match_operand:SF 1 "general_operand" "      Gd,m,d"))]
5109   "TARGET_SOFT_FLOAT && !TARGET_MIPS16
5110    && (register_operand (operands[0], SFmode)
5111        || nonmemory_operand (operands[1], SFmode))"
5112   { return mips_output_move (operands[0], operands[1]); }
5113   [(set_attr "type"     "move,load,store")
5114    (set_attr "mode"     "SF")
5115    (set_attr "length"   "4,*,*")])
5116
5117 (define_insn ""
5118   [(set (match_operand:SF 0 "nonimmediate_operand" "=d,y,d,d,m")
5119         (match_operand:SF 1 "nonimmediate_operand" "d,d,y,m,d"))]
5120   "TARGET_MIPS16
5121    && (register_operand (operands[0], SFmode)
5122        || register_operand (operands[1], SFmode))"
5123   { return mips_output_move (operands[0], operands[1]); }
5124   [(set_attr "type"     "move,move,move,load,store")
5125    (set_attr "mode"     "SF")
5126    (set_attr "length"   "4,4,4,*,*")])
5127
5128
5129 ;; 64-bit floating point moves
5130
5131 (define_expand "movdf"
5132   [(set (match_operand:DF 0 "nonimmediate_operand" "")
5133         (match_operand:DF 1 "general_operand" ""))]
5134   ""
5135 {
5136   if ((reload_in_progress | reload_completed) == 0
5137       && !register_operand (operands[0], DFmode)
5138       && !nonmemory_operand (operands[1], DFmode))
5139     operands[1] = force_reg (DFmode, operands[1]);
5140 })
5141
5142 (define_insn "movdf_internal1a"
5143   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,f,f,m,*f,*d,*d,*d,*m")
5144         (match_operand:DF 1 "general_operand" "f,G,m,fG,*d,*f,*d*G,*m,*d"))]
5145   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_64BIT
5146    && (register_operand (operands[0], DFmode)
5147        || nonmemory_operand (operands[1], DFmode))"
5148   { return mips_output_move (operands[0], operands[1]); }
5149   [(set_attr "type"     "move,xfer,load,store,xfer,xfer,move,load,store")
5150    (set_attr "mode"     "DF")
5151    (set_attr "length"   "4,4,*,*,4,4,4,*,*")])
5152
5153 (define_insn "movdf_internal1b"
5154   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,f,f,m,*f,*d,*d,*d,*m")
5155         (match_operand:DF 1 "general_operand" "f,G,m,fG,*d,*f,*d*G,*m,*d"))]
5156   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_64BIT
5157    && (register_operand (operands[0], DFmode)
5158        || nonmemory_operand (operands[1], DFmode))"
5159   { return mips_output_move (operands[0], operands[1]); }
5160   [(set_attr "type"     "move,xfer,load,store,xfer,xfer,move,load,store")
5161    (set_attr "mode"     "DF")
5162    (set_attr "length"   "4,8,*,*,8,8,8,*,*")])
5163
5164 (define_insn "movdf_internal2"
5165   [(set (match_operand:DF 0 "nonimmediate_operand" "=d,d,m,d,f,f")
5166         (match_operand:DF 1 "general_operand" "dG,m,dG,f,d,f"))]
5167   "(TARGET_SOFT_FLOAT || TARGET_SINGLE_FLOAT) && !TARGET_MIPS16
5168    && (register_operand (operands[0], DFmode)
5169        || nonmemory_operand (operands[1], DFmode))"
5170   { return mips_output_move (operands[0], operands[1]); }
5171   [(set_attr "type"     "move,load,store,xfer,xfer,move")
5172    (set_attr "mode"     "DF")
5173    (set_attr "length"   "8,*,*,4,4,4")])
5174
5175 (define_insn ""
5176   [(set (match_operand:DF 0 "nonimmediate_operand" "=d,y,d,d,m")
5177         (match_operand:DF 1 "nonimmediate_operand" "d,d,y,m,d"))]
5178   "TARGET_MIPS16
5179    && (register_operand (operands[0], DFmode)
5180        || register_operand (operands[1], DFmode))"
5181   { return mips_output_move (operands[0], operands[1]); }
5182   [(set_attr "type"     "move,move,move,load,store")
5183    (set_attr "mode"     "DF")
5184    (set_attr "length"   "8,8,8,*,*")])
5185
5186 (define_split
5187   [(set (match_operand:DI 0 "nonimmediate_operand" "")
5188         (match_operand:DI 1 "general_operand" ""))]
5189   "reload_completed && !TARGET_64BIT
5190    && mips_split_64bit_move_p (operands[0], operands[1])"
5191   [(const_int 0)]
5192 {
5193   mips_split_64bit_move (operands[0], operands[1]);
5194   DONE;
5195 })
5196
5197 (define_split
5198   [(set (match_operand:DF 0 "nonimmediate_operand" "")
5199         (match_operand:DF 1 "general_operand" ""))]
5200   "reload_completed && !TARGET_64BIT
5201    && mips_split_64bit_move_p (operands[0], operands[1])"
5202   [(const_int 0)]
5203 {
5204   mips_split_64bit_move (operands[0], operands[1]);
5205   DONE;
5206 })
5207
5208 ;; Patterns for loading or storing part of a paired floating point
5209 ;; register.  We need them because odd-numbered floating-point registers
5210 ;; are not fully independent: see mips_split_64bit_move.
5211
5212 ;; Load the low word of operand 0 with operand 1.
5213 (define_insn "load_df_low"
5214   [(set (match_operand:DF 0 "register_operand" "=f,f")
5215         (unspec:DF [(match_operand:SI 1 "general_operand" "dJ,m")]
5216                    UNSPEC_LOAD_DF_LOW))]
5217   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_64BIT"
5218 {
5219   operands[0] = mips_subword (operands[0], 0);
5220   return mips_output_move (operands[0], operands[1]);
5221 }
5222   [(set_attr "type"     "xfer,load")
5223    (set_attr "mode"     "SF")
5224    (set_attr "length"   "4")])
5225
5226 ;; Load the high word of operand 0 from operand 1, preserving the value
5227 ;; in the low word.
5228 (define_insn "load_df_high"
5229   [(set (match_operand:DF 0 "register_operand" "=f,f")
5230         (unspec:DF [(match_operand:SI 1 "general_operand" "dJ,m")
5231                     (match_operand:DF 2 "register_operand" "0,0")]
5232                    UNSPEC_LOAD_DF_HIGH))]
5233   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_64BIT"
5234 {
5235   operands[0] = mips_subword (operands[0], 1);
5236   return mips_output_move (operands[0], operands[1]);
5237 }
5238   [(set_attr "type"     "xfer,load")
5239    (set_attr "mode"     "SF")
5240    (set_attr "length"   "4")])
5241
5242 ;; Store the high word of operand 1 in operand 0.  The corresponding
5243 ;; low-word move is done in the normal way.
5244 (define_insn "store_df_high"
5245   [(set (match_operand:SI 0 "nonimmediate_operand" "=d,m")
5246         (unspec:SI [(match_operand:DF 1 "register_operand" "f,f")]
5247                    UNSPEC_STORE_DF_HIGH))]
5248   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_64BIT"
5249 {
5250   operands[1] = mips_subword (operands[1], 1);
5251   return mips_output_move (operands[0], operands[1]);
5252 }
5253   [(set_attr "type"     "xfer,store")
5254    (set_attr "mode"     "SF")
5255    (set_attr "length"   "4")])
5256
5257 ;; Insn to initialize $gp for n32/n64 abicalls.  Operand 0 is the offset
5258 ;; of _gp from the start of this function.  Operand 1 is the incoming
5259 ;; function address.
5260 (define_insn_and_split "loadgp"
5261   [(unspec_volatile [(match_operand 0 "" "")
5262                      (match_operand 1 "register_operand" "")] UNSPEC_LOADGP)]
5263   "TARGET_ABICALLS && TARGET_NEWABI"
5264   "#"
5265   ""
5266   [(set (match_dup 2) (match_dup 3))
5267    (set (match_dup 2) (match_dup 4))
5268    (set (match_dup 2) (match_dup 5))]
5269 {
5270   operands[2] = pic_offset_table_rtx;
5271   operands[3] = gen_rtx_HIGH (Pmode, operands[0]);
5272   operands[4] = gen_rtx_PLUS (Pmode, operands[2], operands[1]);
5273   operands[5] = gen_rtx_LO_SUM (Pmode, operands[2], operands[0]);
5274 }
5275   [(set_attr "length" "12")])
5276
5277 ;; The use of gp is hidden when not using explicit relocations.
5278 ;; This blockage instruction prevents the gp load from being
5279 ;; scheduled after an implicit use of gp.  It also prevents
5280 ;; the load from being deleted as dead.
5281 (define_insn "loadgp_blockage"
5282   [(unspec_volatile [(reg:DI 28)] UNSPEC_BLOCKAGE)]
5283   ""
5284   ""
5285   [(set_attr "type"     "unknown")
5286    (set_attr "mode"     "none")
5287    (set_attr "length"   "0")])
5288
5289 ;; Emit a .cprestore directive, which expands to a single store instruction.
5290 ;; Note that we continue to use .cprestore for explicit reloc code so that
5291 ;; jals inside inlines asms will work correctly.
5292 (define_insn "cprestore"
5293   [(unspec_volatile [(match_operand 0 "const_int_operand" "")]
5294                     UNSPEC_CPRESTORE)]
5295   ""
5296   ".cprestore\t%0"
5297   [(set_attr "type" "store")
5298    (set_attr "length" "4")])
5299 \f
5300 ;; Block moves, see mips.c for more details.
5301 ;; Argument 0 is the destination
5302 ;; Argument 1 is the source
5303 ;; Argument 2 is the length
5304 ;; Argument 3 is the alignment
5305
5306 (define_expand "movstrsi"
5307   [(parallel [(set (match_operand:BLK 0 "general_operand" "")
5308                    (match_operand:BLK 1 "general_operand" ""))
5309               (use (match_operand:SI 2 "" ""))
5310               (use (match_operand:SI 3 "const_int_operand" ""))])]
5311   "!TARGET_MIPS16 && !TARGET_MEMCPY"
5312 {
5313   if (mips_expand_block_move (operands[0], operands[1], operands[2]))
5314     DONE;
5315   else
5316     FAIL;
5317 })
5318 \f
5319 ;;
5320 ;;  ....................
5321 ;;
5322 ;;      SHIFTS
5323 ;;
5324 ;;  ....................
5325
5326 ;; Many of these instructions use trivial define_expands, because we
5327 ;; want to use a different set of constraints when TARGET_MIPS16.
5328
5329 (define_expand "ashlsi3"
5330   [(set (match_operand:SI 0 "register_operand" "=d")
5331         (ashift:SI (match_operand:SI 1 "register_operand" "d")
5332                    (match_operand:SI 2 "arith_operand" "dI")))]
5333   ""
5334 {
5335   /* On the mips16, a shift of more than 8 is a four byte instruction,
5336      so, for a shift between 8 and 16, it is just as fast to do two
5337      shifts of 8 or less.  If there is a lot of shifting going on, we
5338      may win in CSE.  Otherwise combine will put the shifts back
5339      together again.  This can be called by function_arg, so we must
5340      be careful not to allocate a new register if we've reached the
5341      reload pass.  */
5342   if (TARGET_MIPS16
5343       && optimize
5344       && GET_CODE (operands[2]) == CONST_INT
5345       && INTVAL (operands[2]) > 8
5346       && INTVAL (operands[2]) <= 16
5347       && ! reload_in_progress
5348       && ! reload_completed)
5349     {
5350       rtx temp = gen_reg_rtx (SImode);
5351
5352       emit_insn (gen_ashlsi3_internal2 (temp, operands[1], GEN_INT (8)));
5353       emit_insn (gen_ashlsi3_internal2 (operands[0], temp,
5354                                         GEN_INT (INTVAL (operands[2]) - 8)));
5355       DONE;
5356     }
5357 })
5358
5359 (define_insn "ashlsi3_internal1"
5360   [(set (match_operand:SI 0 "register_operand" "=d")
5361         (ashift:SI (match_operand:SI 1 "register_operand" "d")
5362                    (match_operand:SI 2 "arith_operand" "dI")))]
5363   "!TARGET_MIPS16"
5364 {
5365   if (GET_CODE (operands[2]) == CONST_INT)
5366     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
5367
5368   return "sll\t%0,%1,%2";
5369 }
5370   [(set_attr "type"     "arith")
5371    (set_attr "mode"     "SI")])
5372
5373 (define_insn "ashlsi3_internal1_extend"
5374   [(set (match_operand:DI 0 "register_operand" "=d")
5375        (sign_extend:DI (ashift:SI (match_operand:SI 1 "register_operand" "d")
5376                                   (match_operand:SI 2 "arith_operand" "dI"))))]
5377   "TARGET_64BIT && !TARGET_MIPS16"
5378 {
5379   if (GET_CODE (operands[2]) == CONST_INT)
5380     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
5381
5382   return "sll\t%0,%1,%2";
5383 }
5384   [(set_attr "type"    "arith")
5385    (set_attr "mode"    "DI")])
5386
5387
5388 (define_insn "ashlsi3_internal2"
5389   [(set (match_operand:SI 0 "register_operand" "=d,d")
5390         (ashift:SI (match_operand:SI 1 "register_operand" "0,d")
5391                    (match_operand:SI 2 "arith_operand" "d,I")))]
5392   "TARGET_MIPS16"
5393 {
5394   if (which_alternative == 0)
5395     return "sll\t%0,%2";
5396
5397   if (GET_CODE (operands[2]) == CONST_INT)
5398     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
5399
5400   return "sll\t%0,%1,%2";
5401 }
5402   [(set_attr "type"     "arith")
5403    (set_attr "mode"     "SI")
5404    (set_attr_alternative "length"
5405                 [(const_int 4)
5406                  (if_then_else (match_operand:VOID 2 "m16_uimm3_b" "")
5407                                (const_int 4)
5408                                (const_int 8))])])
5409
5410 ;; On the mips16, we can split a 4 byte shift into 2 2 byte shifts.
5411
5412 (define_split
5413   [(set (match_operand:SI 0 "register_operand" "")
5414         (ashift:SI (match_operand:SI 1 "register_operand" "")
5415                    (match_operand:SI 2 "const_int_operand" "")))]
5416   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
5417    && GET_CODE (operands[2]) == CONST_INT
5418    && INTVAL (operands[2]) > 8
5419    && INTVAL (operands[2]) <= 16"
5420   [(set (match_dup 0) (ashift:SI (match_dup 1) (const_int 8)))
5421    (set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))]
5422   { operands[2] = GEN_INT (INTVAL (operands[2]) - 8); })
5423
5424 (define_expand "ashldi3"
5425   [(parallel [(set (match_operand:DI 0 "register_operand" "")
5426                    (ashift:DI (match_operand:DI 1 "register_operand" "")
5427                               (match_operand:SI 2 "arith_operand" "")))
5428               (clobber (match_dup  3))])]
5429   "TARGET_64BIT || (!TARGET_DEBUG_G_MODE && !TARGET_MIPS16)"
5430 {
5431   if (TARGET_64BIT)
5432     {
5433       /* On the mips16, a shift of more than 8 is a four byte
5434          instruction, so, for a shift between 8 and 16, it is just as
5435          fast to do two shifts of 8 or less.  If there is a lot of
5436          shifting going on, we may win in CSE.  Otherwise combine will
5437          put the shifts back together again.  This can be called by
5438          function_arg, so we must be careful not to allocate a new
5439          register if we've reached the reload pass.  */
5440       if (TARGET_MIPS16
5441           && optimize
5442           && GET_CODE (operands[2]) == CONST_INT
5443           && INTVAL (operands[2]) > 8
5444           && INTVAL (operands[2]) <= 16
5445           && ! reload_in_progress
5446           && ! reload_completed)
5447         {
5448           rtx temp = gen_reg_rtx (DImode);
5449
5450           emit_insn (gen_ashldi3_internal4 (temp, operands[1], GEN_INT (8)));
5451           emit_insn (gen_ashldi3_internal4 (operands[0], temp,
5452                                             GEN_INT (INTVAL (operands[2]) - 8)));
5453           DONE;
5454         }
5455
5456       emit_insn (gen_ashldi3_internal4 (operands[0], operands[1],
5457                                         operands[2]));
5458       DONE;
5459     }
5460
5461   operands[3] = gen_reg_rtx (SImode);
5462 })
5463
5464
5465 (define_insn "ashldi3_internal"
5466   [(set (match_operand:DI 0 "register_operand" "=&d")
5467         (ashift:DI (match_operand:DI 1 "register_operand" "d")
5468                    (match_operand:SI 2 "register_operand" "d")))
5469    (clobber (match_operand:SI 3 "register_operand" "=d"))]
5470   "!TARGET_64BIT && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16"
5471   "sll\t%3,%2,26\;\
5472 bgez\t%3,1f%#\;\
5473 sll\t%M0,%L1,%2\;\
5474 %(b\t3f\;\
5475 move\t%L0,%.%)\
5476 \n\n\
5477 %~1:\;\
5478 %(beq\t%3,%.,2f\;\
5479 sll\t%M0,%M1,%2%)\
5480 \n\;\
5481 subu\t%3,%.,%2\;\
5482 srl\t%3,%L1,%3\;\
5483 or\t%M0,%M0,%3\n\
5484 %~2:\;\
5485 sll\t%L0,%L1,%2\n\
5486 %~3:"
5487   [(set_attr "type"     "darith")
5488    (set_attr "mode"     "SI")
5489    (set_attr "length"   "48")])
5490
5491
5492 (define_insn "ashldi3_internal2"
5493   [(set (match_operand:DI 0 "register_operand" "=d")
5494         (ashift:DI (match_operand:DI 1 "register_operand" "d")
5495                    (match_operand:SI 2 "small_int" "IJK")))
5496    (clobber (match_operand:SI 3 "register_operand" "=d"))]
5497   "!TARGET_64BIT && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
5498    && (INTVAL (operands[2]) & 32) != 0"
5499 {
5500   operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
5501   return "sll\t%M0,%L1,%2\;move\t%L0,%.";
5502 }
5503   [(set_attr "type"     "darith")
5504    (set_attr "mode"     "DI")
5505    (set_attr "length"   "8")])
5506
5507
5508 (define_split
5509   [(set (match_operand:DI 0 "register_operand" "")
5510         (ashift:DI (match_operand:DI 1 "register_operand" "")
5511                    (match_operand:SI 2 "small_int" "")))
5512    (clobber (match_operand:SI 3 "register_operand" ""))]
5513   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_64BIT
5514    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
5515    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
5516    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
5517    && (INTVAL (operands[2]) & 32) != 0"
5518
5519   [(set (subreg:SI (match_dup 0) 4) (ashift:SI (subreg:SI (match_dup 1) 0) (match_dup 2)))
5520    (set (subreg:SI (match_dup 0) 0) (const_int 0))]
5521
5522   "operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);")
5523
5524
5525 (define_split
5526   [(set (match_operand:DI 0 "register_operand" "")
5527         (ashift:DI (match_operand:DI 1 "register_operand" "")
5528                    (match_operand:SI 2 "small_int" "")))
5529    (clobber (match_operand:SI 3 "register_operand" ""))]
5530   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_64BIT
5531    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
5532    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
5533    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
5534    && (INTVAL (operands[2]) & 32) != 0"
5535
5536   [(set (subreg:SI (match_dup 0) 0) (ashift:SI (subreg:SI (match_dup 1) 4) (match_dup 2)))
5537    (set (subreg:SI (match_dup 0) 4) (const_int 0))]
5538
5539   "operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);")
5540
5541
5542 (define_insn "ashldi3_internal3"
5543   [(set (match_operand:DI 0 "register_operand" "=d")
5544         (ashift:DI (match_operand:DI 1 "register_operand" "d")
5545                    (match_operand:SI 2 "small_int" "IJK")))
5546    (clobber (match_operand:SI 3 "register_operand" "=d"))]
5547   "!TARGET_64BIT && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
5548    && (INTVAL (operands[2]) & 63) < 32
5549    && (INTVAL (operands[2]) & 63) != 0"
5550 {
5551   int amount = INTVAL (operands[2]);
5552
5553   operands[2] = GEN_INT (amount & 31);
5554   operands[4] = GEN_INT ((-amount) & 31);
5555
5556   return "sll\t%M0,%M1,%2\;srl\t%3,%L1,%4\;or\t%M0,%M0,%3\;sll\t%L0,%L1,%2";
5557 }
5558   [(set_attr "type"     "darith")
5559    (set_attr "mode"     "DI")
5560    (set_attr "length"   "16")])
5561
5562
5563 (define_split
5564   [(set (match_operand:DI 0 "register_operand" "")
5565         (ashift:DI (match_operand:DI 1 "register_operand" "")
5566                    (match_operand:SI 2 "small_int" "")))
5567    (clobber (match_operand:SI 3 "register_operand" ""))]
5568   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_64BIT
5569    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
5570    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
5571    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
5572    && (INTVAL (operands[2]) & 63) < 32
5573    && (INTVAL (operands[2]) & 63) != 0"
5574
5575   [(set (subreg:SI (match_dup 0) 4)
5576         (ashift:SI (subreg:SI (match_dup 1) 4)
5577                    (match_dup 2)))
5578
5579    (set (match_dup 3)
5580         (lshiftrt:SI (subreg:SI (match_dup 1) 0)
5581                      (match_dup 4)))
5582
5583    (set (subreg:SI (match_dup 0) 4)
5584         (ior:SI (subreg:SI (match_dup 0) 4)
5585                 (match_dup 3)))
5586
5587    (set (subreg:SI (match_dup 0) 0)
5588         (ashift:SI (subreg:SI (match_dup 1) 0)
5589                    (match_dup 2)))]
5590 {
5591   int amount = INTVAL (operands[2]);
5592   operands[2] = GEN_INT (amount & 31);
5593   operands[4] = GEN_INT ((-amount) & 31);
5594 })
5595
5596
5597 (define_split
5598   [(set (match_operand:DI 0 "register_operand" "")
5599         (ashift:DI (match_operand:DI 1 "register_operand" "")
5600                    (match_operand:SI 2 "small_int" "")))
5601    (clobber (match_operand:SI 3 "register_operand" ""))]
5602   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_64BIT
5603    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
5604    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
5605    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
5606    && (INTVAL (operands[2]) & 63) < 32
5607    && (INTVAL (operands[2]) & 63) != 0"
5608
5609   [(set (subreg:SI (match_dup 0) 0)
5610         (ashift:SI (subreg:SI (match_dup 1) 0)
5611                    (match_dup 2)))
5612
5613    (set (match_dup 3)
5614         (lshiftrt:SI (subreg:SI (match_dup 1) 4)
5615                      (match_dup 4)))
5616
5617    (set (subreg:SI (match_dup 0) 0)
5618         (ior:SI (subreg:SI (match_dup 0) 0)
5619                 (match_dup 3)))
5620
5621    (set (subreg:SI (match_dup 0) 4)
5622         (ashift:SI (subreg:SI (match_dup 1) 4)
5623                    (match_dup 2)))]
5624 {
5625   int amount = INTVAL (operands[2]);
5626   operands[2] = GEN_INT (amount & 31);
5627   operands[4] = GEN_INT ((-amount) & 31);
5628 })
5629
5630
5631 (define_insn "ashldi3_internal4"
5632   [(set (match_operand:DI 0 "register_operand" "=d")
5633         (ashift:DI (match_operand:DI 1 "register_operand" "d")
5634                    (match_operand:SI 2 "arith_operand" "dI")))]
5635   "TARGET_64BIT && !TARGET_MIPS16"
5636 {
5637   if (GET_CODE (operands[2]) == CONST_INT)
5638     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
5639
5640   return "dsll\t%0,%1,%2";
5641 }
5642   [(set_attr "type"     "arith")
5643    (set_attr "mode"     "DI")])
5644
5645 (define_insn ""
5646   [(set (match_operand:DI 0 "register_operand" "=d,d")
5647         (ashift:DI (match_operand:DI 1 "register_operand" "0,d")
5648                    (match_operand:SI 2 "arith_operand" "d,I")))]
5649   "TARGET_64BIT && TARGET_MIPS16"
5650 {
5651   if (which_alternative == 0)
5652     return "dsll\t%0,%2";
5653
5654   if (GET_CODE (operands[2]) == CONST_INT)
5655     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
5656
5657   return "dsll\t%0,%1,%2";
5658 }
5659   [(set_attr "type"     "arith")
5660    (set_attr "mode"     "DI")
5661    (set_attr_alternative "length"
5662                 [(const_int 4)
5663                  (if_then_else (match_operand:VOID 2 "m16_uimm3_b" "")
5664                                (const_int 4)
5665                                (const_int 8))])])
5666
5667
5668 ;; On the mips16, we can split a 4 byte shift into 2 2 byte shifts.
5669
5670 (define_split
5671   [(set (match_operand:DI 0 "register_operand" "")
5672         (ashift:DI (match_operand:DI 1 "register_operand" "")
5673                    (match_operand:SI 2 "const_int_operand" "")))]
5674   "TARGET_MIPS16 && TARGET_64BIT && !TARGET_DEBUG_D_MODE
5675    && reload_completed
5676    && GET_CODE (operands[2]) == CONST_INT
5677    && INTVAL (operands[2]) > 8
5678    && INTVAL (operands[2]) <= 16"
5679   [(set (match_dup 0) (ashift:DI (match_dup 1) (const_int 8)))
5680    (set (match_dup 0) (ashift:DI (match_dup 0) (match_dup 2)))]
5681   { operands[2] = GEN_INT (INTVAL (operands[2]) - 8); })
5682
5683 (define_expand "ashrsi3"
5684   [(set (match_operand:SI 0 "register_operand" "=d")
5685         (ashiftrt:SI (match_operand:SI 1 "register_operand" "d")
5686                      (match_operand:SI 2 "arith_operand" "dI")))]
5687   ""
5688 {
5689   /* On the mips16, a shift of more than 8 is a four byte instruction,
5690      so, for a shift between 8 and 16, it is just as fast to do two
5691      shifts of 8 or less.  If there is a lot of shifting going on, we
5692      may win in CSE.  Otherwise combine will put the shifts back
5693      together again.  */
5694   if (TARGET_MIPS16
5695       && optimize
5696       && GET_CODE (operands[2]) == CONST_INT
5697       && INTVAL (operands[2]) > 8
5698       && INTVAL (operands[2]) <= 16)
5699     {
5700       rtx temp = gen_reg_rtx (SImode);
5701
5702       emit_insn (gen_ashrsi3_internal2 (temp, operands[1], GEN_INT (8)));
5703       emit_insn (gen_ashrsi3_internal2 (operands[0], temp,
5704                                         GEN_INT (INTVAL (operands[2]) - 8)));
5705       DONE;
5706     }
5707 })
5708
5709 (define_insn "ashrsi3_internal1"
5710   [(set (match_operand:SI 0 "register_operand" "=d")
5711         (ashiftrt:SI (match_operand:SI 1 "register_operand" "d")
5712                      (match_operand:SI 2 "arith_operand" "dI")))]
5713   "!TARGET_MIPS16"
5714 {
5715   if (GET_CODE (operands[2]) == CONST_INT)
5716     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
5717
5718   return "sra\t%0,%1,%2";
5719 }
5720   [(set_attr "type"     "arith")
5721    (set_attr "mode"     "SI")])
5722
5723 (define_insn "ashrsi3_internal2"
5724   [(set (match_operand:SI 0 "register_operand" "=d,d")
5725         (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,d")
5726                      (match_operand:SI 2 "arith_operand" "d,I")))]
5727   "TARGET_MIPS16"
5728 {
5729   if (which_alternative == 0)
5730     return "sra\t%0,%2";
5731
5732   if (GET_CODE (operands[2]) == CONST_INT)
5733     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
5734
5735   return "sra\t%0,%1,%2";
5736 }
5737   [(set_attr "type"     "arith")
5738    (set_attr "mode"     "SI")
5739    (set_attr_alternative "length"
5740                 [(const_int 4)
5741                  (if_then_else (match_operand:VOID 2 "m16_uimm3_b" "")
5742                                (const_int 4)
5743                                (const_int 8))])])
5744
5745
5746 ;; On the mips16, we can split a 4 byte shift into 2 2 byte shifts.
5747
5748 (define_split
5749   [(set (match_operand:SI 0 "register_operand" "")
5750         (ashiftrt:SI (match_operand:SI 1 "register_operand" "")
5751                      (match_operand:SI 2 "const_int_operand" "")))]
5752   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
5753    && GET_CODE (operands[2]) == CONST_INT
5754    && INTVAL (operands[2]) > 8
5755    && INTVAL (operands[2]) <= 16"
5756   [(set (match_dup 0) (ashiftrt:SI (match_dup 1) (const_int 8)))
5757    (set (match_dup 0) (ashiftrt:SI (match_dup 0) (match_dup 2)))]
5758   { operands[2] = GEN_INT (INTVAL (operands[2]) - 8); })
5759
5760 (define_expand "ashrdi3"
5761   [(parallel [(set (match_operand:DI 0 "register_operand" "")
5762                    (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
5763                                 (match_operand:SI 2 "arith_operand" "")))
5764               (clobber (match_dup  3))])]
5765   "TARGET_64BIT || (!TARGET_DEBUG_G_MODE && !TARGET_MIPS16)"
5766 {
5767   if (TARGET_64BIT)
5768     {
5769       /* On the mips16, a shift of more than 8 is a four byte
5770          instruction, so, for a shift between 8 and 16, it is just as
5771          fast to do two shifts of 8 or less.  If there is a lot of
5772          shifting going on, we may win in CSE.  Otherwise combine will
5773          put the shifts back together again.  */
5774       if (TARGET_MIPS16
5775           && optimize
5776           && GET_CODE (operands[2]) == CONST_INT
5777           && INTVAL (operands[2]) > 8
5778           && INTVAL (operands[2]) <= 16)
5779         {
5780           rtx temp = gen_reg_rtx (DImode);
5781
5782           emit_insn (gen_ashrdi3_internal4 (temp, operands[1], GEN_INT (8)));
5783           emit_insn (gen_ashrdi3_internal4 (operands[0], temp,
5784                                             GEN_INT (INTVAL (operands[2]) - 8)));
5785           DONE;
5786         }
5787
5788       emit_insn (gen_ashrdi3_internal4 (operands[0], operands[1],
5789                                         operands[2]));
5790       DONE;
5791     }
5792
5793   operands[3] = gen_reg_rtx (SImode);
5794 })
5795
5796
5797 (define_insn "ashrdi3_internal"
5798   [(set (match_operand:DI 0 "register_operand" "=&d")
5799         (ashiftrt:DI (match_operand:DI 1 "register_operand" "d")
5800                      (match_operand:SI 2 "register_operand" "d")))
5801    (clobber (match_operand:SI 3 "register_operand" "=d"))]
5802   "!TARGET_64BIT && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16"
5803   "sll\t%3,%2,26\;\
5804 bgez\t%3,1f%#\;\
5805 sra\t%L0,%M1,%2\;\
5806 %(b\t3f\;\
5807 sra\t%M0,%M1,31%)\
5808 \n\n\
5809 %~1:\;\
5810 %(beq\t%3,%.,2f\;\
5811 srl\t%L0,%L1,%2%)\
5812 \n\;\
5813 subu\t%3,%.,%2\;\
5814 sll\t%3,%M1,%3\;\
5815 or\t%L0,%L0,%3\n\
5816 %~2:\;\
5817 sra\t%M0,%M1,%2\n\
5818 %~3:"
5819   [(set_attr "type"     "darith")
5820    (set_attr "mode"     "DI")
5821    (set_attr "length"   "48")])
5822
5823
5824 (define_insn "ashrdi3_internal2"
5825   [(set (match_operand:DI 0 "register_operand" "=d")
5826         (ashiftrt:DI (match_operand:DI 1 "register_operand" "d")
5827                      (match_operand:SI 2 "small_int" "IJK")))
5828    (clobber (match_operand:SI 3 "register_operand" "=d"))]
5829   "!TARGET_64BIT && !TARGET_DEBUG_G_MODE && (INTVAL (operands[2]) & 32) != 0"
5830 {
5831   operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
5832   return "sra\t%L0,%M1,%2\;sra\t%M0,%M1,31";
5833 }
5834   [(set_attr "type"     "darith")
5835    (set_attr "mode"     "DI")
5836    (set_attr "length"   "8")])
5837
5838
5839 (define_split
5840   [(set (match_operand:DI 0 "register_operand" "")
5841         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
5842                      (match_operand:SI 2 "small_int" "")))
5843    (clobber (match_operand:SI 3 "register_operand" ""))]
5844   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_64BIT
5845    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
5846    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
5847    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
5848    && (INTVAL (operands[2]) & 32) != 0"
5849
5850   [(set (subreg:SI (match_dup 0) 0) (ashiftrt:SI (subreg:SI (match_dup 1) 4) (match_dup 2)))
5851    (set (subreg:SI (match_dup 0) 4) (ashiftrt:SI (subreg:SI (match_dup 1) 4) (const_int 31)))]
5852
5853   "operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);")
5854
5855
5856 (define_split
5857   [(set (match_operand:DI 0 "register_operand" "")
5858         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
5859                      (match_operand:SI 2 "small_int" "")))
5860    (clobber (match_operand:SI 3 "register_operand" ""))]
5861   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_64BIT
5862    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
5863    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
5864    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
5865    && (INTVAL (operands[2]) & 32) != 0"
5866
5867   [(set (subreg:SI (match_dup 0) 4) (ashiftrt:SI (subreg:SI (match_dup 1) 0) (match_dup 2)))
5868    (set (subreg:SI (match_dup 0) 0) (ashiftrt:SI (subreg:SI (match_dup 1) 0) (const_int 31)))]
5869
5870   "operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);")
5871
5872
5873 (define_insn "ashrdi3_internal3"
5874   [(set (match_operand:DI 0 "register_operand" "=d")
5875         (ashiftrt:DI (match_operand:DI 1 "register_operand" "d")
5876                      (match_operand:SI 2 "small_int" "IJK")))
5877    (clobber (match_operand:SI 3 "register_operand" "=d"))]
5878   "!TARGET_64BIT && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
5879    && (INTVAL (operands[2]) & 63) < 32
5880    && (INTVAL (operands[2]) & 63) != 0"
5881 {
5882   int amount = INTVAL (operands[2]);
5883
5884   operands[2] = GEN_INT (amount & 31);
5885   operands[4] = GEN_INT ((-amount) & 31);
5886
5887   return "srl\t%L0,%L1,%2\;sll\t%3,%M1,%4\;or\t%L0,%L0,%3\;sra\t%M0,%M1,%2";
5888 }
5889   [(set_attr "type"     "darith")
5890    (set_attr "mode"     "DI")
5891    (set_attr "length"   "16")])
5892
5893
5894 (define_split
5895   [(set (match_operand:DI 0 "register_operand" "")
5896         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
5897                      (match_operand:SI 2 "small_int" "")))
5898    (clobber (match_operand:SI 3 "register_operand" ""))]
5899   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_64BIT
5900    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
5901    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
5902    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
5903    && (INTVAL (operands[2]) & 63) < 32
5904    && (INTVAL (operands[2]) & 63) != 0"
5905
5906   [(set (subreg:SI (match_dup 0) 0)
5907         (lshiftrt:SI (subreg:SI (match_dup 1) 0)
5908                      (match_dup 2)))
5909
5910    (set (match_dup 3)
5911         (ashift:SI (subreg:SI (match_dup 1) 4)
5912                    (match_dup 4)))
5913
5914    (set (subreg:SI (match_dup 0) 0)
5915         (ior:SI (subreg:SI (match_dup 0) 0)
5916                 (match_dup 3)))
5917
5918    (set (subreg:SI (match_dup 0) 4)
5919         (ashiftrt:SI (subreg:SI (match_dup 1) 4)
5920                      (match_dup 2)))]
5921 {
5922   int amount = INTVAL (operands[2]);
5923   operands[2] = GEN_INT (amount & 31);
5924   operands[4] = GEN_INT ((-amount) & 31);
5925 })
5926
5927
5928 (define_split
5929   [(set (match_operand:DI 0 "register_operand" "")
5930         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
5931                      (match_operand:SI 2 "small_int" "")))
5932    (clobber (match_operand:SI 3 "register_operand" ""))]
5933   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_64BIT
5934    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
5935    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
5936    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
5937    && (INTVAL (operands[2]) & 63) < 32
5938    && (INTVAL (operands[2]) & 63) != 0"
5939
5940   [(set (subreg:SI (match_dup 0) 4)
5941         (lshiftrt:SI (subreg:SI (match_dup 1) 4)
5942                      (match_dup 2)))
5943
5944    (set (match_dup 3)
5945         (ashift:SI (subreg:SI (match_dup 1) 0)
5946                    (match_dup 4)))
5947
5948    (set (subreg:SI (match_dup 0) 4)
5949         (ior:SI (subreg:SI (match_dup 0) 4)
5950                 (match_dup 3)))
5951
5952    (set (subreg:SI (match_dup 0) 0)
5953         (ashiftrt:SI (subreg:SI (match_dup 1) 0)
5954                      (match_dup 2)))]
5955 {
5956   int amount = INTVAL (operands[2]);
5957   operands[2] = GEN_INT (amount & 31);
5958   operands[4] = GEN_INT ((-amount) & 31);
5959 })
5960
5961
5962 (define_insn "ashrdi3_internal4"
5963   [(set (match_operand:DI 0 "register_operand" "=d")
5964         (ashiftrt:DI (match_operand:DI 1 "register_operand" "d")
5965                      (match_operand:SI 2 "arith_operand" "dI")))]
5966   "TARGET_64BIT && !TARGET_MIPS16"
5967 {
5968   if (GET_CODE (operands[2]) == CONST_INT)
5969     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
5970
5971   return "dsra\t%0,%1,%2";
5972 }
5973   [(set_attr "type"     "arith")
5974    (set_attr "mode"     "DI")])
5975
5976 (define_insn ""
5977   [(set (match_operand:DI 0 "register_operand" "=d,d")
5978         (ashiftrt:DI (match_operand:DI 1 "register_operand" "0,0")
5979                      (match_operand:SI 2 "arith_operand" "d,I")))]
5980   "TARGET_64BIT && TARGET_MIPS16"
5981 {
5982   if (GET_CODE (operands[2]) == CONST_INT)
5983     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
5984
5985   return "dsra\t%0,%2";
5986 }
5987   [(set_attr "type"     "arith")
5988    (set_attr "mode"     "DI")
5989    (set_attr_alternative "length"
5990                 [(const_int 4)
5991                  (if_then_else (match_operand:VOID 2 "m16_uimm3_b" "")
5992                                (const_int 4)
5993                                (const_int 8))])])
5994
5995 ;; On the mips16, we can split a 4 byte shift into 2 2 byte shifts.
5996
5997 (define_split
5998   [(set (match_operand:DI 0 "register_operand" "")
5999         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
6000                      (match_operand:SI 2 "const_int_operand" "")))]
6001   "TARGET_MIPS16 && TARGET_64BIT && !TARGET_DEBUG_D_MODE
6002    && reload_completed
6003    && GET_CODE (operands[2]) == CONST_INT
6004    && INTVAL (operands[2]) > 8
6005    && INTVAL (operands[2]) <= 16"
6006   [(set (match_dup 0) (ashiftrt:DI (match_dup 1) (const_int 8)))
6007    (set (match_dup 0) (ashiftrt:DI (match_dup 0) (match_dup 2)))]
6008   { operands[2] = GEN_INT (INTVAL (operands[2]) - 8); })
6009
6010 (define_expand "lshrsi3"
6011   [(set (match_operand:SI 0 "register_operand" "=d")
6012         (lshiftrt:SI (match_operand:SI 1 "register_operand" "d")
6013                      (match_operand:SI 2 "arith_operand" "dI")))]
6014   ""
6015 {
6016   /* On the mips16, a shift of more than 8 is a four byte instruction,
6017      so, for a shift between 8 and 16, it is just as fast to do two
6018      shifts of 8 or less.  If there is a lot of shifting going on, we
6019      may win in CSE.  Otherwise combine will put the shifts back
6020      together again.  */
6021   if (TARGET_MIPS16
6022       && optimize
6023       && GET_CODE (operands[2]) == CONST_INT
6024       && INTVAL (operands[2]) > 8
6025       && INTVAL (operands[2]) <= 16)
6026     {
6027       rtx temp = gen_reg_rtx (SImode);
6028
6029       emit_insn (gen_lshrsi3_internal2 (temp, operands[1], GEN_INT (8)));
6030       emit_insn (gen_lshrsi3_internal2 (operands[0], temp,
6031                                         GEN_INT (INTVAL (operands[2]) - 8)));
6032       DONE;
6033     }
6034 })
6035
6036 (define_insn "lshrsi3_internal1"
6037   [(set (match_operand:SI 0 "register_operand" "=d")
6038         (lshiftrt:SI (match_operand:SI 1 "register_operand" "d")
6039                      (match_operand:SI 2 "arith_operand" "dI")))]
6040   "!TARGET_MIPS16"
6041 {
6042   if (GET_CODE (operands[2]) == CONST_INT)
6043     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
6044
6045   return "srl\t%0,%1,%2";
6046 }
6047   [(set_attr "type"     "arith")
6048    (set_attr "mode"     "SI")])
6049
6050 (define_insn "lshrsi3_internal2"
6051   [(set (match_operand:SI 0 "register_operand" "=d,d")
6052         (lshiftrt:SI (match_operand:SI 1 "register_operand" "0,d")
6053                      (match_operand:SI 2 "arith_operand" "d,I")))]
6054   "TARGET_MIPS16"
6055 {
6056   if (which_alternative == 0)
6057     return "srl\t%0,%2";
6058
6059   if (GET_CODE (operands[2]) == CONST_INT)
6060     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
6061
6062   return "srl\t%0,%1,%2";
6063 }
6064   [(set_attr "type"     "arith")
6065    (set_attr "mode"     "SI")
6066    (set_attr_alternative "length"
6067                 [(const_int 4)
6068                  (if_then_else (match_operand:VOID 2 "m16_uimm3_b" "")
6069                                (const_int 4)
6070                                (const_int 8))])])
6071
6072
6073 ;; On the mips16, we can split a 4 byte shift into 2 2 byte shifts.
6074
6075 (define_split
6076   [(set (match_operand:SI 0 "register_operand" "")
6077         (lshiftrt:SI (match_operand:SI 1 "register_operand" "")
6078                      (match_operand:SI 2 "const_int_operand" "")))]
6079   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
6080    && GET_CODE (operands[2]) == CONST_INT
6081    && INTVAL (operands[2]) > 8
6082    && INTVAL (operands[2]) <= 16"
6083   [(set (match_dup 0) (lshiftrt:SI (match_dup 1) (const_int 8)))
6084    (set (match_dup 0) (lshiftrt:SI (match_dup 0) (match_dup 2)))]
6085   { operands[2] = GEN_INT (INTVAL (operands[2]) - 8); })
6086
6087 ;; If we load a byte on the mips16 as a bitfield, the resulting
6088 ;; sequence of instructions is too complicated for combine, because it
6089 ;; involves four instructions: a load, a shift, a constant load into a
6090 ;; register, and an and (the key problem here is that the mips16 does
6091 ;; not have and immediate).  We recognize a shift of a load in order
6092 ;; to make it simple enough for combine to understand.
6093 ;;
6094 ;; The length here is the worst case: the length of the split version
6095 ;; will be more accurate. 
6096 (define_insn_and_split ""
6097   [(set (match_operand:SI 0 "register_operand" "=d")
6098         (lshiftrt:SI (match_operand:SI 1 "memory_operand" "m")
6099                      (match_operand:SI 2 "immediate_operand" "I")))]
6100   "TARGET_MIPS16"
6101   "#"
6102   ""
6103   [(set (match_dup 0) (match_dup 1))
6104    (set (match_dup 0) (lshiftrt:SI (match_dup 0) (match_dup 2)))]
6105   ""
6106   [(set_attr "type"     "load")
6107    (set_attr "mode"     "SI")
6108    (set_attr "length"   "16")])
6109
6110 (define_expand "lshrdi3"
6111   [(parallel [(set (match_operand:DI 0 "register_operand" "")
6112                    (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
6113                                 (match_operand:SI 2 "arith_operand" "")))
6114               (clobber (match_dup  3))])]
6115   "TARGET_64BIT || (!TARGET_DEBUG_G_MODE && !TARGET_MIPS16)"
6116 {
6117   if (TARGET_64BIT)
6118     {
6119       /* On the mips16, a shift of more than 8 is a four byte
6120          instruction, so, for a shift between 8 and 16, it is just as
6121          fast to do two shifts of 8 or less.  If there is a lot of
6122          shifting going on, we may win in CSE.  Otherwise combine will
6123          put the shifts back together again.  */
6124       if (TARGET_MIPS16
6125           && optimize
6126           && GET_CODE (operands[2]) == CONST_INT
6127           && INTVAL (operands[2]) > 8
6128           && INTVAL (operands[2]) <= 16)
6129         {
6130           rtx temp = gen_reg_rtx (DImode);
6131
6132           emit_insn (gen_lshrdi3_internal4 (temp, operands[1], GEN_INT (8)));
6133           emit_insn (gen_lshrdi3_internal4 (operands[0], temp,
6134                                             GEN_INT (INTVAL (operands[2]) - 8)));
6135           DONE;
6136         }
6137
6138       emit_insn (gen_lshrdi3_internal4 (operands[0], operands[1],
6139                                         operands[2]));
6140       DONE;
6141     }
6142
6143   operands[3] = gen_reg_rtx (SImode);
6144 })
6145
6146
6147 (define_insn "lshrdi3_internal"
6148   [(set (match_operand:DI 0 "register_operand" "=&d")
6149         (lshiftrt:DI (match_operand:DI 1 "register_operand" "d")
6150                      (match_operand:SI 2 "register_operand" "d")))
6151    (clobber (match_operand:SI 3 "register_operand" "=d"))]
6152   "!TARGET_64BIT && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16"
6153   "sll\t%3,%2,26\;\
6154 bgez\t%3,1f%#\;\
6155 srl\t%L0,%M1,%2\;\
6156 %(b\t3f\;\
6157 move\t%M0,%.%)\
6158 \n\n\
6159 %~1:\;\
6160 %(beq\t%3,%.,2f\;\
6161 srl\t%L0,%L1,%2%)\
6162 \n\;\
6163 subu\t%3,%.,%2\;\
6164 sll\t%3,%M1,%3\;\
6165 or\t%L0,%L0,%3\n\
6166 %~2:\;\
6167 srl\t%M0,%M1,%2\n\
6168 %~3:"
6169   [(set_attr "type"     "darith")
6170    (set_attr "mode"     "DI")
6171    (set_attr "length"   "48")])
6172
6173
6174 (define_insn "lshrdi3_internal2"
6175   [(set (match_operand:DI 0 "register_operand" "=d")
6176         (lshiftrt:DI (match_operand:DI 1 "register_operand" "d")
6177                      (match_operand:SI 2 "small_int" "IJK")))
6178    (clobber (match_operand:SI 3 "register_operand" "=d"))]
6179   "!TARGET_64BIT && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
6180    && (INTVAL (operands[2]) & 32) != 0"
6181 {
6182   operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
6183   return "srl\t%L0,%M1,%2\;move\t%M0,%.";
6184 }
6185   [(set_attr "type"     "darith")
6186    (set_attr "mode"     "DI")
6187    (set_attr "length"   "8")])
6188
6189
6190 (define_split
6191   [(set (match_operand:DI 0 "register_operand" "")
6192         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
6193                      (match_operand:SI 2 "small_int" "")))
6194    (clobber (match_operand:SI 3 "register_operand" ""))]
6195   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_64BIT
6196    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
6197    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
6198    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
6199    && (INTVAL (operands[2]) & 32) != 0"
6200
6201   [(set (subreg:SI (match_dup 0) 0) (lshiftrt:SI (subreg:SI (match_dup 1) 4) (match_dup 2)))
6202    (set (subreg:SI (match_dup 0) 4) (const_int 0))]
6203
6204   "operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);")
6205
6206
6207 (define_split
6208   [(set (match_operand:DI 0 "register_operand" "")
6209         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
6210                      (match_operand:SI 2 "small_int" "")))
6211    (clobber (match_operand:SI 3 "register_operand" ""))]
6212   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_64BIT
6213    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
6214    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
6215    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
6216    && (INTVAL (operands[2]) & 32) != 0"
6217
6218   [(set (subreg:SI (match_dup 0) 4) (lshiftrt:SI (subreg:SI (match_dup 1) 0) (match_dup 2)))
6219    (set (subreg:SI (match_dup 0) 0) (const_int 0))]
6220
6221   "operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);")
6222
6223
6224 (define_insn "lshrdi3_internal3"
6225   [(set (match_operand:DI 0 "register_operand" "=d")
6226         (lshiftrt:DI (match_operand:DI 1 "register_operand" "d")
6227                    (match_operand:SI 2 "small_int" "IJK")))
6228    (clobber (match_operand:SI 3 "register_operand" "=d"))]
6229   "!TARGET_64BIT && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
6230    && (INTVAL (operands[2]) & 63) < 32
6231    && (INTVAL (operands[2]) & 63) != 0"
6232 {
6233   int amount = INTVAL (operands[2]);
6234
6235   operands[2] = GEN_INT (amount & 31);
6236   operands[4] = GEN_INT ((-amount) & 31);
6237
6238   return "srl\t%L0,%L1,%2\;sll\t%3,%M1,%4\;or\t%L0,%L0,%3\;srl\t%M0,%M1,%2";
6239 }
6240   [(set_attr "type"     "darith")
6241    (set_attr "mode"     "DI")
6242    (set_attr "length"   "16")])
6243
6244
6245 (define_split
6246   [(set (match_operand:DI 0 "register_operand" "")
6247         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
6248                      (match_operand:SI 2 "small_int" "")))
6249    (clobber (match_operand:SI 3 "register_operand" ""))]
6250   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_64BIT
6251    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
6252    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
6253    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
6254    && (INTVAL (operands[2]) & 63) < 32
6255    && (INTVAL (operands[2]) & 63) != 0"
6256
6257   [(set (subreg:SI (match_dup 0) 0)
6258         (lshiftrt:SI (subreg:SI (match_dup 1) 0)
6259                      (match_dup 2)))
6260
6261    (set (match_dup 3)
6262         (ashift:SI (subreg:SI (match_dup 1) 4)
6263                    (match_dup 4)))
6264
6265    (set (subreg:SI (match_dup 0) 0)
6266         (ior:SI (subreg:SI (match_dup 0) 0)
6267                 (match_dup 3)))
6268
6269    (set (subreg:SI (match_dup 0) 4)
6270         (lshiftrt:SI (subreg:SI (match_dup 1) 4)
6271                      (match_dup 2)))]
6272 {
6273   int amount = INTVAL (operands[2]);
6274   operands[2] = GEN_INT (amount & 31);
6275   operands[4] = GEN_INT ((-amount) & 31);
6276 })
6277
6278
6279 (define_split
6280   [(set (match_operand:DI 0 "register_operand" "")
6281         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
6282                      (match_operand:SI 2 "small_int" "")))
6283    (clobber (match_operand:SI 3 "register_operand" ""))]
6284   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_64BIT
6285    && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE && !TARGET_MIPS16
6286    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
6287    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
6288    && (INTVAL (operands[2]) & 63) < 32
6289    && (INTVAL (operands[2]) & 63) != 0"
6290
6291   [(set (subreg:SI (match_dup 0) 4)
6292         (lshiftrt:SI (subreg:SI (match_dup 1) 4)
6293                      (match_dup 2)))
6294
6295    (set (match_dup 3)
6296         (ashift:SI (subreg:SI (match_dup 1) 0)
6297                    (match_dup 4)))
6298
6299    (set (subreg:SI (match_dup 0) 4)
6300         (ior:SI (subreg:SI (match_dup 0) 4)
6301                 (match_dup 3)))
6302
6303    (set (subreg:SI (match_dup 0) 0)
6304         (lshiftrt:SI (subreg:SI (match_dup 1) 0)
6305                      (match_dup 2)))]
6306 {
6307   int amount = INTVAL (operands[2]);
6308   operands[2] = GEN_INT (amount & 31);
6309   operands[4] = GEN_INT ((-amount) & 31);
6310 })
6311
6312
6313 (define_insn "lshrdi3_internal4"
6314   [(set (match_operand:DI 0 "register_operand" "=d")
6315         (lshiftrt:DI (match_operand:DI 1 "register_operand" "d")
6316                      (match_operand:SI 2 "arith_operand" "dI")))]
6317   "TARGET_64BIT && !TARGET_MIPS16"
6318 {
6319   if (GET_CODE (operands[2]) == CONST_INT)
6320     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
6321
6322   return "dsrl\t%0,%1,%2";
6323 }
6324   [(set_attr "type"     "arith")
6325    (set_attr "mode"     "DI")])
6326
6327 (define_insn ""
6328   [(set (match_operand:DI 0 "register_operand" "=d,d")
6329         (lshiftrt:DI (match_operand:DI 1 "register_operand" "0,0")
6330                      (match_operand:SI 2 "arith_operand" "d,I")))]
6331   "TARGET_64BIT && TARGET_MIPS16"
6332 {
6333   if (GET_CODE (operands[2]) == CONST_INT)
6334     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
6335
6336   return "dsrl\t%0,%2";
6337 }
6338   [(set_attr "type"     "arith")
6339    (set_attr "mode"     "DI")
6340    (set_attr_alternative "length"
6341                 [(const_int 4)
6342                  (if_then_else (match_operand:VOID 2 "m16_uimm3_b" "")
6343                                (const_int 4)
6344                                (const_int 8))])])
6345
6346 (define_insn "rotrsi3"
6347   [(set (match_operand:SI              0 "register_operand" "=d")
6348         (rotatert:SI (match_operand:SI 1 "register_operand" "d")
6349                      (match_operand:SI 2 "arith_operand"    "dn")))]
6350   "ISA_HAS_ROTR_SI"
6351 {
6352   if (TARGET_SR71K && GET_CODE (operands[2]) != CONST_INT)
6353     return "rorv\t%0,%1,%2";
6354
6355   if ((GET_CODE (operands[2]) == CONST_INT)
6356       && (INTVAL (operands[2]) < 0 || INTVAL (operands[2]) >= 32))
6357     abort ();
6358
6359   return "ror\t%0,%1,%2";
6360 }
6361   [(set_attr "type"     "arith")
6362    (set_attr "mode"     "SI")])
6363
6364 (define_insn "rotrdi3"
6365   [(set (match_operand:DI              0 "register_operand" "=d")
6366         (rotatert:DI (match_operand:DI 1 "register_operand" "d")
6367                      (match_operand:DI 2 "arith_operand"    "dn")))]
6368   "ISA_HAS_ROTR_DI"
6369 {
6370   if (TARGET_SR71K)
6371     {
6372       if (GET_CODE (operands[2]) != CONST_INT)
6373         return "drorv\t%0,%1,%2";
6374
6375       if (INTVAL (operands[2]) >= 32 && INTVAL (operands[2]) <= 63)
6376         return "dror32\t%0,%1,%2";
6377     }
6378
6379   if ((GET_CODE (operands[2]) == CONST_INT)
6380       && (INTVAL (operands[2]) < 0 || INTVAL (operands[2]) >= 64))
6381     abort ();
6382
6383   return "dror\t%0,%1,%2";
6384 }
6385   [(set_attr "type"     "arith")
6386    (set_attr "mode"     "DI")])
6387
6388
6389 ;; On the mips16, we can split a 4 byte shift into 2 2 byte shifts.
6390
6391 (define_split
6392   [(set (match_operand:DI 0 "register_operand" "")
6393         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
6394                      (match_operand:SI 2 "const_int_operand" "")))]
6395   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
6396    && GET_CODE (operands[2]) == CONST_INT
6397    && INTVAL (operands[2]) > 8
6398    && INTVAL (operands[2]) <= 16"
6399   [(set (match_dup 0) (lshiftrt:DI (match_dup 1) (const_int 8)))
6400    (set (match_dup 0) (lshiftrt:DI (match_dup 0) (match_dup 2)))]
6401   { operands[2] = GEN_INT (INTVAL (operands[2]) - 8); })
6402 \f
6403 ;;
6404 ;;  ....................
6405 ;;
6406 ;;      COMPARISONS
6407 ;;
6408 ;;  ....................
6409
6410 ;; Flow here is rather complex:
6411 ;;
6412 ;;  1)  The cmp{si,di,sf,df} routine is called.  It deposits the
6413 ;;      arguments into the branch_cmp array, and the type into
6414 ;;      branch_type.  No RTL is generated.
6415 ;;
6416 ;;  2)  The appropriate branch define_expand is called, which then
6417 ;;      creates the appropriate RTL for the comparison and branch.
6418 ;;      Different CC modes are used, based on what type of branch is
6419 ;;      done, so that we can constrain things appropriately.  There
6420 ;;      are assumptions in the rest of GCC that break if we fold the
6421 ;;      operands into the branches for integer operations, and use cc0
6422 ;;      for floating point, so we use the fp status register instead.
6423 ;;      If needed, an appropriate temporary is created to hold the
6424 ;;      of the integer compare.
6425
6426 (define_expand "cmpsi"
6427   [(set (cc0)
6428         (compare:CC (match_operand:SI 0 "register_operand" "")
6429                     (match_operand:SI 1 "arith_operand" "")))]
6430   ""
6431 {
6432   branch_cmp[0] = operands[0];
6433   branch_cmp[1] = operands[1];
6434   branch_type = CMP_SI;
6435   DONE;
6436 })
6437
6438 (define_expand "tstsi"
6439   [(set (cc0)
6440         (match_operand:SI 0 "register_operand" ""))]
6441   ""
6442 {
6443   branch_cmp[0] = operands[0];
6444   branch_cmp[1] = const0_rtx;
6445   branch_type = CMP_SI;
6446   DONE;
6447 })
6448
6449 (define_expand "cmpdi"
6450   [(set (cc0)
6451         (compare:CC (match_operand:DI 0 "register_operand" "")
6452                     (match_operand:DI 1 "arith_operand" "")))]
6453   "TARGET_64BIT"
6454 {
6455   branch_cmp[0] = operands[0];
6456   branch_cmp[1] = operands[1];
6457   branch_type = CMP_DI;
6458   DONE;
6459 })
6460
6461 (define_expand "tstdi"
6462   [(set (cc0)
6463         (match_operand:DI 0 "register_operand" ""))]
6464   "TARGET_64BIT"
6465 {
6466   branch_cmp[0] = operands[0];
6467   branch_cmp[1] = const0_rtx;
6468   branch_type = CMP_DI;
6469   DONE;
6470 })
6471
6472 (define_expand "cmpdf"
6473   [(set (cc0)
6474         (compare:CC (match_operand:DF 0 "register_operand" "")
6475                     (match_operand:DF 1 "register_operand" "")))]
6476   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
6477 {
6478   branch_cmp[0] = operands[0];
6479   branch_cmp[1] = operands[1];
6480   branch_type = CMP_DF;
6481   DONE;
6482 })
6483
6484 (define_expand "cmpsf"
6485   [(set (cc0)
6486         (compare:CC (match_operand:SF 0 "register_operand" "")
6487                     (match_operand:SF 1 "register_operand" "")))]
6488   "TARGET_HARD_FLOAT"
6489 {
6490   branch_cmp[0] = operands[0];
6491   branch_cmp[1] = operands[1];
6492   branch_type = CMP_SF;
6493   DONE;
6494 })
6495 \f
6496 ;;
6497 ;;  ....................
6498 ;;
6499 ;;      CONDITIONAL BRANCHES
6500 ;;
6501 ;;  ....................
6502
6503 ;; Conditional branches on floating-point equality tests.
6504
6505 (define_insn "branch_fp"
6506   [(set (pc)
6507         (if_then_else
6508          (match_operator:CC 0 "cmp_op"
6509                             [(match_operand:CC 2 "register_operand" "z")
6510                              (const_int 0)])
6511          (label_ref (match_operand 1 "" ""))
6512          (pc)))]
6513   "TARGET_HARD_FLOAT"
6514 {
6515   return mips_output_conditional_branch (insn,
6516                                          operands,
6517                                          /*two_operands_p=*/0,
6518                                          /*float_p=*/1,
6519                                          /*inverted_p=*/0,
6520                                          get_attr_length (insn));
6521 }
6522   [(set_attr "type"     "branch")
6523    (set_attr "mode"     "none")])
6524
6525 (define_insn "branch_fp_inverted"
6526   [(set (pc)
6527         (if_then_else
6528          (match_operator:CC 0 "cmp_op"
6529                             [(match_operand:CC 2 "register_operand" "z")
6530                              (const_int 0)])
6531          (pc)
6532          (label_ref (match_operand 1 "" ""))))]
6533   "TARGET_HARD_FLOAT"
6534 {
6535   return mips_output_conditional_branch (insn,
6536                                          operands,
6537                                          /*two_operands_p=*/0,
6538                                          /*float_p=*/1,
6539                                          /*inverted_p=*/1,
6540                                          get_attr_length (insn));
6541 }
6542   [(set_attr "type"     "branch")
6543    (set_attr "mode"     "none")])
6544
6545 ;; Conditional branches on comparisons with zero.
6546
6547 (define_insn "branch_zero"
6548   [(set (pc)
6549         (if_then_else
6550          (match_operator:SI 0 "cmp_op"
6551                             [(match_operand:SI 2 "register_operand" "d")
6552                              (const_int 0)])
6553         (label_ref (match_operand 1 "" ""))
6554         (pc)))]
6555   "!TARGET_MIPS16"
6556 {
6557   return mips_output_conditional_branch (insn,
6558                                          operands,
6559                                          /*two_operands_p=*/0,
6560                                          /*float_p=*/0,
6561                                          /*inverted_p=*/0,
6562                                          get_attr_length (insn));
6563 }
6564   [(set_attr "type"     "branch")
6565    (set_attr "mode"     "none")])
6566
6567 (define_insn "branch_zero_inverted"
6568   [(set (pc)
6569         (if_then_else
6570          (match_operator:SI 0 "cmp_op"
6571                             [(match_operand:SI 2 "register_operand" "d")
6572                              (const_int 0)])
6573         (pc)
6574         (label_ref (match_operand 1 "" ""))))]
6575   "!TARGET_MIPS16"
6576 {
6577   return mips_output_conditional_branch (insn,
6578                                          operands,
6579                                          /*two_operands_p=*/0,
6580                                          /*float_p=*/0,
6581                                          /*inverted_p=*/1,
6582                                          get_attr_length (insn));
6583 }
6584   [(set_attr "type"     "branch")
6585    (set_attr "mode"     "none")])
6586
6587 (define_insn "branch_zero_di"
6588   [(set (pc)
6589         (if_then_else
6590          (match_operator:DI 0 "cmp_op"
6591                             [(match_operand:DI 2 "register_operand" "d")
6592                              (const_int 0)])
6593         (label_ref (match_operand 1 "" ""))
6594         (pc)))]
6595   "!TARGET_MIPS16"
6596 {
6597   return mips_output_conditional_branch (insn,
6598                                          operands,
6599                                          /*two_operands_p=*/0,
6600                                          /*float_p=*/0,
6601                                          /*inverted_p=*/0,
6602                                          get_attr_length (insn));
6603 }
6604   [(set_attr "type"     "branch")
6605    (set_attr "mode"     "none")])
6606
6607 (define_insn "branch_zero_di_inverted"
6608   [(set (pc)
6609         (if_then_else
6610          (match_operator:DI 0 "cmp_op"
6611                             [(match_operand:DI 2 "register_operand" "d")
6612                              (const_int 0)])
6613         (pc)
6614         (label_ref (match_operand 1 "" ""))))]
6615   "!TARGET_MIPS16"
6616 {
6617   return mips_output_conditional_branch (insn,
6618                                          operands,
6619                                          /*two_operands_p=*/0,
6620                                          /*float_p=*/0,
6621                                          /*inverted_p=*/1,
6622                                          get_attr_length (insn));
6623 }
6624   [(set_attr "type"     "branch")
6625    (set_attr "mode"     "none")])
6626
6627 ;; Conditional branch on equality comparison.
6628
6629 (define_insn "branch_equality"
6630   [(set (pc)
6631         (if_then_else
6632          (match_operator:SI 0 "equality_op"
6633                             [(match_operand:SI 2 "register_operand" "d")
6634                              (match_operand:SI 3 "register_operand" "d")])
6635          (label_ref (match_operand 1 "" ""))
6636          (pc)))]
6637   "!TARGET_MIPS16"
6638 {
6639   return mips_output_conditional_branch (insn,
6640                                          operands,
6641                                          /*two_operands_p=*/1,
6642                                          /*float_p=*/0,
6643                                          /*inverted_p=*/0,
6644                                          get_attr_length (insn));
6645 }
6646   [(set_attr "type"     "branch")
6647    (set_attr "mode"     "none")])
6648
6649 (define_insn "branch_equality_di"
6650   [(set (pc)
6651         (if_then_else
6652          (match_operator:DI 0 "equality_op"
6653                             [(match_operand:DI 2 "register_operand" "d")
6654                              (match_operand:DI 3 "register_operand" "d")])
6655         (label_ref (match_operand 1 "" ""))
6656         (pc)))]
6657   "!TARGET_MIPS16"
6658 {
6659   return mips_output_conditional_branch (insn,
6660                                          operands,
6661                                          /*two_operands_p=*/1,
6662                                          /*float_p=*/0,
6663                                          /*inverted_p=*/0,
6664                                          get_attr_length (insn));
6665 }
6666   [(set_attr "type"     "branch")
6667    (set_attr "mode"     "none")])
6668
6669 (define_insn "branch_equality_inverted"
6670   [(set (pc)
6671         (if_then_else
6672          (match_operator:SI 0 "equality_op"
6673                             [(match_operand:SI 2 "register_operand" "d")
6674                              (match_operand:SI 3 "register_operand" "d")])
6675          (pc)
6676          (label_ref (match_operand 1 "" ""))))]
6677   "!TARGET_MIPS16"
6678 {
6679   return mips_output_conditional_branch (insn,
6680                                          operands,
6681                                          /*two_operands_p=*/1,
6682                                          /*float_p=*/0,
6683                                          /*inverted_p=*/1,
6684                                          get_attr_length (insn));
6685 }
6686   [(set_attr "type"     "branch")
6687    (set_attr "mode"     "none")])
6688
6689 (define_insn "branch_equality_di_inverted"
6690   [(set (pc)
6691         (if_then_else
6692          (match_operator:DI 0 "equality_op"
6693                             [(match_operand:DI 2 "register_operand" "d")
6694                              (match_operand:DI 3 "register_operand" "d")])
6695         (pc)
6696         (label_ref (match_operand 1 "" ""))))]
6697   "!TARGET_MIPS16"
6698 {
6699   return mips_output_conditional_branch (insn,
6700                                          operands,
6701                                          /*two_operands_p=*/1,
6702                                          /*float_p=*/0,
6703                                          /*inverted_p=*/1,
6704                                          get_attr_length (insn));
6705 }
6706   [(set_attr "type"     "branch")
6707    (set_attr "mode"     "none")])
6708
6709 ;; MIPS16 branches
6710
6711 (define_insn ""
6712   [(set (pc)
6713         (if_then_else (match_operator:SI 0 "equality_op"
6714                                          [(match_operand:SI 1 "register_operand" "d,t")
6715                                           (const_int 0)])
6716         (match_operand 2 "pc_or_label_operand" "")
6717         (match_operand 3 "pc_or_label_operand" "")))]
6718   "TARGET_MIPS16"
6719 {
6720   if (operands[2] != pc_rtx)
6721     {
6722       if (which_alternative == 0)
6723         return "b%C0z\t%1,%2";
6724       else
6725         return "bt%C0z\t%2";
6726     }
6727   else
6728     {
6729       if (which_alternative == 0)
6730         return "b%N0z\t%1,%3";
6731       else
6732         return "bt%N0z\t%3";
6733     }
6734 }
6735   [(set_attr "type"     "branch")
6736    (set_attr "mode"     "none")
6737    (set_attr "length"   "8")])
6738
6739 (define_insn ""
6740   [(set (pc)
6741         (if_then_else (match_operator:DI 0 "equality_op"
6742                                          [(match_operand:DI 1 "register_operand" "d,t")
6743                                           (const_int 0)])
6744         (match_operand 2 "pc_or_label_operand" "")
6745         (match_operand 3 "pc_or_label_operand" "")))]
6746   "TARGET_MIPS16"
6747 {
6748   if (operands[2] != pc_rtx)
6749     {
6750       if (which_alternative == 0)
6751         return "b%C0z\t%1,%2";
6752       else
6753         return "bt%C0z\t%2";
6754     }
6755   else
6756     {
6757       if (which_alternative == 0)
6758         return "b%N0z\t%1,%3";
6759       else
6760         return "bt%N0z\t%3";
6761     }
6762 }
6763   [(set_attr "type"     "branch")
6764    (set_attr "mode"     "none")
6765    (set_attr "length"   "8")])
6766
6767 (define_expand "bunordered"
6768   [(set (pc)
6769         (if_then_else (unordered:CC (cc0)
6770                                     (const_int 0))
6771                       (label_ref (match_operand 0 "" ""))
6772                       (pc)))]
6773   ""
6774 {
6775   gen_conditional_branch (operands, UNORDERED);
6776   DONE;
6777 })
6778
6779 (define_expand "bordered"
6780   [(set (pc)
6781         (if_then_else (ordered:CC (cc0)
6782                                   (const_int 0))
6783                       (label_ref (match_operand 0 "" ""))
6784                       (pc)))]
6785   ""
6786 {
6787   gen_conditional_branch (operands, ORDERED);
6788   DONE;
6789 })
6790
6791 (define_expand "bunlt"
6792   [(set (pc)
6793         (if_then_else (unlt:CC (cc0)
6794                                (const_int 0))
6795                       (label_ref (match_operand 0 "" ""))
6796                       (pc)))]
6797   ""
6798 {
6799   gen_conditional_branch (operands, UNLT);
6800   DONE;
6801 })
6802
6803 (define_expand "bunge"
6804   [(set (pc)
6805         (if_then_else (unge:CC (cc0)
6806                                (const_int 0))
6807                       (label_ref (match_operand 0 "" ""))
6808                       (pc)))]
6809   ""
6810 {
6811   gen_conditional_branch (operands, UNGE);
6812   DONE;
6813 })
6814
6815 (define_expand "buneq"
6816   [(set (pc)
6817         (if_then_else (uneq:CC (cc0)
6818                                (const_int 0))
6819                       (label_ref (match_operand 0 "" ""))
6820                       (pc)))]
6821   ""
6822 {
6823   gen_conditional_branch (operands, UNEQ);
6824   DONE;
6825 })
6826
6827 (define_expand "bltgt"
6828   [(set (pc)
6829         (if_then_else (ltgt:CC (cc0)
6830                                (const_int 0))
6831                       (label_ref (match_operand 0 "" ""))
6832                       (pc)))]
6833   ""
6834 {
6835   gen_conditional_branch (operands, LTGT);
6836   DONE;
6837 })
6838
6839 (define_expand "bunle"
6840   [(set (pc)
6841         (if_then_else (unle:CC (cc0)
6842                                (const_int 0))
6843                       (label_ref (match_operand 0 "" ""))
6844                       (pc)))]
6845   ""
6846 {
6847   gen_conditional_branch (operands, UNLE);
6848   DONE;
6849 })
6850
6851 (define_expand "bungt"
6852   [(set (pc)
6853         (if_then_else (ungt:CC (cc0)
6854                                (const_int 0))
6855                       (label_ref (match_operand 0 "" ""))
6856                       (pc)))]
6857   ""
6858 {
6859   gen_conditional_branch (operands, UNGT);
6860   DONE;
6861 })
6862
6863 (define_expand "beq"
6864   [(set (pc)
6865         (if_then_else (eq:CC (cc0)
6866                              (const_int 0))
6867                       (label_ref (match_operand 0 "" ""))
6868                       (pc)))]
6869   ""
6870 {
6871   gen_conditional_branch (operands, EQ);
6872   DONE;
6873 })
6874
6875 (define_expand "bne"
6876   [(set (pc)
6877         (if_then_else (ne:CC (cc0)
6878                              (const_int 0))
6879                       (label_ref (match_operand 0 "" ""))
6880                       (pc)))]
6881   ""
6882 {
6883   gen_conditional_branch (operands, NE);
6884   DONE;
6885 })
6886
6887 (define_expand "bgt"
6888   [(set (pc)
6889         (if_then_else (gt:CC (cc0)
6890                              (const_int 0))
6891                       (label_ref (match_operand 0 "" ""))
6892                       (pc)))]
6893   ""
6894 {
6895   gen_conditional_branch (operands, GT);
6896   DONE;
6897 })
6898
6899 (define_expand "bge"
6900   [(set (pc)
6901         (if_then_else (ge:CC (cc0)
6902                              (const_int 0))
6903                       (label_ref (match_operand 0 "" ""))
6904                       (pc)))]
6905   ""
6906 {
6907   gen_conditional_branch (operands, GE);
6908   DONE;
6909 })
6910
6911 (define_expand "blt"
6912   [(set (pc)
6913         (if_then_else (lt:CC (cc0)
6914                              (const_int 0))
6915                       (label_ref (match_operand 0 "" ""))
6916                       (pc)))]
6917   ""
6918 {
6919   gen_conditional_branch (operands, LT);
6920   DONE;
6921 })
6922
6923 (define_expand "ble"
6924   [(set (pc)
6925         (if_then_else (le:CC (cc0)
6926                              (const_int 0))
6927                       (label_ref (match_operand 0 "" ""))
6928                       (pc)))]
6929   ""
6930 {
6931   gen_conditional_branch (operands, LE);
6932   DONE;
6933 })
6934
6935 (define_expand "bgtu"
6936   [(set (pc)
6937         (if_then_else (gtu:CC (cc0)
6938                               (const_int 0))
6939                       (label_ref (match_operand 0 "" ""))
6940                       (pc)))]
6941   ""
6942 {
6943   gen_conditional_branch (operands, GTU);
6944   DONE;
6945 })
6946
6947 (define_expand "bgeu"
6948   [(set (pc)
6949         (if_then_else (geu:CC (cc0)
6950                               (const_int 0))
6951                       (label_ref (match_operand 0 "" ""))
6952                       (pc)))]
6953   ""
6954 {
6955   gen_conditional_branch (operands, GEU);
6956   DONE;
6957 })
6958
6959 (define_expand "bltu"
6960   [(set (pc)
6961         (if_then_else (ltu:CC (cc0)
6962                               (const_int 0))
6963                       (label_ref (match_operand 0 "" ""))
6964                       (pc)))]
6965   ""
6966 {
6967   gen_conditional_branch (operands, LTU);
6968   DONE;
6969 })
6970
6971 (define_expand "bleu"
6972   [(set (pc)
6973         (if_then_else (leu:CC (cc0)
6974                               (const_int 0))
6975                       (label_ref (match_operand 0 "" ""))
6976                       (pc)))]
6977   ""
6978 {
6979   gen_conditional_branch (operands, LEU);
6980   DONE;
6981 })
6982 \f
6983 ;;
6984 ;;  ....................
6985 ;;
6986 ;;      SETTING A REGISTER FROM A COMPARISON
6987 ;;
6988 ;;  ....................
6989
6990 (define_expand "seq"
6991   [(set (match_operand:SI 0 "register_operand" "=d")
6992         (eq:SI (match_dup 1)
6993                (match_dup 2)))]
6994   ""
6995 {
6996   if (branch_type != CMP_SI && (!TARGET_64BIT || branch_type != CMP_DI))
6997     FAIL;
6998
6999   /* Set up operands from compare.  */
7000   operands[1] = branch_cmp[0];
7001   operands[2] = branch_cmp[1];
7002
7003   if (TARGET_64BIT || !TARGET_DEBUG_C_MODE || TARGET_MIPS16)
7004     {
7005       gen_int_relational (EQ, operands[0], operands[1], operands[2], (int *)0);
7006       DONE;
7007     }
7008
7009   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
7010     operands[2] = force_reg (SImode, operands[2]);
7011
7012   /* Fall through and generate default code.  */
7013 })
7014
7015
7016 (define_insn "seq_si_zero"
7017   [(set (match_operand:SI 0 "register_operand" "=d")
7018         (eq:SI (match_operand:SI 1 "register_operand" "d")
7019                (const_int 0)))]
7020   "!TARGET_MIPS16"
7021   "sltu\t%0,%1,1"
7022   [(set_attr "type"     "arith")
7023    (set_attr "mode"     "SI")])
7024
7025 (define_insn ""
7026   [(set (match_operand:SI 0 "register_operand" "=t")
7027         (eq:SI (match_operand:SI 1 "register_operand" "d")
7028                (const_int 0)))]
7029   "TARGET_MIPS16"
7030   "sltu\t%1,1"
7031   [(set_attr "type"     "arith")
7032    (set_attr "mode"     "SI")])
7033
7034 (define_insn "seq_di_zero"
7035   [(set (match_operand:DI 0 "register_operand" "=d")
7036         (eq:DI (match_operand:DI 1 "register_operand" "d")
7037                (const_int 0)))]
7038   "TARGET_64BIT && !TARGET_MIPS16"
7039   "sltu\t%0,%1,1"
7040   [(set_attr "type"     "arith")
7041    (set_attr "mode"     "DI")])
7042
7043 (define_insn ""
7044   [(set (match_operand:DI 0 "register_operand" "=t")
7045         (eq:DI (match_operand:DI 1 "register_operand" "d")
7046                (const_int 0)))]
7047   "TARGET_64BIT && TARGET_MIPS16"
7048   "sltu\t%1,1"
7049   [(set_attr "type"     "arith")
7050    (set_attr "mode"     "DI")])
7051
7052 (define_insn "seq_si"
7053   [(set (match_operand:SI 0 "register_operand" "=d,d")
7054         (eq:SI (match_operand:SI 1 "register_operand" "%d,d")
7055                (match_operand:SI 2 "uns_arith_operand" "d,K")))]
7056   "TARGET_DEBUG_C_MODE && !TARGET_MIPS16"
7057   "@
7058    xor\t%0,%1,%2\;sltu\t%0,%0,1
7059    xori\t%0,%1,%2\;sltu\t%0,%0,1"
7060   [(set_attr "type"     "arith")
7061    (set_attr "mode"     "SI")
7062    (set_attr "length"   "8")])
7063
7064 (define_split
7065   [(set (match_operand:SI 0 "register_operand" "")
7066         (eq:SI (match_operand:SI 1 "register_operand" "")
7067                (match_operand:SI 2 "uns_arith_operand" "")))]
7068   "TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE && !TARGET_MIPS16
7069     && (GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != 0)"
7070   [(set (match_dup 0)
7071         (xor:SI (match_dup 1)
7072                 (match_dup 2)))
7073    (set (match_dup 0)
7074         (ltu:SI (match_dup 0)
7075                 (const_int 1)))]
7076   "")
7077
7078 (define_insn "seq_di"
7079   [(set (match_operand:DI 0 "register_operand" "=d,d")
7080         (eq:DI (match_operand:DI 1 "register_operand" "%d,d")
7081                (match_operand:DI 2 "uns_arith_operand" "d,K")))]
7082   "TARGET_64BIT && TARGET_DEBUG_C_MODE && !TARGET_MIPS16"
7083   "@
7084    xor\t%0,%1,%2\;sltu\t%0,%0,1
7085    xori\t%0,%1,%2\;sltu\t%0,%0,1"
7086   [(set_attr "type"     "arith")
7087    (set_attr "mode"     "DI")
7088    (set_attr "length"   "8")])
7089
7090 (define_split
7091   [(set (match_operand:DI 0 "register_operand" "")
7092         (eq:DI (match_operand:DI 1 "register_operand" "")
7093                (match_operand:DI 2 "uns_arith_operand" "")))]
7094   "TARGET_64BIT && TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE
7095     && !TARGET_MIPS16
7096     && (GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != 0)"
7097   [(set (match_dup 0)
7098         (xor:DI (match_dup 1)
7099                 (match_dup 2)))
7100    (set (match_dup 0)
7101         (ltu:DI (match_dup 0)
7102                 (const_int 1)))]
7103   "")
7104
7105 ;; On the mips16 the default code is better than using sltu.
7106
7107 (define_expand "sne"
7108   [(set (match_operand:SI 0 "register_operand" "=d")
7109         (ne:SI (match_dup 1)
7110                (match_dup 2)))]
7111   "!TARGET_MIPS16"
7112 {
7113   if (branch_type != CMP_SI && (!TARGET_64BIT || branch_type != CMP_DI))
7114     FAIL;
7115
7116   /* Set up operands from compare.  */
7117   operands[1] = branch_cmp[0];
7118   operands[2] = branch_cmp[1];
7119
7120   if (TARGET_64BIT || !TARGET_DEBUG_C_MODE)
7121     {
7122       gen_int_relational (NE, operands[0], operands[1], operands[2], (int *)0);
7123       DONE;
7124     }
7125
7126   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
7127     operands[2] = force_reg (SImode, operands[2]);
7128
7129   /* Fall through and generate default code.  */
7130 })
7131
7132 (define_insn "sne_si_zero"
7133   [(set (match_operand:SI 0 "register_operand" "=d")
7134         (ne:SI (match_operand:SI 1 "register_operand" "d")
7135                (const_int 0)))]
7136   "!TARGET_MIPS16"
7137   "sltu\t%0,%.,%1"
7138   [(set_attr "type"     "arith")
7139    (set_attr "mode"     "SI")])
7140
7141 (define_insn "sne_di_zero"
7142   [(set (match_operand:DI 0 "register_operand" "=d")
7143         (ne:DI (match_operand:DI 1 "register_operand" "d")
7144                (const_int 0)))]
7145   "TARGET_64BIT && !TARGET_MIPS16"
7146   "sltu\t%0,%.,%1"
7147   [(set_attr "type"     "arith")
7148    (set_attr "mode"     "DI")])
7149
7150 (define_insn "sne_si"
7151   [(set (match_operand:SI 0 "register_operand" "=d,d")
7152         (ne:SI (match_operand:SI 1 "register_operand" "%d,d")
7153                (match_operand:SI 2 "uns_arith_operand" "d,K")))]
7154   "TARGET_DEBUG_C_MODE && !TARGET_MIPS16"
7155   "@
7156     xor\t%0,%1,%2\;sltu\t%0,%.,%0
7157     xori\t%0,%1,%x2\;sltu\t%0,%.,%0"
7158   [(set_attr "type"     "arith")
7159    (set_attr "mode"     "SI")
7160    (set_attr "length"   "8")])
7161
7162 (define_split
7163   [(set (match_operand:SI 0 "register_operand" "")
7164         (ne:SI (match_operand:SI 1 "register_operand" "")
7165                (match_operand:SI 2 "uns_arith_operand" "")))]
7166   "TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE && !TARGET_MIPS16
7167     && (GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != 0)"
7168   [(set (match_dup 0)
7169         (xor:SI (match_dup 1)
7170                 (match_dup 2)))
7171    (set (match_dup 0)
7172         (gtu:SI (match_dup 0)
7173                 (const_int 0)))]
7174   "")
7175
7176 (define_insn "sne_di"
7177   [(set (match_operand:DI 0 "register_operand" "=d,d")
7178         (ne:DI (match_operand:DI 1 "register_operand" "%d,d")
7179                (match_operand:DI 2 "uns_arith_operand" "d,K")))]
7180   "TARGET_64BIT && TARGET_DEBUG_C_MODE && !TARGET_MIPS16"
7181   "@
7182     xor\t%0,%1,%2\;sltu\t%0,%.,%0
7183     xori\t%0,%1,%x2\;sltu\t%0,%.,%0"
7184   [(set_attr "type"     "arith")
7185    (set_attr "mode"     "DI")
7186    (set_attr "length"   "8")])
7187
7188 (define_split
7189   [(set (match_operand:DI 0 "register_operand" "")
7190         (ne:DI (match_operand:DI 1 "register_operand" "")
7191                (match_operand:DI 2 "uns_arith_operand" "")))]
7192   "TARGET_64BIT && TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE
7193     && !TARGET_MIPS16
7194     && (GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != 0)"
7195   [(set (match_dup 0)
7196         (xor:DI (match_dup 1)
7197                 (match_dup 2)))
7198    (set (match_dup 0)
7199         (gtu:DI (match_dup 0)
7200                 (const_int 0)))]
7201   "")
7202
7203 (define_expand "sgt"
7204   [(set (match_operand:SI 0 "register_operand" "=d")
7205         (gt:SI (match_dup 1)
7206                (match_dup 2)))]
7207   ""
7208 {
7209   if (branch_type != CMP_SI && (!TARGET_64BIT || branch_type != CMP_DI))
7210     FAIL;
7211
7212   /* Set up operands from compare.  */
7213   operands[1] = branch_cmp[0];
7214   operands[2] = branch_cmp[1];
7215
7216   if (TARGET_64BIT || !TARGET_DEBUG_C_MODE || TARGET_MIPS16)
7217     {
7218       gen_int_relational (GT, operands[0], operands[1], operands[2], (int *)0);
7219       DONE;
7220     }
7221
7222   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) != 0)
7223     operands[2] = force_reg (SImode, operands[2]);
7224
7225   /* Fall through and generate default code.  */
7226 })
7227
7228 (define_insn "sgt_si"
7229   [(set (match_operand:SI 0 "register_operand" "=d")
7230         (gt:SI (match_operand:SI 1 "register_operand" "d")
7231                (match_operand:SI 2 "reg_or_0_operand" "dJ")))]
7232   "!TARGET_MIPS16"
7233   "slt\t%0,%z2,%1"
7234   [(set_attr "type"     "arith")
7235    (set_attr "mode"     "SI")])
7236
7237 (define_insn ""
7238   [(set (match_operand:SI 0 "register_operand" "=t")
7239         (gt:SI (match_operand:SI 1 "register_operand" "d")
7240                (match_operand:SI 2 "register_operand" "d")))]
7241   "TARGET_MIPS16"
7242   "slt\t%2,%1"
7243   [(set_attr "type"     "arith")
7244    (set_attr "mode"     "SI")])
7245
7246 (define_insn "sgt_di"
7247   [(set (match_operand:DI 0 "register_operand" "=d")
7248         (gt:DI (match_operand:DI 1 "register_operand" "d")
7249                (match_operand:DI 2 "reg_or_0_operand" "dJ")))]
7250   "TARGET_64BIT && !TARGET_MIPS16"
7251   "slt\t%0,%z2,%1"
7252   [(set_attr "type"     "arith")
7253    (set_attr "mode"     "DI")])
7254
7255 (define_insn ""
7256   [(set (match_operand:DI 0 "register_operand" "=d")
7257         (gt:DI (match_operand:DI 1 "register_operand" "d")
7258                (match_operand:DI 2 "register_operand" "d")))]
7259   "TARGET_64BIT && TARGET_MIPS16"
7260   "slt\t%2,%1"
7261   [(set_attr "type"     "arith")
7262    (set_attr "mode"     "DI")])
7263
7264 (define_expand "sge"
7265   [(set (match_operand:SI 0 "register_operand" "=d")
7266         (ge:SI (match_dup 1)
7267                (match_dup 2)))]
7268   ""
7269 {
7270   if (branch_type != CMP_SI && (!TARGET_64BIT || branch_type != CMP_DI))
7271     FAIL;
7272
7273   /* Set up operands from compare.  */
7274   operands[1] = branch_cmp[0];
7275   operands[2] = branch_cmp[1];
7276
7277   if (TARGET_64BIT || !TARGET_DEBUG_C_MODE || TARGET_MIPS16)
7278     {
7279       gen_int_relational (GE, operands[0], operands[1], operands[2], (int *)0);
7280       DONE;
7281     }
7282
7283   /* Fall through and generate default code.  */
7284 })
7285
7286 (define_insn "sge_si"
7287   [(set (match_operand:SI 0 "register_operand" "=d")
7288         (ge:SI (match_operand:SI 1 "register_operand" "d")
7289                (match_operand:SI 2 "arith_operand" "dI")))]
7290   "TARGET_DEBUG_C_MODE && !TARGET_MIPS16"
7291   "slt\t%0,%1,%2\;xori\t%0,%0,0x0001"
7292   [(set_attr "type"     "arith")
7293    (set_attr "mode"     "SI")
7294    (set_attr "length"   "8")])
7295
7296 (define_split
7297   [(set (match_operand:SI 0 "register_operand" "")
7298         (ge:SI (match_operand:SI 1 "register_operand" "")
7299                (match_operand:SI 2 "arith_operand" "")))]
7300   "TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE && !TARGET_MIPS16"
7301   [(set (match_dup 0)
7302         (lt:SI (match_dup 1)
7303                (match_dup 2)))
7304    (set (match_dup 0)
7305         (xor:SI (match_dup 0)
7306                 (const_int 1)))]
7307   "")
7308
7309 (define_insn "sge_di"
7310   [(set (match_operand:DI 0 "register_operand" "=d")
7311         (ge:DI (match_operand:DI 1 "register_operand" "d")
7312                (match_operand:DI 2 "arith_operand" "dI")))]
7313   "TARGET_64BIT && TARGET_DEBUG_C_MODE && !TARGET_MIPS16"
7314   "slt\t%0,%1,%2\;xori\t%0,%0,0x0001"
7315   [(set_attr "type"     "arith")
7316    (set_attr "mode"     "DI")
7317    (set_attr "length"   "8")])
7318
7319 (define_split
7320   [(set (match_operand:DI 0 "register_operand" "")
7321         (ge:DI (match_operand:DI 1 "register_operand" "")
7322                (match_operand:DI 2 "arith_operand" "")))]
7323   "TARGET_64BIT && TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE
7324    && !TARGET_MIPS16"
7325   [(set (match_dup 0)
7326         (lt:DI (match_dup 1)
7327                (match_dup 2)))
7328    (set (match_dup 0)
7329         (xor:DI (match_dup 0)
7330                 (const_int 1)))]
7331   "")
7332
7333 (define_expand "slt"
7334   [(set (match_operand:SI 0 "register_operand" "=d")
7335         (lt:SI (match_dup 1)
7336                (match_dup 2)))]
7337   ""
7338 {
7339   if (branch_type != CMP_SI && (!TARGET_64BIT || branch_type != CMP_DI))
7340     FAIL;
7341
7342   /* Set up operands from compare.  */
7343   operands[1] = branch_cmp[0];
7344   operands[2] = branch_cmp[1];
7345
7346   if (TARGET_64BIT || !TARGET_DEBUG_C_MODE || TARGET_MIPS16)
7347     {
7348       gen_int_relational (LT, operands[0], operands[1], operands[2], (int *)0);
7349       DONE;
7350     }
7351
7352   /* Fall through and generate default code.  */
7353 })
7354
7355 (define_insn "slt_si"
7356   [(set (match_operand:SI 0 "register_operand" "=d")
7357         (lt:SI (match_operand:SI 1 "register_operand" "d")
7358                (match_operand:SI 2 "arith_operand" "dI")))]
7359   "!TARGET_MIPS16"
7360   "slt\t%0,%1,%2"
7361   [(set_attr "type"     "arith")
7362    (set_attr "mode"     "SI")])
7363
7364 (define_insn ""
7365   [(set (match_operand:SI 0 "register_operand" "=t,t")
7366         (lt:SI (match_operand:SI 1 "register_operand" "d,d")
7367                (match_operand:SI 2 "arith_operand" "d,I")))]
7368   "TARGET_MIPS16"
7369   "slt\t%1,%2"
7370   [(set_attr "type"     "arith")
7371    (set_attr "mode"     "SI")
7372    (set_attr_alternative "length"
7373                 [(const_int 4)
7374                  (if_then_else (match_operand:VOID 2 "m16_uimm8_1" "")
7375                                (const_int 4)
7376                                (const_int 8))])])
7377
7378 (define_insn "slt_di"
7379   [(set (match_operand:DI 0 "register_operand" "=d")
7380         (lt:DI (match_operand:DI 1 "register_operand" "d")
7381                (match_operand:DI 2 "arith_operand" "dI")))]
7382   "TARGET_64BIT && !TARGET_MIPS16"
7383   "slt\t%0,%1,%2"
7384   [(set_attr "type"     "arith")
7385    (set_attr "mode"     "DI")])
7386
7387 (define_insn ""
7388   [(set (match_operand:DI 0 "register_operand" "=t,t")
7389         (lt:DI (match_operand:DI 1 "register_operand" "d,d")
7390                (match_operand:DI 2 "arith_operand" "d,I")))]
7391   "TARGET_64BIT && TARGET_MIPS16"
7392   "slt\t%1,%2"
7393   [(set_attr "type"     "arith")
7394    (set_attr "mode"     "DI")
7395    (set_attr_alternative "length"
7396                 [(const_int 4)
7397                  (if_then_else (match_operand:VOID 2 "m16_uimm8_1" "")
7398                                (const_int 4)
7399                                (const_int 8))])])
7400
7401 (define_expand "sle"
7402   [(set (match_operand:SI 0 "register_operand" "=d")
7403         (le:SI (match_dup 1)
7404                (match_dup 2)))]
7405   ""
7406 {
7407   if (branch_type != CMP_SI && (!TARGET_64BIT || branch_type != CMP_DI))
7408     FAIL;
7409
7410   /* Set up operands from compare.  */
7411   operands[1] = branch_cmp[0];
7412   operands[2] = branch_cmp[1];
7413
7414   if (TARGET_64BIT || !TARGET_DEBUG_C_MODE || TARGET_MIPS16)
7415     {
7416       gen_int_relational (LE, operands[0], operands[1], operands[2], (int *)0);
7417       DONE;
7418     }
7419
7420   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32767)
7421     operands[2] = force_reg (SImode, operands[2]);
7422
7423   /* Fall through and generate default code.  */
7424 })
7425
7426 (define_insn "sle_si_const"
7427   [(set (match_operand:SI 0 "register_operand" "=d")
7428         (le:SI (match_operand:SI 1 "register_operand" "d")
7429                (match_operand:SI 2 "small_int" "I")))]
7430   "!TARGET_MIPS16 && INTVAL (operands[2]) < 32767"
7431 {
7432   operands[2] = GEN_INT (INTVAL (operands[2])+1);
7433   return "slt\t%0,%1,%2";
7434 }
7435   [(set_attr "type"     "arith")
7436    (set_attr "mode"     "SI")])
7437
7438 (define_insn ""
7439   [(set (match_operand:SI 0 "register_operand" "=t")
7440         (le:SI (match_operand:SI 1 "register_operand" "d")
7441                (match_operand:SI 2 "small_int" "I")))]
7442   "TARGET_MIPS16 && INTVAL (operands[2]) < 32767"
7443 {
7444   operands[2] = GEN_INT (INTVAL (operands[2])+1);
7445   return "slt\t%1,%2";
7446 }
7447   [(set_attr "type"     "arith")
7448    (set_attr "mode"     "SI")
7449    (set (attr "length") (if_then_else (match_operand:VOID 2 "m16_uimm8_m1_1" "")
7450                                       (const_int 4)
7451                                       (const_int 8)))])
7452
7453 (define_insn "sle_di_const"
7454   [(set (match_operand:DI 0 "register_operand" "=d")
7455         (le:DI (match_operand:DI 1 "register_operand" "d")
7456                (match_operand:DI 2 "small_int" "I")))]
7457   "TARGET_64BIT && !TARGET_MIPS16 && INTVAL (operands[2]) < 32767"
7458 {
7459   operands[2] = GEN_INT (INTVAL (operands[2])+1);
7460   return "slt\t%0,%1,%2";
7461 }
7462   [(set_attr "type"     "arith")
7463    (set_attr "mode"     "DI")])
7464
7465 (define_insn ""
7466   [(set (match_operand:DI 0 "register_operand" "=t")
7467         (le:DI (match_operand:DI 1 "register_operand" "d")
7468                (match_operand:DI 2 "small_int" "I")))]
7469   "TARGET_64BIT && TARGET_MIPS16 && INTVAL (operands[2]) < 32767"
7470 {
7471   operands[2] = GEN_INT (INTVAL (operands[2])+1);
7472   return "slt\t%1,%2";
7473 }
7474   [(set_attr "type"     "arith")
7475    (set_attr "mode"     "DI")
7476    (set (attr "length") (if_then_else (match_operand:VOID 2 "m16_uimm8_m1_1" "")
7477                                       (const_int 4)
7478                                       (const_int 8)))])
7479
7480 (define_insn "sle_si_reg"
7481   [(set (match_operand:SI 0 "register_operand" "=d")
7482         (le:SI (match_operand:SI 1 "register_operand" "d")
7483                (match_operand:SI 2 "register_operand" "d")))]
7484   "TARGET_DEBUG_C_MODE && !TARGET_MIPS16"
7485   "slt\t%0,%z2,%1\;xori\t%0,%0,0x0001"
7486   [(set_attr "type"     "arith")
7487    (set_attr "mode"     "SI")
7488    (set_attr "length"   "8")])
7489
7490 (define_split
7491   [(set (match_operand:SI 0 "register_operand" "")
7492         (le:SI (match_operand:SI 1 "register_operand" "")
7493                (match_operand:SI 2 "register_operand" "")))]
7494   "TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE && !TARGET_MIPS16"
7495   [(set (match_dup 0)
7496         (lt:SI (match_dup 2)
7497                (match_dup 1)))
7498    (set (match_dup 0)
7499         (xor:SI (match_dup 0)
7500                 (const_int 1)))]
7501   "")
7502
7503 (define_insn "sle_di_reg"
7504   [(set (match_operand:DI 0 "register_operand" "=d")
7505         (le:DI (match_operand:DI 1 "register_operand" "d")
7506                (match_operand:DI 2 "register_operand" "d")))]
7507   "TARGET_64BIT && TARGET_DEBUG_C_MODE && !TARGET_MIPS16"
7508   "slt\t%0,%z2,%1\;xori\t%0,%0,0x0001"
7509   [(set_attr "type"     "arith")
7510    (set_attr "mode"     "DI")
7511    (set_attr "length"   "8")])
7512
7513 (define_split
7514   [(set (match_operand:DI 0 "register_operand" "")
7515         (le:DI (match_operand:DI 1 "register_operand" "")
7516                (match_operand:DI 2 "register_operand" "")))]
7517   "TARGET_64BIT && TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE
7518    && !TARGET_MIPS16"
7519   [(set (match_dup 0)
7520         (lt:DI (match_dup 2)
7521                (match_dup 1)))
7522    (set (match_dup 0)
7523         (xor:DI (match_dup 0)
7524                 (const_int 1)))]
7525   "")
7526
7527 (define_expand "sgtu"
7528   [(set (match_operand:SI 0 "register_operand" "=d")
7529         (gtu:SI (match_dup 1)
7530                 (match_dup 2)))]
7531   ""
7532 {
7533   if (branch_type != CMP_SI && (!TARGET_64BIT || branch_type != CMP_DI))
7534     FAIL;
7535
7536   /* Set up operands from compare.  */
7537   operands[1] = branch_cmp[0];
7538   operands[2] = branch_cmp[1];
7539
7540   if (TARGET_64BIT || !TARGET_DEBUG_C_MODE || TARGET_MIPS16)
7541     {
7542       gen_int_relational (GTU, operands[0], operands[1], operands[2], (int *)0);
7543       DONE;
7544     }
7545
7546   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) != 0)
7547     operands[2] = force_reg (SImode, operands[2]);
7548
7549   /* Fall through and generate default code.  */
7550 })
7551
7552 (define_insn "sgtu_si"
7553   [(set (match_operand:SI 0 "register_operand" "=d")
7554         (gtu:SI (match_operand:SI 1 "register_operand" "d")
7555                 (match_operand:SI 2 "reg_or_0_operand" "dJ")))]
7556   "!TARGET_MIPS16"
7557   "sltu\t%0,%z2,%1"
7558   [(set_attr "type"     "arith")
7559    (set_attr "mode"     "SI")])
7560
7561 (define_insn ""
7562   [(set (match_operand:SI 0 "register_operand" "=t")
7563         (gtu:SI (match_operand:SI 1 "register_operand" "d")
7564                 (match_operand:SI 2 "register_operand" "d")))]
7565   "TARGET_MIPS16"
7566   "sltu\t%2,%1"
7567   [(set_attr "type"     "arith")
7568    (set_attr "mode"     "SI")])
7569
7570 (define_insn "sgtu_di"
7571   [(set (match_operand:DI 0 "register_operand" "=d")
7572         (gtu:DI (match_operand:DI 1 "register_operand" "d")
7573                 (match_operand:DI 2 "reg_or_0_operand" "dJ")))]
7574   "TARGET_64BIT && !TARGET_MIPS16"
7575   "sltu\t%0,%z2,%1"
7576   [(set_attr "type"     "arith")
7577    (set_attr "mode"     "DI")])
7578
7579 (define_insn ""
7580   [(set (match_operand:DI 0 "register_operand" "=t")
7581         (gtu:DI (match_operand:DI 1 "register_operand" "d")
7582                 (match_operand:DI 2 "register_operand" "d")))]
7583   "TARGET_64BIT && TARGET_MIPS16"
7584   "sltu\t%2,%1"
7585   [(set_attr "type"     "arith")
7586    (set_attr "mode"     "DI")])
7587
7588 (define_expand "sgeu"
7589   [(set (match_operand:SI 0 "register_operand" "=d")
7590         (geu:SI (match_dup 1)
7591                 (match_dup 2)))]
7592   ""
7593 {
7594   if (branch_type != CMP_SI && (!TARGET_64BIT || branch_type != CMP_DI))
7595     FAIL;
7596
7597   /* Set up operands from compare.  */
7598   operands[1] = branch_cmp[0];
7599   operands[2] = branch_cmp[1];
7600
7601   if (TARGET_64BIT || !TARGET_DEBUG_C_MODE || TARGET_MIPS16)
7602     {
7603       gen_int_relational (GEU, operands[0], operands[1], operands[2], (int *)0);
7604       DONE;
7605     }
7606
7607   /* Fall through and generate default code.  */
7608 })
7609
7610 (define_insn "sgeu_si"
7611   [(set (match_operand:SI 0 "register_operand" "=d")
7612         (geu:SI (match_operand:SI 1 "register_operand" "d")
7613                 (match_operand:SI 2 "arith_operand" "dI")))]
7614   "TARGET_DEBUG_C_MODE && !TARGET_MIPS16"
7615   "sltu\t%0,%1,%2\;xori\t%0,%0,0x0001"
7616   [(set_attr "type"     "arith")
7617    (set_attr "mode"     "SI")
7618    (set_attr "length"   "8")])
7619
7620 (define_split
7621   [(set (match_operand:SI 0 "register_operand" "")
7622         (geu:SI (match_operand:SI 1 "register_operand" "")
7623                 (match_operand:SI 2 "arith_operand" "")))]
7624   "TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE && !TARGET_MIPS16"
7625   [(set (match_dup 0)
7626         (ltu:SI (match_dup 1)
7627                 (match_dup 2)))
7628    (set (match_dup 0)
7629         (xor:SI (match_dup 0)
7630                 (const_int 1)))]
7631   "")
7632
7633 (define_insn "sgeu_di"
7634   [(set (match_operand:DI 0 "register_operand" "=d")
7635         (geu:DI (match_operand:DI 1 "register_operand" "d")
7636                 (match_operand:DI 2 "arith_operand" "dI")))]
7637   "TARGET_64BIT && TARGET_DEBUG_C_MODE && !TARGET_MIPS16"
7638   "sltu\t%0,%1,%2\;xori\t%0,%0,0x0001"
7639   [(set_attr "type"     "arith")
7640    (set_attr "mode"     "DI")
7641    (set_attr "length"   "8")])
7642
7643 (define_split
7644   [(set (match_operand:DI 0 "register_operand" "")
7645         (geu:DI (match_operand:DI 1 "register_operand" "")
7646                 (match_operand:DI 2 "arith_operand" "")))]
7647   "TARGET_64BIT && TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE
7648    && !TARGET_MIPS16"
7649   [(set (match_dup 0)
7650         (ltu:DI (match_dup 1)
7651                 (match_dup 2)))
7652    (set (match_dup 0)
7653         (xor:DI (match_dup 0)
7654                 (const_int 1)))]
7655   "")
7656
7657 (define_expand "sltu"
7658   [(set (match_operand:SI 0 "register_operand" "=d")
7659         (ltu:SI (match_dup 1)
7660                 (match_dup 2)))]
7661   ""
7662 {
7663   if (branch_type != CMP_SI && (!TARGET_64BIT || branch_type != CMP_DI))
7664     FAIL;
7665
7666   /* Set up operands from compare.  */
7667   operands[1] = branch_cmp[0];
7668   operands[2] = branch_cmp[1];
7669
7670   if (TARGET_64BIT || !TARGET_DEBUG_C_MODE || TARGET_MIPS16)
7671     {
7672       gen_int_relational (LTU, operands[0], operands[1], operands[2], (int *)0);
7673       DONE;
7674     }
7675
7676   /* Fall through and generate default code.  */
7677 })
7678
7679 (define_insn "sltu_si"
7680   [(set (match_operand:SI 0 "register_operand" "=d")
7681         (ltu:SI (match_operand:SI 1 "register_operand" "d")
7682                 (match_operand:SI 2 "arith_operand" "dI")))]
7683   "!TARGET_MIPS16"
7684   "sltu\t%0,%1,%2"
7685   [(set_attr "type"     "arith")
7686    (set_attr "mode"     "SI")])
7687
7688 (define_insn ""
7689   [(set (match_operand:SI 0 "register_operand" "=t,t")
7690         (ltu:SI (match_operand:SI 1 "register_operand" "d,d")
7691                 (match_operand:SI 2 "arith_operand" "d,I")))]
7692   "TARGET_MIPS16"
7693   "sltu\t%1,%2"
7694   [(set_attr "type"     "arith")
7695    (set_attr "mode"     "SI")
7696    (set_attr_alternative "length"
7697                 [(const_int 4)
7698                  (if_then_else (match_operand:VOID 2 "m16_uimm8_1" "")
7699                                (const_int 4)
7700                                (const_int 8))])])
7701
7702 (define_insn "sltu_di"
7703   [(set (match_operand:DI 0 "register_operand" "=d")
7704         (ltu:DI (match_operand:DI 1 "register_operand" "d")
7705                 (match_operand:DI 2 "arith_operand" "dI")))]
7706   "TARGET_64BIT && !TARGET_MIPS16"
7707   "sltu\t%0,%1,%2"
7708   [(set_attr "type"     "arith")
7709    (set_attr "mode"     "DI")])
7710
7711 (define_insn ""
7712   [(set (match_operand:DI 0 "register_operand" "=t,t")
7713         (ltu:DI (match_operand:DI 1 "register_operand" "d,d")
7714                 (match_operand:DI 2 "arith_operand" "d,I")))]
7715   "TARGET_64BIT && TARGET_MIPS16"
7716   "sltu\t%1,%2"
7717   [(set_attr "type"     "arith")
7718    (set_attr "mode"     "DI")
7719    (set_attr_alternative "length"
7720                 [(const_int 4)
7721                  (if_then_else (match_operand:VOID 2 "m16_uimm8_1" "")
7722                                (const_int 4)
7723                                (const_int 8))])])
7724
7725 (define_expand "sleu"
7726   [(set (match_operand:SI 0 "register_operand" "=d")
7727         (leu:SI (match_dup 1)
7728                 (match_dup 2)))]
7729   ""
7730 {
7731   if (branch_type != CMP_SI && (!TARGET_64BIT || branch_type != CMP_DI))
7732     FAIL;
7733
7734   /* Set up operands from compare.  */
7735   operands[1] = branch_cmp[0];
7736   operands[2] = branch_cmp[1];
7737
7738   if (TARGET_64BIT || !TARGET_DEBUG_C_MODE || TARGET_MIPS16)
7739     {
7740       gen_int_relational (LEU, operands[0], operands[1], operands[2], (int *)0);
7741       DONE;
7742     }
7743
7744   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32767)
7745     operands[2] = force_reg (SImode, operands[2]);
7746
7747   /* Fall through and generate default code.  */
7748 })
7749
7750 (define_insn "sleu_si_const"
7751   [(set (match_operand:SI 0 "register_operand" "=d")
7752         (leu:SI (match_operand:SI 1 "register_operand" "d")
7753                 (match_operand:SI 2 "small_int" "I")))]
7754   "!TARGET_MIPS16 && INTVAL (operands[2]) < 32767"
7755 {
7756   operands[2] = GEN_INT (INTVAL (operands[2]) + 1);
7757   return "sltu\t%0,%1,%2";
7758 }
7759   [(set_attr "type"     "arith")
7760    (set_attr "mode"     "SI")])
7761
7762 (define_insn ""
7763   [(set (match_operand:SI 0 "register_operand" "=t")
7764         (leu:SI (match_operand:SI 1 "register_operand" "d")
7765                 (match_operand:SI 2 "small_int" "I")))]
7766   "TARGET_MIPS16 && INTVAL (operands[2]) < 32767"
7767 {
7768   operands[2] = GEN_INT (INTVAL (operands[2])+1);
7769   return "sltu\t%1,%2";
7770 }
7771   [(set_attr "type"     "arith")
7772    (set_attr "mode"     "SI")
7773    (set (attr "length") (if_then_else (match_operand:VOID 2 "m16_uimm8_m1_1" "")
7774                                       (const_int 4)
7775                                       (const_int 8)))])
7776
7777 (define_insn "sleu_di_const"
7778   [(set (match_operand:DI 0 "register_operand" "=d")
7779         (leu:DI (match_operand:DI 1 "register_operand" "d")
7780                 (match_operand:DI 2 "small_int" "I")))]
7781   "TARGET_64BIT && !TARGET_MIPS16 && INTVAL (operands[2]) < 32767"
7782 {
7783   operands[2] = GEN_INT (INTVAL (operands[2]) + 1);
7784   return "sltu\t%0,%1,%2";
7785 }
7786   [(set_attr "type"     "arith")
7787    (set_attr "mode"     "DI")])
7788
7789 (define_insn ""
7790   [(set (match_operand:DI 0 "register_operand" "=t")
7791         (leu:DI (match_operand:DI 1 "register_operand" "d")
7792                 (match_operand:DI 2 "small_int" "I")))]
7793   "TARGET_64BIT && TARGET_MIPS16 && INTVAL (operands[2]) < 32767"
7794 {
7795   operands[2] = GEN_INT (INTVAL (operands[2])+1);
7796   return "sltu\t%1,%2";
7797 }
7798   [(set_attr "type"     "arith")
7799    (set_attr "mode"     "DI")
7800    (set (attr "length") (if_then_else (match_operand:VOID 2 "m16_uimm8_m1_1" "")
7801                                       (const_int 4)
7802                                       (const_int 8)))])
7803
7804 (define_insn "sleu_si_reg"
7805   [(set (match_operand:SI 0 "register_operand" "=d")
7806         (leu:SI (match_operand:SI 1 "register_operand" "d")
7807                 (match_operand:SI 2 "register_operand" "d")))]
7808   "TARGET_DEBUG_C_MODE && !TARGET_MIPS16"
7809   "sltu\t%0,%z2,%1\;xori\t%0,%0,0x0001"
7810   [(set_attr "type"     "arith")
7811    (set_attr "mode"     "SI")
7812    (set_attr "length"   "8")])
7813
7814 (define_split
7815   [(set (match_operand:SI 0 "register_operand" "")
7816         (leu:SI (match_operand:SI 1 "register_operand" "")
7817                 (match_operand:SI 2 "register_operand" "")))]
7818   "TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE && !TARGET_MIPS16"
7819   [(set (match_dup 0)
7820         (ltu:SI (match_dup 2)
7821                 (match_dup 1)))
7822    (set (match_dup 0)
7823         (xor:SI (match_dup 0)
7824                 (const_int 1)))]
7825   "")
7826
7827 (define_insn "sleu_di_reg"
7828   [(set (match_operand:DI 0 "register_operand" "=d")
7829         (leu:DI (match_operand:DI 1 "register_operand" "d")
7830                 (match_operand:DI 2 "register_operand" "d")))]
7831   "TARGET_64BIT && TARGET_DEBUG_C_MODE && !TARGET_MIPS16"
7832   "sltu\t%0,%z2,%1\;xori\t%0,%0,0x0001"
7833   [(set_attr "type"     "arith")
7834    (set_attr "mode"     "DI")
7835    (set_attr "length"   "8")])
7836
7837 (define_split
7838   [(set (match_operand:DI 0 "register_operand" "")
7839         (leu:DI (match_operand:DI 1 "register_operand" "")
7840                 (match_operand:DI 2 "register_operand" "")))]
7841   "TARGET_64BIT && TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE
7842    && !TARGET_MIPS16"
7843   [(set (match_dup 0)
7844         (ltu:DI (match_dup 2)
7845                 (match_dup 1)))
7846    (set (match_dup 0)
7847         (xor:DI (match_dup 0)
7848                 (const_int 1)))]
7849   "")
7850 \f
7851 ;;
7852 ;;  ....................
7853 ;;
7854 ;;      FLOATING POINT COMPARISONS
7855 ;;
7856 ;;  ....................
7857
7858 (define_insn "sunordered_df"
7859   [(set (match_operand:CC 0 "register_operand" "=z")
7860         (unordered:CC (match_operand:DF 1 "register_operand" "f")
7861                       (match_operand:DF 2 "register_operand" "f")))]
7862   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
7863   "c.un.d\t%Z0%1,%2"
7864   [(set_attr "type" "fcmp")
7865    (set_attr "mode" "FPSW")])
7866
7867 (define_insn "sunlt_df"
7868   [(set (match_operand:CC 0 "register_operand" "=z")
7869         (unlt:CC (match_operand:DF 1 "register_operand" "f")
7870                  (match_operand:DF 2 "register_operand" "f")))]
7871   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
7872   "c.ult.d\t%Z0%1,%2"
7873   [(set_attr "type" "fcmp")
7874    (set_attr "mode" "FPSW")])
7875
7876 (define_insn "suneq_df"
7877   [(set (match_operand:CC 0 "register_operand" "=z")
7878         (uneq:CC (match_operand:DF 1 "register_operand" "f")
7879                  (match_operand:DF 2 "register_operand" "f")))]
7880   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
7881   "c.ueq.d\t%Z0%1,%2"
7882   [(set_attr "type" "fcmp")
7883    (set_attr "mode" "FPSW")])
7884
7885 (define_insn "sunle_df"
7886   [(set (match_operand:CC 0 "register_operand" "=z")
7887         (unle:CC (match_operand:DF 1 "register_operand" "f")
7888                  (match_operand:DF 2 "register_operand" "f")))]
7889   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
7890   "c.ule.d\t%Z0%1,%2"
7891   [(set_attr "type" "fcmp")
7892    (set_attr "mode" "FPSW")])
7893
7894 (define_insn "seq_df"
7895   [(set (match_operand:CC 0 "register_operand" "=z")
7896         (eq:CC (match_operand:DF 1 "register_operand" "f")
7897                (match_operand:DF 2 "register_operand" "f")))]
7898   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
7899   "c.eq.d\t%Z0%1,%2"
7900   [(set_attr "type" "fcmp")
7901    (set_attr "mode" "FPSW")])
7902
7903 (define_insn "slt_df"
7904   [(set (match_operand:CC 0 "register_operand" "=z")
7905         (lt:CC (match_operand:DF 1 "register_operand" "f")
7906                (match_operand:DF 2 "register_operand" "f")))]
7907   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
7908   "c.lt.d\t%Z0%1,%2"
7909   [(set_attr "type" "fcmp")
7910    (set_attr "mode" "FPSW")])
7911
7912 (define_insn "sle_df"
7913   [(set (match_operand:CC 0 "register_operand" "=z")
7914         (le:CC (match_operand:DF 1 "register_operand" "f")
7915                (match_operand:DF 2 "register_operand" "f")))]
7916   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
7917   "c.le.d\t%Z0%1,%2"
7918   [(set_attr "type" "fcmp")
7919    (set_attr "mode" "FPSW")])
7920
7921 (define_insn "sgt_df"
7922   [(set (match_operand:CC 0 "register_operand" "=z")
7923         (gt:CC (match_operand:DF 1 "register_operand" "f")
7924                (match_operand:DF 2 "register_operand" "f")))]
7925   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
7926   "c.lt.d\t%Z0%2,%1"
7927   [(set_attr "type" "fcmp")
7928    (set_attr "mode" "FPSW")])
7929
7930 (define_insn "sge_df"
7931   [(set (match_operand:CC 0 "register_operand" "=z")
7932         (ge:CC (match_operand:DF 1 "register_operand" "f")
7933                (match_operand:DF 2 "register_operand" "f")))]
7934   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
7935   "c.le.d\t%Z0%2,%1"
7936   [(set_attr "type" "fcmp")
7937    (set_attr "mode" "FPSW")])
7938
7939 (define_insn "sunordered_sf"
7940   [(set (match_operand:CC 0 "register_operand" "=z")
7941         (unordered:CC (match_operand:SF 1 "register_operand" "f")
7942                       (match_operand:SF 2 "register_operand" "f")))]
7943   "TARGET_HARD_FLOAT"
7944   "c.un.s\t%Z0%1,%2"
7945   [(set_attr "type" "fcmp")
7946    (set_attr "mode" "FPSW")])
7947
7948 (define_insn "sunlt_sf"
7949   [(set (match_operand:CC 0 "register_operand" "=z")
7950         (unlt:CC (match_operand:SF 1 "register_operand" "f")
7951                  (match_operand:SF 2 "register_operand" "f")))]
7952   "TARGET_HARD_FLOAT"
7953   "c.ult.s\t%Z0%1,%2"
7954   [(set_attr "type" "fcmp")
7955    (set_attr "mode" "FPSW")])
7956
7957 (define_insn "suneq_sf"
7958   [(set (match_operand:CC 0 "register_operand" "=z")
7959         (uneq:CC (match_operand:SF 1 "register_operand" "f")
7960                  (match_operand:SF 2 "register_operand" "f")))]
7961   "TARGET_HARD_FLOAT"
7962   "c.ueq.s\t%Z0%1,%2"
7963   [(set_attr "type" "fcmp")
7964    (set_attr "mode" "FPSW")])
7965
7966 (define_insn "sunle_sf"
7967   [(set (match_operand:CC 0 "register_operand" "=z")
7968         (unle:CC (match_operand:SF 1 "register_operand" "f")
7969                  (match_operand:SF 2 "register_operand" "f")))]
7970   "TARGET_HARD_FLOAT"
7971   "c.ule.s\t%Z0%1,%2"
7972   [(set_attr "type" "fcmp")
7973    (set_attr "mode" "FPSW")])
7974
7975 (define_insn "seq_sf"
7976   [(set (match_operand:CC 0 "register_operand" "=z")
7977         (eq:CC (match_operand:SF 1 "register_operand" "f")
7978                (match_operand:SF 2 "register_operand" "f")))]
7979   "TARGET_HARD_FLOAT"
7980   "c.eq.s\t%Z0%1,%2"
7981   [(set_attr "type" "fcmp")
7982    (set_attr "mode" "FPSW")])
7983
7984 (define_insn "slt_sf"
7985   [(set (match_operand:CC 0 "register_operand" "=z")
7986         (lt:CC (match_operand:SF 1 "register_operand" "f")
7987                (match_operand:SF 2 "register_operand" "f")))]
7988   "TARGET_HARD_FLOAT"
7989   "c.lt.s\t%Z0%1,%2"
7990   [(set_attr "type" "fcmp")
7991    (set_attr "mode" "FPSW")])
7992
7993 (define_insn "sle_sf"
7994   [(set (match_operand:CC 0 "register_operand" "=z")
7995         (le:CC (match_operand:SF 1 "register_operand" "f")
7996                (match_operand:SF 2 "register_operand" "f")))]
7997   "TARGET_HARD_FLOAT"
7998   "c.le.s\t%Z0%1,%2"
7999   [(set_attr "type" "fcmp")
8000    (set_attr "mode" "FPSW")])
8001
8002 (define_insn "sgt_sf"
8003   [(set (match_operand:CC 0 "register_operand" "=z")
8004         (gt:CC (match_operand:SF 1 "register_operand" "f")
8005                (match_operand:SF 2 "register_operand" "f")))]
8006   "TARGET_HARD_FLOAT"
8007   "c.lt.s\t%Z0%2,%1"
8008   [(set_attr "type" "fcmp")
8009    (set_attr "mode" "FPSW")])
8010
8011 (define_insn "sge_sf"
8012   [(set (match_operand:CC 0 "register_operand" "=z")
8013         (ge:CC (match_operand:SF 1 "register_operand" "f")
8014                (match_operand:SF 2 "register_operand" "f")))]
8015   "TARGET_HARD_FLOAT"
8016   "c.le.s\t%Z0%2,%1"
8017   [(set_attr "type" "fcmp")
8018    (set_attr "mode" "FPSW")])
8019 \f
8020 ;;
8021 ;;  ....................
8022 ;;
8023 ;;      UNCONDITIONAL BRANCHES
8024 ;;
8025 ;;  ....................
8026
8027 ;; Unconditional branches.
8028
8029 (define_insn "jump"
8030   [(set (pc)
8031         (label_ref (match_operand 0 "" "")))]
8032   "!TARGET_MIPS16"
8033 {
8034   if (flag_pic && ! TARGET_EMBEDDED_PIC)
8035     {
8036       if (get_attr_length (insn) <= 8)
8037         return "%*b\t%l0%/";
8038       else
8039         {
8040           output_asm_insn (mips_output_load_label (), operands);
8041           return "%*jr\t%@%/%]";
8042         }
8043     }
8044   else
8045     return "%*j\t%l0%/";
8046 }
8047   [(set_attr "type"     "jump")
8048    (set_attr "mode"     "none")
8049    (set (attr "length")
8050         ;; we can't use `j' when emitting non-embedded PIC, so we emit
8051         ;; branch, if it's in range, or load the address of the branch
8052         ;; target into $at in a PIC-compatible way and then jump to it.
8053         (if_then_else
8054          (ior (eq (symbol_ref "flag_pic && ! TARGET_EMBEDDED_PIC")
8055                   (const_int 0))
8056               (lt (abs (minus (match_dup 0)
8057                               (plus (pc) (const_int 4))))
8058                   (const_int 131072)))
8059          (const_int 4) (const_int 16)))])
8060
8061 ;; We need a different insn for the mips16, because a mips16 branch
8062 ;; does not have a delay slot.
8063
8064 (define_insn ""
8065   [(set (pc)
8066         (label_ref (match_operand 0 "" "")))]
8067   "TARGET_MIPS16"
8068   "b\t%l0"
8069   [(set_attr "type"     "branch")
8070    (set_attr "mode"     "none")
8071    (set_attr "length"   "8")])
8072
8073 (define_expand "indirect_jump"
8074   [(set (pc) (match_operand 0 "register_operand" "d"))]
8075   ""
8076 {
8077   rtx dest;
8078
8079   dest = operands[0];
8080   if (GET_CODE (dest) != REG || GET_MODE (dest) != Pmode)
8081     operands[0] = copy_to_mode_reg (Pmode, dest);
8082
8083   if (!(Pmode == DImode))
8084     emit_jump_insn (gen_indirect_jump_internal1 (operands[0]));
8085   else
8086     emit_jump_insn (gen_indirect_jump_internal2 (operands[0]));
8087
8088   DONE;
8089 })
8090
8091 (define_insn "indirect_jump_internal1"
8092   [(set (pc) (match_operand:SI 0 "register_operand" "d"))]
8093   "!(Pmode == DImode)"
8094   "%*j\t%0%/"
8095   [(set_attr "type"     "jump")
8096    (set_attr "mode"     "none")])
8097
8098 (define_insn "indirect_jump_internal2"
8099   [(set (pc) (match_operand:DI 0 "register_operand" "d"))]
8100   "Pmode == DImode"
8101   "%*j\t%0%/"
8102   [(set_attr "type"     "jump")
8103    (set_attr "mode"     "none")])
8104
8105 (define_expand "tablejump"
8106   [(set (pc)
8107         (match_operand 0 "register_operand" "d"))
8108    (use (label_ref (match_operand 1 "" "")))]
8109   ""
8110 {
8111   if (TARGET_MIPS16)
8112     {
8113       if (GET_MODE (operands[0]) != HImode)
8114         abort ();
8115       if (!(Pmode == DImode))
8116         emit_insn (gen_tablejump_mips161 (operands[0], operands[1]));
8117       else
8118         emit_insn (gen_tablejump_mips162 (operands[0], operands[1]));
8119       DONE;
8120     }
8121
8122   if (GET_MODE (operands[0]) != ptr_mode)
8123     abort ();
8124
8125   if (TARGET_GPWORD)
8126     operands[0] = expand_binop (ptr_mode, add_optab, operands[0],
8127                                 pic_offset_table_rtx, 0, 0, OPTAB_WIDEN);
8128
8129   if (Pmode == SImode)
8130     emit_jump_insn (gen_tablejump_internal1 (operands[0], operands[1]));
8131   else
8132     emit_jump_insn (gen_tablejump_internal2 (operands[0], operands[1]));
8133   DONE;
8134 })
8135
8136 (define_insn "tablejump_internal1"
8137   [(set (pc)
8138         (match_operand:SI 0 "register_operand" "d"))
8139    (use (label_ref (match_operand 1 "" "")))]
8140   ""
8141   "%*j\t%0%/"
8142   [(set_attr "type"     "jump")
8143    (set_attr "mode"     "none")])
8144
8145 (define_insn "tablejump_internal2"
8146   [(set (pc)
8147         (match_operand:DI 0 "register_operand" "d"))
8148    (use (label_ref (match_operand 1 "" "")))]
8149   "TARGET_64BIT"
8150   "%*j\t%0%/"
8151   [(set_attr "type"     "jump")
8152    (set_attr "mode"     "none")])
8153
8154 (define_expand "tablejump_mips161"
8155   [(set (pc) (plus:SI (sign_extend:SI
8156                        (match_operand:HI 0 "register_operand" "d"))
8157                       (label_ref:SI (match_operand 1 "" ""))))]
8158   "TARGET_MIPS16 && !(Pmode == DImode)"
8159 {
8160   rtx t1, t2, t3;
8161
8162   t1 = gen_reg_rtx (SImode);
8163   t2 = gen_reg_rtx (SImode);
8164   t3 = gen_reg_rtx (SImode);
8165   emit_insn (gen_extendhisi2 (t1, operands[0]));
8166   emit_move_insn (t2, gen_rtx_LABEL_REF (SImode, operands[1]));
8167   emit_insn (gen_addsi3 (t3, t1, t2));
8168   emit_jump_insn (gen_tablejump_internal1 (t3, operands[1]));
8169   DONE;
8170 })
8171
8172 (define_expand "tablejump_mips162"
8173   [(set (pc) (plus:DI (sign_extend:DI
8174                        (match_operand:HI 0 "register_operand" "d"))
8175                       (label_ref:DI (match_operand 1 "" ""))))]
8176   "TARGET_MIPS16 && Pmode == DImode"
8177 {
8178   rtx t1, t2, t3;
8179
8180   t1 = gen_reg_rtx (DImode);
8181   t2 = gen_reg_rtx (DImode);
8182   t3 = gen_reg_rtx (DImode);
8183   emit_insn (gen_extendhidi2 (t1, operands[0]));
8184   emit_move_insn (t2, gen_rtx_LABEL_REF (DImode, operands[1]));
8185   emit_insn (gen_adddi3 (t3, t1, t2));
8186   emit_jump_insn (gen_tablejump_internal2 (t3, operands[1]));
8187   DONE;
8188 })
8189
8190 ;; Implement a switch statement when generating embedded PIC code.
8191 ;; Switches are implemented by `tablejump' when not using -membedded-pic.
8192
8193 (define_expand "casesi"
8194   [(set (match_dup 5)
8195         (minus:SI (match_operand:SI 0 "register_operand" "")
8196                   (match_operand:SI 1 "const_int_operand" "")))
8197    (set (cc0)
8198         (compare:CC (match_dup 5)
8199                     (match_operand:SI 2 "arith_operand" "")))
8200    (set (pc)
8201         (if_then_else (gtu (cc0)
8202                            (const_int 0))
8203                       (label_ref (match_operand 4 "" ""))
8204                       (pc)))
8205    (parallel
8206     [(set (pc)
8207           (mem:SI (plus:SI (mult:SI (match_dup 5)
8208                                     (const_int 4))
8209                            (label_ref (match_operand 3 "" "")))))
8210      (clobber (match_scratch:SI 6 ""))
8211      (clobber (reg:SI 31))])]
8212   "TARGET_EMBEDDED_PIC"
8213 {
8214   rtx index;
8215
8216   /* If the index is too large, go to the default label.  */
8217   index = expand_binop (SImode, sub_optab, operands[0],
8218                         operands[1], 0, 0, OPTAB_WIDEN);
8219   emit_insn (gen_cmpsi (index, operands[2]));
8220   emit_insn (gen_bgtu (operands[4]));
8221
8222   /* Do the PIC jump.  */
8223   if (Pmode != DImode)
8224     emit_jump_insn (gen_casesi_internal (index, operands[3],
8225                                          gen_reg_rtx (SImode)));
8226   else
8227     emit_jump_insn (gen_casesi_internal_di (index, operands[3],
8228                                             gen_reg_rtx (DImode)));
8229
8230   DONE;
8231 })
8232
8233 ;; An embedded PIC switch statement looks like this:
8234 ;;      bal     $LS1
8235 ;;      sll     $reg,$index,2
8236 ;; $LS1:
8237 ;;      addu    $reg,$reg,$31
8238 ;;      lw      $reg,$L1-$LS1($reg)
8239 ;;      addu    $reg,$reg,$31
8240 ;;      j       $reg
8241 ;; $L1:
8242 ;;      .word   case1-$LS1
8243 ;;      .word   case2-$LS1
8244 ;;      ...
8245
8246 (define_insn "casesi_internal"
8247   [(set (pc)
8248         (mem:SI (plus:SI (mult:SI (match_operand:SI 0 "register_operand" "d")
8249                                   (const_int 4))
8250                          (label_ref (match_operand 1 "" "")))))
8251    (clobber (match_operand:SI 2 "register_operand" "=d"))
8252    (clobber (reg:SI 31))]
8253   "TARGET_EMBEDDED_PIC"
8254   {
8255     if (set_nomacro)
8256       return "%(bal\\t%S1\;sll\\t%2,%0,2\\n%~%S1:\;addu\\t%2,%2,$31%)\;\\
8257 .set macro\;lw\\t%2,%1-%S1(%2)\;.set nomacro\;addu\\t%2,%2,$31\\n\\t%*j\\t%2%/";
8258     return
8259   "%(bal\\t%S1\;sll\\t%2,%0,2\\n%~%S1:\;addu\\t%2,%2,$31%)\;\\
8260 lw\\t%2,%1-%S1(%2)\;addu\\t%2,%2,$31\\n\\t%*j\\t%2%/"
8261     ;
8262   }
8263   [(set_attr "type"     "jump")
8264    (set_attr "mode"     "none")
8265    (set_attr "length"   "24")])
8266
8267 ;; This code assumes that the table index will never be >= 29 bits wide,
8268 ;; which allows the 'sign extend' from SI to DI be a no-op.
8269 (define_insn "casesi_internal_di"
8270   [(set (pc)
8271         (mem:DI (plus:DI (sign_extend:DI
8272                           (mult:SI (match_operand:SI 0 "register_operand" "d")
8273                                   (const_int 8)))
8274                          (label_ref (match_operand 1 "" "")))))
8275    (clobber (match_operand:DI 2 "register_operand" "=d"))
8276    (clobber (reg:DI 31))]
8277   "TARGET_EMBEDDED_PIC"
8278   {
8279     if (set_nomacro)
8280       return "%(bal\\t%S1\;sll\\t%2,%0,3\\n%~%S1:\;daddu\\t%2,%2,$31%)\;\\
8281 .set macro\;ld\\t%2,%1-%S1(%2)\;.set nomacro\;daddu\\t%2,%2,$31\\n\\t%*j\\t%2%/";
8282     return
8283   "%(bal\\t%S1\;sll\\t%2,%0,3\\n%~%S1:\;daddu\\t%2,%2,$31%)\;\\
8284 ld\\t%2,%1-%S1(%2)\;daddu\\t%2,%2,$31\\n\\t%*j\\t%2%/"
8285     ;
8286   }
8287   [(set_attr "type"     "jump")
8288    (set_attr "mode"     "none")
8289    (set_attr "length"   "24")])
8290
8291 ;; For TARGET_ABICALLS, we save the gp in the jmp_buf as well.
8292 ;; While it is possible to either pull it off the stack (in the
8293 ;; o32 case) or recalculate it given t9 and our target label,
8294 ;; it takes 3 or 4 insns to do so.
8295
8296 (define_expand "builtin_setjmp_setup"
8297   [(use (match_operand 0 "register_operand" ""))]
8298   "TARGET_ABICALLS"
8299 {
8300   rtx addr;
8301
8302   addr = plus_constant (operands[0], GET_MODE_SIZE (Pmode) * 3);
8303   emit_move_insn (gen_rtx_MEM (Pmode, addr), pic_offset_table_rtx);
8304   DONE;
8305 })
8306
8307 ;; Restore the gp that we saved above.  Despite the earlier comment, it seems
8308 ;; that older code did recalculate the gp from $25.  Continue to jump through
8309 ;; $25 for compatibility (we lose nothing by doing so).
8310
8311 (define_expand "builtin_longjmp"
8312   [(use (match_operand 0 "register_operand" "r"))]
8313   "TARGET_ABICALLS"
8314 {
8315   /* The elements of the buffer are, in order:  */
8316   int W = GET_MODE_SIZE (Pmode);
8317   rtx fp = gen_rtx_MEM (Pmode, operands[0]);
8318   rtx lab = gen_rtx_MEM (Pmode, plus_constant (operands[0], 1*W));
8319   rtx stack = gen_rtx_MEM (Pmode, plus_constant (operands[0], 2*W));
8320   rtx gpv = gen_rtx_MEM (Pmode, plus_constant (operands[0], 3*W));
8321   rtx pv = gen_rtx_REG (Pmode, PIC_FUNCTION_ADDR_REGNUM);
8322   /* Use gen_raw_REG to avoid being given pic_offset_table_rtx.
8323      The target is bound to be using $28 as the global pointer
8324      but the current function might not be.  */
8325   rtx gp = gen_raw_REG (Pmode, GLOBAL_POINTER_REGNUM);
8326
8327   /* This bit is similar to expand_builtin_longjmp except that it
8328      restores $gp as well.  */
8329   emit_move_insn (hard_frame_pointer_rtx, fp);
8330   emit_move_insn (pv, lab);
8331   emit_stack_restore (SAVE_NONLOCAL, stack, NULL_RTX);
8332   emit_move_insn (gp, gpv);
8333   emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
8334   emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
8335   emit_insn (gen_rtx_USE (VOIDmode, gp));
8336   emit_indirect_jump (pv);
8337   DONE;
8338 })
8339 \f
8340 ;;
8341 ;;  ....................
8342 ;;
8343 ;;      Function prologue/epilogue
8344 ;;
8345 ;;  ....................
8346 ;;
8347
8348 (define_expand "prologue"
8349   [(const_int 1)]
8350   ""
8351 {
8352   mips_expand_prologue ();
8353   DONE;
8354 })
8355
8356 ;; Block any insns from being moved before this point, since the
8357 ;; profiling call to mcount can use various registers that aren't
8358 ;; saved or used to pass arguments.
8359
8360 (define_insn "blockage"
8361   [(unspec_volatile [(const_int 0)] UNSPEC_BLOCKAGE)]
8362   ""
8363   ""
8364   [(set_attr "type"     "unknown")
8365    (set_attr "mode"     "none")
8366    (set_attr "length"   "0")])
8367
8368 (define_expand "epilogue"
8369   [(const_int 2)]
8370   ""
8371 {
8372   mips_expand_epilogue (false);
8373   DONE;
8374 })
8375
8376 (define_expand "sibcall_epilogue"
8377   [(const_int 2)]
8378   ""
8379 {
8380   mips_expand_epilogue (true);
8381   DONE;
8382 })
8383
8384 ;; Trivial return.  Make it look like a normal return insn as that
8385 ;; allows jump optimizations to work better.
8386
8387 (define_insn "return"
8388   [(return)]
8389   "mips_can_use_return_insn ()"
8390   "%*j\t$31%/"
8391   [(set_attr "type"     "jump")
8392    (set_attr "mode"     "none")])
8393
8394 ;; Normal return.
8395
8396 (define_insn "return_internal"
8397   [(return)
8398    (use (match_operand 0 "pmode_register_operand" ""))]
8399   ""
8400   "%*j\t%0%/"
8401   [(set_attr "type"     "jump")
8402    (set_attr "mode"     "none")])
8403
8404 ;; When generating embedded PIC code we need to get the address of the
8405 ;; current function.  This specialized instruction does just that.
8406
8407 (define_insn "get_fnaddr"
8408   [(set (match_operand 0 "register_operand" "=d")
8409         (unspec [(match_operand 1 "" "")] UNSPEC_GET_FNADDR))
8410    (clobber (reg:SI 31))]
8411   "TARGET_EMBEDDED_PIC
8412    && GET_CODE (operands[1]) == SYMBOL_REF"
8413   "%($LF%= = . + 8\;bal\t$LF%=\;nop;la\t%0,%1-$LF%=%)\;addu\t%0,%0,$31"
8414   [(set_attr "type"     "call")
8415    (set_attr "mode"     "none")
8416    (set_attr "length"   "20")])
8417
8418 ;; This is used in compiling the unwind routines.
8419 (define_expand "eh_return"
8420   [(use (match_operand 0 "general_operand" ""))]
8421   ""
8422 {
8423   enum machine_mode gpr_mode = TARGET_64BIT ? DImode : SImode;
8424
8425   if (GET_MODE (operands[0]) != gpr_mode)
8426     operands[0] = convert_to_mode (gpr_mode, operands[0], 0);
8427   if (TARGET_64BIT)
8428     emit_insn (gen_eh_set_lr_di (operands[0]));
8429   else
8430     emit_insn (gen_eh_set_lr_si (operands[0]));
8431
8432   DONE;
8433 })
8434
8435 ;; Clobber the return address on the stack.  We can't expand this
8436 ;; until we know where it will be put in the stack frame.
8437
8438 (define_insn "eh_set_lr_si"
8439   [(unspec [(match_operand:SI 0 "register_operand" "d")] UNSPEC_EH_RETURN)
8440    (clobber (match_scratch:SI 1 "=&d"))]
8441   "! TARGET_64BIT"
8442   "#")
8443
8444 (define_insn "eh_set_lr_di"
8445   [(unspec [(match_operand:DI 0 "register_operand" "d")] UNSPEC_EH_RETURN)
8446    (clobber (match_scratch:DI 1 "=&d"))]
8447   "TARGET_64BIT"
8448   "#")
8449
8450 (define_split
8451   [(unspec [(match_operand 0 "register_operand" "")] UNSPEC_EH_RETURN)
8452    (clobber (match_scratch 1 ""))]
8453   "reload_completed && !TARGET_DEBUG_D_MODE"
8454   [(const_int 0)]
8455 {
8456   mips_set_return_address (operands[0], operands[1]);
8457   DONE;
8458 })
8459
8460 (define_insn "exception_receiver"
8461   [(set (reg:SI 28)
8462         (unspec_volatile:SI [(const_int 0)] UNSPEC_EH_RECEIVER))]
8463   "TARGET_ABICALLS && TARGET_OLDABI"
8464 {
8465   operands[0] = pic_offset_table_rtx;
8466   operands[1] = mips_gp_save_slot ();
8467   return mips_output_move (operands[0], operands[1]);
8468 }
8469   [(set_attr "type"   "load")
8470    (set_attr "length" "8")])
8471 \f
8472 ;;
8473 ;;  ....................
8474 ;;
8475 ;;      FUNCTION CALLS
8476 ;;
8477 ;;  ....................
8478
8479 ;; Instructions to load a call address from the GOT.  The address might
8480 ;; point to a function or to a lazy binding stub.  In the latter case,
8481 ;; the stub will use the dynamic linker to resolve the function, which
8482 ;; in turn will change the GOT entry to point to the function's real
8483 ;; address.
8484 ;;
8485 ;; This means that every call, even pure and constant ones, can
8486 ;; potentially modify the GOT entry.  And once a stub has been called,
8487 ;; we must not call it again.
8488 ;;
8489 ;; We represent this restriction using an imaginary fixed register that
8490 ;; acts like a GOT version number.  By making the register call-clobbered,
8491 ;; we tell the target-independent code that the address could be changed
8492 ;; by any call insn.
8493 (define_insn "load_callsi"
8494   [(set (match_operand:SI 0 "register_operand" "=c")
8495         (unspec:SI [(match_operand:SI 1 "register_operand" "r")
8496                     (match_operand:SI 2 "immediate_operand" "")
8497                     (reg:SI FAKE_CALL_REGNO)]
8498                    UNSPEC_LOAD_CALL))]
8499   "TARGET_ABICALLS"
8500   "lw\t%0,%R2(%1)"
8501   [(set_attr "type" "load")
8502    (set_attr "length" "4")])
8503
8504 (define_insn "load_calldi"
8505   [(set (match_operand:DI 0 "register_operand" "=c")
8506         (unspec:DI [(match_operand:DI 1 "register_operand" "r")
8507                     (match_operand:DI 2 "immediate_operand" "")
8508                     (reg:DI FAKE_CALL_REGNO)]
8509                    UNSPEC_LOAD_CALL))]
8510   "TARGET_ABICALLS"
8511   "ld\t%0,%R2(%1)"
8512   [(set_attr "type" "load")
8513    (set_attr "length" "4")])
8514
8515 ;; Sibling calls.  All these patterns use jump instructions.
8516
8517 ;; If TARGET_SIBCALLS, call_insn_operand will only accept constant
8518 ;; addresses if a direct jump is acceptable.  Since the 'S' constraint
8519 ;; is defined in terms of call_insn_operand, the same is true of the
8520 ;; constraints.
8521
8522 ;; When we use an indirect jump, we need a register that will be
8523 ;; preserved by the epilogue.  Since TARGET_ABICALLS forces us to
8524 ;; use $25 for this purpose -- and $25 is never clobbered by the
8525 ;; epilogue -- we might as well use it for !TARGET_ABICALLS as well.
8526
8527 (define_expand "sibcall"
8528   [(parallel [(call (match_operand 0 "" "")
8529                     (match_operand 1 "" ""))
8530               (use (match_operand 2 "" ""))     ;; next_arg_reg
8531               (use (match_operand 3 "" ""))])]  ;; struct_value_size_rtx
8532   "TARGET_SIBCALLS"
8533 {
8534   mips_expand_call (0, XEXP (operands[0], 0), operands[1], operands[2], true);
8535   DONE;
8536 })
8537
8538 (define_insn "sibcall_internal"
8539   [(call (mem:SI (match_operand 0 "call_insn_operand" "j,S"))
8540          (match_operand 1 "" ""))]
8541   "TARGET_SIBCALLS && SIBLING_CALL_P (insn)"
8542   "@
8543     %*jr\t%0%/
8544     %*j\t%0%/"
8545   [(set_attr "type" "call")])
8546
8547 (define_expand "sibcall_value"
8548   [(parallel [(set (match_operand 0 "" "")
8549                    (call (match_operand 1 "" "")
8550                          (match_operand 2 "" "")))
8551               (use (match_operand 3 "" ""))])]          ;; next_arg_reg
8552   "TARGET_SIBCALLS"
8553 {
8554   mips_expand_call (operands[0], XEXP (operands[1], 0),
8555                     operands[2], operands[3], true);
8556   DONE;
8557 })
8558
8559 (define_insn "sibcall_value_internal"
8560   [(set (match_operand 0 "register_operand" "=df,df")
8561         (call (mem:SI (match_operand 1 "call_insn_operand" "j,S"))
8562               (match_operand 2 "" "")))]
8563   "TARGET_SIBCALLS && SIBLING_CALL_P (insn)"
8564   "@
8565     %*jr\t%1%/
8566     %*j\t%1%/"
8567   [(set_attr "type" "call")])
8568
8569 (define_insn "sibcall_value_multiple_internal"
8570   [(set (match_operand 0 "register_operand" "=df,df")
8571         (call (mem:SI (match_operand 1 "call_insn_operand" "j,S"))
8572               (match_operand 2 "" "")))
8573    (set (match_operand 3 "register_operand" "=df,df")
8574         (call (mem:SI (match_dup 1))
8575               (match_dup 2)))]
8576   "TARGET_SIBCALLS && SIBLING_CALL_P (insn)"
8577   "@
8578     %*jr\t%1%/
8579     %*j\t%1%/"
8580   [(set_attr "type" "call")])
8581
8582 (define_expand "call"
8583   [(parallel [(call (match_operand 0 "" "")
8584                     (match_operand 1 "" ""))
8585               (use (match_operand 2 "" ""))     ;; next_arg_reg
8586               (use (match_operand 3 "" ""))])]  ;; struct_value_size_rtx
8587   ""
8588 {
8589   mips_expand_call (0, XEXP (operands[0], 0), operands[1], operands[2], false);
8590   DONE;
8591 })
8592
8593 ;; This instruction directly corresponds to an assembly-language "jal".
8594 ;; There are four cases:
8595 ;;
8596 ;;    - -mno-abicalls:
8597 ;;        Both symbolic and register destinations are OK.  The pattern
8598 ;;        always expands to a single mips instruction.
8599 ;;
8600 ;;    - -mabicalls/-mno-explicit-relocs:
8601 ;;        Again, both symbolic and register destinations are OK.
8602 ;;        The call is treated as a multi-instruction black box.
8603 ;;
8604 ;;    - -mabicalls/-mexplicit-relocs with n32 or n64:
8605 ;;        Only "jal $25" is allowed.  This expands to a single "jalr $25"
8606 ;;        instruction.
8607 ;;
8608 ;;    - -mabicalls/-mexplicit-relocs with o32 or o64:
8609 ;;        Only "jal $25" is allowed.  The call is actually two instructions:
8610 ;;        "jalr $25" followed by an insn to reload $gp.
8611 ;;
8612 ;; In the last case, we can generate the individual instructions with
8613 ;; a define_split.  There are several things to be wary of:
8614 ;;
8615 ;;   - We can't expose the load of $gp before reload.  If we did,
8616 ;;     it might get removed as dead, but reload can introduce new
8617 ;;     uses of $gp by rematerializing constants.
8618 ;;
8619 ;;   - We shouldn't restore $gp after calls that never return.
8620 ;;     It isn't valid to insert instructions between a noreturn
8621 ;;     call and the following barrier.
8622 ;;
8623 ;;   - The splitter deliberately changes the liveness of $gp.  The unsplit
8624 ;;     instruction preserves $gp and so have no effect on its liveness.
8625 ;;     But once we generate the separate insns, it becomes obvious that
8626 ;;     $gp is not live on entry to the call.
8627 ;;
8628 ;; ??? The operands[2] = insn check is a hack to make the original insn
8629 ;; available to the splitter.
8630 (define_insn_and_split "call_internal"
8631   [(call (mem:SI (match_operand 0 "call_insn_operand" "c,S"))
8632          (match_operand 1 "" ""))
8633    (clobber (reg:SI 31))]
8634   ""
8635   { return TARGET_SPLIT_CALLS ? "#" : "%*jal\t%0%/"; }
8636   "reload_completed && TARGET_SPLIT_CALLS && (operands[2] = insn)"
8637   [(const_int 0)]
8638 {
8639   emit_call_insn (gen_call_split (operands[0], operands[1]));
8640   if (!find_reg_note (operands[2], REG_NORETURN, 0))
8641     emit_move_insn (pic_offset_table_rtx, mips_gp_save_slot ());
8642   DONE;
8643 }
8644   [(set_attr "jal" "indirect,direct")
8645    (set_attr "extended_mips16" "no,yes")])
8646
8647 (define_insn "call_split"
8648   [(call (mem:SI (match_operand 0 "call_insn_operand" "c"))
8649          (match_operand 1 "" ""))
8650    (clobber (reg:SI 31))
8651    (clobber (reg:SI 28))]
8652   "TARGET_SPLIT_CALLS"
8653   "%*jalr\t%0%/"
8654   [(set_attr "type" "call")])
8655
8656 (define_expand "call_value"
8657   [(parallel [(set (match_operand 0 "" "")
8658                    (call (match_operand 1 "" "")
8659                          (match_operand 2 "" "")))
8660               (use (match_operand 3 "" ""))])]          ;; next_arg_reg
8661   ""
8662 {
8663   mips_expand_call (operands[0], XEXP (operands[1], 0),
8664                     operands[2], operands[3], false);
8665   DONE;
8666 })
8667
8668 ;; See comment for call_internal.
8669 (define_insn_and_split "call_value_internal"
8670   [(set (match_operand 0 "register_operand" "=df,df")
8671         (call (mem:SI (match_operand 1 "call_insn_operand" "c,S"))
8672               (match_operand 2 "" "")))
8673    (clobber (reg:SI 31))]
8674   ""
8675   { return TARGET_SPLIT_CALLS ? "#" : "%*jal\t%1%/"; }
8676   "reload_completed && TARGET_SPLIT_CALLS && (operands[3] = insn)"
8677   [(const_int 0)]
8678 {
8679   emit_call_insn (gen_call_value_split (operands[0], operands[1],
8680                                         operands[2]));
8681   if (!find_reg_note (operands[3], REG_NORETURN, 0))
8682     emit_move_insn (pic_offset_table_rtx, mips_gp_save_slot ());
8683   DONE;
8684 }
8685   [(set_attr "jal" "indirect,direct")
8686    (set_attr "extended_mips16" "no,yes")])
8687
8688 (define_insn "call_value_split"
8689   [(set (match_operand 0 "register_operand" "=df")
8690         (call (mem:SI (match_operand 1 "call_insn_operand" "c"))
8691               (match_operand 2 "" "")))
8692    (clobber (reg:SI 31))
8693    (clobber (reg:SI 28))]
8694   "TARGET_SPLIT_CALLS"
8695   "%*jalr\t%1%/"
8696   [(set_attr "type" "call")])
8697
8698 ;; See comment for call_internal.
8699 (define_insn_and_split "call_value_multiple_internal"
8700   [(set (match_operand 0 "register_operand" "=df,df")
8701         (call (mem:SI (match_operand 1 "call_insn_operand" "c,S"))
8702               (match_operand 2 "" "")))
8703    (set (match_operand 3 "register_operand" "=df,df")
8704         (call (mem:SI (match_dup 1))
8705               (match_dup 2)))
8706    (clobber (reg:SI 31))]
8707   ""
8708   { return TARGET_SPLIT_CALLS ? "#" : "%*jal\t%1%/"; }
8709   "reload_completed && TARGET_SPLIT_CALLS && (operands[4] = insn)"
8710   [(const_int 0)]
8711 {
8712   emit_call_insn (gen_call_value_multiple_split (operands[0], operands[1],
8713                                                  operands[2], operands[3]));
8714   if (!find_reg_note (operands[4], REG_NORETURN, 0))
8715     emit_move_insn (pic_offset_table_rtx, mips_gp_save_slot ());
8716   DONE;
8717 }
8718   [(set_attr "jal" "indirect,direct")
8719    (set_attr "extended_mips16" "no,yes")])
8720
8721 (define_insn "call_value_multiple_split"
8722   [(set (match_operand 0 "register_operand" "=df")
8723         (call (mem:SI (match_operand 1 "call_insn_operand" "c"))
8724               (match_operand 2 "" "")))
8725    (set (match_operand 3 "register_operand" "=df")
8726         (call (mem:SI (match_dup 1))
8727               (match_dup 2)))
8728    (clobber (reg:SI 31))
8729    (clobber (reg:SI 28))]
8730   "TARGET_SPLIT_CALLS"
8731   "%*jalr\t%1%/"
8732   [(set_attr "type" "call")])
8733
8734 ;; Call subroutine returning any type.
8735
8736 (define_expand "untyped_call"
8737   [(parallel [(call (match_operand 0 "" "")
8738                     (const_int 0))
8739               (match_operand 1 "" "")
8740               (match_operand 2 "" "")])]
8741   ""
8742 {
8743   int i;
8744
8745   emit_call_insn (GEN_CALL (operands[0], const0_rtx, NULL, const0_rtx));
8746
8747   for (i = 0; i < XVECLEN (operands[2], 0); i++)
8748     {
8749       rtx set = XVECEXP (operands[2], 0, i);
8750       emit_move_insn (SET_DEST (set), SET_SRC (set));
8751     }
8752
8753   emit_insn (gen_blockage ());
8754   DONE;
8755 })
8756 \f
8757 ;;
8758 ;;  ....................
8759 ;;
8760 ;;      MISC.
8761 ;;
8762 ;;  ....................
8763 ;;
8764
8765
8766 (define_expand "prefetch"
8767   [(prefetch (match_operand 0 "address_operand" "")
8768              (match_operand 1 "const_int_operand" "")
8769              (match_operand 2 "const_int_operand" ""))]
8770   "ISA_HAS_PREFETCH"
8771 {
8772   if (symbolic_operand (operands[0], GET_MODE (operands[0])))
8773     operands[0] = force_reg (GET_MODE (operands[0]), operands[0]);
8774 })
8775
8776 (define_insn "prefetch_si_address"
8777   [(prefetch (plus:SI (match_operand:SI 0 "register_operand" "r")
8778                       (match_operand:SI 3 "const_int_operand" "I"))
8779              (match_operand:SI 1 "const_int_operand" "n")
8780              (match_operand:SI 2 "const_int_operand" "n"))]
8781   "ISA_HAS_PREFETCH && Pmode == SImode"
8782   { return mips_emit_prefetch (operands); }
8783   [(set_attr "type" "prefetch")])
8784
8785 (define_insn "prefetch_indexed_si"
8786   [(prefetch (plus:SI (match_operand:SI 0 "register_operand" "r")
8787                       (match_operand:SI 3 "register_operand" "r"))
8788              (match_operand:SI 1 "const_int_operand" "n")
8789              (match_operand:SI 2 "const_int_operand" "n"))]
8790   "ISA_HAS_PREFETCHX && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && Pmode == SImode"
8791   { return mips_emit_prefetch (operands); }
8792   [(set_attr "type" "prefetchx")])
8793
8794 (define_insn "prefetch_si"
8795   [(prefetch (match_operand:SI 0 "register_operand" "r")
8796              (match_operand:SI 1 "const_int_operand" "n")
8797              (match_operand:SI 2 "const_int_operand" "n"))]
8798   "ISA_HAS_PREFETCH && Pmode == SImode"
8799 {
8800   operands[3] = const0_rtx;
8801   return mips_emit_prefetch (operands);
8802 }
8803   [(set_attr "type" "prefetch")])
8804
8805 (define_insn "prefetch_di_address"
8806   [(prefetch (plus:DI (match_operand:DI 0 "register_operand" "r")
8807                       (match_operand:DI 3 "const_int_operand" "I"))
8808              (match_operand:DI 1 "const_int_operand" "n")
8809              (match_operand:DI 2 "const_int_operand" "n"))]
8810   "ISA_HAS_PREFETCH && Pmode == DImode"
8811   { return mips_emit_prefetch (operands); }
8812   [(set_attr "type" "prefetch")])
8813
8814 (define_insn "prefetch_indexed_di"
8815   [(prefetch (plus:DI (match_operand:DI 0 "register_operand" "r")
8816                       (match_operand:DI 3 "register_operand" "r"))
8817              (match_operand:DI 1 "const_int_operand" "n")
8818              (match_operand:DI 2 "const_int_operand" "n"))]
8819   "ISA_HAS_PREFETCHX && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && Pmode == DImode"
8820   { return mips_emit_prefetch (operands); }
8821   [(set_attr "type" "prefetchx")])
8822
8823 (define_insn "prefetch_di"
8824   [(prefetch (match_operand:DI 0 "register_operand" "r")
8825              (match_operand:DI 1 "const_int_operand" "n")
8826              (match_operand:DI 2 "const_int_operand" "n"))]
8827   "ISA_HAS_PREFETCH && Pmode == DImode"
8828 {
8829   operands[3] = const0_rtx;
8830   return mips_emit_prefetch (operands);
8831 }
8832   [(set_attr "type" "prefetch")])
8833
8834 (define_insn "nop"
8835   [(const_int 0)]
8836   ""
8837   "%(nop%)"
8838   [(set_attr "type"     "nop")
8839    (set_attr "mode"     "none")])
8840
8841 ;; Like nop, but commented out when outside a .set noreorder block.
8842 (define_insn "hazard_nop"
8843   [(const_int 1)]
8844   ""
8845   {
8846     if (set_noreorder)
8847       return "nop";
8848     else
8849       return "#nop";
8850   }
8851   [(set_attr "type"     "arith")])
8852 \f
8853 ;; MIPS4 Conditional move instructions.
8854
8855 (define_insn ""
8856   [(set (match_operand:SI 0 "register_operand" "=d,d")
8857         (if_then_else:SI
8858          (match_operator 4 "equality_op"
8859                          [(match_operand:SI 1 "register_operand" "d,d")
8860                           (const_int 0)])
8861          (match_operand:SI 2 "reg_or_0_operand" "dJ,0")
8862          (match_operand:SI 3 "reg_or_0_operand" "0,dJ")))]
8863   "ISA_HAS_CONDMOVE || ISA_HAS_INT_CONDMOVE"
8864   "@
8865     mov%B4\t%0,%z2,%1
8866     mov%b4\t%0,%z3,%1"
8867   [(set_attr "type" "condmove")
8868    (set_attr "mode" "SI")])
8869
8870 (define_insn ""
8871   [(set (match_operand:SI 0 "register_operand" "=d,d")
8872         (if_then_else:SI
8873          (match_operator 4 "equality_op"
8874                          [(match_operand:DI 1 "register_operand" "d,d")
8875                           (const_int 0)])
8876          (match_operand:SI 2 "reg_or_0_operand" "dJ,0")
8877          (match_operand:SI 3 "reg_or_0_operand" "0,dJ")))]
8878   "ISA_HAS_CONDMOVE || ISA_HAS_INT_CONDMOVE"
8879   "@
8880     mov%B4\t%0,%z2,%1
8881     mov%b4\t%0,%z3,%1"
8882   [(set_attr "type" "condmove")
8883    (set_attr "mode" "SI")])
8884
8885 (define_insn ""
8886   [(set (match_operand:SI 0 "register_operand" "=d,d")
8887         (if_then_else:SI
8888          (match_operator 3 "equality_op" [(match_operand:CC 4
8889                                                             "register_operand"
8890                                                             "z,z")
8891                                           (const_int 0)])
8892          (match_operand:SI 1 "reg_or_0_operand" "dJ,0")
8893          (match_operand:SI 2 "reg_or_0_operand" "0,dJ")))]
8894   "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT"
8895   "@
8896     mov%T3\t%0,%z1,%4
8897     mov%t3\t%0,%z2,%4"
8898   [(set_attr "type" "condmove")
8899    (set_attr "mode" "SI")])
8900
8901 (define_insn ""
8902   [(set (match_operand:DI 0 "register_operand" "=d,d")
8903         (if_then_else:DI
8904          (match_operator 4 "equality_op"
8905                          [(match_operand:SI 1 "register_operand" "d,d")
8906                           (const_int 0)])
8907          (match_operand:DI 2 "reg_or_0_operand" "dJ,0")
8908          (match_operand:DI 3 "reg_or_0_operand" "0,dJ")))]
8909   "(ISA_HAS_CONDMOVE || ISA_HAS_INT_CONDMOVE) && TARGET_64BIT"
8910   "@
8911     mov%B4\t%0,%z2,%1
8912     mov%b4\t%0,%z3,%1"
8913   [(set_attr "type" "condmove")
8914    (set_attr "mode" "DI")])
8915
8916 (define_insn ""
8917   [(set (match_operand:DI 0 "register_operand" "=d,d")
8918         (if_then_else:DI
8919          (match_operator 4 "equality_op"
8920                          [(match_operand:DI 1 "register_operand" "d,d")
8921                           (const_int 0)])
8922          (match_operand:DI 2 "reg_or_0_operand" "dJ,0")
8923          (match_operand:DI 3 "reg_or_0_operand" "0,dJ")))]
8924   "(ISA_HAS_CONDMOVE || ISA_HAS_INT_CONDMOVE) && TARGET_64BIT"
8925   "@
8926     mov%B4\t%0,%z2,%1
8927     mov%b4\t%0,%z3,%1"
8928   [(set_attr "type" "condmove")
8929    (set_attr "mode" "DI")])
8930
8931 (define_insn ""
8932   [(set (match_operand:DI 0 "register_operand" "=d,d")
8933         (if_then_else:DI
8934          (match_operator 3 "equality_op" [(match_operand:CC 4
8935                                                             "register_operand"
8936                                                             "z,z")
8937                                           (const_int 0)])
8938          (match_operand:DI 1 "reg_or_0_operand" "dJ,0")
8939          (match_operand:DI 2 "reg_or_0_operand" "0,dJ")))]
8940   "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT && TARGET_64BIT"
8941   "@
8942     mov%T3\t%0,%z1,%4
8943     mov%t3\t%0,%z2,%4"
8944   [(set_attr "type" "condmove")
8945    (set_attr "mode" "DI")])
8946
8947 (define_insn ""
8948   [(set (match_operand:SF 0 "register_operand" "=f,f")
8949         (if_then_else:SF
8950          (match_operator 4 "equality_op"
8951                          [(match_operand:SI 1 "register_operand" "d,d")
8952                           (const_int 0)])
8953          (match_operand:SF 2 "register_operand" "f,0")
8954          (match_operand:SF 3 "register_operand" "0,f")))]
8955   "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT"
8956   "@
8957     mov%B4.s\t%0,%2,%1
8958     mov%b4.s\t%0,%3,%1"
8959   [(set_attr "type" "condmove")
8960    (set_attr "mode" "SF")])
8961
8962 (define_insn ""
8963   [(set (match_operand:SF 0 "register_operand" "=f,f")
8964         (if_then_else:SF
8965          (match_operator 4 "equality_op"
8966                          [(match_operand:DI 1 "register_operand" "d,d")
8967                           (const_int 0)])
8968          (match_operand:SF 2 "register_operand" "f,0")
8969          (match_operand:SF 3 "register_operand" "0,f")))]
8970   "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT"
8971   "@
8972     mov%B4.s\t%0,%2,%1
8973     mov%b4.s\t%0,%3,%1"
8974   [(set_attr "type" "condmove")
8975    (set_attr "mode" "SF")])
8976
8977 (define_insn ""
8978   [(set (match_operand:SF 0 "register_operand" "=f,f")
8979         (if_then_else:SF
8980          (match_operator 3 "equality_op" [(match_operand:CC 4
8981                                                             "register_operand"
8982                                                             "z,z")
8983                                           (const_int 0)])
8984          (match_operand:SF 1 "register_operand" "f,0")
8985          (match_operand:SF 2 "register_operand" "0,f")))]
8986   "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT"
8987   "@
8988     mov%T3.s\t%0,%1,%4
8989     mov%t3.s\t%0,%2,%4"
8990   [(set_attr "type" "condmove")
8991    (set_attr "mode" "SF")])
8992
8993 (define_insn ""
8994   [(set (match_operand:DF 0 "register_operand" "=f,f")
8995         (if_then_else:DF
8996          (match_operator 4 "equality_op"
8997                          [(match_operand:SI 1 "register_operand" "d,d")
8998                           (const_int 0)])
8999          (match_operand:DF 2 "register_operand" "f,0")
9000          (match_operand:DF 3 "register_operand" "0,f")))]
9001   "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
9002   "@
9003     mov%B4.d\t%0,%2,%1
9004     mov%b4.d\t%0,%3,%1"
9005   [(set_attr "type" "condmove")
9006    (set_attr "mode" "DF")])
9007
9008 (define_insn ""
9009   [(set (match_operand:DF 0 "register_operand" "=f,f")
9010         (if_then_else:DF
9011          (match_operator 4 "equality_op"
9012                          [(match_operand:DI 1 "register_operand" "d,d")
9013                           (const_int 0)])
9014          (match_operand:DF 2 "register_operand" "f,0")
9015          (match_operand:DF 3 "register_operand" "0,f")))]
9016   "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
9017   "@
9018     mov%B4.d\t%0,%2,%1
9019     mov%b4.d\t%0,%3,%1"
9020   [(set_attr "type" "condmove")
9021    (set_attr "mode" "DF")])
9022
9023 (define_insn ""
9024   [(set (match_operand:DF 0 "register_operand" "=f,f")
9025         (if_then_else:DF
9026          (match_operator 3 "equality_op" [(match_operand:CC 4
9027                                                             "register_operand"
9028                                                             "z,z")
9029                                           (const_int 0)])
9030          (match_operand:DF 1 "register_operand" "f,0")
9031          (match_operand:DF 2 "register_operand" "0,f")))]
9032   "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
9033   "@
9034     mov%T3.d\t%0,%1,%4
9035     mov%t3.d\t%0,%2,%4"
9036   [(set_attr "type" "condmove")
9037    (set_attr "mode" "DF")])
9038
9039 ;; These are the main define_expand's used to make conditional moves.
9040
9041 (define_expand "movsicc"
9042   [(set (match_dup 4) (match_operand 1 "comparison_operator" ""))
9043    (set (match_operand:SI 0 "register_operand" "")
9044         (if_then_else:SI (match_dup 5)
9045                          (match_operand:SI 2 "reg_or_0_operand" "")
9046                          (match_operand:SI 3 "reg_or_0_operand" "")))]
9047   "ISA_HAS_CONDMOVE || ISA_HAS_INT_CONDMOVE"
9048 {
9049   gen_conditional_move (operands);
9050   DONE;
9051 })
9052
9053 (define_expand "movdicc"
9054   [(set (match_dup 4) (match_operand 1 "comparison_operator" ""))
9055    (set (match_operand:DI 0 "register_operand" "")
9056         (if_then_else:DI (match_dup 5)
9057                          (match_operand:DI 2 "reg_or_0_operand" "")
9058                          (match_operand:DI 3 "reg_or_0_operand" "")))]
9059   "(ISA_HAS_CONDMOVE || ISA_HAS_INT_CONDMOVE) && TARGET_64BIT"
9060 {
9061   gen_conditional_move (operands);
9062   DONE;
9063 })
9064
9065 (define_expand "movsfcc"
9066   [(set (match_dup 4) (match_operand 1 "comparison_operator" ""))
9067    (set (match_operand:SF 0 "register_operand" "")
9068         (if_then_else:SF (match_dup 5)
9069                          (match_operand:SF 2 "register_operand" "")
9070                          (match_operand:SF 3 "register_operand" "")))]
9071   "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT"
9072 {
9073   gen_conditional_move (operands);
9074   DONE;
9075 })
9076
9077 (define_expand "movdfcc"
9078   [(set (match_dup 4) (match_operand 1 "comparison_operator" ""))
9079    (set (match_operand:DF 0 "register_operand" "")
9080         (if_then_else:DF (match_dup 5)
9081                          (match_operand:DF 2 "register_operand" "")
9082                          (match_operand:DF 3 "register_operand" "")))]
9083   "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
9084 {
9085   gen_conditional_move (operands);
9086   DONE;
9087 })
9088 \f
9089 ;;
9090 ;;  ....................
9091 ;;
9092 ;;      mips16 inline constant tables
9093 ;;
9094 ;;  ....................
9095 ;;
9096
9097 (define_insn "consttable_qi"
9098   [(unspec_volatile [(match_operand:QI 0 "consttable_operand" "=g")]
9099                     UNSPEC_CONSTTABLE_QI)]
9100   "TARGET_MIPS16"
9101 {
9102   assemble_integer (operands[0], 1, BITS_PER_UNIT, 1);
9103   return "";
9104 }
9105   [(set_attr "type"     "unknown")
9106    (set_attr "mode"     "QI")
9107    (set_attr "length"   "8")])
9108
9109 (define_insn "consttable_hi"
9110   [(unspec_volatile [(match_operand:HI 0 "consttable_operand" "=g")]
9111                     UNSPEC_CONSTTABLE_HI)]
9112   "TARGET_MIPS16"
9113 {
9114   assemble_integer (operands[0], 2, BITS_PER_UNIT * 2, 1);
9115   return "";
9116 }
9117   [(set_attr "type"     "unknown")
9118    (set_attr "mode"     "HI")
9119    (set_attr "length"   "8")])
9120
9121 (define_insn "consttable_si"
9122   [(unspec_volatile [(match_operand:SI 0 "consttable_operand" "=g")]
9123                     UNSPEC_CONSTTABLE_SI)]
9124   "TARGET_MIPS16"
9125 {
9126   assemble_integer (operands[0], 4, BITS_PER_UNIT * 4, 1);
9127   return "";
9128 }
9129   [(set_attr "type"     "unknown")
9130    (set_attr "mode"     "SI")
9131    (set_attr "length"   "8")])
9132
9133 (define_insn "consttable_di"
9134   [(unspec_volatile [(match_operand:DI 0 "consttable_operand" "=g")]
9135                     UNSPEC_CONSTTABLE_DI)]
9136   "TARGET_MIPS16"
9137 {
9138   assemble_integer (operands[0], 8, BITS_PER_UNIT * 8, 1);
9139   return "";
9140 }
9141   [(set_attr "type"     "unknown")
9142    (set_attr "mode"     "DI")
9143    (set_attr "length"   "16")])
9144
9145 (define_insn "consttable_sf"
9146   [(unspec_volatile [(match_operand:SF 0 "consttable_operand" "=g")]
9147                     UNSPEC_CONSTTABLE_SF)]
9148   "TARGET_MIPS16"
9149 {
9150   REAL_VALUE_TYPE d;
9151
9152   if (GET_CODE (operands[0]) != CONST_DOUBLE)
9153     abort ();
9154   REAL_VALUE_FROM_CONST_DOUBLE (d, operands[0]);
9155   assemble_real (d, SFmode, GET_MODE_ALIGNMENT (SFmode));
9156   return "";
9157 }
9158   [(set_attr "type"     "unknown")
9159    (set_attr "mode"     "SF")
9160    (set_attr "length"   "8")])
9161
9162 (define_insn "consttable_df"
9163   [(unspec_volatile [(match_operand:DF 0 "consttable_operand" "=g")]
9164                     UNSPEC_CONSTTABLE_DF)]
9165   "TARGET_MIPS16"
9166 {
9167   REAL_VALUE_TYPE d;
9168
9169   if (GET_CODE (operands[0]) != CONST_DOUBLE)
9170     abort ();
9171   REAL_VALUE_FROM_CONST_DOUBLE (d, operands[0]);
9172   assemble_real (d, DFmode, GET_MODE_ALIGNMENT (DFmode));
9173   return "";
9174 }
9175   [(set_attr "type"     "unknown")
9176    (set_attr "mode"     "DF")
9177    (set_attr "length"   "16")])
9178
9179 (define_insn "align_2"
9180   [(unspec_volatile [(const_int 0)] UNSPEC_ALIGN_2)]
9181   "TARGET_MIPS16"
9182   ".align 1"
9183   [(set_attr "type"     "unknown")
9184    (set_attr "mode"     "HI")
9185    (set_attr "length"   "8")])
9186
9187 (define_insn "align_4"
9188   [(unspec_volatile [(const_int 0)] UNSPEC_ALIGN_4)]
9189   "TARGET_MIPS16"
9190   ".align 2"
9191   [(set_attr "type"     "unknown")
9192    (set_attr "mode"     "SI")
9193    (set_attr "length"   "8")])
9194
9195 (define_insn "align_8"
9196   [(unspec_volatile [(const_int 0)] UNSPEC_ALIGN_8)]
9197   "TARGET_MIPS16"
9198   ".align 3"
9199   [(set_attr "type"     "unknown")
9200    (set_attr "mode"     "DI")
9201    (set_attr "length"   "12")])
9202 \f
9203 ;;
9204 ;;  ....................
9205 ;;
9206 ;;      mips16 peepholes
9207 ;;
9208 ;;  ....................
9209 ;;
9210
9211 ;; On the mips16, reload will sometimes decide that a pseudo register
9212 ;; should go into $24, and then later on have to reload that register.
9213 ;; When that happens, we get a load of a general register followed by
9214 ;; a move from the general register to $24 followed by a branch.
9215 ;; These peepholes catch the common case, and fix it to just use the
9216 ;; general register for the branch.
9217
9218 (define_peephole
9219   [(set (match_operand:SI 0 "register_operand" "=t")
9220         (match_operand:SI 1 "register_operand" "d"))
9221    (set (pc)
9222         (if_then_else (match_operator:SI 2 "equality_op" [(match_dup 0)
9223                                                           (const_int 0)])
9224                       (match_operand 3 "pc_or_label_operand" "")
9225                       (match_operand 4 "pc_or_label_operand" "")))]
9226   "TARGET_MIPS16
9227    && GET_CODE (operands[0]) == REG
9228    && REGNO (operands[0]) == 24
9229    && dead_or_set_p (insn, operands[0])
9230    && GET_CODE (operands[1]) == REG
9231    && M16_REG_P (REGNO (operands[1]))"
9232 {
9233   if (operands[3] != pc_rtx)
9234     return "b%C2z\t%1,%3";
9235   else
9236     return "b%N2z\t%1,%4";
9237 }
9238   [(set_attr "type"     "branch")
9239    (set_attr "mode"     "none")
9240    (set_attr "length"   "8")])
9241
9242 (define_peephole
9243   [(set (match_operand:DI 0 "register_operand" "=t")
9244         (match_operand:DI 1 "register_operand" "d"))
9245    (set (pc)
9246         (if_then_else (match_operator:DI 2 "equality_op" [(match_dup 0)
9247                                                           (const_int 0)])
9248                       (match_operand 3 "pc_or_label_operand" "")
9249                       (match_operand 4 "pc_or_label_operand" "")))]
9250   "TARGET_MIPS16 && TARGET_64BIT
9251    && GET_CODE (operands[0]) == REG
9252    && REGNO (operands[0]) == 24
9253    && dead_or_set_p (insn, operands[0])
9254    && GET_CODE (operands[1]) == REG
9255    && M16_REG_P (REGNO (operands[1]))"
9256 {
9257   if (operands[3] != pc_rtx)
9258     return "b%C2z\t%1,%3";
9259   else
9260     return "b%N2z\t%1,%4";
9261 }
9262   [(set_attr "type"     "branch")
9263    (set_attr "mode"     "none")
9264    (set_attr "length"   "8")])
9265
9266 ;; We can also have the reverse reload: reload will spill $24 into
9267 ;; another register, and then do a branch on that register when it
9268 ;; could have just stuck with $24.
9269
9270 (define_peephole
9271   [(set (match_operand:SI 0 "register_operand" "=d")
9272         (match_operand:SI 1 "register_operand" "t"))
9273    (set (pc)
9274         (if_then_else (match_operator:SI 2 "equality_op" [(match_dup 0)
9275                                                           (const_int 0)])
9276                       (match_operand 3 "pc_or_label_operand" "")
9277                       (match_operand 4 "pc_or_label_operand" "")))]
9278   "TARGET_MIPS16
9279    && GET_CODE (operands[1]) == REG
9280    && REGNO (operands[1]) == 24
9281    && GET_CODE (operands[0]) == REG
9282    && M16_REG_P (REGNO (operands[0]))
9283    && dead_or_set_p (insn, operands[0])"
9284 {
9285   if (operands[3] != pc_rtx)
9286     return "bt%C2z\t%3";
9287   else
9288     return "bt%N2z\t%4";
9289 }
9290   [(set_attr "type"     "branch")
9291    (set_attr "mode"     "none")
9292    (set_attr "length"   "8")])
9293
9294 (define_peephole
9295   [(set (match_operand:DI 0 "register_operand" "=d")
9296         (match_operand:DI 1 "register_operand" "t"))
9297    (set (pc)
9298         (if_then_else (match_operator:DI 2 "equality_op" [(match_dup 0)
9299                                                           (const_int 0)])
9300                       (match_operand 3 "pc_or_label_operand" "")
9301                       (match_operand 4 "pc_or_label_operand" "")))]
9302   "TARGET_MIPS16 && TARGET_64BIT
9303    && GET_CODE (operands[1]) == REG
9304    && REGNO (operands[1]) == 24
9305    && GET_CODE (operands[0]) == REG
9306    && M16_REG_P (REGNO (operands[0]))
9307    && dead_or_set_p (insn, operands[0])"
9308 {
9309   if (operands[3] != pc_rtx)
9310     return "bt%C2z\t%3";
9311   else
9312     return "bt%N2z\t%4";
9313 }
9314   [(set_attr "type"     "branch")
9315    (set_attr "mode"     "none")
9316    (set_attr "length"   "8")])
9317
9318 (define_split
9319   [(match_operand 0 "small_data_pattern" "")]
9320   "reload_completed"
9321   [(match_dup 0)]
9322   { operands[0] = mips_rewrite_small_data (operands[0]); })