OSDN Git Service

*** empty log message ***
[pf3gnuchains/gcc-fork.git] / gcc / config / romp / romp.md
1 ;;- Machine description for ROMP chip for GNU C compiler
2 ;;   Copyright (C) 1988, 1991 Free Software Foundation, Inc.
3 ;;   Contributed by Richard Kenner (kenner@nyu.edu)
4
5 ;; This file is part of GNU CC.
6
7 ;; GNU CC 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.
11
12 ;; GNU CC 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.
16
17 ;; You should have received a copy of the GNU General Public License
18 ;; along with GNU CC; see the file COPYING.  If not, write to
19 ;; the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
20
21
22 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
23 \f
24 ;; Define the attributes for the ROMP.
25
26 ;; Insn type.  Used to default other attribute values.
27
28 (define_attr "type"
29   "branch,return,fp,load,loadz,store,call,address,arith,compare,multi,misc"
30   (const_string "arith"))
31
32 ;; Length in bytes.
33
34 (define_attr "length" ""
35   (cond [(eq_attr "type" "branch")
36          (if_then_else (and (ge (minus (pc) (match_dup 0))
37                                 (const_int -256))
38                             (le (minus (pc) (match_dup 0))
39                                 (const_int 254)))
40                        (const_int 2)
41                        (const_int 4))
42          (eq_attr "type" "return")      (const_int 2)
43          (eq_attr "type" "fp")          (const_int 10)
44          (eq_attr "type" "call")        (const_int 4)
45          (eq_attr "type" "load")
46            (cond [(match_operand 1 "short_memory_operand" "") (const_int 2)
47                   (match_operand 1 "symbolic_memory_operand" "") (const_int 8)]
48                  (const_int 4))
49          (eq_attr "type" "loadz")
50            (cond [(match_operand 1 "zero_memory_operand" "") (const_int 2)
51                   (match_operand 1 "symbolic_memory_operand" "") (const_int 8)]
52                  (const_string "4"))
53          (eq_attr "type" "store")
54            (cond [(match_operand 0 "short_memory_operand" "") (const_int 2)
55                   (match_operand 0 "symbolic_memory_operand" "") (const_int 8)]
56                  (const_int 4))]
57         (const_int 4)))
58
59 ;; Whether insn can be placed in a delay slot.
60
61 (define_attr "in_delay_slot" "yes,no" 
62   (cond [(eq_attr "length" "8,10,38")                   (const_string "no")
63          (eq_attr "type" "branch,return,call,multi")    (const_string "no")]
64         (const_string "yes")))
65
66 ;; Whether insn needs a delay slot.
67 (define_attr "needs_delay_slot" "yes,no"
68   (if_then_else (eq_attr "type" "branch,return,call")
69                 (const_string "yes") (const_string "no")))
70
71 ;; What insn does to the condition code.
72
73 (define_attr "cc"
74   "clobber,none,sets,change0,copy1to0,compare,tbit"
75   (cond [(eq_attr "type" "load,loadz")          (const_string "change0")
76          (eq_attr "type" "store")               (const_string "none")
77          (eq_attr "type" "fp,call")             (const_string "clobber")
78          (eq_attr "type" "branch,return")       (const_string "none")
79          (eq_attr "type" "address")             (const_string "change0")
80          (eq_attr "type" "compare")             (const_string "compare")
81          (eq_attr "type" "arith")               (const_string "sets")]
82         (const_string "clobber")))
83 \f
84 ;; Define attributes for `asm' insns.
85
86 (define_asm_attributes [(set_attr "type" "misc")
87                         (set_attr "length" "8")
88                         (set_attr "in_delay_slot" "no")
89                         (set_attr "cc" "clobber")])
90
91 ;; Define the delay slot requirements for branches and calls.  We don't have
92 ;; any annulled insns.
93 ;;
94 (define_delay (eq_attr "needs_delay_slot" "yes")
95   [(eq_attr "in_delay_slot" "yes") (nil) (nil)])
96
97 ;; We cannot give a floating-point comparison a delay slot, even though it
98 ;; could make use of it.  This is because it would confuse next_cc0_user
99 ;; to do so.  Other fp insns can't get a delay slow because they set their
100 ;; result and use their input after the delay slot insn is executed.  This
101 ;; isn't what reorg.c expects.  
102
103 ;; Define load & store delays.  These were obtained by measurements done by
104 ;; jfc@athena.mit.edu.
105 ;;
106 ;; In general, the memory unit can support at most two simultaneous operations.
107 ;;
108 ;; Loads take 5 cycles to return the data and can be pipelined up to the
109 ;; limit of two simultaneous operations.
110 (define_function_unit "memory" 1 2 (eq_attr "type" "load,loadz") 5 0)
111
112 ;; Stores do not return data, but tie up the memory unit for 2 cycles if the
113 ;; next insn is also a store.
114 (define_function_unit "memory" 1 2 (eq_attr "type" "store") 1 2
115   [(eq_attr "type" "store")])
116 \f
117 ;; Move word instructions.
118 ;;
119 ;; If destination is memory but source is not register, force source to
120 ;; register.
121 ;;
122 ;; If source is a constant that is too large to load in a single insn, build
123 ;; it in two pieces.
124 ;;
125 ;; If destination is memory and source is a register, a temporary register
126 ;; will be needed.  In that case, make a PARALLEL of the SET and a
127 ;; CLOBBER of a SCRATCH to allocate the required temporary.
128 ;;
129 ;; This temporary is ACTUALLY only needed when the destination is a
130 ;; relocatable expression.  For generating RTL, however, we always
131 ;; place the CLOBBER.  In insns where it is not needed, the SCRATCH will
132 ;; not be allocated to a register.
133 ;;
134 ;; Also, avoid creating pseudo-registers or SCRATCH rtx's during reload as
135 ;; they will not be correctly handled.  We never need pseudos for that
136 ;; case anyway.
137 ;;
138 ;; We do not use DEFINE_SPLIT for loading constants because the number
139 ;; of cases in the resulting unsplit insn would be too high to deal
140 ;; with practically.
141 (define_expand "movsi"
142   [(set (match_operand:SI 0 "general_operand" "")
143         (match_operand:SI 1 "general_operand" ""))]
144   ""
145   "
146 { rtx op0 = operands[0];
147   rtx op1 = operands[1];
148
149   if (GET_CODE (op1) == REG && REGNO (op1) == 16)
150     DONE;
151
152   if (GET_CODE (op0) == REG && REGNO (op0) == 16)
153     DONE;
154
155   if (GET_CODE (op0) == MEM && ! reload_in_progress)
156     {
157       emit_insn (gen_storesi (operands[0], force_reg (SImode, operands[1])));
158       DONE;
159     }
160   else if (GET_CODE (op1) == CONST_INT)
161     {
162       int const_val = INTVAL (op1);
163
164       /* Try a number of cases to see how to best load the constant.  */
165       if ((const_val & 0xffff) == 0
166           || (const_val & 0xffff0000) == 0
167           || (unsigned) (const_val + 0x8000) < 0x10000)
168         /* Can do this in one insn, so generate it.  */
169         ;
170       else if (((- const_val) & 0xffff) == 0
171                || ((- const_val) & 0xffff0000) == 0
172                || (unsigned) ((- const_val) + 0x8000) < 0x10000)
173         {
174           /* Can do this by loading the negative constant and then negating. */
175           emit_move_insn (operands[0],
176                           gen_rtx (CONST_INT, VOIDmode, - const_val));
177           emit_insn (gen_negsi2 (operands[0], operands[0]));
178           DONE;
179         }
180       else
181         /* Do this the long way.  */
182         {
183           unsigned int high_part = const_val & 0xffff0000;
184           unsigned int low_part = const_val & 0xffff;
185           int i;
186
187           if (low_part >= 0x10 && exact_log2 (low_part) >= 0)
188             i = high_part, high_part = low_part, low_part = i;
189
190           emit_move_insn (operands[0],
191                           gen_rtx (CONST_INT, VOIDmode, low_part));
192           emit_insn (gen_iorsi3 (operands[0], operands[0],
193                                  gen_rtx (CONST_INT, VOIDmode, high_part)));
194           DONE;
195         }
196     }
197 }")
198
199 ;; Move from a symbolic memory location to a register is special.  In this
200 ;; case, we know in advance that the register cannot be r0, so we can improve
201 ;; register allocation by treating it separately.
202
203 (define_insn ""
204   [(set (match_operand:SI 0 "register_operand" "=b")
205         (match_operand:SI 1 "symbolic_memory_operand" "m"))]
206   ""
207   "load %0,%1"
208   [(set_attr "type" "load")])
209
210 ;; Generic single-word move insn.  We avoid the case where the destination is
211 ;; a symbolic address, as that needs a temporary register.
212
213 (define_insn ""
214   [(set (match_operand:SI 0 "reg_or_nonsymb_mem_operand" "=r,r,r,r,r,r,r,r,b,Q")
215         (match_operand:SI 1 "romp_operand" "rR,I,K,L,M,S,s,Q,m,r"))]
216   "register_operand (operands[0], SImode)
217    || register_operand (operands[1], SImode)"
218   "@
219    cas %0,%1,r0
220    lis %0,%1
221    cal %0,%1(r0)
222    cal16 %0,%1(r0)
223    cau %0,%H1(r0)
224    ail %0,r14,%C1
225    get %0,$%1
226    l%M1 %0,%1
227    load %0,%1
228    st%M0 %1,%0"
229   [(set_attr "type" "address,address,address,address,address,arith,misc,load,load,store")
230    (set_attr "length" "2,2,4,4,4,4,8,*,*,*")])
231
232 (define_insn "storesi"
233   [(set (match_operand:SI 0 "memory_operand" "=Q,m")
234         (match_operand:SI 1 "register_operand" "r,r"))
235    (clobber (match_scratch:SI 2 "=X,&b"))]
236   ""
237   "@
238    st%M0 %1,%0
239    store %1,%0,%2"
240   [(set_attr "type" "store")])
241
242 ;; This pattern is used by reload when we store into a symbolic address.  It
243 ;; provides the temporary register required.  This pattern is only used
244 ;; when SECONDARY_OUTPUT_RELOAD_CLASS returns something other than
245 ;; NO_REGS, so we need not have any predicates here.
246
247 (define_expand "reload_outsi"
248   [(parallel [(set (match_operand:SI 0 "symbolic_memory_operand" "=m")
249                    (match_operand:SI 1 "" "r"))
250               (clobber (match_operand:SI 2 "" "=&b"))])]
251   ""
252   "")
253 \f
254 ;; Now do the same for the QI move instructions.
255 (define_expand "movqi"
256   [(set (match_operand:QI 0 "general_operand" "")
257         (match_operand:QI 1 "general_operand" ""))]
258   ""
259   "
260 { rtx op0 = operands[0];
261
262   if (GET_CODE (op0) == MEM && ! reload_in_progress)
263     {
264       emit_insn (gen_storeqi (operands[0], force_reg (QImode, operands[1])));
265       DONE;
266     }
267 }")
268
269 (define_insn ""
270   [(set (match_operand:QI 0 "register_operand" "=b")
271         (match_operand:QI 1 "symbolic_memory_operand" "m"))]
272   "" 
273   "loadc %0,%1"
274   [(set_attr "type" "load")])
275
276 (define_insn ""
277   [(set (match_operand:QI 0 "reg_or_nonsymb_mem_operand" "=r,r,r,r,r,b,Q")
278         (match_operand:QI 1 "romp_operand" "r,I,n,s,Q,m,r"))]
279   "register_operand (operands[0], QImode)
280    || register_operand (operands[1], QImode)"
281   "@
282    cas %0,%1,r0
283    lis %0,%1
284    cal %0,%L1(r0)
285    get %0,$%1
286    lc%M1 %0,%1
287    loadc %0,%1
288    stc%M0 %1,%0"
289   [(set_attr "type" "address,address,address,misc,load,load,store")
290    (set_attr "length" "2,2,4,8,*,*,*")])
291
292 (define_insn "storeqi"
293   [(set (match_operand:QI 0 "memory_operand" "=Q,m")
294         (match_operand:QI 1 "register_operand" "r,r"))
295    (clobber (match_scratch:SI 2 "=X,&b"))]
296   ""
297   "@
298    stc%M0 %1,%0
299    storec %1,%0,%2"
300   [(set_attr "type" "store")])
301
302 (define_expand "reload_outqi"
303   [(set (match_operand:QI 0 "symbolic_memory_operand" "=m")
304         (match_operand:QI 1 "" "r"))
305    (match_operand:SI 2 "" "=&b")]
306   ""
307   "")
308 \f
309 ;; Finally, the HI instructions.
310 (define_expand "movhi"
311   [(set (match_operand:HI 0 "general_operand" "")
312         (match_operand:HI 1 "general_operand" ""))]
313   ""
314   "
315 { rtx op0 = operands[0];
316
317   if (GET_CODE (op0) == MEM && ! reload_in_progress)
318     {
319       emit_insn (gen_storehi (operands[0], force_reg (HImode, operands[1])));
320       DONE;
321     }
322 }")
323
324 (define_insn ""
325   [(set (match_operand:HI 0 "register_operand" "=b")
326         (match_operand:HI 1 "symbolic_memory_operand" "m"))]
327   ""
328   "loadha %0,%1"
329   [(set_attr "type" "load")])
330
331 (define_insn ""
332   [(set (match_operand:HI 0 "reg_or_nonsymb_mem_operand" "=r,r,r,r,r,b,Q")
333         (match_operand:HI 1 "romp_operand" "r,I,n,s,Q,m,r"))]
334   "register_operand (operands[0], HImode)
335    || register_operand (operands[1], HImode)"
336   "@
337    cas %0,%1,r0
338    lis %0,%1
339    cal %0,%L1(r0)
340    get %0,$%1
341    lh%N1 %0,%1
342    loadh %0,%1
343    sth%M0 %1,%0"
344   [(set_attr "type" "address,address,address,misc,loadz,loadz,store")
345    (set_attr "length" "2,2,4,8,*,*,*")])
346
347 (define_insn "storehi"
348   [(set (match_operand:HI 0 "memory_operand" "=Q,m")
349         (match_operand:HI 1 "register_operand" "r,r"))
350    (clobber (match_scratch:SI 2 "=X,&b"))]
351   ""
352   "@
353    sth%M0 %1,%0
354    storeh %1,%0,%2"
355   [(set_attr "type" "store")])
356
357 (define_expand "reload_outhi"
358   [(set (match_operand:HI 0 "symbolic_memory_operand" "=m")
359         (match_operand:HI 1 "" "r"))
360    (match_operand:SI 2 "" "=&b")]
361   ""
362   "")
363 \f
364 ;; For DI move, if we have a constant, break the operation apart into
365 ;; two SImode moves because the optimizer may be able to do a better job
366 ;; with the resulting code.
367 ;;
368 ;; For memory stores, make the required pseudo for a temporary in case we
369 ;; are storing into an absolute address.
370 ;;
371 ;; We need to be careful about the cases where the output is a register that is
372 ;; the second register of the input.
373
374 (define_expand "movdi"
375   [(set (match_operand:DI 0 "general_operand" "")
376         (match_operand:DI 1 "general_operand" ""))]
377   ""
378   "
379 { rtx op0 = operands[0];
380   rtx op1 = operands[1];
381  
382   if (CONSTANT_P (op1))
383     {
384       rtx insns;
385
386       start_sequence ();
387       emit_move_insn (operand_subword (op0, 0, 1, DImode),
388                       operand_subword (op1, 0, 1, DImode));
389       emit_move_insn (operand_subword (op0, 1, 1, DImode),
390                       operand_subword (op1, 1, 1, DImode));
391       insns = get_insns ();
392       end_sequence ();
393
394       emit_no_conflict_block (insns, op0, op1, 0, op1);
395       DONE;
396     }
397
398   if (GET_CODE (op0) == MEM && ! reload_in_progress)
399     {
400       emit_insn (gen_storedi (operands[0], force_reg (DImode, operands[1])));
401       DONE;
402     }
403 }")
404
405 (define_insn ""
406  [(set (match_operand:DI 0 "reg_or_nonsymb_mem_operand" "=r,r,r,Q")
407        (match_operand:DI 1 "reg_or_mem_operand" "r,Q,m,r"))]
408   "register_operand (operands[0], DImode)
409    || register_operand (operands[1], DImode)"
410   "*
411 {
412   switch (which_alternative)
413     {
414     case 0:
415       if (REGNO (operands[0]) == REGNO (operands[1]) + 1)
416         return \"cas %O0,%O1,r0\;cas %0,%1,r0\";
417       else
418         return \"cas %0,%1,r0\;cas %O0,%O1,r0\";
419     case 1:
420       /* Here we must see which word to load first.  We default to the
421          low-order word unless it occurs in the address.  */
422       if (refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
423                              operands[1], 0))
424         return \"l%M1 %O0,%O1\;l%M1 %0,%1\";
425       else
426         return \"l%M1 %0,%1\;l%M1 %O0,%O1\";
427     case 2:
428       return \"get %O0,$%1\;ls %0,0(%O0)\;ls %O0,4(%O0)\";
429     case 3:
430       return \"st%M0 %1,%0\;st%M0 %O1,%O0\";
431     }
432 }"
433   [(set_attr "type" "multi")
434    (set_attr "cc" "change0,change0,change0,none")
435    (set_attr "length" "4,12,8,8")])
436
437 (define_insn "storedi"
438   [(set (match_operand:DI 0 "memory_operand" "=Q,m")
439         (match_operand:DI 1 "register_operand" "r,r"))
440    (clobber (match_scratch:SI 2 "=X,&b"))]
441   ""
442   "@
443    st%M0 %1,%0\;st%M0 %O1,%O0
444    get %2,$%0\;sts %1,0(%2)\;sts %O1,4(%2)"
445   [(set_attr "type" "multi,multi")
446    (set_attr "cc" "none,none")
447    (set_attr "length" "8,12")])
448
449 (define_expand "reload_outdi"
450   [(set (match_operand:DI 0 "symbolic_memory_operand" "=m")
451         (match_operand:DI 1 "" "r"))
452    (match_operand:SI 2 "" "=&b")]
453   ""
454   "")
455
456 ;; Split symbolic memory operands differently.  We first load the address
457 ;; into a register and then do the two loads or stores.  We can only do
458 ;; this if operand_subword won't produce a SUBREG, which is only when
459 ;; operands[0] is a hard register.  Thus, these won't be used during the
460 ;; first insn scheduling pass.
461 (define_split
462   [(set (match_operand:DI 0 "register_operand" "")
463         (match_operand:DI 1 "symbolic_memory_operand" ""))]
464   "GET_CODE (operands[0]) == REG
465    && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER"
466   [(set (match_dup 2) (match_dup 3))
467    (set (match_dup 4) (match_dup 5))
468    (set (match_dup 6) (match_dup 7))]
469   "
470 { operands[2] = operand_subword (operands[0], 1, 0, DImode);
471   operands[3] = XEXP (operands[1], 0);
472   operands[4] = operand_subword (operands[0], 0, 0, DImode);
473   operands[5] = gen_rtx (MEM, SImode, operands[2]);
474   operands[6] = operands[2];
475   operands[7] = gen_rtx (MEM, SImode,
476                          gen_rtx (PLUS, SImode, operands[2],
477                                   gen_rtx (CONST_INT, VOIDmode, 4)));
478
479   if (operands[2] == 0 || operands[4] == 0)
480     FAIL;
481 }")
482
483 (define_split
484   [(set (match_operand:DI 0 "symbolic_memory_operand" "")
485         (match_operand:DI 1 "register_operand" ""))
486    (clobber (match_operand:SI 2 "register_operand" ""))] 
487   "GET_CODE (operands[0]) == REG
488    && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER"
489   [(set (match_dup 2) (match_dup 3))
490    (set (match_dup 4) (match_dup 5))
491    (set (match_dup 6) (match_dup 7))]
492   "
493 { operands[3] = XEXP (operands[0], 0);
494   operands[4] = gen_rtx (MEM, SImode, operands[2]);
495   operands[5] = operand_subword (operands[1], 0, 0, DImode);
496   operands[6] = gen_rtx (MEM, SImode,
497                          gen_rtx (PLUS, SImode, operands[2],
498                                   gen_rtx (CONST_INT, VOIDmode, 4)));
499   operands[7] = operand_subword (operands[1], 1, 0, DImode);
500
501   if (operands[5] == 0 || operands[7] == 0)
502     FAIL;
503 }")
504
505 ;; If the output is a register and the input is memory, we have to be careful
506 ;; and see which word needs to be loaded first.
507 ;;
508 ;; Note that this case doesn't have a CLOBBER.   Therefore, we must either
509 ;; be after reload or operand[0] must not be a MEM.  So we don't need a
510 ;; CLOBBER on the new insns either.
511 ;;
512 ;; Due to a bug in sched.c, we do not want to split this insn if both
513 ;; operands are registers and they overlap unless reload has completed.
514 (define_split
515   [(set (match_operand:DI 0 "general_operand" "")
516         (match_operand:DI 1 "general_operand" ""))]
517   "! symbolic_memory_operand (operands[0], DImode)
518    && ! symbolic_memory_operand (operands[1], DImode)
519    && ! (GET_CODE (operands[0]) == REG
520          && REGNO (operands[0]) >= FIRST_PSEUDO_REGISTER)
521    && ! (GET_CODE (operands[1]) == REG
522          && REGNO (operands[1]) >= FIRST_PSEUDO_REGISTER)
523    && ! (GET_CODE (operands[0]) == REG && GET_CODE (operands[1]) == REG
524          && ! reload_completed
525          && reg_overlap_mentioned_p (operands[0], operands[1]))"
526   [(set (match_dup 2) (match_dup 3))
527    (set (match_dup 4) (match_dup 5))]
528   "
529 { if (GET_CODE (operands[0]) != REG
530       || ! refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
531                               operands[1], 0))
532     {
533       operands[2] = operand_subword (operands[0], 0, 0, DImode);
534       operands[3] = operand_subword (operands[1], 0, 0, DImode);
535       operands[4] = operand_subword (operands[0], 1, 0, DImode);
536       operands[5] = operand_subword (operands[1], 1, 0, DImode);
537     }
538   else
539     {
540       operands[2] = operand_subword (operands[0], 1, 0, DImode);
541       operands[3] = operand_subword (operands[1], 1, 0, DImode);
542       operands[4] = operand_subword (operands[0], 0, 0, DImode);
543       operands[5] = operand_subword (operands[1], 0, 0, DImode);
544     }
545
546   if (operands[2] == 0 || operands[3] == 0
547       || operands[4] == 0 || operands[5] == 0)
548     FAIL;
549 }")
550
551 (define_split
552  [(set (match_operand:DI 0 "general_operand" "")
553        (match_operand:DI 1 "general_operand" ""))
554   (clobber (match_operand:SI 6 "register_operand" ""))]
555   "! symbolic_memory_operand (operands[0], DImode)
556    && ! symbolic_memory_operand (operands[1], DImode)
557    && ! (GET_CODE (operands[0]) == REG
558          && REGNO (operands[0]) >= FIRST_PSEUDO_REGISTER)
559    && ! (GET_CODE (operands[1]) == REG
560          && REGNO (operands[1]) >= FIRST_PSEUDO_REGISTER)"
561  [(parallel [(set (match_dup 2) (match_dup 3))
562              (clobber (match_dup 7))])
563   (parallel [(set (match_dup 4) (match_dup 5))
564              (clobber (match_dup 8))])]
565  "
566 { if (GET_CODE (operands[0]) != REG
567       || ! refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
568                               operands[1], 0))
569     {
570       operands[2] = operand_subword (operands[0], 0, 0, DImode);
571       operands[3] = operand_subword (operands[1], 0, 0, DImode);
572       operands[4] = operand_subword (operands[0], 1, 0, DImode);
573       operands[5] = operand_subword (operands[1], 1, 0, DImode);
574     }
575   else
576     {
577       operands[2] = operand_subword (operands[0], 1, 0, DImode);
578       operands[3] = operand_subword (operands[1], 1, 0, DImode);
579       operands[4] = operand_subword (operands[0], 0, 0, DImode);
580       operands[5] = operand_subword (operands[1], 0, 0, DImode);
581     }
582
583   if (operands[2] == 0 || operands[3] == 0
584       || operands[4] == 0 || operands[5] == 0)
585     FAIL;
586
587   /* We must be sure to make two different SCRATCH operands, since they
588      are not allowed to be shared.  After reload, however, we only have
589      a SCRATCH if we won't use the operand, so it is allowed to share it
590      then.  */
591   if (reload_completed || GET_CODE (operands[6]) != SCRATCH)
592     operands[7] = operands[8] = operands[6];
593   else
594     {
595       operands[7] = gen_rtx (SCRATCH, SImode);
596       operands[8] = gen_rtx (SCRATCH, SImode);
597     }
598 }")
599
600 ;; Define move insns for SF, and DF.
601 ;;
602 ;; For register-register copies or a copy of something to itself, emit a
603 ;; single SET insn since it will likely be optimized away.
604 ;;
605 ;; Otherwise, emit a floating-point move operation unless both input and
606 ;; output are either constant, memory, or a non-floating-point hard register.
607 (define_expand "movdf"
608   [(parallel [(set (match_operand:DF 0 "general_operand" "")
609                    (match_operand:DF 1 "general_operand" ""))
610               (clobber (reg:SI 0))
611               (clobber (reg:SI 15))])]
612   ""
613   "
614 { rtx op0 = operands[0];
615   rtx op1 = operands[1];
616
617   if (op0 == op1)
618     {
619       emit_insn (gen_rtx (SET, VOIDmode, op0, op1));
620       DONE;
621     }
622
623   if ((GET_CODE (op0) == MEM
624        || (GET_CODE (op0) == REG && REGNO (op0) < FIRST_PSEUDO_REGISTER
625            && ! FP_REGNO_P (REGNO (op0))))
626       && (GET_CODE (op1) == MEM
627           || GET_CODE (op1) == CONST_DOUBLE
628           || (GET_CODE (op1) == REG && REGNO (op1) < FIRST_PSEUDO_REGISTER
629               && ! FP_REGNO_P (REGNO (op1)) && ! rtx_equal_p (op0, op1))))
630     {
631       rtx insns;
632
633       if (GET_CODE (op1) == CONST_DOUBLE)
634         op1 = force_const_mem (DFmode, op1);
635
636       start_sequence ();
637       if (GET_CODE (operands[0]) != REG
638           || ! refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
639                                   operands[1]), 0)
640         {
641           emit_move_insn (operand_subword (op0, 0, 1, DFmode),
642                           operand_subword_force (op1, 0, DFmode));
643           emit_move_insn (operand_subword (op0, 1, 1, DFmode),
644                           operand_subword_force (op1, 1, DFmode));
645         }
646       else
647         {
648           emit_move_insn (operand_subword (op0, 1, 1, DFmode),
649                           operand_subword_force (op1, 1, DFmode));
650           emit_move_insn (operand_subword (op0, 0, 1, DFmode),
651                           operand_subword_force (op1, 0, DFmode));
652         }
653
654       insns = get_insns ();
655       end_sequence ();
656
657       emit_no_conflict_block (insns, op0, op1, 0, op1);
658       DONE;
659     }
660 }")
661
662 (define_expand "movsf"
663   [(parallel [(set (match_operand:SF 0 "general_operand" "")
664                    (match_operand:SF 1 "general_operand" ""))
665               (clobber (reg:SI 0))
666               (clobber (reg:SI 15))])]
667   ""
668   "
669 { rtx op0 = operands[0];
670   rtx op1 = operands[1];
671   
672   if (op0 == op1)
673     {
674       emit_insn (gen_rtx (SET, VOIDmode, op0, op1));
675       DONE;
676     }
677
678   if ((GET_CODE (op0) == MEM
679        || (GET_CODE (op0) == REG && REGNO (op0) < FIRST_PSEUDO_REGISTER
680            && ! FP_REGNO_P (REGNO (op0))))
681        && (GET_CODE (op1) == MEM
682            || GET_CODE (op1) == CONST_DOUBLE
683            || (GET_CODE (op1) == REG && REGNO (op1) < FIRST_PSEUDO_REGISTER
684                && ! FP_REGNO_P (REGNO (op1)))))
685     {
686       rtx last;
687
688       if (GET_CODE (op1) == CONST_DOUBLE)
689         op1 = force_const_mem (SFmode, op1);
690
691       last = emit_move_insn (operand_subword (op0, 0, 1, SFmode),
692                              operand_subword_force (op1, 0, SFmode));
693
694       REG_NOTES (last) = gen_rtx (EXPR_LIST, REG_EQUAL, op1, REG_NOTES (last));
695       DONE;
696     }
697 }")
698
699 ;; Define the move insns for SF and DF.  Check for all general regs
700 ;; in the FP insns and make them non-FP if so.  Do the same if the input and
701 ;; output are the same (the insn will be deleted in this case and we don't
702 ;; want to think there are FP insns when there might not be).
703 (define_insn ""
704   [(set (match_operand:SF 0 "general_operand" "=*frg")
705         (match_dup 0))]
706   ""
707   "nopr r0"
708   [(set_attr "type" "address")
709    (set_attr "length" "2")])
710
711 (define_insn ""
712   [(set (match_operand:SF 0 "general_operand" "=r,*fr,r,r,Q,m,frg")
713         (match_operand:SF 1 "general_operand" "r,0,Q,m,r,r,frg"))
714    (clobber (match_operand:SI 2 "reg_0_operand" "=&z,z,z,z,z,z,z"))
715    (clobber (match_operand:SI 3 "reg_15_operand" "=&t,t,t,t,t,t,t"))]
716   ""
717   "*
718 { switch (which_alternative)
719     {
720     case 0:
721       return \"cas %0,%1,r0\";
722     case 1:
723       return \"nopr r0\";
724     case 2:
725       return \"l%M1 %0,%1\";
726     case 3:
727       return \"load %0,%1\";
728     case 4:
729       return \"st%M0 %1,%0\";
730     case 5:
731       return \"store %1,%0,%3\";
732     default:
733       return output_fpop (SET, operands[0], operands[1], 0, insn);
734     }
735 }"
736   [(set_attr "type" "address,address,load,load,store,store,fp")
737    (set_attr "length" "2,2,*,*,*,*,*")])
738
739 (define_insn ""
740   [(set (match_operand:DF 0 "general_operand" "=*frg")
741         (match_dup 0))]
742   ""
743   "nopr r0"
744   [(set_attr "type" "address")
745    (set_attr "length" "2")])
746
747 (define_insn ""
748   [(set (match_operand:DF 0 "general_operand" "=r,*fr,r,r,Q,m,frg")
749         (match_operand:DF 1 "general_operand" "r,0,Q,m,r,r,*frg"))
750    (clobber (match_operand:SI 2 "reg_0_operand" "=&z,z,z,z,z,z,z"))
751    (clobber (match_operand:SI 3 "reg_15_operand" "=&t,t,t,t,t,t,t"))]
752   ""
753   "*
754 { switch (which_alternative)
755     {
756     case 0:
757       if (REGNO (operands[0]) == REGNO (operands[1]) + 1)
758         return \"cas %O0,%O1,r0\;cas %0,%1,r0\";
759       else
760         return \"cas %0,%1,r0\;cas %O0,%O1,r0\";
761     case 1:
762       return \"nopr r0\";
763     case 2:
764       /* Here we must see which word to load first.  We default to the
765          low-order word unless it occurs in the address.  */
766       if (refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
767                              operands[1], 0))
768         return \"l%M1 %O0,%O1\;l%M1 %0,%1\";
769       else
770         return \"l%M1 %0,%1\;l%M1 %O0,%O1\";
771     case 3:
772       return \"get %3,$%1\;ls %0,0(%3)\;ls %O0,4(%3)\";
773     case 4:
774       return \"st%M0 %1,%0\;st%M0 %O1,%O0\";
775     case 5:
776       return \"get %3,$%0\;sts %1,0(%3)\;sts %O1,4(%3)\";
777     default:
778       return output_fpop (SET, operands[0], operands[1], 0, insn);
779     }
780 }"
781   [(set_attr "type" "address,multi,multi,multi,multi,multi,fp")
782    (set_attr "length" "2,4,*,*,*,*,*")])
783
784 ;; Split all the above cases that involve multiple insns and no floating-point
785 ;; data block.  If before reload, we can make a SCRATCH.  Otherwise, use
786 ;; register 15.
787
788 (define_split
789   [(set (match_operand:DF 0 "register_operand" "")
790         (match_operand:DF 1 "symbolic_memory_operand" ""))
791    (clobber (reg:SI 0))
792    (clobber (reg:SI 15))]
793   "GET_CODE (operands[0]) == REG && REGNO (operands[0]) < 16"
794   [(set (reg:SI 15) (match_dup 2))
795    (set (match_dup 3) (match_dup 4))
796    (set (match_dup 5) (match_dup 6))]
797   "
798 { operands[2] = XEXP (operands[1], 0);
799   operands[3] = operand_subword (operands[0], 0, 0, DFmode);
800   operands[4] = gen_rtx (MEM, SImode, gen_rtx (REG, SImode, 15));
801   operands[5] = operand_subword (operands[0], 0, 1, DFmode);
802   operands[6] = gen_rtx (MEM, SImode,
803                          gen_rtx (PLUS, SImode, gen_rtx (REG, SImode, 15),
804                                   gen_rtx (CONST_INT, VOIDmode, 4)));
805
806   if (operands[3] == 0 || operands[5] == 0)
807     FAIL;
808 }")
809
810 (define_split
811   [(set (match_operand:DF 0 "symbolic_memory_operand" "")
812         (match_operand:DF 1 "register_operand" ""))
813    (clobber (reg:SI 0))
814    (clobber (reg:SI 15))]
815   "GET_CODE (operands[1]) == REG && REGNO (operands[1]) < 16"
816   [(set (reg:SI 15) (match_dup 2))
817    (set (match_dup 3) (match_dup 4))
818    (set (match_dup 5) (match_dup 6))]
819   "
820 { operands[2] = XEXP (operands[0], 0);
821   operands[3] = gen_rtx (MEM, SImode, gen_rtx (REG, SImode, 15));
822   operands[4] = operand_subword (operands[1], 0, 0, DFmode);
823   operands[5] = gen_rtx (MEM, SImode,
824                          gen_rtx (PLUS, SImode, gen_rtx (REG, SImode, 15),
825                                   gen_rtx (CONST_INT, VOIDmode, 4)));
826   operands[6] = operand_subword (operands[1], 1, 0, DFmode);
827
828   if (operands[4] == 0 || operands[6] == 0)
829     FAIL;
830 }")
831
832 ;; If the output is a register and the input is memory, we have to be careful
833 ;; and see which word needs to be loaded first.  We also cannot to the
834 ;; split if the input is a constant because it would result in invalid
835 ;; insns.  When the output is a MEM, we must put a CLOBBER on each of the
836 ;; resulting insn, when it is not a MEM, we must not.
837 (define_split
838   [(set (match_operand:DF 0 "memory_operand" "")
839         (match_operand:DF 1 "register_operand" ""))
840    (clobber (reg:SI 0))
841    (clobber (reg:SI 15))]
842   "GET_CODE (operands[1]) == REG && REGNO (operands[1]) < 15"
843   [(parallel [(set (match_dup 2) (match_dup 3))
844               (clobber (match_dup 6))])
845    (parallel [(set (match_dup 4) (match_dup 5))
846               (clobber (match_dup 7))])]
847   "
848 { operands[2] = operand_subword (operands[0], 0, 0, DFmode);
849   operands[3] = operand_subword (operands[1], 0, 0, DFmode);
850   operands[4] = operand_subword (operands[0], 1, 0, DFmode);
851   operands[5] = operand_subword (operands[1], 1, 0, DFmode);
852
853   if (operands[2] == 0 || operands[3] == 0
854       || operands[4] == 0 || operands[5] == 0)
855     FAIL;
856
857   if (reload_completed)
858     operands[6] = operands[7] = gen_rtx (REG, SImode, 15);
859   else
860     {
861       operands[6] = gen_rtx (SCRATCH, SImode);
862       operands[7] = gen_rtx (SCRATCH, SImode);
863     }
864 }")
865
866 (define_split
867   [(set (match_operand:DF 0 "nonmemory_operand" "")
868         (match_operand:DF 1 "general_operand" ""))
869    (clobber (reg:SI 0))
870    (clobber (reg:SI 15))]
871   "! symbolic_memory_operand (operands[1], DFmode)
872    && GET_CODE (operands[1]) != CONST_DOUBLE
873    && (GET_CODE (operands[0]) != REG || REGNO (operands[0]) < 15)
874    && (GET_CODE (operands[1]) != REG || REGNO (operands[1]) < 15)
875    && (GET_CODE (operands[0]) == REG || GET_CODE (operands[1]) == REG)"
876   [(set (match_dup 2) (match_dup 3))
877    (set (match_dup 4) (match_dup 5))]
878   "
879 { if (GET_CODE (operands[0]) != REG
880       || ! refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
881                               operands[1], 0))
882     {
883       operands[2] = operand_subword (operands[0], 0, 0, DFmode);
884       operands[3] = operand_subword (operands[1], 0, 0, DFmode);
885       operands[4] = operand_subword (operands[0], 1, 0, DFmode);
886       operands[5] = operand_subword (operands[1], 1, 0, DFmode);
887     }
888   else
889     {
890       operands[2] = operand_subword (operands[0], 1, 0, DFmode);
891       operands[3] = operand_subword (operands[1], 1, 0, DFmode);
892       operands[4] = operand_subword (operands[0], 0, 0, DFmode);
893       operands[5] = operand_subword (operands[1], 0, 0, DFmode);
894     }
895
896   if (operands[2] == 0 || operands[3] == 0
897       || operands[4] == 0 || operands[5] == 0)
898     FAIL;
899 }")
900 \f
901 ;; Conversions from one integer mode to another.
902 ;; It is possible sometimes to sign- or zero-extend while fetching from memory.
903 ;;
904 ;; First, sign-extensions:
905 (define_expand "extendhisi2"
906   [(set (match_operand:SI 0 "register_operand" "")
907         (sign_extend:SI (match_operand:HI 1 "register_operand" "")))]
908   ""
909   "")
910
911 (define_insn ""
912   [(set (match_operand:SI 0 "register_operand" "=b")
913         (sign_extend:SI (match_operand:HI 1 "symbolic_memory_operand" "m")))]
914   ""
915   "loadha %0,%1"
916   [(set_attr "type" "load")])
917
918 (define_insn ""
919   [(set (match_operand:SI 0 "register_operand" "=r,r,b")
920         (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "r,Q,m")))]
921   ""
922   "@
923    exts %0,%1
924    lha%M1 %0,%1
925    loadha %0,%1"
926   [(set_attr "type" "arith,load,load")
927    (set_attr "length" "2,*,*")])
928
929 (define_expand "extendqisi2"
930   [(set (match_dup 2)
931         (ashift:SI (match_operand:QI 1 "register_operand" "")
932                    (const_int 24)))
933    (set (match_operand:SI 0 "register_operand" "")
934         (ashiftrt:SI (match_dup 2)
935                      (const_int 24)))]
936   ""
937   "
938 { operands[1] = gen_lowpart (SImode, operands[1]);
939   operands[2] = gen_reg_rtx (SImode); }")
940
941 (define_expand "extendqihi2"
942   [(set (match_dup 2)
943         (ashift:SI (match_operand:QI 1 "register_operand" "")
944                    (const_int 24)))
945    (set (match_operand:HI 0 "register_operand" "")
946         (ashiftrt:SI (match_dup 2)
947                      (const_int 24)))]
948   ""
949   "
950 { operands[0] = gen_lowpart (SImode, operands[0]);
951   operands[1] = gen_lowpart (SImode, operands[1]);
952   operands[2] = gen_reg_rtx (SImode); }")
953
954 ;; Define peepholes to eliminate an instruction when we are doing a sign
955 ;; extension but cannot clobber the input.
956 ;;
957 ;; In this case we will shift left 24 bits, but need a copy first.  The shift
958 ;; can be replaced by a "mc03" instruction, but this can only be done if
959 ;; followed by the right shift of 24 or more bits.
960 (define_peephole
961   [(set (match_operand:SI 0 "register_operand" "")
962         (subreg:SI (match_operand:QI 1 "register_operand" "") 0))
963    (set (match_dup 0)
964         (ashift:SI (match_dup 0)
965                    (const_int 24)))
966    (set (match_dup 0)
967         (ashiftrt:SI (match_dup 0)
968                      (match_operand:SI 2 "const_int_operand" "")))]
969   "INTVAL (operands[2]) >= 24"
970   "mc03 %0,%1\;sari16 %0,%S2"
971  [(set_attr "type" "multi")
972   (set_attr "length" "4")
973   (set_attr "cc" "sets")])
974
975 ;; Now zero extensions:
976 (define_expand "zero_extendhisi2"
977   [(set (match_operand:SI 0 "register_operand" "b")
978         (zero_extend:SI (match_operand:HI 1 "register_operand" "")))]
979   ""
980   "")
981
982 (define_insn ""
983   [(set (match_operand:SI 0 "register_operand" "=b")
984         (zero_extend:SI (match_operand:HI 1 "symbolic_memory_operand" "m")))]
985   ""
986   "loadh %0,%1"
987   [(set_attr "type" "load")])
988
989 (define_insn ""
990   [(set (match_operand:SI 0 "register_operand" "=r,r,b")
991         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "r,Q,m")))]
992   ""
993   "@
994    nilz %0,%1,65535
995    lh%N1 %0,%1
996    loadh %0,%1"
997   [(set_attr "type" "arith,loadz,load")])
998
999 (define_expand "zero_extendqisi2"
1000   [(set (match_operand:SI 0 "register_operand" "")
1001         (zero_extend:SI (match_operand:QI 1 "register_operand" "")))]
1002   ""
1003   "")
1004
1005 (define_insn ""
1006   [(set (match_operand:SI 0 "register_operand" "=b")
1007         (zero_extend:SI (match_operand:QI 1 "symbolic_memory_operand" "m")))]
1008   ""
1009   "loadc %0,%1"
1010   [(set_attr "type" "load")])
1011
1012 (define_insn ""
1013   [(set (match_operand:SI 0 "register_operand" "=r,r,b")
1014         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "r,Q,m")))]
1015   ""
1016   "@
1017    nilz %0,%1,255
1018    lc%M1 %0,%1
1019    loadc %0,%1"
1020   [(set_attr "type" "arith,load,load")])
1021
1022 (define_expand "zero_extendqihi2"
1023   [(set (match_operand:HI 0 "register_operand" "")
1024         (zero_extend:HI (match_operand:QI 1 "register_operand" "")))]
1025   ""
1026   "")
1027
1028 (define_insn ""
1029   [(set (match_operand:HI 0 "register_operand" "=b")
1030         (zero_extend:HI (match_operand:QI 1 "symbolic_memory_operand" "m")))]
1031   ""
1032   "loadc %0,%1"
1033   [(set_attr "type" "load")])
1034
1035 (define_insn ""
1036   [(set (match_operand:HI 0 "register_operand" "=r,r,b")
1037         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "r,Q,m")))]
1038   ""
1039   "@
1040    nilz %0,%1,255
1041    lc%M1 %0,%1
1042    loadc %0,%1"
1043   [(set_attr "type" "arith,load,load")])
1044 \f
1045 ;; Various extract and insertion operations.
1046 (define_expand "extzv"
1047   [(set (match_operand:SI 0 "register_operand" "")
1048         (zero_extract:SI (match_operand:SI 1 "register_operand" "")
1049                          (match_operand:SI 2 "const_int_operand" "")
1050                          (match_operand:SI 3 "const_int_operand" "")))]
1051   ""
1052   "
1053 {
1054   if (GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != 8)
1055     FAIL;
1056
1057   if (GET_CODE (operands[3]) != CONST_INT)
1058     FAIL;
1059
1060   if (INTVAL (operands[3]) != 0 && INTVAL (operands[3]) != 8
1061       && INTVAL (operands[3]) != 16 && INTVAL (operands[3]) != 24)
1062     FAIL;
1063 }")
1064
1065 (define_insn ""
1066   [(set (match_operand:SI 0 "register_operand" "=&r")
1067         (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
1068                          (const_int 8)
1069                          (match_operand:SI 2 "const_int_operand" "n")))]
1070   "(INTVAL (operands[2]) & 7) == 0"
1071   "lis %0,0\;mc3%B2 %0,%1"
1072   [(set_attr "type" "multi")
1073    (set_attr "cc" "change0")])
1074
1075 (define_split
1076   [(set (match_operand:SI 0 "register_operand" "=&r")
1077         (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
1078                          (const_int 8)
1079                          (match_operand:SI 2 "const_int_operand" "n")))]
1080   "(INTVAL (operands[2]) & 7) == 0"
1081   [(set (match_dup 0) (const_int 0))
1082    (set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 24))
1083         (zero_extract:SI (match_dup 1) (const_int 8) (match_dup 2)))]
1084   "")
1085
1086 (define_insn ""
1087   [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r")
1088                          (const_int 8)
1089                          (const_int 24))
1090         (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
1091                          (const_int 8)
1092                          (match_operand:SI 2 "const_int_operand" "n")))]
1093   "(INTVAL (operands[2]) & 7) == 0"
1094   "mc3%B2 %0,%1"
1095   [(set_attr "type" "address")
1096    (set_attr "length" "2")])
1097
1098 (define_expand "insv"
1099   [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "")
1100                          (match_operand:SI 1 "const_int_operand" "")
1101                          (match_operand:SI 2 "const_int_operand" ""))
1102         (match_operand:SI 3 "register_operand" ""))]
1103   ""
1104   "
1105 {
1106   if (GET_CODE (operands[2]) != CONST_INT)
1107     FAIL;
1108
1109   if (GET_CODE (operands[1]) != CONST_INT)
1110     FAIL;
1111
1112   if (INTVAL (operands[1]) == 1)
1113     {
1114       emit_insn (gen_bit_insv (operands[0], operands[1], operands[2],
1115                                operands[3]));
1116       DONE;
1117     }
1118   else if (INTVAL (operands[1]) == 8
1119            && (INTVAL (operands[2]) % 8 == 0))
1120     ;                           /* Accept aligned byte-wide field. */
1121   else
1122     FAIL;
1123 }")
1124
1125 ;; For a single-bit insert, it is better to explicitly generate references
1126 ;; to the T bit.  We will call the T bit "CC0" because it can be clobbered
1127 ;; by some CC0 sets (single-bit tests).
1128
1129 (define_expand "bit_insv"
1130   [(set (cc0)
1131         (zero_extract:SI (match_operand:SI 3 "register_operand" "")
1132                          (const_int 1)
1133                          (const_int 31)))
1134    (parallel [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "")
1135                                     (match_operand:SI 1 "const_int_operand" "")
1136                                     (match_operand:SI 2 "const_int_operand" ""))
1137                    (ne (cc0) (const_int 0)))
1138               (clobber (match_scratch:SI 4 ""))])]
1139   ""
1140   "")
1141         
1142 (define_insn ""
1143   [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r")
1144                          (const_int 8)
1145                          (match_operand:SI 1 "const_int_operand" "n"))
1146         (match_operand:SI 2 "register_operand" "r"))]
1147   "(INTVAL (operands[1]) & 7) == 0"
1148   "mc%B1%.3 %0,%2"
1149   [(set_attr "type" "address")
1150    (set_attr "length" "2")])
1151
1152 ;; This pattern cannot have any input reloads since if references CC0.
1153 ;; So we have to add code to support memory, which is the only other
1154 ;; thing that a "register_operand" can become.  There is still a problem
1155 ;; if the address isn't valid and *it* needs a reload, but there is no
1156 ;; way to solve that problem, so let's hope it never happens.
1157
1158 (define_insn ""
1159   [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r,m")
1160                          (const_int 1)
1161                          (match_operand:SI 1 "const_int_operand" "n,m"))
1162         (ne (cc0) (const_int 0)))
1163    (clobber (match_scratch:SI 2 "=X,b"))]
1164   ""
1165   "@
1166    mftbi%t1 %0,%S1
1167    l%M0 %2,%0\;mftb%t1 %2,%S1\;st%M0 %2,%0"
1168   [(set_attr "type" "*,multi")
1169    (set_attr "cc" "none,none")
1170    (set_attr "length" "2,10")])
1171 \f
1172 ;; Arithmetic instructions.  First, add and subtract.
1173 ;;
1174 ;; It may be that the second input is either large or small enough that
1175 ;; the operation cannot be done in a single insn.  In that case, emit two.
1176 (define_expand "addsi3"
1177   [(set (match_operand:SI 0 "register_operand" "")
1178         (plus:SI (match_operand:SI 1 "register_operand" "")
1179                  (match_operand:SI 2 "nonmemory_operand" "")))]
1180   ""
1181   "
1182 {
1183   if (GET_CODE (operands[2]) == CONST_INT
1184       && (unsigned) (INTVAL (operands[2]) + 0x8000) >= 0x10000
1185       && (INTVAL (operands[2]) & 0xffff) != 0)
1186     {
1187       int low = INTVAL (operands[2]) & 0xffff;
1188       int high = (unsigned) INTVAL (operands[2]) >> 16;
1189
1190       if (low & 0x8000)
1191         high++, low |= 0xffff0000;
1192
1193       emit_insn (gen_addsi3 (operands[0], operands[1],
1194                              gen_rtx (CONST_INT, VOIDmode, high << 16)));
1195       operands[1] = operands[0];
1196       operands[2] = gen_rtx (CONST_INT, VOIDmode, low);
1197     }
1198 }")
1199
1200 ;; Put the insn to add a symbolic constant to a register separately to
1201 ;; improve register allocation since it has different register requirements.
1202 (define_insn ""
1203   [(set (match_operand:SI 0 "register_operand" "=b")
1204         (plus:SI (match_operand:SI 1 "register_operand" "%b")
1205                  (match_operand:SI 2 "romp_symbolic_operand" "s")))]
1206    ""
1207    "get %0,$%2(%1)"
1208    [(set_attr "type" "address")
1209     (set_attr "length" "8")])
1210
1211 (define_insn ""
1212   [(set (match_operand:SI 0 "register_operand" "=r,r,r,r,r,r,b")
1213         (plus:SI (match_operand:SI 1 "reg_or_add_operand" "%0,0,r,b,0,r,b")
1214                  (match_operand:SI 2 "reg_or_add_operand" "I,J,K,M,r,b,s")))]
1215   "register_operand (operands[1], SImode)
1216    || register_operand (operands[2], SImode)"
1217   "@
1218    ais %0,%2
1219    sis %0,%n2
1220    ail %0,%1,%2
1221    cau %0,%H2(%1)
1222    a %0,%2
1223    cas %0,%1,%2
1224    get %0,$%2(%1)"
1225   [(set_attr "type" "arith,arith,arith,address,arith,address,misc")
1226    (set_attr "length" "2,2,4,4,2,2,8")])
1227
1228 ;; Now subtract.
1229 ;;
1230 ;; 1.   If third operand is constant integer, convert it to add of the negative
1231 ;;      of that integer.
1232 ;; 2.   If the second operand is not a valid constant integer, force it into a
1233 ;;      register.
1234 (define_expand "subsi3"
1235   [(set (match_operand:SI 0 "register_operand" "")
1236         (minus:SI (match_operand:SI 1 "reg_or_any_cint_operand" "")
1237                   (match_operand:SI 2 "reg_or_any_cint_operand" "")))]
1238   ""
1239   "
1240 {
1241   if (GET_CODE (operands [2]) == CONST_INT)
1242     {
1243       emit_insn (gen_addsi3 (operands[0], operands[1], 
1244                              gen_rtx (CONST_INT,
1245                                       VOIDmode, - INTVAL (operands[2]))));
1246       DONE;
1247     }
1248   else
1249     operands[2] = force_reg (SImode, operands[2]);
1250
1251   if (GET_CODE (operands[1]) != CONST_INT
1252       || (unsigned) (INTVAL (operands[1]) + 0x8000) >= 0x10000)
1253     operands[1] = force_reg (SImode, operands[1]);
1254 }")
1255
1256 (define_insn ""
1257   [(set (match_operand:SI 0 "register_operand" "=r,r,r")
1258         (minus:SI (match_operand:SI 1 "reg_or_D_operand" "K,0,r")
1259                   (match_operand:SI 2 "register_operand" "r,r,0")))]
1260   ""
1261   "@
1262    sfi %0,%2,%1
1263    s %0,%2
1264    sf %0,%1"
1265   [(set_attr "length" "4,2,2")])
1266 \f
1267 ;; Multiply either calls a special RT routine or is done in-line, depending
1268 ;; on the value of a -m flag.
1269 ;;
1270 ;; First define the way we call the subroutine.
1271 (define_expand "mulsi3_subr"
1272   [(set (reg:SI 2) (match_operand:SI 1 "register_operand" ""))
1273    (set (reg:SI 3) (match_operand:SI 2 "register_operand" ""))
1274    (parallel [(set (reg:SI 2) (mult:SI (reg:SI 2) (reg:SI 3)))
1275               (clobber (reg:SI 0))
1276               (clobber (reg:SI 15))])
1277    (set (match_operand:SI 0 "register_operand" "")
1278         (reg:SI 2))]
1279   ""
1280   "")
1281
1282 (define_expand "mulsi3"
1283   [(set (match_operand:SI 0 "register_operand" "")
1284         (mult:SI (match_operand:SI 1 "register_operand" "")
1285                  (match_operand:SI 2 "register_operand" "")))]
1286   ""
1287   "
1288 {
1289   if (! TARGET_IN_LINE_MUL)
1290     {
1291       emit_insn (gen_mulsi3_subr (operands[0], operands[1], operands[2]));
1292       DONE;
1293     }
1294 }")
1295
1296 ;; Define the patterns to match.
1297 ;; We would like to provide a delay slot for the insns that call internal
1298 ;; routines, but doing so is risky since reorg will think that the use of
1299 ;; r2 and r3 is completed in the insn needing the delay slot.  Also, it
1300 ;; won't know that the cc will be clobbered.  So take the safe approach
1301 ;; and don't give them delay slots.
1302 (define_insn ""
1303   [(set (reg:SI 2)
1304         (mult:SI (reg:SI 2) (reg:SI 3)))
1305    (clobber (reg:SI 0))
1306    (clobber (reg:SI 15))]
1307   "! TARGET_IN_LINE_MUL"
1308   "bali%# r15,lmul$$"
1309   [(set_attr "type" "misc")
1310    (set_attr "in_delay_slot" "no")])
1311
1312 (define_insn ""
1313   [(set (match_operand:SI 0 "register_operand" "=&r")
1314         (mult:SI (match_operand:SI 1 "register_operand" "%r")
1315                  (match_operand:SI 2 "register_operand" "r")))]
1316   "TARGET_IN_LINE_MUL"
1317   "*
1318 { return output_in_line_mul (); }"
1319   [(set_attr "length" "38")
1320    (set_attr "type" "multi")])
1321 \f
1322 ;; Handle divide and modulus.  The same function returns both values,
1323 ;; so use divmodsi4.  This divides arg 1 by arg 2 with quotient to go
1324 ;; into arg 0 and remainder in arg 3.
1325 ;;
1326 ;; We want to put REG_EQUAL notes for the two outputs.  So we need a
1327 ;; function to do everything else.
1328 (define_expand "divmodsi4_doit"
1329   [(set (reg:SI 2)
1330         (match_operand:SI 0 "register_operand" ""))
1331    (set (reg:SI 3)
1332         (match_operand:SI 1 "register_operand" ""))
1333    (parallel [(set (reg:SI 2) (div:SI (reg:SI 2) (reg:SI 3)))
1334               (set (reg:SI 3) (mod:SI (reg:SI 2) (reg:SI 3)))
1335               (clobber (reg:SI 0))
1336               (clobber (reg:SI 15))])]
1337   ""
1338   "")
1339
1340 (define_expand "divmodsi4"
1341   [(parallel [(set (match_operand:SI 0 "register_operand" "")
1342                    (div:SI (match_operand:SI 1 "register_operand" "")
1343                            (match_operand:SI 2 "register_operand" "")))
1344               (set (match_operand:SI 3 "register_operand" "")
1345                    (mod:SI (match_dup 1) (match_dup 2)))])]
1346   ""
1347   "
1348 {
1349   rtx insn;
1350
1351   emit_insn (gen_divmodsi4_doit (operands[1], operands[2]));
1352   insn = emit_move_insn (operands[0], gen_rtx (REG, SImode, 2));
1353   REG_NOTES (insn) = gen_rtx (EXPR_LIST, REG_EQUAL,
1354                               gen_rtx (DIV, SImode, operands[1],
1355                                        operands[2]),
1356                               REG_NOTES (insn));
1357   insn = emit_move_insn (operands[3], gen_rtx (REG, SImode, 3));
1358   REG_NOTES (insn) = gen_rtx (EXPR_LIST, REG_EQUAL,
1359                               gen_rtx (MOD, SImode, operands[1],
1360                                        operands[2]),
1361                               REG_NOTES (insn));
1362   DONE;
1363 }")
1364
1365 (define_insn ""
1366   [(set (reg:SI 2)
1367         (div:SI (reg:SI 2) (reg:SI 3)))
1368    (set (reg:SI 3)
1369         (mod:SI (reg:SI 2) (reg:SI 3)))
1370    (clobber (reg:SI 0))
1371    (clobber (reg:SI 15))]
1372   ""
1373   "bali%# r15,ldiv$$"
1374   [(set_attr "type" "misc")
1375    (set_attr "in_delay_slot" "no")])
1376
1377 ;; Similarly for unsigned divide.
1378 (define_expand "udivmodsi4_doit"
1379   [(set (reg:SI 2)
1380         (match_operand:SI 0 "register_operand" ""))
1381    (set (reg:SI 3)
1382         (match_operand:SI 1 "register_operand" ""))
1383    (parallel [(set (reg:SI 2) (udiv:SI (reg:SI 2) (reg:SI 3)))
1384               (set (reg:SI 3) (umod:SI (reg:SI 2) (reg:SI 3)))
1385               (clobber (reg:SI 0))
1386               (clobber (reg:SI 15))])]
1387   ""
1388   "")
1389
1390 (define_expand "udivmodsi4"
1391   [(parallel [(set (match_operand:SI 0 "register_operand" "")
1392                    (udiv:SI (match_operand:SI 1 "register_operand" "")
1393                             (match_operand:SI 2 "register_operand" "")))
1394               (set (match_operand:SI 3 "register_operand" "")
1395                    (umod:SI (match_dup 1) (match_dup 2)))])]
1396   ""
1397   "
1398 {
1399   rtx insn;
1400
1401   emit_insn (gen_udivmodsi4_doit (operands[1], operands[2]));
1402   insn = emit_move_insn (operands[0], gen_rtx (REG, SImode, 2));
1403   REG_NOTES (insn) = gen_rtx (EXPR_LIST, REG_EQUAL,
1404                               gen_rtx (UDIV, SImode, operands[1],
1405                                        operands[2]),
1406                               REG_NOTES (insn));
1407   insn = emit_move_insn (operands[3], gen_rtx (REG, SImode, 3));
1408   REG_NOTES (insn) = gen_rtx (EXPR_LIST, REG_EQUAL,
1409                               gen_rtx (UMOD, SImode, operands[1],
1410                                        operands[2]),
1411                               REG_NOTES (insn));
1412   DONE;
1413 }")
1414
1415 (define_insn ""
1416   [(set (reg:SI 2)
1417         (udiv:SI (reg:SI 2) (reg:SI 3)))
1418    (set (reg:SI 3)
1419         (umod:SI (reg:SI 2) (reg:SI 3)))
1420    (clobber (reg:SI 0))
1421    (clobber (reg:SI 15))]
1422   ""
1423   "bali%# r15,uldiv$$"
1424   [(set_attr "type" "misc")
1425    (set_attr "in_delay_slot" "no")])
1426 \f
1427 ;; Define DImode arithmetic operations.
1428 ;;
1429 ;; It is possible to do certain adds and subtracts with constants in a single
1430 ;; insn, but it doesn't seem worth the trouble.
1431 ;;
1432 ;; Don't use DEFINE_SPLIT on these because the dependency on CC can't be
1433 ;; easily tracked in that case!
1434 (define_insn "adddi3"
1435   [(set (match_operand:DI 0 "register_operand" "=r")
1436         (plus:DI (match_operand:DI 1 "register_operand" "%0")
1437                  (match_operand:DI 2 "register_operand" "r")))]
1438   ""
1439   "a %O0,%O2\;ae %0,%2"
1440   [(set_attr "type" "multi")])
1441
1442 (define_insn "subdi3"
1443   [(set (match_operand:DI 0 "register_operand" "=r")
1444         (minus:DI (match_operand:DI 1 "register_operand" "0")
1445                   (match_operand:DI 2 "register_operand" "r")))]
1446   ""
1447   "s %O0,%O2\;se %0,%2"
1448   [(set_attr "type" "multi")])
1449
1450 (define_insn "negdi2"
1451   [(set (match_operand:DI 0 "register_operand" "=r,&r")
1452         (neg:DI (match_operand:DI 1 "register_operand" "0,r")))]
1453   ""
1454   "twoc %O0,%O1\;onec %0,%1\;aei %0,%0,0"
1455   [(set_attr "type" "multi")
1456    (set_attr "length" "8")])
1457 \f
1458 ;; Unary arithmetic operations.
1459 (define_insn "abssi2"
1460   [(set (match_operand:SI 0 "register_operand" "=r")
1461         (abs:SI (match_operand:SI 1 "register_operand" "r")))]
1462   ""
1463   "abs %0,%1"
1464   [(set_attr "length" "2")])
1465
1466 (define_insn "negsi2"
1467   [(set (match_operand:SI 0 "register_operand" "=r")
1468         (neg:SI (match_operand:SI 1 "register_operand" "r")))]
1469   ""
1470   "twoc %0,%1"
1471   [(set_attr "length" "2")])
1472
1473 (define_insn "one_cmplsi2"
1474   [(set (match_operand:SI 0 "register_operand" "=r")
1475         (not:SI (match_operand:SI 1 "register_operand" "r")))]
1476   ""
1477   "onec %0,%1"
1478   [(set_attr "length" "2")])
1479
1480 \f
1481 ;; Logical insns: AND, IOR, and XOR
1482 ;;
1483 ;; If the operation is being performed on a 32-bit constant such that
1484 ;; it cannot be done in one insn, do it in two.  We may lose a bit on
1485 ;; CSE in pathological cases, but it seems better doing it this way.
1486 (define_expand "andsi3"
1487   [(set (match_operand:SI 0 "register_operand" "")
1488         (and:SI (match_operand:SI 1 "register_operand" "")
1489                 (match_operand:SI 2 "reg_or_any_cint_operand" "")))]
1490   ""
1491   "
1492 {
1493   if (GET_CODE (operands[2]) == CONST_INT)
1494     {
1495       int top = (unsigned) INTVAL (operands[2]) >> 16;
1496       int bottom = INTVAL (operands[2]) & 0xffff;
1497
1498       if (top != 0 && top != 0xffff && bottom != 0 && bottom != 0xffff)
1499         {
1500           emit_insn (gen_andsi3 (operands[0], operands[1],
1501                                  gen_rtx (CONST_INT, VOIDmode,
1502                                           (top << 16) | 0xffff)));
1503           operands[1] = operands[0];
1504           operands[2] = gen_rtx (CONST_INT, VOIDmode, 0xffff0000 | bottom);
1505         }
1506     }
1507 }");
1508
1509 (define_insn ""
1510   [(set (match_operand:SI 0 "register_operand" "=r,r,r")
1511         (and:SI (match_operand:SI 1 "reg_or_and_operand" "%0,r,0")
1512                 (match_operand:SI 2 "reg_or_and_operand" "P,LMO,r")))]
1513   "register_operand (operands[1], SImode)
1514    || register_operand (operands[2], SImode)"
1515   "@
1516    clrb%k2 %0,%b2
1517    ni%z2 %0,%1,%Z2
1518    n %0,%2"
1519   [(set_attr "length" "2,4,2")])
1520
1521 ;; logical OR (IOR)
1522 (define_expand "iorsi3"
1523   [(set (match_operand:SI 0 "register_operand" "")
1524         (ior:SI (match_operand:SI 1 "register_operand" "")
1525                 (match_operand:SI 2 "reg_or_any_cint_operand" "")))]
1526   ""
1527   "
1528 {
1529   if (GET_CODE (operands[2]) == CONST_INT)
1530     {
1531       int top = (unsigned) INTVAL (operands[2]) >> 16;
1532       int bottom = INTVAL (operands[2]) & 0xffff;
1533
1534       if (top != 0 && bottom != 0)
1535         {
1536           emit_insn (gen_iorsi3 (operands[0], operands[1],
1537                                  gen_rtx (CONST_INT, VOIDmode, (top << 16))));
1538           operands[1] = operands[0];
1539           operands[2] = gen_rtx (CONST_INT, VOIDmode, bottom);
1540         }
1541     }
1542 }");
1543
1544 (define_insn ""
1545   [(set (match_operand:SI 0 "register_operand" "=r,r,r")
1546         (ior:SI (match_operand:SI 1 "reg_or_cint_operand" "%0,r,0")
1547                 (match_operand:SI 2 "reg_or_cint_operand" "N,LM,r")))]
1548   "register_operand (operands[1], SImode)
1549    || register_operand (operands[2], SImode)"
1550   "@
1551    setb%h2 %0,%b2
1552    oi%h2 %0,%1,%H2
1553    o %0,%2"
1554   [(set_attr "length" "2,4,2")])
1555
1556 ;; exclusive-or (XOR)
1557 (define_expand "xorsi3"
1558   [(set (match_operand:SI 0 "register_operand" "")
1559         (xor:SI (match_operand:SI 1 "register_operand" "")
1560                 (match_operand:SI 2 "reg_or_any_cint_operand" "")))]
1561   ""
1562   "
1563 {
1564   if (GET_CODE (operands[2]) == CONST_INT)
1565     {
1566       int top = (unsigned) INTVAL (operands[2]) >> 16;
1567       int bottom = INTVAL (operands[2]) & 0xffff;
1568
1569       if (top == 0xffff && bottom == 0xffff)
1570         {
1571           emit_insn (gen_one_cmplsi2 (operands[0], operands[1]));
1572           DONE;
1573         }
1574       else if (top != 0 && bottom != 0)
1575         {
1576           emit_insn (gen_xorsi3 (operands[0], operands[1],
1577                                  gen_rtx (CONST_INT, VOIDmode, (top << 16))));
1578           operands[1] = operands[0];
1579           operands[2] = gen_rtx (CONST_INT, VOIDmode, bottom);
1580         }
1581     }
1582 }");
1583
1584 (define_insn ""
1585   [(set (match_operand:SI 0 "register_operand" "=r,r")
1586         (xor:SI (match_operand:SI 1 "reg_or_cint_operand" "%r,0")
1587                 (match_operand:SI 2 "reg_or_cint_operand" "LM,r")))]
1588   "register_operand (operands[1], SImode)
1589    || register_operand (operands[2], SImode)"
1590   "@
1591    xi%h2 %0,%1,%H2
1592    x %0,%2"
1593   [(set_attr "length" "4,2")])
1594 \f
1595 ;; Various shift insns
1596 (define_insn "ashrsi3"
1597   [(set (match_operand:SI 0 "register_operand" "=r,r")
1598         (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0")
1599                      (match_operand:QI 2 "reg_or_cint_operand" "r,n")))]
1600   ""
1601   "@
1602    sar %0,%2
1603    sari%s2 %0,%S2"
1604   [(set_attr "length" "2")])
1605
1606 (define_insn "lshrsi3"
1607   [(set (match_operand:SI 0 "register_operand" "=r,r")
1608         (lshiftrt:SI (match_operand:SI 1 "register_operand" "0,0")
1609                      (match_operand:QI 2 "reg_or_cint_operand" "r,n")))]
1610   ""
1611   "@
1612    sr %0,%2
1613    sri%s2 %0,%S2"
1614   [(set_attr "length" "2")])
1615
1616 (define_insn ""
1617   [(set (match_operand:SI 0 "register_operand" "=r")
1618         (ashift:SI (match_operand:SI 1 "register_operand" "b")
1619                    (const_int 1)))]
1620   ""
1621   "cas %0,%1,%1"
1622   [(set_attr "length" "2")
1623    (set_attr "type" "address")])
1624
1625 (define_insn "ashlsi3"
1626   [(set (match_operand:SI 0 "register_operand" "=r,r")
1627         (ashift:SI (match_operand:SI 1 "register_operand" "0,0")
1628                    (match_operand:QI 2 "reg_or_cint_operand" "r,n")))]
1629   ""
1630   "@
1631    sl %0,%2
1632    sli%s2 %0,%S2"
1633   [(set_attr "length" "2")])
1634 \f
1635 ;; Function call insns:
1636 ;;
1637 ;; On the ROMP, &fcn is actually a pointer to the data area, which is passed
1638 ;; to the function in r0.  &.fcn is the actual starting address of the
1639 ;; function.  Also, the word at &fcn contains &.fcn.
1640 ;;
1641 ;; For both functions that do and don't return values, there are two cases:
1642 ;; where the function's address is a constant, and where it isn't.
1643 ;;
1644 ;; Operand 1 (2 for `call_value') is the number of arguments and is not used.
1645 (define_expand "call"
1646   [(use (reg:SI 0))
1647    (parallel [(call (mem:SI (match_operand:SI 0 "address_operand" ""))
1648                     (match_operand 1 "" ""))
1649               (clobber (reg:SI 15))])]
1650   ""
1651   "
1652 {
1653   if (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != CONST_INT)
1654     abort();
1655
1656   operands[0] = XEXP (operands[0], 0);
1657   if (GET_CODE (operands[0]) == SYMBOL_REF)
1658     {
1659       extern rtx get_symref ();
1660       char *real_fcnname =
1661                 (char *) alloca (strlen (XSTR (operands[0], 0)) + 2);
1662
1663       /* Copy the data area address to r0.  */
1664       emit_move_insn (gen_rtx (REG, SImode, 0),
1665                       force_reg (SImode, operands[0]));
1666       strcpy (real_fcnname, \".\");
1667       strcat (real_fcnname, XSTR (operands[0], 0));
1668       operands[0] = get_symref (real_fcnname);
1669     }
1670   else
1671     {
1672       rtx data_access;
1673
1674       emit_move_insn (gen_rtx (REG, SImode, 0),
1675                       force_reg (SImode, operands[0]));
1676       data_access = gen_rtx (MEM, SImode, operands[0]);
1677       RTX_UNCHANGING_P (data_access) = 1;
1678       operands[0] = copy_to_reg (data_access);
1679     }
1680 }")
1681
1682 (define_insn ""
1683   [(call (mem:SI (match_operand:SI 0 "register_operand" "b"))
1684          (match_operand 1 "" "g"))
1685    (clobber (reg:SI 15))]
1686   ""
1687   "balr%# r15,%0"
1688   [(set_attr "type" "call")
1689    (set_attr "length" "2")])
1690
1691 (define_insn ""
1692   [(call (mem:SI (match_operand:SI 0 "romp_symbolic_operand" "i"))
1693          (match_operand 1 "" "g"))
1694    (clobber (reg:SI 15))]
1695   "GET_CODE (operands[0]) == SYMBOL_REF"
1696   "bali%# r15,%0"
1697   [(set_attr "type" "call")])
1698
1699 ;; Call a function and return a value.
1700 (define_expand "call_value"
1701   [(use (reg:SI 0))
1702    (parallel [(set (match_operand 0 "" "=fg")
1703                    (call (mem:SI (match_operand:SI 1 "address_operand" ""))
1704                          (match_operand 2 "" "")))
1705               (clobber (reg:SI 15))])]
1706   ""
1707   "
1708 {
1709   if (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != CONST_INT)
1710     abort();
1711
1712   operands[1] = XEXP (operands[1], 0);
1713   if (GET_CODE (operands[1]) == SYMBOL_REF)
1714     {
1715       extern rtx get_symref ();
1716       char *real_fcnname =
1717                 (char *) alloca (strlen (XSTR (operands[1], 0)) + 2);
1718
1719       /* Copy the data area address to r0.  */
1720       emit_move_insn (gen_rtx (REG, SImode, 0),
1721                       force_reg (SImode, operands[1]));
1722       strcpy (real_fcnname, \".\");
1723       strcat (real_fcnname, XSTR (operands[1], 0));
1724       operands[1] = get_symref (real_fcnname);
1725     }
1726   else
1727     {
1728       rtx data_access;
1729
1730       emit_move_insn (gen_rtx (REG, SImode, 0),
1731                       force_reg (SImode, operands[1]));
1732       data_access = gen_rtx (MEM, SImode, operands[1]);
1733       RTX_UNCHANGING_P (data_access) = 1;
1734       operands[1] = copy_to_reg (data_access);
1735     }
1736 }")
1737
1738 (define_insn ""
1739   [(set (match_operand 0 "" "=fg")
1740         (call (mem:SI (match_operand:SI 1 "register_operand" "b"))
1741               (match_operand 2 "" "g")))
1742    (clobber (reg:SI 15))]
1743   ""
1744   "balr%# r15,%1"
1745   [(set_attr "length" "2")
1746    (set_attr "type" "call")])
1747
1748 (define_insn ""
1749   [(set (match_operand 0 "" "=fg")
1750         (call (mem:SI (match_operand:SI 1 "romp_symbolic_operand" "i"))
1751               (match_operand 2 "" "g")))
1752    (clobber (reg:SI 15))]
1753   "GET_CODE (operands[1]) == SYMBOL_REF"
1754   "bali%# r15,%1"
1755   [(set_attr "type" "call")])
1756
1757 ;; No operation insn.
1758 (define_insn "nop"
1759   [(const_int 0)]
1760   ""
1761   "nopr r0"
1762   [(set_attr "type" "address")
1763    (set_attr "length" "2")
1764    (set_attr "cc" "none")])
1765 \f
1766 ;; Here are the floating-point operations.
1767 ;;
1768 ;; Start by providing DEFINE_EXPAND for each operation.
1769 ;; The insns will be handled with MATCH_OPERATOR; the methodology will be
1770 ;; discussed below.
1771
1772 ;; First the conversion operations.
1773
1774 (define_expand "truncdfsf2"
1775   [(parallel [(set (match_operand:SF 0 "general_operand" "")
1776                    (float_truncate:SF (match_operand:DF 1 "general_operand" "")))
1777               (clobber (reg:SI 0))
1778               (clobber (reg:SI 15))])]
1779   ""
1780   "")
1781
1782 (define_expand "extendsfdf2"
1783   [(parallel [(set (match_operand:DF 0 "general_operand" "")
1784                    (float_extend:DF (match_operand:SF 1 "general_operand" "")))
1785               (clobber (reg:SI 0))
1786               (clobber (reg:SI 15))])]
1787   ""
1788   "")
1789
1790 (define_expand "floatsisf2"
1791   [(parallel [(set (match_operand:SF 0 "general_operand" "")
1792                    (float:SF (match_operand:SI 1 "general_operand" "")))
1793               (clobber (reg:SI 0))
1794               (clobber (reg:SI 15))])]
1795   ""
1796   "")
1797
1798 (define_expand "floatsidf2"
1799   [(parallel [(set (match_operand:DF 0 "general_operand" "")
1800                    (float:DF (match_operand:SI 1 "general_operand" "")))
1801               (clobber (reg:SI 0))
1802               (clobber (reg:SI 15))])]
1803   ""
1804   "")
1805
1806 (define_expand "fix_truncsfsi2"
1807   [(parallel [(set (match_operand:SI 0 "general_operand" "")
1808                    (fix:SI (match_operand:SF 1 "general_operand" "")))
1809               (clobber (reg:SI 0))
1810               (clobber (reg:SI 15))])]
1811   ""
1812   "")
1813
1814 (define_expand "fix_truncdfsi2"
1815   [(parallel [(set (match_operand:SI 0 "general_operand" "")
1816                    (fix:SI (match_operand:DF 1 "general_operand" "")))
1817               (clobber (reg:SI 0))
1818               (clobber (reg:SI 15))])]
1819   ""
1820   "")
1821 \f
1822 ;; Now the binary operations.
1823
1824 (define_expand "addsf3"
1825   [(parallel [(set (match_operand:SF 0 "general_operand" "")
1826                    (plus:SF (match_operand:SF 1 "general_operand" "")
1827                             (match_operand:SF 2 "general_operand" "")))
1828               (clobber (reg:SI 0))
1829               (clobber (reg:SI 15))])]
1830   ""
1831   "")
1832
1833 (define_expand "adddf3"
1834   [(parallel [(set (match_operand:DF 0 "general_operand" "")
1835                    (plus:DF (match_operand:DF 1 "general_operand" "")
1836                             (match_operand:DF 2 "general_operand" "")))
1837                (clobber (reg:SI 0))
1838                (clobber (reg:SI 15))])]
1839   ""
1840   "")
1841
1842 (define_expand "subsf3"
1843   [(parallel [(set (match_operand:SF 0 "general_operand" "")
1844                    (minus:SF (match_operand:SF 1 "general_operand" "")
1845                              (match_operand:SF 2 "general_operand" "")))
1846               (clobber (reg:SI 0))
1847               (clobber (reg:SI 15))])]
1848   ""
1849   "")
1850
1851 (define_expand "subdf3"
1852   [(parallel [(set (match_operand:DF 0 "general_operand" "")
1853                    (minus:DF (match_operand:DF 1 "general_operand" "")
1854                              (match_operand:DF 2 "general_operand" "")))
1855               (clobber (reg:SI 0))
1856               (clobber (reg:SI 15))])]
1857   ""
1858   "")
1859
1860 (define_expand "mulsf3"
1861   [(parallel [(set (match_operand:SF 0 "general_operand" "")
1862                    (mult:SF (match_operand:SF 1 "general_operand" "")
1863                             (match_operand:SF 2 "general_operand" "")))
1864               (clobber (reg:SI 0))
1865               (clobber (reg:SI 15))])]
1866   ""
1867   "")
1868
1869 (define_expand "muldf3"
1870   [(parallel [(set (match_operand:DF 0 "general_operand" "")
1871                    (mult:DF (match_operand:DF 1 "general_operand" "")
1872                             (match_operand:DF 2 "general_operand" "")))
1873               (clobber (reg:SI 0))
1874               (clobber (reg:SI 15))])]
1875   ""
1876   "")
1877
1878 (define_expand "divsf3"
1879   [(parallel [(set (match_operand:SF 0 "general_operand" "")
1880                    (div:SF (match_operand:SF 1 "general_operand" "")
1881                            (match_operand:SF 2 "general_operand" "")))
1882               (clobber (reg:SI 0))
1883               (clobber (reg:SI 15))])]
1884   ""
1885   "")
1886
1887 (define_expand "divdf3"
1888   [(parallel [(set (match_operand:DF 0 "general_operand" "")
1889                    (div:DF (match_operand:DF 1 "general_operand" "")
1890                            (match_operand:DF 2 "general_operand" "")))
1891               (clobber (reg:SI 0))
1892               (clobber (reg:SI 15))])]
1893   ""
1894   "")
1895 \f
1896 ;; Unary floating-point operations.
1897 ;;
1898 ;; Negations can be done without floating-point, since this is IEEE.
1899 ;; But we cannot do this if an operand is a hard FP register, since
1900 ;; the SUBREG we create would not be valid.
1901 (define_expand "negsf2"
1902   [(set (match_operand:SF 0 "register_operand" "")
1903         (neg:SF (match_operand:SF 1 "register_operand" "")))]
1904   ""
1905   "
1906 {
1907   if (! (GET_CODE (operands[0]) == REG
1908          && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
1909          && FP_REGNO_P (REGNO (operands[0])))
1910       && ! (GET_CODE (operands[1]) == REG
1911             && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
1912             && FP_REGNO_P (REGNO (operands[1]))))
1913     {
1914       rtx result;
1915       rtx target = operand_subword (operands[0], 0, 1, SFmode);
1916
1917       result = expand_binop (SImode, xor_optab,
1918                              operand_subword_force (operands[1], 0, SFmode),
1919                              gen_rtx (CONST_INT, VOIDmode, 0x80000000),
1920                              target, 0, OPTAB_WIDEN);
1921       if (result == 0)
1922         abort ();
1923
1924       if (result != target)
1925         emit_move_insn (result, target);
1926
1927       /* Make a place for REG_EQUAL.  */
1928       emit_move_insn (operands[0], operands[0]);
1929       DONE;
1930     }
1931 }")
1932
1933 (define_expand "negdf2"
1934   [(set (match_operand:DF 0 "register_operand" "")
1935         (neg:DF (match_operand:DF 1 "register_operand" "")))]
1936   ""
1937   "
1938 {
1939   if (! (GET_CODE (operands[0]) == REG
1940          && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
1941          && FP_REGNO_P (REGNO (operands[0])))
1942       && ! (GET_CODE (operands[1]) == REG
1943             && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
1944             && FP_REGNO_P (REGNO (operands[1]))))
1945     {
1946       rtx result;
1947       rtx target = operand_subword (operands[0], 0, 1, DFmode);
1948       rtx insns;
1949
1950       start_sequence ();
1951       result = expand_binop (SImode, xor_optab,
1952                              operand_subword_force (operands[1], 0, DFmode),
1953                              gen_rtx (CONST_INT, VOIDmode, 0x80000000),
1954                              target, 0, OPTAB_WIDEN);
1955       if (result == 0)
1956         abort ();
1957
1958       if (result != target)
1959         emit_move_insn (result, target);
1960   
1961       emit_move_insn (operand_subword (operands[0], 1, 1, DFmode),
1962                       operand_subword_force (operands[1], 1, DFmode));
1963
1964       insns = get_insns ();
1965       end_sequence ();
1966
1967       emit_no_conflict_block (insns, operands[0], operands[1], 0, 0);
1968       DONE;
1969     }
1970 }")
1971
1972 (define_expand "abssf2"
1973   [(parallel [(set (match_operand:SF 0 "general_operand" "")
1974                    (abs:SF (match_operand:SF 1 "general_operand" "")))
1975               (clobber (reg:SI 0))
1976               (clobber (reg:SI 15))])]
1977   ""
1978   "")
1979
1980 (define_expand "absdf2"
1981   [(parallel [(set (match_operand:DF 0 "general_operand" "")
1982                    (abs:DF (match_operand:DF 1 "general_operand" "")))
1983               (clobber (reg:SI 0))
1984               (clobber (reg:SI 15))])]
1985   ""
1986   "")
1987 \f
1988 ;; Any floating-point operation can be either SFmode or DFmode, and each
1989 ;; operand (including the output) can be either a normal operand or a
1990 ;; conversion from a normal operand.
1991 ;;
1992 ;; We use MATCH_OPERATOR to match a floating-point binary or unary operator
1993 ;; and input and output conversions.  So we need 2^N patterns for each type
1994 ;; of operation, where N is the number of operands, including the output.
1995 ;; There are thus a total of 14 patterns, 8 for binary operations, 4 for
1996 ;; unary operations and two for conversion/move operations (only one
1997 ;; operand can have a conversion for move operations).  In addition, we have
1998 ;; to be careful that a floating-point reload register doesn't get allocated
1999 ;; for an integer.  We take care of this for inputs with PREFERRED_RELOAD_CLASS
2000 ;; but need to have two different constraints for outputs.  This means that
2001 ;; we have to duplicate each pattern where the output could be an integer.
2002 ;; This adds another 7 patterns, for a total of 21.
2003
2004 ;; Start with conversion operations (moves are done above).
2005
2006 (define_insn ""
2007   [(set (match_operand:SI 0 "general_operand" "=g")
2008         (match_operator 1 "float_conversion"
2009                 [(match_operand 2 "general_operand" "frg")]))
2010    (clobber (match_operand:SI 3 "reg_0_operand" "=&z"))
2011    (clobber (match_operand:SI 4 "reg_15_operand" "=&t"))]
2012   ""
2013   "*
2014 { return output_fpop (SET, operands[0], operands[2], 0, insn);
2015 }"
2016   [(set_attr "type" "fp")])
2017
2018 (define_insn ""
2019   [(set (match_operand 0 "general_operand" "=frg")
2020         (match_operator 1 "float_conversion"
2021                 [(match_operand 2 "general_operand" "frg")]))
2022    (clobber (match_operand:SI 3 "reg_0_operand" "=&z"))
2023    (clobber (match_operand:SI 4 "reg_15_operand" "=&t"))]
2024   ""
2025   "*
2026 { return output_fpop (SET, operands[0], operands[2], 0, insn);
2027 }"
2028   [(set_attr "type" "fp")])
2029 \f
2030 ;; Next, binary floating-point operations.
2031
2032 (define_insn ""
2033   [(set (match_operand 0 "general_operand" "=frg")
2034         (match_operator 1 "float_binary"
2035                 [(match_operand 2 "general_operand" "frg")
2036                  (match_operand 3 "general_operand" "frg")]))
2037    (clobber (match_operand:SI 4 "reg_0_operand" "=&z"))
2038    (clobber (match_operand:SI 5 "reg_15_operand" "=&t"))]
2039   "check_precision (GET_MODE (operands[1]), operands[2], operands[3])"
2040   "*
2041 { return output_fpop (GET_CODE (operands[1]), operands[0], 
2042                       operands[2], operands[3], insn);
2043 }"
2044   [(set_attr "type" "fp")])
2045
2046 (define_insn ""
2047   [(set (match_operand 0 "general_operand" "=frg")
2048         (match_operator 1 "float_binary"
2049                 [(match_operand 2 "general_operand" "frg")
2050                  (match_operator 3 "float_conversion"
2051                         [(match_operand 4 "general_operand" "frg")])]))
2052    (clobber (match_operand:SI 5 "reg_0_operand" "=&z"))
2053    (clobber (match_operand:SI 6 "reg_15_operand" "=&t"))]
2054   "check_precision (GET_MODE (operands[1]), operands[2], operands[4])"
2055   "*
2056 { return output_fpop (GET_CODE (operands[1]), operands[0], 
2057                       operands[2], operands[4], insn);
2058 }"
2059   [(set_attr "type" "fp")])
2060
2061 (define_insn ""
2062   [(set (match_operand 0 "general_operand" "=frg")
2063         (match_operator 1 "float_binary"
2064                 [(match_operator 2 "float_conversion"
2065                         [(match_operand 3 "general_operand" "frg")])
2066                  (match_operand 4 "general_operand" "frg")]))
2067    (clobber (match_operand:SI 5 "reg_0_operand" "=&z"))
2068    (clobber (match_operand:SI 6 "reg_15_operand" "=&t"))]
2069   "check_precision (GET_MODE (operands[1]), operands[3], operands[4])"
2070   "*
2071 { return output_fpop (GET_CODE (operands[1]), operands[0], 
2072                       operands[3], operands[4], insn);
2073 }"
2074   [(set_attr "type" "fp")])
2075
2076 (define_insn ""
2077   [(set (match_operand 0 "general_operand" "=frg")
2078         (match_operator 1 "float_binary"
2079                 [(match_operator 2 "float_conversion"
2080                         [(match_operand 3 "general_operand" "frg")])
2081                  (match_operator 4 "float_conversion"
2082                         [(match_operand 5 "general_operand" "frg")])]))
2083    (clobber (match_operand:SI 6 "reg_0_operand" "=&z"))
2084    (clobber (match_operand:SI 7 "reg_15_operand" "=&t"))]
2085   "check_precision (GET_MODE (operands[1]), operands[3], operands[5])"
2086   "*
2087 { return output_fpop (GET_CODE (operands[1]), operands[0], 
2088                       operands[3], operands[5], insn);
2089 }"
2090   [(set_attr "type" "fp")])
2091
2092 (define_insn ""
2093   [(set (match_operand:SI 0 "general_operand" "=g")
2094         (match_operator 1 "float_conversion"
2095                 [(match_operator 2 "float_binary"
2096                         [(match_operand 3 "general_operand" "frg")
2097                          (match_operand 4 "general_operand" "frg")])]))
2098    (clobber (match_operand:SI 5 "reg_0_operand" "=&z"))
2099    (clobber (match_operand:SI 6 "reg_15_operand" "=&t"))]
2100   "check_precision (GET_MODE (operands[2]), operands[3], operands[4])"
2101   "*
2102 { return output_fpop (GET_CODE (operands[2]), operands[0], 
2103                       operands[3], operands[4], insn);
2104 }"
2105   [(set_attr "type" "fp")])
2106
2107 (define_insn ""
2108   [(set (match_operand 0 "general_operand" "=frg")
2109         (match_operator 1 "float_conversion"
2110                 [(match_operator 2 "float_binary"
2111                         [(match_operand 3 "general_operand" "frg")
2112                          (match_operand 4 "general_operand" "frg")])]))
2113    (clobber (match_operand:SI 5 "reg_0_operand" "=&z"))
2114    (clobber (match_operand:SI 6 "reg_15_operand" "=&t"))]
2115   "check_precision (GET_MODE (operands[2]), operands[3], operands[4])"
2116   "*
2117 { return output_fpop (GET_CODE (operands[2]), operands[0], 
2118                       operands[3], operands[4], insn);
2119 }"
2120   [(set_attr "type" "fp")])
2121
2122 (define_insn ""
2123   [(set (match_operand:SI 0 "general_operand" "=g")
2124         (match_operator 1 "float_conversion"
2125                 [(match_operator 2 "float_binary"
2126                         [(match_operand 3 "general_operand" "frg")
2127                          (match_operator 4 "float_conversion"
2128                                 [(match_operand 5 "general_operand" "frg")])])]))
2129    (clobber (match_operand:SI 6 "reg_0_operand" "=&z"))
2130    (clobber (match_operand:SI 7 "reg_15_operand" "=&t"))]
2131   "check_precision (GET_MODE (operands[2]), operands[3], operands[4])"
2132   "*
2133 { return output_fpop (GET_CODE (operands[2]), operands[0], 
2134                       operands[3], operands[5], insn);
2135 }"
2136   [(set_attr "type" "fp")])
2137
2138 (define_insn ""
2139   [(set (match_operand 0 "general_operand" "=frg")
2140         (match_operator 1 "float_conversion"
2141                 [(match_operator 2 "float_binary"
2142                         [(match_operand 3 "general_operand" "frg")
2143                          (match_operator 4 "float_conversion"
2144                                 [(match_operand 5 "general_operand" "frg")])])]))
2145    (clobber (match_operand:SI 6 "reg_0_operand" "=&z"))
2146    (clobber (match_operand:SI 7 "reg_15_operand" "=&t"))]
2147   "check_precision (GET_MODE (operands[2]), operands[3], operands[4])"
2148   "*
2149 { return output_fpop (GET_CODE (operands[2]), operands[0], 
2150                       operands[3], operands[5], insn);
2151 }"
2152   [(set_attr "type" "fp")])
2153
2154 (define_insn ""
2155   [(set (match_operand:SI 0 "general_operand" "=g")
2156         (match_operator 1 "float_conversion"
2157                 [(match_operator 2 "float_binary"
2158                         [(match_operator 3 "float_conversion"
2159                                 [(match_operand 4 "general_operand" "frg")])
2160                          (match_operand 5 "general_operand" "frg")])]))
2161    (clobber (match_operand:SI 6 "reg_0_operand" "=&z"))
2162    (clobber (match_operand:SI 7 "reg_15_operand" "=&t"))]
2163   "check_precision (GET_MODE (operands[2]), operands[4], operands[5])"
2164   "*
2165 { return output_fpop (GET_CODE (operands[2]), operands[0], 
2166                       operands[4], operands[5], insn);
2167 }"
2168   [(set_attr "type" "fp")])
2169
2170 (define_insn ""
2171   [(set (match_operand 0 "general_operand" "=frg")
2172         (match_operator 1 "float_conversion"
2173                 [(match_operator 2 "float_binary"
2174                         [(match_operator 3 "float_conversion"
2175                                 [(match_operand 4 "general_operand" "frg")])
2176                          (match_operand 5 "general_operand" "frg")])]))
2177    (clobber (match_operand:SI 6 "reg_0_operand" "=&z"))
2178    (clobber (match_operand:SI 7 "reg_15_operand" "=&t"))]
2179   "check_precision (GET_MODE (operands[2]), operands[4], operands[5])"
2180   "*
2181 { return output_fpop (GET_CODE (operands[2]), operands[0], 
2182                       operands[4], operands[5], insn);
2183 }"
2184   [(set_attr "type" "fp")])
2185
2186 (define_insn ""
2187   [(set (match_operand:SI 0 "general_operand" "=g")
2188         (match_operator 1 "float_conversion"
2189                 [(match_operator 2 "float_binary"
2190                         [(match_operator 3 "float_conversion"
2191                                 [(match_operand 4 "general_operand" "frg")])
2192                          (match_operator 5 "float_conversion"
2193                                 [(match_operand 6 "general_operand" "frg")])])]))
2194    (clobber (match_operand:SI 7 "reg_0_operand" "=&z"))
2195    (clobber (match_operand:SI 8 "reg_15_operand" "=&t"))]
2196   "check_precision (GET_MODE (operands[2]), operands[4], operands[6])"
2197   "*
2198 { return output_fpop (GET_CODE (operands[2]), operands[0], 
2199                       operands[4], operands[6], insn);
2200 }"
2201   [(set_attr "type" "fp")])
2202
2203 (define_insn ""
2204   [(set (match_operand 0 "general_operand" "=frg")
2205         (match_operator 1 "float_conversion"
2206                 [(match_operator 2 "float_binary"
2207                         [(match_operator 3 "float_conversion"
2208                                 [(match_operand 4 "general_operand" "frg")])
2209                          (match_operator 5 "float_conversion"
2210                                 [(match_operand 6 "general_operand" "frg")])])]))
2211    (clobber (match_operand:SI 7 "reg_0_operand" "=&z"))
2212    (clobber (match_operand:SI 8 "reg_15_operand" "=&t"))]
2213   "check_precision (GET_MODE (operands[2]), operands[4], operands[6])"
2214   "*
2215 { return output_fpop (GET_CODE (operands[2]), operands[0], 
2216                       operands[4], operands[6], insn);
2217 }"
2218   [(set_attr "type" "fp")])
2219 \f
2220 ;; Unary floating-point operations.
2221
2222 (define_insn ""
2223   [(set (match_operand 0 "general_operand" "=frg")
2224         (match_operator 1 "float_unary"
2225                 [(match_operand 2 "general_operand" "frg")]))
2226    (clobber (match_operand:SI 3 "reg_0_operand" "=&z"))
2227    (clobber (match_operand:SI 4 "reg_15_operand" "=&t"))]
2228   "check_precision (GET_MODE (operands[1]), operands[2], 0)"
2229   "*
2230 { return output_fpop (GET_CODE (operands[1]), operands[0], operands[2],
2231                       0, insn);
2232 }"
2233   [(set_attr "type" "fp")])
2234
2235 (define_insn ""
2236   [(set (match_operand 0 "general_operand" "=frg")
2237         (match_operator 1 "float_unary"
2238                 [(match_operator 2 "float_conversion"
2239                         [(match_operand 3 "general_operand" "frg")])]))
2240    (clobber (match_operand:SI 4 "reg_0_operand" "=&z"))
2241    (clobber (match_operand:SI 5 "reg_15_operand" "=&t"))]
2242   "check_precision (GET_MODE (operands[1]), operands[3], 0)"
2243   "*
2244 { return output_fpop (GET_CODE (operands[1]), operands[0], operands[3],
2245                       0, insn);
2246 }"
2247   [(set_attr "type" "fp")])
2248
2249 (define_insn ""
2250   [(set (match_operand:SI 0 "general_operand" "=g")
2251         (match_operator 1 "float_conversion"
2252                 [(match_operator 2 "float_unary"
2253                         [(match_operand 3 "general_operand" "frg")])]))
2254    (clobber (match_operand:SI 4 "reg_0_operand" "=&z"))
2255    (clobber (match_operand:SI 5 "reg_15_operand" "=&t"))]
2256   "check_precision (GET_MODE (operands[2]), operands[3], 0)"
2257   "*
2258 { return output_fpop (GET_CODE (operands[2]), operands[0], operands[3],
2259                       0, insn);
2260 }"
2261   [(set_attr "type" "fp")])
2262
2263 (define_insn ""
2264   [(set (match_operand 0 "general_operand" "=frg")
2265         (match_operator 1 "float_conversion"
2266                 [(match_operator 2 "float_unary"
2267                         [(match_operand 3 "general_operand" "frg")])]))
2268    (clobber (match_operand:SI 4 "reg_0_operand" "=&z"))
2269    (clobber (match_operand:SI 5 "reg_15_operand" "=&t"))]
2270   "check_precision (GET_MODE (operands[2]), operands[3], 0)"
2271   "*
2272 { return output_fpop (GET_CODE (operands[2]), operands[0], operands[3],
2273                       0, insn);
2274 }"
2275   [(set_attr "type" "fp")])
2276
2277 (define_insn ""
2278   [(set (match_operand:SI 0 "general_operand" "=g")
2279         (match_operator 1 "float_conversion"
2280                 [(match_operator 2 "float_unary"
2281                         [(match_operator 3 "float_conversion"
2282                                 [(match_operand 4 "general_operand" "frg")])])]))
2283    (clobber (match_operand:SI 5 "reg_0_operand" "=&z"))
2284    (clobber (match_operand:SI 6 "reg_15_operand" "=&t"))]
2285   "check_precision (GET_MODE (operands[2]), operands[4], 0)"
2286   "*
2287 { return output_fpop (GET_CODE (operands[2]), operands[0], operands[4],
2288                       0, insn);
2289 }"
2290   [(set_attr "type" "fp")])
2291
2292 (define_insn ""
2293   [(set (match_operand 0 "general_operand" "=frg")
2294         (match_operator 1 "float_conversion"
2295                 [(match_operator 2 "float_unary"
2296                         [(match_operator 3 "float_conversion"
2297                                 [(match_operand 4 "general_operand" "frg")])])]))
2298    (clobber (match_operand:SI 5 "reg_0_operand" "=&z"))
2299    (clobber (match_operand:SI 6 "reg_15_operand" "=&t"))]
2300   "check_precision (GET_MODE (operands[2]), operands[4], 0)"
2301   "*
2302 { return output_fpop (GET_CODE (operands[2]), operands[0], operands[4],
2303                       0, insn);
2304 }"
2305   [(set_attr "type" "fp")])
2306 \f
2307 ;; Compare insns are next.  Note that the ROMP has two types of compares,
2308 ;; signed & unsigned, and one type of branch.  Use the routine
2309 ;; `next_insn_tests_no_unsigned' to see which type to use.
2310 (define_expand "tstsi"
2311   [(set (cc0)
2312         (match_operand:SI 0 "register_operand" "r"))]
2313   ""
2314   "")
2315
2316 (define_expand "cmpsi"
2317   [(set (cc0)
2318         (compare (match_operand:SI 0 "register_operand" "")
2319                  (match_operand:SI 1 "reg_or_cint_operand" "")))]
2320   ""
2321   "")
2322
2323 ;; Signed compare, `test' first.
2324
2325 (define_insn ""
2326   [(set (cc0)
2327         (match_operand:SI 0 "register_operand" "r"))]
2328   "next_insn_tests_no_unsigned (insn)"
2329   "cis %0,0"
2330   [(set_attr "length" "2")
2331    (set_attr "type" "compare")])
2332
2333 (define_insn ""
2334   [(set (cc0) (match_operand:SI 0 "register_operand" "r,r,r"))
2335    (set (match_operand:SI 1 "reg_or_nonsymb_mem_operand" "=0,r,Q")
2336         (match_dup 0))]
2337   "next_insn_tests_no_unsigned (insn)"
2338   "@
2339    cis %1,0
2340    nilo %1,%0,65535
2341    st%M1 %0,%1\;cis %0,0"
2342   [(set_attr "type" "compare,compare,store")
2343    (set_attr "length" "2,4,6")
2344    (set_attr "cc" "compare")])
2345
2346 (define_insn ""
2347   [(set (cc0)
2348         (compare (match_operand:SI 0 "register_operand" "r,r,r")
2349                  (match_operand:SI 1 "reg_or_cint_operand" "I,K,r")))]
2350   "next_insn_tests_no_unsigned (insn)"
2351   "@
2352    cis %0,%1
2353    cil %0,%1
2354    c %0,%1"
2355   [(set_attr "length" "2,4,2")
2356    (set_attr "type" "compare")])
2357
2358 ;; Unsigned comparisons, `test' first, again.
2359 (define_insn ""
2360   [(set (cc0)
2361         (match_operand:SI 0 "register_operand" "r"))]
2362   "! next_insn_tests_no_unsigned (insn)"
2363   "clil %0,0"
2364   [(set_attr "type" "compare")])
2365
2366 (define_insn ""
2367   [(set (cc0)
2368         (compare (match_operand:SI 0 "register_operand" "r,r")
2369                  (match_operand:SI 1 "reg_or_cint_operand" "K,r")))]
2370   "! next_insn_tests_no_unsigned (insn)"
2371   "@
2372    clil %0,%1
2373    cl %0,%1"
2374   [(set_attr "length" "4,2")
2375    (set_attr "type" "compare")])
2376
2377 ;; Bit test insn.  Many cases are converted into this by combine.  This
2378 ;; uses the ROMP test bit.
2379
2380 (define_insn ""
2381   [(set (cc0)
2382         (zero_extract (match_operand:SI 0 "register_operand" "r,r")
2383                       (const_int 1)
2384                       (match_operand:SI 1 "reg_or_any_cint_operand" "r,n")))]
2385   "next_insn_tests_no_inequality (insn)"
2386   "@
2387    mttb %0,%1
2388    mttbi%t1 %0,%S1"
2389   [(set_attr "length" "2")
2390    (set_attr "type" "compare")
2391    (set_attr "cc" "tbit")])
2392 \f
2393 ;; Floating-point comparisons.  There are two, equality and order.
2394 ;; The difference will be that a trap for NaN will be given on the orderr
2395 ;; comparisons only.
2396
2397 (define_expand "cmpsf"
2398   [(parallel [(set (cc0) (compare (match_operand:SF 0 "general_operand" "")
2399                                   (match_operand:SF 1 "general_operand" "")))
2400               (clobber (reg:SI 0))
2401               (clobber (reg:SI 15))])]
2402   ""
2403   "")
2404
2405 (define_expand "cmpdf"
2406   [(parallel [(set (cc0) (compare (match_operand:DF 0 "general_operand" "")
2407                                   (match_operand:DF 1 "general_operand" "")))
2408               (clobber (reg:SI 0))
2409               (clobber (reg:SI 15))])]
2410   ""
2411   "")
2412
2413 (define_expand "tstsf"
2414   [(parallel [(set (cc0) (match_operand:SF 0 "general_operand" ""))
2415               (clobber (reg:SI 0))
2416               (clobber (reg:SI 15))])]
2417   ""
2418   "")
2419
2420 (define_expand "tstdf"
2421   [(parallel [(set (cc0) (match_operand:DF 0 "general_operand" ""))
2422               (clobber (reg:SI 0))
2423               (clobber (reg:SI 15))])]
2424   ""
2425   "")
2426 \f
2427 ;; There are four cases for compare and two for test.  These correspond
2428 ;; to each input having a floating-point conversion or not.
2429
2430 (define_insn ""
2431   [(set (cc0) (compare (match_operand 0 "general_operand" "frg")
2432                        (match_operand 1 "general_operand" "frg")))
2433    (clobber (match_operand:SI 2 "reg_0_operand" "=&z"))
2434    (clobber (match_operand:SI 3 "reg_15_operand" "=&t"))]
2435   "GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode"
2436   "*
2437 { return output_fpop (next_insn_tests_no_inequality (insn) ? EQ : GE,
2438                       operands[0], operands[1], 0, insn);
2439 }"
2440   [(set_attr "type" "fp")
2441    (set_attr "cc" "compare")])
2442
2443 (define_insn ""
2444   [(set (cc0) (compare (match_operand 0 "general_operand" "frg")
2445                        (match_operator 1 "float_conversion"
2446                               [(match_operand 2 "general_operand" "frg")])))
2447    (clobber (match_operand:SI 3 "reg_0_operand" "=&z"))
2448    (clobber (match_operand:SI 4 "reg_15_operand" "=&t"))]
2449   ""
2450   "*
2451 { return output_fpop (next_insn_tests_no_inequality (insn) ? EQ : GE,
2452                       operands[0], operands[2], 0, insn);
2453 }"
2454   [(set_attr "type" "fp")
2455    (set_attr "cc" "compare")])
2456
2457 (define_insn ""
2458   [(set (cc0) (compare (match_operator 0 "float_conversion"
2459                               [(match_operand 1 "general_operand" "frg")])
2460                        (match_operand 2 "general_operand" "frg")))
2461    (clobber (match_operand:SI 3 "reg_0_operand" "=&z"))
2462    (clobber (match_operand:SI 4 "reg_15_operand" "=&t"))]
2463   ""
2464   "*
2465 { return output_fpop (next_insn_tests_no_inequality (insn) ? EQ : GE,
2466                       operands[1], operands[2], 0, insn);
2467 }"
2468   [(set_attr "type" "fp")
2469    (set_attr "cc" "compare")])
2470
2471 (define_insn ""
2472   [(set (cc0) (compare (match_operator 0 "float_conversion"
2473                               [(match_operand 1 "general_operand" "frg")])
2474                        (match_operator 2 "float_conversion"
2475                               [(match_operand 3 "general_operand" "frg")])))
2476    (clobber (match_operand:SI 4 "reg_0_operand" "=&z"))
2477    (clobber (match_operand:SI 5 "reg_15_operand" "=&t"))]
2478   ""
2479   "*
2480 { return output_fpop (next_insn_tests_no_inequality (insn) ? EQ : GE,
2481                       operands[1], operands[3], 0, insn);
2482 }"
2483   [(set_attr "type" "fp")
2484    (set_attr "cc" "compare")])
2485
2486 (define_insn ""
2487   [(set (cc0) (match_operand 0 "general_operand" "frg"))
2488    (clobber (match_operand:SI 1 "reg_0_operand" "=&z"))
2489    (clobber (match_operand:SI 2 "reg_15_operand" "=&t"))]
2490   "GET_MODE (operands[0]) == SFmode || GET_MODE (operands[0]) == DFmode"
2491   "*
2492 { return output_fpop (next_insn_tests_no_inequality (insn) ? EQ : GE,
2493                       operands[0], immed_real_const_1 (0, 0,
2494                                                        GET_MODE (operands[0])),
2495                       0, insn);
2496 }"
2497   [(set_attr "type" "fp")
2498    (set_attr "cc" "compare")])
2499
2500 (define_insn ""
2501   [(set (cc0) (match_operator 0 "float_conversion"
2502                         [(match_operand 1 "general_operand" "frg")]))
2503    (clobber (match_operand:SI 2 "reg_0_operand" "=&z"))
2504    (clobber (match_operand:SI 3 "reg_15_operand" "=&t"))]
2505   ""
2506   "*
2507 { return output_fpop (next_insn_tests_no_inequality (insn) ? EQ : GE,
2508                       operands[1], immed_real_const_1 (0, 0,
2509                                                        GET_MODE (operands[1])),
2510                       0, insn);
2511 }"
2512   [(set_attr "type" "fp")
2513    (set_attr "cc" "compare")])
2514 \f
2515 ;; Branch insns.  Unsigned vs. signed have already
2516 ;; been taken care of.  The only insns that need to be concerned about the
2517 ;; test bit are beq and bne because the rest are either always true,
2518 ;; always false, or converted to EQ or NE.
2519
2520 ;; For conditional branches, we use `define_expand' and just have two patterns
2521 ;; that match them.  Operand printing does most of the work.
2522
2523 (define_expand "beq"
2524   [(set (pc)
2525         (if_then_else (eq (cc0)
2526                           (const_int 0))
2527                       (label_ref (match_operand 0 "" ""))
2528                       (pc)))]
2529   ""
2530   "")
2531
2532 (define_expand "bne"
2533   [(set (pc)
2534         (if_then_else (ne (cc0)
2535                           (const_int 0))
2536                       (label_ref (match_operand 0 "" ""))
2537                       (pc)))]
2538   ""
2539   "")
2540
2541 (define_expand "bgt"
2542   [(set (pc)
2543         (if_then_else (gt (cc0)
2544                           (const_int 0))
2545                       (label_ref (match_operand 0 "" ""))
2546                       (pc)))]
2547   ""
2548   "")
2549
2550 (define_expand "bgtu"
2551   [(set (pc)
2552         (if_then_else (gtu (cc0)
2553                            (const_int 0))
2554                       (label_ref (match_operand 0 "" ""))
2555                       (pc)))]
2556   ""
2557   "")
2558
2559 (define_expand "blt"
2560   [(set (pc)
2561         (if_then_else (lt (cc0)
2562                           (const_int 0))
2563                       (label_ref (match_operand 0 "" ""))
2564                       (pc)))]
2565   ""
2566   "")
2567
2568 (define_expand "bltu"
2569   [(set (pc)
2570         (if_then_else (ltu (cc0)
2571                            (const_int 0))
2572                       (label_ref (match_operand 0 "" ""))
2573                       (pc)))]
2574   ""
2575   "")
2576
2577 (define_expand "bge"
2578   [(set (pc)
2579         (if_then_else (ge (cc0)
2580                           (const_int 0))
2581                       (label_ref (match_operand 0 "" ""))
2582                       (pc)))]
2583   ""
2584   "")
2585
2586 (define_expand "bgeu"
2587   [(set (pc)
2588         (if_then_else (geu (cc0)
2589                            (const_int 0))
2590                       (label_ref (match_operand 0 "" ""))
2591                       (pc)))]
2592   ""
2593   "")
2594
2595 (define_expand "ble"
2596   [(set (pc)
2597         (if_then_else (le (cc0)
2598                           (const_int 0))
2599                       (label_ref (match_operand 0 "" ""))
2600                       (pc)))]
2601   ""
2602   "")
2603
2604 (define_expand "bleu"
2605   [(set (pc)
2606         (if_then_else (leu (cc0)
2607                            (const_int 0))
2608                       (label_ref (match_operand 0 "" ""))
2609                       (pc)))]
2610   ""
2611   "")
2612 \f
2613 ;; Define both directions of branch and return.
2614
2615 (define_insn ""
2616   [(set (pc)
2617         (if_then_else (match_operator 1 "comparison_operator"
2618                                       [(cc0) (const_int 0)])
2619                       (label_ref (match_operand 0 "" ""))
2620                       (pc)))]
2621   ""
2622   "*
2623 {
2624   if (restore_compare_p (operands[1]))
2625     return 0;
2626   else if (get_attr_length (insn) == 2)
2627     return \"j%j1 %l0\";
2628   else
2629     return \"b%j1%# %l0\";
2630 }"
2631   [(set_attr "type" "branch")])
2632
2633 (define_insn ""
2634   [(set (pc)
2635         (if_then_else (match_operator 0 "comparison_operator"
2636                                       [(cc0) (const_int 0)])
2637                       (return)
2638                       (pc)))]
2639   "null_epilogue ()"
2640   "*
2641 {
2642   if (restore_compare_p (operands[0]))
2643     return 0;
2644   else
2645     return \"b%j0r%# r15\";
2646 }"
2647   [(set_attr "type" "return")])
2648
2649 (define_insn ""
2650   [(set (pc)
2651         (if_then_else (match_operator 1 "comparison_operator"
2652                                 [(cc0) (const_int 0)])
2653                       (pc)
2654                       (label_ref (match_operand 0 "" ""))))]
2655   ""
2656   "*
2657 {
2658   if (restore_compare_p (operands[1]))
2659     return 0;
2660   else if (get_attr_length (insn) == 2)
2661     return \"j%J1 %l0\";
2662   else
2663     return \"b%J1%# %l0\";
2664 }"
2665   [(set_attr "type" "branch")])
2666
2667 (define_insn ""
2668   [(set (pc)
2669         (if_then_else (match_operator 0 "comparison_operator"
2670                                       [(cc0) (const_int 0)])
2671                       (pc)
2672                       (return)))]
2673   "null_epilogue ()"
2674   "*
2675 {
2676   if (restore_compare_p (operands[0]))
2677     return 0;
2678   else
2679     return \"b%J0r%# r15\";
2680 }"
2681   [(set_attr "type" "return")])
2682
2683 ;; Unconditional branch and return.
2684
2685 (define_insn "jump"
2686   [(set (pc)
2687         (label_ref (match_operand 0 "" "")))]
2688   ""
2689   "*
2690 {
2691   if (get_attr_length (insn) == 2)
2692     return \"j %l0\";
2693   else
2694     return \"b%# %l0\";
2695 }"
2696   [(set_attr "type" "branch")])
2697
2698 (define_insn "return"
2699   [(return)]
2700   "null_epilogue ()"
2701   "br%# r15"
2702   [(set_attr "type" "return")])
2703
2704 (define_insn "indirect_jump"
2705   [(set (pc) (match_operand:SI 0 "register_operand" "r"))]
2706   ""
2707   "br%# %0"
2708   [(set_attr "type" "branch")
2709    (set_attr "length" "2")])
2710
2711 ;; Table jump for switch statements:
2712 (define_insn "tablejump"
2713   [(set (pc)
2714         (match_operand:SI 0 "register_operand" "r"))
2715    (use (label_ref (match_operand 1 "" "")))]
2716   ""
2717   "br%# %0"
2718   [(set_attr "type" "branch")
2719    (set_attr "length" "2")])
2720 \f
2721 ;;- Local variables:
2722 ;;- mode:emacs-lisp
2723 ;;- comment-start: ";;- "
2724 ;;- eval: (set-syntax-table (copy-sequence (syntax-table)))
2725 ;;- eval: (modify-syntax-entry ?[ "(]")
2726 ;;- eval: (modify-syntax-entry ?] ")[")
2727 ;;- eval: (modify-syntax-entry ?{ "(}")
2728 ;;- eval: (modify-syntax-entry ?} "){")
2729 ;;- End: