OSDN Git Service

68c665cc214b11dab5c11fd7178d8f10135428bd
[pf3gnuchains/gcc-fork.git] / gcc / config / m68k / m68k.md
1 ;;- Machine description for GNU compiler, Motorola 68000 Version
2 ;;  Copyright (C) 1987, 1988, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2001, 2002, 2003
3 ;;  Free Software Foundation, Inc.
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, 59 Temple Place - Suite 330,
20 ;; Boston, MA 02111-1307, USA.
21
22 ;;- Information about MCF5200 port.
23
24 ;;- The MCF5200 "ColdFire" architecture is a reduced version of the
25 ;;- 68k ISA.  Differences include reduced support for byte and word
26 ;;- operands and the removal of BCD, bitfield, rotate, and integer
27 ;;- divide instructions.  The TARGET_5200 flag turns the use of the
28 ;;- removed opcodes and addressing modes off.
29 ;;- 
30
31
32 ;;- instruction definitions
33
34 ;;- @@The original PO technology requires these to be ordered by speed,
35 ;;- @@    so that assigner will pick the fastest.
36
37 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
38
39 ;;- When naming insn's (operand 0 of define_insn) be careful about using
40 ;;- names from other targets machine descriptions.
41
42 ;;- cpp macro #define NOTICE_UPDATE_CC in file tm.h handles condition code
43 ;;- updates for most instructions.
44
45 ;;- Operand classes for the register allocator:
46 ;;- 'a' one of the address registers can be used.
47 ;;- 'd' one of the data registers can be used.
48 ;;- 'f' one of the m68881 registers can be used
49 ;;- 'r' either a data or an address register can be used.
50
51 ;;- Immediate Floating point operator constraints
52 ;;- 'G' a floating point constant that is *NOT* one of the standard
53 ;;   68881 constant values (to force calling output_move_const_double
54 ;;   to get it from rom if it is a 68881 constant).
55 ;;
56 ;;   See the functions standard_XXX_constant_p in output-m68k.c for more
57 ;; info.
58
59 ;;- Immediate integer operand constraints:
60 ;;- 'I'  1 .. 8
61 ;;- 'J'  -32768 .. 32767
62 ;;- 'K'  all integers EXCEPT -128 .. 127
63 ;;- 'L'  -8 .. -1
64 ;;- 'M'  all integers EXCEPT -256 .. 255
65 ;;- 'N'  24 .. 31
66 ;;- 'O'  16
67 ;;- 'P'  8 .. 15
68
69 ;;- Assembler specs:
70 ;;- "%."    size separator ("." or "")                  move%.l d0,d1
71 ;;- "%#"    immediate separator ("#" or "")             move%.l %#0,d0
72 ;;- "%-"    push operand "sp@-"                         move%.l d0,%-
73 ;;- "%+"    pop operand "sp@+"                          move%.l d0,%+
74 ;;- "%@"    top of stack "sp@"                          move%.l d0,%@
75 ;;- "%!"    fpcr register
76 ;;- "%$"    single-precision fp specifier ("s" or "")   f%$add.x fp0,fp1
77 ;;- "%&"    double-precision fp specifier ("d" or "")   f%&add.x fp0,fp1
78
79 ;;- Information about 68040 port.
80
81 ;;- The 68040 executes all 68030 and 68881/2 instructions, but some must
82 ;;- be emulated in software by the OS.  It is faster to avoid these
83 ;;- instructions and issue a library call rather than trapping into
84 ;;- the kernel.  The affected instructions are fintrz and fscale.  The
85 ;;- TARGET_68040 flag turns the use of the opcodes off.
86
87 ;;- The '040 also implements a set of new floating-point instructions
88 ;;- which specify the rounding precision in the opcode.  This finally
89 ;;- permit the 68k series to be truly IEEE compliant, and solves all
90 ;;- issues of excess precision accumulating in the extended registers.
91 ;;- By default, GCC does not use these instructions, since such code will
92 ;;- not run on an '030.  To use these instructions, use the -m68040-only
93 ;;- switch.  By changing TARGET_DEFAULT to include TARGET_68040_ONLY,
94 ;;- you can make these instructions the default.
95
96 ;;- These new instructions aren't directly in the md.  They are brought
97 ;;- into play by defining "%$" and "%&" to expand to "s" and "d" rather
98 ;;- than "".
99
100 ;;- Information about 68060 port.
101
102 ;;- The 68060 executes all 68030 and 68881/2 instructions, but some must
103 ;;- be emulated in software by the OS.  It is faster to avoid these
104 ;;- instructions and issue a library call rather than trapping into
105 ;;- the kernel.  The affected instructions are: divs.l <ea>,Dr:Dq;
106 ;;- divu.l <ea>,Dr:Dq; muls.l <ea>,Dr:Dq; mulu.l <ea>,Dr:Dq; and
107 ;;- fscale.  The TARGET_68060 flag turns the use of the opcodes off.
108
109 ;;- Some of these insn's are composites of several m68000 op codes.
110 ;;- The assembler (or final @@??) insures that the appropriate one is
111 ;;- selected.
112
113 ;; UNSPEC usage:
114
115 (define_constants
116   [(UNSPEC_SIN  1)
117    (UNSPEC_COS  2)
118   ])
119
120 ;; UNSPEC_VOLATILE usage:
121
122 (define_constants
123   [(UNSPECV_BLOCKAGE    0)
124   ])
125 \f
126 (define_insn ""
127   [(set (match_operand:DF 0 "push_operand" "=m")
128         (match_operand:DF 1 "general_operand" "ro<>fyE"))]
129   ""
130   "*
131 {
132   if (FP_REG_P (operands[1]))
133     return \"fmove%.d %f1,%0\";
134   return output_move_double (operands);
135 }")
136
137 (define_insn "pushdi"
138   [(set (match_operand:DI 0 "push_operand" "=m")
139         (match_operand:DI 1 "general_operand" "ro<>Fyi"))]
140   ""
141   "*
142 {
143   return output_move_double (operands);
144 }")
145 \f
146 ;; We don't want to allow a constant operand for test insns because
147 ;; (set (cc0) (const_int foo)) has no mode information.  Such insns will
148 ;; be folded while optimizing anyway.
149
150 (define_expand "tstdi"
151   [(parallel [(set (cc0)
152                    (match_operand:DI 0 "nonimmediate_operand" ""))
153               (clobber (match_scratch:SI 1 ""))
154               (clobber (match_scratch:DI 2 ""))])]
155   ""
156   "m68k_last_compare_had_fp_operands = 0;")
157
158 (define_insn ""
159   [(set (cc0)
160         (match_operand:DI 0 "nonimmediate_operand" "am,d"))
161    (clobber (match_scratch:SI 1 "=X,d"))
162    (clobber (match_scratch:DI 2 "=d,X"))]
163   ""
164   "*
165 {
166   if (which_alternative == 0)
167     {
168       rtx xoperands[2];
169
170       xoperands[0] = operands[2];
171       xoperands[1] = operands[0];
172       output_move_double (xoperands);
173       cc_status.flags |= CC_REVERSED;
174       return \"neg%.l %R2\;negx%.l %2\";
175     }
176   if (find_reg_note (insn, REG_DEAD, operands[0]))
177     {
178       cc_status.flags |= CC_REVERSED;
179       return \"neg%.l %R0\;negx%.l %0\";
180     }
181   else
182     /*
183     ** 'sub' clears %1, and also clears the X cc bit
184     ** 'tst' sets the Z cc bit according to the low part of the DImode operand
185     ** 'subx %1' (i.e. subx #0) acts as a (non-existent) tstx on the high part
186     */
187     return \"sub%.l %1,%1\;tst%.l %R0\;subx%.l %1,%0\";
188 }")
189
190 (define_expand "tstsi"
191   [(set (cc0)
192         (match_operand:SI 0 "nonimmediate_operand" ""))]
193   ""
194   "m68k_last_compare_had_fp_operands = 0;")
195
196 (define_insn ""
197   [(set (cc0)
198         (match_operand:SI 0 "nonimmediate_operand" "rm"))]
199   ""
200   "*
201 {
202   if (TARGET_68020 || TARGET_5200 || ! ADDRESS_REG_P (operands[0]))
203     return \"tst%.l %0\";
204   /* If you think that the 68020 does not support tstl a0,
205      reread page B-167 of the 68020 manual more carefully.  */
206   /* On an address reg, cmpw may replace cmpl.  */
207 #ifdef SGS_CMP_ORDER
208   return \"cmp%.w %0,%#0\";
209 #else
210   return \"cmp%.w %#0,%0\";
211 #endif
212 }")
213
214 ;; This can't use an address register, because comparisons
215 ;; with address registers as second operand always test the whole word.
216 (define_expand "tsthi"
217   [(set (cc0)
218         (match_operand:HI 0 "nonimmediate_operand" ""))]
219   ""
220   "m68k_last_compare_had_fp_operands = 0;")
221
222 (define_insn ""
223   [(set (cc0)
224         (match_operand:HI 0 "nonimmediate_operand" "dm"))]
225   ""
226   "tst%.w %0")
227
228 (define_expand "tstqi"
229   [(set (cc0)
230         (match_operand:QI 0 "nonimmediate_operand" ""))]
231   ""
232   "m68k_last_compare_had_fp_operands = 0;")
233
234 (define_insn ""
235   [(set (cc0)
236         (match_operand:QI 0 "nonimmediate_operand" "dm"))]
237   ""
238   "tst%.b %0")
239
240 (define_expand "tstsf"
241   [(set (cc0)
242         (match_operand:SF 0 "general_operand" ""))]
243   "TARGET_68881"
244   "
245 {
246   m68k_last_compare_had_fp_operands = 1;
247 }")
248
249 (define_insn ""
250   [(set (cc0)
251         (match_operand:SF 0 "general_operand" "fdm"))]
252   "TARGET_68881"
253   "*
254 {
255   cc_status.flags = CC_IN_68881;
256   if (FP_REG_P (operands[0]))
257     return \"ftst%.x %0\";
258   return \"ftst%.s %0\";
259 }")
260
261 (define_expand "tstdf"
262   [(set (cc0)
263         (match_operand:DF 0 "general_operand" ""))]
264   "TARGET_68881"
265   "
266 {
267   m68k_last_compare_had_fp_operands = 1;
268 }")
269
270 (define_insn ""
271   [(set (cc0)
272         (match_operand:DF 0 "general_operand" "fm"))]
273   "TARGET_68881"
274   "*
275 {
276   cc_status.flags = CC_IN_68881;
277   if (FP_REG_P (operands[0]))
278     return \"ftst%.x %0\";
279   return \"ftst%.d %0\";
280 }")
281 \f
282 ;; compare instructions.
283
284 (define_expand "cmpdi"
285   [(parallel
286     [(set (cc0)
287           (compare (match_operand:DI 0 "nonimmediate_operand" "")
288                    (match_operand:DI 1 "general_operand" "")))
289      (clobber (match_dup 2))])]
290   ""
291   "m68k_last_compare_had_fp_operands = 0; operands[2] = gen_reg_rtx (DImode);")
292
293 (define_insn ""
294   [(set (cc0)
295         (compare (match_operand:DI 1 "nonimmediate_operand" "0,d")
296                  (match_operand:DI 2 "general_operand" "d,0")))
297    (clobber (match_operand:DI 0 "register_operand" "=d,d"))]
298   ""
299   "*
300 {
301   if (rtx_equal_p (operands[0], operands[1]))
302     return \"sub%.l %R2,%R0\;subx%.l %2,%0\";
303   else
304     {
305       cc_status.flags |= CC_REVERSED;
306       return \"sub%.l %R1,%R0\;subx%.l %1,%0\";
307     }
308 }")
309
310 ;; This is the second "hook" for PIC code (in addition to movsi). See
311 ;; comment of movsi for a description of PIC handling.
312 (define_expand "cmpsi"
313   [(set (cc0)
314         (compare (match_operand:SI 0 "nonimmediate_operand" "")
315                  (match_operand:SI 1 "general_operand" "")))]
316   ""
317   "
318 {
319   m68k_last_compare_had_fp_operands = 0;
320   if (flag_pic && !TARGET_PCREL && symbolic_operand (operands[1], SImode))
321     {
322       /* The source is an address which requires PIC relocation.
323          Call legitimize_pic_address with the source, mode, and a relocation
324          register (a new pseudo, or the final destination if reload_in_progress
325          is set).   Then fall through normally */
326       rtx temp = reload_in_progress ? operands[0] : gen_reg_rtx (Pmode);
327       operands[1] = legitimize_pic_address (operands[1], SImode, temp);
328     }
329 }")
330
331 ;; A composite of the cmp, cmpa, cmpi & cmpm m68000 op codes.
332 (define_insn ""
333   [(set (cc0)
334         (compare (match_operand:SI 0 "nonimmediate_operand" "rKT,rKs,mSr,mSa,>")
335                  (match_operand:SI 1 "general_src_operand" "mSr,mSa,KTr,Ksr,>")))]
336   "!TARGET_5200"
337   "*
338 {
339   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
340 #ifdef SGS_CMP_ORDER
341     return \"cmpm%.l %0,%1\";
342 #else
343     return \"cmpm%.l %1,%0\";
344 #endif
345   if (REG_P (operands[1])
346       || (!REG_P (operands[0]) && GET_CODE (operands[0]) != MEM))
347     { cc_status.flags |= CC_REVERSED;
348 #ifdef SGS_CMP_ORDER
349       return \"cmp%.l %d1,%d0\";
350 #else
351       return \"cmp%.l %d0,%d1\";
352 #endif
353     }
354   if (ADDRESS_REG_P (operands[0])
355       && GET_CODE (operands[1]) == CONST_INT
356       && INTVAL (operands[1]) < 0x8000
357       && INTVAL (operands[1]) >= -0x8000)
358     {
359 #ifdef SGS_CMP_ORDER
360       return \"cmp%.w %0,%1\";
361 #else
362       return \"cmp%.w %1,%0\";
363 #endif
364     }
365 #ifdef SGS_CMP_ORDER
366   return \"cmp%.l %d0,%d1\";
367 #else
368   return \"cmp%.l %d1,%d0\";
369 #endif
370 }")
371
372 (define_insn ""
373   [(set (cc0)
374         (compare (match_operand:SI 0 "nonimmediate_operand" "mrKs,r")
375                  (match_operand:SI 1 "general_operand" "r,mrKs")))]
376   "TARGET_5200"
377   "*
378 {
379   if (REG_P (operands[1])
380       || (!REG_P (operands[0]) && GET_CODE (operands[0]) != MEM))
381     { cc_status.flags |= CC_REVERSED;
382 #ifdef SGS_CMP_ORDER
383       return \"cmp%.l %d1,%d0\";
384 #else
385       return \"cmp%.l %d0,%d1\";
386 #endif
387     }
388 #ifdef SGS_CMP_ORDER
389   return \"cmp%.l %d0,%d1\";
390 #else
391   return \"cmp%.l %d1,%d0\";
392 #endif
393 }")
394
395 (define_expand "cmphi"
396   [(set (cc0)
397         (compare (match_operand:HI 0 "nonimmediate_src_operand" "")
398                  (match_operand:HI 1 "general_src_operand" "")))]
399   "!TARGET_5200"
400   "m68k_last_compare_had_fp_operands = 0;")
401
402 (define_insn ""
403   [(set (cc0)
404         (compare (match_operand:HI 0 "nonimmediate_src_operand" "rnmS,d,n,mS,>")
405                  (match_operand:HI 1 "general_src_operand" "d,rnmS,mS,n,>")))]
406   "!TARGET_5200"
407   "*
408 {
409   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
410 #ifdef SGS_CMP_ORDER
411     return \"cmpm%.w %0,%1\";
412 #else
413     return \"cmpm%.w %1,%0\";
414 #endif
415   if ((REG_P (operands[1]) && !ADDRESS_REG_P (operands[1]))
416       || (!REG_P (operands[0]) && GET_CODE (operands[0]) != MEM))
417     { cc_status.flags |= CC_REVERSED;
418 #ifdef SGS_CMP_ORDER
419       return \"cmp%.w %d1,%d0\";
420 #else
421       return \"cmp%.w %d0,%d1\";
422 #endif
423     }
424 #ifdef SGS_CMP_ORDER
425   return \"cmp%.w %d0,%d1\";
426 #else
427   return \"cmp%.w %d1,%d0\";
428 #endif
429 }")
430
431 (define_expand "cmpqi"
432   [(set (cc0)
433         (compare (match_operand:QI 0 "nonimmediate_src_operand" "")
434                  (match_operand:QI 1 "general_src_operand" "")))]
435   "!TARGET_5200"
436   "m68k_last_compare_had_fp_operands = 0;")
437
438 (define_insn ""
439   [(set (cc0)
440         (compare (match_operand:QI 0 "nonimmediate_src_operand" "dn,dmS,>")
441                  (match_operand:QI 1 "general_src_operand" "dmS,nd,>")))]
442   "!TARGET_5200"
443   "*
444 {
445   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
446 #ifdef SGS_CMP_ORDER
447     return \"cmpm%.b %0,%1\";
448 #else
449     return \"cmpm%.b %1,%0\";
450 #endif
451   if (REG_P (operands[1])
452       || (!REG_P (operands[0]) && GET_CODE (operands[0]) != MEM))
453     { cc_status.flags |= CC_REVERSED;
454 #ifdef SGS_CMP_ORDER
455       return \"cmp%.b %d1,%d0\";
456 #else
457       return \"cmp%.b %d0,%d1\";
458 #endif
459     }
460 #ifdef SGS_CMP_ORDER
461   return \"cmp%.b %d0,%d1\";
462 #else
463   return \"cmp%.b %d1,%d0\";
464 #endif
465 }")
466
467 (define_expand "cmpdf"
468   [(set (cc0)
469         (compare (match_operand:DF 0 "general_operand" "")
470                  (match_operand:DF 1 "general_operand" "")))]
471   "TARGET_68881"
472   "
473 {
474   m68k_last_compare_had_fp_operands = 1;
475 }")
476
477 (define_insn ""
478   [(set (cc0)
479         (compare (match_operand:DF 0 "general_operand" "f,mG")
480                  (match_operand:DF 1 "general_operand" "fmG,f")))]
481   "TARGET_68881"
482   "*
483 {
484   cc_status.flags = CC_IN_68881;
485 #ifdef SGS_CMP_ORDER
486   if (REG_P (operands[0]))
487     {
488       if (REG_P (operands[1]))
489         return \"fcmp%.x %0,%1\";
490       else
491         return \"fcmp%.d %0,%f1\";
492     }
493   cc_status.flags |= CC_REVERSED;
494   return \"fcmp%.d %1,%f0\";
495 #else
496   if (REG_P (operands[0]))
497     {
498       if (REG_P (operands[1]))
499         return \"fcmp%.x %1,%0\";
500       else
501         return \"fcmp%.d %f1,%0\";
502     }
503   cc_status.flags |= CC_REVERSED;
504   return \"fcmp%.d %f0,%1\";
505 #endif
506 }")
507
508 (define_expand "cmpsf"
509  [(set (cc0)
510        (compare (match_operand:SF 0 "general_operand" "")
511                 (match_operand:SF 1 "general_operand" "")))]
512  "TARGET_68881"
513  "
514 {
515   m68k_last_compare_had_fp_operands = 1;
516 }")
517
518 (define_insn ""
519   [(set (cc0)
520         (compare (match_operand:SF 0 "general_operand" "f,mdG")
521                  (match_operand:SF 1 "general_operand" "fmdG,f")))]
522   "TARGET_68881"
523   "*
524 {
525   cc_status.flags = CC_IN_68881;
526 #ifdef SGS_CMP_ORDER
527   if (FP_REG_P (operands[0]))
528     {
529       if (FP_REG_P (operands[1]))
530         return \"fcmp%.x %0,%1\";
531       else
532         return \"fcmp%.s %0,%f1\";
533     }
534   cc_status.flags |= CC_REVERSED;
535   return \"fcmp%.s %1,%f0\";
536 #else
537   if (FP_REG_P (operands[0]))
538     {
539       if (FP_REG_P (operands[1]))
540         return \"fcmp%.x %1,%0\";
541       else
542         return \"fcmp%.s %f1,%0\";
543     }
544   cc_status.flags |= CC_REVERSED;
545   return \"fcmp%.s %f0,%1\";
546 #endif
547 }")
548 \f
549 ;; Recognizers for btst instructions.
550
551 ;; Coldfire/5200 only allows "<Q>" type addresses when the bit position is
552 ;; specified as a constant, so we must disable all patterns that may extract
553 ;; from a MEM at a constant bit position if we can't use this as a constraint.
554
555 (define_insn ""
556   [(set (cc0) (zero_extract (match_operand:QI 0 "memory_src_operand" "oS")
557                             (const_int 1)
558                             (minus:SI (const_int 7)
559                                       (match_operand:SI 1 "general_operand" "di"))))]
560   "!TARGET_5200"
561   "* { return output_btst (operands, operands[1], operands[0], insn, 7); }")
562
563 ;; This is the same as the above pattern except for the constraints.  The 'i'
564 ;; has been deleted.
565
566 (define_insn ""
567   [(set (cc0) (zero_extract (match_operand:QI 0 "memory_operand" "o")
568                             (const_int 1)
569                             (minus:SI (const_int 7)
570                                       (match_operand:SI 1 "general_operand" "d"))))]
571   "TARGET_5200"
572   "* { return output_btst (operands, operands[1], operands[0], insn, 7); }")
573
574 (define_insn ""
575   [(set (cc0) (zero_extract (match_operand:SI 0 "register_operand" "d")
576                             (const_int 1)
577                             (minus:SI (const_int 31)
578                                       (match_operand:SI 1 "general_operand" "di"))))]
579   ""
580   "* { return output_btst (operands, operands[1], operands[0], insn, 31); }")
581
582 ;; The following two patterns are like the previous two
583 ;; except that they use the fact that bit-number operands
584 ;; are automatically masked to 3 or 5 bits.
585
586 (define_insn ""
587   [(set (cc0) (zero_extract (match_operand:QI 0 "memory_operand" "o")
588                             (const_int 1)
589                             (minus:SI (const_int 7)
590                                       (and:SI
591                                        (match_operand:SI 1 "register_operand" "d")
592                                        (const_int 7)))))]
593   ""
594   "* { return output_btst (operands, operands[1], operands[0], insn, 7); }")
595
596 (define_insn ""
597   [(set (cc0) (zero_extract (match_operand:SI 0 "register_operand" "d")
598                             (const_int 1)
599                             (minus:SI (const_int 31)
600                                       (and:SI
601                                        (match_operand:SI 1 "register_operand" "d")
602                                        (const_int 31)))))]
603   ""
604   "* { return output_btst (operands, operands[1], operands[0], insn, 31); }")
605
606 ;; Nonoffsettable mem refs are ok in this one pattern
607 ;; since we don't try to adjust them.
608 (define_insn ""
609   [(set (cc0) (zero_extract (match_operand:QI 0 "memory_operand" "m")
610                             (const_int 1)
611                             (match_operand:SI 1 "const_int_operand" "n")))]
612   "(unsigned) INTVAL (operands[1]) < 8 && !TARGET_5200"
613   "*
614 {
615   operands[1] = GEN_INT (7 - INTVAL (operands[1]));
616   return output_btst (operands, operands[1], operands[0], insn, 7);
617 }")
618
619 (define_insn ""
620   [(set (cc0) (zero_extract (match_operand:SI 0 "register_operand" "do")
621                             (const_int 1)
622                             (match_operand:SI 1 "const_int_operand" "n")))]
623   "!TARGET_5200"
624   "*
625 {
626   if (GET_CODE (operands[0]) == MEM)
627     {
628       operands[0] = adjust_address (operands[0], QImode,
629                                     INTVAL (operands[1]) / 8);
630       operands[1] = GEN_INT (7 - INTVAL (operands[1]) % 8);
631       return output_btst (operands, operands[1], operands[0], insn, 7);
632     }
633   operands[1] = GEN_INT (31 - INTVAL (operands[1]));
634   return output_btst (operands, operands[1], operands[0], insn, 31);
635 }")
636
637 ;; This is the same as the above pattern except for the constraints.
638 ;; The 'o' has been replaced with 'Q'.
639
640 (define_insn ""
641   [(set (cc0) (zero_extract (match_operand:SI 0 "register_operand" "dQ")
642                             (const_int 1)
643                             (match_operand:SI 1 "const_int_operand" "n")))]
644   "TARGET_5200"
645   "*
646 {
647   if (GET_CODE (operands[0]) == MEM)
648     {
649       operands[0] = adjust_address (operands[0], QImode,
650                                     INTVAL (operands[1]) / 8);
651       operands[1] = GEN_INT (7 - INTVAL (operands[1]) % 8);
652       return output_btst (operands, operands[1], operands[0], insn, 7);
653     }
654   operands[1] = GEN_INT (31 - INTVAL (operands[1]));
655   return output_btst (operands, operands[1], operands[0], insn, 31);
656 }")
657
658 \f
659 ;; move instructions
660
661 ;; A special case in which it is not desirable
662 ;; to reload the constant into a data register.
663 (define_insn "pushexthisi_const"
664   [(set (match_operand:SI 0 "push_operand" "=m")
665         (match_operand:SI 1 "const_int_operand" "J"))]
666   "INTVAL (operands[1]) >= -0x8000 && INTVAL (operands[1]) < 0x8000"
667   "*
668 {
669   if (operands[1] == const0_rtx)
670     return \"clr%.l %0\";
671   return \"pea %a1\";
672 }")
673
674 ;This is never used.
675 ;(define_insn "swapsi"
676 ;  [(set (match_operand:SI 0 "nonimmediate_operand" "+r")
677 ;       (match_operand:SI 1 "general_operand" "+r"))
678 ;   (set (match_dup 1) (match_dup 0))]
679 ;  ""
680 ;  "exg %1,%0")
681
682 ;; Special case of fullword move when source is zero.
683 ;; The reason this is special is to avoid loading a zero
684 ;; into a data reg with moveq in order to store it elsewhere.
685
686 (define_insn "movsi_const0"
687   [(set (match_operand:SI 0 "nonimmediate_operand" "=g")
688         (const_int 0))]
689   ;; clr insns on 68000 read before writing.
690   ;; This isn't so on the 68010, but we have no TARGET_68010.
691   "((TARGET_68020 || TARGET_5200)
692     || !(GET_CODE (operands[0]) == MEM && MEM_VOLATILE_P (operands[0])))"
693   "*
694 {
695   if (ADDRESS_REG_P (operands[0]))
696     {
697       /* On the '040, 'subl an,an' takes 2 clocks while lea takes only 1 */
698       if (!TARGET_68040 && !TARGET_68060)
699         return \"sub%.l %0,%0\";
700       else
701         {
702 #ifdef MOTOROLA
703 #ifdef SGS
704           /* Many SGS assemblers croak on size specifiers for constants.  */
705           return \"lea 0,%0\";
706 #else
707           return \"lea 0.w,%0\";
708 #endif
709 #else
710           return \"lea 0:w,%0\";
711 #endif
712         }
713     }
714   /* moveq is faster on the 68000.  */
715   if (DATA_REG_P (operands[0]) && (!TARGET_68020 && !TARGET_5200))
716     return \"moveq %#0,%0\";
717   return \"clr%.l %0\";
718 }")
719
720 ;; General case of fullword move.
721 ;;
722 ;; This is the main "hook" for PIC code.  When generating
723 ;; PIC, movsi is responsible for determining when the source address
724 ;; needs PIC relocation and appropriately calling legitimize_pic_address
725 ;; to perform the actual relocation.
726 ;;
727 ;; In both the PIC and non-PIC cases the patterns generated will
728 ;; matched by the next define_insn.
729 (define_expand "movsi"
730   [(set (match_operand:SI 0 "nonimmediate_operand" "")
731         (match_operand:SI 1 "general_operand" ""))]
732   ""
733   "
734 {
735   if (flag_pic && !TARGET_PCREL && symbolic_operand (operands[1], SImode))
736     {
737       /* The source is an address which requires PIC relocation.
738          Call legitimize_pic_address with the source, mode, and a relocation
739          register (a new pseudo, or the final destination if reload_in_progress
740          is set).   Then fall through normally */
741       rtx temp = reload_in_progress ? operands[0] : gen_reg_rtx (Pmode);
742       operands[1] = legitimize_pic_address (operands[1], SImode, temp);
743     }
744   else if (flag_pic && TARGET_PCREL && ! reload_in_progress)
745     {
746       /* Don't allow writes to memory except via a register;
747          the m68k doesn't consider PC-relative addresses to be writable.  */
748       if (symbolic_operand (operands[0], SImode))
749         operands[0] = force_reg (SImode, XEXP (operands[0], 0));
750       else if (GET_CODE (operands[0]) == MEM
751                && symbolic_operand (XEXP (operands[0], 0), SImode))
752         operands[0] = gen_rtx (MEM, SImode,
753                                force_reg (SImode, XEXP (operands[0], 0)));
754     }
755 }")
756
757 ;; General case of fullword move.  The register constraints
758 ;; force integer constants in range for a moveq to be reloaded
759 ;; if they are headed for memory.
760 (define_insn ""
761   ;; Notes: make sure no alternative allows g vs g.
762   ;; We don't allow f-regs since fixed point cannot go in them.
763   [(set (match_operand:SI 0 "nonimmediate_operand" "=g,d,a<")
764         (match_operand:SI 1 "general_src_operand" "daymSKT,n,i"))]
765
766   "!TARGET_5200"
767   "*
768 {
769   return output_move_simode (operands);
770 }")
771
772 (define_insn ""
773   [(set (match_operand:SI 0 "nonimmediate_operand" "=r<Q>,g")
774         (match_operand:SI 1 "general_operand" "g,r<Q>"))]
775   "TARGET_5200"
776   "* return output_move_simode (operands);")
777
778 ;; Special case of fullword move, where we need to get a non-GOT PIC
779 ;; reference into an address register.
780 (define_insn ""
781   [(set (match_operand:SI 0 "nonimmediate_operand" "=a<")
782         (match_operand:SI 1 "pcrel_address" ""))]
783   "TARGET_PCREL"
784   "*
785 {
786   if (push_operand (operands[0], SImode))
787     return \"pea %a1\";
788   return \"lea %a1,%0\";
789 }")
790
791 (define_expand "movhi"
792   [(set (match_operand:HI 0 "nonimmediate_operand" "")
793         (match_operand:HI 1 "general_operand" ""))]
794   ""
795   "")
796
797 (define_insn ""
798   [(set (match_operand:HI 0 "nonimmediate_operand" "=g")
799         (match_operand:HI 1 "general_src_operand" "gS"))]
800   "!TARGET_5200"
801   "* return output_move_himode (operands);")
802
803  (define_insn ""
804   [(set (match_operand:HI 0 "nonimmediate_operand" "=r<Q>,g")
805         (match_operand:HI 1 "general_operand" "g,r<Q>"))]
806   "TARGET_5200"
807   "* return output_move_himode (operands);")
808
809 (define_expand "movstricthi"
810   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" ""))
811         (match_operand:HI 1 "general_src_operand" ""))]
812   ""
813   "")
814
815 (define_insn ""
816   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+dm"))
817         (match_operand:HI 1 "general_src_operand" "rmSn"))]
818   "!TARGET_5200"
819   "* return output_move_stricthi (operands);")
820
821 (define_insn ""
822   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+d,m"))
823         (match_operand:HI 1 "general_src_operand" "rmn,r"))]
824   "TARGET_5200"
825   "* return output_move_stricthi (operands);")
826
827 (define_expand "movqi"
828   [(set (match_operand:QI 0 "nonimmediate_operand" "")
829         (match_operand:QI 1 "general_src_operand" ""))]
830   ""
831   "")
832
833 (define_insn ""
834   [(set (match_operand:QI 0 "nonimmediate_operand" "=d,*a,m")
835         (match_operand:QI 1 "general_src_operand" "dmSi*a,di*a,dmSi"))]
836   "!TARGET_5200"
837   "* return output_move_qimode (operands);")
838
839 (define_insn ""
840   [(set (match_operand:QI 0 "nonimmediate_operand" "=d<Q>,dm,d*a")
841         (match_operand:QI 1 "general_src_operand" "dmi,d<Q>,di*a"))]
842   "TARGET_5200"
843   "* return output_move_qimode (operands);")
844
845 (define_expand "movstrictqi"
846   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
847         (match_operand:QI 1 "general_src_operand" ""))]
848   ""
849   "")
850
851 (define_insn ""
852   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+dm"))
853         (match_operand:QI 1 "general_src_operand" "dmSn"))]
854   "!TARGET_5200"
855   "* return output_move_strictqi (operands);")
856
857 (define_insn ""
858   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+d,m"))
859         (match_operand:QI 1 "general_src_operand" "dmn,d"))]
860   "TARGET_5200"
861   "* return output_move_strictqi (operands);")
862
863 (define_expand "pushqi1"
864   [(set (reg:SI 15) (plus:SI (reg:SI 15) (const_int -2)))
865    (set (mem:QI (plus:SI (reg:SI 15) (const_int 1)))
866         (match_operand:QI 0 "general_operand" ""))]
867   "!TARGET_5200"
868   "")
869
870 (define_expand "movsf"
871   [(set (match_operand:SF 0 "nonimmediate_operand" "")
872         (match_operand:SF 1 "general_operand" ""))]
873   ""
874   "")
875
876 (define_insn ""
877   [(set (match_operand:SF 0 "nonimmediate_operand" "=rmf")
878         (match_operand:SF 1 "general_operand" "rmfF"))]
879   "!TARGET_5200"
880   "*
881 {
882   if (FP_REG_P (operands[0]))
883     {
884       if (FP_REG_P (operands[1]))
885         return \"f%$move%.x %1,%0\";
886       else if (ADDRESS_REG_P (operands[1]))
887         return \"move%.l %1,%-\;f%$move%.s %+,%0\";
888       else if (GET_CODE (operands[1]) == CONST_DOUBLE)
889         return output_move_const_single (operands);
890       return \"f%$move%.s %f1,%0\";
891     }
892   if (FP_REG_P (operands[1]))
893     {
894       if (ADDRESS_REG_P (operands[0]))
895         return \"fmove%.s %1,%-\;move%.l %+,%0\";
896       return \"fmove%.s %f1,%0\";
897     }
898   if (operands[1] == CONST0_RTX (SFmode)
899       /* clr insns on 68000 read before writing.
900          This isn't so on the 68010, but we have no TARGET_68010.  */
901       && ((TARGET_68020 || TARGET_5200)
902           || !(GET_CODE (operands[0]) == MEM && MEM_VOLATILE_P (operands[0]))))
903     {
904       if (ADDRESS_REG_P (operands[0]))
905         {
906           /* On the '040, 'subl an,an' takes 2 clocks while lea takes only 1 */
907           if (!TARGET_68040 && !TARGET_68060)
908             return \"sub%.l %0,%0\";
909           else
910             {
911 #ifdef MOTOROLA
912 #ifdef SGS
913               /* Many SGS assemblers croak on size specifiers for constants.  */
914               return \"lea 0,%0\";
915 #else
916               return \"lea 0.w,%0\";
917 #endif
918 #else
919               return \"lea 0:w,%0\";
920 #endif
921             }
922         }
923       /* moveq is faster on the 68000.  */
924       if (DATA_REG_P (operands[0]) && !(TARGET_68020 || TARGET_5200))
925         {
926           return \"moveq %#0,%0\";
927         }
928       return \"clr%.l %0\";
929     }
930   return \"move%.l %1,%0\";
931 }")
932
933 (define_insn ""
934   [(set (match_operand:SF 0 "nonimmediate_operand" "=r,g")
935         (match_operand:SF 1 "general_operand" "g,r"))]
936   "TARGET_5200"
937   "* return \"move%.l %1,%0\";")
938
939 (define_expand "movdf"
940   [(set (match_operand:DF 0 "nonimmediate_operand" "")
941         (match_operand:DF 1 "general_operand" ""))]
942   ""
943   "")
944
945 (define_insn ""
946   [(set (match_operand:DF 0 "nonimmediate_operand" "=rm,rf,rf,&rof<>")
947         (match_operand:DF 1 "general_operand" "*rf,m,0,*rofE<>"))]
948 ;  [(set (match_operand:DF 0 "nonimmediate_operand" "=rm,&rf,&rof<>")
949 ;       (match_operand:DF 1 "general_operand" "rf,m,rofF<>"))]
950   "!TARGET_5200"
951   "*
952 {
953   if (FP_REG_P (operands[0]))
954     {
955       if (FP_REG_P (operands[1]))
956         return \"f%&move%.x %1,%0\";
957       if (REG_P (operands[1]))
958         {
959           rtx xoperands[2];
960           xoperands[1] = gen_rtx_REG (SImode, REGNO (operands[1]) + 1);
961           output_asm_insn (\"move%.l %1,%-\", xoperands);
962           output_asm_insn (\"move%.l %1,%-\", operands);
963           return \"f%&move%.d %+,%0\";
964         }
965       if (GET_CODE (operands[1]) == CONST_DOUBLE)
966         return output_move_const_double (operands);
967       return \"f%&move%.d %f1,%0\";
968     }
969   else if (FP_REG_P (operands[1]))
970     {
971       if (REG_P (operands[0]))
972         {
973           output_asm_insn (\"fmove%.d %f1,%-\;move%.l %+,%0\", operands);
974           operands[0] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
975           return \"move%.l %+,%0\";
976         }
977       else
978         return \"fmove%.d %f1,%0\";
979     }
980   return output_move_double (operands);
981 }")
982
983 (define_insn ""
984   [(set (match_operand:DF 0 "nonimmediate_operand" "=r,g")
985         (match_operand:DF 1 "general_operand" "g,r"))]
986   "TARGET_5200"
987   "* return output_move_double (operands);")
988
989 ;; ??? The XFmode patterns are schizophrenic about whether constants are
990 ;; allowed.  Most but not all have predicates and constraint that disallow
991 ;; constants.  Most but not all have output templates that handle constants.
992 ;; See also LEGITIMATE_CONSTANT_P.
993
994 (define_expand "movxf"
995   [(set (match_operand:XF 0 "nonimmediate_operand" "")
996         (match_operand:XF 1 "general_operand" ""))]
997   ""
998   "
999 {
1000   /* We can't rewrite operands during reload.  */
1001   if (! reload_in_progress)
1002     {
1003       if (CONSTANT_P (operands[1]))
1004         {
1005           operands[1] = force_const_mem (XFmode, operands[1]);
1006           if (! memory_address_p (XFmode, XEXP (operands[1], 0)))
1007             operands[1] = adjust_address (operands[1], XFmode, 0);
1008         }
1009       if (flag_pic && TARGET_PCREL)
1010         {
1011           /* Don't allow writes to memory except via a register; the
1012              m68k doesn't consider PC-relative addresses to be writable.  */
1013           if (GET_CODE (operands[0]) == MEM
1014               && symbolic_operand (XEXP (operands[0], 0), SImode))
1015             operands[0] = gen_rtx (MEM, XFmode,
1016                                    force_reg (SImode, XEXP (operands[0], 0)));
1017         }
1018     }
1019 }")
1020
1021 (define_insn ""
1022   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,!r,!f,!r")
1023         (match_operand:XF 1 "nonimmediate_operand" "m,f,f,f,r,!r"))]
1024   "TARGET_68881"
1025   "*
1026 {
1027   if (FP_REG_P (operands[0]))
1028     {
1029       if (FP_REG_P (operands[1]))
1030         return \"fmove%.x %1,%0\";
1031       if (REG_P (operands[1]))
1032         {
1033           rtx xoperands[2];
1034           xoperands[1] = gen_rtx_REG (SImode, REGNO (operands[1]) + 2);
1035           output_asm_insn (\"move%.l %1,%-\", xoperands);
1036           xoperands[1] = gen_rtx_REG (SImode, REGNO (operands[1]) + 1);
1037           output_asm_insn (\"move%.l %1,%-\", xoperands);
1038           output_asm_insn (\"move%.l %1,%-\", operands);
1039           return \"fmove%.x %+,%0\";
1040         }
1041       if (GET_CODE (operands[1]) == CONST_DOUBLE)
1042         return \"fmove%.x %1,%0\";
1043       return \"fmove%.x %f1,%0\";
1044     }
1045   if (FP_REG_P (operands[1]))
1046     {
1047       if (REG_P (operands[0]))
1048         {
1049           output_asm_insn (\"fmove%.x %f1,%-\;move%.l %+,%0\", operands);
1050           operands[0] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1051           output_asm_insn (\"move%.l %+,%0\", operands);
1052           operands[0] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1053           return \"move%.l %+,%0\";
1054         }
1055       /* Must be memory destination.  */
1056       return \"fmove%.x %f1,%0\";
1057     }
1058   return output_move_double (operands);
1059 }
1060 ")
1061
1062 (define_insn ""
1063   [(set (match_operand:XF 0 "nonimmediate_operand" "=rm,rf,&rof<>")
1064         (match_operand:XF 1 "nonimmediate_operand" "rf,m,rof<>"))]
1065   "! TARGET_68881 && ! TARGET_5200"
1066   "*
1067 {
1068   if (FP_REG_P (operands[0]))
1069     {
1070       if (FP_REG_P (operands[1]))
1071         return \"fmove%.x %1,%0\";
1072       if (REG_P (operands[1]))
1073         {
1074           rtx xoperands[2];
1075           xoperands[1] = gen_rtx_REG (SImode, REGNO (operands[1]) + 2);
1076           output_asm_insn (\"move%.l %1,%-\", xoperands);
1077           xoperands[1] = gen_rtx_REG (SImode, REGNO (operands[1]) + 1);
1078           output_asm_insn (\"move%.l %1,%-\", xoperands);
1079           output_asm_insn (\"move%.l %1,%-\", operands);
1080           return \"fmove%.x %+,%0\";
1081         }
1082       if (GET_CODE (operands[1]) == CONST_DOUBLE)
1083         return \"fmove%.x %1,%0\";
1084       return \"fmove%.x %f1,%0\";
1085     }
1086   if (FP_REG_P (operands[1]))
1087     {
1088       if (REG_P (operands[0]))
1089         {
1090           output_asm_insn (\"fmove%.x %f1,%-\;move%.l %+,%0\", operands);
1091           operands[0] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1092           output_asm_insn (\"move%.l %+,%0\", operands);
1093           operands[0] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1094           return \"move%.l %+,%0\";
1095         }
1096       else
1097         return \"fmove%.x %f1,%0\";
1098     }
1099   return output_move_double (operands);
1100 }
1101 ")
1102
1103 (define_insn ""
1104   [(set (match_operand:XF 0 "nonimmediate_operand" "=r,g")
1105         (match_operand:XF 1 "nonimmediate_operand" "g,r"))]
1106   "! TARGET_68881 && TARGET_5200"
1107   "* return output_move_double (operands);")
1108
1109 (define_expand "movdi"
1110   ;; Let's see if it really still needs to handle fp regs, and, if so, why.
1111   [(set (match_operand:DI 0 "nonimmediate_operand" "")
1112         (match_operand:DI 1 "general_operand" ""))]
1113   ""
1114   "")
1115
1116 ;; movdi can apply to fp regs in some cases
1117 (define_insn ""
1118   ;; Let's see if it really still needs to handle fp regs, and, if so, why.
1119   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r,&ro<>")
1120         (match_operand:DI 1 "general_operand" "rF,m,roi<>F"))]
1121 ;  [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,&r,&ro<>,!&rm,!&f")
1122 ;       (match_operand:DI 1 "general_operand" "r,m,roi<>,fF"))]
1123 ;  [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,&rf,&ro<>,!&rm,!&f")
1124 ;       (match_operand:DI 1 "general_operand" "r,m,roi<>,fF,rfF"))]
1125   "!TARGET_5200"
1126   "*
1127 {
1128   if (FP_REG_P (operands[0]))
1129     {
1130       if (FP_REG_P (operands[1]))
1131         return \"fmove%.x %1,%0\";
1132       if (REG_P (operands[1]))
1133         {
1134           rtx xoperands[2];
1135           xoperands[1] = gen_rtx_REG (SImode, REGNO (operands[1]) + 1);
1136           output_asm_insn (\"move%.l %1,%-\", xoperands);
1137           output_asm_insn (\"move%.l %1,%-\", operands);
1138           return \"fmove%.d %+,%0\";
1139         }
1140       if (GET_CODE (operands[1]) == CONST_DOUBLE)
1141         return output_move_const_double (operands);
1142       return \"fmove%.d %f1,%0\";
1143     }
1144   else if (FP_REG_P (operands[1]))
1145     {
1146       if (REG_P (operands[0]))
1147         {
1148           output_asm_insn (\"fmove%.d %f1,%-\;move%.l %+,%0\", operands);
1149           operands[0] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1150           return \"move%.l %+,%0\";
1151         }
1152       else
1153         return \"fmove%.d %f1,%0\";
1154     }
1155   return output_move_double (operands);
1156 }")
1157
1158 (define_insn ""
1159   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,g")
1160         (match_operand:DI 1 "general_operand" "g,r"))]
1161   "TARGET_5200"
1162   "* return output_move_double (operands);")
1163
1164 ;; Thus goes after the move instructions
1165 ;; because the move instructions are better (require no spilling)
1166 ;; when they can apply.  It goes before the add/sub insns
1167 ;; so we will prefer it to them.
1168
1169 (define_insn "pushasi"
1170   [(set (match_operand:SI 0 "push_operand" "=m")
1171         (match_operand:SI 1 "address_operand" "p"))]
1172   ""
1173   "pea %a1")
1174 \f
1175 ;; truncation instructions
1176 (define_insn "truncsiqi2"
1177   [(set (match_operand:QI 0 "nonimmediate_operand" "=dm,d")
1178         (truncate:QI
1179          (match_operand:SI 1 "general_src_operand" "doJS,i")))]
1180   ""
1181   "*
1182 {
1183   if (GET_CODE (operands[0]) == REG)
1184     {
1185       /* Must clear condition codes, since the move.l bases them on
1186          the entire 32 bits, not just the desired 8 bits.  */
1187       CC_STATUS_INIT;
1188       return \"move%.l %1,%0\";
1189     }
1190   if (GET_CODE (operands[1]) == MEM)
1191     operands[1] = adjust_address (operands[1], QImode, 3);
1192   return \"move%.b %1,%0\";
1193 }")
1194
1195 (define_insn "trunchiqi2"
1196   [(set (match_operand:QI 0 "nonimmediate_operand" "=dm,d")
1197         (truncate:QI
1198          (match_operand:HI 1 "general_src_operand" "doJS,i")))]
1199   ""
1200   "*
1201 {
1202   if (GET_CODE (operands[0]) == REG
1203       && (GET_CODE (operands[1]) == MEM
1204           || GET_CODE (operands[1]) == CONST_INT))
1205     {
1206       /* Must clear condition codes, since the move.w bases them on
1207          the entire 16 bits, not just the desired 8 bits.  */
1208       CC_STATUS_INIT;
1209       return \"move%.w %1,%0\";
1210     }
1211   if (GET_CODE (operands[0]) == REG)
1212     {
1213       /* Must clear condition codes, since the move.l bases them on
1214          the entire 32 bits, not just the desired 8 bits.  */
1215       CC_STATUS_INIT;
1216       return \"move%.l %1,%0\";
1217     }
1218   if (GET_CODE (operands[1]) == MEM)
1219     operands[1] = adjust_address (operands[1], QImode, 1);
1220   return \"move%.b %1,%0\";
1221 }")
1222
1223 (define_insn "truncsihi2"
1224   [(set (match_operand:HI 0 "nonimmediate_operand" "=dm,d")
1225         (truncate:HI
1226          (match_operand:SI 1 "general_src_operand" "roJS,i")))]
1227   ""
1228   "*
1229 {
1230   if (GET_CODE (operands[0]) == REG)
1231     {
1232       /* Must clear condition codes, since the move.l bases them on
1233          the entire 32 bits, not just the desired 8 bits.  */
1234       CC_STATUS_INIT;
1235       return \"move%.l %1,%0\";
1236     }
1237   if (GET_CODE (operands[1]) == MEM)
1238     operands[1] = adjust_address (operands[1], QImode, 2);
1239   return \"move%.w %1,%0\";
1240 }")
1241 \f
1242 ;; zero extension instructions
1243
1244 (define_insn "zero_extendqidi2"
1245   [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
1246         (zero_extend:DI (match_operand:QI 1 "general_operand" "dm")))]
1247   ""
1248   "*
1249 {
1250   CC_STATUS_INIT;
1251   operands[2] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1252   return \"moveq %#0,%0\;moveq %#0,%2\;move%.b %1,%2\";
1253 }")
1254
1255 (define_insn "zero_extendhidi2"
1256   [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
1257         (zero_extend:DI (match_operand:HI 1 "general_operand" "rm")))]
1258   ""
1259   "*
1260 {
1261   CC_STATUS_INIT;
1262   operands[2] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1263   return \"moveq %#0,%0\;moveq %#0,%2\;move%.w %1,%2\";
1264 }")
1265
1266 ;; this is the canonical form for (lshiftrt:DI x 32)
1267 (define_expand "zero_extendsidi2"
1268   [(set (match_operand:DI 0 "nonimmediate_operand" "")
1269     (zero_extend:DI (match_operand:SI 1 "general_operand" "")))]
1270   ""
1271   "")
1272
1273 (define_insn "*zero_extendsidi2_cf"
1274   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,m")
1275     (zero_extend:DI (match_operand:SI 1 "general_operand" "rm,r")))]
1276   "TARGET_5200"
1277   "*
1278 {
1279   CC_STATUS_INIT;
1280   if (GET_CODE (operands[0]) == REG)
1281     operands[2] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1282   else if (GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
1283     return \"move%.l %1,%0\;clr%.l %0\";
1284   else if (GET_CODE (XEXP (operands[0], 0)) == POST_INC)
1285     return \"clr%.l %0\;move%.l %1,%0\";
1286   else
1287     operands[2] = adjust_address (operands[0], SImode, 4);
1288   if (GET_CODE (operands[1]) != REG || GET_CODE (operands[2]) != REG
1289       || REGNO (operands[1]) != REGNO (operands[2]))
1290     output_asm_insn (\"move%.l %1,%2\", operands);
1291   if (ADDRESS_REG_P (operands[0]))
1292     return \"sub%.l %0,%0\";
1293   else
1294     return \"clr%.l %0\";
1295 }")
1296
1297 (define_insn "*zero_extendsidi2"
1298   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
1299     (zero_extend:DI (match_operand:SI 1 "general_operand" "rm")))]
1300   "!TARGET_5200"
1301   "*
1302 {
1303   CC_STATUS_INIT;
1304   if (GET_CODE (operands[0]) == REG)
1305     operands[2] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1306   else if (GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
1307     return \"move%.l %1,%0\;clr%.l %0\";
1308   else if (GET_CODE (XEXP (operands[0], 0)) == POST_INC)
1309     return \"clr%.l %0\;move%.l %1,%0\";
1310   else
1311     operands[2] = adjust_address (operands[0], SImode, 4);
1312   if (GET_CODE (operands[1]) != REG || GET_CODE (operands[2]) != REG
1313       || REGNO (operands[1]) != REGNO (operands[2]))
1314     output_asm_insn (\"move%.l %1,%2\", operands);
1315   if (ADDRESS_REG_P (operands[0]))
1316     return \"sub%.l %0,%0\";
1317   else
1318     return \"clr%.l %0\";
1319 }")
1320
1321 (define_expand "zero_extendhisi2"
1322   [(set (match_operand:SI 0 "register_operand" "")
1323         (const_int 0))
1324    (set (strict_low_part (match_dup 2))
1325         (match_operand:HI 1 "general_operand" ""))]
1326   ""
1327   "
1328 {
1329   operands[1] = make_safe_from (operands[1], operands[0]);
1330   operands[2] = gen_lowpart_SUBREG (HImode, operands[0]);
1331 }")
1332
1333 (define_expand "zero_extendqihi2"
1334   [(set (match_operand:HI 0 "register_operand" "")
1335         (const_int 0))
1336    (set (strict_low_part (match_dup 2))
1337         (match_operand:QI 1 "general_operand" ""))]
1338   ""
1339   "
1340 {
1341   operands[1] = make_safe_from (operands[1], operands[0]);
1342   operands[2] = gen_lowpart_SUBREG (QImode, operands[0]);
1343 }")
1344
1345 (define_expand "zero_extendqisi2"
1346   [(set (match_operand:SI 0 "register_operand" "")
1347         (const_int 0))
1348    (set (strict_low_part (match_dup 2))
1349         (match_operand:QI 1 "general_operand" ""))]
1350   ""
1351   "
1352 {
1353   operands[1] = make_safe_from (operands[1], operands[0]);
1354   operands[2] = gen_lowpart_SUBREG (QImode, operands[0]);
1355 }")
1356 \f
1357 ;; Patterns to recognize zero-extend insns produced by the combiner.
1358 ;; We don't allow both operands in memory, because of aliasing problems.
1359 ;; Explicitly disallow two memory operands via the condition since reloading
1360 ;; of this case will result in worse code than the uncombined patterns.
1361
1362 (define_insn ""
1363   [(set (match_operand:SI 0 "nonimmediate_operand" "=do<>,d<")
1364         (zero_extend:SI (match_operand:HI 1 "nonimmediate_src_operand" "r,mS")))]
1365   "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1366   "*
1367 {
1368   if (DATA_REG_P (operands[0]))
1369     {
1370       if (GET_CODE (operands[1]) == REG
1371           && REGNO (operands[0]) == REGNO (operands[1]))
1372         return \"and%.l %#0xFFFF,%0\";
1373       if (reg_mentioned_p (operands[0], operands[1]))
1374         return \"move%.w %1,%0\;and%.l %#0xFFFF,%0\";
1375       return \"clr%.l %0\;move%.w %1,%0\";
1376     }
1377   else if (GET_CODE (operands[0]) == MEM
1378            && GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
1379     return \"move%.w %1,%0\;clr%.w %0\";
1380   else if (GET_CODE (operands[0]) == MEM
1381            && GET_CODE (XEXP (operands[0], 0)) == POST_INC)
1382     return \"clr%.w %0\;move%.w %1,%0\";
1383   else
1384     {
1385       output_asm_insn (\"clr%.w %0\", operands);
1386       operands[0] = adjust_address (operands[0], HImode, 2);
1387       return \"move%.w %1,%0\";
1388     }
1389 }")
1390
1391 (define_insn ""
1392   [(set (match_operand:HI 0 "nonimmediate_operand" "=do<>,d")
1393         (zero_extend:HI (match_operand:QI 1 "nonimmediate_src_operand" "d,mS")))]
1394   "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1395   "*
1396 {
1397   if (DATA_REG_P (operands[0]))
1398     {
1399       if (GET_CODE (operands[1]) == REG
1400           && REGNO (operands[0]) == REGNO (operands[1]))
1401         return (!TARGET_5200 ? \"and%.w %#0xFF,%0\" : \"and%.l %#0xFF,%0\");
1402       if (reg_mentioned_p (operands[0], operands[1]))
1403         return (!TARGET_5200 ? \"move%.b %1,%0\;and%.w %#0xFF,%0\" 
1404                              : \"move%.b %1,%0\;and%.l %#0xFF,%0\");
1405       return \"clr%.w %0\;move%.b %1,%0\";
1406     }
1407   else if (GET_CODE (operands[0]) == MEM
1408            && GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
1409     {
1410       if (REGNO (XEXP (XEXP (operands[0], 0), 0))
1411           == STACK_POINTER_REGNUM)
1412         {
1413           output_asm_insn (\"clr%.w %-\", operands);
1414           operands[0] = gen_rtx_MEM (GET_MODE (operands[0]),
1415                                      plus_constant (stack_pointer_rtx, 1));
1416           return \"move%.b %1,%0\";
1417         }
1418       else
1419         return \"move%.b %1,%0\;clr%.b %0\";
1420     }
1421   else if (GET_CODE (operands[0]) == MEM
1422            && GET_CODE (XEXP (operands[0], 0)) == POST_INC)
1423     return \"clr%.b %0\;move%.b %1,%0\";
1424   else
1425     {
1426       output_asm_insn (\"clr%.b %0\", operands);
1427       operands[0] = adjust_address (operands[0], QImode, 1);
1428       return \"move%.b %1,%0\";
1429     }
1430 }")
1431
1432 (define_insn ""
1433   [(set (match_operand:SI 0 "nonimmediate_operand" "=do<>,d")
1434         (zero_extend:SI (match_operand:QI 1 "nonimmediate_src_operand" "d,mS")))]
1435   "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1436   "*
1437 {
1438   if (DATA_REG_P (operands[0]))
1439     {
1440       if (GET_CODE (operands[1]) == REG
1441           && REGNO (operands[0]) == REGNO (operands[1]))
1442         return \"and%.l %#0xFF,%0\";
1443       if (reg_mentioned_p (operands[0], operands[1]))
1444         return \"move%.b %1,%0\;and%.l %#0xFF,%0\";
1445       return \"clr%.l %0\;move%.b %1,%0\";
1446     }
1447   else if (GET_CODE (operands[0]) == MEM
1448            && GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
1449     {
1450       operands[0] = XEXP (XEXP (operands[0], 0), 0);
1451 #ifdef MOTOROLA
1452 #ifdef SGS
1453       return \"clr%.l -(%0)\;move%.b %1,3(%0)\";
1454 #else
1455       return \"clr%.l -(%0)\;move%.b %1,(3,%0)\";
1456 #endif
1457 #else
1458       return \"clrl %0@-\;moveb %1,%0@(3)\";
1459 #endif
1460     }
1461   else if (GET_CODE (operands[0]) == MEM
1462            && GET_CODE (XEXP (operands[0], 0)) == POST_INC)
1463     {
1464       operands[0] = XEXP (XEXP (operands[0], 0), 0);
1465 #ifdef MOTOROLA
1466 #ifdef SGS
1467       return \"clr%.l (%0)+\;move%.b %1,-1(%0)\";
1468 #else
1469       return \"clr%.l (%0)+\;move%.b %1,(-1,%0)\";
1470 #endif
1471 #else
1472       return \"clrl %0@+\;moveb %1,%0@(-1)\";
1473 #endif
1474     }
1475   else
1476     {
1477       output_asm_insn (\"clr%.l %0\", operands);
1478       operands[0] = adjust_address (operands[0], QImode, 3);
1479       return \"move%.b %1,%0\";
1480     }
1481 }")
1482 \f
1483 ;; sign extension instructions
1484
1485 (define_insn "extendqidi2"
1486   [(set (match_operand:DI 0 "nonimmediate_operand" "=d")
1487         (sign_extend:DI (match_operand:QI 1 "general_src_operand" "rmS")))]
1488   ""
1489   "*
1490 {
1491   CC_STATUS_INIT;
1492   operands[2] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1493   if (TARGET_68020 || TARGET_5200)
1494     return \"move%.b %1,%2\;extb%.l %2\;smi %0\;extb%.l %0\";
1495   else
1496     return \"move%.b %1,%2\;ext%.w %0\;ext%.l %2\;move%.l %2,%0\;smi %0\";
1497 }")
1498
1499 (define_insn "extendhidi2"
1500   [(set (match_operand:DI 0 "nonimmediate_operand" "=d")
1501         (sign_extend:DI
1502          (match_operand:HI 1 "general_src_operand" "rmS")))]
1503   ""
1504   "*
1505 {
1506   CC_STATUS_INIT;
1507   operands[2] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1508   if (TARGET_68020 || TARGET_5200)
1509     return \"move%.w %1,%2\;ext%.l %2\;smi %0\;extb%.l %0\";
1510   else
1511     return \"move%.w %1,%2\;ext%.l %2\;smi %0\;ext%.w %0\;ext%.l %0\";
1512 }")
1513
1514 (define_insn "extendsidi2"
1515   [(set (match_operand:DI 0 "nonimmediate_operand" "=d")
1516         (sign_extend:DI
1517          (match_operand:SI 1 "general_operand" "rm")))]
1518   ""
1519   "*
1520 {
1521   CC_STATUS_INIT;
1522   operands[2] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1523   if (TARGET_68020 || TARGET_5200)
1524     return \"move%.l %1,%2\;smi %0\;extb%.l %0\";
1525   else
1526     return \"move%.l %1,%2\;smi %0\;ext%.w %0\;ext%.l %0\";
1527 }")
1528
1529 ;; Special case when one can avoid register clobbering, copy and test
1530 ;; Maybe there is a way to make that the general case, by forcing the
1531 ;; result of the SI tree to be in the lower register of the DI target
1532
1533 (define_insn "extendplussidi"
1534   [(set (match_operand:DI 0 "register_operand" "=d")
1535     (sign_extend:DI (plus:SI (match_operand:SI 1 "general_operand" "%rmn")
1536             (match_operand:SI 2 "general_operand" "rmn"))))]
1537   ""
1538   "*
1539 {
1540   CC_STATUS_INIT;
1541   operands[3] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1542   if (GET_CODE (operands[1]) == CONST_INT
1543   && (unsigned) INTVAL (operands[1]) > 8)
1544     {
1545       rtx tmp = operands[1];
1546
1547       operands[1] = operands[2];
1548       operands[2] = tmp;
1549     }
1550   if (GET_CODE (operands[1]) == REG
1551       && REGNO (operands[1]) == REGNO (operands[3]))
1552     output_asm_insn (\"add%.l %2,%3\", operands);
1553   else
1554     output_asm_insn (\"move%.l %2,%3\;add%.l %1,%3\", operands);
1555   if (TARGET_68020 || TARGET_5200)
1556     return \"smi %0\;extb%.l %0\";
1557   else
1558     return \"smi %0\;ext%.w %0\;ext%.l %0\";
1559 }")
1560
1561 (define_insn "extendhisi2"
1562   [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,a")
1563         (sign_extend:SI
1564          (match_operand:HI 1 "nonimmediate_src_operand" "0,rmS")))]
1565   ""
1566   "*
1567 {
1568   if (ADDRESS_REG_P (operands[0]))
1569     return \"move%.w %1,%0\";
1570   return \"ext%.l %0\";
1571 }")
1572
1573 (define_insn "extendqihi2"
1574   [(set (match_operand:HI 0 "nonimmediate_operand" "=d")
1575         (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "0")))]
1576   ""
1577   "ext%.w %0")
1578
1579 (define_insn "extendqisi2"
1580   [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
1581         (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "0")))]
1582   "TARGET_68020 || TARGET_5200"
1583   "extb%.l %0")
1584 \f
1585 ;; Conversions between float and double.
1586
1587 (define_expand "extendsfdf2"
1588   [(set (match_operand:DF 0 "nonimmediate_operand" "")
1589         (float_extend:DF
1590          (match_operand:SF 1 "general_operand" "")))]
1591   "TARGET_68881"
1592   "")
1593
1594 (define_insn ""
1595   [(set (match_operand:DF 0 "nonimmediate_operand" "=*fdm,f")
1596         (float_extend:DF
1597           (match_operand:SF 1 "general_operand" "f,dmF")))]
1598   "TARGET_68881"
1599   "*
1600 {
1601   if (FP_REG_P (operands[0]) && FP_REG_P (operands[1]))
1602     {
1603       if (REGNO (operands[0]) == REGNO (operands[1]))
1604         {
1605           /* Extending float to double in an fp-reg is a no-op.
1606              NOTICE_UPDATE_CC has already assumed that the
1607              cc will be set.  So cancel what it did.  */
1608           cc_status = cc_prev_status;
1609           return \"\";
1610         }
1611       return \"f%&move%.x %1,%0\";
1612     }
1613   if (FP_REG_P (operands[0]))
1614     return \"f%&move%.s %f1,%0\";
1615   if (DATA_REG_P (operands[0]) && FP_REG_P (operands[1]))
1616     {
1617       output_asm_insn (\"fmove%.d %f1,%-\;move%.l %+,%0\", operands);
1618       operands[0] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1619       return \"move%.l %+,%0\";
1620     }
1621   return \"fmove%.d %f1,%0\";
1622 }")
1623
1624 ;; This cannot output into an f-reg because there is no way to be
1625 ;; sure of truncating in that case.
1626 (define_expand "truncdfsf2"
1627   [(set (match_operand:SF 0 "nonimmediate_operand" "")
1628         (float_truncate:SF
1629           (match_operand:DF 1 "general_operand" "")))]
1630   "TARGET_68881"
1631   "")
1632
1633 ;; On the '040 we can truncate in a register accurately and easily.
1634 (define_insn ""
1635   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
1636         (float_truncate:SF
1637           (match_operand:DF 1 "general_operand" "fmG")))]
1638   "TARGET_68040_ONLY"
1639   "*
1640 {
1641   if (FP_REG_P (operands[1]))
1642     return \"f%$move%.x %1,%0\";
1643   return \"f%$move%.d %f1,%0\";
1644 }")
1645
1646 (define_insn ""
1647   [(set (match_operand:SF 0 "nonimmediate_operand" "=dm")
1648         (float_truncate:SF
1649           (match_operand:DF 1 "general_operand" "f")))]
1650   "TARGET_68881"
1651   "fmove%.s %f1,%0")
1652 \f
1653 ;; Conversion between fixed point and floating point.
1654 ;; Note that among the fix-to-float insns
1655 ;; the ones that start with SImode come first.
1656 ;; That is so that an operand that is a CONST_INT
1657 ;; (and therefore lacks a specific machine mode).
1658 ;; will be recognized as SImode (which is always valid)
1659 ;; rather than as QImode or HImode.
1660
1661 (define_expand "floatsisf2"
1662   [(set (match_operand:SF 0 "nonimmediate_operand" "")
1663         (float:SF (match_operand:SI 1 "general_operand" "")))]
1664   "TARGET_68881"
1665   "")
1666
1667 (define_insn ""
1668   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
1669         (float:SF (match_operand:SI 1 "general_operand" "dmi")))]
1670   "TARGET_68881"
1671   "f%$move%.l %1,%0")
1672
1673 (define_expand "floatsidf2"
1674   [(set (match_operand:DF 0 "nonimmediate_operand" "")
1675         (float:DF (match_operand:SI 1 "general_operand" "")))]
1676   "TARGET_68881"
1677   "")
1678
1679 (define_insn ""
1680   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
1681         (float:DF (match_operand:SI 1 "general_operand" "dmi")))]
1682   "TARGET_68881"
1683   "f%&move%.l %1,%0")
1684
1685 (define_insn "floathisf2"
1686   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
1687         (float:SF (match_operand:HI 1 "general_operand" "dmn")))]
1688   "TARGET_68881"
1689   "f%$move%.w %1,%0")
1690
1691 (define_insn "floathidf2"
1692   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
1693         (float:DF (match_operand:HI 1 "general_operand" "dmn")))]
1694   "TARGET_68881"
1695   "fmove%.w %1,%0")
1696
1697 (define_insn "floatqisf2"
1698   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
1699         (float:SF (match_operand:QI 1 "general_operand" "dmn")))]
1700   "TARGET_68881"
1701   "fmove%.b %1,%0")
1702
1703 (define_insn "floatqidf2"
1704   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
1705         (float:DF (match_operand:QI 1 "general_operand" "dmn")))]
1706   "TARGET_68881"
1707   "f%&move%.b %1,%0")
1708
1709 ;; New routines to convert floating-point values to integers
1710 ;; to be used on the '040.  These should be faster than trapping
1711 ;; into the kernel to emulate fintrz.  They should also be faster
1712 ;; than calling the subroutines fixsfsi or fixdfsi.
1713
1714 (define_insn "fix_truncdfsi2"
1715   [(set (match_operand:SI 0 "nonimmediate_operand" "=dm")
1716         (fix:SI (fix:DF (match_operand:DF 1 "register_operand" "f"))))
1717    (clobber (match_scratch:SI 2 "=d"))
1718    (clobber (match_scratch:SI 3 "=d"))]
1719   "TARGET_68881 && TARGET_68040"
1720   "*
1721 {
1722   CC_STATUS_INIT;
1723   return \"fmovem%.l %!,%2\;moveq %#16,%3\;or%.l %2,%3\;and%.w %#-33,%3\;fmovem%.l %3,%!\;fmove%.l %1,%0\;fmovem%.l %2,%!\";
1724 }")
1725
1726 (define_insn "fix_truncdfhi2"
1727   [(set (match_operand:HI 0 "nonimmediate_operand" "=dm")
1728         (fix:HI (fix:DF (match_operand:DF 1 "register_operand" "f"))))
1729    (clobber (match_scratch:SI 2 "=d"))
1730    (clobber (match_scratch:SI 3 "=d"))]
1731   "TARGET_68881 && TARGET_68040"
1732   "*
1733 {
1734   CC_STATUS_INIT;
1735   return \"fmovem%.l %!,%2\;moveq %#16,%3\;or%.l %2,%3\;and%.w %#-33,%3\;fmovem%.l %3,%!\;fmove%.w %1,%0\;fmovem%.l %2,%!\";
1736 }")
1737
1738 (define_insn "fix_truncdfqi2"
1739   [(set (match_operand:QI 0 "nonimmediate_operand" "=dm")
1740         (fix:QI (fix:DF (match_operand:DF 1 "register_operand" "f"))))
1741    (clobber (match_scratch:SI 2 "=d"))
1742    (clobber (match_scratch:SI 3 "=d"))]
1743   "TARGET_68881 && TARGET_68040"
1744   "*
1745 {
1746   CC_STATUS_INIT;
1747   return \"fmovem%.l %!,%2\;moveq %#16,%3\;or%.l %2,%3\;and%.w %#-33,%3\;fmovem%.l %3,%!\;fmove%.b %1,%0\;fmovem%.l %2,%!\";
1748 }")
1749
1750 ;; Convert a float to a float whose value is an integer.
1751 ;; This is the first stage of converting it to an integer type.
1752
1753 (define_insn "ftruncdf2"
1754   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
1755         (fix:DF (match_operand:DF 1 "general_operand" "fFm")))]
1756   "TARGET_68881 && !TARGET_68040"
1757   "*
1758 {
1759   if (FP_REG_P (operands[1]))
1760     return \"fintrz%.x %f1,%0\";
1761   return \"fintrz%.d %f1,%0\";
1762 }")
1763
1764 (define_insn "ftruncsf2"
1765   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
1766         (fix:SF (match_operand:SF 1 "general_operand" "dfFm")))]
1767   "TARGET_68881 && !TARGET_68040"
1768   "*
1769 {
1770   if (FP_REG_P (operands[1]))
1771     return \"fintrz%.x %f1,%0\";
1772   return \"fintrz%.s %f1,%0\";
1773 }")
1774
1775 ;; Convert a float whose value is an integer
1776 ;; to an actual integer.  Second stage of converting float to integer type.
1777 (define_insn "fixsfqi2"
1778   [(set (match_operand:QI 0 "nonimmediate_operand" "=dm")
1779         (fix:QI (match_operand:SF 1 "general_operand" "f")))]
1780   "TARGET_68881"
1781   "fmove%.b %1,%0")
1782
1783 (define_insn "fixsfhi2"
1784   [(set (match_operand:HI 0 "nonimmediate_operand" "=dm")
1785         (fix:HI (match_operand:SF 1 "general_operand" "f")))]
1786   "TARGET_68881"
1787   "fmove%.w %1,%0")
1788
1789 (define_insn "fixsfsi2"
1790   [(set (match_operand:SI 0 "nonimmediate_operand" "=dm")
1791         (fix:SI (match_operand:SF 1 "general_operand" "f")))]
1792   "TARGET_68881"
1793   "fmove%.l %1,%0")
1794
1795 (define_insn "fixdfqi2"
1796   [(set (match_operand:QI 0 "nonimmediate_operand" "=dm")
1797         (fix:QI (match_operand:DF 1 "general_operand" "f")))]
1798   "TARGET_68881"
1799   "fmove%.b %1,%0")
1800
1801 (define_insn "fixdfhi2"
1802   [(set (match_operand:HI 0 "nonimmediate_operand" "=dm")
1803         (fix:HI (match_operand:DF 1 "general_operand" "f")))]
1804   "TARGET_68881"
1805   "fmove%.w %1,%0")
1806
1807 (define_insn "fixdfsi2"
1808   [(set (match_operand:SI 0 "nonimmediate_operand" "=dm")
1809         (fix:SI (match_operand:DF 1 "general_operand" "f")))]
1810   "TARGET_68881"
1811   "fmove%.l %1,%0")
1812 \f
1813 ;; add instructions
1814
1815 (define_insn "adddi_lshrdi_63"
1816   [(set (match_operand:DI 0 "nonimmediate_operand" "=d")
1817     (plus:DI (lshiftrt:DI (match_operand:DI 1 "general_operand" "rm")
1818             (const_int 63))
1819         (match_dup 1)))
1820    (clobber (match_scratch:SI 2 "=d"))]
1821   ""
1822   "*
1823 {
1824   operands[3] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1825   if (REG_P (operands[1]) && REGNO (operands[1]) == REGNO (operands[0]))
1826     return
1827     \"move%.l %1,%2\;add%.l %2,%2\;subx%.l %2,%2\;sub%.l %2,%3\;subx%.l %2,%0\";
1828   if (GET_CODE (operands[1]) == REG)
1829     operands[4] = gen_rtx_REG (SImode, REGNO (operands[1]) + 1);
1830   else if (GET_CODE (XEXP (operands[1], 0)) == POST_INC
1831         || GET_CODE (XEXP (operands[1], 0)) == PRE_DEC)
1832     operands[4] = operands[1];
1833   else
1834     operands[4] = adjust_address (operands[1], SImode, 4);
1835   if (GET_CODE (operands[1]) == MEM
1836    && GET_CODE (XEXP (operands[1], 0)) == PRE_DEC)
1837     output_asm_insn (\"move%.l %4,%3\", operands);
1838   output_asm_insn (\"move%.l %1,%0\;smi %2\", operands);
1839   if (TARGET_68020 || TARGET_5200)
1840     output_asm_insn (\"extb%.l %2\", operands);
1841   else
1842     output_asm_insn (\"ext%.w %2\;ext%.l %2\", operands);
1843   if (GET_CODE (operands[1]) != MEM
1844    || GET_CODE (XEXP (operands[1], 0)) != PRE_DEC)
1845     output_asm_insn (\"move%.l %4,%3\", operands);
1846   return \"sub%.l %2,%3\;subx%.l %2,%0\";
1847 }")
1848
1849 (define_insn "adddi_sexthishl32"
1850   [(set (match_operand:DI 0 "nonimmediate_operand" "=o,a,*d,*d")
1851     (plus:DI (ashift:DI (sign_extend:DI
1852           (match_operand:HI 1 "general_operand" "rm,rm,rm,rm"))
1853             (const_int 32))
1854         (match_operand:DI 2 "general_operand" "0,0,0,0")))
1855    (clobber (match_scratch:SI 3 "=&d,X,a,?d"))]
1856   "!TARGET_5200"
1857   "*
1858 {
1859   CC_STATUS_INIT;
1860   if (ADDRESS_REG_P (operands[0]))
1861     return \"add%.w %1,%0\";
1862   else if (ADDRESS_REG_P (operands[3]))
1863     return \"move%.w %1,%3\;add%.l %3,%0\";
1864   else
1865     return \"move%.w %1,%3\;ext%.l %3\;add%.l %3,%0\";
1866 } ")
1867
1868 (define_insn "adddi_dilshr32"
1869   [(set (match_operand:DI 0 "nonimmediate_operand" "=d,o")
1870 ;;    (plus:DI (match_operand:DI 2 "general_operand" "%0")
1871 ;;      (lshiftrt:DI (match_operand:DI 1 "general_operand" "ro")
1872 ;;            (const_int 32))))]
1873     (plus:DI (lshiftrt:DI (match_operand:DI 1 "general_operand" "ro,d")
1874             (const_int 32))
1875         (match_operand:DI 2 "general_operand" "0,0")))]
1876   ""
1877   "*
1878 {
1879   CC_STATUS_INIT;
1880   if (GET_CODE (operands[0]) == REG)
1881     operands[2] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
1882   else
1883     operands[2] = adjust_address (operands[0], SImode, 4);
1884   return \"add%.l %1,%2\;negx%.l %0\;neg%.l %0\";
1885 } ")
1886
1887 (define_insn "adddi_dishl32"
1888   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
1889 ;;    (plus:DI (match_operand:DI 2 "general_operand" "%0")
1890 ;;      (ashift:DI (match_operand:DI 1 "general_operand" "ro")
1891 ;;            (const_int 32))))]
1892     (plus:DI (ashift:DI (match_operand:DI 1 "general_operand" "ro,d")
1893             (const_int 32))
1894         (match_operand:DI 2 "general_operand" "0,0")))]
1895   ""
1896   "*
1897 {
1898   CC_STATUS_INIT;
1899   if (GET_CODE (operands[1]) == REG)
1900     operands[1] = gen_rtx_REG (SImode, REGNO (operands[1]) + 1);
1901   else
1902     operands[1] = adjust_address (operands[1], SImode, 4);
1903   return \"add%.l %1,%0\";
1904 } ")
1905
1906 (define_insn "adddi3"
1907   [(set (match_operand:DI 0 "nonimmediate_operand" "=<,o<>,d,d,d")
1908         (plus:DI (match_operand:DI 1 "general_operand" "%0,0,0,0,0")
1909                  (match_operand:DI 2 "general_operand" "<,d,no>,d,a")))
1910    (clobber (match_scratch:SI 3 "=X,&d,&d,X,&d"))]
1911   ""
1912   "*
1913 {
1914   if (DATA_REG_P (operands[0]))
1915     {
1916       if (DATA_REG_P (operands[2]))
1917         return \"add%.l %R2,%R0\;addx%.l %2,%0\";
1918       else if (GET_CODE (operands[2]) == MEM
1919           && GET_CODE (XEXP (operands[2], 0)) == POST_INC)
1920         return \"move%.l %2,%3\;add%.l %2,%R0\;addx%.l %3,%0\";
1921       else
1922         {
1923           rtx high, low;
1924           rtx xoperands[2];
1925
1926           if (GET_CODE (operands[2]) == REG)
1927             {
1928               low = gen_rtx_REG (SImode, REGNO (operands[2]) + 1);
1929               high = operands[2];
1930             }
1931           else if (CONSTANT_P (operands[2]))
1932             split_double (operands[2], &high, &low);
1933           else
1934             {
1935               low = adjust_address (operands[2], SImode, 4);
1936               high = operands[2];
1937             }
1938
1939           operands[1] = low, operands[2] = high;
1940           xoperands[0] = operands[3];
1941           if (GET_CODE (operands[1]) == CONST_INT
1942               && INTVAL (operands[1]) >= -8 && INTVAL (operands[1]) < 0)
1943             xoperands[1] = GEN_INT (-INTVAL (operands[2]) - 1);
1944           else
1945             xoperands[1] = operands[2];
1946
1947           output_asm_insn (output_move_simode (xoperands), xoperands);
1948           if (GET_CODE (operands[1]) == CONST_INT)
1949             {
1950               if (INTVAL (operands[1]) > 0 && INTVAL (operands[1]) <= 8)
1951                 return \"addq%.l %1,%R0\;addx%.l %3,%0\";
1952               else if (INTVAL (operands[1]) >= -8 && INTVAL (operands[1]) < 0)
1953                 {
1954                   operands[1] = GEN_INT (-INTVAL (operands[1]));
1955                   return \"subq%.l %1,%R0\;subx%.l %3,%0\";
1956                 }
1957             }
1958           return \"add%.l %1,%R0\;addx%.l %3,%0\";
1959         }
1960     }
1961   else if (GET_CODE (operands[0]) == MEM)
1962     {
1963       if (GET_CODE (operands[2]) == MEM
1964           && GET_CODE (XEXP (operands[2], 0)) == PRE_DEC)
1965         return \"add%.l %2,%0\;addx%.l %2,%0\";
1966       CC_STATUS_INIT;
1967       if (GET_CODE (XEXP (operands[0], 0)) == POST_INC)
1968         {
1969           operands[1] = gen_rtx_MEM (SImode,
1970                                      plus_constant (XEXP(operands[0], 0), -8));
1971           return \"move%.l %0,%3\;add%.l %R2,%0\;addx%.l %2,%3\;move%.l %3,%1\";
1972         }
1973       else if (GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
1974         {
1975           operands[1] = XEXP(operands[0], 0);
1976           return \"add%.l %R2,%0\;move%.l %0,%3\;addx%.l %2,%3\;move%.l %3,%1\";
1977         }
1978       else
1979         {
1980           operands[1] = adjust_address (operands[0], SImode, 4);
1981           return \"add%.l %R2,%1\;move%.l %0,%3\;addx%.l %2,%3\;move%.l %3,%0\";
1982         }
1983     }
1984   else
1985     abort ();
1986 } ")
1987
1988 (define_insn "addsi_lshrsi_31"
1989   [(set (match_operand:SI 0 "nonimmediate_operand" "=dm")
1990     (plus:SI (lshiftrt:SI (match_operand:SI 1 "general_operand" "rm")
1991             (const_int 31))
1992         (match_dup 1)))]
1993   ""
1994   "*
1995 {
1996   operands[2] = operands[0];
1997   operands[3] = gen_label_rtx();
1998   if (GET_CODE (operands[0]) == MEM)
1999     {
2000       if (GET_CODE (XEXP (operands[0], 0)) == POST_INC)
2001         operands[0] = gen_rtx_MEM (SImode, XEXP (XEXP (operands[0], 0), 0));
2002       else if (GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
2003         operands[2] = gen_rtx_MEM (SImode, XEXP (XEXP (operands[0], 0), 0));
2004     }
2005   output_asm_insn (\"move%.l %1,%0\", operands);
2006 #ifdef MOTOROLA
2007   output_asm_insn (\"jbpl %l3\", operands);
2008 #else
2009   output_asm_insn (\"jpl %l3\", operands);
2010 #endif
2011   output_asm_insn (\"addq%.l %#1,%2\", operands);
2012   (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
2013                                 CODE_LABEL_NUMBER (operands[3]));
2014   return \"\";
2015 }")
2016
2017 (define_expand "addsi3"
2018   [(set (match_operand:SI 0 "nonimmediate_operand" "")
2019         (plus:SI (match_operand:SI 1 "general_operand" "")
2020                  (match_operand:SI 2 "general_src_operand" "")))]
2021   ""
2022   "")
2023
2024 ;; Note that the middle two alternatives are near-duplicates
2025 ;; in order to handle insns generated by reload.
2026 ;; This is needed since they are not themselves reloaded,
2027 ;; so commutativity won't apply to them.
2028 (define_insn "*addsi3_internal"
2029   [(set (match_operand:SI 0 "nonimmediate_operand" "=m,?a,?a,d,a")
2030         (plus:SI (match_operand:SI 1 "general_operand" "%0,a,rJK,0,0")
2031                  (match_operand:SI 2 "general_src_operand" "dIKLT,rJK,a,mSrIKLT,mSrIKLs")))]
2032
2033
2034   "! TARGET_5200"
2035   "* return output_addsi3 (operands);")
2036
2037 (define_insn "*addsi3_5200"
2038   [(set (match_operand:SI 0 "nonimmediate_operand" "=m,?a,?a,r")
2039         (plus:SI (match_operand:SI 1 "general_operand" "%0,a,rJK,0")
2040                  (match_operand:SI 2 "general_src_operand" "d,rJK,a,mrIKLs")))]
2041   "TARGET_5200"
2042   "* return output_addsi3 (operands);")
2043
2044 (define_insn ""
2045   [(set (match_operand:SI 0 "nonimmediate_operand" "=a")
2046         (plus:SI (match_operand:SI 1 "general_operand" "0")
2047                  (sign_extend:SI
2048                   (match_operand:HI 2 "nonimmediate_src_operand" "rmS"))))]
2049   "!TARGET_5200"
2050   "add%.w %2,%0")
2051
2052 (define_insn "addhi3"
2053   [(set (match_operand:HI 0 "nonimmediate_operand" "=m,r")
2054         (plus:HI (match_operand:HI 1 "general_operand" "%0,0")
2055                  (match_operand:HI 2 "general_src_operand" "dn,rmSn")))]
2056   "!TARGET_5200"
2057   "*
2058 {
2059   if (GET_CODE (operands[2]) == CONST_INT)
2060     {
2061       /* If the constant would be a negative number when interpreted as
2062          HImode, make it negative.  This is usually, but not always, done
2063          elsewhere in the compiler.  First check for constants out of range,
2064          which could confuse us.  */
2065
2066       if (INTVAL (operands[2]) >= 32768)
2067         operands[2] = GEN_INT (INTVAL (operands[2]) - 65536);
2068
2069       if (INTVAL (operands[2]) > 0
2070           && INTVAL (operands[2]) <= 8)
2071         return \"addq%.w %2,%0\";
2072       if (INTVAL (operands[2]) < 0
2073           && INTVAL (operands[2]) >= -8)
2074         {
2075           operands[2] = GEN_INT (- INTVAL (operands[2]));
2076           return \"subq%.w %2,%0\";
2077         }
2078       /* On the CPU32 it is faster to use two addqw instructions to
2079          add a small integer (8 < N <= 16) to a register.  
2080          Likewise for subqw.  */
2081       if (TARGET_CPU32 && REG_P (operands[0]))
2082         {
2083           if (INTVAL (operands[2]) > 8
2084               && INTVAL (operands[2]) <= 16)
2085             {
2086               operands[2] = GEN_INT (INTVAL (operands[2]) - 8);
2087               return \"addq%.w %#8,%0\;addq%.w %2,%0\";
2088             }
2089           if (INTVAL (operands[2]) < -8
2090               && INTVAL (operands[2]) >= -16)
2091             {
2092               operands[2] = GEN_INT (- INTVAL (operands[2]) - 8);
2093               return \"subq%.w %#8,%0\;subq%.w %2,%0\";
2094             }
2095         }
2096       if (ADDRESS_REG_P (operands[0]) && !TARGET_68040)
2097 #ifdef MOTOROLA  
2098             return \"lea (%c2,%0),%0\";
2099 #else
2100             return \"lea %0@(%c2),%0\";
2101 #endif
2102     }
2103   return \"add%.w %2,%0\";
2104 }")
2105
2106 ;; These insns must use MATCH_DUP instead of the more expected
2107 ;; use of a matching constraint because the "output" here is also
2108 ;; an input, so you can't use the matching constraint.  That also means
2109 ;; that you can't use the "%", so you need patterns with the matched
2110 ;; operand in both positions.
2111
2112 (define_insn ""
2113   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+m,d"))
2114         (plus:HI (match_dup 0)
2115                  (match_operand:HI 1 "general_src_operand" "dn,rmSn")))]
2116   "!TARGET_5200"
2117   "*
2118 {
2119   if (GET_CODE (operands[1]) == CONST_INT)
2120     {
2121       /* If the constant would be a negative number when interpreted as
2122          HImode, make it negative.  This is usually, but not always, done
2123          elsewhere in the compiler.  First check for constants out of range,
2124          which could confuse us.  */
2125
2126       if (INTVAL (operands[1]) >= 32768)
2127         operands[1] = GEN_INT (INTVAL (operands[1]) - 65536);
2128
2129       if (INTVAL (operands[1]) > 0
2130           && INTVAL (operands[1]) <= 8)
2131         return \"addq%.w %1,%0\";
2132       if (INTVAL (operands[1]) < 0
2133           && INTVAL (operands[1]) >= -8)
2134         {
2135           operands[1] = GEN_INT (- INTVAL (operands[1]));
2136           return \"subq%.w %1,%0\";
2137         }
2138       /* On the CPU32 it is faster to use two addqw instructions to
2139          add a small integer (8 < N <= 16) to a register. 
2140          Likewise for subqw.  */
2141       if (TARGET_CPU32 && REG_P (operands[0]))
2142         {
2143           if (INTVAL (operands[1]) > 8
2144               && INTVAL (operands[1]) <= 16)
2145             {
2146               operands[1] = GEN_INT (INTVAL (operands[1]) - 8);
2147               return \"addq%.w %#8,%0\;addq%.w %1,%0\";
2148             }
2149           if (INTVAL (operands[1]) < -8
2150               && INTVAL (operands[1]) >= -16)
2151             {
2152               operands[1] = GEN_INT (- INTVAL (operands[1]) - 8);
2153               return \"subq%.w %#8,%0\;subq%.w %1,%0\";
2154             }
2155         }
2156       if (ADDRESS_REG_P (operands[0]) && !TARGET_68040)
2157 #ifdef MOTOROLA  
2158             return \"lea (%c1,%0),%0\";
2159 #else
2160             return \"lea %0@(%c1),%0\";
2161 #endif
2162     }
2163   return \"add%.w %1,%0\";
2164 }")
2165
2166 (define_insn ""
2167   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+m,d"))
2168         (plus:HI (match_operand:HI 1 "general_src_operand" "dn,rmSn")
2169                  (match_dup 0)))]
2170   "!TARGET_5200"
2171   "*
2172 {
2173   if (GET_CODE (operands[1]) == CONST_INT)
2174     {
2175       /* If the constant would be a negative number when interpreted as
2176          HImode, make it negative.  This is usually, but not always, done
2177          elsewhere in the compiler.  First check for constants out of range,
2178          which could confuse us.  */
2179
2180       if (INTVAL (operands[1]) >= 32768)
2181         operands[1] = GEN_INT (INTVAL (operands[1]) - 65536);
2182
2183       if (INTVAL (operands[1]) > 0
2184           && INTVAL (operands[1]) <= 8)
2185         return \"addq%.w %1,%0\";
2186       if (INTVAL (operands[1]) < 0
2187           && INTVAL (operands[1]) >= -8)
2188         {
2189           operands[1] = GEN_INT (- INTVAL (operands[1]));
2190           return \"subq%.w %1,%0\";
2191         }
2192       /* On the CPU32 it is faster to use two addqw instructions to
2193          add a small integer (8 < N <= 16) to a register.
2194          Likewise for subqw.  */
2195       if (TARGET_CPU32 && REG_P (operands[0])) 
2196         {
2197           if (INTVAL (operands[1]) > 8
2198               && INTVAL (operands[1]) <= 16)
2199             {
2200               operands[1] = GEN_INT (INTVAL (operands[1]) - 8);
2201               return \"addq%.w %#8,%0\;addq%.w %1,%0\";
2202             }
2203           if (INTVAL (operands[1]) < -8
2204               && INTVAL (operands[1]) >= -16)
2205             {
2206               operands[1] = GEN_INT (- INTVAL (operands[1]) - 8);
2207               return \"subq%.w %#8,%0\;subq%.w %1,%0\";
2208             }
2209         }
2210       if (ADDRESS_REG_P (operands[0]) && !TARGET_68040)
2211 #ifdef MOTOROLA  
2212             return \"lea (%c1,%0),%0\";
2213 #else
2214             return \"lea %0@(%c1),%0\";
2215 #endif
2216     }
2217   return \"add%.w %1,%0\";
2218 }")
2219
2220 (define_insn "addqi3"
2221   [(set (match_operand:QI 0 "nonimmediate_operand" "=m,d")
2222         (plus:QI (match_operand:QI 1 "general_operand" "%0,0")
2223                  (match_operand:QI 2 "general_src_operand" "dn,dmSn")))]
2224   "!TARGET_5200"
2225   "*
2226 {
2227   if (GET_CODE (operands[2]) == CONST_INT)
2228     {
2229       if (INTVAL (operands[2]) >= 128)
2230         operands[2] = GEN_INT (INTVAL (operands[2]) - 256);
2231
2232       if (INTVAL (operands[2]) > 0
2233           && INTVAL (operands[2]) <= 8)
2234         return \"addq%.b %2,%0\";
2235       if (INTVAL (operands[2]) < 0 && INTVAL (operands[2]) >= -8)
2236        {
2237          operands[2] = GEN_INT (- INTVAL (operands[2]));
2238          return \"subq%.b %2,%0\";
2239        }
2240     }
2241   return \"add%.b %2,%0\";
2242 }")
2243
2244 (define_insn ""
2245   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+m,d"))
2246         (plus:QI (match_dup 0)
2247                  (match_operand:QI 1 "general_src_operand" "dn,dmSn")))]
2248   "!TARGET_5200"
2249   "*
2250 {
2251   if (GET_CODE (operands[1]) == CONST_INT)
2252     {
2253       if (INTVAL (operands[1]) >= 128)
2254         operands[1] = GEN_INT (INTVAL (operands[1]) - 256);
2255
2256       if (INTVAL (operands[1]) > 0
2257           && INTVAL (operands[1]) <= 8)
2258         return \"addq%.b %1,%0\";
2259       if (INTVAL (operands[1]) < 0 && INTVAL (operands[1]) >= -8)
2260        {
2261          operands[1] = GEN_INT (- INTVAL (operands[1]));
2262          return \"subq%.b %1,%0\";
2263        }
2264     }
2265   return \"add%.b %1,%0\";
2266 }")
2267
2268 (define_insn ""
2269   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+m,d"))
2270         (plus:QI (match_operand:QI 1 "general_src_operand" "dn,dmSn")
2271                  (match_dup 0)))]
2272   "!TARGET_5200"
2273   "*
2274 {
2275   if (GET_CODE (operands[1]) == CONST_INT)
2276     {
2277       if (INTVAL (operands[1]) >= 128)
2278         operands[1] = GEN_INT (INTVAL (operands[1]) - 256);
2279
2280       if (INTVAL (operands[1]) > 0
2281           && INTVAL (operands[1]) <= 8)
2282         return \"addq%.b %1,%0\";
2283       if (INTVAL (operands[1]) < 0 && INTVAL (operands[1]) >= -8)
2284        {
2285          operands[1] = GEN_INT (- INTVAL (operands[1]));
2286          return \"subq%.b %1,%0\";
2287        }
2288     }
2289   return \"add%.b %1,%0\";
2290 }")
2291
2292 (define_expand "adddf3"
2293   [(set (match_operand:DF 0 "nonimmediate_operand" "")
2294         (plus:DF (match_operand:DF 1 "general_operand" "")
2295                  (match_operand:DF 2 "general_operand" "")))]
2296   "TARGET_68881"
2297   "")
2298
2299 (define_insn ""
2300   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
2301         (plus:DF (float:DF (match_operand:SI 2 "general_operand" "dmi"))
2302                  (match_operand:DF 1 "general_operand" "0")))]
2303   "TARGET_68881"
2304   "f%&add%.l %2,%0")
2305
2306 (define_insn ""
2307   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
2308         (plus:DF (float:DF (match_operand:HI 2 "general_operand" "dmn"))
2309                  (match_operand:DF 1 "general_operand" "0")))]
2310   "TARGET_68881"
2311   "f%&add%.w %2,%0")
2312
2313 (define_insn ""
2314   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
2315         (plus:DF (float:DF (match_operand:QI 2 "general_operand" "dmn"))
2316                  (match_operand:DF 1 "general_operand" "0")))]
2317   "TARGET_68881"
2318   "f%&add%.b %2,%0")
2319
2320 (define_insn ""
2321   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
2322         (plus:DF (match_operand:DF 1 "general_operand" "%0")
2323                  (match_operand:DF 2 "general_operand" "fmG")))]
2324   "TARGET_68881"
2325   "*
2326 {
2327   if (REG_P (operands[2]))
2328     return \"f%&add%.x %2,%0\";
2329   return \"f%&add%.d %f2,%0\";
2330 }")
2331
2332 (define_expand "addsf3"
2333   [(set (match_operand:SF 0 "nonimmediate_operand" "")
2334         (plus:SF (match_operand:SF 1 "general_operand" "")
2335                  (match_operand:SF 2 "general_operand" "")))]
2336   "TARGET_68881"
2337   "")
2338
2339 (define_insn ""
2340   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
2341         (plus:SF (float:SF (match_operand:SI 2 "general_operand" "dmi"))
2342                  (match_operand:SF 1 "general_operand" "0")))]
2343   "TARGET_68881"
2344   "f%$add%.l %2,%0")
2345
2346 (define_insn ""
2347   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
2348         (plus:SF (float:SF (match_operand:HI 2 "general_operand" "dmn"))
2349                  (match_operand:SF 1 "general_operand" "0")))]
2350   "TARGET_68881"
2351   "f%$add%.w %2,%0")
2352
2353 (define_insn ""
2354   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
2355         (plus:SF (float:SF (match_operand:QI 2 "general_operand" "dmn"))
2356                  (match_operand:SF 1 "general_operand" "0")))]
2357   "TARGET_68881"
2358   "f%$add%.b %2,%0")
2359
2360 (define_insn ""
2361   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
2362         (plus:SF (match_operand:SF 1 "general_operand" "%0")
2363                  (match_operand:SF 2 "general_operand" "fdmF")))]
2364   "TARGET_68881"
2365   "*
2366 {
2367   if (REG_P (operands[2]) && ! DATA_REG_P (operands[2]))
2368     return \"f%$add%.x %2,%0\";
2369   return \"f%$add%.s %f2,%0\";
2370 }")
2371 \f
2372 ;; subtract instructions
2373
2374 (define_insn "subdi_sexthishl32"
2375   [(set (match_operand:DI 0 "nonimmediate_operand" "=o,a,*d,*d")
2376     (minus:DI (match_operand:DI 1 "general_operand" "0,0,0,0")
2377         (ashift:DI (sign_extend:DI (match_operand:HI 2 "general_operand" "rm,rm,rm,rm"))
2378             (const_int 32))))
2379    (clobber (match_scratch:SI 3 "=&d,X,a,?d"))]
2380   "!TARGET_5200"
2381   "*
2382 {
2383   CC_STATUS_INIT;
2384   if (ADDRESS_REG_P (operands[0]))
2385     return \"sub%.w %2,%0\";
2386   else if (ADDRESS_REG_P (operands[3]))
2387     return \"move%.w %2,%3\;sub%.l %3,%0\";
2388   else
2389     return \"move%.w %2,%3\;ext%.l %3\;sub%.l %3,%0\";
2390 } ")
2391
2392 (define_insn "subdi_dishl32"
2393   [(set (match_operand:DI 0 "nonimmediate_operand" "+ro")
2394     (minus:DI (match_dup 0)
2395         (ashift:DI (match_operand:DI 1 "general_operand" "ro")
2396             (const_int 32))))]
2397   ""
2398   "*
2399 {
2400   CC_STATUS_INIT;
2401   if (GET_CODE (operands[1]) == REG)
2402     operands[1] = gen_rtx_REG (SImode, REGNO (operands[1]) + 1);
2403   else
2404     operands[1] = adjust_address (operands[1], SImode, 4);
2405   return \"sub%.l %1,%0\";
2406 } ")
2407
2408 (define_insn "subdi3"
2409   [(set (match_operand:DI 0 "nonimmediate_operand" "=<,o<>,d,d,d")
2410         (minus:DI (match_operand:DI 1 "general_operand" "0,0,0,0,0")
2411                  (match_operand:DI 2 "general_operand" "<,d,no>,d,a")))
2412    (clobber (match_scratch:SI 3 "=X,&d,&d,X,&d"))]
2413   ""
2414   "*
2415 {
2416   if (DATA_REG_P (operands[0]))
2417     {
2418       if (DATA_REG_P (operands[2]))
2419         return \"sub%.l %R2,%R0\;subx%.l %2,%0\";
2420       else if (GET_CODE (operands[2]) == MEM
2421           && GET_CODE (XEXP (operands[2], 0)) == POST_INC)
2422         {
2423           return \"move%.l %2,%3\;sub%.l %2,%R0\;subx%.l %3,%0\";
2424         }
2425       else
2426         {
2427           rtx high, low;
2428           rtx xoperands[2];
2429
2430           if (GET_CODE (operands[2]) == REG)
2431             {
2432               low = gen_rtx_REG (SImode, REGNO (operands[2]) + 1);
2433               high = operands[2];
2434             }
2435           else if (CONSTANT_P (operands[2]))
2436             split_double (operands[2], &high, &low);
2437           else
2438             {
2439               low = adjust_address (operands[2], SImode, 4);
2440               high = operands[2];
2441             }
2442
2443           operands[1] = low, operands[2] = high;
2444           xoperands[0] = operands[3];
2445           if (GET_CODE (operands[1]) == CONST_INT
2446               && INTVAL (operands[1]) >= -8 && INTVAL (operands[1]) < 0)
2447             xoperands[1] = GEN_INT (-INTVAL (operands[2]) - 1);
2448           else
2449             xoperands[1] = operands[2];
2450
2451           output_asm_insn (output_move_simode (xoperands), xoperands);
2452           if (GET_CODE (operands[1]) == CONST_INT)
2453             {
2454               if (INTVAL (operands[1]) > 0 && INTVAL (operands[1]) <= 8)
2455                 return \"subq%.l %1,%R0\;subx%.l %3,%0\";
2456               else if (INTVAL (operands[1]) >= -8 && INTVAL (operands[1]) < 0)
2457                 {
2458                   operands[1] = GEN_INT (-INTVAL (operands[1]));
2459                   return \"addq%.l %1,%R0\;addx%.l %3,%0\";
2460                 }
2461             }
2462           return \"sub%.l %1,%R0\;subx%.l %3,%0\";
2463         }
2464     }
2465   else if (GET_CODE (operands[0]) == MEM)
2466     {
2467       if (GET_CODE (operands[2]) == MEM
2468           && GET_CODE (XEXP (operands[2], 0)) == PRE_DEC)
2469         return \"sub%.l %2,%0\;subx%.l %2,%0\";
2470       CC_STATUS_INIT;
2471       if (GET_CODE (XEXP (operands[0], 0)) == POST_INC)
2472         {
2473           operands[1]
2474             = gen_rtx_MEM (SImode, plus_constant (XEXP (operands[0], 0), -8));
2475           return \"move%.l %0,%3\;sub%.l %R2,%0\;subx%.l %2,%3\;move%.l %3,%1\";
2476         }
2477       else if (GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
2478         {
2479           operands[1] = XEXP(operands[0], 0);
2480           return \"sub%.l %R2,%0\;move%.l %0,%3\;subx%.l %2,%3\;move%.l %3,%1\";
2481         }
2482       else
2483         {
2484           operands[1] = adjust_address (operands[0], SImode, 4);
2485           return \"sub%.l %R2,%1\;move%.l %0,%3\;subx%.l %2,%3\;move%.l %3,%0\";
2486         }
2487     }
2488   else
2489     abort ();
2490 } ")
2491
2492 (define_insn "subsi3"
2493   [(set (match_operand:SI 0 "nonimmediate_operand" "=m,d,a")
2494         (minus:SI (match_operand:SI 1 "general_operand" "0,0,0")
2495                   (match_operand:SI 2 "general_src_operand" "dT,mSrT,mSrs")))]
2496   ""
2497   "sub%.l %2,%0")
2498
2499 (define_insn ""
2500   [(set (match_operand:SI 0 "nonimmediate_operand" "=a")
2501         (minus:SI (match_operand:SI 1 "general_operand" "0")
2502                   (sign_extend:SI
2503                    (match_operand:HI 2 "nonimmediate_src_operand" "rmS"))))]
2504   "!TARGET_5200"
2505   "sub%.w %2,%0")
2506
2507 (define_insn "subhi3"
2508   [(set (match_operand:HI 0 "nonimmediate_operand" "=m,r")
2509         (minus:HI (match_operand:HI 1 "general_operand" "0,0")
2510                   (match_operand:HI 2 "general_src_operand" "dn,rmSn")))]
2511   "!TARGET_5200"
2512   "sub%.w %2,%0")
2513
2514 (define_insn ""
2515   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+m,d"))
2516         (minus:HI (match_dup 0)
2517                   (match_operand:HI 1 "general_src_operand" "dn,rmSn")))]
2518   "!TARGET_5200"
2519   "sub%.w %1,%0")
2520
2521 (define_insn "subqi3"
2522   [(set (match_operand:QI 0 "nonimmediate_operand" "=m,d")
2523         (minus:QI (match_operand:QI 1 "general_operand" "0,0")
2524                   (match_operand:QI 2 "general_src_operand" "dn,dmSn")))]
2525   "!TARGET_5200"
2526   "sub%.b %2,%0")
2527
2528 (define_insn ""
2529   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+m,d"))
2530         (minus:QI (match_dup 0)
2531                   (match_operand:QI 1 "general_src_operand" "dn,dmSn")))]
2532   "!TARGET_5200"
2533   "sub%.b %1,%0")
2534
2535 (define_expand "subdf3"
2536   [(set (match_operand:DF 0 "nonimmediate_operand" "")
2537         (minus:DF (match_operand:DF 1 "general_operand" "")
2538                   (match_operand:DF 2 "general_operand" "")))]
2539   "TARGET_68881"
2540   "")
2541
2542 (define_insn ""
2543   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
2544         (minus:DF (match_operand:DF 1 "general_operand" "0")
2545                   (float:DF (match_operand:SI 2 "general_operand" "dmi"))))]
2546   "TARGET_68881"
2547   "f%&sub%.l %2,%0")
2548
2549 (define_insn ""
2550   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
2551         (minus:DF (match_operand:DF 1 "general_operand" "0")
2552                   (float:DF (match_operand:HI 2 "general_operand" "dmn"))))]
2553   "TARGET_68881"
2554   "f%&sub%.w %2,%0")
2555
2556 (define_insn ""
2557   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
2558         (minus:DF (match_operand:DF 1 "general_operand" "0")
2559                   (float:DF (match_operand:QI 2 "general_operand" "dmn"))))]
2560   "TARGET_68881"
2561   "f%&sub%.b %2,%0")
2562
2563 (define_insn ""
2564   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
2565         (minus:DF (match_operand:DF 1 "general_operand" "0")
2566                   (match_operand:DF 2 "general_operand" "fmG")))]
2567   "TARGET_68881"
2568   "*
2569 {
2570   if (REG_P (operands[2]))
2571     return \"f%&sub%.x %2,%0\";
2572   return \"f%&sub%.d %f2,%0\";
2573 }")
2574
2575 (define_expand "subsf3"
2576   [(set (match_operand:SF 0 "nonimmediate_operand" "")
2577         (minus:SF (match_operand:SF 1 "general_operand" "")
2578                   (match_operand:SF 2 "general_operand" "")))]
2579   "TARGET_68881"
2580   "")
2581
2582 (define_insn ""
2583   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
2584         (minus:SF (match_operand:SF 1 "general_operand" "0")
2585                   (float:SF (match_operand:SI 2 "general_operand" "dmi"))))]
2586   "TARGET_68881"
2587   "f%$sub%.l %2,%0")
2588
2589 (define_insn ""
2590   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
2591         (minus:SF (match_operand:SF 1 "general_operand" "0")
2592                   (float:SF (match_operand:HI 2 "general_operand" "dmn"))))]
2593   "TARGET_68881"
2594   "f%$sub%.w %2,%0")
2595
2596 (define_insn ""
2597   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
2598         (minus:SF (match_operand:SF 1 "general_operand" "0")
2599                   (float:SF (match_operand:QI 2 "general_operand" "dmn"))))]
2600   "TARGET_68881"
2601   "f%$sub%.b %2,%0")
2602
2603 (define_insn ""
2604   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
2605         (minus:SF (match_operand:SF 1 "general_operand" "0")
2606                   (match_operand:SF 2 "general_operand" "fdmF")))]
2607   "TARGET_68881"
2608   "*
2609 {
2610   if (REG_P (operands[2]) && ! DATA_REG_P (operands[2]))
2611     return \"f%$sub%.x %2,%0\";
2612   return \"f%$sub%.s %f2,%0\";
2613 }")
2614 \f
2615 ;; multiply instructions
2616
2617 (define_insn "mulhi3"
2618   [(set (match_operand:HI 0 "nonimmediate_operand" "=d")
2619         (mult:HI (match_operand:HI 1 "general_operand" "%0")
2620                  (match_operand:HI 2 "general_src_operand" "dmSn")))]
2621   ""
2622   "*
2623 {
2624 #if defined(MOTOROLA)
2625   return \"muls%.w %2,%0\";
2626 #else
2627   return \"muls %2,%0\";
2628 #endif
2629 }")
2630
2631 (define_insn "mulhisi3"
2632   [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
2633         (mult:SI (sign_extend:SI
2634                   (match_operand:HI 1 "nonimmediate_operand" "%0"))
2635                  (sign_extend:SI
2636                   (match_operand:HI 2 "nonimmediate_src_operand" "dmS"))))]
2637   ""
2638   "*
2639 {
2640 #if defined(MOTOROLA)
2641   return \"muls%.w %2,%0\";
2642 #else
2643   return \"muls %2,%0\";
2644 #endif
2645 }")
2646
2647 (define_insn ""
2648   [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
2649         (mult:SI (sign_extend:SI
2650                   (match_operand:HI 1 "nonimmediate_operand" "%0"))
2651                  (match_operand:SI 2 "const_int_operand" "n")))]
2652   "INTVAL (operands[2]) >= -0x8000 && INTVAL (operands[2]) <= 0x7fff"
2653   "*
2654 {
2655 #if defined(MOTOROLA)
2656   return \"muls%.w %2,%0\";
2657 #else
2658   return \"muls %2,%0\";
2659 #endif
2660 }")
2661
2662 (define_expand "mulsi3"
2663   [(set (match_operand:SI 0 "nonimmediate_operand" "")
2664         (mult:SI (match_operand:SI 1 "general_operand" "")
2665                  (match_operand:SI 2 "general_operand" "")))]
2666   "TARGET_68020 || TARGET_5200"
2667   "")
2668
2669 (define_insn ""
2670   [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
2671         (mult:SI (match_operand:SI 1 "general_operand" "%0")
2672                  (match_operand:SI 2 "general_src_operand" "dmSTK")))]
2673
2674   "TARGET_68020"
2675   "muls%.l %2,%0")
2676
2677 (define_insn ""
2678   [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
2679         (mult:SI (match_operand:SI 1 "general_operand" "%0")
2680                  (match_operand:SI 2 "general_operand" "d<Q>")))]
2681   "TARGET_5200"
2682   "muls%.l %2,%0")
2683
2684 (define_insn "umulhisi3"
2685   [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
2686         (mult:SI (zero_extend:SI
2687                   (match_operand:HI 1 "nonimmediate_operand" "%0"))
2688                  (zero_extend:SI
2689                   (match_operand:HI 2 "nonimmediate_src_operand" "dmS"))))]
2690   ""
2691   "*
2692 {
2693 #if defined(MOTOROLA)
2694   return \"mulu%.w %2,%0\";
2695 #else
2696   return \"mulu %2,%0\";
2697 #endif
2698 }")
2699
2700 (define_insn ""
2701   [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
2702         (mult:SI (zero_extend:SI
2703                   (match_operand:HI 1 "nonimmediate_operand" "%0"))
2704                  (match_operand:SI 2 "const_int_operand" "n")))]
2705   "INTVAL (operands[2]) >= 0 && INTVAL (operands[2]) <= 0xffff"
2706   "*
2707 {
2708 #if defined(MOTOROLA)
2709   return \"mulu%.w %2,%0\";
2710 #else
2711   return \"mulu %2,%0\";
2712 #endif
2713 }")
2714
2715 ;; We need a separate DEFINE_EXPAND for u?mulsidi3 to be able to use the
2716 ;; proper matching constraint.  This is because the matching is between
2717 ;; the high-numbered word of the DImode operand[0] and operand[1].
2718 (define_expand "umulsidi3"
2719   [(parallel
2720     [(set (subreg:SI (match_operand:DI 0 "register_operand" "") 4)
2721           (mult:SI (match_operand:SI 1 "register_operand" "")
2722                    (match_operand:SI 2 "register_operand" "")))
2723      (set (subreg:SI (match_dup 0) 0)
2724           (truncate:SI (lshiftrt:DI (mult:DI (zero_extend:DI (match_dup 1))
2725                                              (zero_extend:DI (match_dup 2)))
2726                                     (const_int 32))))])]
2727   "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
2728   "")
2729
2730 (define_insn ""
2731   [(set (match_operand:SI 0 "register_operand" "=d")
2732         (mult:SI (match_operand:SI 1 "register_operand" "%0")
2733                   (match_operand:SI 2 "nonimmediate_operand" "dm")))
2734    (set (match_operand:SI 3 "register_operand" "=d")
2735         (truncate:SI (lshiftrt:DI (mult:DI (zero_extend:DI (match_dup 1))
2736                                            (zero_extend:DI (match_dup 2)))
2737                                   (const_int 32))))]
2738   "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
2739   "mulu%.l %2,%3:%0")
2740
2741 ; Match immediate case.  For 2.4 only match things < 2^31.
2742 ; It's tricky with larger values in these patterns since we need to match
2743 ; values between the two parallel multiplies, between a CONST_DOUBLE and
2744 ; a CONST_INT.
2745 (define_insn ""
2746   [(set (match_operand:SI 0 "register_operand" "=d")
2747         (mult:SI (match_operand:SI 1 "register_operand" "%0")
2748                  (match_operand:SI 2 "const_int_operand" "n")))
2749    (set (match_operand:SI 3 "register_operand" "=d")
2750         (truncate:SI (lshiftrt:DI (mult:DI (zero_extend:DI (match_dup 1))
2751                                            (match_dup 2))
2752                                   (const_int 32))))]
2753   "TARGET_68020 && !TARGET_68060 && !TARGET_5200
2754    && (unsigned) INTVAL (operands[2]) <= 0x7fffffff"
2755   "mulu%.l %2,%3:%0")
2756
2757 (define_expand "mulsidi3"
2758   [(parallel
2759     [(set (subreg:SI (match_operand:DI 0 "register_operand" "") 4)
2760           (mult:SI (match_operand:SI 1 "register_operand" "")
2761                    (match_operand:SI 2 "register_operand" "")))
2762      (set (subreg:SI (match_dup 0) 0)
2763           (truncate:SI (lshiftrt:DI (mult:DI (sign_extend:DI (match_dup 1))
2764                                              (sign_extend:DI (match_dup 2)))
2765                                     (const_int 32))))])]
2766   "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
2767   "")
2768
2769 (define_insn ""
2770   [(set (match_operand:SI 0 "register_operand" "=d")
2771         (mult:SI (match_operand:SI 1 "register_operand" "%0")
2772                  (match_operand:SI 2 "nonimmediate_operand" "dm")))
2773    (set (match_operand:SI 3 "register_operand" "=d")
2774         (truncate:SI (lshiftrt:DI (mult:DI (sign_extend:DI (match_dup 1))
2775                                            (sign_extend:DI (match_dup 2)))
2776                                   (const_int 32))))]
2777   "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
2778   "muls%.l %2,%3:%0")
2779
2780 (define_insn ""
2781   [(set (match_operand:SI 0 "register_operand" "=d")
2782         (mult:SI (match_operand:SI 1 "register_operand" "%0")
2783                  (match_operand:SI 2 "const_int_operand" "n")))
2784    (set (match_operand:SI 3 "register_operand" "=d")
2785         (truncate:SI (lshiftrt:DI (mult:DI (sign_extend:DI (match_dup 1))
2786                                            (match_dup 2))
2787                                   (const_int 32))))]
2788   "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
2789   "muls%.l %2,%3:%0")
2790
2791 (define_expand "umulsi3_highpart"
2792   [(parallel
2793     [(set (match_operand:SI 0 "register_operand" "")
2794           (truncate:SI
2795            (lshiftrt:DI
2796             (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" ""))
2797                      (zero_extend:DI (match_operand:SI 2 "general_operand" "")))
2798             (const_int 32))))
2799      (clobber (match_dup 3))])]
2800   "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
2801   "
2802 {
2803   operands[3] = gen_reg_rtx (SImode);
2804
2805   if (GET_CODE (operands[2]) == CONST_INT)
2806     {
2807       operands[2] = immed_double_const (INTVAL (operands[2]) & 0xffffffff,
2808                                         0, DImode);
2809
2810       /* We have to adjust the operand order for the matching constraints.  */
2811       emit_insn (gen_const_umulsi3_highpart (operands[0], operands[3],
2812                                              operands[1], operands[2]));
2813       DONE;
2814     }
2815 }")
2816
2817 (define_insn ""
2818   [(set (match_operand:SI 0 "register_operand" "=d")
2819         (truncate:SI
2820          (lshiftrt:DI
2821           (mult:DI (zero_extend:DI (match_operand:SI 2 "register_operand" "%1"))
2822                    (zero_extend:DI (match_operand:SI 3 "nonimmediate_operand" "dm")))
2823           (const_int 32))))
2824    (clobber (match_operand:SI 1 "register_operand" "=d"))]
2825   "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
2826   "mulu%.l %3,%0:%1")
2827
2828 (define_insn "const_umulsi3_highpart"
2829   [(set (match_operand:SI 0 "register_operand" "=d")
2830         (truncate:SI
2831          (lshiftrt:DI
2832           (mult:DI (zero_extend:DI (match_operand:SI 2 "register_operand" "1"))
2833                    (match_operand:DI 3 "const_uint32_operand" "n"))
2834           (const_int 32))))
2835    (clobber (match_operand:SI 1 "register_operand" "=d"))]
2836   "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
2837   "mulu%.l %3,%0:%1")
2838
2839 (define_expand "smulsi3_highpart"
2840   [(parallel
2841     [(set (match_operand:SI 0 "register_operand" "")
2842           (truncate:SI
2843            (lshiftrt:DI
2844             (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" ""))
2845                      (sign_extend:DI (match_operand:SI 2 "general_operand" "")))
2846             (const_int 32))))
2847      (clobber (match_dup 3))])]
2848   "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
2849   "
2850 {
2851   operands[3] = gen_reg_rtx (SImode);
2852   if (GET_CODE (operands[2]) == CONST_INT)
2853     {
2854       /* We have to adjust the operand order for the matching constraints.  */
2855       emit_insn (gen_const_smulsi3_highpart (operands[0], operands[3],
2856                                              operands[1], operands[2]));
2857       DONE;
2858     }
2859 }")
2860
2861 (define_insn ""
2862   [(set (match_operand:SI 0 "register_operand" "=d")
2863         (truncate:SI
2864          (lshiftrt:DI
2865           (mult:DI (sign_extend:DI (match_operand:SI 2 "register_operand" "%1"))
2866                    (sign_extend:DI (match_operand:SI 3 "nonimmediate_operand" "dm")))
2867           (const_int 32))))
2868    (clobber (match_operand:SI 1 "register_operand" "=d"))]
2869   "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
2870   "muls%.l %3,%0:%1")
2871
2872 (define_insn "const_smulsi3_highpart"
2873   [(set (match_operand:SI 0 "register_operand" "=d")
2874         (truncate:SI
2875          (lshiftrt:DI
2876           (mult:DI (sign_extend:DI (match_operand:SI 2 "register_operand" "1"))
2877                    (match_operand:DI 3 "const_sint32_operand" "n"))
2878           (const_int 32))))
2879    (clobber (match_operand:SI 1 "register_operand" "=d"))]
2880   "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
2881   "muls%.l %3,%0:%1")
2882
2883 (define_expand "muldf3"
2884   [(set (match_operand:DF 0 "nonimmediate_operand" "")
2885         (mult:DF (match_operand:DF 1 "general_operand" "")
2886                  (match_operand:DF 2 "general_operand" "")))]
2887   "TARGET_68881"
2888   "")
2889
2890 (define_insn ""
2891   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
2892         (mult:DF (float:DF (match_operand:SI 2 "general_operand" "dmi"))
2893                  (match_operand:DF 1 "general_operand" "0")))]
2894   "TARGET_68881"
2895   "f%&mul%.l %2,%0")
2896
2897 (define_insn ""
2898   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
2899         (mult:DF (float:DF (match_operand:HI 2 "general_operand" "dmn"))
2900                  (match_operand:DF 1 "general_operand" "0")))]
2901   "TARGET_68881"
2902   "f%&mul%.w %2,%0")
2903
2904 (define_insn ""
2905   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
2906         (mult:DF (float:DF (match_operand:QI 2 "general_operand" "dmn"))
2907                  (match_operand:DF 1 "general_operand" "0")))]
2908   "TARGET_68881"
2909   "f%&mul%.b %2,%0")
2910
2911 (define_insn ""
2912   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
2913         (mult:DF (match_operand:DF 1 "general_operand" "%0")
2914                  (match_operand:DF 2 "general_operand" "fmG")))]
2915   "TARGET_68881"
2916   "*
2917 {
2918   if (GET_CODE (operands[2]) == CONST_DOUBLE
2919       && floating_exact_log2 (operands[2]) && !TARGET_68040 && !TARGET_68060)
2920     {
2921       int i = floating_exact_log2 (operands[2]);
2922       operands[2] = GEN_INT (i);
2923       return \"fscale%.l %2,%0\";
2924     }
2925   if (REG_P (operands[2]))
2926     return \"f%&mul%.x %2,%0\";
2927   return \"f%&mul%.d %f2,%0\";
2928 }")
2929
2930 (define_expand "mulsf3"
2931   [(set (match_operand:SF 0 "nonimmediate_operand" "")
2932         (mult:SF (match_operand:SF 1 "general_operand" "")
2933                  (match_operand:SF 2 "general_operand" "")))]
2934   "TARGET_68881"
2935   "")
2936
2937 (define_insn ""
2938   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
2939         (mult:SF (float:SF (match_operand:SI 2 "general_operand" "dmi"))
2940                  (match_operand:SF 1 "general_operand" "0")))]
2941   "TARGET_68881"
2942   "*
2943 {
2944   return (TARGET_68040_ONLY
2945           ? \"fsmul%.l %2,%0\"
2946           : \"fsglmul%.l %2,%0\");
2947 }")
2948
2949 (define_insn ""
2950   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
2951         (mult:SF (float:SF (match_operand:HI 2 "general_operand" "dmn"))
2952                  (match_operand:SF 1 "general_operand" "0")))]
2953   "TARGET_68881"
2954   "*
2955 {
2956   return (TARGET_68040_ONLY
2957           ? \"fsmul%.w %2,%0\"
2958           : \"fsglmul%.w %2,%0\");
2959 }")
2960
2961 (define_insn ""
2962   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
2963         (mult:SF (float:SF (match_operand:QI 2 "general_operand" "dmn"))
2964                  (match_operand:SF 1 "general_operand" "0")))]
2965   "TARGET_68881"
2966   "*
2967 {
2968   return (TARGET_68040_ONLY
2969           ? \"fsmul%.b %2,%0\"
2970           : \"fsglmul%.b %2,%0\");
2971 }")
2972
2973 (define_insn ""
2974   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
2975         (mult:SF (match_operand:SF 1 "general_operand" "%0")
2976                  (match_operand:SF 2 "general_operand" "fdmF")))]
2977   "TARGET_68881"
2978   "*
2979 {
2980   if (REG_P (operands[2]) && ! DATA_REG_P (operands[2]))
2981     return (TARGET_68040_ONLY
2982             ? \"fsmul%.x %2,%0\"
2983             : \"fsglmul%.x %2,%0\");
2984   return (TARGET_68040_ONLY
2985           ? \"fsmul%.s %f2,%0\"
2986           : \"fsglmul%.s %f2,%0\");
2987 }")
2988 \f
2989 ;; divide instructions
2990
2991 (define_expand "divdf3"
2992   [(set (match_operand:DF 0 "nonimmediate_operand" "")
2993         (div:DF (match_operand:DF 1 "general_operand" "")
2994                 (match_operand:DF 2 "general_operand" "")))]
2995   "TARGET_68881"
2996   "")
2997
2998 (define_insn ""
2999   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
3000         (div:DF (match_operand:DF 1 "general_operand" "0")
3001                 (float:DF (match_operand:SI 2 "general_operand" "dmi"))))]
3002   "TARGET_68881"
3003   "f%&div%.l %2,%0")
3004
3005 (define_insn ""
3006   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
3007         (div:DF (match_operand:DF 1 "general_operand" "0")
3008                 (float:DF (match_operand:HI 2 "general_operand" "dmn"))))]
3009   "TARGET_68881"
3010   "f%&div%.w %2,%0")
3011
3012 (define_insn ""
3013   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
3014         (div:DF (match_operand:DF 1 "general_operand" "0")
3015                 (float:DF (match_operand:QI 2 "general_operand" "dmn"))))]
3016   "TARGET_68881"
3017   "f%&div%.b %2,%0")
3018
3019 (define_insn ""
3020   [(set (match_operand:DF 0 "nonimmediate_operand" "=f")
3021         (div:DF (match_operand:DF 1 "general_operand" "0")
3022                 (match_operand:DF 2 "general_operand" "fmG")))]
3023   "TARGET_68881"
3024   "*
3025 {
3026   if (REG_P (operands[2]))
3027     return \"f%&div%.x %2,%0\";
3028   return \"f%&div%.d %f2,%0\";
3029 }")
3030
3031 (define_expand "divsf3"
3032   [(set (match_operand:SF 0 "nonimmediate_operand" "")
3033         (div:SF (match_operand:SF 1 "general_operand" "")
3034                 (match_operand:SF 2 "general_operand" "")))]
3035   "TARGET_68881"
3036   "")
3037
3038 (define_insn ""
3039   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
3040         (div:SF (match_operand:SF 1 "general_operand" "0")
3041                 (float:SF (match_operand:SI 2 "general_operand" "dmi"))))]
3042   "TARGET_68881"
3043   "*
3044 {
3045   return (TARGET_68040_ONLY
3046           ? \"fsdiv%.l %2,%0\"
3047           : \"fsgldiv%.l %2,%0\");
3048 }")
3049
3050 (define_insn ""
3051   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
3052         (div:SF (match_operand:SF 1 "general_operand" "0")
3053                 (float:SF (match_operand:HI 2 "general_operand" "dmn"))))]
3054   "TARGET_68881"
3055   "*
3056 {
3057   return (TARGET_68040_ONLY
3058           ? \"fsdiv%.w %2,%0\"
3059           : \"fsgldiv%.w %2,%0\");
3060 }")
3061
3062 (define_insn ""
3063   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
3064         (div:SF (match_operand:SF 1 "general_operand" "0")
3065                 (float:SF (match_operand:QI 2 "general_operand" "dmn"))))]
3066   "TARGET_68881"
3067   "*
3068 {
3069   return (TARGET_68040_ONLY
3070           ? \"fsdiv%.b %2,%0\"
3071           : \"fsgldiv%.b %2,%0\");
3072 }")
3073
3074 (define_insn ""
3075   [(set (match_operand:SF 0 "nonimmediate_operand" "=f")
3076         (div:SF (match_operand:SF 1 "general_operand" "0")
3077                 (match_operand:SF 2 "general_operand" "fdmF")))]
3078   "TARGET_68881"
3079   "*
3080 {
3081   if (REG_P (operands[2]) && ! DATA_REG_P (operands[2]))
3082     return (TARGET_68040_ONLY
3083             ? \"fsdiv%.x %2,%0\"
3084             : \"fsgldiv%.x %2,%0\");
3085   return (TARGET_68040_ONLY
3086           ? \"fsdiv%.s %f2,%0\"
3087           : \"fsgldiv%.s %f2,%0\");
3088 }")
3089 \f
3090 ;; Remainder instructions.
3091
3092 (define_insn "divmodsi4"
3093   [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
3094         (div:SI (match_operand:SI 1 "general_operand" "0")
3095                 (match_operand:SI 2 "general_src_operand" "dmSTK")))
3096    (set (match_operand:SI 3 "nonimmediate_operand" "=d")
3097         (mod:SI (match_dup 1) (match_dup 2)))]
3098   "TARGET_68020 && !TARGET_5200"
3099   "*
3100 {
3101   if (find_reg_note (insn, REG_UNUSED, operands[3]))
3102     return \"divs%.l %2,%0\";
3103   else
3104     return \"divsl%.l %2,%3:%0\";
3105 }")
3106
3107 (define_insn "udivmodsi4"
3108   [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
3109         (udiv:SI (match_operand:SI 1 "general_operand" "0")
3110                  (match_operand:SI 2 "general_src_operand" "dmSTK")))
3111    (set (match_operand:SI 3 "nonimmediate_operand" "=d")
3112         (umod:SI (match_dup 1) (match_dup 2)))]
3113   "TARGET_68020 && !TARGET_5200"
3114   "*
3115 {
3116   if (find_reg_note (insn, REG_UNUSED, operands[3]))
3117     return \"divu%.l %2,%0\";
3118   else
3119     return \"divul%.l %2,%3:%0\";
3120 }")
3121
3122 (define_insn "divmodhi4"
3123   [(set (match_operand:HI 0 "nonimmediate_operand" "=d")
3124         (div:HI (match_operand:HI 1 "general_operand" "0")
3125                 (match_operand:HI 2 "general_src_operand" "dmSKT")))
3126    (set (match_operand:HI 3 "nonimmediate_operand" "=d")
3127         (mod:HI (match_dup 1) (match_dup 2)))]
3128   "!TARGET_5200"
3129   "*
3130 {
3131 #ifdef MOTOROLA
3132   output_asm_insn (\"ext%.l %0\;divs%.w %2,%0\", operands);
3133 #else
3134   output_asm_insn (\"extl %0\;divs %2,%0\", operands);
3135 #endif
3136   if (!find_reg_note(insn, REG_UNUSED, operands[3]))
3137     {
3138       CC_STATUS_INIT;
3139       return \"move%.l %0,%3\;swap %3\";
3140     }
3141   else
3142     return \"\";
3143 }")
3144
3145 (define_insn "udivmodhi4"
3146   [(set (match_operand:HI 0 "nonimmediate_operand" "=d")
3147         (udiv:HI (match_operand:HI 1 "general_operand" "0")
3148                  (match_operand:HI 2 "general_src_operand" "dmSKT")))
3149    (set (match_operand:HI 3 "nonimmediate_operand" "=d")
3150         (umod:HI (match_dup 1) (match_dup 2)))]
3151   "!TARGET_5200"
3152   "*
3153 {
3154 #ifdef MOTOROLA
3155   output_asm_insn (\"and%.l %#0xFFFF,%0\;divu%.w %2,%0\", operands);
3156 #else
3157   output_asm_insn (\"and%.l %#0xFFFF,%0\;divu %2,%0\", operands);
3158 #endif
3159   if (!find_reg_note(insn, REG_UNUSED, operands[3]))
3160     {
3161       CC_STATUS_INIT;
3162       return \"move%.l %0,%3\;swap %3\";
3163     }
3164   else
3165     return \"\";
3166 }")
3167 \f
3168 ;; logical-and instructions
3169
3170 ;; "anddi3" is mainly here to help combine().
3171 (define_insn "anddi3"
3172   [(set (match_operand:DI 0 "nonimmediate_operand" "=o,d")
3173         (and:DI (match_operand:DI 1 "general_operand" "%0,0")
3174                 (match_operand:DI 2 "general_operand" "dn,don")))]
3175   "!TARGET_5200"
3176   "*
3177 {
3178   CC_STATUS_INIT;
3179   /* We can get CONST_DOUBLE, but also const1_rtx etc.  */
3180   if (CONSTANT_P (operands[2]))
3181     {
3182       rtx hi, lo;
3183
3184       split_double (operands[2], &hi, &lo);
3185
3186       switch (INTVAL (hi))
3187         {
3188           case 0 :
3189             output_asm_insn (\"clr%.l %0\", operands);
3190             break;
3191           case -1 :
3192             break;
3193           default :
3194             {
3195             rtx xoperands[3];
3196
3197             xoperands[0] = operands[0];
3198             xoperands[2] = hi;
3199             output_asm_insn (output_andsi3 (xoperands), xoperands);
3200             }
3201         }
3202       if (GET_CODE (operands[0]) == REG)
3203         operands[0] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
3204       else
3205         operands[0] = adjust_address (operands[0], SImode, 4);
3206       switch (INTVAL (lo))
3207         {
3208           case 0 :
3209             output_asm_insn (\"clr%.l %0\", operands);
3210             break;
3211           case -1 :
3212             break;
3213           default :
3214             {
3215             rtx xoperands[3];
3216
3217             xoperands[0] = operands[0];
3218             xoperands[2] = lo;
3219             output_asm_insn (output_andsi3 (xoperands), xoperands);
3220             }
3221         }
3222       return \"\";
3223     }
3224   if (GET_CODE (operands[0]) != REG)
3225     {
3226       operands[1] = adjust_address (operands[0], SImode, 4);
3227       return \"and%.l %2,%0\;and%.l %R2,%1\";
3228     }
3229   if (GET_CODE (operands[2]) != REG)
3230     {
3231       operands[1] = adjust_address (operands[2], SImode, 4);
3232       return \"and%.l %2,%0\;and%.l %1,%R0\";
3233     }
3234   return \"and%.l %2,%0\;and%.l %R2,%R0\";
3235 }")
3236
3237 ;; Prevent AND from being made with sp.  This doesn't exist in the machine
3238 ;; and reload will cause inefficient code.  Since sp is a FIXED_REG, we
3239 ;; can't allocate pseudos into it.
3240
3241 (define_expand "andsi3"
3242   [(set (match_operand:SI 0 "not_sp_operand" "")
3243         (and:SI (match_operand:SI 1 "general_operand" "")
3244                 (match_operand:SI 2 "general_src_operand" "")))]
3245   ""
3246   "")
3247
3248 (define_insn "andsi3_internal"
3249   [(set (match_operand:SI 0 "not_sp_operand" "=m,d")
3250         (and:SI (match_operand:SI 1 "general_operand" "%0,0")
3251                 (match_operand:SI 2 "general_src_operand" "dKT,dmSM")))]
3252   "!TARGET_5200"
3253   "*
3254 {
3255   return output_andsi3 (operands);
3256 }")
3257
3258 (define_insn "andsi3_5200"
3259   [(set (match_operand:SI 0 "not_sp_operand" "=m,d")
3260         (and:SI (match_operand:SI 1 "general_operand" "%0,0")
3261                 (match_operand:SI 2 "general_src_operand" "d,dmsK")))]
3262   "TARGET_5200"
3263   "and%.l %2,%0")
3264
3265 (define_insn "andhi3"
3266   [(set (match_operand:HI 0 "nonimmediate_operand" "=m,d")
3267         (and:HI (match_operand:HI 1 "general_operand" "%0,0")
3268                 (match_operand:HI 2 "general_src_operand" "dn,dmSn")))]
3269   "!TARGET_5200"
3270   "and%.w %2,%0")
3271
3272 (define_insn ""
3273   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+m,d"))
3274         (and:HI (match_dup 0)
3275                 (match_operand:HI 1 "general_src_operand" "dn,dmSn")))]
3276   "!TARGET_5200"
3277   "and%.w %1,%0")
3278
3279 (define_insn ""
3280   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+m,d"))
3281         (and:HI (match_operand:HI 1 "general_src_operand" "dn,dmSn")
3282                 (match_dup 0)))]
3283   "!TARGET_5200"
3284   "and%.w %1,%0")
3285
3286 (define_insn "andqi3"
3287   [(set (match_operand:QI 0 "nonimmediate_operand" "=m,d")
3288         (and:QI (match_operand:QI 1 "general_operand" "%0,0")
3289                 (match_operand:QI 2 "general_src_operand" "dn,dmSn")))]
3290   "!TARGET_5200"
3291   "and%.b %2,%0")
3292
3293 (define_insn ""
3294   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+m,d"))
3295         (and:QI (match_dup 0)
3296                 (match_operand:QI 1 "general_src_operand" "dn,dmSn")))]
3297   "!TARGET_5200"
3298   "and%.b %1,%0")
3299
3300 (define_insn ""
3301   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+m,d"))
3302         (and:QI (match_operand:QI 1 "general_src_operand" "dn,dmSn")
3303                 (match_dup 0)))]
3304   "!TARGET_5200"
3305   "and%.b %1,%0")
3306 \f
3307 ;; inclusive-or instructions
3308
3309 (define_insn "iordi_zext"
3310   [(set (match_operand:DI 0 "nonimmediate_operand" "=o,d")
3311     (ior:DI (zero_extend:DI (match_operand 1 "general_operand" "dn,dmn"))
3312         (match_operand:DI 2 "general_operand" "0,0")))]
3313   "!TARGET_5200"
3314   "*
3315 {
3316   int byte_mode;
3317
3318   CC_STATUS_INIT;
3319   if (GET_CODE (operands[0]) == REG)
3320     operands[0] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
3321   else
3322     operands[0] = adjust_address (operands[0], SImode, 4);
3323   if (GET_MODE (operands[1]) == SImode)
3324     return \"or%.l %1,%0\";
3325   byte_mode = (GET_MODE (operands[1]) == QImode);
3326   if (GET_CODE (operands[0]) == MEM)
3327     operands[0] = adjust_address (operands[0], byte_mode ? QImode : HImode,
3328                                   byte_mode ? 3 : 2);
3329   if (byte_mode)
3330     return \"or%.b %1,%0\";
3331   else
3332     return \"or%.w %1,%0\";
3333 }")
3334
3335 ;; "iordi3" is mainly here to help combine().
3336 (define_insn "iordi3"
3337   [(set (match_operand:DI 0 "nonimmediate_operand" "=o,d")
3338         (ior:DI (match_operand:DI 1 "general_operand" "%0,0")
3339                 (match_operand:DI 2 "general_operand" "dn,don")))]
3340   "!TARGET_5200"
3341   "*
3342 {
3343   CC_STATUS_INIT;
3344   /* We can get CONST_DOUBLE, but also const1_rtx etc.  */
3345   if (CONSTANT_P (operands[2]))
3346     {
3347       rtx hi, lo;
3348
3349       split_double (operands[2], &hi, &lo);
3350
3351       switch (INTVAL (hi))
3352         {
3353           case 0 :
3354             break;
3355           case -1 :
3356             /* FIXME : a scratch register would be welcome here if operand[0]
3357                is not a register */
3358             output_asm_insn (\"move%.l %#-1,%0\", operands);
3359             break;
3360           default :
3361             {
3362             rtx xoperands[3];
3363
3364             xoperands[0] = operands[0];
3365             xoperands[2] = hi;
3366             output_asm_insn (output_iorsi3 (xoperands), xoperands);
3367             }
3368         }
3369       if (GET_CODE (operands[0]) == REG)
3370         operands[0] = gen_rtx_REG (SImode, REGNO (operands[0]) + 1);
3371       else
3372         operands[0] = adjust_address (operands[0], SImode, 4);
3373       switch (INTVAL (lo))
3374         {
3375           case 0 :
3376             break;
3377           case -1 :
3378             /* FIXME : a scratch register would be welcome here if operand[0]
3379                is not a register */
3380             output_asm_insn (\"move%.l %#-1,%0\", operands);
3381             break;
3382           default :
3383             {
3384             rtx xoperands[3];
3385
3386             xoperands[0] = operands[0];
3387             xoperands[2] = lo;
3388             output_asm_insn (output_iorsi3 (xoperands), xoperands);
3389             }
3390         }
3391       return \"\";
3392     }
3393   if (GET_CODE (operands[0]) != REG)
3394     {
3395       operands[1] = adjust_address (operands[0], SImode, 4);
3396       return \"or%.l %2,%0\;or%.l %R2,%1\";
3397     }
3398   if (GET_CODE (operands[2]) != REG)
3399     {
3400       operands[1] = adjust_address (operands[2], SImode, 4);
3401       return \"or%.l %2,%0\;or%.l %1,%R0\";
3402     }
3403   return \"or%.l %2,%0\;or%.l %R2,%R0\";
3404 }")
3405
3406 (define_expand "iorsi3"
3407   [(set (match_operand:SI 0 "nonimmediate_operand" "")
3408         (ior:SI (match_operand:SI 1 "general_operand" "")
3409                 (match_operand:SI 2 "general_src_operand" "")))]
3410   ""
3411   "")
3412
3413 (define_insn "iorsi3_internal"
3414   [(set (match_operand:SI 0 "nonimmediate_operand" "=m,d")
3415         (ior:SI (match_operand:SI 1 "general_operand" "%0,0")
3416                 (match_operand:SI 2 "general_src_operand" "dKT,dmSMT")))]
3417   "! TARGET_5200"
3418   "*
3419 {
3420   return output_iorsi3 (operands);
3421 }")
3422
3423 (define_insn "iorsi3_5200"
3424   [(set (match_operand:SI 0 "nonimmediate_operand" "=m,d")
3425         (ior:SI (match_operand:SI 1 "general_operand" "%0,0")
3426                 (match_operand:SI 2 "general_src_operand" "d,dmsK")))]
3427   "TARGET_5200"
3428   "or%.l %2,%0")
3429
3430 (define_insn "iorhi3"
3431   [(set (match_operand:HI 0 "nonimmediate_operand" "=m,d")
3432         (ior:HI (match_operand:HI 1 "general_operand" "%0,0")
3433                 (match_operand:HI 2 "general_src_operand" "dn,dmSn")))]
3434   "!TARGET_5200"
3435   "or%.w %2,%0")
3436
3437 (define_insn ""
3438   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+m,d"))
3439         (ior:HI (match_dup 0)
3440                 (match_operand:HI 1 "general_src_operand" "dn,dmSn")))]
3441   "!TARGET_5200"
3442   "or%.w %1,%0")
3443
3444 (define_insn ""
3445   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+m,d"))
3446         (ior:HI (match_operand:HI 1 "general_src_operand" "dn,dmSn")
3447                 (match_dup 0)))]
3448   "!TARGET_5200"
3449   "or%.w %1,%0")
3450
3451 (define_insn "iorqi3"
3452   [(set (match_operand:QI 0 "nonimmediate_operand" "=m,d")
3453         (ior:QI (match_operand:QI 1 "general_operand" "%0,0")
3454                 (match_operand:QI 2 "general_src_operand" "dn,dmSn")))]
3455   "!TARGET_5200"
3456   "or%.b %2,%0")
3457
3458 (define_insn ""
3459   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+m,d"))
3460         (ior:QI (match_dup 0)
3461                 (match_operand:QI 1 "general_src_operand" "dn,dmSn")))]
3462   "!TARGET_5200"
3463   "or%.b %1,%0")
3464
3465 (define_insn ""
3466   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+m,d"))
3467         (ior:QI (match_operand:QI 1 "general_src_operand" "dn,dmSn")
3468                 (match_dup 0)))]
3469   "!TARGET_5200"
3470   "or%.b %1,%0")
3471
3472 ;; On all 68k models, this makes faster code in a special case.
3473 ;; See also ashlsi_16, ashrsi_16 and lshrsi_16.
3474
3475 (def