OSDN Git Service

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