OSDN Git Service

* gcc/gcc/config/avr/avr.c (avr_arch_types): Add avr6 entry.
[pf3gnuchains/gcc-fork.git] / gcc / config / avr / avr.md
1 ;; -*- Mode: Scheme -*-
2 ;;   Machine description for GNU compiler,
3 ;;   for ATMEL AVR micro controllers.
4 ;;   Copyright (C) 1998, 1999, 2000, 2001, 2002, 2004, 2005, 2006, 2007, 2008
5 ;;   Free Software Foundation, Inc.
6 ;;   Contributed by Denis Chertykov (denisc@overta.ru)
7
8 ;; This file is part of GCC.
9
10 ;; GCC 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 3, or (at your option)
13 ;; any later version.
14
15 ;; GCC 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.
19
20 ;; You should have received a copy of the GNU General Public License
21 ;; along with GCC; see the file COPYING3.  If not see
22 ;; <http://www.gnu.org/licenses/>.
23
24 ;; Special characters after '%':
25 ;;  A  No effect (add 0).
26 ;;  B  Add 1 to REG number, MEM address or CONST_INT.
27 ;;  C  Add 2.
28 ;;  D  Add 3.
29 ;;  j  Branch condition.
30 ;;  k  Reverse branch condition.
31 ;;  o  Displacement for (mem (plus (reg) (const_int))) operands.
32 ;;  p  POST_INC or PRE_DEC address as a pointer (X, Y, Z)
33 ;;  r  POST_INC or PRE_DEC address as a register (r26, r28, r30)
34 ;;  ~  Output 'r' if not AVR_MEGA.
35 ;;  !  Output 'e' if AVR_HAVE_EIJMP_EICALL.
36
37 ;; UNSPEC usage:
38 ;;  0  Length of a string, see "strlenhi".
39 ;;  1  Jump by register pair Z or by table addressed by Z, see "casesi".
40
41 (define_constants
42   [(REG_X       26)
43    (REG_Y       28)
44    (REG_Z       30)
45    (REG_W       24)
46    (REG_SP      32)
47    (TMP_REGNO   0)      ; temporary register r0
48    (ZERO_REGNO  1)      ; zero register r1
49    
50    (SREG_ADDR   0x5F)
51    (RAMPZ_ADDR  0x5B)
52    
53    (UNSPEC_STRLEN       0)
54    (UNSPEC_INDEX_JMP    1)
55    (UNSPEC_SEI          2)
56    (UNSPEC_CLI          3)
57
58    (UNSPECV_PROLOGUE_SAVES      0)
59    (UNSPECV_EPILOGUE_RESTORES   1)])
60
61 (include "predicates.md")
62 (include "constraints.md")
63   
64 ;; Condition code settings.
65 (define_attr "cc" "none,set_czn,set_zn,set_n,compare,clobber"
66   (const_string "none"))
67
68 (define_attr "type" "branch,branch1,arith,xcall"
69   (const_string "arith"))
70
71 (define_attr "mcu_have_movw" "yes,no"
72   (const (if_then_else (symbol_ref "AVR_HAVE_MOVW")
73                        (const_string "yes")
74                        (const_string "no"))))
75
76 (define_attr "mcu_mega" "yes,no"
77   (const (if_then_else (symbol_ref "AVR_MEGA")
78                        (const_string "yes")
79                        (const_string "no"))))
80   
81
82 ;; The size of instructions in bytes.
83 ;; XXX may depend from "cc"
84
85 (define_attr "length" ""
86   (cond [(eq_attr "type" "branch")
87          (if_then_else (and (ge (minus (pc) (match_dup 0))
88                                 (const_int -63))
89                             (le (minus (pc) (match_dup 0))
90                                 (const_int 62)))
91                        (const_int 1)
92                        (if_then_else (and (ge (minus (pc) (match_dup 0))
93                                               (const_int -2045))
94                                           (le (minus (pc) (match_dup 0))
95                                               (const_int 2045)))
96                                      (const_int 2)
97                                      (const_int 3)))
98          (eq_attr "type" "branch1")
99          (if_then_else (and (ge (minus (pc) (match_dup 0))
100                                 (const_int -62))
101                             (le (minus (pc) (match_dup 0))
102                                 (const_int 61)))
103                        (const_int 2)
104                        (if_then_else (and (ge (minus (pc) (match_dup 0))
105                                               (const_int -2044))
106                                           (le (minus (pc) (match_dup 0))
107                                               (const_int 2043)))
108                                      (const_int 3)
109                                      (const_int 4)))
110          (eq_attr "type" "xcall")
111          (if_then_else (eq_attr "mcu_mega" "no")
112                        (const_int 1)
113                        (const_int 2))]
114         (const_int 2)))
115
116 (define_insn "*pushqi"
117   [(set (mem:QI (post_dec (reg:HI REG_SP)))
118         (match_operand:QI 0 "reg_or_0_operand" "r,L"))]
119   ""
120   "@
121         push %0
122         push __zero_reg__"
123   [(set_attr "length" "1,1")])
124
125
126 (define_insn "*pushhi"
127   [(set (mem:HI (post_dec (reg:HI REG_SP)))
128         (match_operand:HI 0 "reg_or_0_operand" "r,L"))]
129   ""
130   "@
131         push %B0\;push %A0
132         push __zero_reg__\;push __zero_reg__"
133   [(set_attr "length" "2,2")])
134
135 (define_insn "*pushsi"
136   [(set (mem:SI (post_dec (reg:HI REG_SP)))
137         (match_operand:SI 0 "reg_or_0_operand" "r,L"))]
138   ""
139   "@
140         push %D0\;push %C0\;push %B0\;push %A0
141         push __zero_reg__\;push __zero_reg__\;push __zero_reg__\;push __zero_reg__"
142   [(set_attr "length" "4,4")])
143
144 (define_insn "*pushsf"
145   [(set (mem:SF (post_dec (reg:HI REG_SP)))
146         (match_operand:SF 0 "register_operand" "r"))]
147   ""
148   "push %D0
149         push %C0
150         push %B0
151         push %A0"
152   [(set_attr "length" "4")])
153
154 ;;========================================================================
155 ;; move byte
156 ;; The last alternative (any immediate constant to any register) is
157 ;; very expensive.  It should be optimized by peephole2 if a scratch
158 ;; register is available, but then that register could just as well be
159 ;; allocated for the variable we are loading.  But, most of NO_LD_REGS
160 ;; are call-saved registers, and most of LD_REGS are call-used registers,
161 ;; so this may still be a win for registers live across function calls.
162
163 (define_expand "movqi"
164   [(set (match_operand:QI 0 "nonimmediate_operand" "")
165         (match_operand:QI 1 "general_operand" ""))]
166   ""
167   "/* One of the ops has to be in a register.  */
168    if (!register_operand(operand0, QImode)
169        && ! (register_operand(operand1, QImode) || const0_rtx == operand1))
170        operands[1] = copy_to_mode_reg(QImode, operand1);
171   ")
172
173 (define_insn "*movqi"
174   [(set (match_operand:QI 0 "nonimmediate_operand" "=r,d,Qm,r,q,r,*r")
175         (match_operand:QI 1 "general_operand"       "r,i,rL,Qm,r,q,i"))]
176   "(register_operand (operands[0],QImode)
177     || register_operand (operands[1], QImode) || const0_rtx == operands[1])"
178   "* return output_movqi (insn, operands, NULL);"
179   [(set_attr "length" "1,1,5,5,1,1,4")
180    (set_attr "cc" "none,none,clobber,clobber,none,none,clobber")])
181
182 ;; This is used in peephole2 to optimize loading immediate constants
183 ;; if a scratch register from LD_REGS happens to be available.
184
185 (define_insn "*reload_inqi"
186   [(set (match_operand:QI 0 "register_operand" "=l")
187         (match_operand:QI 1 "immediate_operand" "i"))
188    (clobber (match_operand:QI 2 "register_operand" "=&d"))]
189   "reload_completed"
190   "ldi %2,lo8(%1)
191         mov %0,%2"
192   [(set_attr "length" "2")
193    (set_attr "cc" "none")])
194
195 (define_peephole2
196   [(match_scratch:QI 2 "d")
197    (set (match_operand:QI 0 "l_register_operand" "")
198         (match_operand:QI 1 "immediate_operand" ""))]
199   "(operands[1] != const0_rtx
200     && operands[1] != const1_rtx
201     && operands[1] != constm1_rtx)"
202   [(parallel [(set (match_dup 0) (match_dup 1))
203               (clobber (match_dup 2))])]
204   "if (!avr_peep2_scratch_safe (operands[2]))
205      FAIL;")
206
207 ;;============================================================================
208 ;; move word (16 bit)
209
210 (define_expand "movhi"
211   [(set (match_operand:HI 0 "nonimmediate_operand" "")
212         (match_operand:HI 1 "general_operand"       ""))]
213   ""
214   "
215 {
216    /* One of the ops has to be in a register.  */
217   if (!register_operand(operand0, HImode)
218       && !(register_operand(operand1, HImode) || const0_rtx == operands[1]))
219     {
220       operands[1] = copy_to_mode_reg(HImode, operand1);
221     }
222 }")
223
224 (define_insn "*movhi_sp"
225   [(set (match_operand:HI 0 "register_operand" "=q,r")
226         (match_operand:HI 1 "register_operand"  "r,q"))]
227   "((stack_register_operand(operands[0], HImode) && register_operand (operands[1], HImode))
228     || (register_operand (operands[0], HImode) && stack_register_operand(operands[1], HImode)))"
229   "* return output_movhi (insn, operands, NULL);"
230   [(set_attr "length" "5,2")
231    (set_attr "cc" "none,none")])
232
233 (define_peephole2
234   [(match_scratch:QI 2 "d")
235    (set (match_operand:HI 0 "l_register_operand" "")
236         (match_operand:HI 1 "immediate_operand" ""))]
237   "(operands[1] != const0_rtx 
238     && operands[1] != constm1_rtx)"
239   [(parallel [(set (match_dup 0) (match_dup 1))
240               (clobber (match_dup 2))])]
241   "if (!avr_peep2_scratch_safe (operands[2]))
242      FAIL;")
243
244 ;; '*' because it is not used in rtl generation, only in above peephole
245 (define_insn "*reload_inhi"
246   [(set (match_operand:HI 0 "register_operand" "=r")
247         (match_operand:HI 1 "immediate_operand" "i"))
248    (clobber (match_operand:QI 2 "register_operand" "=&d"))]
249   "reload_completed"
250   "* return output_reload_inhi (insn, operands, NULL);"
251   [(set_attr "length" "4")
252    (set_attr "cc" "none")])
253
254 (define_insn "*movhi"
255   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,m,d,*r,q,r")
256         (match_operand:HI 1 "general_operand"       "r,m,rL,i,i,r,q"))]
257   "(register_operand (operands[0],HImode)
258     || register_operand (operands[1],HImode) || const0_rtx == operands[1])"
259   "* return output_movhi (insn, operands, NULL);"
260   [(set_attr "length" "2,6,7,2,6,5,2")
261    (set_attr "cc" "none,clobber,clobber,none,clobber,none,none")])
262
263 (define_peephole2 ; movw
264   [(set (match_operand:QI 0 "even_register_operand" "")
265         (match_operand:QI 1 "even_register_operand" ""))
266    (set (match_operand:QI 2 "odd_register_operand" "")
267         (match_operand:QI 3 "odd_register_operand" ""))]
268   "(AVR_HAVE_MOVW
269     && REGNO (operands[0]) == REGNO (operands[2]) - 1
270     && REGNO (operands[1]) == REGNO (operands[3]) - 1)"
271   [(set (match_dup 4) (match_dup 5))]
272   {
273     operands[4] = gen_rtx_REG (HImode, REGNO (operands[0]));
274     operands[5] = gen_rtx_REG (HImode, REGNO (operands[1]));
275   })
276
277 (define_peephole2 ; movw_r
278   [(set (match_operand:QI 0 "odd_register_operand" "")
279         (match_operand:QI 1 "odd_register_operand" ""))
280    (set (match_operand:QI 2 "even_register_operand" "")
281         (match_operand:QI 3 "even_register_operand" ""))]
282   "(AVR_HAVE_MOVW
283     && REGNO (operands[2]) == REGNO (operands[0]) - 1
284     && REGNO (operands[3]) == REGNO (operands[1]) - 1)"
285   [(set (match_dup 4) (match_dup 5))]
286   {
287     operands[4] = gen_rtx_REG (HImode, REGNO (operands[2]));
288     operands[5] = gen_rtx_REG (HImode, REGNO (operands[3]));
289   })
290
291 ;;==========================================================================
292 ;; move double word (32 bit)
293
294 (define_expand "movsi"
295   [(set (match_operand:SI 0 "nonimmediate_operand" "")
296         (match_operand:SI 1 "general_operand"  ""))]
297   ""
298   "
299 {
300   /* One of the ops has to be in a register.  */
301   if (!register_operand (operand0, SImode)
302       && !(register_operand (operand1, SImode) || const0_rtx == operand1))
303     {
304       operands[1] = copy_to_mode_reg (SImode, operand1);
305     }
306 }")
307
308
309
310 (define_peephole2
311   [(match_scratch:QI 2 "d")
312    (set (match_operand:SI 0 "l_register_operand" "")
313         (match_operand:SI 1 "immediate_operand" ""))]
314   "(operands[1] != const0_rtx
315     && operands[1] != constm1_rtx)"
316   [(parallel [(set (match_dup 0) (match_dup 1))
317               (clobber (match_dup 2))])]
318   "if (!avr_peep2_scratch_safe (operands[2]))
319      FAIL;")
320
321 ;; '*' because it is not used in rtl generation.
322 (define_insn "*reload_insi"
323   [(set (match_operand:SI 0 "register_operand" "=r")
324         (match_operand:SI 1 "immediate_operand" "i"))
325    (clobber (match_operand:QI 2 "register_operand" "=&d"))]
326   "reload_completed"
327   "* return output_reload_insisf (insn, operands, NULL);"
328   [(set_attr "length" "8")
329    (set_attr "cc" "none")])
330
331
332 (define_insn "*movsi"
333   [(set (match_operand:SI 0 "nonimmediate_operand" "=r,r,r,Qm,!d,r")
334         (match_operand:SI 1 "general_operand"       "r,L,Qm,rL,i,i"))]
335   "(register_operand (operands[0],SImode)
336     || register_operand (operands[1],SImode) || const0_rtx == operands[1])"
337   "* return output_movsisf (insn, operands, NULL);"
338   [(set_attr "length" "4,4,8,9,4,10")
339    (set_attr "cc" "none,set_zn,clobber,clobber,none,clobber")])
340
341 ;; fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
342 ;; move floating point numbers (32 bit)
343
344 (define_expand "movsf"
345   [(set (match_operand:SF 0 "nonimmediate_operand" "")
346         (match_operand:SF 1 "general_operand"  ""))]
347   ""
348   "
349 {
350   /* One of the ops has to be in a register.  */
351   if (!register_operand (operand1, SFmode)
352       && !register_operand (operand0, SFmode))
353     {
354       operands[1] = copy_to_mode_reg (SFmode, operand1);
355     }
356 }")
357
358 (define_insn "*movsf"
359   [(set (match_operand:SF 0 "nonimmediate_operand" "=r,r,r,Qm,!d,r")
360         (match_operand:SF 1 "general_operand"       "r,G,Qm,r,F,F"))]
361   "register_operand (operands[0], SFmode)
362    || register_operand (operands[1], SFmode)"
363   "* return output_movsisf (insn, operands, NULL);"
364   [(set_attr "length" "4,4,8,9,4,10")
365    (set_attr "cc" "none,set_zn,clobber,clobber,none,clobber")])
366
367 ;;=========================================================================
368 ;; move string (like memcpy)
369 ;; implement as RTL loop
370
371 (define_expand "movmemhi"
372   [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
373           (match_operand:BLK 1 "memory_operand" ""))
374           (use (match_operand:HI 2 "const_int_operand" ""))
375           (use (match_operand:HI 3 "const_int_operand" ""))])]
376   ""
377   "{
378   int prob;
379   HOST_WIDE_INT count;
380   enum machine_mode mode;
381   rtx label = gen_label_rtx ();
382   rtx loop_reg;
383   rtx jump;
384
385   /* Copy pointers into new psuedos - they will be changed.  */
386   rtx addr0 = copy_to_mode_reg (Pmode, XEXP (operands[0], 0));
387   rtx addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
388
389   /* Create rtx for tmp register - we use this as scratch.  */
390   rtx tmp_reg_rtx  = gen_rtx_REG (QImode, TMP_REGNO);
391
392   if (GET_CODE (operands[2]) != CONST_INT)
393     FAIL;
394
395   count = INTVAL (operands[2]);
396   if (count <= 0)
397     FAIL;
398
399   /* Work out branch probability for latter use.  */
400   prob = REG_BR_PROB_BASE - REG_BR_PROB_BASE / count;
401
402   /* See if constant fit 8 bits.  */
403   mode = (count < 0x100) ? QImode : HImode;
404   /* Create loop counter register.  */
405   loop_reg = copy_to_mode_reg (mode, gen_int_mode (count, mode));
406
407   /* Now create RTL code for move loop.  */
408   /* Label at top of loop.  */
409   emit_label (label);
410
411   /* Move one byte into scratch and inc pointer.  */
412   emit_move_insn (tmp_reg_rtx, gen_rtx_MEM (QImode, addr1));
413   emit_move_insn (addr1, gen_rtx_PLUS (Pmode, addr1, const1_rtx));
414
415   /* Move to mem and inc pointer.  */
416   emit_move_insn (gen_rtx_MEM (QImode, addr0), tmp_reg_rtx);
417   emit_move_insn (addr0, gen_rtx_PLUS (Pmode, addr0, const1_rtx));
418
419   /* Decrement count.  */
420   emit_move_insn (loop_reg, gen_rtx_PLUS (mode, loop_reg, constm1_rtx));
421
422   /* Compare with zero and jump if not equal. */
423   emit_cmp_and_jump_insns (loop_reg, const0_rtx, NE, NULL_RTX, mode, 1,
424                            label);
425   /* Set jump probability based on loop count.  */
426   jump = get_last_insn ();
427   REG_NOTES (jump) = gen_rtx_EXPR_LIST (REG_BR_PROB,
428                     GEN_INT (prob),
429                     REG_NOTES (jump));
430   DONE;
431 }")
432
433 ;; =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2 =%2
434 ;; memset (%0, %2, %1)
435
436 (define_expand "setmemhi"
437   [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
438                    (match_operand 2 "const_int_operand" ""))
439               (use (match_operand:HI 1 "const_int_operand" ""))
440               (use (match_operand:HI 3 "const_int_operand" "n"))
441               (clobber (match_scratch:HI 4 ""))
442               (clobber (match_dup 5))])]
443   ""
444   "{
445   rtx addr0;
446   int cnt8;
447   enum machine_mode mode;
448
449   /* If value to set is not zero, use the library routine.  */
450   if (operands[2] != const0_rtx)
451     FAIL;
452
453   if (GET_CODE (operands[1]) != CONST_INT)
454     FAIL;
455
456   cnt8 = byte_immediate_operand (operands[1], GET_MODE (operands[1]));
457   mode = cnt8 ? QImode : HImode;
458   operands[5] = gen_rtx_SCRATCH (mode);
459   operands[1] = copy_to_mode_reg (mode,
460                                   gen_int_mode (INTVAL (operands[1]), mode));
461   addr0 = copy_to_mode_reg (Pmode, XEXP (operands[0], 0));
462   operands[0] = gen_rtx_MEM (BLKmode, addr0);
463 }")
464
465 (define_insn "*clrmemqi"
466   [(set (mem:BLK (match_operand:HI 0 "register_operand" "e"))
467         (const_int 0))
468    (use (match_operand:QI 1 "register_operand" "r"))
469    (use (match_operand:QI 2 "const_int_operand" "n"))
470    (clobber (match_scratch:HI 3 "=0"))
471    (clobber (match_scratch:QI 4 "=&1"))]
472   ""
473   "st %a0+,__zero_reg__
474         dec %1
475         brne .-6"
476   [(set_attr "length" "3")
477    (set_attr "cc" "clobber")])
478
479 (define_insn "*clrmemhi"
480   [(set (mem:BLK (match_operand:HI 0 "register_operand" "e,e"))
481         (const_int 0))
482    (use (match_operand:HI 1 "register_operand" "!w,d"))
483    (use (match_operand:HI 2 "const_int_operand" "n,n"))
484    (clobber (match_scratch:HI 3 "=0,0"))
485    (clobber (match_scratch:HI 4 "=&1,&1"))]
486   ""
487   "*{
488      if (which_alternative==0)
489        return (AS2 (st,%a0+,__zero_reg__) CR_TAB
490                AS2 (sbiw,%A1,1) CR_TAB
491                AS1 (brne,.-6));
492      else
493        return (AS2 (st,%a0+,__zero_reg__) CR_TAB
494                AS2 (subi,%A1,1) CR_TAB
495                AS2 (sbci,%B1,0) CR_TAB
496                AS1 (brne,.-8));
497 }"
498   [(set_attr "length" "3,4")
499    (set_attr "cc" "clobber,clobber")])
500
501 (define_expand "strlenhi"
502     [(set (match_dup 4)
503           (unspec:HI [(match_operand:BLK 1 "memory_operand" "")
504                       (match_operand:QI 2 "const_int_operand" "")
505                       (match_operand:HI 3 "immediate_operand" "")]
506                      UNSPEC_STRLEN))
507      (set (match_dup 4) (plus:HI (match_dup 4)
508                                  (const_int -1)))
509      (set (match_operand:HI 0 "register_operand" "")
510           (minus:HI (match_dup 4)
511                     (match_dup 5)))]
512    ""
513    "{
514   rtx addr;
515   if (! (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) == 0))
516     FAIL;
517   addr = copy_to_mode_reg (Pmode, XEXP (operands[1],0));
518   operands[1] = gen_rtx_MEM (BLKmode, addr); 
519   operands[5] = addr;
520   operands[4] = gen_reg_rtx (HImode);
521 }")
522
523 (define_insn "*strlenhi"
524   [(set (match_operand:HI 0 "register_operand" "=e")
525         (unspec:HI [(mem:BLK (match_operand:HI 1 "register_operand" "%0"))
526                     (const_int 0)
527                     (match_operand:HI 2 "immediate_operand" "i")]
528                    UNSPEC_STRLEN))]
529   ""
530   "ld __tmp_reg__,%a0+
531         tst __tmp_reg__
532         brne .-6"
533   [(set_attr "length" "3")
534    (set_attr "cc" "clobber")])
535
536 ;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
537 ; add bytes
538
539 (define_insn "addqi3"
540   [(set (match_operand:QI 0 "register_operand" "=r,d,r,r")
541         (plus:QI (match_operand:QI 1 "register_operand" "%0,0,0,0")
542                  (match_operand:QI 2 "nonmemory_operand" "r,i,P,N")))]
543   ""
544   "@
545         add %0,%2
546         subi %0,lo8(-(%2))
547         inc %0
548         dec %0"
549   [(set_attr "length" "1,1,1,1")
550    (set_attr "cc" "set_czn,set_czn,set_zn,set_zn")])
551
552
553 (define_expand "addhi3"
554   [(set (match_operand:HI 0 "register_operand" "")
555         (plus:HI (match_operand:HI 1 "register_operand" "")
556                  (match_operand:HI 2 "nonmemory_operand" "")))]
557   ""
558   "
559 {
560   if (GET_CODE (operands[2]) == CONST_INT)
561     {
562       short tmp = INTVAL (operands[2]);
563       operands[2] = GEN_INT(tmp);
564     }
565 }")
566
567
568 (define_insn "*addhi3_zero_extend"
569   [(set (match_operand:HI 0 "register_operand" "=r")
570         (plus:HI (zero_extend:HI
571                   (match_operand:QI 1 "register_operand" "r"))
572                  (match_operand:HI 2 "register_operand" "0")))]
573   ""
574   "add %A0,%1
575         adc %B0,__zero_reg__"
576   [(set_attr "length" "2")
577    (set_attr "cc" "set_n")])
578
579 (define_insn "*addhi3_zero_extend1"
580   [(set (match_operand:HI 0 "register_operand" "=r")
581         (plus:HI (match_operand:HI 1 "register_operand" "%0")
582                  (zero_extend:HI
583                   (match_operand:QI 2 "register_operand" "r"))))]
584   ""
585   "add %A0,%2
586         adc %B0,__zero_reg__"
587   [(set_attr "length" "2")
588    (set_attr "cc" "set_n")])
589
590 (define_insn "*addhi3_zero_extend2"
591   [(set (match_operand:HI 0 "register_operand" "=r")
592         (plus:HI
593          (zero_extend:HI (match_operand:QI 1 "register_operand" "%0"))
594          (zero_extend:HI (match_operand:QI 2 "register_operand" "r"))))]
595   ""
596   "add %0,%2
597         mov %B0,__zero_reg__
598         adc %B0,__zero_reg__"
599   [(set_attr "length" "3")
600    (set_attr "cc" "set_n")])
601
602 (define_insn "*addhi3_sp_R_pc2"
603   [(set (match_operand:HI 1 "stack_register_operand" "=q")
604         (plus:HI (match_operand:HI 2 "stack_register_operand" "q")
605                  (match_operand:HI 0 "avr_sp_immediate_operand" "R")))]
606   "AVR_2_BYTE_PC"
607   "*{
608       if (CONST_INT_P (operands[0]))
609         {
610           switch(INTVAL (operands[0]))
611             {
612             case -6: 
613               return \"rcall .\" CR_TAB 
614                      \"rcall .\" CR_TAB 
615                      \"rcall .\";
616             case -5: 
617               return \"rcall .\" CR_TAB 
618                      \"rcall .\" CR_TAB 
619                      \"push __tmp_reg__\";
620             case -4: 
621               return \"rcall .\" CR_TAB 
622                      \"rcall .\";
623             case -3: 
624               return \"rcall .\" CR_TAB 
625                      \"push __tmp_reg__\";
626             case -2: 
627               return \"rcall .\";
628             case -1: 
629               return \"push __tmp_reg__\";
630             case 0: 
631               return \"\";
632             case 1: 
633               return \"pop __tmp_reg__\";
634             case 2: 
635               return \"pop __tmp_reg__\" CR_TAB 
636                      \"pop __tmp_reg__\";
637             case 3: 
638               return \"pop __tmp_reg__\" CR_TAB 
639                      \"pop __tmp_reg__\" CR_TAB 
640                      \"pop __tmp_reg__\";
641             case 4: 
642               return \"pop __tmp_reg__\" CR_TAB 
643                      \"pop __tmp_reg__\" CR_TAB 
644                      \"pop __tmp_reg__\" CR_TAB 
645                      \"pop __tmp_reg__\";
646             case 5: 
647               return \"pop __tmp_reg__\" CR_TAB 
648                      \"pop __tmp_reg__\" CR_TAB 
649                      \"pop __tmp_reg__\" CR_TAB 
650                      \"pop __tmp_reg__\" CR_TAB 
651                      \"pop __tmp_reg__\";
652             }
653         }
654       return \"bug\";
655     }"
656   [(set (attr "length") 
657         (cond [(eq (const_int -6) (symbol_ref "INTVAL (operands[0])")) (const_int 3)
658                (eq (const_int -5) (symbol_ref "INTVAL (operands[0])")) (const_int 3)
659                (eq (const_int -4) (symbol_ref "INTVAL (operands[0])")) (const_int 2)
660                (eq (const_int -3) (symbol_ref "INTVAL (operands[0])")) (const_int 2)
661                (eq (const_int -2) (symbol_ref "INTVAL (operands[0])")) (const_int 1)
662                (eq (const_int -1) (symbol_ref "INTVAL (operands[0])")) (const_int 1)
663                (eq (const_int  0) (symbol_ref "INTVAL (operands[0])")) (const_int 0)
664                (eq (const_int  1) (symbol_ref "INTVAL (operands[0])")) (const_int 1)
665                (eq (const_int  2) (symbol_ref "INTVAL (operands[0])")) (const_int 2)
666                (eq (const_int  3) (symbol_ref "INTVAL (operands[0])")) (const_int 3)
667                (eq (const_int  4) (symbol_ref "INTVAL (operands[0])")) (const_int 4)
668                (eq (const_int  5) (symbol_ref "INTVAL (operands[0])")) (const_int 5)]
669                (const_int 0)))])
670
671 (define_insn "*addhi3_sp_R_pc3"
672   [(set (match_operand:HI 1 "stack_register_operand" "=q")
673         (plus:HI (match_operand:HI 2 "stack_register_operand" "q")
674                  (match_operand:QI 0 "avr_sp_immediate_operand" "R")))]
675   "AVR_3_BYTE_PC"
676   "*{
677       if (CONST_INT_P (operands[0]))
678         {
679           switch(INTVAL (operands[0]))
680             {
681             case -6: 
682               return \"rcall .\" CR_TAB 
683                      \"rcall .\";
684             case -5: 
685               return \"rcall .\" CR_TAB 
686                      \"push __tmp_reg__\" CR_TAB 
687                      \"push __tmp_reg__\";
688             case -4: 
689               return \"rcall .\" CR_TAB 
690                      \"push __tmp_reg__\";
691             case -3: 
692               return \"rcall .\";
693             case -2: 
694               return \"push __tmp_reg__\" CR_TAB 
695                      \"push __tmp_reg__\";
696             case -1: 
697               return \"push __tmp_reg__\";
698             case 0: 
699               return \"\";
700             case 1: 
701               return \"pop __tmp_reg__\";
702             case 2: 
703               return \"pop __tmp_reg__\" CR_TAB 
704                      \"pop __tmp_reg__\";
705             case 3: 
706               return \"pop __tmp_reg__\" CR_TAB 
707                      \"pop __tmp_reg__\" CR_TAB 
708                      \"pop __tmp_reg__\";
709             case 4: 
710               return \"pop __tmp_reg__\" CR_TAB 
711                      \"pop __tmp_reg__\" CR_TAB 
712                      \"pop __tmp_reg__\" CR_TAB 
713                      \"pop __tmp_reg__\";
714             case 5: 
715               return \"pop __tmp_reg__\" CR_TAB 
716                      \"pop __tmp_reg__\" CR_TAB 
717                      \"pop __tmp_reg__\" CR_TAB 
718                      \"pop __tmp_reg__\" CR_TAB 
719                      \"pop __tmp_reg__\";
720             }
721         }
722       return \"bug\";
723     }"
724   [(set (attr "length") 
725         (cond [(eq (const_int -6) (symbol_ref "INTVAL (operands[0])")) (const_int 2)
726                (eq (const_int -5) (symbol_ref "INTVAL (operands[0])")) (const_int 3)
727                (eq (const_int -4) (symbol_ref "INTVAL (operands[0])")) (const_int 2)
728                (eq (const_int -3) (symbol_ref "INTVAL (operands[0])")) (const_int 1)
729                (eq (const_int -2) (symbol_ref "INTVAL (operands[0])")) (const_int 2)
730                (eq (const_int -1) (symbol_ref "INTVAL (operands[0])")) (const_int 1)
731                (eq (const_int  0) (symbol_ref "INTVAL (operands[0])")) (const_int 0)
732                (eq (const_int  1) (symbol_ref "INTVAL (operands[0])")) (const_int 1)
733                (eq (const_int  2) (symbol_ref "INTVAL (operands[0])")) (const_int 2)
734                (eq (const_int  3) (symbol_ref "INTVAL (operands[0])")) (const_int 3)
735                (eq (const_int  4) (symbol_ref "INTVAL (operands[0])")) (const_int 4)
736                (eq (const_int  5) (symbol_ref "INTVAL (operands[0])")) (const_int 5)]
737                (const_int 0)))])
738
739 (define_insn "*addhi3"
740   [(set (match_operand:HI 0 "register_operand" "=r,!w,!w,d,r,r")
741         (plus:HI
742          (match_operand:HI 1 "register_operand" "%0,0,0,0,0,0")
743          (match_operand:HI 2 "nonmemory_operand" "r,I,J,i,P,N")))]
744   ""
745   "@
746         add %A0,%A2\;adc %B0,%B2
747         adiw %A0,%2
748         sbiw %A0,%n2
749         subi %A0,lo8(-(%2))\;sbci %B0,hi8(-(%2))
750         sec\;adc %A0,__zero_reg__\;adc %B0,__zero_reg__
751         sec\;sbc %A0,__zero_reg__\;sbc %B0,__zero_reg__"
752   [(set_attr "length" "2,1,1,2,3,3")
753    (set_attr "cc" "set_n,set_czn,set_czn,set_czn,set_n,set_n")])
754
755 (define_insn "addsi3"
756   [(set (match_operand:SI 0 "register_operand" "=r,!w,!w,d,r,r")
757           (plus:SI
758            (match_operand:SI 1 "register_operand" "%0,0,0,0,0,0")
759            (match_operand:SI 2 "nonmemory_operand" "r,I,J,i,P,N")))]
760   ""
761   "@
762         add %A0,%A2\;adc %B0,%B2\;adc %C0,%C2\;adc %D0,%D2
763         adiw %0,%2\;adc %C0,__zero_reg__\;adc %D0,__zero_reg__
764         sbiw %0,%n2\;sbc %C0,__zero_reg__\;sbc %D0,__zero_reg__
765         subi %0,lo8(-(%2))\;sbci %B0,hi8(-(%2))\;sbci %C0,hlo8(-(%2))\;sbci %D0,hhi8(-(%2))
766         sec\;adc %A0,__zero_reg__\;adc %B0,__zero_reg__\;adc %C0,__zero_reg__\;adc %D0,__zero_reg__
767         sec\;sbc %A0,__zero_reg__\;sbc %B0,__zero_reg__\;sbc %C0,__zero_reg__\;sbc %D0,__zero_reg__"
768   [(set_attr "length" "4,3,3,4,5,5")
769    (set_attr "cc" "set_n,set_n,set_czn,set_czn,set_n,set_n")])
770
771 (define_insn "*addsi3_zero_extend"
772   [(set (match_operand:SI 0 "register_operand" "=r")
773         (plus:SI (zero_extend:SI
774                   (match_operand:QI 1 "register_operand" "r"))
775                  (match_operand:SI 2 "register_operand" "0")))]
776   ""
777   "add %A0,%1
778         adc %B0,__zero_reg__
779         adc %C0,__zero_reg__
780         adc %D0,__zero_reg__"
781   [(set_attr "length" "4")
782    (set_attr "cc" "set_n")])
783
784 ;-----------------------------------------------------------------------------
785 ; sub bytes
786 (define_insn "subqi3"
787   [(set (match_operand:QI 0 "register_operand" "=r,d")
788         (minus:QI (match_operand:QI 1 "register_operand" "0,0")
789                   (match_operand:QI 2 "nonmemory_operand" "r,i")))]
790   ""
791   "@
792         sub %0,%2
793         subi %0,lo8(%2)"
794   [(set_attr "length" "1,1")
795    (set_attr "cc" "set_czn,set_czn")])
796
797 (define_insn "subhi3"
798   [(set (match_operand:HI 0 "register_operand" "=r,d")
799         (minus:HI (match_operand:HI 1 "register_operand" "0,0")
800                   (match_operand:HI 2 "nonmemory_operand" "r,i")))]
801   ""
802   "@
803         sub %A0,%A2\;sbc %B0,%B2
804         subi %A0,lo8(%2)\;sbci %B0,hi8(%2)"
805   [(set_attr "length" "2,2")
806    (set_attr "cc" "set_czn,set_czn")])
807
808 (define_insn "*subhi3_zero_extend1"
809   [(set (match_operand:HI 0 "register_operand" "=r")
810         (minus:HI (match_operand:HI 1 "register_operand" "0")
811                   (zero_extend:HI
812                    (match_operand:QI 2 "register_operand" "r"))))]
813   ""
814   "sub %A0,%2
815         sbc %B0,__zero_reg__"
816   [(set_attr "length" "2")
817    (set_attr "cc" "set_n")])
818
819 (define_insn "subsi3"
820   [(set (match_operand:SI 0 "register_operand" "=r,d")
821         (minus:SI (match_operand:SI 1 "register_operand" "0,0")
822                  (match_operand:SI 2 "nonmemory_operand" "r,i")))]
823   ""
824   "@
825         sub %0,%2\;sbc %B0,%B2\;sbc %C0,%C2\;sbc %D0,%D2
826         subi %A0,lo8(%2)\;sbci %B0,hi8(%2)\;sbci %C0,hlo8(%2)\;sbci %D0,hhi8(%2)"
827   [(set_attr "length" "4,4")
828    (set_attr "cc" "set_czn,set_czn")])
829
830 (define_insn "*subsi3_zero_extend"
831   [(set (match_operand:SI 0 "register_operand" "=r")
832         (minus:SI (match_operand:SI 1 "register_operand" "0")
833                   (zero_extend:SI
834                    (match_operand:QI 2 "register_operand" "r"))))]
835   ""
836   "sub %A0,%2
837         sbc %B0,__zero_reg__
838         sbc %C0,__zero_reg__
839         sbc %D0,__zero_reg__"
840   [(set_attr "length" "4")
841    (set_attr "cc" "set_n")])
842
843 ;******************************************************************************
844 ; mul
845
846 (define_expand "mulqi3"
847   [(set (match_operand:QI 0 "register_operand" "")
848         (mult:QI (match_operand:QI 1 "register_operand" "")
849                  (match_operand:QI 2 "register_operand" "")))]
850   ""
851   "{
852   if (!AVR_HAVE_MUL)
853     {
854       emit_insn (gen_mulqi3_call (operands[0], operands[1], operands[2]));
855       DONE;
856     }
857 }")
858
859 (define_insn "*mulqi3_enh"
860   [(set (match_operand:QI 0 "register_operand" "=r")
861         (mult:QI (match_operand:QI 1 "register_operand" "r")
862                  (match_operand:QI 2 "register_operand" "r")))]
863   "AVR_HAVE_MUL"
864   "mul %1,%2
865         mov %0,r0
866         clr r1"
867   [(set_attr "length" "3")
868    (set_attr "cc" "clobber")])
869
870 (define_expand "mulqi3_call"
871   [(set (reg:QI 24) (match_operand:QI 1 "register_operand" ""))
872    (set (reg:QI 22) (match_operand:QI 2 "register_operand" ""))
873    (parallel [(set (reg:QI 24) (mult:QI (reg:QI 24) (reg:QI 22)))
874               (clobber (reg:QI 22))])
875    (set (match_operand:QI 0 "register_operand" "") (reg:QI 24))]
876   ""
877   "")
878
879 (define_insn "*mulqi3_call"
880   [(set (reg:QI 24) (mult:QI (reg:QI 24) (reg:QI 22)))
881    (clobber (reg:QI 22))]
882   "!AVR_HAVE_MUL"
883   "%~call __mulqi3"
884   [(set_attr "type" "xcall")
885    (set_attr "cc" "clobber")])
886
887 (define_insn "mulqihi3"
888   [(set (match_operand:HI 0 "register_operand" "=r")
889         (mult:HI (sign_extend:HI (match_operand:QI 1 "register_operand" "d"))
890                  (sign_extend:HI (match_operand:QI 2 "register_operand" "d"))))]
891   "AVR_HAVE_MUL"
892   "muls %1,%2
893         movw %0,r0
894         clr r1"
895   [(set_attr "length" "3")
896    (set_attr "cc" "clobber")])
897
898 (define_insn "umulqihi3"
899   [(set (match_operand:HI 0 "register_operand" "=r")
900         (mult:HI (zero_extend:HI (match_operand:QI 1 "register_operand" "r"))
901                  (zero_extend:HI (match_operand:QI 2 "register_operand" "r"))))]
902   "AVR_HAVE_MUL"
903   "mul %1,%2
904         movw %0,r0
905         clr r1"
906   [(set_attr "length" "3")
907    (set_attr "cc" "clobber")])
908
909 (define_expand "mulhi3"
910   [(set (match_operand:HI 0 "register_operand" "")
911         (mult:HI (match_operand:HI 1 "register_operand" "")
912                  (match_operand:HI 2 "register_operand" "")))]
913   ""
914   "
915 {
916   if (!AVR_HAVE_MUL)
917     {
918       emit_insn (gen_mulhi3_call (operands[0], operands[1], operands[2]));
919       DONE;
920     }
921 }")
922
923 (define_insn "*mulhi3_enh"
924   [(set (match_operand:HI 0 "register_operand" "=&r")
925         (mult:HI (match_operand:HI 1 "register_operand" "r")
926                  (match_operand:HI 2 "register_operand" "r")))]
927   "AVR_HAVE_MUL"
928   "mul %A1,%A2
929         movw %0,r0
930         mul %A1,%B2
931         add %B0,r0
932         mul %B1,%A2
933         add %B0,r0
934         clr r1"
935   [(set_attr "length" "7")
936    (set_attr "cc" "clobber")])
937
938 (define_expand "mulhi3_call"
939   [(set (reg:HI 24) (match_operand:HI 1 "register_operand" ""))
940    (set (reg:HI 22) (match_operand:HI 2 "register_operand" ""))
941    (parallel [(set (reg:HI 24) (mult:HI (reg:HI 24) (reg:HI 22)))
942               (clobber (reg:HI 22))
943               (clobber (reg:QI 21))])
944    (set (match_operand:HI 0 "register_operand" "") (reg:HI 24))]
945   ""
946   "")
947
948 (define_insn "*mulhi3_call"
949   [(set (reg:HI 24) (mult:HI (reg:HI 24) (reg:HI 22)))
950    (clobber (reg:HI 22))
951    (clobber (reg:QI 21))]
952   "!AVR_HAVE_MUL"
953   "%~call __mulhi3"
954   [(set_attr "type" "xcall")
955    (set_attr "cc" "clobber")])
956
957 ;; Operand 2 (reg:SI 18) not clobbered on the enhanced core.
958 ;; All call-used registers clobbered otherwise - normal library call.
959 (define_expand "mulsi3"
960   [(set (reg:SI 22) (match_operand:SI 1 "register_operand" ""))
961    (set (reg:SI 18) (match_operand:SI 2 "register_operand" ""))
962    (parallel [(set (reg:SI 22) (mult:SI (reg:SI 22) (reg:SI 18)))
963               (clobber (reg:HI 26))
964               (clobber (reg:HI 30))])
965    (set (match_operand:SI 0 "register_operand" "") (reg:SI 22))]
966   "AVR_HAVE_MUL"
967   "")
968
969 (define_insn "*mulsi3_call"
970   [(set (reg:SI 22) (mult:SI (reg:SI 22) (reg:SI 18)))
971    (clobber (reg:HI 26))
972    (clobber (reg:HI 30))]
973   "AVR_HAVE_MUL"
974   "%~call __mulsi3"
975   [(set_attr "type" "xcall")
976    (set_attr "cc" "clobber")])
977
978 ; / % / % / % / % / % / % / % / % / % / % / % / % / % / % / % / % / % / % / %
979 ; divmod
980
981 ;; Generate libgcc.S calls ourselves, because:
982 ;;  - we know exactly which registers are clobbered (for QI and HI
983 ;;    modes, some of the call-used registers are preserved)
984 ;;  - we get both the quotient and the remainder at no extra cost
985
986 (define_expand "divmodqi4"
987   [(set (reg:QI 24) (match_operand:QI 1 "register_operand" ""))
988    (set (reg:QI 22) (match_operand:QI 2 "register_operand" ""))
989    (parallel [(set (reg:QI 24) (div:QI (reg:QI 24) (reg:QI 22)))
990               (set (reg:QI 25) (mod:QI (reg:QI 24) (reg:QI 22)))
991               (clobber (reg:QI 22))
992               (clobber (reg:QI 23))])
993    (set (match_operand:QI 0 "register_operand" "") (reg:QI 24))
994    (set (match_operand:QI 3 "register_operand" "") (reg:QI 25))]
995   ""
996   "")
997
998 (define_insn "*divmodqi4_call"
999   [(set (reg:QI 24) (div:QI (reg:QI 24) (reg:QI 22)))
1000    (set (reg:QI 25) (mod:QI (reg:QI 24) (reg:QI 22)))
1001    (clobber (reg:QI 22))
1002    (clobber (reg:QI 23))]
1003   ""
1004   "%~call __divmodqi4"
1005   [(set_attr "type" "xcall")
1006    (set_attr "cc" "clobber")])
1007
1008 (define_expand "udivmodqi4"
1009   [(set (reg:QI 24) (match_operand:QI 1 "register_operand" ""))
1010    (set (reg:QI 22) (match_operand:QI 2 "register_operand" ""))
1011    (parallel [(set (reg:QI 24) (udiv:QI (reg:QI 24) (reg:QI 22)))
1012               (set (reg:QI 25) (umod:QI (reg:QI 24) (reg:QI 22)))
1013               (clobber (reg:QI 23))])
1014    (set (match_operand:QI 0 "register_operand" "") (reg:QI 24))
1015    (set (match_operand:QI 3 "register_operand" "") (reg:QI 25))]
1016   ""
1017   "")
1018
1019 (define_insn "*udivmodqi4_call"
1020   [(set (reg:QI 24) (udiv:QI (reg:QI 24) (reg:QI 22)))
1021    (set (reg:QI 25) (umod:QI (reg:QI 24) (reg:QI 22)))
1022    (clobber (reg:QI 23))]
1023   ""
1024   "%~call __udivmodqi4"
1025   [(set_attr "type" "xcall")
1026    (set_attr "cc" "clobber")])
1027
1028 (define_expand "divmodhi4"
1029   [(set (reg:HI 24) (match_operand:HI 1 "register_operand" ""))
1030    (set (reg:HI 22) (match_operand:HI 2 "register_operand" ""))
1031    (parallel [(set (reg:HI 22) (div:HI (reg:HI 24) (reg:HI 22)))
1032               (set (reg:HI 24) (mod:HI (reg:HI 24) (reg:HI 22)))
1033               (clobber (reg:HI 26))
1034               (clobber (reg:QI 21))])
1035    (set (match_operand:HI 0 "register_operand" "") (reg:HI 22))
1036    (set (match_operand:HI 3 "register_operand" "") (reg:HI 24))]
1037   ""
1038   "")
1039
1040 (define_insn "*divmodhi4_call"
1041   [(set (reg:HI 22) (div:HI (reg:HI 24) (reg:HI 22)))
1042    (set (reg:HI 24) (mod:HI (reg:HI 24) (reg:HI 22)))
1043    (clobber (reg:HI 26))
1044    (clobber (reg:QI 21))]
1045   ""
1046   "%~call __divmodhi4"
1047   [(set_attr "type" "xcall")
1048    (set_attr "cc" "clobber")])
1049
1050 (define_expand "udivmodhi4"
1051   [(set (reg:HI 24) (match_operand:HI 1 "register_operand" ""))
1052    (set (reg:HI 22) (match_operand:HI 2 "register_operand" ""))
1053    (parallel [(set (reg:HI 22) (udiv:HI (reg:HI 24) (reg:HI 22)))
1054               (set (reg:HI 24) (umod:HI (reg:HI 24) (reg:HI 22)))
1055               (clobber (reg:HI 26))
1056               (clobber (reg:QI 21))])
1057    (set (match_operand:HI 0 "register_operand" "") (reg:HI 22))
1058    (set (match_operand:HI 3 "register_operand" "") (reg:HI 24))]
1059   ""
1060   "")
1061
1062 (define_insn "*udivmodhi4_call"
1063   [(set (reg:HI 22) (udiv:HI (reg:HI 24) (reg:HI 22)))
1064    (set (reg:HI 24) (umod:HI (reg:HI 24) (reg:HI 22)))
1065    (clobber (reg:HI 26))
1066    (clobber (reg:QI 21))]
1067   ""
1068   "%~call __udivmodhi4"
1069   [(set_attr "type" "xcall")
1070    (set_attr "cc" "clobber")])
1071
1072 (define_expand "divmodsi4"
1073   [(set (reg:SI 22) (match_operand:SI 1 "register_operand" ""))
1074    (set (reg:SI 18) (match_operand:SI 2 "register_operand" ""))
1075    (parallel [(set (reg:SI 18) (div:SI (reg:SI 22) (reg:SI 18)))
1076               (set (reg:SI 22) (mod:SI (reg:SI 22) (reg:SI 18)))
1077               (clobber (reg:HI 26))
1078               (clobber (reg:HI 30))])
1079    (set (match_operand:SI 0 "register_operand" "") (reg:SI 18))
1080    (set (match_operand:SI 3 "register_operand" "") (reg:SI 22))]
1081   ""
1082   "")
1083
1084 (define_insn "*divmodsi4_call"
1085   [(set (reg:SI 18) (div:SI (reg:SI 22) (reg:SI 18)))
1086    (set (reg:SI 22) (mod:SI (reg:SI 22) (reg:SI 18)))
1087    (clobber (reg:HI 26))
1088    (clobber (reg:HI 30))]
1089   ""
1090   "%~call __divmodsi4"
1091   [(set_attr "type" "xcall")
1092    (set_attr "cc" "clobber")])
1093
1094 (define_expand "udivmodsi4"
1095   [(set (reg:SI 22) (match_operand:SI 1 "register_operand" ""))
1096    (set (reg:SI 18) (match_operand:SI 2 "register_operand" ""))
1097    (parallel [(set (reg:SI 18) (udiv:SI (reg:SI 22) (reg:SI 18)))
1098               (set (reg:SI 22) (umod:SI (reg:SI 22) (reg:SI 18)))
1099               (clobber (reg:HI 26))
1100               (clobber (reg:HI 30))])
1101    (set (match_operand:SI 0 "register_operand" "") (reg:SI 18))
1102    (set (match_operand:SI 3 "register_operand" "") (reg:SI 22))]
1103   ""
1104   "")
1105
1106 (define_insn "*udivmodsi4_call"
1107   [(set (reg:SI 18) (udiv:SI (reg:SI 22) (reg:SI 18)))
1108    (set (reg:SI 22) (umod:SI (reg:SI 22) (reg:SI 18)))
1109    (clobber (reg:HI 26))
1110    (clobber (reg:HI 30))]
1111   ""
1112   "%~call __udivmodsi4"
1113   [(set_attr "type" "xcall")
1114    (set_attr "cc" "clobber")])
1115
1116 ;&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
1117 ; and
1118
1119 (define_insn "andqi3"
1120   [(set (match_operand:QI 0 "register_operand" "=r,d")
1121         (and:QI (match_operand:QI 1 "register_operand" "%0,0")
1122                 (match_operand:QI 2 "nonmemory_operand" "r,i")))]
1123   ""
1124   "@
1125         and %0,%2
1126         andi %0,lo8(%2)"
1127   [(set_attr "length" "1,1")
1128    (set_attr "cc" "set_zn,set_zn")])
1129
1130 (define_insn "andhi3"
1131   [(set (match_operand:HI 0 "register_operand" "=r,d,r")
1132           (and:HI (match_operand:HI 1 "register_operand" "%0,0,0")
1133                   (match_operand:HI 2 "nonmemory_operand" "r,i,M")))
1134    (clobber (match_scratch:QI 3 "=X,X,&d"))]
1135   ""
1136   "*{
1137   if (which_alternative==0)
1138     return (AS2 (and,%A0,%A2) CR_TAB
1139             AS2 (and,%B0,%B2));
1140   else if (which_alternative==1)
1141     {
1142       if (GET_CODE (operands[2]) == CONST_INT)
1143         {
1144           int mask = INTVAL (operands[2]);
1145           if ((mask & 0xff) != 0xff)
1146             output_asm_insn (AS2 (andi,%A0,lo8(%2)), operands);
1147           if ((mask & 0xff00) != 0xff00)
1148             output_asm_insn (AS2 (andi,%B0,hi8(%2)), operands);
1149           return \"\";
1150         }
1151         return (AS2 (andi,%A0,lo8(%2)) CR_TAB
1152                 AS2 (andi,%B0,hi8(%2)));
1153      }
1154   return (AS2 (ldi,%3,lo8(%2)) CR_TAB
1155           AS2 (and,%A0,%3)     CR_TAB
1156           AS1 (clr,%B0));
1157 }"
1158   [(set_attr "length" "2,2,3")
1159    (set_attr "cc" "set_n,clobber,set_n")])
1160
1161 (define_insn "andsi3"
1162   [(set (match_operand:SI 0 "register_operand" "=r,d")
1163         (and:SI (match_operand:SI 1 "register_operand" "%0,0")
1164                 (match_operand:SI 2 "nonmemory_operand" "r,i")))]
1165   ""
1166   "*{
1167   if (which_alternative==0)
1168     return (AS2 (and, %0,%2)   CR_TAB
1169             AS2 (and, %B0,%B2) CR_TAB
1170             AS2 (and, %C0,%C2) CR_TAB
1171             AS2 (and, %D0,%D2));
1172   else if (which_alternative==1)
1173     {
1174       if (GET_CODE (operands[2]) == CONST_INT)
1175         {
1176           HOST_WIDE_INT mask = INTVAL (operands[2]);
1177           if ((mask & 0xff) != 0xff)
1178             output_asm_insn (AS2 (andi,%A0,lo8(%2)), operands);
1179           if ((mask & 0xff00) != 0xff00)
1180             output_asm_insn (AS2 (andi,%B0,hi8(%2)), operands);
1181           if ((mask & 0xff0000L) != 0xff0000L)
1182             output_asm_insn (AS2 (andi,%C0,hlo8(%2)), operands);
1183           if ((mask & 0xff000000L) != 0xff000000L)
1184             output_asm_insn (AS2 (andi,%D0,hhi8(%2)), operands);
1185           return \"\";
1186         }
1187       return (AS2 (andi, %A0,lo8(%2))  CR_TAB
1188               AS2 (andi, %B0,hi8(%2)) CR_TAB
1189               AS2 (andi, %C0,hlo8(%2)) CR_TAB
1190               AS2 (andi, %D0,hhi8(%2)));
1191     }
1192   return \"bug\";
1193 }"
1194   [(set_attr "length" "4,4")
1195    (set_attr "cc" "set_n,set_n")])
1196
1197 ;;|||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
1198 ;; ior
1199
1200 (define_insn "iorqi3"
1201   [(set (match_operand:QI 0 "register_operand" "=r,d")
1202         (ior:QI (match_operand:QI 1 "register_operand" "%0,0")
1203                 (match_operand:QI 2 "nonmemory_operand" "r,i")))]
1204   ""
1205   "@
1206         or %0,%2
1207         ori %0,lo8(%2)"
1208   [(set_attr "length" "1,1")
1209    (set_attr "cc" "set_zn,set_zn")])
1210
1211 (define_insn "iorhi3"
1212   [(set (match_operand:HI 0 "register_operand" "=r,d")
1213         (ior:HI (match_operand:HI 1 "register_operand" "%0,0")
1214                 (match_operand:HI 2 "nonmemory_operand" "r,i")))]
1215   ""
1216   "*{
1217   if (which_alternative==0)
1218     return (AS2 (or,%A0,%A2) CR_TAB
1219             AS2 (or,%B0,%B2));
1220   if (GET_CODE (operands[2]) == CONST_INT)
1221      {
1222         int mask = INTVAL (operands[2]);
1223         if (mask & 0xff)
1224           output_asm_insn (AS2 (ori,%A0,lo8(%2)), operands);
1225         if (mask & 0xff00)
1226           output_asm_insn (AS2 (ori,%B0,hi8(%2)), operands);
1227         return \"\";
1228       }
1229    return (AS2 (ori,%0,lo8(%2)) CR_TAB
1230            AS2 (ori,%B0,hi8(%2)));
1231 }"  
1232   [(set_attr "length" "2,2")
1233    (set_attr "cc" "set_n,clobber")])
1234
1235 (define_insn "*iorhi3_clobber"
1236   [(set (match_operand:HI 0 "register_operand" "=r,r")
1237         (ior:HI (match_operand:HI 1 "register_operand" "%0,0")
1238                 (match_operand:HI 2 "immediate_operand" "M,i")))
1239    (clobber (match_scratch:QI 3 "=&d,&d"))]
1240   ""
1241   "@
1242         ldi %3,lo8(%2)\;or %A0,%3
1243         ldi %3,lo8(%2)\;or %A0,%3\;ldi %3,hi8(%2)\;or %B0,%3"
1244   [(set_attr "length" "2,4")
1245    (set_attr "cc" "clobber,set_n")])
1246
1247 (define_insn "iorsi3"
1248   [(set (match_operand:SI 0 "register_operand"        "=r,d")
1249         (ior:SI (match_operand:SI 1 "register_operand" "%0,0")
1250                 (match_operand:SI 2 "nonmemory_operand" "r,i")))]
1251   ""
1252   "*{
1253   if (which_alternative==0)
1254     return (AS2 (or, %0,%2)   CR_TAB
1255             AS2 (or, %B0,%B2) CR_TAB
1256             AS2 (or, %C0,%C2) CR_TAB
1257             AS2 (or, %D0,%D2));
1258   if (GET_CODE (operands[2]) == CONST_INT)
1259      {
1260         HOST_WIDE_INT mask = INTVAL (operands[2]);
1261         if (mask & 0xff)
1262           output_asm_insn (AS2 (ori,%A0,lo8(%2)), operands);
1263         if (mask & 0xff00)
1264           output_asm_insn (AS2 (ori,%B0,hi8(%2)), operands);
1265         if (mask & 0xff0000L)
1266           output_asm_insn (AS2 (ori,%C0,hlo8(%2)), operands);
1267         if (mask & 0xff000000L)
1268           output_asm_insn (AS2 (ori,%D0,hhi8(%2)), operands);
1269         return \"\";
1270       }
1271   return (AS2 (ori, %A0,lo8(%2))  CR_TAB
1272           AS2 (ori, %B0,hi8(%2)) CR_TAB
1273           AS2 (ori, %C0,hlo8(%2)) CR_TAB
1274           AS2 (ori, %D0,hhi8(%2)));
1275 }"
1276   [(set_attr "length" "4,4")
1277    (set_attr "cc" "set_n,clobber")])
1278
1279 (define_insn "*iorsi3_clobber"
1280   [(set (match_operand:SI 0 "register_operand"        "=r,r")
1281         (ior:SI (match_operand:SI 1 "register_operand" "%0,0")
1282                 (match_operand:SI 2 "immediate_operand" "M,i")))
1283    (clobber (match_scratch:QI 3 "=&d,&d"))]
1284   ""
1285   "@
1286         ldi %3,lo8(%2)\;or %A0,%3
1287         ldi %3,lo8(%2)\;or %A0,%3\;ldi %3,hi8(%2)\;or %B0,%3\;ldi %3,hlo8(%2)\;or %C0,%3\;ldi %3,hhi8(%2)\;or %D0,%3"
1288   [(set_attr "length" "2,8")
1289    (set_attr "cc" "clobber,set_n")])
1290
1291 ;;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
1292 ;; xor
1293
1294 (define_insn "xorqi3"
1295   [(set (match_operand:QI 0 "register_operand" "=r")
1296         (xor:QI (match_operand:QI 1 "register_operand" "%0")
1297                 (match_operand:QI 2 "register_operand" "r")))]
1298   ""
1299   "eor %0,%2"
1300   [(set_attr "length" "1")
1301    (set_attr "cc" "set_zn")])
1302
1303 (define_insn "xorhi3"
1304   [(set (match_operand:HI 0 "register_operand" "=r")
1305         (xor:HI (match_operand:HI 1 "register_operand" "%0")
1306                 (match_operand:HI 2 "register_operand" "r")))]
1307   ""
1308   "eor %0,%2
1309         eor %B0,%B2"
1310   [(set_attr "length" "2")
1311    (set_attr "cc" "set_n")])
1312
1313 (define_insn "xorsi3"
1314   [(set (match_operand:SI 0 "register_operand" "=r")
1315         (xor:SI (match_operand:SI 1 "register_operand" "%0")
1316                 (match_operand:SI 2 "register_operand" "r")))]
1317   ""
1318   "eor %0,%2
1319         eor %B0,%B2
1320         eor %C0,%C2
1321         eor %D0,%D2"
1322   [(set_attr "length" "4")
1323    (set_attr "cc" "set_n")])
1324
1325 ;;<< << << << << << << << << << << << << << << << << << << << << << << << << <<
1326 ;; arithmetic shift left
1327
1328 (define_insn "ashlqi3"
1329   [(set (match_operand:QI 0 "register_operand"           "=r,r,r,r,!d,r,r")
1330         (ashift:QI (match_operand:QI 1 "register_operand" "0,0,0,0,0,0,0")
1331                    (match_operand:QI 2 "general_operand"  "r,L,P,K,n,n,Qm")))]
1332   ""
1333   "* return ashlqi3_out (insn, operands, NULL);"
1334   [(set_attr "length" "5,0,1,2,4,6,9")
1335    (set_attr "cc" "clobber,none,set_czn,set_czn,set_czn,set_czn,clobber")])
1336
1337 (define_insn "ashlhi3"
1338   [(set (match_operand:HI 0 "register_operand"           "=r,r,r,r,r,r,r")
1339         (ashift:HI (match_operand:HI 1 "register_operand" "0,0,0,r,0,0,0")
1340                    (match_operand:QI 2 "general_operand"  "r,L,P,O,K,n,Qm")))]
1341   ""
1342   "* return ashlhi3_out (insn, operands, NULL);"
1343   [(set_attr "length" "6,0,2,2,4,10,10")
1344    (set_attr "cc" "clobber,none,set_n,clobber,set_n,clobber,clobber")])
1345
1346 (define_insn "ashlsi3"
1347   [(set (match_operand:SI 0 "register_operand"           "=r,r,r,r,r,r,r")
1348         (ashift:SI (match_operand:SI 1 "register_operand" "0,0,0,r,0,0,0")
1349                    (match_operand:QI 2 "general_operand"  "r,L,P,O,K,n,Qm")))]
1350   ""
1351   "* return ashlsi3_out (insn, operands, NULL);"
1352   [(set_attr "length" "8,0,4,4,8,10,12")
1353    (set_attr "cc" "clobber,none,set_n,clobber,set_n,clobber,clobber")])
1354
1355 ;; Optimize if a scratch register from LD_REGS happens to be available.
1356
1357 (define_peephole2
1358   [(match_scratch:QI 3 "d")
1359    (set (match_operand:HI 0 "register_operand" "")
1360         (ashift:HI (match_operand:HI 1 "register_operand" "")
1361                    (match_operand:QI 2 "const_int_operand" "")))]
1362   ""
1363   [(parallel [(set (match_dup 0) (ashift:HI (match_dup 1) (match_dup 2)))
1364               (clobber (match_dup 3))])]
1365   "if (!avr_peep2_scratch_safe (operands[3]))
1366      FAIL;")
1367
1368 (define_insn "*ashlhi3_const"
1369   [(set (match_operand:HI 0 "register_operand"            "=r,r,r,r,r")
1370         (ashift:HI (match_operand:HI 1 "register_operand"  "0,0,r,0,0")
1371                    (match_operand:QI 2 "const_int_operand" "L,P,O,K,n")))
1372    (clobber (match_scratch:QI 3 "=X,X,X,X,&d"))]
1373   "reload_completed"
1374   "* return ashlhi3_out (insn, operands, NULL);"
1375   [(set_attr "length" "0,2,2,4,10")
1376    (set_attr "cc" "none,set_n,clobber,set_n,clobber")])
1377
1378 (define_peephole2
1379   [(match_scratch:QI 3 "d")
1380    (set (match_operand:SI 0 "register_operand" "")
1381         (ashift:SI (match_operand:SI 1 "register_operand" "")
1382                    (match_operand:QI 2 "const_int_operand" "")))]
1383   ""
1384   [(parallel [(set (match_dup 0) (ashift:SI (match_dup 1) (match_dup 2)))
1385               (clobber (match_dup 3))])]
1386   "if (!avr_peep2_scratch_safe (operands[3]))
1387      FAIL;")
1388
1389 (define_insn "*ashlsi3_const"
1390   [(set (match_operand:SI 0 "register_operand"            "=r,r,r,r")
1391         (ashift:SI (match_operand:SI 1 "register_operand"  "0,0,r,0")
1392                    (match_operand:QI 2 "const_int_operand" "L,P,O,n")))
1393    (clobber (match_scratch:QI 3 "=X,X,X,&d"))]
1394   "reload_completed"
1395   "* return ashlsi3_out (insn, operands, NULL);"
1396   [(set_attr "length" "0,4,4,10")
1397    (set_attr "cc" "none,set_n,clobber,clobber")])
1398
1399 ;; >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >>
1400 ;; arithmetic shift right
1401
1402 (define_insn "ashrqi3"
1403   [(set (match_operand:QI 0 "register_operand" "=r,r,r,r,r,r")
1404         (ashiftrt:QI (match_operand:QI 1 "register_operand" "0,0,0,0,0,0")
1405                      (match_operand:QI 2 "general_operand"  "r,L,P,K,n,Qm")))]
1406   ""
1407   "* return ashrqi3_out (insn, operands, NULL);"
1408   [(set_attr "length" "5,0,1,2,5,9")
1409    (set_attr "cc" "clobber,none,clobber,clobber,clobber,clobber")])
1410
1411 (define_insn "ashrhi3"
1412   [(set (match_operand:HI 0 "register_operand"             "=r,r,r,r,r,r,r")
1413         (ashiftrt:HI (match_operand:HI 1 "register_operand" "0,0,0,r,0,0,0")
1414                      (match_operand:QI 2 "general_operand"  "r,L,P,O,K,n,Qm")))]
1415   ""
1416   "* return ashrhi3_out (insn, operands, NULL);"
1417   [(set_attr "length" "6,0,2,4,4,10,10")
1418    (set_attr "cc" "clobber,none,clobber,set_n,clobber,clobber,clobber")])
1419
1420 (define_insn "ashrsi3"
1421   [(set (match_operand:SI 0 "register_operand"             "=r,r,r,r,r,r,r")
1422         (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0,0,r,0,0,0")
1423                      (match_operand:QI 2 "general_operand"  "r,L,P,O,K,n,Qm")))]
1424   ""
1425   "* return ashrsi3_out (insn, operands, NULL);"
1426   [(set_attr "length" "8,0,4,6,8,10,12")
1427    (set_attr "cc" "clobber,none,clobber,set_n,clobber,clobber,clobber")])
1428
1429 ;; Optimize if a scratch register from LD_REGS happens to be available.
1430
1431 (define_peephole2
1432   [(match_scratch:QI 3 "d")
1433    (set (match_operand:HI 0 "register_operand" "")
1434         (ashiftrt:HI (match_operand:HI 1 "register_operand" "")
1435                      (match_operand:QI 2 "const_int_operand" "")))]
1436   ""
1437   [(parallel [(set (match_dup 0) (ashiftrt:HI (match_dup 1) (match_dup 2)))
1438               (clobber (match_dup 3))])]
1439   "if (!avr_peep2_scratch_safe (operands[3]))
1440      FAIL;")
1441
1442 (define_insn "*ashrhi3_const"
1443   [(set (match_operand:HI 0 "register_operand"              "=r,r,r,r,r")
1444         (ashiftrt:HI (match_operand:HI 1 "register_operand"  "0,0,r,0,0")
1445                      (match_operand:QI 2 "const_int_operand" "L,P,O,K,n")))
1446    (clobber (match_scratch:QI 3 "=X,X,X,X,&d"))]
1447   "reload_completed"
1448   "* return ashrhi3_out (insn, operands, NULL);"
1449   [(set_attr "length" "0,2,4,4,10")
1450    (set_attr "cc" "none,clobber,set_n,clobber,clobber")])
1451
1452 (define_peephole2
1453   [(match_scratch:QI 3 "d")
1454    (set (match_operand:SI 0 "register_operand" "")
1455         (ashiftrt:SI (match_operand:SI 1 "register_operand" "")
1456                      (match_operand:QI 2 "const_int_operand" "")))]
1457   ""
1458   [(parallel [(set (match_dup 0) (ashiftrt:SI (match_dup 1) (match_dup 2)))
1459               (clobber (match_dup 3))])]
1460   "if (!avr_peep2_scratch_safe (operands[3]))
1461      FAIL;")
1462
1463 (define_insn "*ashrsi3_const"
1464   [(set (match_operand:SI 0 "register_operand"              "=r,r,r,r")
1465         (ashiftrt:SI (match_operand:SI 1 "register_operand"  "0,0,r,0")
1466                      (match_operand:QI 2 "const_int_operand" "L,P,O,n")))
1467    (clobber (match_scratch:QI 3 "=X,X,X,&d"))]
1468   "reload_completed"
1469   "* return ashrsi3_out (insn, operands, NULL);"
1470   [(set_attr "length" "0,4,4,10")
1471    (set_attr "cc" "none,clobber,set_n,clobber")])
1472
1473 ;; >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >>
1474 ;; logical shift right
1475
1476 (define_insn "lshrqi3"
1477   [(set (match_operand:QI 0 "register_operand"             "=r,r,r,r,!d,r,r")
1478         (lshiftrt:QI (match_operand:QI 1 "register_operand" "0,0,0,0,0,0,0")
1479                      (match_operand:QI 2 "general_operand"  "r,L,P,K,n,n,Qm")))]
1480   ""
1481   "* return lshrqi3_out (insn, operands, NULL);"
1482   [(set_attr "length" "5,0,1,2,4,6,9")
1483    (set_attr "cc" "clobber,none,set_czn,set_czn,set_czn,set_czn,clobber")])
1484
1485 (define_insn "lshrhi3"
1486   [(set (match_operand:HI 0 "register_operand"             "=r,r,r,r,r,r,r")
1487         (lshiftrt:HI (match_operand:HI 1 "register_operand" "0,0,0,r,0,0,0")
1488                      (match_operand:QI 2 "general_operand"  "r,L,P,O,K,n,Qm")))]
1489   ""
1490   "* return lshrhi3_out (insn, operands, NULL);"
1491   [(set_attr "length" "6,0,2,2,4,10,10")
1492    (set_attr "cc" "clobber,none,clobber,clobber,clobber,clobber,clobber")])
1493
1494 (define_insn "lshrsi3"
1495   [(set (match_operand:SI 0 "register_operand"             "=r,r,r,r,r,r,r")
1496         (lshiftrt:SI (match_operand:SI 1 "register_operand" "0,0,0,r,0,0,0")
1497                      (match_operand:QI 2 "general_operand"  "r,L,P,O,K,n,Qm")))]
1498   ""
1499   "* return lshrsi3_out (insn, operands, NULL);"
1500   [(set_attr "length" "8,0,4,4,8,10,12")
1501    (set_attr "cc" "clobber,none,clobber,clobber,clobber,clobber,clobber")])
1502
1503 ;; Optimize if a scratch register from LD_REGS happens to be available.
1504
1505 (define_peephole2
1506   [(match_scratch:QI 3 "d")
1507    (set (match_operand:HI 0 "register_operand" "")
1508         (lshiftrt:HI (match_operand:HI 1 "register_operand" "")
1509                      (match_operand:QI 2 "const_int_operand" "")))]
1510   ""
1511   [(parallel [(set (match_dup 0) (lshiftrt:HI (match_dup 1) (match_dup 2)))
1512               (clobber (match_dup 3))])]
1513   "if (!avr_peep2_scratch_safe (operands[3]))
1514      FAIL;")
1515
1516 (define_insn "*lshrhi3_const"
1517   [(set (match_operand:HI 0 "register_operand"              "=r,r,r,r,r")
1518         (lshiftrt:HI (match_operand:HI 1 "register_operand"  "0,0,r,0,0")
1519                      (match_operand:QI 2 "const_int_operand" "L,P,O,K,n")))
1520    (clobber (match_scratch:QI 3 "=X,X,X,X,&d"))]
1521   "reload_completed"
1522   "* return lshrhi3_out (insn, operands, NULL);"
1523   [(set_attr "length" "0,2,2,4,10")
1524    (set_attr "cc" "none,clobber,clobber,clobber,clobber")])
1525
1526 (define_peephole2
1527   [(match_scratch:QI 3 "d")
1528    (set (match_operand:SI 0 "register_operand" "")
1529         (lshiftrt:SI (match_operand:SI 1 "register_operand" "")
1530                      (match_operand:QI 2 "const_int_operand" "")))]
1531   ""
1532   [(parallel [(set (match_dup 0) (lshiftrt:SI (match_dup 1) (match_dup 2)))
1533               (clobber (match_dup 3))])]
1534   "if (!avr_peep2_scratch_safe (operands[3]))
1535      FAIL;")
1536
1537 (define_insn "*lshrsi3_const"
1538   [(set (match_operand:SI 0 "register_operand"              "=r,r,r,r")
1539         (lshiftrt:SI (match_operand:SI 1 "register_operand"  "0,0,r,0")
1540                      (match_operand:QI 2 "const_int_operand" "L,P,O,n")))
1541    (clobber (match_scratch:QI 3 "=X,X,X,&d"))]
1542   "reload_completed"
1543   "* return lshrsi3_out (insn, operands, NULL);"
1544   [(set_attr "length" "0,4,4,10")
1545    (set_attr "cc" "none,clobber,clobber,clobber")])
1546
1547 ;; abs(x) abs(x) abs(x) abs(x) abs(x) abs(x) abs(x) abs(x) abs(x) abs(x) abs(x)
1548 ;; abs
1549
1550 (define_insn "absqi2"
1551   [(set (match_operand:QI 0 "register_operand" "=r")
1552         (abs:QI (match_operand:QI 1 "register_operand" "0")))]
1553   ""
1554   "sbrc %0,7
1555         neg %0"
1556   [(set_attr "length" "2")
1557    (set_attr "cc" "clobber")])
1558
1559
1560 (define_insn "abssf2"
1561   [(set (match_operand:SF 0 "register_operand" "=d,r")
1562         (abs:SF (match_operand:SF 1 "register_operand" "0,0")))]
1563   ""
1564   "@
1565         andi %D0,0x7f
1566         clt\;bld %D0,7"
1567   [(set_attr "length" "1,2")
1568    (set_attr "cc" "set_n,clobber")])
1569
1570 ;; 0 - x  0 - x  0 - x  0 - x  0 - x  0 - x  0 - x  0 - x  0 - x  0 - x  0 - x
1571 ;; neg
1572
1573 (define_insn "negqi2"
1574   [(set (match_operand:QI 0 "register_operand" "=r")
1575         (neg:QI (match_operand:QI 1 "register_operand" "0")))]
1576   ""
1577   "neg %0"
1578   [(set_attr "length" "1")
1579    (set_attr "cc" "set_zn")])
1580
1581 (define_insn "neghi2"
1582   [(set (match_operand:HI 0 "register_operand"       "=!d,r,&r")
1583         (neg:HI (match_operand:HI 1 "register_operand" "0,0,r")))]
1584   ""
1585   "@
1586         com %B0\;neg %A0\;sbci %B0,lo8(-1)
1587         com %B0\;neg %A0\;sbc %B0,__zero_reg__\;inc %B0
1588         clr %A0\;clr %B0\;sub %A0,%A1\;sbc %B0,%B1"
1589   [(set_attr "length" "3,4,4")
1590    (set_attr "cc" "set_czn,set_n,set_czn")])
1591
1592 (define_insn "negsi2"
1593   [(set (match_operand:SI 0 "register_operand"       "=!d,r,&r")
1594         (neg:SI (match_operand:SI 1 "register_operand" "0,0,r")))]
1595   ""
1596   "@
1597         com %D0\;com %C0\;com %B0\;neg %A0\;sbci %B0,lo8(-1)\;sbci %C0,lo8(-1)\;sbci %D0,lo8(-1)
1598         com %D0\;com %C0\;com %B0\;com %A0\;adc %A0,__zero_reg__\;adc %B0,__zero_reg__\;adc %C0,__zero_reg__\;adc %D0,__zero_reg__
1599         clr %A0\;clr %B0\;{clr %C0\;clr %D0|movw %C0,%A0}\;sub %A0,%A1\;sbc %B0,%B1\;sbc %C0,%C1\;sbc %D0,%D1"
1600   [(set_attr_alternative "length"
1601                          [(const_int 7)
1602                           (const_int 8)
1603                           (if_then_else (eq_attr "mcu_have_movw" "yes")
1604                                         (const_int 7)
1605                                         (const_int 8))])
1606    (set_attr "cc" "set_czn,set_n,set_czn")])
1607
1608 (define_insn "negsf2"
1609   [(set (match_operand:SF 0 "register_operand" "=d,r")
1610         (neg:SF (match_operand:SF 1 "register_operand" "0,0")))]
1611   ""
1612   "@
1613         subi %D0,0x80
1614         bst %D0,7\;com %D0\;bld %D0,7\;com %D0"
1615   [(set_attr "length" "1,4")
1616    (set_attr "cc" "set_n,set_n")])
1617
1618 ;; !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
1619 ;; not
1620
1621 (define_insn "one_cmplqi2"
1622   [(set (match_operand:QI 0 "register_operand" "=r")
1623         (not:QI (match_operand:QI 1 "register_operand" "0")))]
1624   ""
1625   "com %0"
1626   [(set_attr "length" "1")
1627    (set_attr "cc" "set_czn")])
1628
1629 (define_insn "one_cmplhi2"
1630   [(set (match_operand:HI 0 "register_operand" "=r")
1631         (not:HI (match_operand:HI 1 "register_operand" "0")))]
1632   ""
1633   "com %0
1634         com %B0"
1635   [(set_attr "length" "2")
1636    (set_attr "cc" "set_n")])
1637
1638 (define_insn "one_cmplsi2"
1639   [(set (match_operand:SI 0 "register_operand" "=r")
1640         (not:SI (match_operand:SI 1 "register_operand" "0")))]
1641   ""
1642   "com %0
1643         com %B0
1644         com %C0
1645         com %D0"
1646   [(set_attr "length" "4")
1647    (set_attr "cc" "set_n")])
1648
1649 ;; xx<---x xx<---x xx<---x xx<---x xx<---x xx<---x xx<---x xx<---x xx<---x
1650 ;; sign extend
1651
1652 (define_insn "extendqihi2"
1653   [(set (match_operand:HI 0 "register_operand" "=r,r")
1654         (sign_extend:HI (match_operand:QI 1 "register_operand" "0,*r")))]
1655   ""
1656   "@
1657         clr %B0\;sbrc %0,7\;com %B0
1658         mov %A0,%A1\;clr %B0\;sbrc %A0,7\;com %B0"
1659   [(set_attr "length" "3,4")
1660    (set_attr "cc" "set_n,set_n")])
1661
1662 (define_insn "extendqisi2"
1663   [(set (match_operand:SI 0 "register_operand" "=r,r")
1664         (sign_extend:SI (match_operand:QI 1 "register_operand" "0,*r")))]
1665   ""
1666   "@
1667         clr %B0\;sbrc %A0,7\;com %B0\;mov %C0,%B0\;mov %D0,%B0
1668         mov %A0,%A1\;clr %B0\;sbrc %A0,7\;com %B0\;mov %C0,%B0\;mov %D0,%B0"
1669   [(set_attr "length" "5,6")
1670    (set_attr "cc" "set_n,set_n")])
1671
1672 (define_insn "extendhisi2"
1673   [(set (match_operand:SI 0 "register_operand"               "=r,&r")
1674         (sign_extend:SI (match_operand:HI 1 "register_operand" "0,*r")))]
1675   ""
1676   "@
1677         clr %C0\;sbrc %B0,7\;com %C0\;mov %D0,%C0
1678         {mov %A0,%A1\;mov %B0,%B1|movw %A0,%A1}\;clr %C0\;sbrc %B0,7\;com %C0\;mov %D0,%C0"
1679   [(set_attr_alternative "length"
1680                          [(const_int 4)
1681                           (if_then_else (eq_attr "mcu_have_movw" "yes")
1682                                         (const_int 5)
1683                                         (const_int 6))])
1684    (set_attr "cc" "set_n,set_n")])
1685
1686 ;; xx<---x xx<---x xx<---x xx<---x xx<---x xx<---x xx<---x xx<---x xx<---x
1687 ;; zero extend
1688
1689 (define_insn_and_split "zero_extendqihi2"
1690   [(set (match_operand:HI 0 "register_operand" "=r")
1691         (zero_extend:HI (match_operand:QI 1 "register_operand" "r")))]
1692   ""
1693   "#"
1694   "reload_completed"
1695   [(set (match_dup 2) (match_dup 1))
1696    (set (match_dup 3) (const_int 0))]
1697   "unsigned int low_off = subreg_lowpart_offset (QImode, HImode);
1698    unsigned int high_off = subreg_highpart_offset (QImode, HImode);
1699    
1700    operands[2] = simplify_gen_subreg (QImode, operands[0], HImode, low_off);
1701    operands[3] = simplify_gen_subreg (QImode, operands[0], HImode, high_off);
1702   ")
1703
1704 (define_insn_and_split "zero_extendqisi2"
1705   [(set (match_operand:SI 0 "register_operand" "=r")
1706         (zero_extend:SI (match_operand:QI 1 "register_operand" "r")))]
1707   ""
1708   "#"
1709   "reload_completed"
1710   [(set (match_dup 2) (zero_extend:HI (match_dup 1)))
1711    (set (match_dup 3) (const_int 0))]
1712   "unsigned int low_off = subreg_lowpart_offset (HImode, SImode);
1713    unsigned int high_off = subreg_highpart_offset (HImode, SImode);
1714    
1715    operands[2] = simplify_gen_subreg (HImode, operands[0], SImode, low_off);
1716    operands[3] = simplify_gen_subreg (HImode, operands[0], SImode, high_off);
1717   ")
1718
1719 (define_insn_and_split "zero_extendhisi2"
1720   [(set (match_operand:SI 0 "register_operand" "=r")
1721         (zero_extend:SI (match_operand:HI 1 "register_operand" "r")))]
1722   ""
1723   "#"
1724   "reload_completed"
1725   [(set (match_dup 2) (match_dup 1))
1726    (set (match_dup 3) (const_int 0))]
1727   "unsigned int low_off = subreg_lowpart_offset (HImode, SImode);
1728    unsigned int high_off = subreg_highpart_offset (HImode, SImode);
1729    
1730    operands[2] = simplify_gen_subreg (HImode, operands[0], SImode, low_off);
1731    operands[3] = simplify_gen_subreg (HImode, operands[0], SImode, high_off);
1732   ")
1733
1734 (define_insn_and_split "zero_extendqidi2"
1735   [(set (match_operand:DI 0 "register_operand" "=r")
1736         (zero_extend:DI (match_operand:QI 1 "register_operand" "r")))]
1737   ""
1738   "#"
1739   "reload_completed"
1740   [(set (match_dup 2) (zero_extend:SI (match_dup 1)))
1741    (set (match_dup 3) (const_int 0))]
1742   "unsigned int low_off = subreg_lowpart_offset (SImode, DImode);
1743    unsigned int high_off = subreg_highpart_offset (SImode, DImode);
1744    
1745    operands[2] = simplify_gen_subreg (SImode, operands[0], DImode, low_off);
1746    operands[3] = simplify_gen_subreg (SImode, operands[0], DImode, high_off);
1747   ")
1748
1749 (define_insn_and_split "zero_extendhidi2"
1750   [(set (match_operand:DI 0 "register_operand" "=r")
1751         (zero_extend:DI (match_operand:HI 1 "register_operand" "r")))]
1752   ""
1753   "#"
1754   "reload_completed"
1755   [(set (match_dup 2) (zero_extend:SI (match_dup 1)))
1756    (set (match_dup 3) (const_int 0))]
1757   "unsigned int low_off = subreg_lowpart_offset (SImode, DImode);
1758    unsigned int high_off = subreg_highpart_offset (SImode, DImode);
1759    
1760    operands[2] = simplify_gen_subreg (SImode, operands[0], DImode, low_off);
1761    operands[3] = simplify_gen_subreg (SImode, operands[0], DImode, high_off);
1762   ")
1763
1764 (define_insn_and_split "zero_extendsidi2"
1765   [(set (match_operand:DI 0 "register_operand" "=r")
1766         (zero_extend:DI (match_operand:SI 1 "register_operand" "r")))]
1767   ""
1768   "#"
1769   "reload_completed"
1770   [(set (match_dup 2) (match_dup 1))
1771    (set (match_dup 3) (const_int 0))]
1772   "unsigned int low_off = subreg_lowpart_offset (SImode, DImode);
1773    unsigned int high_off = subreg_highpart_offset (SImode, DImode);
1774    
1775    operands[2] = simplify_gen_subreg (SImode, operands[0], DImode, low_off);
1776    operands[3] = simplify_gen_subreg (SImode, operands[0], DImode, high_off);
1777   ")
1778
1779 ;;<=><=><=><=><=><=><=><=><=><=><=><=><=><=><=><=><=><=><=><=><=><=><=><=><=>
1780 ;; compare
1781
1782 (define_insn "tstqi"
1783   [(set (cc0)
1784         (match_operand:QI 0 "register_operand" "r"))]
1785   ""
1786   "tst %0"
1787   [(set_attr "cc" "compare")
1788    (set_attr "length" "1")])
1789
1790 (define_insn "*negated_tstqi"
1791   [(set (cc0)
1792         (neg:QI (match_operand:QI 0 "register_operand" "r")))]
1793   ""
1794   "cp __zero_reg__,%0"
1795   [(set_attr "cc" "compare")
1796    (set_attr "length" "1")])
1797
1798 (define_insn "tsthi"
1799   [(set (cc0)
1800         (match_operand:HI 0 "register_operand" "!w,r"))]
1801   ""
1802   "* return out_tsthi (insn,NULL);"
1803 [(set_attr "cc" "compare,compare")
1804  (set_attr "length" "1,2")])
1805
1806 (define_insn "*negated_tsthi"
1807   [(set (cc0)
1808         (neg:HI (match_operand:HI 0 "register_operand" "r")))]
1809   ""
1810   "cp __zero_reg__,%A0
1811         cpc __zero_reg__,%B0"
1812 [(set_attr "cc" "compare")
1813  (set_attr "length" "2")])
1814
1815 (define_insn "tstsi"
1816   [(set (cc0)
1817         (match_operand:SI 0 "register_operand" "r"))]
1818   ""
1819   "* return out_tstsi (insn,NULL);"
1820   [(set_attr "cc" "compare")
1821    (set_attr "length" "4")])
1822
1823 (define_insn "*negated_tstsi"
1824   [(set (cc0)
1825         (neg:SI (match_operand:SI 0 "register_operand" "r")))]
1826   ""
1827   "cp __zero_reg__,%A0
1828         cpc __zero_reg__,%B0
1829         cpc __zero_reg__,%C0
1830         cpc __zero_reg__,%D0"
1831   [(set_attr "cc" "compare")
1832    (set_attr "length" "4")])
1833
1834
1835 (define_insn "cmpqi"
1836   [(set (cc0)
1837         (compare (match_operand:QI 0 "register_operand"  "r,d")
1838                  (match_operand:QI 1 "nonmemory_operand" "r,i")))]
1839   ""
1840   "@
1841         cp %0,%1
1842         cpi %0,lo8(%1)"
1843   [(set_attr "cc" "compare,compare")
1844    (set_attr "length" "1,1")])
1845
1846 (define_insn "*cmpqi_sign_extend"
1847   [(set (cc0)
1848         (compare (sign_extend:HI
1849                   (match_operand:QI 0 "register_operand"  "d"))
1850                  (match_operand:HI 1 "const_int_operand" "n")))]
1851   "INTVAL (operands[1]) >= -128 && INTVAL (operands[1]) <= 127"
1852   "cpi %0,lo8(%1)"
1853   [(set_attr "cc" "compare")
1854    (set_attr "length" "1")])
1855
1856 (define_insn "cmphi"
1857   [(set (cc0)
1858         (compare (match_operand:HI 0 "register_operand"  "r,d,d,r,r")
1859                  (match_operand:HI 1 "nonmemory_operand" "r,M,i,M,i")))
1860    (clobber (match_scratch:QI 2 "=X,X,&d,&d,&d"))]
1861   ""
1862   "*{
1863   switch (which_alternative)
1864     {
1865     case 0:
1866       return (AS2 (cp,%A0,%A1) CR_TAB
1867               AS2 (cpc,%B0,%B1));
1868     case 1:
1869       if (reg_unused_after (insn, operands[0])
1870           && INTVAL (operands[1]) >= 0 && INTVAL (operands[1]) <= 63
1871           && test_hard_reg_class (ADDW_REGS, operands[0]))
1872         return AS2 (sbiw,%0,%1);
1873        else
1874         return (AS2 (cpi,%0,%1) CR_TAB
1875                 AS2 (cpc,%B0,__zero_reg__));
1876     case 2:
1877       if (reg_unused_after (insn, operands[0]))
1878         return (AS2 (subi,%0,lo8(%1))  CR_TAB
1879                 AS2 (sbci,%B0,hi8(%1)));
1880       else
1881         return (AS2 (ldi, %2,hi8(%1))  CR_TAB
1882                 AS2 (cpi, %A0,lo8(%1)) CR_TAB
1883                 AS2 (cpc, %B0,%2));
1884    case 3:
1885       return (AS2 (ldi, %2,lo8(%1))  CR_TAB
1886               AS2 (cp, %A0,%2) CR_TAB
1887               AS2 (cpc, %B0,__zero_reg__));
1888
1889    case 4:
1890       return (AS2 (ldi, %2,lo8(%1))  CR_TAB
1891               AS2 (cp, %A0,%2)       CR_TAB
1892               AS2 (ldi, %2,hi8(%1)) CR_TAB
1893               AS2 (cpc, %B0,%2));
1894     }
1895   return \"bug\";
1896 }" 
1897   [(set_attr "cc" "compare,compare,compare,compare,compare")
1898    (set_attr "length" "2,2,3,3,4")])
1899
1900
1901 (define_insn "cmpsi"
1902   [(set (cc0)
1903         (compare (match_operand:SI 0 "register_operand"  "r,d,d,r,r")
1904                  (match_operand:SI 1 "nonmemory_operand" "r,M,i,M,i")))
1905    (clobber (match_scratch:QI 2 "=X,X,&d,&d,&d"))]
1906   ""
1907   "*{
1908   switch (which_alternative)
1909     {
1910     case 0:
1911       return (AS2 (cp,%A0,%A1) CR_TAB
1912               AS2 (cpc,%B0,%B1) CR_TAB
1913               AS2 (cpc,%C0,%C1) CR_TAB
1914               AS2 (cpc,%D0,%D1));
1915     case 1:
1916       if (reg_unused_after (insn, operands[0])
1917           && INTVAL (operands[1]) >= 0 && INTVAL (operands[1]) <= 63
1918           && test_hard_reg_class (ADDW_REGS, operands[0]))
1919         return (AS2 (sbiw,%0,%1) CR_TAB
1920                 AS2 (cpc,%C0,__zero_reg__) CR_TAB
1921                 AS2 (cpc,%D0,__zero_reg__));
1922       else
1923         return (AS2 (cpi,%A0,lo8(%1))  CR_TAB
1924                 AS2 (cpc,%B0,__zero_reg__) CR_TAB
1925                 AS2 (cpc,%C0,__zero_reg__) CR_TAB
1926                 AS2 (cpc,%D0,__zero_reg__));
1927     case 2:
1928       if (reg_unused_after (insn, operands[0]))
1929         return (AS2 (subi,%A0,lo8(%1))  CR_TAB
1930                 AS2 (sbci,%B0,hi8(%1))  CR_TAB
1931                 AS2 (sbci,%C0,hlo8(%1))  CR_TAB
1932                 AS2 (sbci,%D0,hhi8(%1)));
1933       else
1934        return (AS2 (cpi, %A0,lo8(%1))   CR_TAB
1935                AS2 (ldi, %2,hi8(%1))  CR_TAB
1936                AS2 (cpc, %B0,%2)       CR_TAB
1937                AS2 (ldi, %2,hlo8(%1))  CR_TAB
1938                AS2 (cpc, %C0,%2)       CR_TAB
1939                AS2 (ldi, %2,hhi8(%1)) CR_TAB
1940                AS2 (cpc, %D0,%2));
1941     case 3:
1942         return (AS2 (ldi,%2,lo8(%1))        CR_TAB
1943                 AS2 (cp,%A0,%2)            CR_TAB
1944                 AS2 (cpc,%B0,__zero_reg__) CR_TAB
1945                 AS2 (cpc,%C0,__zero_reg__) CR_TAB
1946                 AS2 (cpc,%D0,__zero_reg__));
1947     case 4:
1948        return (AS2 (ldi, %2,lo8(%1))   CR_TAB
1949                AS2 (cp, %A0,%2)        CR_TAB
1950                AS2 (ldi, %2,hi8(%1))  CR_TAB
1951                AS2 (cpc, %B0,%2)       CR_TAB
1952                AS2 (ldi, %2,hlo8(%1))  CR_TAB
1953                AS2 (cpc, %C0,%2)       CR_TAB
1954                AS2 (ldi, %2,hhi8(%1)) CR_TAB
1955                AS2 (cpc, %D0,%2));
1956     }
1957   return \"bug\";
1958 }"
1959   [(set_attr "cc" "compare,compare,compare,compare,compare")
1960    (set_attr "length" "4,4,7,5,8")])
1961
1962 ;; ----------------------------------------------------------------------
1963 ;; JUMP INSTRUCTIONS
1964 ;; ----------------------------------------------------------------------
1965 ;; Conditional jump instructions
1966
1967 (define_expand "beq"
1968   [(set (pc)
1969         (if_then_else (eq (cc0) (const_int 0))
1970                       (label_ref (match_operand 0 "" ""))
1971                       (pc)))]
1972   ""
1973   "")
1974
1975 (define_expand "bne"
1976   [(set (pc)
1977         (if_then_else (ne (cc0) (const_int 0))
1978                       (label_ref (match_operand 0 "" ""))
1979                       (pc)))]
1980   ""
1981   "")
1982
1983 (define_expand "bge"
1984   [(set (pc)
1985         (if_then_else (ge (cc0) (const_int 0))
1986                       (label_ref (match_operand 0 "" ""))
1987                       (pc)))]
1988   ""
1989   "")
1990
1991 (define_expand "bgeu"
1992   [(set (pc)
1993         (if_then_else (geu (cc0) (const_int 0))
1994                       (label_ref (match_operand 0 "" ""))
1995                       (pc)))]
1996   ""
1997   "")
1998
1999 (define_expand "blt"
2000   [(set (pc)
2001         (if_then_else (lt (cc0) (const_int 0))
2002                       (label_ref (match_operand 0 "" ""))
2003                       (pc)))]
2004   ""
2005   "")
2006
2007 (define_expand "bltu"
2008   [(set (pc)
2009         (if_then_else (ltu (cc0) (const_int 0))
2010                       (label_ref (match_operand 0 "" ""))
2011                       (pc)))]
2012   ""
2013   "")
2014
2015
2016
2017 /****************************************************************
2018  AVR not have following conditional jumps: LE,LEU,GT,GTU.
2019  Convert them all to proper jumps.
2020 *****************************************************************/
2021
2022 (define_expand "ble"
2023   [(set (pc)
2024         (if_then_else (le (cc0) (const_int 0))
2025                       (label_ref (match_operand 0 "" ""))
2026                       (pc)))]
2027   ""
2028   "")
2029
2030 (define_expand "bleu"
2031   [(set (pc)
2032         (if_then_else (leu (cc0) (const_int 0))
2033                       (label_ref (match_operand 0 "" ""))
2034                       (pc)))]
2035   ""
2036   "")
2037
2038 (define_expand "bgt"
2039   [(set (pc)
2040         (if_then_else (gt (cc0) (const_int 0))
2041                       (label_ref (match_operand 0 "" ""))
2042                       (pc)))]
2043   ""
2044   "")
2045
2046 (define_expand "bgtu"
2047   [(set (pc)
2048         (if_then_else (gtu (cc0) (const_int 0))
2049                       (label_ref (match_operand 0 "" ""))
2050                       (pc)))]
2051   ""
2052   "")
2053
2054 ;; Test a single bit in a QI/HI/SImode register.
2055 (define_insn "*sbrx_branch"
2056   [(set (pc)
2057         (if_then_else
2058          (match_operator 0 "eqne_operator"
2059                          [(zero_extract
2060                            (match_operand:QI 1 "register_operand" "r")
2061                            (const_int 1)
2062                            (match_operand 2 "const_int_operand" "n"))
2063                           (const_int 0)])
2064          (label_ref (match_operand 3 "" ""))
2065          (pc)))]
2066   ""
2067   "* return avr_out_sbxx_branch (insn, operands);"
2068   [(set (attr "length")
2069         (if_then_else (and (ge (minus (pc) (match_dup 3)) (const_int -2046))
2070                            (le (minus (pc) (match_dup 3)) (const_int 2046)))
2071                       (const_int 2)
2072                       (if_then_else (eq_attr "mcu_mega" "no")
2073                                     (const_int 2)
2074                                     (const_int 4))))
2075    (set_attr "cc" "clobber")])
2076
2077 (define_insn "*sbrx_and_branchhi"
2078   [(set (pc)
2079         (if_then_else
2080          (match_operator 0 "eqne_operator"
2081                          [(and:HI
2082                            (match_operand:HI 1 "register_operand" "r")
2083                            (match_operand:HI 2 "single_one_operand" "n"))
2084                           (const_int 0)])
2085          (label_ref (match_operand 3 "" ""))
2086          (pc)))]
2087   ""
2088   "* return avr_out_sbxx_branch (insn, operands);"
2089   [(set (attr "length")
2090         (if_then_else (and (ge (minus (pc) (match_dup 3)) (const_int -2046))
2091                            (le (minus (pc) (match_dup 3)) (const_int 2046)))
2092                       (const_int 2)
2093                       (if_then_else (eq_attr "mcu_mega" "no")
2094                                     (const_int 2)
2095                                     (const_int 4))))
2096    (set_attr "cc" "clobber")])
2097
2098 (define_insn "*sbrx_and_branchsi"
2099   [(set (pc)
2100         (if_then_else
2101          (match_operator 0 "eqne_operator"
2102                          [(and:SI
2103                            (match_operand:SI 1 "register_operand" "r")
2104                            (match_operand:SI 2 "single_one_operand" "n"))
2105                           (const_int 0)])
2106          (label_ref (match_operand 3 "" ""))
2107          (pc)))]
2108   ""
2109   "* return avr_out_sbxx_branch (insn, operands);"
2110   [(set (attr "length")
2111         (if_then_else (and (ge (minus (pc) (match_dup 3)) (const_int -2046))
2112                            (le (minus (pc) (match_dup 3)) (const_int 2046)))
2113                       (const_int 2)
2114                       (if_then_else (eq_attr "mcu_mega" "no")
2115                                     (const_int 2)
2116                                     (const_int 4))))
2117    (set_attr "cc" "clobber")])
2118
2119 ;; Convert sign tests to bit 7/15/31 tests that match the above insns.
2120 (define_peephole2
2121   [(set (cc0) (match_operand:QI 0 "register_operand" ""))
2122    (set (pc) (if_then_else (ge (cc0) (const_int 0))
2123                            (label_ref (match_operand 1 "" ""))
2124                            (pc)))]
2125   ""
2126   [(set (pc) (if_then_else (eq (zero_extract (match_dup 0)
2127                                              (const_int 1)
2128                                              (const_int 7))
2129                                (const_int 0))
2130                            (label_ref (match_dup 1))
2131                            (pc)))]
2132   "")
2133
2134 (define_peephole2
2135   [(set (cc0) (match_operand:QI 0 "register_operand" ""))
2136    (set (pc) (if_then_else (lt (cc0) (const_int 0))
2137                            (label_ref (match_operand 1 "" ""))
2138                            (pc)))]
2139   ""
2140   [(set (pc) (if_then_else (ne (zero_extract (match_dup 0)
2141                                              (const_int 1)
2142                                              (const_int 7))
2143                                (const_int 0))
2144                            (label_ref (match_dup 1))
2145                            (pc)))]
2146   "")
2147
2148 (define_peephole2
2149   [(set (cc0) (match_operand:HI 0 "register_operand" ""))
2150    (set (pc) (if_then_else (ge (cc0) (const_int 0))
2151                            (label_ref (match_operand 1 "" ""))
2152                            (pc)))]
2153   ""
2154   [(set (pc) (if_then_else (eq (and:HI (match_dup 0) (const_int -32768))
2155                                (const_int 0))
2156                            (label_ref (match_dup 1))
2157                            (pc)))]
2158   "")
2159
2160 (define_peephole2
2161   [(set (cc0) (match_operand:HI 0 "register_operand" ""))
2162    (set (pc) (if_then_else (lt (cc0) (const_int 0))
2163                            (label_ref (match_operand 1 "" ""))
2164                            (pc)))]
2165   ""
2166   [(set (pc) (if_then_else (ne (and:HI (match_dup 0) (const_int -32768))
2167                                (const_int 0))
2168                            (label_ref (match_dup 1))
2169                            (pc)))]
2170   "")
2171
2172 (define_peephole2
2173   [(set (cc0) (match_operand:SI 0 "register_operand" ""))
2174    (set (pc) (if_then_else (ge (cc0) (const_int 0))
2175                            (label_ref (match_operand 1 "" ""))
2176                            (pc)))]
2177   ""
2178   [(set (pc) (if_then_else (eq (and:SI (match_dup 0) (match_dup 2))
2179                                (const_int 0))
2180                            (label_ref (match_dup 1))
2181                            (pc)))]
2182   "operands[2] = GEN_INT (-2147483647 - 1);")
2183
2184 (define_peephole2
2185   [(set (cc0) (match_operand:SI 0 "register_operand" ""))
2186    (set (pc) (if_then_else (lt (cc0) (const_int 0))
2187                            (label_ref (match_operand 1 "" ""))
2188                            (pc)))]
2189   ""
2190   [(set (pc) (if_then_else (ne (and:SI (match_dup 0) (match_dup 2))
2191                                (const_int 0))
2192                            (label_ref (match_dup 1))
2193                            (pc)))]
2194   "operands[2] = GEN_INT (-2147483647 - 1);")
2195
2196 ;; ************************************************************************
2197 ;; Implementation of conditional jumps here.
2198 ;;  Compare with 0 (test) jumps
2199 ;; ************************************************************************
2200
2201 (define_insn "branch"
2202   [(set (pc)
2203         (if_then_else (match_operator 1 "simple_comparison_operator"
2204                         [(cc0)
2205                          (const_int 0)])
2206                       (label_ref (match_operand 0 "" ""))
2207                       (pc)))]
2208   ""
2209   "*
2210    return ret_cond_branch (operands[1], avr_jump_mode (operands[0],insn), 0);"
2211   [(set_attr "type" "branch")
2212    (set_attr "cc" "clobber")])
2213
2214 (define_insn "difficult_branch"
2215   [(set (pc)
2216         (if_then_else (match_operator 1 "difficult_comparison_operator"
2217                         [(cc0)
2218                          (const_int 0)])
2219                       (label_ref (match_operand 0 "" ""))
2220                       (pc)))]
2221   ""
2222   "*
2223    return ret_cond_branch (operands[1], avr_jump_mode (operands[0],insn), 0);"
2224   [(set_attr "type" "branch1")
2225    (set_attr "cc" "clobber")])
2226
2227 ;; revers branch
2228
2229 (define_insn "rvbranch"
2230   [(set (pc)
2231         (if_then_else (match_operator 1 "simple_comparison_operator" 
2232                         [(cc0)
2233                          (const_int 0)])
2234                       (pc)
2235                       (label_ref (match_operand 0 "" ""))))]
2236   ""
2237   "*
2238    return ret_cond_branch (operands[1], avr_jump_mode (operands[0], insn), 1);"
2239   [(set_attr "type" "branch1")
2240    (set_attr "cc" "clobber")])
2241
2242 (define_insn "difficult_rvbranch"
2243   [(set (pc)
2244         (if_then_else (match_operator 1 "difficult_comparison_operator" 
2245                         [(cc0)
2246                          (const_int 0)])
2247                       (pc)
2248                       (label_ref (match_operand 0 "" ""))))]
2249   ""
2250   "*
2251    return ret_cond_branch (operands[1], avr_jump_mode (operands[0], insn), 1);"
2252   [(set_attr "type" "branch")
2253    (set_attr "cc" "clobber")])
2254
2255 ;; **************************************************************************
2256 ;; Unconditional and other jump instructions.
2257
2258 (define_insn "jump"
2259   [(set (pc)
2260         (label_ref (match_operand 0 "" "")))]
2261   ""
2262   "*{
2263   if (AVR_MEGA && get_attr_length (insn) != 1)
2264     return AS1 (jmp,%0);
2265   return AS1 (rjmp,%0);
2266 }"
2267   [(set (attr "length")
2268         (if_then_else (match_operand 0 "symbol_ref_operand" "") 
2269                 (if_then_else (eq_attr "mcu_mega" "no")
2270                               (const_int 1)
2271                               (const_int 2))
2272                 (if_then_else (and (ge (minus (pc) (match_dup 0)) (const_int -2047))
2273                                    (le (minus (pc) (match_dup 0)) (const_int 2047)))
2274                               (const_int 1)
2275                               (const_int 2))))
2276    (set_attr "cc" "none")])
2277
2278 ;; call
2279
2280 (define_expand "call"
2281   [(call (match_operand:HI 0 "call_insn_operand" "")
2282          (match_operand:HI 1 "general_operand" ""))]
2283   ;; Operand 1 not used on the AVR.
2284   ""
2285   "")
2286
2287 ;; call value
2288
2289 (define_expand "call_value"
2290   [(set (match_operand 0 "register_operand" "")
2291         (call (match_operand:HI 1 "call_insn_operand" "")
2292               (match_operand:HI 2 "general_operand" "")))]
2293   ;; Operand 2 not used on the AVR.
2294   ""
2295   "")
2296
2297 (define_insn "call_insn"
2298   [(call (mem:HI (match_operand:HI 0 "nonmemory_operand" "!z,*r,s,n"))
2299          (match_operand:HI 1 "general_operand" "X,X,X,X"))]
2300 ;; We don't need in saving Z register because r30,r31 is a call used registers
2301   ;; Operand 1 not used on the AVR.
2302   "(register_operand (operands[0], HImode) || CONSTANT_P (operands[0]))"
2303   "*{
2304   if (which_alternative==0)
2305      return \"%!icall\";
2306   else if (which_alternative==1)
2307     {
2308       if (AVR_HAVE_MOVW)
2309         return (AS2 (movw, r30, %0) CR_TAB
2310                \"%!icall\");
2311       else
2312         return (AS2 (mov, r30, %A0) CR_TAB
2313                 AS2 (mov, r31, %B0) CR_TAB
2314                 \"%!icall\");
2315     }
2316   else if (which_alternative==2)
2317     return AS1(%~call,%c0);
2318   return (AS2 (ldi,r30,lo8(%0)) CR_TAB
2319           AS2 (ldi,r31,hi8(%0)) CR_TAB
2320           \"%!icall\");
2321 }"
2322   [(set_attr "cc" "clobber,clobber,clobber,clobber")
2323    (set_attr_alternative "length"
2324                          [(const_int 1)
2325                           (if_then_else (eq_attr "mcu_have_movw" "yes")
2326                                         (const_int 2)
2327                                         (const_int 3))
2328                           (if_then_else (eq_attr "mcu_mega" "yes")
2329                                         (const_int 2)
2330                                         (const_int 1))
2331                           (const_int 3)])])
2332
2333 (define_insn "call_value_insn"
2334   [(set (match_operand 0 "register_operand" "=r,r,r,r")
2335         (call (mem:HI (match_operand:HI 1 "nonmemory_operand" "!z,*r,s,n"))
2336 ;; We don't need in saving Z register because r30,r31 is a call used registers
2337               (match_operand:HI 2 "general_operand" "X,X,X,X")))]
2338   ;; Operand 2 not used on the AVR.
2339   "(register_operand (operands[0], VOIDmode) || CONSTANT_P (operands[0]))"
2340   "*{
2341   if (which_alternative==0)
2342      return \"%!icall\";
2343   else if (which_alternative==1)
2344     {
2345       if (AVR_HAVE_MOVW)
2346         return (AS2 (movw, r30, %1) CR_TAB
2347                 \"%!icall\");
2348       else
2349         return (AS2 (mov, r30, %A1) CR_TAB
2350                 AS2 (mov, r31, %B1) CR_TAB
2351                 \"%!icall\");
2352     }
2353   else if (which_alternative==2)
2354     return AS1(%~call,%c1);
2355   return (AS2 (ldi, r30, lo8(%1)) CR_TAB
2356           AS2 (ldi, r31, hi8(%1)) CR_TAB
2357           \"%!icall\");
2358 }"
2359   [(set_attr "cc" "clobber,clobber,clobber,clobber")
2360    (set_attr_alternative "length"
2361                          [(const_int 1)
2362                           (if_then_else (eq_attr "mcu_have_movw" "yes")
2363                                         (const_int 2)
2364                                         (const_int 3))
2365                           (if_then_else (eq_attr "mcu_mega" "yes")
2366                                         (const_int 2)
2367                                         (const_int 1))
2368                           (const_int 3)])])
2369
2370 (define_insn "nop"
2371   [(const_int 0)]
2372   ""
2373   "nop"
2374   [(set_attr "cc" "none")
2375    (set_attr "length" "1")])
2376
2377 ; indirect jump
2378 (define_insn "indirect_jump"
2379   [(set (pc) (match_operand:HI 0 "register_operand" "!z,*r"))]
2380   "!AVR_HAVE_EIJMP_EICALL"
2381   "@
2382         ijmp
2383         push %A0\;push %B0\;ret"
2384   [(set_attr "length" "1,3")
2385    (set_attr "cc" "none,none")])
2386
2387 (define_insn "*indirect_jump_avr6"
2388   [(set (pc) (match_operand:HI 0 "register_operand" "z"))]
2389   "AVR_HAVE_EIJMP_EICALL"
2390   "eijmp"
2391   [(set_attr "length" "1")
2392    (set_attr "cc" "none")])
2393
2394 ;; table jump
2395
2396 ;; Table made from "rjmp" instructions for <=8K devices.
2397 (define_insn "*tablejump_rjmp"
2398   [(set (pc) (unspec:HI [(match_operand:HI 0 "register_operand" "!z,*r")]
2399                         UNSPEC_INDEX_JMP))
2400    (use (label_ref (match_operand 1 "" "")))
2401    (clobber (match_dup 0))]
2402   "(!AVR_HAVE_JMP_CALL) && (!AVR_HAVE_EIJMP_EICALL)"
2403   "@
2404         ijmp
2405         push %A0\;push %B0\;ret"
2406   [(set_attr "length" "1,3")
2407    (set_attr "cc" "none,none")])
2408
2409 ;; Not a prologue, but similar idea - move the common piece of code to libgcc.
2410 (define_insn "*tablejump_lib"
2411   [(set (pc) (unspec:HI [(match_operand:HI 0 "register_operand" "z")]
2412                         UNSPEC_INDEX_JMP))
2413    (use (label_ref (match_operand 1 "" "")))
2414    (clobber (match_dup 0))]
2415   "AVR_MEGA && TARGET_CALL_PROLOGUES"
2416   "jmp __tablejump2__"
2417   [(set_attr "length" "2")
2418    (set_attr "cc" "clobber")])
2419
2420 (define_insn "*tablejump_enh"
2421   [(set (pc) (unspec:HI [(match_operand:HI 0 "register_operand" "z")]
2422                         UNSPEC_INDEX_JMP))
2423    (use (label_ref (match_operand 1 "" "")))
2424    (clobber (match_dup 0))]
2425   "AVR_MEGA && AVR_HAVE_LPMX"
2426   "lsl r30
2427         rol r31
2428         lpm __tmp_reg__,Z+
2429         lpm r31,Z
2430         mov r30,__tmp_reg__
2431         %!ijmp"
2432   [(set_attr "length" "6")
2433    (set_attr "cc" "clobber")])
2434
2435 (define_insn "*tablejump"
2436   [(set (pc) (unspec:HI [(match_operand:HI 0 "register_operand" "z")]
2437                         UNSPEC_INDEX_JMP))
2438    (use (label_ref (match_operand 1 "" "")))
2439    (clobber (match_dup 0))]
2440   "AVR_HAVE_JMP_CALL && !AVR_HAVE_EIJMP_EICALL"
2441   "lsl r30
2442         rol r31
2443         lpm
2444         inc r30
2445         push r0
2446         lpm
2447         push r0
2448         ret"
2449   [(set_attr "length" "8")
2450    (set_attr "cc" "clobber")])
2451
2452 (define_expand "casesi"
2453   [(set (match_dup 6)
2454         (minus:HI (subreg:HI (match_operand:SI 0 "register_operand" "") 0)
2455                   (match_operand:HI 1 "register_operand" "")))
2456    (parallel [(set (cc0)
2457                    (compare (match_dup 6)
2458                             (match_operand:HI 2 "register_operand" "")))
2459               (clobber (match_scratch:QI 9 ""))])
2460    
2461    (set (pc)
2462         (if_then_else (gtu (cc0)
2463                            (const_int 0))
2464                       (label_ref (match_operand 4 "" ""))
2465                       (pc)))
2466
2467    (set (match_dup 6)
2468         (plus:HI (match_dup 6) (label_ref (match_operand:HI 3 "" ""))))
2469
2470    (parallel [(set (pc) (unspec:HI [(match_dup 6)] UNSPEC_INDEX_JMP))
2471               (use (label_ref (match_dup 3)))
2472               (clobber (match_dup 6))])]
2473   ""
2474   "
2475 {
2476   operands[6] = gen_reg_rtx (HImode);
2477 }")
2478
2479
2480 ;; ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
2481 ;; This instruction sets Z flag
2482
2483 (define_insn "sez"
2484   [(set (cc0) (const_int 0))]
2485   ""
2486   "sez"
2487   [(set_attr "length" "1")
2488    (set_attr "cc" "compare")])
2489
2490 ;; Clear/set/test a single bit in I/O address space.
2491
2492 (define_insn "*cbi"
2493   [(set (mem:QI (match_operand 0 "low_io_address_operand" "n"))
2494         (and:QI (mem:QI (match_dup 0))
2495                 (match_operand:QI 1 "single_zero_operand" "n")))]
2496   "(optimize > 0)"
2497 {
2498   operands[2] = GEN_INT (exact_log2 (~INTVAL (operands[1]) & 0xff));
2499   return AS2 (cbi,%0-0x20,%2);
2500 }
2501   [(set_attr "length" "1")
2502    (set_attr "cc" "none")])
2503
2504 (define_insn "*sbi"
2505   [(set (mem:QI (match_operand 0 "low_io_address_operand" "n"))
2506         (ior:QI (mem:QI (match_dup 0))
2507                 (match_operand:QI 1 "single_one_operand" "n")))]
2508   "(optimize > 0)"
2509 {
2510   operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1]) & 0xff));
2511   return AS2 (sbi,%0-0x20,%2);
2512 }
2513   [(set_attr "length" "1")
2514    (set_attr "cc" "none")])
2515
2516 ;; Lower half of the I/O space - use sbic/sbis directly.
2517 (define_insn "*sbix_branch"
2518   [(set (pc)
2519         (if_then_else
2520          (match_operator 0 "eqne_operator"
2521                          [(zero_extract
2522                            (mem:QI (match_operand 1 "low_io_address_operand" "n"))
2523                            (const_int 1)
2524                            (match_operand 2 "const_int_operand" "n"))
2525                           (const_int 0)])
2526          (label_ref (match_operand 3 "" ""))
2527          (pc)))]
2528   "(optimize > 0)"
2529   "* return avr_out_sbxx_branch (insn, operands);"
2530   [(set (attr "length")
2531         (if_then_else (and (ge (minus (pc) (match_dup 3)) (const_int -2046))
2532                            (le (minus (pc) (match_dup 3)) (const_int 2046)))
2533                       (const_int 2)
2534                       (if_then_else (eq_attr "mcu_mega" "no")
2535                                     (const_int 2)
2536                                     (const_int 4))))
2537    (set_attr "cc" "clobber")])
2538
2539 ;; Tests of bit 7 are pessimized to sign tests, so we need this too...
2540 (define_insn "*sbix_branch_bit7"
2541   [(set (pc)
2542         (if_then_else
2543          (match_operator 0 "gelt_operator"
2544                          [(mem:QI (match_operand 1 "low_io_address_operand" "n"))
2545                           (const_int 0)])
2546          (label_ref (match_operand 2 "" ""))
2547          (pc)))]
2548   "(optimize > 0)"
2549 {
2550   operands[3] = operands[2];
2551   operands[2] = GEN_INT (7);
2552   return avr_out_sbxx_branch (insn, operands);
2553 }
2554   [(set (attr "length")
2555         (if_then_else (and (ge (minus (pc) (match_dup 2)) (const_int -2046))
2556                            (le (minus (pc) (match_dup 2)) (const_int 2046)))
2557                       (const_int 2)
2558                       (if_then_else (eq_attr "mcu_mega" "no")
2559                                     (const_int 2)
2560                                     (const_int 4))))
2561    (set_attr "cc" "clobber")])
2562
2563 ;; Upper half of the I/O space - read port to __tmp_reg__ and use sbrc/sbrs.
2564 (define_insn "*sbix_branch_tmp"
2565   [(set (pc)
2566         (if_then_else
2567          (match_operator 0 "eqne_operator"
2568                          [(zero_extract
2569                            (mem:QI (match_operand 1 "high_io_address_operand" "n"))
2570                            (const_int 1)
2571                            (match_operand 2 "const_int_operand" "n"))
2572                           (const_int 0)])
2573          (label_ref (match_operand 3 "" ""))
2574          (pc)))]
2575   "(optimize > 0)"
2576   "* return avr_out_sbxx_branch (insn, operands);"
2577   [(set (attr "length")
2578         (if_then_else (and (ge (minus (pc) (match_dup 3)) (const_int -2046))
2579                            (le (minus (pc) (match_dup 3)) (const_int 2045)))
2580                       (const_int 3)
2581                       (if_then_else (eq_attr "mcu_mega" "no")
2582                                     (const_int 3)
2583                                     (const_int 5))))
2584    (set_attr "cc" "clobber")])
2585
2586 (define_insn "*sbix_branch_tmp_bit7"
2587   [(set (pc)
2588         (if_then_else
2589          (match_operator 0 "gelt_operator"
2590                          [(mem:QI (match_operand 1 "high_io_address_operand" "n"))
2591                           (const_int 0)])
2592          (label_ref (match_operand 2 "" ""))
2593          (pc)))]
2594   "(optimize > 0)"
2595 {
2596   operands[3] = operands[2];
2597   operands[2] = GEN_INT (7);
2598   return avr_out_sbxx_branch (insn, operands);
2599 }
2600   [(set (attr "length")
2601         (if_then_else (and (ge (minus (pc) (match_dup 2)) (const_int -2046))
2602                            (le (minus (pc) (match_dup 2)) (const_int 2045)))
2603                       (const_int 3)
2604                       (if_then_else (eq_attr "mcu_mega" "no")
2605                                     (const_int 3)
2606                                     (const_int 5))))
2607    (set_attr "cc" "clobber")])
2608
2609 ;; ************************* Peepholes ********************************
2610
2611 (define_peephole
2612   [(set (match_operand:SI 0 "d_register_operand" "")
2613         (plus:SI (match_dup 0)
2614                  (const_int -1)))
2615    (parallel
2616     [(set (cc0)
2617           (compare (match_dup 0)
2618                    (const_int -1)))
2619      (clobber (match_operand:QI 1 "d_register_operand" ""))])
2620    (set (pc)
2621         (if_then_else (ne (cc0) (const_int 0))
2622                       (label_ref (match_operand 2 "" ""))
2623                       (pc)))]
2624   ""
2625   "*
2626 {
2627   CC_STATUS_INIT;
2628   if (test_hard_reg_class (ADDW_REGS, operands[0]))
2629     output_asm_insn (AS2 (sbiw,%0,1) CR_TAB
2630                      AS2 (sbc,%C0,__zero_reg__) CR_TAB
2631                      AS2 (sbc,%D0,__zero_reg__) \"\\n\", operands);
2632   else
2633     output_asm_insn (AS2 (subi,%A0,1) CR_TAB
2634                      AS2 (sbc,%B0,__zero_reg__) CR_TAB
2635                      AS2 (sbc,%C0,__zero_reg__) CR_TAB
2636                      AS2 (sbc,%D0,__zero_reg__) \"\\n\", operands);
2637   switch (avr_jump_mode (operands[2],insn))
2638   {
2639     case 1:
2640       return AS1 (brcc,%2);
2641     case 2:
2642       return (AS1 (brcs,.+2) CR_TAB
2643               AS1 (rjmp,%2));
2644   }
2645   return (AS1 (brcs,.+4) CR_TAB
2646           AS1 (jmp,%2));
2647 }")
2648
2649 (define_peephole
2650   [(set (match_operand:HI 0 "d_register_operand" "")
2651         (plus:HI (match_dup 0)
2652                  (const_int -1)))
2653    (parallel
2654     [(set (cc0)
2655           (compare (match_dup 0)
2656                    (const_int 65535)))
2657      (clobber (match_operand:QI 1 "d_register_operand" ""))])
2658    (set (pc)
2659         (if_then_else (ne (cc0) (const_int 0))
2660                       (label_ref (match_operand 2 "" ""))
2661                       (pc)))]
2662   ""
2663   "*
2664 {
2665   CC_STATUS_INIT;
2666   if (test_hard_reg_class (ADDW_REGS, operands[0]))
2667     output_asm_insn (AS2 (sbiw,%0,1), operands);
2668   else
2669     output_asm_insn (AS2 (subi,%A0,1) CR_TAB
2670                      AS2 (sbc,%B0,__zero_reg__) \"\\n\", operands);
2671   switch (avr_jump_mode (operands[2],insn))
2672   {
2673     case 1:
2674       return AS1 (brcc,%2);
2675     case 2:
2676       return (AS1 (brcs,.+2) CR_TAB
2677               AS1 (rjmp,%2));
2678   }
2679   return (AS1 (brcs,.+4) CR_TAB
2680           AS1 (jmp,%2));
2681 }")
2682
2683 (define_peephole
2684   [(set (match_operand:QI 0 "d_register_operand" "")
2685         (plus:QI (match_dup 0)
2686                  (const_int -1)))
2687    (set (cc0)
2688         (compare (match_dup 0)
2689                  (const_int -1)))
2690    (set (pc)
2691         (if_then_else (ne (cc0) (const_int 0))
2692                       (label_ref (match_operand 1 "" ""))
2693                       (pc)))]
2694   ""
2695   "*
2696 {
2697   CC_STATUS_INIT;
2698   cc_status.value1 = operands[0];
2699   cc_status.flags |= CC_OVERFLOW_UNUSABLE;
2700   output_asm_insn (AS2 (subi,%A0,1), operands);
2701   switch (avr_jump_mode (operands[1],insn))
2702   {
2703     case 1:
2704       return AS1 (brcc,%1);
2705     case 2:
2706       return (AS1 (brcs,.+2) CR_TAB
2707               AS1 (rjmp,%1));
2708   }
2709   return (AS1 (brcs,.+4) CR_TAB
2710           AS1 (jmp,%1));
2711 }")
2712
2713 (define_peephole
2714   [(set (cc0) (match_operand:QI 0 "register_operand" ""))
2715    (set (pc)
2716         (if_then_else (eq (cc0) (const_int 0))
2717                       (label_ref (match_operand 1 "" ""))
2718                       (pc)))]
2719   "jump_over_one_insn_p (insn, operands[1])"
2720   "cpse %0,__zero_reg__")
2721
2722 (define_peephole
2723   [(set (cc0)
2724         (compare (match_operand:QI 0 "register_operand" "")
2725                  (match_operand:QI 1 "register_operand" "")))
2726    (set (pc)
2727         (if_then_else (eq (cc0) (const_int 0))
2728                       (label_ref (match_operand 2 "" ""))
2729                       (pc)))]
2730   "jump_over_one_insn_p (insn, operands[2])"
2731   "cpse %0,%1")
2732
2733 ;;pppppppppppppppppppppppppppppppppppppppppppppppppppp
2734 ;;prologue/epilogue support instructions
2735
2736 (define_insn "popqi"
2737   [(set (match_operand:QI 0 "register_operand" "=r")
2738         (mem:QI (post_inc (reg:HI REG_SP))))]
2739   ""
2740   "pop %0"
2741   [(set_attr "cc" "none")
2742    (set_attr "length" "1")])
2743
2744 (define_insn "pophi"
2745   [(set (match_operand:HI 0 "register_operand" "=r")
2746         (mem:HI (post_inc (reg:HI REG_SP))))]
2747   ""
2748   "pop %A0\;pop %B0"
2749   [(set_attr "cc" "none")
2750    (set_attr "length" "2")])
2751
2752 ;; Enable Interrupts
2753 (define_insn "enable_interrupt"
2754   [(unspec [(const_int 0)] UNSPEC_SEI)]
2755   ""
2756   "sei"
2757   [(set_attr "length" "1")
2758   (set_attr "cc" "none")
2759   ])
2760
2761 ;; Disable Interrupts
2762 (define_insn "disable_interrupt"
2763   [(unspec [(const_int 0)] UNSPEC_CLI)]
2764   ""
2765   "cli"
2766   [(set_attr "length" "1")
2767   (set_attr "cc" "none")
2768   ])
2769
2770 ;;  Library prologue saves
2771 (define_insn "call_prologue_saves"
2772   [(unspec_volatile:HI [(const_int 0)] UNSPECV_PROLOGUE_SAVES)
2773    (match_operand:HI 0 "immediate_operand" "")
2774    (set (reg:HI REG_SP) (minus:HI 
2775                            (reg:HI REG_SP)
2776                            (match_operand:HI 1 "immediate_operand" "")))
2777    (use (reg:HI REG_X))
2778    (clobber (reg:HI REG_Z))]
2779   ""
2780   "ldi r30,pm_lo8(1f)
2781         ldi r31,pm_hi8(1f)
2782         %~jmp __prologue_saves__+((18 - %0) * 2)
2783 1:"
2784   [(set_attr_alternative "length"
2785                          [(if_then_else (eq_attr "mcu_mega" "yes")
2786                                         (const_int 6)
2787                                         (const_int 5))])
2788   (set_attr "cc" "clobber")
2789   ])
2790   
2791 ;  epilogue  restores using library
2792 (define_insn "epilogue_restores"
2793   [(unspec_volatile:QI [(const_int 0)] UNSPECV_EPILOGUE_RESTORES)
2794    (set (reg:HI REG_Y ) (plus:HI 
2795                            (reg:HI REG_Y)
2796                            (match_operand:HI 0 "immediate_operand" ""))) 
2797    (set (reg:HI REG_SP) (reg:HI REG_Y))
2798    (clobber  (reg:QI REG_Z))]
2799   ""
2800   "ldi r30, lo8(%0)
2801         %~jmp __epilogue_restores__ + ((18 - %0) * 2)"
2802   [(set_attr_alternative "length"
2803                          [(if_then_else (eq_attr "mcu_mega" "yes")
2804                                         (const_int 3)
2805                                         (const_int 2))])
2806   (set_attr "cc" "clobber")
2807   ])
2808   
2809 ; return
2810 (define_insn "return"
2811   [(return)]
2812   "reload_completed && avr_simple_epilogue ()"
2813   "ret"
2814   [(set_attr "cc" "none")
2815    (set_attr "length" "1")])
2816
2817 (define_insn "return_from_epilogue"
2818   [(return)]
2819   "(reload_completed 
2820     && cfun->machine 
2821     && !(cfun->machine->is_interrupt || cfun->machine->is_signal)
2822     && !cfun->machine->is_naked)"
2823   "ret"
2824   [(set_attr "cc" "none")
2825    (set_attr "length" "1")])
2826
2827 (define_insn "return_from_interrupt_epilogue"
2828   [(return)]
2829   "(reload_completed 
2830     && cfun->machine 
2831     && (cfun->machine->is_interrupt || cfun->machine->is_signal)
2832     && !cfun->machine->is_naked)"
2833   "reti"
2834   [(set_attr "cc" "none")
2835    (set_attr "length" "1")])
2836
2837 (define_insn "return_from_naked_epilogue"
2838   [(return)]
2839   "(reload_completed 
2840     && cfun->machine 
2841     && cfun->machine->is_naked)"
2842   ""
2843   [(set_attr "cc" "none")
2844    (set_attr "length" "0")])
2845
2846 (define_expand "prologue"
2847   [(const_int 0)]
2848   ""
2849   "
2850   {
2851     expand_prologue (); 
2852     DONE;
2853   }")
2854
2855 (define_expand "epilogue"
2856   [(const_int 0)]
2857   ""
2858   "
2859   {
2860     expand_epilogue (); 
2861     DONE;
2862   }")