Merge from mainline (gomp-merge-2005-02-26).
[official-gcc.git] / gcc / config / i860 / i860.md
blob8a9628b6f18641cd31e8281f7b9a0593a655a96f
1 ;;  GCC Machine description for the Intel i860 microprocessor
2 ;;  Copyright (C) 1989, 1990, 1997, 1998, 1999, 2000, 2003, 2004
3 ;;  Free Software Foundation, Inc.
5 ;; This file is part of GCC.
7 ;; GCC is free software; you can redistribute it and/or modify
8 ;; it under the terms of the GNU General Public License as published by
9 ;; the Free Software Foundation; either version 2, or (at your option)
10 ;; any later version.
12 ;; GCC is distributed in the hope that it will be useful,
13 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
14 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 ;; GNU General Public License for more details.
17 ;; You should have received a copy of the GNU General Public License
18 ;; along with GCC; see the file COPYING.  If not, write to
19 ;; the Free Software Foundation, 59 Temple Place - Suite 330,
20 ;; Boston, MA 02111-1307, USA.
23 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
25 ;;- cpp macro #define NOTICE_UPDATE_CC in file tm.h handles condition code
26 ;;- updates for most instructions.
29 ;; UNSPEC_VOLATILE usage
32 (define_constants
33   [; Blockage
34    (UNSPECV_BLOCKAGE            0)
35   ])
37 ;;- Operand classes for the register allocator:
39 /* Bit-test instructions.  */
41 (define_insn ""
42   [(set (cc0) (eq (and:SI (match_operand:SI 0 "register_operand" "r")
43                           (match_operand:SI 1 "logic_operand" "rL"))
44                   (const_int 0)))]
45   ""
46   "*
48   CC_STATUS_PARTIAL_INIT;
49   return \"and %1,%0,%?r0\";
50 }")
52 (define_insn ""
53   [(set (cc0) (ne (and:SI (match_operand:SI 0 "register_operand" "r")
54                           (match_operand:SI 1 "logic_operand" "rL"))
55                   (const_int 0)))]
56   ""
57   "*
59   CC_STATUS_PARTIAL_INIT;
60   cc_status.flags |= CC_NEGATED;
61   return \"and %1,%0,%?r0\";
62 }")
64 (define_insn ""
65   [(set (cc0) (eq (and:SI (match_operand:SI 0 "register_operand" "r")
66                           (match_operand:SI 1 "immediate_operand" "i"))
67                   (const_int 0)))]
68   "GET_CODE (operands[1]) == CONST_INT && (INTVAL (operands[1]) & 0xffff) == 0"
69   "*
71   CC_STATUS_PARTIAL_INIT;
72   return \"andh %H1,%0,%?r0\";
73 }")
75 (define_insn ""
76   [(set (cc0) (ne (and:SI (match_operand:SI 0 "register_operand" "r")
77                           (match_operand:SI 1 "immediate_operand" "i"))
78                   (const_int 0)))]
79   "GET_CODE (operands[1]) == CONST_INT && (INTVAL (operands[1]) & 0xffff) == 0"
80   "*
82   CC_STATUS_PARTIAL_INIT;
83   cc_status.flags |= CC_NEGATED;
84   return \"andh %H1,%0,%?r0\";
85 }")
87 (define_insn ""
88   [(set (cc0) (eq (ashiftrt:SI
89                    (sign_extend:SI
90                     (ashift:QI (match_operand:QI 0 "register_operand" "r")
91                                (match_operand:QI 1 "logic_int" "n")))
92                    (match_operand:SI 2 "logic_int" "n"))
93                   (const_int 0)))]
94   ""
95   "*
97   int width = 8 - INTVAL (operands[2]);
98   int pos = 8 - width - INTVAL (operands[1]);
100   CC_STATUS_PARTIAL_INIT;
101   operands[2] = GEN_INT (~((-1) << width) << pos);
102   return \"and %2,%0,%?r0\";
105 ;; -------------------------------------------------------------------------
106 ;; SImode signed integer comparisons
107 ;; -------------------------------------------------------------------------
109 (define_insn "cmpeqsi"
110   [(set (cc0) (eq (match_operand:SI 0 "logic_operand" "r,rL")
111                   (match_operand:SI 1 "logic_operand" "L,r")))]
112   ""
113   "*
115   CC_STATUS_PARTIAL_INIT;
116   if (REG_P (operands[0]))
117     return \"xor %1,%0,%?r0\";
118   else
119     return \"xor %0,%1,%?r0\";
122 (define_insn "cmpnesi"
123   [(set (cc0) (ne (match_operand:SI 0 "logic_operand" "r,rL")
124                   (match_operand:SI 1 "logic_operand" "L,r")))]
125   ""
126   "*
128   CC_STATUS_PARTIAL_INIT;
129   cc_status.flags |= CC_NEGATED;
130   if (REG_P (operands[0]))
131     return \"xor %1,%0,%?r0\";
132   else
133     return \"xor %0,%1,%?r0\";
136 (define_insn "cmpltsi"
137   [(set (cc0) (lt (match_operand:SI 0 "arith_operand" "r,rI")
138                   (match_operand:SI 1 "arith_operand" "I,r")))]
139   ""
140   "*
142   CC_STATUS_PARTIAL_INIT;
143   if (REG_P (operands[1]))
144     return \"subs %0,%1,%?r0\";
145   else
146     {
147       cc_status.flags |= CC_REVERSED;
148       operands[1] = GEN_INT (- INTVAL (operands[1]));
149       return \"adds %1,%0,%?r0\";
150     }
153 (define_insn "cmpgtsi"
154   [(set (cc0) (gt (match_operand:SI 0 "arith_operand" "r,rI")
155                   (match_operand:SI 1 "arith_operand" "I,r")))]
156   ""
157   "*
159   CC_STATUS_PARTIAL_INIT;
160   if (REG_P (operands[0]))
161     return \"subs %1,%0,%?r0\";
162   else
163     {
164       cc_status.flags |= CC_REVERSED;
165       operands[0] = GEN_INT (- INTVAL (operands[0]));
166       return \"adds %0,%1,%?r0\";
167     }
170 (define_insn "cmplesi"
171   [(set (cc0) (le (match_operand:SI 0 "arith_operand" "r,rI")
172                   (match_operand:SI 1 "arith_operand" "I,r")))]
173   ""
174   "*
176   CC_STATUS_PARTIAL_INIT;
177   cc_status.flags |= CC_NEGATED;
178   if (REG_P (operands[0]))
179     return \"subs %1,%0,%?r0\";
180   else
181     {
182       cc_status.flags |= CC_REVERSED;
183       operands[0] = GEN_INT (- INTVAL (operands[0]));
184       return \"adds %0,%1,%?r0\";
185     }
188 (define_insn "cmpgesi"
189   [(set (cc0) (ge (match_operand:SI 0 "arith_operand" "r,rI")
190                   (match_operand:SI 1 "arith_operand" "I,r")))]
191   ""
192   "*
194   CC_STATUS_PARTIAL_INIT;
195   cc_status.flags |= CC_NEGATED;
196   if (REG_P (operands[1]))
197     return \"subs %0,%1,%?r0\";
198   else
199     {
200       cc_status.flags |= CC_REVERSED;
201       operands[1] = GEN_INT (- INTVAL (operands[1]));
202       return \"adds %1,%0,%?r0\";
203     }
206 ;; -------------------------------------------------------------------------
207 ;; SImode unsigned integer comparisons
208 ;; -------------------------------------------------------------------------
210 ;; WARNING!  There is a small i860 hardware limitation (bug?) which we
211 ;; may run up against (if we are not careful) when we are trying to do
212 ;; unsigned comparisons like (x >= 0), (x < 0), (0 <= x), and (0 > x).
213 ;; Specifically, we must avoid using an `addu' instruction to perform
214 ;; such comparisons because the result (in the CC bit register) will
215 ;; come out wrong.  (This fact is documented in a footnote on page 7-10
216 ;; of the 1991 version of the i860 Microprocessor Family Programmer's
217 ;; Reference Manual).  Note that unsigned comparisons of this sort are
218 ;; always redundant anyway, because an unsigned quantity can never be
219 ;; less than zero.  When we see cases like this, we generate an
220 ;; `or K,%r0,%r0' instruction instead (where K is a constant 0 or -1)
221 ;; so as to get the CC bit register set properly for any subsequent
222 ;; conditional jump instruction.
224 (define_insn "cmpgeusi"
225   [(set (cc0) (geu (match_operand:SI 0 "arith_operand" "r,rI")
226                    (match_operand:SI 1 "arith_operand" "I,r")))]
227   ""
228   "*
230   CC_STATUS_PARTIAL_INIT;
231   if (REG_P (operands[1]))
232     return \"subu %0,%1,%?r0\";
233   else
234     {
235       if (INTVAL (operands[1]) == 0)
236         return \"or 0,%?r0,%?r0\";
237       else
238         {
239           cc_status.flags |= CC_REVERSED;
240           operands[1] = GEN_INT (- INTVAL (operands[1]));
241           return \"addu %1,%0,%?r0\";
242         }
243     }
246 (define_insn "cmpleusi"
247   [(set (cc0) (leu (match_operand:SI 0 "arith_operand" "r,rI")
248                    (match_operand:SI 1 "arith_operand" "I,r")))]
249   ""
250   "*
252   CC_STATUS_PARTIAL_INIT;
253   if (REG_P (operands[0]))
254     return \"subu %1,%0,%?r0\";
255   else
256     {
257       if (INTVAL (operands[0]) == 0)
258         return \"or 0,%?r0,%?r0\";
259       else
260         {
261           cc_status.flags |= CC_REVERSED;
262           operands[0] = GEN_INT (- INTVAL (operands[0]));
263           return \"addu %0,%1,%?r0\";
264         }
265     }
268 ;; -------------------------------------------------------------------------
269 ;; SFmode floating-point comparisons
270 ;; -------------------------------------------------------------------------
272 (define_insn "cmpeqsf"
273   [(set (cc0) (eq (match_operand:SF 0 "reg_or_0_operand" "fG")
274                   (match_operand:SF 1 "reg_or_0_operand" "fG")))]
275   ""
276   "*
278   CC_STATUS_PARTIAL_INIT;
279   return \"pfeq.ss %r0,%r1,%?f0\";
282 (define_insn "cmpnesf"
283   [(set (cc0) (ne (match_operand:SF 0 "reg_or_0_operand" "fG")
284                   (match_operand:SF 1 "reg_or_0_operand" "fG")))]
285   ""
286   "*
288   CC_STATUS_PARTIAL_INIT;
289   cc_status.flags |= CC_NEGATED;
290   return \"pfeq.ss %r1,%r0,%?f0\";
293 ;; NOTE:  The i860 Programmer's Reference Manual says that when we are
294 ;; doing (A < B) or (A > B) comparisons, we have to use pfgt for these
295 ;; in order to be IEEE compliant (in case a trap occurs during these
296 ;; operations).  Conversely, for (A <= B) or (A >= B) comparisons, we
297 ;; must use pfle to be IEEE compliant.
299 (define_insn "cmpltsf"
300   [(set (cc0) (lt (match_operand:SF 0 "reg_or_0_operand" "fG")
301                   (match_operand:SF 1 "reg_or_0_operand" "fG")))]
302   ""
303   "*
305   CC_STATUS_PARTIAL_INIT;
306   return \"pfgt.ss %r1,%r0,%?f0\";
309 (define_insn "cmpgtsf"
310   [(set (cc0) (gt (match_operand:SF 0 "reg_or_0_operand" "fG")
311                   (match_operand:SF 1 "reg_or_0_operand" "fG")))]
312   ""
313   "*
315   CC_STATUS_PARTIAL_INIT;
316   return \"pfgt.ss %r0,%r1,%?f0\";
319 ;; NOTE:  The pfle opcode *clears* the CC flag if the first operand is
320 ;; less than or equal to the second.  Thus, we have to set CC_NEGATED
321 ;; for the following two patterns.
323 (define_insn "cmplesf"
324   [(set (cc0) (le (match_operand:SF 0 "reg_or_0_operand" "fG")
325                   (match_operand:SF 1 "reg_or_0_operand" "fG")))]
326   ""
327   "*
329   CC_STATUS_PARTIAL_INIT;
330   cc_status.flags |= CC_NEGATED;
331   return \"pfle.ss %r0,%r1,%?f0\";
334 (define_insn "cmpgesf"
335   [(set (cc0) (ge (match_operand:SF 0 "reg_or_0_operand" "fG")
336                   (match_operand:SF 1 "reg_or_0_operand" "fG")))]
337   ""
338   "*
340   CC_STATUS_PARTIAL_INIT;
341   cc_status.flags |= CC_NEGATED;
342   return \"pfle.ss %r1,%r0,%?f0\";
345 ;; -------------------------------------------------------------------------
346 ;; DFmode floating-point comparisons
347 ;; -------------------------------------------------------------------------
349 (define_insn "cmpeqdf"
350   [(set (cc0) (eq (match_operand:DF 0 "reg_or_0_operand" "fG")
351                   (match_operand:DF 1 "reg_or_0_operand" "fG")))]
352   ""
353   "*
355   CC_STATUS_PARTIAL_INIT;
356   return \"pfeq.dd %r0,%r1,%?f0\";
359 (define_insn "cmpnedf"
360   [(set (cc0) (ne (match_operand:DF 0 "reg_or_0_operand" "fG")
361                   (match_operand:DF 1 "reg_or_0_operand" "fG")))]
362   ""
363   "*
365   CC_STATUS_PARTIAL_INIT;
366   cc_status.flags |= CC_NEGATED;
367   return \"pfeq.dd %r1,%r0,%?f0\";
370 ;; NOTE:  The i860 Programmer's Reference Manual says that when we are
371 ;; doing (A < B) or (A > B) comparisons, we have to use pfgt for these
372 ;; in order to be IEEE compliant (in case a trap occurs during these
373 ;; operations).  Conversely, for (A <= B) or (A >= B) comparisons, we
374 ;; must use pfle to be IEEE compliant.
376 (define_insn "cmpltdf"
377   [(set (cc0) (lt (match_operand:DF 0 "reg_or_0_operand" "fG")
378                   (match_operand:DF 1 "reg_or_0_operand" "fG")))]
379   ""
380   "*
382   CC_STATUS_PARTIAL_INIT;
383   return \"pfgt.dd %r1,%r0,%?f0\";
386 (define_insn "cmpgtdf"
387   [(set (cc0) (gt (match_operand:DF 0 "reg_or_0_operand" "fG")
388                   (match_operand:DF 1 "reg_or_0_operand" "fG")))]
389   ""
390   "*
392   CC_STATUS_PARTIAL_INIT;
393   return \"pfgt.dd %r0,%r1,%?f0\";
396 ;; NOTE:  The pfle opcode *clears* the CC flag if the first operand is
397 ;; less than or equal to the second.  Thus, we have to set CC_NEGATED
398 ;; for the following two patterns.
400 (define_insn "cmpledf"
401   [(set (cc0) (le (match_operand:DF 0 "reg_or_0_operand" "fG")
402                   (match_operand:DF 1 "reg_or_0_operand" "fG")))]
403   ""
404   "*
406   CC_STATUS_PARTIAL_INIT;
407   cc_status.flags |= CC_NEGATED;
408   return \"pfle.dd %r0,%r1,%?f0\";
411 (define_insn "cmpgedf"
412   [(set (cc0) (ge (match_operand:DF 0 "reg_or_0_operand" "fG")
413                   (match_operand:DF 1 "reg_or_0_operand" "fG")))]
414   ""
415   "*
417   CC_STATUS_PARTIAL_INIT;
418   cc_status.flags |= CC_NEGATED;
419   return \"pfle.dd %r1,%r0,%?f0\";
422 ;; ------------------------------------------------------------------------
423 ;; Integer EQ/NE comparisons against constant values which will fit in the
424 ;; 16-bit immediate field of an instruction.  These are made by combining.
425 ;; ------------------------------------------------------------------------
427 (define_insn ""
428   [(set (cc0) (eq (zero_extend:SI (match_operand:HI 0 "load_operand" "m"))
429                   (match_operand:SI 1 "small_int" "I")))]
430   "INTVAL (operands[1]) >= 0"
431   "*
433   CC_STATUS_PARTIAL_INIT;
434   return \"ld.s %0,%?r31\;xor %1,%?r31,%?r0\";
437 (define_insn ""
438   [(set (cc0) (eq (match_operand:SI 0 "small_int" "I")
439                   (zero_extend:SI (match_operand:HI 1 "load_operand" "m"))))]
440   "INTVAL (operands[0]) >= 0"
441   "*
443   CC_STATUS_PARTIAL_INIT;
444   return \"ld.s %1,%?r31\;xor %0,%?r31,%?r0\";
447 ;; ------------------------------------------------------------------------
448 ;; Define the real conditional branch instructions.
449 ;; ------------------------------------------------------------------------
451 (define_insn "cbranch"
452   [(set (pc) (if_then_else (eq (cc0) (const_int 0))
453                            (label_ref (match_operand 0 "" ""))
454                            (pc)))]
455   ""
456   "*
458   if ((cc_prev_status.flags & CC_NEGATED) == 0)
459     return \"bnc %l0\";
460   else
461     return \"bc %l0\";
464 (define_insn "flipped_cbranch"
465   [(set (pc) (if_then_else (ne (cc0)
466                                (const_int 0))
467                            (pc)
468                            (label_ref (match_operand 0 "" ""))))]
469   ""
470   "*
472   if ((cc_prev_status.flags & CC_NEGATED) == 0)
473     return \"bnc %l0\";
474   else
475     return \"bc %l0\";
478 (define_insn "inverse_cbranch"
479   [(set (pc) (if_then_else (eq (cc0)
480                                (const_int 0))
481                            (pc)
482                            (label_ref (match_operand 0 "" ""))))]
483   ""
484   "*
486   if ((cc_prev_status.flags & CC_NEGATED) == 0)
487     return \"bc %l0\";
488   else
489     return \"bnc %l0\";
493 (define_insn "flipped_inverse_cbranch"
494   [(set (pc) (if_then_else (ne (cc0)
495                                (const_int 0))
496                            (label_ref (match_operand 0 "" ""))
497                            (pc)))]
498   ""
499   "*
501   if ((cc_prev_status.flags & CC_NEGATED) == 0)
502     return \"bc %l0\";
503   else
504     return \"bnc %l0\";
507 ;; Simple BTE/BTNE compare-and-branch insns made by combining.
508 ;; Note that it is wrong to add similar patterns for QI or HImode
509 ;; because bte/btne always compare the whole register.
511 (define_insn ""
512   [(set (pc)
513         (if_then_else (eq (match_operand:SI 0 "register_operand" "r")
514                           (match_operand:SI 1 "bte_operand" "rK"))
515                       (label_ref (match_operand 2 "" ""))
516                       (pc)))]
517   ""
518   "bte %1,%0,%2")
520 (define_insn ""
521   [(set (pc)
522         (if_then_else (ne (match_operand:SI 0 "register_operand" "r")
523                           (match_operand:SI 1 "bte_operand" "rK"))
524                       (label_ref (match_operand 2 "" ""))
525                       (pc)))]
526   ""
527   "btne %1,%0,%2")
529 (define_insn ""
530   [(set (pc)
531         (if_then_else (eq (match_operand:SI 0 "register_operand" "r")
532                           (match_operand:SI 1 "bte_operand" "rK"))
533                       (pc)
534                       (label_ref (match_operand 2 "" ""))))]
535   ""
536   "btne %1,%0,%2")
538 (define_insn ""
539   [(set (pc)
540         (if_then_else (ne (match_operand:SI 0 "register_operand" "r")
541                           (match_operand:SI 1 "bte_operand" "rK"))
542                       (pc)
543                       (label_ref (match_operand 2 "" ""))))]
544   ""
545   "bte %1,%0,%2")
547 ;; Load byte/halfword, zero-extend, & compare-and-branch insns.
548 ;; These are made by combining.
550 (define_insn ""
551   [(set (pc)
552         (if_then_else (eq (zero_extend:SI (match_operand:QI 0 "memory_operand" "m"))
553                           (match_operand:SI 1 "bte_operand" "K"))
554                       (label_ref (match_operand 2 "" ""))
555                       (pc)))
556    (match_scratch:SI 3 "=r")]
557   ""
558   "ld.b %0,%3;bte %1,%3,%2")
560 (define_insn ""
561   [(set (pc)
562         (if_then_else (ne (zero_extend:SI (match_operand:QI 0 "memory_operand" "m"))
563                           (match_operand:SI 1 "bte_operand" "K"))
564                       (label_ref (match_operand 2 "" ""))
565                       (pc)))
566    (match_scratch:SI 3 "=r")]
567   ""
568   "ld.b %0,%3;btne %1,%3,%2")
570 (define_insn ""
571   [(set (pc)
572         (if_then_else (eq (zero_extend:SI (match_operand:QI 0 "memory_operand" "m"))
573                           (match_operand:SI 1 "bte_operand" "K"))
574                       (pc)
575                       (label_ref (match_operand 2 "" ""))))
576    (match_scratch:SI 3 "=r")]
577   ""
578   "ld.b %0,%3;btne %1,%3,%2")
580 (define_insn ""
581   [(set (pc)
582         (if_then_else (ne (zero_extend:SI (match_operand:QI 0 "memory_operand" "m"))
583                           (match_operand:SI 1 "bte_operand" "K"))
584                       (pc)
585                       (label_ref (match_operand 2 "" ""))))
586    (match_scratch:SI 3 "=r")]
587   ""
588   "ld.b %0,%3;bte %1,%3,%2")
590 (define_insn ""
591   [(set (pc)
592         (if_then_else (eq (zero_extend:SI (match_operand:HI 0 "memory_operand" "m"))
593                           (match_operand:SI 1 "bte_operand" "K"))
594                       (label_ref (match_operand 2 "" ""))
595                       (pc)))
596    (match_scratch:SI 3 "=r")]
597   ""
598   "ld.s %0,%3;bte %1,%3,%2")
600 (define_insn ""
601   [(set (pc)
602         (if_then_else (ne (zero_extend:SI (match_operand:HI 0 "memory_operand" "m"))
603                           (match_operand:SI 1 "bte_operand" "K"))
604                       (label_ref (match_operand 2 "" ""))
605                       (pc)))
606    (match_scratch:SI 3 "=r")]
607   ""
608   "ld.s %0,%3;btne %1,%3,%2")
610 (define_insn ""
611   [(set (pc)
612         (if_then_else (eq (zero_extend:SI (match_operand:HI 0 "memory_operand" "m"))
613                           (match_operand:SI 1 "bte_operand" "K"))
614                       (pc)
615                       (label_ref (match_operand 2 "" ""))))
616    (match_scratch:SI 3 "=r")]
617   ""
618   "ld.s %0,%3;btne %1,%3,%2")
620 (define_insn ""
621   [(set (pc)
622         (if_then_else (ne (zero_extend:SI (match_operand:HI 0 "memory_operand" "m"))
623                           (match_operand:SI 1 "bte_operand" "K"))
624                       (pc)
625                       (label_ref (match_operand 2 "" ""))))
626    (match_scratch:SI 3 "=r")]
627   ""
628   "ld.s %0,%3;bte %1,%3,%2")
631 ;; Generation of conditionals.
633 ;; We save the compare operands in the cmpxx patterns and use then when
634 ;; we generate the branch.
636 (define_expand "cmpsi"
637   [(set (cc0) (compare (match_operand:SI 0 "register_operand" "")
638                        (match_operand:SI 1 "compare_operand" "")))]
639   ""
640   "
641 { i860_compare_op0 = operands[0];
642   i860_compare_op1 = operands[1];
643   DONE;
646 (define_expand "cmpsf"
647   [(set (cc0) (compare (match_operand:SF 0 "register_operand" "")
648                        (match_operand:SF 1 "register_operand" "")))]
649   ""
650   "
651 { i860_compare_op0 = operands[0];
652   i860_compare_op1 = operands[1];
653   DONE;
656 (define_expand "cmpdf"
657   [(set (cc0) (compare (match_operand:DF 0 "register_operand" "")
658                        (match_operand:DF 1 "register_operand" "")))]
659   ""
660   "
661 { i860_compare_op0 = operands[0];
662   i860_compare_op1 = operands[1];
663   DONE;
666 ;; These are the standard-named conditional branch patterns.
667 ;; Detailed comments are found in the first one only.
669 (define_expand "beq"
670   [(set (pc)
671         (if_then_else (eq (cc0)
672                           (const_int 0))
673                       (label_ref (match_operand 0 "" ""))
674                       (pc)))]
675   ""
676   "
678   /* Emit a single-condition compare insn according to
679      the type of operands and the condition to be tested.  */
681   if (GET_MODE_CLASS (GET_MODE (i860_compare_op0)) == MODE_INT)
682     emit_insn (gen_cmpeqsi (i860_compare_op0, i860_compare_op1));
683   else if (GET_MODE (i860_compare_op0) == SFmode)
684     emit_insn (gen_cmpeqsf (i860_compare_op0, i860_compare_op1));
685   else if (GET_MODE (i860_compare_op0) == DFmode)
686     emit_insn (gen_cmpeqdf (i860_compare_op0, i860_compare_op1));
687   else
688     abort ();
690   /* Emit branch-if-true.  */
692   emit_jump_insn (gen_flipped_inverse_cbranch (operands[0]));
693   DONE;
696 (define_expand "bne"
697   [(set (pc)
698         (if_then_else (ne (cc0)
699                           (const_int 0))
700                       (label_ref (match_operand 0 "" ""))
701                       (pc)))]
702   ""
703   "
705   if (GET_MODE_CLASS (GET_MODE (i860_compare_op0)) == MODE_INT)
706     emit_insn (gen_cmpeqsi (i860_compare_op0, i860_compare_op1));
707   else if (GET_MODE (i860_compare_op0) == SFmode)
708     emit_insn (gen_cmpeqsf (i860_compare_op0, i860_compare_op1));
709   else if (GET_MODE (i860_compare_op0) == DFmode)
710     emit_insn (gen_cmpeqdf (i860_compare_op0, i860_compare_op1));
711   else
712     abort ();
714   emit_jump_insn (gen_flipped_cbranch (operands[0]));
716   DONE;
719 (define_expand "bgt"
720   [(set (pc)
721         (if_then_else (gt (cc0)
722                           (const_int 0))
723                       (label_ref (match_operand 0 "" ""))
724                       (pc)))]
725   ""
726   "
728   if (GET_MODE_CLASS (GET_MODE (i860_compare_op0)) == MODE_INT)
729     emit_insn (gen_cmpgtsi (i860_compare_op0, i860_compare_op1));
730   else if (GET_MODE (i860_compare_op0) == SFmode)
731     emit_insn (gen_cmpgtsf (i860_compare_op0, i860_compare_op1));
732   else if (GET_MODE (i860_compare_op0) == DFmode)
733     emit_insn (gen_cmpgtdf (i860_compare_op0, i860_compare_op1));
734   else
735     abort ();
737   emit_jump_insn (gen_flipped_inverse_cbranch (operands[0]));
738   DONE;
741 (define_expand "blt"
742   [(set (pc)
743         (if_then_else (lt (cc0)
744                           (const_int 0))
745                       (label_ref (match_operand 0 "" ""))
746                       (pc)))]
747   ""
748   "
750   if (GET_MODE_CLASS (GET_MODE (i860_compare_op0)) == MODE_INT)
751     emit_insn (gen_cmpltsi (i860_compare_op0, i860_compare_op1));
752   else if (GET_MODE (i860_compare_op0) == SFmode)
753     emit_insn (gen_cmpltsf (i860_compare_op0, i860_compare_op1));
754   else if (GET_MODE (i860_compare_op0) == DFmode)
755     emit_insn (gen_cmpltdf (i860_compare_op0, i860_compare_op1));
756   else
757     abort ();
759   emit_jump_insn (gen_flipped_inverse_cbranch (operands[0]));
760   DONE;
763 (define_expand "ble"
764   [(set (pc)
765         (if_then_else (le (cc0)
766                           (const_int 0))
767                       (label_ref (match_operand 0 "" ""))
768                       (pc)))]
769   ""
770   "
772   if (GET_MODE_CLASS (GET_MODE (i860_compare_op0)) == MODE_INT)
773     {
774       emit_insn (gen_cmpgtsi (i860_compare_op0, i860_compare_op1));
775       emit_jump_insn (gen_flipped_cbranch (operands[0]));
776     }
777   else
778     {
779       if (GET_MODE (i860_compare_op0) == SFmode)
780         emit_insn (gen_cmplesf (i860_compare_op0, i860_compare_op1));
781       else if (GET_MODE (i860_compare_op0) == DFmode)
782         emit_insn (gen_cmpledf (i860_compare_op0, i860_compare_op1));
783       else
784         abort ();
785       emit_jump_insn (gen_flipped_inverse_cbranch (operands[0]));
786     }
787   DONE;
790 (define_expand "bge"
791   [(set (pc)
792         (if_then_else (ge (cc0)
793                           (const_int 0))
794                       (label_ref (match_operand 0 "" ""))
795                       (pc)))]
796   ""
797   "
799   if (GET_MODE_CLASS (GET_MODE (i860_compare_op0)) == MODE_INT)
800     {
801       emit_insn (gen_cmpltsi (i860_compare_op0, i860_compare_op1));
802       emit_jump_insn (gen_flipped_cbranch (operands[0]));
803     }
804   else
805     {
806       if (GET_MODE (i860_compare_op0) == SFmode)
807         emit_insn (gen_cmpgesf (i860_compare_op0, i860_compare_op1));
808       else if (GET_MODE (i860_compare_op0) == DFmode)
809         emit_insn (gen_cmpgedf (i860_compare_op0, i860_compare_op1));
810       else
811         abort ();
812       emit_jump_insn (gen_flipped_inverse_cbranch (operands[0]));
813     }
814   DONE;
817 (define_expand "bgtu"
818   [(set (pc)
819         (if_then_else (gtu (cc0)
820                            (const_int 0))
821                       (label_ref (match_operand 0 "" ""))
822                       (pc)))]
823   ""
824   "
826   if (GET_MODE_CLASS (GET_MODE (i860_compare_op0)) != MODE_INT)
827     abort ();
829   emit_insn (gen_cmpleusi (i860_compare_op0, i860_compare_op1));
830   emit_jump_insn (gen_flipped_cbranch (operands[0]));
831   DONE;
834 (define_expand "bltu"
835   [(set (pc)
836         (if_then_else (ltu (cc0)
837                            (const_int 0))
838                       (label_ref (match_operand 0 "" ""))
839                       (pc)))]
840   ""
841   "
843   if (GET_MODE_CLASS (GET_MODE (i860_compare_op0)) != MODE_INT)
844     abort ();
846   emit_insn (gen_cmpgeusi (i860_compare_op0, i860_compare_op1));
847   emit_jump_insn (gen_flipped_cbranch (operands[0]));
848   DONE;
851 (define_expand "bgeu"
852   [(set (pc)
853         (if_then_else (geu (cc0)
854                            (const_int 0))
855                       (label_ref (match_operand 0 "" ""))
856                       (pc)))]
857   ""
858   "
860   if (GET_MODE_CLASS (GET_MODE (i860_compare_op0)) != MODE_INT)
861     abort ();
863   emit_insn (gen_cmpgeusi (i860_compare_op0, i860_compare_op1));
864   emit_jump_insn (gen_flipped_inverse_cbranch (operands[0]));
865   DONE;
868 (define_expand "bleu"
869   [(set (pc)
870         (if_then_else (leu (cc0)
871                            (const_int 0))
872                       (label_ref (match_operand 0 "" ""))
873                       (pc)))]
874   ""
875   "
877   if (GET_MODE_CLASS (GET_MODE (i860_compare_op0)) != MODE_INT)
878     abort ();
880   emit_insn (gen_cmpleusi (i860_compare_op0, i860_compare_op1));
881   emit_jump_insn (gen_flipped_inverse_cbranch (operands[0]));
882   DONE;
885 ;; Move instructions
887 ;; Note that source operands for `mov' pseudo-instructions are no longer
888 ;; allowed (by the SVR4 assembler) to be "big" things, i.e. constants that
889 ;; won't fit in 16-bits.  (This includes any sort of a relocatable address
890 ;; also.)  Thus, we must use an explicit orh/or pair of instructions if
891 ;; the source operand is something "big".
893 (define_insn "movsi"
894   [(set (match_operand:SI 0 "general_operand" "=r,m,f")
895         (match_operand:SI 1 "general_operand" "rmif,rfJ,rmfJ"))]
896   ""
897   "*
899   if (GET_CODE (operands[0]) == MEM)
900     {
901       if (CONSTANT_ADDRESS_P (XEXP (operands[0], 0)))
902         return output_store (operands);
903       if (FP_REG_P (operands[1]))
904         return \"fst.l %1,%0\";
905       return \"st.l %r1,%0\";
906     }
907   if (GET_CODE (operands[1]) == MEM)
908     {
909       if (CONSTANT_ADDRESS_P (XEXP (operands[1], 0)))
910         return output_load (operands);
911       if (FP_REG_P (operands[0]))
912         return \"fld.l %1,%0\";
913       return \"ld.l %1,%0\";
914     }
915   if (FP_REG_P (operands[1]) && FP_REG_P (operands[0]))
916     return \"fmov.ss %1,%0\";
917   if (FP_REG_P (operands[1]))
918     return \"fxfr %1,%0\";
919   if (FP_REG_P (operands[0]) && operands[1] == const0_rtx)
920     return \"fmov.ss %?f0,%0\";
921   if (FP_REG_P (operands[0]))
922     return \"ixfr %1,%0\";
924   if (GET_CODE (operands[1]) == REG)
925     return \"shl %?r0,%1,%0\";
927   CC_STATUS_PARTIAL_INIT;
929   if (GET_CODE (operands[1]) == CONST_INT)
930     {
931       if((INTVAL (operands[1]) & 0xffff0000) == 0)
932         return \"or %L1,%?r0,%0\";
933       if((INTVAL (operands[1]) & 0x0000ffff) == 0)
934         return \"orh %H1,%?r0,%0\";
935     }
936   return \"orh %H1,%?r0,%0\;or %L1,%0,%0\";
939 (define_insn "movhi"
940   [(set (match_operand:HI 0 "general_operand" "=r,m,!*f,!r")
941         (match_operand:HI 1 "general_operand" "rmi,rJ,rJ*f,*f"))]
942   ""
943   "*
945   if (GET_CODE (operands[0]) == MEM)
946     {
947       if (CONSTANT_ADDRESS_P (XEXP (operands[0], 0)))
948         return output_store (operands);
949       return \"st.s %r1,%0\";
950     }
951   if (GET_CODE (operands[1]) == MEM)
952     {
953       if (CONSTANT_ADDRESS_P (XEXP (operands[1], 0)))
954         return output_load (operands);
955       return \"ld.s %1,%0\";
956     }
957   if (FP_REG_P (operands[1]) && FP_REG_P (operands[0]))
958     return \"fmov.ss %1,%0\";
959   if (FP_REG_P (operands[1]))
960     return \"fxfr %1,%0\";
961   if (FP_REG_P (operands[0]) && operands[1] == const0_rtx)
962     return \"fmov.ss %?f0,%0\";
963   if (FP_REG_P (operands[0]))
964     return \"ixfr %1,%0\";
966   if (GET_CODE (operands[1]) == REG)
967     return \"shl %?r0,%1,%0\";
969   CC_STATUS_PARTIAL_INIT;
971   return \"or %L1,%?r0,%0\";
974 (define_insn "movqi"
975   [(set (match_operand:QI 0 "general_operand" "=r,m,!*f,!r")
976         (match_operand:QI 1 "general_operand" "rmi,rJ,rJ*f,*f"))]
977   ""
978   "*
980   if (GET_CODE (operands[0]) == MEM)
981     {
982       if (CONSTANT_ADDRESS_P (XEXP (operands[0], 0)))
983         return output_store (operands);
984       return \"st.b %r1,%0\";
985     }
986   if (GET_CODE (operands[1]) == MEM)
987     {
988       if (CONSTANT_ADDRESS_P (XEXP (operands[1], 0)))
989         return output_load (operands);
990       return \"ld.b %1,%0\";
991     }
992   if (FP_REG_P (operands[1]) && FP_REG_P (operands[0]))
993     return \"fmov.ss %1,%0\";
994   if (FP_REG_P (operands[1]))
995     return \"fxfr %1,%0\";
996   if (FP_REG_P (operands[0]) && operands[1] == const0_rtx)
997     return \"fmov.ss %?f0,%0\";
998   if (FP_REG_P (operands[0]))
999     return \"ixfr %1,%0\";
1001   if (GET_CODE (operands[1]) == REG)
1002     return \"shl %?r0,%1,%0\";
1004   CC_STATUS_PARTIAL_INIT;
1006   return \"or %L1,%?r0,%0\";
1009 ;; The definition of this insn does not really explain what it does,
1010 ;; but it should suffice
1011 ;; that anything generated as this insn will be recognized as one
1012 ;; and that it won't successfully combine with anything.
1013 (define_expand "movmemsi"
1014   [(parallel [(set (match_operand:BLK 0 "general_operand" "")
1015                    (match_operand:BLK 1 "general_operand" ""))
1016               (use (match_operand:SI 2 "nonmemory_operand" ""))
1017               (use (match_operand:SI 3 "immediate_operand" ""))
1018               (clobber (match_dup 4))
1019               (clobber (match_dup 5))
1020               (clobber (match_dup 6))
1021               (clobber (match_dup 7))
1022               (clobber (match_dup 8))])]
1023   ""
1024   "
1026   operands[4] = gen_reg_rtx (SImode);
1027   operands[5] = gen_reg_rtx (SImode);
1028   operands[6] = gen_reg_rtx (SImode);
1029   operands[7] = copy_to_mode_reg (SImode, XEXP (operands[0], 0));
1030   operands[8] = copy_to_mode_reg (SImode, XEXP (operands[1], 0));
1032   operands[0] = replace_equiv_address (operands[0], operands[7]);
1033   operands[1] = replace_equiv_address (operands[1], operands[8]);
1036 (define_insn ""
1037   [(set (mem:BLK (match_operand:SI 0 "register_operand" "r"))
1038         (mem:BLK (match_operand:SI 1 "register_operand" "r")))
1039    (use (match_operand:SI 2 "general_operand" "rn"))
1040    (use (match_operand:SI 3 "immediate_operand" "i"))
1041    (clobber (match_operand:SI 4 "register_operand" "=r"))
1042    (clobber (match_operand:SI 5 "register_operand" "=r"))
1043    (clobber (match_operand:SI 6 "register_operand" "=r"))
1044    (clobber (match_dup 0))
1045    (clobber (match_dup 1))]
1046   ""
1047   "* return output_block_move (operands);")
1049 ;; Floating point move insns
1051 ;; This pattern forces (set (reg:DF ...) (const_double ...))
1052 ;; to be reloaded by putting the constant into memory.
1053 ;; It must come before the more general movdf pattern.
1054 (define_insn ""
1055   [(set (match_operand:DF 0 "general_operand" "=r,f,o")
1056         (match_operand:DF 1 "" "mG,m,G"))]
1057   "GET_CODE (operands[1]) == CONST_DOUBLE"
1058   "*
1060   if (FP_REG_P (operands[0]) || operands[1] == CONST0_RTX (DFmode))
1061     return output_fp_move_double (operands);
1062   return output_move_double (operands);
1065 (define_insn "movdf"
1066   [(set (match_operand:DF 0 "general_operand" "=*rm,*r,?f,?*rm")
1067         (match_operand:DF 1 "general_operand" "*r,m,*rfmG,f"))]
1068   ""
1069   "*
1071   if (GET_CODE (operands[0]) == MEM
1072       && CONSTANT_ADDRESS_P (XEXP (operands[0], 0)))
1073     return output_store (operands);
1074   if (GET_CODE (operands[1]) == MEM
1075       && CONSTANT_ADDRESS_P (XEXP (operands[1], 0)))
1076     return output_load (operands);
1078   if (FP_REG_P (operands[0]) || FP_REG_P (operands[1]))
1079     return output_fp_move_double (operands);
1080   return output_move_double (operands);
1083 (define_insn "movdi"
1084   [(set (match_operand:DI 0 "general_operand" "=rm,r,?f,?rm")
1085         (match_operand:DI 1 "general_operand" "r,miF,rfmG,f"))]
1086   ""
1087   "*
1089   if (GET_CODE (operands[0]) == MEM
1090       && CONSTANT_ADDRESS_P (XEXP (operands[0], 0)))
1091     return output_store (operands);
1092   if (GET_CODE (operands[1]) == MEM
1093       && CONSTANT_ADDRESS_P (XEXP (operands[1], 0)))
1094     return output_load (operands);
1096   /* ??? How can we have a DFmode arg here with DImode above?  */
1097   if (FP_REG_P (operands[0]) && operands[1] == CONST0_RTX (DFmode))
1098     return \"fmov.dd %?f0,%0\";
1100   if (FP_REG_P (operands[0]) || FP_REG_P (operands[1]))
1101     return output_fp_move_double (operands);
1102   return output_move_double (operands);
1105 ;; The alternative m/r is separate from m/f
1106 ;; The first alternative is separate from the second for the same reason.
1107 (define_insn "movsf"
1108   [(set (match_operand:SF 0 "general_operand" "=*rf,*rf,*r,m,m")
1109         (match_operand:SF 1 "general_operand" "*r,fmG,F,*r,f"))]
1110   ""
1111   "*
1113   if (GET_CODE (operands[0]) == MEM
1114       && CONSTANT_ADDRESS_P (XEXP (operands[0], 0)))
1115     return output_store (operands);
1116   if (GET_CODE (operands[1]) == MEM
1117       && CONSTANT_ADDRESS_P (XEXP (operands[1], 0)))
1118     return output_load (operands);
1119   if (FP_REG_P (operands[0]))
1120     {
1121       if (FP_REG_P (operands[1]))
1122         return \"fmov.ss %1,%0\";
1123       if (GET_CODE (operands[1]) == REG)
1124         return \"ixfr %1,%0\";
1125       if (operands[1] == CONST0_RTX (SFmode))
1126         return \"fmov.ss %?f0,%0\";
1127       if (CONSTANT_ADDRESS_P (XEXP (operands[1], 0)))
1128         {
1129           if (! ((cc_prev_status.flags & CC_KNOW_HI_R31)
1130                  && (cc_prev_status.flags & CC_HI_R31_ADJ)
1131                  && cc_prev_status.mdep == XEXP(operands[1],0)))
1132             {
1133               CC_STATUS_INIT;
1134               cc_status.flags |= CC_KNOW_HI_R31 | CC_HI_R31_ADJ;
1135               cc_status.mdep = XEXP (operands[1], 0);
1136               return \"orh %h1,%?r0,%?r31\;fld.l %L1(%?r31),%0\";
1137             }
1138           return \"fld.l %L1(%?r31),%0\";
1139         }
1140       return \"fld.l %1,%0\";
1141     }
1142   if (FP_REG_P (operands[1]) || GET_CODE (operands[1]) == CONST_DOUBLE)
1143     {
1144       if (GET_CODE (operands[0]) == REG && FP_REG_P (operands[1]))
1145         return \"fxfr %1,%0\";
1146       if (GET_CODE (operands[0]) == REG)
1147         {
1148           CC_STATUS_PARTIAL_INIT;
1149           if (GET_CODE (operands[1]) == CONST_DOUBLE)
1150             {
1151               register unsigned long ul;
1153               ul = sfmode_constant_to_ulong (operands[1]);
1154               if ((ul & 0x0000ffff) == 0)
1155                 return \"orh %H1,%?r0,%0\";
1156               if ((ul & 0xffff0000) == 0)
1157                 return \"or %L1,%?r0,%0\";
1158             }
1159           return \"orh %H1,%?r0,%0\;or %L1,%0,%0\";
1160         }
1161       /* Now operand 0 must be memory.
1162          If operand 1 is CONST_DOUBLE, its value must be 0.  */
1163       if (CONSTANT_ADDRESS_P (XEXP (operands[0], 0)))
1164         {
1165           if (! ((cc_prev_status.flags & CC_KNOW_HI_R31)
1166                  && (cc_prev_status.flags & CC_HI_R31_ADJ)
1167                  && XEXP (operands[0], 0) == cc_prev_status.mdep))
1168             {
1169               CC_STATUS_INIT;
1170               cc_status.flags |= CC_KNOW_HI_R31 | CC_HI_R31_ADJ;
1171               cc_status.mdep = XEXP (operands[0], 0);
1172               output_asm_insn (\"orh %h0,%?r0,%?r31\", operands);
1173             }
1174           return \"fst.l %r1,%L0(%?r31)\";
1175         }
1176       return \"fst.l %r1,%0\";
1177     }
1178   if (GET_CODE (operands[0]) == MEM)
1179     return \"st.l %r1,%0\";
1180   if (GET_CODE (operands[1]) == MEM)
1181     return \"ld.l %1,%0\";
1182   if (operands[1] == CONST0_RTX (SFmode))
1183     return \"shl %?r0,%?r0,%0\";
1184   return \"mov %1,%0\";
1187 ;; Special load insns for REG+REG addresses.
1188 ;; Such addresses are not "legitimate" because st rejects them.
1190 (define_insn ""
1191   [(set (match_operand:DF 0 "register_operand" "=rf")
1192         (match_operand:DF 1 "indexed_operand" "m"))]
1193   ""
1194   "*
1196   if (FP_REG_P (operands[0]))
1197     return output_fp_move_double (operands);
1198   return output_move_double (operands);
1201 (define_insn ""
1202   [(set (match_operand:SF 0 "register_operand" "=rf")
1203         (match_operand:SF 1 "indexed_operand" "m"))]
1204   ""
1205   "*
1207   if (FP_REG_P (operands[0]))
1208     return \"fld.l %1,%0\";
1209   return \"ld.l %1,%0\";
1212 (define_insn ""
1213   [(set (match_operand:SI 0 "register_operand" "=rf")
1214         (match_operand:SI 1 "indexed_operand" "m"))]
1215   ""
1216   "*
1218   if (FP_REG_P (operands[0]))
1219     return \"fld.l %1,%0\";
1220   return \"ld.l %1,%0\";
1223 (define_insn ""
1224   [(set (match_operand:HI 0 "register_operand" "=r")
1225         (match_operand:HI 1 "indexed_operand" "m"))]
1226   ""
1227   "ld.s %1,%0")
1229 (define_insn ""
1230   [(set (match_operand:QI 0 "register_operand" "=r")
1231         (match_operand:QI 1 "indexed_operand" "m"))]
1232   ""
1233   "ld.b %1,%0")
1235 ;; Likewise for floating-point store insns.
1237 (define_insn ""
1238   [(set (match_operand:DF 0 "indexed_operand" "=m")
1239         (match_operand:DF 1 "register_operand" "f"))]
1240   ""
1241   "fst.d %1,%0")
1243 (define_insn ""
1244   [(set (match_operand:SF 0 "indexed_operand" "=m")
1245         (match_operand:SF 1 "register_operand" "f"))]
1246   ""
1247   "fst.l %1,%0")
1249 ;;- truncation instructions
1250 (define_insn "truncsiqi2"
1251   [(set (match_operand:QI 0 "general_operand" "=g")
1252         (truncate:QI
1253          (match_operand:SI 1 "register_operand" "r")))]
1254   ""
1255   "*
1257   if (GET_CODE (operands[0]) == MEM)
1258   {
1259     if (CONSTANT_ADDRESS_P (XEXP (operands[0], 0)))
1260       {
1261         if (! ((cc_prev_status.flags & CC_KNOW_HI_R31)
1262                && (cc_prev_status.flags & CC_HI_R31_ADJ)
1263                && XEXP (operands[0], 0) == cc_prev_status.mdep))
1264           {
1265             CC_STATUS_INIT;
1266             cc_status.flags |= CC_KNOW_HI_R31 | CC_HI_R31_ADJ;
1267             cc_status.mdep = XEXP (operands[0], 0);
1268             output_asm_insn (\"orh %h0,%?r0,%?r31\", operands);
1269           }
1270         return \"st.b %1,%L0(%?r31)\";
1271       }
1272     else
1273       return \"st.b %1,%0\";
1274   }
1275   return \"shl %?r0,%1,%0\";
1278 (define_insn "trunchiqi2"
1279   [(set (match_operand:QI 0 "general_operand" "=g")
1280         (truncate:QI
1281          (match_operand:HI 1 "register_operand" "r")))]
1282   ""
1283   "*
1285   if (GET_CODE (operands[0]) == MEM)
1286   {
1287     if (CONSTANT_ADDRESS_P (XEXP (operands[0], 0)))
1288       {
1289         if (! ((cc_prev_status.flags & CC_KNOW_HI_R31)
1290                && (cc_prev_status.flags & CC_HI_R31_ADJ)
1291                && XEXP (operands[0], 0) == cc_prev_status.mdep))
1292           {
1293             CC_STATUS_INIT;
1294             cc_status.flags |= CC_KNOW_HI_R31 | CC_HI_R31_ADJ;
1295             cc_status.mdep = XEXP (operands[0], 0);
1296             output_asm_insn (\"orh %h0,%?r0,%?r31\", operands);
1297           }
1298         return \"st.b %1,%L0(%?r31)\";
1299       }
1300     else
1301       return \"st.b %1,%0\";
1302   }
1303   return \"shl %?r0,%1,%0\";
1306 (define_insn "truncsihi2"
1307   [(set (match_operand:HI 0 "general_operand" "=g")
1308         (truncate:HI
1309          (match_operand:SI 1 "register_operand" "r")))]
1310   ""
1311   "*
1313   if (GET_CODE (operands[0]) == MEM)
1314   {
1315     if (CONSTANT_ADDRESS_P (XEXP (operands[0], 0)))
1316       {
1317         if (! ((cc_prev_status.flags & CC_KNOW_HI_R31)
1318                && (cc_prev_status.flags & CC_HI_R31_ADJ)
1319                && XEXP (operands[0], 0) == cc_prev_status.mdep))
1320           {
1321             CC_STATUS_INIT;
1322             cc_status.flags |= CC_KNOW_HI_R31 | CC_HI_R31_ADJ;
1323             cc_status.mdep = XEXP (operands[0], 0);
1324             output_asm_insn (\"orh %h0,%?r0,%?r31\", operands);
1325           }
1326         return \"st.s %1,%L0(%?r31)\";
1327       }
1328     else
1329       return \"st.s %1,%0\";
1330   }
1331   return \"shl %?r0,%1,%0\";
1334 ;;- zero extension instructions
1336 (define_insn "zero_extendhisi2"
1337   [(set (match_operand:SI 0 "register_operand" "=r")
1338         (zero_extend:SI
1339          (match_operand:HI 1 "register_operand" "r")))]
1340   ""
1341   "*
1343   CC_STATUS_PARTIAL_INIT;
1344   return \"and 0xffff,%1,%0\";
1347 (define_insn "zero_extendqihi2"
1348   [(set (match_operand:HI 0 "register_operand" "=r")
1349         (zero_extend:HI
1350          (match_operand:QI 1 "register_operand" "r")))]
1351   ""
1352   "*
1354   CC_STATUS_PARTIAL_INIT;
1355   return \"and 0xff,%1,%0\";
1358 (define_insn "zero_extendqisi2"
1359   [(set (match_operand:SI 0 "register_operand" "=r")
1360         (zero_extend:SI
1361          (match_operand:QI 1 "register_operand" "r")))]
1362   ""
1363   "*
1365   CC_STATUS_PARTIAL_INIT;
1366   return \"and 0xff,%1,%0\";
1369 ;; Sign extension instructions.
1371 (define_insn ""
1372   [(set (match_operand:SI 0 "register_operand" "=r")
1373         (sign_extend:SI
1374          (match_operand:HI 1 "indexed_operand" "m")))]
1375   ""
1376   "ld.s %1,%0")
1378 (define_insn ""
1379   [(set (match_operand:HI 0 "register_operand" "=r")
1380         (sign_extend:HI
1381          (match_operand:QI 1 "indexed_operand" "m")))]
1382   ""
1383   "ld.b %1,%0")
1385 (define_insn ""
1386   [(set (match_operand:SI 0 "register_operand" "=r")
1387         (sign_extend:SI
1388          (match_operand:QI 1 "indexed_operand" "m")))]
1389   ""
1390   "ld.b %1,%0")
1392 (define_insn "extendhisi2"
1393   [(set (match_operand:SI 0 "register_operand" "=r")
1394         (sign_extend:SI
1395          (match_operand:HI 1 "nonimmediate_operand" "mr")))]
1396   ""
1397   "*
1399   if (REG_P (operands[1]))
1400     return \"shl 16,%1,%0\;shra 16,%0,%0\";
1401   if (GET_CODE (operands[1]) == CONST_INT)
1402     abort ();
1403   if (CONSTANT_ADDRESS_P (XEXP (operands[1], 0)))
1404     {
1405       CC_STATUS_INIT;
1406       cc_status.flags |= CC_KNOW_HI_R31 | CC_HI_R31_ADJ;
1407       cc_status.mdep = XEXP (operands[1], 0);
1408       return \"orh %h1,%?r0,%?r31\;ld.s %L1(%?r31),%0\";
1409     }
1410   else
1411     return \"ld.s %1,%0\";
1414 (define_insn "extendqihi2"
1415   [(set (match_operand:HI 0 "register_operand" "=r")
1416         (sign_extend:HI
1417          (match_operand:QI 1 "nonimmediate_operand" "mr")))]
1418   ""
1419   "*
1421   if (REG_P (operands[1]))
1422     return \"shl 24,%1,%0\;shra 24,%0,%0\";
1423   if (GET_CODE (operands[1]) == CONST_INT)
1424     abort ();
1425   if (CONSTANT_ADDRESS_P (XEXP (operands[1], 0)))
1426     {
1427       CC_STATUS_INIT;
1428       cc_status.flags |= CC_KNOW_HI_R31 | CC_HI_R31_ADJ;
1429       cc_status.mdep = XEXP (operands[1], 0);
1430       return \"orh %h1,%?r0,%?r31\;ld.b %L1(%?r31),%0\";
1431     }
1432   else
1433     return \"ld.b %1,%0\";
1436 (define_insn "extendqisi2"
1437   [(set (match_operand:SI 0 "register_operand" "=r")
1438         (sign_extend:SI
1439          (match_operand:QI 1 "nonimmediate_operand" "mr")))]
1440   ""
1441   "*
1443   if (REG_P (operands[1]))
1444     return \"shl 24,%1,%0\;shra 24,%0,%0\";
1445   if (GET_CODE (operands[1]) == CONST_INT)
1446     abort ();
1447   if (CONSTANT_ADDRESS_P (XEXP (operands[1], 0)))
1448     {
1449       CC_STATUS_INIT;
1450       cc_status.flags |= CC_KNOW_HI_R31 | CC_HI_R31_ADJ;
1451       cc_status.mdep = XEXP (operands[1], 0);
1452       return \"orh %h1,%?r0,%?r31\;ld.b %L1(%?r31),%0\";
1453     }
1454   else
1455     return \"ld.b %1,%0\";
1458 ;; Signed bitfield extractions come out looking like
1459 ;;      (shiftrt (sign_extend (shift <Y> <C1>)) <C2>)
1460 ;; which we expand poorly as four shift insns.
1461 ;; These patterns yield two shifts:
1462 ;;      (shiftrt (shift <Y> <C3>) <C4>)
1463 (define_insn ""
1464   [(set (match_operand:SI 0 "register_operand" "=r")
1465         (ashiftrt:SI
1466          (sign_extend:SI
1467           (match_operand:QI 1 "register_operand" "r"))
1468          (match_operand:SI 2 "logic_int" "n")))]
1469   "INTVAL (operands[2]) < 8"
1470   "*
1472   return \"shl 24,%1,%0\;shra 24+%2,%0,%0\";
1475 (define_insn ""
1476   [(set (match_operand:SI 0 "register_operand" "=r")
1477         (ashiftrt:SI
1478          (sign_extend:SI
1479           (subreg:QI (ashift:SI (match_operand:SI 1 "register_operand" "r")
1480                                 (match_operand:SI 2 "logic_int" "n")) 0))
1481          (match_operand:SI 3 "logic_int" "n")))]
1482   "INTVAL (operands[3]) < 8"
1483   "*
1485   return \"shl 0x18+%2,%1,%0\;shra 0x18+%3,%0,%0\";
1488 (define_insn ""
1489   [(set (match_operand:SI 0 "register_operand" "=r")
1490         (ashiftrt:SI
1491          (sign_extend:SI
1492           (ashift:QI (match_operand:QI 1 "register_operand" "r")
1493                      (match_operand:QI 2 "logic_int" "n")))
1494          (match_operand:SI 3 "logic_int" "n")))]
1495   "INTVAL (operands[3]) < 8"
1496   "*
1498   return \"shl 0x18+%2,%1,%0\;shra 0x18+%3,%0,%0\";
1501 ;; Special patterns for optimizing bit-field instructions.
1503 ;; First two patterns are for bitfields that came from memory
1504 ;; testing only the high bit.  They work with old combiner.
1506 (define_insn ""
1507   [(set (cc0)
1508         (eq (zero_extend:SI (subreg:QI (lshiftrt:SI (match_operand:SI 0 "register_operand" "r")
1509                                                     (const_int 7)) 0))
1510             (const_int 0)))]
1511   ""
1512   "*
1514   CC_STATUS_PARTIAL_INIT;
1515   return \"and 128,%0,%?r0\";
1518 (define_insn ""
1519   [(set (cc0)
1520         (eq (sign_extend:SI (subreg:QI (ashiftrt:SI (match_operand:SI 0 "register_operand" "r")
1521                                                     (const_int 7)) 0))
1522             (const_int 0)))]
1523   ""
1524   "*
1526   CC_STATUS_PARTIAL_INIT;
1527   return \"and 128,%0,%?r0\";
1530 ;; The next two patterns are good for bitfields coming from memory
1531 ;; (via pseudo-register) or from a register, though this optimization
1532 ;; is only good for values contained wholly within the bottom 13 bits.
1533 (define_insn ""
1534   [(set (cc0)
1535         (eq 
1536          (and:SI (lshiftrt:SI (match_operand:SI 0 "register_operand" "r")
1537                               (match_operand:SI 1 "logic_int" "n"))
1538                  (match_operand:SI 2 "logic_int" "n"))
1539          (const_int 0)))]
1540   "LOGIC_INTVAL (INTVAL (operands[2]) << INTVAL (operands[1]))"
1541   "*
1543   CC_STATUS_PARTIAL_INIT;
1544   operands[2] = GEN_INT (INTVAL (operands[2]) << INTVAL (operands[1]));
1545   return \"and %2,%0,%?r0\";
1548 (define_insn ""
1549   [(set (cc0)
1550         (eq 
1551          (and:SI (ashiftrt:SI (match_operand:SI 0 "register_operand" "r")
1552                               (match_operand:SI 1 "logic_int" "n"))
1553                  (match_operand:SI 2 "logic_int" "n"))
1554          (const_int 0)))]
1555   "LOGIC_INTVAL (INTVAL (operands[2]) << INTVAL (operands[1]))"
1556   "*
1558   CC_STATUS_PARTIAL_INIT;
1559   operands[2] = GEN_INT (INTVAL (operands[2]) << INTVAL (operands[1]));
1560   return \"and %2,%0,%?r0\";
1563 ;; Conversions between float and double.
1565 (define_insn "extendsfdf2"
1566   [(set (match_operand:DF 0 "register_operand" "=f")
1567         (float_extend:DF
1568          (match_operand:SF 1 "register_operand" "f")))]
1569   ""
1570   "fmov.sd %1,%0")
1572 (define_insn "truncdfsf2"
1573   [(set (match_operand:SF 0 "register_operand" "=f")
1574         (float_truncate:SF
1575          (match_operand:DF 1 "register_operand" "f")))]
1576   ""
1577   "fmov.ds %1,%0")
1579 ;; Conversion between fixed point and floating point.
1580 ;; Note that among the fix-to-float insns
1581 ;; the ones that start with SImode come first.
1582 ;; That is so that an operand that is a CONST_INT
1583 ;; (and therefore lacks a specific machine mode)
1584 ;; will be recognized as SImode (which is always valid)
1585 ;; rather than as QImode or HImode.
1587 ;; This pattern forces (set (reg:SF ...) (float:SF (const_int ...)))
1588 ;; to be reloaded by putting the constant into memory.
1589 ;; It must come before the more general floatsisf2 pattern.
1590 (define_expand "floatsidf2"
1591   [(set (match_dup 2) (match_dup 3))
1592    (set (match_dup 4) (xor:SI (match_operand:SI 1 "register_operand" "")
1593                               (const_int -2147483648)))
1594    (set (match_dup 5) (match_dup 3))
1595    (set (subreg:SI (match_dup 5) 0) (match_dup 4))
1596    (set (match_operand:DF 0 "register_operand" "")
1597         (minus:DF (match_dup 5) (match_dup 2)))]
1598   ""
1599   "
1601   REAL_VALUE_TYPE d;
1602   /* 4503601774854144 is  (1 << 30) * ((1 << 22) + (1 << 1)).  */
1603   d = REAL_VALUE_ATOF (\"4503601774854144\", DFmode);
1604   operands[2] = gen_reg_rtx (DFmode);
1605   operands[3] = CONST_DOUBLE_FROM_REAL_VALUE (d, DFmode);
1606   operands[4] = gen_reg_rtx (SImode);
1607   operands[5] = gen_reg_rtx (DFmode);
1610 ;; Floating to fixed conversion.
1612 (define_expand "fix_truncdfsi2"
1613   ;; This first insn produces a double-word value
1614   ;; in which only the low word is valid.
1615   [(set (match_dup 2)
1616         (fix:DI (fix:DF (match_operand:DF 1 "register_operand" "f"))))
1617    (set (match_operand:SI 0 "register_operand" "=f")
1618         (subreg:SI (match_dup 2) 0))]
1619   ""
1620   "
1622   operands[2] = gen_reg_rtx (DImode);
1625 ;; Recognize the first insn generated above.
1626 ;; This RTL looks like a fix_truncdfdi2 insn,
1627 ;; but we don't call it that, because only 32 bits
1628 ;; of the result are valid.
1629 ;; This pattern will work for the intended purposes 
1630 ;; as long as we do not have any fixdfdi2 or fix_truncdfdi2.
1631 (define_insn ""
1632   [(set (match_operand:DI 0 "register_operand" "=f")
1633         (fix:DI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
1634   ""
1635   "ftrunc.dd %1,%0")
1637 (define_expand "fix_truncsfsi2"
1638   ;; This first insn produces a double-word value
1639   ;; in which only the low word is valid.
1640   [(set (match_dup 2)
1641         (fix:DI (fix:SF (match_operand:SF 1 "register_operand" "f"))))
1642    (set (match_operand:SI 0 "register_operand" "=f")
1643         (subreg:SI (match_dup 2) 0))]
1644   ""
1645   "
1647   operands[2] = gen_reg_rtx (DImode);
1650 ;; Recognize the first insn generated above.
1651 ;; This RTL looks like a fix_truncsfdi2 insn,
1652 ;; but we don't call it that, because only 32 bits
1653 ;; of the result are valid.
1654 ;; This pattern will work for the intended purposes 
1655 ;; as long as we do not have any fixsfdi2 or fix_truncsfdi2.
1656 (define_insn ""
1657   [(set (match_operand:DI 0 "register_operand" "=f")
1658         (fix:DI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
1659   ""
1660   "ftrunc.sd %1,%0")
1662 ;;- arithmetic instructions
1664 (define_insn "addsi3"
1665   [(set (match_operand:SI 0 "register_operand" "=r,*f")
1666         (plus:SI (match_operand:SI 1 "nonmemory_operand" "%r,*f")
1667                  (match_operand:SI 2 "arith_operand" "rI,*f")))]
1668   ""
1669   "*
1671   if (which_alternative == 1)
1672     return \"fiadd.ss %2,%1,%0\";
1673   CC_STATUS_PARTIAL_INIT;
1674   return \"addu %2,%1,%0\";
1677 (define_insn "adddi3"
1678   [(set (match_operand:DI 0 "register_operand" "=f")
1679         (plus:DI (match_operand:DI 1 "register_operand" "%f")
1680                  (match_operand:DI 2 "register_operand" "f")))]
1681   ""
1682   "fiadd.dd %1,%2,%0")
1684 (define_insn "subsi3"
1685   [(set (match_operand:SI 0 "register_operand" "=r,r,*f")
1686         (minus:SI (match_operand:SI 1 "register_operand" "r,I,*f")
1687                   (match_operand:SI 2 "arith_operand" "rI,r,*f")))]
1688   ""
1689   "*
1691   if (which_alternative == 2)
1692     return \"fisub.ss %1,%2,%0\";
1693   CC_STATUS_PARTIAL_INIT;
1694   if (REG_P (operands[2]))
1695     return \"subu %1,%2,%0\";
1696   operands[2] = GEN_INT (- INTVAL (operands[2]));
1697   return \"addu %2,%1,%0\";
1700 (define_insn "subdi3"
1701   [(set (match_operand:DI 0 "register_operand" "=f")
1702         (minus:DI (match_operand:DI 1 "register_operand" "f")
1703                   (match_operand:DI 2 "register_operand" "f")))]
1704   ""
1705   "fisub.dd %1,%2,%0")
1707 (define_expand "mulsi3"
1708   [(set (subreg:SI (match_dup 4) 0) (match_operand:SI 1 "general_operand" ""))
1709    (set (subreg:SI (match_dup 5) 0) (match_operand:SI 2 "general_operand" ""))
1710    (clobber (match_dup 3))
1711    (set (subreg:SI (match_dup 3) 0)
1712         (mult:SI (subreg:SI (match_dup 4) 0) (subreg:SI (match_dup 5) 0)))
1713    (set (match_operand:SI 0 "register_operand" "") (subreg:SI (match_dup 3) 0))]
1714   ""
1715   "
1717   if (WORDS_BIG_ENDIAN)
1718     emit_insn (gen_mulsi3_big (operands[0], operands[1], operands[2]));
1719   else
1720     emit_insn (gen_mulsi3_little (operands[0], operands[1], operands[2]));
1721   DONE;
1724 (define_expand "mulsi3_little"
1725   [(set (subreg:SI (match_dup 4) 0) (match_operand:SI 1 "general_operand" ""))
1726    (set (subreg:SI (match_dup 5) 0) (match_operand:SI 2 "general_operand" ""))
1727    (clobber (match_dup 3))
1728    (set (subreg:SI (match_dup 3) 0)
1729         (mult:SI (subreg:SI (match_dup 4) 0) (subreg:SI (match_dup 5) 0)))
1730    (set (match_operand:SI 0 "register_operand" "") (subreg:SI (match_dup 3) 0))]
1731   "! WORDS_BIG_ENDIAN"
1732   "
1734   operands[3] = gen_reg_rtx (DImode);
1735   operands[4] = gen_reg_rtx (DImode);
1736   operands[5] = gen_reg_rtx (DImode);
1739 (define_expand "mulsi3_big"
1740   [(set (subreg:SI (match_dup 4) 4) (match_operand:SI 1 "general_operand" ""))
1741    (set (subreg:SI (match_dup 5) 4) (match_operand:SI 2 "general_operand" ""))
1742    (clobber (match_dup 3))
1743    (set (subreg:SI (match_dup 3) 4)
1744         (mult:SI (subreg:SI (match_dup 4) 4) (subreg:SI (match_dup 5) 4)))
1745    (set (match_operand:SI 0 "register_operand" "") (subreg:SI (match_dup 3) 4))]
1746   "WORDS_BIG_ENDIAN"
1747   "
1749   operands[3] = gen_reg_rtx (DImode);
1750   operands[4] = gen_reg_rtx (DImode);
1751   operands[5] = gen_reg_rtx (DImode);
1754 (define_insn ""
1755   [(set (subreg:SI (match_operand:DI 0 "register_operand" "=f") 0)
1756         (mult:SI (subreg:SI (match_operand:DI 1 "register_operand" "f") 0)
1757                  (subreg:SI (match_operand:DI 2 "register_operand" "f") 0)))]
1758   "! WORDS_BIG_ENDIAN"
1759   "fmlow.dd %2,%1,%0")
1761 (define_insn ""
1762   [(set (subreg:SI (match_operand:DI 0 "register_operand" "=f") 4)
1763         (mult:SI (subreg:SI (match_operand:DI 1 "register_operand" "f") 4)
1764                  (subreg:SI (match_operand:DI 2 "register_operand" "f") 4)))]
1765   "WORDS_BIG_ENDIAN"
1766   "fmlow.dd %2,%1,%0")
1768 ;;- and instructions (with compliment also)                        
1769 (define_insn "andsi3"
1770   [(set (match_operand:SI 0 "register_operand" "=r")
1771         (and:SI (match_operand:SI 1 "nonmemory_operand" "%r")
1772                 (match_operand:SI 2 "nonmemory_operand" "rL")))]
1773   ""
1774   "*
1776   rtx xop[3];
1778   CC_STATUS_PARTIAL_INIT;
1779   if (REG_P (operands[2]) || LOGIC_INT (operands[2]))
1780     return \"and %2,%1,%0\";
1781   if ((INTVAL (operands[2]) & 0xffff) == 0)
1782     {
1783       operands[2]
1784         = GEN_INT ((unsigned HOST_WIDE_INT) INTVAL (operands[2]) >> 16);
1785       return \"andh %2,%1,%0\";
1786     }
1787   xop[0] = operands[0];
1788   xop[1] = operands[1];
1789   xop[2] = GEN_INT (~INTVAL (operands[2]) & 0xffff);
1790   output_asm_insn (\"andnot %2,%1,%0\", xop);
1791   operands[2] = GEN_INT (~(unsigned HOST_WIDE_INT) INTVAL (operands[2]) >> 16);
1792   return \"andnoth %2,%0,%0\";
1795 (define_insn ""
1796   [(set (match_operand:SI 0 "register_operand" "=r")
1797         (and:SI (not:SI (match_operand:SI 1 "register_operand" "rn"))
1798                 (match_operand:SI 2 "register_operand" "r")))]
1799   ""
1800   "*
1802   rtx xop[3];
1804   CC_STATUS_PARTIAL_INIT;
1805   if (REG_P (operands[1]) || LOGIC_INT (operands[1]))
1806     return \"andnot %1,%2,%0\";
1807   if ((INTVAL (operands[1]) & 0xffff) == 0)
1808     {
1809       operands[1]
1810         = GEN_INT ((unsigned HOST_WIDE_INT) INTVAL (operands[1]) >> 16);
1811       return \"andnoth %1,%2,%0\";
1812     }
1813   xop[0] = operands[0];
1814   xop[1] = GEN_INT (INTVAL (operands[1]) & 0xffff);
1815   xop[2] = operands[2];
1816   output_asm_insn (\"andnot %1,%2,%0\", xop);
1817   operands[1] = GEN_INT ((unsigned HOST_WIDE_INT) INTVAL (operands[1]) >> 16);
1818   return \"andnoth %1,%0,%0\";
1821 (define_insn "iorsi3"
1822   [(set (match_operand:SI 0 "register_operand" "=r")
1823         (ior:SI (match_operand:SI 1 "nonmemory_operand" "%r")
1824                 (match_operand:SI 2 "nonmemory_operand" "rL")))]
1825   ""
1826   "*
1828   rtx xop[3];
1830   CC_STATUS_PARTIAL_INIT;
1831   if (REG_P (operands[2]) || LOGIC_INT (operands[2]))
1832     return \"or %2,%1,%0\";
1833   if ((INTVAL (operands[2]) & 0xffff) == 0)
1834     {
1835       operands[2]
1836         = GEN_INT ((unsigned HOST_WIDE_INT) INTVAL (operands[2]) >> 16);
1837       return \"orh %2,%1,%0\";
1838     }
1839   xop[0] = operands[0];
1840   xop[1] = operands[1];
1841   xop[2] = GEN_INT (INTVAL (operands[2]) & 0xffff);
1842   output_asm_insn (\"or %2,%1,%0\", xop);
1843   operands[2] = GEN_INT ((unsigned HOST_WIDE_INT) INTVAL (operands[2]) >> 16);
1844   return \"orh %2,%0,%0\";
1847 (define_insn "xorsi3"
1848   [(set (match_operand:SI 0 "register_operand" "=r")
1849         (xor:SI (match_operand:SI 1 "nonmemory_operand" "%r")
1850                 (match_operand:SI 2 "nonmemory_operand" "rL")))]
1851   ""
1852   "*
1854   rtx xop[3];
1856   CC_STATUS_PARTIAL_INIT;
1857   if (REG_P (operands[2]) || LOGIC_INT (operands[2]))
1858     return \"xor %2,%1,%0\";
1859   if ((INTVAL (operands[2]) & 0xffff) == 0)
1860     {
1861       operands[2]
1862         = GEN_INT ((unsigned HOST_WIDE_INT) INTVAL (operands[2]) >> 16);
1863       return \"xorh %2,%1,%0\";
1864     }
1865   xop[0] = operands[0];
1866   xop[1] = operands[1];
1867   xop[2] = GEN_INT (INTVAL (operands[2]) & 0xffff);
1868   output_asm_insn (\"xor %2,%1,%0\", xop);
1869   operands[2] = GEN_INT ((unsigned HOST_WIDE_INT) INTVAL (operands[2]) >> 16);
1870   return \"xorh %2,%0,%0\";
1873 ;(The i860 instruction set doesn't allow an immediate second operand in
1874 ; a subtraction.)
1875 (define_insn "negsi2"
1876   [(set (match_operand:SI 0 "general_operand" "=r")
1877         (neg:SI (match_operand:SI 1 "arith_operand" "r")))]
1878   ""
1879   "*
1881   CC_STATUS_PARTIAL_INIT;
1882   return \"subu %?r0,%1,%0\";
1885 (define_insn "one_cmplsi2"
1886   [(set (match_operand:SI 0 "general_operand" "=r")
1887         (not:SI (match_operand:SI 1 "arith_operand" "r")))]
1888   ""
1889   "*
1891   CC_STATUS_PARTIAL_INIT;
1892   return \"subu -1,%1,%0\";
1895 ;; Floating point arithmetic instructions.
1897 (define_insn "adddf3"
1898   [(set (match_operand:DF 0 "register_operand" "=f")
1899         (plus:DF (match_operand:DF 1 "register_operand" "f")
1900                  (match_operand:DF 2 "register_operand" "f")))]
1901   ""
1902   "fadd.dd %1,%2,%0")
1904 (define_insn "addsf3"
1905   [(set (match_operand:SF 0 "register_operand" "=f")
1906         (plus:SF (match_operand:SF 1 "register_operand" "f")
1907                  (match_operand:SF 2 "register_operand" "f")))]
1908   ""
1909   "fadd.ss %1,%2,%0")
1911 (define_insn "subdf3"
1912   [(set (match_operand:DF 0 "register_operand" "=f")
1913         (minus:DF (match_operand:DF 1 "register_operand" "f")
1914                   (match_operand:DF 2 "register_operand" "f")))]
1915   ""
1916   "fsub.dd %1,%2,%0")
1918 (define_insn "subsf3"
1919   [(set (match_operand:SF 0 "register_operand" "=f")
1920         (minus:SF (match_operand:SF 1 "register_operand" "f")
1921                   (match_operand:SF 2 "register_operand" "f")))]
1922   ""
1923   "fsub.ss %1,%2,%0")
1925 (define_insn "muldf3"
1926   [(set (match_operand:DF 0 "register_operand" "=f")
1927         (mult:DF (match_operand:DF 1 "register_operand" "f")
1928                  (match_operand:DF 2 "register_operand" "f")))]
1929   ""
1930   "fmul.dd %1,%2,%0")
1932 (define_insn "mulsf3"
1933   [(set (match_operand:SF 0 "register_operand" "=f")
1934         (mult:SF (match_operand:SF 1 "register_operand" "f")
1935                  (match_operand:SF 2 "register_operand" "f")))]
1936   ""
1937   "fmul.ss %1,%2,%0")
1939 (define_insn "negdf2"
1940   [(set (match_operand:DF 0 "register_operand" "=f")
1941         (neg:DF (match_operand:DF 1 "register_operand" "f")))]
1942   ""
1943   "fsub.dd %?f0,%1,%0")
1945 (define_insn "negsf2"
1946   [(set (match_operand:SF 0 "register_operand" "=f")
1947         (neg:SF (match_operand:SF 1 "register_operand" "f")))]
1948   ""
1949   "fsub.ss %?f0,%1,%0")
1951 (define_insn "divdf3"
1952   [(set (match_operand:DF 0 "register_operand" "=&f")
1953         (div:DF (match_operand:DF 1 "register_operand" "f")
1954                  (match_operand:DF 2 "register_operand" "f")))
1955    (clobber (match_scratch:DF 3 "=&f"))
1956    (clobber (match_scratch:DF 4 "=&f"))]
1957   ""
1958   "*
1960   CC_STATUS_PARTIAL_INIT;
1961   if (((cc_prev_status.flags & CC_KNOW_HI_R31) == 0)
1962       || (cc_prev_status.flags & CC_HI_R31_ADJ)
1963       || (cc_prev_status.mdep != CONST2_RTX (SFmode)))
1964     {
1965       cc_status.flags |= CC_KNOW_HI_R31;
1966       cc_status.flags &= ~CC_HI_R31_ADJ;
1967       cc_status.mdep = CONST2_RTX (SFmode); 
1968       return \"frcp.dd %2,%3\;fmul.dd %2,%3,%0\;fmov.dd %?f0,%4\;\\
1969 orh 0x4000,%?r0,%?r31\;ixfr %?r31,%R4\;fsub.dd %4,%0,%0\;\\
1970 fmul.dd %3,%0,%3\;fmul.dd %2,%3,%0\;fsub.dd %4,%0,%0\;\\
1971 fmul.dd %3,%0,%3\;fmul.dd %2,%3,%0\;fsub.dd %4,%0,%0\;\\
1972 fmul.dd %3,%1,%3\;fmul.dd %0,%3,%0\";
1973     }
1974   else
1975     return \"frcp.dd %2,%3\;fmul.dd %2,%3,%0\;fmov.dd %?f0,%4\;\\
1976 ixfr %?r31,%R4\;fsub.dd %4,%0,%0\;\\
1977 fmul.dd %3,%0,%3\;fmul.dd %2,%3,%0\;fsub.dd %4,%0,%0\;\\
1978 fmul.dd %3,%0,%3\;fmul.dd %2,%3,%0\;fsub.dd %4,%0,%0\;\\
1979 fmul.dd %3,%1,%3\;fmul.dd %0,%3,%0\";
1982 (define_insn "divsf3"
1983   [(set (match_operand:SF 0 "register_operand" "=&f")
1984         (div:SF (match_operand:SF 1 "register_operand" "f")
1985                  (match_operand:SF 2 "register_operand" "f")))
1986    (clobber (match_scratch:SF 3 "=&f"))
1987    (clobber (match_scratch:SF 4 "=&f"))]
1988   ""
1989   "*
1991   CC_STATUS_PARTIAL_INIT;
1992   if (((cc_prev_status.flags & CC_KNOW_HI_R31) == 0)
1993       || (cc_prev_status.flags & CC_HI_R31_ADJ)
1994       || (cc_prev_status.mdep != CONST2_RTX (SFmode)))
1995     {
1996       cc_status.flags |= CC_KNOW_HI_R31;
1997       cc_status.flags &= ~CC_HI_R31_ADJ;
1998       cc_status.mdep = CONST2_RTX (SFmode);
1999       output_asm_insn (\"orh 0x4000,%?r0,%?r31\", operands);
2000     }
2001   return \"ixfr %?r31,%4\;frcp.ss %2,%0\;\\
2002 fmul.ss %2,%0,%3\;fsub.ss %4,%3,%3\;fmul.ss %0,%3,%0\;\\
2003 fmul.ss %2,%0,%3\;fsub.ss %4,%3,%3\;\\
2004 fmul.ss %1,%0,%4\;fmul.ss %3,%4,%0\";
2007 ;; Shift instructions
2009 ;; Optimized special case of shifting, which must precede the general case.
2011 (define_insn ""
2012   [(set (match_operand:SI 0 "register_operand" "=r")
2013         (ashiftrt:SI (match_operand:SI 1 "memory_operand" "m")
2014                      (const_int 24)))]
2015   ""
2016   "*
2018   if (CONSTANT_ADDRESS_P (XEXP (operands[1], 0)))
2019     {
2020       CC_STATUS_INIT;
2021       cc_status.flags |= CC_KNOW_HI_R31 | CC_HI_R31_ADJ;
2022       cc_status.mdep = XEXP (operands[1], 0);
2023       return \"orh %h1,%?r0,%?r31\;ld.b %L1(%?r31),%0\";
2024     }
2025   return \"ld.b %1,%0\";
2029 ;;- Arithmetic shift instructions.
2030 (define_insn "ashlsi3"
2031   [(set (match_operand:SI 0 "register_operand" "=r")
2032         (ashift:SI (match_operand:SI 1 "register_operand" "r")
2033                    (match_operand:SI 2 "shift_operand" "rn")))]
2034   ""
2035   "*
2037   return \"shl %2,%1,%0\";
2040 (define_insn "ashlhi3"
2041   [(set (match_operand:HI 0 "register_operand" "=r")
2042         (ashift:HI (match_operand:HI 1 "register_operand" "r")
2043                    (match_operand:HI 2 "shift_operand" "rn")))]
2044   ""
2045   "*
2047   return \"shl %2,%1,%0\";
2050 (define_insn "ashlqi3"
2051   [(set (match_operand:QI 0 "register_operand" "=r")
2052         (ashift:QI (match_operand:QI 1 "register_operand" "r")
2053                    (match_operand:QI 2 "shift_operand" "rn")))]
2054   ""
2055   "*
2057   return \"shl %2,%1,%0\";
2060 (define_insn "ashrsi3"
2061   [(set (match_operand:SI 0 "register_operand" "=r")
2062         (ashiftrt:SI (match_operand:SI 1 "register_operand" "r")
2063                      (match_operand:SI 2 "shift_operand" "rn")))]
2064   ""
2065   "*
2067   return \"shra %2,%1,%0\";
2070 (define_insn "lshrsi3"
2071   [(set (match_operand:SI 0 "register_operand" "=r")
2072         (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
2073                      (match_operand:SI 2 "shift_operand" "rn")))]
2074   ""
2075   "*
2077   return \"shr %2,%1,%0\";
2080 ;; Unconditional and other jump instructions.
2082 (define_insn "jump"
2083   [(set (pc) (label_ref (match_operand 0 "" "")))]
2084   ""
2085   "*
2087   return \"br %l0\;nop\";
2090 (define_insn "tablejump"
2091   [(set (pc) (match_operand:SI 0 "register_operand" "r"))
2092    (use (label_ref (match_operand 1 "" "")))]
2093   ""
2094   "bri %0\;nop")
2096 ;;- jump to subroutine
2097 (define_expand "call"
2098   [(call (match_operand:SI 0 "memory_operand" "m")
2099          (match_operand 1 "" "i"))]
2100   ;; operand[2] is next_arg_register
2101   ""
2102   "
2104   /* Make sure the address is just one reg and will stay that way.  */
2105   if (! call_insn_operand (operands[0], QImode))
2106     operands[0]
2107       = replace_equiv_address (operands[0],
2108                                copy_to_mode_reg (Pmode,
2109                                                  XEXP (operands[0], 0)));
2110   if (INTVAL (operands[1]) > 0)
2111     {
2112       emit_move_insn (arg_pointer_rtx, stack_pointer_rtx);
2113       emit_insn (gen_rtx_USE (VOIDmode, arg_pointer_rtx));
2114     }
2117 ;;- Jump to subroutine.
2118 (define_insn ""
2119   [(call (match_operand:SI 0 "call_insn_operand" "m")
2120          (match_operand 1 "" "i"))]
2121   ;; operand[2] is next_arg_register
2122   ""
2123   "*
2125   /* strip the MEM.  */
2126   operands[0] = XEXP (operands[0], 0);
2127   CC_STATUS_INIT;
2128   if (GET_CODE (operands[0]) == REG)
2129     return \"calli %0\;nop\";
2130   return \"call %0\;nop\";
2133 (define_expand "call_value"
2134   [(set (match_operand 0 "register_operand" "=rf")
2135         (call (match_operand:SI 1 "memory_operand" "m")
2136               (match_operand 2 "" "i")))]
2137   ;; operand 3 is next_arg_register
2138   ""
2139   "
2141   /* Make sure the address is just one reg and will stay that way.  */
2142   if (! call_insn_operand (operands[1], QImode))
2143     operands[1]
2144       = replace_equiv_address (operands[1],
2145                                copy_to_mode_reg (Pmode,
2146                                                  XEXP (operands[1], 0)));
2147   if (INTVAL (operands[2]) > 0)
2148     {
2149       emit_move_insn (arg_pointer_rtx, stack_pointer_rtx);
2150       emit_insn (gen_rtx_USE (VOIDmode, arg_pointer_rtx));
2151     }
2154 (define_insn ""
2155   [(set (match_operand 0 "register_operand" "=rf")
2156         (call (match_operand:SI 1 "call_insn_operand" "m")
2157               (match_operand 2 "" "i")))]
2158   ;; operand 3 is next_arg_register
2159   ""
2160   "*
2162   /* Strip the MEM.  */
2163   operands[1] = XEXP (operands[1], 0);
2164   CC_STATUS_INIT;
2165   if (GET_CODE (operands[1]) == REG)
2166     return \"calli %1\;nop\";
2167   return \"call %1\;nop\";
2170 ;; Call subroutine returning any type.
2172 (define_expand "untyped_call"
2173   [(parallel [(call (match_operand 0 "" "")
2174                     (const_int 0))
2175               (match_operand 1 "" "")
2176               (match_operand 2 "" "")])]
2177   ""
2178   "
2180   int i;
2182   emit_call_insn (GEN_CALL (operands[0], const0_rtx, NULL, const0_rtx));
2184   for (i = 0; i < XVECLEN (operands[2], 0); i++)
2185     {
2186       rtx set = XVECEXP (operands[2], 0, i);
2187       emit_move_insn (SET_DEST (set), SET_SRC (set));
2188     }
2190   /* The optimizer does not know that the call sets the function value
2191      registers we stored in the result block.  We avoid problems by
2192      claiming that all hard registers are used and clobbered at this
2193      point.  */
2194   emit_insn (gen_blockage ());
2196   DONE;
2199 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
2200 ;; all of memory.  This blocks insns from being moved across this point.
2202 (define_insn "blockage"
2203   [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
2204   ""
2205   "")
2207 (define_insn "nop"
2208   [(const_int 0)]
2209   ""
2210   "nop")
2212 (define_insn "indirect_jump"
2213   [(set (pc) (match_operand:SI 0 "register_operand" "r"))]
2214   ""
2215   "bri %0")
2218 ;; A special insn that does the work to get setup just
2219 ;; before a table jump.
2221 (define_insn ""
2222   [(set (match_operand:SI 0 "register_operand" "=r")
2223         (mem:SI (plus:SI (match_operand:SI 1 "register_operand" "r")
2224                          (label_ref (match_operand 2 "" "")))))]
2225   ""
2226   "*
2228   CC_STATUS_INIT;
2229   return \"orh %H2,%?r0,%?r31\;or %L2,%?r31,%?r31\;ld.l %?r31(%1),%0\";