OSDN Git Service

Trivial simplification of many patterns.
[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 Free Software Foundation, Inc.
3
4 ;; This file is part of GNU CC.
5
6 ;; GNU CC is free software; you can redistribute it and/or modify
7 ;; it under the terms of the GNU General Public License as published by
8 ;; the Free Software Foundation; either version 2, or (at your option)
9 ;; any later version.
10
11 ;; GNU CC is distributed in the hope that it will be useful,
12 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
13 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14 ;; GNU General Public License for more details.
15
16 ;; You should have received a copy of the GNU General Public License
17 ;; along with GNU CC; see the file COPYING.  If not, write to
18 ;; the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
19
20
21 ;;- instruction definitions
22
23 ;;- @@The original PO technology requires these to be ordered by speed,
24 ;;- @@    so that assigner will pick the fastest.
25
26 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
27
28 ;;- When naming insn's (operand 0 of define_insn) be careful about using
29 ;;- names from other targets machine descriptions.
30
31 ;;- cpp macro #define NOTICE_UPDATE_CC in file tm.h handles condition code
32 ;;- updates for most instructions.
33
34 ;;- Operand classes for the register allocator:
35 ;;- 'a' one of the address registers can be used.
36 ;;- 'd' one of the data registers can be used.
37 ;;- 'f' one of the m68881 registers can be used
38 ;;- 'r' either a data or an address register can be used.
39 ;;- 'x' if one of the Sun FPA registers                    
40 ;;- 'y' if one of the Low Sun FPA registers (fpa0-fpa15).
41
42 ;;- Immediate Floating point operator constraints
43 ;;- 'G' a floating point constant that is *NOT* one of the standard
44 ;;   68881 constant values (to force calling output_move_const_double
45 ;;   to get it from rom if it is a 68881 constant).
46 ;;- 'H' one of the standard FPA constant values
47 ;;
48 ;;   See the functions standard_XXX_constant_p in output-m68k.c for more
49 ;; info.
50
51 ;;- Immediate integer operand constraints:
52 ;;- 'I'  1 .. 8
53 ;;- 'J'  -32768 .. 32767
54 ;;- 'K'  all integers EXCEPT -128 .. 127
55 ;;- 'L'  -8 .. -1
56
57 ;;- Assembler specs:
58 ;;- "%."    size separator ("." or "")                  move%.l d0,d1
59 ;;- "%#"    immediate separator ("#" or "")             move%.l %#0,d0
60 ;;- "%-"    push operand "sp@-"                         move%.l d0,%-
61 ;;- "%+"    pop operand "sp@+"                          move%.l d0,%+
62 ;;- "%@"    top of stack "sp@"                          move%.l d0,%@
63 ;;- "%!"    fpcr register
64 ;;- "%$"    single-precision fp specifier ("s" or "")   f%$add.x fp0,fp1
65 ;;- "%&"    double-precision fp specifier ("d" or "")   f%&add.x fp0,fp1
66
67 ;;- Information about 68040 port.
68
69 ;;- The 68040 executes all 68030 and 68881/2 instructions, but some must
70 ;;- be emulated in software by the OS.  It is faster to avoid these
71 ;;- instructions and issue a library call rather than trapping into
72 ;;- the kernel.  The affected instructions are fintrz and fscale.  The
73 ;;- TARGET_68040 flag turns the use of the opcodes off.
74
75 ;;- The '040 also implements a set of new floating-point instructions
76 ;;- which specify the rounding precision in the opcode.  This finally
77 ;;- permit the 68k series to be truly IEEE compliant, and solves all
78 ;;- issues of excess precision accumulating in the extended registers.
79 ;;- By default, GCC does not use these instructions, since such code will
80 ;;- not run on an '030.  To use these instructions, use the -m68040-only
81 ;;- switch.  By changing TARGET_DEFAULT to include TARGET_68040_ONLY,
82 ;;- you can make these instructions the default.
83
84 ;;- These new instructions aren't directly in the md.  They are brought
85 ;;- into play by defining "%$" and "%&" to expand to "s" and "d" rather
86 ;;- than "".
87
88
89 ;;-             FPA port explanation:
90
91 ;;-             Usage of the Sun FPA and the 68881 together
92
93 ;;- The current port of gcc to the sun fpa disallows use of the m68881
94 ;;- instructions completely if code is targeted for the fpa.  This is
95 ;;- for the following reasons:
96
97 ;;- 1) Expressing the preference hierarchy (ie. use the fpa if you
98 ;;- can, the 68881 otherwise, and data registers only if you are
99 ;;- forced to it) is a bitch with the current constraint scheme,
100 ;;- especially since it would have to work for any combination of
101 ;;- -mfpa, -m68881.
102
103 ;;- 2) There are no instructions to move between the two types of
104 ;;- registers; the stack must be used as an intermediary.
105
106 ;;- It could indeed be done; I think the best way would be to have
107 ;;- separate patterns for TARGET_FPA (which implies a 68881),
108 ;;- TARGET_68881, and no floating point co-processor.  Use
109 ;;- define_expands for all of the named instruction patterns, and
110 ;;- include code in the FPA instruction to deal with the 68881 with
111 ;;- preferences specifically set to favor the fpa.  Some of this has
112 ;;- already been done:
113 ;;-
114 ;;-     1) Separation of most of the patterns out into a TARGET_FPA
115 ;;- case and a TARGET_68881 case (the exceptions are the patterns
116 ;;- which would need one define_expand and three define_insn's under
117 ;;- it (with a lot of duplicate code between them) to replace the
118 ;;- current single define_insn.  These are mov{[ds]f,[ds]i} and the
119 ;;- first two patterns in the md.
120 ;;-
121 ;;- Some would still have to be done:
122 ;;-
123 ;;-     1) Add code to the fpa patterns which correspond to 68881
124 ;;- patterns to deal with the 68881 case (including preferences!).
125 ;;- What you might actually do here is combine the fpa and 68881 code
126 ;;- back together into one pattern for those instructions where it's
127 ;;- absolutely necessary and save yourself some duplicate code.  I'm
128 ;;- not completely sure as to whether you could get away with doing
129 ;;- this only for the mov* insns, or if you'd have to do it for all
130 ;;- named insns.
131 ;;-     2) Add code to the mov{[ds]f,[ds]i} instructions to handle
132 ;;- moving between fpa regs and 68881 regs.
133
134 ;;- Since the fpa is more powerful than the 68881 and also has more
135 ;;- registers, and since I think the resultant md would be medium ugly
136 ;;- (lot's of duplicate code, ugly constraint strings), I elected not
137 ;;- to do this change.
138
139 ;;- Another reason why someone *might* want to do the change is to
140 ;;- control which register classes are accessed in a slightly cleaner
141 ;;- way than I have.  See the blurb on CONDITIONAL_REGISTER_USAGE in
142 ;;- the internals manual.
143
144 ;;- Yet another reason why someone might want to do this change is to
145 ;;- allow use of some of the 68881 insns which have no equivalent on
146 ;;- the fpa.  The sqrt instruction comes fairly quickly to mind.
147
148 ;;- If this is ever done, don't forget to change sun3.h so that
149 ;;- it *will* define __HAVE_68881__ when the FPA is in use.
150
151 ;;-             Condition code hack
152
153 ;;- When a floating point compare is done in the fpa, the resulting
154 ;;- condition codes are left in the fpastatus register.  The values in
155 ;;- this register must be moved into the 68000 cc register before any
156 ;;- jump is executed.  Once this has been done, regular jump
157 ;;- instructions are fine (ie. floating point jumps are not necessary.
158 ;;- They are only done if the cc is in the 68881).
159
160 ;;- The instructions that move the fpastatus register to the 68000
161 ;;- register clobber a data register (the move cannot be done direct).
162 ;;- These instructions might be bundled either with the compare
163 ;;- instruction, or the branch instruction.  If we were using both the
164 ;;- fpa and the 68881 together, we would wish to only mark the
165 ;;- register clobbered if we were doing the compare in the fpa, but I
166 ;;- think that that decision (whether to clobber the register or not)
167 ;;- must be done before register allocation (makes sense) and hence we
168 ;;- can't know if the floating point compare will be done in the fpa
169 ;;- or the fp.  So whenever we are asked for code that uses the fpa,
170 ;;- we will mark a data register as clobbered.  This is reasonable, as
171 ;;- almost all floating point compare operations done with fpa code
172 ;;- enabled will be done in the fpa.  It's even more reasonable since
173 ;;- we decided to make the 68881 and the fpa mutually exclusive.
174
175 ;;- We place to code to move the fpastatus register inside of a
176 ;;- define_expand so that we can do it conditionally based on whether
177 ;;- we are targeting an fpa or not.
178
179 ;;- This still leaves us with the question of where we wish to put the
180 ;;- code to move the fpastatus reg.  If we put it in the compare
181 ;;- instruction, we can restrict the clobbering of the register to
182 ;;- floating point compares, but we can't take advantage of floating
183 ;;- point subtracts & etc. that alter the fpastatus register.  If we
184 ;;- put it in the branch instruction, all branches compiled with fpa
185 ;;- code enabled will clobber a data register, but we will be able to
186 ;;- take advantage of fpa subtracts.  This balance favors putting the
187 ;;- code in with the compare instruction.
188
189 ;;- Note that if some enterprising hacker should decide to switch
190 ;;- this, he'll need to modify the code in NOTICE_UPDATE_CC.
191
192 ;;-             Usage of the top 16 fpa registers
193
194 ;;- The only locations which we may transfer fpa registers 16-31 from
195 ;;- or to are the fpa registers 0-15.  (68000 registers and memory
196 ;;- locations are impossible).  This causes problems in gcc, which
197 ;;- assumes that mov?? instructions require no additional registers
198 ;;- (see section 11.7) and since floating point moves *must* be
199 ;;- supported into general registers (see section 12.3 under
200 ;;- HARD_REGNO_OK_FOR_MODE_P) from anywhere.
201
202 ;;- My solution was to reserve fpa0 for moves into or out of these top
203 ;;- 16 registers and to disparage the choice to reload into or out of
204 ;;- these registers as much as I could.  That alternative is always
205 ;;- last in the list, so it will not be used unless all else fails.  I
206 ;;- will note that according to my current information, sun's compiler
207 ;;- doesn't use these top 16 registers at all.
208
209 ;;- There is another possible way to do it.  I *believe* that if you
210 ;;- make absolutely sure that the code will not be executed in the
211 ;;- reload pass, you can support the mov?? names with define_expands
212 ;;- which require new registers.  This may be possible by the
213 ;;- appropriate juggling of constraints.  I may come back to this later.
214
215 ;;-             Usage of constant RAM
216
217 ;;- This has been handled correctly (I believe) but the way I've done
218 ;;- it could use a little explanation.  The constant RAM can only be
219 ;;- accessed when the instruction is in "command register" mode.
220 ;;- "command register" mode means that no accessing of memory or the
221 ;;- 68000 registers is being done.  This can be expressed easily in
222 ;;- constraints, so generally the mode of the instruction is
223 ;;- determined by a branch off of which_alternative.  In outputting
224 ;;- instructions, a 'w' means to output an access to the constant ram
225 ;;- (if the arg is CONST_DOUBLE and is one of the available
226 ;;- constants), and 'x' means to output a register pair (if the arg is
227 ;;- a 68000 register) and a 'y' is the combination of the above two
228 ;;- processes.  You use a 'y' in two operand DF instructions where you
229 ;;- *know* the other operand is an fpa register, you use an 'x' in DF
230 ;;- instructions where the arg might be a 68000 register and the
231 ;;- instruction is *not* in "command register" mode, and you use a 'w'
232 ;;- in two situations: 1) The instruction *is* in command register
233 ;;- mode (and hence won't be accessing 68000 registers), or 2) The
234 ;;- instruction is a two operand SF instruction where you know the
235 ;;- other operand is an fpa register.
236
237 ;;-             Optimization issues
238
239 ;;- I actually think that I've included all of the fpa instructions
240 ;;- that should be included.  Note that if someone is interested in
241 ;;- doing serious floating point work on the sun fpa, I would advise
242 ;;- the use of the "asm" instruction in gcc to allow you to use the
243 ;;- sin, cos, and exponential functions on the fpa board.
244
245 ;;- END FPA Explanation Section.
246
247
248 ;;- Some of these insn's are composites of several m68000 op codes.
249 ;;- The assembler (or final @@??) insures that the appropriate one is
250 ;;- selected.
251 \f
252 (define_insn ""
253   [(set (match_operand:DF 0 "push_operand" "=m")
254         (match_operand:DF 1 "general_operand" "ro<>fyE"))]
255   ""
256   "*
257 {
258   if (FP_REG_P (operands[1]))
259     return \"fmove%.d %f1,%0\";
260   if (FPA_REG_P (operands[1]))
261     return \"fpmove%.d %1, %x0\";
262   return output_move_double (operands);
263 }")
264
265 (define_insn ""
266   [(set (match_operand:DI 0 "push_operand" "=m")
267         (match_operand:DI 1 "general_operand" "ro<>Fy"))]
268   ""
269   "*
270 {
271   return output_move_double (operands);
272 }")
273 \f
274 ;; We don't want to allow a constant operand for test insns because
275 ;; (set (cc0) (const_int foo)) has no mode information.  Such insns will
276 ;; be folded while optimizing anyway.
277 (define_insn "tstsi"
278   [(set (cc0)
279         (match_operand:SI 0 "nonimmediate_operand" "rm"))]
280   ""
281   "*
282 {
283 #ifdef ISI_OV
284   /* ISI's assembler fails to handle tstl a0.  */
285   if (! ADDRESS_REG_P (operands[0]))
286 #else
287   if (TARGET_68020 || ! ADDRESS_REG_P (operands[0]))
288 #endif
289     return \"tst%.l %0\";
290   /* If you think that the 68020 does not support tstl a0,
291      reread page B-167 of the 68020 manual more carefully.  */
292   /* On an address reg, cmpw may replace cmpl.  */
293 #ifdef SGS_CMP_ORDER
294   return \"cmp%.w %0,%#0\";
295 #else
296   return \"cmp%.w %#0,%0\";
297 #endif
298 }")
299
300 ;; This can't use an address register, because comparisons
301 ;; with address registers as second operand always test the whole word.
302 (define_insn "tsthi"
303   [(set (cc0)
304         (match_operand:HI 0 "nonimmediate_operand" "dm"))]
305   ""
306   "tst%.w %0")
307
308 (define_insn "tstqi"
309   [(set (cc0)
310         (match_operand:QI 0 "nonimmediate_operand" "dm"))]
311   ""
312   "tst%.b %0")
313   
314 (define_expand "tstsf"
315   [(set (cc0)
316         (match_operand:SF 0 "general_operand" ""))]
317   "TARGET_68881 || TARGET_FPA"
318   "
319 {
320   if (TARGET_FPA)
321     {
322       emit_insn (gen_tstsf_fpa (operands[0]));
323       DONE;
324     }
325 }")
326
327 (define_insn "tstsf_fpa"
328   [(set (cc0)
329         (match_operand:SF 0 "general_operand" "xmdF"))
330    (clobber (match_scratch:SI 1 "=d"))]
331   "TARGET_FPA"
332   "fptst%.s %x0\;fpmove fpastatus,%1\;movw %1,cc")
333
334 (define_insn ""
335   [(set (cc0)
336         (match_operand:SF 0 "general_operand" "fdm"))]
337   "TARGET_68881"
338   "*
339 {
340   cc_status.flags = CC_IN_68881;
341   if (FP_REG_P (operands[0]))
342     return \"ftst%.x %0\";
343   return \"ftst%.s %0\";
344 }")
345
346 (define_expand "tstdf"
347   [(set (cc0)
348         (match_operand:DF 0 "general_operand" ""))]
349   "TARGET_68881 || TARGET_FPA"
350   "
351 {
352   if (TARGET_FPA)
353     {
354       emit_insn (gen_tstsf_fpa (operands[0]));
355       DONE;
356     }
357 }")
358
359 (define_insn "tstdf_fpa"
360   [(set (cc0)
361         (match_operand:DF 0 "general_operand" "xrmF"))
362    (clobber (match_scratch:SI 1 "=d"))]
363   "TARGET_FPA"
364   "fptst%.d %x0\;fpmove fpastatus,%1\;movw %1,cc")
365
366 (define_insn ""
367   [(set (cc0)
368         (match_operand:DF 0 "general_operand" "fm"))]
369   "TARGET_68881"
370   "*
371 {
372   cc_status.flags = CC_IN_68881;
373   if (FP_REG_P (operands[0]))
374     return \"ftst%.x %0\";
375   return \"ftst%.d %0\";
376 }")
377 \f
378 ;; compare instructions.
379
380 ;; A composite of the cmp, cmpa, & cmpi m68000 op codes.
381 (define_insn "cmpsi"
382   [(set (cc0)
383         (compare (match_operand:SI 0 "nonimmediate_operand" "rKs,mr,>")
384                  (match_operand:SI 1 "general_operand" "mr,Ksr,>")))]
385   ""
386   "*
387 {
388   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
389 #ifdef SGS_CMP_ORDER
390     return \"cmpm%.l %0,%1\";
391 #else
392     return \"cmpm%.l %1,%0\";
393 #endif
394   if (REG_P (operands[1])
395       || (!REG_P (operands[0]) && GET_CODE (operands[0]) != MEM))
396     { cc_status.flags |= CC_REVERSED;
397 #ifdef SGS_CMP_ORDER
398       return \"cmp%.l %d1,%d0\";
399 #else
400       return \"cmp%.l %d0,%d1\";
401 #endif
402     }
403 #ifdef SGS_CMP_ORDER
404   return \"cmp%.l %d0,%d1\";
405 #else
406   return \"cmp%.l %d1,%d0\";
407 #endif
408 }")
409
410 (define_insn "cmphi"
411   [(set (cc0)
412         (compare (match_operand:HI 0 "nonimmediate_operand" "rnm,d,n,m,>")
413                  (match_operand:HI 1 "general_operand" "d,rnm,m,n,>")))]
414   ""
415   "*
416 {
417   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
418 #ifdef SGS_CMP_ORDER
419     return \"cmpm%.w %0,%1\";
420 #else
421     return \"cmpm%.w %1,%0\";
422 #endif
423   if ((REG_P (operands[1]) && !ADDRESS_REG_P (operands[1]))
424       || (!REG_P (operands[0]) && GET_CODE (operands[0]) != MEM))
425     { cc_status.flags |= CC_REVERSED;
426 #ifdef SGS_CMP_ORDER
427       return \"cmp%.w %d1,%d0\";
428 #else
429       return \"cmp%.w %d0,%d1\";
430 #endif
431     }
432 #ifdef SGS_CMP_ORDER
433   return \"cmp%.w %d0,%d1\";
434 #else
435   return \"cmp%.w %d1,%d0\";
436 #endif
437 }")
438
439 (define_insn "cmpqi"
440   [(set (cc0)
441         (compare (match_operand:QI 0 "nonimmediate_operand" "dn,md,>")
442                  (match_operand:QI 1 "general_operand" "dm,nd,>")))]
443   ""
444   "*
445 {
446   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
447 #ifdef SGS_CMP_ORDER
448     return \"cmpm%.b %0,%1\";
449 #else
450     return \"cmpm%.b %1,%0\";
451 #endif
452   if (REG_P (operands[1])
453       || (!REG_P (operands[0]) && GET_CODE (operands[0]) != MEM))
454     { cc_status.flags |= CC_REVERSED;
455 #ifdef SGS_CMP_ORDER
456       return \"cmp%.b %d1,%d0\";
457 #else
458       return \"cmp%.b %d0,%d1\";
459 #endif
460     }
461 #ifdef SGS_CMP_ORDER
462   return \"cmp%.b %d0,%d1\";
463 #else
464   return \"cmp%.b %d1,%d0\";
465 #endif
466 }")
467
468 (define_expand "cmpdf"
469   [(set (cc0)
470         (compare (match_operand:DF 0 "general_operand" "")
471                  (match_operand:DF 1 "general_operand" "")))]
472   "TARGET_68881 || TARGET_FPA"
473   "
474 {
475   if (TARGET_FPA)
476     {
477       emit_insn (gen_cmpdf_fpa (operands[0], operands[1]));
478       DONE;
479     }
480 }")
481
482 (define_insn "cmpdf_fpa"
483   [(set (cc0)
484         (compare (match_operand:DF 0 "general_operand" "x,y")
485                  (match_operand:DF 1 "general_operand" "xH,rmF")))
486    (clobber (match_scratch:SI 2 "=d,d"))]
487   "TARGET_FPA"
488   "fpcmp%.d %y1,%0\;fpmove fpastatus,%2\;movw %2,cc")
489
490 (define_insn ""
491   [(set (cc0)
492         (compare (match_operand:DF 0 "general_operand" "f,mG")
493                  (match_operand:DF 1 "general_operand" "fmG,f")))]
494   "TARGET_68881"
495   "*
496 {
497   cc_status.flags = CC_IN_68881;
498 #ifdef SGS_CMP_ORDER
499   if (REG_P (operands[0]))
500     {
501       if (REG_P (operands[1]))
502         return \"fcmp%.x %0,%1\";
503       else
504         return \"fcmp%.d %0,%f1\";
505     }
506   cc_status.flags |= CC_REVERSED;
507   return \"fcmp%.d %1,%f0\";
508 #else
509   if (REG_P (operands[0]))
510     {
511       if (REG_P (operands[1]))
512         return \"fcmp%.x %1,%0\";
513       else
514         return \"fcmp%.d %f1,%0\";
515     }
516   cc_status.flags |= CC_REVERSED;
517   return \"fcmp%.d %f0,%1\";
518 #endif
519 }")
520
521 (define_expand "cmpsf"
522  [(set (cc0)
523        (compare (match_operand:SF 0 "general_operand" "")
524                 (match_operand:SF 1 "general_operand" "")))]
525  "TARGET_68881 || TARGET_FPA"
526  "
527 {
528   if (TARGET_FPA)
529     {
530       emit_insn (gen_cmpsf_fpa (operands[0], operands[1]));
531       DONE;
532     }
533 }")
534
535 (define_insn "cmpsf_fpa"
536   [(set (cc0)
537         (compare (match_operand:SF 0 "general_operand" "x,y")
538                  (match_operand:SF 1 "general_operand" "xH,rmF")))
539    (clobber (match_scratch:SI 2 "=d,d"))]
540   "TARGET_FPA"
541   "fpcmp%.s %w1,%x0\;fpmove fpastatus,%2\;movw %2,cc")
542
543 (define_insn ""
544   [(set (cc0)
545         (compare (match_operand:SF 0 "general_operand" "f,mdG")
546                  (match_operand:SF 1 "general_operand" "fmdG,f")))]
547   "TARGET_68881"
548   "*
549 {
550   cc_status.flags = CC_IN_68881;
551 #ifdef SGS_CMP_ORDER
552   if (FP_REG_P (operands[0]))
553     {
554       if (FP_REG_P (operands[1]))
555         return \"fcmp%.x %0,%1\";
556       else
557         return \"fcmp%.s %0,%f1\";
558     }
559   cc_status.flags |= CC_REVERSED;
560   return \"fcmp%.s %1,%f0\";
561 #else
562   if (FP_REG_P (operands[0]))
563     {
564       if (FP_REG_P (operands[1]))
565         return \"fcmp%.x %1,%0\";
566       else
567         return \"fcmp%.s %f1,%0\";
568     }
569   cc_status.flags |= CC_REVERSED;
570   return \"fcmp%.s %f0,%1\";
571 #endif
572 }")
573 \f
574 ;; Recognizers for btst instructions.
575
576 (define_insn ""
577   [(set (cc0) (zero_extract (match_operand:QI 0 "nonimmediate_operand" "do")
578                             (const_int 1)
579                             (minus:SI (const_int 7)
580                                       (match_operand:SI 1 "general_operand" "di"))))]
581   ""
582   "* { return output_btst (operands, operands[1], operands[0], insn, 7); }")
583
584 (define_insn ""
585   [(set (cc0) (zero_extract (match_operand:SI 0 "nonimmediate_operand" "d")
586                             (const_int 1)
587                             (minus:SI (const_int 31)
588                                       (match_operand:SI 1 "general_operand" "di"))))]
589   ""
590   "* { return output_btst (operands, operands[1], operands[0], insn, 31); }")
591
592 ;; The following two patterns are like the previous two
593 ;; except that they use the fact that bit-number operands
594 ;; are automatically masked to 3 or 5 bits.
595
596 (define_insn ""
597   [(set (cc0) (zero_extract (match_operand:QI 0 "nonimmediate_operand" "do")
598                             (const_int 1)
599                             (minus:SI (const_int 7)
600                                       (and:SI
601                                        (match_operand:SI 1 "register_operand" "d")
602                                        (const_int 7)))))]
603   ""
604   "* { return output_btst (operands, operands[1], operands[0], insn, 7); }")
605
606 (define_insn ""
607   [(set (cc0) (zero_extract (match_operand:SI 0 "nonimmediate_operand" "d")
608                             (const_int 1)
609                             (minus:SI (const_int 31)
610                                       (and:SI
611                                        (match_operand:SI 1 "register_operand" "d")
612                                        (const_int 31)))))]
613   ""
614   "* { return output_btst (operands, operands[1], operands[0], insn, 31); }")
615
616 ;; Nonoffsettable mem refs are ok in this one pattern
617 ;; since we don't try to adjust them.
618 (define_insn ""
619   [(set (cc0) (zero_extract (match_operand:QI 0 "nonimmediate_operand" "md")
620                             (const_int 1)
621                             (match_operand:SI 1 "const_int_operand" "n")))]
622   "(unsigned) INTVAL (operands[1]) < 8"
623   "*
624 {
625   operands[1] = gen_rtx (CONST_INT, VOIDmode, 7 - INTVAL (operands[1]));
626   return output_btst (operands, operands[1], operands[0], insn, 7);
627 }")
628
629 (define_insn ""
630   [(set (cc0) (zero_extract (match_operand:SI 0 "nonimmediate_operand" "do")
631                             (const_int 1)
632                             (match_operand:SI 1 "const_int_operand" "n")))]
633   ""
634   "*
635 {
636   if (GET_CODE (operands[0]) == MEM)
637     {
638       operands[0] = adj_offsettable_operand (operands[0],
639                                              INTVAL (operands[1]) / 8);
640       operands[1] = gen_rtx (CONST_INT, VOIDmode, 
641                              7 - INTVAL (operands[1]) % 8);
642       return output_btst (operands, operands[1], operands[0], insn, 7);
643     }
644   operands[1] = gen_rtx (CONST_INT, VOIDmode,
645                          31 - INTVAL (operands[1]));
646   return output_btst (operands, operands[1], operands[0], insn, 31);
647 }")
648
649 \f
650 ;; move instructions
651
652 ;; A special case in which it is not desirable
653 ;; to reload the constant into a data register.
654 (define_insn ""
655   [(set (match_operand:SI 0 "push_operand" "=m")
656         (match_operand:SI 1 "const_int_operand" "J"))]
657   "INTVAL (operands[1]) >= -0x8000 && INTVAL (operands[1]) < 0x8000"
658   "*
659 {
660   if (operands[1] == const0_rtx)
661     return \"clr%.l %0\";
662   return \"pea %a1\";
663 }")
664
665 ;This is never used.
666 ;(define_insn "swapsi"
667 ;  [(set (match_operand:SI 0 "general_operand" "+r")
668 ;       (match_operand:SI 1 "general_operand" "+r"))
669 ;   (set (match_dup 1) (match_dup 0))]
670 ;  ""
671 ;  "exg %1,%0")
672
673 ;; Special case of fullword move when source is zero.
674 ;; The reason this is special is to avoid loading a zero
675 ;; into a data reg with moveq in order to store it elsewhere.
676    
677 (define_insn ""
678   [(set (match_operand:SI 0 "general_operand" "=g")
679         (const_int 0))]
680   ;; clr insns on 68000 read before writing.
681   ;; This isn't so on the 68010, but we have no alternative for it.
682   "(TARGET_68020
683     || !(GET_CODE (operands[0]) == MEM && MEM_VOLATILE_P (operands[0])))"
684   "*
685 {
686   if (ADDRESS_REG_P (operands[0]))
687     return \"sub%.l %0,%0\";
688   /* moveq is faster on the 68000.  */
689   if (DATA_REG_P (operands[0]) && !TARGET_68020)
690 #if defined(MOTOROLA) && !defined(CRDS)
691     return \"moveq%.l %#0,%0\";
692 #else
693     return \"moveq %#0,%0\";
694 #endif
695   return \"clr%.l %0\";
696 }")
697
698 ;; General case of fullword move. 
699 ;;
700 ;; This is the main "hook" for PIC code.  When generating
701 ;; PIC, movsi is responsible for determining when the source address
702 ;; needs PIC relocation and appropriately calling legitimize_pic_address
703 ;; to perform the actual relocation.
704 ;;
705 ;; In both the PIC and non-PIC cases the patterns generated will
706 ;; matched by the next define_insn. 
707 (define_expand "movsi"
708   [(set (match_operand:SI 0 "general_operand" "")
709         (match_operand:SI 1 "general_operand" ""))]
710   ""
711   "
712 {
713   if (flag_pic && symbolic_operand (operands[1], SImode)) 
714     {
715       /* The source is an address which requires PIC relocation.  
716          Call legitimize_pic_address with the source, mode, and a relocation
717          register (a new pseudo, or the final destination if reload_in_progress
718          is set).   Then fall through normally */
719       extern rtx legitimize_pic_address();
720       rtx temp = reload_in_progress ? operands[0] : gen_reg_rtx (Pmode);
721       operands[1] = legitimize_pic_address (operands[1], SImode, temp);
722     }
723 }")
724
725 ;; General case of fullword move.  The register constraints
726 ;; force integer constants in range for a moveq to be reloaded
727 ;; if they are headed for memory.
728 (define_insn ""
729   ;; Notes: make sure no alternative allows g vs g.
730   ;; We don't allow f-regs since fixed point cannot go in them.
731   ;; We do allow y and x regs since fixed point is allowed in them.
732   [(set (match_operand:SI 0 "general_operand" "=g,da,y,!*x*r*m")
733         (match_operand:SI 1 "general_operand" "daymKs,i,g,*x*r*m"))]
734   ""
735   "*
736 {
737   if (which_alternative == 3)
738     return \"fpmove%.l %x1,fpa0\;fpmove%.l fpa0,%x0\";  
739   if (FPA_REG_P (operands[1]) || FPA_REG_P (operands[0]))
740     return \"fpmove%.l %x1,%x0\";
741   if (GET_CODE (operands[1]) == CONST_INT)
742     {
743       if (operands[1] == const0_rtx
744           && (DATA_REG_P (operands[0])
745               || GET_CODE (operands[0]) == MEM)
746           /* clr insns on 68000 read before writing.
747              This isn't so on the 68010, but we have no alternative for it.  */
748           && (TARGET_68020
749               || !(GET_CODE (operands[0]) == MEM
750                    && MEM_VOLATILE_P (operands[0]))))
751         return \"clr%.l %0\";
752       else if (DATA_REG_P (operands[0])
753                && INTVAL (operands[1]) < 128
754                && INTVAL (operands[1]) >= -128)
755         {
756 #if defined(MOTOROLA) && !defined(CRDS)
757           return \"moveq%.l %1,%0\";
758 #else
759           return \"moveq %1,%0\";
760 #endif
761         }
762       else if (DATA_REG_P (operands[0])
763                 /* if -256 < N < 256 but N is not in range for a moveq
764                    N^ff will be, so use moveq #N^ff, dreg; not.b dreg.  */
765                && INTVAL (operands[1]) < 256
766                && INTVAL (operands[1]) >= -256)
767         {
768           operands[1] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) ^ 0xff);
769 #if defined(MOTOROLA) && !defined(CRDS)
770           return \"moveq%.l %1,%0\;not%.b %0\";
771 #else
772           return \"moveq %1,%0\;not%.b %0\";
773 #endif   
774         }
775       else if (ADDRESS_REG_P (operands[0])
776                && INTVAL (operands[1]) < 0x8000
777                && INTVAL (operands[1]) >= -0x8000)
778         return \"move%.w %1,%0\";
779       else if (push_operand (operands[0], SImode)
780                && INTVAL (operands[1]) < 0x8000
781                && INTVAL (operands[1]) >= -0x8000)
782         return \"pea %a1\";
783     }
784   else if ((GET_CODE (operands[1]) == SYMBOL_REF
785             || GET_CODE (operands[1]) == CONST)
786            && push_operand (operands[0], SImode))
787     return \"pea %a1\";
788   else if ((GET_CODE (operands[1]) == SYMBOL_REF
789             || GET_CODE (operands[1]) == CONST)
790            && ADDRESS_REG_P (operands[0]))
791     return \"lea %a1,%0\";
792   return \"move%.l %1,%0\";
793 }")
794
795 (define_insn "movhi"
796   [(set (match_operand:HI 0 "general_operand" "=g")
797         (match_operand:HI 1 "general_operand" "g"))]
798   ""
799   "*
800 {
801   if (GET_CODE (operands[1]) == CONST_INT)
802     {
803       if (operands[1] == const0_rtx
804           && (DATA_REG_P (operands[0])
805               || GET_CODE (operands[0]) == MEM)
806           /* clr insns on 68000 read before writing.
807              This isn't so on the 68010, but we have no alternative for it.  */
808           && (TARGET_68020
809               || !(GET_CODE (operands[0]) == MEM
810                    && MEM_VOLATILE_P (operands[0]))))
811         return \"clr%.w %0\";
812       else if (DATA_REG_P (operands[0])
813                && INTVAL (operands[1]) < 128
814                && INTVAL (operands[1]) >= -128)
815         {
816 #if defined(MOTOROLA) && !defined(CRDS)
817           return \"moveq%.l %1,%0\";
818 #else
819           return \"moveq %1,%0\";
820 #endif
821         }
822       else if (INTVAL (operands[1]) < 0x8000
823                && INTVAL (operands[1]) >= -0x8000)
824         return \"move%.w %1,%0\";
825     }
826   else if (CONSTANT_P (operands[1]))
827     return \"move%.l %1,%0\";
828 #ifndef SGS_NO_LI
829   /* Recognize the insn before a tablejump, one that refers
830      to a table of offsets.  Such an insn will need to refer
831      to a label on the insn.  So output one.  Use the label-number
832      of the table of offsets to generate this label.  This code,
833      and similar code below, assumes that there will be at most one
834      reference to each table.  */
835   if (GET_CODE (operands[1]) == MEM
836       && GET_CODE (XEXP (operands[1], 0)) == PLUS
837       && GET_CODE (XEXP (XEXP (operands[1], 0), 1)) == LABEL_REF
838       && GET_CODE (XEXP (XEXP (operands[1], 0), 0)) != PLUS)
839     {
840       rtx labelref = XEXP (XEXP (operands[1], 0), 1);
841 #if defined (MOTOROLA) && !defined (SGS_SWITCH_TABLES)
842 #ifdef SGS
843       asm_fprintf (asm_out_file, \"\\tset %LLI%d,.+2\\n\",
844                    CODE_LABEL_NUMBER (XEXP (labelref, 0)));
845 #else /* not SGS */
846       asm_fprintf (asm_out_file, \"\\t.set %LLI%d,.+2\\n\",
847                    CODE_LABEL_NUMBER (XEXP (labelref, 0)));
848 #endif /* not SGS */
849 #else /* SGS_SWITCH_TABLES or not MOTOROLA */
850       ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, \"LI\",
851                                  CODE_LABEL_NUMBER (XEXP (labelref, 0)));
852 #ifdef SGS_SWITCH_TABLES
853       /* Set flag saying we need to define the symbol
854          LD%n (with value L%n-LI%n) at the end of the switch table.  */
855       switch_table_difference_label_flag = 1;
856 #endif /* SGS_SWITCH_TABLES */
857 #endif /* SGS_SWITCH_TABLES or not MOTOROLA */
858     }
859 #endif /* SGS_NO_LI */
860   return \"move%.w %1,%0\";
861 }")
862
863 (define_insn "movstricthi"
864   [(set (strict_low_part (match_operand:HI 0 "general_operand" "+dm"))
865         (match_operand:HI 1 "general_operand" "rmn"))]
866   ""
867   "*
868 {
869   if (GET_CODE (operands[1]) == CONST_INT)
870     {
871       if (operands[1] == const0_rtx
872           && (DATA_REG_P (operands[0])
873               || GET_CODE (operands[0]) == MEM)
874           /* clr insns on 68000 read before writing.
875              This isn't so on the 68010, but we have no alternative for it.  */
876           && (TARGET_68020
877               || !(GET_CODE (operands[0]) == MEM
878                    && MEM_VOLATILE_P (operands[0]))))
879         return \"clr%.w %0\";
880     }
881   return \"move%.w %1,%0\";
882 }")
883
884 (define_insn "movqi"
885   [(set (match_operand:QI 0 "general_operand" "=d,*a,m,m,?*a")
886         (match_operand:QI 1 "general_operand" "dmi*a,d*a,dmi,?*a,m"))]
887   ""
888   "*
889 {
890   rtx xoperands[4];
891
892   /* This is probably useless, since it loses for pushing a struct
893      of several bytes a byte at a time.  */
894   if (GET_CODE (operands[0]) == MEM
895       && GET_CODE (XEXP (operands[0], 0)) == PRE_DEC
896       && XEXP (XEXP (operands[0], 0), 0) == stack_pointer_rtx
897       && ! ADDRESS_REG_P (operands[1]))
898     {
899       xoperands[1] = operands[1];
900       xoperands[2]
901         = gen_rtx (MEM, QImode,
902                    gen_rtx (PLUS, VOIDmode, stack_pointer_rtx, const1_rtx));
903       /* Just pushing a byte puts it in the high byte of the halfword.  */
904       /* We must put it in the low-order, high-numbered byte.  */
905       output_asm_insn (\"move%.b %1,%-\;move%.b %@,%2\", xoperands);
906       return \"\";
907     }
908
909   /* Moving a byte into an address register is not possible.  */
910   /* Use d0 as an intermediate, but don't clobber its contents.  */
911   if (ADDRESS_REG_P (operands[0]) && GET_CODE (operands[1]) == MEM)
912     {
913       /* ??? For 2.5, don't allow this choice and use secondary reloads
914          instead.
915
916          See if the address register is used in the address.  If it
917          is, we have to generate a more complex sequence than those below.  */
918       if (refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
919                              operands[1], NULL_RTX))
920         {
921           /* See if the stack pointer is used in the address.  If it isn't,
922              we can push d0 or d1 (the insn can't use both of them) on
923              the stack, perform our move into d0/d1, copy the byte from d0/1,
924              and pop d0/1.  */
925           if (! reg_mentioned_p (stack_pointer_rtx, operands[1]))
926             {
927               if (refers_to_regno_p (0, 1, operands[1], NULL_RTX))
928                 return \"move%.l %/d0,%-\;move%.b %1,%/d0\;move%.l %/d0,%0\;move%.l %+,%/d0\";
929               else
930                 return \"move%.l %/d1,%-\;move%.b %1,%/d1\;move%.l %/d1,%0\;move%.l %+,%/d1\";
931             }
932           else
933             {
934               /* Otherwise, we know that d0 cannot be used in the address
935                  (since sp and one address register is).  Assume that sp is
936                  being used as a base register and replace the address
937                  register that is our operand[0] with d0.  */
938               rtx reg_map[FIRST_PSEUDO_REGISTER];
939               int i;
940
941               for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
942                 reg_map[i] = 0;
943
944               reg_map[REGNO (operands[0])] = gen_rtx (REG, Pmode, 0);
945               operands[1] = copy_rtx (operands[1]);
946               replace_regs (operands[1], reg_map, FIRST_PSEUDO_REGISTER, 0);
947               return \"exg %/d0,%0\;move%.b %1,%/d0\;exg %/d0,%0\";
948             }
949         }
950
951       /* If the address of operand 1 uses d0, choose d1 as intermediate.  */
952       if (refers_to_regno_p (0, 1, operands[1], NULL_RTX))
953         return \"exg %/d1,%0\;move%.b %1,%/d1\;exg %/d1,%0\";
954       /* Otherwise d0 is usable.
955          (An effective address on the 68k can't use two d-regs.)  */
956       else
957         return \"exg %/d0,%0\;move%.b %1,%/d0\;exg %/d0,%0\";
958     }
959     
960   /* Likewise for moving from an address reg.  */
961   if (ADDRESS_REG_P (operands[1]) && GET_CODE (operands[0]) == MEM)
962     {
963       /* ??? For 2.5, don't allow this choice and use secondary reloads
964          instead.
965
966          See if the address register is used in the address.  If it
967          is, we have to generate a more complex sequence than those below.  */
968       if (refers_to_regno_p (REGNO (operands[1]), REGNO (operands[1]) + 1,
969                              operands[0], NULL_RTX))
970         {
971           /* See if the stack pointer is used in the address.  If it isn't,
972              we can push d0 or d1 (the insn can't use both of them) on
973              the stack, copy the byte to d0/1, perform our move from d0/d1, 
974              and pop d0/1.  */
975           if (! reg_mentioned_p (stack_pointer_rtx, operands[0]))
976             {
977               if (refers_to_regno_p (0, 1, operands[0], NULL_RTX))
978                 return \"move%.l %/d0,%-\;move%.l %1,%/d0\;move%.b %/d0,%0\;move%.l %+,%/d0\";
979               else
980                 return \"move%.l %/d1,%-\;move%.l %1,%/d1\;move%.b %/d1,%0\;move%.l %+,%/d1\";
981             }
982           else
983             {
984               /* Otherwise, we know that d0 cannot be used in the address
985                  (since sp and one address register is).  Assume that sp is
986                  being used as a base register and replace the address
987                  register that is our operand[1] with d0.  */
988               rtx reg_map[FIRST_PSEUDO_REGISTER];
989               int i;
990
991               for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
992                 reg_map[i] = 0;
993
994               reg_map[REGNO (operands[1])] = gen_rtx (REG, Pmode, 0);
995               operands[0] = copy_rtx (operands[0]);
996               replace_regs (operands[0], reg_map, FIRST_PSEUDO_REGISTER, 0);
997               return \"exg %/d0,%1\;move%.b %/d0,%0\;exg %/d0,%1\";
998             }
999         }
1000
1001       if (refers_to_regno_p (0, 1, operands[0], NULL_RTX))
1002         return \"exg %/d1,%1\;move%.b %/d1,%0\;exg %/d1,%1\";
1003       else
1004         return \"exg %/d0,%1\;move%.b %/d0,%0\;exg %/d0,%1\";
1005     }
1006
1007   /* clr and st insns on 68000 read before writing.
1008      This isn't so on the 68010, but we have no alternative for it.  */
1009   if (TARGET_68020
1010       || !(GET_CODE (operands[0]) == MEM && MEM_VOLATILE_P (operands[0])))
1011     {
1012       if (operands[1] == const0_rtx)
1013         return \"clr%.b %0\";
1014       if (GET_CODE (operands[1]) == CONST_INT
1015           && INTVAL (operands[1]) == -1)
1016         {
1017           CC_STATUS_INIT;
1018           return \"st %0\";
1019         }
1020     }
1021   if (GET_CODE (operands[1]) != CONST_INT && CONSTANT_P (operands[1]))
1022     return \"move%.l %1,%0\";
1023   if (ADDRESS_REG_P (operands[0]) || ADDRESS_REG_P (operands[1]))
1024     return \"move%.w %1,%0\";
1025   return \"move%.b %1,%0\";
1026 }")
1027
1028 (define_insn "movstrictqi"
1029   [(set (strict_low_part (match_operand:QI 0 "general_operand" "+dm"))
1030         (match_operand:QI 1 "general_operand" "dmn"))]
1031   ""
1032   "*
1033 {
1034   if (operands[1] == const0_rtx
1035       /* clr insns on 68000 read before writing.
1036          This isn't so on the 68010, but we have no alternative for it.  */
1037       && (TARGET_68020
1038           || !(GET_CODE (operands[0]) == MEM && MEM_VOLATILE_P (operands[0]))))
1039     return \"clr%.b %0\";
1040   return \"move%.b %1,%0\";
1041 }")
1042
1043 (define_insn "movsf"
1044   [(set (match_operand:SF 0 "general_operand" "=rmf,x,y,rm,!x,!rm")
1045         (match_operand:SF 1 "general_operand" "rmfF,xH,rmF,y,rm,x"))]
1046 ;  [(set (match_operand:SF 0 "general_operand" "=rmf")
1047 ;       (match_operand:SF 1 "general_operand" "rmfF"))]
1048   ""
1049   "*
1050 {
1051   if (which_alternative >= 4)
1052     return \"fpmove%.s %1,fpa0\;fpmove%.s fpa0,%0\";
1053   if (FPA_REG_P (operands[0]))
1054     {
1055       if (FPA_REG_P (operands[1]))
1056         return \"fpmove%.s %x1,%x0\";
1057       else if (GET_CODE (operands[1]) == CONST_DOUBLE)
1058         return output_move_const_single (operands);
1059       else if (FP_REG_P (operands[1]))
1060         return \"fmove%.s %1,sp@-\;fpmove%.d sp@+, %0\";
1061       return \"fpmove%.s %x1,%x0\";
1062     }
1063   if (FPA_REG_P (operands[1]))
1064     {
1065       if (FP_REG_P (operands[0]))
1066         return \"fpmove%.s %x1,sp@-\;fmove%.s sp@+,%0\";
1067       else
1068         return \"fpmove%.s %x1,%x0\";
1069     }
1070   if (FP_REG_P (operands[0]))
1071     {
1072       if (FP_REG_P (operands[1]))
1073         return \"f%$move%.x %1,%0\";
1074       else if (ADDRESS_REG_P (operands[1]))
1075         return \"move%.l %1,%-\;f%$move%.s %+,%0\";
1076       else if (GET_CODE (operands[1]) == CONST_DOUBLE)
1077         return output_move_const_single (operands);
1078       return \"f%$move%.s %f1,%0\";
1079     }
1080   if (FP_REG_P (operands[1]))
1081     {
1082       if (ADDRESS_REG_P (operands[0]))
1083         return \"fmove%.s %1,%-\;move%.l %+,%0\";
1084       return \"fmove%.s %f1,%0\";
1085     }
1086   return \"move%.l %1,%0\";
1087 }")
1088
1089 (define_insn "movdf"
1090   [(set (match_operand:DF 0 "general_operand" "=rm,rf,rf,&rof<>,y,rm,x,!x,!rm")
1091         (match_operand:DF 1 "general_operand" "rf,m,0,rofE<>,rmE,y,xH,rm,x"))]
1092 ;  [(set (match_operand:DF 0 "general_operand" "=rm,&rf,&rof<>")
1093 ;       (match_operand:DF 1 "general_operand" "rf,m,rofF<>"))]
1094   ""
1095   "*
1096 {
1097   if (which_alternative == 7)
1098     return \"fpmove%.d %x1,fpa0\;fpmove%.d fpa0,%x0\";
1099   if (FPA_REG_P (operands[0]))
1100     {
1101       if (GET_CODE (operands[1]) == CONST_DOUBLE)
1102         return output_move_const_double (operands);
1103       if (FP_REG_P (operands[1]))
1104         return \"fmove%.d %1,sp@-\;fpmove%.d sp@+,%x0\";
1105       return \"fpmove%.d %x1,%x0\";
1106     }
1107   else if (FPA_REG_P (operands[1]))
1108     {
1109       if (FP_REG_P(operands[0]))
1110         return \"fpmove%.d %x1,sp@-\;fmoved sp@+,%0\";
1111       else
1112         return \"fpmove%.d %x1,%x0\";
1113     }
1114   if (FP_REG_P (operands[0]))
1115     {
1116       if (FP_REG_P (operands[1]))
1117         return \"f%&move%.x %1,%0\";
1118       if (REG_P (operands[1]))
1119         {
1120           rtx xoperands[2];
1121           xoperands[1] = gen_rtx (REG, SImode, REGNO (operands[1]) + 1);
1122           output_asm_insn (\"move%.l %1,%-\", xoperands);
1123           output_asm_insn (\"move%.l %1,%-\", operands);
1124           return \"f%&move%.d %+,%0\";
1125         }
1126       if (GET_CODE (operands[1]) == CONST_DOUBLE)
1127         return output_move_const_double (operands);
1128       return \"f%&move%.d %f1,%0\";
1129     }
1130   else if (FP_REG_P (operands[1]))
1131     {
1132       if (REG_P (operands[0]))
1133         {
1134           output_asm_insn (\"fmove%.d %f1,%-\;move%.l %+,%0\", operands);
1135           operands[0] = gen_rtx (REG, SImode, REGNO (operands[0]) + 1);
1136           return \"move%.l %+,%0\";
1137         }
1138       else
1139         return \"fmove%.d %f1,%0\";
1140     }
1141   return output_move_double (operands);
1142 }
1143 ")
1144
1145 (define_expand "movxf"
1146   [(set (match_operand:XF 0 "nonimmediate_operand" "")
1147         (match_operand:XF 1 "general_operand" ""))]
1148   ""
1149   "
1150 {
1151   if (CONSTANT_P (operands[1]))
1152     {
1153       operands[1] = force_const_mem (XFmode, operands[1]);
1154       if (! memory_address_p (XFmode, XEXP (operands[1], 0))
1155           && ! reload_in_progress)
1156         operands[1] = change_address (operands[1], XFmode,
1157                                       XEXP (operands[1], 0));
1158     }
1159 }")
1160
1161 (define_insn ""
1162   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,!r,!f")
1163         (match_operand:XF 1 "nonimmediate_operand" "m,f,f,f,r"))]
1164   "TARGET_68881"
1165   "*
1166 {
1167   if (FP_REG_P (operands[0]))
1168     {
1169       if (FP_REG_P (operands[1]))
1170         return \"fmove%.x %1,%0\";
1171       if (REG_P (operands[1]))
1172         {
1173           rtx xoperands[2];
1174           xoperands[1] = gen_rtx (REG, SImode, REGNO (operands[1]) + 2);
1175           output_asm_insn (\"move%.l %1,%-\", xoperands);
1176           xoperands[1] = gen_rtx (REG, SImode, REGNO (operands[1]) + 1);
1177           output_asm_insn (\"move%.l %1,%-\", xoperands);
1178           output_asm_insn (\"move%.l %1,%-\", operands);
1179           return \"fmove%.x %+,%0\";
1180         }
1181       if (GET_CODE (operands[1]) == CONST_DOUBLE)
1182         return \"fmove%.x %1,%0\";
1183       return \"fmove%.x %f1,%0\";
1184     }
1185   if (REG_P (operands[0]))
1186     {
1187       output_asm_insn (\"fmove%.x %f1,%-\;move%.l %+,%0\", operands);
1188       operands[0] = gen_rtx (REG, SImode, REGNO (operands[0]) + 1);
1189       output_asm_insn (\"move%.l %+,%0\", operands);
1190       operands[0] = gen_rtx (REG, SImode, REGNO (operands[0]) + 1);
1191       return \"move%.l %+,%0\";
1192     }
1193   return \"fmove%.x %f1,%0\";
1194 }
1195 ")
1196
1197 (define_insn ""
1198   [(set (match_operand:XF 0 "nonimmediate_operand" "=rm,rf,&rof<>")
1199         (match_operand:XF 1 "nonimmediate_operand" "rf,m,rof<>"))]
1200   "! TARGET_68881"
1201   "*
1202 {
1203   if (FP_REG_P (operands[0]))
1204     {
1205       if (FP_REG_P (operands[1]))
1206         return \"fmove%.x %1,%0\";
1207       if (REG_P (operands[1]))
1208         {
1209           rtx xoperands[2];
1210           xoperands[1] = gen_rtx (REG, SImode, REGNO (operands[1]) + 2);
1211           output_asm_insn (\"move%.l %1,%-\", xoperands);
1212           xoperands[1] = gen_rtx (REG, SImode, REGNO (operands[1]) + 1);
1213           output_asm_insn (\"move%.l %1,%-\", xoperands);
1214           output_asm_insn (\"move%.l %1,%-\", operands);
1215           return \"fmove%.x %+,%0\";
1216         }
1217       if (GET_CODE (operands[1]) == CONST_DOUBLE)
1218         return \"fmove%.x %1,%0\";
1219       return \"fmove%.x %f1,%0\";
1220     }
1221   if (FP_REG_P (operands[1]))
1222     {
1223       if (REG_P (operands[0]))
1224         {
1225           output_asm_insn (\"fmove%.x %f1,%-\;move%.l %+,%0\", operands);
1226           operands[0] = gen_rtx (REG, SImode, REGNO (operands[0]) + 1);
1227           output_asm_insn (\"move%.l %+,%0\", operands);
1228           operands[0] = gen_rtx (REG, SImode, REGNO (operands[0]) + 1);
1229           return \"move%.l %+,%0\";
1230         }
1231       else
1232         return \"fmove%.x %f1,%0\";
1233     }
1234   return output_move_double (operands);
1235 }
1236 ")
1237
1238 ;; movdi can apply to fp regs in some cases
1239 (define_insn "movdi"
1240   ;; Let's see if it really still needs to handle fp regs, and, if so, why.
1241   [(set (match_operand:DI 0 "general_operand" "=rm,r,&ro<>,y,rm,!*x,!rm")
1242         (match_operand:DI 1 "general_operand" "rF,m,roi<>F,rmiF,y,rmF,*x"))]
1243 ;  [(set (match_operand:DI 0 "general_operand" "=rm,&r,&ro<>,!&rm,!&f,y,rm,x,!x,!rm")
1244 ;       (match_operand:DI 1 "general_operand" "r,m,roi<>,fF,rfmF,rmi,y,rm,x"))]
1245 ;  [(set (match_operand:DI 0 "general_operand" "=rm,&rf,&ro<>,!&rm,!&f")
1246 ;       (match_operand:DI 1 "general_operand" "r,m,roi<>,fF,rfF"))]
1247   ""
1248   "*
1249 {
1250   if (which_alternative == 8)
1251     return \"fpmove%.d %x1,fpa0\;fpmove%.d fpa0,%x0\";
1252   if (FPA_REG_P (operands[0]) || FPA_REG_P (operands[1]))
1253     return \"fpmove%.d %x1,%x0\";
1254   if (FP_REG_P (operands[0]))
1255     {
1256       if (FP_REG_P (operands[1]))
1257         return \"fmove%.x %1,%0\";
1258       if (REG_P (operands[1]))
1259         {
1260           rtx xoperands[2];
1261           xoperands[1] = gen_rtx (REG, SImode, REGNO (operands[1]) + 1);
1262           output_asm_insn (\"move%.l %1,%-\", xoperands);
1263           output_asm_insn (\"move%.l %1,%-\", operands);
1264           return \"fmove%.d %+,%0\";
1265         }
1266       if (GET_CODE (operands[1]) == CONST_DOUBLE)
1267         return output_move_const_double (operands);
1268       return \"fmove%.d %f1,%0\";
1269     }
1270   else if (FP_REG_P (operands[1]))
1271     {
1272       if (REG_P (operands[0]))
1273         {
1274           output_asm_insn (\"fmove%.d %f1,%-\;move%.l %+,%0\", operands);
1275           operands[0] = gen_rtx (REG, SImode, REGNO (operands[0]) + 1);
1276           return \"move%.l %+,%0\";
1277         }
1278       else
1279         return \"fmove%.d %f1,%0\";
1280     }
1281   return output_move_double (operands);
1282 }
1283 ")
1284
1285 ;; Thus goes after the move instructions
1286 ;; because the move instructions are better (require no spilling)
1287 ;; when they can apply.  It goes before the add/sub insns
1288 ;; so we will prefer it to them.
1289
1290 (define_insn "pushasi"
1291   [(set (match_operand:SI 0 "push_operand" "=m")
1292         (match_operand:SI 1 "address_operand" "p"))]
1293   ""
1294   "pea %a1")
1295 \f
1296 ;; truncation instructions
1297 (define_insn "truncsiqi2"
1298   [(set (match_operand:QI 0 "general_operand" "=dm,d")
1299         (truncate:QI
1300          (match_operand:SI 1 "general_operand" "doJ,i")))]
1301   ""
1302   "*
1303 {
1304   if (GET_CODE (operands[0]) == REG)
1305     {
1306       /* Must clear condition codes, since the move.l bases them on
1307          the entire 32 bits, not just the desired 8 bits.  */
1308       CC_STATUS_INIT;
1309       return \"move%.l %1,%0\";
1310     }
1311   if (GET_CODE (operands[1]) == MEM)
1312     operands[1] = adj_offsettable_operand (operands[1], 3);
1313   return \"move%.b %1,%0\";
1314 }")
1315
1316 (define_insn "trunchiqi2"
1317   [(set (match_operand:QI 0 "general_operand" "=dm,d")
1318         (truncate:QI
1319          (match_operand:HI 1 "general_operand" "doJ,i")))]
1320   ""
1321   "*
1322 {
1323   if (GET_CODE (operands[0]) == REG
1324       && (GET_CODE (operands[1]) == MEM
1325           || GET_CODE (operands[1]) == CONST_INT))
1326     {
1327       /* Must clear condition codes, since the move.w bases them on
1328          the entire 16 bits, not just the desired 8 bits.  */
1329       CC_STATUS_INIT;
1330       return \"move%.w %1,%0\";
1331     }
1332   if (GET_CODE (operands[0]) == REG)
1333     {
1334       /* Must clear condition codes, since the move.l bases them on
1335          the entire 32 bits, not just the desired 8 bits.  */
1336       CC_STATUS_INIT;
1337       return \"move%.l %1,%0\";
1338     }
1339   if (GET_CODE (operands[1]) == MEM)
1340     operands[1] = adj_offsettable_operand (operands[1], 1);
1341   return \"move%.b %1,%0\";
1342 }")
1343
1344 (define_insn "truncsihi2"
1345   [(set (match_operand:HI 0 "general_operand" "=dm,d")
1346         (truncate:HI
1347          (match_operand:SI 1 "general_operand" "roJ,i")))]
1348   ""
1349   "*
1350 {
1351   if (GET_CODE (operands[0]) == REG)
1352     {
1353       /* Must clear condition codes, since the move.l bases them on
1354          the entire 32 bits, not just the desired 8 bits.  */
1355       CC_STATUS_INIT;
1356       return \"move%.l %1,%0\";
1357     }
1358   if (GET_CODE (operands[1]) == MEM)
1359     operands[1] = adj_offsettable_operand (operands[1], 2);
1360   return \"move%.w %1,%0\";
1361 }")
1362 \f
1363 ;; zero extension instructions
1364
1365 (define_expand "zero_extendhisi2"
1366   [(set (match_operand:SI 0 "register_operand" "")
1367         (const_int 0))
1368    (set (strict_low_part (match_dup 2))
1369         (match_operand:HI 1 "general_operand" ""))]
1370   ""
1371   "
1372 {
1373   operands[1] = make_safe_from (operands[1], operands[0]);
1374   if (GET_CODE (operands[0]) == SUBREG)
1375     operands[2] = gen_rtx (SUBREG, HImode, SUBREG_REG (operands[0]),
1376                            SUBREG_WORD (operands[0]));
1377   else
1378     operands[2] = gen_rtx (SUBREG, HImode, operands[0], 0);
1379 }")
1380
1381 (define_expand "zero_extendqihi2"
1382   [(set (match_operand:HI 0 "register_operand" "")
1383         (const_int 0))
1384    (set (strict_low_part (match_dup 2))
1385         (match_operand:QI 1 "general_operand" ""))]
1386   ""
1387   "
1388 {
1389   operands[1] = make_safe_from (operands[1], operands[0]);
1390   if (GET_CODE (operands[0]) == SUBREG)
1391     operands[2] = gen_rtx (SUBREG, QImode, SUBREG_REG (operands[0]),
1392                            SUBREG_WORD (operands[0]));
1393   else
1394     operands[2] = gen_rtx (SUBREG, QImode, operands[0], 0);
1395 }")
1396
1397 (define_expand "zero_extendqisi2"
1398   [(set (match_operand:SI 0 "register_operand" "")
1399         (const_int 0))
1400    (set (strict_low_part (match_dup 2))
1401         (match_operand:QI 1 "general_operand" ""))]
1402   ""
1403   "
1404 {
1405   operands[1] = make_safe_from (operands[1], operands[0]);
1406   if (GET_CODE (operands[0]) == SUBREG)
1407     operands[2] = gen_rtx (SUBREG, QImode, SUBREG_REG (operands[0]),
1408                            SUBREG_WORD (operands[0]));
1409   else
1410     operands[2] = gen_rtx (SUBREG, QImode, operands[0], 0);
1411 }")
1412 \f
1413 ;; Patterns to recognize zero-extend insns produced by the combiner.
1414 ;; We don't allow both operands in memory, because of aliasing problems.
1415 ;; Explicitly disallow two memory operands via the condition since reloading
1416 ;; of this case will result in worse code than the uncombined patterns.
1417
1418 (define_insn ""
1419   [(set (match_operand:SI 0 "general_operand" "=do<>,d<")
1420         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "r,m")))]
1421   "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1422   "*
1423 {
1424   if (DATA_REG_P (operands[0]))
1425     {
1426       if (GET_CODE (operands[1]) == REG
1427           && REGNO (operands[0]) == REGNO (operands[1]))
1428         return \"and%.l %#0xFFFF,%0\";
1429       if (reg_mentioned_p (operands[0], operands[1]))
1430         return \"move%.w %1,%0\;and%.l %#0xFFFF,%0\";
1431       return \"clr%.l %0\;move%.w %1,%0\";
1432     }
1433   else if (GET_CODE (operands[0]) == MEM
1434            && GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
1435     return \"move%.w %1,%0\;clr%.w %0\";
1436   else if (GET_CODE (operands[0]) == MEM
1437            && GET_CODE (XEXP (operands[0], 0)) == POST_INC)
1438     return \"clr%.w %0\;move%.w %1,%0\";
1439   else
1440     {
1441       output_asm_insn (\"clr%.w %0\", operands);
1442       operands[0] = adj_offsettable_operand (operands[0], 2);
1443       return \"move%.w %1,%0\";
1444     }
1445 }")
1446
1447 (define_insn ""
1448   [(set (match_operand:HI 0 "general_operand" "=do<>,d")
1449         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "d,m")))]
1450   "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1451   "*
1452 {
1453   if (DATA_REG_P (operands[0]))
1454     {
1455       if (GET_CODE (operands[1]) == REG
1456           && REGNO (operands[0]) == REGNO (operands[1]))
1457         return \"and%.w %#0xFF,%0\";
1458       if (reg_mentioned_p (operands[0], operands[1]))
1459         return \"move%.b %1,%0\;and%.w %#0xFF,%0\";
1460       return \"clr%.w %0\;move%.b %1,%0\";
1461     }
1462   else if (GET_CODE (operands[0]) == MEM
1463            && GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
1464     {
1465       if (REGNO (XEXP (XEXP (operands[0], 0), 0))
1466           == STACK_POINTER_REGNUM)
1467         {
1468           output_asm_insn (\"clr%.w %-\", operands);
1469           operands[0] = gen_rtx (MEM, GET_MODE (operands[0]),
1470                                  plus_constant (stack_pointer_rtx, 1));
1471           return \"move%.b %1,%0\";
1472         }
1473       else
1474         return \"move%.b %1,%0\;clr%.b %0\";
1475     }
1476   else if (GET_CODE (operands[0]) == MEM
1477            && GET_CODE (XEXP (operands[0], 0)) == POST_INC)
1478     return \"clr%.b %0\;move%.b %1,%0\";
1479   else
1480     {
1481       output_asm_insn (\"clr%.b %0\", operands);
1482       operands[0] = adj_offsettable_operand (operands[0], 1);
1483       return \"move%.b %1,%0\";
1484     }
1485 }")
1486
1487 (define_insn ""
1488   [(set (match_operand:SI 0 "general_operand" "=do<>,d")
1489         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "d,m")))]
1490   "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1491   "*
1492 {
1493   if (DATA_REG_P (operands[0]))
1494     {
1495       if (GET_CODE (operands[1]) == REG
1496           && REGNO (operands[0]) == REGNO (operands[1]))
1497         return \"and%.l %#0xFF,%0\";
1498       if (reg_mentioned_p (operands[0], operands[1]))
1499         return \"move%.b %1,%0\;and%.l %#0xFF,%0\";
1500       return \"clr%.l %0\;move%.b %1,%0\";
1501     }
1502   else if (GET_CODE (operands[0]) == MEM
1503            && GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
1504     {
1505       operands[0] = XEXP (XEXP (operands[0], 0), 0);
1506 #ifdef MOTOROLA
1507 #ifdef SGS
1508       return \"clr%.l -(%0)\;move%.b %1,3(%0)\";
1509 #else
1510       return \"clr%.l -(%0)\;move%.b %1,(3,%0)\";
1511 #endif
1512 #else
1513       return \"clrl %0@-\;moveb %1,%0@(3)\";
1514 #endif
1515     }
1516   else if (GET_CODE (operands[0]) == MEM
1517            && GET_CODE (XEXP (operands[0], 0)) == POST_INC)
1518     {
1519       operands[0] = XEXP (XEXP (operands[0], 0), 0);
1520 #ifdef MOTOROLA
1521 #ifdef SGS
1522       return \"clr%.l (%0)+\;move%.b %1,-1(%0)\";
1523 #else
1524       return \"clr%.l (%0)+\;move%.b %1,(-1,%0)\";
1525 #endif
1526 #else
1527       return \"clrl %0@+\;moveb %1,%0@(-1)\";
1528 #endif
1529     }
1530   else
1531     {
1532       output_asm_insn (\"clr%.l %0\", operands);
1533       operands[0] = adj_offsettable_operand (operands[0], 3);
1534       return \"move%.b %1,%0\";
1535     }
1536 }")
1537 \f
1538 ;; sign extension instructions
1539
1540 (define_insn "extendhisi2"
1541   [(set (match_operand:SI 0 "general_operand" "=*d,a")
1542         (sign_extend:SI
1543          (match_operand:HI 1 "nonimmediate_operand" "0,rm")))]
1544   ""
1545   "*
1546 {
1547   if (ADDRESS_REG_P (operands[0]))
1548     return \"move%.w %1,%0\";
1549   return \"ext%.l %0\";
1550 }")
1551
1552 (define_insn "extendqihi2"
1553   [(set (match_operand:HI 0 "general_operand" "=d")
1554         (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "0")))]
1555   ""
1556   "ext%.w %0")
1557
1558 (define_insn "extendqisi2"
1559   [(set (match_operand:SI 0 "general_operand" "=d")
1560         (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "0")))]
1561   "TARGET_68020"
1562   "extb%.l %0")
1563 \f
1564 ;; Conversions between float and double.
1565
1566 (define_expand "extendsfdf2"
1567   [(set (match_operand:DF 0 "general_operand" "")
1568         (float_extend:DF
1569          (match_operand:SF 1 "general_operand" "")))]
1570   "TARGET_68881 || TARGET_FPA"
1571   "")
1572
1573 (define_insn ""
1574   [(set (match_operand:DF 0 "general_operand" "=x,y")
1575         (float_extend:DF
1576          (match_operand:SF 1 "general_operand" "xH,rmF")))]
1577   "TARGET_FPA"
1578   "fpstod %w1,%0")
1579
1580 (define_insn ""
1581   [(set (match_operand:DF 0 "general_operand" "=*fdm,f")
1582         (float_extend:DF
1583           (match_operand:SF 1 "general_operand" "f,dmF")))]
1584   "TARGET_68881"
1585   "*
1586 {
1587   if (FP_REG_P (operands[0]) && FP_REG_P (operands[1]))
1588     {
1589       if (REGNO (operands[0]) == REGNO (operands[1]))
1590         {
1591           /* Extending float to double in an fp-reg is a no-op.
1592              NOTICE_UPDATE_CC has already assumed that the
1593              cc will be set.  So cancel what it did.  */
1594           cc_status = cc_prev_status;
1595           return \"\";
1596         }
1597       return \"f%&move%.x %1,%0\";
1598     }
1599   if (FP_REG_P (operands[0]))
1600     return \"f%&move%.s %f1,%0\";
1601   if (DATA_REG_P (operands[0]) && FP_REG_P (operands[1]))
1602     {
1603       output_asm_insn (\"fmove%.d %f1,%-\;move%.l %+,%0\", operands);
1604       operands[0] = gen_rtx (REG, SImode, REGNO (operands[0]) + 1);
1605       return \"move%.l %+,%0\";
1606     }
1607   return \"fmove%.d %f1,%0\";
1608 }")
1609
1610 ;; This cannot output into an f-reg because there is no way to be
1611 ;; sure of truncating in that case.
1612 ;; But on the Sun FPA, we can be sure.
1613 (define_expand "truncdfsf2"
1614   [(set (match_operand:SF 0 "general_operand" "")
1615         (float_truncate:SF
1616           (match_operand:DF 1 "general_operand" "")))]
1617   "TARGET_68881 || TARGET_FPA"
1618   "")
1619
1620 (define_insn ""
1621   [(set (match_operand:SF 0 "general_operand" "=x,y")
1622         (float_truncate:SF
1623           (match_operand:DF 1 "general_operand" "xH,rmF")))]
1624   "TARGET_FPA"
1625   "fpdtos %y1,%0")
1626
1627 ;; On the '040 we can truncate in a register accurately and easily.
1628 (define_insn ""
1629   [(set (match_operand:SF 0 "general_operand" "=f")
1630         (float_truncate:SF
1631           (match_operand:DF 1 "general_operand" "fmG")))]
1632   "TARGET_68040_ONLY"
1633   "*
1634 {
1635   if (FP_REG_P (operands[1]))
1636     return \"f%$move%.x %1,%0\";
1637   return \"f%$move%.d %f1,%0\";
1638 }")
1639
1640 (define_insn ""
1641   [(set (match_operand:SF 0 "general_operand" "=dm")
1642         (float_truncate:SF
1643           (match_operand:DF 1 "general_operand" "f")))]
1644   "TARGET_68881"
1645   "fmove%.s %f1,%0")
1646 \f
1647 ;; Conversion between fixed point and floating point.
1648 ;; Note that among the fix-to-float insns
1649 ;; the ones that start with SImode come first.
1650 ;; That is so that an operand that is a CONST_INT
1651 ;; (and therefore lacks a specific machine mode).
1652 ;; will be recognized as SImode (which is always valid)
1653 ;; rather than as QImode or HImode.
1654
1655 (define_expand "floatsisf2"
1656   [(set (match_operand:SF 0 "general_operand" "")
1657         (float:SF (match_operand:SI 1 "general_operand" "")))]
1658   "TARGET_68881 || TARGET_FPA"
1659   "")
1660
1661 (define_insn ""
1662   [(set (match_operand:SF 0 "general_operand" "=y,x")
1663         (float:SF (match_operand:SI 1 "general_operand" "rmi,x")))]
1664   "TARGET_FPA"
1665   "fpltos %1,%0")
1666
1667 (define_insn ""
1668   [(set (match_operand:SF 0 "general_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 "general_operand" "")
1675         (float:DF (match_operand:SI 1 "general_operand" "")))]
1676   "TARGET_68881 || TARGET_FPA"
1677   "")
1678
1679 (define_insn ""
1680   [(set (match_operand:DF 0 "general_operand" "=y,x")
1681         (float:DF (match_operand:SI 1 "general_operand" "rmi,x")))]
1682   "TARGET_FPA"
1683   "fpltod %1,%0")
1684
1685 (define_insn ""
1686   [(set (match_operand:DF 0 "general_operand" "=f")
1687         (float:DF (match_operand:SI 1 "general_operand" "dmi")))]
1688   "TARGET_68881"
1689   "f%&move%.l %1,%0")
1690
1691 (define_insn "floathisf2"
1692   [(set (match_operand:SF 0 "general_operand" "=f")
1693         (float:SF (match_operand:HI 1 "general_operand" "dmn")))]
1694   "TARGET_68881"
1695   "f%$move%.w %1,%0")
1696
1697 (define_insn "floathidf2"
1698   [(set (match_operand:DF 0 "general_operand" "=f")
1699         (float:DF (match_operand:HI 1 "general_operand" "dmn")))]
1700   "TARGET_68881"
1701   "fmove%.w %1,%0")
1702
1703 (define_insn "floatqisf2"
1704   [(set (match_operand:SF 0 "general_operand" "=f")
1705         (float:SF (match_operand:QI 1 "general_operand" "dmn")))]
1706   "TARGET_68881"
1707   "fmove%.b %1,%0")
1708
1709 (define_insn "floatqidf2"
1710   [(set (match_operand:DF 0 "general_operand" "=f")
1711         (float:DF (match_operand:QI 1 "general_operand" "dmn")))]
1712   "TARGET_68881"
1713   "f%&move%.b %1,%0")
1714
1715 ;; New routines to convert floating-point values to integers
1716 ;; to be used on the '040.  These should be faster than trapping
1717 ;; into the kernel to emulate fintrz.  They should also be faster
1718 ;; than calling the subroutines fixsfsi or fixdfsi.
1719
1720 (define_insn "fix_truncdfsi2"
1721   [(set (match_operand:SI 0 "general_operand" "=dm")
1722         (fix:SI (fix:DF (match_operand:DF 1 "register_operand" "f"))))
1723    (clobber (match_scratch:SI 2 "=d"))
1724    (clobber (match_scratch:SI 3 "=d"))]
1725   "TARGET_68881 && TARGET_68040"
1726   "*
1727 {
1728   CC_STATUS_INIT;
1729   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,%!\";
1730 }")
1731
1732 (define_insn "fix_truncdfhi2"
1733   [(set (match_operand:HI 0 "general_operand" "=dm")
1734         (fix:HI (fix:DF (match_operand:DF 1 "register_operand" "f"))))
1735    (clobber (match_scratch:SI 2 "=d"))
1736    (clobber (match_scratch:SI 3 "=d"))]
1737   "TARGET_68881 && TARGET_68040"
1738   "*
1739 {
1740   CC_STATUS_INIT;
1741   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,%!\";
1742 }")
1743
1744 (define_insn "fix_truncdfqi2"
1745   [(set (match_operand:QI 0 "general_operand" "=dm")
1746         (fix:QI (fix:DF (match_operand:DF 1 "register_operand" "f"))))
1747    (clobber (match_scratch:SI 2 "=d"))
1748    (clobber (match_scratch:SI 3 "=d"))]
1749   "TARGET_68881 && TARGET_68040"
1750   "*
1751 {
1752   CC_STATUS_INIT;
1753   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,%!\";
1754 }")
1755
1756 ;; Convert a float to a float whose value is an integer.
1757 ;; This is the first stage of converting it to an integer type.
1758
1759 (define_insn "ftruncdf2"
1760   [(set (match_operand:DF 0 "general_operand" "=f")
1761         (fix:DF (match_operand:DF 1 "general_operand" "fFm")))]
1762   "TARGET_68881 && !TARGET_68040"
1763   "*
1764 {
1765   if (FP_REG_P (operands[1]))
1766     return \"fintrz%.x %f1,%0\";
1767   return \"fintrz%.d %f1,%0\";
1768 }")
1769
1770 (define_insn "ftruncsf2"
1771   [(set (match_operand:SF 0 "general_operand" "=f")
1772         (fix:SF (match_operand:SF 1 "general_operand" "dfFm")))]
1773   "TARGET_68881 && !TARGET_68040"
1774   "*
1775 {
1776   if (FP_REG_P (operands[1]))
1777     return \"fintrz%.x %f1,%0\";
1778   return \"fintrz%.s %f1,%0\";
1779 }")
1780
1781 ;; Convert a float whose value is an integer
1782 ;; to an actual integer.  Second stage of converting float to integer type.
1783 (define_insn "fixsfqi2"
1784   [(set (match_operand:QI 0 "general_operand" "=dm")
1785         (fix:QI (match_operand:SF 1 "general_operand" "f")))]
1786   "TARGET_68881"
1787   "fmove%.b %1,%0")
1788
1789 (define_insn "fixsfhi2"
1790   [(set (match_operand:HI 0 "general_operand" "=dm")
1791         (fix:HI (match_operand:SF 1 "general_operand" "f")))]
1792   "TARGET_68881"
1793   "fmove%.w %1,%0")
1794
1795 (define_insn "fixsfsi2"
1796   [(set (match_operand:SI 0 "general_operand" "=dm")
1797         (fix:SI (match_operand:SF 1 "general_operand" "f")))]
1798   "TARGET_68881"
1799   "fmove%.l %1,%0")
1800
1801 (define_insn "fixdfqi2"
1802   [(set (match_operand:QI 0 "general_operand" "=dm")
1803         (fix:QI (match_operand:DF 1 "general_operand" "f")))]
1804   "TARGET_68881"
1805   "fmove%.b %1,%0")
1806
1807 (define_insn "fixdfhi2"
1808   [(set (match_operand:HI 0 "general_operand" "=dm")
1809         (fix:HI (match_operand:DF 1 "general_operand" "f")))]
1810   "TARGET_68881"
1811   "fmove%.w %1,%0")
1812
1813 (define_insn "fixdfsi2"
1814   [(set (match_operand:SI 0 "general_operand" "=dm")
1815         (fix:SI (match_operand:DF 1 "general_operand" "f")))]
1816   "TARGET_68881"
1817   "fmove%.l %1,%0")
1818
1819 ;; Convert a float to an integer.
1820 ;; On the Sun FPA, this is done in one step.
1821
1822 (define_insn ""
1823   [(set (match_operand:SI 0 "general_operand" "=x,y")
1824         (fix:SI (fix:SF (match_operand:SF 1 "general_operand" "xH,rmF"))))]
1825   "TARGET_FPA"
1826   "fpstol %w1,%0")
1827
1828 (define_insn ""
1829   [(set (match_operand:SI 0 "general_operand" "=x,y")
1830         (fix:SI (fix:DF (match_operand:DF 1 "general_operand" "xH,rmF"))))]
1831   "TARGET_FPA"
1832   "fpdtol %y1,%0")
1833 \f
1834 ;; add instructions
1835
1836 ;; Note that the middle two alternatives are near-duplicates
1837 ;; in order to handle insns generated by reload.
1838 ;; This is needed since they are not themselves reloaded,
1839 ;; so commutativity won't apply to them.
1840 (define_insn "addsi3"
1841   [(set (match_operand:SI 0 "general_operand" "=m,?a,?a,r")
1842         (plus:SI (match_operand:SI 1 "general_operand" "%0,a,rJK,0")
1843                  (match_operand:SI 2 "general_operand" "dIKLs,rJK,a,mrIKLs")))]
1844   ""
1845   "*
1846 {
1847   if (! operands_match_p (operands[0], operands[1]))
1848     {
1849       if (!ADDRESS_REG_P (operands[1]))
1850         {
1851           rtx tmp = operands[1];
1852
1853           operands[1] = operands[2];
1854           operands[2] = tmp;
1855         }
1856
1857       /* These insns can result from reloads to access
1858          stack slots over 64k from the frame pointer.  */
1859       if (GET_CODE (operands[2]) == CONST_INT
1860           && INTVAL (operands[2]) + 0x8000 >= (unsigned) 0x10000)
1861         return \"move%.l %2,%0\;add%.l %1,%0\";
1862 #ifdef SGS
1863       if (GET_CODE (operands[2]) == REG)
1864         return \"lea 0(%1,%2.l),%0\";
1865       else
1866         return \"lea %c2(%1),%0\";
1867 #else /* not SGS */
1868 #ifdef MOTOROLA
1869       if (GET_CODE (operands[2]) == REG)
1870         return \"lea (%1,%2.l),%0\";
1871       else
1872         return \"lea (%c2,%1),%0\";
1873 #else /* not MOTOROLA (MIT syntax) */
1874       if (GET_CODE (operands[2]) == REG)
1875         return \"lea %1@(0,%2:l),%0\";
1876       else
1877         return \"lea %1@(%c2),%0\";
1878 #endif /* not MOTOROLA */
1879 #endif /* not SGS */
1880     }
1881   if (GET_CODE (operands[2]) == CONST_INT)
1882     {
1883 #ifndef NO_ADDSUB_Q
1884       if (INTVAL (operands[2]) > 0
1885           && INTVAL (operands[2]) <= 8)
1886         return (ADDRESS_REG_P (operands[0])
1887                 ? \"addq%.w %2,%0\"
1888                 : \"addq%.l %2,%0\");
1889       if (INTVAL (operands[2]) < 0
1890           && INTVAL (operands[2]) >= -8)
1891         {
1892           operands[2] = gen_rtx (CONST_INT, VOIDmode,
1893                                  - INTVAL (operands[2]));
1894           return (ADDRESS_REG_P (operands[0])
1895                   ? \"subq%.w %2,%0\"
1896                   : \"subq%.l %2,%0\");
1897         }
1898       /* On everything except the 68000 it is faster to use two
1899          addqw instructions to add a small integer (8 < N <= 16)
1900          to an address register.  Likewise for subqw.*/
1901       if (INTVAL (operands[2]) > 8
1902           && INTVAL (operands[2]) <= 16
1903           && ADDRESS_REG_P (operands[0])
1904           && TARGET_68020) 
1905         {
1906           operands[2] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[2]) - 8);
1907           return \"addq%.w %#8,%0\;addq%.w %2,%0\";
1908         }
1909       if (INTVAL (operands[2]) < -8
1910           && INTVAL (operands[2]) >= -16
1911           && ADDRESS_REG_P (operands[0])
1912           && TARGET_68020) 
1913         {
1914           operands[2] = gen_rtx (CONST_INT, VOIDmode, 
1915                                   - INTVAL (operands[2]) - 8);
1916           return \"subq%.w %#8,%0\;subq%.w %2,%0\";
1917         }
1918 #endif
1919       if (ADDRESS_REG_P (operands[0])
1920           && INTVAL (operands[2]) >= -0x8000
1921           && INTVAL (operands[2]) < 0x8000)
1922         return \"add%.w %2,%0\";
1923     }
1924   return \"add%.l %2,%0\";
1925 }")
1926
1927 (define_insn ""
1928   [(set (match_operand:SI 0 "general_operand" "=a")
1929         (plus:SI (match_operand:SI 1 "general_operand" "0")
1930                  (sign_extend:SI
1931                   (match_operand:HI 2 "nonimmediate_operand" "rm"))))]
1932   ""
1933   "add%.w %2,%0")
1934
1935 (define_insn "addhi3"
1936   [(set (match_operand:HI 0 "general_operand" "=m,r")
1937         (plus:HI (match_operand:HI 1 "general_operand" "%0,0")
1938                  (match_operand:HI 2 "general_operand" "dn,rmn")))]
1939   ""
1940   "*
1941 {
1942 #ifndef NO_ADDSUB_Q
1943   if (GET_CODE (operands[2]) == CONST_INT)
1944     {
1945       /* If the constant would be a negative number when interpreted as
1946          HImode, make it negative.  This is usually, but not always, done
1947          elsewhere in the compiler.  First check for constants out of range,
1948          which could confuse us.  */
1949
1950       if (INTVAL (operands[2]) >= 32768)
1951         operands[2] = gen_rtx (CONST_INT, VOIDmode,
1952                                INTVAL (operands[2]) - 65536);
1953
1954       if (INTVAL (operands[2]) > 0
1955           && INTVAL (operands[2]) <= 8)
1956         return \"addq%.w %2,%0\";
1957       if (INTVAL (operands[2]) < 0
1958           && INTVAL (operands[2]) >= -8)
1959         {
1960           operands[2] = gen_rtx (CONST_INT, VOIDmode,
1961                                  - INTVAL (operands[2]));
1962           return \"subq%.w %2,%0\";
1963         }
1964       /* On everything except the 68000 it is faster to use two
1965          addqw instructions to add a small integer (8 < N <= 16)
1966          to an address register.  Likewise for subqw. */
1967       if (INTVAL (operands[2]) > 8
1968           && INTVAL (operands[2]) <= 16
1969           && ADDRESS_REG_P (operands[0])
1970           && TARGET_68020) 
1971         {
1972           operands[2] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[2]) - 8);
1973           return \"addq%.w %#8,%0\;addq%.w %2,%0\";
1974         }
1975       if (INTVAL (operands[2]) < -8
1976           && INTVAL (operands[2]) >= -16
1977           && ADDRESS_REG_P (operands[0])
1978           && TARGET_68020) 
1979         {
1980           operands[2] = gen_rtx (CONST_INT, VOIDmode, 
1981                                  - INTVAL (operands[2]) - 8);
1982           return \"subq%.w %#8,%0\;subq%.w %2,%0\";
1983         }
1984     }
1985 #endif
1986   return \"add%.w %2,%0\";
1987 }")
1988
1989 ;; These insns must use MATCH_DUP instead of the more expected
1990 ;; use of a matching constraint because the "output" here is also
1991 ;; an input, so you can't use the matching constraint.  That also means
1992 ;; that you can't use the "%", so you need patterns with the matched
1993 ;; operand in both positions.
1994
1995 (define_insn ""
1996   [(set (strict_low_part (match_operand:HI 0 "general_operand" "+m,d"))
1997         (plus:HI (match_dup 0)
1998                  (match_operand:HI 1 "general_operand" "dn,rmn")))]
1999   ""
2000   "*
2001 {
2002 #ifndef NO_ADDSUB_Q
2003   if (GET_CODE (operands[1]) == CONST_INT)
2004     {
2005       /* If the constant would be a negative number when interpreted as
2006          HImode, make it negative.  This is usually, but not always, done
2007          elsewhere in the compiler.  First check for constants out of range,
2008          which could confuse us.  */
2009
2010       if (INTVAL (operands[1]) >= 32768)
2011         operands[1] = gen_rtx (CONST_INT, VOIDmode,
2012                                INTVAL (operands[1]) - 65536);
2013
2014       if (INTVAL (operands[1]) > 0
2015           && INTVAL (operands[1]) <= 8)
2016         return \"addq%.w %1,%0\";
2017       if (INTVAL (operands[1]) < 0
2018           && INTVAL (operands[1]) >= -8)
2019         {
2020           operands[1] = gen_rtx (CONST_INT, VOIDmode,
2021                                  - INTVAL (operands[1]));
2022           return \"subq%.w %1,%0\";
2023         }
2024       /* On everything except the 68000 it is faster to use two
2025          addqw instructions to add a small integer (8 < N <= 16)
2026          to an address register.  Likewise for subqw. */
2027       if (INTVAL (operands[1]) > 8
2028           && INTVAL (operands[1]) <= 16
2029           && ADDRESS_REG_P (operands[0])
2030           && TARGET_68020) 
2031         {
2032           operands[1] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) - 8);
2033           return \"addq%.w %#8,%0\;addq%.w %1,%0\";
2034         }
2035       if (INTVAL (operands[1]) < -8
2036           && INTVAL (operands[1]) >= -16
2037           && ADDRESS_REG_P (operands[0])
2038           && TARGET_68020) 
2039         {
2040           operands[1] = gen_rtx (CONST_INT, VOIDmode, 
2041                                  - INTVAL (operands[1]) - 8);
2042           return \"subq%.w %#8,%0\;subq%.w %1,%0\";
2043         }
2044     }
2045 #endif
2046   return \"add%.w %1,%0\";
2047 }")
2048
2049 (define_insn ""
2050   [(set (strict_low_part (match_operand:HI 0 "general_operand" "+m,d"))
2051         (plus:HI (match_operand:HI 1 "general_operand" "dn,rmn")
2052                  (match_dup 0)))]
2053   ""
2054   "*
2055 {
2056 #ifndef NO_ADDSUB_Q
2057   if (GET_CODE (operands[1]) == CONST_INT)
2058     {
2059       /* If the constant would be a negative number when interpreted as
2060          HImode, make it negative.  This is usually, but not always, done
2061          elsewhere in the compiler.  First check for constants out of range,
2062          which could confuse us.  */
2063
2064       if (INTVAL (operands[1]) >= 32768)
2065         operands[1] = gen_rtx (CONST_INT, VOIDmode,
2066                                INTVAL (operands[1]) - 65536);
2067
2068       if (INTVAL (operands[1]) > 0
2069           && INTVAL (operands[1]) <= 8)
2070         return \"addq%.w %1,%0\";
2071       if (INTVAL (operands[1]) < 0
2072           && INTVAL (operands[1]) >= -8)
2073         {
2074           operands[1] = gen_rtx (CONST_INT, VOIDmode,
2075                                  - INTVAL (operands[1]));
2076           return \"subq%.w %1,%0\";
2077         }
2078       /* On everything except the 68000 it is faster to use two
2079          addqw instructions to add a small integer (8 < N <= 16)
2080          to an address register.  Likewise for subqw. */
2081       if (INTVAL (operands[1]) > 8
2082           && INTVAL (operands[1]) <= 16
2083           && ADDRESS_REG_P (operands[0])
2084           && TARGET_68020) 
2085         {
2086           operands[1] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) - 8);
2087           return \"addq%.w %#8,%0\;addq%.w %1,%0\";
2088         }
2089       if (INTVAL (operands[1]) < -8
2090           && INTVAL (operands[1]) >= -16
2091           && ADDRESS_REG_P (operands[0])
2092           && TARGET_68020) 
2093         {
2094           operands[1] = gen_rtx (CONST_INT, VOIDmode, 
2095                                  - INTVAL (operands[1]) - 8);
2096           return \"subq%.w %#8,%0\;subq%.w %1,%0\";
2097         }
2098     }
2099 #endif
2100   return \"add%.w %1,%0\";
2101 }")
2102
2103 (define_insn "addqi3"
2104   [(set (match_operand:QI 0 "general_operand" "=m,d")
2105         (plus:QI (match_operand:QI 1 "general_operand" "%0,0")
2106                  (match_operand:QI 2 "general_operand" "dn,dmn")))]
2107   ""
2108   "*
2109 {
2110 #ifndef NO_ADDSUB_Q
2111   if (GET_CODE (operands[2]) == CONST_INT)
2112     {
2113       if (INTVAL (operands[2]) >= 128)
2114         operands[2] = gen_rtx (CONST_INT, VOIDmode,
2115                                INTVAL (operands[2]) - 256);
2116
2117       if (INTVAL (operands[2]) > 0
2118           && INTVAL (operands[2]) <= 8)
2119         return \"addq%.b %2,%0\";
2120       if (INTVAL (operands[2]) < 0 && INTVAL (operands[2]) >= -8)
2121        {
2122          operands[2] = gen_rtx (CONST_INT, VOIDmode, - INTVAL (operands[2]));
2123          return \"subq%.b %2,%0\";
2124        }
2125     }
2126 #endif
2127   return \"add%.b %2,%0\";
2128 }")
2129
2130 (define_insn ""
2131   [(set (strict_low_part (match_operand:QI 0 "general_operand" "+m,d"))
2132         (plus:QI (match_dup 0)
2133                  (match_operand:QI 1 "general_operand" "dn,dmn")))]
2134   ""
2135   "*
2136 {
2137 #ifndef NO_ADDSUB_Q
2138   if (GET_CODE (operands[1]) == CONST_INT)
2139     {
2140       if (INTVAL (operands[1]) >= 128)
2141         operands[1] = gen_rtx (CONST_INT, VOIDmode,
2142                                INTVAL (operands[1]) - 256);
2143
2144       if (INTVAL (operands[1]) > 0
2145           && INTVAL (operands[1]) <= 8)
2146         return \"addq%.b %1,%0\";
2147       if (INTVAL (operands[1]) < 0 && INTVAL (operands[1]) >= -8)
2148        {
2149          operands[1] = gen_rtx (CONST_INT, VOIDmode, - INTVAL (operands[1]));
2150          return \"subq%.b %1,%0\";
2151        }
2152     }
2153 #endif
2154   return \"add%.b %1,%0\";
2155 }")
2156
2157 (define_insn ""
2158   [(set (strict_low_part (match_operand:QI 0 "general_operand" "+m,d"))
2159         (plus:QI (match_operand:QI 1 "general_operand" "dn,dmn")
2160                  (match_dup 0)))]
2161   ""
2162   "*
2163 {
2164 #ifndef NO_ADDSUB_Q
2165   if (GET_CODE (operands[1]) == CONST_INT)
2166     {
2167       if (INTVAL (operands[1]) >= 128)
2168         operands[1] = gen_rtx (CONST_INT, VOIDmode,
2169                                INTVAL (operands[1]) - 256);
2170
2171       if (INTVAL (operands[1]) > 0
2172           && INTVAL (operands[1]) <= 8)
2173         return \"addq%.b %1,%0\";
2174       if (INTVAL (operands[1]) < 0 && INTVAL (operands[1]) >= -8)
2175        {
2176          operands[1] = gen_rtx (CONST_INT, VOIDmode, - INTVAL (operands[1]));
2177          return \"subq%.b %1,%0\";
2178        }
2179     }
2180 #endif
2181   return \"add%.b %1,%0\";
2182 }")
2183
2184 (define_expand "adddf3"
2185   [(set (match_operand:DF 0 "general_operand" "")
2186         (plus:DF (match_operand:DF 1 "general_operand" "")
2187                  (match_operand:DF 2 "general_operand" "")))]
2188   "TARGET_68881 || TARGET_FPA"
2189   "")
2190
2191 (define_insn ""
2192   [(set (match_operand:DF 0 "general_operand" "=x,y")
2193         (plus:DF (match_operand:DF 1 "general_operand" "%xH,y")
2194                  (match_operand:DF 2 "general_operand" "xH,dmF")))]
2195   "TARGET_FPA"
2196   "*
2197 {
2198   if (rtx_equal_p (operands[0], operands[1]))
2199     return \"fpadd%.d %y2,%0\";
2200   if (rtx_equal_p (operands[0], operands[2]))
2201     return \"fpadd%.d %y1,%0\";
2202   if (which_alternative == 0)
2203     return \"fpadd3%.d %w2,%w1,%0\";
2204   return \"fpadd3%.d %x2,%x1,%0\";
2205 }")
2206
2207 (define_insn ""
2208   [(set (match_operand:DF 0 "general_operand" "=f")
2209         (plus:DF (match_operand:DF 1 "general_operand" "%0")
2210                  (match_operand:DF 2 "general_operand" "fmG")))]
2211   "TARGET_68881"
2212   "*
2213 {
2214   if (REG_P (operands[2]))
2215     return \"f%&add%.x %2,%0\";
2216   return \"f%&add%.d %f2,%0\";
2217 }")
2218
2219 (define_expand "addsf3"
2220   [(set (match_operand:SF 0 "general_operand" "")
2221         (plus:SF (match_operand:SF 1 "general_operand" "")
2222                  (match_operand:SF 2 "general_operand" "")))]
2223   "TARGET_68881 || TARGET_FPA"
2224   "")
2225
2226 (define_insn ""
2227   [(set (match_operand:SF 0 "general_operand" "=x,y")
2228         (plus:SF (match_operand:SF 1 "general_operand" "%xH,y")
2229                  (match_operand:SF 2 "general_operand" "xH,rmF")))]
2230   "TARGET_FPA"
2231   "*
2232 {
2233   if (rtx_equal_p (operands[0], operands[1]))
2234     return \"fpadd%.s %w2,%0\";
2235   if (rtx_equal_p (operands[0], operands[2]))
2236     return \"fpadd%.s %w1,%0\";
2237   if (which_alternative == 0)
2238     return \"fpadd3%.s %w2,%w1,%0\";
2239   return \"fpadd3%.s %2,%1,%0\";
2240 }")
2241
2242 (define_insn ""
2243   [(set (match_operand:SF 0 "general_operand" "=f")
2244         (plus:SF (match_operand:SF 1 "general_operand" "%0")
2245                  (match_operand:SF 2 "general_operand" "fdmF")))]
2246   "TARGET_68881"
2247   "*
2248 {
2249   if (REG_P (operands[2]) && ! DATA_REG_P (operands[2]))
2250     return \"f%$add%.x %2,%0\";
2251   return \"f%$add%.s %f2,%0\";
2252 }")
2253 \f
2254 ;; subtract instructions
2255
2256 (define_insn "subsi3"
2257   [(set (match_operand:SI 0 "general_operand" "=m,r")
2258         (minus:SI (match_operand:SI 1 "general_operand" "0,0")
2259                   (match_operand:SI 2 "general_operand" "ds,mrs")))]
2260   ""
2261   "sub%.l %2,%0")
2262
2263 (define_insn ""
2264   [(set (match_operand:SI 0 "general_operand" "=a")
2265         (minus:SI (match_operand:SI 1 "general_operand" "0")
2266                   (sign_extend:SI
2267                    (match_operand:HI 2 "nonimmediate_operand" "rm"))))]
2268   ""
2269   "sub%.w %2,%0")
2270
2271 (define_insn "subhi3"
2272   [(set (match_operand:HI 0 "general_operand" "=m,r")
2273         (minus:HI (match_operand:HI 1 "general_operand" "0,0")
2274                   (match_operand:HI 2 "general_operand" "dn,rmn")))]
2275   ""
2276   "sub%.w %2,%0")
2277
2278 (define_insn ""
2279   [(set (strict_low_part (match_operand:HI 0 "general_operand" "+m,d"))
2280         (minus:HI (match_dup 0)
2281                   (match_operand:HI 1 "general_operand" "dn,rmn")))]
2282   ""
2283   "sub%.w %1,%0")
2284
2285 (define_insn "subqi3"
2286   [(set (match_operand:QI 0 "general_operand" "=m,d")
2287         (minus:QI (match_operand:QI 1 "general_operand" "0,0")
2288                   (match_operand:QI 2 "general_operand" "dn,dmn")))]
2289   ""
2290   "sub%.b %2,%0")
2291
2292 (define_insn ""
2293   [(set (strict_low_part (match_operand:QI 0 "general_operand" "+m,d"))
2294         (minus:QI (match_dup 0)
2295                   (match_operand:QI 1 "general_operand" "dn,dmn")))]
2296   ""
2297   "sub%.b %1,%0")
2298
2299 (define_expand "subdf3"
2300   [(set (match_operand:DF 0 "general_operand" "")
2301         (minus:DF (match_operand:DF 1 "general_operand" "")
2302                   (match_operand:DF 2 "general_operand" "")))]
2303   "TARGET_68881 || TARGET_FPA"
2304   "")
2305
2306 (define_insn ""
2307   [(set (match_operand:DF 0 "general_operand" "=x,y,y")
2308         (minus:DF (match_operand:DF 1 "general_operand" "xH,y,dmF")
2309                   (match_operand:DF 2 "general_operand" "xH,dmF,0")))]
2310   "TARGET_FPA"
2311   "*
2312 {
2313   if (rtx_equal_p (operands[0], operands[2]))
2314     return \"fprsub%.d %y1,%0\";
2315   if (rtx_equal_p (operands[0], operands[1]))
2316     return \"fpsub%.d %y2,%0\";
2317   if (which_alternative == 0)
2318     return \"fpsub3%.d %w2,%w1,%0\";
2319   return \"fpsub3%.d %x2,%x1,%0\";
2320 }")
2321
2322 (define_insn ""
2323   [(set (match_operand:DF 0 "general_operand" "=f")
2324         (minus:DF (match_operand:DF 1 "general_operand" "0")
2325                   (match_operand:DF 2 "general_operand" "fmG")))]
2326   "TARGET_68881"
2327   "*
2328 {
2329   if (REG_P (operands[2]))
2330     return \"f%&sub%.x %2,%0\";
2331   return \"f%&sub%.d %f2,%0\";
2332 }")
2333
2334 (define_expand "subsf3"
2335   [(set (match_operand:SF 0 "general_operand" "")
2336         (minus:SF (match_operand:SF 1 "general_operand" "")
2337                   (match_operand:SF 2 "general_operand" "")))]
2338   "TARGET_68881 || TARGET_FPA"
2339   "")
2340
2341 (define_insn ""
2342   [(set (match_operand:SF 0 "general_operand" "=x,y,y")
2343         (minus:SF (match_operand:SF 1 "general_operand" "xH,y,rmF")
2344                   (match_operand:SF 2 "general_operand" "xH,rmF,0")))]
2345   "TARGET_FPA"
2346   "*
2347 {
2348   if (rtx_equal_p (operands[0], operands[2]))
2349     return \"fprsub%.s %w1,%0\";
2350   if (rtx_equal_p (operands[0], operands[1]))
2351     return \"fpsub%.s %w2,%0\";
2352   if (which_alternative == 0)
2353     return \"fpsub3%.s %w2,%w1,%0\";
2354   return \"fpsub3%.s %2,%1,%0\";
2355 }")
2356
2357 (define_insn ""
2358   [(set (match_operand:SF 0 "general_operand" "=f")
2359         (minus:SF (match_operand:SF 1 "general_operand" "0")
2360                   (match_operand:SF 2 "general_operand" "fdmF")))]
2361   "TARGET_68881"
2362   "*
2363 {
2364   if (REG_P (operands[2]) && ! DATA_REG_P (operands[2]))
2365     return \"f%$sub%.x %2,%0\";
2366   return \"f%$sub%.s %f2,%0\";
2367 }")
2368 \f
2369 ;; multiply instructions
2370
2371 (define_insn "mulhi3"
2372   [(set (match_operand:HI 0 "general_operand" "=d")
2373         (mult:HI (match_operand:HI 1 "general_operand" "%0")
2374                  (match_operand:HI 2 "general_operand" "dmn")))]
2375   ""
2376   "*
2377 {
2378 #if defined(MOTOROLA) && !defined(CRDS)
2379   return \"muls%.w %2,%0\";
2380 #else
2381   return \"muls %2,%0\";
2382 #endif
2383 }")
2384
2385 (define_insn "mulhisi3"
2386   [(set (match_operand:SI 0 "general_operand" "=d")
2387         (mult:SI (sign_extend:SI
2388                   (match_operand:HI 1 "nonimmediate_operand" "%0"))
2389                  (sign_extend:SI
2390                   (match_operand:HI 2 "nonimmediate_operand" "dm"))))]
2391   ""
2392   "*
2393 {
2394 #if defined(MOTOROLA) && !defined(CRDS)
2395   return \"muls%.w %2,%0\";
2396 #else
2397   return \"muls %2,%0\";
2398 #endif
2399 }")
2400
2401 (define_insn ""
2402   [(set (match_operand:SI 0 "general_operand" "=d")
2403         (mult:SI (sign_extend:SI
2404                   (match_operand:HI 1 "nonimmediate_operand" "%0"))
2405                  (match_operand:SI 2 "const_int_operand" "n")))]
2406   "INTVAL (operands[2]) >= -0x8000 && INTVAL (operands[2]) <= 0x7fff"
2407   "*
2408 {
2409 #if defined(MOTOROLA) && !defined(CRDS)
2410   return \"muls%.w %2,%0\";
2411 #else
2412   return \"muls %2,%0\";
2413 #endif
2414 }")
2415
2416 (define_insn "mulsi3"
2417   [(set (match_operand:SI 0 "general_operand" "=d")
2418         (mult:SI (match_operand:SI 1 "general_operand" "%0")
2419                  (match_operand:SI 2 "general_operand" "dmsK")))]
2420   "TARGET_68020"
2421   "muls%.l %2,%0")
2422
2423 (define_insn "umulhisi3"
2424   [(set (match_operand:SI 0 "general_operand" "=d")
2425         (mult:SI (zero_extend:SI
2426                   (match_operand:HI 1 "nonimmediate_operand" "%0"))
2427                  (zero_extend:SI
2428                   (match_operand:HI 2 "nonimmediate_operand" "dm"))))]
2429   ""
2430   "*
2431 {
2432 #if defined(MOTOROLA) && !defined(CRDS)
2433   return \"mulu%.w %2,%0\";
2434 #else
2435   return \"mulu %2,%0\";
2436 #endif
2437 }")
2438
2439 (define_insn ""
2440   [(set (match_operand:SI 0 "general_operand" "=d")
2441         (mult:SI (zero_extend:SI
2442                   (match_operand:HI 1 "nonimmediate_operand" "%0"))
2443                  (match_operand:SI 2 "const_int_operand" "n")))]
2444   "INTVAL (operands[2]) >= 0 && INTVAL (operands[2]) <= 0xffff"
2445   "*
2446 {
2447 #if defined(MOTOROLA) && !defined(CRDS)
2448   return \"mulu%.w %2,%0\";
2449 #else
2450   return \"mulu %2,%0\";
2451 #endif
2452 }")
2453
2454 ;; We need a separate DEFINE_EXPAND for u?mulsidi3 to be able to use the
2455 ;; proper matching constraint.  This is because the matching is between
2456 ;; the high-numbered word of the DImode operand[0] and operand[1].
2457 (define_expand "umulsidi3"
2458   [(parallel
2459     [(set (subreg:SI (match_operand:DI 0 "register_operand" "") 1)
2460           (mult:SI (match_operand:SI 1 "register_operand" "")
2461                    (match_operand:SI 2 "nonimmediate_operand" "")))
2462      (set (subreg:SI (match_dup 0) 0)
2463           (truncate:SI (lshiftrt:DI (mult:DI (zero_extend:DI (match_dup 1))
2464                                              (zero_extend:DI (match_dup 2)))
2465                                     (const_int 32))))])]
2466   "TARGET_68020"
2467   "")
2468
2469 (define_insn ""
2470   [(set (match_operand:SI 0 "register_operand" "=d")
2471         (mult:SI (match_operand:SI 1 "register_operand" "%0")
2472                   (match_operand:SI 2 "nonimmediate_operand" "dm")))
2473    (set (match_operand:SI 3 "register_operand" "=d")
2474         (truncate:SI (lshiftrt:DI (mult:DI (zero_extend:DI (match_dup 1))
2475                                            (zero_extend:DI (match_dup 2)))
2476                                   (const_int 32))))]
2477   "TARGET_68020"
2478   "mulu%.l %2,%3:%0")
2479
2480 ; Match immediate case.  For 2.4 only match things < 2^31.
2481 ; It's tricky with larger values in these patterns since we need to match
2482 ; values between the two parallel multiplies, between a CONST_DOUBLE and
2483 ; a CONST_INT.
2484 (define_insn ""
2485   [(set (match_operand:SI 0 "register_operand" "=d")
2486         (mult:SI (match_operand:SI 1 "register_operand" "%0")
2487                  (match_operand:SI 2 "const_int_operand" "n")))
2488    (set (match_operand:SI 3 "register_operand" "=d")
2489         (truncate:SI (lshiftrt:DI (mult:DI (zero_extend:DI (match_dup 1))
2490                                            (match_dup 2))
2491                                   (const_int 32))))]
2492   "TARGET_68020
2493    && (unsigned) INTVAL (operands[2]) <= 0x7fffffff"
2494   "mulu%.l %2,%3:%0")
2495
2496 (define_expand "mulsidi3"
2497   [(parallel
2498     [(set (subreg:SI (match_operand:DI 0 "register_operand" "") 1)
2499           (mult:SI (match_operand:SI 1 "register_operand" "")
2500                    (match_operand:SI 2 "nonimmediate_operand" "")))
2501      (set (subreg:SI (match_dup 0) 0)
2502           (truncate:SI (lshiftrt:DI (mult:DI (sign_extend:DI (match_dup 1))
2503                                              (sign_extend:DI (match_dup 2)))
2504                                     (const_int 32))))])]
2505   "TARGET_68020"
2506   "")
2507
2508 (define_insn ""
2509   [(set (match_operand:SI 0 "register_operand" "=d")
2510         (mult:SI (match_operand:SI 1 "register_operand" "%0")
2511                  (match_operand:SI 2 "nonimmediate_operand" "dm")))
2512    (set (match_operand:SI 3 "register_operand" "=d")
2513         (truncate:SI (lshiftrt:DI (mult:DI (sign_extend:DI (match_dup 1))
2514                                            (sign_extend:DI (match_dup 2)))
2515                                   (const_int 32))))]
2516   "TARGET_68020"
2517   "muls%.l %2,%3:%0")
2518
2519 (define_insn ""
2520   [(set (match_operand:SI 0 "register_operand" "=d")
2521         (mult:SI (match_operand:SI 1 "register_operand" "%0")
2522                  (match_operand:SI 2 "const_int_operand" "n")))
2523    (set (match_operand:SI 3 "register_operand" "=d")
2524         (truncate:SI (lshiftrt:DI (mult:DI (sign_extend:DI (match_dup 1))
2525                                            (match_dup 2))
2526                                   (const_int 32))))]
2527   "TARGET_68020
2528    /* This test is a noop on 32 bit machines,
2529       but important for a cross-compiler hosted on 64-bit machines.  */
2530    && INTVAL (operands[2]) <= 0x7fffffff
2531    && INTVAL (operands[2]) >= -0x80000000"
2532   "muls%.l %2,%3:%0")
2533
2534 (define_expand "muldf3"
2535   [(set (match_operand:DF 0 "general_operand" "")
2536         (mult:DF (match_operand:DF 1 "general_operand" "")
2537                  (match_operand:DF 2 "general_operand" "")))]
2538   "TARGET_68881 || TARGET_FPA"
2539   "")
2540
2541 (define_insn ""
2542   [(set (match_operand:DF 0 "general_operand" "=x,y")
2543         (mult:DF (match_operand:DF 1 "general_operand" "%xH,y")
2544                  (match_operand:DF 2 "general_operand" "xH,rmF")))]
2545   "TARGET_FPA"
2546   "*
2547 {
2548   if (rtx_equal_p (operands[1], operands[2]))
2549     return \"fpsqr%.d %y1,%0\";
2550   if (rtx_equal_p (operands[0], operands[1]))
2551     return \"fpmul%.d %y2,%0\";
2552   if (rtx_equal_p (operands[0], operands[2]))
2553     return \"fpmul%.d %y1,%0\";
2554   if (which_alternative == 0)
2555     return \"fpmul3%.d %w2,%w1,%0\";
2556   return \"fpmul3%.d %x2,%x1,%0\";
2557 }")
2558
2559 (define_insn ""
2560   [(set (match_operand:DF 0 "general_operand" "=f")
2561         (mult:DF (match_operand:DF 1 "general_operand" "%0")
2562                  (match_operand:DF 2 "general_operand" "fmG")))]
2563   "TARGET_68881"
2564   "*
2565 {
2566   if (GET_CODE (operands[2]) == CONST_DOUBLE
2567       && floating_exact_log2 (operands[2]) && !TARGET_68040)
2568     {
2569       int i = floating_exact_log2 (operands[2]);
2570       operands[2] = gen_rtx (CONST_INT, VOIDmode, i);
2571       return \"fscale%.l %2,%0\";
2572     }
2573   if (REG_P (operands[2]))
2574     return \"f%&mul%.x %2,%0\";
2575   return \"f%&mul%.d %f2,%0\";
2576 }")
2577
2578 (define_expand "mulsf3"
2579   [(set (match_operand:SF 0 "general_operand" "")
2580         (mult:SF (match_operand:SF 1 "general_operand" "")
2581                  (match_operand:SF 2 "general_operand" "")))]
2582   "TARGET_68881 || TARGET_FPA"
2583   "")
2584
2585 (define_insn ""
2586   [(set (match_operand:SF 0 "general_operand" "=x,y")
2587         (mult:SF (match_operand:SF 1 "general_operand" "%xH,y")
2588                  (match_operand:SF 2 "general_operand" "xH,rmF")))]
2589   "TARGET_FPA"
2590   "*
2591 {
2592   if (rtx_equal_p (operands[1], operands[2]))
2593     return \"fpsqr%.s %w1,%0\";
2594   if (rtx_equal_p (operands[0], operands[1]))
2595     return \"fpmul%.s %w2,%0\";
2596   if (rtx_equal_p (operands[0], operands[2]))
2597     return \"fpmul%.s %w1,%0\";
2598   if (which_alternative == 0)
2599     return \"fpmul3%.s %w2,%w1,%0\";
2600   return \"fpmul3%.s %2,%1,%0\";
2601 }")
2602
2603 (define_insn ""
2604   [(set (match_operand:SF 0 "general_operand" "=f")
2605         (mult:SF (match_operand:SF 1 "general_operand" "%0")
2606                  (match_operand:SF 2 "general_operand" "fdmF")))]
2607   "TARGET_68881"
2608   "*
2609 {
2610 #ifdef FSGLMUL_USE_S
2611   if (REG_P (operands[2]) && ! DATA_REG_P (operands[2]))
2612     return (TARGET_68040_ONLY
2613             ? \"fsmul%.s %2,%0\"
2614             : \"fsglmul%.s %2,%0\");
2615 #else
2616   if (REG_P (operands[2]) && ! DATA_REG_P (operands[2]))
2617     return (TARGET_68040_ONLY
2618             ? \"fsmul%.x %2,%0\"
2619             : \"fsglmul%.x %2,%0\");
2620 #endif
2621   return (TARGET_68040_ONLY
2622           ? \"fsmul%.s %f2,%0\"
2623           : \"fsglmul%.s %f2,%0\");
2624 }")
2625 \f
2626 ;; divide instructions
2627
2628 (define_insn "divhi3"
2629   [(set (match_operand:HI 0 "general_operand" "=d")
2630         (div:HI (match_operand:HI 1 "general_operand" "0")
2631                 (match_operand:HI 2 "general_operand" "dmn")))]
2632   ""
2633   "*
2634 {
2635 #ifdef MOTOROLA
2636   return \"ext%.l %0\;divs%.w %2,%0\";
2637 #else
2638   return \"extl %0\;divs %2,%0\";
2639 #endif
2640 }")
2641
2642 ;; These patterns don't work because the divs instruction is undefined if
2643 ;; the quotient is more than 16 bits.  This valid C would be miscompiled:
2644 ;; int n; short d; unsigned short q; ... q = (unsigned int) (n / d);
2645 ;; Imagine what happens when n = 100000 and d = 1.
2646 ;;(define_insn "divhisi3"
2647 ;;  [(set (match_operand:HI 0 "general_operand" "=d")
2648 ;;      (truncate:HI
2649 ;;       (div:SI
2650 ;;        (match_operand:SI 1 "general_operand" "0")
2651 ;;        (sign_extend:SI (match_operand:HI 2 "nonimmediate_operand" "dm")))))]
2652 ;;  ""
2653 ;;  "*
2654 ;;{
2655 ;;#ifdef MOTOROLA
2656 ;;  return \"divs%.w %2,%0\";
2657 ;;#else
2658 ;;  return \"divs %2,%0\";
2659 ;;#endif
2660 ;;}")
2661
2662 ;;(define_insn ""
2663 ;;  [(set (match_operand:HI 0 "general_operand" "=d")
2664 ;;      (truncate:HI (div:SI (match_operand:SI 1 "general_operand" "0")
2665 ;;                           (match_operand:SI 2 "const_int_operand" "n"))))]
2666 ;;  ""
2667 ;;  "*
2668 ;;{
2669 ;;#ifdef MOTOROLA
2670 ;;  return \"divs%.w %2,%0\";
2671 ;;#else
2672 ;;  return \"divs %2,%0\";
2673 ;;#endif
2674 ;;}")
2675
2676 (define_insn "udivhi3"
2677   [(set (match_operand:HI 0 "general_operand" "=d")
2678         (udiv:HI (match_operand:HI 1 "general_operand" "0")
2679                  (match_operand:HI 2 "general_operand" "dmn")))]
2680   ""
2681   "*
2682 {
2683 #ifdef MOTOROLA
2684   return \"and%.l %#0xFFFF,%0\;divu%.w %2,%0\";
2685 #else
2686   return \"andl %#0xFFFF,%0\;divu %2,%0\";
2687 #endif
2688 }")
2689
2690 ;; See comment before divhisi3 why these are commented out.
2691 ;;(define_insn "udivhisi3"
2692 ;;  [(set (match_operand:HI 0 "general_operand" "=d")
2693 ;;      (truncate:HI
2694 ;;       (udiv:SI
2695 ;;        (match_operand:SI 1 "general_operand" "0")
2696 ;;        (zero_extend:SI (match_operand:HI 2 "nonimmediate_operand" "dm")))))]
2697 ;;  ""
2698 ;;  "*
2699 ;;{
2700 ;;#ifdef MOTOROLA
2701 ;;  return \"divu%.w %2,%0\";
2702 ;;#else
2703 ;;  return \"divu %2,%0\";
2704 ;;#endif
2705 ;;}")
2706
2707 ;;(define_insn ""
2708 ;;  [(set (match_operand:HI 0 "general_operand" "=d")
2709 ;;      (truncate:HI (udiv:SI (match_operand:SI 1 "general_operand" "0")
2710 ;;                            (match_operand:SI 2 "const_int_operand" "n"))))]
2711 ;;  ""
2712 ;;  "*
2713 ;;{
2714 ;;#ifdef MOTOROLA
2715 ;;  return \"divu%.w %2,%0\";
2716 ;;#else
2717 ;;  return \"divu %2,%0\";
2718 ;;#endif
2719 ;;}")
2720
2721 (define_expand "divdf3"
2722   [(set (match_operand:DF 0 "general_operand" "")
2723         (div:DF (match_operand:DF 1 "general_operand" "")
2724                 (match_operand:DF 2 "general_operand" "")))]
2725   "TARGET_68881 || TARGET_FPA"
2726   "")
2727
2728 (define_insn ""
2729   [(set (match_operand:DF 0 "general_operand" "=x,y,y")
2730         (div:DF (match_operand:DF 1 "general_operand" "xH,y,rmF")
2731                 (match_operand:DF 2 "general_operand" "xH,rmF,0")))]
2732   "TARGET_FPA"
2733   "*
2734 {
2735   if (rtx_equal_p (operands[0], operands[2]))
2736     return \"fprdiv%.d %y1,%0\";
2737   if (rtx_equal_p (operands[0], operands[1]))
2738     return \"fpdiv%.d %y2,%0\";
2739   if (which_alternative == 0)
2740     return \"fpdiv3%.d %w2,%w1,%0\";
2741   return \"fpdiv3%.d %x2,%x1,%x0\";
2742 }")
2743
2744 (define_insn ""
2745   [(set (match_operand:DF 0 "general_operand" "=f")
2746         (div:DF (match_operand:DF 1 "general_operand" "0")
2747                 (match_operand:DF 2 "general_operand" "fmG")))]
2748   "TARGET_68881"
2749   "*
2750 {
2751   if (REG_P (operands[2]))
2752     return \"f%&div%.x %2,%0\";
2753   return \"f%&div%.d %f2,%0\";
2754 }")
2755
2756 (define_expand "divsf3"
2757   [(set (match_operand:SF 0 "general_operand" "")
2758         (div:SF (match_operand:SF 1 "general_operand" "")
2759                 (match_operand:SF 2 "general_operand" "")))]
2760   "TARGET_68881 || TARGET_FPA"
2761   "")
2762
2763 (define_insn ""
2764   [(set (match_operand:SF 0 "general_operand" "=x,y,y")
2765         (div:SF (match_operand:SF 1 "general_operand" "xH,y,rmF")
2766                 (match_operand:SF 2 "general_operand" "xH,rmF,0")))]
2767   "TARGET_FPA"
2768   "*
2769 {
2770   if (rtx_equal_p (operands[0], operands[1]))
2771     return \"fpdiv%.s %w2,%0\";
2772   if (rtx_equal_p (operands[0], operands[2]))
2773     return \"fprdiv%.s %w1,%0\";
2774   if (which_alternative == 0)
2775     return \"fpdiv3%.s %w2,%w1,%0\";
2776   return \"fpdiv3%.s %2,%1,%0\";
2777 }")
2778
2779 (define_insn ""
2780   [(set (match_operand:SF 0 "general_operand" "=f")
2781         (div:SF (match_operand:SF 1 "general_operand" "0")
2782                 (match_operand:SF 2 "general_operand" "fdmF")))]
2783   "TARGET_68881"
2784   "*
2785 {
2786 #ifdef FSGLDIV_USE_S
2787   if (REG_P (operands[2]) && ! DATA_REG_P (operands[2]))
2788     return (TARGET_68040_ONLY
2789             ? \"fsdiv%.s %2,%0\"
2790             : \"fsgldiv%.s %2,%0\");
2791 #else
2792   if (REG_P (operands[2]) && ! DATA_REG_P (operands[2]))
2793     return (TARGET_68040_ONLY
2794             ? \"fsdiv%.x %2,%0\"
2795             : \"fsgldiv%.x %2,%0\");
2796 #endif
2797   return (TARGET_68040_ONLY
2798           ? \"fsdiv%.s %f2,%0\"
2799           : \"fsgldiv%.s %f2,%0\");
2800 }")
2801 \f
2802 ;; Remainder instructions.
2803
2804 (define_insn "modhi3"
2805   [(set (match_operand:HI 0 "general_operand" "=d")
2806         (mod:HI (match_operand:HI 1 "general_operand" "0")
2807                 (match_operand:HI 2 "general_operand" "dmn")))]
2808   ""
2809   "*
2810 {
2811   /* The swap insn produces cc's that don't correspond to the result.  */
2812   CC_STATUS_INIT;
2813 #ifdef MOTOROLA
2814   return \"ext%.l %0\;divs%.w %2,%0\;swap %0\";
2815 #else
2816   return \"extl %0\;divs %2,%0\;swap %0\";
2817 #endif
2818 }")
2819
2820 ;; See comment before divhisi3 why these are commented out.
2821 ;;(define_insn "modhisi3"
2822 ;;  [(set (match_operand:HI 0 "general_operand" "=d")
2823 ;;      (truncate:HI
2824 ;;       (mod:SI
2825 ;;        (match_operand:SI 1 "general_operand" "0")
2826 ;;        (sign_extend:SI (match_operand:HI 2 "nonimmediate_operand" "dm")))))]
2827 ;;  ""
2828 ;;  "*
2829 ;;{
2830 ;;  /* The swap insn produces cc's that don't correspond to the result.  */
2831 ;;  CC_STATUS_INIT;
2832 ;;#ifdef MOTOROLA
2833 ;;  return \"divs%.w %2,%0\;swap %0\";
2834 ;;#else
2835 ;;  return \"divs %2,%0\;swap %0\";
2836 ;;#endif
2837 ;;}")
2838
2839 ;;(define_insn ""
2840 ;;  [(set (match_operand:HI 0 "general_operand" "=d")
2841 ;;      (truncate:HI (mod:SI (match_operand:SI 1 "general_operand" "0")
2842 ;;                           (match_operand:SI 2 "const_int_operand" "n"))))]
2843 ;;  ""
2844 ;;  "*
2845 ;;{
2846 ;;  /* The swap insn produces cc's that don't correspond to the result.  */
2847 ;;  CC_STATUS_INIT;
2848 ;;#ifdef MOTOROLA
2849 ;;  return \"divs%.w %2,%0\;swap %0\";
2850 ;;#else
2851 ;;  return \"divs %2,%0\;swap %0\";
2852 ;;#endif
2853 ;;}")
2854
2855 (define_insn "umodhi3"
2856   [(set (match_operand:HI 0 "general_operand" "=d")
2857         (umod:HI (match_operand:HI 1 "general_operand" "0")
2858                  (match_operand:HI 2 "general_operand" "dmn")))]
2859   ""
2860   "*
2861 {
2862   /* The swap insn produces cc's that don't correspond to the result.  */
2863   CC_STATUS_INIT;
2864 #ifdef MOTOROLA
2865   return \"and%.l %#0xFFFF,%0\;divu%.w %2,%0\;swap %0\";
2866 #else
2867   return \"andl %#0xFFFF,%0\;divu %2,%0\;swap %0\";
2868 #endif
2869 }")
2870
2871 ;; See comment before divhisi3 why these are commented out.
2872 ;;(define_insn "umodhisi3"
2873 ;;  [(set (match_operand:HI 0 "general_operand" "=d")
2874 ;;      (truncate:HI
2875 ;;       (umod:SI
2876 ;;        (match_operand:SI 1 "general_operand" "0")
2877 ;;        (zero_extend:SI (match_operand:HI 2 "nonimmediate_operand" "dm")))))]
2878 ;;  ""
2879 ;;  "*
2880 ;;{
2881 ;;  /* The swap insn produces cc's that don't correspond to the result.  */
2882 ;;  CC_STATUS_INIT;
2883 ;;#ifdef MOTOROLA
2884 ;;  return \"divu%.w %2,%0\;swap %0\";
2885 ;;#else
2886 ;;  return \"divu %2,%0\;swap %0\";
2887 ;;#endif
2888 ;;}")
2889
2890 ;;(define_insn ""
2891 ;;  [(set (match_operand:HI 0 "general_operand" "=d")
2892 ;;      (truncate:HI (umod:SI (match_operand:SI 1 "general_operand" "0")
2893 ;;                            (match_operand:SI 2 "const_int_operand" "n"))))]
2894 ;;  ""
2895 ;;  "*
2896 ;;{
2897 ;;  /* The swap insn produces cc's that don't correspond to the result.  */
2898 ;;  CC_STATUS_INIT;
2899 ;;#ifdef MOTOROLA
2900 ;;  return \"divu%.w %2,%0\;swap %0\";
2901 ;;#else
2902 ;;  return \"divu %2,%0\;swap %0\";
2903 ;;#endif
2904 ;;}")
2905
2906 (define_insn "divmodsi4"
2907   [(set (match_operand:SI 0 "general_operand" "=d")
2908         (div:SI (match_operand:SI 1 "general_operand" "0")
2909                 (match_operand:SI 2 "general_operand" "dmsK")))
2910    (set (match_operand:SI 3 "general_operand" "=d")
2911         (mod:SI (match_dup 1) (match_dup 2)))]
2912   "TARGET_68020"
2913   "*
2914 {
2915   if (find_reg_note (insn, REG_UNUSED, operands[3]))
2916     return \"divs%.l %2,%0\";
2917   else
2918     return \"divsl%.l %2,%3:%0\";
2919 }")
2920
2921 (define_insn "udivmodsi4"
2922   [(set (match_operand:SI 0 "general_operand" "=d")
2923         (udiv:SI (match_operand:SI 1 "general_operand" "0")
2924                  (match_operand:SI 2 "general_operand" "dmsK")))
2925    (set (match_operand:SI 3 "general_operand" "=d")
2926         (umod:SI (match_dup 1) (match_dup 2)))]
2927   "TARGET_68020"
2928   "*
2929 {
2930   if (find_reg_note (insn, REG_UNUSED, operands[3]))
2931     return \"divu%.l %2,%0\";
2932   else
2933     return \"divul%.l %2,%3:%0\";
2934 }")
2935 \f
2936 ;; logical-and instructions
2937
2938 ;; Prevent AND from being made with sp.  This doesn't exist in the machine
2939 ;; and reload will cause inefficient code.  Since sp is a FIXED_REG, we
2940 ;; can't allocate pseudos into it.
2941 (define_insn "andsi3"
2942   [(set (match_operand:SI 0 "not_sp_operand" "=m,d")
2943         (and:SI (match_operand:SI 1 "general_operand" "%0,0")
2944                 (match_operand:SI 2 "general_operand" "dKs,dmKs")))]
2945   ""
2946   "*
2947 {
2948   int logval;
2949   if (GET_CODE (operands[2]) == CONST_INT
2950       && (INTVAL (operands[2]) | 0xffff) == 0xffffffff
2951       && (DATA_REG_P (operands[0])
2952           || offsettable_memref_p (operands[0])))
2953     { 
2954       if (GET_CODE (operands[0]) != REG)
2955         operands[0] = adj_offsettable_operand (operands[0], 2);
2956       operands[2] = gen_rtx (CONST_INT, VOIDmode,
2957                              INTVAL (operands[2]) & 0xffff);
2958       /* Do not delete a following tstl %0 insn; that would be incorrect.  */
2959       CC_STATUS_INIT;
2960       if (operands[2] == const0_rtx)
2961         return \"clr%.w %0\";
2962       return \"and%.w %2,%0\";
2963     }
2964   if (GET_CODE (operands[2]) == CONST_INT
2965       && (logval = exact_log2 (~ INTVAL (operands[2]))) >= 0
2966       && (DATA_REG_P (operands[0])
2967           || offsettable_memref_p (operands[0])))
2968     { 
2969       if (DATA_REG_P (operands[0]))
2970         {
2971           operands[1] = gen_rtx (CONST_INT, VOIDmode, logval);
2972         }
2973       else
2974         {
2975           operands[0] = adj_offsettable_operand (operands[0], 3 - (logval / 8));
2976           operands[1] = gen_rtx (CONST_INT, VOIDmode, logval % 8);
2977         }
2978       /* This does not set condition codes in a standard way.  */
2979       CC_STATUS_INIT;
2980       return \"bclr %1,%0\";
2981     }
2982   return \"and%.l %2,%0\";
2983 }")
2984
2985 (define_insn "andhi3"
2986   [(set (match_operand:HI 0 "general_operand" "=m,d")
2987         (and:HI (match_operand:HI 1 "general_operand" "%0,0")
2988                 (match_operand:HI 2 "general_operand" "dn,dmn")))]
2989   ""
2990   "and%.w %2,%0")
2991
2992 (define_insn ""
2993   [(set (strict_low_part (match_operand:HI 0 "general_operand" "+m,d"))
2994         (and:HI (match_dup 0)
2995                 (match_operand:HI 1 "general_operand" "dn,dmn")))]
2996   ""
2997   "and%.w %1,%0")
2998
2999 (define_insn ""
3000   [(set (strict_low_part (match_operand:HI 0 "general_operand" "+m,d"))
3001         (and:HI (match_operand:HI 1 "general_operand" "dn,dmn")
3002                 (match_dup 0)))]
3003   ""
3004   "and%.w %1,%0")
3005
3006 (define_insn "andqi3"
3007   [(set (match_operand:QI 0 "general_operand" "=m,d")
3008         (and:QI (match_operand:QI 1 "general_operand" "%0,0")
3009                 (match_operand:QI 2 "general_operand" "dn,dmn")))]
3010   ""
3011   "and%.b %2,%0")
3012
3013 (define_insn ""
3014   [(set (strict_low_part (match_operand:QI 0 "general_operand" "+m,d"))
3015         (and:QI (match_dup 0)
3016                 (match_operand:QI 1 "general_operand" "dn,dmn")))]
3017   ""
3018   "and%.b %1,%0")
3019
3020 (define_insn ""
3021   [(set (strict_low_part (match_operand:QI 0 "general_operand" "+m,d"))
3022         (and:QI (match_operand:QI 1 "general_operand" "dn,dmn")
3023                 (match_dup 0)))]
3024   ""
3025   "and%.b %1,%0")
3026 \f
3027 ;; inclusive-or instructions
3028
3029 (define_insn "iorsi3"
3030   [(set (match_operand:SI 0 "general_operand" "=m,d")
3031         (ior:SI (match_operand:SI 1 "general_operand" "%0,0")
3032                 (match_operand:SI 2 "general_operand" "dKs,dmKs")))]
3033   ""
3034   "*
3035 {
3036   register int logval;
3037   if (GET_CODE (operands[2]) == CONST_INT
3038       && INTVAL (operands[2]) >> 16 == 0
3039       && (DATA_REG_P (operands[0])
3040           || offsettable_memref_p (operands[0])))
3041     { 
3042       if (GET_CODE (operands[0]) != REG)
3043         operands[0] = adj_offsettable_operand (operands[0], 2);
3044       /* Do not delete a following tstl %0 insn; that would be incorrect.  */
3045       CC_STATUS_INIT;
3046       return \"or%.w %2,%0\";
3047     }
3048   if (GET_CODE (operands[2]) == CONST_INT
3049       && (logval = exact_log2 (INTVAL (operands[2]))) >= 0
3050       && (DATA_REG_P (operands[0])
3051           || offsettable_memref_p (operands[0])))
3052     { 
3053       if (DATA_REG_P (operands[0]))
3054         {
3055           operands[1] = gen_rtx (CONST_INT, VOIDmode, logval);
3056         }
3057       else
3058         {
3059           operands[0] = adj_offsettable_operand (operands[0], 3 - (logval / 8));
3060           operands[1] = gen_rtx (CONST_INT, VOIDmode, logval % 8);
3061         }
3062       CC_STATUS_INIT;
3063       return \"bset %1,%0\";
3064     }
3065   return \"or%.l %2,%0\";
3066 }")
3067
3068 (define_insn "iorhi3"
3069   [(set (match_operand:HI 0 "general_operand" "=m,d")
3070         (ior:HI (match_operand:HI 1 "general_operand" "%0,0")
3071                 (match_operand:HI 2 "general_operand" "dn,dmn")))]
3072   ""
3073   "or%.w %2,%0")
3074
3075 (define_insn ""
3076   [(set (strict_low_part (match_operand:HI 0 "general_operand" "+m,d"))
3077         (ior:HI (match_dup 0)
3078                 (match_operand:HI 1 "general_operand" "dn,dmn")))]
3079   ""
3080   "or%.w %1,%0")
3081
3082 (define_insn ""
3083   [(set (strict_low_part (match_operand:HI 0 "general_operand" "+m,d"))
3084         (ior:HI (match_operand:HI 1 "general_operand" "dn,dmn")
3085                 (match_dup 0)))]
3086   ""
3087   "or%.w %1,%0")
3088
3089 (define_insn "iorqi3"
3090   [(set (match_operand:QI 0 "general_operand" "=m,d")
3091         (ior:QI (match_operand:QI 1 "general_operand" "%0,0")
3092                 (match_operand:QI 2 "general_operand" "dn,dmn")))]
3093   ""
3094   "or%.b %2,%0")
3095
3096 (define_insn ""
3097   [(set (strict_low_part (match_operand:QI 0 "general_operand" "+m,d"))
3098         (ior:QI (match_dup 0)
3099                 (match_operand:QI 1 "general_operand" "dn,dmn")))]
3100   ""
3101   "or%.b %1,%0")
3102
3103 (define_insn ""
3104   [(set (strict_low_part (match_operand:QI 0 "general_operand" "+m,d"))
3105         (ior:QI (match_operand:QI 1 "general_operand" "dn,dmn")
3106                 (match_dup 0)))]
3107   ""
3108   "or%.b %1,%0")
3109 \f
3110 ;; xor instructions
3111
3112 (define_insn "xorsi3"
3113   [(set (match_operand:SI 0 "general_operand" "=do,m")
3114         (xor:SI (match_operand:SI 1 "general_operand" "%0,0")
3115                 (match_operand:SI 2 "general_operand" "di,dKs")))]
3116   ""
3117   "*
3118 {
3119   if (GET_CODE (operands[2]) == CONST_INT
3120       && INTVAL (operands[2]) >> 16 == 0
3121       && (offsettable_memref_p (operands[0]) || DATA_REG_P (operands[0])))
3122     { 
3123       if (! DATA_REG_P (operands[0]))
3124         operands[0] = adj_offsettable_operand (operands[0], 2);
3125       /* Do not delete a following tstl %0 insn; that would be incorrect.  */
3126       CC_STATUS_INIT;
3127       return \"eor%.w %2,%0\";
3128     }
3129   return \"eor%.l %2,%0\";
3130 }")
3131
3132 (define_insn "xorhi3"
3133   [(set (match_operand:HI 0 "general_operand" "=dm")
3134         (xor:HI (match_operand:HI 1 "general_operand" "%0")
3135                 (match_operand:HI 2 "general_operand" "dn")))]
3136   ""
3137   "eor%.w %2,%0")
3138
3139 (define_insn ""
3140   [(set (strict_low_part (match_operand:HI 0 "general_operand" "+dm"))
3141         (xor:HI (match_dup 0)
3142                 (match_operand:HI 1 "general_operand" "dn")))]
3143   ""
3144   "eor%.w %1,%0")
3145
3146
3147 (define_insn ""
3148   [(set (strict_low_part (match_operand:HI 0 "general_operand" "+dm"))
3149         (xor:HI (match_operand:HI 1 "general_operand" "dn")
3150                 (match_dup 0)))]
3151   ""
3152   "eor%.w %1,%0")
3153
3154 (define_insn "xorqi3"
3155   [(set (match_operand:QI 0 "general_operand" "=dm")
3156         (xor:QI (match_operand:QI 1 "general_operand" "%0")
3157                 (match_operand:QI 2 "general_operand" "dn")))]
3158   ""
3159   "eor%.b %2,%0")
3160
3161 (define_insn ""
3162   [(set (strict_low_part (match_operand:QI 0 "general_operand" "+dm"))
3163         (xor:QI (match_dup 0)
3164                 (match_operand:QI 1 "general_operand" "dn")))]
3165   ""
3166   "eor%.b %1,%0")
3167
3168 (define_insn ""
3169   [(set (strict_low_part (match_operand:QI 0 "general_operand" "+dm"))
3170         (xor:QI (match_operand:QI 1 "general_operand" "dn")
3171                 (match_dup 0)))]
3172   ""
3173   "eor%.b %1,%0")
3174 \f
3175 ;; negation instructions
3176
3177 (define_insn "negsi2"
3178   [(set (match_operand:SI 0 "general_operand" "=dm")
3179         (neg:SI (match_operand:SI 1 "general_operand" "0")))]
3180   ""
3181   "neg%.l %0")
3182
3183 (define_insn "neghi2"
3184   [(set (match_operand:HI 0 "general_operand" "=dm")
3185         (neg:HI (match_operand:HI 1 "general_operand" "0")))]
3186   ""
3187   "neg%.w %0")
3188
3189 (define_insn ""
3190   [(set (strict_low_part (match_operand:HI 0 "general_operand" "+dm"))
3191         (neg:HI (match_dup 0)))]
3192   ""
3193   "neg%.w %0")
3194
3195 (define_insn "negqi2"
3196   [(set (match_operand:QI 0 "general_operand" "=dm")
3197         (neg:QI (match_operand:QI 1 "general_operand" "0")))]
3198   ""
3199   "neg%.b %0")
3200
3201 (define_insn ""
3202   [(set (strict_low_part (match_operand:QI 0 "general_operand" "+dm"))
3203         (neg:QI (match_dup 0)))]
3204   ""
3205   "neg%.b %0")
3206
3207 (define_expand "negsf2"
3208   [(set (match_operand:SF 0 "general_operand" "")
3209         (neg:SF (match_operand:SF 1 "general_operand" "")))]
3210   "TARGET_68881 || TARGET_FPA"
3211   "")
3212
3213 (define_insn ""
3214   [(set (match_operand:SF 0 "general_operand" "=x,y")
3215         (neg:SF (match_operand:SF 1 "general_operand" "xH,rmF")))]
3216   "TARGET_FPA"
3217   "fpneg%.s %w1,%0")
3218
3219 (define_insn ""
3220   [(set (match_operand:SF 0 "general_operand" "=f,d")
3221         (neg:SF (match_operand:SF 1 "general_operand" "fdmF,0")))]
3222   "TARGET_68881"
3223   "*
3224 {
3225   if (DATA_REG_P (operands[0]))
3226     {
3227       operands[1] = gen_rtx (CONST_INT, VOIDmode, 31);
3228       return \"bchg %1,%0\";
3229     }
3230   if (REG_P (operands[1]) && ! DATA_REG_P (operands[1]))
3231     return \"f%$neg%.x %1,%0\";
3232   return \"f%$neg%.s %f1,%0\";
3233 }")
3234
3235 (define_expand "negdf2"
3236   [(set (match_operand:DF 0 "general_operand" "")
3237         (neg:DF (match_operand:DF 1 "general_operand" "")))]
3238   "TARGET_68881 || TARGET_FPA"
3239   "")
3240
3241 (define_insn ""
3242   [(set (match_operand:DF 0 "general_operand" "=x,y")
3243         (neg:DF (match_operand:DF 1 "general_operand" "xH,rmF")))]
3244   "TARGET_FPA"
3245   "fpneg%.d %y1, %0")
3246
3247 (define_insn ""
3248   [(set (match_operand:DF 0 "general_operand" "=f,d")
3249         (neg:DF (match_operand:DF 1 "general_operand" "fmF,0")))]
3250   "TARGET_68881"
3251   "*
3252 {
3253   if (DATA_REG_P (operands[0]))
3254     {
3255       operands[1] = gen_rtx (CONST_INT, VOIDmode, 31);
3256       return \"bchg %1,%0\";
3257     }
3258   if (REG_P (operands[1]) && ! DATA_REG_P (operands[1]))
3259     return \"f%&neg%.x %1,%0\";
3260   return \"f%&neg%.d %f1,%0\";
3261 }")
3262 \f
3263 ;; Sqrt instruction for the 68881
3264
3265 (define_insn "sqrtdf2"
3266   [(set (match_operand:DF 0 "general_operand" "=f")
3267         (sqrt:DF (match_operand:DF 1 "general_operand" "fm")))]
3268   "TARGET_68881"
3269   "*
3270 {
3271   if (FP_REG_P (operands[1]))
3272     return \"fsqrt%.x %1,%0\";
3273   else
3274     return \"fsqrt%.d %1,%0\";
3275 }")
3276
3277 ;; Absolute value instructions
3278
3279 (define_expand "abssf2"
3280   [(set (match_operand:SF 0 "general_operand" "")
3281         (abs:SF (match_operand:SF 1 "general_operand" "")))]
3282   "TARGET_68881 || TARGET_FPA"
3283   "")
3284
3285 (define_insn ""
3286   [(set (match_operand:SF 0 "general_operand" "=x,y")
3287         (abs:SF (match_operand:SF 1 "general_operand" "xH,rmF")))]
3288   "TARGET_FPA"
3289   "fpabs%.s %y1,%0")
3290
3291 (define_insn ""
3292   [(set (match_operand:SF 0 "general_operand" "=f")
3293         (abs:SF (match_operand:SF 1 "general_operand" "fdmF")))]
3294   "TARGET_68881"
3295   "*
3296 {
3297   if (REG_P (operands[1]) && ! DATA_REG_P (operands[1]))
3298     return \"f%$abs%.x %1,%0\";
3299   return \"f%$abs%.s %f1,%0\";
3300 }")
3301
3302 (define_expand "absdf2"
3303   [(set (match_operand:DF 0 "general_operand" "")
3304         (abs:DF (match_operand:DF 1 "general_operand" "")))]
3305   "TARGET_68881 || TARGET_FPA"
3306   "")
3307
3308 (define_insn ""
3309   [(set (match_operand:DF 0 "general_operand" "=x,y")
3310         (abs:DF (match_operand:DF 1 "general_operand" "xH,rmF")))]
3311   "TARGET_FPA"
3312   "fpabs%.d %y1,%0")
3313
3314 (define_insn ""
3315   [(set (match_operand:DF 0 "general_operand" "=f")
3316         (abs:DF (match_operand:DF 1 "general_operand" "fmF")))]
3317   "TARGET_68881"
3318   "*
3319 {
3320   if (REG_P (operands[1]) && ! DATA_REG_P (operands[1]))
3321     return \"f%&abs%.x %1,%0\";
3322   return \"f%&abs%.d %f1,%0\";
3323 }")
3324 \f
3325 ;; one complement instructions
3326
3327 (define_insn "one_cmplsi2"
3328   [(set (match_operand:SI 0 "general_operand" "=dm")
3329         (not:SI (match_operand:SI 1 "general_operand" "0")))]
3330   ""
3331   "not%.l %0")
3332
3333 (define_insn "one_cmplhi2"
3334   [(set (match_operand:HI 0 "general_operand" "=dm")
3335         (not:HI (match_operand:HI 1 "general_operand" "0")))]
3336   ""
3337   "not%.w %0")
3338
3339 (define_insn ""
3340   [(set (strict_low_part (match_operand:HI 0 "general_operand" "+dm"))
3341         (not:HI (match_dup 0)))]
3342   ""
3343   "not%.w %0")
3344
3345 (define_insn "one_cmplqi2"
3346   [(set (match_operand:QI 0 "general_operand" "=dm")
3347         (not:QI (match_operand:QI 1 "general_operand" "0")))]
3348   ""
3349   "not%.b %0")
3350
3351 (define_insn ""
3352   [(set (strict_low_part (match_operand:QI 0 "general_operand" "+dm"))
3353         (not:QI (match_dup 0)))]
3354   ""
3355   "not%.b %0")
3356 \f
3357 ;; arithmetic shift instructions
3358 ;; We don't need the shift memory by 1 bit instruction
3359
3360 ;; On all 68k models, this makes faster code in a special case.
3361
3362 (define_insn ""
3363   [(set (match_operand:SI 0 "register_operand" "=d")
3364         (ashift:SI (match_operand:SI 1 "register_operand" "0")
3365                    (const_int 16)))]
3366   ""
3367   "*
3368 {
3369   CC_STATUS_INIT;
3370   return \"swap %0\;clr%.w %0\";
3371 }")
3372
3373 ;; On the 68000, this makes faster code in a special case.
3374
3375 (define_insn ""
3376   [(set (match_operand:SI 0 "register_operand" "=d")
3377         (ashift:SI (match_operand:SI 1 "register_operand" "0")
3378                    (match_operand:SI 2 "const_int_operand" "n")))]
3379   "(! TARGET_68020
3380     && INTVAL (operands[2]) > 16 && INTVAL (operands[2]) <= 24)"
3381   "*
3382 {
3383   CC_STATUS_INIT;
3384
3385   operands[2] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[2]) - 16);
3386   return \"asl%.w %2,%0\;swap %0\;clr%.w %0\";
3387 }")
3388
3389 (define_insn "ashlsi3"
3390   [(set (match_operand:SI 0 "register_operand" "=d")
3391         (ashift:SI (match_operand:SI 1 "register_operand" "0")
3392                    (match_operand:SI 2 "general_operand" "dI")))]
3393   ""
3394   "*
3395 {
3396   if (operands[2] == const1_rtx)
3397     return \"add%.l %0,%0\";
3398   return \"asl%.l %2,%0\";
3399 }")
3400
3401 (define_insn "ashlhi3"
3402   [(set (match_operand:HI 0 "register_operand" "=d")
3403         (ashift:HI (match_operand:HI 1 "register_operand" "0")
3404                    (match_operand:HI 2 "general_operand" "dI")))]
3405   ""
3406   "asl%.w %2,%0")
3407
3408 (define_insn ""
3409   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+d"))
3410         (ashift:HI (match_dup 0)
3411                    (match_operand:HI 1 "general_operand" "dI")))]
3412   ""
3413   "asl%.w %1,%0")
3414
3415 (define_insn "ashlqi3"
3416   [(set (match_operand:QI 0 "register_operand" "=d")
3417         (ashift:QI (match_operand:QI 1 "register_operand" "0")
3418                    (match_operand:QI 2 "general_operand" "dI")))]
3419   ""
3420   "asl%.b %2,%0")
3421
3422 (define_insn ""
3423   [(set (strict_low_part (match_operand:QI 0 "register_operand" "+d"))
3424         (ashift:QI (match_dup 0)
3425                    (match_operand:QI 1 "general_operand" "dI")))]
3426   ""
3427   "asl%.b %1,%0")
3428
3429 ;; On all 68k models, this makes faster code in a special case.
3430
3431 (define_insn ""
3432   [(set (match_operand:SI 0 "register_operand" "=d")
3433         (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
3434                      (const_int 16)))]
3435   ""
3436   "swap %0\;ext%.l %0")
3437
3438 ;; On the 68000, this makes faster code in a special case.
3439
3440 (define_insn ""
3441   [(set (match_operand:SI 0 "register_operand" "=d")
3442         (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
3443                      (match_operand:SI 2 "const_int_operand" "n")))]
3444   "(! TARGET_68020
3445     && INTVAL (operands[2]) > 16 && INTVAL (operands[2]) <= 24)"
3446   "*
3447 {
3448   operands[2] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[2]) - 16);
3449   return \"swap %0\;asr%.w %2,%0\;ext%.l %0\";
3450 }")
3451
3452 (define_insn ""
3453   [(set (match_operand:SI 0 "register_operand" "=d")
3454         (ashiftrt:SI (match_operand:SI 1 "register_operand" "d")
3455                      (match_operand:SI 2 "const_int_operand" "M")))]
3456   "TARGET_68020 && operands[0] != operands[1] && INTVAL (operands[2]) > 8"
3457   "*
3458 {
3459   operands[2] = GEN_INT (32 - INTVAL (operands[2]));
3460   return \"bfexts %1{%#0:%b2},%0\";
3461 }")
3462
3463 (define_insn "ashrsi3"
3464   [(set (match_operand:SI 0 "register_operand" "=d")
3465         (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
3466                      (match_operand:SI 2 "general_operand" "dI")))]
3467   ""
3468   "asr%.l %2,%0")
3469
3470 (define_insn "ashrhi3"
3471   [(set (match_operand:HI 0 "register_operand" "=d")
3472         (ashiftrt:HI (match_operand:HI 1 "register_operand" "0")
3473                      (match_operand:HI 2 "general_operand" "dI")))]
3474   ""
3475   "asr%.w %2,%0")
3476
3477 (define_insn ""
3478   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+d"))
3479         (ashiftrt:HI (match_dup 0)
3480                      (match_operand:HI 1 "general_operand" "dI")))]
3481   ""
3482   "asr%.w %1,%0")
3483
3484 (define_insn "ashrqi3"
3485   [(set (match_operand:QI 0 "register_operand" "=d")
3486         (ashiftrt:QI (match_operand:QI 1 "register_operand" "0")
3487                      (match_operand:QI 2 "general_operand" "dI")))]
3488   ""
3489   "asr%.b %2,%0")
3490
3491 (define_insn ""
3492   [(set (strict_low_part (match_operand:QI 0 "register_operand" "+d"))
3493         (ashiftrt:QI (match_dup 0)
3494                      (match_operand:QI 1 "general_operand" "dI")))]
3495   ""
3496   "asr%.b %1,%0")
3497 \f
3498 ;; logical shift instructions
3499
3500
3501 ;; On all 68k models, this makes faster code in a special case.
3502
3503 (define_insn ""
3504   [(set (match_operand:SI 0 "register_operand" "=d")
3505         (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
3506                      (const_int 16)))]
3507   ""
3508   "*
3509 {
3510   CC_STATUS_INIT;
3511   return \"clr%.w %0\;swap %0\";
3512 }")
3513
3514 ;; On the 68000, this makes faster code in a special case.
3515
3516 (define_insn ""
3517   [(set (match_operand:SI 0 "register_operand" "=d")
3518         (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
3519                      (match_operand:SI 2 "const_int_operand" "n")))]
3520   "(! TARGET_68020
3521     && INTVAL (operands[2]) > 16 && INTVAL (operands[2]) <= 24)"
3522   "*
3523 {
3524   /* I think lsr%.w sets the CC properly.  */
3525   operands[2] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[2]) - 16);
3526   return \"clr%.w %0\;swap %0\;lsr%.w %2,%0\";
3527 }")
3528
3529 (define_insn ""
3530   [(set (match_operand:SI 0 "register_operand" "=d")
3531         (lshiftrt:SI (match_operand:SI 1 "register_operand" "d")
3532                      (match_operand:SI 2 "const_int_operand" "M")))]
3533   "TARGET_68020 && operands[0] != operands[1] && INTVAL (operands[2]) > 8"
3534   "*
3535 {
3536   operands[2] = GEN_INT (32 - INTVAL (operands[2]));
3537   return \"bfextu %1{%#0:%b2},%0\";
3538 }")
3539
3540 (define_insn "lshrsi3"
3541   [(set (match_operand:SI 0 "register_operand" "=d")
3542         (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
3543                      (match_operand:SI 2 "general_operand" "dI")))]
3544   ""
3545   "lsr%.l %2,%0")
3546
3547 (define_insn "lshrhi3"
3548   [(set (match_operand:HI 0 "register_operand" "=d")
3549         (lshiftrt:HI (match_operand:HI 1 "register_operand" "0")
3550                      (match_operand:HI 2 "general_operand" "dI")))]
3551   ""
3552   "lsr%.w %2,%0")
3553
3554 (define_insn ""
3555   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+d"))
3556         (lshiftrt:HI (match_dup 0)
3557                      (match_operand:HI 1 "general_operand" "dI")))]
3558   ""
3559   "lsr%.w %1,%0")
3560
3561 (define_insn "lshrqi3"
3562   [(set (match_operand:QI 0 "register_operand" "=d")
3563         (lshiftrt:QI (match_operand:QI 1 "register_operand" "0")
3564                      (match_operand:QI 2 "general_operand" "dI")))]
3565   ""
3566   "lsr%.b %2,%0")
3567
3568 (define_insn ""
3569   [(set (strict_low_part (match_operand:QI 0 "register_operand" "+d"))
3570         (lshiftrt:QI (match_dup 0)
3571                      (match_operand:QI 1 "general_operand" "dI")))]
3572   ""
3573   "lsr%.b %1,%0")
3574 \f
3575 ;; rotate instructions
3576
3577 (define_insn "rotlsi3"
3578   [(set (match_operand:SI 0 "register_operand" "=d")
3579         (rotate:SI (match_operand:SI 1 "register_operand" "0")
3580                    (match_operand:SI 2 "general_operand" "dI")))]
3581   ""
3582   "rol%.l %2,%0")
3583
3584 (define_insn "rotlhi3"
3585   [(set (match_operand:HI 0 "register_operand" "=d")
3586         (rotate:HI (match_operand:HI 1 "register_operand" "0")
3587                    (match_operand:HI 2 "general_operand" "dI")))]
3588   ""
3589   "rol%.w %2,%0")
3590
3591
3592 (define_insn ""
3593   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+d"))
3594         (rotate:HI (match_dup 0)
3595                    (match_operand:HI 1 "general_operand" "dI")))]
3596   ""
3597   "rol%.w %1,%0")
3598
3599 (define_insn "rotlqi3"
3600   [(set (match_operand:QI 0 "register_operand" "=d")
3601         (rotate:QI (match_operand:QI 1 "register_operand" "0")
3602                    (match_operand:QI 2 "general_operand" "dI")))]
3603   ""
3604   "rol%.b %2,%0")
3605
3606 (define_insn ""
3607   [(set (strict_low_part (match_operand:QI 0 "register_operand" "+d"))
3608         (rotate:QI (match_dup 0)
3609                    (match_operand:QI 1 "general_operand" "dI")))]
3610   ""
3611   "rol%.b %1,%0")
3612
3613 (define_insn "rotrsi3"
3614   [(set (match_operand:SI 0 "register_operand" "=d")
3615         (rotatert:SI (match_operand:SI 1 "register_operand" "0")
3616                      (match_operand:SI 2 "general_operand" "dI")))]
3617   ""
3618   "ror%.l %2,%0")
3619
3620 (define_insn "rotrhi3"
3621   [(set (match_operand:HI 0 "register_operand" "=d")
3622         (rotatert:HI (match_operand:HI 1 "register_operand" "0")
3623                      (match_operand:HI 2 "general_operand" "dI")))]
3624   ""
3625   "ror%.w %2,%0")
3626
3627 (define_insn ""
3628   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+d"))
3629         (rotatert:HI (match_dup 0)
3630                      (match_operand:HI 1 "general_operand" "dI")))]
3631   ""
3632   "ror%.w %1,%0")
3633
3634 (define_insn "rotrqi3"
3635   [(set (match_operand:QI 0 "register_operand" "=d")
3636         (rotatert:QI (match_operand:QI 1 "register_operand" "0")
3637                      (match_operand:QI 2 "general_operand" "dI")))]
3638   ""
3639   "ror%.b %2,%0")
3640
3641 (define_insn ""
3642   [(set (strict_low_part (match_operand:QI 0 "register_operand" "+d"))
3643         (rotatert:QI (match_dup 0)
3644                      (match_operand:QI 1 "general_operand" "dI")))]
3645   ""
3646   "ror%.b %1,%0")
3647 \f
3648 ;; Special cases of bit-field insns which we should
3649 ;; recognize in preference to the general case.
3650 ;; These handle aligned 8-bit and 16-bit fields,
3651 ;; which can usually be done with move instructions.
3652
3653 ;
3654 ; Special case for 32-bit field in memory.  This only occurs when 32-bit
3655 ; alignment of structure members is specified.
3656 ;
3657 ; The move is allowed to be odd byte aligned, because that's still faster
3658 ; than an odd byte aligned bit field instruction.
3659 ;
3660 (define_insn ""
3661   [(set (zero_extract:SI (match_operand:QI 0 "nonimmediate_operand" "+o")
3662                          (const_int 32)
3663                          (match_operand:SI 2 "const_int_operand" "n"))
3664         (match_operand:SI 3 "general_operand" "rmi"))]
3665   "TARGET_68020 && TARGET_BITFIELD
3666    && (INTVAL (operands[2]) % 8) == 0
3667    && ! mode_dependent_address_p (XEXP (operands[0], 0))"
3668   "*
3669 {
3670   operands[0]
3671     = adj_offsettable_operand (operands[0], INTVAL (operands[2]) / 8);
3672
3673   return \"move%.l %3,%0\";
3674 }")
3675
3676 (define_insn ""
3677   [(set (zero_extract:SI (match_operand:SI 0 "nonimmediate_operand" "+do")
3678                          (match_operand:SI 1 "const_int_operand" "n")
3679                          (match_operand:SI 2 "const_int_operand" "n"))
3680         (match_operand:SI 3 "register_operand" "d"))]
3681   "TARGET_68020 && TARGET_BITFIELD
3682    && (INTVAL (operands[1]) == 8 || INTVAL (operands[1]) == 16)
3683    && INTVAL (operands[2]) % INTVAL (operands[1]) == 0
3684    && (GET_CODE (operands[0]) == REG
3685        || ! mode_dependent_address_p (XEXP (operands[0], 0)))"
3686   "*
3687 {
3688   if (REG_P (operands[0]))
3689     {
3690       if (INTVAL (operands[1]) + INTVAL (operands[2]) != 32)
3691         return \"bfins %3,%0{%b2:%b1}\";
3692     }
3693   else
3694     operands[0]
3695       = adj_offsettable_operand (operands[0], INTVAL (operands[2]) / 8);
3696
3697   if (GET_CODE (operands[3]) == MEM)
3698     operands[3] = adj_offsettable_operand (operands[3],
3699                                            (32 - INTVAL (operands[1])) / 8);
3700   if (INTVAL (operands[1]) == 8)
3701     return \"move%.b %3,%0\";
3702   return \"move%.w %3,%0\";
3703 }")
3704
3705
3706 ;
3707 ; Special case for 32-bit field in memory.  This only occurs when 32-bit
3708 ; alignment of structure members is specified.
3709 ;
3710 ; The move is allowed to be odd byte aligned, because that's still faster
3711 ; than an odd byte aligned bit field instruction.
3712 ;
3713 (define_insn ""
3714   [(set (match_operand:SI 0 "general_operand" "=rm")
3715         (zero_extract:SI (match_operand:QI 1 "nonimmediate_operand" "o")
3716                          (const_int 32)
3717                          (match_operand:SI 3 "const_int_operand" "n")))]
3718   "TARGET_68020 && TARGET_BITFIELD
3719    && (INTVAL (operands[3]) % 8) == 0
3720    && ! mode_dependent_address_p (XEXP (operands[1], 0))"
3721   "*
3722 {
3723   operands[1]
3724     = adj_offsettable_operand (operands[1], INTVAL (operands[3]) / 8);
3725
3726   return \"move%.l %1,%0\";
3727 }")
3728
3729 (define_insn ""
3730   [(set (match_operand:SI 0 "general_operand" "=&d")
3731         (zero_extract:SI (match_operand:SI 1 "nonimmediate_operand" "do")
3732                          (match_operand:SI 2 "const_int_operand" "n")
3733                          (match_operand:SI 3 "const_int_operand" "n")))]
3734   "TARGET_68020 && TARGET_BITFIELD
3735    && INTVAL (operands[3]) % INTVAL (operands[2]) == 0
3736    && (GET_CODE (operands[1]) == REG
3737        || ! mode_dependent_address_p (XEXP (operands[1], 0)))"
3738   "*
3739 {
3740   cc_status.flags |= CC_NOT_NEGATIVE;
3741   if (REG_P (operands[1]))
3742     {
3743       if (INTVAL (operands[2]) + INTVAL (operands[3]) != 32)
3744         return \"bfextu %1{%b3:%b2},%0\";
3745     }
3746   else
3747     operands[1]
3748       = adj_offsettable_operand (operands[1], INTVAL (operands[3]) / 8);
3749
3750   output_asm_insn (\"clr%.l %0\", operands);
3751   if (GET_CODE (operands[0]) == MEM)
3752     operands[0] = adj_offsettable_operand (operands[0],
3753                                            (32 - INTVAL (operands[1])) / 8);
3754   if (INTVAL (operands[2]) == 8)
3755     return \"move%.b %1,%0\";
3756   return \"move%.w %1,%0\";
3757 }")
3758
3759 ;
3760 ; Special case for 32-bit field in memory.  This only occurs when 32-bit
3761 ; alignment of structure members is specified.
3762 ;
3763 ; The move is allowed to be odd byte aligned, because that's still faster
3764 ; than an odd byte aligned bit field instruction.
3765 ;
3766 (define_insn ""
3767   [(set (match_operand:SI 0 "general_operand" "=rm")
3768         (sign_extract:SI (match_operand:QI 1 "nonimmediate_operand" "o")
3769                          (const_int 32)
3770                          (match_operand:SI 3 "const_int_operand" "n")))]
3771   "TARGET_68020 && TARGET_BITFIELD
3772    && (INTVAL (operands[3]) % 8) == 0
3773    && ! mode_dependent_address_p (XEXP (operands[1], 0))"
3774   "*
3775 {
3776   operands[1]
3777     = adj_offsettable_operand (operands[1], INTVAL (operands[3]) / 8);
3778
3779   return \"move%.l %1,%0\";
3780 }")
3781
3782 (define_insn ""
3783   [(set (match_operand:SI 0 "general_operand" "=d")
3784         (sign_extract:SI (match_operand:SI 1 "nonimmediate_operand" "do")
3785                          (match_operand:SI 2 "const_int_operand" "n")
3786                          (match_operand:SI 3 "const_int_operand" "n")))]
3787   "TARGET_68020 && TARGET_BITFIELD
3788    && INTVAL (operands[3]) % INTVAL (operands[2]) == 0
3789    && (GET_CODE (operands[1]) == REG
3790        || ! mode_dependent_address_p (XEXP (operands[1], 0)))"
3791   "*
3792 {
3793   if (REG_P (operands[1]))
3794     {
3795       if (INTVAL (operands[2]) + INTVAL (operands[3]) != 32)
3796         return \"bfexts %1{%b3:%b2},%0\";
3797     }
3798   else
3799     operands[1]
3800       = adj_offsettable_operand (operands[1], INTVAL (operands[3]) / 8);
3801
3802   if (INTVAL (operands[2]) == 8)
3803     return \"move%.b %1,%0\;extb%.l %0\";
3804   return \"move%.w %1,%0\;ext%.l %0\";
3805 }")
3806 \f
3807 ;; Bit field instructions, general cases.
3808 ;; "o,d" constraint causes a nonoffsettable memref to match the "o"
3809 ;; so that its address is reloaded.
3810
3811 (define_insn "extv"
3812   [(set (match_operand:SI 0 "general_operand" "=d,d")
3813         (sign_extract:SI (match_operand:QI 1 "nonimmediate_operand" "o,d")
3814                          (match_operand:SI 2 "general_operand" "di,di")
3815                          (match_operand:SI 3 "general_operand" "di,di")))]
3816   "TARGET_68020 && TARGET_BITFIELD"
3817   "bfexts %1{%b3:%b2},%0")
3818
3819 (define_insn "extzv"
3820   [(set (match_operand:SI 0 "general_operand" "=d,d")
3821         (zero_extract:SI (match_operand:QI 1 "nonimmediate_operand" "o,d")
3822                          (match_operand:SI 2 "general_operand" "di,di")
3823                          (match_operand:SI 3 "general_operand" "di,di")))]
3824   "TARGET_68020 && TARGET_BITFIELD"
3825   "*
3826 {
3827   if (GET_CODE (operands[2]) == CONST_INT)
3828     {
3829       if (INTVAL (operands[2]) != 32)
3830         cc_status.flags |= CC_NOT_NEGATIVE;
3831     }
3832   else
3833     {
3834       CC_STATUS_INIT;
3835     }
3836   return \"bfextu %1{%b3:%b2},%0\";
3837 }")
3838
3839 (define_insn ""
3840   [(set (zero_extract:SI (match_operand:QI 0 "nonimmediate_operand" "+o,d")
3841                          (match_operand:SI 1 "general_operand" "di,di")
3842                          (match_operand:SI 2 "general_operand" "di,di"))
3843         (xor:SI (zero_extract:SI (match_dup 0) (match_dup 1) (match_dup 2))
3844                 (match_operand 3 "const_int_operand" "n,n")))]
3845   "TARGET_68020 && TARGET_BITFIELD
3846    && (INTVAL (operands[3]) == -1
3847        || (GET_CODE (operands[1]) == CONST_INT
3848            && (~ INTVAL (operands[3]) & ((1 << INTVAL (operands[1]))- 1)) == 0))"
3849   "*
3850 {
3851   CC_STATUS_INIT;
3852   return \"bfchg %0{%b2:%b1}\";
3853 }")
3854
3855 (define_insn ""
3856   [(set (zero_extract:SI (match_operand:QI 0 "nonimmediate_operand" "+o,d")
3857                          (match_operand:SI 1 "general_operand" "di,di")
3858                          (match_operand:SI 2 "general_operand" "di,di"))
3859         (const_int 0))]
3860   "TARGET_68020 && TARGET_BITFIELD"
3861   "*
3862 {
3863   CC_STATUS_INIT;
3864   return \"bfclr %0{%b2:%b1}\";
3865 }")
3866
3867 (define_insn ""
3868   [(set (zero_extract:SI (match_operand:QI 0 "nonimmediate_operand" "+o,d")
3869                          (match_operand:SI 1 "general_operand" "di,di")
3870                          (match_operand:SI 2 "general_operand" "di,di"))
3871         (const_int -1))]
3872   "TARGET_68020 && TARGET_BITFIELD"
3873   "*
3874 {
3875   CC_STATUS_INIT;
3876   return \"bfset %0{%b2:%b1}\";
3877 }")
3878
3879 (define_insn "insv"
3880   [(set (zero_extract:SI (match_operand:QI 0 "nonimmediate_operand" "+o,d")
3881                          (match_operand:SI 1 "general_operand" "di,di")
3882                          (match_operand:SI 2 "general_operand" "di,di"))
3883         (match_operand:SI 3 "register_operand" "d,d"))]
3884   "TARGET_68020 && TARGET_BITFIELD"
3885   "bfins %3,%0{%b2:%b1}")
3886
3887 ;; Now recognize bit field insns that operate on registers
3888 ;; (or at least were intended to do so).
3889
3890 (define_insn ""
3891   [(set (match_operand:SI 0 "general_operand" "=d")
3892         (sign_extract:SI (match_operand:SI 1 "nonimmediate_operand" "d")
3893                          (match_operand:SI 2 "general_operand" "di")
3894                          (match_operand:SI 3 "general_operand" "di")))]
3895   "TARGET_68020 && TARGET_BITFIELD"
3896   "bfexts %1{%b3:%b2},%0")
3897
3898 (define_insn ""
3899   [(set (match_operand:SI 0 "general_operand" "=d")
3900         (zero_extract:SI (match_operand:SI 1 "nonimmediate_operand" "d")
3901                          (match_operand:SI 2 "general_operand" "di")
3902                          (match_operand:SI 3 "general_operand" "di")))]
3903   "TARGET_68020 && TARGET_BITFIELD"
3904   "*
3905 {
3906   if (GET_CODE (operands[2]) == CONST_INT)
3907     {
3908       if (INTVAL (operands[2]) != 32)
3909         cc_status.flags |= CC_NOT_NEGATIVE;
3910     }
3911   else
3912     {
3913       CC_STATUS_INIT;
3914     }
3915   return \"bfextu %1{%b3:%b2},%0\";
3916 }")
3917
3918 (define_insn ""
3919   [(set (zero_extract:SI (match_operand:SI 0 "nonimmediate_operand" "+d")
3920                          (match_operand:SI 1 "general_operand" "di")
3921                          (match_operand:SI 2 "general_operand" "di"))
3922         (const_int 0))]
3923   "TARGET_68020 && TARGET_BITFIELD"
3924   "*
3925 {
3926   CC_STATUS_INIT;
3927   return \"bfclr %0{%b2:%b1}\";
3928 }")
3929
3930 (define_insn ""
3931   [(set (zero_extract:SI (match_operand:SI 0 "nonimmediate_operand" "+d")
3932                          (match_operand:SI 1 "general_operand" "di")
3933                          (match_operand:SI 2 "general_operand" "di"))
3934         (const_int -1))]
3935   "TARGET_68020 && TARGET_BITFIELD"
3936   "*
3937 {
3938   CC_STATUS_INIT;
3939   return \"bfset %0{%b2:%b1}\";
3940 }")
3941
3942 (define_insn ""
3943   [(set (zero_extract:SI (match_operand:SI 0 "nonimmediate_operand" "+d")
3944                          (match_operand:SI 1 "general_operand" "di")
3945                          (match_operand:SI 2 "general_operand" "di"))
3946         (match_operand:SI 3 "register_operand" "d"))]
3947   "TARGET_68020 && TARGET_BITFIELD"
3948   "*
3949 {
3950 #if 0
3951   /* These special cases are now recognized by a specific pattern.  */
3952   if (GET_CODE (operands[1]) == CONST_INT && GET_CODE (operands[2]) == CONST_INT
3953       && INTVAL (operands[1]) == 16 && INTVAL (operands[2]) == 16)
3954     return \"move%.w %3,%0\";
3955   if (GET_CODE (operands[1]) == CONST_INT && GET_CODE (operands[2]) == CONST_INT
3956       && INTVAL (operands[1]) == 24 && INTVAL (operands[2]) == 8)
3957     return \"move%.b %3,%0\";
3958 #endif
3959   return \"bfins %3,%0{%b2:%b1}\";
3960 }")
3961 \f
3962 ;; Special patterns for optimizing bit-field instructions.
3963
3964 (define_insn ""
3965   [(set (cc0)
3966         (zero_extract:SI (match_operand:QI 0 "memory_operand" "o")
3967                          (match_operand:SI 1 "const_int_operand" "n")
3968                          (match_operand:SI 2 "general_operand" "di")))]
3969   "TARGET_68020 && TARGET_BITFIELD"
3970   "*
3971 {
3972   if (operands[1] == const1_rtx
3973       && GET_CODE (operands[2]) == CONST_INT)
3974     {    
3975       int width = GET_CODE (operands[0]) == REG ? 31 : 7;
3976       return output_btst (operands,
3977                           gen_rtx (CONST_INT, VOIDmode,
3978                                    width - INTVAL (operands[2])),
3979                           operands[0],
3980                           insn, 1000);
3981       /* Pass 1000 as SIGNPOS argument so that btst will
3982          not think we are testing the sign bit for an `and'
3983          and assume that nonzero implies a negative result.  */
3984     }
3985   if (INTVAL (operands[1]) != 32)
3986     cc_status.flags = CC_NOT_NEGATIVE;
3987   return \"bftst %0{%b2:%b1}\";
3988 }")
3989
3990   
3991 ;;; now handle the register cases
3992 (define_insn ""
3993   [(set (cc0)
3994         (zero_extract:SI (match_operand:SI 0 "nonimmediate_operand" "d")
3995                          (match_operand:SI 1 "const_int_operand" "n")
3996                          (match_operand:SI 2 "general_operand" "di")))]
3997   "TARGET_68020 && TARGET_BITFIELD"
3998   "*
3999 {
4000   if (operands[1] == const1_rtx
4001       && GET_CODE (operands[2]) == CONST_INT)
4002     {    
4003       int width = GET_CODE (operands[0]) == REG ? 31 : 7;
4004       return output_btst (operands,
4005                           gen_rtx (CONST_INT, VOIDmode,
4006                                    width - INTVAL (operands[2])),
4007                           operands[0],
4008                           insn, 1000);
4009       /* Pass 1000 as SIGNPOS argument so that btst will
4010          not think we are testing the sign bit for an `and'
4011          and assume that nonzero implies a negative result.  */
4012     }
4013   if (INTVAL (operands[1]) != 32)
4014     cc_status.flags = CC_NOT_NEGATIVE;
4015   return \"bftst %0{%b2:%b1}\";
4016 }")
4017 \f
4018 (define_insn "seq"
4019   [(set (match_operand:QI 0 "general_operand" "=d")
4020         (eq:QI (cc0) (const_int 0)))]
4021   ""
4022   "*
4023   cc_status = cc_prev_status;
4024   OUTPUT_JUMP (\"seq %0\", \"fseq %0\", \"seq %0\");
4025 ")
4026
4027 (define_insn "sne"
4028   [(set (match_operand:QI 0 "general_operand" "=d")
4029         (ne:QI (cc0) (const_int 0)))]
4030   ""
4031   "*
4032   cc_status = cc_prev_status;
4033   OUTPUT_JUMP (\"sne %0\", \"fsne %0\", \"sne %0\");
4034 ")
4035
4036 (define_insn "sgt"
4037   [(set (match_operand:QI 0 "general_operand" "=d")
4038         (gt:QI (cc0) (const_int 0)))]
4039   ""
4040   "*
4041   cc_status = cc_prev_status;
4042   OUTPUT_JUMP (\"sgt %0\", \"fsgt %0\", 0);
4043 ")
4044
4045 (define_insn "sgtu"
4046   [(set (match_operand:QI 0 "general_operand" "=d")
4047         (gtu:QI (cc0) (const_int 0)))]
4048   ""
4049   "* cc_status = cc_prev_status;
4050      return \"shi %0\"; ")
4051
4052 (define_insn "slt"
4053   [(set (match_operand:QI 0 "general_operand" "=d")
4054         (lt:QI (cc0) (const_int 0)))]
4055   ""
4056   "* cc_status = cc_prev_status;
4057      OUTPUT_JUMP (\"slt %0\", \"fslt %0\", \"smi %0\"); ")
4058
4059 (define_insn "sltu"
4060   [(set (match_operand:QI 0 "general_operand" "=d")
4061         (ltu:QI (cc0) (const_int 0)))]
4062   ""
4063   "* cc_status = cc_prev_status;
4064      return \"scs %0\"; ")
4065
4066 (define_insn "sge"
4067   [(set (match_operand:QI 0 "general_operand" "=d")
4068         (ge:QI (cc0) (const_int 0)))]
4069   ""
4070   "* cc_status = cc_prev_status;
4071      OUTPUT_JUMP (\"sge %0\", \"fsge %0\", \"spl %0\"); ")
4072
4073 (define_insn "sgeu"
4074   [(set (match_operand:QI 0 "general_operand" "=d")
4075         (geu:QI (cc0) (const_int 0)))]
4076   ""
4077   "* cc_status = cc_prev_status;
4078      return \"scc %0\"; ")
4079
4080 (define_insn "sle"
4081   [(set (match_operand:QI 0 "general_operand" "=d")
4082         (le:QI (cc0) (const_int 0)))]
4083   ""
4084   "*
4085   cc_status = cc_prev_status;
4086   OUTPUT_JUMP (\"sle %0\", \"fsle %0\", 0);
4087 ")
4088
4089 (define_insn "sleu"
4090   [(set (match_operand:QI 0 "general_operand" "=d")
4091         (leu:QI (cc0) (const_int 0)))]
4092   ""
4093   "* cc_status = cc_prev_status;
4094      return \"sls %0\"; ")
4095 \f
4096 ;; Basic conditional jump instructions.
4097
4098 (define_insn "beq"
4099   [(set (pc)
4100         (if_then_else (eq (cc0)
4101                           (const_int 0))
4102                       (label_ref (match_operand 0 "" ""))
4103                       (pc)))]
4104   ""
4105   "*
4106 {
4107 #ifdef MOTOROLA
4108   OUTPUT_JUMP (\"jbeq %l0\", \"fbeq %l0\", \"jbeq %l0\");
4109 #else
4110   OUTPUT_JUMP (\"jeq %l0\", \"fjeq %l0\", \"jeq %l0\");
4111 #endif
4112 }")
4113
4114 (define_insn "bne"
4115   [(set (pc)
4116         (if_then_else (ne (cc0)
4117                           (const_int 0))
4118                       (label_ref (match_operand 0 "" ""))
4119                       (pc)))]
4120   ""
4121   "*
4122 {
4123 #ifdef MOTOROLA
4124   OUTPUT_JUMP (\"jbne %l0\", \"fbne %l0\", \"jbne %l0\");
4125 #else
4126   OUTPUT_JUMP (\"jne %l0\", \"fjne %l0\", \"jne %l0\");
4127 #endif
4128 }")
4129
4130 (define_insn "bgt"
4131   [(set (pc)
4132         (if_then_else (gt (cc0)
4133                           (const_int 0))
4134                       (label_ref (match_operand 0 "" ""))
4135                       (pc)))]
4136   ""
4137   "*
4138 #ifdef MOTOROLA
4139   OUTPUT_JUMP (\"jbgt %l0\", \"fbgt %l0\", 0);
4140 #else
4141   OUTPUT_JUMP (\"jgt %l0\", \"fjgt %l0\", 0);
4142 #endif
4143 ")
4144
4145 (define_insn "bgtu"
4146   [(set (pc)
4147         (if_then_else (gtu (cc0)
4148                            (const_int 0))
4149                       (label_ref (match_operand 0 "" ""))
4150                       (pc)))]
4151   ""
4152   "*
4153 #ifdef MOTOROLA
4154   return \"jbhi %l0\";
4155 #else
4156   return \"jhi %l0\";
4157 #endif
4158 ")
4159
4160 (define_insn "blt"
4161   [(set (pc)
4162         (if_then_else (lt (cc0)
4163                           (const_int 0))
4164                       (label_ref (match_operand 0 "" ""))
4165                       (pc)))]
4166   ""
4167   "*
4168 #ifdef MOTOROLA
4169   OUTPUT_JUMP (\"jblt %l0\", \"fblt %l0\", \"jbmi %l0\");
4170 #else
4171   OUTPUT_JUMP (\"jlt %l0\", \"fjlt %l0\", \"jmi %l0\");
4172 #endif
4173 ")
4174
4175 (define_insn "bltu"
4176   [(set (pc)
4177         (if_then_else (ltu (cc0)
4178                            (const_int 0))
4179                       (label_ref (match_operand 0 "" ""))
4180                       (pc)))]
4181   ""
4182   "*
4183 #ifdef MOTOROLA
4184   return \"jbcs %l0\";
4185 #else
4186   return \"jcs %l0\";
4187 #endif
4188 ")
4189
4190 (define_insn "bge"
4191   [(set (pc)
4192         (if_then_else (ge (cc0)
4193                           (const_int 0))
4194                       (label_ref (match_operand 0 "" ""))
4195                       (pc)))]
4196   ""
4197   "*
4198 #ifdef MOTOROLA
4199   OUTPUT_JUMP (\"jbge %l0\", \"fbge %l0\", \"jbpl %l0\");
4200 #else
4201   OUTPUT_JUMP (\"jge %l0\", \"fjge %l0\", \"jpl %l0\");
4202 #endif
4203 ")
4204
4205 (define_insn "bgeu"
4206   [(set (pc)
4207         (if_then_else (geu (cc0)
4208                            (const_int 0))
4209                       (label_ref (match_operand 0 "" ""))
4210                       (pc)))]
4211   ""
4212   "*
4213 #ifdef MOTOROLA
4214   return \"jbcc %l0\";
4215 #else
4216   return \"jcc %l0\";
4217 #endif
4218 ")
4219
4220 (define_insn "ble"
4221   [(set (pc)
4222         (if_then_else (le (cc0)
4223                           (const_int 0))
4224                       (label_ref (match_operand 0 "" ""))
4225                       (pc)))]
4226   ""
4227   "*
4228 #ifdef MOTOROLA
4229   OUTPUT_JUMP (\"jble %l0\", \"fble %l0\", 0);
4230 #else
4231   OUTPUT_JUMP (\"jle %l0\", \"fjle %l0\", 0);
4232 #endif
4233 ")
4234
4235 (define_insn "bleu"
4236   [(set (pc)
4237         (if_then_else (leu (cc0)
4238                            (const_int 0))
4239                       (label_ref (match_operand 0 "" ""))
4240                       (pc)))]
4241   ""
4242   "*
4243 #ifdef MOTOROLA
4244   return \"jbls %l0\";
4245 #else
4246   return \"jls %l0\";
4247 #endif
4248 ")
4249 \f
4250 ;; Negated conditional jump instructions.
4251
4252 (define_insn ""
4253   [(set (pc)
4254         (if_then_else (eq (cc0)
4255                           (const_int 0))
4256                       (pc)
4257                       (label_ref (match_operand 0 "" ""))))]
4258   ""
4259   "*
4260 {
4261 #ifdef MOTOROLA
4262   OUTPUT_JUMP (\"jbne %l0\", \"fbne %l0\", \"jbne %l0\");
4263 #else
4264   OUTPUT_JUMP (\"jne %l0\", \"fjne %l0\", \"jne %l0\");
4265 #endif
4266 }")
4267
4268 (define_insn ""
4269   [(set (pc)
4270         (if_then_else (ne (cc0)
4271                           (const_int 0))
4272                       (pc)
4273                       (label_ref (match_operand 0 "" ""))))]
4274   ""
4275   "*
4276 {
4277 #ifdef MOTOROLA
4278   OUTPUT_JUMP (\"jbeq %l0\", \"fbeq %l0\", \"jbeq %l0\");
4279 #else
4280   OUTPUT_JUMP (\"jeq %l0\", \"fjeq %l0\", \"jeq %l0\");
4281 #endif
4282 }")
4283
4284 (define_insn ""
4285   [(set (pc)
4286         (if_then_else (gt (cc0)
4287                           (const_int 0))
4288                       (pc)
4289                       (label_ref (match_operand 0 "" ""))))]
4290   ""
4291   "*
4292 #ifdef MOTOROLA
4293   OUTPUT_JUMP (\"jble %l0\", \"fbngt %l0\", 0);
4294 #else
4295   OUTPUT_JUMP (\"jle %l0\", \"fjngt %l0\", 0);
4296 #endif
4297 ")
4298
4299 (define_insn ""
4300   [(set (pc)
4301         (if_then_else (gtu (cc0)
4302                            (const_int 0))
4303                       (pc)
4304                       (label_ref (match_operand 0 "" ""))))]
4305   ""
4306   "*
4307 #ifdef MOTOROLA
4308   return \"jbls %l0\";
4309 #else
4310   return \"jls %l0\";
4311 #endif
4312 ")
4313
4314 (define_insn ""
4315   [(set (pc)
4316         (if_then_else (lt (cc0)
4317                           (const_int 0))
4318                       (pc)
4319                       (label_ref (match_operand 0 "" ""))))]
4320   ""
4321   "*
4322 #ifdef MOTOROLA
4323   OUTPUT_JUMP (\"jbge %l0\", \"fbnlt %l0\", \"jbpl %l0\");
4324 #else
4325   OUTPUT_JUMP (\"jge %l0\", \"fjnlt %l0\", \"jpl %l0\");
4326 #endif
4327 ")
4328
4329 (define_insn ""
4330   [(set (pc)
4331         (if_then_else (ltu (cc0)
4332                            (const_int 0))
4333                       (pc)
4334                       (label_ref (match_operand 0 "" ""))))]
4335   ""
4336   "*
4337 #ifdef MOTOROLA
4338   return \"jbcc %l0\";
4339 #else
4340   return \"jcc %l0\";
4341 #endif
4342 ")
4343
4344 (define_insn ""
4345   [(set (pc)
4346         (if_then_else (ge (cc0)
4347                           (const_int 0))
4348                       (pc)
4349                       (label_ref (match_operand 0 "" ""))))]
4350   ""
4351   "*
4352 #ifdef MOTOROLA
4353   OUTPUT_JUMP (\"jblt %l0\", \"fbnge %l0\", \"jbmi %l0\");
4354 #else
4355   OUTPUT_JUMP (\"jlt %l0\", \"fjnge %l0\", \"jmi %l0\");
4356 #endif
4357 ")
4358
4359 (define_insn ""
4360   [(set (pc)
4361         (if_then_else (geu (cc0)
4362                            (const_int 0))
4363                       (pc)
4364                       (label_ref (match_operand 0 "" ""))))]
4365   ""
4366   "*
4367 #ifdef MOTOROLA
4368   return \"jbcs %l0\";
4369 #else
4370   return \"jcs %l0\";
4371 #endif
4372 ")
4373
4374 (define_insn ""
4375   [(set (pc)
4376         (if_then_else (le (cc0)
4377                           (const_int 0))
4378                       (pc)
4379                       (label_ref (match_operand 0 "" ""))))]
4380   ""
4381   "*
4382 #ifdef MOTOROLA
4383   OUTPUT_JUMP (\"jbgt %l0\", \"fbnle %l0\", 0);
4384 #else
4385   OUTPUT_JUMP (\"jgt %l0\", \"fjnle %l0\", 0);
4386 #endif
4387 ")
4388
4389 (define_insn ""
4390   [(set (pc)
4391         (if_then_else (leu (cc0)
4392                            (const_int 0))
4393                       (pc)
4394                       (label_ref (match_operand 0 "" ""))))]
4395   ""
4396   "*
4397 #ifdef MOTOROLA
4398   return \"jbhi %l0\";
4399 #else
4400   return \"jhi %l0\";
4401 #endif
4402 ")
4403 \f
4404 ;; Unconditional and other jump instructions
4405 (define_insn "jump"
4406   [(set (pc)
4407         (label_ref (match_operand 0 "" "")))]
4408   ""
4409   "*
4410 #ifdef MOTOROLA
4411   return \"jbra %l0\";
4412 #else
4413   return \"jra %l0\";
4414 #endif
4415 ")
4416
4417 ;; We support two different ways of handling dispatch tables.
4418 ;; The NeXT uses absolute tables, and other machines use relative.
4419 ;; This define_expand can generate either kind.
4420 (define_expand "tablejump"
4421   [(parallel [(set (pc) (match_operand 0 "" ""))
4422               (use (label_ref (match_operand 1 "" "")))])]
4423   ""
4424   "
4425 {
4426 #ifdef CASE_VECTOR_PC_RELATIVE
4427     operands[0] = gen_rtx (PLUS, SImode, pc_rtx, operands[0]);
4428 #endif
4429 }")
4430
4431 ;; Jump to variable address from dispatch table of absolute addresses.
4432 (define_insn ""
4433   [(set (pc) (match_operand:SI 0 "register_operand" "a"))
4434    (use (label_ref (match_operand 1 "" "")))]
4435   ""
4436   "*
4437 #ifdef MOTOROLA
4438   return \"jmp (%0)\";
4439 #else
4440   return \"jmp %0@\";
4441 #endif
4442 ")
4443
4444 ;; Jump to variable address from dispatch table of relative addresses.
4445 (define_insn ""
4446   [(set (pc)
4447         (plus:SI (pc) (match_operand:HI 0 "register_operand" "r")))
4448    (use (label_ref (match_operand 1 "" "")))]
4449   ""
4450   "*
4451 #ifdef ASM_RETURN_CASE_JUMP
4452  ASM_RETURN_CASE_JUMP;
4453 #else
4454 #ifdef SGS
4455 #ifdef ASM_OUTPUT_CASE_LABEL
4456   return \"jmp 6(%%pc,%0.w)\";
4457 #else
4458 #ifdef CRDS
4459   return \"jmp 2(pc,%0.w)\";
4460 #else
4461   return \"jmp 2(%%pc,%0.w)\";
4462 #endif  /* end !CRDS */
4463 #endif
4464 #else /* not SGS */
4465 #ifdef MOTOROLA
4466   return \"jmp (2,pc,%0.w)\";
4467 #else
4468   return \"jmp pc@(2,%0:w)\";
4469 #endif
4470 #endif
4471 #endif
4472 ")
4473
4474 ;; Decrement-and-branch insns.
4475 (define_insn ""
4476   [(set (pc)
4477         (if_then_else
4478          (ne (match_operand:HI 0 "general_operand" "+g")
4479              (const_int 0))
4480          (label_ref (match_operand 1 "" ""))
4481          (pc)))
4482    (set (match_dup 0)
4483         (plus:HI (match_dup 0)
4484                  (const_int -1)))]
4485   ""
4486   "*
4487 {
4488   CC_STATUS_INIT;
4489   if (DATA_REG_P (operands[0]))
4490     return \"dbra %0,%l1\";
4491   if (GET_CODE (operands[0]) == MEM)
4492     {
4493 #ifdef MOTOROLA
4494 #ifdef NO_ADDSUB_Q
4495       return \"sub%.w %#1,%0\;jbcc %l1\";
4496 #else
4497       return \"subq%.w %#1,%0\;jbcc %l1\";
4498 #endif
4499 #else /* not MOTOROLA */
4500       return \"subqw %#1,%0\;jcc %l1\";
4501 #endif
4502     }
4503 #ifdef MOTOROLA
4504 #ifdef SGS_CMP_ORDER
4505 #ifdef NO_ADDSUB_Q
4506   return \"sub%.w %#1,%0\;cmp%.w %0,%#-1\;jbne %l1\";
4507 #else
4508   return \"subq%.w %#1,%0\;cmp%.w %0,%#-1\;jbne %l1\";
4509 #endif
4510 #else /* not SGS_CMP_ORDER */
4511   return \"subq%.w %#1,%0\;cmp%.w %#-1,%0\;jbne %l1\";
4512 #endif
4513 #else /* not MOTOROLA */
4514   return \"subqw %#1,%0\;cmpw %#-1,%0\;jne %l1\";
4515 #endif
4516 }")
4517
4518 (define_insn ""
4519   [(set (pc)
4520         (if_then_else
4521          (ne (match_operand:SI 0 "general_operand" "+g")
4522              (const_int 0))
4523          (label_ref (match_operand 1 "" ""))
4524          (pc)))
4525    (set (match_dup 0)
4526         (plus:SI (match_dup 0)
4527                  (const_int -1)))]
4528   ""
4529   "*
4530 {
4531   CC_STATUS_INIT;
4532 #ifdef MOTOROLA
4533 #ifdef NO_ADDSUB_Q
4534   if (DATA_REG_P (operands[0]))
4535     return \"dbra %0,%l1\;clr%.w %0\;sub%.l %#1,%0\;jbcc %l1\";
4536   if (GET_CODE (operands[0]) == MEM)
4537     return \"sub%.l %#1,%0\;jbcc %l1\";
4538 #else
4539   if (DATA_REG_P (operands[0]))
4540     return \"dbra %0,%l1\;clr%.w %0\;subq%.l %#1,%0\;jbcc %l1\";
4541   if (GET_CODE (operands[0]) == MEM)
4542     return \"subq%.l %#1,%0\;jbcc %l1\";
4543 #endif /* NO_ADDSUB_Q */
4544 #ifdef SGS_CMP_ORDER
4545 #ifdef NO_ADDSUB_Q
4546   return \"sub.l %#1,%0\;cmp.l %0,%#-1\;jbne %l1\";
4547 #else
4548   return \"subq.l %#1,%0\;cmp.l %0,%#-1\;jbne %l1\";
4549 #endif
4550 #else /* not SGS_CMP_ORDER */
4551   return \"subq.l %#1,%0\;cmp.l %#-1,%0\;jbne %l1\";
4552 #endif /* not SGS_CMP_ORDER */
4553 #else /* not MOTOROLA */
4554   if (DATA_REG_P (operands[0]))
4555     return \"dbra %0,%l1\;clr%.w %0\;subql %#1,%0\;jcc %l1\";
4556   if (GET_CODE (operands[0]) == MEM)
4557     return \"subql %#1,%0\;jcc %l1\";
4558   return \"subql %#1,%0\;cmpl %#-1,%0\;jne %l1\";
4559 #endif /* not MOTOROLA */
4560 }")
4561
4562 ;; Two dbra patterns that use REG_NOTES info generated by strength_reduce.
4563
4564 (define_insn ""
4565   [(set (pc)
4566         (if_then_else
4567           (ge (plus:HI (match_operand:HI 0 "general_operand" "+g")
4568                        (const_int -1))
4569               (const_int 0))
4570           (label_ref (match_operand 1 "" ""))
4571           (pc)))
4572    (set (match_dup 0)
4573         (plus:HI (match_dup 0)
4574                  (const_int -1)))]
4575   "find_reg_note (insn, REG_NONNEG, 0)"
4576   "*
4577 {
4578   CC_STATUS_INIT;
4579 #ifdef MOTOROLA
4580 #ifdef NO_ADDSUB_Q
4581   if (DATA_REG_P (operands[0]))
4582     return \"dbra %0,%l1\";
4583   if (GET_CODE (operands[0]) == MEM)
4584     return \"sub%.w %#1,%0\;jbcc %l1\";
4585 #else
4586   if (DATA_REG_P (operands[0]))
4587     return \"dbra %0,%l1\";
4588   if (GET_CODE (operands[0]) == MEM)
4589     return \"subq%.w %#1,%0\;jbcc %l1\";
4590 #endif
4591 #ifdef SGS_CMP_ORDER
4592 #ifdef NO_ADDSUB_Q
4593   return \"sub.w %#1,%0\;cmp.w %0,%#-1\;jbne %l1\";
4594 #else
4595   return \"subq.w %#1,%0\;cmp.w %0,%#-1\;jbne %l1\";
4596 #endif
4597 #else /* not SGS_CMP_ORDER */
4598   return \"subq.w %#1,%0\;cmp.w %#-1,%0\;jbne %l1\";
4599 #endif /* not SGS_CMP_ORDER */
4600 #else /* not MOTOROLA */
4601   if (DATA_REG_P (operands[0]))
4602     return \"dbra %0,%l1\";
4603   if (GET_CODE (operands[0]) == MEM)
4604     return \"subqw %#1,%0\;jcc %l1\";
4605   return \"subqw %#1,%0\;cmpw %#-1,%0\;jne %l1\";
4606 #endif /* not MOTOROLA */
4607 }")
4608
4609 (define_insn "decrement_and_branch_until_zero"
4610   [(set (pc)
4611         (if_then_else
4612           (ge (plus:SI (match_operand:SI 0 "general_operand" "+g")
4613                        (const_int -1))
4614               (const_int 0))
4615           (label_ref (match_operand 1 "" ""))
4616           (pc)))
4617    (set (match_dup 0)
4618         (plus:SI (match_dup 0)
4619                  (const_int -1)))]
4620   "find_reg_note (insn, REG_NONNEG, 0)"
4621   "*
4622 {
4623   CC_STATUS_INIT;
4624 #ifdef MOTOROLA
4625 #ifdef NO_ADDSUB_Q
4626   if (DATA_REG_P (operands[0]))
4627     return \"dbra %0,%l1\;clr%.w %0\;sub%.l %#1,%0\;jbcc %l1\";
4628   if (GET_CODE (operands[0]) == MEM)
4629     return \"sub%.l %#1,%0\;jbcc %l1\";
4630 #else
4631   if (DATA_REG_P (operands[0]))
4632     return \"dbra %0,%l1\;clr%.w %0\;subq%.l %#1,%0\;jbcc %l1\";
4633   if (GET_CODE (operands[0]) == MEM)
4634     return \"subq%.l %#1,%0\;jbcc %l1\";
4635 #endif
4636 #ifdef SGS_CMP_ORDER
4637 #ifdef NO_ADDSUB_Q
4638   return \"sub.l %#1,%0\;cmp.l %0,%#-1\;jbne %l1\";
4639 #else
4640   return \"subq.l %#1,%0\;cmp.l %0,%#-1\;jbne %l1\";
4641 #endif
4642 #else /* not SGS_CMP_ORDER */
4643   return \"subq.l %#1,%0\;cmp.l %#-1,%0\;jbne %l1\";
4644 #endif /* not SGS_CMP_ORDER */
4645 #else /* not MOTOROLA */
4646   if (DATA_REG_P (operands[0]))
4647     return \"dbra %0,%l1\;clr%.w %0\;subql %#1,%0\;jcc %l1\";
4648   if (GET_CODE (operands[0]) == MEM)
4649     return \"subql %#1,%0\;jcc %l1\";
4650   return \"subql %#1,%0\;cmpl %#-1,%0\;jne %l1\";
4651 #endif /* not MOTOROLA */
4652 }")
4653
4654
4655 ;; PIC calls are handled by loading the address of the function into a 
4656 ;; register (via movsi), then emitting a register indirect call using
4657 ;; the "jsr" function call syntax.
4658 ;;
4659 ;; It is important to note that the "jsr" syntax is always used for 
4660 ;; PIC calls, even on machines in which GCC normally uses the "jbsr"
4661 ;; syntax for non-PIC calls.  This keeps at least 1 assembler (Sun)
4662 ;; from emitting incorrect code for a PIC call.
4663 ;;
4664 ;; We have different patterns for PIC calls and non-PIC calls.  The
4665 ;; different patterns are only used to choose the right syntax
4666 ;; ("jsr" vs "jbsr").
4667 ;;
4668 ;; On svr4 m68k, PIC stuff is done differently. To be able to support
4669 ;; dynamic linker LAZY BINDING, all the procedure calls need to go 
4670 ;; through the PLT (Procedure Linkage Table) section in PIC mode. The 
4671 ;; svr4 m68k assembler recognizes this syntax: `bsr FUNC@PLTPC' and it 
4672 ;; will create the correct relocation entry (R_68K_PLT32) for `FUNC', 
4673 ;; that tells the linker editor to create an entry for `FUNC' in PLT
4674 ;; section at link time. However, all global objects reference are still
4675 ;; done by using `OBJ@GOT'. So, the goal here is to output the function 
4676 ;; call operand as `FUNC@PLTPC', but output object operand as `OBJ@GOT'. 
4677 ;; We need to have a way to differentiate these two different operands.
4678 ;;
4679 ;; The strategy I use here is to use SYMBOL_REF_FLAG to differentiate 
4680 ;; these two different operands. The macro LEGITIMATE_PIC_OPERAND_P needs
4681 ;; to be changed to recognize function calls symbol_ref operand as a legal 
4682 ;; PIC operand (by checking whether SYMBOL_REF_FLAG is set). This will 
4683 ;; avoid the compiler to load this symbol_ref operand into a register. 
4684 ;; Remember, the operand "foo@PLTPC" cannot be called via jsr directly 
4685 ;; since the value is a PC relative offset, not a real address.
4686 ;;
4687 ;; All global objects are treated in the similar way as in SUN3. The only 
4688 ;; difference is: on m68k svr4, the reference of such global object needs 
4689 ;; to end with a suffix "@GOT" so the assembler and linker know to create
4690 ;; an entry for it in GOT (Global Offset Table) section. This is done in 
4691 ;; m68k.c.
4692
4693 ;; Call subroutine with no return value.
4694 (define_expand "call"
4695   [(call (match_operand:QI 0 "memory_operand" "")
4696          (match_operand:SI 1 "general_operand" ""))]
4697   ;; Operand 1 not really used on the m68000.
4698
4699   ""
4700   "
4701 {
4702   if (flag_pic && GET_CODE (XEXP (operands[0], 0)) == SYMBOL_REF)
4703 #ifdef MOTOROLA
4704     SYMBOL_REF_FLAG (XEXP (operands[0], 0)) = 1;
4705 #else
4706     operands[0] = gen_rtx (MEM, GET_MODE (operands[0]),
4707                            force_reg (Pmode, XEXP (operands[0], 0)));
4708 #endif
4709 }")
4710
4711 ;; This is a normal call sequence.
4712 (define_insn ""
4713   [(call (match_operand:QI 0 "memory_operand" "o")
4714          (match_operand:SI 1 "general_operand" "g"))]
4715   ;; Operand 1 not really used on the m68000.
4716
4717   "! flag_pic"
4718   "*
4719 #ifdef MOTOROLA
4720 #ifdef MOTOROLA_BSR
4721   if (GET_CODE (operands[0]) == MEM 
4722       && GET_CODE (XEXP (operands[0], 0)) == SYMBOL_REF)
4723     return \"bsr %0\";
4724 #endif
4725   return \"jsr %0\";
4726 #else
4727   return \"jbsr %0\";
4728 #endif
4729 ")
4730
4731 ;; This is a PIC call sequence.
4732 (define_insn ""
4733   [(call (match_operand:QI 0 "memory_operand" "o")
4734          (match_operand:SI 1 "general_operand" "g"))]
4735   ;; Operand 1 not really used on the m68000.
4736
4737   "flag_pic"
4738   "*
4739 #ifdef MOTOROLA
4740   if (GET_CODE (operands[0]) == MEM 
4741       && GET_CODE (XEXP (operands[0], 0)) == SYMBOL_REF)
4742 #ifdef HPUX_ASM
4743     return \"bsr.l %0\";
4744 #else
4745     return \"bsr %0@PLTPC\";
4746 #endif
4747 #endif
4748   return \"jsr %0\";
4749 ")
4750
4751 ;; Call subroutine, returning value in operand 0
4752 ;; (which must be a hard register).
4753 ;; See comments before "call" regarding PIC calls.
4754 (define_expand "call_value"
4755   [(set (match_operand 0 "" "")
4756         (call (match_operand:QI 1 "memory_operand" "")
4757      (match_operand:SI 2 "general_operand" "")))]
4758   ;; Operand 2 not really used on the m68000.
4759   ""
4760   "
4761 {
4762   if (flag_pic && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF)
4763 #ifdef MOTOROLA
4764     SYMBOL_REF_FLAG (XEXP (operands[1], 0)) = 1;
4765 #else
4766     operands[1] = gen_rtx (MEM, GET_MODE (operands[1]),
4767                            force_reg (Pmode, XEXP (operands[1], 0)));
4768 #endif
4769 }")
4770
4771 ;; This is a normal call_value
4772 (define_insn ""
4773   [(set (match_operand 0 "" "=rf")
4774         (call (match_operand:QI 1 "memory_operand" "o")
4775               (match_operand:SI 2 "general_operand" "g")))]
4776   ;; Operand 2 not really used on the m68000.
4777   "! flag_pic"
4778   "*
4779 #ifdef MOTOROLA
4780 #ifdef MOTOROLA_BSR
4781   if (GET_CODE (operands[1]) == MEM 
4782       && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF)
4783     return \"bsr %1\";
4784 #endif
4785   return \"jsr %1\";
4786 #else
4787   return \"jbsr %1\";
4788 #endif
4789 ")
4790
4791 ;; This is a PIC call_value
4792 (define_insn ""
4793   [(set (match_operand 0 "" "=rf")
4794         (call (match_operand:QI 1 "memory_operand" "o")
4795               (match_operand:SI 2 "general_operand" "g")))]
4796   ;; Operand 2 not really used on the m68000.
4797   "flag_pic"
4798   "*
4799 #ifdef MOTOROLA
4800   if (GET_CODE (operands[1]) == MEM 
4801       && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF)
4802 #ifdef HPUX_ASM
4803     return \"bsr.l %1\";
4804 #else
4805     return \"bsr %1@PLTPC\";
4806 #endif
4807 #endif
4808   return \"jsr %1\";
4809 ")
4810
4811 ;; Call subroutine returning any type.
4812
4813 (define_expand "untyped_call"
4814   [(parallel [(call (match_operand 0 "" "")
4815                     (const_int 0))
4816               (match_operand 1 "" "")
4817               (match_operand 2 "" "")])]
4818   "NEEDS_UNTYPED_CALL"
4819   "
4820 {
4821   int i;
4822
4823   emit_call_insn (gen_call (operands[0], const0_rtx, NULL, const0_rtx));
4824
4825   for (i = 0; i < XVECLEN (operands[2], 0); i++)
4826     {
4827       rtx set = XVECEXP (operands[2], 0, i);
4828       emit_move_insn (SET_DEST (set), SET_SRC (set));
4829     }
4830
4831   /* The optimizer does not know that the call sets the function value
4832      registers we stored in the result block.  We avoid problems by
4833      claiming that all hard registers are used and clobbered at this
4834      point.  */
4835   emit_insn (gen_blockage ());
4836
4837   DONE;
4838 }")
4839
4840 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
4841 ;; all of memory.  This blocks insns from being moved across this point.
4842
4843 (define_insn "blockage"
4844   [(unspec_volatile [(const_int 0)] 0)]
4845   ""
4846   "")
4847
4848 (define_insn "nop"
4849   [(const_int 0)]
4850   ""
4851   "nop")
4852
4853 (define_insn "probe"
4854  [(reg:SI 15)]
4855  "NEED_PROBE"
4856  "*
4857 {
4858   operands[0] = gen_rtx (PLUS, SImode, stack_pointer_rtx,
4859                          gen_rtx (CONST_INT, VOIDmode, NEED_PROBE));
4860   return \"tstl %a0\";
4861 }")
4862
4863 ;; Used for frameless functions which save no regs and allocate no locals.
4864 (define_insn "return"
4865   [(return)]
4866   "USE_RETURN_INSN"
4867   "*
4868 {
4869   if (current_function_pops_args == 0)
4870     return \"rts\";
4871   operands[0] = gen_rtx (CONST_INT, VOIDmode, current_function_pops_args);
4872   return \"rtd %0\";
4873 }")
4874
4875 (define_insn "indirect_jump"
4876   [(set (pc) (match_operand:SI 0 "address_operand" "p"))]
4877   ""
4878   "jmp %a0")
4879 \f
4880 ;; This should not be used unless the add/sub insns can't be.
4881
4882 (define_insn ""
4883   [(set (match_operand:SI 0 "general_operand" "=a")
4884         (match_operand:QI 1 "address_operand" "p"))]
4885   ""
4886   "*
4887 {
4888 #ifndef SGS_NO_LI
4889   /* Recognize an insn that refers to a table of offsets.  Such an insn will
4890      need to refer to a label on the insn.  So output one.  Use the
4891      label-number of the table of offsets to generate this label.  This code,
4892      and similar code above, assumes that there will be at most one reference
4893      to each table.  */
4894   if (GET_CODE (operands[1]) == PLUS
4895       && GET_CODE (XEXP (operands[1], 1)) == LABEL_REF
4896       && GET_CODE (XEXP (operands[1], 0)) != PLUS)
4897     {
4898       rtx labelref = XEXP (operands[1], 1);
4899 #if defined (MOTOROLA) && !defined (SGS_SWITCH_TABLES)
4900 #ifdef SGS
4901       asm_fprintf (asm_out_file, \"\\tset %LLI%d,.+2\\n\",
4902                    CODE_LABEL_NUMBER (XEXP (labelref, 0)));
4903 #else /* not SGS */
4904       asm_fprintf (asm_out_file, \"\\t.set %LLI%d,.+2\\n\",
4905                    CODE_LABEL_NUMBER (XEXP (labelref, 0)));
4906 #endif /* not SGS */
4907 #else /* SGS_SWITCH_TABLES or not MOTOROLA */
4908       ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, \"LI\",
4909                                  CODE_LABEL_NUMBER (XEXP (labelref, 0)));
4910 #ifdef SGS_SWITCH_TABLES
4911       /* Set flag saying we need to define the symbol
4912          LD%n (with value L%n-LI%n) at the end of the switch table.  */
4913       switch_table_difference_label_flag = 1;
4914 #endif /* SGS_SWITCH_TABLES */
4915 #endif /* SGS_SWITCH_TABLES or not MOTOROLA */
4916     }
4917 #endif /* SGS_NO_LI */
4918
4919   return \"lea %a1,%0\";
4920 }")
4921 \f
4922 ;; This is the first machine-dependent peephole optimization.
4923 ;; It is useful when a floating value is returned from a function call
4924 ;; and then is moved into an FP register.
4925 ;; But it is mainly intended to test the support for these optimizations.
4926
4927 (define_peephole
4928   [(set (reg:SI 15) (plus:SI (reg:SI 15) (const_int 4)))
4929    (set (match_operand:DF 0 "register_operand" "=f")
4930         (match_operand:DF 1 "register_operand" "ad"))]
4931   "FP_REG_P (operands[0]) && ! FP_REG_P (operands[1])"
4932   "*
4933 {
4934   rtx xoperands[2];
4935   xoperands[1] = gen_rtx (REG, SImode, REGNO (operands[1]) + 1);
4936   output_asm_insn (\"move%.l %1,%@\", xoperands);
4937   output_asm_insn (\"move%.l %1,%-\", operands);
4938   return \"fmove%.d %+,%0\";
4939 }
4940 ")
4941
4942 ;; Optimize a stack-adjust followed by a push of an argument.
4943 ;; This is said to happen frequently with -msoft-float
4944 ;; when there are consecutive library calls.
4945
4946 (define_peephole
4947   [(set (reg:SI 15) (plus:SI (reg:SI 15)
4948                              (match_operand:SI 0 "const_int_operand" "n")))
4949    (set (match_operand:SF 1 "push_operand" "=m")
4950         (match_operand:SF 2 "general_operand" "rmfF"))]
4951   "INTVAL (operands[0]) >= 4
4952    && ! reg_mentioned_p (stack_pointer_rtx, operands[2])"
4953   "*
4954 {
4955   if (INTVAL (operands[0]) > 4)
4956     {
4957       rtx xoperands[2];
4958       xoperands[0] = stack_pointer_rtx;
4959       xoperands[1] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[0]) - 4);
4960 #ifndef NO_ADDSUB_Q
4961       if (INTVAL (xoperands[1]) <= 8)
4962         output_asm_insn (\"addq%.w %1,%0\", xoperands);
4963       else if (INTVAL (xoperands[1]) <= 16 && TARGET_68020)
4964         {
4965           xoperands[1] = gen_rtx (CONST_INT, VOIDmode, 
4966                                   INTVAL (xoperands[1]) - 8);
4967           output_asm_insn (\"addq%.w %#8,%0\;addq%.w %1,%0\", xoperands);
4968         }
4969       else
4970 #endif
4971         if (INTVAL (xoperands[1]) <= 0x7FFF)
4972           output_asm_insn (\"add%.w %1,%0\", xoperands);
4973       else
4974         output_asm_insn (\"add%.l %1,%0\", xoperands);
4975     }
4976   if (FP_REG_P (operands[2]))
4977     return \"fmove%.s %2,%@\";
4978   return \"move%.l %2,%@\";
4979 }")
4980
4981 ;; Speed up stack adjust followed by a fullword fixedpoint push.
4982
4983 (define_peephole
4984   [(set (reg:SI 15) (plus:SI (reg:SI 15)
4985                              (match_operand:SI 0 "const_int_operand" "n")))
4986    (set (match_operand:SI 1 "push_operand" "=m")
4987         (match_operand:SI 2 "general_operand" "g"))]
4988   "INTVAL (operands[0]) >= 4
4989    && ! reg_mentioned_p (stack_pointer_rtx, operands[2])"
4990   "*
4991 {
4992   if (INTVAL (operands[0]) > 4)
4993     {
4994       rtx xoperands[2];
4995       xoperands[0] = stack_pointer_rtx;
4996       xoperands[1] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[0]) - 4);
4997 #ifndef NO_ADDSUB_Q
4998       if (INTVAL (xoperands[1]) <= 8)
4999         output_asm_insn (\"addq%.w %1,%0\", xoperands);
5000       else if (INTVAL (xoperands[1]) <= 16 && TARGET_68020)
5001         {
5002           xoperands[1] = gen_rtx (CONST_INT, VOIDmode, 
5003                                   INTVAL (xoperands[1]) - 8);
5004           output_asm_insn (\"addq%.w %#8,%0\;addq%.w %1,%0\", xoperands);
5005         }
5006       else
5007 #endif
5008         if (INTVAL (xoperands[1]) <= 0x7FFF)
5009           output_asm_insn (\"add%.w %1,%0\", xoperands);
5010       else
5011         output_asm_insn (\"add%.l %1,%0\", xoperands);
5012     }
5013   if (operands[2] == const0_rtx)
5014     return \"clr%.l %@\";
5015   return \"move%.l %2,%@\";
5016 }")
5017
5018 ;; Speed up pushing a single byte but leaving four bytes of space.
5019
5020 (define_peephole
5021   [(set (mem:QI (pre_dec:SI (reg:SI 15)))
5022         (match_operand:QI 1 "general_operand" "dami"))
5023    (set (reg:SI 15) (minus:SI (reg:SI 15) (const_int 2)))]
5024   "! reg_mentioned_p (stack_pointer_rtx, operands[1])"
5025   "*
5026 {
5027   rtx xoperands[4];
5028
5029   if (GET_CODE (operands[1]) == REG)
5030     return \"move%.l %1,%-\";
5031
5032   xoperands[1] = operands[1];
5033   xoperands[2]
5034     = gen_rtx (MEM, QImode,
5035                gen_rtx (PLUS, VOIDmode, stack_pointer_rtx,
5036                         gen_rtx (CONST_INT, VOIDmode, 3)));
5037   xoperands[3] = stack_pointer_rtx;
5038   output_asm_insn (\"subq%.w %#4,%3\;move%.b %1,%2\", xoperands);
5039   return \"\";
5040 }")
5041
5042 (define_peephole
5043   [(set (match_operand:SI 0 "register_operand" "=d")
5044         (const_int 0))
5045    (set (strict_low_part (subreg:HI (match_dup 0) 0))
5046         (match_operand:HI 1 "general_operand" "rmn"))]
5047   "strict_low_part_peephole_ok (HImode, prev_nonnote_insn (insn), operands[0])"
5048   "*
5049 {
5050   if (GET_CODE (operands[1]) == CONST_INT)
5051     {
5052       if (operands[1] == const0_rtx
5053           && (DATA_REG_P (operands[0])
5054               || GET_CODE (operands[0]) == MEM)
5055           /* clr insns on 68000 read before writing.
5056              This isn't so on the 68010, but we have no alternative for it.  */
5057           && (TARGET_68020
5058               || !(GET_CODE (operands[0]) == MEM
5059                    && MEM_VOLATILE_P (operands[0]))))
5060         return \"clr%.w %0\";
5061     }
5062   return \"move%.w %1,%0\";
5063 }")
5064
5065 ;; dbCC peepholes
5066 ;;
5067 ;; Turns
5068 ;;   loop:
5069 ;;           [ ... ]
5070 ;;           jCC label          ; abnormal loop termination
5071 ;;           dbra dN, loop      ; normal loop termination
5072 ;;
5073 ;; Into
5074 ;;   loop:
5075 ;;           [ ... ]
5076 ;;           dbCC dN, loop
5077 ;;           jCC label
5078 ;;
5079 ;; Which moves the jCC condition outside the inner loop for free.
5080 ;;
5081 (define_peephole
5082   [(set (pc) (if_then_else (match_operator 3 "valid_dbcc_comparison_p"
5083                              [(cc0) (const_int 0)])
5084                            (label_ref (match_operand 2 "" ""))
5085                            (pc)))
5086    (parallel
5087     [(set (pc)
5088           (if_then_else
5089             (ge (plus:HI (match_operand:HI 0 "register_operand" "+d")
5090                          (const_int -1))
5091                 (const_int 0))
5092             (label_ref (match_operand 1 "" ""))
5093             (pc)))
5094      (set (match_dup 0)
5095           (plus:HI (match_dup 0)
5096                    (const_int -1)))])]
5097   "DATA_REG_P (operands[0])"
5098   "*
5099 {
5100   CC_STATUS_INIT;
5101   output_dbcc_and_branch (operands);
5102   return \"\";
5103 }")
5104
5105 (define_peephole
5106   [(set (pc) (if_then_else (match_operator 3 "valid_dbcc_comparison_p"
5107                              [(cc0) (const_int 0)])
5108                            (label_ref (match_operand 2 "" ""))
5109                            (pc)))
5110    (parallel
5111     [(set (pc)
5112           (if_then_else
5113             (ge (plus:SI (match_operand:SI 0 "register_operand" "+d")
5114                          (const_int -1))
5115                 (const_int 0))
5116             (label_ref (match_operand 1 "" ""))
5117             (pc)))
5118      (set (match_dup 0)
5119           (plus:SI (match_dup 0)
5120                    (const_int -1)))])]
5121   "DATA_REG_P (operands[0])"
5122   "*
5123 {
5124   CC_STATUS_INIT;
5125   output_dbcc_and_branch (operands);
5126   return \"\";
5127 }")
5128
5129 \f
5130 ;; FPA multiply and add.
5131 (define_insn ""
5132   [(set (match_operand:DF 0 "register_operand" "=x,y,y")
5133         (plus:DF (mult:DF (match_operand:DF 1 "general_operand" "%x,dmF,y")
5134                           (match_operand:DF 2 "general_operand" "xH,y,y"))
5135                  (match_operand:DF 3 "general_operand" "xH,y,dmF")))]
5136    "TARGET_FPA"
5137    "@
5138     fpma%.d %1,%w2,%w3,%0
5139     fpma%.d %x1,%x2,%x3,%0
5140     fpma%.d %x1,%x2,%x3,%0")
5141
5142 (define_insn ""
5143   [(set (match_operand:SF 0 "register_operand" "=x,y,y")
5144         (plus:SF (mult:SF (match_operand:SF 1 "general_operand" "%x,ydmF,y")
5145                           (match_operand:SF 2 "general_operand" "xH,y,ydmF"))
5146                  (match_operand:SF 3 "general_operand" "xH,ydmF,ydmF")))]
5147    "TARGET_FPA"
5148    "@
5149     fpma%.s %1,%w2,%w3,%0
5150     fpma%.s %1,%2,%3,%0
5151     fpma%.s %1,%2,%3,%0")
5152
5153 ;; FPA Multiply and subtract
5154 (define_insn ""
5155   [(set (match_operand:DF 0 "register_operand" "=x,y,y")
5156         (minus:DF (match_operand:DF 1 "general_operand" "xH,rmF,y")
5157                   (mult:DF (match_operand:DF 2 "general_operand" "%xH,y,y")
5158                            (match_operand:DF 3 "general_operand" "x,y,rmF"))))]
5159   "TARGET_FPA"
5160   "@
5161    fpms%.d %3,%w2,%w1,%0
5162    fpms%.d %x3,%2,%x1,%0
5163    fpms%.d %x3,%2,%x1,%0")
5164
5165 (define_insn ""
5166   [(set (match_operand:SF 0 "register_operand" "=x,y,y")
5167         (minus:SF (match_operand:SF 1 "general_operand" "xH,rmF,yrmF")
5168                   (mult:SF (match_operand:SF 2 "general_operand" "%xH,rmF,y")
5169                            (match_operand:SF 3 "general_operand" "x,y,yrmF"))))]
5170   "TARGET_FPA"
5171   "@
5172    fpms%.s %3,%w2,%w1,%0
5173    fpms%.s %3,%2,%1,%0
5174    fpms%.s %3,%2,%1,%0")
5175
5176 (define_insn ""
5177   [(set (match_operand:DF 0 "register_operand" "=x,y,y")
5178         (minus:DF (mult:DF (match_operand:DF 1 "general_operand" "%xH,y,y")
5179                            (match_operand:DF 2 "general_operand" "x,y,rmF"))
5180                   (match_operand:DF 3 "general_operand" "xH,rmF,y")))]
5181   "TARGET_FPA"
5182   "@
5183    fpmr%.d %2,%w1,%w3,%0
5184    fpmr%.d %x2,%1,%x3,%0
5185    fpmr%.d %x2,%1,%x3,%0")
5186
5187 (define_insn ""
5188   [(set (match_operand:SF 0 "register_operand" "=x,y,y")
5189         (minus:SF (mult:SF (match_operand:SF 1 "general_operand" "%xH,rmF,y")
5190                            (match_operand:SF 2 "general_operand" "x,y,yrmF"))
5191                   (match_operand:SF 3 "general_operand" "xH,rmF,yrmF")))]
5192   "TARGET_FPA"
5193   "@
5194    fpmr%.s %2,%w1,%w3,%0
5195    fpmr%.s %x2,%1,%x3,%0
5196    fpmr%.s %x2,%1,%x3,%0")
5197
5198 ;; FPA Add and multiply
5199 (define_insn ""
5200   [(set (match_operand:DF 0 "register_operand" "=x,y,y")
5201         (mult:DF (plus:DF (match_operand:DF 1 "general_operand" "%xH,y,y")
5202                           (match_operand:DF 2 "general_operand" "x,y,rmF"))
5203                  (match_operand:DF 3 "general_operand" "xH,rmF,y")))]
5204   "TARGET_FPA"
5205   "@
5206    fpam%.d %2,%w1,%w3,%0
5207    fpam%.d %x2,%1,%x3,%0
5208    fpam%.d %x2,%1,%x3,%0")
5209
5210 (define_insn ""
5211   [(set (match_operand:SF 0 "register_operand" "=x,y,y")
5212         (mult:SF (plus:SF (match_operand:SF 1 "general_operand" "%xH,rmF,y")
5213                           (match_operand:SF 2 "general_operand" "x,y,yrmF"))
5214                  (match_operand:SF 3 "general_operand" "xH,rmF,yrmF")))]
5215   "TARGET_FPA"
5216   "@
5217    fpam%.s %2,%w1,%w3,%0
5218    fpam%.s %x2,%1,%x3,%0
5219    fpam%.s %x2,%1,%x3,%0")
5220
5221 ;;FPA Subtract and multiply
5222 (define_insn ""
5223   [(set (match_operand:DF 0 "register_operand" "=x,y,y")
5224         (mult:DF (minus:DF (match_operand:DF 1 "general_operand" "xH,y,y")
5225                            (match_operand:DF 2 "general_operand" "x,y,rmF"))
5226                  (match_operand:DF 3 "general_operand" "xH,rmF,y")))]
5227   "TARGET_FPA"
5228   "@
5229    fpsm%.d %2,%w1,%w3,%0
5230    fpsm%.d %x2,%1,%x3,%0
5231    fpsm%.d %x2,%1,%x3,%0")
5232
5233 (define_insn ""
5234   [(set (match_operand:DF 0 "register_operand" "=x,y,y")
5235         (mult:DF (match_operand:DF 1 "general_operand" "xH,rmF,y")
5236                  (minus:DF (match_operand:DF 2 "general_operand" "xH,y,y")
5237                            (match_operand:DF 3 "general_operand" "x,y,rmF"))))]
5238   "TARGET_FPA"
5239   "@
5240    fpsm%.d %3,%w2,%w1,%0
5241    fpsm%.d %x3,%2,%x1,%0
5242    fpsm%.d %x3,%2,%x1,%0")
5243
5244 (define_insn ""
5245   [(set (match_operand:SF 0 "register_operand" "=x,y,y")
5246         (mult:SF (minus:SF (match_operand:SF 1 "general_operand" "xH,rmF,y")
5247                            (match_operand:SF 2 "general_operand" "x,y,yrmF"))
5248                  (match_operand:SF 3 "general_operand" "xH,rmF,yrmF")))]
5249   "TARGET_FPA"
5250   "@
5251    fpsm%.s %2,%w1,%w3,%0
5252    fpsm%.s %x2,%1,%x3,%0
5253    fpsm%.s %x2,%1,%x3,%0")
5254
5255 (define_insn ""
5256   [(set (match_operand:SF 0 "register_operand" "=x,y,y")
5257         (mult:SF (match_operand:SF 1 "general_operand" "xH,rmF,yrmF")
5258                  (minus:SF (match_operand:SF 2 "general_operand" "xH,rmF,y")
5259                            (match_operand:SF 3 "general_operand" "x,y,yrmF"))))]
5260   "TARGET_FPA"
5261   "@
5262    fpsm%.s %3,%w2,%w1,%0
5263    fpsm%.s %x3,%2,%x1,%0
5264    fpsm%.s %x3,%2,%x1,%0")
5265
5266 (define_insn "tstxf"
5267   [(set (cc0)
5268         (match_operand:XF 0 "nonimmediate_operand" "fm"))]
5269   "TARGET_68881"
5270   "*
5271 {
5272   cc_status.flags = CC_IN_68881;
5273   return \"ftst%.x %0\";
5274 }")
5275
5276
5277 (define_expand "cmpxf"
5278   [(set (cc0)
5279         (compare (match_operand:XF 0 "general_operand" "f,mG")
5280                  (match_operand:XF 1 "general_operand" "fmG,f")))]
5281   "TARGET_68881"
5282   "
5283 {
5284   if (CONSTANT_P (operands[0]))
5285       operands[0] = force_const_mem (XFmode, operands[0]);
5286   if (CONSTANT_P (operands[1]))
5287       operands[1] = force_const_mem (XFmode, operands[1]);
5288 }")
5289
5290 (define_insn ""
5291   [(set (cc0)
5292         (compare (match_operand:XF 0 "nonimmediate_operand" "f,mG")
5293                  (match_operand:XF 1 "nonimmediate_operand" "fmG,f")))]
5294   "TARGET_68881"
5295   "*
5296 {
5297   cc_status.flags = CC_IN_68881;
5298 #ifdef SGS_CMP_ORDER
5299   if (REG_P (operands[0]))
5300     {
5301       if (REG_P (operands[1]))
5302         return \"fcmp%.x %0,%1\";
5303       else
5304         return \"fcmp%.x %0,%f1\";
5305     }
5306   cc_status.flags |= CC_REVERSED;
5307   return \"fcmp%.x %1,%f0\";
5308 #else
5309   if (REG_P (operands[0]))
5310     {
5311       if (REG_P (operands[1]))
5312         return \"fcmp%.x %1,%0\";
5313       else
5314         return \"fcmp%.x %f1,%0\";
5315     }
5316   cc_status.flags |= CC_REVERSED;
5317   return \"fcmp%.x %f0,%1\";
5318 #endif
5319 }")
5320
5321 (define_insn "extendsfxf2"
5322   [(set (match_operand:XF 0 "general_operand" "=fm,f")
5323         (float_extend:XF (match_operand:SF 1 "general_operand" "f,m")))]
5324   "TARGET_68881"
5325   "*
5326 {
5327   if (FP_REG_P (operands[0]) && FP_REG_P (operands[1]))
5328     {
5329       if (REGNO (operands[0]) == REGNO (operands[1]))
5330         {
5331           /* Extending float to double in an fp-reg is a no-op.
5332              NOTICE_UPDATE_CC has already assumed that the
5333              cc will be set.  So cancel what it did.  */
5334           cc_status = cc_prev_status;
5335           return \"\";
5336         }
5337       return \"f%$move%.x %1,%0\";
5338     }
5339   if (FP_REG_P (operands[0]))
5340     return \"f%$move%.s %f1,%0\";
5341   return \"fmove%.x %f1,%0\";
5342 }")
5343
5344
5345 (define_insn "extenddfxf2"
5346   [(set (match_operand:XF 0 "general_operand" "=fm,f")
5347         (float_extend:XF
5348           (match_operand:DF 1 "general_operand" "f,m")))]
5349   "TARGET_68881"
5350   "*
5351 {
5352   if (FP_REG_P (operands[0]) && FP_REG_P (operands[1]))
5353     {
5354       if (REGNO (operands[0]) == REGNO (operands[1]))
5355         {
5356           /* Extending float to double in an fp-reg is a no-op.
5357              NOTICE_UPDATE_CC has already assumed that the
5358              cc will be set.  So cancel what it did.  */
5359           cc_status = cc_prev_status;
5360           return \"\";
5361         }
5362       return \"fmove%.x %1,%0\";
5363     }
5364   if (FP_REG_P (operands[0]))
5365     return \"f%&move%.d %f1,%0\";
5366   return \"fmove%.x %f1,%0\";
5367 }")
5368
5369 (define_insn "truncxfdf2"
5370   [(set (match_operand:DF 0 "general_operand" "=m,!r")
5371         (float_truncate:DF
5372           (match_operand:XF 1 "general_operand" "f,f")))]
5373   "TARGET_68881"
5374   "*
5375 {
5376   if (REG_P (operands[0]))
5377     {
5378       output_asm_insn (\"fmove%.d %f1,%-\;move%.l %+,%0\", operands);
5379       operands[0] = gen_rtx (REG, SImode, REGNO (operands[0]) + 1);
5380       return \"move%.l %+,%0\";
5381     }
5382   return \"fmove%.d %f1,%0\";
5383 }")
5384  
5385 (define_insn "truncxfsf2"
5386   [(set (match_operand:SF 0 "general_operand" "=dm")
5387         (float_truncate:SF
5388           (match_operand:XF 1 "general_operand" "f")))]
5389   "TARGET_68881"
5390   "fmove%.s %f1,%0")
5391
5392 (define_insn "floatsixf2"
5393   [(set (match_operand:XF 0 "general_operand" "=f")
5394         (float:XF (match_operand:SI 1 "general_operand" "dmi")))]
5395   "TARGET_68881"
5396   "fmove%.l %1,%0")
5397
5398 (define_insn "floathixf2"
5399   [(set (match_operand:XF 0 "general_operand" "=f")
5400         (float:XF (match_operand:HI 1 "general_operand" "dmn")))]
5401   "TARGET_68881"
5402   "fmove%.w %1,%0")
5403
5404 (define_insn "floatqixf2"
5405   [(set (match_operand:XF 0 "general_operand" "=f")
5406         (float:XF (match_operand:QI 1 "general_operand" "dmn")))]
5407   "TARGET_68881"
5408   "fmove%.b %1,%0")
5409
5410 (define_insn "ftruncxf2"
5411   [(set (match_operand:XF 0 "general_operand" "=f")
5412         (fix:XF (match_operand:XF 1 "general_operand" "fFm")))]
5413   "TARGET_68881"
5414   "*
5415 {
5416   if (FP_REG_P (operands[1]))
5417     return \"fintrz%.x %f1,%0\";
5418   return \"fintrz%.x %f1,%0\";
5419 }")
5420
5421 (define_insn "fixxfqi2"
5422   [(set (match_operand:QI 0 "general_operand" "=dm")
5423         (fix:QI (match_operand:XF 1 "general_operand" "f")))]
5424   "TARGET_68881"
5425   "fmove%.b %1,%0")
5426
5427 (define_insn "fixxfhi2"
5428   [(set (match_operand:HI 0 "general_operand" "=dm")
5429         (fix:HI (match_operand:XF 1 "general_operand" "f")))]
5430   "TARGET_68881"
5431   "fmove%.w %1,%0")
5432
5433 (define_insn "fixxfsi2"
5434   [(set (match_operand:SI 0 "general_operand" "=dm")
5435         (fix:SI (match_operand:XF 1 "general_operand" "f")))]
5436   "TARGET_68881"
5437   "fmove%.l %1,%0")
5438
5439 (define_expand "addxf3"
5440   [(set (match_operand:XF 0 "general_operand" "")
5441         (plus:XF (match_operand:XF 1 "general_operand" "")
5442                  (match_operand:XF 2 "general_operand" "")))]
5443   "TARGET_68881"
5444   "
5445 {
5446   if (CONSTANT_P (operands[1]))
5447     operands[1] = force_const_mem (XFmode, operands[1]);
5448   if (CONSTANT_P (operands[2]))
5449     operands[2] = force_const_mem (XFmode, operands[2]);
5450 }")
5451
5452 (define_insn ""
5453   [(set (match_operand:XF 0 "general_operand" "=f")
5454         (plus:XF (match_operand:XF 1 "nonimmediate_operand" "%0")
5455                  (match_operand:XF 2 "nonimmediate_operand" "fmG")))]
5456   "TARGET_68881"
5457   "*
5458 {
5459   if (REG_P (operands[2]))
5460     return \"fadd%.x %2,%0\";
5461   return \"fadd%.x %f2,%0\";
5462 }")
5463
5464 (define_expand "subxf3"
5465   [(set (match_operand:XF 0 "general_operand" "")
5466         (minus:XF (match_operand:XF 1 "general_operand" "")
5467                  (match_operand:XF 2 "general_operand" "")))]
5468   "TARGET_68881"
5469   "
5470 {
5471   if (CONSTANT_P (operands[1]))
5472     operands[1] = force_const_mem (XFmode, operands[1]);
5473   if (CONSTANT_P (operands[2]))
5474     operands[2] = force_const_mem (XFmode, operands[2]);
5475 }")
5476
5477 (define_insn ""
5478   [(set (match_operand:XF 0 "general_operand" "=f")
5479         (minus:XF (match_operand:XF 1 "nonimmediate_operand" "0")
5480                  (match_operand:XF 2 "nonimmediate_operand" "fmG")))]
5481   "TARGET_68881"
5482   "*
5483 {
5484   if (REG_P (operands[2]))
5485     return \"fsub%.x %2,%0\";
5486   return \"fsub%.x %f2,%0\";
5487 }")
5488
5489 (define_expand "mulxf3"
5490   [(set (match_operand:XF 0 "general_operand" "")
5491         (mult:XF (match_operand:XF 1 "general_operand" "")
5492                 (match_operand:XF 2 "general_operand" "")))]
5493   "TARGET_68881"
5494   "
5495 {
5496   if (CONSTANT_P (operands[1]))
5497     operands[1] = force_const_mem (XFmode, operands[1]);
5498   if (CONSTANT_P (operands[2]))
5499     operands[2] = force_const_mem (XFmode, operands[2]);
5500 }")
5501
5502 (define_insn ""
5503   [(set (match_operand:XF 0 "general_operand" "=f")
5504         (mult:XF (match_operand:XF 1 "nonimmediate_operand" "%0")
5505                 (match_operand:XF 2 "nonimmediate_operand" "fmG")))]
5506   "TARGET_68881"
5507   "*
5508 {
5509   if (REG_P (operands[2]))
5510     return \"fmul%.x %2,%0\";
5511   return \"fmul%.x %f2,%0\";
5512 }")
5513
5514 (define_expand "divxf3"
5515   [(set (match_operand:XF 0 "general_operand" "")
5516         (div:XF (match_operand:XF 1 "general_operand" "")
5517                 (match_operand:XF 2 "general_operand" "")))]
5518   "TARGET_68881"
5519   "
5520 {
5521   if (CONSTANT_P (operands[1]))
5522     operands[1] = force_const_mem (XFmode, operands[1]);
5523   if (CONSTANT_P (operands[2]))
5524     operands[2] = force_const_mem (XFmode, operands[2]);
5525 }")
5526
5527 (define_insn ""
5528   [(set (match_operand:XF 0 "general_operand" "=f")
5529         (div:XF (match_operand:XF 1 "nonimmediate_operand" "0")
5530                 (match_operand:XF 2 "nonimmediate_operand" "fmG")))]
5531   "TARGET_68881"
5532   "*
5533 {
5534   if (REG_P (operands[2]))
5535     return \"fdiv%.x %2,%0\";
5536   return \"fdiv%.x %f2,%0\";
5537 }")
5538
5539 (define_insn "negxf2"
5540   [(set (match_operand:XF 0 "general_operand" "=f")
5541         (neg:XF (match_operand:XF 1 "nonimmediate_operand" "fmF")))]
5542   "TARGET_68881"
5543   "*
5544 {
5545   if (REG_P (operands[1]) && ! DATA_REG_P (operands[1]))
5546     return \"fneg%.x %1,%0\";
5547   return \"fneg%.x %f1,%0\";
5548 }")
5549
5550 (define_insn "absxf2"
5551   [(set (match_operand:XF 0 "general_operand" "=f")
5552         (abs:XF (match_operand:XF 1 "nonimmediate_operand" "fmF")))]
5553   "TARGET_68881"
5554   "*
5555 {
5556   if (REG_P (operands[1]) && ! DATA_REG_P (operands[1]))
5557     return \"fabs%.x %1,%0\";
5558   return \"fabs%.x %f1,%0\";
5559 }")
5560
5561 (define_insn "sqrtxf2"
5562   [(set (match_operand:XF 0 "general_operand" "=f")
5563         (sqrt:XF (match_operand:DF 1 "nonimmediate_operand" "fm")))]
5564   "TARGET_68881"
5565   "*
5566 {
5567     return \"fsqrt%.x %1,%0\";
5568 }")