|
|
1.1 root 1: ;;- Machine description for GNU C compiler for Alliant FX systems
1.1.1.2 root 2: ;; Copyright (C) 1989, 1994 Free Software Foundation, Inc.
3: ;; Adapted from m68k.md by Paul Petersen ([email protected])
4: ;; and Joe Weening ([email protected]).
1.1 root 5:
6: ;; This file is part of GNU CC.
7:
8: ;; GNU CC is free software; you can redistribute it and/or modify
9: ;; it under the terms of the GNU General Public License as published by
10: ;; the Free Software Foundation; either version 2, or (at your option)
11: ;; any later version.
12:
13: ;; GNU CC is distributed in the hope that it will be useful,
14: ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
15: ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16: ;; GNU General Public License for more details.
17:
18: ;; You should have received a copy of the GNU General Public License
19: ;; along with GNU CC; see the file COPYING. If not, write to
1.1.1.3 ! root 20: ;; the Free Software Foundation, 59 Temple Place - Suite 330,
! 21: ;; Boston, MA 02111-1307, USA.
1.1 root 22:
23:
24: ;;- instruction definitions
25:
26: ;;- @@The original PO technology requires these to be ordered by speed,
27: ;;- @@ so that assigner will pick the fastest.
28:
29: ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
30:
31: ;;- When naming insn's (operand 0 of define_insn) be careful about using
32: ;;- names from other targets machine descriptions.
33:
34: ;;- cpp macro #define NOTICE_UPDATE_CC in file tm.h handles condition code
35: ;;- updates for most instructions.
36:
37: ;;- Operand classes for the register allocator:
38: ;;- 'a' one of the address registers can be used.
39: ;;- 'd' one of the data registers can be used.
40: ;;- 'f' one of the CE floating point registers can be used
41: ;;- 'r' either a data or an address register can be used.
42:
43: ;;- Immediate integer operand constraints:
44: ;;- 'I' 1 .. 8
45: ;;- 'J' -32768 .. 32767
46: ;;- 'K' -128 .. 127
47: ;;- 'L' -8 .. -1
48:
49: ;;- Some remnants of constraint codes for the m68k ('x','y','G','H')
50: ;;- may remain in the insn definitions.
51:
52: ;;- Some of these insn's are composites of several Alliant op codes.
53: ;;- The assembler (or final @@??) insures that the appropriate one is
54: ;;- selected.
55:
56: ;; We don't want to allow a constant operand for test insns because
57: ;; (set (cc0) (const_int foo)) has no mode information. Such insns will
58: ;; be folded while optimizing anyway.
59:
60: (define_insn "tstsi"
61: [(set (cc0)
62: (match_operand:SI 0 "nonimmediate_operand" "rm"))]
63: ""
64: "*
65: {
66: if (TARGET_68020 || ! ADDRESS_REG_P (operands[0]))
67: return \"tst%.l %0\";
68: /* If you think that the 68020 does not support tstl a0,
69: reread page B-167 of the 68020 manual more carefully. */
70: /* On an address reg, cmpw may replace cmpl. */
71: return \"cmp%.w %#0,%0\";
72: }")
73:
74: (define_insn "tsthi"
75: [(set (cc0)
76: (match_operand:HI 0 "nonimmediate_operand" "rm"))]
77: ""
78: "*
79: {
80: if (TARGET_68020 || ! ADDRESS_REG_P (operands[0]))
81: return \"tst%.w %0\";
82: return \"cmp%.w %#0,%0\";
83: }")
84:
85: (define_insn "tstqi"
86: [(set (cc0)
87: (match_operand:QI 0 "nonimmediate_operand" "dm"))]
88: ""
89: "tst%.b %0")
90:
91: (define_insn "tstsf"
92: [(set (cc0)
93: (match_operand:SF 0 "nonimmediate_operand" "fm"))]
94: "TARGET_CE"
95: "*
96: {
97: cc_status.flags = CC_IN_FP;
98: return \"ftest%.s %0\";
99: }")
100:
101: (define_insn "tstdf"
102: [(set (cc0)
103: (match_operand:DF 0 "nonimmediate_operand" "fm"))]
104: "TARGET_CE"
105: "*
106: {
107: cc_status.flags = CC_IN_FP;
108: return \"ftest%.d %0\";
109: }")
110:
111: ;; compare instructions.
112:
113: ;; A composite of the cmp, cmpa, & cmpi m68000 op codes.
114: (define_insn "cmpsi"
115: [(set (cc0)
116: (compare (match_operand:SI 0 "nonimmediate_operand" "rKs,mr,>")
117: (match_operand:SI 1 "general_operand" "mr,Ksr,>")))]
118: ""
119: "*
120: {
121: if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
122: return \"cmpm%.l %1,%0\";
123: if (REG_P (operands[1])
124: || (!REG_P (operands[0]) && GET_CODE (operands[0]) != MEM))
125: {
126: cc_status.flags |= CC_REVERSED;
127: return \"cmp%.l %d0,%d1\";
128: }
129: return \"cmp%.l %d1,%d0\";
130: }")
131:
132: (define_insn "cmphi"
133: [(set (cc0)
134: (compare (match_operand:HI 0 "nonimmediate_operand" "rnm,d,n,m")
135: (match_operand:HI 1 "general_operand" "d,rnm,m,n")))]
136: ""
137: "*
138: {
139: if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
140: return \"cmpm%.w %1,%0\";
141: if ((REG_P (operands[1]) && !ADDRESS_REG_P (operands[1]))
142: || (!REG_P (operands[0]) && GET_CODE (operands[0]) != MEM))
143: { cc_status.flags |= CC_REVERSED;
144: return \"cmp%.w %d0,%d1\";
145: }
146: return \"cmp%.w %d1,%d0\";
147: }")
148:
149: (define_insn "cmpqi"
150: [(set (cc0)
151: (compare (match_operand:QI 0 "nonimmediate_operand" "dn,md,>")
152: (match_operand:QI 1 "general_operand" "dm,nd,>")))]
153: ""
154: "*
155: {
156: if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
157: return \"cmpm%.b %1,%0\";
158: if (REG_P (operands[1])
159: || (!REG_P (operands[0]) && GET_CODE (operands[0]) != MEM))
160: {
161: cc_status.flags |= CC_REVERSED;
162: return \"cmp%.b %d0,%d1\";
163: }
164: return \"cmp%.b %d1,%d0\";
165: }")
166:
167: (define_insn "cmpdf"
168: [(set (cc0)
169: (compare (match_operand:DF 0 "nonimmediate_operand" "f,m")
170: (match_operand:DF 1 "nonimmediate_operand" "fm,f")))]
171: "TARGET_CE"
172: "*
173: {
174: cc_status.flags = CC_IN_FP;
175: if (FP_REG_P (operands[0]))
176: return \"fcmp%.d %1,%0\";
177: cc_status.flags |= CC_REVERSED;
178: return \"fcmp%.d %0,%1\";
179: }")
180:
181: (define_insn "cmpsf"
182: [(set (cc0)
183: (compare (match_operand:SF 0 "nonimmediate_operand" "f,m")
184: (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
185: "TARGET_CE"
186: "*
187: {
188: cc_status.flags = CC_IN_FP;
189: if (FP_REG_P (operands[0]))
190: return \"fcmp%.s %1,%0\";
191: cc_status.flags |= CC_REVERSED;
192: return \"fcmp%.s %0,%1\";
193: }")
194:
195: ;; Recognizers for btst instructions.
196:
197: (define_insn ""
198: [(set (cc0) (zero_extract (match_operand:QI 0 "nonimmediate_operand" "do")
199: (const_int 1)
200: (minus:SI (const_int 7)
201: (match_operand:SI 1 "general_operand" "di"))))]
202: ""
203: "* { return output_btst (operands, operands[1], operands[0], insn, 7); }")
204:
205: (define_insn ""
206: [(set (cc0) (zero_extract (match_operand:SI 0 "nonimmediate_operand" "d")
207: (const_int 1)
208: (minus:SI (const_int 31)
209: (match_operand:SI 1 "general_operand" "di"))))]
210: ""
211: "* { return output_btst (operands, operands[1], operands[0], insn, 31); }")
212:
213: ;; The following two patterns are like the previous two
214: ;; except that they use the fact that bit-number operands
215: ;; are automatically masked to 3 or 5 bits.
216:
217: (define_insn ""
218: [(set (cc0) (zero_extract (match_operand:QI 0 "nonimmediate_operand" "do")
219: (const_int 1)
220: (minus:SI (const_int 7)
221: (and:SI
222: (match_operand:SI 1 "general_operand" "d")
223: (const_int 7)))))]
224: ""
225: "* { return output_btst (operands, operands[1], operands[0], insn, 7); }")
226:
227: (define_insn ""
228: [(set (cc0) (zero_extract (match_operand:SI 0 "nonimmediate_operand" "d")
229: (const_int 1)
230: (minus:SI (const_int 31)
231: (and:SI
232: (match_operand:SI 1 "general_operand" "d")
233: (const_int 31)))))]
234: ""
235: "* { return output_btst (operands, operands[1], operands[0], insn, 31); }")
236:
237: ;; Nonoffsettable mem refs are ok in this one pattern
238: ;; since we don't try to adjust them.
239: (define_insn ""
240: [(set (cc0) (zero_extract (match_operand:QI 0 "nonimmediate_operand" "md")
241: (const_int 1)
242: (match_operand:SI 1 "general_operand" "i")))]
243: "GET_CODE (operands[1]) == CONST_INT
244: && (unsigned) INTVAL (operands[1]) < 8"
245: "*
246: {
247: operands[1] = gen_rtx (CONST_INT, VOIDmode, 7 - INTVAL (operands[1]));
248: return output_btst (operands, operands[1], operands[0], insn, 7);
249: }")
250:
251:
252: (define_insn ""
253: [(set (cc0) (zero_extract (match_operand:SI 0 "nonimmediate_operand" "do")
254: (const_int 1)
255: (match_operand:SI 1 "general_operand" "i")))]
256: "GET_CODE (operands[1]) == CONST_INT"
257: "*
258: {
259: if (GET_CODE (operands[0]) == MEM)
260: {
261: operands[0] = adj_offsettable_operand (operands[0],
262: INTVAL (operands[1]) / 8);
263: operands[1] = gen_rtx (CONST_INT, VOIDmode,
264: 7 - INTVAL (operands[1]) % 8);
265: return output_btst (operands, operands[1], operands[0], insn, 7);
266: }
267: operands[1] = gen_rtx (CONST_INT, VOIDmode,
268: 31 - INTVAL (operands[1]));
269: return output_btst (operands, operands[1], operands[0], insn, 31);
270: }")
271:
272:
273: ;; move instructions
274:
275: ;; A special case in which it is not desirable
276: ;; to reload the constant into a data register.
277: (define_insn ""
278: [(set (match_operand:SI 0 "push_operand" "=m")
279: (match_operand:SI 1 "general_operand" "J"))]
280: "GET_CODE (operands[1]) == CONST_INT
281: && INTVAL (operands[1]) >= -0x8000
282: && INTVAL (operands[1]) < 0x8000"
283: "*
284: {
285: if (operands[1] == const0_rtx)
286: return \"clr%.l %0\";
287: return \"pea %a1\";
288: }")
289:
290: ;This is never used.
291: ;(define_insn "swapsi"
292: ; [(set (match_operand:SI 0 "general_operand" "r")
293: ; (match_operand:SI 1 "general_operand" "r"))
294: ; (set (match_dup 1) (match_dup 0))]
295: ; ""
296: ; "exg %1,%0")
297:
298: ;; Special case of fullword move when source is zero.
299: ;; The reason this is special is to avoid loading a zero
300: ;; into a data reg with moveq in order to store it elsewhere.
301:
302: (define_insn ""
303: [(set (match_operand:SI 0 "general_operand" "=a,g")
304: (const_int 0))]
305: ""
306: "@
307: sub%.l %0,%0
308: clr%.l %0")
309:
310: ;; General case of fullword move. The register constraints
311: ;; force integer constants in range for a moveq to be reloaded
312: ;; if they are headed for memory.
313: (define_insn "movsi"
314: ;; Notes: make sure no alternative allows g vs g.
315: ;; We don't allow f-regs since fixed point cannot go in them.
316: ;; We do allow y and x regs since fixed point is allowed in them.
317: [(set (match_operand:SI 0 "general_operand" "=g,da,y,!*x*r*m")
318: (match_operand:SI 1 "general_operand" "daymKs,i,g,*x*r*m"))]
319: ""
320: "*
321: {
322: if (GET_CODE (operands[1]) == CONST_INT)
323: {
324: if (operands[1] == const0_rtx
325: && (DATA_REG_P (operands[0])
326: || GET_CODE (operands[0]) == MEM))
327: return \"clr%.l %0\";
328: else if (DATA_REG_P (operands[0])
329: && INTVAL (operands[1]) < 128
330: && INTVAL (operands[1]) >= -128)
331: return \"moveq %1,%0\";
332: else if (ADDRESS_REG_P (operands[0])
333: && INTVAL (operands[1]) < 0x8000
334: && INTVAL (operands[1]) >= -0x8000)
335: return \"mov%.w %1,%0\";
336: else if (push_operand (operands[0], SImode)
337: && INTVAL (operands[1]) < 0x8000
338: && INTVAL (operands[1]) >= -0x8000)
339: return \"pea %a1\";
340: }
341: else if ((GET_CODE (operands[1]) == SYMBOL_REF
342: || GET_CODE (operands[1]) == CONST)
343: && push_operand (operands[0], SImode))
344: return \"pea %a1\";
345: else if ((GET_CODE (operands[1]) == SYMBOL_REF
346: || GET_CODE (operands[1]) == CONST)
347: && ADDRESS_REG_P (operands[0]))
348: return \"lea %a1,%0\";
349: return \"mov%.l %1,%0\";
350: }")
351:
352: (define_insn "movhi"
353: [(set (match_operand:HI 0 "general_operand" "=g")
354: (match_operand:HI 1 "general_operand" "g"))]
355: ""
356: "*
357: {
358: if (GET_CODE (operands[1]) == CONST_INT)
359: {
360: if (operands[1] == const0_rtx
361: && (DATA_REG_P (operands[0])
362: || GET_CODE (operands[0]) == MEM))
363: return \"clr%.w %0\";
364: else if (DATA_REG_P (operands[0])
365: && INTVAL (operands[1]) < 128
366: && INTVAL (operands[1]) >= -128)
367: {
368: return \"moveq %1,%0\";
369: }
370: else if (INTVAL (operands[1]) < 0x8000
371: && INTVAL (operands[1]) >= -0x8000)
372: return \"mov%.w %1,%0\";
373: }
374: else if (CONSTANT_P (operands[1]))
375: return \"mov%.l %1,%0\";
376: /* Recognize the insn before a tablejump, one that refers
377: to a table of offsets. Such an insn will need to refer
378: to a label on the insn. So output one. Use the label-number
379: of the table of offsets to generate this label. */
380: if (GET_CODE (operands[1]) == MEM
381: && GET_CODE (XEXP (operands[1], 0)) == PLUS
382: && (GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == LABEL_REF
383: || GET_CODE (XEXP (XEXP (operands[1], 0), 1)) == LABEL_REF)
384: && GET_CODE (XEXP (XEXP (operands[1], 0), 0)) != PLUS
385: && GET_CODE (XEXP (XEXP (operands[1], 0), 1)) != PLUS)
386: {
387: rtx labelref;
388: if (GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == LABEL_REF)
389: labelref = XEXP (XEXP (operands[1], 0), 0);
390: else
391: labelref = XEXP (XEXP (operands[1], 0), 1);
392: ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, \"LI\",
393: CODE_LABEL_NUMBER (XEXP (labelref, 0)));
394: }
395: return \"mov%.w %1,%0\";
396: }")
397:
398: (define_insn "movstricthi"
399: [(set (strict_low_part (match_operand:HI 0 "general_operand" "+dm"))
400: (match_operand:HI 1 "general_operand" "rmn"))]
401: ""
402: "*
403: {
404: if (operands[1] == const0_rtx)
405: return \"clr%.w %0\";
406: return \"mov%.w %1,%0\";
407: }")
408:
409: (define_insn "movqi"
410: [(set (match_operand:QI 0 "general_operand" "=d,*a,m,m,?*a")
411: (match_operand:QI 1 "general_operand" "dmi*a,d*a,dmi,?*a,m"))]
412: ""
413: "*
414: {
415: rtx xoperands[4];
416: if (ADDRESS_REG_P (operands[0]) && GET_CODE (operands[1]) == MEM)
417: {
418: xoperands[1] = operands[1];
419: xoperands[2]
420: = gen_rtx (MEM, QImode,
421: gen_rtx (PLUS, VOIDmode, stack_pointer_rtx, const1_rtx));
422: xoperands[3] = stack_pointer_rtx;
423: /* Just pushing a byte puts it in the high byte of the halfword. */
424: /* We must put it in the low half, the second byte. */
425: output_asm_insn (\"subq%.w %#2,%3\;mov%.b %1,%2\", xoperands);
426: return \"mov%.w %+,%0\";
427: }
428: if (ADDRESS_REG_P (operands[1]) && GET_CODE (operands[0]) == MEM)
429: {
430: xoperands[0] = operands[0];
431: xoperands[1] = operands[1];
432: xoperands[2]
433: = gen_rtx (MEM, QImode,
434: gen_rtx (PLUS, VOIDmode, stack_pointer_rtx, const1_rtx));
435: xoperands[3] = stack_pointer_rtx;
436: output_asm_insn (\"mov%.w %1,%-\;mov%.b %2,%0\;addq%.w %#2,%3\", xoperands);
437: return \"\";
438: }
439: if (operands[1] == const0_rtx)
440: return \"clr%.b %0\";
441: if (GET_CODE (operands[1]) == CONST_INT
442: && INTVAL (operands[1]) == -1)
443: return \"st %0\";
444: if (GET_CODE (operands[1]) != CONST_INT && CONSTANT_P (operands[1]))
445: return \"mov%.l %1,%0\";
446: if (ADDRESS_REG_P (operands[0]) || ADDRESS_REG_P (operands[1]))
447: return \"mov%.w %1,%0\";
448: return \"mov%.b %1,%0\";
449: }")
450:
451: (define_insn "movstrictqi"
452: [(set (strict_low_part (match_operand:QI 0 "general_operand" "+dm"))
453: (match_operand:QI 1 "general_operand" "dmn"))]
454: ""
455: "*
456: {
457: if (operands[1] == const0_rtx)
458: return \"clr%.b %0\";
459: return \"mov%.b %1,%0\";
460: }")
461:
462: ;; Floating-point moves on a CE are faster using an FP register than
463: ;; with movl instructions. (Especially for double floats, but also
464: ;; for single floats, even though it takes an extra instruction.) But
465: ;; on an IP, the FP registers are simulated and so should be avoided.
466: ;; We do this by using define_expand for movsf and movdf, and using
467: ;; different constraints for each target type. The constraints for
468: ;; TARGET_CE allow general registers because they sometimes need to
469: ;; hold floats, but they are not preferable.
470:
471: (define_expand "movsf"
472: [(set (match_operand:SF 0 "general_operand" "")
473: (match_operand:SF 1 "nonimmediate_operand" ""))]
474: ""
475: "")
476:
477: (define_insn ""
478: [(set (match_operand:SF 0 "general_operand" "=f,m,!*r,!f*m")
479: (match_operand:SF 1 "nonimmediate_operand" "fm,f,f*r*m,*r"))]
480: "TARGET_CE"
481: "*
482: {
483: if (FP_REG_P (operands[0]))
484: {
485: if (FP_REG_P (operands[1]))
486: return \"fmove%.s %1,%0\";
487: if (REG_P (operands[1]))
488: return \"mov%.l %1,%-\;fmove%.s %+,%0\";
489: return \"fmove%.s %1,%0\";
490: }
491: if (FP_REG_P (operands[1]))
492: {
493: if (REG_P (operands[0]))
494: return \"fmove%.s %1,%-\;mov%.l %+,%0\";
495: return \"fmove%.s %1,%0\";
496: }
497: return \"mov%.l %1,%0\";
498: }")
499:
500: (define_insn ""
501: [(set (match_operand:SF 0 "general_operand" "=frm")
502: (match_operand:SF 1 "nonimmediate_operand" "frm"))]
503: "!TARGET_CE"
504: "*
505: {
506: if (FP_REG_P (operands[0]))
507: {
508: if (FP_REG_P (operands[1]))
509: return \"fmove%.s %1,%0\";
510: if (REG_P (operands[1]))
511: return \"mov%.l %1,%-\;fmove%.s %+,%0\";
512: return \"fmove%.s %1,%0\";
513: }
514: if (FP_REG_P (operands[1]))
515: {
516: if (REG_P (operands[0]))
517: return \"fmove%.s %1,%-\;mov%.l %+,%0\";
518: return \"fmove%.s %1,%0\";
519: }
520: return \"mov%.l %1,%0\";
521: }")
522:
523: (define_expand "movdf"
524: [(set (match_operand:DF 0 "general_operand" "")
525: (match_operand:DF 1 "nonimmediate_operand" ""))]
526: ""
527: "")
528:
529: (define_insn ""
530: [(set (match_operand:DF 0 "general_operand" "=f,m,!*r,!f*m")
531: (match_operand:DF 1 "nonimmediate_operand" "fm,f,f*r*m,*r"))]
532: "TARGET_CE"
533: "*
534: {
535: if (FP_REG_P (operands[0]))
536: {
537: if (FP_REG_P (operands[1]))
538: return \"fmove%.d %1,%0\";
539: if (REG_P (operands[1]))
540: {
541: rtx xoperands[2];
542: xoperands[1] = gen_rtx (REG, SImode, REGNO (operands[1]) + 1);
543: output_asm_insn (\"mov%.l %1,%-\", xoperands);
544: output_asm_insn (\"mov%.l %1,%-\", operands);
545: return \"fmove%.d %+,%0\";
546: }
547: return \"fmove%.d %1,%0\";
548: }
549: else if (FP_REG_P (operands[1]))
550: {
551: if (REG_P (operands[0]))
552: {
553: output_asm_insn (\"fmove%.d %1,%-\;mov%.l %+,%0\", operands);
554: operands[0] = gen_rtx (REG, SImode, REGNO (operands[0]) + 1);
555: return \"mov%.l %+,%0\";
556: }
557: return \"fmove%.d %1,%0\";
558: }
559: return output_move_double (operands);
560: }")
561:
562: (define_insn ""
563: [(set (match_operand:DF 0 "general_operand" "=frm")
564: (match_operand:DF 1 "nonimmediate_operand" "frm"))]
565: "!TARGET_CE"
566: "*
567: {
568: if (FP_REG_P (operands[0]))
569: {
570: if (FP_REG_P (operands[1]))
571: return \"fmove%.d %1,%0\";
572: if (REG_P (operands[1]))
573: {
574: rtx xoperands[2];
575: xoperands[1] = gen_rtx (REG, SImode, REGNO (operands[1]) + 1);
576: output_asm_insn (\"mov%.l %1,%-\", xoperands);
577: output_asm_insn (\"mov%.l %1,%-\", operands);
578: return \"fmove%.d %+,%0\";
579: }
580: return \"fmove%.d %1,%0\";
581: }
582: else if (FP_REG_P (operands[1]))
583: {
584: if (REG_P (operands[0]))
585: {
586: output_asm_insn (\"fmove%.d %1,%-\;mov%.l %+,%0\", operands);
587: operands[0] = gen_rtx (REG, SImode, REGNO (operands[0]) + 1);
588: return \"mov%.l %+,%0\";
589: }
590: return \"fmove%.d %1,%0\";
591: }
592: return output_move_double (operands);
593: }")
594:
595: (define_insn "movdi"
596: [(set (match_operand:DI 0 "general_operand" "=rm,&r,&ro<>")
597: (match_operand:DI 1 "general_operand" "r,m,roi<>"))]
598: ""
599: "*
600: {
601: return output_move_double (operands);
602: }
603: ")
604:
605: ;; This goes after the move instructions
606: ;; because the move instructions are better (require no spilling)
607: ;; when they can apply. It goes before the add/sub insns
608: ;; so we will prefer it to them.
609:
610: (define_insn "pushasi"
611: [(set (match_operand:SI 0 "push_operand" "=m")
612: (match_operand:SI 1 "address_operand" "p"))]
613: ""
614: "pea %a1")
615:
616: ;; truncation instructions
617: (define_insn "truncsiqi2"
618: [(set (match_operand:QI 0 "general_operand" "=dm,d")
619: (truncate:QI
620: (match_operand:SI 1 "general_operand" "doJ,i")))]
621: ""
622: "*
623: {
624: if (GET_CODE (operands[0]) == REG)
625: return \"mov%.l %1,%0\";
626: if (GET_CODE (operands[1]) == MEM)
627: operands[1] = adj_offsettable_operand (operands[1], 3);
628: return \"mov%.b %1,%0\";
629: }")
630:
631: (define_insn "trunchiqi2"
632: [(set (match_operand:QI 0 "general_operand" "=dm,d")
633: (truncate:QI
634: (match_operand:HI 1 "general_operand" "doJ,i")))]
635: ""
636: "*
637: {
638: if (GET_CODE (operands[0]) == REG
639: && (GET_CODE (operands[1]) == MEM
640: || GET_CODE (operands[1]) == CONST_INT))
641: return \"mov%.w %1,%0\";
642: if (GET_CODE (operands[0]) == REG)
643: return \"mov%.l %1,%0\";
644: if (GET_CODE (operands[1]) == MEM)
645: operands[1] = adj_offsettable_operand (operands[1], 1);
646: return \"mov%.b %1,%0\";
647: }")
648:
649: (define_insn "truncsihi2"
650: [(set (match_operand:HI 0 "general_operand" "=dm,d")
651: (truncate:HI
652: (match_operand:SI 1 "general_operand" "roJ,i")))]
653: ""
654: "*
655: {
656: if (GET_CODE (operands[0]) == REG)
657: return \"mov%.l %1,%0\";
658: if (GET_CODE (operands[1]) == MEM)
659: operands[1] = adj_offsettable_operand (operands[1], 2);
660: return \"mov%.w %1,%0\";
661: }")
662:
663: ;; zero extension instructions
664:
665: (define_expand "zero_extendhisi2"
666: [(set (match_operand:SI 0 "register_operand" "")
667: (const_int 0))
668: (set (strict_low_part (subreg:HI (match_dup 0) 0))
669: (match_operand:HI 1 "general_operand" ""))]
670: ""
671: "operands[1] = make_safe_from (operands[1], operands[0]);")
672:
673: (define_expand "zero_extendqihi2"
674: [(set (match_operand:HI 0 "register_operand" "")
675: (const_int 0))
676: (set (strict_low_part (subreg:QI (match_dup 0) 0))
677: (match_operand:QI 1 "general_operand" ""))]
678: ""
679: "operands[1] = make_safe_from (operands[1], operands[0]);")
680:
681: (define_expand "zero_extendqisi2"
682: [(set (match_operand:SI 0 "register_operand" "")
683: (const_int 0))
684: (set (strict_low_part (subreg:QI (match_dup 0) 0))
685: (match_operand:QI 1 "general_operand" ""))]
686: ""
687: " operands[1] = make_safe_from (operands[1], operands[0]); ")
688:
689: ;; Patterns to recognize zero-extend insns produced by the combiner.
690: (define_insn ""
691: [(set (match_operand:SI 0 "general_operand" "=do<>")
692: (zero_extend:SI
693: (match_operand:HI 1 "nonimmediate_operand" "rm")))]
694: ""
695: "*
696: {
697: if (DATA_REG_P (operands[0]))
698: {
699: if (GET_CODE (operands[1]) == REG
700: && REGNO (operands[0]) == REGNO (operands[1]))
701: return \"and%.l %#0xFFFF,%0\";
702: if (reg_mentioned_p (operands[0], operands[1]))
703: return \"mov%.w %1,%0\;and%.l %#0xFFFF,%0\";
704: return \"clr%.l %0\;mov%.w %1,%0\";
705: }
706: else if (GET_CODE (operands[0]) == MEM
707: && GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
708: return \"mov%.w %1,%0\;clr%.w %0\";
709: else if (GET_CODE (operands[0]) == MEM
710: && GET_CODE (XEXP (operands[0], 0)) == POST_INC)
711: return \"clr%.w %0\;mov%.w %1,%0\";
712: else
713: {
714: output_asm_insn (\"clr%.w %0\", operands);
715: operands[0] = adj_offsettable_operand (operands[0], 2);
716: return \"mov%.w %1,%0\";
717: }
718: }")
719:
720: (define_insn ""
721: [(set (match_operand:HI 0 "general_operand" "=do<>")
722: (zero_extend:HI
723: (match_operand:QI 1 "nonimmediate_operand" "dm")))]
724: ""
725: "*
726: {
727: if (DATA_REG_P (operands[0]))
728: {
729: if (GET_CODE (operands[1]) == REG
730: && REGNO (operands[0]) == REGNO (operands[1]))
731: return \"and%.w %#0xFF,%0\";
732: if (reg_mentioned_p (operands[0], operands[1]))
733: return \"mov%.b %1,%0\;and%.w %#0xFF,%0\";
734: return \"clr%.w %0\;mov%.b %1,%0\";
735: }
736: else if (GET_CODE (operands[0]) == MEM
737: && GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
738: {
739: if (REGNO (XEXP (XEXP (operands[0], 0), 0))
740: == STACK_POINTER_REGNUM)
741: return \"clr%.w %-\;mov%.b %1,%0\";
742: else
743: return \"mov%.b %1,%0\;clr%.b %0\";
744: }
745: else if (GET_CODE (operands[0]) == MEM
746: && GET_CODE (XEXP (operands[0], 0)) == POST_INC)
747: return \"clr%.b %0\;mov%.b %1,%0\";
748: else
749: {
750: output_asm_insn (\"clr%.b %0\", operands);
751: operands[0] = adj_offsettable_operand (operands[0], 1);
752: return \"mov%.b %1,%0\";
753: }
754: }")
755:
756: (define_insn ""
757: [(set (match_operand:SI 0 "general_operand" "=do<>")
758: (zero_extend:SI
759: (match_operand:QI 1 "nonimmediate_operand" "dm")))]
760: ""
761: "*
762: {
763: if (DATA_REG_P (operands[0]))
764: {
765: if (GET_CODE (operands[1]) == REG
766: && REGNO (operands[0]) == REGNO (operands[1]))
767: return \"and%.l %#0xFF,%0\";
768: if (reg_mentioned_p (operands[0], operands[1]))
769: return \"mov%.b %1,%0\;and%.l %#0xFF,%0\";
770: return \"clr%.l %0\;mov%.b %1,%0\";
771: }
772: else if (GET_CODE (operands[0]) == MEM
773: && GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)
774: {
775: operands[0] = XEXP (XEXP (operands[0], 0), 0);
776: return \"clr%.l %0@-\;mov%.b %1,%0@(3)\";
777: }
778: else if (GET_CODE (operands[0]) == MEM
779: && GET_CODE (XEXP (operands[0], 0)) == POST_INC)
780: {
781: operands[0] = XEXP (XEXP (operands[0], 0), 0);
782: return \"clr%.l %0@+\;mov%.b %1,%0@(-1)\";
783: }
784: else
785: {
786: output_asm_insn (\"clr%.l %0\", operands);
787: operands[0] = adj_offsettable_operand (operands[0], 3);
788: return \"mov%.b %1,%0\";
789: }
790: }")
791:
792: ;; sign extension instructions
793:
794: (define_insn "extendhisi2"
795: [(set (match_operand:SI 0 "general_operand" "=*d,a")
796: (sign_extend:SI
797: (match_operand:HI 1 "nonimmediate_operand" "0,rmn")))]
798: ""
799: "@
800: ext%.l %0
801: mov%.w %1,%0")
802:
803: (define_insn "extendqihi2"
804: [(set (match_operand:HI 0 "general_operand" "=d")
805: (sign_extend:HI
806: (match_operand:QI 1 "nonimmediate_operand" "0")))]
807: ""
808: "ext%.w %0")
809:
810: (define_insn "extendqisi2"
811: [(set (match_operand:SI 0 "general_operand" "=d")
812: (sign_extend:SI
813: (match_operand:QI 1 "nonimmediate_operand" "0")))]
814: "TARGET_68020"
815: "extb%.l %0")
816:
817: ;; Conversions between float and double.
818:
819: (define_insn "extendsfdf2"
820: [(set (match_operand:DF 0 "general_operand" "=f,m")
821: (float_extend:DF
822: (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
823: "TARGET_CE"
824: "fmovesd %1,%0")
825:
826: (define_insn "truncdfsf2"
827: [(set (match_operand:SF 0 "general_operand" "=f,m")
828: (float_truncate:SF
829: (match_operand:DF 1 "nonimmediate_operand" "fm,f")))]
830: "TARGET_CE"
831: "fmoveds %1,%0")
832:
833: ;; Conversion between fixed point and floating point.
834: ;; Note that among the fix-to-float insns
835: ;; the ones that start with SImode come first.
836: ;; That is so that an operand that is a CONST_INT
837: ;; (and therefore lacks a specific machine mode).
838: ;; will be recognized as SImode (which is always valid)
839: ;; rather than as QImode or HImode.
840:
841: (define_insn "floatsisf2"
842: [(set (match_operand:SF 0 "register_operand" "=f")
843: (float:SF (match_operand:SI 1 "nonimmediate_operand" "dm")))]
844: "TARGET_CE"
845: "fmovels %1,%0")
846:
847: (define_insn "floatsidf2"
848: [(set (match_operand:DF 0 "register_operand" "=f")
849: (float:DF (match_operand:SI 1 "nonimmediate_operand" "dm")))]
850: "TARGET_CE"
851: "fmoveld %1,%0")
852:
853: (define_insn "floathisf2"
854: [(set (match_operand:SF 0 "register_operand" "=f")
855: (float:SF (match_operand:HI 1 "nonimmediate_operand" "dm")))]
856: "TARGET_CE"
857: "fmovews %1,%0")
858:
859: (define_insn "floathidf2"
860: [(set (match_operand:DF 0 "register_operand" "=f")
861: (float:DF (match_operand:HI 1 "nonimmediate_operand" "dm")))]
862: "TARGET_CE"
863: "fmovewd %1,%0")
864:
865: (define_insn "floatqisf2"
866: [(set (match_operand:SF 0 "register_operand" "=f")
867: (float:SF (match_operand:QI 1 "nonimmediate_operand" "dm")))]
868: "TARGET_CE"
869: "fmovebs %1,%0")
870:
871: (define_insn "floatqidf2"
872: [(set (match_operand:DF 0 "register_operand" "=f")
873: (float:DF (match_operand:QI 1 "nonimmediate_operand" "dm")))]
874: "TARGET_CE"
875: "fmovebd %1,%0")
876:
877: ;; Float-to-fix conversion insns.
878:
879: (define_insn "fix_truncsfqi2"
880: [(set (match_operand:QI 0 "general_operand" "=dm")
881: (fix:QI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
882: "TARGET_CE"
883: "fmovesb %1,%0")
884:
885: (define_insn "fix_truncsfhi2"
886: [(set (match_operand:HI 0 "general_operand" "=dm")
887: (fix:HI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
888: "TARGET_CE"
889: "fmovesw %1,%0")
890:
891: (define_insn "fix_truncsfsi2"
892: [(set (match_operand:SI 0 "general_operand" "=dm")
893: (fix:SI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
894: "TARGET_CE"
895: "fmovesl %1,%0")
896:
897: (define_insn "fix_truncdfqi2"
898: [(set (match_operand:QI 0 "general_operand" "=dm")
899: (fix:QI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
900: "TARGET_CE"
901: "fmovedb %1,%0")
902:
903: (define_insn "fix_truncdfhi2"
904: [(set (match_operand:HI 0 "general_operand" "=dm")
905: (fix:HI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
906: "TARGET_CE"
907: "fmovedw %1,%0")
908:
909: (define_insn "fix_truncdfsi2"
910: [(set (match_operand:SI 0 "general_operand" "=dm")
911: (fix:SI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
912: "TARGET_CE"
913: "fmovedl %1,%0")
914:
915: ;; add instructions
916:
917: (define_insn "addsi3"
918: [(set (match_operand:SI 0 "general_operand" "=m,r,!a,!a")
919: (plus:SI (match_operand:SI 1 "general_operand" "%0,0,a,rJK")
920: (match_operand:SI 2 "general_operand" "dIKLs,mrIKLs,rJK,a")))]
921: ""
922: "*
923: {
924: if (! operands_match_p (operands[0], operands[1]))
925: {
926: if (!ADDRESS_REG_P (operands[1]))
927: {
928: rtx tmp = operands[1];
929:
930: operands[1] = operands[2];
931: operands[2] = tmp;
932: }
933:
934: /* These insns can result from reloads to access
935: stack slots over 64k from the frame pointer. */
936: if (GET_CODE (operands[2]) == CONST_INT
937: && INTVAL (operands[2]) + 0x8000 >= (unsigned) 0x10000)
938: return \"mov%.l %2,%0\;add%.l %1,%0\";
939: if (GET_CODE (operands[2]) == REG)
940: return \"lea %1@[%2:L:B],%0\";
941: else
942: return \"lea %1@(%c2),%0\";
943: }
944: if (GET_CODE (operands[2]) == CONST_INT)
945: {
946: if (INTVAL (operands[2]) > 0
947: && INTVAL (operands[2]) <= 8)
948: return (ADDRESS_REG_P (operands[0])
949: ? \"addq%.w %2,%0\"
950: : \"addq%.l %2,%0\");
951: if (INTVAL (operands[2]) < 0
952: && INTVAL (operands[2]) >= -8)
953: {
954: operands[2] = gen_rtx (CONST_INT, VOIDmode,
955: - INTVAL (operands[2]));
956: return (ADDRESS_REG_P (operands[0])
957: ? \"subq%.w %2,%0\"
958: : \"subq%.l %2,%0\");
959: }
960: if (ADDRESS_REG_P (operands[0])
961: && INTVAL (operands[2]) >= -0x8000
962: && INTVAL (operands[2]) < 0x8000)
963: return \"add%.w %2,%0\";
964: }
965: return \"add%.l %2,%0\";
966: }")
967:
968: (define_insn ""
969: [(set (match_operand:SI 0 "general_operand" "=a")
970: (plus:SI (match_operand:SI 1 "general_operand" "0")
971: (sign_extend:SI (match_operand:HI 2 "nonimmediate_operand" "rmn"))))]
972: ""
973: "add%.w %2,%0")
974:
975: (define_insn "addhi3"
976: [(set (match_operand:HI 0 "general_operand" "=mr,mr,m,r")
977: (plus:HI (match_operand:HI 1 "general_operand" "%0,0,0,0")
978: (match_operand:HI 2 "general_operand" "I,L,dn,rmn")))]
979: ""
980: "@
981: addq%.w %2,%0
982: subq%.w #%n2,%0
983: add%.w %2,%0
984: add%.w %2,%0")
985:
986: (define_insn ""
987: [(set (strict_low_part (match_operand:HI 0 "general_operand" "+m,d"))
988: (plus:HI (match_dup 0)
989: (match_operand:HI 1 "general_operand" "dn,rmn")))]
990: ""
991: "add%.w %1,%0")
992:
993: (define_insn "addqi3"
994: [(set (match_operand:QI 0 "general_operand" "=md,mr,m,d")
995: (plus:QI (match_operand:QI 1 "general_operand" "%0,0,0,0")
996: (match_operand:QI 2 "general_operand" "I,L,dn,dmn")))]
997: ""
998: "@
999: addq%.b %2,%0
1000: subq%.b #%n2,%0
1001: add%.b %2,%0
1002: add%.b %2,%0")
1003:
1004: (define_insn ""
1005: [(set (strict_low_part (match_operand:QI 0 "general_operand" "+m,d"))
1006: (plus:QI (match_dup 0)
1007: (match_operand:QI 1 "general_operand" "dn,dmn")))]
1008: ""
1009: "add%.b %1,%0")
1010:
1011: (define_insn "adddf3"
1012: [(set (match_operand:DF 0 "register_operand" "=f")
1013: (plus:DF (match_operand:DF 1 "nonimmediate_operand" "%f")
1014: (match_operand:DF 2 "nonimmediate_operand" "fm")))]
1015: "TARGET_CE"
1016: "fadd%.d %2,%1,%0")
1017:
1018: (define_insn "addsf3"
1019: [(set (match_operand:SF 0 "register_operand" "=f")
1020: (plus:SF (match_operand:SF 1 "nonimmediate_operand" "%f")
1021: (match_operand:SF 2 "nonimmediate_operand" "fm")))]
1022: "TARGET_CE"
1023: "fadd%.s %2,%1,%0")
1024:
1025: ;; subtract instructions
1026:
1027: (define_insn "subsi3"
1028: [(set (match_operand:SI 0 "general_operand" "=m,r,!a,?d")
1029: (minus:SI (match_operand:SI 1 "general_operand" "0,0,a,mrIKs")
1030: (match_operand:SI 2 "general_operand" "dIKs,mrIKs,J,0")))]
1031: ""
1032: "*
1033: {
1034: if (! operands_match_p (operands[0], operands[1]))
1035: {
1036: if (operands_match_p (operands[0], operands[2]))
1037: {
1038: if (GET_CODE (operands[1]) == CONST_INT)
1039: {
1040: if (INTVAL (operands[1]) > 0
1041: && INTVAL (operands[1]) <= 8)
1042: return \"subq%.l %1,%0\;neg%.l %0\";
1043: }
1044: return \"sub%.l %1,%0\;neg%.l %0\";
1045: }
1046: /* This case is matched by J, but negating -0x8000
1047: in an lea would give an invalid displacement.
1048: So do this specially. */
1049: if (INTVAL (operands[2]) == -0x8000)
1050: return \"mov%.l %1,%0\;sub%.l %2,%0\";
1051: return \"lea %1@(%n2),%0\";
1052: }
1053: if (GET_CODE (operands[2]) == CONST_INT)
1054: {
1055: if (INTVAL (operands[2]) > 0
1056: && INTVAL (operands[2]) <= 8)
1057: return \"subq%.l %2,%0\";
1058: if (ADDRESS_REG_P (operands[0])
1059: && INTVAL (operands[2]) >= -0x8000
1060: && INTVAL (operands[2]) < 0x8000)
1061: return \"sub%.w %2,%0\";
1062: }
1063: return \"sub%.l %2,%0\";
1064: }")
1065:
1066: (define_insn ""
1067: [(set (match_operand:SI 0 "general_operand" "=a")
1068: (minus:SI (match_operand:SI 1 "general_operand" "0")
1069: (sign_extend:SI (match_operand:HI 2 "nonimmediate_operand" "rmn"))))]
1070: ""
1071: "sub%.w %2,%0")
1072:
1073: (define_insn "subhi3"
1074: [(set (match_operand:HI 0 "general_operand" "=m,r")
1075: (minus:HI (match_operand:HI 1 "general_operand" "0,0")
1076: (match_operand:HI 2 "general_operand" "dn,rmn")))]
1077: ""
1078: "sub%.w %2,%0")
1079:
1080: (define_insn ""
1081: [(set (strict_low_part (match_operand:HI 0 "general_operand" "+m,d"))
1082: (minus:HI (match_dup 0)
1083: (match_operand:HI 1 "general_operand" "dn,rmn")))]
1084: ""
1085: "sub%.w %1,%0")
1086:
1087: (define_insn "subqi3"
1088: [(set (match_operand:QI 0 "general_operand" "=m,d")
1089: (minus:QI (match_operand:QI 1 "general_operand" "0,0")
1090: (match_operand:QI 2 "general_operand" "dn,dmn")))]
1091: ""
1092: "sub%.b %2,%0")
1093:
1094: (define_insn ""
1095: [(set (strict_low_part (match_operand:QI 0 "general_operand" "+m,d"))
1096: (minus:QI (match_dup 0)
1097: (match_operand:QI 1 "general_operand" "dn,dmn")))]
1098: ""
1099: "sub%.b %1,%0")
1100:
1101: (define_insn "subdf3"
1102: [(set (match_operand:DF 0 "register_operand" "=f,f,f")
1103: (minus:DF (match_operand:DF 1 "nonimmediate_operand" "f,f,m")
1104: (match_operand:DF 2 "nonimmediate_operand" "f,m,f")))]
1105: "TARGET_CE"
1106: "@
1107: fsub%.d %2,%1,%0
1108: fsub%.d %2,%1,%0
1109: frsub%.d %1,%2,%0")
1110:
1111: (define_insn "subsf3"
1112: [(set (match_operand:SF 0 "register_operand" "=f,f,f")
1113: (minus:SF (match_operand:SF 1 "nonimmediate_operand" "f,f,m")
1114: (match_operand:SF 2 "nonimmediate_operand" "f,m,f")))]
1115: "TARGET_CE"
1116: "@
1117: fsub%.s %2,%1,%0
1118: fsub%.s %2,%1,%0
1119: frsub%.s %1,%2,%0")
1120:
1121: ;; multiply instructions
1122:
1123: (define_insn "mulhi3"
1124: [(set (match_operand:HI 0 "general_operand" "=d")
1125: (mult:HI (match_operand:HI 1 "general_operand" "%0")
1126: (match_operand:HI 2 "general_operand" "dmn")))]
1127: ""
1128: "muls %2,%0")
1129:
1130: (define_insn "mulhisi3"
1131: [(set (match_operand:SI 0 "general_operand" "=d")
1132: (mult:SI (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "%0"))
1133: (sign_extend:SI (match_operand:HI 2 "nonimmediate_operand" "dm"))))]
1134: ""
1135: "muls %2,%0")
1136:
1137: (define_insn ""
1138: [(set (match_operand:SI 0 "general_operand" "=d")
1139: (mult:SI (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "%0"))
1140: (match_operand:SI 2 "const_int_operand" "n")))]
1141: ""
1142: "muls %2,%0")
1143:
1144: (define_insn "mulsi3"
1145: [(set (match_operand:SI 0 "general_operand" "=d")
1146: (mult:SI (match_operand:SI 1 "general_operand" "%0")
1147: (match_operand:SI 2 "general_operand" "dmsK")))]
1148: "TARGET_68020"
1149: "muls%.l %2,%0")
1150:
1151: (define_insn "umulhisi3"
1152: [(set (match_operand:SI 0 "general_operand" "=d")
1153: (mult:SI (zero_extend:SI
1154: (match_operand:HI 1 "nonimmediate_operand" "%0"))
1155: (zero_extend:SI
1156: (match_operand:HI 2 "nonimmediate_operand" "dm"))))]
1157: ""
1158: "mulu %2,%0")
1159:
1160: (define_insn ""
1161: [(set (match_operand:SI 0 "general_operand" "=d")
1162: (mult:SI (zero_extend:SI
1163: (match_operand:HI 1 "nonimmediate_operand" "%0"))
1164: (match_operand:SI 2 "const_int_operand" "n")))]
1165: ""
1166: "mulu %2,%0")
1167:
1168: (define_insn "muldf3"
1169: [(set (match_operand:DF 0 "register_operand" "=f")
1170: (mult:DF (match_operand:DF 1 "nonimmediate_operand" "%f")
1171: (match_operand:DF 2 "nonimmediate_operand" "fm")))]
1172: "TARGET_CE"
1173: "fmul%.d %2,%1,%0")
1174:
1175: (define_insn "mulsf3"
1176: [(set (match_operand:SF 0 "register_operand" "=f")
1177: (mult:SF (match_operand:SF 1 "nonimmediate_operand" "%f")
1178: (match_operand:SF 2 "nonimmediate_operand" "fm")))]
1179: "TARGET_CE"
1180: "fmul%.s %2,%1,%0")
1181:
1182: ;; divide instructions
1183:
1184: (define_insn "divhi3"
1185: [(set (match_operand:HI 0 "general_operand" "=d")
1186: (div:HI (match_operand:HI 1 "general_operand" "0")
1187: (match_operand:HI 2 "general_operand" "dmn")))]
1188: ""
1189: "extl %0\;divs %2,%0")
1190:
1191: (define_insn "divhisi3"
1192: [(set (match_operand:HI 0 "general_operand" "=d")
1193: (truncate:HI
1194: (div:SI
1195: (match_operand:SI 1 "general_operand" "0")
1196: (sign_extend:SI (match_operand:HI 2 "nonimmediate_operand" "dm")))))]
1197: ""
1198: "divs %2,%0")
1199:
1200: (define_insn ""
1201: [(set (match_operand:HI 0 "general_operand" "=d")
1202: (truncate:HI (div:SI (match_operand:SI 1 "general_operand" "0")
1203: (match_operand:SI 2 "const_int_operand" "n"))))]
1204: ""
1205: "divs %2,%0")
1206:
1207: (define_insn "divsi3"
1208: [(set (match_operand:SI 0 "general_operand" "=d")
1209: (div:SI (match_operand:SI 1 "general_operand" "0")
1210: (match_operand:SI 2 "general_operand" "dmsK")))]
1211: "TARGET_68020"
1212: "divs%.l %2,%0,%0")
1213:
1214: (define_insn "udivhi3"
1215: [(set (match_operand:HI 0 "general_operand" "=d")
1216: (udiv:HI (match_operand:HI 1 "general_operand" "0")
1217: (match_operand:HI 2 "general_operand" "dmn")))]
1218: ""
1219: "and%.l %#0xFFFF,%0\;divu %2,%0")
1220:
1221: (define_insn "udivhisi3"
1222: [(set (match_operand:HI 0 "general_operand" "=d")
1223: (truncate:HI
1224: (udiv:SI
1225: (match_operand:SI 1 "general_operand" "0")
1226: (zero_extend:SI (match_operand:HI 2 "nonimmediate_operand" "dm")))))]
1227: ""
1228: "divu %2,%0")
1229:
1230: (define_insn ""
1231: [(set (match_operand:HI 0 "general_operand" "=d")
1232: (truncate:HI (udiv:SI (match_operand:SI 1 "nonimmediate_operand" "0")
1233: (match_operand:HI 2 "const_int_operand" "n"))))]
1234: ""
1235: "divu %2,%0")
1236:
1237: (define_insn "udivsi3"
1238: [(set (match_operand:SI 0 "general_operand" "=d")
1239: (udiv:SI (match_operand:SI 1 "general_operand" "0")
1240: (match_operand:SI 2 "general_operand" "dmsK")))]
1241: "TARGET_68020"
1242: "divu%.l %2,%0,%0")
1243:
1244: (define_insn "divdf3"
1245: [(set (match_operand:DF 0 "register_operand" "=f,f,f")
1246: (div:DF (match_operand:DF 1 "nonimmediate_operand" "f,f,m")
1247: (match_operand:DF 2 "nonimmediate_operand" "f,m,f")))]
1248: "TARGET_CE"
1249: "@
1250: fdiv%.d %2,%1,%0
1251: fdiv%.d %2,%1,%0
1252: frdiv%.d %1,%2,%0")
1253:
1254: (define_insn "divsf3"
1255: [(set (match_operand:SF 0 "register_operand" "=f,f,f")
1256: (div:SF (match_operand:SF 1 "nonimmediate_operand" "f,f,m")
1257: (match_operand:SF 2 "nonimmediate_operand" "f,m,f")))]
1258: "TARGET_CE"
1259: "@
1260: fdiv%.s %2,%1,%0
1261: fdiv%.s %2,%1,%0
1262: frdiv%.s %1,%2,%0")
1263:
1264: ;; Remainder instructions.
1265:
1266: (define_insn "modhi3"
1267: [(set (match_operand:HI 0 "general_operand" "=d")
1268: (mod:HI (match_operand:HI 1 "general_operand" "0")
1269: (match_operand:HI 2 "general_operand" "dmn")))]
1270: ""
1271: "extl %0\;divs %2,%0\;swap %0")
1272:
1273: (define_insn "modhisi3"
1274: [(set (match_operand:HI 0 "general_operand" "=d")
1275: (truncate:HI
1276: (mod:SI
1277: (match_operand:SI 1 "general_operand" "0")
1278: (sign_extend:SI (match_operand:HI 2 "nonimmediate_operand" "dm")))))]
1279: ""
1280: "divs %2,%0\;swap %0")
1281:
1282: (define_insn ""
1283: [(set (match_operand:HI 0 "general_operand" "=d")
1284: (truncate:HI (mod:SI (match_operand:SI 1 "general_operand" "0")
1285: (match_operand:SI 2 "const_int_operand" "n"))))]
1286: ""
1287: "divs %2,%0\;swap %0")
1288:
1289: (define_insn "umodhi3"
1290: [(set (match_operand:HI 0 "general_operand" "=d")
1291: (umod:HI (match_operand:HI 1 "general_operand" "0")
1292: (match_operand:HI 2 "general_operand" "dmn")))]
1293: ""
1294: "and%.l %#0xFFFF,%0\;divu %2,%0\;swap %0")
1295:
1296: (define_insn "umodhisi3"
1297: [(set (match_operand:HI 0 "general_operand" "=d")
1298: (truncate:HI
1299: (umod:SI
1300: (match_operand:SI 1 "general_operand" "0")
1301: (zero_extend:SI (match_operand:HI 2 "nonimmediate_operand" "dm")))))]
1302: ""
1303: "divu %2,%0\;swap %0")
1304:
1305: (define_insn ""
1306: [(set (match_operand:HI 0 "general_operand" "=d")
1307: (truncate:HI (umod:SI (match_operand:SI 1 "general_operand" "0")
1308: (match_operand:SI 2 "const_int_operand" "n"))))]
1309: ""
1310: "divu %2,%0\;swap %0")
1311:
1312: (define_insn "divmodsi4"
1313: [(set (match_operand:SI 0 "general_operand" "=d")
1314: (div:SI (match_operand:SI 1 "general_operand" "0")
1315: (match_operand:SI 2 "general_operand" "dmsK")))
1316: (set (match_operand:SI 3 "general_operand" "=d")
1317: (mod:SI (match_dup 1) (match_dup 2)))]
1318: "TARGET_68020"
1319: "divs%.l %2,%0,%3")
1320:
1321: (define_insn "udivmodsi4"
1322: [(set (match_operand:SI 0 "general_operand" "=d")
1323: (udiv:SI (match_operand:SI 1 "general_operand" "0")
1324: (match_operand:SI 2 "general_operand" "dmsK")))
1325: (set (match_operand:SI 3 "general_operand" "=d")
1326: (umod:SI (match_dup 1) (match_dup 2)))]
1327: "TARGET_68020"
1328: "divu%.l %2,%0,%3")
1329:
1330: ;; logical-and instructions
1331:
1332: (define_insn "andsi3"
1333: [(set (match_operand:SI 0 "general_operand" "=m,d")
1334: (and:SI (match_operand:SI 1 "general_operand" "%0,0")
1335: (match_operand:SI 2 "general_operand" "dKs,dmKs")))]
1336: ""
1337: "*
1338: {
1339: if (GET_CODE (operands[2]) == CONST_INT
1340: && (INTVAL (operands[2]) | 0xffff) == 0xffffffff
1341: && (DATA_REG_P (operands[0])
1342: || offsettable_memref_p (operands[0])))
1343: {
1344: if (GET_CODE (operands[0]) != REG)
1345: operands[0] = adj_offsettable_operand (operands[0], 2);
1346: operands[2] = gen_rtx (CONST_INT, VOIDmode,
1347: INTVAL (operands[2]) & 0xffff);
1348: /* Do not delete a following tstl %0 insn; that would be incorrect. */
1349: CC_STATUS_INIT;
1350: if (operands[2] == const0_rtx)
1351: return \"clr%.w %0\";
1352: return \"and%.w %2,%0\";
1353: }
1354: return \"and%.l %2,%0\";
1355: }")
1356:
1357: (define_insn "andhi3"
1358: [(set (match_operand:HI 0 "general_operand" "=m,d")
1359: (and:HI (match_operand:HI 1 "general_operand" "%0,0")
1360: (match_operand:HI 2 "general_operand" "dn,dmn")))]
1361: ""
1362: "and%.w %2,%0")
1363:
1364: (define_insn "andqi3"
1365: [(set (match_operand:QI 0 "general_operand" "=m,d")
1366: (and:QI (match_operand:QI 1 "general_operand" "%0,0")
1367: (match_operand:QI 2 "general_operand" "dn,dmn")))]
1368: ""
1369: "and%.b %2,%0")
1370:
1371:
1372: ;; inclusive-or instructions
1373:
1374: (define_insn "iorsi3"
1375: [(set (match_operand:SI 0 "general_operand" "=m,d")
1376: (ior:SI (match_operand:SI 1 "general_operand" "%0,0")
1377: (match_operand:SI 2 "general_operand" "dKs,dmKs")))]
1378: ""
1379: "*
1380: {
1381: register int logval;
1382: if (GET_CODE (operands[2]) == CONST_INT
1383: && INTVAL (operands[2]) >> 16 == 0
1384: && (DATA_REG_P (operands[0])
1385: || offsettable_memref_p (operands[0])))
1386: {
1387: if (GET_CODE (operands[0]) != REG)
1388: operands[0] = adj_offsettable_operand (operands[0], 2);
1389: /* Do not delete a following tstl %0 insn; that would be incorrect. */
1390: CC_STATUS_INIT;
1391: return \"or%.w %2,%0\";
1392: }
1393: if (GET_CODE (operands[2]) == CONST_INT
1394: && (logval = exact_log2 (INTVAL (operands[2]))) >= 0
1395: && (DATA_REG_P (operands[0])
1396: || offsettable_memref_p (operands[0])))
1397: {
1398: if (DATA_REG_P (operands[0]))
1399: operands[1] = gen_rtx (CONST_INT, VOIDmode, logval);
1400: else
1401: {
1402: operands[0] = adj_offsettable_operand (operands[0], 3 - (logval / 8));
1403: operands[1] = gen_rtx (CONST_INT, VOIDmode, logval % 8);
1404: }
1405: return \"bset %1,%0\";
1406: }
1407: return \"or%.l %2,%0\";
1408: }")
1409:
1410: (define_insn "iorhi3"
1411: [(set (match_operand:HI 0 "general_operand" "=m,d")
1412: (ior:HI (match_operand:HI 1 "general_operand" "%0,0")
1413: (match_operand:HI 2 "general_operand" "dn,dmn")))]
1414: ""
1415: "or%.w %2,%0")
1416:
1417: (define_insn "iorqi3"
1418: [(set (match_operand:QI 0 "general_operand" "=m,d")
1419: (ior:QI (match_operand:QI 1 "general_operand" "%0,0")
1420: (match_operand:QI 2 "general_operand" "dn,dmn")))]
1421: ""
1422: "or%.b %2,%0")
1423:
1424: ;; xor instructions
1425:
1426: (define_insn "xorsi3"
1427: [(set (match_operand:SI 0 "general_operand" "=do,m")
1428: (xor:SI (match_operand:SI 1 "general_operand" "%0,0")
1429: (match_operand:SI 2 "general_operand" "di,dKs")))]
1430: ""
1431: "*
1432: {
1433: if (GET_CODE (operands[2]) == CONST_INT
1434: && INTVAL (operands[2]) >> 16 == 0
1435: && (offsettable_memref_p (operands[0]) || DATA_REG_P (operands[0])))
1436: {
1437: if (! DATA_REG_P (operands[0]))
1438: operands[0] = adj_offsettable_operand (operands[0], 2);
1439: /* Do not delete a following tstl %0 insn; that would be incorrect. */
1440: CC_STATUS_INIT;
1441: return \"eor%.w %2,%0\";
1442: }
1443: return \"eor%.l %2,%0\";
1444: }")
1445:
1446: (define_insn "xorhi3"
1447: [(set (match_operand:HI 0 "general_operand" "=dm")
1448: (xor:HI (match_operand:HI 1 "general_operand" "%0")
1449: (match_operand:HI 2 "general_operand" "dn")))]
1450: ""
1451: "eor%.w %2,%0")
1452:
1453: (define_insn "xorqi3"
1454: [(set (match_operand:QI 0 "general_operand" "=dm")
1455: (xor:QI (match_operand:QI 1 "general_operand" "%0")
1456: (match_operand:QI 2 "general_operand" "dn")))]
1457: ""
1458: "eor%.b %2,%0")
1459:
1460: ;; negation instructions
1461:
1462: (define_insn "negsi2"
1463: [(set (match_operand:SI 0 "general_operand" "=dm")
1464: (neg:SI (match_operand:SI 1 "general_operand" "0")))]
1465: ""
1466: "neg%.l %0")
1467:
1468: (define_insn "neghi2"
1469: [(set (match_operand:HI 0 "general_operand" "=dm")
1470: (neg:HI (match_operand:HI 1 "general_operand" "0")))]
1471: ""
1472: "neg%.w %0")
1473:
1474: (define_insn "negqi2"
1475: [(set (match_operand:QI 0 "general_operand" "=dm")
1476: (neg:QI (match_operand:QI 1 "general_operand" "0")))]
1477: ""
1478: "neg%.b %0")
1479:
1480: (define_insn "negsf2"
1481: [(set (match_operand:SF 0 "register_operand" "=f")
1482: (neg:SF (match_operand:SF 1 "nonimmediate_operand" "fm")))]
1483: "TARGET_CE"
1484: "fneg%.s %1,%0")
1485:
1486: (define_insn "negdf2"
1487: [(set (match_operand:DF 0 "register_operand" "=f")
1488: (neg:DF (match_operand:DF 1 "nonimmediate_operand" "fm")))]
1489: "TARGET_CE"
1490: "fneg%.d %1,%0")
1491:
1492: ;; Absolute value instructions
1493:
1494: (define_insn "abssf2"
1495: [(set (match_operand:SF 0 "register_operand" "=f")
1496: (abs:SF (match_operand:SF 1 "nonimmediate_operand" "fm")))]
1497: "TARGET_CE"
1498: "fabs%.s %1,%0")
1499:
1500: (define_insn "absdf2"
1501: [(set (match_operand:DF 0 "register_operand" "=f")
1502: (abs:DF (match_operand:DF 1 "nonimmediate_operand" "fm")))]
1503: "TARGET_CE"
1504: "fabs%.d %1,%0")
1505:
1506: ;; Square root instructions
1507:
1508: (define_insn "sqrtsf2"
1509: [(set (match_operand:SF 0 "register_operand" "=f")
1510: (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "fm")))]
1511: "TARGET_CE"
1512: "fsqrt%.s %1,%0")
1513:
1514: (define_insn "sqrtdf2"
1515: [(set (match_operand:DF 0 "register_operand" "=f")
1516: (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "fm")))]
1517: "TARGET_CE"
1518: "fsqrt%.d %1,%0")
1519:
1520: ;; one complement instructions
1521:
1522: (define_insn "one_cmplsi2"
1523: [(set (match_operand:SI 0 "general_operand" "=dm")
1524: (not:SI (match_operand:SI 1 "general_operand" "0")))]
1525: ""
1526: "not%.l %0")
1527:
1528: (define_insn "one_cmplhi2"
1529: [(set (match_operand:HI 0 "general_operand" "=dm")
1530: (not:HI (match_operand:HI 1 "general_operand" "0")))]
1531: ""
1532: "not%.w %0")
1533:
1534: (define_insn "one_cmplqi2"
1535: [(set (match_operand:QI 0 "general_operand" "=dm")
1536: (not:QI (match_operand:QI 1 "general_operand" "0")))]
1537: ""
1538: "not%.b %0")
1539:
1540:
1541: ;; arithmetic shift instructions
1542: ;; We don't need the shift memory by 1 bit instruction
1543:
1544: (define_insn "ashlsi3"
1545: [(set (match_operand:SI 0 "general_operand" "=d")
1546: (ashift:SI (match_operand:SI 1 "general_operand" "0")
1547: (match_operand:SI 2 "general_operand" "dI")))]
1548: ""
1549: "asl%.l %2,%0")
1550:
1551: (define_insn "ashlhi3"
1552: [(set (match_operand:HI 0 "general_operand" "=d")
1553: (ashift:HI (match_operand:HI 1 "general_operand" "0")
1554: (match_operand:HI 2 "general_operand" "dI")))]
1555: ""
1556: "asl%.w %2,%0")
1557:
1558: (define_insn "ashlqi3"
1559: [(set (match_operand:QI 0 "general_operand" "=d")
1560: (ashift:QI (match_operand:QI 1 "general_operand" "0")
1561: (match_operand:QI 2 "general_operand" "dI")))]
1562: ""
1563: "asl%.b %2,%0")
1564:
1565: (define_insn "ashrsi3"
1566: [(set (match_operand:SI 0 "general_operand" "=d")
1567: (ashiftrt:SI (match_operand:SI 1 "general_operand" "0")
1568: (match_operand:SI 2 "general_operand" "dI")))]
1569: ""
1570: "asr%.l %2,%0")
1571:
1572: (define_insn "ashrhi3"
1573: [(set (match_operand:HI 0 "general_operand" "=d")
1574: (ashiftrt:HI (match_operand:HI 1 "general_operand" "0")
1575: (match_operand:HI 2 "general_operand" "dI")))]
1576: ""
1577: "asr%.w %2,%0")
1578:
1579: (define_insn "ashrqi3"
1580: [(set (match_operand:QI 0 "general_operand" "=d")
1581: (ashiftrt:QI (match_operand:QI 1 "general_operand" "0")
1582: (match_operand:QI 2 "general_operand" "dI")))]
1583: ""
1584: "asr%.b %2,%0")
1585:
1586: ;; logical shift instructions
1587:
1588: (define_insn "lshrsi3"
1589: [(set (match_operand:SI 0 "general_operand" "=d")
1590: (lshiftrt:SI (match_operand:SI 1 "general_operand" "0")
1591: (match_operand:SI 2 "general_operand" "dI")))]
1592: ""
1593: "lsr%.l %2,%0")
1594:
1595: (define_insn "lshrhi3"
1596: [(set (match_operand:HI 0 "general_operand" "=d")
1597: (lshiftrt:HI (match_operand:HI 1 "general_operand" "0")
1598: (match_operand:HI 2 "general_operand" "dI")))]
1599: ""
1600: "lsr%.w %2,%0")
1601:
1602: (define_insn "lshrqi3"
1603: [(set (match_operand:QI 0 "general_operand" "=d")
1604: (lshiftrt:QI (match_operand:QI 1 "general_operand" "0")
1605: (match_operand:QI 2 "general_operand" "dI")))]
1606: ""
1607: "lsr%.b %2,%0")
1608:
1609: ;; rotate instructions
1610:
1611: (define_insn "rotlsi3"
1612: [(set (match_operand:SI 0 "general_operand" "=d")
1613: (rotate:SI (match_operand:SI 1 "general_operand" "0")
1614: (match_operand:SI 2 "general_operand" "dI")))]
1615: ""
1616: "rol%.l %2,%0")
1617:
1618: (define_insn "rotlhi3"
1619: [(set (match_operand:HI 0 "general_operand" "=d")
1620: (rotate:HI (match_operand:HI 1 "general_operand" "0")
1621: (match_operand:HI 2 "general_operand" "dI")))]
1622: ""
1623: "rol%.w %2,%0")
1624:
1625: (define_insn "rotlqi3"
1626: [(set (match_operand:QI 0 "general_operand" "=d")
1627: (rotate:QI (match_operand:QI 1 "general_operand" "0")
1628: (match_operand:QI 2 "general_operand" "dI")))]
1629: ""
1630: "rol%.b %2,%0")
1631:
1632: (define_insn "rotrsi3"
1633: [(set (match_operand:SI 0 "general_operand" "=d")
1634: (rotatert:SI (match_operand:SI 1 "general_operand" "0")
1635: (match_operand:SI 2 "general_operand" "dI")))]
1636: ""
1637: "ror%.l %2,%0")
1638:
1639: (define_insn "rotrhi3"
1640: [(set (match_operand:HI 0 "general_operand" "=d")
1641: (rotatert:HI (match_operand:HI 1 "general_operand" "0")
1642: (match_operand:HI 2 "general_operand" "dI")))]
1643: ""
1644: "ror%.w %2,%0")
1645:
1646: (define_insn "rotrqi3"
1647: [(set (match_operand:QI 0 "general_operand" "=d")
1648: (rotatert:QI (match_operand:QI 1 "general_operand" "0")
1649: (match_operand:QI 2 "general_operand" "dI")))]
1650: ""
1651: "ror%.b %2,%0")
1652:
1653: ;; Special cases of bit-field insns which we should
1654: ;; recognize in preference to the general case.
1655: ;; These handle aligned 8-bit and 16-bit fields,
1656: ;; which can usually be done with move instructions.
1657:
1658: (define_insn ""
1659: [(set (zero_extract:SI (match_operand:SI 0 "nonimmediate_operand" "+do")
1660: (match_operand:SI 1 "const_int_operand" "i")
1661: (match_operand:SI 2 "const_int_operand" "i"))
1662: (match_operand:SI 3 "general_operand" "d"))]
1663: "TARGET_68020 && TARGET_BITFIELD
1664: && (INTVAL (operands[1]) == 8 || INTVAL (operands[1]) == 16)
1665: && INTVAL (operands[2]) % INTVAL (operands[1]) == 0
1666: && (GET_CODE (operands[0]) == REG
1667: || ! mode_dependent_address_p (XEXP (operands[0], 0)))"
1668: "*
1669: {
1670: if (REG_P (operands[0]))
1671: {
1672: if (INTVAL (operands[1]) + INTVAL (operands[2]) != 32)
1673: return \"bfins %3,[%c2,%c1]%0\";
1674: }
1675: else
1676: operands[0]
1677: = adj_offsettable_operand (operands[0], INTVAL (operands[2]) / 8);
1678:
1679: if (GET_CODE (operands[3]) == MEM)
1680: operands[3] = adj_offsettable_operand (operands[3],
1681: (32 - INTVAL (operands[1])) / 8);
1682: if (INTVAL (operands[1]) == 8)
1683: return \"mov%.b %3,%0\";
1684: return \"mov%.w %3,%0\";
1685: }")
1686:
1687: (define_insn ""
1688: [(set (match_operand:SI 0 "general_operand" "=&d")
1689: (zero_extract:SI (match_operand:SI 1 "nonimmediate_operand" "do")
1690: (match_operand:SI 2 "const_int_operand" "i")
1691: (match_operand:SI 3 "const_int_operand" "i")))]
1692: "TARGET_68020 && TARGET_BITFIELD
1693: && (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
1694: && INTVAL (operands[3]) % INTVAL (operands[2]) == 0
1695: && (GET_CODE (operands[1]) == REG
1696: || ! mode_dependent_address_p (XEXP (operands[1], 0)))"
1697: "*
1698: {
1699: if (REG_P (operands[1]))
1700: {
1701: if (INTVAL (operands[2]) + INTVAL (operands[3]) != 32)
1702: return \"bfextu [%c3,%c2]%1,%0\";
1703: }
1704: else
1705: operands[1]
1706: = adj_offsettable_operand (operands[1], INTVAL (operands[3]) / 8);
1707:
1708: output_asm_insn (\"clrl %0\", operands);
1709: if (GET_CODE (operands[0]) == MEM)
1710: operands[0] = adj_offsettable_operand (operands[0],
1711: (32 - INTVAL (operands[1])) / 8);
1712: if (INTVAL (operands[2]) == 8)
1713: return \"mov%.b %1,%0\";
1714: return \"mov%.w %1,%0\";
1715: }")
1716:
1717: (define_insn ""
1718: [(set (match_operand:SI 0 "general_operand" "=d")
1719: (sign_extract:SI (match_operand:SI 1 "nonimmediate_operand" "do")
1720: (match_operand:SI 2 "const_int_operand" "i")
1721: (match_operand:SI 3 "const_int_operand" "i")))]
1722: "TARGET_68020 && TARGET_BITFIELD
1723: && (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
1724: && INTVAL (operands[3]) % INTVAL (operands[2]) == 0
1725: && (GET_CODE (operands[1]) == REG
1726: || ! mode_dependent_address_p (XEXP (operands[1], 0)))"
1727: "*
1728: {
1729: if (REG_P (operands[1]))
1730: {
1731: if (INTVAL (operands[2]) + INTVAL (operands[3]) != 32)
1732: return \"bfexts [%c3,%c2]%1,%0\";
1733: }
1734: else
1735: operands[1]
1736: = adj_offsettable_operand (operands[1], INTVAL (operands[3]) / 8);
1737:
1738: if (INTVAL (operands[2]) == 8)
1739: return \"mov%.b %1,%0\;extb%.l %0\";
1740: return \"mov%.w %1,%0\;ext%.l %0\";
1741: }")
1742:
1743: ;; Bit field instructions, general cases.
1744: ;; "o,d" constraint causes a nonoffsettable memref to match the "o"
1745: ;; so that its address is reloaded.
1746:
1747: (define_insn "extv"
1748: [(set (match_operand:SI 0 "general_operand" "=d,d")
1749: (sign_extract:SI (match_operand:QI 1 "nonimmediate_operand" "o,d")
1750: (match_operand:SI 2 "general_operand" "di,di")
1751: (match_operand:SI 3 "general_operand" "di,di")))]
1752: "TARGET_68020 && TARGET_BITFIELD"
1753: "bfexts [%c3,%c2]%1,%0")
1754:
1755: (define_insn "extzv"
1756: [(set (match_operand:SI 0 "general_operand" "=d,d")
1757: (zero_extract:SI (match_operand:QI 1 "nonimmediate_operand" "o,d")
1758: (match_operand:SI 2 "general_operand" "di,di")
1759: (match_operand:SI 3 "general_operand" "di,di")))]
1760: "TARGET_68020 && TARGET_BITFIELD"
1761: "bfextu [%c3,%c2]%1,%0")
1762:
1763: (define_insn ""
1764: [(set (zero_extract:SI (match_operand:QI 0 "nonimmediate_operand" "+o,d")
1765: (match_operand:SI 1 "general_operand" "di,di")
1766: (match_operand:SI 2 "general_operand" "di,di"))
1767: (xor:SI (zero_extract:SI (match_dup 0) (match_dup 1) (match_dup 2))
1768: (match_operand:SI 3 "const_int_operand" "i,i")))]
1769: "TARGET_68020 && TARGET_BITFIELD
1770: && (INTVAL (operands[3]) == -1
1771: || (GET_CODE (operands[1]) == CONST_INT
1772: && (~ INTVAL (operands[3]) & ((1 << INTVAL (operands[1]))- 1)) == 0))"
1773: "*
1774: {
1775: CC_STATUS_INIT;
1776: return \"bfchg [%c2,%c1]%0\";
1777: }")
1778:
1779: (define_insn ""
1780: [(set (zero_extract:SI (match_operand:QI 0 "nonimmediate_operand" "+o,d")
1781: (match_operand:SI 1 "general_operand" "di,di")
1782: (match_operand:SI 2 "general_operand" "di,di"))
1783: (const_int 0))]
1784: "TARGET_68020 && TARGET_BITFIELD"
1785: "*
1786: {
1787: CC_STATUS_INIT;
1788: return \"bfclr [%c2,%c1]%0\";
1789: }")
1790:
1791: (define_insn ""
1792: [(set (zero_extract:SI (match_operand:QI 0 "nonimmediate_operand" "+o,d")
1793: (match_operand:SI 1 "general_operand" "di,di")
1794: (match_operand:SI 2 "general_operand" "di,di"))
1795: (const_int -1))]
1796: "TARGET_68020 && TARGET_BITFIELD"
1797: "*
1798: {
1799: CC_STATUS_INIT;
1800: return \"bfset [%c2,%c1]%0\";
1801: }")
1802:
1803: (define_insn "insv"
1804: [(set (zero_extract:SI (match_operand:QI 0 "nonimmediate_operand" "+o,d")
1805: (match_operand:SI 1 "general_operand" "di,di")
1806: (match_operand:SI 2 "general_operand" "di,di"))
1807: (match_operand:SI 3 "general_operand" "d,d"))]
1808: "TARGET_68020 && TARGET_BITFIELD"
1809: "bfins %3,[%c2,%c1]%0")
1810:
1811: ;; Now recognize bit field insns that operate on registers
1812: ;; (or at least were intended to do so).
1813:
1814: (define_insn ""
1815: [(set (match_operand:SI 0 "general_operand" "=d")
1816: (sign_extract:SI (match_operand:SI 1 "nonimmediate_operand" "d")
1817: (match_operand:SI 2 "general_operand" "di")
1818: (match_operand:SI 3 "general_operand" "di")))]
1819: "TARGET_68020 && TARGET_BITFIELD"
1820: "bfexts [%c3,%c2]%1,%0")
1821:
1822: (define_insn ""
1823: [(set (match_operand:SI 0 "general_operand" "=d")
1824: (zero_extract:SI (match_operand:SI 1 "nonimmediate_operand" "d")
1825: (match_operand:SI 2 "general_operand" "di")
1826: (match_operand:SI 3 "general_operand" "di")))]
1827: "TARGET_68020 && TARGET_BITFIELD"
1828: "bfextu [%c3,%c2]%1,%0")
1829:
1830: (define_insn ""
1831: [(set (zero_extract:SI (match_operand:SI 0 "nonimmediate_operand" "+d")
1832: (match_operand:SI 1 "general_operand" "di")
1833: (match_operand:SI 2 "general_operand" "di"))
1834: (const_int 0))]
1835: "TARGET_68020 && TARGET_BITFIELD"
1836: "*
1837: {
1838: CC_STATUS_INIT;
1839: return \"bfclr [%c2,%c1]%0\";
1840: }")
1841:
1842: (define_insn ""
1843: [(set (zero_extract:SI (match_operand:SI 0 "nonimmediate_operand" "+d")
1844: (match_operand:SI 1 "general_operand" "di")
1845: (match_operand:SI 2 "general_operand" "di"))
1846: (const_int -1))]
1847: "TARGET_68020 && TARGET_BITFIELD"
1848: "*
1849: {
1850: CC_STATUS_INIT;
1851: return \"bfset [%c2,%c1]%0\";
1852: }")
1853:
1854: (define_insn ""
1855: [(set (zero_extract:SI (match_operand:SI 0 "nonimmediate_operand" "+d")
1856: (match_operand:SI 1 "general_operand" "di")
1857: (match_operand:SI 2 "general_operand" "di"))
1858: (match_operand:SI 3 "general_operand" "d"))]
1859: "TARGET_68020 && TARGET_BITFIELD"
1860: "*
1861: {
1862: return \"bfins %3,[%c2,%c1]%0\";
1863: }")
1864:
1865: ;; Special patterns for optimizing bit-field instructions.
1866:
1867: (define_insn ""
1868: [(set (cc0)
1869: (zero_extract:SI (match_operand:QI 0 "memory_operand" "o")
1870: (match_operand:SI 1 "const_int_operand" "i")
1871: (match_operand:SI 2 "general_operand" "di")))]
1872: "TARGET_68020 && TARGET_BITFIELD"
1873: "*
1874: {
1875: if (operands[1] == const1_rtx
1876: && GET_CODE (operands[2]) == CONST_INT)
1877: {
1878: int width = GET_CODE (operands[0]) == REG ? 31 : 7;
1879: return output_btst (operands,
1880: gen_rtx (CONST_INT, VOIDmode,
1881: width - INTVAL (operands[2])),
1882: operands[0],
1883: insn, 1000);
1884: /* Pass 1000 as SIGNPOS argument so that btst will
1885: not think we are testing the sign bit for an `and'
1886: and assume that nonzero implies a negative result. */
1887: }
1888: if (INTVAL (operands[1]) != 32)
1889: cc_status.flags = CC_NOT_NEGATIVE;
1890: return \"bftst [%c2,%c1]%0\";
1891: }")
1892:
1893: ;;; now handle the register cases
1894: (define_insn ""
1895: [(set (cc0)
1896: (zero_extract:SI (match_operand:SI 0 "nonimmediate_operand" "d")
1897: (match_operand:SI 1 "const_int_operand" "i")
1898: (match_operand:SI 2 "general_operand" "di")))]
1899: "TARGET_68020 && TARGET_BITFIELD"
1900: "*
1901: {
1902: if (operands[1] == const1_rtx
1903: && GET_CODE (operands[2]) == CONST_INT)
1904: {
1905: int width = GET_CODE (operands[0]) == REG ? 31 : 7;
1906: return output_btst (operands,
1907: gen_rtx (CONST_INT, VOIDmode,
1908: width - INTVAL (operands[2])),
1909: operands[0],
1910: insn, 1000);
1911: /* Pass 1000 as SIGNPOS argument so that btst will
1912: not think we are testing the sign bit for an `and'
1913: and assume that nonzero implies a negative result. */
1914: }
1915: if (INTVAL (operands[1]) != 32)
1916: cc_status.flags = CC_NOT_NEGATIVE;
1917: return \"bftst [%c2,%c1]%0\";
1918: }")
1919:
1920:
1921: (define_insn "seq"
1922: [(set (match_operand:QI 0 "general_operand" "=d")
1923: (eq:QI (cc0) (const_int 0)))]
1924: ""
1925: "*
1926: cc_status = cc_prev_status;
1927: OUTPUT_JUMP (\"seq %0\", \"fseq %0\", \"seq %0\");
1928: ")
1929:
1930: (define_insn "sne"
1931: [(set (match_operand:QI 0 "general_operand" "=d")
1932: (ne:QI (cc0) (const_int 0)))]
1933: ""
1934: "*
1935: cc_status = cc_prev_status;
1936: OUTPUT_JUMP (\"sne %0\", \"fsneq %0\", \"sne %0\");
1937: ")
1938:
1939: (define_insn "sgt"
1940: [(set (match_operand:QI 0 "general_operand" "=d")
1941: (gt:QI (cc0) (const_int 0)))]
1942: ""
1943: "*
1944: cc_status = cc_prev_status;
1945: OUTPUT_JUMP (\"sgt %0\", \"fsgt %0\", \"and%.b %#0xc,%!\;sgt %0\");
1946: ")
1947:
1948: (define_insn "sgtu"
1949: [(set (match_operand:QI 0 "general_operand" "=d")
1950: (gtu:QI (cc0) (const_int 0)))]
1951: ""
1952: "* cc_status = cc_prev_status;
1953: return \"shi %0\"; ")
1954:
1955: (define_insn "slt"
1956: [(set (match_operand:QI 0 "general_operand" "=d")
1957: (lt:QI (cc0) (const_int 0)))]
1958: ""
1959: "* cc_status = cc_prev_status;
1960: OUTPUT_JUMP (\"slt %0\", \"fslt %0\", \"smi %0\"); ")
1961:
1962: (define_insn "sltu"
1963: [(set (match_operand:QI 0 "general_operand" "=d")
1964: (ltu:QI (cc0) (const_int 0)))]
1965: ""
1966: "* cc_status = cc_prev_status;
1967: return \"scs %0\"; ")
1968:
1969: (define_insn "sge"
1970: [(set (match_operand:QI 0 "general_operand" "=d")
1971: (ge:QI (cc0) (const_int 0)))]
1972: ""
1973: "* cc_status = cc_prev_status;
1974: OUTPUT_JUMP (\"sge %0\", \"fsge %0\", \"spl %0\"); ")
1975:
1976: (define_insn "sgeu"
1977: [(set (match_operand:QI 0 "general_operand" "=d")
1978: (geu:QI (cc0) (const_int 0)))]
1979: ""
1980: "* cc_status = cc_prev_status;
1981: return \"scc %0\"; ")
1982:
1983: (define_insn "sle"
1984: [(set (match_operand:QI 0 "general_operand" "=d")
1985: (le:QI (cc0) (const_int 0)))]
1986: ""
1987: "*
1988: cc_status = cc_prev_status;
1989: OUTPUT_JUMP (\"sle %0\", \"fsle %0\", \"and%.b %#0xc,%!\;sle %0\");
1990: ")
1991:
1992: (define_insn "sleu"
1993: [(set (match_operand:QI 0 "general_operand" "=d")
1994: (leu:QI (cc0) (const_int 0)))]
1995: ""
1996: "* cc_status = cc_prev_status;
1997: return \"sls %0\"; ")
1998:
1999: ;; Basic conditional jump instructions.
2000:
2001: (define_insn "beq"
2002: [(set (pc)
2003: (if_then_else (eq (cc0)
2004: (const_int 0))
2005: (label_ref (match_operand 0 "" ""))
2006: (pc)))]
2007: ""
2008: "*
2009: {
2010: OUTPUT_JUMP (\"jeq %l0\", \"fbeq %l0\", \"jeq %l0\");
2011: }")
2012:
2013: (define_insn "bne"
2014: [(set (pc)
2015: (if_then_else (ne (cc0)
2016: (const_int 0))
2017: (label_ref (match_operand 0 "" ""))
2018: (pc)))]
2019: ""
2020: "*
2021: {
2022: OUTPUT_JUMP (\"jne %l0\", \"fbneq %l0\", \"jne %l0\");
2023: }")
2024:
2025: (define_insn "bgt"
2026: [(set (pc)
2027: (if_then_else (gt (cc0)
2028: (const_int 0))
2029: (label_ref (match_operand 0 "" ""))
2030: (pc)))]
2031: ""
2032: "*
2033: OUTPUT_JUMP (\"jgt %l0\", \"fbgt %l0\", \"and%.b %#0xc,%!\;jgt %l0\");
2034: ")
2035:
2036: (define_insn "bgtu"
2037: [(set (pc)
2038: (if_then_else (gtu (cc0)
2039: (const_int 0))
2040: (label_ref (match_operand 0 "" ""))
2041: (pc)))]
2042: ""
2043: "*
2044: return \"jhi %l0\";
2045: ")
2046:
2047: (define_insn "blt"
2048: [(set (pc)
2049: (if_then_else (lt (cc0)
2050: (const_int 0))
2051: (label_ref (match_operand 0 "" ""))
2052: (pc)))]
2053: ""
2054: "*
2055: OUTPUT_JUMP (\"jlt %l0\", \"fblt %l0\", \"jmi %l0\");
2056: ")
2057:
2058: (define_insn "bltu"
2059: [(set (pc)
2060: (if_then_else (ltu (cc0)
2061: (const_int 0))
2062: (label_ref (match_operand 0 "" ""))
2063: (pc)))]
2064: ""
2065: "*
2066: return \"jcs %l0\";
2067: ")
2068:
2069: (define_insn "bge"
2070: [(set (pc)
2071: (if_then_else (ge (cc0)
2072: (const_int 0))
2073: (label_ref (match_operand 0 "" ""))
2074: (pc)))]
2075: ""
2076: "*
2077: OUTPUT_JUMP (\"jge %l0\", \"fbge %l0\", \"jpl %l0\");
2078: ")
2079:
2080: (define_insn "bgeu"
2081: [(set (pc)
2082: (if_then_else (geu (cc0)
2083: (const_int 0))
2084: (label_ref (match_operand 0 "" ""))
2085: (pc)))]
2086: ""
2087: "*
2088: return \"jcc %l0\";
2089: ")
2090:
2091: (define_insn "ble"
2092: [(set (pc)
2093: (if_then_else (le (cc0)
2094: (const_int 0))
2095: (label_ref (match_operand 0 "" ""))
2096: (pc)))]
2097: ""
2098: "*
2099: OUTPUT_JUMP (\"jle %l0\", \"fble %l0\", \"and%.b %#0xc,%!\;jle %l0\");
2100: ")
2101:
2102: (define_insn "bleu"
2103: [(set (pc)
2104: (if_then_else (leu (cc0)
2105: (const_int 0))
2106: (label_ref (match_operand 0 "" ""))
2107: (pc)))]
2108: ""
2109: "*
2110: return \"jls %l0\";
2111: ")
2112:
2113: ;; Negated conditional jump instructions.
2114:
2115: (define_insn ""
2116: [(set (pc)
2117: (if_then_else (eq (cc0)
2118: (const_int 0))
2119: (pc)
2120: (label_ref (match_operand 0 "" ""))))]
2121: ""
2122: "*
2123: {
2124: OUTPUT_JUMP (\"jne %l0\", \"fbneq %l0\", \"jne %l0\");
2125: }")
2126:
2127: (define_insn ""
2128: [(set (pc)
2129: (if_then_else (ne (cc0)
2130: (const_int 0))
2131: (pc)
2132: (label_ref (match_operand 0 "" ""))))]
2133: ""
2134: "*
2135: {
2136: OUTPUT_JUMP (\"jeq %l0\", \"fbeq %l0\", \"jeq %l0\");
2137: }")
2138:
2139: (define_insn ""
2140: [(set (pc)
2141: (if_then_else (gt (cc0)
2142: (const_int 0))
2143: (pc)
2144: (label_ref (match_operand 0 "" ""))))]
2145: ""
2146: "*
2147: OUTPUT_JUMP (\"jle %l0\", \"fbngt %l0\", \"and%.b %#0xc,%!\;jle %l0\");
2148: ")
2149:
2150: (define_insn ""
2151: [(set (pc)
2152: (if_then_else (gtu (cc0)
2153: (const_int 0))
2154: (pc)
2155: (label_ref (match_operand 0 "" ""))))]
2156: ""
2157: "*
2158: return \"jls %l0\";
2159: ")
2160:
2161: (define_insn ""
2162: [(set (pc)
2163: (if_then_else (lt (cc0)
2164: (const_int 0))
2165: (pc)
2166: (label_ref (match_operand 0 "" ""))))]
2167: ""
2168: "*
2169: OUTPUT_JUMP (\"jge %l0\", \"fbnlt %l0\", \"jpl %l0\");
2170: ")
2171:
2172: (define_insn ""
2173: [(set (pc)
2174: (if_then_else (ltu (cc0)
2175: (const_int 0))
2176: (pc)
2177: (label_ref (match_operand 0 "" ""))))]
2178: ""
2179: "*
2180: return \"jcc %l0\";
2181: ")
2182:
2183: (define_insn ""
2184: [(set (pc)
2185: (if_then_else (ge (cc0)
2186: (const_int 0))
2187: (pc)
2188: (label_ref (match_operand 0 "" ""))))]
2189: ""
2190: "*
2191: OUTPUT_JUMP (\"jlt %l0\", \"fbnge %l0\", \"jmi %l0\");
2192: ")
2193:
2194: (define_insn ""
2195: [(set (pc)
2196: (if_then_else (geu (cc0)
2197: (const_int 0))
2198: (pc)
2199: (label_ref (match_operand 0 "" ""))))]
2200: ""
2201: "*
2202: return \"jcs %l0\";
2203: ")
2204:
2205: (define_insn ""
2206: [(set (pc)
2207: (if_then_else (le (cc0)
2208: (const_int 0))
2209: (pc)
2210: (label_ref (match_operand 0 "" ""))))]
2211: ""
2212: "*
2213: OUTPUT_JUMP (\"jgt %l0\", \"fbnle %l0\", \"and%.b %#0xc,%!\;jgt %l0\");
2214: ")
2215:
2216: (define_insn ""
2217: [(set (pc)
2218: (if_then_else (leu (cc0)
2219: (const_int 0))
2220: (pc)
2221: (label_ref (match_operand 0 "" ""))))]
2222: ""
2223: "*
2224: return \"jhi %l0\";
2225: ")
2226:
2227: ;; Subroutines of "casesi".
2228:
2229: (define_expand "casesi_1"
2230: [(set (match_operand:SI 3 "general_operand" "")
2231: (plus:SI (match_operand:SI 0 "general_operand" "")
2232: ;; Note operand 1 has been negated!
2233: (match_operand:SI 1 "immediate_operand" "")))
2234: (set (cc0) (compare (match_operand:SI 2 "nonimmediate_operand" "")
2235: (match_dup 3)))
2236: (set (pc) (if_then_else (ltu (cc0) (const_int 0))
2237: (label_ref (match_operand 4 "" "")) (pc)))]
2238: ""
2239: "")
2240:
2241: (define_expand "casesi_2"
1.1.1.2 root 2242: [(set (match_operand:HI 0 "" "") (mem:HI (match_operand:SI 1 "" "")))
1.1 root 2243: ;; The USE here is so that at least one jump-insn will refer to the label,
2244: ;; to keep it alive in jump_optimize.
2245: (parallel [(set (pc)
1.1.1.2 root 2246: (plus:SI (pc) (sign_extend:SI (match_dup 0))))
1.1 root 2247: (use (label_ref (match_operand 2 "" "")))])]
2248: ""
2249: "")
2250:
2251: ;; Operand 0 is index (in bytes); operand 1 is minimum, operand 2 the maximum;
2252: ;; operand 3 is CODE_LABEL for the table;
2253: ;; operand 4 is the CODE_LABEL to go to if index out of range.
2254: (define_expand "casesi"
2255: ;; We don't use these for generating the RTL, but we must describe
2256: ;; the operands here.
1.1.1.2 root 2257: [(match_operand:HI 0 "general_operand" "")
1.1 root 2258: (match_operand:SI 1 "immediate_operand" "")
2259: (match_operand:SI 2 "general_operand" "")
2260: (match_operand 3 "" "")
2261: (match_operand 4 "" "")]
2262: ""
2263: "
2264: {
2265: rtx table_elt_addr;
2266: rtx index_diff;
2267:
2268: operands[1] = negate_rtx (SImode, operands[1]);
2269: index_diff = gen_reg_rtx (SImode);
2270: /* Emit the first few insns. */
2271: emit_insn (gen_casesi_1 (operands[0], operands[1], operands[2],
2272: index_diff, operands[4]));
2273: /* Construct a memory address. This may emit some insns. */
2274: table_elt_addr
2275: = memory_address_noforce
2276: (HImode,
2277: gen_rtx (PLUS, Pmode,
2278: gen_rtx (MULT, Pmode, index_diff,
2279: gen_rtx (CONST_INT, VOIDmode, 2)),
2280: gen_rtx (LABEL_REF, VOIDmode, operands[3])));
2281: /* Emit the last few insns. */
2282: emit_insn (gen_casesi_2 (gen_reg_rtx (HImode), table_elt_addr, operands[3]));
2283: DONE;
2284: }")
2285:
2286: ;; Recognize one of the insns resulting from casesi_2.
2287: (define_insn ""
2288: [(set (pc)
1.1.1.2 root 2289: (plus:SI (pc)
2290: (sign_extend:SI (match_operand:HI 0 "general_operand" "r"))))
1.1 root 2291: (use (label_ref (match_operand 1 "" "")))]
2292: ""
2293: "*
2294: return \"jmp pc@(2:B)[%0:W:B]\";
2295: ")
2296:
2297: ;; Unconditional and other jump instructions
2298: (define_insn "jump"
2299: [(set (pc)
2300: (label_ref (match_operand 0 "" "")))]
2301: ""
2302: "*
2303: return \"jra %l0\";
2304: ")
2305:
2306: (define_insn ""
2307: [(set (pc)
2308: (if_then_else
2309: (ne (match_operand:HI 0 "general_operand" "d,m,g")
2310: (const_int 0))
2311: (label_ref (match_operand 1 "" ""))
2312: (pc)))
2313: (set (match_dup 0)
2314: (plus:HI (match_dup 0)
2315: (const_int -1)))]
2316: ""
2317: "@
2318: dbra %0,%l1
2319: subq%.w %#1,%0\;jcc %l1
2320: subq%.w %#1,%0\;cmp%.w %#-1,%0\;jne %l1")
2321:
2322: (define_insn ""
2323: [(set (pc)
2324: (if_then_else
2325: (ne (match_operand:SI 0 "general_operand" "d,m,g")
2326: (const_int 0))
2327: (label_ref (match_operand 1 "" ""))
2328: (pc)))
2329: (set (match_dup 0)
2330: (plus:SI (match_dup 0)
2331: (const_int -1)))]
2332: ""
2333: "@
2334: dbra %0,%l1\;clr%.w %0\;subq%.l %#1,%0\;jcc %l1
2335: subq%.l %#1,%0\;jcc %l1
2336: subq%.l %#1,%0\;cmp%.l %#-1,%0\;jne %l1")
2337:
2338: ;; dbra patterns that use REG_NOTES info generated by strength_reduce.
2339:
2340: (define_insn "decrement_and_branch_until_zero"
2341: [(set (pc)
2342: (if_then_else
2343: (ge (match_operand:SI 0 "general_operand" "d,m,g")
2344: (const_int 1))
2345: (label_ref (match_operand 1 "" ""))
2346: (pc)))
2347: (set (match_dup 0)
2348: (plus:SI (match_dup 0)
2349: (const_int -1)))]
2350: "find_reg_note (insn, REG_NONNEG, 0)"
2351: "@
2352: dbra %0,%l1\;clrw %0\;subql %#1,%0\;jcc %l1
2353: subq%.l %#1,%0\;jcc %l1
2354: subq%.l %#1,%0\;cmp%.l %#-1,%0\;jne %l1")
2355:
2356: ;; Call subroutine with no return value.
2357: (define_insn "call"
2358: [(call (match_operand:QI 0 "memory_operand" "o")
2359: (match_operand:SI 1 "general_operand" "g"))]
2360: ""
2361: "*
2362: {
2363: rtx xoperands[2];
2364: int size = XINT(operands[1],0);
2365:
2366: if (size == 0)
2367: output_asm_insn (\"sub%.l a0,a0\;jbsr %0\", operands);
2368: else
2369: {
2370: xoperands[1] = gen_rtx (CONST_INT, VOIDmode, size/4);
2371: output_asm_insn (\"mov%.l sp,a0\;pea %a1\", xoperands);
2372: output_asm_insn (\"jbsr %0\", operands);
2373: size = size + 4;
2374: xoperands[1] = gen_rtx (CONST_INT, VOIDmode, size);
2375: if (size <= 8)
2376: output_asm_insn (\"addq%.l %1,sp\", xoperands);
2377: else if (size < 0x8000)
2378: output_asm_insn (\"add%.w %1,sp\", xoperands);
2379: else
2380: output_asm_insn (\"add%.l %1,sp\", xoperands);
2381: }
2382: return \"mov%.l a6@(-4),a0\";
2383: }")
2384:
2385: ;; Call subroutine, returning value in operand 0
2386: ;; (which must be a hard register).
2387: (define_insn "call_value"
2388: [(set (match_operand 0 "" "=rf")
2389: (call (match_operand:QI 1 "memory_operand" "o")
2390: (match_operand:SI 2 "general_operand" "g")))]
2391: ""
2392: "*
2393: {
2394: rtx xoperands[3];
2395: int size = XINT(operands[2],0);
2396:
2397: if (size == 0)
2398: output_asm_insn(\"sub%.l a0,a0\;jbsr %1\", operands);
2399: else
2400: {
2401: xoperands[2] = gen_rtx (CONST_INT, VOIDmode, size/4);
2402: output_asm_insn (\"mov%.l sp,a0\;pea %a2\", xoperands);
2403: output_asm_insn (\"jbsr %1\", operands);
2404: size = size + 4;
2405: xoperands[2] = gen_rtx (CONST_INT, VOIDmode, size);
2406: if (size <= 8)
2407: output_asm_insn (\"addq%.l %2,sp\", xoperands);
2408: else if (size < 0x8000)
2409: output_asm_insn (\"add%.w %2,sp\", xoperands);
2410: else
2411: output_asm_insn (\"add%.l %2,sp\", xoperands);
2412: }
2413: return \"mov%.l a6@(-4),a0\";
2414: }")
2415:
2416: ;; Call subroutine returning any type.
2417:
2418: (define_expand "untyped_call"
2419: [(parallel [(call (match_operand 0 "" "")
2420: (const_int 0))
2421: (match_operand 1 "" "")
2422: (match_operand 2 "" "")])]
2423: ""
2424: "
2425: {
2426: int i;
2427:
2428: emit_call_insn (gen_call (operands[0], const0_rtx, NULL, const0_rtx));
2429:
2430: for (i = 0; i < XVECLEN (operands[2], 0); i++)
2431: {
2432: rtx set = XVECEXP (operands[2], 0, i);
2433: emit_move_insn (SET_DEST (set), SET_SRC (set));
2434: }
2435:
2436: /* The optimizer does not know that the call sets the function value
2437: registers we stored in the result block. We avoid problems by
2438: claiming that all hard registers are used and clobbered at this
2439: point. */
2440: emit_insn (gen_blockage ());
2441:
2442: DONE;
2443: }")
2444:
2445: ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
2446: ;; all of memory. This blocks insns from being moved across this point.
2447:
2448: (define_insn "blockage"
2449: [(unspec_volatile [(const_int 0)] 0)]
2450: ""
2451: "")
2452:
2453: (define_insn "nop"
2454: [(const_int 0)]
2455: ""
2456: "nop")
2457:
2458: ;; This should not be used unless the add/sub insns can't be.
2459:
2460: (define_insn ""
2461: [(set (match_operand:SI 0 "general_operand" "=a")
2462: (match_operand:QI 1 "address_operand" "p"))]
2463: ""
2464: "lea %a1,%0")
2465:
2466: ;; This is the first machine-dependent peephole optimization.
2467: ;; It is useful when a floating value is returned from a function call
2468: ;; and then is moved into an FP register.
2469: ;; But it is mainly intended to test the support for these optimizations.
2470:
2471: ;Not applicable to Alliant -- floating results are returned in fp0
2472: ;(define_peephole
2473: ; [(set (reg:SI 15) (plus:SI (reg:SI 15) (const_int 4)))
2474: ; (set (match_operand:DF 0 "register_operand" "f")
2475: ; (match_operand:DF 1 "register_operand" "ad"))]
2476: ; "FP_REG_P (operands[0]) && ! FP_REG_P (operands[1])"
2477: ; "*
2478: ;{
2479: ; rtx xoperands[2];
2480: ; xoperands[1] = gen_rtx (REG, SImode, REGNO (operands[1]) + 1);
2481: ; output_asm_insn (\"mov%.l %1,%@\", xoperands);
2482: ; output_asm_insn (\"mov%.l %1,%-\", operands);
2483: ; return \"fmove%.d %+,%0\";
2484: ;}
2485: ;")
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.