* configure.ac: Check for MIPS TLS.
[official-gcc.git] / gcc / config / mips / mips.md
blob9948e0627cd7e970a0b34b9831a0f2a589820a1a
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, 2005 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.
9 ;; This file is part of GCC.
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.
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.
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.
26 (define_constants
27   [(UNSPEC_LOAD_DF_LOW           0)
28    (UNSPEC_LOAD_DF_HIGH          1)
29    (UNSPEC_STORE_DF_HIGH         2)
30    (UNSPEC_GET_FNADDR            3)
31    (UNSPEC_BLOCKAGE              4)
32    (UNSPEC_CPRESTORE             5)
33    (UNSPEC_EH_RECEIVER           6)
34    (UNSPEC_EH_RETURN             7)
35    (UNSPEC_CONSTTABLE_INT        8)
36    (UNSPEC_CONSTTABLE_FLOAT      9)
37    (UNSPEC_ALIGN                14)
38    (UNSPEC_HIGH                 17)
39    (UNSPEC_LOAD_LEFT            18)
40    (UNSPEC_LOAD_RIGHT           19)
41    (UNSPEC_STORE_LEFT           20)
42    (UNSPEC_STORE_RIGHT          21)
43    (UNSPEC_LOADGP               22)
44    (UNSPEC_LOAD_CALL            23)
45    (UNSPEC_LOAD_GOT             24)
46    (UNSPEC_GP                   25)
47    (UNSPEC_MFHILO               26)
48    (UNSPEC_TLS_LDM              27)
49    (UNSPEC_TLS_GET_TP           28)
51    (UNSPEC_ADDRESS_FIRST        100)
53    (FAKE_CALL_REGNO             79)
55    ;; For MIPS Paired-Singled Floating Point Instructions.
57    (UNSPEC_MOVE_TF_PS           200)
58    (UNSPEC_C                    201)
60    ;; MIPS64/MIPS32R2 alnv.ps
61    (UNSPEC_ALNV_PS              202)
63    ;; MIPS-3D instructions
64    (UNSPEC_CABS                 203)
66    (UNSPEC_ADDR_PS              204)
67    (UNSPEC_CVT_PW_PS            205)
68    (UNSPEC_CVT_PS_PW            206)
69    (UNSPEC_MULR_PS              207)
71    (UNSPEC_RSQRT1               208)
72    (UNSPEC_RSQRT2               209)
73    (UNSPEC_RECIP1               210)
74    (UNSPEC_RECIP2               211)
75   ]
78 (include "predicates.md")
80 ;; ....................
82 ;;      Attributes
84 ;; ....................
86 (define_attr "got" "unset,xgot_high,load"
87   (const_string "unset"))
89 ;; For jal instructions, this attribute is DIRECT when the target address
90 ;; is symbolic and INDIRECT when it is a register.
91 (define_attr "jal" "unset,direct,indirect"
92   (const_string "unset"))
94 ;; This attribute is YES if the instruction is a jal macro (not a
95 ;; real jal instruction).
97 ;; jal is always a macro in SVR4 PIC since it includes an instruction to
98 ;; restore $gp.  Direct jals are also macros in NewABI PIC since they
99 ;; load the target address into $25.
100 (define_attr "jal_macro" "no,yes"
101   (cond [(eq_attr "jal" "direct")
102          (symbol_ref "TARGET_ABICALLS != 0")
103          (eq_attr "jal" "indirect")
104          (symbol_ref "(TARGET_ABICALLS && !TARGET_NEWABI) != 0")]
105         (const_string "no")))
107 ;; Classification of each insn.
108 ;; branch       conditional branch
109 ;; jump         unconditional jump
110 ;; call         unconditional call
111 ;; load         load instruction(s)
112 ;; fpload       floating point load
113 ;; fpidxload    floating point indexed load
114 ;; store        store instruction(s)
115 ;; fpstore      floating point store
116 ;; fpidxstore   floating point indexed store
117 ;; prefetch     memory prefetch (register + offset)
118 ;; prefetchx    memory indexed prefetch (register + register)
119 ;; condmove     conditional moves
120 ;; xfer         transfer to/from coprocessor
121 ;; mthilo       transfer to hi/lo registers
122 ;; mfhilo       transfer from hi/lo registers
123 ;; const        load constant
124 ;; arith        integer arithmetic and logical instructions
125 ;; shift        integer shift instructions
126 ;; slt          set less than instructions
127 ;; clz          the clz and clo instructions
128 ;; trap         trap if instructions
129 ;; imul         integer multiply
130 ;; imadd        integer multiply-add
131 ;; idiv         integer divide
132 ;; fmove        floating point register move
133 ;; fadd         floating point add/subtract
134 ;; fmul         floating point multiply
135 ;; fmadd        floating point multiply-add
136 ;; fdiv         floating point divide
137 ;; frdiv        floating point reciprocal divide
138 ;; frdiv1       floating point reciprocal divide step 1
139 ;; frdiv2       floating point reciprocal divide step 2
140 ;; fabs         floating point absolute value
141 ;; fneg         floating point negation
142 ;; fcmp         floating point compare
143 ;; fcvt         floating point convert
144 ;; fsqrt        floating point square root
145 ;; frsqrt       floating point reciprocal square root
146 ;; frsqrt1      floating point reciprocal square root step1
147 ;; frsqrt2      floating point reciprocal square root step2
148 ;; multi        multiword sequence (or user asm statements)
149 ;; nop          no operation
150 (define_attr "type"
151   "unknown,branch,jump,call,load,fpload,fpidxload,store,fpstore,fpidxstore,prefetch,prefetchx,condmove,xfer,mthilo,mfhilo,const,arith,shift,slt,clz,trap,imul,imadd,idiv,fmove,fadd,fmul,fmadd,fdiv,frdiv,frdiv1,frdiv2,fabs,fneg,fcmp,fcvt,fsqrt,frsqrt,frsqrt1,frsqrt2,multi,nop"
152   (cond [(eq_attr "jal" "!unset") (const_string "call")
153          (eq_attr "got" "load") (const_string "load")]
154         (const_string "unknown")))
156 ;; Main data type used by the insn
157 (define_attr "mode" "unknown,none,QI,HI,SI,DI,SF,DF,FPSW"
158   (const_string "unknown"))
160 ;; Is this an extended instruction in mips16 mode?
161 (define_attr "extended_mips16" "no,yes"
162   (const_string "no"))
164 ;; Length of instruction in bytes.
165 (define_attr "length" ""
166    (cond [;; Direct branch instructions have a range of [-0x40000,0x3fffc].
167           ;; If a branch is outside this range, we have a choice of two
168           ;; sequences.  For PIC, an out-of-range branch like:
169           ;;
170           ;;    bne     r1,r2,target
171           ;;    dslot
172           ;;
173           ;; becomes the equivalent of:
174           ;;
175           ;;    beq     r1,r2,1f
176           ;;    dslot
177           ;;    la      $at,target
178           ;;    jr      $at
179           ;;    nop
180           ;; 1:
181           ;;
182           ;; where the load address can be up to three instructions long
183           ;; (lw, nop, addiu).
184           ;;
185           ;; The non-PIC case is similar except that we use a direct
186           ;; jump instead of an la/jr pair.  Since the target of this
187           ;; jump is an absolute 28-bit bit address (the other bits
188           ;; coming from the address of the delay slot) this form cannot
189           ;; cross a 256MB boundary.  We could provide the option of
190           ;; using la/jr in this case too, but we do not do so at
191           ;; present.
192           ;;
193           ;; Note that this value does not account for the delay slot
194           ;; instruction, whose length is added separately.  If the RTL
195           ;; pattern has no explicit delay slot, mips_adjust_insn_length
196           ;; will add the length of the implicit nop.  The values for
197           ;; forward and backward branches will be different as well.
198           (eq_attr "type" "branch")
199           (cond [(and (le (minus (match_dup 1) (pc)) (const_int 131064))
200                       (le (minus (pc) (match_dup 1)) (const_int 131068)))
201                   (const_int 4)
202                  (ne (symbol_ref "flag_pic") (const_int 0))
203                  (const_int 24)
204                  ] (const_int 12))
206           (eq_attr "got" "load")
207           (const_int 4)
208           (eq_attr "got" "xgot_high")
209           (const_int 8)
211           (eq_attr "type" "const")
212           (symbol_ref "mips_const_insns (operands[1]) * 4")
213           (eq_attr "type" "load,fpload")
214           (symbol_ref "mips_fetch_insns (operands[1]) * 4")
215           (eq_attr "type" "store,fpstore")
216           (symbol_ref "mips_fetch_insns (operands[0]) * 4")
218           ;; In the worst case, a call macro will take 8 instructions:
219           ;;
220           ;;     lui $25,%call_hi(FOO)
221           ;;     addu $25,$25,$28
222           ;;     lw $25,%call_lo(FOO)($25)
223           ;;     nop
224           ;;     jalr $25
225           ;;     nop
226           ;;     lw $gp,X($sp)
227           ;;     nop
228           (eq_attr "jal_macro" "yes")
229           (const_int 32)
231           (and (eq_attr "extended_mips16" "yes")
232                (ne (symbol_ref "TARGET_MIPS16") (const_int 0)))
233           (const_int 8)
235           ;; Various VR4120 errata require a nop to be inserted after a macc
236           ;; instruction.  The assembler does this for us, so account for
237           ;; the worst-case length here.
238           (and (eq_attr "type" "imadd")
239                (ne (symbol_ref "TARGET_FIX_VR4120") (const_int 0)))
240           (const_int 8)
242           ;; VR4120 errata MD(4): if there are consecutive dmult instructions,
243           ;; the result of the second one is missed.  The assembler should work
244           ;; around this by inserting a nop after the first dmult.
245           (and (eq_attr "type" "imul")
246                (and (eq_attr "mode" "DI")
247                     (ne (symbol_ref "TARGET_FIX_VR4120") (const_int 0))))
248           (const_int 8)
250           (eq_attr "type" "idiv")
251           (symbol_ref "mips_idiv_insns () * 4")
252           ] (const_int 4)))
254 ;; Attribute describing the processor.  This attribute must match exactly
255 ;; with the processor_type enumeration in mips.h.
256 (define_attr "cpu"
257   "default,4kc,5kc,20kc,m4k,r3000,r3900,r6000,r4000,r4100,r4111,r4120,r4130,r4300,r4600,r4650,r5000,r5400,r5500,r7000,r8000,r9000,sb1,sr71000"
258   (const (symbol_ref "mips_tune")))
260 ;; The type of hardware hazard associated with this instruction.
261 ;; DELAY means that the next instruction cannot read the result
262 ;; of this one.  HILO means that the next two instructions cannot
263 ;; write to HI or LO.
264 (define_attr "hazard" "none,delay,hilo"
265   (cond [(and (eq_attr "type" "load,fpload,fpidxload")
266               (ne (symbol_ref "ISA_HAS_LOAD_DELAY") (const_int 0)))
267          (const_string "delay")
269          (and (eq_attr "type" "xfer")
270               (ne (symbol_ref "ISA_HAS_XFER_DELAY") (const_int 0)))
271          (const_string "delay")
273          (and (eq_attr "type" "fcmp")
274               (ne (symbol_ref "ISA_HAS_FCMP_DELAY") (const_int 0)))
275          (const_string "delay")
277          ;; The r4000 multiplication patterns include an mflo instruction.
278          (and (eq_attr "type" "imul")
279               (ne (symbol_ref "TARGET_FIX_R4000") (const_int 0)))
280          (const_string "hilo")
282          (and (eq_attr "type" "mfhilo")
283               (eq (symbol_ref "ISA_HAS_HILO_INTERLOCKS") (const_int 0)))
284          (const_string "hilo")]
285         (const_string "none")))
287 ;; Is it a single instruction?
288 (define_attr "single_insn" "no,yes"
289   (symbol_ref "get_attr_length (insn) == (TARGET_MIPS16 ? 2 : 4)"))
291 ;; Can the instruction be put into a delay slot?
292 (define_attr "can_delay" "no,yes"
293   (if_then_else (and (eq_attr "type" "!branch,call,jump")
294                      (and (eq_attr "hazard" "none")
295                           (eq_attr "single_insn" "yes")))
296                 (const_string "yes")
297                 (const_string "no")))
299 ;; Attribute defining whether or not we can use the branch-likely instructions
300 (define_attr "branch_likely" "no,yes"
301   (const
302    (if_then_else (ne (symbol_ref "GENERATE_BRANCHLIKELY") (const_int 0))
303                  (const_string "yes")
304                  (const_string "no"))))
306 ;; True if an instruction might assign to hi or lo when reloaded.
307 ;; This is used by the TUNE_MACC_CHAINS code.
308 (define_attr "may_clobber_hilo" "no,yes"
309   (if_then_else (eq_attr "type" "imul,imadd,idiv,mthilo")
310                 (const_string "yes")
311                 (const_string "no")))
313 ;; Describe a user's asm statement.
314 (define_asm_attributes
315   [(set_attr "type" "multi")
316    (set_attr "can_delay" "no")])
318 ;; This mode macro allows 32-bit and 64-bit GPR patterns to be generated
319 ;; from the same template.
320 (define_mode_macro GPR [SI (DI "TARGET_64BIT")])
322 ;; This mode macro allows :P to be used for patterns that operate on
323 ;; pointer-sized quantities.  Exactly one of the two alternatives will match.
324 (define_mode_macro P [(SI "Pmode == SImode") (DI "Pmode == DImode")])
326 ;; This mode macro allows :MOVECC to be used anywhere that a
327 ;; conditional-move-type condition is needed.
328 (define_mode_macro MOVECC [SI (DI "TARGET_64BIT") (CC "TARGET_HARD_FLOAT")])
330 ;; This mode macro allows the QI and HI extension patterns to be defined from
331 ;; the same template.
332 (define_mode_macro SHORT [QI HI])
334 ;; This mode macro allows :ANYF to be used wherever a scalar or vector
335 ;; floating-point mode is allowed.
336 (define_mode_macro ANYF [(SF "TARGET_HARD_FLOAT")
337                          (DF "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT")
338                          (V2SF "TARGET_PAIRED_SINGLE_FLOAT")])
340 ;; Like ANYF, but only applies to scalar modes.
341 (define_mode_macro SCALARF [(SF "TARGET_HARD_FLOAT")
342                             (DF "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT")])
344 ;; In GPR templates, a string like "<d>subu" will expand to "subu" in the
345 ;; 32-bit version and "dsubu" in the 64-bit version.
346 (define_mode_attr d [(SI "") (DI "d")])
348 ;; This attribute gives the length suffix for a sign- or zero-extension
349 ;; instruction.
350 (define_mode_attr size [(QI "b") (HI "h")])
352 ;; This attributes gives the mode mask of a SHORT.
353 (define_mode_attr mask [(QI "0x00ff") (HI "0xffff")])
355 ;; Mode attributes for GPR loads and stores.
356 (define_mode_attr load [(SI "lw") (DI "ld")])
357 (define_mode_attr store [(SI "sw") (DI "sd")])
359 ;; Similarly for MIPS IV indexed FPR loads and stores.
360 (define_mode_attr loadx [(SF "lwxc1") (DF "ldxc1") (V2SF "ldxc1")])
361 (define_mode_attr storex [(SF "swxc1") (DF "sdxc1") (V2SF "sdxc1")])
363 ;; The unextended ranges of the MIPS16 addiu and daddiu instructions
364 ;; are different.  Some forms of unextended addiu have an 8-bit immediate
365 ;; field but the equivalent daddiu has only a 5-bit field.
366 (define_mode_attr si8_di5 [(SI "8") (DI "5")])
368 ;; This attribute gives the best constraint to use for registers of
369 ;; a given mode.
370 (define_mode_attr reg [(SI "d") (DI "d") (CC "z")])
372 ;; This attribute gives the format suffix for floating-point operations.
373 (define_mode_attr fmt [(SF "s") (DF "d") (V2SF "ps")])
375 ;; This attribute gives the upper-case mode name for one unit of a
376 ;; floating-point mode.
377 (define_mode_attr UNITMODE [(SF "SF") (DF "DF") (V2SF "SF")])
379 ;; This attribute works around the early SB-1 rev2 core "F2" erratum:
381 ;; In certain cases, div.s and div.ps may have a rounding error
382 ;; and/or wrong inexact flag.
384 ;; Therefore, we only allow div.s if not working around SB-1 rev2
385 ;; errata or if a slight loss of precision is OK.
386 (define_mode_attr divide_condition
387   [DF (SF "!TARGET_FIX_SB1 || flag_unsafe_math_optimizations")
388    (V2SF "TARGET_SB1 && (!TARGET_FIX_SB1 || flag_unsafe_math_optimizations)")])
390 ; This attribute gives the condition for which sqrt instructions exist.
391 (define_mode_attr sqrt_condition
392   [(SF "!ISA_MIPS1") (DF "!ISA_MIPS1") (V2SF "TARGET_SB1")])
394 ; This attribute gives the condition for which recip and rsqrt instructions
395 ; exist.
396 (define_mode_attr recip_condition
397   [(SF "ISA_HAS_FP4") (DF "ISA_HAS_FP4") (V2SF "TARGET_SB1")])
399 ;; This code macro allows all branch instructions to be generated from
400 ;; a single define_expand template.
401 (define_code_macro any_cond [unordered ordered unlt unge uneq ltgt unle ungt
402                              eq ne gt ge lt le gtu geu ltu leu])
404 ;; This code macro allows signed and unsigned widening multiplications
405 ;; to use the same template.
406 (define_code_macro any_extend [sign_extend zero_extend])
408 ;; This code macro allows the three shift instructions to be generated
409 ;; from the same template.
410 (define_code_macro any_shift [ashift ashiftrt lshiftrt])
412 ;; This code macro allows all native floating-point comparisons to be
413 ;; generated from the same template.
414 (define_code_macro fcond [unordered uneq unlt unle eq lt le])
416 ;; <u> expands to an empty string when doing a signed operation and
417 ;; "u" when doing an unsigned operation.
418 (define_code_attr u [(sign_extend "") (zero_extend "u")])
420 ;; <su> is like <u>, but the signed form expands to "s" rather than "".
421 (define_code_attr su [(sign_extend "s") (zero_extend "u")])
423 ;; <optab> expands to the name of the optab for a particular code.
424 (define_code_attr optab [(ashift "ashl")
425                          (ashiftrt "ashr")
426                          (lshiftrt "lshr")])
428 ;; <insn> expands to the name of the insn that implements a particular code.
429 (define_code_attr insn [(ashift "sll")
430                         (ashiftrt "sra")
431                         (lshiftrt "srl")])
433 ;; <fcond> is the c.cond.fmt condition associated with a particular code.
434 (define_code_attr fcond [(unordered "un")
435                          (uneq "ueq")
436                          (unlt "ult")
437                          (unle "ule")
438                          (eq "eq")
439                          (lt "lt")
440                          (le "le")])
442 ;; .........................
444 ;;      Branch, call and jump delay slots
446 ;; .........................
448 (define_delay (and (eq_attr "type" "branch")
449                    (eq (symbol_ref "TARGET_MIPS16") (const_int 0)))
450   [(eq_attr "can_delay" "yes")
451    (nil)
452    (and (eq_attr "branch_likely" "yes")
453         (eq_attr "can_delay" "yes"))])
455 (define_delay (eq_attr "type" "jump")
456   [(eq_attr "can_delay" "yes")
457    (nil)
458    (nil)])
460 (define_delay (and (eq_attr "type" "call")
461                    (eq_attr "jal_macro" "no"))
462   [(eq_attr "can_delay" "yes")
463    (nil)
464    (nil)])
466 ;; Pipeline descriptions.
468 ;; generic.md provides a fallback for processors without a specific
469 ;; pipeline description.  It is derived from the old define_function_unit
470 ;; version and uses the "alu" and "imuldiv" units declared below.
472 ;; Some of the processor-specific files are also derived from old
473 ;; define_function_unit descriptions and simply override the parts of
474 ;; generic.md that don't apply.  The other processor-specific files
475 ;; are self-contained.
476 (define_automaton "alu,imuldiv")
478 (define_cpu_unit "alu" "alu")
479 (define_cpu_unit "imuldiv" "imuldiv")
481 (include "3000.md")
482 (include "4000.md")
483 (include "4100.md")
484 (include "4130.md")
485 (include "4300.md")
486 (include "4600.md")
487 (include "5000.md")
488 (include "5400.md")
489 (include "5500.md")
490 (include "6000.md")
491 (include "7000.md")
492 (include "9000.md")
493 (include "sb1.md")
494 (include "sr71k.md")
495 (include "generic.md")
498 ;;  ....................
500 ;;      CONDITIONAL TRAPS
502 ;;  ....................
505 (define_insn "trap"
506   [(trap_if (const_int 1) (const_int 0))]
507   ""
509   if (ISA_HAS_COND_TRAP)
510     return "teq\t$0,$0";
511   else if (TARGET_MIPS16)
512     return "break 0";
513   else
514     return "break";
516   [(set_attr "type" "trap")])
518 (define_expand "conditional_trap"
519   [(trap_if (match_operator 0 "comparison_operator"
520                             [(match_dup 2) (match_dup 3)])
521             (match_operand 1 "const_int_operand"))]
522   "ISA_HAS_COND_TRAP"
524   if (GET_MODE_CLASS (GET_MODE (cmp_operands[0])) == MODE_INT
525       && operands[1] == const0_rtx)
526     {
527       mips_gen_conditional_trap (operands);
528       DONE;
529     }
530   else
531     FAIL;
534 (define_insn "*conditional_trap<mode>"
535   [(trap_if (match_operator:GPR 0 "trap_comparison_operator"
536                                 [(match_operand:GPR 1 "reg_or_0_operand" "dJ")
537                                  (match_operand:GPR 2 "arith_operand" "dI")])
538             (const_int 0))]
539   "ISA_HAS_COND_TRAP"
540   "t%C0\t%z1,%2"
541   [(set_attr "type" "trap")])
544 ;;  ....................
546 ;;      ADDITION
548 ;;  ....................
551 (define_insn "add<mode>3"
552   [(set (match_operand:ANYF 0 "register_operand" "=f")
553         (plus:ANYF (match_operand:ANYF 1 "register_operand" "f")
554                    (match_operand:ANYF 2 "register_operand" "f")))]
555   ""
556   "add.<fmt>\t%0,%1,%2"
557   [(set_attr "type" "fadd")
558    (set_attr "mode" "<UNITMODE>")])
560 (define_expand "add<mode>3"
561   [(set (match_operand:GPR 0 "register_operand")
562         (plus:GPR (match_operand:GPR 1 "register_operand")
563                   (match_operand:GPR 2 "arith_operand")))]
564   "")
566 (define_insn "*add<mode>3"
567   [(set (match_operand:GPR 0 "register_operand" "=d,d")
568         (plus:GPR (match_operand:GPR 1 "register_operand" "d,d")
569                   (match_operand:GPR 2 "arith_operand" "d,Q")))]
570   "!TARGET_MIPS16"
571   "@
572     <d>addu\t%0,%1,%2
573     <d>addiu\t%0,%1,%2"
574   [(set_attr "type" "arith")
575    (set_attr "mode" "<MODE>")])
577 ;; We need to recognize MIPS16 stack pointer additions explicitly, since
578 ;; we don't have a constraint for $sp.  These insns will be generated by
579 ;; the save_restore_insns functions.
581 (define_insn "*add<mode>3_sp1"
582   [(set (reg:GPR 29)
583         (plus:GPR (reg:GPR 29)
584                   (match_operand:GPR 0 "const_arith_operand" "")))]
585   "TARGET_MIPS16"
586   "<d>addiu\t%$,%$,%0"
587   [(set_attr "type" "arith")
588    (set_attr "mode" "<MODE>")
589    (set (attr "length") (if_then_else (match_operand 0 "m16_simm8_8")
590                                       (const_int 4)
591                                       (const_int 8)))])
593 (define_insn "*add<mode>3_sp2"
594   [(set (match_operand:GPR 0 "register_operand" "=d")
595         (plus:GPR (reg:GPR 29)
596                   (match_operand:GPR 1 "const_arith_operand" "")))]
597   "TARGET_MIPS16"
598   "<d>addiu\t%0,%$,%1"
599   [(set_attr "type" "arith")
600    (set_attr "mode" "<MODE>")
601    (set (attr "length") (if_then_else (match_operand 1 "m16_uimm<si8_di5>_4")
602                                       (const_int 4)
603                                       (const_int 8)))])
605 (define_insn "*add<mode>3_mips16"
606   [(set (match_operand:GPR 0 "register_operand" "=d,d,d")
607         (plus:GPR (match_operand:GPR 1 "register_operand" "0,d,d")
608                   (match_operand:GPR 2 "arith_operand" "Q,O,d")))]
609   "TARGET_MIPS16"
610   "@
611     <d>addiu\t%0,%2
612     <d>addiu\t%0,%1,%2
613     <d>addu\t%0,%1,%2"
614   [(set_attr "type" "arith")
615    (set_attr "mode" "<MODE>")
616    (set_attr_alternative "length"
617                 [(if_then_else (match_operand 2 "m16_simm<si8_di5>_1")
618                                (const_int 4)
619                                (const_int 8))
620                  (if_then_else (match_operand 2 "m16_simm4_1")
621                                (const_int 4)
622                                (const_int 8))
623                  (const_int 4)])])
626 ;; On the mips16, we can sometimes split an add of a constant which is
627 ;; a 4 byte instruction into two adds which are both 2 byte
628 ;; instructions.  There are two cases: one where we are adding a
629 ;; constant plus a register to another register, and one where we are
630 ;; simply adding a constant to a register.
632 (define_split
633   [(set (match_operand:SI 0 "register_operand")
634         (plus:SI (match_dup 0)
635                  (match_operand:SI 1 "const_int_operand")))]
636   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
637    && REG_P (operands[0])
638    && M16_REG_P (REGNO (operands[0]))
639    && GET_CODE (operands[1]) == CONST_INT
640    && ((INTVAL (operands[1]) > 0x7f
641         && INTVAL (operands[1]) <= 0x7f + 0x7f)
642        || (INTVAL (operands[1]) < - 0x80
643            && INTVAL (operands[1]) >= - 0x80 - 0x80))"
644   [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
645    (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))]
647   HOST_WIDE_INT val = INTVAL (operands[1]);
649   if (val >= 0)
650     {
651       operands[1] = GEN_INT (0x7f);
652       operands[2] = GEN_INT (val - 0x7f);
653     }
654   else
655     {
656       operands[1] = GEN_INT (- 0x80);
657       operands[2] = GEN_INT (val + 0x80);
658     }
661 (define_split
662   [(set (match_operand:SI 0 "register_operand")
663         (plus:SI (match_operand:SI 1 "register_operand")
664                  (match_operand:SI 2 "const_int_operand")))]
665   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
666    && REG_P (operands[0])
667    && M16_REG_P (REGNO (operands[0]))
668    && REG_P (operands[1])
669    && M16_REG_P (REGNO (operands[1]))
670    && REGNO (operands[0]) != REGNO (operands[1])
671    && GET_CODE (operands[2]) == CONST_INT
672    && ((INTVAL (operands[2]) > 0x7
673         && INTVAL (operands[2]) <= 0x7 + 0x7f)
674        || (INTVAL (operands[2]) < - 0x8
675            && INTVAL (operands[2]) >= - 0x8 - 0x80))"
676   [(set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))
677    (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 3)))]
679   HOST_WIDE_INT val = INTVAL (operands[2]);
681   if (val >= 0)
682     {
683       operands[2] = GEN_INT (0x7);
684       operands[3] = GEN_INT (val - 0x7);
685     }
686   else
687     {
688       operands[2] = GEN_INT (- 0x8);
689       operands[3] = GEN_INT (val + 0x8);
690     }
693 (define_split
694   [(set (match_operand:DI 0 "register_operand")
695         (plus:DI (match_dup 0)
696                  (match_operand:DI 1 "const_int_operand")))]
697   "TARGET_MIPS16 && TARGET_64BIT && reload_completed && !TARGET_DEBUG_D_MODE
698    && REG_P (operands[0])
699    && M16_REG_P (REGNO (operands[0]))
700    && GET_CODE (operands[1]) == CONST_INT
701    && ((INTVAL (operands[1]) > 0xf
702         && INTVAL (operands[1]) <= 0xf + 0xf)
703        || (INTVAL (operands[1]) < - 0x10
704            && INTVAL (operands[1]) >= - 0x10 - 0x10))"
705   [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1)))
706    (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))]
708   HOST_WIDE_INT val = INTVAL (operands[1]);
710   if (val >= 0)
711     {
712       operands[1] = GEN_INT (0xf);
713       operands[2] = GEN_INT (val - 0xf);
714     }
715   else
716     {
717       operands[1] = GEN_INT (- 0x10);
718       operands[2] = GEN_INT (val + 0x10);
719     }
722 (define_split
723   [(set (match_operand:DI 0 "register_operand")
724         (plus:DI (match_operand:DI 1 "register_operand")
725                  (match_operand:DI 2 "const_int_operand")))]
726   "TARGET_MIPS16 && TARGET_64BIT && reload_completed && !TARGET_DEBUG_D_MODE
727    && REG_P (operands[0])
728    && M16_REG_P (REGNO (operands[0]))
729    && REG_P (operands[1])
730    && M16_REG_P (REGNO (operands[1]))
731    && REGNO (operands[0]) != REGNO (operands[1])
732    && GET_CODE (operands[2]) == CONST_INT
733    && ((INTVAL (operands[2]) > 0x7
734         && INTVAL (operands[2]) <= 0x7 + 0xf)
735        || (INTVAL (operands[2]) < - 0x8
736            && INTVAL (operands[2]) >= - 0x8 - 0x10))"
737   [(set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))
738    (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 3)))]
740   HOST_WIDE_INT val = INTVAL (operands[2]);
742   if (val >= 0)
743     {
744       operands[2] = GEN_INT (0x7);
745       operands[3] = GEN_INT (val - 0x7);
746     }
747   else
748     {
749       operands[2] = GEN_INT (- 0x8);
750       operands[3] = GEN_INT (val + 0x8);
751     }
754 (define_insn "*addsi3_extended"
755   [(set (match_operand:DI 0 "register_operand" "=d,d")
756         (sign_extend:DI
757              (plus:SI (match_operand:SI 1 "register_operand" "d,d")
758                       (match_operand:SI 2 "arith_operand" "d,Q"))))]
759   "TARGET_64BIT && !TARGET_MIPS16"
760   "@
761     addu\t%0,%1,%2
762     addiu\t%0,%1,%2"
763   [(set_attr "type" "arith")
764    (set_attr "mode" "SI")])
766 ;; Split this insn so that the addiu splitters can have a crack at it.
767 ;; Use a conservative length estimate until the split.
768 (define_insn_and_split "*addsi3_extended_mips16"
769   [(set (match_operand:DI 0 "register_operand" "=d,d,d")
770         (sign_extend:DI
771              (plus:SI (match_operand:SI 1 "register_operand" "0,d,d")
772                       (match_operand:SI 2 "arith_operand" "Q,O,d"))))]
773   "TARGET_64BIT && TARGET_MIPS16"
774   "#"
775   "&& reload_completed"
776   [(set (match_dup 3) (plus:SI (match_dup 1) (match_dup 2)))]
777   { operands[3] = gen_lowpart (SImode, operands[0]); }
778   [(set_attr "type" "arith")
779    (set_attr "mode" "SI")
780    (set_attr "extended_mips16" "yes")])
783 ;;  ....................
785 ;;      SUBTRACTION
787 ;;  ....................
790 (define_insn "sub<mode>3"
791   [(set (match_operand:ANYF 0 "register_operand" "=f")
792         (minus:ANYF (match_operand:ANYF 1 "register_operand" "f")
793                     (match_operand:ANYF 2 "register_operand" "f")))]
794   ""
795   "sub.<fmt>\t%0,%1,%2"
796   [(set_attr "type" "fadd")
797    (set_attr "mode" "<UNITMODE>")])
799 (define_insn "sub<mode>3"
800   [(set (match_operand:GPR 0 "register_operand" "=d")
801         (minus:GPR (match_operand:GPR 1 "register_operand" "d")
802                    (match_operand:GPR 2 "register_operand" "d")))]
803   ""
804   "<d>subu\t%0,%1,%2"
805   [(set_attr "type" "arith")
806    (set_attr "mode" "<MODE>")])
808 (define_insn "*subsi3_extended"
809   [(set (match_operand:DI 0 "register_operand" "=d")
810         (sign_extend:DI
811             (minus:SI (match_operand:SI 1 "register_operand" "d")
812                       (match_operand:SI 2 "register_operand" "d"))))]
813   "TARGET_64BIT"
814   "subu\t%0,%1,%2"
815   [(set_attr "type" "arith")
816    (set_attr "mode" "DI")])
819 ;;  ....................
821 ;;      MULTIPLICATION
823 ;;  ....................
826 (define_expand "mul<mode>3"
827   [(set (match_operand:SCALARF 0 "register_operand")
828         (mult:SCALARF (match_operand:SCALARF 1 "register_operand")
829                       (match_operand:SCALARF 2 "register_operand")))]
830   ""
831   "")
833 (define_insn "*mul<mode>3"
834   [(set (match_operand:SCALARF 0 "register_operand" "=f")
835         (mult:SCALARF (match_operand:SCALARF 1 "register_operand" "f")
836                       (match_operand:SCALARF 2 "register_operand" "f")))]
837   "!TARGET_4300_MUL_FIX"
838   "mul.<fmt>\t%0,%1,%2"
839   [(set_attr "type" "fmul")
840    (set_attr "mode" "<MODE>")])
842 ;; Early VR4300 silicon has a CPU bug where multiplies with certain
843 ;; operands may corrupt immediately following multiplies. This is a
844 ;; simple fix to insert NOPs.
846 (define_insn "*mul<mode>3_r4300"
847   [(set (match_operand:SCALARF 0 "register_operand" "=f")
848         (mult:SCALARF (match_operand:SCALARF 1 "register_operand" "f")
849                       (match_operand:SCALARF 2 "register_operand" "f")))]
850   "TARGET_4300_MUL_FIX"
851   "mul.<fmt>\t%0,%1,%2\;nop"
852   [(set_attr "type" "fmul")
853    (set_attr "mode" "<MODE>")
854    (set_attr "length" "8")])
856 (define_insn "mulv2sf3"
857   [(set (match_operand:V2SF 0 "register_operand" "=f")
858         (mult:V2SF (match_operand:V2SF 1 "register_operand" "f")
859                    (match_operand:V2SF 2 "register_operand" "f")))]
860   "TARGET_PAIRED_SINGLE_FLOAT"
861   "mul.ps\t%0,%1,%2"
862   [(set_attr "type" "fmul")
863    (set_attr "mode" "SF")])
865 ;; The original R4000 has a cpu bug.  If a double-word or a variable
866 ;; shift executes while an integer multiplication is in progress, the
867 ;; shift may give an incorrect result.  Avoid this by keeping the mflo
868 ;; with the mult on the R4000.
870 ;; From "MIPS R4000PC/SC Errata, Processor Revision 2.2 and 3.0"
871 ;; (also valid for MIPS R4000MC processors):
873 ;; "16. R4000PC, R4000SC: Please refer to errata 28 for an update to
874 ;;      this errata description.
875 ;;      The following code sequence causes the R4000 to incorrectly
876 ;;      execute the Double Shift Right Arithmetic 32 (dsra32)
877 ;;      instruction.  If the dsra32 instruction is executed during an
878 ;;      integer multiply, the dsra32 will only shift by the amount in
879 ;;      specified in the instruction rather than the amount plus 32
880 ;;      bits.
881 ;;      instruction 1:          mult    rs,rt           integer multiply
882 ;;      instruction 2-12:       dsra32  rd,rt,rs        doubleword shift
883 ;;                                                      right arithmetic + 32
884 ;;      Workaround: A dsra32 instruction placed after an integer
885 ;;      multiply should not be one of the 11 instructions after the
886 ;;      multiply instruction."
888 ;; and:
890 ;; "28. R4000PC, R4000SC: The text from errata 16 should be replaced by
891 ;;      the following description.
892 ;;      All extended shifts (shift by n+32) and variable shifts (32 and
893 ;;      64-bit versions) may produce incorrect results under the
894 ;;      following conditions:
895 ;;      1) An integer multiply is currently executing
896 ;;      2) These types of shift instructions are executed immediately
897 ;;         following an integer divide instruction.
898 ;;      Workaround:
899 ;;      1) Make sure no integer multiply is running wihen these
900 ;;         instruction are executed.  If this cannot be predicted at
901 ;;         compile time, then insert a "mfhi" to R0 instruction
902 ;;         immediately after the integer multiply instruction.  This
903 ;;         will cause the integer multiply to complete before the shift
904 ;;         is executed.
905 ;;      2) Separate integer divide and these two classes of shift
906 ;;         instructions by another instruction or a noop."
908 ;; These processors have PRId values of 0x00004220 and 0x00004300,
909 ;; respectively.
911 (define_expand "mul<mode>3"
912   [(set (match_operand:GPR 0 "register_operand")
913         (mult:GPR (match_operand:GPR 1 "register_operand")
914                   (match_operand:GPR 2 "register_operand")))]
915   ""
917   if (GENERATE_MULT3_<MODE>)
918     emit_insn (gen_mul<mode>3_mult3 (operands[0], operands[1], operands[2]));
919   else if (!TARGET_FIX_R4000)
920     emit_insn (gen_mul<mode>3_internal (operands[0], operands[1],
921                                         operands[2]));
922   else
923     emit_insn (gen_mul<mode>3_r4000 (operands[0], operands[1], operands[2]));
924   DONE;
927 (define_insn "mulsi3_mult3"
928   [(set (match_operand:SI 0 "register_operand" "=d,l")
929         (mult:SI (match_operand:SI 1 "register_operand" "d,d")
930                  (match_operand:SI 2 "register_operand" "d,d")))
931    (clobber (match_scratch:SI 3 "=h,h"))
932    (clobber (match_scratch:SI 4 "=l,X"))]
933   "GENERATE_MULT3_SI"
935   if (which_alternative == 1)
936     return "mult\t%1,%2";
937   if (TARGET_MAD
938       || TARGET_MIPS5400
939       || TARGET_MIPS5500
940       || TARGET_MIPS7000
941       || TARGET_MIPS9000
942       || ISA_MIPS32
943       || ISA_MIPS32R2
944       || ISA_MIPS64)
945     return "mul\t%0,%1,%2";
946   return "mult\t%0,%1,%2";
948   [(set_attr "type" "imul")
949    (set_attr "mode" "SI")])
951 (define_insn "muldi3_mult3"
952   [(set (match_operand:DI 0 "register_operand" "=d")
953         (mult:DI (match_operand:DI 1 "register_operand" "d")
954                  (match_operand:DI 2 "register_operand" "d")))
955    (clobber (match_scratch:DI 3 "=h"))
956    (clobber (match_scratch:DI 4 "=l"))]
957   "TARGET_64BIT && GENERATE_MULT3_DI"
958   "dmult\t%0,%1,%2"
959   [(set_attr "type" "imul")
960    (set_attr "mode" "DI")])
962 ;; If a register gets allocated to LO, and we spill to memory, the reload
963 ;; will include a move from LO to a GPR.  Merge it into the multiplication
964 ;; if it can set the GPR directly.
966 ;; Operand 0: LO
967 ;; Operand 1: GPR (1st multiplication operand)
968 ;; Operand 2: GPR (2nd multiplication operand)
969 ;; Operand 3: HI
970 ;; Operand 4: GPR (destination)
971 (define_peephole2
972   [(parallel
973        [(set (match_operand:SI 0 "register_operand")
974              (mult:SI (match_operand:SI 1 "register_operand")
975                       (match_operand:SI 2 "register_operand")))
976         (clobber (match_operand:SI 3 "register_operand"))
977         (clobber (scratch:SI))])
978    (set (match_operand:SI 4 "register_operand")
979         (unspec [(match_dup 0) (match_dup 3)] UNSPEC_MFHILO))]
980   "GENERATE_MULT3_SI && peep2_reg_dead_p (2, operands[0])"
981   [(parallel
982        [(set (match_dup 4)
983              (mult:SI (match_dup 1)
984                       (match_dup 2)))
985         (clobber (match_dup 3))
986         (clobber (match_dup 0))])])
988 (define_insn "mul<mode>3_internal"
989   [(set (match_operand:GPR 0 "register_operand" "=l")
990         (mult:GPR (match_operand:GPR 1 "register_operand" "d")
991                   (match_operand:GPR 2 "register_operand" "d")))
992    (clobber (match_scratch:GPR 3 "=h"))]
993   "!TARGET_FIX_R4000"
994   "<d>mult\t%1,%2"
995   [(set_attr "type" "imul")
996    (set_attr "mode" "<MODE>")])
998 (define_insn "mul<mode>3_r4000"
999   [(set (match_operand:GPR 0 "register_operand" "=d")
1000         (mult:GPR (match_operand:GPR 1 "register_operand" "d")
1001                   (match_operand:GPR 2 "register_operand" "d")))
1002    (clobber (match_scratch:GPR 3 "=h"))
1003    (clobber (match_scratch:GPR 4 "=l"))]
1004   "TARGET_FIX_R4000"
1005   "<d>mult\t%1,%2\;mflo\t%0"
1006   [(set_attr "type" "imul")
1007    (set_attr "mode" "<MODE>")
1008    (set_attr "length" "8")])
1010 ;; On the VR4120 and VR4130, it is better to use "mtlo $0; macc" instead
1011 ;; of "mult; mflo".  They have the same latency, but the first form gives
1012 ;; us an extra cycle to compute the operands.
1014 ;; Operand 0: LO
1015 ;; Operand 1: GPR (1st multiplication operand)
1016 ;; Operand 2: GPR (2nd multiplication operand)
1017 ;; Operand 3: HI
1018 ;; Operand 4: GPR (destination)
1019 (define_peephole2
1020   [(parallel
1021        [(set (match_operand:SI 0 "register_operand")
1022              (mult:SI (match_operand:SI 1 "register_operand")
1023                       (match_operand:SI 2 "register_operand")))
1024         (clobber (match_operand:SI 3 "register_operand"))])
1025    (set (match_operand:SI 4 "register_operand")
1026         (unspec:SI [(match_dup 0) (match_dup 3)] UNSPEC_MFHILO))]
1027   "ISA_HAS_MACC && !GENERATE_MULT3_SI"
1028   [(set (match_dup 0)
1029         (const_int 0))
1030    (parallel
1031        [(set (match_dup 0)
1032              (plus:SI (mult:SI (match_dup 1)
1033                                (match_dup 2))
1034                       (match_dup 0)))
1035         (set (match_dup 4)
1036              (plus:SI (mult:SI (match_dup 1)
1037                                (match_dup 2))
1038                       (match_dup 0)))
1039         (clobber (match_dup 3))])])
1041 ;; Multiply-accumulate patterns
1043 ;; For processors that can copy the output to a general register:
1045 ;; The all-d alternative is needed because the combiner will find this
1046 ;; pattern and then register alloc/reload will move registers around to
1047 ;; make them fit, and we don't want to trigger unnecessary loads to LO.
1049 ;; The last alternative should be made slightly less desirable, but adding
1050 ;; "?" to the constraint is too strong, and causes values to be loaded into
1051 ;; LO even when that's more costly.  For now, using "*d" mostly does the
1052 ;; trick.
1053 (define_insn "*mul_acc_si"
1054   [(set (match_operand:SI 0 "register_operand" "=l,*d,*d")
1055         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "d,d,d")
1056                           (match_operand:SI 2 "register_operand" "d,d,d"))
1057                  (match_operand:SI 3 "register_operand" "0,l,*d")))
1058    (clobber (match_scratch:SI 4 "=h,h,h"))
1059    (clobber (match_scratch:SI 5 "=X,3,l"))
1060    (clobber (match_scratch:SI 6 "=X,X,&d"))]
1061   "(TARGET_MIPS3900
1062    || ISA_HAS_MADD_MSUB)
1063    && !TARGET_MIPS16"
1065   static const char *const madd[] = { "madd\t%1,%2", "madd\t%0,%1,%2" };
1066   if (which_alternative == 2)
1067     return "#";
1068   if (ISA_HAS_MADD_MSUB && which_alternative != 0)
1069     return "#";
1070   return madd[which_alternative];
1072   [(set_attr "type"     "imadd,imadd,multi")
1073    (set_attr "mode"     "SI")
1074    (set_attr "length"   "4,4,8")])
1076 ;; Split the above insn if we failed to get LO allocated.
1077 (define_split
1078   [(set (match_operand:SI 0 "register_operand")
1079         (plus:SI (mult:SI (match_operand:SI 1 "register_operand")
1080                           (match_operand:SI 2 "register_operand"))
1081                  (match_operand:SI 3 "register_operand")))
1082    (clobber (match_scratch:SI 4))
1083    (clobber (match_scratch:SI 5))
1084    (clobber (match_scratch:SI 6))]
1085   "reload_completed && !TARGET_DEBUG_D_MODE
1086    && GP_REG_P (true_regnum (operands[0]))
1087    && GP_REG_P (true_regnum (operands[3]))"
1088   [(parallel [(set (match_dup 6)
1089                    (mult:SI (match_dup 1) (match_dup 2)))
1090               (clobber (match_dup 4))
1091               (clobber (match_dup 5))])
1092    (set (match_dup 0) (plus:SI (match_dup 6) (match_dup 3)))]
1093   "")
1095 ;; Splitter to copy result of MADD to a general register
1096 (define_split
1097   [(set (match_operand:SI                   0 "register_operand")
1098         (plus:SI (mult:SI (match_operand:SI 1 "register_operand")
1099                           (match_operand:SI 2 "register_operand"))
1100                  (match_operand:SI          3 "register_operand")))
1101    (clobber (match_scratch:SI               4))
1102    (clobber (match_scratch:SI               5))
1103    (clobber (match_scratch:SI               6))]
1104   "reload_completed && !TARGET_DEBUG_D_MODE
1105    && GP_REG_P (true_regnum (operands[0]))
1106    && true_regnum (operands[3]) == LO_REGNUM"
1107   [(parallel [(set (match_dup 3)
1108                    (plus:SI (mult:SI (match_dup 1) (match_dup 2))
1109                             (match_dup 3)))
1110               (clobber (match_dup 4))
1111               (clobber (match_dup 5))
1112               (clobber (match_dup 6))])
1113    (set (match_dup 0) (unspec:SI [(match_dup 5) (match_dup 4)] UNSPEC_MFHILO))]
1114   "")
1116 (define_insn "*macc"
1117   [(set (match_operand:SI 0 "register_operand" "=l,d")
1118         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "d,d")
1119                           (match_operand:SI 2 "register_operand" "d,d"))
1120                  (match_operand:SI 3 "register_operand" "0,l")))
1121    (clobber (match_scratch:SI 4 "=h,h"))
1122    (clobber (match_scratch:SI 5 "=X,3"))]
1123   "ISA_HAS_MACC"
1125   if (which_alternative == 1)
1126     return "macc\t%0,%1,%2";
1127   else if (TARGET_MIPS5500)
1128     return "madd\t%1,%2";
1129   else
1130     /* The VR4130 assumes that there is a two-cycle latency between a macc
1131        that "writes" to $0 and an instruction that reads from it.  We avoid
1132        this by assigning to $1 instead.  */
1133     return "%[macc\t%@,%1,%2%]";
1135   [(set_attr "type" "imadd")
1136    (set_attr "mode" "SI")])
1138 (define_insn "*msac"
1139   [(set (match_operand:SI 0 "register_operand" "=l,d")
1140         (minus:SI (match_operand:SI 1 "register_operand" "0,l")
1141                   (mult:SI (match_operand:SI 2 "register_operand" "d,d")
1142                            (match_operand:SI 3 "register_operand" "d,d"))))
1143    (clobber (match_scratch:SI 4 "=h,h"))
1144    (clobber (match_scratch:SI 5 "=X,1"))]
1145   "ISA_HAS_MSAC"
1147   if (which_alternative == 1)
1148     return "msac\t%0,%2,%3";
1149   else if (TARGET_MIPS5500)
1150     return "msub\t%2,%3";
1151   else
1152     return "msac\t$0,%2,%3";
1154   [(set_attr "type"     "imadd")
1155    (set_attr "mode"     "SI")])
1157 ;; An msac-like instruction implemented using negation and a macc.
1158 (define_insn_and_split "*msac_using_macc"
1159   [(set (match_operand:SI 0 "register_operand" "=l,d")
1160         (minus:SI (match_operand:SI 1 "register_operand" "0,l")
1161                   (mult:SI (match_operand:SI 2 "register_operand" "d,d")
1162                            (match_operand:SI 3 "register_operand" "d,d"))))
1163    (clobber (match_scratch:SI 4 "=h,h"))
1164    (clobber (match_scratch:SI 5 "=X,1"))
1165    (clobber (match_scratch:SI 6 "=d,d"))]
1166   "ISA_HAS_MACC && !ISA_HAS_MSAC"
1167   "#"
1168   "&& reload_completed"
1169   [(set (match_dup 6)
1170         (neg:SI (match_dup 3)))
1171    (parallel
1172        [(set (match_dup 0)
1173              (plus:SI (mult:SI (match_dup 2)
1174                                (match_dup 6))
1175                       (match_dup 1)))
1176         (clobber (match_dup 4))
1177         (clobber (match_dup 5))])]
1178   ""
1179   [(set_attr "type"     "imadd")
1180    (set_attr "length"   "8")])
1182 ;; Patterns generated by the define_peephole2 below.
1184 (define_insn "*macc2"
1185   [(set (match_operand:SI 0 "register_operand" "=l")
1186         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "d")
1187                           (match_operand:SI 2 "register_operand" "d"))
1188                  (match_dup 0)))
1189    (set (match_operand:SI 3 "register_operand" "=d")
1190         (plus:SI (mult:SI (match_dup 1)
1191                           (match_dup 2))
1192                  (match_dup 0)))
1193    (clobber (match_scratch:SI 4 "=h"))]
1194   "ISA_HAS_MACC && reload_completed"
1195   "macc\t%3,%1,%2"
1196   [(set_attr "type"     "imadd")
1197    (set_attr "mode"     "SI")])
1199 (define_insn "*msac2"
1200   [(set (match_operand:SI 0 "register_operand" "=l")
1201         (minus:SI (match_dup 0)
1202                   (mult:SI (match_operand:SI 1 "register_operand" "d")
1203                            (match_operand:SI 2 "register_operand" "d"))))
1204    (set (match_operand:SI 3 "register_operand" "=d")
1205         (minus:SI (match_dup 0)
1206                   (mult:SI (match_dup 1)
1207                            (match_dup 2))))
1208    (clobber (match_scratch:SI 4 "=h"))]
1209   "ISA_HAS_MSAC && reload_completed"
1210   "msac\t%3,%1,%2"
1211   [(set_attr "type"     "imadd")
1212    (set_attr "mode"     "SI")])
1214 ;; Convert macc $0,<r1>,<r2> & mflo <r3> into macc <r3>,<r1>,<r2>
1215 ;; Similarly msac.
1217 ;; Operand 0: LO
1218 ;; Operand 1: macc/msac
1219 ;; Operand 2: HI
1220 ;; Operand 3: GPR (destination)
1221 (define_peephole2
1222   [(parallel
1223        [(set (match_operand:SI 0 "register_operand")
1224              (match_operand:SI 1 "macc_msac_operand"))
1225         (clobber (match_operand:SI 2 "register_operand"))
1226         (clobber (scratch:SI))])
1227    (set (match_operand:SI 3 "register_operand")
1228         (unspec:SI [(match_dup 0) (match_dup 2)] UNSPEC_MFHILO))]
1229   ""
1230   [(parallel [(set (match_dup 0)
1231                    (match_dup 1))
1232               (set (match_dup 3)
1233                    (match_dup 1))
1234               (clobber (match_dup 2))])]
1235   "")
1237 ;; When we have a three-address multiplication instruction, it should
1238 ;; be faster to do a separate multiply and add, rather than moving
1239 ;; something into LO in order to use a macc instruction.
1241 ;; This peephole needs a scratch register to cater for the case when one
1242 ;; of the multiplication operands is the same as the destination.
1244 ;; Operand 0: GPR (scratch)
1245 ;; Operand 1: LO
1246 ;; Operand 2: GPR (addend)
1247 ;; Operand 3: GPR (destination)
1248 ;; Operand 4: macc/msac
1249 ;; Operand 5: HI
1250 ;; Operand 6: new multiplication
1251 ;; Operand 7: new addition/subtraction
1252 (define_peephole2
1253   [(match_scratch:SI 0 "d")
1254    (set (match_operand:SI 1 "register_operand")
1255         (match_operand:SI 2 "register_operand"))
1256    (match_dup 0)
1257    (parallel
1258        [(set (match_operand:SI 3 "register_operand")
1259              (match_operand:SI 4 "macc_msac_operand"))
1260         (clobber (match_operand:SI 5 "register_operand"))
1261         (clobber (match_dup 1))])]
1262   "GENERATE_MULT3_SI
1263    && true_regnum (operands[1]) == LO_REGNUM
1264    && peep2_reg_dead_p (2, operands[1])
1265    && GP_REG_P (true_regnum (operands[3]))"
1266   [(parallel [(set (match_dup 0)
1267                    (match_dup 6))
1268               (clobber (match_dup 5))
1269               (clobber (match_dup 1))])
1270    (set (match_dup 3)
1271         (match_dup 7))]
1273   operands[6] = XEXP (operands[4], GET_CODE (operands[4]) == PLUS ? 0 : 1);
1274   operands[7] = gen_rtx_fmt_ee (GET_CODE (operands[4]), SImode,
1275                                 operands[2], operands[0]);
1278 ;; Same as above, except LO is the initial target of the macc.
1280 ;; Operand 0: GPR (scratch)
1281 ;; Operand 1: LO
1282 ;; Operand 2: GPR (addend)
1283 ;; Operand 3: macc/msac
1284 ;; Operand 4: HI
1285 ;; Operand 5: GPR (destination)
1286 ;; Operand 6: new multiplication
1287 ;; Operand 7: new addition/subtraction
1288 (define_peephole2
1289   [(match_scratch:SI 0 "d")
1290    (set (match_operand:SI 1 "register_operand")
1291         (match_operand:SI 2 "register_operand"))
1292    (match_dup 0)
1293    (parallel
1294        [(set (match_dup 1)
1295              (match_operand:SI 3 "macc_msac_operand"))
1296         (clobber (match_operand:SI 4 "register_operand"))
1297         (clobber (scratch:SI))])
1298    (match_dup 0)
1299    (set (match_operand:SI 5 "register_operand")
1300         (unspec:SI [(match_dup 1) (match_dup 4)] UNSPEC_MFHILO))]
1301   "GENERATE_MULT3_SI && peep2_reg_dead_p (3, operands[1])"
1302   [(parallel [(set (match_dup 0)
1303                    (match_dup 6))
1304               (clobber (match_dup 4))
1305               (clobber (match_dup 1))])
1306    (set (match_dup 5)
1307         (match_dup 7))]
1309   operands[6] = XEXP (operands[4], GET_CODE (operands[4]) == PLUS ? 0 : 1);
1310   operands[7] = gen_rtx_fmt_ee (GET_CODE (operands[4]), SImode,
1311                                 operands[2], operands[0]);
1314 (define_insn "*mul_sub_si"
1315   [(set (match_operand:SI 0 "register_operand" "=l,*d,*d")
1316         (minus:SI (match_operand:SI 1 "register_operand" "0,l,*d")
1317                   (mult:SI (match_operand:SI 2 "register_operand" "d,d,d")
1318                            (match_operand:SI 3 "register_operand" "d,d,d"))))
1319    (clobber (match_scratch:SI 4 "=h,h,h"))
1320    (clobber (match_scratch:SI 5 "=X,1,l"))
1321    (clobber (match_scratch:SI 6 "=X,X,&d"))]
1322   "ISA_HAS_MADD_MSUB"
1323   "@
1324    msub\t%2,%3
1325    #
1326    #"
1327   [(set_attr "type"     "imadd,multi,multi")
1328    (set_attr "mode"     "SI")
1329    (set_attr "length"   "4,8,8")])
1331 ;; Split the above insn if we failed to get LO allocated.
1332 (define_split
1333   [(set (match_operand:SI 0 "register_operand")
1334         (minus:SI (match_operand:SI 1 "register_operand")
1335                   (mult:SI (match_operand:SI 2 "register_operand")
1336                            (match_operand:SI 3 "register_operand"))))
1337    (clobber (match_scratch:SI 4))
1338    (clobber (match_scratch:SI 5))
1339    (clobber (match_scratch:SI 6))]
1340   "reload_completed && !TARGET_DEBUG_D_MODE
1341    && GP_REG_P (true_regnum (operands[0]))
1342    && GP_REG_P (true_regnum (operands[1]))"
1343   [(parallel [(set (match_dup 6)
1344                    (mult:SI (match_dup 2) (match_dup 3)))
1345               (clobber (match_dup 4))
1346               (clobber (match_dup 5))])
1347    (set (match_dup 0) (minus:SI (match_dup 1) (match_dup 6)))]
1348   "")
1350 ;; Splitter to copy result of MSUB to a general register
1351 (define_split
1352   [(set (match_operand:SI 0 "register_operand")
1353         (minus:SI (match_operand:SI 1 "register_operand")
1354                   (mult:SI (match_operand:SI 2 "register_operand")
1355                            (match_operand:SI 3 "register_operand"))))
1356    (clobber (match_scratch:SI 4))
1357    (clobber (match_scratch:SI 5))
1358    (clobber (match_scratch:SI 6))]
1359   "reload_completed && !TARGET_DEBUG_D_MODE
1360    && GP_REG_P (true_regnum (operands[0]))
1361    && true_regnum (operands[1]) == LO_REGNUM"
1362   [(parallel [(set (match_dup 1)
1363                    (minus:SI (match_dup 1)
1364                              (mult:SI (match_dup 2) (match_dup 3))))
1365               (clobber (match_dup 4))
1366               (clobber (match_dup 5))
1367               (clobber (match_dup 6))])
1368    (set (match_dup 0) (unspec:SI [(match_dup 5) (match_dup 4)] UNSPEC_MFHILO))]
1369   "")
1371 (define_insn "*muls"
1372   [(set (match_operand:SI                  0 "register_operand" "=l,d")
1373         (neg:SI (mult:SI (match_operand:SI 1 "register_operand" "d,d")
1374                          (match_operand:SI 2 "register_operand" "d,d"))))
1375    (clobber (match_scratch:SI              3                    "=h,h"))
1376    (clobber (match_scratch:SI              4                    "=X,l"))]
1377   "ISA_HAS_MULS"
1378   "@
1379    muls\t$0,%1,%2
1380    muls\t%0,%1,%2"
1381   [(set_attr "type"     "imul")
1382    (set_attr "mode"     "SI")])
1384 ;; ??? We could define a mulditi3 pattern when TARGET_64BIT.
1386 (define_expand "<u>mulsidi3"
1387   [(parallel
1388       [(set (match_operand:DI 0 "register_operand")
1389             (mult:DI (any_extend:DI (match_operand:SI 1 "register_operand"))
1390                      (any_extend:DI (match_operand:SI 2 "register_operand"))))
1391        (clobber (scratch:DI))
1392        (clobber (scratch:DI))
1393        (clobber (scratch:DI))])]
1394   "!TARGET_64BIT || !TARGET_FIX_R4000"
1396   if (!TARGET_64BIT)
1397     {
1398       if (!TARGET_FIX_R4000)
1399         emit_insn (gen_<u>mulsidi3_32bit_internal (operands[0], operands[1],
1400                                                    operands[2]));
1401       else
1402         emit_insn (gen_<u>mulsidi3_32bit_r4000 (operands[0], operands[1],
1403                                                 operands[2]));
1404       DONE;
1405     }
1408 (define_insn "<u>mulsidi3_32bit_internal"
1409   [(set (match_operand:DI 0 "register_operand" "=x")
1410         (mult:DI (any_extend:DI (match_operand:SI 1 "register_operand" "d"))
1411                  (any_extend:DI (match_operand:SI 2 "register_operand" "d"))))]
1412   "!TARGET_64BIT && !TARGET_FIX_R4000"
1413   "mult<u>\t%1,%2"
1414   [(set_attr "type" "imul")
1415    (set_attr "mode" "SI")])
1417 (define_insn "<u>mulsidi3_32bit_r4000"
1418   [(set (match_operand:DI 0 "register_operand" "=d")
1419         (mult:DI (any_extend:DI (match_operand:SI 1 "register_operand" "d"))
1420                  (any_extend:DI (match_operand:SI 2 "register_operand" "d"))))
1421    (clobber (match_scratch:DI 3 "=x"))]
1422   "!TARGET_64BIT && TARGET_FIX_R4000"
1423   "mult<u>\t%1,%2\;mflo\t%L0;mfhi\t%M0"
1424   [(set_attr "type" "imul")
1425    (set_attr "mode" "SI")
1426    (set_attr "length" "12")])
1428 (define_insn_and_split "*<u>mulsidi3_64bit"
1429   [(set (match_operand:DI 0 "register_operand" "=d")
1430         (mult:DI (any_extend:DI (match_operand:SI 1 "register_operand" "d"))
1431                  (any_extend:DI (match_operand:SI 2 "register_operand" "d"))))
1432    (clobber (match_scratch:DI 3 "=l"))
1433    (clobber (match_scratch:DI 4 "=h"))
1434    (clobber (match_scratch:DI 5 "=d"))]
1435   "TARGET_64BIT && !TARGET_FIX_R4000"
1436   "#"
1437   "&& reload_completed"
1438   [(parallel
1439        [(set (match_dup 3)
1440              (sign_extend:DI
1441                 (mult:SI (match_dup 1)
1442                          (match_dup 2))))
1443         (set (match_dup 4)
1444              (ashiftrt:DI
1445                 (mult:DI (any_extend:DI (match_dup 1))
1446                          (any_extend:DI (match_dup 2)))
1447                 (const_int 32)))])
1449    ;; OP5 <- LO, OP0 <- HI
1450    (set (match_dup 5) (unspec:DI [(match_dup 3) (match_dup 4)] UNSPEC_MFHILO))
1451    (set (match_dup 0) (unspec:DI [(match_dup 4) (match_dup 3)] UNSPEC_MFHILO))
1453    ;; Zero-extend OP5.
1454    (set (match_dup 5)
1455         (ashift:DI (match_dup 5)
1456                    (const_int 32)))
1457    (set (match_dup 5)
1458         (lshiftrt:DI (match_dup 5)
1459                      (const_int 32)))
1461    ;; Shift OP0 into place.
1462    (set (match_dup 0)
1463         (ashift:DI (match_dup 0)
1464                    (const_int 32)))
1466    ;; OR the two halves together
1467    (set (match_dup 0)
1468         (ior:DI (match_dup 0)
1469                 (match_dup 5)))]
1470   ""
1471   [(set_attr "type" "imul")
1472    (set_attr "mode" "SI")
1473    (set_attr "length" "24")])
1475 (define_insn "*<u>mulsidi3_64bit_parts"
1476   [(set (match_operand:DI 0 "register_operand" "=l")
1477         (sign_extend:DI
1478            (mult:SI (match_operand:SI 2 "register_operand" "d")
1479                     (match_operand:SI 3 "register_operand" "d"))))
1480    (set (match_operand:DI 1 "register_operand" "=h")
1481         (ashiftrt:DI
1482            (mult:DI (any_extend:DI (match_dup 2))
1483                     (any_extend:DI (match_dup 3)))
1484            (const_int 32)))]
1485   "TARGET_64BIT && !TARGET_FIX_R4000"
1486   "mult<u>\t%2,%3"
1487   [(set_attr "type" "imul")
1488    (set_attr "mode" "SI")])
1490 ;; Widening multiply with negation.
1491 (define_insn "*muls<u>_di"
1492   [(set (match_operand:DI 0 "register_operand" "=x")
1493         (neg:DI
1494          (mult:DI
1495           (any_extend:DI (match_operand:SI 1 "register_operand" "d"))
1496           (any_extend:DI (match_operand:SI 2 "register_operand" "d")))))]
1497   "!TARGET_64BIT && ISA_HAS_MULS"
1498   "muls<u>\t$0,%1,%2"
1499   [(set_attr "type" "imul")
1500    (set_attr "mode" "SI")])
1502 (define_insn "*msac<u>_di"
1503   [(set (match_operand:DI 0 "register_operand" "=x")
1504         (minus:DI
1505            (match_operand:DI 3 "register_operand" "0")
1506            (mult:DI
1507               (any_extend:DI (match_operand:SI 1 "register_operand" "d"))
1508               (any_extend:DI (match_operand:SI 2 "register_operand" "d")))))]
1509   "!TARGET_64BIT && ISA_HAS_MSAC"
1511   if (TARGET_MIPS5500)
1512     return "msub<u>\t%1,%2";
1513   else
1514     return "msac<u>\t$0,%1,%2";
1516   [(set_attr "type" "imadd")
1517    (set_attr "mode" "SI")])
1519 ;; _highpart patterns
1521 (define_expand "<su>mulsi3_highpart"
1522   [(set (match_operand:SI 0 "register_operand")
1523         (truncate:SI
1524          (lshiftrt:DI
1525           (mult:DI (any_extend:DI (match_operand:SI 1 "register_operand"))
1526                    (any_extend:DI (match_operand:SI 2 "register_operand")))
1527           (const_int 32))))]
1528   "ISA_HAS_MULHI || !TARGET_FIX_R4000"
1530   if (ISA_HAS_MULHI)
1531     emit_insn (gen_<su>mulsi3_highpart_mulhi_internal (operands[0],
1532                                                        operands[1],
1533                                                        operands[2]));
1534   else
1535     emit_insn (gen_<su>mulsi3_highpart_internal (operands[0], operands[1],
1536                                                  operands[2]));
1537   DONE;
1540 (define_insn "<su>mulsi3_highpart_internal"
1541   [(set (match_operand:SI 0 "register_operand" "=h")
1542         (truncate:SI
1543          (lshiftrt:DI
1544           (mult:DI (any_extend:DI (match_operand:SI 1 "register_operand" "d"))
1545                    (any_extend:DI (match_operand:SI 2 "register_operand" "d")))
1546           (const_int 32))))
1547    (clobber (match_scratch:SI 3 "=l"))]
1548   "!ISA_HAS_MULHI && !TARGET_FIX_R4000"
1549   "mult<u>\t%1,%2"
1550   [(set_attr "type" "imul")
1551    (set_attr "mode" "SI")])
1553 (define_insn "<su>mulsi3_highpart_mulhi_internal"
1554   [(set (match_operand:SI 0 "register_operand" "=h,d")
1555         (truncate:SI
1556          (lshiftrt:DI
1557           (mult:DI
1558            (any_extend:DI (match_operand:SI 1 "register_operand" "d,d"))
1559            (any_extend:DI (match_operand:SI 2 "register_operand" "d,d")))
1560           (const_int 32))))
1561    (clobber (match_scratch:SI 3 "=l,l"))
1562    (clobber (match_scratch:SI 4 "=X,h"))]
1563   "ISA_HAS_MULHI"
1564   "@
1565    mult<u>\t%1,%2
1566    mulhi<u>\t%0,%1,%2"
1567   [(set_attr "type" "imul")
1568    (set_attr "mode" "SI")])
1570 (define_insn "*<su>mulsi3_highpart_neg_mulhi_internal"
1571   [(set (match_operand:SI 0 "register_operand" "=h,d")
1572         (truncate:SI
1573          (lshiftrt:DI
1574           (neg:DI
1575            (mult:DI
1576             (any_extend:DI (match_operand:SI 1 "register_operand" "d,d"))
1577             (any_extend:DI (match_operand:SI 2 "register_operand" "d,d"))))
1578           (const_int 32))))
1579    (clobber (match_scratch:SI 3 "=l,l"))
1580    (clobber (match_scratch:SI 4 "=X,h"))]
1581   "ISA_HAS_MULHI"
1582   "@
1583    mulshi<u>\t%.,%1,%2
1584    mulshi<u>\t%0,%1,%2"
1585   [(set_attr "type" "imul")
1586    (set_attr "mode" "SI")])
1588 ;; Disable unsigned multiplication for -mfix-vr4120.  This is for VR4120
1589 ;; errata MD(0), which says that dmultu does not always produce the
1590 ;; correct result.
1591 (define_insn "<su>muldi3_highpart"
1592   [(set (match_operand:DI 0 "register_operand" "=h")
1593         (truncate:DI
1594          (lshiftrt:TI
1595           (mult:TI
1596            (any_extend:TI (match_operand:DI 1 "register_operand" "d"))
1597            (any_extend:TI (match_operand:DI 2 "register_operand" "d")))
1598           (const_int 64))))
1599    (clobber (match_scratch:DI 3 "=l"))]
1600   "TARGET_64BIT && !TARGET_FIX_R4000
1601    && !(<CODE> == ZERO_EXTEND && TARGET_FIX_VR4120)"
1602   "dmult<u>\t%1,%2"
1603   [(set_attr "type" "imul")
1604    (set_attr "mode" "DI")])
1606 ;; The R4650 supports a 32 bit multiply/ 64 bit accumulate
1607 ;; instruction.  The HI/LO registers are used as a 64 bit accumulator.
1609 (define_insn "madsi"
1610   [(set (match_operand:SI 0 "register_operand" "+l")
1611         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "d")
1612                           (match_operand:SI 2 "register_operand" "d"))
1613                  (match_dup 0)))
1614    (clobber (match_scratch:SI 3 "=h"))]
1615   "TARGET_MAD"
1616   "mad\t%1,%2"
1617   [(set_attr "type"     "imadd")
1618    (set_attr "mode"     "SI")])
1620 (define_insn "*<su>mul_acc_di"
1621   [(set (match_operand:DI 0 "register_operand" "=x")
1622         (plus:DI
1623          (mult:DI (any_extend:DI (match_operand:SI 1 "register_operand" "d"))
1624                   (any_extend:DI (match_operand:SI 2 "register_operand" "d")))
1625          (match_operand:DI 3 "register_operand" "0")))]
1626   "(TARGET_MAD || ISA_HAS_MACC)
1627    && !TARGET_64BIT"
1629   if (TARGET_MAD)
1630     return "mad<u>\t%1,%2";
1631   else if (TARGET_MIPS5500)
1632     return "madd<u>\t%1,%2";
1633   else
1634     /* See comment in *macc.  */
1635     return "%[macc<u>\t%@,%1,%2%]";
1637   [(set_attr "type" "imadd")
1638    (set_attr "mode" "SI")])
1640 ;; Floating point multiply accumulate instructions.
1642 (define_insn "*madd<mode>"
1643   [(set (match_operand:ANYF 0 "register_operand" "=f")
1644         (plus:ANYF (mult:ANYF (match_operand:ANYF 1 "register_operand" "f")
1645                               (match_operand:ANYF 2 "register_operand" "f"))
1646                    (match_operand:ANYF 3 "register_operand" "f")))]
1647   "ISA_HAS_FP4 && TARGET_FUSED_MADD"
1648   "madd.<fmt>\t%0,%3,%1,%2"
1649   [(set_attr "type" "fmadd")
1650    (set_attr "mode" "<UNITMODE>")])
1652 (define_insn "*msub<mode>"
1653   [(set (match_operand:ANYF 0 "register_operand" "=f")
1654         (minus:ANYF (mult:ANYF (match_operand:ANYF 1 "register_operand" "f")
1655                                (match_operand:ANYF 2 "register_operand" "f"))
1656                     (match_operand:ANYF 3 "register_operand" "f")))]
1657   "ISA_HAS_FP4 && TARGET_FUSED_MADD"
1658   "msub.<fmt>\t%0,%3,%1,%2"
1659   [(set_attr "type" "fmadd")
1660    (set_attr "mode" "<UNITMODE>")])
1662 (define_insn "*nmadd<mode>"
1663   [(set (match_operand:ANYF 0 "register_operand" "=f")
1664         (neg:ANYF (plus:ANYF
1665                    (mult:ANYF (match_operand:ANYF 1 "register_operand" "f")
1666                               (match_operand:ANYF 2 "register_operand" "f"))
1667                    (match_operand:ANYF 3 "register_operand" "f"))))]
1668   "ISA_HAS_NMADD_NMSUB && TARGET_FUSED_MADD
1669    && HONOR_SIGNED_ZEROS (<MODE>mode)"
1670   "nmadd.<fmt>\t%0,%3,%1,%2"
1671   [(set_attr "type" "fmadd")
1672    (set_attr "mode" "<UNITMODE>")])
1674 (define_insn "*nmadd<mode>_fastmath"
1675   [(set (match_operand:ANYF 0 "register_operand" "=f")
1676         (minus:ANYF
1677          (mult:ANYF (neg:ANYF (match_operand:ANYF 1 "register_operand" "f"))
1678                     (match_operand:ANYF 2 "register_operand" "f"))
1679          (match_operand:ANYF 3 "register_operand" "f")))]
1680   "ISA_HAS_NMADD_NMSUB && TARGET_FUSED_MADD
1681    && !HONOR_SIGNED_ZEROS (<MODE>mode)"
1682   "nmadd.<fmt>\t%0,%3,%1,%2"
1683   [(set_attr "type" "fmadd")
1684    (set_attr "mode" "<UNITMODE>")])
1686 (define_insn "*nmsub<mode>"
1687   [(set (match_operand:ANYF 0 "register_operand" "=f")
1688         (neg:ANYF (minus:ANYF
1689                    (mult:ANYF (match_operand:ANYF 2 "register_operand" "f")
1690                               (match_operand:ANYF 3 "register_operand" "f"))
1691                    (match_operand:ANYF 1 "register_operand" "f"))))]
1692   "ISA_HAS_NMADD_NMSUB && TARGET_FUSED_MADD
1693    && HONOR_SIGNED_ZEROS (<MODE>mode)"
1694   "nmsub.<fmt>\t%0,%1,%2,%3"
1695   [(set_attr "type" "fmadd")
1696    (set_attr "mode" "<UNITMODE>")])
1698 (define_insn "*nmsub<mode>_fastmath"
1699   [(set (match_operand:ANYF 0 "register_operand" "=f")
1700         (minus:ANYF
1701          (match_operand:ANYF 1 "register_operand" "f")
1702          (mult:ANYF (match_operand:ANYF 2 "register_operand" "f")
1703                     (match_operand:ANYF 3 "register_operand" "f"))))]
1704   "ISA_HAS_NMADD_NMSUB && TARGET_FUSED_MADD
1705    && !HONOR_SIGNED_ZEROS (<MODE>mode)"
1706   "nmsub.<fmt>\t%0,%1,%2,%3"
1707   [(set_attr "type" "fmadd")
1708    (set_attr "mode" "<UNITMODE>")])
1711 ;;  ....................
1713 ;;      DIVISION and REMAINDER
1715 ;;  ....................
1718 (define_expand "div<mode>3"
1719   [(set (match_operand:ANYF 0 "register_operand")
1720         (div:ANYF (match_operand:ANYF 1 "reg_or_1_operand")
1721                   (match_operand:ANYF 2 "register_operand")))]
1722   "<divide_condition>"
1724   if (const_1_operand (operands[1], <MODE>mode))
1725     if (!(ISA_HAS_FP4 && flag_unsafe_math_optimizations))
1726       operands[1] = force_reg (<MODE>mode, operands[1]);
1729 ;; These patterns work around the early SB-1 rev2 core "F1" erratum:
1731 ;; If an mfc1 or dmfc1 happens to access the floating point register
1732 ;; file at the same time a long latency operation (div, sqrt, recip,
1733 ;; sqrt) iterates an intermediate result back through the floating
1734 ;; point register file bypass, then instead returning the correct
1735 ;; register value the mfc1 or dmfc1 operation returns the intermediate
1736 ;; result of the long latency operation.
1738 ;; The workaround is to insert an unconditional 'mov' from/to the
1739 ;; long latency op destination register.
1741 (define_insn "*div<mode>3"
1742   [(set (match_operand:ANYF 0 "register_operand" "=f")
1743         (div:ANYF (match_operand:ANYF 1 "register_operand" "f")
1744                   (match_operand:ANYF 2 "register_operand" "f")))]
1745   "<divide_condition>"
1747   if (TARGET_FIX_SB1)
1748     return "div.<fmt>\t%0,%1,%2\;mov.<fmt>\t%0,%0";
1749   else
1750     return "div.<fmt>\t%0,%1,%2";
1752   [(set_attr "type" "fdiv")
1753    (set_attr "mode" "<UNITMODE>")
1754    (set (attr "length")
1755         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
1756                       (const_int 8)
1757                       (const_int 4)))])
1759 (define_insn "*recip<mode>3"
1760   [(set (match_operand:ANYF 0 "register_operand" "=f")
1761         (div:ANYF (match_operand:ANYF 1 "const_1_operand" "")
1762                   (match_operand:ANYF 2 "register_operand" "f")))]
1763   "<recip_condition> && flag_unsafe_math_optimizations"
1765   if (TARGET_FIX_SB1)
1766     return "recip.<fmt>\t%0,%2\;mov.<fmt>\t%0,%0";
1767   else
1768     return "recip.<fmt>\t%0,%2";
1770   [(set_attr "type" "frdiv")
1771    (set_attr "mode" "<UNITMODE>")
1772    (set (attr "length")
1773         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
1774                       (const_int 8)
1775                       (const_int 4)))])
1777 ;; VR4120 errata MD(A1): signed division instructions do not work correctly
1778 ;; with negative operands.  We use special libgcc functions instead.
1779 (define_insn "divmod<mode>4"
1780   [(set (match_operand:GPR 0 "register_operand" "=l")
1781         (div:GPR (match_operand:GPR 1 "register_operand" "d")
1782                  (match_operand:GPR 2 "register_operand" "d")))
1783    (set (match_operand:GPR 3 "register_operand" "=h")
1784         (mod:GPR (match_dup 1)
1785                  (match_dup 2)))]
1786   "!TARGET_FIX_VR4120"
1787   { return mips_output_division ("<d>div\t$0,%1,%2", operands); }
1788   [(set_attr "type" "idiv")
1789    (set_attr "mode" "<MODE>")])
1791 (define_insn "udivmod<mode>4"
1792   [(set (match_operand:GPR 0 "register_operand" "=l")
1793         (udiv:GPR (match_operand:GPR 1 "register_operand" "d")
1794                   (match_operand:GPR 2 "register_operand" "d")))
1795    (set (match_operand:GPR 3 "register_operand" "=h")
1796         (umod:GPR (match_dup 1)
1797                   (match_dup 2)))]
1798   ""
1799   { return mips_output_division ("<d>divu\t$0,%1,%2", operands); }
1800   [(set_attr "type" "idiv")
1801    (set_attr "mode" "<MODE>")])
1804 ;;  ....................
1806 ;;      SQUARE ROOT
1808 ;;  ....................
1810 ;; These patterns work around the early SB-1 rev2 core "F1" erratum (see
1811 ;; "*div[sd]f3" comment for details).
1813 (define_insn "sqrt<mode>2"
1814   [(set (match_operand:ANYF 0 "register_operand" "=f")
1815         (sqrt:ANYF (match_operand:ANYF 1 "register_operand" "f")))]
1816   "<sqrt_condition>"
1818   if (TARGET_FIX_SB1)
1819     return "sqrt.<fmt>\t%0,%1\;mov.<fmt>\t%0,%0";
1820   else
1821     return "sqrt.<fmt>\t%0,%1";
1823   [(set_attr "type" "fsqrt")
1824    (set_attr "mode" "<UNITMODE>")
1825    (set (attr "length")
1826         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
1827                       (const_int 8)
1828                       (const_int 4)))])
1830 (define_insn "*rsqrt<mode>a"
1831   [(set (match_operand:ANYF 0 "register_operand" "=f")
1832         (div:ANYF (match_operand:ANYF 1 "const_1_operand" "")
1833                   (sqrt:ANYF (match_operand:ANYF 2 "register_operand" "f"))))]
1834   "<recip_condition> && flag_unsafe_math_optimizations"
1836   if (TARGET_FIX_SB1)
1837     return "rsqrt.<fmt>\t%0,%2\;mov.<fmt>\t%0,%0";
1838   else
1839     return "rsqrt.<fmt>\t%0,%2";
1841   [(set_attr "type" "frsqrt")
1842    (set_attr "mode" "<UNITMODE>")
1843    (set (attr "length")
1844         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
1845                       (const_int 8)
1846                       (const_int 4)))])
1848 (define_insn "*rsqrt<mode>b"
1849   [(set (match_operand:ANYF 0 "register_operand" "=f")
1850         (sqrt:ANYF (div:ANYF (match_operand:ANYF 1 "const_1_operand" "")
1851                              (match_operand:ANYF 2 "register_operand" "f"))))]
1852   "<recip_condition> && flag_unsafe_math_optimizations"
1854   if (TARGET_FIX_SB1)
1855     return "rsqrt.<fmt>\t%0,%2\;mov.<fmt>\t%0,%0";
1856   else
1857     return "rsqrt.<fmt>\t%0,%2";
1859   [(set_attr "type" "frsqrt")
1860    (set_attr "mode" "<UNITMODE>")
1861    (set (attr "length")
1862         (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
1863                       (const_int 8)
1864                       (const_int 4)))])
1867 ;;  ....................
1869 ;;      ABSOLUTE VALUE
1871 ;;  ....................
1873 ;; Do not use the integer abs macro instruction, since that signals an
1874 ;; exception on -2147483648 (sigh).
1876 (define_insn "abs<mode>2"
1877   [(set (match_operand:GPR 0 "register_operand" "=d")
1878         (abs:GPR (match_operand:GPR 1 "register_operand" "d")))]
1879   "!TARGET_MIPS16"
1881   if (REGNO (operands[0]) == REGNO (operands[1]) && GENERATE_BRANCHLIKELY)
1882     return "%(bltzl\t%1,1f\;<d>subu\t%0,%.,%0\n%~1:%)";
1883   else
1884     return "%(bgez\t%1,1f\;move\t%0,%1\;<d>subu\t%0,%.,%0\n%~1:%)";
1886   [(set_attr "type" "multi")
1887    (set_attr "mode" "<MODE>")
1888    (set_attr "length" "12")])
1890 (define_insn "abs<mode>2"
1891   [(set (match_operand:ANYF 0 "register_operand" "=f")
1892         (abs:ANYF (match_operand:ANYF 1 "register_operand" "f")))]
1893   ""
1894   "abs.<fmt>\t%0,%1"
1895   [(set_attr "type" "fabs")
1896    (set_attr "mode" "<UNITMODE>")])
1899 ;;  ....................
1901 ;;      FIND FIRST BIT INSTRUCTION
1903 ;;  ....................
1906 (define_insn "ffs<mode>2"
1907   [(set (match_operand:GPR 0 "register_operand" "=&d")
1908         (ffs:GPR (match_operand:GPR 1 "register_operand" "d")))
1909    (clobber (match_scratch:GPR 2 "=&d"))
1910    (clobber (match_scratch:GPR 3 "=&d"))]
1911   "!TARGET_MIPS16"
1913   if (optimize && find_reg_note (insn, REG_DEAD, operands[1]))
1914     return "%(\
1915 move\t%0,%.\;\
1916 beq\t%1,%.,2f\n\
1917 %~1:\tand\t%2,%1,0x0001\;\
1918 <d>addu\t%0,%0,1\;\
1919 beq\t%2,%.,1b\;\
1920 <d>srl\t%1,%1,1\n\
1921 %~2:%)";
1923   return "%(\
1924 move\t%0,%.\;\
1925 move\t%3,%1\;\
1926 beq\t%3,%.,2f\n\
1927 %~1:\tand\t%2,%3,0x0001\;\
1928 <d>addu\t%0,%0,1\;\
1929 beq\t%2,%.,1b\;\
1930 <d>srl\t%3,%3,1\n\
1931 %~2:%)";
1933   [(set_attr "type" "multi")
1934    (set_attr "mode" "<MODE>")
1935    (set_attr "length" "28")])
1938 ;;  ...................
1940 ;;  Count leading zeroes.
1942 ;;  ...................
1945 (define_insn "clz<mode>2"
1946   [(set (match_operand:GPR 0 "register_operand" "=d")
1947         (clz:GPR (match_operand:GPR 1 "register_operand" "d")))]
1948   "ISA_HAS_CLZ_CLO"
1949   "<d>clz\t%0,%1"
1950   [(set_attr "type" "clz")
1951    (set_attr "mode" "<MODE>")])
1954 ;;  ....................
1956 ;;      NEGATION and ONE'S COMPLEMENT
1958 ;;  ....................
1960 (define_insn "negsi2"
1961   [(set (match_operand:SI 0 "register_operand" "=d")
1962         (neg:SI (match_operand:SI 1 "register_operand" "d")))]
1963   ""
1965   if (TARGET_MIPS16)
1966     return "neg\t%0,%1";
1967   else
1968     return "subu\t%0,%.,%1";
1970   [(set_attr "type"     "arith")
1971    (set_attr "mode"     "SI")])
1973 (define_insn "negdi2"
1974   [(set (match_operand:DI 0 "register_operand" "=d")
1975         (neg:DI (match_operand:DI 1 "register_operand" "d")))]
1976   "TARGET_64BIT && !TARGET_MIPS16"
1977   "dsubu\t%0,%.,%1"
1978   [(set_attr "type"     "arith")
1979    (set_attr "mode"     "DI")])
1981 (define_insn "neg<mode>2"
1982   [(set (match_operand:ANYF 0 "register_operand" "=f")
1983         (neg:ANYF (match_operand:ANYF 1 "register_operand" "f")))]
1984   ""
1985   "neg.<fmt>\t%0,%1"
1986   [(set_attr "type" "fneg")
1987    (set_attr "mode" "<UNITMODE>")])
1989 (define_insn "one_cmpl<mode>2"
1990   [(set (match_operand:GPR 0 "register_operand" "=d")
1991         (not:GPR (match_operand:GPR 1 "register_operand" "d")))]
1992   ""
1994   if (TARGET_MIPS16)
1995     return "not\t%0,%1";
1996   else
1997     return "nor\t%0,%.,%1";
1999   [(set_attr "type" "arith")
2000    (set_attr "mode" "<MODE>")])
2003 ;;  ....................
2005 ;;      LOGICAL
2007 ;;  ....................
2010 ;; Many of these instructions use trivial define_expands, because we
2011 ;; want to use a different set of constraints when TARGET_MIPS16.
2013 (define_expand "and<mode>3"
2014   [(set (match_operand:GPR 0 "register_operand")
2015         (and:GPR (match_operand:GPR 1 "register_operand")
2016                  (match_operand:GPR 2 "uns_arith_operand")))]
2017   ""
2019   if (TARGET_MIPS16)
2020     operands[2] = force_reg (<MODE>mode, operands[2]);
2023 (define_insn "*and<mode>3"
2024   [(set (match_operand:GPR 0 "register_operand" "=d,d")
2025         (and:GPR (match_operand:GPR 1 "register_operand" "%d,d")
2026                  (match_operand:GPR 2 "uns_arith_operand" "d,K")))]
2027   "!TARGET_MIPS16"
2028   "@
2029    and\t%0,%1,%2
2030    andi\t%0,%1,%x2"
2031   [(set_attr "type" "arith")
2032    (set_attr "mode" "<MODE>")])
2034 (define_insn "*and<mode>3_mips16"
2035   [(set (match_operand:GPR 0 "register_operand" "=d")
2036         (and:GPR (match_operand:GPR 1 "register_operand" "%0")
2037                  (match_operand:GPR 2 "register_operand" "d")))]
2038   "TARGET_MIPS16"
2039   "and\t%0,%2"
2040   [(set_attr "type" "arith")
2041    (set_attr "mode" "<MODE>")])
2043 (define_expand "ior<mode>3"
2044   [(set (match_operand:GPR 0 "register_operand")
2045         (ior:GPR (match_operand:GPR 1 "register_operand")
2046                  (match_operand:GPR 2 "uns_arith_operand")))]
2047   ""
2049   if (TARGET_MIPS16)
2050     operands[2] = force_reg (<MODE>mode, operands[2]);
2053 (define_insn "*ior<mode>3"
2054   [(set (match_operand:GPR 0 "register_operand" "=d,d")
2055         (ior:GPR (match_operand:GPR 1 "register_operand" "%d,d")
2056                  (match_operand:GPR 2 "uns_arith_operand" "d,K")))]
2057   "!TARGET_MIPS16"
2058   "@
2059    or\t%0,%1,%2
2060    ori\t%0,%1,%x2"
2061   [(set_attr "type" "arith")
2062    (set_attr "mode" "<MODE>")])
2064 (define_insn "*ior<mode>3_mips16"
2065   [(set (match_operand:GPR 0 "register_operand" "=d")
2066         (ior:GPR (match_operand:GPR 1 "register_operand" "%0")
2067                  (match_operand:GPR 2 "register_operand" "d")))]
2068   "TARGET_MIPS16"
2069   "or\t%0,%2"
2070   [(set_attr "type" "arith")
2071    (set_attr "mode" "<MODE>")])
2073 (define_expand "xor<mode>3"
2074   [(set (match_operand:GPR 0 "register_operand")
2075         (xor:GPR (match_operand:GPR 1 "register_operand")
2076                  (match_operand:GPR 2 "uns_arith_operand")))]
2077   ""
2078   "")
2080 (define_insn ""
2081   [(set (match_operand:GPR 0 "register_operand" "=d,d")
2082         (xor:GPR (match_operand:GPR 1 "register_operand" "%d,d")
2083                  (match_operand:GPR 2 "uns_arith_operand" "d,K")))]
2084   "!TARGET_MIPS16"
2085   "@
2086    xor\t%0,%1,%2
2087    xori\t%0,%1,%x2"
2088   [(set_attr "type" "arith")
2089    (set_attr "mode" "<MODE>")])
2091 (define_insn ""
2092   [(set (match_operand:GPR 0 "register_operand" "=d,t,t")
2093         (xor:GPR (match_operand:GPR 1 "register_operand" "%0,d,d")
2094                  (match_operand:GPR 2 "uns_arith_operand" "d,K,d")))]
2095   "TARGET_MIPS16"
2096   "@
2097    xor\t%0,%2
2098    cmpi\t%1,%2
2099    cmp\t%1,%2"
2100   [(set_attr "type" "arith")
2101    (set_attr "mode" "<MODE>")
2102    (set_attr_alternative "length"
2103                 [(const_int 4)
2104                  (if_then_else (match_operand:VOID 2 "m16_uimm8_1")
2105                                (const_int 4)
2106                                (const_int 8))
2107                  (const_int 4)])])
2109 (define_insn "*nor<mode>3"
2110   [(set (match_operand:GPR 0 "register_operand" "=d")
2111         (and:GPR (not:GPR (match_operand:GPR 1 "register_operand" "d"))
2112                  (not:GPR (match_operand:GPR 2 "register_operand" "d"))))]
2113   "!TARGET_MIPS16"
2114   "nor\t%0,%1,%2"
2115   [(set_attr "type" "arith")
2116    (set_attr "mode" "<MODE>")])
2119 ;;  ....................
2121 ;;      TRUNCATION
2123 ;;  ....................
2127 (define_insn "truncdfsf2"
2128   [(set (match_operand:SF 0 "register_operand" "=f")
2129         (float_truncate:SF (match_operand:DF 1 "register_operand" "f")))]
2130   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
2131   "cvt.s.d\t%0,%1"
2132   [(set_attr "type"     "fcvt")
2133    (set_attr "mode"     "SF")])
2135 ;; Integer truncation patterns.  Truncating SImode values to smaller
2136 ;; modes is a no-op, as it is for most other GCC ports.  Truncating
2137 ;; DImode values to SImode is not a no-op for TARGET_64BIT since we
2138 ;; need to make sure that the lower 32 bits are properly sign-extended
2139 ;; (see TRULY_NOOP_TRUNCATION).  Truncating DImode values into modes
2140 ;; smaller than SImode is equivalent to two separate truncations:
2142 ;;                        A       B
2143 ;;    DI ---> HI  ==  DI ---> SI ---> HI
2144 ;;    DI ---> QI  ==  DI ---> SI ---> QI
2146 ;; Step A needs a real instruction but step B does not.
2148 (define_insn "truncdisi2"
2149   [(set (match_operand:SI 0 "nonimmediate_operand" "=d,m")
2150         (truncate:SI (match_operand:DI 1 "register_operand" "d,d")))]
2151   "TARGET_64BIT"
2152   "@
2153     sll\t%0,%1,0
2154     sw\t%1,%0"
2155   [(set_attr "type" "shift,store")
2156    (set_attr "mode" "SI")
2157    (set_attr "extended_mips16" "yes,*")])
2159 (define_insn "truncdihi2"
2160   [(set (match_operand:HI 0 "nonimmediate_operand" "=d,m")
2161         (truncate:HI (match_operand:DI 1 "register_operand" "d,d")))]
2162   "TARGET_64BIT"
2163   "@
2164     sll\t%0,%1,0
2165     sh\t%1,%0"
2166   [(set_attr "type" "shift,store")
2167    (set_attr "mode" "SI")
2168    (set_attr "extended_mips16" "yes,*")])
2170 (define_insn "truncdiqi2"
2171   [(set (match_operand:QI 0 "nonimmediate_operand" "=d,m")
2172         (truncate:QI (match_operand:DI 1 "register_operand" "d,d")))]
2173   "TARGET_64BIT"
2174   "@
2175     sll\t%0,%1,0
2176     sb\t%1,%0"
2177   [(set_attr "type" "shift,store")
2178    (set_attr "mode" "SI")
2179    (set_attr "extended_mips16" "yes,*")])
2181 ;; Combiner patterns to optimize shift/truncate combinations.
2183 (define_insn ""
2184   [(set (match_operand:SI 0 "register_operand" "=d")
2185         (truncate:SI
2186           (ashiftrt:DI (match_operand:DI 1 "register_operand" "d")
2187                        (match_operand:DI 2 "const_arith_operand" ""))))]
2188   "TARGET_64BIT && !TARGET_MIPS16 && INTVAL (operands[2]) >= 32"
2189   "dsra\t%0,%1,%2"
2190   [(set_attr "type" "shift")
2191    (set_attr "mode" "SI")])
2193 (define_insn ""
2194   [(set (match_operand:SI 0 "register_operand" "=d")
2195         (truncate:SI (lshiftrt:DI (match_operand:DI 1 "register_operand" "d")
2196                                   (const_int 32))))]
2197   "TARGET_64BIT && !TARGET_MIPS16"
2198   "dsra\t%0,%1,32"
2199   [(set_attr "type" "shift")
2200    (set_attr "mode" "SI")])
2203 ;; Combiner patterns for truncate/sign_extend combinations.  They use
2204 ;; the shift/truncate patterns above.
2206 (define_insn_and_split ""
2207   [(set (match_operand:SI 0 "register_operand" "=d")
2208         (sign_extend:SI
2209             (truncate:HI (match_operand:DI 1 "register_operand" "d"))))]
2210   "TARGET_64BIT && !TARGET_MIPS16"
2211   "#"
2212   "&& reload_completed"
2213   [(set (match_dup 2)
2214         (ashift:DI (match_dup 1)
2215                    (const_int 48)))
2216    (set (match_dup 0)
2217         (truncate:SI (ashiftrt:DI (match_dup 2)
2218                                   (const_int 48))))]
2219   { operands[2] = gen_lowpart (DImode, operands[0]); })
2221 (define_insn_and_split ""
2222   [(set (match_operand:SI 0 "register_operand" "=d")
2223         (sign_extend:SI
2224             (truncate:QI (match_operand:DI 1 "register_operand" "d"))))]
2225   "TARGET_64BIT && !TARGET_MIPS16"
2226   "#"
2227   "&& reload_completed"
2228   [(set (match_dup 2)
2229         (ashift:DI (match_dup 1)
2230                    (const_int 56)))
2231    (set (match_dup 0)
2232         (truncate:SI (ashiftrt:DI (match_dup 2)
2233                                   (const_int 56))))]
2234   { operands[2] = gen_lowpart (DImode, operands[0]); })
2237 ;; Combiner patterns to optimize truncate/zero_extend combinations.
2239 (define_insn ""
2240   [(set (match_operand:SI 0 "register_operand" "=d")
2241         (zero_extend:SI (truncate:HI
2242                          (match_operand:DI 1 "register_operand" "d"))))]
2243   "TARGET_64BIT && !TARGET_MIPS16"
2244   "andi\t%0,%1,0xffff"
2245   [(set_attr "type"     "arith")
2246    (set_attr "mode"     "SI")])
2248 (define_insn ""
2249   [(set (match_operand:SI 0 "register_operand" "=d")
2250         (zero_extend:SI (truncate:QI
2251                          (match_operand:DI 1 "register_operand" "d"))))]
2252   "TARGET_64BIT && !TARGET_MIPS16"
2253   "andi\t%0,%1,0xff"
2254   [(set_attr "type"     "arith")
2255    (set_attr "mode"     "SI")])
2257 (define_insn ""
2258   [(set (match_operand:HI 0 "register_operand" "=d")
2259         (zero_extend:HI (truncate:QI
2260                          (match_operand:DI 1 "register_operand" "d"))))]
2261   "TARGET_64BIT && !TARGET_MIPS16"
2262   "andi\t%0,%1,0xff"
2263   [(set_attr "type"     "arith")
2264    (set_attr "mode"     "HI")])
2267 ;;  ....................
2269 ;;      ZERO EXTENSION
2271 ;;  ....................
2273 ;; Extension insns.
2275 (define_insn_and_split "zero_extendsidi2"
2276   [(set (match_operand:DI 0 "register_operand" "=d,d")
2277         (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,W")))]
2278   "TARGET_64BIT"
2279   "@
2280    #
2281    lwu\t%0,%1"
2282   "&& reload_completed && REG_P (operands[1])"
2283   [(set (match_dup 0)
2284         (ashift:DI (match_dup 1) (const_int 32)))
2285    (set (match_dup 0)
2286         (lshiftrt:DI (match_dup 0) (const_int 32)))]
2287   { operands[1] = gen_lowpart (DImode, operands[1]); }
2288   [(set_attr "type" "multi,load")
2289    (set_attr "mode" "DI")
2290    (set_attr "length" "8,*")])
2292 (define_expand "zero_extend<SHORT:mode><GPR:mode>2"
2293   [(set (match_operand:GPR 0 "register_operand")
2294         (zero_extend:GPR (match_operand:SHORT 1 "nonimmediate_operand")))]
2295   ""
2297   if (TARGET_MIPS16 && !memory_operand (operands[1], <SHORT:MODE>mode))
2298     {
2299       emit_insn (gen_and<GPR:mode>3 (operands[0],
2300                                      gen_lowpart (<GPR:MODE>mode, operands[1]),
2301                                      force_reg (<GPR:MODE>mode,
2302                                                 GEN_INT (<SHORT:mask>))));
2303       DONE;
2304     }
2307 (define_insn "*zero_extend<SHORT:mode><GPR:mode>2"
2308   [(set (match_operand:GPR 0 "register_operand" "=d,d")
2309         (zero_extend:GPR
2310              (match_operand:SHORT 1 "nonimmediate_operand" "d,m")))]
2311   "!TARGET_MIPS16"
2312   "@
2313    andi\t%0,%1,<SHORT:mask>
2314    l<SHORT:size>u\t%0,%1"
2315   [(set_attr "type" "arith,load")
2316    (set_attr "mode" "<GPR:MODE>")])
2318 (define_insn "*zero_extend<SHORT:mode><GPR:mode>2_mips16"
2319   [(set (match_operand:GPR 0 "register_operand" "=d")
2320         (zero_extend:GPR (match_operand:SHORT 1 "memory_operand" "m")))]
2321   "TARGET_MIPS16"
2322   "l<SHORT:size>u\t%0,%1"
2323   [(set_attr "type" "load")
2324    (set_attr "mode" "<GPR:MODE>")])
2326 (define_expand "zero_extendqihi2"
2327   [(set (match_operand:HI 0 "register_operand")
2328         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand")))]
2329   ""
2331   if (TARGET_MIPS16 && !memory_operand (operands[1], QImode))
2332     {
2333       emit_insn (gen_zero_extendqisi2 (gen_lowpart (SImode, operands[0]),
2334                                        operands[1]));
2335       DONE;
2336     }
2339 (define_insn "*zero_extendqihi2"
2340   [(set (match_operand:HI 0 "register_operand" "=d,d")
2341         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "d,m")))]
2342   "!TARGET_MIPS16"
2343   "@
2344    andi\t%0,%1,0x00ff
2345    lbu\t%0,%1"
2346   [(set_attr "type" "arith,load")
2347    (set_attr "mode" "HI")])
2349 (define_insn "*zero_extendqihi2_mips16"
2350   [(set (match_operand:HI 0 "register_operand" "=d")
2351         (zero_extend:HI (match_operand:QI 1 "memory_operand" "m")))]
2352   "TARGET_MIPS16"
2353   "lbu\t%0,%1"
2354   [(set_attr "type" "load")
2355    (set_attr "mode" "HI")])
2358 ;;  ....................
2360 ;;      SIGN EXTENSION
2362 ;;  ....................
2364 ;; Extension insns.
2365 ;; Those for integer source operand are ordered widest source type first.
2367 ;; When TARGET_64BIT, all SImode integer registers should already be in
2368 ;; sign-extended form (see TRULY_NOOP_TRUNCATION and truncdisi2).  We can
2369 ;; therefore get rid of register->register instructions if we constrain
2370 ;; the source to be in the same register as the destination.
2372 ;; The register alternative has type "arith" so that the pre-reload
2373 ;; scheduler will treat it as a move.  This reflects what happens if
2374 ;; the register alternative needs a reload.
2375 (define_insn_and_split "extendsidi2"
2376   [(set (match_operand:DI 0 "register_operand" "=d,d")
2377         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "0,m")))]
2378   "TARGET_64BIT"
2379   "@
2380    #
2381    lw\t%0,%1"
2382   "&& reload_completed && register_operand (operands[1], VOIDmode)"
2383   [(const_int 0)]
2385   emit_note (NOTE_INSN_DELETED);
2386   DONE;
2388   [(set_attr "type" "arith,load")
2389    (set_attr "mode" "DI")])
2391 (define_expand "extend<SHORT:mode><GPR:mode>2"
2392   [(set (match_operand:GPR 0 "register_operand")
2393         (sign_extend:GPR (match_operand:SHORT 1 "nonimmediate_operand")))]
2394   "")
2396 (define_insn_and_split "*extend<SHORT:mode><GPR:mode>2"
2397   [(set (match_operand:GPR 0 "register_operand" "=d,d")
2398         (sign_extend:GPR
2399              (match_operand:SHORT 1 "nonimmediate_operand" "d,m")))]
2400   "!ISA_HAS_SEB_SEH"
2401   "@
2402    #
2403    l<SHORT:size>\t%0,%1"
2404   "&& reload_completed && REG_P (operands[1])"
2405   [(set (match_dup 0) (ashift:GPR (match_dup 1) (match_dup 2)))
2406    (set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))]
2408   operands[1] = gen_lowpart (<GPR:MODE>mode, operands[1]);
2409   operands[2] = GEN_INT (GET_MODE_BITSIZE (<GPR:MODE>mode)
2410                          - GET_MODE_BITSIZE (<SHORT:MODE>mode));
2412   [(set_attr "type" "arith,load")
2413    (set_attr "mode" "<GPR:MODE>")
2414    (set_attr "length" "8,*")])
2416 (define_insn "*extend<SHORT:mode><GPR:mode>2_se<SHORT:size>"
2417   [(set (match_operand:GPR 0 "register_operand" "=d,d")
2418         (sign_extend:GPR
2419              (match_operand:SHORT 1 "nonimmediate_operand" "d,m")))]
2420   "ISA_HAS_SEB_SEH"
2421   "@
2422    se<SHORT:size>\t%0,%1
2423    l<SHORT:size>\t%0,%1"
2424   [(set_attr "type" "arith,load")
2425    (set_attr "mode" "<GPR:MODE>")])
2427 ;; This pattern generates the same code as extendqisi2; split it into
2428 ;; that form after reload.
2429 (define_insn_and_split "extendqihi2"
2430   [(set (match_operand:HI 0 "register_operand" "=d,d")
2431         (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "d,m")))]
2432   ""
2433   "#"
2434   "reload_completed"
2435   [(set (match_dup 0) (sign_extend:SI (match_dup 1)))]
2436   { operands[0] = gen_lowpart (SImode, operands[0]); }
2437   [(set_attr "type" "arith,load")
2438    (set_attr "mode" "SI")
2439    (set_attr "length" "8,*")])
2441 (define_insn "extendsfdf2"
2442   [(set (match_operand:DF 0 "register_operand" "=f")
2443         (float_extend:DF (match_operand:SF 1 "register_operand" "f")))]
2444   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
2445   "cvt.d.s\t%0,%1"
2446   [(set_attr "type"     "fcvt")
2447    (set_attr "mode"     "DF")])
2450 ;;  ....................
2452 ;;      CONVERSIONS
2454 ;;  ....................
2456 (define_expand "fix_truncdfsi2"
2457   [(set (match_operand:SI 0 "register_operand")
2458         (fix:SI (match_operand:DF 1 "register_operand")))]
2459   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
2461   if (!ISA_HAS_TRUNC_W)
2462     {
2463       emit_insn (gen_fix_truncdfsi2_macro (operands[0], operands[1]));
2464       DONE;
2465     }
2468 (define_insn "fix_truncdfsi2_insn"
2469   [(set (match_operand:SI 0 "register_operand" "=f")
2470         (fix:SI (match_operand:DF 1 "register_operand" "f")))]
2471   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && ISA_HAS_TRUNC_W"
2472   "trunc.w.d %0,%1"
2473   [(set_attr "type"     "fcvt")
2474    (set_attr "mode"     "DF")
2475    (set_attr "length"   "4")])
2477 (define_insn "fix_truncdfsi2_macro"
2478   [(set (match_operand:SI 0 "register_operand" "=f")
2479         (fix:SI (match_operand:DF 1 "register_operand" "f")))
2480    (clobber (match_scratch:DF 2 "=d"))]
2481   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !ISA_HAS_TRUNC_W"
2483   if (set_nomacro)
2484     return ".set\tmacro\;trunc.w.d %0,%1,%2\;.set\tnomacro";
2485   else
2486     return "trunc.w.d %0,%1,%2";
2488   [(set_attr "type"     "fcvt")
2489    (set_attr "mode"     "DF")
2490    (set_attr "length"   "36")])
2492 (define_expand "fix_truncsfsi2"
2493   [(set (match_operand:SI 0 "register_operand")
2494         (fix:SI (match_operand:SF 1 "register_operand")))]
2495   "TARGET_HARD_FLOAT"
2497   if (!ISA_HAS_TRUNC_W)
2498     {
2499       emit_insn (gen_fix_truncsfsi2_macro (operands[0], operands[1]));
2500       DONE;
2501     }
2504 (define_insn "fix_truncsfsi2_insn"
2505   [(set (match_operand:SI 0 "register_operand" "=f")
2506         (fix:SI (match_operand:SF 1 "register_operand" "f")))]
2507   "TARGET_HARD_FLOAT && ISA_HAS_TRUNC_W"
2508   "trunc.w.s %0,%1"
2509   [(set_attr "type"     "fcvt")
2510    (set_attr "mode"     "DF")
2511    (set_attr "length"   "4")])
2513 (define_insn "fix_truncsfsi2_macro"
2514   [(set (match_operand:SI 0 "register_operand" "=f")
2515         (fix:SI (match_operand:SF 1 "register_operand" "f")))
2516    (clobber (match_scratch:SF 2 "=d"))]
2517   "TARGET_HARD_FLOAT && !ISA_HAS_TRUNC_W"
2519   if (set_nomacro)
2520     return ".set\tmacro\;trunc.w.s %0,%1,%2\;.set\tnomacro";
2521   else
2522     return "trunc.w.s %0,%1,%2";
2524   [(set_attr "type"     "fcvt")
2525    (set_attr "mode"     "DF")
2526    (set_attr "length"   "36")])
2529 (define_insn "fix_truncdfdi2"
2530   [(set (match_operand:DI 0 "register_operand" "=f")
2531         (fix:DI (match_operand:DF 1 "register_operand" "f")))]
2532   "TARGET_HARD_FLOAT && TARGET_FLOAT64 && TARGET_DOUBLE_FLOAT"
2533   "trunc.l.d %0,%1"
2534   [(set_attr "type"     "fcvt")
2535    (set_attr "mode"     "DF")
2536    (set_attr "length"   "4")])
2539 (define_insn "fix_truncsfdi2"
2540   [(set (match_operand:DI 0 "register_operand" "=f")
2541         (fix:DI (match_operand:SF 1 "register_operand" "f")))]
2542   "TARGET_HARD_FLOAT && TARGET_FLOAT64 && TARGET_DOUBLE_FLOAT"
2543   "trunc.l.s %0,%1"
2544   [(set_attr "type"     "fcvt")
2545    (set_attr "mode"     "SF")
2546    (set_attr "length"   "4")])
2549 (define_insn "floatsidf2"
2550   [(set (match_operand:DF 0 "register_operand" "=f")
2551         (float:DF (match_operand:SI 1 "register_operand" "f")))]
2552   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
2553   "cvt.d.w\t%0,%1"
2554   [(set_attr "type"     "fcvt")
2555    (set_attr "mode"     "DF")
2556    (set_attr "length"   "4")])
2559 (define_insn "floatdidf2"
2560   [(set (match_operand:DF 0 "register_operand" "=f")
2561         (float:DF (match_operand:DI 1 "register_operand" "f")))]
2562   "TARGET_HARD_FLOAT && TARGET_FLOAT64 && TARGET_DOUBLE_FLOAT"
2563   "cvt.d.l\t%0,%1"
2564   [(set_attr "type"     "fcvt")
2565    (set_attr "mode"     "DF")
2566    (set_attr "length"   "4")])
2569 (define_insn "floatsisf2"
2570   [(set (match_operand:SF 0 "register_operand" "=f")
2571         (float:SF (match_operand:SI 1 "register_operand" "f")))]
2572   "TARGET_HARD_FLOAT"
2573   "cvt.s.w\t%0,%1"
2574   [(set_attr "type"     "fcvt")
2575    (set_attr "mode"     "SF")
2576    (set_attr "length"   "4")])
2579 (define_insn "floatdisf2"
2580   [(set (match_operand:SF 0 "register_operand" "=f")
2581         (float:SF (match_operand:DI 1 "register_operand" "f")))]
2582   "TARGET_HARD_FLOAT && TARGET_FLOAT64 && TARGET_DOUBLE_FLOAT"
2583   "cvt.s.l\t%0,%1"
2584   [(set_attr "type"     "fcvt")
2585    (set_attr "mode"     "SF")
2586    (set_attr "length"   "4")])
2589 (define_expand "fixuns_truncdfsi2"
2590   [(set (match_operand:SI 0 "register_operand")
2591         (unsigned_fix:SI (match_operand:DF 1 "register_operand")))]
2592   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
2594   rtx reg1 = gen_reg_rtx (DFmode);
2595   rtx reg2 = gen_reg_rtx (DFmode);
2596   rtx reg3 = gen_reg_rtx (SImode);
2597   rtx label1 = gen_label_rtx ();
2598   rtx label2 = gen_label_rtx ();
2599   REAL_VALUE_TYPE offset;
2601   real_2expN (&offset, 31);
2603   if (reg1)                     /* Turn off complaints about unreached code.  */
2604     {
2605       emit_move_insn (reg1, CONST_DOUBLE_FROM_REAL_VALUE (offset, DFmode));
2606       do_pending_stack_adjust ();
2608       emit_insn (gen_cmpdf (operands[1], reg1));
2609       emit_jump_insn (gen_bge (label1));
2611       emit_insn (gen_fix_truncdfsi2 (operands[0], operands[1]));
2612       emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx,
2613                                    gen_rtx_LABEL_REF (VOIDmode, label2)));
2614       emit_barrier ();
2616       emit_label (label1);
2617       emit_move_insn (reg2, gen_rtx_MINUS (DFmode, operands[1], reg1));
2618       emit_move_insn (reg3, GEN_INT (trunc_int_for_mode
2619                                      (BITMASK_HIGH, SImode)));
2621       emit_insn (gen_fix_truncdfsi2 (operands[0], reg2));
2622       emit_insn (gen_iorsi3 (operands[0], operands[0], reg3));
2624       emit_label (label2);
2626       /* Allow REG_NOTES to be set on last insn (labels don't have enough
2627          fields, and can't be used for REG_NOTES anyway).  */
2628       emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
2629       DONE;
2630     }
2634 (define_expand "fixuns_truncdfdi2"
2635   [(set (match_operand:DI 0 "register_operand")
2636         (unsigned_fix:DI (match_operand:DF 1 "register_operand")))]
2637   "TARGET_HARD_FLOAT && TARGET_64BIT && TARGET_DOUBLE_FLOAT"
2639   rtx reg1 = gen_reg_rtx (DFmode);
2640   rtx reg2 = gen_reg_rtx (DFmode);
2641   rtx reg3 = gen_reg_rtx (DImode);
2642   rtx label1 = gen_label_rtx ();
2643   rtx label2 = gen_label_rtx ();
2644   REAL_VALUE_TYPE offset;
2646   real_2expN (&offset, 63);
2648   emit_move_insn (reg1, CONST_DOUBLE_FROM_REAL_VALUE (offset, DFmode));
2649   do_pending_stack_adjust ();
2651   emit_insn (gen_cmpdf (operands[1], reg1));
2652   emit_jump_insn (gen_bge (label1));
2654   emit_insn (gen_fix_truncdfdi2 (operands[0], operands[1]));
2655   emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx,
2656                                gen_rtx_LABEL_REF (VOIDmode, label2)));
2657   emit_barrier ();
2659   emit_label (label1);
2660   emit_move_insn (reg2, gen_rtx_MINUS (DFmode, operands[1], reg1));
2661   emit_move_insn (reg3, GEN_INT (BITMASK_HIGH));
2662   emit_insn (gen_ashldi3 (reg3, reg3, GEN_INT (32)));
2664   emit_insn (gen_fix_truncdfdi2 (operands[0], reg2));
2665   emit_insn (gen_iordi3 (operands[0], operands[0], reg3));
2667   emit_label (label2);
2669   /* Allow REG_NOTES to be set on last insn (labels don't have enough
2670      fields, and can't be used for REG_NOTES anyway).  */
2671   emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
2672   DONE;
2676 (define_expand "fixuns_truncsfsi2"
2677   [(set (match_operand:SI 0 "register_operand")
2678         (unsigned_fix:SI (match_operand:SF 1 "register_operand")))]
2679   "TARGET_HARD_FLOAT"
2681   rtx reg1 = gen_reg_rtx (SFmode);
2682   rtx reg2 = gen_reg_rtx (SFmode);
2683   rtx reg3 = gen_reg_rtx (SImode);
2684   rtx label1 = gen_label_rtx ();
2685   rtx label2 = gen_label_rtx ();
2686   REAL_VALUE_TYPE offset;
2688   real_2expN (&offset, 31);
2690   emit_move_insn (reg1, CONST_DOUBLE_FROM_REAL_VALUE (offset, SFmode));
2691   do_pending_stack_adjust ();
2693   emit_insn (gen_cmpsf (operands[1], reg1));
2694   emit_jump_insn (gen_bge (label1));
2696   emit_insn (gen_fix_truncsfsi2 (operands[0], operands[1]));
2697   emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx,
2698                                gen_rtx_LABEL_REF (VOIDmode, label2)));
2699   emit_barrier ();
2701   emit_label (label1);
2702   emit_move_insn (reg2, gen_rtx_MINUS (SFmode, operands[1], reg1));
2703   emit_move_insn (reg3, GEN_INT (trunc_int_for_mode
2704                                  (BITMASK_HIGH, SImode)));
2706   emit_insn (gen_fix_truncsfsi2 (operands[0], reg2));
2707   emit_insn (gen_iorsi3 (operands[0], operands[0], reg3));
2709   emit_label (label2);
2711   /* Allow REG_NOTES to be set on last insn (labels don't have enough
2712      fields, and can't be used for REG_NOTES anyway).  */
2713   emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
2714   DONE;
2718 (define_expand "fixuns_truncsfdi2"
2719   [(set (match_operand:DI 0 "register_operand")
2720         (unsigned_fix:DI (match_operand:SF 1 "register_operand")))]
2721   "TARGET_HARD_FLOAT && TARGET_64BIT && TARGET_DOUBLE_FLOAT"
2723   rtx reg1 = gen_reg_rtx (SFmode);
2724   rtx reg2 = gen_reg_rtx (SFmode);
2725   rtx reg3 = gen_reg_rtx (DImode);
2726   rtx label1 = gen_label_rtx ();
2727   rtx label2 = gen_label_rtx ();
2728   REAL_VALUE_TYPE offset;
2730   real_2expN (&offset, 63);
2732   emit_move_insn (reg1, CONST_DOUBLE_FROM_REAL_VALUE (offset, SFmode));
2733   do_pending_stack_adjust ();
2735   emit_insn (gen_cmpsf (operands[1], reg1));
2736   emit_jump_insn (gen_bge (label1));
2738   emit_insn (gen_fix_truncsfdi2 (operands[0], operands[1]));
2739   emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx,
2740                                gen_rtx_LABEL_REF (VOIDmode, label2)));
2741   emit_barrier ();
2743   emit_label (label1);
2744   emit_move_insn (reg2, gen_rtx_MINUS (SFmode, operands[1], reg1));
2745   emit_move_insn (reg3, GEN_INT (BITMASK_HIGH));
2746   emit_insn (gen_ashldi3 (reg3, reg3, GEN_INT (32)));
2748   emit_insn (gen_fix_truncsfdi2 (operands[0], reg2));
2749   emit_insn (gen_iordi3 (operands[0], operands[0], reg3));
2751   emit_label (label2);
2753   /* Allow REG_NOTES to be set on last insn (labels don't have enough
2754      fields, and can't be used for REG_NOTES anyway).  */
2755   emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
2756   DONE;
2760 ;;  ....................
2762 ;;      DATA MOVEMENT
2764 ;;  ....................
2766 ;; Bit field extract patterns which use lwl/lwr or ldl/ldr.
2768 (define_expand "extv"
2769   [(set (match_operand 0 "register_operand")
2770         (sign_extract (match_operand:QI 1 "memory_operand")
2771                       (match_operand 2 "immediate_operand")
2772                       (match_operand 3 "immediate_operand")))]
2773   "!TARGET_MIPS16"
2775   if (mips_expand_unaligned_load (operands[0], operands[1],
2776                                   INTVAL (operands[2]),
2777                                   INTVAL (operands[3])))
2778     DONE;
2779   else
2780     FAIL;
2783 (define_expand "extzv"
2784   [(set (match_operand 0 "register_operand")
2785         (zero_extract (match_operand:QI 1 "memory_operand")
2786                       (match_operand 2 "immediate_operand")
2787                       (match_operand 3 "immediate_operand")))]
2788   "!TARGET_MIPS16"
2790   if (mips_expand_unaligned_load (operands[0], operands[1],
2791                                   INTVAL (operands[2]),
2792                                   INTVAL (operands[3])))
2793     DONE;
2794   else
2795     FAIL;
2798 (define_expand "insv"
2799   [(set (zero_extract (match_operand:QI 0 "memory_operand")
2800                       (match_operand 1 "immediate_operand")
2801                       (match_operand 2 "immediate_operand"))
2802         (match_operand 3 "reg_or_0_operand"))]
2803   "!TARGET_MIPS16"
2805   if (mips_expand_unaligned_store (operands[0], operands[3],
2806                                    INTVAL (operands[1]),
2807                                    INTVAL (operands[2])))
2808     DONE;
2809   else
2810     FAIL;
2813 ;; Unaligned word moves generated by the bit field patterns.
2815 ;; As far as the rtl is concerned, both the left-part and right-part
2816 ;; instructions can access the whole field.  However, the real operand
2817 ;; refers to just the first or the last byte (depending on endianness).
2818 ;; We therefore use two memory operands to each instruction, one to
2819 ;; describe the rtl effect and one to use in the assembly output.
2821 ;; Operands 0 and 1 are the rtl-level target and source respectively.
2822 ;; This allows us to use the standard length calculations for the "load"
2823 ;; and "store" type attributes.
2825 (define_insn "mov_<load>l"
2826   [(set (match_operand:GPR 0 "register_operand" "=d")
2827         (unspec:GPR [(match_operand:BLK 1 "memory_operand" "m")
2828                      (match_operand:QI 2 "memory_operand" "m")]
2829                     UNSPEC_LOAD_LEFT))]
2830   "!TARGET_MIPS16"
2831   "<load>l\t%0,%2"
2832   [(set_attr "type" "load")
2833    (set_attr "mode" "<MODE>")])
2835 (define_insn "mov_<load>r"
2836   [(set (match_operand:GPR 0 "register_operand" "=d")
2837         (unspec:GPR [(match_operand:BLK 1 "memory_operand" "m")
2838                      (match_operand:QI 2 "memory_operand" "m")
2839                      (match_operand:GPR 3 "register_operand" "0")]
2840                     UNSPEC_LOAD_RIGHT))]
2841   "!TARGET_MIPS16"
2842   "<load>r\t%0,%2"
2843   [(set_attr "type" "load")
2844    (set_attr "mode" "<MODE>")])
2846 (define_insn "mov_<store>l"
2847   [(set (match_operand:BLK 0 "memory_operand" "=m")
2848         (unspec:BLK [(match_operand:GPR 1 "reg_or_0_operand" "dJ")
2849                      (match_operand:QI 2 "memory_operand" "m")]
2850                     UNSPEC_STORE_LEFT))]
2851   "!TARGET_MIPS16"
2852   "<store>l\t%z1,%2"
2853   [(set_attr "type" "store")
2854    (set_attr "mode" "<MODE>")])
2856 (define_insn "mov_<store>r"
2857   [(set (match_operand:BLK 0 "memory_operand" "+m")
2858         (unspec:BLK [(match_operand:GPR 1 "reg_or_0_operand" "dJ")
2859                      (match_operand:QI 2 "memory_operand" "m")
2860                      (match_dup 0)]
2861                     UNSPEC_STORE_RIGHT))]
2862   "!TARGET_MIPS16"
2863   "<store>r\t%z1,%2"
2864   [(set_attr "type" "store")
2865    (set_attr "mode" "<MODE>")])
2867 ;; An instruction to calculate the high part of a 64-bit SYMBOL_GENERAL.
2868 ;; The required value is:
2870 ;;      (%highest(op1) << 48) + (%higher(op1) << 32) + (%hi(op1) << 16)
2872 ;; which translates to:
2874 ;;      lui     op0,%highest(op1)
2875 ;;      daddiu  op0,op0,%higher(op1)
2876 ;;      dsll    op0,op0,16
2877 ;;      daddiu  op0,op0,%hi(op1)
2878 ;;      dsll    op0,op0,16
2880 ;; The split is deferred until after flow2 to allow the peephole2 below
2881 ;; to take effect.
2882 (define_insn_and_split "*lea_high64"
2883   [(set (match_operand:DI 0 "register_operand" "=d")
2884         (high:DI (match_operand:DI 1 "general_symbolic_operand" "")))]
2885   "TARGET_EXPLICIT_RELOCS && ABI_HAS_64BIT_SYMBOLS"
2886   "#"
2887   "&& flow2_completed"
2888   [(set (match_dup 0) (high:DI (match_dup 2)))
2889    (set (match_dup 0) (lo_sum:DI (match_dup 0) (match_dup 2)))
2890    (set (match_dup 0) (ashift:DI (match_dup 0) (const_int 16)))
2891    (set (match_dup 0) (lo_sum:DI (match_dup 0) (match_dup 3)))
2892    (set (match_dup 0) (ashift:DI (match_dup 0) (const_int 16)))]
2894   operands[2] = mips_unspec_address (operands[1], SYMBOL_64_HIGH);
2895   operands[3] = mips_unspec_address (operands[1], SYMBOL_64_MID);
2897   [(set_attr "length" "20")])
2899 ;; Use a scratch register to reduce the latency of the above pattern
2900 ;; on superscalar machines.  The optimized sequence is:
2902 ;;      lui     op1,%highest(op2)
2903 ;;      lui     op0,%hi(op2)
2904 ;;      daddiu  op1,op1,%higher(op2)
2905 ;;      dsll32  op1,op1,0
2906 ;;      daddu   op1,op1,op0
2907 (define_peephole2
2908   [(set (match_operand:DI 1 "register_operand")
2909         (high:DI (match_operand:DI 2 "general_symbolic_operand")))
2910    (match_scratch:DI 0 "d")]
2911   "TARGET_EXPLICIT_RELOCS && ABI_HAS_64BIT_SYMBOLS"
2912   [(set (match_dup 1) (high:DI (match_dup 3)))
2913    (set (match_dup 0) (high:DI (match_dup 4)))
2914    (set (match_dup 1) (lo_sum:DI (match_dup 1) (match_dup 3)))
2915    (set (match_dup 1) (ashift:DI (match_dup 1) (const_int 32)))
2916    (set (match_dup 1) (plus:DI (match_dup 1) (match_dup 0)))]
2918   operands[3] = mips_unspec_address (operands[2], SYMBOL_64_HIGH);
2919   operands[4] = mips_unspec_address (operands[2], SYMBOL_64_LOW);
2922 ;; On most targets, the expansion of (lo_sum (high X) X) for a 64-bit
2923 ;; SYMBOL_GENERAL X will take 6 cycles.  This next pattern allows combine
2924 ;; to merge the HIGH and LO_SUM parts of a move if the HIGH part is only
2925 ;; used once.  We can then use the sequence:
2927 ;;      lui     op0,%highest(op1)
2928 ;;      lui     op2,%hi(op1)
2929 ;;      daddiu  op0,op0,%higher(op1)
2930 ;;      daddiu  op2,op2,%lo(op1)
2931 ;;      dsll32  op0,op0,0
2932 ;;      daddu   op0,op0,op2
2934 ;; which takes 4 cycles on most superscalar targets.
2935 (define_insn_and_split "*lea64"
2936   [(set (match_operand:DI 0 "register_operand" "=d")
2937         (match_operand:DI 1 "general_symbolic_operand" ""))
2938    (clobber (match_scratch:DI 2 "=&d"))]
2939   "TARGET_EXPLICIT_RELOCS && ABI_HAS_64BIT_SYMBOLS && cse_not_expected"
2940   "#"
2941   "&& reload_completed"
2942   [(set (match_dup 0) (high:DI (match_dup 3)))
2943    (set (match_dup 2) (high:DI (match_dup 4)))
2944    (set (match_dup 0) (lo_sum:DI (match_dup 0) (match_dup 3)))
2945    (set (match_dup 2) (lo_sum:DI (match_dup 2) (match_dup 4)))
2946    (set (match_dup 0) (ashift:DI (match_dup 0) (const_int 32)))
2947    (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))]
2949   operands[3] = mips_unspec_address (operands[1], SYMBOL_64_HIGH);
2950   operands[4] = mips_unspec_address (operands[1], SYMBOL_64_LOW);
2952   [(set_attr "length" "24")])
2954 ;; Insns to fetch a global symbol from a big GOT.
2956 (define_insn_and_split "*xgot_hi<mode>"
2957   [(set (match_operand:P 0 "register_operand" "=d")
2958         (high:P (match_operand:P 1 "global_got_operand" "")))]
2959   "TARGET_EXPLICIT_RELOCS && TARGET_XGOT"
2960   "#"
2961   "&& reload_completed"
2962   [(set (match_dup 0) (high:P (match_dup 2)))
2963    (set (match_dup 0) (plus:P (match_dup 0) (match_dup 3)))]
2965   operands[2] = mips_unspec_address (operands[1], SYMBOL_GOTOFF_GLOBAL);
2966   operands[3] = pic_offset_table_rtx;
2968   [(set_attr "got" "xgot_high")
2969    (set_attr "mode" "<MODE>")])
2971 (define_insn_and_split "*xgot_lo<mode>"
2972   [(set (match_operand:P 0 "register_operand" "=d")
2973         (lo_sum:P (match_operand:P 1 "register_operand" "d")
2974                   (match_operand:P 2 "global_got_operand" "")))]
2975   "TARGET_EXPLICIT_RELOCS && TARGET_XGOT"
2976   "#"
2977   "&& reload_completed"
2978   [(set (match_dup 0)
2979         (unspec:P [(match_dup 1) (match_dup 3)] UNSPEC_LOAD_GOT))]
2980   { operands[3] = mips_unspec_address (operands[2], SYMBOL_GOTOFF_GLOBAL); }
2981   [(set_attr "got" "load")
2982    (set_attr "mode" "<MODE>")])
2984 ;; Insns to fetch a global symbol from a normal GOT.
2986 (define_insn_and_split "*got_disp<mode>"
2987   [(set (match_operand:P 0 "register_operand" "=d")
2988         (match_operand:P 1 "global_got_operand" ""))]
2989   "TARGET_EXPLICIT_RELOCS && !TARGET_XGOT"
2990   "#"
2991   "&& reload_completed"
2992   [(set (match_dup 0)
2993         (unspec:P [(match_dup 2) (match_dup 3)] UNSPEC_LOAD_GOT))]
2995   operands[2] = pic_offset_table_rtx;
2996   operands[3] = mips_unspec_address (operands[1], SYMBOL_GOTOFF_GLOBAL);
2998   [(set_attr "got" "load")
2999    (set_attr "mode" "<MODE>")])
3001 ;; Insns for loading the high part of a local symbol.
3003 (define_insn_and_split "*got_page<mode>"
3004   [(set (match_operand:P 0 "register_operand" "=d")
3005         (high:P (match_operand:P 1 "local_got_operand" "")))]
3006   "TARGET_EXPLICIT_RELOCS"
3007   "#"
3008   "&& reload_completed"
3009   [(set (match_dup 0)
3010         (unspec:P [(match_dup 2) (match_dup 3)] UNSPEC_LOAD_GOT))]
3012   operands[2] = pic_offset_table_rtx;
3013   operands[3] = mips_unspec_address (operands[1], SYMBOL_GOTOFF_PAGE);
3015   [(set_attr "got" "load")
3016    (set_attr "mode" "<MODE>")])
3018 ;; Lower-level instructions for loading an address from the GOT.
3019 ;; We could use MEMs, but an unspec gives more optimization
3020 ;; opportunities.
3022 (define_insn "load_got<mode>"
3023   [(set (match_operand:P 0 "register_operand" "=d")
3024         (unspec:P [(match_operand:P 1 "register_operand" "d")
3025                    (match_operand:P 2 "immediate_operand" "")]
3026                   UNSPEC_LOAD_GOT))]
3027   ""
3028   "<load>\t%0,%R2(%1)"
3029   [(set_attr "type" "load")
3030    (set_attr "mode" "<MODE>")
3031    (set_attr "length" "4")])
3033 ;; Instructions for adding the low 16 bits of an address to a register.
3034 ;; Operand 2 is the address: print_operand works out which relocation
3035 ;; should be applied.
3037 (define_insn "*low<mode>"
3038   [(set (match_operand:P 0 "register_operand" "=d")
3039         (lo_sum:P (match_operand:P 1 "register_operand" "d")
3040                   (match_operand:P 2 "immediate_operand" "")))]
3041   "!TARGET_MIPS16"
3042   "<d>addiu\t%0,%1,%R2"
3043   [(set_attr "type" "arith")
3044    (set_attr "mode" "<MODE>")])
3046 (define_insn "*low<mode>_mips16"
3047   [(set (match_operand:P 0 "register_operand" "=d")
3048         (lo_sum:P (match_operand:P 1 "register_operand" "0")
3049                   (match_operand:P 2 "immediate_operand" "")))]
3050   "TARGET_MIPS16"
3051   "<d>addiu\t%0,%R2"
3052   [(set_attr "type" "arith")
3053    (set_attr "mode" "<MODE>")
3054    (set_attr "length" "8")])
3056 ;; 64-bit integer moves
3058 ;; Unlike most other insns, the move insns can't be split with
3059 ;; different predicates, because register spilling and other parts of
3060 ;; the compiler, have memoized the insn number already.
3062 (define_expand "movdi"
3063   [(set (match_operand:DI 0 "")
3064         (match_operand:DI 1 ""))]
3065   ""
3067   if (mips_legitimize_move (DImode, operands[0], operands[1]))
3068     DONE;
3071 ;; For mips16, we need a special case to handle storing $31 into
3072 ;; memory, since we don't have a constraint to match $31.  This
3073 ;; instruction can be generated by save_restore_insns.
3075 (define_insn "*mov<mode>_ra"
3076   [(set (match_operand:GPR 0 "stack_operand" "=m")
3077         (reg:GPR 31))]
3078   "TARGET_MIPS16"
3079   "<store>\t$31,%0"
3080   [(set_attr "type" "store")
3081    (set_attr "mode" "<MODE>")])
3083 (define_insn "*movdi_32bit"
3084   [(set (match_operand:DI 0 "nonimmediate_operand" "=d,d,d,m,*x,*d,*B*C*D,*B*C*D,*d,*m")
3085         (match_operand:DI 1 "move_operand" "d,i,m,d,*J*d,*x,*d,*m,*B*C*D,*B*C*D"))]
3086   "!TARGET_64BIT && !TARGET_MIPS16
3087    && (register_operand (operands[0], DImode)
3088        || reg_or_0_operand (operands[1], DImode))"
3089   { return mips_output_move (operands[0], operands[1]); }
3090   [(set_attr "type"     "arith,arith,load,store,mthilo,mfhilo,xfer,load,xfer,store")
3091    (set_attr "mode"     "DI")
3092    (set_attr "length"   "8,16,*,*,8,8,8,*,8,*")])
3094 (define_insn "*movdi_32bit_mips16"
3095   [(set (match_operand:DI 0 "nonimmediate_operand" "=d,y,d,d,d,d,m,*d")
3096         (match_operand:DI 1 "move_operand" "d,d,y,K,N,m,d,*x"))]
3097   "!TARGET_64BIT && TARGET_MIPS16
3098    && (register_operand (operands[0], DImode)
3099        || register_operand (operands[1], DImode))"
3100   { return mips_output_move (operands[0], operands[1]); }
3101   [(set_attr "type"     "arith,arith,arith,arith,arith,load,store,mfhilo")
3102    (set_attr "mode"     "DI")
3103    (set_attr "length"   "8,8,8,8,12,*,*,8")])
3105 (define_insn "*movdi_64bit"
3106   [(set (match_operand:DI 0 "nonimmediate_operand" "=d,d,e,d,m,*f,*f,*f,*d,*m,*x,*B*C*D,*B*C*D,*d,*m")
3107         (match_operand:DI 1 "move_operand" "d,U,T,m,dJ,*f,*d*J,*m,*f,*f,*J*d,*d,*m,*B*C*D,*B*C*D"))]
3108   "TARGET_64BIT && !TARGET_MIPS16
3109    && (register_operand (operands[0], DImode)
3110        || reg_or_0_operand (operands[1], DImode))"
3111   { return mips_output_move (operands[0], operands[1]); }
3112   [(set_attr "type"     "arith,const,const,load,store,fmove,xfer,fpload,xfer,fpstore,mthilo,xfer,load,xfer,store")
3113    (set_attr "mode"     "DI")
3114    (set_attr "length"   "4,*,*,*,*,4,4,*,4,*,4,8,*,8,*")])
3116 (define_insn "*movdi_64bit_mips16"
3117   [(set (match_operand:DI 0 "nonimmediate_operand" "=d,y,d,d,d,d,d,m")
3118         (match_operand:DI 1 "move_operand" "d,d,y,K,N,U,m,d"))]
3119   "TARGET_64BIT && TARGET_MIPS16
3120    && (register_operand (operands[0], DImode)
3121        || register_operand (operands[1], DImode))"
3122   { return mips_output_move (operands[0], operands[1]); }
3123   [(set_attr "type"     "arith,arith,arith,arith,arith,const,load,store")
3124    (set_attr "mode"     "DI")
3125    (set_attr_alternative "length"
3126                 [(const_int 4)
3127                  (const_int 4)
3128                  (const_int 4)
3129                  (if_then_else (match_operand:VOID 1 "m16_uimm8_1")
3130                                (const_int 4)
3131                                (const_int 8))
3132                  (if_then_else (match_operand:VOID 1 "m16_nuimm8_1")
3133                                (const_int 8)
3134                                (const_int 12))
3135                  (const_string "*")
3136                  (const_string "*")
3137                  (const_string "*")])])
3140 ;; On the mips16, we can split ld $r,N($r) into an add and a load,
3141 ;; when the original load is a 4 byte instruction but the add and the
3142 ;; load are 2 2 byte instructions.
3144 (define_split
3145   [(set (match_operand:DI 0 "register_operand")
3146         (mem:DI (plus:DI (match_dup 0)
3147                          (match_operand:DI 1 "const_int_operand"))))]
3148   "TARGET_64BIT && TARGET_MIPS16 && reload_completed
3149    && !TARGET_DEBUG_D_MODE
3150    && REG_P (operands[0])
3151    && M16_REG_P (REGNO (operands[0]))
3152    && GET_CODE (operands[1]) == CONST_INT
3153    && ((INTVAL (operands[1]) < 0
3154         && INTVAL (operands[1]) >= -0x10)
3155        || (INTVAL (operands[1]) >= 32 * 8
3156            && INTVAL (operands[1]) <= 31 * 8 + 0x8)
3157        || (INTVAL (operands[1]) >= 0
3158            && INTVAL (operands[1]) < 32 * 8
3159            && (INTVAL (operands[1]) & 7) != 0))"
3160   [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1)))
3161    (set (match_dup 0) (mem:DI (plus:DI (match_dup 0) (match_dup 2))))]
3163   HOST_WIDE_INT val = INTVAL (operands[1]);
3165   if (val < 0)
3166     operands[2] = const0_rtx;
3167   else if (val >= 32 * 8)
3168     {
3169       int off = val & 7;
3171       operands[1] = GEN_INT (0x8 + off);
3172       operands[2] = GEN_INT (val - off - 0x8);
3173     }
3174   else
3175     {
3176       int off = val & 7;
3178       operands[1] = GEN_INT (off);
3179       operands[2] = GEN_INT (val - off);
3180     }
3183 ;; 32-bit Integer moves
3185 ;; Unlike most other insns, the move insns can't be split with
3186 ;; different predicates, because register spilling and other parts of
3187 ;; the compiler, have memoized the insn number already.
3189 (define_expand "movsi"
3190   [(set (match_operand:SI 0 "")
3191         (match_operand:SI 1 ""))]
3192   ""
3194   if (mips_legitimize_move (SImode, operands[0], operands[1]))
3195     DONE;
3198 ;; The difference between these two is whether or not ints are allowed
3199 ;; in FP registers (off by default, use -mdebugh to enable).
3201 (define_insn "*movsi_internal"
3202   [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,e,d,m,*f,*f,*f,*d,*m,*d,*z,*x,*B*C*D,*B*C*D,*d,*m")
3203         (match_operand:SI 1 "move_operand" "d,U,T,m,dJ,*f,*d*J,*m,*f,*f,*z,*d,*J*d,*d,*m,*B*C*D,*B*C*D"))]
3204   "!TARGET_MIPS16
3205    && (register_operand (operands[0], SImode)
3206        || reg_or_0_operand (operands[1], SImode))"
3207   { return mips_output_move (operands[0], operands[1]); }
3208   [(set_attr "type"     "arith,const,const,load,store,fmove,xfer,fpload,xfer,fpstore,xfer,xfer,mthilo,xfer,load,xfer,store")
3209    (set_attr "mode"     "SI")
3210    (set_attr "length"   "4,*,*,*,*,4,4,*,4,*,4,4,4,4,*,4,*")])
3212 (define_insn "*movsi_mips16"
3213   [(set (match_operand:SI 0 "nonimmediate_operand" "=d,y,d,d,d,d,d,m")
3214         (match_operand:SI 1 "move_operand" "d,d,y,K,N,U,m,d"))]
3215   "TARGET_MIPS16
3216    && (register_operand (operands[0], SImode)
3217        || register_operand (operands[1], SImode))"
3218   { return mips_output_move (operands[0], operands[1]); }
3219   [(set_attr "type"     "arith,arith,arith,arith,arith,const,load,store")
3220    (set_attr "mode"     "SI")
3221    (set_attr_alternative "length"
3222                 [(const_int 4)
3223                  (const_int 4)
3224                  (const_int 4)
3225                  (if_then_else (match_operand:VOID 1 "m16_uimm8_1")
3226                                (const_int 4)
3227                                (const_int 8))
3228                  (if_then_else (match_operand:VOID 1 "m16_nuimm8_1")
3229                                (const_int 8)
3230                                (const_int 12))
3231                  (const_string "*")
3232                  (const_string "*")
3233                  (const_string "*")])])
3235 ;; On the mips16, we can split lw $r,N($r) into an add and a load,
3236 ;; when the original load is a 4 byte instruction but the add and the
3237 ;; load are 2 2 byte instructions.
3239 (define_split
3240   [(set (match_operand:SI 0 "register_operand")
3241         (mem:SI (plus:SI (match_dup 0)
3242                          (match_operand:SI 1 "const_int_operand"))))]
3243   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
3244    && REG_P (operands[0])
3245    && M16_REG_P (REGNO (operands[0]))
3246    && GET_CODE (operands[1]) == CONST_INT
3247    && ((INTVAL (operands[1]) < 0
3248         && INTVAL (operands[1]) >= -0x80)
3249        || (INTVAL (operands[1]) >= 32 * 4
3250            && INTVAL (operands[1]) <= 31 * 4 + 0x7c)
3251        || (INTVAL (operands[1]) >= 0
3252            && INTVAL (operands[1]) < 32 * 4
3253            && (INTVAL (operands[1]) & 3) != 0))"
3254   [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
3255    (set (match_dup 0) (mem:SI (plus:SI (match_dup 0) (match_dup 2))))]
3257   HOST_WIDE_INT val = INTVAL (operands[1]);
3259   if (val < 0)
3260     operands[2] = const0_rtx;
3261   else if (val >= 32 * 4)
3262     {
3263       int off = val & 3;
3265       operands[1] = GEN_INT (0x7c + off);
3266       operands[2] = GEN_INT (val - off - 0x7c);
3267     }
3268   else
3269     {
3270       int off = val & 3;
3272       operands[1] = GEN_INT (off);
3273       operands[2] = GEN_INT (val - off);
3274     }
3277 ;; On the mips16, we can split a load of certain constants into a load
3278 ;; and an add.  This turns a 4 byte instruction into 2 2 byte
3279 ;; instructions.
3281 (define_split
3282   [(set (match_operand:SI 0 "register_operand")
3283         (match_operand:SI 1 "const_int_operand"))]
3284   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
3285    && REG_P (operands[0])
3286    && M16_REG_P (REGNO (operands[0]))
3287    && GET_CODE (operands[1]) == CONST_INT
3288    && INTVAL (operands[1]) >= 0x100
3289    && INTVAL (operands[1]) <= 0xff + 0x7f"
3290   [(set (match_dup 0) (match_dup 1))
3291    (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))]
3293   int val = INTVAL (operands[1]);
3295   operands[1] = GEN_INT (0xff);
3296   operands[2] = GEN_INT (val - 0xff);
3299 ;; This insn handles moving CCmode values.  It's really just a
3300 ;; slightly simplified copy of movsi_internal2, with additional cases
3301 ;; to move a condition register to a general register and to move
3302 ;; between the general registers and the floating point registers.
3304 (define_insn "movcc"
3305   [(set (match_operand:CC 0 "nonimmediate_operand" "=d,*d,*d,*m,*d,*f,*f,*f,*m")
3306         (match_operand:CC 1 "general_operand" "z,*d,*m,*d,*f,*d,*f,*m,*f"))]
3307   "ISA_HAS_8CC && TARGET_HARD_FLOAT"
3308   { return mips_output_move (operands[0], operands[1]); }
3309   [(set_attr "type"     "xfer,arith,load,store,xfer,xfer,fmove,fpload,fpstore")
3310    (set_attr "mode"     "SI")
3311    (set_attr "length"   "8,4,*,*,4,4,4,*,*")])
3313 ;; Reload condition code registers.  reload_incc and reload_outcc
3314 ;; both handle moves from arbitrary operands into condition code
3315 ;; registers.  reload_incc handles the more common case in which
3316 ;; a source operand is constrained to be in a condition-code
3317 ;; register, but has not been allocated to one.
3319 ;; Sometimes, such as in movcc, we have a CCmode destination whose
3320 ;; constraints do not include 'z'.  reload_outcc handles the case
3321 ;; when such an operand is allocated to a condition-code register.
3323 ;; Note that reloads from a condition code register to some
3324 ;; other location can be done using ordinary moves.  Moving
3325 ;; into a GPR takes a single movcc, moving elsewhere takes
3326 ;; two.  We can leave these cases to the generic reload code.
3327 (define_expand "reload_incc"
3328   [(set (match_operand:CC 0 "fcc_reload_operand" "=z")
3329         (match_operand:CC 1 "general_operand" ""))
3330    (clobber (match_operand:TF 2 "register_operand" "=&f"))]
3331   "ISA_HAS_8CC && TARGET_HARD_FLOAT"
3333   mips_emit_fcc_reload (operands[0], operands[1], operands[2]);
3334   DONE;
3337 (define_expand "reload_outcc"
3338   [(set (match_operand:CC 0 "fcc_reload_operand" "=z")
3339         (match_operand:CC 1 "register_operand" ""))
3340    (clobber (match_operand:TF 2 "register_operand" "=&f"))]
3341   "ISA_HAS_8CC && TARGET_HARD_FLOAT"
3343   mips_emit_fcc_reload (operands[0], operands[1], operands[2]);
3344   DONE;
3347 ;; MIPS4 supports loading and storing a floating point register from
3348 ;; the sum of two general registers.  We use two versions for each of
3349 ;; these four instructions: one where the two general registers are
3350 ;; SImode, and one where they are DImode.  This is because general
3351 ;; registers will be in SImode when they hold 32 bit values, but,
3352 ;; since the 32 bit values are always sign extended, the [ls][wd]xc1
3353 ;; instructions will still work correctly.
3355 ;; ??? Perhaps it would be better to support these instructions by
3356 ;; modifying GO_IF_LEGITIMATE_ADDRESS and friends.  However, since
3357 ;; these instructions can only be used to load and store floating
3358 ;; point registers, that would probably cause trouble in reload.
3360 (define_insn "*<ANYF:loadx>_<P:mode>"
3361   [(set (match_operand:ANYF 0 "register_operand" "=f")
3362         (mem:ANYF (plus:P (match_operand:P 1 "register_operand" "d")
3363                           (match_operand:P 2 "register_operand" "d"))))]
3364   "ISA_HAS_FP4"
3365   "<ANYF:loadx>\t%0,%1(%2)"
3366   [(set_attr "type" "fpidxload")
3367    (set_attr "mode" "<ANYF:UNITMODE>")])
3369 (define_insn "*<ANYF:storex>_<P:mode>"
3370   [(set (mem:ANYF (plus:P (match_operand:P 1 "register_operand" "d")
3371                           (match_operand:P 2 "register_operand" "d")))
3372         (match_operand:ANYF 0 "register_operand" "f"))]
3373   "ISA_HAS_FP4"
3374   "<ANYF:storex>\t%0,%1(%2)"
3375   [(set_attr "type" "fpidxstore")
3376    (set_attr "mode" "<ANYF:UNITMODE>")])
3378 ;; 16-bit Integer moves
3380 ;; Unlike most other insns, the move insns can't be split with
3381 ;; different predicates, because register spilling and other parts of
3382 ;; the compiler, have memoized the insn number already.
3383 ;; Unsigned loads are used because LOAD_EXTEND_OP returns ZERO_EXTEND.
3385 (define_expand "movhi"
3386   [(set (match_operand:HI 0 "")
3387         (match_operand:HI 1 ""))]
3388   ""
3390   if (mips_legitimize_move (HImode, operands[0], operands[1]))
3391     DONE;
3394 (define_insn "*movhi_internal"
3395   [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d,m,*d,*f,*f,*x")
3396         (match_operand:HI 1 "move_operand"         "d,I,m,dJ,*f,*d,*f,*d"))]
3397   "!TARGET_MIPS16
3398    && (register_operand (operands[0], HImode)
3399        || reg_or_0_operand (operands[1], HImode))"
3400   "@
3401     move\t%0,%1
3402     li\t%0,%1
3403     lhu\t%0,%1
3404     sh\t%z1,%0
3405     mfc1\t%0,%1
3406     mtc1\t%1,%0
3407     mov.s\t%0,%1
3408     mt%0\t%1"
3409   [(set_attr "type"     "arith,arith,load,store,xfer,xfer,fmove,mthilo")
3410    (set_attr "mode"     "HI")
3411    (set_attr "length"   "4,4,*,*,4,4,4,4")])
3413 (define_insn "*movhi_mips16"
3414   [(set (match_operand:HI 0 "nonimmediate_operand" "=d,y,d,d,d,d,m")
3415         (match_operand:HI 1 "move_operand"         "d,d,y,K,N,m,d"))]
3416   "TARGET_MIPS16
3417    && (register_operand (operands[0], HImode)
3418        || register_operand (operands[1], HImode))"
3419   "@
3420     move\t%0,%1
3421     move\t%0,%1
3422     move\t%0,%1
3423     li\t%0,%1
3424     #
3425     lhu\t%0,%1
3426     sh\t%1,%0"
3427   [(set_attr "type"     "arith,arith,arith,arith,arith,load,store")
3428    (set_attr "mode"     "HI")
3429    (set_attr_alternative "length"
3430                 [(const_int 4)
3431                  (const_int 4)
3432                  (const_int 4)
3433                  (if_then_else (match_operand:VOID 1 "m16_uimm8_1")
3434                                (const_int 4)
3435                                (const_int 8))
3436                  (if_then_else (match_operand:VOID 1 "m16_nuimm8_1")
3437                                (const_int 8)
3438                                (const_int 12))
3439                  (const_string "*")
3440                  (const_string "*")])])
3443 ;; On the mips16, we can split lh $r,N($r) into an add and a load,
3444 ;; when the original load is a 4 byte instruction but the add and the
3445 ;; load are 2 2 byte instructions.
3447 (define_split
3448   [(set (match_operand:HI 0 "register_operand")
3449         (mem:HI (plus:SI (match_dup 0)
3450                          (match_operand:SI 1 "const_int_operand"))))]
3451   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
3452    && REG_P (operands[0])
3453    && M16_REG_P (REGNO (operands[0]))
3454    && GET_CODE (operands[1]) == CONST_INT
3455    && ((INTVAL (operands[1]) < 0
3456         && INTVAL (operands[1]) >= -0x80)
3457        || (INTVAL (operands[1]) >= 32 * 2
3458            && INTVAL (operands[1]) <= 31 * 2 + 0x7e)
3459        || (INTVAL (operands[1]) >= 0
3460            && INTVAL (operands[1]) < 32 * 2
3461            && (INTVAL (operands[1]) & 1) != 0))"
3462   [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
3463    (set (match_dup 0) (mem:HI (plus:SI (match_dup 0) (match_dup 2))))]
3465   HOST_WIDE_INT val = INTVAL (operands[1]);
3467   if (val < 0)
3468     operands[2] = const0_rtx;
3469   else if (val >= 32 * 2)
3470     {
3471       int off = val & 1;
3473       operands[1] = GEN_INT (0x7e + off);
3474       operands[2] = GEN_INT (val - off - 0x7e);
3475     }
3476   else
3477     {
3478       int off = val & 1;
3480       operands[1] = GEN_INT (off);
3481       operands[2] = GEN_INT (val - off);
3482     }
3485 ;; 8-bit Integer moves
3487 ;; Unlike most other insns, the move insns can't be split with
3488 ;; different predicates, because register spilling and other parts of
3489 ;; the compiler, have memoized the insn number already.
3490 ;; Unsigned loads are used because LOAD_EXTEND_OP returns ZERO_EXTEND.
3492 (define_expand "movqi"
3493   [(set (match_operand:QI 0 "")
3494         (match_operand:QI 1 ""))]
3495   ""
3497   if (mips_legitimize_move (QImode, operands[0], operands[1]))
3498     DONE;
3501 (define_insn "*movqi_internal"
3502   [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,m,*d,*f,*f,*x")
3503         (match_operand:QI 1 "move_operand"         "d,I,m,dJ,*f,*d,*f,*d"))]
3504   "!TARGET_MIPS16
3505    && (register_operand (operands[0], QImode)
3506        || reg_or_0_operand (operands[1], QImode))"
3507   "@
3508     move\t%0,%1
3509     li\t%0,%1
3510     lbu\t%0,%1
3511     sb\t%z1,%0
3512     mfc1\t%0,%1
3513     mtc1\t%1,%0
3514     mov.s\t%0,%1
3515     mt%0\t%1"
3516   [(set_attr "type"     "arith,arith,load,store,xfer,xfer,fmove,mthilo")
3517    (set_attr "mode"     "QI")
3518    (set_attr "length"   "4,4,*,*,4,4,4,4")])
3520 (define_insn "*movqi_mips16"
3521   [(set (match_operand:QI 0 "nonimmediate_operand" "=d,y,d,d,d,d,m")
3522         (match_operand:QI 1 "move_operand"         "d,d,y,K,N,m,d"))]
3523   "TARGET_MIPS16
3524    && (register_operand (operands[0], QImode)
3525        || register_operand (operands[1], QImode))"
3526   "@
3527     move\t%0,%1
3528     move\t%0,%1
3529     move\t%0,%1
3530     li\t%0,%1
3531     #
3532     lbu\t%0,%1
3533     sb\t%1,%0"
3534   [(set_attr "type"     "arith,arith,arith,arith,arith,load,store")
3535    (set_attr "mode"     "QI")
3536    (set_attr "length"   "4,4,4,4,8,*,*")])
3538 ;; On the mips16, we can split lb $r,N($r) into an add and a load,
3539 ;; when the original load is a 4 byte instruction but the add and the
3540 ;; load are 2 2 byte instructions.
3542 (define_split
3543   [(set (match_operand:QI 0 "register_operand")
3544         (mem:QI (plus:SI (match_dup 0)
3545                          (match_operand:SI 1 "const_int_operand"))))]
3546   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
3547    && REG_P (operands[0])
3548    && M16_REG_P (REGNO (operands[0]))
3549    && GET_CODE (operands[1]) == CONST_INT
3550    && ((INTVAL (operands[1]) < 0
3551         && INTVAL (operands[1]) >= -0x80)
3552        || (INTVAL (operands[1]) >= 32
3553            && INTVAL (operands[1]) <= 31 + 0x7f))"
3554   [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
3555    (set (match_dup 0) (mem:QI (plus:SI (match_dup 0) (match_dup 2))))]
3557   HOST_WIDE_INT val = INTVAL (operands[1]);
3559   if (val < 0)
3560     operands[2] = const0_rtx;
3561   else
3562     {
3563       operands[1] = GEN_INT (0x7f);
3564       operands[2] = GEN_INT (val - 0x7f);
3565     }
3568 ;; 32-bit floating point moves
3570 (define_expand "movsf"
3571   [(set (match_operand:SF 0 "")
3572         (match_operand:SF 1 ""))]
3573   ""
3575   if (mips_legitimize_move (SFmode, operands[0], operands[1]))
3576     DONE;
3579 (define_insn "*movsf_hardfloat"
3580   [(set (match_operand:SF 0 "nonimmediate_operand" "=f,f,f,m,m,*f,*d,*d,*d,*m")
3581         (match_operand:SF 1 "move_operand" "f,G,m,f,G,*d,*f,*G*d,*m,*d"))]
3582   "TARGET_HARD_FLOAT
3583    && (register_operand (operands[0], SFmode)
3584        || reg_or_0_operand (operands[1], SFmode))"
3585   { return mips_output_move (operands[0], operands[1]); }
3586   [(set_attr "type"     "fmove,xfer,fpload,fpstore,store,xfer,xfer,arith,load,store")
3587    (set_attr "mode"     "SF")
3588    (set_attr "length"   "4,4,*,*,*,4,4,4,*,*")])
3590 (define_insn "*movsf_softfloat"
3591   [(set (match_operand:SF 0 "nonimmediate_operand" "=d,d,m")
3592         (match_operand:SF 1 "move_operand" "Gd,m,d"))]
3593   "TARGET_SOFT_FLOAT && !TARGET_MIPS16
3594    && (register_operand (operands[0], SFmode)
3595        || reg_or_0_operand (operands[1], SFmode))"
3596   { return mips_output_move (operands[0], operands[1]); }
3597   [(set_attr "type"     "arith,load,store")
3598    (set_attr "mode"     "SF")
3599    (set_attr "length"   "4,*,*")])
3601 (define_insn "*movsf_mips16"
3602   [(set (match_operand:SF 0 "nonimmediate_operand" "=d,y,d,d,m")
3603         (match_operand:SF 1 "move_operand" "d,d,y,m,d"))]
3604   "TARGET_MIPS16
3605    && (register_operand (operands[0], SFmode)
3606        || register_operand (operands[1], SFmode))"
3607   { return mips_output_move (operands[0], operands[1]); }
3608   [(set_attr "type"     "arith,arith,arith,load,store")
3609    (set_attr "mode"     "SF")
3610    (set_attr "length"   "4,4,4,*,*")])
3613 ;; 64-bit floating point moves
3615 (define_expand "movdf"
3616   [(set (match_operand:DF 0 "")
3617         (match_operand:DF 1 ""))]
3618   ""
3620   if (mips_legitimize_move (DFmode, operands[0], operands[1]))
3621     DONE;
3624 (define_insn "*movdf_hardfloat_64bit"
3625   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,f,f,m,m,*f,*d,*d,*d,*m")
3626         (match_operand:DF 1 "move_operand" "f,G,m,f,G,*d,*f,*d*G,*m,*d"))]
3627   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_64BIT
3628    && (register_operand (operands[0], DFmode)
3629        || reg_or_0_operand (operands[1], DFmode))"
3630   { return mips_output_move (operands[0], operands[1]); }
3631   [(set_attr "type"     "fmove,xfer,fpload,fpstore,store,xfer,xfer,arith,load,store")
3632    (set_attr "mode"     "DF")
3633    (set_attr "length"   "4,4,*,*,*,4,4,4,*,*")])
3635 (define_insn "*movdf_hardfloat_32bit"
3636   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,f,f,m,m,*f,*d,*d,*d,*m")
3637         (match_operand:DF 1 "move_operand" "f,G,m,f,G,*d,*f,*d*G,*m,*d"))]
3638   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_64BIT
3639    && (register_operand (operands[0], DFmode)
3640        || reg_or_0_operand (operands[1], DFmode))"
3641   { return mips_output_move (operands[0], operands[1]); }
3642   [(set_attr "type"     "fmove,xfer,fpload,fpstore,store,xfer,xfer,arith,load,store")
3643    (set_attr "mode"     "DF")
3644    (set_attr "length"   "4,8,*,*,*,8,8,8,*,*")])
3646 (define_insn "*movdf_softfloat"
3647   [(set (match_operand:DF 0 "nonimmediate_operand" "=d,d,m,d,f,f")
3648         (match_operand:DF 1 "move_operand" "dG,m,dG,f,d,f"))]
3649   "(TARGET_SOFT_FLOAT || TARGET_SINGLE_FLOAT) && !TARGET_MIPS16
3650    && (register_operand (operands[0], DFmode)
3651        || reg_or_0_operand (operands[1], DFmode))"
3652   { return mips_output_move (operands[0], operands[1]); }
3653   [(set_attr "type"     "arith,load,store,xfer,xfer,fmove")
3654    (set_attr "mode"     "DF")
3655    (set_attr "length"   "8,*,*,4,4,4")])
3657 (define_insn "*movdf_mips16"
3658   [(set (match_operand:DF 0 "nonimmediate_operand" "=d,y,d,d,m")
3659         (match_operand:DF 1 "move_operand" "d,d,y,m,d"))]
3660   "TARGET_MIPS16
3661    && (register_operand (operands[0], DFmode)
3662        || register_operand (operands[1], DFmode))"
3663   { return mips_output_move (operands[0], operands[1]); }
3664   [(set_attr "type"     "arith,arith,arith,load,store")
3665    (set_attr "mode"     "DF")
3666    (set_attr "length"   "8,8,8,*,*")])
3668 (define_split
3669   [(set (match_operand:DI 0 "nonimmediate_operand")
3670         (match_operand:DI 1 "move_operand"))]
3671   "reload_completed && !TARGET_64BIT
3672    && mips_split_64bit_move_p (operands[0], operands[1])"
3673   [(const_int 0)]
3675   mips_split_64bit_move (operands[0], operands[1]);
3676   DONE;
3679 (define_split
3680   [(set (match_operand:DF 0 "nonimmediate_operand")
3681         (match_operand:DF 1 "move_operand"))]
3682   "reload_completed && !TARGET_64BIT
3683    && mips_split_64bit_move_p (operands[0], operands[1])"
3684   [(const_int 0)]
3686   mips_split_64bit_move (operands[0], operands[1]);
3687   DONE;
3690 ;; When generating mips16 code, split moves of negative constants into
3691 ;; a positive "li" followed by a negation.
3692 (define_split
3693   [(set (match_operand 0 "register_operand")
3694         (match_operand 1 "const_int_operand"))]
3695   "TARGET_MIPS16 && reload_completed && INTVAL (operands[1]) < 0"
3696   [(set (match_dup 2)
3697         (match_dup 3))
3698    (set (match_dup 2)
3699         (neg:SI (match_dup 2)))]
3701   operands[2] = gen_lowpart (SImode, operands[0]);
3702   operands[3] = GEN_INT (-INTVAL (operands[1]));
3705 ;; 64-bit paired-single floating point moves
3707 (define_expand "movv2sf"
3708   [(set (match_operand:V2SF 0)
3709         (match_operand:V2SF 1))]
3710   "TARGET_PAIRED_SINGLE_FLOAT"
3712   if (mips_legitimize_move (V2SFmode, operands[0], operands[1]))
3713     DONE;
3716 (define_insn "movv2sf_hardfloat_64bit"
3717   [(set (match_operand:V2SF 0 "nonimmediate_operand" "=f,f,f,m,m,*f,*d,*d,*d,*m")
3718         (match_operand:V2SF 1 "move_operand" "f,YG,m,f,YG,*d,*f,*d*YG,*m,*d"))]
3719   "TARGET_PAIRED_SINGLE_FLOAT
3720    && TARGET_64BIT
3721    && (register_operand (operands[0], V2SFmode)
3722        || reg_or_0_operand (operands[1], V2SFmode))"
3723   { return mips_output_move (operands[0], operands[1]); }
3724   [(set_attr "type" "fmove,xfer,fpload,fpstore,store,xfer,xfer,arith,load,store")
3725    (set_attr "mode" "SF")
3726    (set_attr "length" "4,4,*,*,*,4,4,4,*,*")])
3728 ;; The HI and LO registers are not truly independent.  If we move an mthi
3729 ;; instruction before an mflo instruction, it will make the result of the
3730 ;; mflo unpredictable.  The same goes for mtlo and mfhi.
3732 ;; We cope with this by making the mflo and mfhi patterns use both HI and LO.
3733 ;; Operand 1 is the register we want, operand 2 is the other one.
3735 ;; When generating VR4120 or VR4130 code, we use macc{,hi} and
3736 ;; dmacc{,hi} instead of mfhi and mflo.  This avoids both the normal
3737 ;; MIPS III hi/lo hazards and the errata related to -mfix-vr4130.
3739 (define_expand "mfhilo_<mode>"
3740   [(set (match_operand:GPR 0 "register_operand")
3741         (unspec:GPR [(match_operand:GPR 1 "register_operand")
3742                      (match_operand:GPR 2 "register_operand")]
3743                     UNSPEC_MFHILO))])
3745 (define_insn "*mfhilo_<mode>"
3746   [(set (match_operand:GPR 0 "register_operand" "=d,d")
3747         (unspec:GPR [(match_operand:GPR 1 "register_operand" "h,l")
3748                      (match_operand:GPR 2 "register_operand" "l,h")]
3749                     UNSPEC_MFHILO))]
3750   "!ISA_HAS_MACCHI"
3751   "mf%1\t%0"
3752   [(set_attr "type" "mfhilo")
3753    (set_attr "mode" "<MODE>")])
3755 (define_insn "*mfhilo_<mode>_macc"
3756   [(set (match_operand:GPR 0 "register_operand" "=d,d")
3757         (unspec:GPR [(match_operand:GPR 1 "register_operand" "h,l")
3758                      (match_operand:GPR 2 "register_operand" "l,h")]
3759                     UNSPEC_MFHILO))]
3760   "ISA_HAS_MACCHI"
3762   if (REGNO (operands[1]) == HI_REGNUM)
3763     return "<d>macchi\t%0,%.,%.";
3764   else
3765     return "<d>macc\t%0,%.,%.";
3767   [(set_attr "type" "mfhilo")
3768    (set_attr "mode" "<MODE>")])
3770 ;; Patterns for loading or storing part of a paired floating point
3771 ;; register.  We need them because odd-numbered floating-point registers
3772 ;; are not fully independent: see mips_split_64bit_move.
3774 ;; Load the low word of operand 0 with operand 1.
3775 (define_insn "load_df_low"
3776   [(set (match_operand:DF 0 "register_operand" "=f,f")
3777         (unspec:DF [(match_operand:SI 1 "general_operand" "dJ,m")]
3778                    UNSPEC_LOAD_DF_LOW))]
3779   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_64BIT"
3781   operands[0] = mips_subword (operands[0], 0);
3782   return mips_output_move (operands[0], operands[1]);
3784   [(set_attr "type"     "xfer,fpload")
3785    (set_attr "mode"     "SF")])
3787 ;; Load the high word of operand 0 from operand 1, preserving the value
3788 ;; in the low word.
3789 (define_insn "load_df_high"
3790   [(set (match_operand:DF 0 "register_operand" "=f,f")
3791         (unspec:DF [(match_operand:SI 1 "general_operand" "dJ,m")
3792                     (match_operand:DF 2 "register_operand" "0,0")]
3793                    UNSPEC_LOAD_DF_HIGH))]
3794   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_64BIT"
3796   operands[0] = mips_subword (operands[0], 1);
3797   return mips_output_move (operands[0], operands[1]);
3799   [(set_attr "type"     "xfer,fpload")
3800    (set_attr "mode"     "SF")])
3802 ;; Store the high word of operand 1 in operand 0.  The corresponding
3803 ;; low-word move is done in the normal way.
3804 (define_insn "store_df_high"
3805   [(set (match_operand:SI 0 "nonimmediate_operand" "=d,m")
3806         (unspec:SI [(match_operand:DF 1 "register_operand" "f,f")]
3807                    UNSPEC_STORE_DF_HIGH))]
3808   "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_64BIT"
3810   operands[1] = mips_subword (operands[1], 1);
3811   return mips_output_move (operands[0], operands[1]);
3813   [(set_attr "type"     "xfer,fpstore")
3814    (set_attr "mode"     "SF")])
3816 ;; Insn to initialize $gp for n32/n64 abicalls.  Operand 0 is the offset
3817 ;; of _gp from the start of this function.  Operand 1 is the incoming
3818 ;; function address.
3819 (define_insn_and_split "loadgp"
3820   [(unspec_volatile [(match_operand 0 "" "")
3821                      (match_operand 1 "register_operand" "")] UNSPEC_LOADGP)]
3822   "TARGET_ABICALLS && TARGET_NEWABI"
3823   "#"
3824   ""
3825   [(set (match_dup 2) (match_dup 3))
3826    (set (match_dup 2) (match_dup 4))
3827    (set (match_dup 2) (match_dup 5))]
3829   operands[2] = pic_offset_table_rtx;
3830   operands[3] = gen_rtx_HIGH (Pmode, operands[0]);
3831   operands[4] = gen_rtx_PLUS (Pmode, operands[2], operands[1]);
3832   operands[5] = gen_rtx_LO_SUM (Pmode, operands[2], operands[0]);
3834   [(set_attr "length" "12")])
3836 ;; The use of gp is hidden when not using explicit relocations.
3837 ;; This blockage instruction prevents the gp load from being
3838 ;; scheduled after an implicit use of gp.  It also prevents
3839 ;; the load from being deleted as dead.
3840 (define_insn "loadgp_blockage"
3841   [(unspec_volatile [(reg:DI 28)] UNSPEC_BLOCKAGE)]
3842   ""
3843   ""
3844   [(set_attr "type"     "unknown")
3845    (set_attr "mode"     "none")
3846    (set_attr "length"   "0")])
3848 ;; Emit a .cprestore directive, which normally expands to a single store
3849 ;; instruction.  Note that we continue to use .cprestore for explicit reloc
3850 ;; code so that jals inside inline asms will work correctly.
3851 (define_insn "cprestore"
3852   [(unspec_volatile [(match_operand 0 "const_int_operand" "I,i")]
3853                     UNSPEC_CPRESTORE)]
3854   ""
3856   if (set_nomacro && which_alternative == 1)
3857     return ".set\tmacro\;.cprestore\t%0\;.set\tnomacro";
3858   else
3859     return ".cprestore\t%0";
3861   [(set_attr "type" "store")
3862    (set_attr "length" "4,12")])
3864 ;; Block moves, see mips.c for more details.
3865 ;; Argument 0 is the destination
3866 ;; Argument 1 is the source
3867 ;; Argument 2 is the length
3868 ;; Argument 3 is the alignment
3870 (define_expand "movmemsi"
3871   [(parallel [(set (match_operand:BLK 0 "general_operand")
3872                    (match_operand:BLK 1 "general_operand"))
3873               (use (match_operand:SI 2 ""))
3874               (use (match_operand:SI 3 "const_int_operand"))])]
3875   "!TARGET_MIPS16 && !TARGET_MEMCPY"
3877   if (mips_expand_block_move (operands[0], operands[1], operands[2]))
3878     DONE;
3879   else
3880     FAIL;
3884 ;;  ....................
3886 ;;      SHIFTS
3888 ;;  ....................
3890 (define_expand "<optab><mode>3"
3891   [(set (match_operand:GPR 0 "register_operand")
3892         (any_shift:GPR (match_operand:GPR 1 "register_operand")
3893                        (match_operand:SI 2 "arith_operand")))]
3894   ""
3896   /* On the mips16, a shift of more than 8 is a four byte instruction,
3897      so, for a shift between 8 and 16, it is just as fast to do two
3898      shifts of 8 or less.  If there is a lot of shifting going on, we
3899      may win in CSE.  Otherwise combine will put the shifts back
3900      together again.  This can be called by function_arg, so we must
3901      be careful not to allocate a new register if we've reached the
3902      reload pass.  */
3903   if (TARGET_MIPS16
3904       && optimize
3905       && GET_CODE (operands[2]) == CONST_INT
3906       && INTVAL (operands[2]) > 8
3907       && INTVAL (operands[2]) <= 16
3908       && !reload_in_progress
3909       && !reload_completed)
3910     {
3911       rtx temp = gen_reg_rtx (<MODE>mode);
3913       emit_insn (gen_<optab><mode>3 (temp, operands[1], GEN_INT (8)));
3914       emit_insn (gen_<optab><mode>3 (operands[0], temp,
3915                                      GEN_INT (INTVAL (operands[2]) - 8)));
3916       DONE;
3917     }
3920 (define_insn "*<optab><mode>3"
3921   [(set (match_operand:GPR 0 "register_operand" "=d")
3922         (any_shift:GPR (match_operand:GPR 1 "register_operand" "d")
3923                        (match_operand:SI 2 "arith_operand" "dI")))]
3924   "!TARGET_MIPS16"
3926   if (GET_CODE (operands[2]) == CONST_INT)
3927     operands[2] = GEN_INT (INTVAL (operands[2])
3928                            & (GET_MODE_BITSIZE (<MODE>mode) - 1));
3930   return "<d><insn>\t%0,%1,%2";
3932   [(set_attr "type" "shift")
3933    (set_attr "mode" "<MODE>")])
3935 (define_insn "*<optab>si3_extend"
3936   [(set (match_operand:DI 0 "register_operand" "=d")
3937         (sign_extend:DI
3938            (any_shift:SI (match_operand:SI 1 "register_operand" "d")
3939                          (match_operand:SI 2 "arith_operand" "dI"))))]
3940   "TARGET_64BIT && !TARGET_MIPS16"
3942   if (GET_CODE (operands[2]) == CONST_INT)
3943     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
3945   return "<insn>\t%0,%1,%2";
3947   [(set_attr "type" "shift")
3948    (set_attr "mode" "SI")])
3950 (define_insn "*<optab>si3_mips16"
3951   [(set (match_operand:SI 0 "register_operand" "=d,d")
3952         (any_shift:SI (match_operand:SI 1 "register_operand" "0,d")
3953                       (match_operand:SI 2 "arith_operand" "d,I")))]
3954   "TARGET_MIPS16"
3956   if (which_alternative == 0)
3957     return "<insn>\t%0,%2";
3959   operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
3960   return "<insn>\t%0,%1,%2";
3962   [(set_attr "type" "shift")
3963    (set_attr "mode" "SI")
3964    (set_attr_alternative "length"
3965                 [(const_int 4)
3966                  (if_then_else (match_operand 2 "m16_uimm3_b")
3967                                (const_int 4)
3968                                (const_int 8))])])
3970 ;; We need separate DImode MIPS16 patterns because of the irregularity
3971 ;; of right shifts.
3972 (define_insn "*ashldi3_mips16"
3973   [(set (match_operand:DI 0 "register_operand" "=d,d")
3974         (ashift:DI (match_operand:DI 1 "register_operand" "0,d")
3975                    (match_operand:SI 2 "arith_operand" "d,I")))]
3976   "TARGET_64BIT && TARGET_MIPS16"
3978   if (which_alternative == 0)
3979     return "dsll\t%0,%2";
3981   operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
3982   return "dsll\t%0,%1,%2";
3984   [(set_attr "type" "shift")
3985    (set_attr "mode" "DI")
3986    (set_attr_alternative "length"
3987                 [(const_int 4)
3988                  (if_then_else (match_operand 2 "m16_uimm3_b")
3989                                (const_int 4)
3990                                (const_int 8))])])
3992 (define_insn "*ashrdi3_mips16"
3993   [(set (match_operand:DI 0 "register_operand" "=d,d")
3994         (ashiftrt:DI (match_operand:DI 1 "register_operand" "0,0")
3995                      (match_operand:SI 2 "arith_operand" "d,I")))]
3996   "TARGET_64BIT && TARGET_MIPS16"
3998   if (GET_CODE (operands[2]) == CONST_INT)
3999     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
4001   return "dsra\t%0,%2";
4003   [(set_attr "type" "shift")
4004    (set_attr "mode" "DI")
4005    (set_attr_alternative "length"
4006                 [(const_int 4)
4007                  (if_then_else (match_operand 2 "m16_uimm3_b")
4008                                (const_int 4)
4009                                (const_int 8))])])
4011 (define_insn "*lshrdi3_mips16"
4012   [(set (match_operand:DI 0 "register_operand" "=d,d")
4013         (lshiftrt:DI (match_operand:DI 1 "register_operand" "0,0")
4014                      (match_operand:SI 2 "arith_operand" "d,I")))]
4015   "TARGET_64BIT && TARGET_MIPS16"
4017   if (GET_CODE (operands[2]) == CONST_INT)
4018     operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
4020   return "dsrl\t%0,%2";
4022   [(set_attr "type" "shift")
4023    (set_attr "mode" "DI")
4024    (set_attr_alternative "length"
4025                 [(const_int 4)
4026                  (if_then_else (match_operand 2 "m16_uimm3_b")
4027                                (const_int 4)
4028                                (const_int 8))])])
4030 ;; On the mips16, we can split a 4 byte shift into 2 2 byte shifts.
4032 (define_split
4033   [(set (match_operand:GPR 0 "register_operand")
4034         (any_shift:GPR (match_operand:GPR 1 "register_operand")
4035                        (match_operand:GPR 2 "const_int_operand")))]
4036   "TARGET_MIPS16 && reload_completed && !TARGET_DEBUG_D_MODE
4037    && GET_CODE (operands[2]) == CONST_INT
4038    && INTVAL (operands[2]) > 8
4039    && INTVAL (operands[2]) <= 16"
4040   [(set (match_dup 0) (any_shift:GPR (match_dup 1) (const_int 8)))
4041    (set (match_dup 0) (any_shift:GPR (match_dup 0) (match_dup 2)))]
4042   { operands[2] = GEN_INT (INTVAL (operands[2]) - 8); })
4044 ;; If we load a byte on the mips16 as a bitfield, the resulting
4045 ;; sequence of instructions is too complicated for combine, because it
4046 ;; involves four instructions: a load, a shift, a constant load into a
4047 ;; register, and an and (the key problem here is that the mips16 does
4048 ;; not have and immediate).  We recognize a shift of a load in order
4049 ;; to make it simple enough for combine to understand.
4051 ;; The length here is the worst case: the length of the split version
4052 ;; will be more accurate.
4053 (define_insn_and_split ""
4054   [(set (match_operand:SI 0 "register_operand" "=d")
4055         (lshiftrt:SI (match_operand:SI 1 "memory_operand" "m")
4056                      (match_operand:SI 2 "immediate_operand" "I")))]
4057   "TARGET_MIPS16"
4058   "#"
4059   ""
4060   [(set (match_dup 0) (match_dup 1))
4061    (set (match_dup 0) (lshiftrt:SI (match_dup 0) (match_dup 2)))]
4062   ""
4063   [(set_attr "type"     "load")
4064    (set_attr "mode"     "SI")
4065    (set_attr "length"   "16")])
4067 (define_insn "rotr<mode>3"
4068   [(set (match_operand:GPR 0 "register_operand" "=d")
4069         (rotatert:GPR (match_operand:GPR 1 "register_operand" "d")
4070                       (match_operand:SI 2 "arith_operand" "dI")))]
4071   "ISA_HAS_ROTR_<MODE>"
4073   if (GET_CODE (operands[2]) == CONST_INT)
4074     gcc_assert (INTVAL (operands[2]) >= 0
4075                 && INTVAL (operands[2]) < GET_MODE_BITSIZE (<MODE>mode));
4077   return "<d>ror\t%0,%1,%2";
4079   [(set_attr "type" "shift")
4080    (set_attr "mode" "<MODE>")])
4083 ;;  ....................
4085 ;;      COMPARISONS
4087 ;;  ....................
4089 ;; Flow here is rather complex:
4091 ;;  1)  The cmp{si,di,sf,df} routine is called.  It deposits the arguments
4092 ;;      into cmp_operands[] but generates no RTL.
4094 ;;  2)  The appropriate branch define_expand is called, which then
4095 ;;      creates the appropriate RTL for the comparison and branch.
4096 ;;      Different CC modes are used, based on what type of branch is
4097 ;;      done, so that we can constrain things appropriately.  There
4098 ;;      are assumptions in the rest of GCC that break if we fold the
4099 ;;      operands into the branches for integer operations, and use cc0
4100 ;;      for floating point, so we use the fp status register instead.
4101 ;;      If needed, an appropriate temporary is created to hold the
4102 ;;      of the integer compare.
4104 (define_expand "cmp<mode>"
4105   [(set (cc0)
4106         (compare:CC (match_operand:GPR 0 "register_operand")
4107                     (match_operand:GPR 1 "nonmemory_operand")))]
4108   ""
4110   cmp_operands[0] = operands[0];
4111   cmp_operands[1] = operands[1];
4112   DONE;
4115 (define_expand "cmp<mode>"
4116   [(set (cc0)
4117         (compare:CC (match_operand:SCALARF 0 "register_operand")
4118                     (match_operand:SCALARF 1 "register_operand")))]
4119   ""
4121   cmp_operands[0] = operands[0];
4122   cmp_operands[1] = operands[1];
4123   DONE;
4127 ;;  ....................
4129 ;;      CONDITIONAL BRANCHES
4131 ;;  ....................
4133 ;; Conditional branches on floating-point equality tests.
4135 (define_insn "branch_fp"
4136   [(set (pc)
4137         (if_then_else
4138          (match_operator:CC 0 "comparison_operator"
4139                             [(match_operand:CC 2 "register_operand" "z")
4140                              (const_int 0)])
4141          (label_ref (match_operand 1 "" ""))
4142          (pc)))]
4143   "TARGET_HARD_FLOAT"
4145   return mips_output_conditional_branch (insn,
4146                                          operands,
4147                                          /*two_operands_p=*/0,
4148                                          /*float_p=*/1,
4149                                          /*inverted_p=*/0,
4150                                          get_attr_length (insn));
4152   [(set_attr "type"     "branch")
4153    (set_attr "mode"     "none")])
4155 (define_insn "branch_fp_inverted"
4156   [(set (pc)
4157         (if_then_else
4158          (match_operator:CC 0 "comparison_operator"
4159                             [(match_operand:CC 2 "register_operand" "z")
4160                              (const_int 0)])
4161          (pc)
4162          (label_ref (match_operand 1 "" ""))))]
4163   "TARGET_HARD_FLOAT"
4165   return mips_output_conditional_branch (insn,
4166                                          operands,
4167                                          /*two_operands_p=*/0,
4168                                          /*float_p=*/1,
4169                                          /*inverted_p=*/1,
4170                                          get_attr_length (insn));
4172   [(set_attr "type"     "branch")
4173    (set_attr "mode"     "none")])
4175 ;; Conditional branches on comparisons with zero.
4177 (define_insn "*branch_zero<mode>"
4178   [(set (pc)
4179         (if_then_else
4180          (match_operator:GPR 0 "comparison_operator"
4181                              [(match_operand:GPR 2 "register_operand" "d")
4182                               (const_int 0)])
4183          (label_ref (match_operand 1 "" ""))
4184          (pc)))]
4185   "!TARGET_MIPS16"
4187   return mips_output_conditional_branch (insn,
4188                                          operands,
4189                                          /*two_operands_p=*/0,
4190                                          /*float_p=*/0,
4191                                          /*inverted_p=*/0,
4192                                          get_attr_length (insn));
4194   [(set_attr "type" "branch")
4195    (set_attr "mode" "none")])
4197 (define_insn "*branch_zero<mode>_inverted"
4198   [(set (pc)
4199         (if_then_else
4200          (match_operator:GPR 0 "comparison_operator"
4201                              [(match_operand:GPR 2 "register_operand" "d")
4202                               (const_int 0)])
4203          (pc)
4204          (label_ref (match_operand 1 "" ""))))]
4205   "!TARGET_MIPS16"
4207   return mips_output_conditional_branch (insn,
4208                                          operands,
4209                                          /*two_operands_p=*/0,
4210                                          /*float_p=*/0,
4211                                          /*inverted_p=*/1,
4212                                          get_attr_length (insn));
4214   [(set_attr "type" "branch")
4215    (set_attr "mode" "none")])
4217 ;; Conditional branch on equality comparison.
4219 (define_insn "*branch_equality<mode>"
4220   [(set (pc)
4221         (if_then_else
4222          (match_operator:GPR 0 "equality_operator"
4223                              [(match_operand:GPR 2 "register_operand" "d")
4224                               (match_operand:GPR 3 "register_operand" "d")])
4225          (label_ref (match_operand 1 "" ""))
4226          (pc)))]
4227   "!TARGET_MIPS16"
4229   return mips_output_conditional_branch (insn,
4230                                          operands,
4231                                          /*two_operands_p=*/1,
4232                                          /*float_p=*/0,
4233                                          /*inverted_p=*/0,
4234                                          get_attr_length (insn));
4236   [(set_attr "type" "branch")
4237    (set_attr "mode" "none")])
4239 (define_insn "*branch_equality<mode>_inverted"
4240   [(set (pc)
4241         (if_then_else
4242          (match_operator:GPR 0 "equality_operator"
4243                              [(match_operand:GPR 2 "register_operand" "d")
4244                               (match_operand:GPR 3 "register_operand" "d")])
4245          (pc)
4246          (label_ref (match_operand 1 "" ""))))]
4247   "!TARGET_MIPS16"
4249   return mips_output_conditional_branch (insn,
4250                                          operands,
4251                                          /*two_operands_p=*/1,
4252                                          /*float_p=*/0,
4253                                          /*inverted_p=*/1,
4254                                          get_attr_length (insn));
4256   [(set_attr "type" "branch")
4257    (set_attr "mode" "none")])
4259 ;; MIPS16 branches
4261 (define_insn "*branch_equality<mode>_mips16"
4262   [(set (pc)
4263         (if_then_else
4264          (match_operator:GPR 0 "equality_operator"
4265                              [(match_operand:GPR 1 "register_operand" "d,t")
4266                               (const_int 0)])
4267          (match_operand 2 "pc_or_label_operand" "")
4268          (match_operand 3 "pc_or_label_operand" "")))]
4269   "TARGET_MIPS16"
4271   if (operands[2] != pc_rtx)
4272     {
4273       if (which_alternative == 0)
4274         return "b%C0z\t%1,%2";
4275       else
4276         return "bt%C0z\t%2";
4277     }
4278   else
4279     {
4280       if (which_alternative == 0)
4281         return "b%N0z\t%1,%3";
4282       else
4283         return "bt%N0z\t%3";
4284     }
4286   [(set_attr "type" "branch")
4287    (set_attr "mode" "none")
4288    (set_attr "length" "8")])
4290 (define_expand "b<code>"
4291   [(set (pc)
4292         (if_then_else (any_cond:CC (cc0)
4293                                    (const_int 0))
4294                       (label_ref (match_operand 0 ""))
4295                       (pc)))]
4296   ""
4298   gen_conditional_branch (operands, <CODE>);
4299   DONE;
4303 ;;  ....................
4305 ;;      SETTING A REGISTER FROM A COMPARISON
4307 ;;  ....................
4309 (define_expand "seq"
4310   [(set (match_operand:SI 0 "register_operand")
4311         (eq:SI (match_dup 1)
4312                (match_dup 2)))]
4313   ""
4314   { if (mips_emit_scc (EQ, operands[0])) DONE; else FAIL; })
4316 (define_insn "*seq_<mode>"
4317   [(set (match_operand:GPR 0 "register_operand" "=d")
4318         (eq:GPR (match_operand:GPR 1 "register_operand" "d")
4319                 (const_int 0)))]
4320   "!TARGET_MIPS16"
4321   "sltu\t%0,%1,1"
4322   [(set_attr "type" "slt")
4323    (set_attr "mode" "<MODE>")])
4325 (define_insn "*seq_<mode>_mips16"
4326   [(set (match_operand:GPR 0 "register_operand" "=t")
4327         (eq:GPR (match_operand:GPR 1 "register_operand" "d")
4328                 (const_int 0)))]
4329   "TARGET_MIPS16"
4330   "sltu\t%1,1"
4331   [(set_attr "type" "slt")
4332    (set_attr "mode" "<MODE>")])
4334 ;; "sne" uses sltu instructions in which the first operand is $0.
4335 ;; This isn't possible in mips16 code.
4337 (define_expand "sne"
4338   [(set (match_operand:SI 0 "register_operand")
4339         (ne:SI (match_dup 1)
4340                (match_dup 2)))]
4341   "!TARGET_MIPS16"
4342   { if (mips_emit_scc (NE, operands[0])) DONE; else FAIL; })
4344 (define_insn "*sne_<mode>"
4345   [(set (match_operand:GPR 0 "register_operand" "=d")
4346         (ne:GPR (match_operand:GPR 1 "register_operand" "d")
4347                 (const_int 0)))]
4348   "!TARGET_MIPS16"
4349   "sltu\t%0,%.,%1"
4350   [(set_attr "type" "slt")
4351    (set_attr "mode" "<MODE>")])
4353 (define_expand "sgt"
4354   [(set (match_operand:SI 0 "register_operand")
4355         (gt:SI (match_dup 1)
4356                (match_dup 2)))]
4357   ""
4358   { if (mips_emit_scc (GT, operands[0])) DONE; else FAIL; })
4360 (define_insn "*sgt_<mode>"
4361   [(set (match_operand:GPR 0 "register_operand" "=d")
4362         (gt:GPR (match_operand:GPR 1 "register_operand" "d")
4363                 (match_operand:GPR 2 "reg_or_0_operand" "dJ")))]
4364   "!TARGET_MIPS16"
4365   "slt\t%0,%z2,%1"
4366   [(set_attr "type" "slt")
4367    (set_attr "mode" "<MODE>")])
4369 (define_insn "*sgt_<mode>_mips16"
4370   [(set (match_operand:GPR 0 "register_operand" "=t")
4371         (gt:GPR (match_operand:GPR 1 "register_operand" "d")
4372                 (match_operand:GPR 2 "register_operand" "d")))]
4373   "TARGET_MIPS16"
4374   "slt\t%2,%1"
4375   [(set_attr "type" "slt")
4376    (set_attr "mode" "<MODE>")])
4378 (define_expand "sge"
4379   [(set (match_operand:SI 0 "register_operand")
4380         (ge:SI (match_dup 1)
4381                (match_dup 2)))]
4382   ""
4383   { if (mips_emit_scc (GE, operands[0])) DONE; else FAIL; })
4385 (define_insn "*sge_<mode>"
4386   [(set (match_operand:GPR 0 "register_operand" "=d")
4387         (ge:GPR (match_operand:GPR 1 "register_operand" "d")
4388                 (const_int 1)))]
4389   "!TARGET_MIPS16"
4390   "slt\t%0,%.,%1"
4391   [(set_attr "type" "slt")
4392    (set_attr "mode" "<MODE>")])
4394 (define_expand "slt"
4395   [(set (match_operand:SI 0 "register_operand")
4396         (lt:SI (match_dup 1)
4397                (match_dup 2)))]
4398   ""
4399   { if (mips_emit_scc (LT, operands[0])) DONE; else FAIL; })
4401 (define_insn "*slt_<mode>"
4402   [(set (match_operand:GPR 0 "register_operand" "=d")
4403         (lt:GPR (match_operand:GPR 1 "register_operand" "d")
4404                 (match_operand:GPR 2 "arith_operand" "dI")))]
4405   "!TARGET_MIPS16"
4406   "slt\t%0,%1,%2"
4407   [(set_attr "type" "slt")
4408    (set_attr "mode" "<MODE>")])
4410 (define_insn "*slt_<mode>_mips16"
4411   [(set (match_operand:GPR 0 "register_operand" "=t,t")
4412         (lt:GPR (match_operand:GPR 1 "register_operand" "d,d")
4413                 (match_operand:GPR 2 "arith_operand" "d,I")))]
4414   "TARGET_MIPS16"
4415   "slt\t%1,%2"
4416   [(set_attr "type" "slt")
4417    (set_attr "mode" "<MODE>")
4418    (set_attr_alternative "length"
4419                 [(const_int 4)
4420                  (if_then_else (match_operand 2 "m16_uimm8_1")
4421                                (const_int 4)
4422                                (const_int 8))])])
4424 (define_expand "sle"
4425   [(set (match_operand:SI 0 "register_operand")
4426         (le:SI (match_dup 1)
4427                (match_dup 2)))]
4428   ""
4429   { if (mips_emit_scc (LE, operands[0])) DONE; else FAIL; })
4431 (define_insn "*sle_<mode>"
4432   [(set (match_operand:GPR 0 "register_operand" "=d")
4433         (le:GPR (match_operand:GPR 1 "register_operand" "d")
4434                 (match_operand:GPR 2 "sle_operand" "")))]
4435   "!TARGET_MIPS16"
4437   operands[2] = GEN_INT (INTVAL (operands[2]) + 1);
4438   return "slt\t%0,%1,%2";
4440   [(set_attr "type" "slt")
4441    (set_attr "mode" "<MODE>")])
4443 (define_insn "*sle_<mode>_mips16"
4444   [(set (match_operand:GPR 0 "register_operand" "=t")
4445         (le:GPR (match_operand:GPR 1 "register_operand" "d")
4446                 (match_operand:GPR 2 "sle_operand" "")))]
4447   "TARGET_MIPS16"
4449   operands[2] = GEN_INT (INTVAL (operands[2]) + 1);
4450   return "slt\t%1,%2";
4452   [(set_attr "type" "slt")
4453    (set_attr "mode" "<MODE>")
4454    (set (attr "length") (if_then_else (match_operand 2 "m16_uimm8_m1_1")
4455                                       (const_int 4)
4456                                       (const_int 8)))])
4458 (define_expand "sgtu"
4459   [(set (match_operand:SI 0 "register_operand")
4460         (gtu:SI (match_dup 1)
4461                 (match_dup 2)))]
4462   ""
4463   { if (mips_emit_scc (GTU, operands[0])) DONE; else FAIL; })
4465 (define_insn "*sgtu_<mode>"
4466   [(set (match_operand:GPR 0 "register_operand" "=d")
4467         (gtu:GPR (match_operand:GPR 1 "register_operand" "d")
4468                  (match_operand:GPR 2 "reg_or_0_operand" "dJ")))]
4469   "!TARGET_MIPS16"
4470   "sltu\t%0,%z2,%1"
4471   [(set_attr "type" "slt")
4472    (set_attr "mode" "<MODE>")])
4474 (define_insn "*sgtu_<mode>_mips16"
4475   [(set (match_operand:GPR 0 "register_operand" "=t")
4476         (gtu:GPR (match_operand:GPR 1 "register_operand" "d")
4477                  (match_operand:GPR 2 "register_operand" "d")))]
4478   "TARGET_MIPS16"
4479   "sltu\t%2,%1"
4480   [(set_attr "type" "slt")
4481    (set_attr "mode" "<MODE>")])
4483 (define_expand "sgeu"
4484   [(set (match_operand:SI 0 "register_operand")
4485         (geu:SI (match_dup 1)
4486                 (match_dup 2)))]
4487   ""
4488   { if (mips_emit_scc (GEU, operands[0])) DONE; else FAIL; })
4490 (define_insn "*sge_<mode>"
4491   [(set (match_operand:GPR 0 "register_operand" "=d")
4492         (geu:GPR (match_operand:GPR 1 "register_operand" "d")
4493                  (const_int 1)))]
4494   "!TARGET_MIPS16"
4495   "sltu\t%0,%.,%1"
4496   [(set_attr "type" "slt")
4497    (set_attr "mode" "<MODE>")])
4499 (define_expand "sltu"
4500   [(set (match_operand:SI 0 "register_operand")
4501         (ltu:SI (match_dup 1)
4502                 (match_dup 2)))]
4503   ""
4504   { if (mips_emit_scc (LTU, operands[0])) DONE; else FAIL; })
4506 (define_insn "*sltu_<mode>"
4507   [(set (match_operand:GPR 0 "register_operand" "=d")
4508         (ltu:GPR (match_operand:GPR 1 "register_operand" "d")
4509                  (match_operand:GPR 2 "arith_operand" "dI")))]
4510   "!TARGET_MIPS16"
4511   "sltu\t%0,%1,%2"
4512   [(set_attr "type" "slt")
4513    (set_attr "mode" "<MODE>")])
4515 (define_insn "*sltu_<mode>_mips16"
4516   [(set (match_operand:GPR 0 "register_operand" "=t,t")
4517         (ltu:GPR (match_operand:GPR 1 "register_operand" "d,d")
4518                  (match_operand:GPR 2 "arith_operand" "d,I")))]
4519   "TARGET_MIPS16"
4520   "sltu\t%1,%2"
4521   [(set_attr "type" "slt")
4522    (set_attr "mode" "<MODE>")
4523    (set_attr_alternative "length"
4524                 [(const_int 4)
4525                  (if_then_else (match_operand 2 "m16_uimm8_1")
4526                                (const_int 4)
4527                                (const_int 8))])])
4529 (define_expand "sleu"
4530   [(set (match_operand:SI 0 "register_operand")
4531         (leu:SI (match_dup 1)
4532                 (match_dup 2)))]
4533   ""
4534   { if (mips_emit_scc (LEU, operands[0])) DONE; else FAIL; })
4536 (define_insn "*sleu_<mode>"
4537   [(set (match_operand:GPR 0 "register_operand" "=d")
4538         (leu:GPR (match_operand:GPR 1 "register_operand" "d")
4539                  (match_operand:GPR 2 "sleu_operand" "")))]
4540   "!TARGET_MIPS16"
4542   operands[2] = GEN_INT (INTVAL (operands[2]) + 1);
4543   return "sltu\t%0,%1,%2";
4545   [(set_attr "type" "slt")
4546    (set_attr "mode" "<MODE>")])
4548 (define_insn "*sleu_<mode>_mips16"
4549   [(set (match_operand:GPR 0 "register_operand" "=t")
4550         (leu:GPR (match_operand:GPR 1 "register_operand" "d")
4551                  (match_operand:GPR 2 "sleu_operand" "")))]
4552   "TARGET_MIPS16"
4554   operands[2] = GEN_INT (INTVAL (operands[2]) + 1);
4555   return "sltu\t%1,%2";
4557   [(set_attr "type" "slt")
4558    (set_attr "mode" "<MODE>")
4559    (set (attr "length") (if_then_else (match_operand 2 "m16_uimm8_m1_1")
4560                                       (const_int 4)
4561                                       (const_int 8)))])
4564 ;;  ....................
4566 ;;      FLOATING POINT COMPARISONS
4568 ;;  ....................
4570 (define_insn "s<code>_<mode>"
4571   [(set (match_operand:CC 0 "register_operand" "=z")
4572         (fcond:CC (match_operand:SCALARF 1 "register_operand" "f")
4573                   (match_operand:SCALARF 2 "register_operand" "f")))]
4574   ""
4575   "c.<fcond>.<fmt>\t%Z0%1,%2"
4576   [(set_attr "type" "fcmp")
4577    (set_attr "mode" "FPSW")])
4579 (define_insn "sgt_<mode>"
4580   [(set (match_operand:CC 0 "register_operand" "=z")
4581         (gt:CC (match_operand:SCALARF 1 "register_operand" "f")
4582                (match_operand:SCALARF 2 "register_operand" "f")))]
4583   ""
4584   "c.lt.<fmt>\t%Z0%2,%1"
4585   [(set_attr "type" "fcmp")
4586    (set_attr "mode" "FPSW")])
4588 (define_insn "sge_<mode>"
4589   [(set (match_operand:CC 0 "register_operand" "=z")
4590         (ge:CC (match_operand:SCALARF 1 "register_operand" "f")
4591                (match_operand:SCALARF 2 "register_operand" "f")))]
4592   ""
4593   "c.le.<fmt>\t%Z0%2,%1"
4594   [(set_attr "type" "fcmp")
4595    (set_attr "mode" "FPSW")])
4598 ;;  ....................
4600 ;;      UNCONDITIONAL BRANCHES
4602 ;;  ....................
4604 ;; Unconditional branches.
4606 (define_insn "jump"
4607   [(set (pc)
4608         (label_ref (match_operand 0 "" "")))]
4609   "!TARGET_MIPS16"
4611   if (flag_pic)
4612     {
4613       if (get_attr_length (insn) <= 8)
4614         return "%*b\t%l0%/";
4615       else
4616         {
4617           output_asm_insn (mips_output_load_label (), operands);
4618           return "%*jr\t%@%/%]";
4619         }
4620     }
4621   else
4622     return "%*j\t%l0%/";
4624   [(set_attr "type"     "jump")
4625    (set_attr "mode"     "none")
4626    (set (attr "length")
4627         ;; We can't use `j' when emitting PIC.  Emit a branch if it's
4628         ;; in range, otherwise load the address of the branch target into
4629         ;; $at and then jump to it.
4630         (if_then_else
4631          (ior (eq (symbol_ref "flag_pic") (const_int 0))
4632               (lt (abs (minus (match_dup 0)
4633                               (plus (pc) (const_int 4))))
4634                   (const_int 131072)))
4635          (const_int 4) (const_int 16)))])
4637 ;; We need a different insn for the mips16, because a mips16 branch
4638 ;; does not have a delay slot.
4640 (define_insn ""
4641   [(set (pc)
4642         (label_ref (match_operand 0 "" "")))]
4643   "TARGET_MIPS16"
4644   "b\t%l0"
4645   [(set_attr "type"     "branch")
4646    (set_attr "mode"     "none")
4647    (set_attr "length"   "8")])
4649 (define_expand "indirect_jump"
4650   [(set (pc) (match_operand 0 "register_operand"))]
4651   ""
4653   operands[0] = force_reg (Pmode, operands[0]);
4654   if (Pmode == SImode)
4655     emit_jump_insn (gen_indirect_jumpsi (operands[0]));
4656   else
4657     emit_jump_insn (gen_indirect_jumpdi (operands[0]));
4658   DONE;
4661 (define_insn "indirect_jump<mode>"
4662   [(set (pc) (match_operand:P 0 "register_operand" "d"))]
4663   ""
4664   "%*j\t%0%/"
4665   [(set_attr "type" "jump")
4666    (set_attr "mode" "none")])
4668 (define_expand "tablejump"
4669   [(set (pc)
4670         (match_operand 0 "register_operand"))
4671    (use (label_ref (match_operand 1 "")))]
4672   ""
4674   if (TARGET_MIPS16)
4675     operands[0] = expand_binop (Pmode, add_optab,
4676                                 convert_to_mode (Pmode, operands[0], false),
4677                                 gen_rtx_LABEL_REF (Pmode, operands[1]),
4678                                 0, 0, OPTAB_WIDEN);
4679   else if (TARGET_GPWORD)
4680     operands[0] = expand_binop (Pmode, add_optab, operands[0],
4681                                 pic_offset_table_rtx, 0, 0, OPTAB_WIDEN);
4683   if (Pmode == SImode)
4684     emit_jump_insn (gen_tablejumpsi (operands[0], operands[1]));
4685   else
4686     emit_jump_insn (gen_tablejumpdi (operands[0], operands[1]));
4687   DONE;
4690 (define_insn "tablejump<mode>"
4691   [(set (pc)
4692         (match_operand:P 0 "register_operand" "d"))
4693    (use (label_ref (match_operand 1 "" "")))]
4694   ""
4695   "%*j\t%0%/"
4696   [(set_attr "type" "jump")
4697    (set_attr "mode" "none")])
4699 ;; For TARGET_ABICALLS, we save the gp in the jmp_buf as well.
4700 ;; While it is possible to either pull it off the stack (in the
4701 ;; o32 case) or recalculate it given t9 and our target label,
4702 ;; it takes 3 or 4 insns to do so.
4704 (define_expand "builtin_setjmp_setup"
4705   [(use (match_operand 0 "register_operand"))]
4706   "TARGET_ABICALLS"
4708   rtx addr;
4710   addr = plus_constant (operands[0], GET_MODE_SIZE (Pmode) * 3);
4711   emit_move_insn (gen_rtx_MEM (Pmode, addr), pic_offset_table_rtx);
4712   DONE;
4715 ;; Restore the gp that we saved above.  Despite the earlier comment, it seems
4716 ;; that older code did recalculate the gp from $25.  Continue to jump through
4717 ;; $25 for compatibility (we lose nothing by doing so).
4719 (define_expand "builtin_longjmp"
4720   [(use (match_operand 0 "register_operand"))]
4721   "TARGET_ABICALLS"
4723   /* The elements of the buffer are, in order:  */
4724   int W = GET_MODE_SIZE (Pmode);
4725   rtx fp = gen_rtx_MEM (Pmode, operands[0]);
4726   rtx lab = gen_rtx_MEM (Pmode, plus_constant (operands[0], 1*W));
4727   rtx stack = gen_rtx_MEM (Pmode, plus_constant (operands[0], 2*W));
4728   rtx gpv = gen_rtx_MEM (Pmode, plus_constant (operands[0], 3*W));
4729   rtx pv = gen_rtx_REG (Pmode, PIC_FUNCTION_ADDR_REGNUM);
4730   /* Use gen_raw_REG to avoid being given pic_offset_table_rtx.
4731      The target is bound to be using $28 as the global pointer
4732      but the current function might not be.  */
4733   rtx gp = gen_raw_REG (Pmode, GLOBAL_POINTER_REGNUM);
4735   /* This bit is similar to expand_builtin_longjmp except that it
4736      restores $gp as well.  */
4737   emit_move_insn (hard_frame_pointer_rtx, fp);
4738   emit_move_insn (pv, lab);
4739   emit_stack_restore (SAVE_NONLOCAL, stack, NULL_RTX);
4740   emit_move_insn (gp, gpv);
4741   emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
4742   emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
4743   emit_insn (gen_rtx_USE (VOIDmode, gp));
4744   emit_indirect_jump (pv);
4745   DONE;
4749 ;;  ....................
4751 ;;      Function prologue/epilogue
4753 ;;  ....................
4756 (define_expand "prologue"
4757   [(const_int 1)]
4758   ""
4760   mips_expand_prologue ();
4761   DONE;
4764 ;; Block any insns from being moved before this point, since the
4765 ;; profiling call to mcount can use various registers that aren't
4766 ;; saved or used to pass arguments.
4768 (define_insn "blockage"
4769   [(unspec_volatile [(const_int 0)] UNSPEC_BLOCKAGE)]
4770   ""
4771   ""
4772   [(set_attr "type"     "unknown")
4773    (set_attr "mode"     "none")
4774    (set_attr "length"   "0")])
4776 (define_expand "epilogue"
4777   [(const_int 2)]
4778   ""
4780   mips_expand_epilogue (false);
4781   DONE;
4784 (define_expand "sibcall_epilogue"
4785   [(const_int 2)]
4786   ""
4788   mips_expand_epilogue (true);
4789   DONE;
4792 ;; Trivial return.  Make it look like a normal return insn as that
4793 ;; allows jump optimizations to work better.
4795 (define_insn "return"
4796   [(return)]
4797   "mips_can_use_return_insn ()"
4798   "%*j\t$31%/"
4799   [(set_attr "type"     "jump")
4800    (set_attr "mode"     "none")])
4802 ;; Normal return.
4804 (define_insn "return_internal"
4805   [(return)
4806    (use (match_operand 0 "pmode_register_operand" ""))]
4807   ""
4808   "%*j\t%0%/"
4809   [(set_attr "type"     "jump")
4810    (set_attr "mode"     "none")])
4812 ;; This is used in compiling the unwind routines.
4813 (define_expand "eh_return"
4814   [(use (match_operand 0 "general_operand"))]
4815   ""
4817   enum machine_mode gpr_mode = TARGET_64BIT ? DImode : SImode;
4819   if (GET_MODE (operands[0]) != gpr_mode)
4820     operands[0] = convert_to_mode (gpr_mode, operands[0], 0);
4821   if (TARGET_64BIT)
4822     emit_insn (gen_eh_set_lr_di (operands[0]));
4823   else
4824     emit_insn (gen_eh_set_lr_si (operands[0]));
4826   DONE;
4829 ;; Clobber the return address on the stack.  We can't expand this
4830 ;; until we know where it will be put in the stack frame.
4832 (define_insn "eh_set_lr_si"
4833   [(unspec [(match_operand:SI 0 "register_operand" "d")] UNSPEC_EH_RETURN)
4834    (clobber (match_scratch:SI 1 "=&d"))]
4835   "! TARGET_64BIT"
4836   "#")
4838 (define_insn "eh_set_lr_di"
4839   [(unspec [(match_operand:DI 0 "register_operand" "d")] UNSPEC_EH_RETURN)
4840    (clobber (match_scratch:DI 1 "=&d"))]
4841   "TARGET_64BIT"
4842   "#")
4844 (define_split
4845   [(unspec [(match_operand 0 "register_operand")] UNSPEC_EH_RETURN)
4846    (clobber (match_scratch 1))]
4847   "reload_completed && !TARGET_DEBUG_D_MODE"
4848   [(const_int 0)]
4850   mips_set_return_address (operands[0], operands[1]);
4851   DONE;
4854 (define_insn_and_split "exception_receiver"
4855   [(set (reg:SI 28)
4856         (unspec_volatile:SI [(const_int 0)] UNSPEC_EH_RECEIVER))]
4857   "TARGET_ABICALLS && TARGET_OLDABI"
4858   "#"
4859   "&& reload_completed"
4860   [(const_int 0)]
4862   mips_restore_gp ();
4863   DONE;
4865   [(set_attr "type"   "load")
4866    (set_attr "length" "12")])
4869 ;;  ....................
4871 ;;      FUNCTION CALLS
4873 ;;  ....................
4875 ;; Instructions to load a call address from the GOT.  The address might
4876 ;; point to a function or to a lazy binding stub.  In the latter case,
4877 ;; the stub will use the dynamic linker to resolve the function, which
4878 ;; in turn will change the GOT entry to point to the function's real
4879 ;; address.
4881 ;; This means that every call, even pure and constant ones, can
4882 ;; potentially modify the GOT entry.  And once a stub has been called,
4883 ;; we must not call it again.
4885 ;; We represent this restriction using an imaginary fixed register that
4886 ;; acts like a GOT version number.  By making the register call-clobbered,
4887 ;; we tell the target-independent code that the address could be changed
4888 ;; by any call insn.
4889 (define_insn "load_call<mode>"
4890   [(set (match_operand:P 0 "register_operand" "=c")
4891         (unspec:P [(match_operand:P 1 "register_operand" "r")
4892                    (match_operand:P 2 "immediate_operand" "")
4893                    (reg:P FAKE_CALL_REGNO)]
4894                   UNSPEC_LOAD_CALL))]
4895   "TARGET_ABICALLS"
4896   "<load>\t%0,%R2(%1)"
4897   [(set_attr "type" "load")
4898    (set_attr "mode" "<MODE>")
4899    (set_attr "length" "4")])
4901 ;; Sibling calls.  All these patterns use jump instructions.
4903 ;; If TARGET_SIBCALLS, call_insn_operand will only accept constant
4904 ;; addresses if a direct jump is acceptable.  Since the 'S' constraint
4905 ;; is defined in terms of call_insn_operand, the same is true of the
4906 ;; constraints.
4908 ;; When we use an indirect jump, we need a register that will be
4909 ;; preserved by the epilogue.  Since TARGET_ABICALLS forces us to
4910 ;; use $25 for this purpose -- and $25 is never clobbered by the
4911 ;; epilogue -- we might as well use it for !TARGET_ABICALLS as well.
4913 (define_expand "sibcall"
4914   [(parallel [(call (match_operand 0 "")
4915                     (match_operand 1 ""))
4916               (use (match_operand 2 ""))        ;; next_arg_reg
4917               (use (match_operand 3 ""))])]     ;; struct_value_size_rtx
4918   "TARGET_SIBCALLS"
4920   mips_expand_call (0, XEXP (operands[0], 0), operands[1], operands[2], true);
4921   DONE;
4924 (define_insn "sibcall_internal"
4925   [(call (mem:SI (match_operand 0 "call_insn_operand" "j,S"))
4926          (match_operand 1 "" ""))]
4927   "TARGET_SIBCALLS && SIBLING_CALL_P (insn)"
4928   "@
4929     %*jr\t%0%/
4930     %*j\t%0%/"
4931   [(set_attr "type" "call")])
4933 (define_expand "sibcall_value"
4934   [(parallel [(set (match_operand 0 "")
4935                    (call (match_operand 1 "")
4936                          (match_operand 2 "")))
4937               (use (match_operand 3 ""))])]             ;; next_arg_reg
4938   "TARGET_SIBCALLS"
4940   mips_expand_call (operands[0], XEXP (operands[1], 0),
4941                     operands[2], operands[3], true);
4942   DONE;
4945 (define_insn "sibcall_value_internal"
4946   [(set (match_operand 0 "register_operand" "=df,df")
4947         (call (mem:SI (match_operand 1 "call_insn_operand" "j,S"))
4948               (match_operand 2 "" "")))]
4949   "TARGET_SIBCALLS && SIBLING_CALL_P (insn)"
4950   "@
4951     %*jr\t%1%/
4952     %*j\t%1%/"
4953   [(set_attr "type" "call")])
4955 (define_insn "sibcall_value_multiple_internal"
4956   [(set (match_operand 0 "register_operand" "=df,df")
4957         (call (mem:SI (match_operand 1 "call_insn_operand" "j,S"))
4958               (match_operand 2 "" "")))
4959    (set (match_operand 3 "register_operand" "=df,df")
4960         (call (mem:SI (match_dup 1))
4961               (match_dup 2)))]
4962   "TARGET_SIBCALLS && SIBLING_CALL_P (insn)"
4963   "@
4964     %*jr\t%1%/
4965     %*j\t%1%/"
4966   [(set_attr "type" "call")])
4968 (define_expand "call"
4969   [(parallel [(call (match_operand 0 "")
4970                     (match_operand 1 ""))
4971               (use (match_operand 2 ""))        ;; next_arg_reg
4972               (use (match_operand 3 ""))])]     ;; struct_value_size_rtx
4973   ""
4975   mips_expand_call (0, XEXP (operands[0], 0), operands[1], operands[2], false);
4976   DONE;
4979 ;; This instruction directly corresponds to an assembly-language "jal".
4980 ;; There are four cases:
4982 ;;    - -mno-abicalls:
4983 ;;        Both symbolic and register destinations are OK.  The pattern
4984 ;;        always expands to a single mips instruction.
4986 ;;    - -mabicalls/-mno-explicit-relocs:
4987 ;;        Again, both symbolic and register destinations are OK.
4988 ;;        The call is treated as a multi-instruction black box.
4990 ;;    - -mabicalls/-mexplicit-relocs with n32 or n64:
4991 ;;        Only "jal $25" is allowed.  This expands to a single "jalr $25"
4992 ;;        instruction.
4994 ;;    - -mabicalls/-mexplicit-relocs with o32 or o64:
4995 ;;        Only "jal $25" is allowed.  The call is actually two instructions:
4996 ;;        "jalr $25" followed by an insn to reload $gp.
4998 ;; In the last case, we can generate the individual instructions with
4999 ;; a define_split.  There are several things to be wary of:
5001 ;;   - We can't expose the load of $gp before reload.  If we did,
5002 ;;     it might get removed as dead, but reload can introduce new
5003 ;;     uses of $gp by rematerializing constants.
5005 ;;   - We shouldn't restore $gp after calls that never return.
5006 ;;     It isn't valid to insert instructions between a noreturn
5007 ;;     call and the following barrier.
5009 ;;   - The splitter deliberately changes the liveness of $gp.  The unsplit
5010 ;;     instruction preserves $gp and so have no effect on its liveness.
5011 ;;     But once we generate the separate insns, it becomes obvious that
5012 ;;     $gp is not live on entry to the call.
5014 ;; ??? The operands[2] = insn check is a hack to make the original insn
5015 ;; available to the splitter.
5016 (define_insn_and_split "call_internal"
5017   [(call (mem:SI (match_operand 0 "call_insn_operand" "c,S"))
5018          (match_operand 1 "" ""))
5019    (clobber (reg:SI 31))]
5020   ""
5021   { return TARGET_SPLIT_CALLS ? "#" : "%*jal\t%0%/"; }
5022   "reload_completed && TARGET_SPLIT_CALLS && (operands[2] = insn)"
5023   [(const_int 0)]
5025   emit_call_insn (gen_call_split (operands[0], operands[1]));
5026   if (!find_reg_note (operands[2], REG_NORETURN, 0))
5027     mips_restore_gp ();
5028   DONE;
5030   [(set_attr "jal" "indirect,direct")
5031    (set_attr "extended_mips16" "no,yes")])
5033 (define_insn "call_split"
5034   [(call (mem:SI (match_operand 0 "call_insn_operand" "c"))
5035          (match_operand 1 "" ""))
5036    (clobber (reg:SI 31))
5037    (clobber (reg:SI 28))]
5038   "TARGET_SPLIT_CALLS"
5039   "%*jalr\t%0%/"
5040   [(set_attr "type" "call")])
5042 (define_expand "call_value"
5043   [(parallel [(set (match_operand 0 "")
5044                    (call (match_operand 1 "")
5045                          (match_operand 2 "")))
5046               (use (match_operand 3 ""))])]             ;; next_arg_reg
5047   ""
5049   mips_expand_call (operands[0], XEXP (operands[1], 0),
5050                     operands[2], operands[3], false);
5051   DONE;
5054 ;; See comment for call_internal.
5055 (define_insn_and_split "call_value_internal"
5056   [(set (match_operand 0 "register_operand" "=df,df")
5057         (call (mem:SI (match_operand 1 "call_insn_operand" "c,S"))
5058               (match_operand 2 "" "")))
5059    (clobber (reg:SI 31))]
5060   ""
5061   { return TARGET_SPLIT_CALLS ? "#" : "%*jal\t%1%/"; }
5062   "reload_completed && TARGET_SPLIT_CALLS && (operands[3] = insn)"
5063   [(const_int 0)]
5065   emit_call_insn (gen_call_value_split (operands[0], operands[1],
5066                                         operands[2]));
5067   if (!find_reg_note (operands[3], REG_NORETURN, 0))
5068     mips_restore_gp ();
5069   DONE;
5071   [(set_attr "jal" "indirect,direct")
5072    (set_attr "extended_mips16" "no,yes")])
5074 (define_insn "call_value_split"
5075   [(set (match_operand 0 "register_operand" "=df")
5076         (call (mem:SI (match_operand 1 "call_insn_operand" "c"))
5077               (match_operand 2 "" "")))
5078    (clobber (reg:SI 31))
5079    (clobber (reg:SI 28))]
5080   "TARGET_SPLIT_CALLS"
5081   "%*jalr\t%1%/"
5082   [(set_attr "type" "call")])
5084 ;; See comment for call_internal.
5085 (define_insn_and_split "call_value_multiple_internal"
5086   [(set (match_operand 0 "register_operand" "=df,df")
5087         (call (mem:SI (match_operand 1 "call_insn_operand" "c,S"))
5088               (match_operand 2 "" "")))
5089    (set (match_operand 3 "register_operand" "=df,df")
5090         (call (mem:SI (match_dup 1))
5091               (match_dup 2)))
5092    (clobber (reg:SI 31))]
5093   ""
5094   { return TARGET_SPLIT_CALLS ? "#" : "%*jal\t%1%/"; }
5095   "reload_completed && TARGET_SPLIT_CALLS && (operands[4] = insn)"
5096   [(const_int 0)]
5098   emit_call_insn (gen_call_value_multiple_split (operands[0], operands[1],
5099                                                  operands[2], operands[3]));
5100   if (!find_reg_note (operands[4], REG_NORETURN, 0))
5101     mips_restore_gp ();
5102   DONE;
5104   [(set_attr "jal" "indirect,direct")
5105    (set_attr "extended_mips16" "no,yes")])
5107 (define_insn "call_value_multiple_split"
5108   [(set (match_operand 0 "register_operand" "=df")
5109         (call (mem:SI (match_operand 1 "call_insn_operand" "c"))
5110               (match_operand 2 "" "")))
5111    (set (match_operand 3 "register_operand" "=df")
5112         (call (mem:SI (match_dup 1))
5113               (match_dup 2)))
5114    (clobber (reg:SI 31))
5115    (clobber (reg:SI 28))]
5116   "TARGET_SPLIT_CALLS"
5117   "%*jalr\t%1%/"
5118   [(set_attr "type" "call")])
5120 ;; Call subroutine returning any type.
5122 (define_expand "untyped_call"
5123   [(parallel [(call (match_operand 0 "")
5124                     (const_int 0))
5125               (match_operand 1 "")
5126               (match_operand 2 "")])]
5127   ""
5129   int i;
5131   emit_call_insn (GEN_CALL (operands[0], const0_rtx, NULL, const0_rtx));
5133   for (i = 0; i < XVECLEN (operands[2], 0); i++)
5134     {
5135       rtx set = XVECEXP (operands[2], 0, i);
5136       emit_move_insn (SET_DEST (set), SET_SRC (set));
5137     }
5139   emit_insn (gen_blockage ());
5140   DONE;
5144 ;;  ....................
5146 ;;      MISC.
5148 ;;  ....................
5152 (define_insn "prefetch"
5153   [(prefetch (match_operand:QI 0 "address_operand" "p")
5154              (match_operand 1 "const_int_operand" "n")
5155              (match_operand 2 "const_int_operand" "n"))]
5156   "ISA_HAS_PREFETCH && TARGET_EXPLICIT_RELOCS"
5158   operands[1] = mips_prefetch_cookie (operands[1], operands[2]);
5159   return "pref\t%1,%a0";
5161   [(set_attr "type" "prefetch")])
5163 (define_insn "*prefetch_indexed_<mode>"
5164   [(prefetch (plus:P (match_operand:P 0 "register_operand" "d")
5165                      (match_operand:P 1 "register_operand" "d"))
5166              (match_operand 2 "const_int_operand" "n")
5167              (match_operand 3 "const_int_operand" "n"))]
5168   "ISA_HAS_PREFETCHX && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
5170   operands[2] = mips_prefetch_cookie (operands[2], operands[3]);
5171   return "prefx\t%2,%1(%0)";
5173   [(set_attr "type" "prefetchx")])
5175 (define_insn "nop"
5176   [(const_int 0)]
5177   ""
5178   "%(nop%)"
5179   [(set_attr "type"     "nop")
5180    (set_attr "mode"     "none")])
5182 ;; Like nop, but commented out when outside a .set noreorder block.
5183 (define_insn "hazard_nop"
5184   [(const_int 1)]
5185   ""
5186   {
5187     if (set_noreorder)
5188       return "nop";
5189     else
5190       return "#nop";
5191   }
5192   [(set_attr "type"     "nop")])
5194 ;; MIPS4 Conditional move instructions.
5196 (define_insn "*mov<GPR:mode>_on_<MOVECC:mode>"
5197   [(set (match_operand:GPR 0 "register_operand" "=d,d")
5198         (if_then_else:GPR
5199          (match_operator:MOVECC 4 "equality_operator"
5200                 [(match_operand:MOVECC 1 "register_operand" "<MOVECC:reg>,<MOVECC:reg>")
5201                  (const_int 0)])
5202          (match_operand:GPR 2 "reg_or_0_operand" "dJ,0")
5203          (match_operand:GPR 3 "reg_or_0_operand" "0,dJ")))]
5204   "ISA_HAS_CONDMOVE"
5205   "@
5206     mov%T4\t%0,%z2,%1
5207     mov%t4\t%0,%z3,%1"
5208   [(set_attr "type" "condmove")
5209    (set_attr "mode" "<GPR:MODE>")])
5211 (define_insn "*mov<SCALARF:mode>_on_<MOVECC:mode>"
5212   [(set (match_operand:SCALARF 0 "register_operand" "=f,f")
5213         (if_then_else:SCALARF
5214          (match_operator:MOVECC 4 "equality_operator"
5215                 [(match_operand:MOVECC 1 "register_operand" "<MOVECC:reg>,<MOVECC:reg>")
5216                  (const_int 0)])
5217          (match_operand:SCALARF 2 "register_operand" "f,0")
5218          (match_operand:SCALARF 3 "register_operand" "0,f")))]
5219   "ISA_HAS_CONDMOVE"
5220   "@
5221     mov%T4.<fmt>\t%0,%2,%1
5222     mov%t4.<fmt>\t%0,%3,%1"
5223   [(set_attr "type" "condmove")
5224    (set_attr "mode" "<SCALARF:MODE>")])
5226 ;; These are the main define_expand's used to make conditional moves.
5228 (define_expand "mov<mode>cc"
5229   [(set (match_dup 4) (match_operand 1 "comparison_operator"))
5230    (set (match_operand:GPR 0 "register_operand")
5231         (if_then_else:GPR (match_dup 5)
5232                           (match_operand:GPR 2 "reg_or_0_operand")
5233                           (match_operand:GPR 3 "reg_or_0_operand")))]
5234   "ISA_HAS_CONDMOVE"
5236   gen_conditional_move (operands);
5237   DONE;
5240 (define_expand "mov<mode>cc"
5241   [(set (match_dup 4) (match_operand 1 "comparison_operator"))
5242    (set (match_operand:SCALARF 0 "register_operand")
5243         (if_then_else:SCALARF (match_dup 5)
5244                               (match_operand:SCALARF 2 "register_operand")
5245                               (match_operand:SCALARF 3 "register_operand")))]
5246   "ISA_HAS_CONDMOVE"
5248   gen_conditional_move (operands);
5249   DONE;
5253 ;;  ....................
5255 ;;      mips16 inline constant tables
5257 ;;  ....................
5260 (define_insn "consttable_int"
5261   [(unspec_volatile [(match_operand 0 "consttable_operand" "")
5262                      (match_operand 1 "const_int_operand" "")]
5263                     UNSPEC_CONSTTABLE_INT)]
5264   "TARGET_MIPS16"
5266   assemble_integer (operands[0], INTVAL (operands[1]),
5267                     BITS_PER_UNIT * INTVAL (operands[1]), 1);
5268   return "";
5270   [(set (attr "length") (symbol_ref "INTVAL (operands[1])"))])
5272 (define_insn "consttable_float"
5273   [(unspec_volatile [(match_operand 0 "consttable_operand" "")]
5274                     UNSPEC_CONSTTABLE_FLOAT)]
5275   "TARGET_MIPS16"
5277   REAL_VALUE_TYPE d;
5279   gcc_assert (GET_CODE (operands[0]) == CONST_DOUBLE);
5280   REAL_VALUE_FROM_CONST_DOUBLE (d, operands[0]);
5281   assemble_real (d, GET_MODE (operands[0]),
5282                  GET_MODE_BITSIZE (GET_MODE (operands[0])));
5283   return "";
5285   [(set (attr "length")
5286         (symbol_ref "GET_MODE_SIZE (GET_MODE (operands[0]))"))])
5288 (define_insn "align"
5289   [(unspec_volatile [(match_operand 0 "const_int_operand" "")] UNSPEC_ALIGN)]
5290   ""
5291   ".align\t%0"
5292   [(set (attr "length") (symbol_ref "(1 << INTVAL (operands[0])) - 1"))])
5294 (define_split
5295   [(match_operand 0 "small_data_pattern")]
5296   "reload_completed"
5297   [(match_dup 0)]
5298   { operands[0] = mips_rewrite_small_data (operands[0]); })
5300 ; Thread-Local Storage
5302 ; The TLS base pointer is acessed via "rdhwr $v1, $29".  No current
5303 ; MIPS architecture defines this register, and no current
5304 ; implementation provides it; instead, any OS which supports TLS is
5305 ; expected to trap and emulate this instruction.  rdhwr is part of the
5306 ; MIPS 32r2 specification, but we use it on any architecture because
5307 ; we expect it to be emulated.  Use .set to force the assembler to
5308 ; accept it.
5310 (define_insn "tls_get_tp_<mode>"
5311   [(set (match_operand:P 0 "register_operand" "=v")
5312         (unspec:P [(const_int 0)]
5313                   UNSPEC_TLS_GET_TP))]
5314   "HAVE_AS_TLS && !TARGET_MIPS16"
5315   ".set\tpush\;.set\tmips32r2\t\;rdhwr\t%0,$29\;.set\tpop"
5316   [(set_attr "type" "unknown")
5317    (set_attr "mode" "<MODE>")])
5319 ; The MIPS Paired-Single Floating Point and MIPS-3D Instructions.
5321 (include "mips-ps-3d.md")