* config/h8300/h8300.h (CONDITIONAL_REGISTER_USAGE): Replace a
[official-gcc.git] / gcc / config / h8300 / h8300.md
blob4d85dd1206676f7b47276274c45ebd983dce61c0
1 ;; GCC machine description for Hitachi H8/300
2 ;; Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
3 ;; 2001, 2002 Free Software Foundation, Inc.
5 ;;   Contributed by Steve Chamberlain (sac@cygnus.com),
6 ;;   Jim Wilson (wilson@cygnus.com), and Doug Evans (dje@cygnus.com).
8 ;; This file is part of GNU CC.
10 ;; GNU CC is free software; you can redistribute it and/or modify
11 ;; it under the terms of the GNU General Public License as published by
12 ;; the Free Software Foundation; either version 2, or (at your option)
13 ;; any later version.
15 ;; GNU CC is distributed in the hope that it will be useful,
16 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
17 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18 ;; GNU General Public License for more details.
20 ;; You should have received a copy of the GNU General Public License
21 ;; along with GNU CC; see the file COPYING.  If not, write to
22 ;; the Free Software Foundation, 59 Temple Place - Suite 330,
23 ;; Boston, MA 02111-1307, USA.
25 ;; Some of the extend instructions accept a general_operand_src, which
26 ;; allows all the normal memory addressing modes.  The length computations
27 ;; don't take this into account.  The lengths in the MD file should be
28 ;; "worst case" and then be adjusted to their correct values by
29 ;; h8300_adjust_insn_length.
31 ;; On the H8/300H and H8/S, adds/subs operate on the 32bit "er"
32 ;; registers.  Right now GCC doesn't expose the "e" half to the
33 ;; compiler, so using add/subs for addhi and subhi is safe.  Long
34 ;; term, we want to expose the "e" half to the compiler (gives us 8
35 ;; more 16bit registers).  At that point addhi and subhi can't use
36 ;; adds/subs.
38 ;; There's currently no way to have a insv/extzv expander for the H8/300H
39 ;; because word_mode is different for the H8/300 and H8/300H.
41 ;; Shifts/rotates by small constants should be handled by special
42 ;; patterns so we get the length and cc status correct.
44 ;; Bitfield operations no longer accept memory operands.  We need
45 ;; to add variants which operate on memory back to the MD.
47 ;; ??? Implement remaining bit ops available on the h8300
49 ;; ----------------------------------------------------------------------
50 ;; CONSTANTS
51 ;; ----------------------------------------------------------------------
53 (define_constants
54   [(SC_REG       3)
55    (FP_REG       6)
56    (SP_REG       7)
57    (MAC_REG      8)
58    (AP_REG       9)
59    (RAP_REG     10)])
61 ;; ----------------------------------------------------------------------
62 ;; ATTRIBUTES
63 ;; ----------------------------------------------------------------------
65 (define_attr "cpu" "h8300,h8300h"
66   (const (symbol_ref "cpu_type")))
68 (define_attr "type" "branch,arith"
69   (const_string "arith"))
71 ;; The size of instructions in bytes.
73 (define_attr "length" ""
74   (cond [(eq_attr "type" "branch")
75          (if_then_else (and (ge (minus (match_dup 0) (pc))
76                                 (const_int -126))
77                             (le (minus (match_dup 0) (pc))
78                                 (const_int 126)))
79                        (const_int 2)
80                        (if_then_else (and (eq_attr "cpu" "h8300h")
81                                           (and (ge (minus (pc) (match_dup 0))
82                                                    (const_int -32000))
83                                                (le (minus (pc) (match_dup 0))
84                                                    (const_int 32000))))
85                                      (const_int 4)
86                                      (const_int 6)))]
87         (const_int 200)))
89 ;; The necessity of instruction length adjustment.
91 (define_attr "adjust_length" "yes,no"
92   (cond [(eq_attr "type" "branch") (const_string "no")]
93         (const_string "yes")))
95 ;; Condition code settings.
97 ;; none - insn does not affect cc
98 ;; none_0hit - insn does not affect cc but it does modify operand 0
99 ;;      This attribute is used to keep track of when operand 0 changes.
100 ;;      See the description of NOTICE_UPDATE_CC for more info.
101 ;; set_znv - insn sets z,n,v to usable values (like a tst insn); c is unknown.
102 ;; set_zn  - insn sets z,n to usable values; v,c are unknown.
103 ;; compare - compare instruction
104 ;; clobber - value of cc is unknown
106 (define_attr "cc" "none,none_0hit,set_znv,set_zn,compare,clobber"
107   (const_string "clobber"))
109 ;; ----------------------------------------------------------------------
110 ;; MOVE INSTRUCTIONS
111 ;; ----------------------------------------------------------------------
113 ;; movqi
115 (define_insn "pushqi1_h8300"
116   [(parallel [(set (reg:HI SP_REG)
117                    (plus:HI (reg:HI SP_REG) (const_int -2)))
118               (set (mem:QI (plus:HI (reg:HI SP_REG) (const_int -1)))
119                    (match_operand:QI 0 "register_operand" "r"))])]
120   "TARGET_H8300"
121   "mov.w\\t%T0,@-r7"
122   [(set_attr "length" "2")
123    (set_attr "cc" "clobber")])
125 (define_insn "pushqi1_h8300hs"
126   [(parallel [(set (reg:SI SP_REG)
127                    (plus:SI (reg:SI SP_REG) (const_int -4)))
128               (set (mem:QI (plus:SI (reg:SI SP_REG) (const_int -3)))
129                    (match_operand:QI 0 "register_operand" "r"))])]
130   "TARGET_H8300H || TARGET_H8300S"
131   "mov.l\\t%S0,@-er7"
132   [(set_attr "length" "4")
133    (set_attr "cc" "clobber")])
135 (define_expand "pushqi1"
136   [(use (match_operand:QI 0 "register_operand" ""))]
137   ""
138   "
140   if (TARGET_H8300)
141     emit_insn (gen_pushqi1_h8300 (operands[0]));
142   else
143     emit_insn (gen_pushqi1_h8300hs (operands[0]));
144   DONE;
147 (define_insn ""
148   [(set (match_operand:QI 0 "general_operand_dst" "=r,r ,<,r,r,m")
149         (match_operand:QI 1 "general_operand_src" " I,r>,r,n,m,r"))]
150   "TARGET_H8300
151    && (register_operand (operands[0], QImode)
152        || register_operand (operands[1], QImode))"
153   "@
154    sub.b        %X0,%X0
155    mov.b        %R1,%X0
156    mov.b        %X1,%R0
157    mov.b        %R1,%X0
158    mov.b        %R1,%X0
159    mov.b        %X1,%R0"
160   [(set_attr "length" "2,2,2,2,4,4")
161    (set_attr "cc" "set_zn,set_znv,set_znv,set_znv,set_znv,set_znv")])
163 (define_insn ""
164   [(set (match_operand:QI 0 "general_operand_dst" "=r,r ,<,r,r,m")
165         (match_operand:QI 1 "general_operand_src" " I,r>,r,n,m,r"))]
166   "(TARGET_H8300H || TARGET_H8300S)
167    && (register_operand (operands[0], QImode)
168        || register_operand (operands[1], QImode))"
169   "@
170    sub.b        %X0,%X0
171    mov.b        %R1,%X0
172    mov.b        %X1,%R0
173    mov.b        %R1,%X0
174    mov.b        %R1,%X0
175    mov.b        %X1,%R0"
176   [(set_attr "length" "2,2,2,2,8,8")
177    (set_attr "cc" "set_zn,set_znv,set_znv,clobber,set_znv,set_znv")])
179 (define_expand "movqi"
180   [(set (match_operand:QI 0 "general_operand_dst" "")
181         (match_operand:QI 1 "general_operand_src" ""))]
182   ""
183   "
185   /* One of the ops has to be in a register.  */
186   if (!register_operand (operand0, QImode)
187       && !register_operand (operand1, QImode))
188     {
189       operands[1] = copy_to_mode_reg (QImode, operand1);
190     }
193 (define_insn "movstrictqi"
194   [(set (strict_low_part (match_operand:QI 0 "general_operand_dst" "+r,r,r,r"))
195                          (match_operand:QI 1 "general_operand_src" "I,r,n,m"))]
196   ""
197   "@
198    sub.b        %X0,%X0
199    mov.b        %X1,%X0
200    mov.b        %R1,%X0
201    mov.b        %R1,%X0"
202   [(set_attr_alternative "length"
203      [(const_int 2) (const_int 2) (const_int 2)
204       (if_then_else (eq_attr "cpu" "h8300") (const_int 4) (const_int 8))])
205    (set_attr "cc" "set_zn,set_znv,set_znv,set_znv")])
207 ;; movhi
209 (define_expand "pushhi1_h8300"
210   [(set (mem:HI (pre_dec:HI (reg:HI SP_REG)))
211         (match_operand:HI 0 "register_operand" ""))]
212   "TARGET_H8300"
213   "")
215 (define_insn "pushhi1_h8300hs"
216   [(parallel [(set (reg:SI SP_REG)
217                    (plus:SI (reg:SI SP_REG) (const_int -4)))
218               (set (mem:HI (plus:SI (reg:SI SP_REG) (const_int -2)))
219                    (match_operand:HI 0 "register_operand" "r"))])]
220   "TARGET_H8300H || TARGET_H8300S"
221   "mov.l\\t%S0,@-er7"
222   [(set_attr "length" "4")
223    (set_attr "cc" "clobber")])
225 (define_expand "pushhi1"
226   [(use (match_operand:HI 0 "register_operand" ""))]
227   ""
228   "
230   if (TARGET_H8300)
231     emit_insn (gen_pushhi1_h8300 (operands[0]));
232   else
233     emit_insn (gen_pushhi1_h8300hs (operands[0]));
234   DONE;
237 (define_insn ""
238   [(set (match_operand:HI 0 "general_operand_dst" "=r,r,<,r,r,m")
239         (match_operand:HI 1 "general_operand_src" "I,r>,r,i,m,r"))]
240   "TARGET_H8300
241    && (register_operand (operands[0], HImode)
242        || register_operand (operands[1], HImode))
243    && !(GET_CODE (operands[0]) == MEM
244         && GET_CODE (XEXP (operands[0], 0)) == PRE_DEC
245         && GET_CODE (XEXP (XEXP (operands[0], 0), 0)) == REG
246         && GET_CODE (operands[1]) == REG
247         && REGNO (XEXP (XEXP (operands[0], 0), 0)) == REGNO (operands[1]))"
248   "@
249    sub.w        %T0,%T0
250    mov.w        %T1,%T0
251    mov.w        %T1,%T0
252    mov.w        %T1,%T0
253    mov.w        %T1,%T0
254    mov.w        %T1,%T0"
255   [(set_attr "length" "2,2,2,4,4,4")
256    (set_attr "cc" "set_zn,set_znv,set_znv,set_znv,set_znv,set_znv")])
258 (define_insn ""
259   [(set (match_operand:HI 0 "general_operand_dst" "=r,r,<,r,r,m")
260         (match_operand:HI 1 "general_operand_src" "I,r>,r,i,m,r"))]
261   "(TARGET_H8300H || TARGET_H8300S)
262    && (register_operand (operands[0], HImode)
263        || register_operand (operands[1], HImode))"
264   "@
265    sub.w        %T0,%T0
266    mov.w        %T1,%T0
267    mov.w        %T1,%T0
268    mov.w        %T1,%T0
269    mov.w        %T1,%T0
270    mov.w        %T1,%T0"
271   [(set_attr "length" "2,2,2,4,8,8")
272    (set_attr "cc" "set_zn,set_znv,set_znv,set_znv,set_znv,set_znv")])
274 (define_expand "movhi"
275   [(set (match_operand:HI 0 "general_operand_dst" "")
276         (match_operand:HI 1 "general_operand_src" ""))]
277   ""
278   "
280   /* One of the ops has to be in a register.  */
281   if (!register_operand (operand1, HImode)
282       && !register_operand (operand0, HImode))
283     {
284       operands[1] = copy_to_mode_reg (HImode, operand1);
285     }
288 (define_insn "movstricthi"
289   [(set (strict_low_part (match_operand:HI 0 "general_operand_dst" "+r,r,r,r"))
290                          (match_operand:HI 1 "general_operand_src" "I,r,i,m"))]
291   ""
292   "@
293    sub.w        %T0,%T0
294    mov.w        %T1,%T0
295    mov.w        %T1,%T0
296    mov.w        %T1,%T0"
297   [(set_attr_alternative "length"
298      [(const_int 2) (const_int 2) (const_int 4)
299       (if_then_else (eq_attr "cpu" "h8300") (const_int 4) (const_int 8))])
300    (set_attr "cc" "set_zn,set_znv,set_znv,set_znv")])
302 ;; movsi
304 (define_expand "movsi"
305   [(set (match_operand:SI 0 "general_operand_dst" "")
306         (match_operand:SI 1 "general_operand_src" ""))]
307   ""
308   "
310   if (TARGET_H8300)
311     {
312       if (do_movsi (operands))
313         DONE;
314     }
315   else
316     {
317       /* One of the ops has to be in a register.  */
318       if (!register_operand (operand1, SImode)
319           && !register_operand (operand0, SImode))
320         {
321           operands[1] = copy_to_mode_reg (SImode, operand1);
322         }
323     }
326 (define_expand "movsf"
327   [(set (match_operand:SF 0 "general_operand_dst" "")
328         (match_operand:SF 1 "general_operand_src" ""))]
329   ""
330   "
332   if (TARGET_H8300)
333     {
334       if (do_movsi (operands))
335         DONE;
336     }
337   else
338     {
339       /* One of the ops has to be in a register.  */
340       if (!register_operand (operand1, SFmode)
341           && !register_operand (operand0, SFmode))
342         {
343           operands[1] = copy_to_mode_reg (SFmode, operand1);
344         }
345     }
348 (define_insn "movsi_h8300"
349   [(set (match_operand:SI 0 "general_operand_dst" "=r,r,r,o,<,r")
350         (match_operand:SI 1 "general_operand_src" "I,r,io,r,r,>"))]
351   "TARGET_H8300
352    && (register_operand (operands[0], SImode)
353        || register_operand (operands[1], SImode))"
354   "*
356   int rn = -1;
357   switch (which_alternative)
358     {
359     case 0:
360       return \"sub.w    %e0,%e0\;sub.w  %f0,%f0\";
361     case 1:
362       if (REGNO (operands[0]) < REGNO (operands[1]))
363         return \"mov.w  %e1,%e0\;mov.w  %f1,%f0\";
364       else
365         return \"mov.w  %f1,%f0\;mov.w  %e1,%e0\";
366     case 2:
367       /* Make sure we don't trample the register we index with.  */
368       if (GET_CODE (operands[1]) == MEM)
369         {
370           rtx inside = XEXP (operands[1], 0);
371           if (REG_P (inside))
372             {
373               rn = REGNO (inside);
374             }
375           else if (GET_CODE (inside) == PLUS)
376             {
377               rtx lhs = XEXP (inside, 0);
378               rtx rhs = XEXP (inside, 1);
379               if (REG_P (lhs)) rn = REGNO (lhs);
380               if (REG_P (rhs)) rn = REGNO (rhs);
381             }
382         }
383       if (rn == REGNO (operands[0]))
384         {
385           /* Move the second word first.  */
386           return \"mov.w        %f1,%f0\;mov.w  %e1,%e0\";
387         }
388       else
389         {
390           /* See if either half is zero.  If so, use sub.w to clear
391              that half.  */
392           if (GET_CODE (operands[1]) == CONST_INT)
393             {
394               if ((INTVAL (operands[1]) & 0xffff) == 0)
395                 return \"mov.w  %e1,%e0\;sub.w  %f0,%f0\";
396               if (((INTVAL (operands[1]) >> 16) & 0xffff) == 0)
397                 return \"sub.w  %e0,%e0\;mov.w  %f1,%f0\";
398             }
399           return \"mov.w        %e1,%e0\;mov.w  %f1,%f0\";
400         }
401     case 3:
402       return \"mov.w    %e1,%e0\;mov.w  %f1,%f0\";
403     case 4:
404       return \"mov.w    %f1,%T0\;mov.w  %e1,%T0\";
405     case 5:
406       return \"mov.w    %T1,%e0\;mov.w  %T1,%f0\";
407     default:
408       abort ();
409     }
411   [(set_attr "length" "4,4,8,8,4,4")
412    (set_attr "cc" "clobber")])
414 (define_insn "movsf_h8300"
415   [(set (match_operand:SF 0 "general_operand_dst" "=r,r,r,o,<,r")
416         (match_operand:SF 1 "general_operand_src" "I,r,io,r,r,>"))]
417   "TARGET_H8300
418    && (register_operand (operands[0], SFmode)
419        || register_operand (operands[1], SFmode))"
420   "*
422   /* Copy of the movsi stuff.  */
423   int rn = -1;
424   switch (which_alternative)
425     {
426     case 0:
427       return \"sub.w    %e0,%e0\;sub.w  %f0,%f0\";
428     case 1:
429       if (REGNO (operands[0]) < REGNO (operands[1]))
430         return \"mov.w  %e1,%e0\;mov.w  %f1,%f0\";
431       else
432         return \"mov.w  %f1,%f0\;mov.w  %e1,%e0\";
433     case 2:
434       /* Make sure we don't trample the register we index with.  */
435       if (GET_CODE (operands[1]) == MEM)
436         {
437           rtx inside = XEXP (operands[1], 0);
438           if (REG_P (inside))
439             {
440               rn = REGNO (inside);
441             }
442           else if (GET_CODE (inside) == PLUS)
443             {
444               rtx lhs = XEXP (inside, 0);
445               rtx rhs = XEXP (inside, 1);
446               if (REG_P (lhs)) rn = REGNO (lhs);
447               if (REG_P (rhs)) rn = REGNO (rhs);
448             }
449         }
450       if (rn == REGNO (operands[0]))
451         /* Move the second word first.  */
452         return \"mov.w  %f1,%f0\;mov.w  %e1,%e0\";
453       else
454         /* Move the first word first.  */
455         return \"mov.w  %e1,%e0\;mov.w  %f1,%f0\";
457     case 3:
458       return \"mov.w    %e1,%e0\;mov.w  %f1,%f0\";
459     case 4:
460       return \"mov.w    %f1,%T0\;mov.w  %e1,%T0\";
461     case 5:
462       return \"mov.w    %T1,%e0\;mov.w  %T1,%f0\";
463     default:
464       abort ();
465     }
467   [(set_attr "length" "4,4,8,8,4,4")
468    (set_attr "cc" "clobber")])
470 (define_insn "movsi_h8300hs"
471   [(set (match_operand:SI 0 "general_operand_dst" "=r,r,r,r,m,<,r,*a,*a,r")
472         (match_operand:SI 1 "general_operand_src" "I,r,i,m,r,r,>,I,r,*a"))]
473   "(TARGET_H8300S || TARGET_H8300H)
474    && (register_operand (operands[0], SImode)
475        || register_operand (operands[1], SImode))
476    && !(GET_CODE (operands[0]) == MEM
477         && GET_CODE (XEXP (operands[0], 0)) == PRE_DEC
478         && GET_CODE (XEXP (XEXP (operands[0], 0), 0)) == REG
479         && GET_CODE (operands[1]) == REG
480         && REGNO (XEXP (XEXP (operands[0], 0), 0)) == REGNO (operands[1]))"
481   "*
483   switch (which_alternative)
484     {
485     case 0:
486       return \"sub.l    %S0,%S0\";
487     case 7:
488       return \"clrmac\";
489     case 8:
490       return \"clrmac\;ldmac %1,macl\";
491     case 9:
492       return \"stmac    macl,%0\";
493     default:
494       if (GET_CODE (operands[1]) == CONST_INT)
495         {
496           int val = INTVAL (operands[1]);
498           /* Look for constants which can be made by adding an 8-bit
499              number to zero in one of the two low bytes.  */
500           if (val == (val & 0xff))
501             {
502               operands[1] = GEN_INT ((char) val & 0xff);
503               return \"sub.l\\t%S0,%S0\;add.b\\t%1,%w0\";
504             }
506           if (val == (val & 0xff00))
507             {
508               operands[1] = GEN_INT ((char) (val >> 8) & 0xff);
509               return \"sub.l\\t%S0,%S0\;add.b\\t%1,%x0\";
510             }
512           /* Look for constants that can be obtained by subs, inc, and
513              dec to 0.  */
514           switch (val & 0xffffffff)
515             {
516             case 0xffffffff:
517               return \"sub.l\\t%S0,%S0\;subs\\t#1,%S0\";
518             case 0xfffffffe:
519               return \"sub.l\\t%S0,%S0\;subs\\t#2,%S0\";
520             case 0xfffffffc:
521               return \"sub.l\\t%S0,%S0\;subs\\t#4,%S0\";
523             case 0x0000ffff:
524               return \"sub.l\\t%S0,%S0\;dec.w\\t#1,%f0\";
525             case 0x0000fffe:
526               return \"sub.l\\t%S0,%S0\;dec.w\\t#2,%f0\";
528             case 0xffff0000:
529               return \"sub.l\\t%S0,%S0\;dec.w\\t#1,%e0\";
530             case 0xfffe0000:
531               return \"sub.l\\t%S0,%S0\;dec.w\\t#2,%e0\";
533             case 0x00010000:
534               return \"sub.l\\t%S0,%S0\;inc.w\\t#1,%e0\";
535             case 0x00020000:
536               return \"sub.l\\t%S0,%S0\;inc.w\\t#2,%e0\";
537             }
538         }
539     }
540    return \"mov.l       %S1,%S0\";
542   [(set_attr "length" "2,2,6,10,10,4,4,2,6,4")
543    (set_attr "cc" "set_zn,set_znv,clobber,set_znv,set_znv,set_znv,set_znv,none_0hit,none_0hit,set_znv")])
545 (define_insn "movsf_h8300h"
546   [(set (match_operand:SF 0 "general_operand_dst" "=r,r,r,m,<,r")
547         (match_operand:SF 1 "general_operand_src" "I,r,im,r,r,>"))]
548   "(TARGET_H8300H || TARGET_H8300S)
549    && (register_operand (operands[0], SFmode)
550        || register_operand (operands[1], SFmode))"
551   "@
552    sub.l        %S0,%S0
553    mov.l        %S1,%S0
554    mov.l        %S1,%S0
555    mov.l        %S1,%S0
556    mov.l        %S1,%S0
557    mov.l        %S1,%S0"
558   [(set_attr "length" "2,2,10,10,4,4")
559    (set_attr "cc" "set_zn,set_znv,set_znv,set_znv,set_znv,set_znv")])
561 ;; ----------------------------------------------------------------------
562 ;; TEST INSTRUCTIONS
563 ;; ----------------------------------------------------------------------
565 (define_insn ""
566   [(set (cc0) (zero_extract:HI (match_operand:QI 0 "bit_memory_operand" "r,U")
567                                (const_int 1)
568                                (match_operand 1 "const_int_operand" "n,n")))]
569   "TARGET_H8300"
570   "btst %Z1,%Y0"
571   [(set_attr "length" "2,4")
572    (set_attr "cc" "set_zn,set_zn")])
574 (define_insn ""
575   [(set (cc0) (zero_extract:HI (match_operand:HI 0 "register_operand" "r")
576                                (const_int 1)
577                                (match_operand 1 "const_int_operand" "n")))]
578   "TARGET_H8300"
579   "btst %Z1,%Y0"
580   [(set_attr "length" "2")
581    (set_attr "cc" "set_zn")])
583 (define_insn ""
584   [(set (cc0) (zero_extract:SI (match_operand:QI 0 "bit_memory_operand" "r,U")
585                                (const_int 1)
586                                (match_operand 1 "const_int_operand" "n,n")))]
587   "TARGET_H8300H || TARGET_H8300S"
588   "btst %Z1,%Y0"
589   [(set_attr "length" "2,8")
590    (set_attr "cc" "set_zn,set_zn")])
592 (define_insn ""
593   [(set (cc0) (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
594                                (const_int 1)
595                                (match_operand 1 "const_int_operand" "n")))]
596   "(TARGET_H8300H || TARGET_H8300S)
597    && INTVAL (operands[1]) <= 15"
598   "btst %Z1,%Y0"
599   [(set_attr "length" "2")
600    (set_attr "cc" "set_zn")])
602 (define_insn "tstqi"
603   [(set (cc0) (match_operand:QI 0 "register_operand" "r"))]
604   ""
605   "mov.b        %X0,%X0"
606   [(set_attr "length" "2")
607    (set_attr "cc" "set_znv")])
609 (define_insn "tsthi"
610   [(set (cc0) (match_operand:HI 0 "register_operand" "r"))]
611   ""
612   "mov.w        %T0,%T0"
613   [(set_attr "length" "2")
614    (set_attr "cc" "set_znv")])
616 (define_insn "tstsi"
617   [(set (cc0) (match_operand:SI 0 "register_operand" "r"))]
618   "TARGET_H8300H || TARGET_H8300S"
619   "mov.l        %S0,%S0"
620   [(set_attr "length" "2")
621    (set_attr "cc" "set_znv")])
623 (define_insn "cmpqi"
624   [(set (cc0)
625         (compare:QI (match_operand:QI 0 "register_operand" "r")
626                     (match_operand:QI 1 "nonmemory_operand" "rn")))]
627   ""
628   "cmp.b        %X1,%X0"
629   [(set_attr "length" "2")
630    (set_attr "cc" "compare")])
632 (define_expand "cmphi"
633   [(set (cc0)
634         (compare:HI (match_operand:HI 0 "register_operand" "")
635                     (match_operand:HI 1 "nonmemory_operand" "")))]
636   ""
637   "
639   /* Force operand1 into a register if we're compiling
640      for the H8/300.  */
641   if (GET_CODE (operands[1]) != REG && TARGET_H8300)
642     operands[1] = force_reg (HImode, operands[1]);
645 (define_insn ""
646   [(set (cc0)
647         (compare:HI (match_operand:HI 0 "register_operand" "r")
648                     (match_operand:HI 1 "register_operand" "r")))]
649   "TARGET_H8300"
650   "cmp.w        %T1,%T0"
651   [(set_attr "length" "2")
652    (set_attr "cc" "compare")])
654 (define_insn ""
655   [(set (cc0)
656         (compare:HI (match_operand:HI 0 "register_operand" "r,r")
657                     (match_operand:HI 1 "nonmemory_operand" "r,n")))]
658   "TARGET_H8300H || TARGET_H8300S"
659   "cmp.w        %T1,%T0"
660   [(set_attr "length" "2,4")
661    (set_attr "cc" "compare,compare")])
663 (define_insn "cmpsi"
664   [(set (cc0)
665         (compare:SI (match_operand:SI 0 "register_operand" "r,r")
666                     (match_operand:SI 1 "nonmemory_operand" "r,i")))]
667   "TARGET_H8300H || TARGET_H8300S"
668   "cmp.l        %S1,%S0"
669   [(set_attr "length" "2,6")
670    (set_attr "cc" "compare,compare")])
672 ;; ----------------------------------------------------------------------
673 ;; ADD INSTRUCTIONS
674 ;; ----------------------------------------------------------------------
676 (define_insn "addqi3"
677   [(set (match_operand:QI 0 "register_operand" "=r")
678         (plus:QI (match_operand:QI 1 "register_operand" "%0")
679                  (match_operand:QI 2 "nonmemory_operand" "rn")))]
680   ""
681   "add.b        %X2,%X0"
682   [(set_attr "length" "2")
683    (set_attr "cc" "set_zn")])
685 (define_expand "addhi3"
686   [(set (match_operand:HI 0 "register_operand" "")
687         (plus:HI (match_operand:HI 1 "register_operand" "")
688                  (match_operand:HI 2 "nonmemory_operand" "")))]
689   ""
690   "")
692 (define_insn ""
693   [(set (match_operand:HI 0 "register_operand" "=r,r,r,r,&r")
694         (plus:HI (match_operand:HI 1 "register_operand" "%0,0,0,0,g")
695                  (match_operand:HI 2 "nonmemory_operand" "L,N,n,r,r")))]
696   "TARGET_H8300"
697   "@
698    adds %2,%T0
699    subs %G2,%T0
700    add.b        %s2,%s0\;addx   %t2,%t0
701    add.w        %T2,%T0
702    mov.w        %T1,%T0\;add.w  %T2,%T0"
703   [(set_attr "length" "2,2,4,2,6")
704    (set_attr "cc" "none_0hit,none_0hit,clobber,set_zn,set_zn")])
706 (define_insn ""
707   [(set (match_operand:HI 0 "register_operand" "=r,r,r,r")
708         (plus:HI (match_operand:HI 1 "register_operand" "%0,0,0,0")
709                  (match_operand:HI 2 "nonmemory_operand" "L,N,n,r")))]
710   "TARGET_H8300H || TARGET_H8300S"
711   "@
712    adds %2,%S0
713    subs %G2,%S0
714    add.w        %T2,%T0
715    add.w        %T2,%T0"
716   [(set_attr "length" "2,2,4,2")
717    (set_attr "cc" "none_0hit,none_0hit,set_zn,set_zn")])
719 (define_split
720   [(set (match_operand:HI 0 "register_operand" "")
721         (plus:HI (match_dup 0)
722                  (match_operand:HI 1 "two_insn_adds_subs_operand" "")))]
723   ""
724   [(const_int 0)]
725   "split_adds_subs (HImode, operands); DONE;")
727 (define_expand "addsi3"
728   [(set (match_operand:SI 0 "register_operand" "")
729         (plus:SI (match_operand:SI 1 "register_operand" "")
730                  (match_operand:SI 2 "nonmemory_operand" "")))]
731   ""
732   "")
734 (define_insn "addsi_h8300"
735   [(set (match_operand:SI 0 "register_operand" "=r,r,&r")
736         (plus:SI (match_operand:SI 1 "register_operand" "%0,0,r")
737                  (match_operand:SI 2 "nonmemory_operand" "n,r,r")))]
738   "TARGET_H8300"
739   "@
740    add  %w2,%w0\;addx   %x2,%x0\;addx   %y2,%y0\;addx   %z2,%z0
741    add.w        %f2,%f0\;addx   %y2,%y0\;addx   %z2,%z0
742    mov.w        %f1,%f0\;mov.w  %e1,%e0\;add.w  %f2,%f0\;addx   %y2,%y0\;addx   %z2,%z0"
743   [(set_attr "length" "8,6,10")
744    (set_attr "cc" "clobber")])
746 (define_insn "addsi_h8300h"
747   [(set (match_operand:SI 0 "register_operand" "=r,r,r,r")
748         (plus:SI (match_operand:SI 1 "register_operand" "%0,0,0,0")
749                  (match_operand:SI 2 "nonmemory_operand" "L,N,i,r")))]
750   "TARGET_H8300H || TARGET_H8300S"
751   "@
752    adds %2,%S0
753    subs %G2,%S0
754    add.l        %S2,%S0
755    add.l        %S2,%S0"
756   [(set_attr "length" "2,2,6,2")
757    (set_attr "cc" "none_0hit,none_0hit,set_zn,set_zn")])
759 (define_split
760   [(set (match_operand:SI 0 "register_operand" "")
761         (plus:SI (match_dup 0)
762                  (match_operand:SI 1 "two_insn_adds_subs_operand" "")))]
763   "TARGET_H8300H || TARGET_H8300S"
764   [(const_int 0)]
765   "split_adds_subs (SImode, operands); DONE;")
767 ;; ----------------------------------------------------------------------
768 ;; SUBTRACT INSTRUCTIONS
769 ;; ----------------------------------------------------------------------
771 (define_insn "subqi3"
772   [(set (match_operand:QI 0 "register_operand" "=r")
773         (minus:QI (match_operand:QI 1 "register_operand" "0")
774                   (match_operand:QI 2 "register_operand" "r")))]
775   ""
776   "sub.b        %X2,%X0"
777   [(set_attr "length" "2")
778    (set_attr "cc" "set_zn")])
780 (define_expand "subhi3"
781   [(set (match_operand:HI 0 "register_operand" "")
782         (minus:HI (match_operand:HI 1 "general_operand" "")
783                   (match_operand:HI 2 "nonmemory_operand" "")))]
784   ""
785   "")
787 (define_insn ""
788   [(set (match_operand:HI 0 "register_operand" "=r,&r")
789         (minus:HI (match_operand:HI 1 "general_operand" "0,0")
790                   (match_operand:HI 2 "nonmemory_operand" "r,n")))]
791   "TARGET_H8300"
792   "@
793    sub.w        %T2,%T0
794    add.b        %E2,%s0\;addx   %F2,%t0"
795   [(set_attr "length" "2,4")
796    (set_attr "cc" "set_zn,clobber")])
798 (define_insn ""
799   [(set (match_operand:HI 0 "register_operand" "=r,&r")
800         (minus:HI (match_operand:HI 1 "general_operand" "0,0")
801                   (match_operand:HI 2 "nonmemory_operand" "r,n")))]
802   "TARGET_H8300H || TARGET_H8300S"
803   "@
804    sub.w        %T2,%T0
805    sub.w        %T2,%T0"
806   [(set_attr "length" "2,4")
807    (set_attr "cc" "set_zn,set_zn")])
809 (define_expand "subsi3"
810   [(set (match_operand:SI 0 "register_operand" "")
811         (minus:SI (match_operand:SI 1 "register_operand" "")
812                   (match_operand:SI 2 "nonmemory_operand" "")))]
813   ""
814   "")
816 (define_insn "subsi3_h8300"
817   [(set (match_operand:SI 0 "register_operand" "=r")
818         (minus:SI (match_operand:SI 1 "register_operand" "0")
819                   (match_operand:SI 2 "register_operand" "r")))]
820   "TARGET_H8300"
821   "sub.w        %f2,%f0\;subx   %y2,%y0\;subx   %z2,%z0"
822   [(set_attr "length" "6")
823    (set_attr "cc" "clobber")])
825 (define_insn "subsi3_h8300h"
826   [(set (match_operand:SI 0 "register_operand" "=r,r")
827         (minus:SI (match_operand:SI 1 "general_operand" "0,0")
828                   (match_operand:SI 2 "nonmemory_operand" "r,i")))]
829   "TARGET_H8300H || TARGET_H8300S"
830   "@
831    sub.l        %S2,%S0
832    sub.l        %S2,%S0"
833   [(set_attr "length" "2,6")
834    (set_attr "cc" "set_zn,set_zn")])
836 ;; ----------------------------------------------------------------------
837 ;; MULTIPLY INSTRUCTIONS
838 ;; ----------------------------------------------------------------------
840 ;; Note that the H8/300 can only handle umulqihi3.
842 (define_insn "mulqihi3"
843   [(set (match_operand:HI 0 "register_operand" "=r")
844         (mult:HI (sign_extend:HI (match_operand:QI 1 "general_operand" "%0"))
845                  (sign_extend:HI (match_operand:QI 2 "register_operand" "r"))))]
846   "TARGET_H8300H || TARGET_H8300S"
847   "mulxs.b      %X2,%T0"
848   [(set_attr "length" "4")
849    (set_attr "cc" "set_zn")])
851 (define_insn "mulhisi3"
852   [(set (match_operand:SI 0 "register_operand" "=r")
853         (mult:SI (sign_extend:SI (match_operand:HI 1 "general_operand" "%0"))
854                  (sign_extend:SI (match_operand:HI 2 "register_operand" "r"))))]
855   "TARGET_H8300H || TARGET_H8300S"
856   "mulxs.w      %T2,%S0"
857   [(set_attr "length" "4")
858    (set_attr "cc" "set_zn")])
860 (define_insn "umulqihi3"
861   [(set (match_operand:HI 0 "register_operand" "=r")
862         (mult:HI (zero_extend:HI (match_operand:QI 1 "general_operand" "%0"))
863                  (zero_extend:HI (match_operand:QI 2 "register_operand" "r"))))]
864   ""
865   "mulxu        %X2,%T0"
866   [(set_attr "length" "2")
867    (set_attr "cc" "none_0hit")])
869 (define_insn "umulhisi3"
870   [(set (match_operand:SI 0 "register_operand" "=r")
871         (mult:SI (zero_extend:SI (match_operand:HI 1 "general_operand" "%0"))
872                  (zero_extend:SI (match_operand:HI 2 "register_operand" "r"))))]
873   "TARGET_H8300H || TARGET_H8300S"
874   "mulxu.w      %T2,%S0"
875   [(set_attr "length" "2")
876    (set_attr "cc" "none_0hit")])
878 ;; This is a "bridge" instruction.  Combine can't cram enough insns
879 ;; together to crate a MAC instruction directly, but it can create
880 ;; this instruction, which then allows combine to create the real
881 ;; MAC insn.
883 ;; Unfortunately, if combine doesn't create a MAC instruction, this
884 ;; insn must generate reasonably correct code.  Egad.
885 (define_insn ""
886   [(set (match_operand:SI 0 "register_operand" "=a")
887         (mult:SI
888           (sign_extend:SI
889             (mem:HI (post_inc:SI (match_operand:SI 1 "register_operand" "r"))))
890           (sign_extend:SI
891             (mem:HI (post_inc:SI (match_operand:SI 2 "register_operand" "r"))))))]
892   "TARGET_MAC"
893   "clrmac\;mac  @%2+,@%1+"
894   [(set_attr "length" "6")
895    (set_attr "cc" "none_0hit")])
897 (define_insn ""
898   [(set (match_operand:SI 0 "register_operand" "=a")
899         (plus:SI (mult:SI
900           (sign_extend:SI (mem:HI
901             (post_inc:SI (match_operand:SI 1 "register_operand" "r"))))
902           (sign_extend:SI (mem:HI
903             (post_inc:SI (match_operand:SI 2 "register_operand" "r")))))
904               (match_operand:SI 3 "register_operand" "0")))]
905   "TARGET_MAC"
906   "mac  @%2+,@%1+"
907   [(set_attr "length" "4")
908    (set_attr "cc" "none_0hit")])
910 ;; ----------------------------------------------------------------------
911 ;; DIVIDE/MOD INSTRUCTIONS
912 ;; ----------------------------------------------------------------------
914 (define_insn "udivmodqi4"
915   [(set (match_operand:QI 0 "register_operand" "=r")
916         (truncate:QI
917           (udiv:HI
918             (match_operand:HI 1 "general_operand" "0")
919             (zero_extend:HI (match_operand:QI 2 "register_operand" "r")))))
920    (set (match_operand:QI 3 "register_operand" "=r")
921         (truncate:QI
922           (umod:HI
923             (match_dup 1)
924             (zero_extend:HI (match_dup 2)))))]
925   "TARGET_H8300H || TARGET_H8300S"
926   "*
928   if (find_reg_note (insn, REG_UNUSED, operands[3]))
929     return \"divxu.b\\t%X2,%T0\";
930   else
931     return \"divxu.b\\t%X2,%T0\;mov.b\\t%t0,%s3\";
933   [(set_attr "length" "4")
934    (set_attr "cc" "clobber")])
936 (define_insn "divmodqi4"
937   [(set (match_operand:QI 0 "register_operand" "=r")
938         (truncate:QI
939           (div:HI
940             (match_operand:HI 1 "general_operand" "0")
941             (sign_extend:HI (match_operand:QI 2 "register_operand" "r")))))
942    (set (match_operand:QI 3 "register_operand" "=r")
943         (truncate:QI
944           (mod:HI
945             (match_dup 1)
946             (sign_extend:HI (match_dup 2)))))]
947   "TARGET_H8300H || TARGET_H8300S"
948   "*
950   if (find_reg_note (insn, REG_UNUSED, operands[3]))
951     return \"divxs.b\\t%X2,%T0\";
952   else
953     return \"divxs.b\\t%X2,%T0\;mov.b\\t%t0,%s3\";
955   [(set_attr "length" "6")
956    (set_attr "cc" "clobber")])
958 (define_insn "udivmodhi4"
959   [(set (match_operand:HI 0 "register_operand" "=r")
960         (truncate:HI
961           (udiv:SI
962             (match_operand:SI 1 "general_operand" "0")
963             (zero_extend:SI (match_operand:HI 2 "register_operand" "r")))))
964    (set (match_operand:HI 3 "register_operand" "=r")
965         (truncate:HI
966           (umod:SI
967             (match_dup 1)
968             (zero_extend:SI (match_dup 2)))))]
969   "TARGET_H8300H || TARGET_H8300S"
970   "*
972   if (find_reg_note (insn, REG_UNUSED, operands[3]))
973     return \"divxu.w\\t%T2,%S0\";
974   else
975     return \"divxu.w\\t%T2,%S0\;mov.w\\t%e0,%f3\";
977   [(set_attr "length" "4")
978    (set_attr "cc" "clobber")])
980 (define_insn "divmodhi4"
981   [(set (match_operand:HI 0 "register_operand" "=r")
982         (truncate:HI
983           (div:SI
984             (match_operand:SI 1 "general_operand" "0")
985             (sign_extend:SI (match_operand:HI 2 "register_operand" "r")))))
986    (set (match_operand:HI 3 "register_operand" "=r")
987         (truncate:HI
988           (mod:SI
989             (match_dup 1)
990             (sign_extend:SI (match_dup 2)))))]
991   "TARGET_H8300H || TARGET_H8300S"
992   "*
994   if (find_reg_note (insn, REG_UNUSED, operands[3]))
995     return \"divxs.w\\t%T2,%S0\";
996   else
997     return \"divxs.w\\t%T2,%S0\;mov.w\\t%e0,%f3\";
999   [(set_attr "length" "6")
1000    (set_attr "cc" "clobber")])
1002 ;; ----------------------------------------------------------------------
1003 ;; AND INSTRUCTIONS
1004 ;; ----------------------------------------------------------------------
1006 (define_insn ""
1007   [(set (match_operand:QI 0 "bit_operand" "=r,U")
1008         (and:QI (match_operand:QI 1 "bit_operand" "%0,0")
1009                 (match_operand:QI 2 "nonmemory_operand" "rn,O")))]
1010   "register_operand (operands[0], QImode) || o_operand (operands[2], QImode)"
1011   "@
1012    and  %X2,%X0
1013    bclr %W2,%R0"
1014   [(set_attr "length" "2,8")
1015    (set_attr "adjust_length" "no")
1016    (set_attr "cc" "set_znv,none_0hit")])
1018 (define_expand "andqi3"
1019   [(set (match_operand:QI 0 "bit_operand" "")
1020         (and:QI (match_operand:QI 1 "bit_operand" "")
1021                 (match_operand:QI 2 "nonmemory_operand" "")))]
1022   ""
1023   "
1025   if (fix_bit_operand (operands, 'O', AND))
1026     DONE;
1029 (define_expand "andhi3"
1030   [(set (match_operand:HI 0 "register_operand" "")
1031         (and:HI (match_operand:HI 1 "register_operand" "")
1032                 (match_operand:HI 2 "nonmemory_operand" "")))]
1033   ""
1034   "")
1036 (define_insn ""
1037   [(set (match_operand:HI 0 "register_operand" "=r")
1038         (and:HI (match_operand:HI 1 "register_operand" "%0")
1039                 (match_operand:HI 2 "nonmemory_operand" "rn")))]
1040   "TARGET_H8300"
1041   "* return output_logical_op (HImode, AND, operands);"
1042   [(set_attr "length" "4")
1043    (set_attr "cc" "clobber")])
1045 (define_insn ""
1046   [(set (match_operand:HI 0 "register_operand" "=r,r")
1047         (and:HI (match_operand:HI 1 "register_operand" "%0,0")
1048                 (match_operand:HI 2 "nonmemory_operand" "r,n")))]
1049   "TARGET_H8300H || TARGET_H8300S"
1050   "* return output_logical_op (HImode, AND, operands);"
1051   [(set_attr "length" "2,4")
1052    (set_attr "cc" "set_znv,clobber")])
1054 (define_insn "*andorhi3"
1055   [(set (match_operand:HI 0 "register_operand" "=r")
1056         (ior:HI (and:HI (match_operand:HI 2 "register_operand" "r")
1057                         (match_operand:HI 3 "const_int_operand" "n"))
1058         (match_operand:HI 1 "register_operand" "0")))]
1059   "exact_log2 (INTVAL (operands[3]) & 0xffff) != -1"
1060   "*
1062   operands[3] = GEN_INT (INTVAL (operands[3]) & 0xffff);
1063   if (INTVAL (operands[3]) > 128)
1064     {
1065       operands[3] = GEN_INT (INTVAL (operands[3]) >> 8);
1066       return \"bld\\t%V3,%t2\;bst\\t%V3,%t0\";
1067     }
1068   return \"bld\\t%V3,%s2\;bst\\t%V3,%s0\";
1070   [(set_attr "length" "4")
1071    (set_attr "cc" "clobber")])
1073 (define_expand "andsi3"
1074   [(set (match_operand:SI 0 "register_operand" "")
1075         (and:SI (match_operand:SI 1 "register_operand" "")
1076                 (match_operand:SI 2 "nonmemory_operand" "")))]
1077   ""
1078   "")
1080 (define_insn ""
1081   [(set (match_operand:SI 0 "register_operand" "=r")
1082         (and:SI (match_operand:SI 1 "register_operand" "%0")
1083                 (match_operand:SI 2 "nonmemory_operand" "rn")))]
1084   "TARGET_H8300"
1085   "* return output_logical_op (SImode, AND, operands);"
1086   [(set_attr "length" "8")
1087    (set_attr "cc" "clobber")])
1089 (define_insn ""
1090   [(set (match_operand:SI 0 "register_operand" "=r,r")
1091         (and:SI (match_operand:SI 1 "register_operand" "%0,0")
1092                 (match_operand:SI 2 "nonmemory_operand" "r,n")))]
1093   "TARGET_H8300H || TARGET_H8300S"
1094   "* return output_logical_op (SImode, AND, operands);"
1095   [(set_attr "length" "4,6")
1096    (set_attr "cc" "set_znv,clobber")])
1098 ;; ----------------------------------------------------------------------
1099 ;; OR INSTRUCTIONS
1100 ;; ----------------------------------------------------------------------
1102 (define_insn ""
1103   [(set (match_operand:QI 0 "bit_operand" "=r,U")
1104         (ior:QI (match_operand:QI 1 "bit_operand" "%0,0")
1105                 (match_operand:QI 2 "nonmemory_operand" "rn,n")))]
1106   "register_operand (operands[0], QImode)
1107    || (GET_CODE (operands[2]) == CONST_INT
1108        && exact_log2 (INTVAL (operands[2]) & 0xff) != -1)"
1109   "*
1111   switch (which_alternative)
1112     {
1113     case 0:
1114       return \"or\t%X2,%X0\";
1115     case 1:
1116       operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
1117       return \"bset\t%V2,%R0\";
1118     default:
1119       abort ();
1120     }
1122   [(set_attr "length" "2,8")
1123    (set_attr "adjust_length" "no")
1124    (set_attr "cc" "set_znv,none_0hit")])
1126 (define_expand "iorqi3"
1127   [(set (match_operand:QI 0 "bit_operand" "")
1128         (ior:QI (match_operand:QI 1 "bit_operand" "")
1129                 (match_operand:QI 2 "nonmemory_operand" "")))]
1130   ""
1131   "
1133   if (fix_bit_operand (operands, 'P', IOR))
1134     DONE;
1137 (define_expand "iorhi3"
1138   [(set (match_operand:HI 0 "register_operand" "")
1139         (ior:HI (match_operand:HI 1 "register_operand" "")
1140                 (match_operand:HI 2 "nonmemory_operand" "")))]
1141   ""
1142   "")
1144 (define_insn ""
1145   [(set (match_operand:HI 0 "general_operand" "=r,r")
1146         (ior:HI (match_operand:HI 1 "general_operand" "%0,0")
1147                 (match_operand:HI 2 "general_operand" "J,rn")))]
1148   "TARGET_H8300"
1149   "* return output_logical_op (HImode, IOR, operands);"
1150   [(set_attr "length" "2,4")
1151    (set_attr "cc" "clobber,clobber")])
1153 (define_insn ""
1154   [(set (match_operand:HI 0 "general_operand" "=r,r,r")
1155         (ior:HI (match_operand:HI 1 "general_operand" "%0,0,0")
1156                 (match_operand:HI 2 "general_operand" "J,r,n")))]
1157   "TARGET_H8300H || TARGET_H8300S"
1158   "* return output_logical_op (HImode, IOR, operands);"
1159   [(set_attr "length" "2,2,4")
1160    (set_attr "cc" "clobber,set_znv,clobber")])
1162 (define_expand "iorsi3"
1163   [(set (match_operand:SI 0 "register_operand" "")
1164         (ior:SI (match_operand:SI 1 "register_operand" "")
1165                 (match_operand:SI 2 "nonmemory_operand" "")))]
1166   ""
1167   "")
1169 (define_insn ""
1170   [(set (match_operand:SI 0 "register_operand" "=r,r")
1171         (ior:SI (match_operand:SI 1 "register_operand" "%0,0")
1172                 (match_operand:SI 2 "nonmemory_operand" "J,rn")))]
1173   "TARGET_H8300"
1174   "* return output_logical_op (SImode, IOR, operands);"
1175   [(set_attr "length" "2,8")
1176    (set_attr "cc" "clobber,clobber")])
1178 (define_insn ""
1179   [(set (match_operand:SI 0 "register_operand" "=r,r,r")
1180         (ior:SI (match_operand:SI 1 "register_operand" "%0,0,0")
1181                 (match_operand:SI 2 "nonmemory_operand" "J,r,n")))]
1182   "TARGET_H8300H || TARGET_H8300S"
1183   "* return output_logical_op (SImode, IOR, operands);"
1184   [(set_attr "length" "2,4,6")
1185    (set_attr "cc" "clobber,set_znv,clobber")])
1187 ;; ----------------------------------------------------------------------
1188 ;; XOR INSTRUCTIONS
1189 ;; ----------------------------------------------------------------------
1191 (define_insn ""
1192   [(set (match_operand:QI 0 "bit_operand" "=r,U")
1193         (xor:QI (match_operand:QI 1 "bit_operand" "%0,0")
1194                 (match_operand:QI 2 "nonmemory_operand" "rn,n")))]
1195   "register_operand (operands[0], QImode)
1196    || (GET_CODE (operands[2]) == CONST_INT
1197        && exact_log2 (INTVAL (operands[2]) & 0xff) != -1)"
1198   "*
1200   switch (which_alternative)
1201     {
1202     case 0:
1203       return \"xor\t%X2,%X0\";
1204     case 1:
1205       operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
1206       return \"bnot\t%V2,%R0\";
1207     default:
1208       abort ();
1209     }
1211   [(set_attr "length" "2,8")
1212    (set_attr "adjust_length" "no")
1213    (set_attr "cc" "set_znv,none_0hit")])
1215 (define_expand "xorqi3"
1216   [(set (match_operand:QI 0 "bit_operand" "")
1217         (xor:QI (match_operand:QI 1 "bit_operand" "")
1218                 (match_operand:QI 2 "nonmemory_operand" "")))]
1219   ""
1220   "
1222   if (fix_bit_operand (operands, 'O', XOR))
1223     DONE;
1226 (define_expand "xorhi3"
1227   [(set (match_operand:HI 0 "register_operand" "")
1228         (xor:HI (match_operand:HI 1 "register_operand" "")
1229                 (match_operand:HI 2 "nonmemory_operand" "")))]
1230   ""
1231   "")
1233 (define_insn ""
1234   [(set (match_operand:HI 0 "register_operand" "=r,r")
1235         (xor:HI (match_operand:HI 1 "register_operand" "%0,0")
1236                 (match_operand:HI 2 "nonmemory_operand" "J,rn")))]
1237   "TARGET_H8300"
1238   "* return output_logical_op (HImode, XOR, operands);"
1239   [(set_attr "length" "2,4")
1240    (set_attr "cc" "clobber,clobber")])
1242 (define_insn ""
1243   [(set (match_operand:HI 0 "register_operand" "=r,r,r")
1244         (xor:HI (match_operand:HI 1 "register_operand" "%0,0,0")
1245                 (match_operand:HI 2 "nonmemory_operand" "J,r,n")))]
1246   "TARGET_H8300H || TARGET_H8300S"
1247   "* return output_logical_op (HImode, XOR, operands);"
1248   [(set_attr "length" "2,2,4")
1249    (set_attr "cc" "clobber,set_znv,clobber")])
1251 (define_expand "xorsi3"
1252   [(set (match_operand:SI 0 "register_operand" "")
1253         (xor:SI (match_operand:SI 1 "register_operand" "")
1254                 (match_operand:SI 2 "nonmemory_operand" "")))]
1255   ""
1256   "")
1258 (define_insn ""
1259   [(set (match_operand:SI 0 "register_operand" "=r,r")
1260         (xor:SI (match_operand:SI 1 "register_operand" "%0,0")
1261                 (match_operand:SI 2 "nonmemory_operand" "J,rn")))]
1262   "TARGET_H8300"
1263   "* return output_logical_op (SImode, XOR, operands);"
1264   [(set_attr "length" "2,8")
1265    (set_attr "cc" "clobber,clobber")])
1267 (define_insn ""
1268   [(set (match_operand:SI 0 "register_operand" "=r,r,r")
1269         (xor:SI (match_operand:SI 1 "register_operand" "%0,0,0")
1270                 (match_operand:SI 2 "nonmemory_operand" "J,r,n")))]
1271   "TARGET_H8300H || TARGET_H8300S"
1272   "* return output_logical_op (SImode, XOR, operands);"
1273   [(set_attr "length" "2,4,6")
1274    (set_attr "cc" "clobber,set_znv,clobber")])
1276 ;; ----------------------------------------------------------------------
1277 ;; NEGATION INSTRUCTIONS
1278 ;; ----------------------------------------------------------------------
1280 (define_insn "negqi2"
1281   [(set (match_operand:QI 0 "register_operand" "=r")
1282         (neg:QI (match_operand:QI 1 "register_operand" "0")))]
1283   ""
1284   "neg  %X0"
1285   [(set_attr "length" "2")
1286    (set_attr "cc" "set_zn")])
1288 (define_expand "neghi2"
1289   [(set (match_operand:HI 0 "register_operand" "")
1290         (neg:HI (match_operand:HI 1 "register_operand" "")))]
1291   ""
1292   "
1294   if (TARGET_H8300)
1295     {
1296       emit_insn (gen_neghi2_h8300 (operands[0], operands[1]));
1297       DONE;
1298     }
1301 (define_expand "neghi2_h8300"
1302   [(set (match_dup 2)
1303         (not:HI (match_operand:HI 1 "register_operand" "")))
1304    (set (match_dup 2) (plus:HI (match_dup 2) (const_int 1)))
1305    (set (match_operand:HI 0 "register_operand" "")
1306         (match_dup 2))]
1307   ""
1308   "operands[2] = gen_reg_rtx (HImode);")
1310 (define_insn "neghi2_h8300h"
1311   [(set (match_operand:HI 0 "register_operand" "=r")
1312         (neg:HI (match_operand:HI 1 "register_operand" "0")))]
1313   "TARGET_H8300H || TARGET_H8300S"
1314   "neg  %T0"
1315   [(set_attr "length" "2")
1316    (set_attr "cc" "set_zn")])
1318 (define_expand "negsi2"
1319   [(set (match_operand:SI 0 "register_operand" "")
1320         (neg:SI (match_operand:SI 1 "register_operand" "")))]
1321   ""
1322   "
1324   if (TARGET_H8300)
1325     {
1326       emit_insn (gen_negsi2_h8300 (operands[0], operands[1]));
1327       DONE;
1328     }
1331 (define_expand "negsi2_h8300"
1332   [(set (match_dup 2)
1333         (not:SI (match_operand:SI 1 "register_operand" "")))
1334    (set (match_dup 2) (plus:SI (match_dup 2) (const_int 1)))
1335    (set (match_operand:SI 0 "register_operand" "")
1336         (match_dup 2))]
1337   ""
1338   "operands[2] = gen_reg_rtx (SImode);")
1340 (define_insn "negsi2_h8300h"
1341   [(set (match_operand:SI 0 "register_operand" "=r")
1342         (neg:SI (match_operand:SI 1 "register_operand" "0")))]
1343   "TARGET_H8300H || TARGET_H8300S"
1344   "neg  %S0"
1345   [(set_attr "length" "2")
1346    (set_attr "cc" "set_zn")])
1348 ;; ----------------------------------------------------------------------
1349 ;; NOT INSTRUCTIONS
1350 ;; ----------------------------------------------------------------------
1352 (define_insn "one_cmplqi2"
1353   [(set (match_operand:QI 0 "register_operand" "=r")
1354         (not:QI (match_operand:QI 1 "register_operand" "0")))]
1355   ""
1356   "not  %X0"
1357   [(set_attr "length" "2")
1358    (set_attr "cc" "set_znv")])
1360 (define_expand "one_cmplhi2"
1361   [(set (match_operand:HI 0 "register_operand" "=r")
1362         (not:HI (match_operand:HI 1 "register_operand" "0")))]
1363   ""
1364   "")
1366 (define_insn ""
1367   [(set (match_operand:HI 0 "register_operand" "=r")
1368         (not:HI (match_operand:HI 1 "register_operand" "0")))]
1369   "TARGET_H8300"
1370   "not  %s0\;not        %t0"
1371   [(set_attr "cc" "clobber")
1372    (set_attr "length" "4")])
1374 (define_insn ""
1375   [(set (match_operand:HI 0 "register_operand" "=r")
1376         (not:HI (match_operand:HI 1 "register_operand" "0")))]
1377   "TARGET_H8300H || TARGET_H8300S"
1378   "not  %T0"
1379   [(set_attr "cc" "set_znv")
1380    (set_attr "length" "2")])
1382 (define_expand "one_cmplsi2"
1383   [(set (match_operand:SI 0 "register_operand" "=r")
1384         (not:SI (match_operand:SI 1 "register_operand" "0")))]
1385   ""
1386   "")
1388 (define_insn ""
1389   [(set (match_operand:SI 0 "register_operand" "=r")
1390         (not:SI (match_operand:SI 1 "register_operand" "0")))]
1391   "TARGET_H8300"
1392   "not  %w0\;not        %x0\;not        %y0\;not        %z0"
1393   [(set_attr "cc" "clobber")
1394    (set_attr "length" "8")])
1396 (define_insn ""
1397   [(set (match_operand:SI 0 "register_operand" "=r")
1398         (not:SI (match_operand:SI 1 "register_operand" "0")))]
1399   "TARGET_H8300H || TARGET_H8300S"
1400   "not  %S0"
1401   [(set_attr "cc" "set_znv")
1402    (set_attr "length" "2")])
1404 ;; ----------------------------------------------------------------------
1405 ;; JUMP INSTRUCTIONS
1406 ;; ----------------------------------------------------------------------
1408 ;; Conditional jump instructions
1410 (define_expand "ble"
1411   [(set (pc)
1412         (if_then_else (le (cc0)
1413                           (const_int 0))
1414                       (label_ref (match_operand 0 "" ""))
1415                       (pc)))]
1416   ""
1417   "")
1419 (define_expand "bleu"
1420   [(set (pc)
1421         (if_then_else (leu (cc0)
1422                            (const_int 0))
1423                       (label_ref (match_operand 0 "" ""))
1424                       (pc)))]
1425   ""
1426   "")
1428 (define_expand "bge"
1429   [(set (pc)
1430         (if_then_else (ge (cc0)
1431                           (const_int 0))
1432                       (label_ref (match_operand 0 "" ""))
1433                       (pc)))]
1434   ""
1435   "")
1437 (define_expand "bgeu"
1438   [(set (pc)
1439         (if_then_else (geu (cc0)
1440                            (const_int 0))
1441                       (label_ref (match_operand 0 "" ""))
1442                       (pc)))]
1443   ""
1444   "")
1446 (define_expand "blt"
1447   [(set (pc)
1448         (if_then_else (lt (cc0)
1449                           (const_int 0))
1450                       (label_ref (match_operand 0 "" ""))
1451                       (pc)))]
1452   ""
1453   "")
1455 (define_expand "bltu"
1456   [(set (pc)
1457         (if_then_else (ltu (cc0)
1458                            (const_int 0))
1459                       (label_ref (match_operand 0 "" ""))
1460                       (pc)))]
1461   ""
1462   "")
1464 (define_expand "bgt"
1465   [(set (pc)
1466         (if_then_else (gt (cc0)
1467                           (const_int 0))
1468                       (label_ref (match_operand 0 "" ""))
1469                       (pc)))]
1470   ""
1471   "")
1473 (define_expand "bgtu"
1474   [(set (pc)
1475         (if_then_else (gtu (cc0)
1476                            (const_int 0))
1477                       (label_ref (match_operand 0 "" ""))
1478                       (pc)))]
1479   ""
1480   "")
1482 (define_expand "beq"
1483   [(set (pc)
1484         (if_then_else (eq (cc0)
1485                           (const_int 0))
1486                       (label_ref (match_operand 0 "" ""))
1487                       (pc)))]
1488   ""
1489   "")
1491 (define_expand "bne"
1492   [(set (pc)
1493         (if_then_else (ne (cc0)
1494                           (const_int 0))
1495                       (label_ref (match_operand 0 "" ""))
1496                       (pc)))]
1497   ""
1498   "")
1500 (define_insn "branch_true"
1501   [(set (pc)
1502         (if_then_else (match_operator 1 "comparison_operator"
1503                                       [(cc0) (const_int 0)])
1504                       (label_ref (match_operand 0 "" ""))
1505                       (pc)))]
1506   ""
1507   "*
1509   if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0
1510       && (GET_CODE (operands[1]) == GT
1511           || GET_CODE (operands[1]) == GE
1512           || GET_CODE (operands[1]) == LE
1513           || GET_CODE (operands[1]) == LT))
1514     {
1515       cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
1516       return 0;
1517     }
1519   if (get_attr_length (insn) == 2)
1520     return \"b%j1       %l0\";
1521   else if (get_attr_length (insn) == 4)
1522     return \"b%j1       %l0:16\";
1523   else
1524     return \"b%k1       .Lh8BR%=\;jmp   @%l0\\n.Lh8BR%=:\";
1526  [(set_attr "type" "branch")
1527    (set_attr "cc" "none")])
1529 (define_insn "branch_false"
1530   [(set (pc)
1531         (if_then_else (match_operator 1 "comparison_operator"
1532                                       [(cc0) (const_int 0)])
1533                       (pc)
1534                       (label_ref (match_operand 0 "" ""))))]
1535   ""
1536   "*
1538   if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0
1539       && (GET_CODE (operands[1]) == GT
1540           || GET_CODE (operands[1]) == GE
1541           || GET_CODE (operands[1]) == LE
1542           || GET_CODE (operands[1]) == LT))
1543     {
1544       cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
1545       return 0;
1546     }
1548   if (get_attr_length (insn) == 2)
1549     return \"b%k1       %l0\";
1550   else if (get_attr_length (insn) == 4)
1551     return \"b%k1       %l0:16\";
1552   else
1553     return \"b%j1       .Lh8BR%=\;jmp   @%l0\\n.Lh8BR%=:\";
1555   [(set_attr "type" "branch")
1556    (set_attr "cc" "none")])
1558 ;; Unconditional and other jump instructions.
1560 (define_insn "jump"
1561   [(set (pc)
1562         (label_ref (match_operand 0 "" "")))]
1563   ""
1564   "*
1566   if (get_attr_length (insn) == 2)
1567     return \"bra        %l0\";
1568   else if (get_attr_length (insn) == 4)
1569     return \"bra        %l0:16\";
1570   else
1571     return \"jmp        @%l0\";
1573   [(set_attr "type" "branch")
1574    (set_attr "cc" "none")])
1576 ;; This is a define expand, because pointers may be either 16 or 32 bits.
1578 (define_expand "tablejump"
1579   [(parallel [(set (pc) (match_operand 0 "register_operand" ""))
1580               (use (label_ref (match_operand 1 "" "")))])]
1581   ""
1582   "")
1584 (define_insn "tablejump_h8300"
1585   [(set (pc) (match_operand:HI 0 "register_operand" "r"))
1586    (use (label_ref (match_operand 1 "" "")))]
1587   "TARGET_H8300"
1588   "jmp  @%0"
1589   [(set_attr "cc" "none")
1590    (set_attr "length" "2")])
1592 (define_insn "tablejump_h8300h"
1593   [(set (pc) (match_operand:SI 0 "register_operand" "r"))
1594    (use (label_ref (match_operand 1 "" "")))]
1595   "TARGET_H8300H || TARGET_H8300S"
1596   "jmp  @%0"
1597   [(set_attr "cc" "none")
1598    (set_attr "length" "2")])
1600 ;; This is a define expand, because pointers may be either 16 or 32 bits.
1602 (define_expand "indirect_jump"
1603   [(set (pc) (match_operand 0 "jump_address_operand" ""))]
1604   ""
1605   "")
1607 (define_insn "indirect_jump_h8300"
1608   [(set (pc) (match_operand:HI 0 "jump_address_operand" "Vr"))]
1609   "TARGET_H8300"
1610   "jmp  @%0"
1611   [(set_attr "cc" "none")
1612    (set_attr "length" "2")])
1614 (define_insn "indirect_jump_h8300h"
1615   [(set (pc) (match_operand:SI 0 "jump_address_operand" "Vr"))]
1616   "TARGET_H8300H || TARGET_H8300S"
1617   "jmp @%0"
1618   [(set_attr "cc" "none")
1619    (set_attr "length" "2")])
1621 ;; Call subroutine with no return value.
1623 ;; ??? Even though we use HImode here, this works on the H8/300H and H8/S.
1625 (define_insn "call"
1626   [(call (match_operand:QI 0 "call_insn_operand" "or")
1627          (match_operand:HI 1 "general_operand" "g"))]
1628   ""
1629   "*
1631   if (GET_CODE (XEXP (operands[0], 0)) == SYMBOL_REF
1632       && SYMBOL_REF_FLAG (XEXP (operands[0], 0)))
1633     return \"jsr\\t@%0:8\";
1634   else
1635     return \"jsr\\t%0\";
1637   [(set_attr "cc" "clobber")
1638    (set (attr "length")
1639         (if_then_else (match_operand:QI 0 "small_call_insn_operand" "")
1640                       (const_int 4)
1641                       (const_int 8)))])
1643 ;; Call subroutine, returning value in operand 0
1644 ;; (which must be a hard register).
1646 ;; ??? Even though we use HImode here, this works on the H8/300H and H8/S.
1648 (define_insn "call_value"
1649   [(set (match_operand 0 "" "=r")
1650         (call (match_operand:QI 1 "call_insn_operand" "or")
1651               (match_operand:HI 2 "general_operand" "g")))]
1652   ""
1653   "*
1655   if (GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF
1656       && SYMBOL_REF_FLAG (XEXP (operands[1], 0)))
1657     return \"jsr\\t@%1:8\";
1658   else
1659     return \"jsr\\t%1\";
1661   [(set_attr "cc" "clobber")
1662    (set (attr "length")
1663         (if_then_else (match_operand:QI 0 "small_call_insn_operand" "")
1664                       (const_int 4)
1665                       (const_int 8)))])
1667 (define_insn "nop"
1668   [(const_int 0)]
1669   ""
1670   "nop"
1671   [(set_attr "cc" "none")
1672    (set_attr "length" "2")])
1674 ;; ----------------------------------------------------------------------
1675 ;; EXTEND INSTRUCTIONS
1676 ;; ----------------------------------------------------------------------
1678 (define_expand "zero_extendqihi2"
1679   [(set (match_operand:HI 0 "register_operand" "")
1680         (zero_extend:HI (match_operand:QI 1 "general_operand_src" "")))]
1681   ""
1682   "")
1684 (define_insn ""
1685   [(set (match_operand:HI 0 "register_operand" "=r,r")
1686         (zero_extend:HI (match_operand:QI 1 "general_operand_src" "0,g>")))]
1687   "TARGET_H8300"
1688   "@
1689   mov.b #0,%t0
1690   mov.b %R1,%s0\;mov.b  #0,%t0"
1691   [(set_attr "length" "2,10")
1692    (set_attr "cc" "clobber,clobber")])
1694 (define_insn ""
1695   [(set (match_operand:HI 0 "register_operand" "=r,r")
1696         (zero_extend:HI (match_operand:QI 1 "general_operand_src" "0,g>")))]
1697   "TARGET_H8300H || TARGET_H8300S"
1698   "@
1699   extu.w        %T0
1700   mov.b %R1,%s0\;extu.w %T0"
1701   [(set_attr "length" "2,10")
1702    (set_attr "cc" "set_znv,set_znv")])
1704 ;; The compiler can synthesize a 300H variant of this which is
1705 ;; just as efficient as one that we'd create
1706 (define_insn "zero_extendqisi2"
1707   [(set (match_operand:SI 0 "register_operand" "=r,r")
1708         (zero_extend:SI (match_operand:QI 1 "general_operand_src" "0,g>")))]
1709   "TARGET_H8300"
1710   "@
1711   mov.b #0,%x0\;sub.w   %e0,%e0
1712   mov.b %R1,%w0\;mov.b  #0,%x0\;sub.w   %e0,%e0"
1713   [(set_attr "length" "4,6")
1714    (set_attr "cc" "clobber,clobber")])
1716 (define_expand "zero_extendhisi2"
1717   [(set (match_operand:SI 0 "register_operand" "")
1718         (zero_extend:SI (match_operand:HI 1 "register_operand" "")))]
1719   ""
1720   "")
1722 ;; %e prints the high part of a CONST_INT, not the low part.  Arggh.
1723 (define_insn ""
1724   [(set (match_operand:SI 0 "register_operand" "=r,r,r")
1725         (zero_extend:SI (match_operand:HI 1 "general_operand_src" "0,i,g>")))]
1726   "TARGET_H8300"
1727   "@
1728   sub.w %e0,%e0
1729   mov.w %f1,%f0\;sub.w  %e0,%e0
1730   mov.w %e1,%f0\;sub.w  %e0,%e0"
1731   [(set_attr "length" "2,4,4")
1732    (set_attr "cc" "clobber,clobber,clobber")])
1734 (define_insn ""
1735   [(set (match_operand:SI 0 "register_operand" "=r")
1736         (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))]
1737   "TARGET_H8300H || TARGET_H8300S"
1738   "extu.l       %S0"
1739   [(set_attr "length" "2")
1740    (set_attr "cc" "set_znv")])
1742 (define_expand "extendqihi2"
1743   [(set (match_operand:HI 0 "register_operand" "")
1744         (sign_extend:HI (match_operand:QI 1 "register_operand" "")))]
1745   ""
1746   "")
1748 (define_insn ""
1749   [(set (match_operand:HI 0 "register_operand" "=r,r")
1750         (sign_extend:HI (match_operand:QI 1 "general_operand_src" "0,g>")))]
1751   "TARGET_H8300"
1752   "@
1753   bld   #7,%s0\;subx    %t0,%t0
1754   mov.b %R1,%s0\;bld    #7,%s0\;subx    %t0,%t0"
1755   [(set_attr "length" "4,8")
1756    (set_attr "cc" "clobber,clobber")])
1758 (define_insn ""
1759   [(set (match_operand:HI 0 "register_operand" "=r")
1760         (sign_extend:HI (match_operand:QI 1 "register_operand" "0")))]
1761   "TARGET_H8300H || TARGET_H8300S"
1762   "exts.w       %T0"
1763   [(set_attr "length" "2")
1764    (set_attr "cc" "set_znv")])
1766 ;; The compiler can synthesize a 300H variant of this which is
1767 ;; just as efficient as one that we'd create
1768 (define_insn "extendqisi2"
1769   [(set (match_operand:SI 0 "register_operand" "=r,r")
1770         (sign_extend:SI (match_operand:QI 1 "general_operand_src" "0,g>")))]
1771   "TARGET_H8300"
1772   "@
1773   bld   #7,%w0\;subx    %x0,%x0\;subx   %y0,%y0\;subx   %z0,%z0
1774   mov.b %R1,%w0\;bld    #7,%w0\;subx    %x0,%x0\;subx   %y0,%y0\;subx   %z0,%z0"
1775   [(set_attr "length" "8,10")
1776    (set_attr "cc" "clobber,clobber")])
1778 (define_expand "extendhisi2"
1779   [(set (match_operand:SI 0 "register_operand" "")
1780         (sign_extend:SI (match_operand:HI 1 "register_operand" "")))]
1781   ""
1782   "")
1784 (define_insn ""
1785   [(set (match_operand:SI 0 "register_operand" "=r,r")
1786         (sign_extend:SI (match_operand:HI 1 "general_operand_src" "0,g>")))]
1787   "TARGET_H8300"
1788   "@
1789   bld   #7,%x0\;subx    %y0,%y0\;subx   %z0,%z0
1790   mov.w %T1,%f0\;bld    #7,%x0\;subx    %y0,%y0\;subx   %z0,%z0"
1791   [(set_attr "length" "6,8")
1792    (set_attr "cc" "clobber,clobber")])
1794 (define_insn ""
1795   [(set (match_operand:SI 0 "register_operand" "=r")
1796         (sign_extend:SI (match_operand:HI 1 "register_operand" "0")))]
1797   "TARGET_H8300H || TARGET_H8300S"
1798   "exts.l       %S0"
1799   [(set_attr "length" "2")
1800    (set_attr "cc" "set_znv")])
1802 ;; ----------------------------------------------------------------------
1803 ;; SHIFTS
1804 ;; ----------------------------------------------------------------------
1806 ;; We make some attempt to provide real efficient shifting.  One example is
1807 ;; doing an 8 bit shift of a 16 bit value by moving a byte reg into the other
1808 ;; reg and moving 0 into the former reg.
1810 ;; We also try to achieve this in a uniform way.  IE: We don't try to achieve
1811 ;; this in both rtl and at insn emit time.  Ideally, we'd use rtl as that would
1812 ;; give the optimizer more cracks at the code.  However, we wish to do things
1813 ;; like optimizing shifting the sign bit to bit 0 by rotating the other way.
1814 ;; There is rtl to handle this (rotate + and), but the H8/300 doesn't handle
1815 ;; 16 bit rotates.  Also, if we emit complicated rtl, combine may not be able
1816 ;; to detect cases it can optimize.
1818 ;; For these and other fuzzy reasons, I've decided to go the less pretty but
1819 ;; easier "do it at insn emit time" route.
1821 ;; QI BIT SHIFTS
1823 (define_expand "ashlqi3"
1824   [(set (match_operand:QI 0 "register_operand" "")
1825         (ashift:QI (match_operand:QI 1 "register_operand" "")
1826                    (match_operand:QI 2 "nonmemory_operand" "")))]
1827   ""
1828   "if (expand_a_shift (QImode, ASHIFT, operands)) DONE; else FAIL;")
1830 (define_expand "ashrqi3"
1831   [(set (match_operand:QI 0 "register_operand" "")
1832         (ashiftrt:QI (match_operand:QI 1 "register_operand" "")
1833                      (match_operand:QI 2 "nonmemory_operand" "")))]
1834   ""
1835   "if (expand_a_shift (QImode, ASHIFTRT, operands)) DONE; else FAIL;")
1837 (define_expand "lshrqi3"
1838   [(set (match_operand:QI 0 "register_operand" "")
1839         (lshiftrt:QI (match_operand:QI 1 "register_operand" "")
1840                      (match_operand:QI 2 "nonmemory_operand" "")))]
1841   ""
1842   "if (expand_a_shift (QImode, LSHIFTRT, operands)) DONE; else FAIL;")
1844 (define_insn ""
1845   [(set (match_operand:QI 0 "register_operand" "=r,r")
1846         (match_operator:QI 3 "nshift_operator"
1847                         [ (match_operand:QI 1 "register_operand" "0,0")
1848                           (match_operand:QI 2 "nonmemory_operand" "KM,rn")]))
1849    (clobber (match_scratch:QI 4 "=X,&r"))]
1850   ""
1851   "* return output_a_shift (operands);"
1852   [(set_attr "length" "20")
1853    (set_attr "cc" "clobber")])
1855 ;; HI BIT SHIFTS
1857 (define_expand "ashlhi3"
1858   [(set (match_operand:HI 0 "register_operand" "")
1859         (ashift:HI (match_operand:HI 1 "nonmemory_operand" "")
1860                    (match_operand:QI 2 "nonmemory_operand" "")))]
1861   ""
1862   "if (expand_a_shift (HImode, ASHIFT, operands)) DONE; else FAIL;")
1864 (define_expand "lshrhi3"
1865   [(set (match_operand:HI 0 "register_operand" "")
1866         (lshiftrt:HI (match_operand:HI 1 "general_operand" "")
1867                      (match_operand:QI 2 "nonmemory_operand" "")))]
1868   ""
1869   "if (expand_a_shift (HImode, LSHIFTRT, operands)) DONE; else FAIL;")
1871 (define_expand "ashrhi3"
1872   [(set (match_operand:HI 0 "register_operand" "")
1873         (ashiftrt:HI (match_operand:HI 1 "register_operand" "")
1874                      (match_operand:QI 2 "nonmemory_operand" "")))]
1875   ""
1876   "if (expand_a_shift (HImode, ASHIFTRT, operands)) DONE; else FAIL;")
1878 (define_insn ""
1879   [(set (match_operand:HI 0 "register_operand" "=r,r")
1880         (match_operator:HI 3 "nshift_operator"
1881                         [ (match_operand:HI 1 "register_operand" "0,0")
1882                           (match_operand:QI 2 "nonmemory_operand" "KM,rn")]))
1883    (clobber (match_scratch:QI 4 "=X,&r"))]
1884   ""
1885   "* return output_a_shift (operands);"
1886   [(set_attr "length" "20")
1887    (set_attr "cc" "clobber")])
1889 ;;  SI BIT SHIFTS
1891 (define_expand "ashlsi3"
1892   [(set (match_operand:SI 0 "register_operand" "")
1893         (ashift:SI (match_operand:SI 1 "general_operand" "")
1894                    (match_operand:QI 2 "nonmemory_operand" "")))]
1895   ""
1896   "if (expand_a_shift (SImode, ASHIFT, operands)) DONE; else FAIL;")
1898 (define_expand "lshrsi3"
1899   [(set (match_operand:SI 0 "register_operand" "")
1900         (lshiftrt:SI (match_operand:SI 1 "general_operand" "")
1901                      (match_operand:QI 2 "nonmemory_operand" "")))]
1902   ""
1903   "if (expand_a_shift (SImode, LSHIFTRT, operands)) DONE; else FAIL;")
1905 (define_expand "ashrsi3"
1906   [(set (match_operand:SI 0 "register_operand" "")
1907         (ashiftrt:SI (match_operand:SI 1 "general_operand" "")
1908                      (match_operand:QI 2 "nonmemory_operand" "")))]
1909   ""
1910   "if (expand_a_shift (SImode, ASHIFTRT, operands)) DONE; else FAIL;")
1912 (define_insn ""
1913   [(set (match_operand:SI 0 "register_operand" "=r,r")
1914         (match_operator:SI 3 "nshift_operator"
1915                         [ (match_operand:SI 1 "register_operand" "0,0")
1916                           (match_operand:QI 2 "nonmemory_operand" "K,rn")]))
1917    (clobber (match_scratch:QI 4 "=X,&r"))]
1918   ""
1919   "* return output_a_shift (operands);"
1920   [(set_attr "length" "20")
1921    (set_attr "cc" "clobber")])
1923 ;; ----------------------------------------------------------------------
1924 ;; ROTATIONS
1925 ;; ----------------------------------------------------------------------
1927 (define_expand "rotlqi3"
1928   [(set (match_operand:QI 0 "register_operand" "")
1929         (rotate:QI (match_operand:QI 1 "register_operand" "")
1930                    (match_operand:QI 2 "nonmemory_operand" "")))]
1931   ""
1932   "if (expand_a_rotate (ROTATE, operands)) DONE; else FAIL;")
1934 (define_insn "*rotlqi3_1"
1935   [(set (match_operand:QI 0 "register_operand" "=r")
1936         (rotate:QI (match_operand:QI 1 "register_operand" "0")
1937                    (match_operand:QI 2 "immediate_operand" "")))]
1938   ""
1939   "* return emit_a_rotate (ROTATE, operands);"
1940   [(set_attr "length" "20")
1941    (set_attr "cc" "clobber")])
1943 (define_expand "rotlhi3"
1944   [(set (match_operand:HI 0 "register_operand" "")
1945         (rotate:HI (match_operand:HI 1 "register_operand" "")
1946                    (match_operand:QI 2 "nonmemory_operand" "")))]
1947   ""
1948   "if (expand_a_rotate (ROTATE, operands)) DONE; else FAIL;")
1950 (define_insn "*rotlhi3_1"
1951   [(set (match_operand:HI 0 "register_operand" "=r")
1952         (rotate:HI (match_operand:HI 1 "register_operand" "0")
1953                    (match_operand:QI 2 "immediate_operand" "")))]
1954   ""
1955   "* return emit_a_rotate (ROTATE, operands);"
1956   [(set_attr "length" "20")
1957    (set_attr "cc" "clobber")])
1959 (define_expand "rotlsi3"
1960   [(set (match_operand:SI 0 "register_operand" "")
1961         (rotate:SI (match_operand:SI 1 "register_operand" "")
1962                    (match_operand:QI 2 "nonmemory_operand" "")))]
1963   "TARGET_H8300H || TARGET_H8300S"
1964   "if (expand_a_rotate (ROTATE, operands)) DONE; else FAIL;")
1966 (define_insn "*rotlsi3_1"
1967   [(set (match_operand:SI 0 "register_operand" "=r")
1968         (rotate:SI (match_operand:SI 1 "register_operand" "0")
1969                    (match_operand:QI 2 "immediate_operand" "")))]
1970   "TARGET_H8300H || TARGET_H8300S"
1971   "* return emit_a_rotate (ROTATE, operands);"
1972   [(set_attr "length" "20")
1973    (set_attr "cc" "clobber")])
1975 ;; -----------------------------------------------------------------
1976 ;; BIT FIELDS
1977 ;; -----------------------------------------------------------------
1978 ;; The H8/300 has given 1/8th of its opcode space to bitfield
1979 ;; instructions so let's use them as well as we can.
1981 ;; You'll never believe all these patterns perform one basic action --
1982 ;; load a bit from the source, optionally invert the bit, then store it
1983 ;; in the destination (which is known to be zero).
1985 ;; Combine obviously need some work to better identify this situation and
1986 ;; canonicalize the form better.
1989 ;; Normal loads with a 16bit destination.
1992 (define_insn ""
1993   [(set (match_operand:HI 0 "register_operand" "=&r")
1994         (zero_extract:HI (match_operand:HI 1 "register_operand" "r")
1995                          (const_int 1)
1996                          (match_operand:HI 2 "immediate_operand" "n")))]
1997   "TARGET_H8300"
1998   "sub.w        %0,%0\;bld      %Z2,%Y1\;bst    #0,%X0"
1999   [(set_attr "cc" "clobber")
2000    (set_attr "length" "6")])
2003 ;; Inverted loads with a 16bit destination.
2006 (define_insn ""
2007   [(set (match_operand:HI 0 "register_operand" "=&r")
2008         (zero_extract:HI (xor:HI (match_operand:HI 1 "register_operand" "r")
2009                                  (match_operand:HI 3 "p_operand" "P"))
2010                          (const_int 1)
2011                          (match_operand:HI 2 "const_int_operand" "n")))]
2012   "TARGET_H8300
2013    && (1 << INTVAL (operands[2])) == INTVAL (operands[3])"
2014   "sub.w        %0,%0\;bild     %Z2,%Y1\;bst    #0,%X0"
2015   [(set_attr "cc" "clobber")
2016    (set_attr "length" "8")])
2019 ;; Normal loads with a 32bit destination.
2022 (define_insn ""
2023   [(set (match_operand:SI 0 "register_operand" "=&r")
2024         (zero_extract:SI (match_operand:HI 1 "register_operand" "r")
2025                          (const_int 1)
2026                          (match_operand 2 "const_int_operand" "n")))]
2027   "TARGET_H8300
2028    && INTVAL (operands[2]) < 16"
2029   "* return output_simode_bld (0, operands);"
2030   [(set_attr "cc" "clobber")
2031    (set_attr "length" "6")])
2033 (define_insn ""
2034   [(set (match_operand:SI 0 "register_operand" "=&r")
2035         (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
2036                          (const_int 1)
2037                          (match_operand 2 "const_int_operand" "n")))]
2038   "(TARGET_H8300H || TARGET_H8300S)
2039    && INTVAL (operands[2]) < 16"
2040   "* return output_simode_bld (0, operands);"
2041   [(set_attr "cc" "clobber")
2042    (set_attr "length" "6")])
2045 ;; Inverted loads with a 32bit destination.
2048 (define_insn ""
2049   [(set (match_operand:SI 0 "register_operand" "=&r")
2050         (zero_extract:SI (xor:HI (match_operand:HI 1 "register_operand" "r")
2051                                  (match_operand:HI 3 "const_int_operand" "n"))
2052                          (const_int 1)
2053                          (match_operand 2 "const_int_operand" "n")))]
2054   "TARGET_H8300
2055    && INTVAL (operands[2]) < 16
2056    && (1 << INTVAL (operands[2])) == INTVAL (operands[3])"
2057   "* return output_simode_bld (1, operands);"
2058   [(set_attr "cc" "clobber")
2059    (set_attr "length" "6")])
2061 (define_insn ""
2062   [(set (match_operand:SI 0 "register_operand" "=&r")
2063         (zero_extract:SI (xor:SI (match_operand:SI 1 "register_operand" "r")
2064                                  (match_operand 3 "const_int_operand" "n"))
2065                          (const_int 1)
2066                          (match_operand 2 "const_int_operand" "n")))]
2067   "(TARGET_H8300H || TARGET_H8300S)
2068    && INTVAL (operands[2]) < 16
2069    && (1 << INTVAL (operands[2])) == INTVAL (operands[3])"
2070   "* return output_simode_bld (1, operands);"
2071   [(set_attr "cc" "clobber")
2072    (set_attr "length" "6")])
2074 (define_expand "insv"
2075   [(set (zero_extract:HI (match_operand:HI 0 "general_operand" "")
2076                          (match_operand:HI 1 "general_operand" "")
2077                          (match_operand:HI 2 "general_operand" ""))
2078         (match_operand:HI 3 "general_operand" ""))]
2079   "TARGET_H8300"
2080   "
2082   /* We only have single bit bitfield instructions.  */
2083   if (INTVAL (operands[1]) != 1)
2084     FAIL;
2086   /* For now, we don't allow memory operands.  */
2087   if (GET_CODE (operands[0]) == MEM
2088       || GET_CODE (operands[3]) == MEM)
2089     FAIL;
2092 (define_insn ""
2093   [(set (zero_extract:HI (match_operand:HI 0 "register_operand" "+r")
2094                          (const_int 1)
2095                          (match_operand:HI 1 "immediate_operand" "n"))
2096         (match_operand:HI 2 "register_operand" "r"))]
2097   ""
2098   "bld  #0,%R2\;bst     %Z1,%Y0 ; i1"
2099   [(set_attr "cc" "clobber")
2100    (set_attr "length" "4")])
2102 (define_expand "extzv"
2103   [(set (match_operand:HI 0 "register_operand" "")
2104         (zero_extract:HI (match_operand:HI 1 "bit_operand" "")
2105                          (match_operand:HI 2 "general_operand" "")
2106                          (match_operand:HI 3 "general_operand" "")))]
2107   "TARGET_H8300"
2108   "
2110   /* We only have single bit bitfield instructions.  */
2111   if (INTVAL (operands[2]) != 1)
2112     FAIL;
2114   /* For now, we don't allow memory operands.  */
2115   if (GET_CODE (operands[1]) == MEM)
2116     FAIL;
2119 ;; BAND, BOR, and BXOR patterns
2121 (define_insn ""
2122   [(set (match_operand:HI 0 "bit_operand" "=Ur")
2123         (match_operator:HI 4 "bit_operator"
2124            [(zero_extract:HI (match_operand:HI 1 "register_operand" "r")
2125                              (const_int 1)
2126                              (match_operand:HI 2 "immediate_operand" "n"))
2127             (match_operand:HI 3 "bit_operand" "0")]))]
2128   ""
2129   "bld  %Z2,%Y1\;%b4    #0,%R0\;bst     #0,%R0; bl1"
2130   [(set_attr "cc" "clobber")
2131    (set_attr "length" "6")
2132    (set_attr "adjust_length" "no")])
2134 (define_insn ""
2135   [(set (match_operand:HI 0 "bit_operand" "=Ur")
2136         (match_operator:HI 5 "bit_operator"
2137            [(zero_extract:HI (match_operand:HI 1 "register_operand" "r")
2138                              (const_int 1)
2139                              (match_operand:HI 2 "immediate_operand" "n"))
2140             (zero_extract:HI (match_operand:HI 3 "register_operand" "r")
2141                              (const_int 1)
2142                              (match_operand:HI 4 "immediate_operand" "n"))]))]
2143   ""
2144   "bld  %Z2,%Y1\;%b5    %Z4,%Y3\;bst    #0,%R0; bl3"
2145   [(set_attr "cc" "clobber")
2146    (set_attr "length" "6")
2147    (set_attr "adjust_length" "no")])
2149 ;; -----------------------------------------------------------------
2150 ;; COMBINE PATTERNS
2151 ;; -----------------------------------------------------------------
2153 (define_insn ""
2154   [(set (match_operand:HI 0 "register_operand" "=r")
2155         (ior:HI (zero_extend:HI (match_operand:QI 1 "register_operand" "r"))
2156                 (match_operand:HI 2 "register_operand" "0")))]
2157   "REG_P (operands[0])
2158    && REG_P (operands[1])
2159    && REGNO (operands[0]) != REGNO (operands[1])"
2160   "or\\t%X1,%s0"
2161   [(set_attr "cc" "clobber")
2162    (set_attr "length" "2")])
2164 (define_insn ""
2165   [(set (match_operand:SI 0 "register_operand" "=r")
2166         (ior:SI (zero_extend:SI (match_operand:HI 1 "register_operand" "r"))
2167                 (match_operand:SI 2 "register_operand" "0")))]
2168   "(TARGET_H8300H || TARGET_H8300S)
2169    && REG_P (operands[0])
2170    && REG_P (operands[1])
2171    && (REGNO (operands[0]) != REGNO (operands[1]))"
2172   "or.w\\t%T1,%f0"
2173   [(set_attr "cc" "clobber")
2174    (set_attr "length" "2")])
2176 (define_insn ""
2177   [(set (match_operand:SI 0 "register_operand" "=r")
2178         (ior:SI (zero_extend:SI (match_operand:QI 1 "register_operand" "r"))
2179                 (match_operand:SI 2 "register_operand" "0")))]
2180   "REG_P (operands[0])
2181    && REG_P (operands[1])
2182    && REGNO (operands[0]) != REGNO (operands[1])"
2183   "or\\t%X1,%s0"
2184   [(set_attr "cc" "clobber")
2185    (set_attr "length" "2")])
2187 (define_insn ""
2188   [(set (match_operand:HI 0 "register_operand" "=r")
2189         (xor:HI (zero_extend:HI (match_operand:QI 1 "register_operand" "r"))
2190                 (match_operand:HI 2 "register_operand" "0")))]
2191   "REG_P (operands[0])
2192    && REG_P (operands[1])
2193    && REGNO (operands[0]) != REGNO (operands[1])"
2194   "xor\\t%X1,%s0"
2195   [(set_attr "cc" "clobber")
2196    (set_attr "length" "2")])
2198 (define_insn ""
2199   [(set (match_operand:SI 0 "register_operand" "=r")
2200         (xor:SI (zero_extend:SI (match_operand:HI 1 "register_operand" "r"))
2201                 (match_operand:SI 2 "register_operand" "0")))]
2202   "(TARGET_H8300H || TARGET_H8300S)
2203    && REG_P (operands[0])
2204    && REG_P (operands[1])
2205    && (REGNO (operands[0]) != REGNO (operands[1]))"
2206   "xor.w\\t%T1,%f0"
2207   [(set_attr "cc" "clobber")
2208    (set_attr "length" "2")])
2210 (define_insn ""
2211   [(set (match_operand:SI 0 "register_operand" "=r")
2212         (xor:SI (zero_extend:SI (match_operand:QI 1 "register_operand" "r"))
2213                 (match_operand:SI 2 "register_operand" "0")))]
2214   "REG_P (operands[0])
2215    && REG_P (operands[1])
2216    && REGNO (operands[0]) != REGNO (operands[1])"
2217   "xor\\t%X1,%s0"
2218   [(set_attr "cc" "clobber")
2219    (set_attr "length" "2")])
2221 (define_insn ""
2222   [(set (match_operand:HI 0 "register_operand" "=r")
2223         (ior:HI (zero_extend:HI (match_operand:QI 1 "register_operand" "0"))
2224                 (ashift:HI (match_operand:HI 2 "register_operand" "r")
2225                            (const_int 8))))]
2226   "REG_P (operands[0])
2227    && REG_P (operands[2])
2228    && REGNO (operands[0]) != REGNO (operands[2])"
2229   "mov.b\\t%s2,%t0"
2230   [(set_attr "cc" "clobber")
2231    (set_attr "length" "2")])
2233 (define_insn ""
2234   [(set (match_operand:SI 0 "register_operand" "=r")
2235         (ior:SI (zero_extend:SI (match_operand:HI 1 "register_operand" "0"))
2236                 (ashift:SI (match_operand:SI 2 "register_operand" "r")
2237                            (const_int 16))))]
2238   "(TARGET_H8300H || TARGET_H8300S)
2239    && REG_P (operands[0])
2240    && REG_P (operands[2])
2241    && (REGNO (operands[0]) != REGNO (operands[2]))"
2242   "mov.w\\t%f2,%e0"
2243   [(set_attr "cc" "clobber")
2244    (set_attr "length" "2")])