-diff -ur ../gcc-4.3.4.orig/libiberty/Makefile.in ./libiberty/Makefile.in
---- ../gcc-4.3.4.orig/libiberty/Makefile.in 2007-07-25 08:26:45.000000000 +0200
-+++ ./libiberty/Makefile.in 2009-10-02 15:20:13.000000000 +0200
-@@ -344,7 +344,8 @@
+diff -Naurp libiberty/Makefile.in libiberty/Makefile.in
+--- libiberty/Makefile.in 2010-03-02 00:09:56.000000000 -0600
++++ libiberty/Makefile.in 2011-01-18 17:27:57.000000000 -0600
+@@ -321,7 +321,8 @@ libiberty.html : $(srcdir)/libiberty.tex
@MAINT@ echo stamp > stamp-functions
INSTALL_DEST = @INSTALL_DEST@
# This is tricky. Even though CC in the Makefile contains
# multilib-specific flags, it's overridden by FLAGS_TO_PASS from the
-Only in ./libiberty: Makefile.in.orig
--- /dev/null
+diff -rupN gcc/config/avr/avr.c gcc/config/avr/avr.c
+--- gcc/config/avr/avr.c 2010-04-02 14:54:46.000000000 -0500
++++ gcc/config/avr/avr.c 2010-09-21 14:31:30.000000000 -0500
+@@ -192,6 +192,19 @@ static const struct attribute_spec avr_a
+ #undef TARGET_CAN_ELIMINATE
+ #define TARGET_CAN_ELIMINATE avr_can_eliminate
+
++#undef TARGET_SCALAR_MODE_SUPPORTED_P
++#define TARGET_SCALAR_MODE_SUPPORTED_P avr_scalar_mode_supported_p
++
++ /* Implement TARGET_SCALAR_MODE_SUPPORTED_P. */
++ static bool
++ avr_scalar_mode_supported_p (enum machine_mode mode)
++ {
++ if (ALL_FIXED_POINT_MODE_P (mode))
++ return true;
++
++ return default_scalar_mode_supported_p (mode);
++ }
++
+ struct gcc_target targetm = TARGET_INITIALIZER;
+ \f
+ void
+@@ -1609,9 +1622,9 @@ output_movqi (rtx insn, rtx operands[],
+
+ *l = 1;
+
+- if (register_operand (dest, QImode))
++ if (register_operand (dest, VOIDmode))
+ {
+- if (register_operand (src, QImode)) /* mov r,r */
++ if (register_operand (src, VOIDmode)) /* mov r,r */
+ {
+ if (test_hard_reg_class (STACK_REG, dest))
+ return AS2 (out,%0,%1);
+@@ -1699,9 +1712,9 @@ output_movhi (rtx insn, rtx operands[],
+ if (!l)
+ l = &dummy;
+
+- if (register_operand (dest, HImode))
++ if (register_operand (dest, VOIDmode))
+ {
+- if (register_operand (src, HImode)) /* mov r,r */
++ if (register_operand (src, VOIDmode)) /* mov r,r */
+ {
+ if (test_hard_reg_class (STACK_REG, dest))
+ {
+@@ -2424,6 +2437,14 @@ output_movsisf(rtx insn, rtx operands[],
+ {
+ if (test_hard_reg_class (LD_REGS, dest)) /* ldi d,i */
+ {
++ if (AVR_HAVE_MOVW
++ && (UINTVAL (src) >> 16) == (UINTVAL (src) & 0xffff))
++ {
++ *l = 3;
++ return (AS2 (ldi,%A0,lo8(%1)) CR_TAB
++ AS2 (ldi,%B0,hi8(%1)) CR_TAB
++ AS2 (movw,%C0,%A0));
++ }
+ *l = 4;
+ return (AS2 (ldi,%A0,lo8(%1)) CR_TAB
+ AS2 (ldi,%B0,hi8(%1)) CR_TAB
+@@ -4354,6 +4375,196 @@ avr_rotate_bytes (rtx operands[])
+ return true;
+ }
+
++/* Outputs instructions needed for fixed point conversion. */
++
++const char *
++fract_out (rtx insn ATTRIBUTE_UNUSED, rtx operands[], int intsigned, int *len)
++{
++ int i, k = 0;
++ int sbit[2], ilen[2], flen[2], tlen[2];
++ int rdest, rsource, offset;
++ int start, end, dir;
++ int hadbst = 0, hadlsl = 0;
++ int clrword = -1, lastclr = 0, clr = 0;
++ char buf[20];
++
++ if (!len)
++ len = &k;
++
++ for (i = 0; i < 2; i++)
++ {
++ enum machine_mode mode = GET_MODE (operands[i]);
++ tlen[i] = GET_MODE_SIZE (mode);
++ if (SCALAR_INT_MODE_P (mode))
++ {
++ sbit[i] = intsigned;
++ ilen[i] = GET_MODE_BITSIZE(mode) / 8;
++ flen[i] = 0;
++ }
++ else if (ALL_SCALAR_FIXED_POINT_MODE_P (mode))
++ {
++ sbit[i] = SIGNED_SCALAR_FIXED_POINT_MODE_P (mode);
++ ilen[i] = (GET_MODE_IBIT (mode) + 1) / 8;
++ flen[i] = (GET_MODE_FBIT (mode) + 1) / 8;
++ }
++ else
++ fatal_insn ("unsupported fixed-point conversion", insn);
++ }
++
++ rdest = true_regnum (operands[0]);
++ rsource = true_regnum (operands[1]);
++ offset = flen[1] - flen[0];
++
++ /* Store the sign bit if the destination is a signed
++ fract and the source has a sign in the integer part. */
++ if (sbit[0] && !ilen[0] && sbit[1] && ilen[1])
++ {
++ /* To avoid using bst and bld if the source and
++ destination registers overlap we can use a single lsl
++ since we don't care about preserving the source register. */
++ if (rdest < rsource + tlen[1] && rdest + tlen[0] > rsource)
++ {
++ sprintf (buf, "lsl r%d", rsource + tlen[1] - 1);
++ hadlsl = 1;
++ }
++ else
++ {
++ sprintf (buf, "bst r%d, 7", rsource + tlen[1] - 1);
++ hadbst = 1;
++ }
++ output_asm_insn (buf, operands);
++ ++*len;
++ }
++
++ /* Pick the correct direction. */
++ if (rdest < rsource + offset)
++ {
++ dir = 1;
++ start = 0;
++ end = tlen[0];
++ }
++ else
++ {
++ dir = -1;
++ start = tlen[0] - 1;
++ end = -1;
++ }
++
++ /* Move registers into place, clearing registers that do not overlap. */
++ for (i = start; i != end; i += dir)
++ {
++ int destloc = rdest + i, sourceloc = rsource + i + offset;
++ if (sourceloc < rsource || sourceloc >= rsource + tlen[1])
++ {
++ if (AVR_HAVE_MOVW && i+dir != end
++ && (sourceloc+dir < rsource || sourceloc+dir >= rsource + tlen[1])
++ && ((dir == 1 && !(destloc%2) && !(sourceloc%2))
++ || (dir == -1 && (destloc%2) && (sourceloc%2)))
++ && clrword != -1)
++ {
++ sprintf (buf, "movw r%d, r%d", destloc&0xfe, clrword&0xfe);
++ i += dir;
++ }
++ else
++ {
++ /* Do not clear the register if it is going to get
++ sign extended with a mov later. */
++ if (sbit[0] && sbit[1] && i != tlen[0] - 1 && i >= flen[0])
++ continue;
++
++ sprintf (buf, "clr r%d", destloc);
++ if (lastclr)
++ clrword = destloc;
++ clr=1;
++ }
++ }
++ else if (destloc == sourceloc)
++ continue;
++ else
++ if (AVR_HAVE_MOVW && i+dir != end
++ && sourceloc+dir >= rsource && sourceloc+dir < rsource + tlen[1]
++ && ((dir == 1 && !(destloc%2) && !(sourceloc%2))
++ || (dir == -1 && (destloc%2) && (sourceloc%2))))
++ {
++ sprintf (buf, "movw r%d, r%d", destloc&0xfe, sourceloc&0xfe);
++ i += dir;
++ }
++ else
++ sprintf (buf, "mov r%d, r%d", destloc, sourceloc);
++
++ output_asm_insn (buf, operands);
++ ++*len;
++
++ lastclr = clr;
++ clr = 0;
++ }
++
++ /* Perform sign extension if needed. */
++ if (sbit[0] && sbit[1] && ilen[0] > ilen[1])
++ {
++ sprintf (buf, "sbrc r%d, 7", rdest+tlen[1]-1-offset);
++ output_asm_insn (buf, operands);
++ sprintf (buf, "com r%d", rdest+tlen[0]-1);
++ output_asm_insn (buf, operands);
++ *len += 2;
++ /* Sign extend additional bytes. */
++ start = rdest + tlen[0] - 2;
++ end = rdest + flen[0] + ilen[1] - 1;
++ for (i = start; i != end; i--)
++ {
++ if (AVR_HAVE_MOVW && i != start && i-1 != end)
++ sprintf (buf, "movw r%d, r%d", --i, rdest+tlen[0]-2);
++ else
++ sprintf (buf, "mov r%d, r%d", i, rdest+tlen[0]-1);
++ output_asm_insn (buf, operands);
++ ++*len;
++ }
++ }
++
++ /* Perform shifts, only needed if one operand
++ is a signed fract, and the other is not. */
++ if (sbit[0] && !ilen[0] && (!sbit[1] || ilen[1]))
++ {
++ start = rdest+flen[0]-1;
++ end = rdest + flen[0] - flen[1];
++ if (end < rdest)
++ end = rdest;
++ for (i = start; i >= end; i--)
++ {
++ if (i == start && !hadlsl)
++ sprintf (buf, "lsr r%d", i);
++ else
++ sprintf (buf, "ror r%d", i);
++ output_asm_insn (buf, operands);
++ ++*len;
++ }
++
++ if (hadbst)
++ {
++ sprintf (buf, "bld r%d, 7", rdest + tlen[0] - 1);
++ output_asm_insn (buf, operands);
++ ++*len;
++ }
++ }
++ else if (sbit[1] && !ilen[1] && (!sbit[0] || ilen[0]))
++ {
++ start = rdest + flen[0] - flen[1];
++ if (start < rdest)
++ start = rdest;
++ for (i = start; i<rdest+flen[0]; i++)
++ {
++ if (i == start)
++ sprintf (buf, "lsl r%d", i);
++ else
++ sprintf (buf, "rol r%d", i);
++ output_asm_insn (buf, operands);
++ ++*len;
++ }
++ }
++
++ return "";
++}
++
+ /* Modifies the length assigned to instruction INSN
+ LEN is the initially computed length of the insn. */
+
+diff -rupN gcc/config/avr/avr-fixed.md gcc/config/avr/avr-fixed.md
+--- gcc/config/avr/avr-fixed.md 1969-12-31 18:00:00.000000000 -0600
++++ gcc/config/avr/avr-fixed.md 2010-09-21 14:31:30.000000000 -0500
+@@ -0,0 +1,338 @@
++;; -*- Mode: Scheme -*-
++;; This file contains instructions that support fixed-point operations
++;; for ATMEL AVR micro controllers.
++;; Copyright (C) 2009
++;; Free Software Foundation, Inc.
++;; Contributed by Sean D'Epagnier (sean@depagnier.com)
++
++;; This file is part of GCC.
++
++;; GCC is free software; you can redistribute it and/or modify
++;; it under the terms of the GNU General Public License as published by
++;; the Free Software Foundation; either version 3, or (at your option)
++;; any later version.
++
++;; GCC is distributed in the hope that it will be useful,
++;; but WITHOUT ANY WARRANTY; without even the implied warranty of
++;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
++;; GNU General Public License for more details.
++
++;; You should have received a copy of the GNU General Public License
++;; along with GCC; see the file COPYING3. If not see
++;; <http://www.gnu.org/licenses/>.
++
++(define_mode_iterator ALLQQ [(QQ "") (UQQ "")])
++(define_mode_iterator ALLHQ [(HQ "") (UHQ "")])
++(define_mode_iterator ALLHA [(HA "") (UHA "")])
++(define_mode_iterator ALLHQHA [(HQ "") (UHQ "") (HA "") (UHA "")])
++(define_mode_iterator ALLSA [(SA "") (USA "")])
++
++;;; Conversions
++
++(define_mode_iterator FIXED1 [(QQ "") (UQQ "") (HQ "") (UHQ "")
++ (SQ "") (USQ "") (DQ "") (UDQ "")
++ (HA "") (UHA "") (SA "") (USA "")
++ (DA "") (UDA "") (TA "") (UTA "")
++ (QI "") (HI "") (SI "") (DI "")])
++(define_mode_iterator FIXED2 [(QQ "") (UQQ "") (HQ "") (UHQ "")
++ (SQ "") (USQ "") (DQ "") (UDQ "")
++ (HA "") (UHA "") (SA "") (USA "")
++ (DA "") (UDA "") (TA "") (UTA "")
++ (QI "") (HI "") (SI "") (DI "")])
++
++(define_insn "fract<FIXED2:mode><FIXED1:mode>2"
++ [(set (match_operand:FIXED1 0 "register_operand" "=r")
++ (fract_convert:FIXED1 (match_operand:FIXED2 1 "register_operand" "r")))]
++ ""
++ "* return fract_out (insn, operands, 1, NULL);"
++ [(set_attr "cc" "clobber")])
++
++(define_insn "fractuns<FIXED2:mode><FIXED1:mode>2"
++ [(set (match_operand:FIXED1 0 "register_operand" "=r")
++ (unsigned_fract_convert:FIXED1 (match_operand:FIXED2 1 "register_operand" "r")))]
++ ""
++ "* return fract_out (insn, operands, 0, NULL);"
++ [(set_attr "cc" "clobber")])
++
++;;; Addition/Subtraction, mostly identical to integer versions
++
++(define_insn "add<ALLQQ:mode>3"
++ [(set (match_operand:ALLQQ 0 "register_operand" "=r,d")
++ (plus:ALLQQ (match_operand:ALLQQ 1 "register_operand" "%0,0")
++ (match_operand:ALLQQ 2 "nonmemory_operand" "r,i")))]
++ ""
++ "@
++ add %0,%2
++ subi %0,lo8(-(%2))"
++ [(set_attr "length" "1,1")
++ (set_attr "cc" "set_czn,set_czn")])
++
++(define_insn "sub<ALLQQ:mode>3"
++ [(set (match_operand:ALLQQ 0 "register_operand" "=r,d")
++ (minus:ALLQQ (match_operand:ALLQQ 1 "register_operand" "0,0")
++ (match_operand:ALLQQ 2 "nonmemory_operand" "r,i")))]
++ ""
++ "@
++ sub %0,%2
++ subi %0,lo8(%2)"
++ [(set_attr "length" "1,1")
++ (set_attr "cc" "set_czn,set_czn")])
++
++
++(define_insn "add<ALLHQHA:mode>3"
++ [(set (match_operand:ALLHQHA 0 "register_operand" "=r,d")
++ (plus:ALLHQHA (match_operand:ALLHQHA 1 "register_operand" "%0,0")
++ (match_operand:ALLHQHA 2 "nonmemory_operand" "r,i")))]
++ ""
++ "@
++ add %A0,%A2\;adc %B0,%B2
++ subi %A0,lo8(-(%2))\;sbci %B0,hi8(-(%2))"
++ [(set_attr "length" "2,2")
++ (set_attr "cc" "set_n,set_czn")])
++
++(define_insn "sub<ALLHQHA:mode>3"
++ [(set (match_operand:ALLHQHA 0 "register_operand" "=r,d")
++ (minus:ALLHQHA (match_operand:ALLHQHA 1 "register_operand" "0,0")
++ (match_operand:ALLHQHA 2 "nonmemory_operand" "r,i")))]
++ ""
++ "@
++ sub %A0,%A2\;sbc %B0,%B2
++ subi %A0,lo8(%2)\;sbci %B0,hi8(%2)"
++ [(set_attr "length" "2,2")
++ (set_attr "cc" "set_czn,set_czn")])
++
++(define_insn "add<ALLSA:mode>3"
++ [(set (match_operand:ALLSA 0 "register_operand" "=r,d")
++ (plus:ALLSA (match_operand:ALLSA 1 "register_operand" "%0,0")
++ (match_operand:ALLSA 2 "nonmemory_operand" "r,i")))]
++ ""
++ "@
++ add %A0,%A2\;adc %B0,%B2\;adc %C0,%C2\;adc %D0,%D2
++ subi %0,lo8(-(%2))\;sbci %B0,hi8(-(%2))\;sbci %C0,hlo8(-(%2))\;sbci %D0,hhi8(-(%2))"
++ [(set_attr "length" "4,4")
++ (set_attr "cc" "set_n,set_czn")])
++
++(define_insn "sub<ALLSA:mode>3"
++ [(set (match_operand:ALLSA 0 "register_operand" "=r,d")
++ (minus:ALLSA (match_operand:ALLSA 1 "register_operand" "0,0")
++ (match_operand:ALLSA 2 "nonmemory_operand" "r,i")))]
++ ""
++ "@
++ sub %0,%2\;sbc %B0,%B2\;sbc %C0,%C2\;sbc %D0,%D2
++ subi %A0,lo8(%2)\;sbci %B0,hi8(%2)\;sbci %C0,hlo8(%2)\;sbci %D0,hhi8(%2)"
++ [(set_attr "length" "4,4")
++ (set_attr "cc" "set_czn,set_czn")])
++
++;******************************************************************************
++; mul
++
++(define_insn "mulqq3"
++ [(set (match_operand:QQ 0 "register_operand" "=r")
++ (mult:QQ (match_operand:QQ 1 "register_operand" "a")
++ (match_operand:QQ 2 "register_operand" "a")))]
++ "AVR_HAVE_MUL"
++ "fmuls %1,%2\;mov %0,r1\;clr r1"
++ [(set_attr "length" "3")
++ (set_attr "cc" "clobber")])
++
++(define_insn "muluqq3"
++ [(set (match_operand:UQQ 0 "register_operand" "=r")
++ (mult:UQQ (match_operand:UQQ 1 "register_operand" "r")
++ (match_operand:UQQ 2 "register_operand" "r")))]
++ "AVR_HAVE_MUL"
++ "mul %1,%2\;mov %0,r1\;clr r1"
++ [(set_attr "length" "3")
++ (set_attr "cc" "clobber")])
++
++;; (reg:ALLHQ 20) not clobbered on the enhanced core.
++;; use registers from 16-23 so we can use fmuls
++;; All call-used registers clobbered otherwise - normal library call.
++(define_expand "mul<ALLHQ:mode>3"
++ [(set (reg:ALLHQ 22) (match_operand:ALLHQ 1 "register_operand" ""))
++ (set (reg:ALLHQ 20) (match_operand:ALLHQ 2 "register_operand" ""))
++ (parallel [(set (reg:ALLHQ 18) (mult:ALLHQ (reg:ALLHQ 22) (reg:ALLHQ 20)))
++ (clobber (reg:ALLHQ 22))])
++ (set (match_operand:ALLHQ 0 "register_operand" "") (reg:ALLHQ 18))]
++ "AVR_HAVE_MUL"
++ "")
++
++(define_insn "*mul<ALLHQ:mode>3_enh_call"
++ [(set (reg:ALLHQ 18) (mult:ALLHQ (reg:ALLHQ 22) (reg:ALLHQ 20)))
++ (clobber (reg:ALLHQ 22))]
++ "AVR_HAVE_MUL"
++ "%~call __mul<ALLHQ:mode>3"
++ [(set_attr "type" "xcall")
++ (set_attr "cc" "clobber")])
++
++; Special calls for with and without mul.
++(define_expand "mul<ALLHA:mode>3"
++ [(set (reg:ALLHA 22) (match_operand:ALLHA 1 "register_operand" ""))
++ (set (reg:ALLHA 20) (match_operand:ALLHA 2 "register_operand" ""))
++ (parallel [(set (reg:ALLHA 18) (mult:ALLHA (reg:ALLHA 22) (reg:ALLHA 20)))
++ (clobber (reg:ALLHA 22))])
++ (set (match_operand:ALLHA 0 "register_operand" "") (reg:ALLHA 18))]
++ ""
++ "
++{
++ if (!AVR_HAVE_MUL)
++ {
++ emit_insn (gen_mul<ALLHA:mode>3_call (operands[0], operands[1], operands[2]));
++ DONE;
++ }
++}")
++
++(define_insn "*mul<ALLHA:mode>3_enh"
++ [(set (reg:ALLHA 18) (mult:ALLHA (reg:ALLHA 22) (reg:ALLHA 20)))
++ (clobber (reg:ALLHA 22))]
++ "AVR_HAVE_MUL"
++ "%~call __mul<ALLHA:mode>3"
++ [(set_attr "type" "xcall")
++ (set_attr "cc" "clobber")])
++
++; Without multiplier, clobbers both inputs, and needs a separate output register
++(define_expand "mul<ALLHA:mode>3_call"
++ [(set (reg:ALLHA 24) (match_operand:ALLHA 1 "register_operand" ""))
++ (set (reg:ALLHA 22) (match_operand:ALLHA 2 "register_operand" ""))
++ (parallel [(set (reg:ALLHA 18) (mult:ALLHA (reg:ALLHA 22) (reg:ALLHA 24)))
++ (clobber (reg:ALLHA 22))
++ (clobber (reg:ALLHA 24))])
++ (set (match_operand:ALLHA 0 "register_operand" "") (reg:ALLHA 18))]
++ "!AVR_HAVE_MUL"
++ "")
++
++(define_insn "*mul<ALLHA:mode>3_call"
++ [(set (reg:ALLHA 18) (mult:ALLHA (reg:ALLHA 22) (reg:ALLHA 24)))
++ (clobber (reg:ALLHA 22))
++ (clobber (reg:ALLHA 24))]
++ "!AVR_HAVE_MUL"
++ "%~call __mul<ALLHA:mode>3"
++ [(set_attr "type" "xcall")
++ (set_attr "cc" "clobber")])
++
++;; On the enhanced core, don't clobber either input, and use a separate output,
++;; r2 is needed as a zero register since r1 is used for mul
++(define_expand "mul<ALLSA:mode>3"
++ [(set (reg:ALLSA 16) (match_operand:ALLSA 1 "register_operand" ""))
++ (set (reg:ALLSA 20) (match_operand:ALLSA 2 "register_operand" ""))
++ (parallel [(set (reg:ALLSA 24) (mult:ALLSA (reg:ALLSA 16) (reg:ALLSA 20)))
++ (clobber (reg:QI 15))])
++ (set (match_operand:ALLSA 0 "register_operand" "") (reg:ALLSA 24))]
++ ""
++ "
++{
++ if (!AVR_HAVE_MUL)
++ {
++ emit_insn (gen_mul<ALLSA:mode>3_call (operands[0], operands[1], operands[2]));
++ DONE;
++ }
++}")
++
++(define_insn "*mul<ALLSA:mode>3_enh"
++ [(set (reg:ALLSA 24) (mult:ALLSA (reg:ALLSA 16) (reg:ALLSA 20)))
++ (clobber (reg:QI 15))]
++ "AVR_HAVE_MUL"
++ "%~call __mul<ALLSA:mode>3"
++ [(set_attr "type" "xcall")
++ (set_attr "cc" "clobber")])
++
++; Without multiplier, clobbers both inputs, needs a separate output, and also
++; needs two more scratch registers
++(define_expand "mul<ALLSA:mode>3_call"
++ [(set (reg:ALLSA 18) (match_operand:ALLSA 1 "register_operand" ""))
++ (set (reg:ALLSA 24) (match_operand:ALLSA 2 "register_operand" ""))
++ (parallel [(set (reg:ALLSA 14) (mult:ALLSA (reg:ALLSA 18) (reg:ALLSA 24)))
++ (clobber (reg:ALLSA 18))
++ (clobber (reg:ALLSA 24))
++ (clobber (reg:HI 22))])
++ (set (match_operand:ALLSA 0 "register_operand" "") (reg:ALLSA 14))]
++ "!AVR_HAVE_MUL"
++ "")
++
++(define_insn "*mul<ALLSA:mode>3_call"
++ [(set (reg:ALLSA 14) (mult:ALLSA (reg:ALLSA 18) (reg:ALLSA 24)))
++ (clobber (reg:ALLSA 18))
++ (clobber (reg:ALLSA 24))
++ (clobber (reg:HI 22))]
++ "!AVR_HAVE_MUL"
++ "%~call __mul<ALLSA:mode>3"
++ [(set_attr "type" "xcall")
++ (set_attr "cc" "clobber")])
++
++; / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
++; div
++
++(define_code_iterator usdiv [udiv div]) ; do signed and unsigned in one shot
++
++(define_expand "<usdiv:code><ALLQQ:mode>3"
++ [(set (reg:ALLQQ 25) (match_operand:ALLQQ 1 "register_operand" ""))
++ (set (reg:ALLQQ 22) (match_operand:ALLQQ 2 "register_operand" ""))
++ (parallel [(set (reg:ALLQQ 24) (usdiv:ALLQQ (reg:ALLQQ 25) (reg:ALLQQ 22)))
++ (clobber (reg:ALLQQ 25))
++ (clobber (reg:QI 23))])
++ (set (match_operand:ALLQQ 0 "register_operand" "") (reg:ALLQQ 24))]
++ ""
++ "")
++
++(define_insn "*<usdiv:code><ALLQQ:mode>3_call"
++ [(set (reg:ALLQQ 24) (usdiv:ALLQQ (reg:ALLQQ 25) (reg:ALLQQ 22)))
++ (clobber (reg:ALLQQ 25))
++ (clobber (reg:QI 23))]
++ ""
++ "%~call __<usdiv:code><ALLQQ:mode>3"
++ [(set_attr "type" "xcall")
++ (set_attr "cc" "clobber")])
++
++(define_expand "<usdiv:code><ALLHQHA:mode>3"
++ [(set (reg:ALLHQHA 26) (match_operand:ALLHQHA 1 "register_operand" ""))
++ (set (reg:ALLHQHA 22) (match_operand:ALLHQHA 2 "register_operand" ""))
++ (parallel [(set (reg:ALLHQHA 24) (usdiv:ALLHQHA (reg:ALLHQHA 26) (reg:ALLHQHA 22)))
++ (clobber (reg:ALLHQHA 26))
++ (clobber (reg:QI 21))])
++ (set (match_operand:ALLHQHA 0 "register_operand" "") (reg:ALLHQHA 24))]
++ ""
++ "")
++
++(define_insn "*<usdiv:code><ALLHQHA:mode>3_call"
++ [(set (reg:ALLHQHA 24) (usdiv:ALLHQHA (reg:ALLHQHA 26) (reg:ALLHQHA 22)))
++ (clobber (reg:ALLHQHA 26))
++ (clobber (reg:QI 21))]
++ ""
++ "%~call __<usdiv:code><ALLHQHA:mode>3"
++ [(set_attr "type" "xcall")
++ (set_attr "cc" "clobber")])
++
++; note the first parameter gets passed in already offset by 2 bytes
++(define_expand "<usdiv:code><ALLSA:mode>3"
++ [(set (reg:ALLSA 24) (match_operand:ALLSA 1 "register_operand" ""))
++ (set (reg:ALLSA 18) (match_operand:ALLSA 2 "register_operand" ""))
++ (parallel [(set (reg:ALLSA 22) (usdiv:ALLSA (reg:ALLSA 24) (reg:ALLSA 18)))
++ (clobber (reg:HI 26))
++ (clobber (reg:HI 30))])
++ (set (match_operand:ALLSA 0 "register_operand" "") (reg:ALLSA 22))]
++ ""
++ "")
++
++(define_insn "*<usdiv:code><ALLSA:mode>3_call"
++ [(set (reg:ALLSA 22) (usdiv:ALLSA (reg:ALLSA 24) (reg:ALLSA 18)))
++ (clobber (reg:HI 26))
++ (clobber (reg:HI 30))]
++ ""
++ "%~call __<usdiv:code><ALLSA:mode>3"
++ [(set_attr "type" "xcall")
++ (set_attr "cc" "clobber")])
++
++
++;; abs must be defined for fixed types for correct operation
++
++;; abs(x) abs(x) abs(x) abs(x) abs(x) abs(x) abs(x) abs(x) abs(x) abs(x) abs(x)
++
++;; abs
++
++(define_insn "abs<ALLQQ:mode>2"
++ [(set (match_operand:ALLQQ 0 "register_operand" "=r")
++ (abs:ALLQQ (match_operand:ALLQQ 1 "register_operand" "0")))]
++ ""
++ "sbrc %0,7
++ neg %0"
++ [(set_attr "length" "2")
++ (set_attr "cc" "clobber")])
+diff -rupN gcc/config/avr/avr.md gcc/config/avr/avr.md
+--- gcc/config/avr/avr.md 2010-04-02 14:54:46.000000000 -0500
++++ gcc/config/avr/avr.md 2010-09-21 14:33:24.000000000 -0500
+@@ -66,6 +66,15 @@
+ (include "predicates.md")
+ (include "constraints.md")
+
++; fixed-point instructions.
++(include "avr-fixed.md")
++(define_mode_iterator ALLQ [(QI "") (QQ "") (UQQ "")])
++(define_mode_iterator ALLH [(HI "") (HQ "") (UHQ "") (HA "") (UHA "")])
++(define_mode_iterator ALLS [(SI "") (SA "") (USA "")])
++(define_mode_iterator ALLQS [(QI "") (QQ "") (UQQ "")
++ (HI "") (HQ "") (UHQ "") (HA "") (UHA "")
++ (SI "") (SA "") (USA "")])
++
+ ;; Condition code settings.
+ (define_attr "cc" "none,set_czn,set_zn,set_n,compare,clobber"
+ (const_string "none"))
+@@ -181,9 +190,9 @@
+ })
+
+
+-(define_insn "*pushqi"
+- [(set (mem:QI (post_dec (reg:HI REG_SP)))
+- (match_operand:QI 0 "reg_or_0_operand" "r,L"))]
++(define_insn "*push<ALLQ:mode>"
++ [(set (mem:ALLQ (post_dec (reg:HI REG_SP)))
++ (match_operand:ALLQ 0 "reg_or_0_operand" "r,L"))]
+ ""
+ "@
+ push %0
+@@ -191,18 +200,18 @@
+ [(set_attr "length" "1,1")])
+
+
+-(define_insn "*pushhi"
+- [(set (mem:HI (post_dec (reg:HI REG_SP)))
+- (match_operand:HI 0 "reg_or_0_operand" "r,L"))]
++(define_insn "*push<ALLH:mode>"
++ [(set (mem:ALLH (post_dec (reg:HI REG_SP)))
++ (match_operand:ALLH 0 "reg_or_0_operand" "r,L"))]
+ ""
+ "@
+ push %B0\;push %A0
+ push __zero_reg__\;push __zero_reg__"
+ [(set_attr "length" "2,2")])
+
+-(define_insn "*pushsi"
+- [(set (mem:SI (post_dec (reg:HI REG_SP)))
+- (match_operand:SI 0 "reg_or_0_operand" "r,L"))]
++(define_insn "*push<ALLS:mode>"
++ [(set (mem:ALLS (post_dec (reg:HI REG_SP)))
++ (match_operand:ALLS 0 "reg_or_0_operand" "r,L"))]
+ ""
+ "@
+ push %D0\;push %C0\;push %B0\;push %A0
+@@ -228,21 +237,21 @@
+ ;; are call-saved registers, and most of LD_REGS are call-used registers,
+ ;; so this may still be a win for registers live across function calls.
+
+-(define_expand "movqi"
+- [(set (match_operand:QI 0 "nonimmediate_operand" "")
+- (match_operand:QI 1 "general_operand" ""))]
++(define_expand "mov<ALLQ:mode>"
++ [(set (match_operand:ALLQ 0 "nonimmediate_operand" "")
++ (match_operand:ALLQ 1 "general_operand" ""))]
+ ""
+ "/* One of the ops has to be in a register. */
+- if (!register_operand(operand0, QImode)
+- && ! (register_operand(operand1, QImode) || const0_rtx == operand1))
+- operands[1] = copy_to_mode_reg(QImode, operand1);
++ if (!register_operand(operand0, <ALLQ:MODE>mode)
++ && ! (register_operand(operand1, <ALLQ:MODE>mode) || const0_rtx == operand1))
++ operands[1] = copy_to_mode_reg(<ALLQ:MODE>mode, operand1);
+ ")
+
+-(define_insn "*movqi"
+- [(set (match_operand:QI 0 "nonimmediate_operand" "=r,d,Qm,r,q,r,*r")
+- (match_operand:QI 1 "general_operand" "rL,i,rL,Qm,r,q,i"))]
+- "(register_operand (operands[0],QImode)
+- || register_operand (operands[1], QImode) || const0_rtx == operands[1])"
++(define_insn "*mov<ALLQ:mode>"
++ [(set (match_operand:ALLQ 0 "nonimmediate_operand" "=r,d,Qm,r,q,r,*r")
++ (match_operand:ALLQ 1 "general_operand" "r,i,rL,Qm,r,q,i"))]
++ "(register_operand (operands[0],<ALLQ:MODE>mode)
++ || register_operand (operands[1], <ALLQ:MODE>mode) || const0_rtx == operands[1])"
+ "* return output_movqi (insn, operands, NULL);"
+ [(set_attr "length" "1,1,5,5,1,1,4")
+ (set_attr "cc" "none,none,clobber,clobber,none,none,clobber")])
+@@ -274,17 +283,17 @@
+ ;;============================================================================
+ ;; move word (16 bit)
+
+-(define_expand "movhi"
+- [(set (match_operand:HI 0 "nonimmediate_operand" "")
+- (match_operand:HI 1 "general_operand" ""))]
++(define_expand "mov<ALLH:mode>"
++ [(set (match_operand:ALLH 0 "nonimmediate_operand" "")
++ (match_operand:ALLH 1 "general_operand" ""))]
+ ""
+ "
+ {
+ /* One of the ops has to be in a register. */
+- if (!register_operand(operand0, HImode)
+- && !(register_operand(operand1, HImode) || const0_rtx == operands[1]))
++ if (!register_operand(operand0, <ALLH:MODE>mode)
++ && !(register_operand(operand1, <ALLH:MODE>mode) || const0_rtx == operands[1]))
+ {
+- operands[1] = copy_to_mode_reg(HImode, operand1);
++ operands[1] = copy_to_mode_reg(<ALLH:MODE>mode, operand1);
+ }
+ }")
+
+@@ -339,20 +348,20 @@
+ [(set_attr "length" "4")
+ (set_attr "cc" "none")])
+
+-(define_insn "*movhi"
+- [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,m,d,*r,q,r")
+- (match_operand:HI 1 "general_operand" "rL,m,rL,i,i,r,q"))]
+- "(register_operand (operands[0],HImode)
+- || register_operand (operands[1],HImode) || const0_rtx == operands[1])"
++(define_insn "*mov<ALLH:mode>"
++ [(set (match_operand:ALLH 0 "nonimmediate_operand" "=r,r,m,d,*r,q,r")
++ (match_operand:ALLH 1 "general_operand" "r,m,rL,i,i,r,q"))]
++ "(register_operand (operands[0],<ALLH:MODE>mode)
++ || register_operand (operands[1],<ALLH:MODE>mode) || const0_rtx == operands[1])"
+ "* return output_movhi (insn, operands, NULL);"
+ [(set_attr "length" "2,6,7,2,6,5,2")
+ (set_attr "cc" "none,clobber,clobber,none,clobber,none,none")])
+
+ (define_peephole2 ; movw
+- [(set (match_operand:QI 0 "even_register_operand" "")
+- (match_operand:QI 1 "even_register_operand" ""))
+- (set (match_operand:QI 2 "odd_register_operand" "")
+- (match_operand:QI 3 "odd_register_operand" ""))]
++ [(set (match_operand:ALLQ 0 "even_register_operand" "")
++ (match_operand:ALLQ 1 "even_register_operand" ""))
++ (set (match_operand:ALLQ 2 "odd_register_operand" "")
++ (match_operand:ALLQ 3 "odd_register_operand" ""))]
+ "(AVR_HAVE_MOVW
+ && REGNO (operands[0]) == REGNO (operands[2]) - 1
+ && REGNO (operands[1]) == REGNO (operands[3]) - 1)"
+@@ -363,10 +372,10 @@
+ })
+
+ (define_peephole2 ; movw_r
+- [(set (match_operand:QI 0 "odd_register_operand" "")
+- (match_operand:QI 1 "odd_register_operand" ""))
+- (set (match_operand:QI 2 "even_register_operand" "")
+- (match_operand:QI 3 "even_register_operand" ""))]
++ [(set (match_operand:ALLQ 0 "odd_register_operand" "")
++ (match_operand:ALLQ 1 "odd_register_operand" ""))
++ (set (match_operand:ALLQ 2 "even_register_operand" "")
++ (match_operand:ALLQ 3 "even_register_operand" ""))]
+ "(AVR_HAVE_MOVW
+ && REGNO (operands[2]) == REGNO (operands[0]) - 1
+ && REGNO (operands[3]) == REGNO (operands[1]) - 1)"
+@@ -379,26 +388,24 @@
+ ;;==========================================================================
+ ;; move double word (32 bit)
+
+-(define_expand "movsi"
+- [(set (match_operand:SI 0 "nonimmediate_operand" "")
+- (match_operand:SI 1 "general_operand" ""))]
++(define_expand "mov<ALLS:mode>"
++ [(set (match_operand:ALLS 0 "nonimmediate_operand" "")
++ (match_operand:ALLS 1 "general_operand" ""))]
+ ""
+ "
+ {
+ /* One of the ops has to be in a register. */
+- if (!register_operand (operand0, SImode)
+- && !(register_operand (operand1, SImode) || const0_rtx == operand1))
++ if (!register_operand (operand0, <ALLS:MODE>mode)
++ && !(register_operand (operand1, <ALLS:MODE>mode) || const0_rtx == operand1))
+ {
+- operands[1] = copy_to_mode_reg (SImode, operand1);
++ operands[1] = copy_to_mode_reg (<ALLS:MODE>mode, operand1);
+ }
+ }")
+
+-
+-
+ (define_peephole2 ; movsi_lreg_const
+ [(match_scratch:QI 2 "d")
+- (set (match_operand:SI 0 "l_register_operand" "")
+- (match_operand:SI 1 "immediate_operand" ""))
++ (set (match_operand:ALLS 0 "l_register_operand" "")
++ (match_operand:ALLS 1 "immediate_operand" ""))
+ (match_dup 2)]
+ "(operands[1] != const0_rtx
+ && operands[1] != constm1_rtx)"
+@@ -408,8 +415,8 @@
+
+ ;; '*' because it is not used in rtl generation.
+ (define_insn "*reload_insi"
+- [(set (match_operand:SI 0 "register_operand" "=r")
+- (match_operand:SI 1 "immediate_operand" "i"))
++ [(set (match_operand:ALLS 0 "register_operand" "=r")
++ (match_operand:ALLS 1 "immediate_operand" "i"))
+ (clobber (match_operand:QI 2 "register_operand" "=&d"))]
+ "reload_completed"
+ "* return output_reload_insisf (insn, operands, NULL);"
+@@ -417,11 +424,11 @@
+ (set_attr "cc" "none")])
+
+
+-(define_insn "*movsi"
+- [(set (match_operand:SI 0 "nonimmediate_operand" "=r,r,r,Qm,!d,r")
+- (match_operand:SI 1 "general_operand" "r,L,Qm,rL,i,i"))]
+- "(register_operand (operands[0],SImode)
+- || register_operand (operands[1],SImode) || const0_rtx == operands[1])"
++(define_insn "*mov<ALLS:mode>"
++ [(set (match_operand:ALLS 0 "nonimmediate_operand" "=r,r,r,Qm,!d,r")
++ (match_operand:ALLS 1 "general_operand" "r,L,Qm,rL,i,i"))]
++ "(register_operand (operands[0],<ALLS:MODE>mode)
++ || register_operand (operands[1],<ALLS:MODE>mode) || const0_rtx == operands[1])"
+ "* return output_movsisf (insn, operands, NULL);"
+ [(set_attr "length" "4,4,8,9,4,10")
+ (set_attr "cc" "none,set_zn,clobber,clobber,none,clobber")])
+@@ -958,23 +965,54 @@
+ [(set_attr "type" "xcall")
+ (set_attr "cc" "clobber")])
+
+-(define_insn "mulqihi3"
++;; Define code iterators
++(define_code_iterator any_extend [sign_extend zero_extend])
++(define_code_attr s [(sign_extend "s") (zero_extend "")])
++(define_code_attr u [(sign_extend "") (zero_extend "u")])
++(define_code_attr su [(sign_extend "s") (zero_extend "u")])
++
++(define_insn "<any_extend:su>mulqi3_highpart"
++ [(set (match_operand:QI 0 "register_operand" "=r")
++ (truncate:QI
++ (lshiftrt:HI
++ (mult:HI (any_extend:HI (match_operand:QI 1 "register_operand" "d"))
++ (any_extend:HI (match_operand:QI 2 "register_operand" "d")))
++ (const_int 8))))]
++ "AVR_HAVE_MUL && !optimize_size"
++ "mul<any_extend:s> %1,%2
++ mov %0,r1
++ clr r1"
++ [(set_attr "length" "3")
++ (set_attr "cc" "clobber")])
++
++(define_insn "<any_extend:u>mulqihi3"
+ [(set (match_operand:HI 0 "register_operand" "=r")
+- (mult:HI (sign_extend:HI (match_operand:QI 1 "register_operand" "d"))
+- (sign_extend:HI (match_operand:QI 2 "register_operand" "d"))))]
++ (mult:HI (any_extend:HI (match_operand:QI 1 "register_operand" "d"))
++ (any_extend:HI (match_operand:QI 2 "register_operand" "d"))))]
+ "AVR_HAVE_MUL"
+- "muls %1,%2
++ "mul<any_extend:s> %1,%2
+ movw %0,r0
+ clr r1"
+ [(set_attr "length" "3")
+ (set_attr "cc" "clobber")])
+
+-(define_insn "umulqihi3"
++(define_insn "*sumulqihi3"
+ [(set (match_operand:HI 0 "register_operand" "=r")
+- (mult:HI (zero_extend:HI (match_operand:QI 1 "register_operand" "r"))
+- (zero_extend:HI (match_operand:QI 2 "register_operand" "r"))))]
++ (mult:HI (sign_extend:HI (match_operand:QI 1 "register_operand" "a"))
++ (zero_extend:HI (match_operand:QI 2 "register_operand" "a"))))]
+ "AVR_HAVE_MUL"
+- "mul %1,%2
++ "mulsu %1,%2
++ movw %0,r0
++ clr r1"
++ [(set_attr "length" "3")
++ (set_attr "cc" "clobber")])
++
++(define_insn "*usmulqihi3"
++ [(set (match_operand:HI 0 "register_operand" "=r")
++ (mult:HI (zero_extend:HI (match_operand:QI 1 "register_operand" "a"))
++ (sign_extend:HI (match_operand:QI 2 "register_operand" "a"))))]
++ "AVR_HAVE_MUL"
++ "mulsu %2,%1
+ movw %0,r0
+ clr r1"
+ [(set_attr "length" "3")
+@@ -1028,6 +1066,50 @@
+ [(set_attr "type" "xcall")
+ (set_attr "cc" "clobber")])
+
++(define_expand "<any_extend:u>mulhisi3"
++ [(set (reg:HI 18) (match_operand:SI 1 "register_operand" ""))
++ (set (reg:HI 20) (match_operand:SI 2 "register_operand" ""))
++ (set (reg:SI 22)
++ (mult:SI (any_extend:SI (reg:HI 18))
++ (any_extend:SI (reg:HI 20))))
++ (set (match_operand:SI 0 "register_operand" "") (reg:SI 22))]
++ "!optimize_size"
++ "")
++
++(define_insn "*<any_extend:u>mulhisi3_call"
++ [(set (reg:SI 22)
++ (mult:SI (any_extend:SI (reg:HI 18))
++ (any_extend:SI (reg:HI 20))))]
++ "!optimize_size"
++ "%~call __<any_extend:u>mulhisi3"
++ [(set_attr "type" "xcall")
++ (set_attr "cc" "clobber")])
++
++(define_expand "<any_extend:su>mulhi3_highpart"
++ [(set (reg:HI 18) (match_operand:HI 1 "register_operand" ""))
++ (set (reg:HI 20) (match_operand:HI 2 "register_operand" ""))
++ (set (reg:HI 24) (truncate:HI (lshiftrt:SI
++ (mult:SI (any_extend:SI (reg:HI 18))
++ (any_extend:SI (reg:HI 20)))
++ (const_int 16))))
++ (set (match_operand:SI 0 "register_operand" "") (reg:HI 24))]
++ "AVR_HAVE_MUL"
++ "")
++
++(define_insn_and_split "*<any_extend:su>mulhi3_highpart_call"
++ [(set (reg:HI 24) (truncate:HI (lshiftrt:SI
++ (mult:SI (any_extend:SI (reg:HI 18))
++ (any_extend:SI (reg:HI 20)))
++ (const_int 16))))]
++ "AVR_HAVE_MUL"
++ ""
++ ""
++ [(set (reg:SI 22)
++ (mult:SI (any_extend:SI (reg:HI 18))
++ (any_extend:SI (reg:HI 20))))
++ (clobber (reg:HI 22))]
++ "")
++
+ ;; Operand 2 (reg:SI 18) not clobbered on the enhanced core.
+ ;; All call-used registers clobbered otherwise - normal library call.
+ (define_expand "mulsi3"
+@@ -1572,9 +1654,9 @@
+ ;;<< << << << << << << << << << << << << << << << << << << << << << << << << <<
+ ;; arithmetic shift left
+
+-(define_expand "ashlqi3"
+- [(set (match_operand:QI 0 "register_operand" "")
+- (ashift:QI (match_operand:QI 1 "register_operand" "")
++(define_expand "ashl<ALLQ:mode>3"
++ [(set (match_operand:ALLQ 0 "register_operand" "")
++ (ashift:ALLQ (match_operand:ALLQ 1 "register_operand" "")
+ (match_operand:QI 2 "general_operand" "")))]
+ ""
+ "")
+@@ -1608,27 +1690,27 @@
+ (set (match_dup 0) (and:QI (match_dup 0) (const_int -64)))]
+ "")
+
+-(define_insn "*ashlqi3"
+- [(set (match_operand:QI 0 "register_operand" "=r,r,r,r,!d,r,r")
+- (ashift:QI (match_operand:QI 1 "register_operand" "0,0,0,0,0,0,0")
++(define_insn "*ashl<ALLQ:mode>3"
++ [(set (match_operand:ALLQ 0 "register_operand" "=r,r,r,r,!d,r,r")
++ (ashift:ALLQ (match_operand:ALLQ 1 "register_operand" "0,0,0,0,0,0,0")
+ (match_operand:QI 2 "general_operand" "r,L,P,K,n,n,Qm")))]
+ ""
+ "* return ashlqi3_out (insn, operands, NULL);"
+ [(set_attr "length" "5,0,1,2,4,6,9")
+ (set_attr "cc" "clobber,none,set_czn,set_czn,set_czn,set_czn,clobber")])
+
+-(define_insn "ashlhi3"
+- [(set (match_operand:HI 0 "register_operand" "=r,r,r,r,r,r,r")
+- (ashift:HI (match_operand:HI 1 "register_operand" "0,0,0,r,0,0,0")
++(define_insn "ashl<ALLH:mode>3"
++ [(set (match_operand:ALLH 0 "register_operand" "=r,r,r,r,r,r,r")
++ (ashift:ALLH (match_operand:ALLH 1 "register_operand" "0,0,0,r,0,0,0")
+ (match_operand:QI 2 "general_operand" "r,L,P,O,K,n,Qm")))]
+ ""
+ "* return ashlhi3_out (insn, operands, NULL);"
+ [(set_attr "length" "6,0,2,2,4,10,10")
+ (set_attr "cc" "clobber,none,set_n,clobber,set_n,clobber,clobber")])
+
+-(define_insn "ashlsi3"
+- [(set (match_operand:SI 0 "register_operand" "=r,r,r,r,r,r,r")
+- (ashift:SI (match_operand:SI 1 "register_operand" "0,0,0,r,0,0,0")
++(define_insn "ashl<ALLS:mode>3"
++ [(set (match_operand:ALLS 0 "register_operand" "=r,r,r,r,r,r,r")
++ (ashift:ALLS (match_operand:ALLS 1 "register_operand" "0,0,0,r,0,0,0")
+ (match_operand:QI 2 "general_operand" "r,L,P,O,K,n,Qm")))]
+ ""
+ "* return ashlsi3_out (insn, operands, NULL);"
+@@ -1674,17 +1756,17 @@
+
+ (define_peephole2
+ [(match_scratch:QI 3 "d")
+- (set (match_operand:HI 0 "register_operand" "")
+- (ashift:HI (match_operand:HI 1 "register_operand" "")
++ (set (match_operand:ALLH 0 "register_operand" "")
++ (ashift:ALLH (match_operand:ALLH 1 "register_operand" "")
+ (match_operand:QI 2 "const_int_operand" "")))]
+ ""
+- [(parallel [(set (match_dup 0) (ashift:HI (match_dup 1) (match_dup 2)))
++ [(parallel [(set (match_dup 0) (ashift:ALLH (match_dup 1) (match_dup 2)))
+ (clobber (match_dup 3))])]
+ "")
+
+-(define_insn "*ashlhi3_const"
+- [(set (match_operand:HI 0 "register_operand" "=r,r,r,r,r")
+- (ashift:HI (match_operand:HI 1 "register_operand" "0,0,r,0,0")
++(define_insn "*ashl<ALLH:mode>3_const"
++ [(set (match_operand:ALLH 0 "register_operand" "=r,r,r,r,r")
++ (ashift:ALLH (match_operand:ALLH 1 "register_operand" "0,0,r,0,0")
+ (match_operand:QI 2 "const_int_operand" "L,P,O,K,n")))
+ (clobber (match_scratch:QI 3 "=X,X,X,X,&d"))]
+ "reload_completed"
+@@ -1694,17 +1776,17 @@
+
+ (define_peephole2
+ [(match_scratch:QI 3 "d")
+- (set (match_operand:SI 0 "register_operand" "")
+- (ashift:SI (match_operand:SI 1 "register_operand" "")
++ (set (match_operand:ALLS 0 "register_operand" "")
++ (ashift:ALLS (match_operand:ALLS 1 "register_operand" "")
+ (match_operand:QI 2 "const_int_operand" "")))]
+ ""
+- [(parallel [(set (match_dup 0) (ashift:SI (match_dup 1) (match_dup 2)))
++ [(parallel [(set (match_dup 0) (ashift:ALLS (match_dup 1) (match_dup 2)))
+ (clobber (match_dup 3))])]
+ "")
+
+-(define_insn "*ashlsi3_const"
+- [(set (match_operand:SI 0 "register_operand" "=r,r,r,r")
+- (ashift:SI (match_operand:SI 1 "register_operand" "0,0,r,0")
++(define_insn "*ashl<ALLS:mode>3_const"
++ [(set (match_operand:ALLS 0 "register_operand" "=r,r,r,r")
++ (ashift:ALLS (match_operand:ALLS 1 "register_operand" "0,0,r,0")
+ (match_operand:QI 2 "const_int_operand" "L,P,O,n")))
+ (clobber (match_scratch:QI 3 "=X,X,X,&d"))]
+ "reload_completed"
+@@ -1715,27 +1797,27 @@
+ ;; >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >>
+ ;; arithmetic shift right
+
+-(define_insn "ashrqi3"
+- [(set (match_operand:QI 0 "register_operand" "=r,r,r,r,r,r")
+- (ashiftrt:QI (match_operand:QI 1 "register_operand" "0,0,0,0,0,0")
++(define_insn "ashr<ALLQ:mode>3"
++ [(set (match_operand:ALLQ 0 "register_operand" "=r,r,r,r,r,r")
++ (ashiftrt:ALLQ (match_operand:ALLQ 1 "register_operand" "0,0,0,0,0,0")
+ (match_operand:QI 2 "general_operand" "r,L,P,K,n,Qm")))]
+ ""
+ "* return ashrqi3_out (insn, operands, NULL);"
+ [(set_attr "length" "5,0,1,2,5,9")
+ (set_attr "cc" "clobber,none,clobber,clobber,clobber,clobber")])
+
+-(define_insn "ashrhi3"
+- [(set (match_operand:HI 0 "register_operand" "=r,r,r,r,r,r,r")
+- (ashiftrt:HI (match_operand:HI 1 "register_operand" "0,0,0,r,0,0,0")
++(define_insn "ashr<ALLH:mode>3"
++ [(set (match_operand:ALLH 0 "register_operand" "=r,r,r,r,r,r,r")
++ (ashiftrt:ALLH (match_operand:ALLH 1 "register_operand" "0,0,0,r,0,0,0")
+ (match_operand:QI 2 "general_operand" "r,L,P,O,K,n,Qm")))]
+ ""
+ "* return ashrhi3_out (insn, operands, NULL);"
+ [(set_attr "length" "6,0,2,4,4,10,10")
+ (set_attr "cc" "clobber,none,clobber,set_n,clobber,clobber,clobber")])
+
+-(define_insn "ashrsi3"
+- [(set (match_operand:SI 0 "register_operand" "=r,r,r,r,r,r,r")
+- (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0,0,r,0,0,0")
++(define_insn "ashr<ALLS:mode>3"
++ [(set (match_operand:ALLS 0 "register_operand" "=r,r,r,r,r,r,r")
++ (ashiftrt:ALLS (match_operand:ALLS 1 "register_operand" "0,0,0,r,0,0,0")
+ (match_operand:QI 2 "general_operand" "r,L,P,O,K,n,Qm")))]
+ ""
+ "* return ashrsi3_out (insn, operands, NULL);"
+@@ -1746,17 +1828,17 @@
+
+ (define_peephole2
+ [(match_scratch:QI 3 "d")
+- (set (match_operand:HI 0 "register_operand" "")
+- (ashiftrt:HI (match_operand:HI 1 "register_operand" "")
++ (set (match_operand:ALLH 0 "register_operand" "")
++ (ashiftrt:ALLH (match_operand:ALLH 1 "register_operand" "")
+ (match_operand:QI 2 "const_int_operand" "")))]
+ ""
+- [(parallel [(set (match_dup 0) (ashiftrt:HI (match_dup 1) (match_dup 2)))
++ [(parallel [(set (match_dup 0) (ashiftrt:ALLH (match_dup 1) (match_dup 2)))
+ (clobber (match_dup 3))])]
+ "")
+
+ (define_insn "*ashrhi3_const"
+- [(set (match_operand:HI 0 "register_operand" "=r,r,r,r,r")
+- (ashiftrt:HI (match_operand:HI 1 "register_operand" "0,0,r,0,0")
++ [(set (match_operand:ALLH 0 "register_operand" "=r,r,r,r,r")
++ (ashiftrt:ALLH (match_operand:ALLH 1 "register_operand" "0,0,r,0,0")
+ (match_operand:QI 2 "const_int_operand" "L,P,O,K,n")))
+ (clobber (match_scratch:QI 3 "=X,X,X,X,&d"))]
+ "reload_completed"
+@@ -1766,17 +1848,17 @@
+
+ (define_peephole2
+ [(match_scratch:QI 3 "d")
+- (set (match_operand:SI 0 "register_operand" "")
+- (ashiftrt:SI (match_operand:SI 1 "register_operand" "")
++ (set (match_operand:ALLS 0 "register_operand" "")
++ (ashiftrt:ALLS (match_operand:ALLS 1 "register_operand" "")
+ (match_operand:QI 2 "const_int_operand" "")))]
+ ""
+- [(parallel [(set (match_dup 0) (ashiftrt:SI (match_dup 1) (match_dup 2)))
++ [(parallel [(set (match_dup 0) (ashiftrt:ALLS (match_dup 1) (match_dup 2)))
+ (clobber (match_dup 3))])]
+ "")
+
+ (define_insn "*ashrsi3_const"
+- [(set (match_operand:SI 0 "register_operand" "=r,r,r,r")
+- (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0,r,0")
++ [(set (match_operand:ALLS 0 "register_operand" "=r,r,r,r")
++ (ashiftrt:ALLS (match_operand:ALLS 1 "register_operand" "0,0,r,0")
+ (match_operand:QI 2 "const_int_operand" "L,P,O,n")))
+ (clobber (match_scratch:QI 3 "=X,X,X,&d"))]
+ "reload_completed"
+@@ -1787,54 +1869,54 @@
+ ;; >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >>
+ ;; logical shift right
+
+-(define_expand "lshrqi3"
+- [(set (match_operand:QI 0 "register_operand" "")
+- (lshiftrt:QI (match_operand:QI 1 "register_operand" "")
+- (match_operand:QI 2 "general_operand" "")))]
++(define_expand "lshr<ALLQ:mode>3"
++ [(set (match_operand:ALLQ 0 "register_operand" "")
++ (lshiftrt:ALLQ (match_operand:ALLQ 1 "register_operand" "")
++ (match_operand:ALLQ 2 "general_operand" "")))]
+ ""
+ "")
+
+ (define_split ; lshrqi3_const4
+- [(set (match_operand:QI 0 "d_register_operand" "")
+- (lshiftrt:QI (match_dup 0)
++ [(set (match_operand:ALLQ 0 "d_register_operand" "")
++ (lshiftrt:ALLQ (match_dup 0)
+ (const_int 4)))]
+ ""
+- [(set (match_dup 0) (rotate:QI (match_dup 0) (const_int 4)))
+- (set (match_dup 0) (and:QI (match_dup 0) (const_int 15)))]
++ [(set (match_dup 0) (rotate:ALLQ (match_dup 0) (const_int 4)))
++ (set (match_dup 0) (and:ALLQ (match_dup 0) (const_int 15)))]
+ "")
+
+ (define_split ; lshrqi3_const5
+- [(set (match_operand:QI 0 "d_register_operand" "")
+- (lshiftrt:QI (match_dup 0)
++ [(set (match_operand:ALLQ 0 "d_register_operand" "")
++ (lshiftrt:ALLQ (match_dup 0)
+ (const_int 5)))]
+ ""
+- [(set (match_dup 0) (rotate:QI (match_dup 0) (const_int 4)))
+- (set (match_dup 0) (lshiftrt:QI (match_dup 0) (const_int 1)))
+- (set (match_dup 0) (and:QI (match_dup 0) (const_int 7)))]
++ [(set (match_dup 0) (rotate:ALLQ (match_dup 0) (const_int 4)))
++ (set (match_dup 0) (lshiftrt:ALLQ (match_dup 0) (const_int 1)))
++ (set (match_dup 0) (and:ALLQ (match_dup 0) (const_int 7)))]
+ "")
+
+ (define_split ; lshrqi3_const6
+- [(set (match_operand:QI 0 "d_register_operand" "")
+- (lshiftrt:QI (match_dup 0)
++ [(set (match_operand:ALLQ 0 "d_register_operand" "")
++ (lshiftrt:ALLQ (match_dup 0)
+ (const_int 6)))]
+ ""
+- [(set (match_dup 0) (rotate:QI (match_dup 0) (const_int 4)))
+- (set (match_dup 0) (lshiftrt:QI (match_dup 0) (const_int 2)))
+- (set (match_dup 0) (and:QI (match_dup 0) (const_int 3)))]
++ [(set (match_dup 0) (rotate:ALLQ (match_dup 0) (const_int 4)))
++ (set (match_dup 0) (lshiftrt:ALLQ (match_dup 0) (const_int 2)))
++ (set (match_dup 0) (and:ALLQ (match_dup 0) (const_int 3)))]
+ "")
+
+ (define_insn "*lshrqi3"
+- [(set (match_operand:QI 0 "register_operand" "=r,r,r,r,!d,r,r")
+- (lshiftrt:QI (match_operand:QI 1 "register_operand" "0,0,0,0,0,0,0")
+- (match_operand:QI 2 "general_operand" "r,L,P,K,n,n,Qm")))]
++ [(set (match_operand:ALLQ 0 "register_operand" "=r,r,r,r,!d,r,r")
++ (lshiftrt:ALLQ (match_operand:ALLQ 1 "register_operand" "0,0,0,0,0,0,0")
++ (match_operand:ALLQ 2 "general_operand" "r,L,P,K,n,n,Qm")))]
+ ""
+ "* return lshrqi3_out (insn, operands, NULL);"
+ [(set_attr "length" "5,0,1,2,4,6,9")
+ (set_attr "cc" "clobber,none,set_czn,set_czn,set_czn,set_czn,clobber")])
+
+-(define_insn "lshrhi3"
+- [(set (match_operand:HI 0 "register_operand" "=r,r,r,r,r,r,r")
+- (lshiftrt:HI (match_operand:HI 1 "register_operand" "0,0,0,r,0,0,0")
++(define_insn "lshr<ALLH:mode>3"
++ [(set (match_operand:ALLH 0 "register_operand" "=r,r,r,r,r,r,r")
++ (lshiftrt:ALLH (match_operand:ALLH 1 "register_operand" "0,0,0,r,0,0,0")
+ (match_operand:QI 2 "general_operand" "r,L,P,O,K,n,Qm")))]
+ ""
+ "* return lshrhi3_out (insn, operands, NULL);"
+@@ -1889,17 +1971,17 @@
+
+ (define_peephole2
+ [(match_scratch:QI 3 "d")
+- (set (match_operand:HI 0 "register_operand" "")
+- (lshiftrt:HI (match_operand:HI 1 "register_operand" "")
++ (set (match_operand:ALLH 0 "register_operand" "")
++ (lshiftrt:ALLH (match_operand:ALLH 1 "register_operand" "")
+ (match_operand:QI 2 "const_int_operand" "")))]
+ ""
+- [(parallel [(set (match_dup 0) (lshiftrt:HI (match_dup 1) (match_dup 2)))
++ [(parallel [(set (match_dup 0) (lshiftrt:ALLH (match_dup 1) (match_dup 2)))
+ (clobber (match_dup 3))])]
+ "")
+
+-(define_insn "*lshrhi3_const"
+- [(set (match_operand:HI 0 "register_operand" "=r,r,r,r,r")
+- (lshiftrt:HI (match_operand:HI 1 "register_operand" "0,0,r,0,0")
++(define_insn "*lshr<ALLH:mode>3_const"
++ [(set (match_operand:ALLH 0 "register_operand" "=r,r,r,r,r")
++ (lshiftrt:ALLH (match_operand:ALLH 1 "register_operand" "0,0,r,0,0")
+ (match_operand:QI 2 "const_int_operand" "L,P,O,K,n")))
+ (clobber (match_scratch:QI 3 "=X,X,X,X,&d"))]
+ "reload_completed"
+@@ -1917,9 +1999,9 @@
+ (clobber (match_dup 3))])]
+ "")
+
+-(define_insn "*lshrsi3_const"
+- [(set (match_operand:SI 0 "register_operand" "=r,r,r,r")
+- (lshiftrt:SI (match_operand:SI 1 "register_operand" "0,0,r,0")
++(define_insn "*lshr<ALLS:mode>3_const"
++ [(set (match_operand:ALLS 0 "register_operand" "=r,r,r,r")
++ (lshiftrt:ALLS (match_operand:ALLS 1 "register_operand" "0,0,r,0")
+ (match_operand:QI 2 "const_int_operand" "L,P,O,n")))
+ (clobber (match_scratch:QI 3 "=X,X,X,&d"))]
+ "reload_completed"
+@@ -2163,27 +2245,27 @@
+ ;; compare
+
+ ; Optimize negated tests into reverse compare if overflow is undefined.
+-(define_insn "*negated_tstqi"
++(define_insn "*negated_tst<ALLQ:mode>"
+ [(set (cc0)
+- (compare (neg:QI (match_operand:QI 0 "register_operand" "r"))
++ (compare (neg:ALLQ (match_operand:ALLQ 0 "register_operand" "r"))
+ (const_int 0)))]
+ "(!flag_wrapv && !flag_trapv && flag_strict_overflow)"
+ "cp __zero_reg__,%0"
+ [(set_attr "cc" "compare")
+ (set_attr "length" "1")])
+
+-(define_insn "*reversed_tstqi"
++(define_insn "*reversed_tst<ALLQ:mode>"
+ [(set (cc0)
+ (compare (const_int 0)
+- (match_operand:QI 0 "register_operand" "r")))]
++ (match_operand:ALLQ 0 "register_operand" "r")))]
+ ""
+ "cp __zero_reg__,%0"
+ [(set_attr "cc" "compare")
+ (set_attr "length" "2")])
+
+-(define_insn "*negated_tsthi"
++(define_insn "*negated_tst<ALLH:mode>"
+ [(set (cc0)
+- (compare (neg:HI (match_operand:HI 0 "register_operand" "r"))
++ (compare (neg:ALLH (match_operand:ALLH 0 "register_operand" "r"))
+ (const_int 0)))]
+ "(!flag_wrapv && !flag_trapv && flag_strict_overflow)"
+ "cp __zero_reg__,%A0
+@@ -2193,10 +2275,10 @@
+
+ ;; Leave here the clobber used by the cmphi pattern for simplicity, even
+ ;; though it is unused, because this pattern is synthesized by avr_reorg.
+-(define_insn "*reversed_tsthi"
++(define_insn "*reversed_tst<ALLH:mode>"
+ [(set (cc0)
+ (compare (const_int 0)
+- (match_operand:HI 0 "register_operand" "r")))
++ (match_operand:ALLH 0 "register_operand" "r")))
+ (clobber (match_scratch:QI 1 "=X"))]
+ ""
+ "cp __zero_reg__,%A0
+@@ -2204,9 +2286,9 @@
+ [(set_attr "cc" "compare")
+ (set_attr "length" "2")])
+
+-(define_insn "*negated_tstsi"
++(define_insn "*negated_tst<ALLS:mode>"
+ [(set (cc0)
+- (compare (neg:SI (match_operand:SI 0 "register_operand" "r"))
++ (compare (neg:ALLS (match_operand:ALLS 0 "register_operand" "r"))
+ (const_int 0)))]
+ "(!flag_wrapv && !flag_trapv && flag_strict_overflow)"
+ "cp __zero_reg__,%A0
+@@ -2216,10 +2298,10 @@
+ [(set_attr "cc" "compare")
+ (set_attr "length" "4")])
+
+-(define_insn "*reversed_tstsi"
++(define_insn "*reversed_tst<ALLS:mode>"
+ [(set (cc0)
+ (compare (const_int 0)
+- (match_operand:SI 0 "register_operand" "r")))
++ (match_operand:ALLS 0 "register_operand" "r")))
+ (clobber (match_scratch:QI 1 "=X"))]
+ ""
+ "cp __zero_reg__,%A0
+@@ -2230,10 +2312,10 @@
+ (set_attr "length" "4")])
+
+
+-(define_insn "*cmpqi"
++(define_insn "*cmp<ALLQ:mode>"
+ [(set (cc0)
+- (compare (match_operand:QI 0 "register_operand" "r,r,d")
+- (match_operand:QI 1 "nonmemory_operand" "L,r,i")))]
++ (compare (match_operand:ALLQ 0 "register_operand" "r,r,d")
++ (match_operand:ALLQ 1 "nonmemory_operand" "L,r,i")))]
+ ""
+ "@
+ tst %0
+@@ -2252,10 +2334,10 @@
+ [(set_attr "cc" "compare")
+ (set_attr "length" "1")])
+
+-(define_insn "*cmphi"
++(define_insn "*cmp<ALLH:mode>"
+ [(set (cc0)
+- (compare (match_operand:HI 0 "register_operand" "!w,r,r,d,d,r,r")
+- (match_operand:HI 1 "nonmemory_operand" "L,L,r,M,i,M,i")))
++ (compare (match_operand:ALLH 0 "register_operand" "!w,r,r,d,d,r,r")
++ (match_operand:ALLH 1 "nonmemory_operand" "L,L,r,M,i,M,i")))
+ (clobber (match_scratch:QI 2 "=X,X,X,X,&d,&d,&d"))]
+ ""
+ "*{
+@@ -2300,10 +2382,10 @@
+ (set_attr "length" "1,2,2,2,3,3,4")])
+
+
+-(define_insn "*cmpsi"
++(define_insn "*cmp<ALLS:mode>"
+ [(set (cc0)
+- (compare (match_operand:SI 0 "register_operand" "r,r,d,d,r,r")
+- (match_operand:SI 1 "nonmemory_operand" "L,r,M,i,M,i")))
++ (compare (match_operand:ALLS 0 "register_operand" "r,r,d,d,r,r")
++ (match_operand:ALLS 1 "nonmemory_operand" "L,r,M,i,M,i")))
+ (clobber (match_scratch:QI 2 "=X,X,X,&d,&d,&d"))]
+ ""
+ "*{
+diff -rupN gcc/config/avr/avr-modes.def gcc/config/avr/avr-modes.def
+--- gcc/config/avr/avr-modes.def 1969-12-31 18:00:00.000000000 -0600
++++ gcc/config/avr/avr-modes.def 2010-09-21 14:31:30.000000000 -0500
+@@ -0,0 +1,34 @@
++/* Definitions of target machine for GCC for AVR.
++ Copyright (C) 2009 Free Software Foundation, Inc.
++
++This file is part of GCC.
++
++GCC is free software; you can redistribute it and/or modify
++it under the terms of the GNU General Public License as published by
++the Free Software Foundation; either version 3, or (at your option)
++any later version.
++
++GCC is distributed in the hope that it will be useful,
++but WITHOUT ANY WARRANTY; without even the implied warranty of
++MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
++GNU General Public License for more details.
++
++You should have received a copy of the GNU General Public License
++along with GCC; see the file COPYING3. If not see
++<http://www.gnu.org/licenses/>. */
++
++/* On 8 bit machines it requires fewer instructions for fixed point
++ routines if the decimal place is on a byte boundary which is not
++ the default for signed accum types. */
++
++ADJUST_IBIT (HA, 7);
++ADJUST_FBIT (HA, 8);
++
++ADJUST_IBIT (SA, 15);
++ADJUST_FBIT (SA, 16);
++
++ADJUST_IBIT (DA, 31);
++ADJUST_FBIT (DA, 32);
++
++ADJUST_IBIT (TA, 63);
++ADJUST_FBIT (TA, 64);
+diff -rupN gcc/config/avr/avr-protos.h gcc/config/avr/avr-protos.h
+--- gcc/config/avr/avr-protos.h 2010-01-08 17:01:45.000000000 -0600
++++ gcc/config/avr/avr-protos.h 2010-09-21 14:31:30.000000000 -0500
+@@ -84,6 +84,8 @@ extern const char *lshrhi3_out (rtx insn
+ extern const char *lshrsi3_out (rtx insn, rtx operands[], int *len);
+ extern bool avr_rotate_bytes (rtx operands[]);
+
++extern const char *fract_out (rtx insn, rtx operands[], int intsigned, int *l);
++
+ extern void expand_prologue (void);
+ extern void expand_epilogue (void);
+ extern int avr_epilogue_uses (int regno);
+diff -rupN gcc/config/avr/libgcc-fixed.S gcc/config/avr/libgcc-fixed.S
+--- gcc/config/avr/libgcc-fixed.S 1969-12-31 18:00:00.000000000 -0600
++++ gcc/config/avr/libgcc-fixed.S 2010-09-21 14:31:30.000000000 -0500
+@@ -0,0 +1,1123 @@
++/* -*- Mode: Asm -*- */
++/* Copyright (C) 2009
++ Free Software Foundation, Inc.
++ Contributed by Sean D'Epagnier
++
++This file is free software; you can redistribute it and/or modify it
++under the terms of the GNU General Public License as published by the
++Free Software Foundation; either version 3, or (at your option) any
++later version.
++
++In addition to the permissions in the GNU General Public License, the
++Free Software Foundation gives you unlimited permission to link the
++compiled version of this file into combinations with other programs,
++and to distribute those combinations without any restriction coming
++from the use of this file. (The General Public License restrictions
++do apply in other respects; for example, they cover modification of
++the file, and distribution when not linked into a combine
++executable.)
++
++This file is distributed in the hope that it will be useful, but
++WITHOUT ANY WARRANTY; without even the implied warranty of
++MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
++General Public License for more details.
++
++You should have received a copy of the GNU General Public License
++along with this program; see the file COPYING. If not, write to
++the Free Software Foundation, 51 Franklin Street, Fifth Floor,
++Boston, MA 02110-1301, USA. */
++
++/* Fixed point library routines for avr. */
++
++#define __zero_reg__ r1
++#define __tmp_reg__ r0
++#define __SREG__ 0x3f
++#define __SP_H__ 0x3e
++#define __SP_L__ 0x3d
++#define __RAMPZ__ 0x3B
++
++/* Conversions to float. */
++#if defined (L_fractqqsf)
++ .global __fractqqsf
++ .func __fractqqsf
++__fractqqsf:
++ clr r25
++ sbrc r24, 7 ; if negative
++ ser r25 ; sign extend
++ mov r23, r24 ; move in place
++ mov r24, r25 ; sign extend lower byte
++ lsl r23
++ clr r22
++ rjmp __fractsasf ; call larger conversion
++.endfunc
++#endif /* defined (L_fractqqsf) */
++
++#if defined (L_fractuqqsf)
++ .global __fractuqqsf
++ .func __fractuqqsf
++__fractuqqsf:
++ clr r22
++ mov r23, r24
++ clr r24
++ clr r25
++ rjmp __fractsasf ; call larger conversion
++.endfunc
++#endif /* defined (L_fractuqqsf) */
++
++#if defined (L_fracthqsf)
++ .global __fracthqsf
++ .func __fracthqsf
++__fracthqsf:
++ mov_l r22, r24 ; put fractional part in place
++ mov_h r23, r25
++ clr r25
++ sbrc r23, 7 ; if negative
++ ser r25 ; sign extend
++ mov r24, r25 ; sign extend lower byte
++ lsl r22
++ rol r23
++ rjmp __fractsasf ; call larger conversion
++.endfunc
++#endif /* defined (L_fracthqsf) */
++
++#if defined (L_fractuhqsf)
++ .global __fractuhqsf
++ .func __fractuhqsf
++__fractuhqsf:
++ mov_l r22, r24 ; put fractional part in place
++ mov_h r23, r25
++ clr r24
++ clr r25
++ rjmp __fractsasf ; call larger conversion
++.endfunc
++#endif /* defined (L_fractuhqsf) */
++
++#if defined (L_fracthasf)
++ .global __fracthasf
++ .func __fracthasf
++__fracthasf:
++ clr r22
++ mov r23, r24 ; move into place
++ mov r24, r25
++ clr r25
++ sbrc r24, 7 ; if negative
++ ser r25 ; sign extend
++ rjmp __fractsasf ; call larger conversion
++#endif /* defined (L_fracthasf) */
++
++#if defined (L_fractuhasf)
++ .global __fractuhasf
++ .func __fractuhasf
++__fractuhasf:
++ clr r22
++ mov r23, r24 ; move into place
++ rjmp __fractsasf ; call larger conversion
++.endfunc
++#endif /* defined (L_fractuhasf) */
++
++#if defined (L_fractsasf)
++ .global __fractsasf
++ .func __fractsasf
++__fractsasf:
++ rcall __floatsisf
++ tst r25
++ breq __fractsasf_exit ; skip if zero
++ subi r25, 0x08 ; adjust exponent
++__fractsasf_exit:
++ ret
++.endfunc
++#endif /* defined (L_fractsasf) */
++
++#if defined (L_fractusasf)
++ .global __fractusasf
++ .func __fractusasf
++__fractusasf:
++ rcall __floatunsisf
++ tst r25
++ breq __fractusasf_exit ; skip if zero
++ subi r25, 0x08 ; adjust exponent
++__fractusasf_exit:
++ ret
++.endfunc
++#endif /* defined (L_fractusasf) */
++
++#if defined (L_fractsfqq) /* Conversions from float. */
++ .global __fractsfqq
++ .func __fractsfqq
++__fractsfqq:
++ subi r25, -11 ; adjust exponent
++ subi r24, 128
++ rjmp __fixsfsi
++.endfunc
++#endif /* defined (L_fractqq) */
++
++#if defined (L_fractsfuqq)
++ .global __fractsfuqq
++ .func __fractsfuqq
++__fractsfuqq:
++ subi r25, -12 ; adjust exponent
++ rjmp __fixsfsi
++.endfunc
++#endif /* defined (L_fractuqq) */
++
++#if defined (L_fractsfhq)
++ .global __fractsfhq
++ .func __fractsfhq
++__fractsfhq:
++ subi r25, -15 ; adjust exponent
++ subi r24, 128
++ rjmp __fixsfsi
++.endfunc
++#endif /* defined (L_fractsfhq) */
++
++#if defined (L_fractsfuhq)
++ .global __fractsfuhq
++ .func __fractsfuhq
++__fractsfuhq:
++ subi r25, -16 ; adjust exponent
++ rjmp __fixsfsi
++.endfunc
++#endif /* defined (L_fractsfuhq) */
++
++#if defined (L_fractsfha)
++ .global __fractsfha
++ .func __fractsfha
++__fractsfha:
++.endfunc
++ .global __fractsfuha
++ .func __fractsfuha
++__fractsfuha:
++ subi r25, -12 ; adjust exponent
++ rjmp __fixsfsi
++.endfunc
++#endif /* defined (L_fractsfha) */
++
++#if defined (L_fractsfsa)
++ .global __fractsfsa
++ .func __fractsfsa
++__fractsfsa:
++.endfunc
++ .global __fractsfusa
++ .func __fractsfusa
++__fractsfusa:
++ subi r25, -8 ; adjust exponent
++ rjmp __fixsfsi
++.endfunc
++#endif /* defined (L_fractsfsa) */
++
++/* For multiplication the functions here are called directly from
++ avr-fixed.md patterns, instead of using the standard libcall mechanisms.
++ This can make better code because GCC knows exactly which
++ of the call-used registers (not all of them) are clobbered. */
++
++/* mulqq and muluqq open coded on the enhanced core */
++#if !defined (__AVR_HAVE_MUL__)
++/*******************************************************
++ Fractional Multiplication 8 x 8
++*******************************************************/
++#define r_arg2 r22 /* multiplicand */
++#define r_arg1 r24 /* multiplier */
++#define r_res __tmp_reg__ /* result */
++
++#if defined (L_mulqq3)
++ .global __mulqq3
++ .func __mulqq3
++__mulqq3:
++ mov r_res, r_arg1
++ eor r_res, r_arg2
++ bst r_res, 7
++ lsl r_arg1
++ lsl r_arg2
++ brcc __mulqq3_skipneg
++ neg r_arg2
++__mulqq3_skipneg:
++ rcall __muluqq3
++ lsr r_arg1
++ brtc __mulqq3_exit
++ neg r_arg1
++__mulqq3_exit:
++ ret
++
++.endfunc
++#endif /* defined (L_mulqq3) */
++
++#if defined (L_muluqq3)
++ .global __muluqq3
++ .func __muluqq3
++__muluqq3:
++ clr r_res ; clear result
++__muluqq3_loop:
++ lsr r_arg2 ; shift multiplicand
++ sbrc r_arg1,7
++ add r_res,r_arg2
++ breq __muluqq3_exit ; while multiplicand != 0
++ lsl r_arg1
++ brne __muluqq3_loop ; exit if multiplier = 0
++__muluqq3_exit:
++ mov r_arg1,r_res ; result to return register
++ ret
++#undef r_arg2
++#undef r_arg1
++#undef r_res
++
++.endfunc
++#endif /* defined (L_muluqq3) */
++#endif /* !defined (__AVR_HAVE_MUL__) */
++
++/*******************************************************
++ Fractional Multiplication 16 x 16
++*******************************************************/
++
++#if defined (__AVR_HAVE_MUL__)
++#define r_arg1L r22 /* multiplier Low */
++#define r_arg1H r23 /* multiplier High */
++#define r_arg2L r20 /* multiplicand Low */
++#define r_arg2H r21 /* multiplicand High */
++#define r_resL r18 /* result Low */
++#define r_resH r19 /* result High */
++
++#if defined (L_mulhq3)
++ .global __mulhq3
++ .func __mulhq3
++__mulhq3:
++ fmuls r_arg1H, r_arg2H
++ movw r_resL, r0
++ fmulsu r_arg2H, r_arg1L
++ clr r_arg1L
++ sbc r_resH, r_arg1L
++ add r_resL, r1
++ adc r_resH, r_arg1L
++ fmulsu r_arg1H, r_arg2L
++ sbc r_resH, r_arg1L
++ add r_resL, r1
++ adc r_resH, r_arg1L
++ clr __zero_reg__
++ ret
++.endfunc
++#endif /* defined (L_mulhq3) */
++
++#if defined (L_muluhq3)
++ .global __muluhq3
++ .func __muluhq3
++__muluhq3:
++ mul r_arg1H, r_arg2H
++ movw r_resL, r0
++ mul r_arg1H, r_arg2L
++ add r_resL, r1
++ clr __zero_reg__
++ adc r_resH, __zero_reg__
++ mul r_arg1L, r_arg2H
++ add r_resL, r1
++ clr __zero_reg__
++ adc r_resH, __zero_reg__
++ ret
++.endfunc
++#endif /* defined (L_muluhq3) */
++
++#else
++#define r_arg1L r24 /* multiplier Low */
++#define r_arg1H r25 /* multiplier High */
++#define r_arg2L r22 /* multiplicand Low */
++#define r_arg2H r23 /* multiplicand High */
++#define r_resL __tmp_reg__ /* result Low */
++#define r_resH __zero_reg__ /* result High */
++
++#if defined (L_mulhq3)
++ .global __mulhq3
++ .func __mulhq3
++__mulhq3:
++ mov r_resL, r_arg1H
++ eor r_resL, r_arg2H
++ bst r_resL, 7
++ lsl r_arg1L
++ rol r_arg1H
++ lsl r_arg2L
++ rol r_arg2H
++ brcc mulhq3_skipneg
++ com r_arg2H
++ neg r_arg2L
++ sbci r_arg2H, -1
++mulhq3_skipneg:
++ rcall __muluhq3
++ lsr r_arg1H
++ ror r_arg1L
++ brtc mulhq3_exit
++ com r_arg1H
++ neg r_arg1L
++ sbci r_arg1H, -1
++mulhq3_exit:
++ ret
++.endfunc
++#endif /* defined (L_mulhq3) */
++
++#if defined (L_muluhq3)
++ .global __muluhq3
++ .func __muluhq3
++__muluhq3:
++ clr r_resL ; clear result
++__muluhq3_loop:
++ lsr r_arg2H ; shift multiplicand
++ ror r_arg2L
++ sbrs r_arg1H,7
++ rjmp __muluhq3_skip
++ add r_resL,r_arg2L ; result + multiplicand
++ adc r_resH,r_arg2H
++__muluhq3_skip:
++ lsl r_arg1L ; shift multiplier
++ rol r_arg1H
++ brne __muluhq3_loop
++ cpi r_arg1L, 0
++ brne __muluhq3_loop ; exit multiplier = 0
++ mov_l r_arg1L,r_resL
++ mov_h r_arg1H,r_resH ; result to return register
++ clr __zero_reg__ ; zero the zero reg
++ ret
++.endfunc
++#endif /* defined (L_muluhq3) */
++
++#endif /* defined (__AVR_HAVE_MUL__) */
++
++#undef r_arg1L
++#undef r_arg1H
++#undef r_arg2L
++#undef r_arg2H
++#undef r_resL
++#undef r_resH
++
++/*******************************************************
++ Fixed Multiplication 8.8 x 8.8
++*******************************************************/
++
++#if defined (__AVR_HAVE_MUL__)
++#define r_arg1L r22 /* multiplier Low */
++#define r_arg1H r23 /* multiplier High */
++#define r_arg2L r20 /* multiplicand Low */
++#define r_arg2H r21 /* multiplicand High */
++#define r_resL r18 /* result Low */
++#define r_resH r19 /* result High */
++
++#if defined (L_mulha3)
++ .global __mulha3
++ .func __mulha3
++__mulha3:
++ mul r_arg1L, r_arg2L
++ mov r_resL, r1
++ muls r_arg1H, r_arg2H
++ mov r_resH, r0
++ mulsu r_arg1H, r_arg2L
++ add r_resL, r0
++ adc r_resH, r1
++ mulsu r_arg2H, r_arg1L
++ add r_resL, r0
++ adc r_resH, r1
++ clr __zero_reg__
++ ret
++.endfunc
++#endif /* defined (L_mulha3) */
++
++#if defined (L_muluha3)
++ .global __muluha3
++ .func __muluha3
++__muluha3:
++ mul r_arg1L, r_arg2L
++ mov r_resL, r1
++ mul r_arg1H, r_arg2H
++ mov r_resH, r0
++ mul r_arg1H, r_arg2L
++ add r_resL, r0
++ adc r_resH, r1
++ mul r_arg1L, r_arg2H
++ add r_resL, r0
++ adc r_resH, r1
++ clr __zero_reg__
++ ret
++.endfunc
++#endif /* defined (L_muluha3) */
++
++#else
++
++#define r_arg1L r24 /* multiplier Low */
++#define r_arg1H r25 /* multiplier High */
++#define r_arg2L r22 /* multiplicand Low */
++#define r_arg2H r23 /* multiplicand High */
++#define r_resL r18 /* result Low */
++#define r_resH r19 /* result High */
++#define r_scratchL r0 /* scratch Low */
++#define r_scratchH r1
++
++#if defined (L_mulha3)
++ .global __mulha3
++ .func __mulha3
++__mulha3:
++ mov r_resL, r_arg1H
++ eor r_resL, r_arg2H
++ bst r_resL, 7
++ sbrs r_arg1H, 7
++ rjmp __mulha3_arg1pos
++ com r_arg1H
++ neg r_arg1L
++ sbci r_arg1H,-1
++__mulha3_arg1pos:
++ sbrs r_arg2H, 7
++ rjmp __mulha3_arg2pos
++ com r_arg2H
++ neg r_arg2L
++ sbci r_arg2H,-1
++__mulha3_arg2pos:
++ rcall __muluha3
++ brtc __mulha3_exit
++ com r_resH
++ neg r_resL
++ sbci r_resH,-1
++__mulha3_exit:
++ ret
++.endfunc
++#endif /* defined (L_mulha3) */
++
++#if defined (L_muluha3)
++ .global __muluha3
++ .func __muluha3
++__muluha3:
++ clr r_resL ; clear result
++ clr r_resH
++ mov_l r0, r_arg1L ; save multiplicand
++ mov_h r1, r_arg1H
++__muluha3_loop1:
++ sbrs r_arg2H,0
++ rjmp __muluha3_skip1
++ add r_resL,r_arg1L ; result + multiplicand
++ adc r_resH,r_arg1H
++__muluha3_skip1:
++ lsl r_arg1L ; shift multiplicand
++ rol r_arg1H
++ sbiw r_arg1L,0
++ breq __muluha3_loop1_done ; exit multiplicand = 0
++ lsr r_arg2H
++ brne __muluha3_loop1 ; exit multiplier = 0
++__muluha3_loop1_done:
++ mov_l r_arg1L, r_scratchL ; restore multiplicand
++ mov_h r_arg1H, r_scratchH
++__muluha3_loop2:
++ lsr r_arg1H ; shift multiplicand
++ ror r_arg1L
++ sbiw r_arg1L,0
++ breq __muluha3_exit ; exit if multiplicand = 0
++ sbrs r_arg2L,7
++ rjmp __muluha3_skip2
++ add r_resL,r_arg1L ; result + multiplicand
++ adc r_resH,r_arg1H
++__muluha3_skip2:
++ lsl r_arg2L
++ brne __muluha3_loop2 ; exit if multiplier = 0
++__muluha3_exit:
++ clr __zero_reg__ ; got clobbered
++ ret
++.endfunc
++#endif /* defined (L_muluha3) */
++
++#endif /* defined (__AVR_HAVE_MUL__) */
++
++#undef r_arg1L
++#undef r_arg1H
++#undef r_arg2L
++#undef r_arg2H
++#undef r_resL
++#undef r_resH
++
++/*******************************************************
++ Fixed Multiplication 16.16 x 16.16
++*******************************************************/
++
++#if defined (__AVR_HAVE_MUL__)
++/* uses nonstandard registers because mulus only works from 16-23 */
++#define r_clr r15
++
++#define r_arg1L r16 /* multiplier Low */
++#define r_arg1H r17
++#define r_arg1HL r18
++#define r_arg1HH r19 /* multiplier High */
++
++#define r_arg2L r20 /* multiplicand Low */
++#define r_arg2H r21
++#define r_arg2HL r22
++#define r_arg2HH r23 /* multiplicand High */
++
++#define r_resL r24 /* result Low */
++#define r_resH r25
++#define r_resHL r26
++#define r_resHH r27 /* result High */
++
++#if defined (L_mulsa3)
++ .global __mulsa3
++ .func __mulsa3
++__mulsa3:
++ clr r_clr
++ clr r_resH
++ clr r_resHL
++ clr r_resHH
++ mul r_arg1H, r_arg2L
++ mov r_resL, r1
++ mul r_arg1L, r_arg2H
++ add r_resL, r1
++ adc r_resH, r_clr
++ mul r_arg1L, r_arg2HL
++ add r_resL, r0
++ adc r_resH, r1
++ adc r_resHL, r_clr
++ mul r_arg1H, r_arg2H
++ add r_resL, r0
++ adc r_resH, r1
++ adc r_resHL, r_clr
++ mul r_arg1HL, r_arg2L
++ add r_resL, r0
++ adc r_resH, r1
++ adc r_resHL, r_clr
++ mulsu r_arg2HH, r_arg1L
++ sbc r_resHH, r_clr
++ add r_resH, r0
++ adc r_resHL, r1
++ adc r_resHH, r_clr
++ mul r_arg1H, r_arg2HL
++ add r_resH, r0
++ adc r_resHL, r1
++ adc r_resHH, r_clr
++ mul r_arg1HL, r_arg2H
++ add r_resH, r0
++ adc r_resHL, r1
++ adc r_resHH, r_clr
++ mulsu r_arg1HH, r_arg2L
++ sbc r_resHH, r_clr
++ add r_resH, r0
++ adc r_resHL, r1
++ adc r_resHH, r_clr
++ mulsu r_arg2HH, r_arg1H
++ add r_resHL, r0
++ adc r_resHH, r1
++ mul r_arg1HL, r_arg2HL
++ add r_resHL, r0
++ adc r_resHH, r1
++ mulsu r_arg1HH, r_arg2H
++ add r_resHL, r0
++ adc r_resHH, r1
++ mulsu r_arg2HH, r_arg1HL
++ add r_resHH, r0
++ mulsu r_arg1HH, r_arg2HL
++ add r_resHH, r0
++ clr __zero_reg__
++ ret
++.endfunc
++#endif
++
++#if defined (L_mulusa3)
++ .global __mulusa3
++ .func __mulusa3
++__mulusa3:
++ clr r_clr
++ clr r_resH
++ clr r_resHL
++ clr r_resHH
++ mul r_arg1H, r_arg2L
++ mov r_resL, r1
++ mul r_arg1L, r_arg2H
++ add r_resL, r1
++ adc r_resH, r_clr
++ mul r_arg1L, r_arg2HL
++ add r_resL, r0
++ adc r_resH, r1
++ adc r_resHL, r_clr
++ mul r_arg1H, r_arg2H
++ add r_resL, r0
++ adc r_resH, r1
++ adc r_resHL, r_clr
++ mul r_arg1HL, r_arg2L
++ add r_resL, r0
++ adc r_resH, r1
++ adc r_resHL, r_clr
++ mul r_arg1L, r_arg2HH
++ add r_resH, r0
++ adc r_resHL, r1
++ adc r_resHH, r_clr
++ mul r_arg1H, r_arg2HL
++ add r_resH, r0
++ adc r_resHL, r1
++ adc r_resHH, r_clr
++ mul r_arg1HL, r_arg2H
++ add r_resH, r0
++ adc r_resHL, r1
++ adc r_resHH, r_clr
++ mul r_arg1HH, r_arg2L
++ add r_resH, r0
++ adc r_resHL, r1
++ adc r_resHH, r_clr
++ mul r_arg1H, r_arg2HH
++ add r_resHL, r0
++ adc r_resHH, r1
++ mul r_arg1HL, r_arg2HL
++ add r_resHL, r0
++ adc r_resHH, r1
++ mul r_arg1HH, r_arg2H
++ add r_resHL, r0
++ adc r_resHH, r1
++ mul r_arg1HL, r_arg2HH
++ add r_resHH, r0
++ mul r_arg1HH, r_arg2HL
++ add r_resHH, r0
++ clr __zero_reg__
++ ret
++.endfunc
++#endif
++
++#else
++
++#define r_arg1L r18 /* multiplier Low */
++#define r_arg1H r19
++#define r_arg1HL r20
++#define r_arg1HH r21 /* multiplier High */
++
++/* these registers needed for sbiw */
++#define r_arg2L r24 /* multiplicand Low */
++#define r_arg2H r25
++#define r_arg2HL r26
++#define r_arg2HH r27 /* multiplicand High */
++
++#define r_resL r14 /* result Low */
++#define r_resH r15
++#define r_resHL r16
++#define r_resHH r17 /* result High */
++
++#define r_scratchL r0 /* scratch Low */
++#define r_scratchH r1
++#define r_scratchHL r22
++#define r_scratchHH r23 /* scratch High */
++
++#if defined (L_mulsa3)
++ .global __mulsa3
++ .func __mulsa3
++__mulsa3:
++ mov r_resL, r_arg1HH
++ eor r_resL, r_arg2HH
++ bst r_resL, 7
++ sbrs r_arg1HH, 7
++ rjmp __mulsa3_arg1pos
++ com r_arg1HH
++ com r_arg1HL
++ com r_arg1H
++ neg r_arg1L
++ sbci r_arg1H,-1
++ sbci r_arg1HL,-1
++ sbci r_arg1HH,-1
++__mulsa3_arg1pos:
++ sbrs r_arg2HH, 7
++ rjmp __mulsa3_arg2pos
++ com r_arg2HH
++ com r_arg2HL
++ com r_arg2H
++ neg r_arg2L
++ sbci r_arg2H,-1
++ sbci r_arg2HL,-1
++ sbci r_arg2HH,-1
++__mulsa3_arg2pos:
++ rcall __mulusa3
++ brtc __mulsa3_exit
++ com r_resHH
++ com r_resHL
++ com r_resH
++ com r_resL
++ adc r_resL,__zero_reg__
++ adc r_resH,__zero_reg__
++ adc r_resHL,__zero_reg__
++ adc r_resHH,__zero_reg__
++__mulsa3_exit:
++ ret
++.endfunc
++#endif /* defined (L_mulsa3) */
++
++#if defined (L_mulusa3)
++ .global __mulusa3
++ .func __mulusa3
++__mulusa3:
++ clr r_resL ; clear result
++ clr r_resH
++ mov_l r_resHL, r_resL
++ mov_h r_resHH, r_resH
++ mov_l r_scratchL, r_arg1L ; save multiplicand
++ mov_h r_scratchH, r_arg1H
++ mov_l r_scratchHL, r_arg1HL
++ mov_h r_scratchHH, r_arg1HH
++__mulusa3_loop1:
++ sbrs r_arg2HL,0
++ rjmp __mulusa3_skip1
++ add r_resL,r_arg1L ; result + multiplicand
++ adc r_resH,r_arg1H
++ adc r_resHL,r_arg1HL
++ adc r_resHH,r_arg1HH
++__mulusa3_skip1:
++ lsl r_arg1L ; shift multiplicand
++ rol r_arg1H
++ rol r_arg1HL
++ rol r_arg1HH
++ lsr r_arg2HH
++ ror r_arg2HL
++ sbiw r_arg2HL,0
++ brne __mulusa3_loop1 ; exit multiplier = 0
++__mulusa3_loop1_done:
++ mov_l r_arg1L, r_scratchL ; restore multiplicand
++ mov_h r_arg1H, r_scratchH
++ mov_l r_arg1HL, r_scratchHL
++ mov_h r_arg1HH, r_scratchHH
++__mulusa3_loop2:
++ lsr r_arg1HH ; shift multiplicand
++ ror r_arg1HL
++ ror r_arg1H
++ ror r_arg1L
++ sbrs r_arg2H,7
++ rjmp __mulusa3_skip2
++ add r_resL,r_arg1L ; result + multiplicand
++ adc r_resH,r_arg1H
++ adc r_resHL,r_arg1HL
++ adc r_resHH,r_arg1HH
++__mulusa3_skip2:
++ lsl r_arg2L
++ rol r_arg2H
++ sbiw r_arg2L,0
++ brne __mulusa3_loop2 ; exit if multiplier = 0
++__mulusa3_exit:
++ clr __zero_reg__ ; got clobbered
++ ret
++.endfunc
++#endif /* defined (L_mulusa3) */
++
++#undef r_scratchL
++#undef r_scratchH
++#undef r_scratchHL
++#undef r_scratchHH
++
++#endif
++
++#undef r_arg1L
++#undef r_arg1H
++#undef r_arg1HL
++#undef r_arg1HH
++
++#undef r_arg2L
++#undef r_arg2H
++#undef r_arg2HL
++#undef r_arg2HH
++
++#undef r_resL
++#undef r_resH
++#undef r_resHL
++#undef r_resHH
++
++/*******************************************************
++ Fractional Division 8 / 8
++*******************************************************/
++#define r_divd r25 /* dividend */
++#define r_quo r24 /* quotient */
++#define r_div r22 /* divisor */
++#define r_cnt r23 /* loop count */
++
++#if defined (L_divqq3)
++ .global __divqq3
++ .func __divqq3
++__divqq3:
++ mov r0, r_divd
++ eor r0, r_div
++ sbrc r_div, 7
++ neg r_div
++ sbrc r_divd, 7
++ neg r_divd
++ cp r_divd, r_div
++ breq __divqq3_minus1 ; if equal return -1
++ rcall __udivuqq3
++ lsr r_quo
++ sbrc r0, 7 ; negate result if needed
++ neg r_quo
++ ret
++__divqq3_minus1:
++ ldi r_quo, 0x80
++ ret
++.endfunc
++#endif /* defined (L_divqq3) */
++
++#if defined (L_udivuqq3)
++ .global __udivuqq3
++ .func __udivuqq3
++__udivuqq3:
++ clr r_quo ; clear quotient
++ ldi r_cnt,8 ; init loop counter
++__udivuqq3_loop:
++ lsl r_divd ; shift dividend
++ brcs __udivuqq3_ep ; dividend overflow
++ cp r_divd,r_div ; compare dividend & divisor
++ brcc __udivuqq3_ep ; dividend >= divisor
++ rol r_quo ; shift quotient (with CARRY)
++ rjmp __udivuqq3_cont
++__udivuqq3_ep:
++ sub r_divd,r_div ; restore dividend
++ lsl r_quo ; shift quotient (without CARRY)
++__udivuqq3_cont:
++ dec r_cnt ; decrement loop counter
++ brne __udivuqq3_loop
++ com r_quo ; complement result
++ ; because C flag was complemented in loop
++ ret
++.endfunc
++#endif /* defined (L_udivuqq3) */
++
++#undef r_divd
++#undef r_quo
++#undef r_div
++#undef r_cnt
++
++
++/*******************************************************
++ Fractional Division 16 / 16
++*******************************************************/
++#define r_divdL r26 /* dividend Low */
++#define r_divdH r27 /* dividend Hig */
++#define r_quoL r24 /* quotient Low */
++#define r_quoH r25 /* quotient High */
++#define r_divL r22 /* divisor */
++#define r_divH r23 /* divisor */
++#define r_cnt 21
++
++#if defined (L_divhq3)
++ .global __divhq3
++ .func __divhq3
++__divhq3:
++ mov r0, r_divdH
++ eor r0, r_divH
++ sbrs r_divH, 7
++ rjmp __divhq3_divpos
++ com r_divH
++ neg r_divL
++ sbci r_divH,-1
++__divhq3_divpos:
++ sbrs r_divdH, 7
++ rjmp __divhq3_divdpos
++ com r_divdH
++ neg r_divdL
++ sbci r_divdH,-1
++__divhq3_divdpos:
++ cp r_divdL, r_divL
++ cpc r_divdH, r_divH
++ breq __divhq3_minus1 ; if equal return -1
++ rcall __udivuhq3
++ lsr r_quoH
++ ror r_quoL
++ sbrs r0, 7 ; negate result if needed
++ ret
++ com r_quoH
++ neg r_quoL
++ sbci r_quoH,-1
++ ret
++__divhq3_minus1:
++ ldi r_quoH, 0x80
++ clr r_quoL
++ ret
++.endfunc
++#endif /* defined (L_divhq3) */
++
++#if defined (L_udivuhq3)
++ .global __udivuhq3
++ .func __udivuhq3
++__udivuhq3:
++ sub r_quoH,r_quoH ; clear quotient and carry
++ .global __udivuha3_entry
++__udivuha3_entry:
++ clr r_quoL ; clear quotient
++ ldi r_cnt,16 ; init loop counter
++__udivuhq3_loop:
++ rol r_divdL ; shift dividend (with CARRY)
++ rol r_divdH
++ brcs __udivuhq3_ep ; dividend overflow
++ cp r_divdL,r_divL ; compare dividend & divisor
++ cpc r_divdH,r_divH
++ brcc __udivuhq3_ep ; dividend >= divisor
++ rol r_quoL ; shift quotient (with CARRY)
++ rjmp __udivuhq3_cont
++__udivuhq3_ep:
++ sub r_divdL,r_divL ; restore dividend
++ sbc r_divdH,r_divH
++ lsl r_quoL ; shift quotient (without CARRY)
++__udivuhq3_cont:
++ rol r_quoH ; shift quotient
++ dec r_cnt ; decrement loop counter
++ brne __udivuhq3_loop
++ com r_quoL ; complement result
++ com r_quoH ; because C flag was complemented in loop
++ ret
++.endfunc
++#endif /* defined (L_udivuhq3) */
++
++/*******************************************************
++ Fixed Division 8.8 / 8.8
++*******************************************************/
++#if defined (L_divha3)
++ .global __divha3
++ .func __divha3
++__divha3:
++ mov r0, r_divdH
++ eor r0, r_divH
++ sbrs r_divH, 7
++ rjmp __divha3_divpos
++ com r_divH
++ neg r_divL
++ sbci r_divH,-1
++__divha3_divpos:
++ sbrs r_divdH, 7
++ rjmp __divha3_divdpos
++ com r_divdH
++ neg r_divdL
++ sbci r_divdH,-1
++__divha3_divdpos:
++ rcall __udivuha3
++ sbrs r0, 7 ; negate result if needed
++ ret
++ com r_quoH
++ neg r_quoL
++ sbci r_quoH,-1
++ ret
++.endfunc
++#endif /* defined (L_divha3) */
++
++#if defined (L_udivuha3)
++ .global __udivuha3
++ .func __udivuha3
++__udivuha3:
++ mov r_quoH, r_divdL
++ mov r_divdL, r_divdH
++ clr r_divdH
++ lsl r_quoH ; shift quotient into carry
++ rjmp __udivuha3_entry ; same as fractional after rearrange
++.endfunc
++#endif /* defined (L_udivuha3) */
++
++#undef r_divdL
++#undef r_divdH
++#undef r_quoL
++#undef r_quoH
++#undef r_divL
++#undef r_divH
++#undef r_cnt
++
++/*******************************************************
++ Fixed Division 16.16 / 16.16
++*******************************************************/
++#define r_arg1L r24 /* arg1 gets passed already in place */
++#define r_arg1H r25
++#define r_arg1HL r26
++#define r_arg1HH r27
++#define r_divdL r26 /* dividend Low */
++#define r_divdH r27
++#define r_divdHL r30
++#define r_divdHH r31 /* dividend High */
++#define r_quoL r22 /* quotient Low */
++#define r_quoH r23
++#define r_quoHL r24
++#define r_quoHH r25 /* quotient High */
++#define r_divL r18 /* divisor Low */
++#define r_divH r19
++#define r_divHL r20
++#define r_divHH r21 /* divisor High */
++#define r_cnt __zero_reg__ /* loop count (0 after the loop!) */
++
++#if defined (L_divsa3)
++ .global __divsa3
++ .func __divsa3
++__divsa3:
++ mov r0, r27
++ eor r0, r_divHH
++ sbrs r_divHH, 7
++ rjmp __divsa3_divpos
++ com r_divHH
++ com r_divHL
++ com r_divH
++ neg r_divL
++ sbci r_divH,-1
++ sbci r_divHL,-1
++ sbci r_divHH,-1
++__divsa3_divpos:
++ sbrs r_arg1HH, 7
++ rjmp __divsa3_arg1pos
++ com r_arg1HH
++ com r_arg1HL
++ com r_arg1H
++ neg r_arg1L
++ sbci r_arg1H,-1
++ sbci r_arg1HL,-1
++ sbci r_arg1HH,-1
++__divsa3_arg1pos:
++ rcall __udivusa3
++ sbrs r0, 7 ; negate result if needed
++ ret
++ com r_quoHH
++ com r_quoHL
++ com r_quoH
++ neg r_quoL
++ sbci r_quoH,-1
++ sbci r_quoHL,-1
++ sbci r_quoHH,-1
++ ret
++.endfunc
++#endif /* defined (L_divsa3) */
++
++#if defined (L_udivusa3)
++ .global __udivusa3
++ .func __udivusa3
++__udivusa3:
++ ldi r_divdHL, 32 ; init loop counter
++ mov r_cnt, r_divdHL
++ clr r_divdHL
++ clr r_divdHH
++ mov_l r_quoL, r_divdHL
++ mov_h r_quoH, r_divdHH
++ lsl r_quoHL ; shift quotient into carry
++ rol r_quoHH
++__udivusa3_loop:
++ rol r_divdL ; shift dividend (with CARRY)
++ rol r_divdH
++ rol r_divdHL
++ rol r_divdHH
++ brcs __udivusa3_ep ; dividend overflow
++ cp r_divdL,r_divL ; compare dividend & divisor
++ cpc r_divdH,r_divH
++ cpc r_divdHL,r_divHL
++ cpc r_divdHH,r_divHH
++ brcc __udivusa3_ep ; dividend >= divisor
++ rol r_quoL ; shift quotient (with CARRY)
++ rjmp __udivusa3_cont
++__udivusa3_ep:
++ sub r_divdL,r_divL ; restore dividend
++ sbc r_divdH,r_divH
++ sbc r_divdHL,r_divHL
++ sbc r_divdHH,r_divHH
++ lsl r_quoL ; shift quotient (without CARRY)
++__udivusa3_cont:
++ rol r_quoH ; shift quotient
++ rol r_quoHL
++ rol r_quoHH
++ dec r_cnt ; decrement loop counter
++ brne __udivusa3_loop
++ com r_quoL ; complement result
++ com r_quoH ; because C flag was complemented in loop
++ com r_quoHL
++ com r_quoHH
++ ret
++.endfunc
++#endif /* defined (L_udivusa3) */
++
++#undef r_divdL
++#undef r_divdH
++#undef r_divdHL
++#undef r_divdHH
++#undef r_quoL
++#undef r_quoH
++#undef r_quoHL
++#undef r_quoHH
++#undef r_divL
++#undef r_divH
++#undef r_divHL
++#undef r_divHH
++#undef r_cnt
+diff -rupN gcc/config/avr/libgcc.S gcc/config/avr/libgcc.S
+--- gcc/config/avr/libgcc.S 2009-05-23 02:16:07.000000000 -0500
++++ gcc/config/avr/libgcc.S 2010-09-21 14:31:30.000000000 -0500
+@@ -162,6 +162,23 @@ __mulhi3_exit:
+ .global __mulhisi3
+ .func __mulhisi3
+ __mulhisi3:
++#if defined (__AVR_HAVE_MUL__)
++ muls r21, r19
++ movw r24, r0
++ mul r20, r18
++ movw r22, r0
++ mulsu r21, r18
++ add r23, r0
++ adc r24, r1
++ clr r1
++ adc r25, r1
++ mulsu r19, r20
++ add r23, r0
++ adc r24, r1
++ clr r1
++ adc r25, r1
++ ret
++#else
+ mov_l r18, r24
+ mov_h r19, r25
+ clr r24
+@@ -173,6 +190,7 @@ __mulhisi3:
+ dec r20
+ mov r21, r20
+ rjmp __mulsi3
++#endif /* defined (__AVR_HAVE_MUL__) */
+ .endfunc
+ #endif /* defined (L_mulhisi3) */
+
+@@ -180,13 +198,31 @@ __mulhisi3:
+ .global __umulhisi3
+ .func __umulhisi3
+ __umulhisi3:
+- mov_l r18, r24
+- mov_h r19, r25
++#if defined (__AVR_HAVE_MUL__)
++ mul r21, r19
++ movw r24, r0
++ mul r20, r18
++ movw r22, r0
++ mul r21, r18
++ add r23, r0
++ adc r24, r1
++ clr r1
++ adc r25, r1
++ mul r19, r20
++ add r23, r0
++ adc r24, r1
++ clr r1
++ adc r25, r1
++ ret
++#else
++ mov_l r22, r20
++ mov_h r23, r21
+ clr r24
+ clr r25
+ clr r20
+ clr r21
+ rjmp __mulsi3
++#endif
+ .endfunc
+ #endif /* defined (L_umulhisi3) */
+
+@@ -199,7 +235,6 @@ __umulhisi3:
+ #define r_arg1HL r24
+ #define r_arg1HH r25 /* multiplier High */
+
+-
+ #define r_arg2L r18 /* multiplicand Low */
+ #define r_arg2H r19
+ #define r_arg2HL r20
+@@ -555,6 +590,23 @@ __divmodsi4_neg1:
+ .endfunc
+ #endif /* defined (L_divmodsi4) */
+
++#undef r_remHH
++#undef r_remHL
++#undef r_remH
++#undef r_remL
++
++#undef r_arg1HH
++#undef r_arg1HL
++#undef r_arg1H
++#undef r_arg1L
++
++#undef r_arg2HH
++#undef r_arg2HL
++#undef r_arg2H
++#undef r_arg2L
++
++#undef r_cnt
++
+ /**********************************
+ * This is a prologue subroutine
+ **********************************/
+@@ -897,3 +949,4 @@ __tablejump_elpm__:
+ .endfunc
+ #endif /* defined (L_tablejump_elpm) */
+
++#include "libgcc-fixed.S"
+diff -rupN gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2009-12-24 14:32:38.000000000 -0600
++++ gcc/config/avr/t-avr 2010-09-21 14:31:30.000000000 -0500
+@@ -36,6 +36,8 @@ LIB1ASMSRC = avr/libgcc.S
+ LIB1ASMFUNCS = \
+ _mulqi3 \
+ _mulhi3 \
++ _mulhisi3 \
++ _umulhisi3 \
+ _mulsi3 \
+ _udivmodqi4 \
+ _divmodqi4 \
+@@ -54,6 +56,39 @@ LIB1ASMFUNCS = \
+ _ctors \
+ _dtors
+
++# Fixed point routines
++LIB1ASMFUNCS += \
++ _fractqqsf \
++ _fractuqqsf \
++ _fracthqsf \
++ _fractuhqsf \
++ _fracthasf \
++ _fractuhasf \
++ _fractsasf \
++ _fractusasf \
++ _fractsfqq \
++ _fractsfuqq \
++ _fractsfhq \
++ _fractsfuhq \
++ _fractsfha \
++ _fractsfsa \
++ _mulqq3 \
++ _muluqq3 \
++ _mulhq3 \
++ _muluhq3 \
++ _mulha3 \
++ _muluha3 \
++ _mulsa3 \
++ _mulusa3 \
++ _divqq3 \
++ _udivuqq3 \
++ _divhq3 \
++ _udivuhq3 \
++ _divha3 \
++ _udivuha3 \
++ _divsa3 \
++ _udivusa3
++
+ # We do not have the DF type.
+ # Most of the C functions in libgcc2 use almost all registers,
+ # so use -mcall-prologues for smaller code size.
+diff -rupN gcc/cse.c gcc/cse.c
+--- gcc/cse.c 2010-01-12 14:25:10.000000000 -0600
++++ gcc/cse.c 2010-09-21 14:31:30.000000000 -0500
+@@ -3703,9 +3703,10 @@ fold_rtx (rtx x, rtx insn)
+ && exact_log2 (- INTVAL (const_arg1)) >= 0)))
+ break;
+
+- /* ??? Vector mode shifts by scalar
++ /* ??? Vector and Fixed Point shifts by scalar
+ shift operand are not supported yet. */
+- if (is_shift && VECTOR_MODE_P (mode))
++ if (is_shift && (VECTOR_MODE_P (mode)
++ || ALL_FIXED_POINT_MODE_P (mode)))
+ break;
+
+ if (is_shift
+diff -rupN gcc/dwarf2out.c gcc/dwarf2out.c
+--- gcc/dwarf2out.c 2010-07-01 07:31:19.000000000 -0500
++++ gcc/dwarf2out.c 2010-09-21 14:35:35.000000000 -0500
+@@ -12017,6 +12017,12 @@ base_type_die (tree type)
+
+ add_AT_unsigned (base_type_result, DW_AT_byte_size,
+ int_size_in_bytes (type));
++
++ /* version 3 dwarf specifies that for fixed-point types DW_AT_binary_scale
++ describes the location of the decimal place */
++ if (TREE_CODE (type) == FIXED_POINT_TYPE)
++ add_AT_int (base_type_result, DW_AT_binary_scale, -TYPE_FBIT (type));
++
+ add_AT_unsigned (base_type_result, DW_AT_encoding, encoding);
+
+ return base_type_result;
+@@ -15482,7 +15488,11 @@ add_const_value_attribute (dw_die_ref di
+
+ case HIGH:
+ case CONST_FIXED:
+- return false;
++ {
++ add_AT_double (die, DW_AT_const_value,
++ CONST_FIXED_VALUE_HIGH (rtl), CONST_FIXED_VALUE_LOW (rtl));
++ }
++ break;
+
+ case MEM:
+ if (GET_CODE (XEXP (rtl, 0)) == CONST_STRING
+diff -rupN gcc/fold-const.c gcc/fold-const.c
+--- gcc/fold-const.c 2010-04-06 05:36:57.000000000 -0500
++++ gcc/fold-const.c 2010-09-21 14:31:30.000000000 -0500
+@@ -12305,6 +12305,11 @@ fold_binary_loc (location_t loc,
+ if (TREE_CODE (arg1) == INTEGER_CST && tree_int_cst_sgn (arg1) < 0)
+ return NULL_TREE;
+
++ /* Since fixed point types cannot perform bitwise and, or, etc..
++ don't try to convert to an expression with them. */
++ if (TREE_CODE(type) == FIXED_POINT_TYPE)
++ return NULL_TREE;
++
+ /* Turn (a OP c1) OP c2 into a OP (c1+c2). */
+ if (TREE_CODE (op0) == code && host_integerp (arg1, false)
+ && TREE_INT_CST_LOW (arg1) < TYPE_PRECISION (type)
+diff -rupN gcc/varasm.c gcc/varasm.c
+--- gcc/varasm.c 2010-03-27 06:56:30.000000000 -0500
++++ gcc/varasm.c 2010-09-21 14:31:30.000000000 -0500
+@@ -2709,7 +2709,7 @@ assemble_integer (rtx x, unsigned int si
+ else
+ mclass = MODE_INT;
+
+- omode = mode_for_size (subsize * BITS_PER_UNIT, mclass, 0);
++ omode = mode_for_size (subsize * BITS_PER_UNIT, MODE_INT, 0);
+ imode = mode_for_size (size * BITS_PER_UNIT, mclass, 0);
+
+ for (i = 0; i < size; i += subsize)
--- /dev/null
+diff -Naurp gcc/config/avr/avr.c gcc/config/avr/avr.c
+--- gcc/config/avr/avr.c 2011-09-02 11:40:55.000000000 +0300
++++ gcc/config/avr/avr.c 2011-09-02 11:40:01.000000000 +0300
+@@ -52,6 +52,7 @@
+ static int avr_naked_function_p (tree);
+ static int interrupt_function_p (tree);
+ static int signal_function_p (tree);
++static int nmi_function_p (tree);
+ static int avr_OS_task_function_p (tree);
+ static int avr_OS_main_function_p (tree);
+ static int avr_regs_to_save (HARD_REG_SET *);
+@@ -122,6 +123,7 @@ static const struct attribute_spec avr_a
+ { "progmem", 0, 0, false, false, false, avr_handle_progmem_attribute },
+ { "signal", 0, 0, true, false, false, avr_handle_fndecl_attribute },
+ { "interrupt", 0, 0, true, false, false, avr_handle_fndecl_attribute },
++ { "nmi", 0, 0, true, false, false, avr_handle_fndecl_attribute },
+ { "naked", 0, 0, false, true, true, avr_handle_fntype_attribute },
+ { "OS_task", 0, 0, false, true, true, avr_handle_fntype_attribute },
+ { "OS_main", 0, 0, false, true, true, avr_handle_fntype_attribute },
+@@ -314,6 +316,21 @@ signal_function_p (tree func)
+ return a != NULL_TREE;
+ }
+
++/* Return nonzero if FUNC is a nmi function as specified
++ by the "nmi" attribute. */
++
++static int
++nmi_function_p (tree func)
++{
++ tree a;
++
++ if (TREE_CODE (func) != FUNCTION_DECL)
++ return 0;
++
++ a = lookup_attribute ("nmi", DECL_ATTRIBUTES (func));
++ return a != NULL_TREE;
++}
++
+ /* Return nonzero if FUNC is a OS_task function. */
+
+ static int
+@@ -543,6 +560,7 @@ expand_prologue (void)
+ cfun->machine->is_naked = avr_naked_function_p (current_function_decl);
+ cfun->machine->is_interrupt = interrupt_function_p (current_function_decl);
+ cfun->machine->is_signal = signal_function_p (current_function_decl);
++ cfun->machine->is_nmi = nmi_function_p (current_function_decl);
+ cfun->machine->is_OS_task = avr_OS_task_function_p (current_function_decl);
+ cfun->machine->is_OS_main = avr_OS_main_function_p (current_function_decl);
+ cfun->machine->stack_usage = 0;
+@@ -583,18 +601,49 @@ expand_prologue (void)
+
+ /* Push SREG. */
+ insn = emit_move_insn (tmp_reg_rtx,
+- gen_rtx_MEM (QImode, GEN_INT (SREG_ADDR)));
++ gen_rtx_MEM (QImode, GEN_INT (AVR_SREG_ADDR)));
+ RTX_FRAME_RELATED_P (insn) = 1;
+ insn = emit_move_insn (pushbyte, tmp_reg_rtx);
+ RTX_FRAME_RELATED_P (insn) = 1;
+ cfun->machine->stack_usage++;
+
++ /* Push RAMPD, RAMPX, RAMPY. */
++ if (AVR_HAVE_RAMPX_Y_D)
++ {
++ /* Push RAMPD. */
++ insn = emit_move_insn (tmp_reg_rtx,
++ gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPD_ADDR)));
++ RTX_FRAME_RELATED_P (insn) = 1;
++ insn = emit_move_insn (pushbyte, tmp_reg_rtx);
++ RTX_FRAME_RELATED_P (insn) = 1;
++
++ /* Push RAMPX. */
++ if (TEST_HARD_REG_BIT (set, REG_X) && TEST_HARD_REG_BIT (set, REG_X + 1))
++ {
++ insn = emit_move_insn (tmp_reg_rtx,
++ gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPX_ADDR)));
++ RTX_FRAME_RELATED_P (insn) = 1;
++ insn = emit_move_insn (pushbyte, tmp_reg_rtx);
++ RTX_FRAME_RELATED_P (insn) = 1;
++ }
++
++ /* Push RAMPY. */
++ if (TEST_HARD_REG_BIT (set, REG_Y) && TEST_HARD_REG_BIT (set, REG_Y + 1))
++ {
++ insn = emit_move_insn (tmp_reg_rtx,
++ gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPY_ADDR)));
++ RTX_FRAME_RELATED_P (insn) = 1;
++ insn = emit_move_insn (pushbyte, tmp_reg_rtx);
++ RTX_FRAME_RELATED_P (insn) = 1;
++ }
++ }
++
+ /* Push RAMPZ. */
+ if(AVR_HAVE_RAMPZ
+ && (TEST_HARD_REG_BIT (set, REG_Z) && TEST_HARD_REG_BIT (set, REG_Z + 1)))
+ {
+ insn = emit_move_insn (tmp_reg_rtx,
+- gen_rtx_MEM (QImode, GEN_INT (RAMPZ_ADDR)));
++ gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPZ_ADDR)));
+ RTX_FRAME_RELATED_P (insn) = 1;
+ insn = emit_move_insn (pushbyte, tmp_reg_rtx);
+ RTX_FRAME_RELATED_P (insn) = 1;
+@@ -607,6 +656,41 @@ expand_prologue (void)
+
+ /* Prevent any attempt to delete the setting of ZERO_REG! */
+ emit_use (zero_reg_rtx);
++
++
++ /*
++ Clear RAMP? registers if used for data access in the interrupt/signal
++ context. Do this after the zero register has been explictly cleared.
++ */
++ if (AVR_HAVE_RAMPX_Y_D)
++ {
++ /* Set RAMPD to 0. */
++ insn = emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPD_ADDR)), const0_rtx);
++ RTX_FRAME_RELATED_P (insn) = 1;
++
++ if (TEST_HARD_REG_BIT (set, REG_X) && TEST_HARD_REG_BIT (set, REG_X + 1))
++ {
++ /* Set RAMPX to 0. */
++ insn = emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPX_ADDR)), const0_rtx);
++ RTX_FRAME_RELATED_P (insn) = 1;
++ }
++
++ if (TEST_HARD_REG_BIT (set, REG_Y) && TEST_HARD_REG_BIT (set, REG_Y + 1))
++ {
++ /* Set RAMPY to 0. */
++ insn = emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPY_ADDR)), const0_rtx);
++ RTX_FRAME_RELATED_P (insn) = 1;
++ }
++
++ if(AVR_HAVE_RAMPZ
++ && (TEST_HARD_REG_BIT (set, REG_Z) && TEST_HARD_REG_BIT (set, REG_Z + 1)))
++ {
++ /* Set RAMPZ to 0. */
++ insn = emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPZ_ADDR)), const0_rtx);
++ RTX_FRAME_RELATED_P (insn) = 1;
++ }
++ }
++
+ }
+ if (minimize && (frame_pointer_needed
+ || (AVR_2_BYTE_PC && live_seq > 6)
+@@ -698,16 +782,16 @@ expand_prologue (void)
+ insn = emit_move_insn (stack_pointer_rtx, frame_pointer_rtx);
+ RTX_FRAME_RELATED_P (insn) = 1;
+ }
+- else if (TARGET_NO_INTERRUPTS
+- || cfun->machine->is_signal
+- || cfun->machine->is_OS_main)
++ else if ((!AVR_XMEGA && TARGET_NO_INTERRUPTS)
++ || (!AVR_XMEGA && cfun->machine->is_signal)
++ || (!AVR_XMEGA && cfun->machine->is_OS_main))
+ {
+ insn =
+ emit_insn (gen_movhi_sp_r_irq_off (stack_pointer_rtx,
+ frame_pointer_rtx));
+ RTX_FRAME_RELATED_P (insn) = 1;
+ }
+- else if (cfun->machine->is_interrupt)
++ else if (!AVR_XMEGA && cfun->machine->is_interrupt)
+ {
+ insn = emit_insn (gen_movhi_sp_r_irq_on (stack_pointer_rtx,
+ frame_pointer_rtx));
+@@ -878,13 +962,13 @@ expand_epilogue (void)
+ {
+ emit_move_insn (stack_pointer_rtx, frame_pointer_rtx);
+ }
+- else if (TARGET_NO_INTERRUPTS
+- || cfun->machine->is_signal)
++ else if ((!AVR_XMEGA && TARGET_NO_INTERRUPTS)
++ || (!AVR_XMEGA && cfun->machine->is_signal))
+ {
+ emit_insn (gen_movhi_sp_r_irq_off (stack_pointer_rtx,
+ frame_pointer_rtx));
+ }
+- else if (cfun->machine->is_interrupt)
++ else if (!AVR_XMEGA && cfun->machine->is_interrupt)
+ {
+ emit_insn (gen_movhi_sp_r_irq_on (stack_pointer_rtx,
+ frame_pointer_rtx));
+@@ -937,14 +1021,39 @@ expand_epilogue (void)
+ && (TEST_HARD_REG_BIT (set, REG_Z) && TEST_HARD_REG_BIT (set, REG_Z + 1)))
+ {
+ emit_insn (gen_popqi (tmp_reg_rtx));
+- emit_move_insn (gen_rtx_MEM(QImode, GEN_INT(RAMPZ_ADDR)),
++ emit_move_insn (gen_rtx_MEM(QImode, GEN_INT(AVR_RAMPZ_ADDR)),
++ tmp_reg_rtx);
++ }
++
++ /* Restore RAMPY, RAMPX, RAMPD using tmp reg as scratch. */
++ if (AVR_HAVE_RAMPX_Y_D)
++ {
++ /* Pop RAMPY. */
++ if (TEST_HARD_REG_BIT (set, REG_Y) && TEST_HARD_REG_BIT (set, REG_Y + 1))
++ {
++ emit_insn (gen_popqi (tmp_reg_rtx));
++ emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPY_ADDR)),
++ tmp_reg_rtx);
++ }
++
++ /* Pop RAMPX. */
++ if (TEST_HARD_REG_BIT (set, REG_X) && TEST_HARD_REG_BIT (set, REG_X + 1))
++ {
++ emit_insn (gen_popqi (tmp_reg_rtx));
++ emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPX_ADDR)),
++ tmp_reg_rtx);
++ }
++
++ /* Pop RAMPD. */
++ emit_insn (gen_popqi (tmp_reg_rtx));
++ emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPD_ADDR)),
+ tmp_reg_rtx);
+ }
+
+ /* Restore SREG using tmp reg as scratch. */
+ emit_insn (gen_popqi (tmp_reg_rtx));
+
+- emit_move_insn (gen_rtx_MEM(QImode, GEN_INT(SREG_ADDR)),
++ emit_move_insn (gen_rtx_MEM(QImode, GEN_INT(AVR_SREG_ADDR)),
+ tmp_reg_rtx);
+
+ /* Restore tmp REG. */
+@@ -1722,9 +1831,17 @@ output_movhi (rtx insn, rtx operands[],
+ return *l = 1, AS2 (out,__SP_L__,%A1);
+ /* Use simple load of stack pointer if no interrupts are
+ used. */
+- else if (TARGET_NO_INTERRUPTS)
++ else if (!AVR_XMEGA && TARGET_NO_INTERRUPTS)
+ return *l = 2, (AS2 (out,__SP_H__,%B1) CR_TAB
+ AS2 (out,__SP_L__,%A1));
++ if(AVR_XMEGA)
++ {
++ *l = 2;
++ return (AS2 (out,__SP_L__,%A1) CR_TAB
++ AS2 (out,__SP_H__,%B1));
++ }
++ else
++ {
+ *l = 5;
+ return (AS2 (in,__tmp_reg__,__SREG__) CR_TAB
+ "cli" CR_TAB
+@@ -1732,6 +1849,7 @@ output_movhi (rtx insn, rtx operands[],
+ AS2 (out,__SREG__,__tmp_reg__) CR_TAB
+ AS2 (out,__SP_L__,%A1));
+ }
++ }
+ else if (test_hard_reg_class (STACK_REG, src))
+ {
+ *l = 2;
+@@ -1865,7 +1983,7 @@ out_movqi_r_mr (rtx insn, rtx op[], int
+
+ if (CONSTANT_ADDRESS_P (x))
+ {
+- if (CONST_INT_P (x) && INTVAL (x) == SREG_ADDR)
++ if (CONST_INT_P (x) && INTVAL (x) == AVR_SREG_ADDR)
+ {
+ *l = 1;
+ return AS2 (in,%0,__SREG__);
+@@ -1873,7 +1991,8 @@ out_movqi_r_mr (rtx insn, rtx op[], int
+ if (optimize > 0 && io_address_operand (x, QImode))
+ {
+ *l = 1;
+- return AS2 (in,%0,%m1-0x20);
++ op[2] = GEN_INT(AVR_IO_OFFSET);
++ return AS2 (in,%0,%m1-%2);
+ }
+ *l = 2;
+ return AS2 (lds,%0,%m1);
+@@ -2061,8 +2180,9 @@ out_movhi_r_mr (rtx insn, rtx op[], int
+ if (optimize > 0 && io_address_operand (base, HImode))
+ {
+ *l = 2;
+- return (AS2 (in,%A0,%m1-0x20) CR_TAB
+- AS2 (in,%B0,%m1+1-0x20));
++ op[2] = GEN_INT(AVR_IO_OFFSET);
++ return (AS2 (in,%A0,%m1-%2) CR_TAB
++ AS2 (in,%B0,%m1+1-%2));
+ }
+ *l = 4;
+ return (AS2 (lds,%A0,%m1) CR_TAB
+@@ -2561,7 +2681,7 @@ out_movqi_mr_r (rtx insn, rtx op[], int
+
+ if (CONSTANT_ADDRESS_P (x))
+ {
+- if (CONST_INT_P (x) && INTVAL (x) == SREG_ADDR)
++ if (CONST_INT_P (x) && INTVAL (x) == AVR_SREG_ADDR)
+ {
+ *l = 1;
+ return AS2 (out,__SREG__,%1);
+@@ -2569,7 +2689,8 @@ out_movqi_mr_r (rtx insn, rtx op[], int
+ if (optimize > 0 && io_address_operand (x, QImode))
+ {
+ *l = 1;
+- return AS2 (out,%m0-0x20,%1);
++ op[2] = GEN_INT(AVR_IO_OFFSET);
++ return AS2 (out,%m0-%2,%1);
+ }
+ *l = 2;
+ return AS2 (sts,%m0,%1);
+@@ -2648,9 +2769,18 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ if (optimize > 0 && io_address_operand (base, HImode))
+ {
+ *l = 2;
+- return (AS2 (out,%m0+1-0x20,%B1) CR_TAB
+- AS2 (out,%m0-0x20,%A1));
++ op[2] = GEN_INT(AVR_IO_OFFSET);
++ if (AVR_XMEGA)
++ return (AS2 (out,%A0-%2,%A1) CR_TAB
++ AS2 (out,%B0-%2,%B1));
++ else
++ return (AS2 (out,%m0+1-%2,%B1) CR_TAB
++ AS2 (out,%m0-%2,%A1));
+ }
++ if (AVR_XMEGA)
++ return *l = 4, (AS2 (sts,%A0,%A1) CR_TAB
++ AS2 (sts,%B0,%B1));
++ else
+ return *l = 4, (AS2 (sts,%m0+1,%B1) CR_TAB
+ AS2 (sts,%m0,%A1));
+ }
+@@ -2667,11 +2797,20 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ AS2 (adiw,r26,1) CR_TAB
+ AS2 (st,X,__tmp_reg__));
+ else
++ {
++ if (!AVR_XMEGA)
+ return *l=5, (AS2 (mov,__tmp_reg__,r27) CR_TAB
+ AS2 (adiw,r26,1) CR_TAB
+ AS2 (st,X,__tmp_reg__) CR_TAB
+ AS2 (sbiw,r26,1) CR_TAB
+ AS2 (st,X,r26));
++ else
++ return *l=5, (AS2 (mov,__tmp_reg__,r27) CR_TAB
++ AS2 (st,X,r26) CR_TAB
++ AS2 (adiw,r26,1) CR_TAB
++ AS2 (st,X,__tmp_reg__) CR_TAB
++ AS2 (sbiw,r26,1));
++ }
+ }
+ else
+ {
+@@ -2679,14 +2818,27 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ return *l=2, (AS2 (st,X+,%A1) CR_TAB
+ AS2 (st,X,%B1));
+ else
++ {
++ if (!AVR_XMEGA)
+ return *l=3, (AS2 (adiw,r26,1) CR_TAB
+ AS2 (st,X,%B1) CR_TAB
+ AS2 (st,-X,%A1));
++ else
++ return *l=3, (AS2 (st,X+,%A1) CR_TAB
++ AS2 (st,X,%B1) CR_TAB
++ AS2 (sbiw,r26,1));
++ }
+ }
+ }
+ else
++ {
++ if (!AVR_XMEGA)
+ return *l=2, (AS2 (std,%0+1,%B1) CR_TAB
+ AS2 (st,%0,%A1));
++ else
++ return *l=2, (AS2 (st,%0,%A1) CR_TAB
++ AS2 (std,%0+1,%B1));
++ }
+ }
+ else if (GET_CODE (base) == PLUS)
+ {
+@@ -2697,6 +2849,8 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ if (reg_base != REG_Y)
+ fatal_insn ("incorrect insn:",insn);
+
++ if (!AVR_XMEGA)
++ {
+ if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest)))
+ return *l = 4, (AS2 (adiw,r28,%o0-62) CR_TAB
+ AS2 (std,Y+63,%B1) CR_TAB
+@@ -2710,11 +2864,29 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ AS2 (subi,r28,lo8(%o0)) CR_TAB
+ AS2 (sbci,r29,hi8(%o0)));
+ }
++ else
++ {
++ if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest)))
++ return *l = 4, (AS2 (adiw,r28,%o0-62) CR_TAB
++ AS2 (std,Y+62,%A1) CR_TAB
++ AS2 (std,Y+63,%B1) CR_TAB
++ AS2 (sbiw,r28,%o0-62));
++
++ return *l = 6, (AS2 (subi,r28,lo8(-%o0)) CR_TAB
++ AS2 (sbci,r29,hi8(-%o0)) CR_TAB
++ AS2 (st,Y,%A1) CR_TAB
++ AS2 (std,Y+1,%B1) CR_TAB
++ AS2 (subi,r28,lo8(%o0)) CR_TAB
++ AS2 (sbci,r29,hi8(%o0)));
++ }
++ }
+ if (reg_base == REG_X)
+ {
+ /* (X + d) = R */
+ if (reg_src == REG_X)
+ {
++ if (!AVR_XMEGA)
++ {
+ *l = 7;
+ return (AS2 (mov,__tmp_reg__,r26) CR_TAB
+ AS2 (mov,__zero_reg__,r27) CR_TAB
+@@ -2724,21 +2896,57 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ AS1 (clr,__zero_reg__) CR_TAB
+ AS2 (sbiw,r26,%o0));
+ }
++ else
++ {
++ *l = 7;
++ return (AS2 (mov,__tmp_reg__,r26) CR_TAB
++ AS2 (mov,__zero_reg__,r27) CR_TAB
++ AS2 (adiw,r26,%o0) CR_TAB
++ AS2 (st,X+,__tmp_reg__) CR_TAB
++ AS2 (st,X,__zero_reg__) CR_TAB
++ AS1 (clr,__zero_reg__) CR_TAB
++ AS2 (sbiw,r26,%o0+1));
++ }
++ }
++ if (!AVR_XMEGA)
++ {
+ *l = 4;
+ return (AS2 (adiw,r26,%o0+1) CR_TAB
+ AS2 (st,X,%B1) CR_TAB
+ AS2 (st,-X,%A1) CR_TAB
+ AS2 (sbiw,r26,%o0));
+ }
++ else
++ {
++ *l = 4;
++ return (AS2 (adiw,r26,%o0) CR_TAB
++ AS2 (st,X+,%A1) CR_TAB
++ AS2 (st,X,%B1) CR_TAB
++ AS2 (sbiw,r26,%o0+1));
++ }
++ }
++
++ if (!AVR_XMEGA)
+ return *l=2, (AS2 (std,%B0,%B1) CR_TAB
+ AS2 (std,%A0,%A1));
++ else
++ return *l=2, (AS2 (std,%A0,%A1) CR_TAB
++ AS2 (std,%B0,%B1));
+ }
+ else if (GET_CODE (base) == PRE_DEC) /* (--R) */
++ {
++ if (mem_volatile_p && AVR_XMEGA)
++ return *l = 4, (AS2 (sbiw,%r0,2) CR_TAB
++ AS2 (st,%p0+,%A1) CR_TAB
++ AS2 (st,%p0,%B1) CR_TAB
++ AS2 (sbiw,%r0,1));
++ else
+ return *l=2, (AS2 (st,%0,%B1) CR_TAB
+ AS2 (st,%0,%A1));
++ }
+ else if (GET_CODE (base) == POST_INC) /* (R++) */
+ {
+- if (mem_volatile_p)
++ if (mem_volatile_p && !AVR_XMEGA)
+ {
+ if (REGNO (XEXP (base, 0)) == REG_X)
+ {
+@@ -4874,6 +5082,16 @@ avr_asm_declare_function_name (FILE *fil
+ }
+ }
+
++ else if (cfun->machine->is_nmi)
++ {
++ if (strncmp (name, "__vector", strlen ("__vector")) != 0)
++ {
++ warning_at (DECL_SOURCE_LOCATION (decl), 0,
++ "%qs appears to be a misspelled nmi handler",
++ name);
++ }
++ }
++
+ ASM_OUTPUT_TYPE_DIRECTIVE (file, name, "function");
+ ASM_OUTPUT_LABEL (file, name);
+ }
+@@ -5174,7 +5392,8 @@ avr_file_start (void)
+ /* fprintf (asm_out_file, "\t.arch %s\n", avr_mcu_name);*/
+ fputs ("__SREG__ = 0x3f\n"
+ "__SP_H__ = 0x3e\n"
+- "__SP_L__ = 0x3d\n", asm_out_file);
++ "__SP_L__ = 0x3d\n"
++ "__CCP__ = 0x34\n", asm_out_file);
+
+ fputs ("__tmp_reg__ = 0\n"
+ "__zero_reg__ = 1\n", asm_out_file);
+@@ -6273,16 +6492,17 @@ avr_out_sbxx_branch (rtx insn, rtx opera
+
+ if (GET_CODE (operands[1]) == CONST_INT)
+ {
+- if (INTVAL (operands[1]) < 0x40)
++ operands[4] = GEN_INT(AVR_IO_OFFSET); /* operands[3] is for the jump */
++ if (low_io_address_operand (operands[1], VOIDmode))
+ {
+ if (comp == EQ)
+- output_asm_insn (AS2 (sbis,%m1-0x20,%2), operands);
++ output_asm_insn (AS2 (sbis,%1-%4,%2), operands);
+ else
+- output_asm_insn (AS2 (sbic,%m1-0x20,%2), operands);
++ output_asm_insn (AS2 (sbic,%1-%4,%2), operands);
+ }
+ else
+ {
+- output_asm_insn (AS2 (in,__tmp_reg__,%m1-0x20), operands);
++ output_asm_insn (AS2 (in,__tmp_reg__,%1-%4), operands);
+ if (comp == EQ)
+ output_asm_insn (AS2 (sbrs,__tmp_reg__,%2), operands);
+ else
+diff -Naurp gcc/config/avr/avr-c.c gcc/config/avr/avr-c.c
+--- gcc/config/avr/avr-c.c 2009-12-24 23:32:38.000000000 +0300
++++ gcc/config/avr/avr-c.c 2011-09-02 11:40:01.000000000 +0300
+@@ -81,5 +81,18 @@ avr_cpu_cpp_builtins (struct cpp_reader
+
+ if (TARGET_NO_INTERRUPTS)
+ cpp_define (pfile, "__NO_INTERRUPTS__");
++
++ if (avr_current_arch->xmega)
++ {
++ cpp_define (pfile, "__AVR_XMEGA__");
++ cpp_define (pfile, "__AVR_HAVE_SPMX__");
++ }
++ if (avr_current_arch->have_rampx_y_d)
++ {
++ cpp_define (pfile, "__AVR_HAVE_RAMPX__");
++ cpp_define (pfile, "__AVR_HAVE_RAMPY__");
++ cpp_define (pfile, "__AVR_HAVE_RAMPD__");
++ }
++
+ }
+
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2009-07-17 21:49:03.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-02 11:42:48.000000000 +0300
+@@ -36,7 +36,14 @@ const struct base_arch_s avr_arch_types[
+ { 0, 1, 0, 1, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=4", "avr4" },
+ { 0, 1, 1, 1, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=5", "avr5" },
+ { 0, 1, 1, 1, 1, 1, 0, 0, 0, 0x0060, "__AVR_ARCH__=51", "avr51" },
+- { 0, 1, 1, 1, 1, 1, 1, 0, 0, 0x0060, "__AVR_ARCH__=6", "avr6" }
++ { 0, 1, 1, 1, 1, 1, 1, 0, 0, 0x0060, "__AVR_ARCH__=6", "avr6" },
++ { 0, 1, 0, 1, 0, 0, 0, 1, 0, 0x2000, "__AVR_ARCH__=101", "avrxmega1" },
++ { 0, 1, 1, 1, 0, 0, 0, 1, 0, 0x2000, "__AVR_ARCH__=102", "avrxmega2" },
++ { 0, 1, 1, 1, 0, 0, 0, 1, 1, 0x2000, "__AVR_ARCH__=103", "avrxmega3" },
++ { 0, 1, 1, 1, 1, 1, 0, 1, 0, 0x2000, "__AVR_ARCH__=104", "avrxmega4" },
++ { 0, 1, 1, 1, 1, 1, 0, 1, 1, 0x2000, "__AVR_ARCH__=105", "avrxmega5" },
++ { 0, 1, 1, 1, 1, 1, 1, 1, 0, 0x2000, "__AVR_ARCH__=106", "avrxmega6" },
++ { 0, 1, 1, 1, 1, 1, 1, 1, 1, 0x2000, "__AVR_ARCH__=107", "avrxmega7" }
+ };
+
+ /* List of all known AVR MCU types - if updated, it has to be kept
+@@ -189,6 +196,38 @@ const struct mcu_type_s avr_mcu_types[]
+ { "avr6", ARCH_AVR6, NULL, 0, 0x0200, "m2561" },
+ { "atmega2560", ARCH_AVR6, "__AVR_ATmega2560__", 0, 0x0200, "m2561" },
+ { "atmega2561", ARCH_AVR6, "__AVR_ATmega2561__", 0, 0x0200, "m2561" },
++ /* Enhanced, == 256K. */
++ /* Xmega, <= 8K FLASH. */
++ /* Xmega, > 8K, <= 64K FLASH, <= 64K RAM. */
++ { "avrxmega2", ARCH_AVRXMEGA2, NULL, 0, 0x2000, "x32a4" },
++ { "atxmega16a4", ARCH_AVRXMEGA2, "__AVR_ATxmega16A4__", 0, 0x2000, "x16a4" },
++ { "atxmega16d4", ARCH_AVRXMEGA2, "__AVR_ATxmega16D4__", 0, 0x2000, "x16d4" },
++ { "atxmega16x1", ARCH_AVRXMEGA2, "__AVR_ATxmega16X1__", 0, 0x2000, "x16x1" },
++ { "atxmega32a4", ARCH_AVRXMEGA2, "__AVR_ATxmega32A4__", 0, 0x2000, "x32a4" },
++ { "atxmega32d4", ARCH_AVRXMEGA2, "__AVR_ATxmega32D4__", 0, 0x2000, "x32d4" },
++ /* Xmega, > 8K, <= 64K FLASH, > 64K RAM. */
++ /* { "avrxmega3", ARCH_AVRXMEGA3, NULL }, */
++ /* Xmega, > 64K, <= 128K FLASH, <= 64K RAM. */
++ { "avrxmega4", ARCH_AVRXMEGA4, NULL, 0, 0x2000, "x64d3" },
++ { "atxmega64a3", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3__", 0, 0x2000, "x64a3" },
++ { "atxmega64d3", ARCH_AVRXMEGA4, "__AVR_ATxmega64D3__", 0, 0x2000, "x64d3" },
++ /* Xmega, > 64K, <= 128K FLASH, > 64K RAM. */
++ { "avrxmega5", ARCH_AVRXMEGA5, NULL, 0, 0x2000, "x64a1" },
++ { "atxmega64a1", ARCH_AVRXMEGA5, "__AVR_ATxmega64A1__", 0, 0x2000, "x64a1" },
++ { "atxmega64a1u", ARCH_AVRXMEGA5, "__AVR_ATxmega64A1U__", 0, 0x2000, "x64a1u" },
++ /* Xmega, > 128K, <= 256K FLASH, <= 64K RAM. */
++ { "avrxmega6", ARCH_AVRXMEGA6, NULL, 0, 0x2000, "x128a3" },
++ { "atxmega128a3", ARCH_AVRXMEGA6, "__AVR_ATxmega128A3__", 0, 0x2000, "x128a3" },
++ { "atxmega128d3", ARCH_AVRXMEGA6, "__AVR_ATxmega128D3__", 0, 0x2000, "x128d3" },
++ { "atxmega192a3", ARCH_AVRXMEGA6, "__AVR_ATxmega192A3__", 0, 0x2000, "x192a3" },
++ { "atxmega192d3", ARCH_AVRXMEGA6, "__AVR_ATxmega192D3__", 0, 0x2000, "x192d3" },
++ { "atxmega256a3", ARCH_AVRXMEGA6, "__AVR_ATxmega256A3__", 0, 0x2000, "x256a3" },
++ { "atxmega256a3b",ARCH_AVRXMEGA6, "__AVR_ATxmega256A3B__", 0, 0x2000, "x256a3b" },
++ { "atxmega256d3", ARCH_AVRXMEGA6, "__AVR_ATxmega256D3__", 0, 0x2000, "x256d3" },
++ /* Xmega, > 128K, <= 256K FLASH, > 64K RAM. */
++ { "avrxmega7", ARCH_AVRXMEGA7, NULL, 0, 0x2000, "x128a1" },
++ { "atxmega128a1", ARCH_AVRXMEGA7, "__AVR_ATxmega128A1__", 0, 0x2000, "x128a1" },
++ { "atxmega128a1u", ARCH_AVRXMEGA7, "__AVR_ATxmega128A1U__", 0, 0x2000, "x128a1u" },
+ /* Assembler only. */
+ { "avr1", ARCH_AVR1, NULL, 0, 0x0060, "s1200" },
+ { "at90s1200", ARCH_AVR1, "__AVR_AT90S1200__", 0, 0x0060, "s1200" },
+diff -Naurp gcc/config/avr/avr.h gcc/config/avr/avr.h
+--- gcc/config/avr/avr.h 2010-01-12 02:12:14.000000000 +0300
++++ gcc/config/avr/avr.h 2011-09-02 11:40:01.000000000 +0300
+@@ -45,11 +45,11 @@ struct base_arch_s {
+ /* Core have 'EICALL' and 'EIJMP' instructions. */
+ int have_eijmp_eicall;
+
+- /* Reserved for xmega architecture. */
+- int reserved;
++ /* Core is in Xmega family. */
++ int xmega;
+
+- /* Reserved for xmega architecture. */
+- int reserved2;
++ /* Core have RAMPX, RAMPY and RAMPD registers. */
++ int have_rampx_y_d;
+
+ /* Default start of data section address for architecture. */
+ int default_data_section_start;
+@@ -75,7 +75,14 @@ enum avr_arch
+ ARCH_AVR4,
+ ARCH_AVR5,
+ ARCH_AVR51,
+- ARCH_AVR6
++ ARCH_AVR6,
++ ARCH_AVRXMEGA1,
++ ARCH_AVRXMEGA2,
++ ARCH_AVRXMEGA3,
++ ARCH_AVRXMEGA4,
++ ARCH_AVRXMEGA5,
++ ARCH_AVRXMEGA6,
++ ARCH_AVRXMEGA7
+ };
+
+ struct mcu_type_s {
+@@ -118,10 +125,18 @@ extern GTY(()) section *progmem_section;
+ #define AVR_HAVE_RAMPZ (avr_current_arch->have_elpm)
+ #define AVR_HAVE_EIJMP_EICALL (avr_current_arch->have_eijmp_eicall)
+ #define AVR_HAVE_8BIT_SP (avr_current_device->short_sp || TARGET_TINY_STACK)
++#define AVR_XMEGA (avr_current_arch->xmega)
++#define AVR_HAVE_RAMPX_Y_D (avr_current_arch->have_rampx_y_d)
+
+ #define AVR_2_BYTE_PC (!AVR_HAVE_EIJMP_EICALL)
+ #define AVR_3_BYTE_PC (AVR_HAVE_EIJMP_EICALL)
+
++#define AVR_IO_OFFSET (AVR_XMEGA ? 0 : 0x20)
++#define AVR_RAMPD_ADDR (AVR_XMEGA ? 0x38 : 0)
++#define AVR_RAMPX_ADDR (AVR_XMEGA ? 0x39 : 0)
++#define AVR_RAMPY_ADDR (AVR_XMEGA ? 0x3A : 0)
++#define AVR_RAMPZ_ADDR (AVR_XMEGA ? 0x3B : 0x5B)
++#define AVR_SREG_ADDR (AVR_XMEGA ? 0x3F: 0x5F)
+ #define TARGET_VERSION fprintf (stderr, " (GNU assembler syntax)");
+
+ #define OVERRIDE_OPTIONS avr_override_options ()
+@@ -842,6 +857,10 @@ struct GTY(()) machine_function
+ as specified by the "signal" attribute. */
+ int is_signal;
+
++ /* 'true' - if current function is a signal function
++ as specified by the "nmi" attribute. */
++ int is_nmi;
++
+ /* 'true' - if current function is a 'task' function
+ as specified by the "OS_task" attribute. */
+ int is_OS_task;
+diff -Naurp gcc/config/avr/avr.md gcc/config/avr/avr.md
+--- gcc/config/avr/avr.md 2011-09-02 11:40:55.000000000 +0300
++++ gcc/config/avr/avr.md 2011-09-02 11:40:01.000000000 +0300
+@@ -49,9 +49,6 @@
+ (TMP_REGNO 0) ; temporary register r0
+ (ZERO_REGNO 1) ; zero register r1
+
+- (SREG_ADDR 0x5F)
+- (RAMPZ_ADDR 0x5B)
+-
+ (UNSPEC_STRLEN 0)
+ (UNSPEC_INDEX_JMP 1)
+ (UNSPEC_SEI 2)
+@@ -2962,7 +2959,8 @@
+ "(optimize > 0)"
+ {
+ operands[2] = GEN_INT (exact_log2 (~INTVAL (operands[1]) & 0xff));
+- return AS2 (cbi,%m0-0x20,%2);
++ operands[3] = GEN_INT(AVR_IO_OFFSET);
++ return AS2 (cbi,%0-%3,%2);
+ }
+ [(set_attr "length" "1")
+ (set_attr "cc" "none")])
+@@ -2974,7 +2972,8 @@
+ "(optimize > 0)"
+ {
+ operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1]) & 0xff));
+- return AS2 (sbi,%m0-0x20,%2);
++ operands[3] = GEN_INT(AVR_IO_OFFSET);
++ return AS2 (sbi,%0-%3,%2);
+ }
+ [(set_attr "length" "1")
+ (set_attr "cc" "none")])
+diff -Naurp gcc/config/avr/libgcc.S gcc/config/avr/libgcc.S
+--- gcc/config/avr/libgcc.S 2011-09-02 11:40:55.000000000 +0300
++++ gcc/config/avr/libgcc.S 2011-09-02 11:40:01.000000000 +0300
+@@ -637,11 +637,19 @@ __prologue_saves__:
+ in r29,__SP_H__
+ sub r28,r26
+ sbc r29,r27
++
++/* Restore stack pointer. */
++#if defined (__AVR_XMEGA__)
++ out __SP_L__,r28
++ out __SP_H__,r29
++#else
+ in __tmp_reg__,__SREG__
+ cli
+ out __SP_H__,r29
+ out __SREG__,__tmp_reg__
+ out __SP_L__,r28
++#endif
++
+ #if defined (__AVR_HAVE_EIJMP_EICALL__)
+ eijmp
+ #else
+@@ -679,11 +687,18 @@ __epilogue_restores__:
+ ldd r27,Y+1
+ add r28,r30
+ adc r29,__zero_reg__
++
++/* Restore stack pointer. */
++#if defined(__AVR_XMEGA__)
++ out __SP_L__,r28
++ out __SP_H__,r29
++#else
+ in __tmp_reg__,__SREG__
+ cli
+ out __SP_H__,r29
+ out __SREG__,__tmp_reg__
+ out __SP_L__,r28
++#endif
+ mov_l r28, r26
+ mov_h r29, r27
+ ret
+diff -Naurp gcc/config/avr/predicates.md gcc/config/avr/predicates.md
+--- gcc/config/avr/predicates.md 2009-12-24 22:53:57.000000000 +0300
++++ gcc/config/avr/predicates.md 2011-09-02 11:40:01.000000000 +0300
+@@ -45,17 +45,23 @@
+ ;; Return true if OP is a valid address for lower half of I/O space.
+ (define_predicate "low_io_address_operand"
+ (and (match_code "const_int")
+- (match_test "IN_RANGE((INTVAL (op)), 0x20, 0x3F)")))
++ (if_then_else (match_test "AVR_XMEGA")
++ (match_test "IN_RANGE((INTVAL (op)), 0x00, 0x1F)")
++ (match_test "IN_RANGE((INTVAL (op)), 0x20, 0x3F)"))))
+
+ ;; Return true if OP is a valid address for high half of I/O space.
+ (define_predicate "high_io_address_operand"
+ (and (match_code "const_int")
+- (match_test "IN_RANGE((INTVAL (op)), 0x40, 0x5F)")))
++ (if_then_else (match_test "AVR_XMEGA")
++ (match_test "IN_RANGE((INTVAL (op)), 0x20, 0x3F)")
++ (match_test "IN_RANGE((INTVAL (op)), 0x40, 0x5F)"))))
+
+ ;; Return true if OP is a valid address of I/O space.
+ (define_predicate "io_address_operand"
+ (and (match_code "const_int")
+- (match_test "IN_RANGE((INTVAL (op)), 0x20, (0x60 - GET_MODE_SIZE(mode)))")))
++ (if_then_else (match_test "AVR_XMEGA")
++ (match_test "IN_RANGE((INTVAL (op)), 0x0, (0x40 - GET_MODE_SIZE(mode)))")
++ (match_test "IN_RANGE((INTVAL (op)), 0x20, (0x60 - GET_MODE_SIZE(mode)))"))))
+
+ ;; Return 1 if OP is the zero constant for MODE.
+ (define_predicate "const0_operand"
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-02 11:40:55.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-02 11:41:56.000000000 +0300
+@@ -107,8 +107,8 @@ fp-bit.c: $(srcdir)/config/fp-bit.c $(sr
+
+ FPBIT = fp-bit.c
+
+-MULTILIB_OPTIONS = mmcu=avr2/mmcu=avr25/mmcu=avr3/mmcu=avr31/mmcu=avr35/mmcu=avr4/mmcu=avr5/mmcu=avr51/mmcu=avr6
+-MULTILIB_DIRNAMES = avr2 avr25 avr3 avr31 avr35 avr4 avr5 avr51 avr6
++MULTILIB_OPTIONS = mmcu=avr2/mmcu=avr25/mmcu=avr3/mmcu=avr31/mmcu=avr35/mmcu=avr4/mmcu=avr5/mmcu=avr51/mmcu=avr6/mmcu=avrxmega2/mmcu=avrxmega4/mmcu=avrxmega5/mmcu=avrxmega6/mmcu=avrxmega7
++MULTILIB_DIRNAMES = avr2 avr25 avr3 avr31 avr35 avr4 avr5 avr51 avr6 avrxmega2 avrxmega4 avrxmega5 avrxmega6 avrxmega7
+
+ # The many avr2 matches are not listed here - this is the default.
+ MULTILIB_MATCHES = \
+@@ -223,7 +223,25 @@ MULTILIB_MATCHES = \
+ mmcu?avr51=mmcu?m3000s \
+ mmcu?avr51=mmcu?m3001b \
+ mmcu?avr6=mmcu?atmega2560 \
+- mmcu?avr6=mmcu?atmega2561
++ mmcu?avr6=mmcu?atmega2561 \
++ mmcu?avrxmega2=mmcu?atxmega16a4 \
++ mmcu?avrxmega2=mmcu?atxmega16d4 \
++ mmcu?avrxmega2=mmcu?atxmega16x1 \
++ mmcu?avrxmega2=mmcu?atxmega32d4 \
++ mmcu?avrxmega2=mmcu?atxmega32a4 \
++ mmcu?avrxmega4=mmcu?atxmega64a3 \
++ mmcu?avrxmega4=mmcu?atxmega64d3 \
++ mmcu?avrxmega5=mmcu?atxmega64a1 \
++ mmcu?avrxmega5=mmcu?atxmega64a1u \
++ mmcu?avrxmega6=mmcu?atxmega128a3 \
++ mmcu?avrxmega6=mmcu?atxmega128d3 \
++ mmcu?avrxmega6=mmcu?atxmega192a3 \
++ mmcu?avrxmega6=mmcu?atxmega192d3 \
++ mmcu?avrxmega6=mmcu?atxmega256a3 \
++ mmcu?avrxmega6=mmcu?atxmega256a3b \
++ mmcu?avrxmega6=mmcu?atxmega256d3 \
++ mmcu?avrxmega7=mmcu?atxmega128a1 \
++ mmcu?avrxmega7=mmcu?atxmega128a1u
+
+ MULTILIB_EXCEPTIONS =
+
--- /dev/null
+diff -Naurp gcc/config/avr/avr.c gcc/config/avr/avr.c
+--- gcc/config/avr/avr.c 2011-09-02 11:45:05.000000000 +0300
++++ gcc/config/avr/avr.c 2011-09-02 11:46:03.000000000 +0300
+@@ -232,8 +232,8 @@ avr_override_options (void)
+ avr_current_arch = &avr_arch_types[avr_current_device->arch];
+ avr_extra_arch_macro = avr_current_device->macro;
+
+- tmp_reg_rtx = gen_rtx_REG (QImode, TMP_REGNO);
+- zero_reg_rtx = gen_rtx_REG (QImode, ZERO_REGNO);
++ tmp_reg_rtx = gen_rtx_REG (QImode, AVR_TINY ? TMP_REGNO_AVRTINY10 : TMP_REGNO);
++ zero_reg_rtx = gen_rtx_REG (QImode, AVR_TINY ? ZERO_REGNO_AVRTINY10 : ZERO_REGNO);
+
+ init_machine_status = avr_init_machine_status;
+ }
+@@ -1641,7 +1641,7 @@ avr_simplify_comparison_p (enum machine_
+ int
+ function_arg_regno_p(int r)
+ {
+- return (r >= 8 && r <= 25);
++ return (AVR_TINY ? r >= 20 && r <= 25 : r >= 8 && r <= 25);
+ }
+
+ /* Initializing the variable cum for the state at the beginning
+@@ -1651,7 +1651,11 @@ void
+ init_cumulative_args (CUMULATIVE_ARGS *cum, tree fntype, rtx libname,
+ tree fndecl ATTRIBUTE_UNUSED)
+ {
++ if (AVR_TINY)
++ cum->nregs = 6;
++ else
+ cum->nregs = 18;
++
+ cum->regno = FIRST_CUM_REG;
+ if (!libname && fntype)
+ {
+@@ -1675,9 +1679,8 @@ avr_num_arg_regs (enum machine_mode mode
+ else
+ size = GET_MODE_SIZE (mode);
+
+- /* Align all function arguments to start in even-numbered registers.
++ /* if not AVR_TINY, Align all function arguments to start in even-numbered registers.
+ Odd-sized arguments leave holes above them. */
+-
+ return (size + 1) & ~1;
+ }
+
+@@ -2009,10 +2012,20 @@ out_movqi_r_mr (rtx insn, rtx op[], int
+ fatal_insn ("incorrect insn:",insn);
+
+ if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (src)))
+- return *l = 3, (AS2 (adiw,r28,%o1-63) CR_TAB
++ return *l = 3, AVR_TINY ? (AS2 (subi,r28,lo8(-(%o1-63))) CR_TAB
++ AS2 (sbci,r29,hi8(-(%o1-63))) CR_TAB
++ AS2 (subi,r28,lo8(-63)) CR_TAB
++ AS2 (sbci,r29,hi8(-63)) CR_TAB
++ AS2 (ld,%0,Y) CR_TAB
++ AS2 (subi,r28,lo8(63)) CR_TAB
++ AS2 (sbci,r29,hi8(63)) CR_TAB
++ AS2 (subi,r28,lo8(%o1-63)) CR_TAB
++ AS2 (sbci,r29,hi8(%o1-63)))
++ : (AS2 (adiw,r28,%o1-63) CR_TAB
+ AS2 (ldd,%0,Y+63) CR_TAB
+ AS2 (sbiw,r28,%o1-63));
+
++
+ return *l = 5, (AS2 (subi,r28,lo8(-%o1)) CR_TAB
+ AS2 (sbci,r29,hi8(-%o1)) CR_TAB
+ AS2 (ld,%0,Y) CR_TAB
+@@ -2025,15 +2038,38 @@ out_movqi_r_mr (rtx insn, rtx op[], int
+ it but I have this situation with extremal optimizing options. */
+ if (reg_overlap_mentioned_p (dest, XEXP (x,0))
+ || reg_unused_after (insn, XEXP (x,0)))
+- return *l = 2, (AS2 (adiw,r26,%o1) CR_TAB
++ return *l = 2, AVR_TINY ? (AS2 (subi,r26,lo8(-(%o1))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o1))) CR_TAB
++ AS2 (ld,%0,X))
++ : (AS2 (adiw,r26,%o1) CR_TAB
+ AS2 (ld,%0,X));
+
+- return *l = 3, (AS2 (adiw,r26,%o1) CR_TAB
++ return *l = 3, AVR_TINY ? (AS2 (subi,r26,lo8(-(%o1))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o1))) CR_TAB
++ AS2 (ld,%0,X) CR_TAB
++ AS2 (subi,r26,lo8(%o1)) CR_TAB
++ AS2 (sbci,r27,hi8(%o1)))
++ : (AS2 (adiw,r26,%o1) CR_TAB
+ AS2 (ld,%0,X) CR_TAB
+ AS2 (sbiw,r26,%o1));
+ }
++
+ *l = 1;
+- return AS2 (ldd,%0,%1);
++ op[2] = XEXP(x, 0);
++ if(REGNO(op[2]) == REG_Y)
++ return AVR_TINY ? ( AS2 (subi,%A2,lo8(-(%o1))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o1))) CR_TAB
++ AS2 (ld,%0,Y) CR_TAB
++ AS2 (subi,%A2,lo8(%o1)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o1)))
++ : AS2 (ldd,%0,%1);
++ if(REGNO(op[2]) == REG_Z)
++ return AVR_TINY ? ( AS2 (subi,%A2,lo8(-(%o1))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o1))) CR_TAB
++ AS2 (ld,%0,Z) CR_TAB
++ AS2 (subi,%A2,lo8(%o1)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o1)))
++ : AS2 (ldd,%0,%1);
+ }
+ *l = 1;
+ return AS2 (ld,%0,%1);
+@@ -2073,14 +2109,34 @@ out_movhi_r_mr (rtx insn, rtx op[], int
+ AS2 (ld,%B0,X));
+ }
+ *l = 3;
+- return (AS2 (ld,%A0,X+) CR_TAB
++ return AVR_TINY ? (AS2 (ld,%A0,X+) CR_TAB
++ AS2 (ld,%B0,X) CR_TAB
++ AS2 (subi,r26,lo8(1)) CR_TAB
++ AS2 (sbci,r27,hi8(1)))
++ : (AS2 (ld,%A0,X+) CR_TAB
+ AS2 (ld,%B0,X) CR_TAB
+ AS2 (sbiw,r26,1));
+ }
+ else /* (R) */
+ {
+ *l = 2;
+- return (AS2 (ld,%A0,%1) CR_TAB
++ if(reg_base == REG_Y)
++ return AVR_TINY ? (AS2 (ld,%A0,%1) CR_TAB
++ AS2 (subi,r28,lo8((-1))) CR_TAB
++ AS2 (sbci,r29,hi8((-1))) CR_TAB
++ AS2 (ld,%B0,%1) CR_TAB
++ AS2 (subi,r28,lo8(1)) CR_TAB
++ AS2 (sbci,r29,hi8(1)))
++ : (AS2 (ld,%A0,%1) CR_TAB
++ AS2 (ldd,%B0,%1+1));
++ if(reg_base == REG_Z)
++ return AVR_TINY ? (AS2 (ld,%A0,%1) CR_TAB
++ AS2 (subi,r30,lo8((-1))) CR_TAB
++ AS2 (sbci,r31,hi8((-1))) CR_TAB
++ AS2 (ld,%B0,%1) CR_TAB
++ AS2 (subi,r30,lo8(1)) CR_TAB
++ AS2 (sbci,r31,hi8(1)))
++ : (AS2 (ld,%A0,%1) CR_TAB
+ AS2 (ldd,%B0,%1+1));
+ }
+ }
+@@ -2095,12 +2151,30 @@ out_movhi_r_mr (rtx insn, rtx op[], int
+ fatal_insn ("incorrect insn:",insn);
+
+ if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (src)))
+- return *l = 4, (AS2 (adiw,r28,%o1-62) CR_TAB
++ return *l = 4, AVR_TINY ? (AS2 (subi,r28,lo8(-(%o1-62))) CR_TAB
++ AS2 (sbci,r29,hi8(-(%o1-62))) CR_TAB
++ AS2 (subi,r28,lo8(-62)) CR_TAB
++ AS2 (sbci,r29,hi8(-62)) CR_TAB
++ AS2 (ld,%A0,Y+) CR_TAB
++ AS2 (ld,%B0,Y) CR_TAB
++ AS2 (subi,r28,lo8(63)) CR_TAB
++ AS2 (sbci,r29,hi8(63)) CR_TAB
++ AS2 (subi,r28,lo8(%o1-62)) CR_TAB
++ AS2 (sbci,r29,hi8(%o1-62)))
++ : (AS2 (adiw,r28,%o1-62) CR_TAB
+ AS2 (ldd,%A0,Y+62) CR_TAB
+ AS2 (ldd,%B0,Y+63) CR_TAB
+ AS2 (sbiw,r28,%o1-62));
+
+- return *l = 6, (AS2 (subi,r28,lo8(-%o1)) CR_TAB
++ return *l = 6, AVR_TINY ? (AS2 (subi,r28,lo8(-%o1)) CR_TAB
++ AS2 (sbci,r29,hi8(-%o1)) CR_TAB
++ AS2 (ld,%A0,Y+) CR_TAB
++ AS2 (ld,%B0,Y) CR_TAB
++ AS2 (subi,r28,lo8(1)) CR_TAB
++ AS2 (sbci,r29,hi8(1)) CR_TAB
++ AS2 (subi,r28,lo8(%o1)) CR_TAB
++ AS2 (sbci,r29,hi8(%o1)))
++ : (AS2 (subi,r28,lo8(-%o1)) CR_TAB
+ AS2 (sbci,r29,hi8(-%o1)) CR_TAB
+ AS2 (ld,%A0,Y) CR_TAB
+ AS2 (ldd,%B0,Y+1) CR_TAB
+@@ -2115,12 +2189,23 @@ out_movhi_r_mr (rtx insn, rtx op[], int
+
+ *l = 4;
+ if (reg_base == reg_dest)
+- return (AS2 (adiw,r26,%o1) CR_TAB
++ return AVR_TINY ? (AS2 (subi,r26,lo8(-%o1)) CR_TAB
++ AS2 (sbci,r27,hi8(-%o1)) CR_TAB
++ AS2 (ld,__tmp_reg__,X+) CR_TAB
++ AS2 (ld,%B0,X) CR_TAB
++ AS2 (mov,%A0,__tmp_reg__))
++ : (AS2 (adiw,r26,%o1) CR_TAB
+ AS2 (ld,__tmp_reg__,X+) CR_TAB
+ AS2 (ld,%B0,X) CR_TAB
+ AS2 (mov,%A0,__tmp_reg__));
+
+- return (AS2 (adiw,r26,%o1) CR_TAB
++ return AVR_TINY ? (AS2 (subi,r26,lo8(-%o1)) CR_TAB
++ AS2 (sbci,r27,hi8(-%o1)) CR_TAB
++ AS2 (ld,%A0,X+) CR_TAB
++ AS2 (ld,%B0,X) CR_TAB
++ AS2 (subi,r26,lo8(%o1+1)) CR_TAB
++ AS2 (sbci,r27,hi8(%o1+1)))
++ : (AS2 (adiw,r26,%o1) CR_TAB
+ AS2 (ld,%A0,X+) CR_TAB
+ AS2 (ld,%B0,X) CR_TAB
+ AS2 (sbiw,r26,%o1+1));
+@@ -2129,14 +2214,54 @@ out_movhi_r_mr (rtx insn, rtx op[], int
+ if (reg_base == reg_dest)
+ {
+ *l = 3;
+- return (AS2 (ldd,__tmp_reg__,%A1) CR_TAB
++ op[2] = XEXP(base, 0);
++
++ if(REGNO(op[2]) == REG_Y)
++ return AVR_TINY ? ( AS2 (subi,%A2,lo8(-(%o1))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o1))) CR_TAB
++ AS2 (ld,__tmp_reg__,Y+) CR_TAB
++ AS2 (ld,%B0,Y) CR_TAB
++ AS2 (subi,%A2,lo8(%o1+1)) CR_TAB
++ AS2 (subi,%B2,hi8(%o1+1)) CR_TAB
++ AS2 (mov,%A0,__tmp_reg__))
++ : (AS2 (ldd,__tmp_reg__,%A1) CR_TAB
++ AS2 (ldd,%B0,%B1) CR_TAB
++ AS2 (mov,%A0,__tmp_reg__));
++ if(REGNO(op[2]) == REG_Z)
++ return AVR_TINY ? ( AS2 (subi,%A2,lo8(-(%o1))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o1))) CR_TAB
++ AS2 (ld,__tmp_reg__,Z+) CR_TAB
++ AS2 (ld,%B0,Z) CR_TAB
++ AS2 (subi,%A2,lo8(%o1+1)) CR_TAB
++ AS2 (subi,%B2,hi8(%o1+1)) CR_TAB
++ AS2 (mov,%A0,__tmp_reg__))
++ : (AS2 (ldd,__tmp_reg__,%A1) CR_TAB
+ AS2 (ldd,%B0,%B1) CR_TAB
+ AS2 (mov,%A0,__tmp_reg__));
+ }
+-
+ *l = 2;
+- return (AS2 (ldd,%A0,%A1) CR_TAB
++
++ op[2] = XEXP(base, 0);
++
++ if(REGNO(op[2]) == REG_Y)
++ return AVR_TINY ? ( AS2 (subi,%A2,lo8(-(%o1))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o1))) CR_TAB
++ AS2 (ld,%A0,Y+) CR_TAB
++ AS2 (ld,%B0,Y) CR_TAB
++ AS2 (subi,%A2,lo8(%o1+1)) CR_TAB
++ AS2 (subi,%B2,hi8(%o1+1)))
++ : (AS2 (ldd,%A0,%A1) CR_TAB
++ AS2 (ldd,%B0,%B1));
++ if(REGNO(op[2]) == REG_Z)
++ return AVR_TINY ? ( AS2 (subi,%A2,lo8(-(%o1))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o1))) CR_TAB
++ AS2 (ld,%A0,Z+) CR_TAB
++ AS2 (ld,%B0,Z) CR_TAB
++ AS2 (subi,%A2,lo8(%o1+1)) CR_TAB
++ AS2 (subi,%B2,hi8(%o1+1)))
++ : (AS2 (ldd,%A0,%A1) CR_TAB
+ AS2 (ldd,%B0,%B1));
++
+ }
+ else if (GET_CODE (base) == PRE_DEC) /* (--R) */
+ {
+@@ -2148,7 +2273,13 @@ out_movhi_r_mr (rtx insn, rtx op[], int
+ if (REGNO (XEXP (base, 0)) == REG_X)
+ {
+ *l = 4;
+- return (AS2 (sbiw,r26,2) CR_TAB
++ return AVR_TINY ? (AS2 (subi,r26,lo8(2)) CR_TAB
++ AS2 (sbci,r27,hi8(2)) CR_TAB
++ AS2 (ld,%A0,X+) CR_TAB
++ AS2 (ld,%B0,X) CR_TAB
++ AS2 (subi,r26,lo8(1)) CR_TAB
++ AS2 (sbci,r27,hi8(1)))
++ : (AS2 (sbiw,r26,2) CR_TAB
+ AS2 (ld,%A0,X+) CR_TAB
+ AS2 (ld,%B0,X) CR_TAB
+ AS2 (sbiw,r26,1));
+@@ -2156,7 +2287,16 @@ out_movhi_r_mr (rtx insn, rtx op[], int
+ else
+ {
+ *l = 3;
+- return (AS2 (sbiw,%r1,2) CR_TAB
++ //FIXME:check the code once again for AVR_TINY
++ return AVR_TINY ? (AS2 (subi,%A1,lo8(3)) CR_TAB
++ AS2 (sbci,%B1,hi8(3)) CR_TAB
++ AS2 (ld,%A0,%p1) CR_TAB
++ AS2 (subi,%A1,lo8(-1)) CR_TAB
++ AS2 (sbci,%B1,hi8(-1)) CR_TAB
++ AS2 (ld,%B0,%p1) CR_TAB
++ AS2 (subi,%A1,lo8(1)) CR_TAB
++ AS2 (sbci,%B1,hi8(1)))
++ : (AS2 (sbiw,%r1,2) CR_TAB
+ AS2 (ld,%A0,%p1) CR_TAB
+ AS2 (ldd,%B0,%p1+1));
+ }
+@@ -2212,13 +2352,23 @@ out_movsi_r_mr (rtx insn, rtx op[], int
+ {
+ if (reg_dest == REG_X)
+ /* "ld r26,-X" is undefined */
+- return *l=7, (AS2 (adiw,r26,3) CR_TAB
++ return *l=7, AVR_TINY ? (AS2 (subi,r26,lo8(-3)) CR_TAB
++ AS2 (sbci,r27,hi8(-3)) CR_TAB
++ AS2 (ld,r29,X) CR_TAB
++ AS2 (ld,r28,-X) CR_TAB
++ AS2 (ld,__tmp_reg__,-X) CR_TAB
++ AS2 (subi,r26,lo8(1)) CR_TAB
++ AS2 (sbci,r27,hi8(1)) CR_TAB
++ AS2 (ld,r26,X) CR_TAB
++ AS2 (mov,r27,__tmp_reg__))
++ : (AS2 (adiw,r26,3) CR_TAB
+ AS2 (ld,r29,X) CR_TAB
+ AS2 (ld,r28,-X) CR_TAB
+ AS2 (ld,__tmp_reg__,-X) CR_TAB
+ AS2 (sbiw,r26,1) CR_TAB
+ AS2 (ld,r26,X) CR_TAB
+ AS2 (mov,r27,__tmp_reg__));
++
+ else if (reg_dest == REG_X - 2)
+ return *l=5, (AS2 (ld,%A0,X+) CR_TAB
+ AS2 (ld,%B0,X+) CR_TAB
+@@ -2231,7 +2381,13 @@ out_movsi_r_mr (rtx insn, rtx op[], int
+ AS2 (ld,%C0,X+) CR_TAB
+ AS2 (ld,%D0,X));
+ else
+- return *l=5, (AS2 (ld,%A0,X+) CR_TAB
++ return *l=5, AVR_TINY ? (AS2 (ld,%A0,X+) CR_TAB
++ AS2 (ld,%B0,X+) CR_TAB
++ AS2 (ld,%C0,X+) CR_TAB
++ AS2 (ld,%D0,X) CR_TAB
++ AS2 (subi,r26,lo8(3)) CR_TAB
++ AS2 (sbci,r27,hi8(3)))
++ : (AS2 (ld,%A0,X+) CR_TAB
+ AS2 (ld,%B0,X+) CR_TAB
+ AS2 (ld,%C0,X+) CR_TAB
+ AS2 (ld,%D0,X) CR_TAB
+@@ -2240,22 +2396,97 @@ out_movsi_r_mr (rtx insn, rtx op[], int
+ else
+ {
+ if (reg_dest == reg_base)
+- return *l=5, (AS2 (ldd,%D0,%1+3) CR_TAB
++ {
++ if(reg_base == REG_Y)
++ return *l=5, AVR_TINY ? (AS2 (subi,r28,lo8(-3)) CR_TAB
++ AS2 (sbci,r29,hi8(-3)) CR_TAB
++ AS2 (ld,%D0,Y) CR_TAB
++ AS2 (ld,%C0,-Y) CR_TAB
++ AS2 (subi,r28,lo8(1)) CR_TAB
++ AS2 (sbci,r29,hi8(1)) CR_TAB
++ AS2 (ld,__tmp_reg__,%1) CR_TAB
++ AS2 (subi,r28,lo8(1)) CR_TAB
++ AS2 (sbci,r29,hi8(1)) CR_TAB
++ AS2 (ld,%A0,%1) CR_TAB
++ AS2 (mov,%B0,__tmp_reg__))
++ : (AS2 (ldd,%D0,%1+3) CR_TAB
++ AS2 (ldd,%C0,%1+2) CR_TAB
++ AS2 (ldd,__tmp_reg__,%1+1) CR_TAB
++ AS2 (ld,%A0,%1) CR_TAB
++ AS2 (mov,%B0,__tmp_reg__));
++ if(reg_base == REG_Z)
++ return *l=5, AVR_TINY ? (AS2 (subi,r30,lo8(-3)) CR_TAB
++ AS2 (sbci,r31,hi8(-3)) CR_TAB
++ AS2 (ld,%D0,Z) CR_TAB
++ AS2 (ld,%C0,-Z) CR_TAB
++ AS2 (subi,r30,lo8(1)) CR_TAB
++ AS2 (sbci,r31,hi8(1)) CR_TAB
++ AS2 (ld,__tmp_reg__,%1) CR_TAB
++ AS2 (subi,r30,lo8(1)) CR_TAB
++ AS2 (sbci,r31,hi8(1)) CR_TAB
++ AS2 (ld,%A0,%1) CR_TAB
++ AS2 (mov,%B0,__tmp_reg__))
++ : (AS2 (ldd,%D0,%1+3) CR_TAB
+ AS2 (ldd,%C0,%1+2) CR_TAB
+ AS2 (ldd,__tmp_reg__,%1+1) CR_TAB
+ AS2 (ld,%A0,%1) CR_TAB
+ AS2 (mov,%B0,__tmp_reg__));
++ }
++
+ else if (reg_base == reg_dest + 2)
+- return *l=5, (AS2 (ld ,%A0,%1) CR_TAB
++ {
++ if(reg_base == REG_Y)
++ return *l=5, AVR_TINY ? (AS2 (ld ,%A0,Y+) CR_TAB
++ AS2 (ld,%B0,Y+) CR_TAB
++ AS2 (ld,__tmp_reg__,Y+) CR_TAB
++ AS2 (ld,%D0,Y) CR_TAB
++ AS2 (subi,r28,lo8(3)) CR_TAB
++ AS2 (sbci,r29,hi8(3)) CR_TAB
++ AS2 (mov,%C0,__tmp_reg__))
++ : (AS2 (ld ,%A0,%1) CR_TAB
++ AS2 (ldd,%B0,%1+1) CR_TAB
++ AS2 (ldd,__tmp_reg__,%1+2) CR_TAB
++ AS2 (ldd,%D0,%1+3) CR_TAB
++ AS2 (mov,%C0,__tmp_reg__));
++ if(reg_base == REG_Z)
++ return *l=5, AVR_TINY ? (AS2 (ld ,%A0,Z+) CR_TAB
++ AS2 (ld,%B0,Z+) CR_TAB
++ AS2 (ld,__tmp_reg__,Z+) CR_TAB
++ AS2 (ld,%D0,Z) CR_TAB
++ AS2 (subi,r30,lo8(3)) CR_TAB
++ AS2 (sbci,r31,hi8(3)) CR_TAB
++ AS2 (mov,%C0,__tmp_reg__))
++ : (AS2 (ld ,%A0,%1) CR_TAB
+ AS2 (ldd,%B0,%1+1) CR_TAB
+ AS2 (ldd,__tmp_reg__,%1+2) CR_TAB
+ AS2 (ldd,%D0,%1+3) CR_TAB
+ AS2 (mov,%C0,__tmp_reg__));
++ }
+ else
+- return *l=4, (AS2 (ld ,%A0,%1) CR_TAB
++ {
++ if(reg_base == REG_Y)
++ return *l=4, AVR_TINY ? (AS2 (ld ,%A0,Y+) CR_TAB
++ AS2 (ld,%B0,Y+) CR_TAB
++ AS2 (ld,%C0,Y+) CR_TAB
++ AS2 (ld,%D0,Y) CR_TAB
++ AS2 (subi,r28,lo8(3)) CR_TAB
++ AS2 (sbci,r29,hi8(3)))
++ : (AS2 (ld ,%A0,%1) CR_TAB
+ AS2 (ldd,%B0,%1+1) CR_TAB
+ AS2 (ldd,%C0,%1+2) CR_TAB
+ AS2 (ldd,%D0,%1+3));
++ if(reg_base == REG_Z)
++ return *l=4, AVR_TINY ? (AS2 (ld ,%A0,Z+) CR_TAB
++ AS2 (ld,%B0,Z+) CR_TAB
++ AS2 (ld,%C0,Z+) CR_TAB
++ AS2 (ld,%D0,Z) CR_TAB
++ AS2 (subi,r30,lo8(3)) CR_TAB
++ AS2 (sbci,r31,hi8(3)))
++ : (AS2 (ld ,%A0,%1) CR_TAB
++ AS2 (ldd,%B0,%1+1) CR_TAB
++ AS2 (ldd,%C0,%1+2) CR_TAB
++ AS2 (ldd,%D0,%1+3));
++ }
+ }
+ }
+ else if (GET_CODE (base) == PLUS) /* (R + i) */
+@@ -2268,14 +2499,36 @@ out_movsi_r_mr (rtx insn, rtx op[], int
+ fatal_insn ("incorrect insn:",insn);
+
+ if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (src)))
+- return *l = 6, (AS2 (adiw,r28,%o1-60) CR_TAB
++ return *l = 6, AVR_TINY ? (AS2 (subi,r28,lo8(-(%o1-60))) CR_TAB
++ AS2 (sbci,r29,hi8(-(%o1-60))) CR_TAB
++ AS2 (subi,r28,lo8(-60)) CR_TAB
++ AS2 (sbci,r29,hi8(-60)) CR_TAB
++ AS2 (ld,%A0,Y+) CR_TAB
++ AS2 (ld,%B0,Y+) CR_TAB
++ AS2 (ld,%C0,Y+) CR_TAB
++ AS2 (ld,%D0,Y) CR_TAB
++ AS2 (subi,r28,lo8(63)) CR_TAB
++ AS2 (sbci,r29,hi8(63)) CR_TAB
++ AS2 (subi,r28,lo8(%o1-60)) CR_TAB
++ AS2 (sbci,r29,hi8(%o1-60)))
++ : (AS2 (adiw,r28,%o1-60) CR_TAB
+ AS2 (ldd,%A0,Y+60) CR_TAB
+ AS2 (ldd,%B0,Y+61) CR_TAB
+ AS2 (ldd,%C0,Y+62) CR_TAB
+ AS2 (ldd,%D0,Y+63) CR_TAB
+ AS2 (sbiw,r28,%o1-60));
+
+- return *l = 8, (AS2 (subi,r28,lo8(-%o1)) CR_TAB
++ return *l = 8, AVR_TINY ? (AS2 (subi,r28,lo8(-%o1)) CR_TAB
++ AS2 (sbci,r29,hi8(-%o1)) CR_TAB
++ AS2 (ld,%A0,Y+) CR_TAB
++ AS2 (ld,%B0,Y+) CR_TAB
++ AS2 (ld,%C0,Y+) CR_TAB
++ AS2 (ld,%D0,Y) CR_TAB
++ AS2 (subi,r28,lo8(3)) CR_TAB
++ AS2 (sbci,r29,hi8(3)) CR_TAB
++ AS2 (subi,r28,lo8(%o1)) CR_TAB
++ AS2 (sbci,r29,hi8(%o1)))
++ : (AS2 (subi,r28,lo8(-%o1)) CR_TAB
+ AS2 (sbci,r29,hi8(-%o1)) CR_TAB
+ AS2 (ld,%A0,Y) CR_TAB
+ AS2 (ldd,%B0,Y+1) CR_TAB
+@@ -2293,7 +2546,16 @@ out_movsi_r_mr (rtx insn, rtx op[], int
+ {
+ *l = 7;
+ /* "ld r26,-X" is undefined */
+- return (AS2 (adiw,r26,%o1+3) CR_TAB
++ return AVR_TINY ? (AS2 (subi,r26,lo8(-(%o1+3))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o1+3))) CR_TAB
++ AS2 (ld,r29,X) CR_TAB
++ AS2 (ld,r28,-X) CR_TAB
++ AS2 (ld,__tmp_reg__,-X) CR_TAB
++ AS2 (subi,r26,lo8(1)) CR_TAB
++ AS2 (sbci,r27,hi8(1)) CR_TAB
++ AS2 (ld,r26,X) CR_TAB
++ AS2 (mov,r27,__tmp_reg__))
++ : (AS2 (adiw,r26,%o1+3) CR_TAB
+ AS2 (ld,r29,X) CR_TAB
+ AS2 (ld,r28,-X) CR_TAB
+ AS2 (ld,__tmp_reg__,-X) CR_TAB
+@@ -2303,14 +2565,29 @@ out_movsi_r_mr (rtx insn, rtx op[], int
+ }
+ *l = 6;
+ if (reg_dest == REG_X - 2)
+- return (AS2 (adiw,r26,%o1) CR_TAB
++ return AVR_TINY ? (AS2 (subi,r26,lo8(-(%o1))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o1))) CR_TAB
++ AS2 (ld,r24,X+) CR_TAB
++ AS2 (ld,r25,X+) CR_TAB
++ AS2 (ld,__tmp_reg__,X+) CR_TAB
++ AS2 (ld,r27,X) CR_TAB
++ AS2 (mov,r26,__tmp_reg__))
++ : (AS2 (adiw,r26,%o1) CR_TAB
+ AS2 (ld,r24,X+) CR_TAB
+ AS2 (ld,r25,X+) CR_TAB
+ AS2 (ld,__tmp_reg__,X+) CR_TAB
+ AS2 (ld,r27,X) CR_TAB
+ AS2 (mov,r26,__tmp_reg__));
+
+- return (AS2 (adiw,r26,%o1) CR_TAB
++ return AVR_TINY ? (AS2 (subi,r26,lo8(-(%o1))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o1))) CR_TAB
++ AS2 (ld,%A0,X+) CR_TAB
++ AS2 (ld,%B0,X+) CR_TAB
++ AS2 (ld,%C0,X+) CR_TAB
++ AS2 (ld,%D0,X) CR_TAB
++ AS2 (subi,r26,lo8(%o1+3)) CR_TAB
++ AS2 (sbci,r27,hi8(%o1+3)))
++ : (AS2 (adiw,r26,%o1) CR_TAB
+ AS2 (ld,%A0,X+) CR_TAB
+ AS2 (ld,%B0,X+) CR_TAB
+ AS2 (ld,%C0,X+) CR_TAB
+@@ -2318,18 +2595,99 @@ out_movsi_r_mr (rtx insn, rtx op[], int
+ AS2 (sbiw,r26,%o1+3));
+ }
+ if (reg_dest == reg_base)
+- return *l=5, (AS2 (ldd,%D0,%D1) CR_TAB
++ {
++ op[2] = XEXP(base, 0);
++
++ if(REGNO(op[2]) == REG_Y)
++ return *l=5, AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o1+4))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o1+4))) CR_TAB
++ AS2 (ld,%D0,-Y) CR_TAB
++ AS2 (ld,%C0,-Y) CR_TAB
++ AS2 (ld,__tmp_reg__,-Y) CR_TAB
++ AS2 (ld,%A0,-Y) CR_TAB
++ AS2 (subi,%A2,lo8(%o1)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o1)) CR_TAB
++ AS2 (mov,%B0,__tmp_reg__))
++ : (AS2 (ldd,%D0,%D1) CR_TAB
++ AS2 (ldd,%C0,%C1) CR_TAB
++ AS2 (ldd,__tmp_reg__,%B1) CR_TAB
++ AS2 (ldd,%A0,%A1) CR_TAB
++ AS2 (mov,%B0,__tmp_reg__));
++ if(REGNO(op[2]) == REG_Z)
++ return *l=5, AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o1+4))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o1+4))) CR_TAB
++ AS2 (ld,%D0,-Z) CR_TAB
++ AS2 (ld,%C0,-Z) CR_TAB
++ AS2 (ld,__tmp_reg__,-Z) CR_TAB
++ AS2 (ld,%A0,-Z) CR_TAB
++ AS2 (subi,%A2,lo8(%o1)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o1)) CR_TAB
++ AS2 (mov,%B0,__tmp_reg__))
++ : (AS2 (ldd,%D0,%D1) CR_TAB
+ AS2 (ldd,%C0,%C1) CR_TAB
+ AS2 (ldd,__tmp_reg__,%B1) CR_TAB
+ AS2 (ldd,%A0,%A1) CR_TAB
+ AS2 (mov,%B0,__tmp_reg__));
++ }
+ else if (reg_dest == reg_base - 2)
+- return *l=5, (AS2 (ldd,%A0,%A1) CR_TAB
++ {
++ op[2] = XEXP(base, 0);
++
++ if(REGNO(op[2]) == REG_Y)
++ return *l=5, AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o1))) CR_TAB
++ AS2 (subi,%B2,hi8(-(%o1))) CR_TAB
++ AS2 (ld,%A0,Y+) CR_TAB
++ AS2 (ld,%B0,Y+) CR_TAB
++ AS2 (ld,__tmp_reg__,Y+) CR_TAB
++ AS2 (ld,%D0,Y) CR_TAB
++ AS2 (subi,%A2,lo8(%o1+3)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o1+3)) CR_TAB
++ AS2 (mov,%C0,__tmp_reg__))
++ : (AS2 (ldd,%A0,%A1) CR_TAB
+ AS2 (ldd,%B0,%B1) CR_TAB
+ AS2 (ldd,__tmp_reg__,%C1) CR_TAB
+ AS2 (ldd,%D0,%D1) CR_TAB
+ AS2 (mov,%C0,__tmp_reg__));
+- return *l=4, (AS2 (ldd,%A0,%A1) CR_TAB
++ if(REGNO(op[2]) == REG_Z)
++ return *l=5, AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o1))) CR_TAB
++ AS2 (subi,%B2,hi8(-(%o1))) CR_TAB
++ AS2 (ld,%A0,Z+) CR_TAB
++ AS2 (ld,%B0,Z+) CR_TAB
++ AS2 (ld,__tmp_reg__,Z+) CR_TAB
++ AS2 (ld,%D0,Z) CR_TAB
++ AS2 (subi,%A2,lo8(%o1+3)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o1+3)) CR_TAB
++ AS2 (mov,%C0,__tmp_reg__))
++ : (AS2 (ldd,%A0,%A1) CR_TAB
++ AS2 (ldd,%B0,%B1) CR_TAB
++ AS2 (ldd,__tmp_reg__,%C1) CR_TAB
++ AS2 (ldd,%D0,%D1) CR_TAB
++ AS2 (mov,%C0,__tmp_reg__));
++ }
++ op[2] = XEXP(base, 0);
++ if(REGNO(op[2]) == REG_Y)
++ return *l=4, AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o1))) CR_TAB
++ AS2 (subi,%B2,hi8(-(%o1))) CR_TAB
++ AS2 (ld,%A0,Y+) CR_TAB
++ AS2 (ld,%B0,Y+) CR_TAB
++ AS2 (ld,%C0,Y+) CR_TAB
++ AS2 (ld,%D0,Y) CR_TAB
++ AS2 (subi,%A2,lo8(%o1+3)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o1+3)))
++ : (AS2 (ldd,%A0,%A1) CR_TAB
++ AS2 (ldd,%B0,%B1) CR_TAB
++ AS2 (ldd,%C0,%C1) CR_TAB
++ AS2 (ldd,%D0,%D1));
++ if(REGNO(op[2]) == REG_Z)
++ return *l=4, AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o1))) CR_TAB
++ AS2 (subi,%B2,hi8(-(%o1))) CR_TAB
++ AS2 (ld,%A0,Z+) CR_TAB
++ AS2 (ld,%B0,Z+) CR_TAB
++ AS2 (ld,%C0,Z+) CR_TAB
++ AS2 (ld,%D0,Z) CR_TAB
++ AS2 (subi,%A2,lo8(%o1+3)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o1+3)))
++ : (AS2 (ldd,%A0,%A1) CR_TAB
+ AS2 (ldd,%B0,%B1) CR_TAB
+ AS2 (ldd,%C0,%C1) CR_TAB
+ AS2 (ldd,%D0,%D1));
+@@ -2380,14 +2738,30 @@ out_movsi_mr_r (rtx insn, rtx op[], int
+ {
+ /* "st X+,r26" is undefined */
+ if (reg_unused_after (insn, base))
+- return *l=6, (AS2 (mov,__tmp_reg__,r27) CR_TAB
++ return *l=6, AVR_TINY ? (AS2 (mov,__tmp_reg__,r27) CR_TAB
++ AS2 (st,X,r26) CR_TAB
++ AS2 (subi,r26,lo8(-1)) CR_TAB
++ AS2 (sbci,r27,hi8(-1)) CR_TAB
++ AS2 (st,X+,__tmp_reg__) CR_TAB
++ AS2 (st,X+,r28) CR_TAB
++ AS2 (st,X,r29))
++ : (AS2 (mov,__tmp_reg__,r27) CR_TAB
+ AS2 (st,X,r26) CR_TAB
+ AS2 (adiw,r26,1) CR_TAB
+ AS2 (st,X+,__tmp_reg__) CR_TAB
+ AS2 (st,X+,r28) CR_TAB
+ AS2 (st,X,r29));
+ else
+- return *l=7, (AS2 (mov,__tmp_reg__,r27) CR_TAB
++ return *l=7, AVR_TINY ? (AS2 (mov,__tmp_reg__,r27) CR_TAB
++ AS2 (st,X,r26) CR_TAB
++ AS2 (subi,r26,lo8(-1)) CR_TAB
++ AS2 (sbci,r27,hi8(-1)) CR_TAB
++ AS2 (st,X+,__tmp_reg__) CR_TAB
++ AS2 (st,X+,r28) CR_TAB
++ AS2 (st,X,r29) CR_TAB
++ AS2 (subi,r26,lo8(3)) CR_TAB
++ AS2 (sbci,r27,hi8(3)))
++ : (AS2 (mov,__tmp_reg__,r27) CR_TAB
+ AS2 (st,X,r26) CR_TAB
+ AS2 (adiw,r26,1) CR_TAB
+ AS2 (st,X+,__tmp_reg__) CR_TAB
+@@ -2406,7 +2780,16 @@ out_movsi_mr_r (rtx insn, rtx op[], int
+ AS2 (st,%0,__tmp_reg__) CR_TAB
+ AS1 (clr,__zero_reg__));
+ else
+- return *l=8, (AS2 (mov,__zero_reg__,%C1) CR_TAB
++ return *l=8, AVR_TINY ? (AS2 (mov,__zero_reg__,%C1) CR_TAB
++ AS2 (mov,__tmp_reg__,%D1) CR_TAB
++ AS2 (st,%0+,%A1) CR_TAB
++ AS2 (st,%0+,%B1) CR_TAB
++ AS2 (st,%0+,__zero_reg__) CR_TAB
++ AS2 (st,%0,__tmp_reg__) CR_TAB
++ AS1 (clr,__zero_reg__) CR_TAB
++ AS2 (subi,r26,lo8(3)) CR_TAB
++ AS2 (sbci,r27,hi8(3)))
++ : (AS2 (mov,__zero_reg__,%C1) CR_TAB
+ AS2 (mov,__tmp_reg__,%D1) CR_TAB
+ AS2 (st,%0+,%A1) CR_TAB
+ AS2 (st,%0+,%B1) CR_TAB
+@@ -2415,18 +2798,44 @@ out_movsi_mr_r (rtx insn, rtx op[], int
+ AS1 (clr,__zero_reg__) CR_TAB
+ AS2 (sbiw,r26,3));
+ }
+- return *l=5, (AS2 (st,%0+,%A1) CR_TAB
++ return *l=5, AVR_TINY ? (AS2 (st,%0+,%A1) CR_TAB
++ AS2 (st,%0+,%B1) CR_TAB
++ AS2 (st,%0+,%C1) CR_TAB
++ AS2 (st,%0,%D1) CR_TAB
++ AS2 (subi,r26,lo8(3)) CR_TAB
++ AS2 (sbci,r27,hi8(3)))
++ : (AS2 (st,%0+,%A1) CR_TAB
+ AS2 (st,%0+,%B1) CR_TAB
+ AS2 (st,%0+,%C1) CR_TAB
+ AS2 (st,%0,%D1) CR_TAB
+ AS2 (sbiw,r26,3));
+ }
+ else
+- return *l=4, (AS2 (st,%0,%A1) CR_TAB
++ {
++ if(reg_base == REG_Y)
++ return *l=4, AVR_TINY ? (AS2 (st,Y+,%A1) CR_TAB
++ AS2 (st,Y+,%B1) CR_TAB
++ AS2 (st,Y+,%C1) CR_TAB
++ AS2 (st,Y,%D1) CR_TAB
++ AS2 (subi,r28,lo8(3)) CR_TAB
++ AS2 (sbci,r29,lo8(3)))
++ : (AS2 (st,%0,%A1) CR_TAB
++ AS2 (std,%0+1,%B1) CR_TAB
++ AS2 (std,%0+2,%C1) CR_TAB
++ AS2 (std,%0+3,%D1));
++ if(reg_base == REG_Z)
++ return *l=4, AVR_TINY ? (AS2 (st,Z+,%A1) CR_TAB
++ AS2 (st,Z+,%B1) CR_TAB
++ AS2 (st,Z+,%C1) CR_TAB
++ AS2 (st,Z,%D1) CR_TAB
++ AS2 (subi,r30,lo8(3)) CR_TAB
++ AS2 (sbci,r31,lo8(3)))
++ : (AS2 (st,%0,%A1) CR_TAB
+ AS2 (std,%0+1,%B1) CR_TAB
+ AS2 (std,%0+2,%C1) CR_TAB
+ AS2 (std,%0+3,%D1));
+ }
++ }
+ else if (GET_CODE (base) == PLUS) /* (R + i) */
+ {
+ int disp = INTVAL (XEXP (base, 1));
+@@ -2437,14 +2846,35 @@ out_movsi_mr_r (rtx insn, rtx op[], int
+ fatal_insn ("incorrect insn:",insn);
+
+ if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest)))
+- return *l = 6, (AS2 (adiw,r28,%o0-60) CR_TAB
++ return *l = 6, AVR_TINY ? (AS2 (subi,r28,lo8(-(%o0-60))) CR_TAB
++ AS2 (sbci,r29,hi8(-(%o0-60))) CR_TAB
++ AS2 (subi,r28,lo8(-60)) CR_TAB
++ AS2 (sbci,r29,lo8(-60)) CR_TAB
++ AS2 (st,Y+,%A1) CR_TAB
++ AS2 (st,Y+,%B1) CR_TAB
++ AS2 (st,Y+,%C1) CR_TAB
++ AS2 (st,Y,%D1) CR_TAB
++ AS2 (subi,r28,lo8(63)) CR_TAB
++ AS2 (sbci,r29,lo8(63)) CR_TAB
++ AS2 (subi,r28,lo8(%o0-60)) CR_TAB
++ AS2 (sbci,r29,hi8(%o0-60)))
++ : (AS2 (adiw,r28,%o0-60) CR_TAB
+ AS2 (std,Y+60,%A1) CR_TAB
+ AS2 (std,Y+61,%B1) CR_TAB
+ AS2 (std,Y+62,%C1) CR_TAB
+ AS2 (std,Y+63,%D1) CR_TAB
+ AS2 (sbiw,r28,%o0-60));
+-
+- return *l = 8, (AS2 (subi,r28,lo8(-%o0)) CR_TAB
++ return *l = 8, AVR_TINY ? (AS2 (subi,r28,lo8(-%o0)) CR_TAB
++ AS2 (sbci,r29,hi8(-%o0)) CR_TAB
++ AS2 (st,Y+,%A1) CR_TAB
++ AS2 (st,Y+,%B1) CR_TAB
++ AS2 (st,Y+,%C1) CR_TAB
++ AS2 (st,Y,%D1) CR_TAB
++ AS2 (subi,r28,lo8(3)) CR_TAB
++ AS2 (sbci,r29,lo8(3)) CR_TAB
++ AS2 (subi,r28,lo8(%o0)) CR_TAB
++ AS2 (sbci,r29,hi8(%o0)))
++ : (AS2 (subi,r28,lo8(-%o0)) CR_TAB
+ AS2 (sbci,r29,hi8(-%o0)) CR_TAB
+ AS2 (st,Y,%A1) CR_TAB
+ AS2 (std,Y+1,%B1) CR_TAB
+@@ -2459,7 +2889,18 @@ out_movsi_mr_r (rtx insn, rtx op[], int
+ if (reg_src == REG_X)
+ {
+ *l = 9;
+- return (AS2 (mov,__tmp_reg__,r26) CR_TAB
++ return AVR_TINY ? (AS2 (mov,__tmp_reg__,r26) CR_TAB
++ AS2 (mov,__zero_reg__,r27) CR_TAB
++ AS2 (subi,r26,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o0))) CR_TAB
++ AS2 (st,X+,__tmp_reg__) CR_TAB
++ AS2 (st,X+,__zero_reg__) CR_TAB
++ AS2 (st,X+,r28) CR_TAB
++ AS2 (st,X,r29) CR_TAB
++ AS1 (clr,__zero_reg__) CR_TAB
++ AS2 (subi,r26,lo8(%o0+3)) CR_TAB
++ AS2 (sbci,r27,hi8(%o0+3)))
++ : (AS2 (mov,__tmp_reg__,r26) CR_TAB
+ AS2 (mov,__zero_reg__,r27) CR_TAB
+ AS2 (adiw,r26,%o0) CR_TAB
+ AS2 (st,X+,__tmp_reg__) CR_TAB
+@@ -2472,7 +2913,18 @@ out_movsi_mr_r (rtx insn, rtx op[], int
+ else if (reg_src == REG_X - 2)
+ {
+ *l = 9;
+- return (AS2 (mov,__tmp_reg__,r26) CR_TAB
++ return AVR_TINY ? (AS2 (mov,__tmp_reg__,r26) CR_TAB
++ AS2 (mov,__zero_reg__,r27) CR_TAB
++ AS2 (subi,r26,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o0))) CR_TAB
++ AS2 (st,X+,r24) CR_TAB
++ AS2 (st,X+,r25) CR_TAB
++ AS2 (st,X+,__tmp_reg__) CR_TAB
++ AS2 (st,X,__zero_reg__) CR_TAB
++ AS1 (clr,__zero_reg__) CR_TAB
++ AS2 (subi,r26,lo8(%o0+3)) CR_TAB
++ AS2 (sbci,r27,hi8(%o0+3)))
++ : (AS2 (mov,__tmp_reg__,r26) CR_TAB
+ AS2 (mov,__zero_reg__,r27) CR_TAB
+ AS2 (adiw,r26,%o0) CR_TAB
+ AS2 (st,X+,r24) CR_TAB
+@@ -2483,14 +2935,46 @@ out_movsi_mr_r (rtx insn, rtx op[], int
+ AS2 (sbiw,r26,%o0+3));
+ }
+ *l = 6;
+- return (AS2 (adiw,r26,%o0) CR_TAB
++ return AVR_TINY ? (AS2 (subi,r26,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o0))) CR_TAB
++ AS2 (st,X+,%A1) CR_TAB
++ AS2 (st,X+,%B1) CR_TAB
++ AS2 (st,X+,%C1) CR_TAB
++ AS2 (st,X,%D1) CR_TAB
++ AS2 (subi,r26,lo8(%o0+3)) CR_TAB
++ AS2 (sbci,r27,hi8(%o0+3)))
++ : (AS2 (adiw,r26,%o0) CR_TAB
+ AS2 (st,X+,%A1) CR_TAB
+ AS2 (st,X+,%B1) CR_TAB
+ AS2 (st,X+,%C1) CR_TAB
+ AS2 (st,X,%D1) CR_TAB
+ AS2 (sbiw,r26,%o0+3));
+ }
+- return *l=4, (AS2 (std,%A0,%A1) CR_TAB
++ op[2] = XEXP(base, 0);
++ if(REGNO(op[2]) == REG_Y)
++ return *l=4, AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o0))) CR_TAB
++ AS2 (st,Y+,%A1) CR_TAB
++ AS2 (st,Y+,%B1) CR_TAB
++ AS2 (st,Y+,%C1) CR_TAB
++ AS2 (st,Y,%D1) CR_TAB
++ AS2 (subi,%A2,lo8(%o0+3)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o0+3)))
++ : (AS2 (std,%A0,%A1) CR_TAB
++ AS2 (std,%B0,%B1) CR_TAB
++ AS2 (std,%C0,%C1) CR_TAB
++ AS2 (std,%D0,%D1));
++
++ if(REGNO(op[2]) == REG_Z)
++ return *l=4, AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o0))) CR_TAB
++ AS2 (st,Z+,%A1) CR_TAB
++ AS2 (st,Z+,%B1) CR_TAB
++ AS2 (st,Z+,%C1) CR_TAB
++ AS2 (st,Z,%D1) CR_TAB
++ AS2 (subi,%A2,lo8(%o0+3)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o0+3)))
++ : (AS2 (std,%A0,%A1) CR_TAB
+ AS2 (std,%B0,%B1) CR_TAB
+ AS2 (std,%C0,%C1) CR_TAB
+ AS2 (std,%D0,%D1));
+@@ -2707,7 +3191,16 @@ out_movqi_mr_r (rtx insn, rtx op[], int
+ fatal_insn ("incorrect insn:",insn);
+
+ if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest)))
+- return *l = 3, (AS2 (adiw,r28,%o0-63) CR_TAB
++ return *l = 3, AVR_TINY ? (AS2 (subi,r28,lo8(-(%o0-63))) CR_TAB
++ AS2 (sbci,r29,hi8(-(%o0-63))) CR_TAB
++ AS2 (subi,r28,lo8(-63)) CR_TAB
++ AS2 (sbci,r29,hi8(-63)) CR_TAB
++ AS2 (st,Y,%1) CR_TAB
++ AS2 (subi,r28,lo8(63)) CR_TAB
++ AS2 (sbci,r29,hi8(63)) CR_TAB
++ AS2 (subi,r28,lo8(%o0-63)) CR_TAB
++ AS2 (sbci,r29,hi8(%o0-63)))
++ : (AS2 (adiw,r28,%o0-63) CR_TAB
+ AS2 (std,Y+63,%1) CR_TAB
+ AS2 (sbiw,r28,%o0-63));
+
+@@ -2722,11 +3215,21 @@ out_movqi_mr_r (rtx insn, rtx op[], int
+ if (reg_overlap_mentioned_p (src, XEXP (x, 0)))
+ {
+ if (reg_unused_after (insn, XEXP (x,0)))
+- return *l = 3, (AS2 (mov,__tmp_reg__,%1) CR_TAB
++ return *l = 3, AVR_TINY ? (AS2 (mov,__tmp_reg__,%1) CR_TAB
++ AS2 (subi,r26,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o0))) CR_TAB
++ AS2 (st,X,__tmp_reg__))
++ : (AS2 (mov,__tmp_reg__,%1) CR_TAB
+ AS2 (adiw,r26,%o0) CR_TAB
+ AS2 (st,X,__tmp_reg__));
+
+- return *l = 4, (AS2 (mov,__tmp_reg__,%1) CR_TAB
++ return *l = 4, AVR_TINY ? (AS2 (mov,__tmp_reg__,%1) CR_TAB
++ AS2 (subi,r26,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o0))) CR_TAB
++ AS2 (st,X,__tmp_reg__) CR_TAB
++ AS2 (subi,r26,lo8(%o0)) CR_TAB
++ AS2 (sbci,r27,hi8(%o0)))
++ : (AS2 (mov,__tmp_reg__,%1) CR_TAB
+ AS2 (adiw,r26,%o0) CR_TAB
+ AS2 (st,X,__tmp_reg__) CR_TAB
+ AS2 (sbiw,r26,%o0));
+@@ -2734,16 +3237,38 @@ out_movqi_mr_r (rtx insn, rtx op[], int
+ else
+ {
+ if (reg_unused_after (insn, XEXP (x,0)))
+- return *l = 2, (AS2 (adiw,r26,%o0) CR_TAB
++ return *l = 2, AVR_TINY ? (AS2 (subi,r26,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o0))) CR_TAB
++ AS2 (st,X,%1))
++ : (AS2 (adiw,r26,%o0) CR_TAB
+ AS2 (st,X,%1));
+
+- return *l = 3, (AS2 (adiw,r26,%o0) CR_TAB
++ return *l = 3, AVR_TINY ? (AS2 (subi,r26,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o0))) CR_TAB
++ AS2 (st,X,%1) CR_TAB
++ AS2 (subi,r26,lo8(%o0)) CR_TAB
++ AS2 (sbci,r27,hi8(%o0)))
++ : (AS2 (adiw,r26,%o0) CR_TAB
+ AS2 (st,X,%1) CR_TAB
+ AS2 (sbiw,r26,%o0));
+ }
+ }
+ *l = 1;
+- return AS2 (std,%0,%1);
++ op[2] = XEXP(x, 0);
++ if(REGNO(op[2]) == REG_Y)
++ return AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o0))) CR_TAB
++ AS2 (st,Y,%1) CR_TAB
++ AS2 (subi,%A2,lo8(%o0)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o0)))
++ : AS2 (std,%0,%1);
++ if(REGNO(op[2]) == REG_Z)
++ return AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o0))) CR_TAB
++ AS2 (st,Z,%1) CR_TAB
++ AS2 (subi,%A2,lo8(%o0)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o0)))
++ : AS2 (std,%0,%1);
+ }
+ *l = 1;
+ return AS2 (st,%0,%1);
+@@ -2792,20 +3317,39 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ {
+ /* "st X+,r26" and "st -X,r26" are undefined. */
+ if (!mem_volatile_p && reg_unused_after (insn, src))
+- return *l=4, (AS2 (mov,__tmp_reg__,r27) CR_TAB
++ return *l=4, AVR_TINY ? (AS2 (mov,__tmp_reg__,r27) CR_TAB
++ AS2 (st,X,r26) CR_TAB
++ AS2 (subi,r26,lo8(-1)) CR_TAB
++ AS2 (sbci,r27,hi8(-1)) CR_TAB
++ AS2 (st,X,__tmp_reg__))
++ : (AS2 (mov,__tmp_reg__,r27) CR_TAB
+ AS2 (st,X,r26) CR_TAB
+ AS2 (adiw,r26,1) CR_TAB
+ AS2 (st,X,__tmp_reg__));
+ else
+ {
+ if (!AVR_XMEGA)
+- return *l=5, (AS2 (mov,__tmp_reg__,r27) CR_TAB
++ return *l=5, AVR_TINY ? (AS2 (mov,__tmp_reg__,r27) CR_TAB
++ AS2 (subi,r26,lo8(-1)) CR_TAB
++ AS2 (sbci,r27,hi8(-1)) CR_TAB
++ AS2 (st,X,__tmp_reg__) CR_TAB
++ AS2 (subi,r26,lo8(1)) CR_TAB
++ AS2 (sbci,r27,hi8(1)) CR_TAB
++ AS2 (st,X,r26))
++ : (AS2 (mov,__tmp_reg__,r27) CR_TAB
+ AS2 (adiw,r26,1) CR_TAB
+ AS2 (st,X,__tmp_reg__) CR_TAB
+ AS2 (sbiw,r26,1) CR_TAB
+ AS2 (st,X,r26));
+ else
+- return *l=5, (AS2 (mov,__tmp_reg__,r27) CR_TAB
++ return *l=5, AVR_TINY ? (AS2 (mov,__tmp_reg__,r27) CR_TAB
++ AS2 (st,X,r26) CR_TAB
++ AS2 (subi,r26,lo8(-1)) CR_TAB
++ AS2 (sbci,r27,hi8(-1)) CR_TAB
++ AS2 (st,X,__tmp_reg__) CR_TAB
++ AS2 (subi,r26,lo8(1)) CR_TAB
++ AS2 (sbci,r27,hi8(1)))
++ : (AS2 (mov,__tmp_reg__,r27) CR_TAB
+ AS2 (st,X,r26) CR_TAB
+ AS2 (adiw,r26,1) CR_TAB
+ AS2 (st,X,__tmp_reg__) CR_TAB
+@@ -2820,11 +3364,19 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ else
+ {
+ if (!AVR_XMEGA)
+- return *l=3, (AS2 (adiw,r26,1) CR_TAB
++ return *l=3, AVR_TINY ? (AS2 (subi,r26,lo8(-1)) CR_TAB
++ AS2 (sbci,r27,hi8(-1)) CR_TAB
++ AS2 (st,X,%B1) CR_TAB
++ AS2 (st,-X,%A1))
++ : (AS2 (adiw,r26,1) CR_TAB
+ AS2 (st,X,%B1) CR_TAB
+ AS2 (st,-X,%A1));
+ else
+- return *l=3, (AS2 (st,X+,%A1) CR_TAB
++ return *l=3, AVR_TINY ? (AS2 (st,X+,%A1) CR_TAB
++ AS2 (st,X,%B1) CR_TAB
++ AS2 (subi,r26,lo8(1)) CR_TAB
++ AS2 (sbci,r27,hi8(1)))
++ : (AS2 (st,X+,%A1) CR_TAB
+ AS2 (st,X,%B1) CR_TAB
+ AS2 (sbiw,r26,1));
+ }
+@@ -2833,13 +3385,41 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ else
+ {
+ if (!AVR_XMEGA)
+- return *l=2, (AS2 (std,%0+1,%B1) CR_TAB
++ {
++ if(reg_base == REG_Y)
++ return *l=2, AVR_TINY ? (AS2 (subi,r28,lo8(-1)) CR_TAB
++ AS2 (sbci,r29,hi8(-1)) CR_TAB
++ AS2 (st,Y,%B1) CR_TAB
++ AS2 (st,-Y,%A1))
++ : (AS2 (std,%0+1,%B1) CR_TAB
++ AS2 (st,%0,%A1));
++ if(reg_base == REG_Z)
++ return *l=2, AVR_TINY ? (AS2 (subi,r30,lo8(-1)) CR_TAB
++ AS2 (sbci,r31,hi8(-1)) CR_TAB
++ AS2 (st,Z,%B1) CR_TAB
++ AS2 (st,-Z,%A1))
++ : (AS2 (std,%0+1,%B1) CR_TAB
+ AS2 (st,%0,%A1));
++ }
+ else
+- return *l=2, (AS2 (st,%0,%A1) CR_TAB
++ {
++ if(reg_base == REG_Y)
++ return *l=2, AVR_TINY ? (AS2 (st,Y+,%A1) CR_TAB
++ AS2 (st,Y,%B1) CR_TAB
++ AS2 (subi,r28,lo8(1)) CR_TAB
++ AS2 (sbci,r29,hi8(1)))
++ : (AS2 (st,%0,%A1) CR_TAB
++ AS2 (std,%0+1,%B1));
++ if(reg_base == REG_Z)
++ return *l=2, AVR_TINY ? (AS2 (st,Z+,%A1) CR_TAB
++ AS2 (st,Z,%B1) CR_TAB
++ AS2 (subi,r30,lo8(1)) CR_TAB
++ AS2 (sbci,r31,hi8(1)))
++ : (AS2 (st,%0,%A1) CR_TAB
+ AS2 (std,%0+1,%B1));
+ }
+ }
++ }
+ else if (GET_CODE (base) == PLUS)
+ {
+ int disp = INTVAL (XEXP (base, 1));
+@@ -2852,12 +3432,30 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ if (!AVR_XMEGA)
+ {
+ if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest)))
+- return *l = 4, (AS2 (adiw,r28,%o0-62) CR_TAB
++ return *l = 4, AVR_TINY ? (AS2 (subi,r28,lo8(-(%o0-62))) CR_TAB
++ AS2 (sbci,r29,hi8(-(%o0-62))) CR_TAB
++ AS2 (subi,r28,lo8(-63)) CR_TAB
++ AS2 (sbci,r29,hi8(-63)) CR_TAB
++ AS2 (st,Y,%B1) CR_TAB
++ AS2 (st,-Y,%A1) CR_TAB
++ AS2 (subi,r28,lo8(62)) CR_TAB
++ AS2 (sbci,r29,hi8(62)) CR_TAB
++ AS2 (subi,r28,lo8(%o0-62)) CR_TAB
++ AS2 (sbci,r29,hi8(%o0-62)))
++ : (AS2 (adiw,r28,%o0-62) CR_TAB
+ AS2 (std,Y+63,%B1) CR_TAB
+ AS2 (std,Y+62,%A1) CR_TAB
+ AS2 (sbiw,r28,%o0-62));
+
+- return *l = 6, (AS2 (subi,r28,lo8(-%o0)) CR_TAB
++ return *l = 6, AVR_TINY ? (AS2 (subi,r28,lo8(-%o0)) CR_TAB
++ AS2 (sbci,r29,hi8(-%o0)) CR_TAB
++ AS2 (subi,r28,lo8(-1)) CR_TAB
++ AS2 (sbci,r29,hi8(-1)) CR_TAB
++ AS2 (st,Y,%B1) CR_TAB
++ AS2 (st,-Y,%A1) CR_TAB
++ AS2 (subi,r28,lo8(%o0)) CR_TAB
++ AS2 (sbci,r29,hi8(%o0)))
++ : (AS2 (subi,r28,lo8(-%o0)) CR_TAB
+ AS2 (sbci,r29,hi8(-%o0)) CR_TAB
+ AS2 (std,Y+1,%B1) CR_TAB
+ AS2 (st,Y,%A1) CR_TAB
+@@ -2867,12 +3465,30 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ else
+ {
+ if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest)))
+- return *l = 4, (AS2 (adiw,r28,%o0-62) CR_TAB
++ return *l = 4, AVR_TINY ? (AS2 (subi,r28,lo8(-(%o0-62))) CR_TAB
++ AS2 (sbci,r29,hi8(-(%o0-62))) CR_TAB
++ AS2 (subi,r28,lo8(-62)) CR_TAB
++ AS2 (sbci,r29,hi8(-62)) CR_TAB
++ AS2 (st,Y+,%A1) CR_TAB
++ AS2 (st,Y,%B1) CR_TAB
++ AS2 (subi,r28,lo8(63)) CR_TAB
++ AS2 (sbci,r29,hi8(63)) CR_TAB
++ AS2 (subi,r28,lo8(%o0-62)) CR_TAB
++ AS2 (sbci,r29,hi8(%o0-62)))
++ : (AS2 (adiw,r28,%o0-62) CR_TAB
+ AS2 (std,Y+62,%A1) CR_TAB
+ AS2 (std,Y+63,%B1) CR_TAB
+ AS2 (sbiw,r28,%o0-62));
+
+- return *l = 6, (AS2 (subi,r28,lo8(-%o0)) CR_TAB
++ return *l = 6, AVR_TINY ? (AS2 (subi,r28,lo8(-%o0)) CR_TAB
++ AS2 (sbci,r29,hi8(-%o0)) CR_TAB
++ AS2 (st,Y+,%A1) CR_TAB
++ AS2 (st,Y,%B1) CR_TAB
++ AS2 (subi,r28,lo8(1)) CR_TAB
++ AS2 (sbci,r29,hi8(1)) CR_TAB
++ AS2 (subi,r28,lo8(%o0)) CR_TAB
++ AS2 (sbci,r29,hi8(%o0)))
++ : (AS2 (subi,r28,lo8(-%o0)) CR_TAB
+ AS2 (sbci,r29,hi8(-%o0)) CR_TAB
+ AS2 (st,Y,%A1) CR_TAB
+ AS2 (std,Y+1,%B1) CR_TAB
+@@ -2888,7 +3504,16 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ if (!AVR_XMEGA)
+ {
+ *l = 7;
+- return (AS2 (mov,__tmp_reg__,r26) CR_TAB
++ return AVR_TINY ? (AS2 (mov,__tmp_reg__,r26) CR_TAB
++ AS2 (mov,__zero_reg__,r27) CR_TAB
++ AS2 (subi,r26,lo8(-(%o0+1))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o0+1))) CR_TAB
++ AS2 (st,X,__zero_reg__) CR_TAB
++ AS2 (st,-X,__tmp_reg__) CR_TAB
++ AS1 (clr,__zero_reg__) CR_TAB
++ AS2 (subi,r26,lo8(%o0)) CR_TAB
++ AS2 (sbci,r27,hi8(%o0)))
++ : (AS2 (mov,__tmp_reg__,r26) CR_TAB
+ AS2 (mov,__zero_reg__,r27) CR_TAB
+ AS2 (adiw,r26,%o0+1) CR_TAB
+ AS2 (st,X,__zero_reg__) CR_TAB
+@@ -2899,19 +3524,35 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ else
+ {
+ *l = 7;
+- return (AS2 (mov,__tmp_reg__,r26) CR_TAB
++ return AVR_TINY ? (AS2 (mov,__tmp_reg__,r26) CR_TAB
+ AS2 (mov,__zero_reg__,r27) CR_TAB
+- AS2 (adiw,r26,%o0) CR_TAB
++ AS2 (subi,r26,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o0))) CR_TAB
+ AS2 (st,X+,__tmp_reg__) CR_TAB
+ AS2 (st,X,__zero_reg__) CR_TAB
+ AS1 (clr,__zero_reg__) CR_TAB
+- AS2 (sbiw,r26,%o0+1));
++ AS2 (subi,r26,lo8(%o0+1)) CR_TAB
++ AS2 (sbci,r27,hi8(%o0+1)))
++ : (AS2 (mov,__tmp_reg__,r26) CR_TAB
++ AS2 (mov,__zero_reg__,r27) CR_TAB
++ AS2 (adiw,r26,%o0+1) CR_TAB
++ AS2 (st,X+,__tmp_reg__) CR_TAB
++ AS2 (st,X,__zero_reg__) CR_TAB
++ AS1 (clr,__zero_reg__) CR_TAB
++ AS2 (sbiw,r26,%o0));
++
+ }
+ }
+ if (!AVR_XMEGA)
+ {
+ *l = 4;
+- return (AS2 (adiw,r26,%o0+1) CR_TAB
++ return AVR_TINY ? (AS2 (subi,r26,lo8(-(%o0+1))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o0+1))) CR_TAB
++ AS2 (st,X,%B1) CR_TAB
++ AS2 (st,-X,%A1) CR_TAB
++ AS2 (subi,r26,lo8(%o0)) CR_TAB
++ AS2 (sbci,r27,hi8(%o0)))
++ : (AS2 (adiw,r26,%o0+1) CR_TAB
+ AS2 (st,X,%B1) CR_TAB
+ AS2 (st,-X,%A1) CR_TAB
+ AS2 (sbiw,r26,%o0));
+@@ -2919,7 +3560,13 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ else
+ {
+ *l = 4;
+- return (AS2 (adiw,r26,%o0) CR_TAB
++ return AVR_TINY ? (AS2 (subi,r26,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,r27,hi8(-(%o0))) CR_TAB
++ AS2 (st,X+,%A1) CR_TAB
++ AS2 (st,X,%B1) CR_TAB
++ AS2 (subi,r26,lo8(%o0)) CR_TAB
++ AS2 (sbci,r27,hi8(%o0)))
++ : (AS2 (adiw,r26,%o0) CR_TAB
+ AS2 (st,X+,%A1) CR_TAB
+ AS2 (st,X,%B1) CR_TAB
+ AS2 (sbiw,r26,%o0+1));
+@@ -2927,11 +3574,49 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ }
+
+ if (!AVR_XMEGA)
+- return *l=2, (AS2 (std,%B0,%B1) CR_TAB
++ {
++ op[2] = XEXP(base, 0);
++ if(REGNO(op[2]) == REG_Y)
++ return *l=2, AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o0+2))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o0+2))) CR_TAB
++ AS2 (st,-Y,%B1) CR_TAB
++ AS2 (st,-Y,%A1) CR_TAB
++ AS2 (subi,%A2,lo8(%o0)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o0)))
++ : (AS2 (std,%B0,%B1) CR_TAB
+ AS2 (std,%A0,%A1));
++ if(REGNO(op[2]) == REG_Z)
++ return *l=2, AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o0+1))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o0+1))) CR_TAB
++ AS2 (st,-Z,%B1) CR_TAB
++ AS2 (st,-Z,%A1) CR_TAB
++ AS2 (subi,%A2,lo8(%o0)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o0)))
++ : (AS2 (std,%B0,%B1) CR_TAB
++ AS2 (std,%A0,%A1));
++ }
+ else
+- return *l=2, (AS2 (std,%A0,%A1) CR_TAB
++ {
++ op[2] = XEXP(base, 0);
++ if(REGNO(op[2]) == REG_Y)
++ return *l=2, AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o0))) CR_TAB
++ AS2 (st,Y+,%A1) CR_TAB
++ AS2 (st,Y,%B1) CR_TAB
++ AS2 (subi,%A2,lo8(%o0+1)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o0+1)))
++ : (AS2 (std,%A0,%A1) CR_TAB
+ AS2 (std,%B0,%B1));
++ if(REGNO(op[2]) == REG_Z)
++ return *l=2, AVR_TINY ? (AS2 (subi,%A2,lo8(-(%o0))) CR_TAB
++ AS2 (sbci,%B2,hi8(-(%o0))) CR_TAB
++ AS2 (st,Z+,%A1) CR_TAB
++ AS2 (st,Z,%B1) CR_TAB
++ AS2 (subi,%A2,lo8(%o0+1)) CR_TAB
++ AS2 (sbci,%B2,hi8(%o0+1)))
++ : (AS2 (std,%A0,%A1) CR_TAB
++ AS2 (std,%B0,%B1));
++ }
+ }
+ else if (GET_CODE (base) == PRE_DEC) /* (--R) */
+ {
+@@ -2951,15 +3636,30 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ if (REGNO (XEXP (base, 0)) == REG_X)
+ {
+ *l = 4;
+- return (AS2 (adiw,r26,1) CR_TAB
++ return AVR_TINY ? (AS2 (subi,r26,lo8(-1)) CR_TAB
++ AS2 (sbci,r27,hi8(-1)) CR_TAB
++ AS2 (st,X,%B1) CR_TAB
++ AS2 (st,-X,%A1) CR_TAB
++ AS2 (subi,r26,lo8(-2)) CR_TAB
++ AS2 (sbci,r27,hi8(-2)))
++ : (AS2 (adiw,r26,1) CR_TAB
+ AS2 (st,X,%B1) CR_TAB
+ AS2 (st,-X,%A1) CR_TAB
+ AS2 (adiw,r26,2));
+ }
+ else
+ {
++ //FIXME:check the code once again for AVR_TINY
+ *l = 3;
+- return (AS2 (std,%p0+1,%B1) CR_TAB
++ return AVR_TINY ? (AS2 (subi,%A0,lo8(-1)) CR_TAB
++ AS2 (sbci,%B0,hi8(-1)) CR_TAB
++ AS2 (st,%p0,%B1) CR_TAB
++ AS2 (subi,%A0,lo8(1)) CR_TAB
++ AS2 (sbci,%B0,hi8(1)) CR_TAB
++ AS2 (st,%p0,%A1) CR_TAB
++ AS2 (subi,%A0,lo8(-3)) CR_TAB
++ AS2 (sbci,%B0,hi8(-3)))
++ : (AS2 (std,%p0+1,%B1) CR_TAB
+ AS2 (st,%p0,%A1) CR_TAB
+ AS2 (adiw,%r0,2));
+ }
+@@ -3049,7 +3749,9 @@ out_tsthi (rtx insn, rtx op, int *l)
+ if (test_hard_reg_class (ADDW_REGS, op))
+ {
+ if (l) *l = 1;
+- return AS2 (sbiw,%0,0);
++ return AVR_TINY ? (AS2 (subi,%A0,lo8(0)) CR_TAB
++ AS2 (sbci,%B0,hi8(0)))
++ : AS2 (sbiw,%0,0);
+ }
+ if (l) *l = 2;
+ return (AS2 (cp,%A0,__zero_reg__) CR_TAB
+@@ -3070,7 +3772,11 @@ out_tstsi (rtx insn, rtx op, int *l)
+ if (test_hard_reg_class (ADDW_REGS, op))
+ {
+ if (l) *l = 3;
+- return (AS2 (sbiw,%A0,0) CR_TAB
++ return AVR_TINY ? (AS2 (subi,%A0,lo8(-(-0))) CR_TAB
++ AS2 (sbci,%B0,hi8(-(-0))) CR_TAB
++ AS2 (cpc,%C0,__zero_reg__) CR_TAB
++ AS2 (cpc,%D0,__zero_reg__))
++ : (AS2 (sbiw,%A0,0) CR_TAB
+ AS2 (cpc,%C0,__zero_reg__) CR_TAB
+ AS2 (cpc,%D0,__zero_reg__));
+ }
+@@ -5392,10 +6098,12 @@ avr_file_start (void)
+ /* fprintf (asm_out_file, "\t.arch %s\n", avr_mcu_name);*/
+ fputs ("__SREG__ = 0x3f\n"
+ "__SP_H__ = 0x3e\n"
+- "__SP_L__ = 0x3d\n"
+- "__CCP__ = 0x34\n", asm_out_file);
++ "__SP_L__ = 0x3d\n", asm_out_file);
++
++ AVR_TINY ? fputs ("__CCP__ = 0x3c\n", asm_out_file) : fputs ("__CCP__ = 0x34\n", asm_out_file);
+
+- fputs ("__tmp_reg__ = 0\n"
++ AVR_TINY ? fputs ("__tmp_reg__ = 16\n"
++ "__zero_reg__ = 17\n", asm_out_file) : fputs ("__tmp_reg__ = 0\n"
+ "__zero_reg__ = 1\n", asm_out_file);
+
+ /* FIXME: output these only if there is anything in the .data / .bss
+diff -Naurp gcc/config/avr/avr-c.c gcc/config/avr/avr-c.c
+--- gcc/config/avr/avr-c.c 2011-09-02 11:45:05.000000000 +0300
++++ gcc/config/avr/avr-c.c 2011-09-02 11:46:03.000000000 +0300
+@@ -94,5 +94,9 @@ avr_cpu_cpp_builtins (struct cpp_reader
+ cpp_define (pfile, "__AVR_HAVE_RAMPD__");
+ }
+
++ if (avr_current_arch->avrtiny)
++ {
++ cpp_define (pfile, "__AVR_TINY__");
++ }
+ }
+
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-02 11:45:05.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-02 11:46:03.000000000 +0300
+@@ -26,24 +26,25 @@
+ /* List of all known AVR MCU architectyres. */
+
+ const struct base_arch_s avr_arch_types[] = {
+- { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0x0060, NULL, "avr2" }, /* unknown device specified */
+- { 1, 0, 0, 0, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=1", "avr1" },
+- { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=2", "avr2" },
+- { 0, 0, 0, 1, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=25", "avr25" },
+- { 0, 0, 1, 0, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=3", "avr3" },
+- { 0, 0, 1, 0, 1, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=31", "avr31" },
+- { 0, 0, 1, 1, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=35", "avr35" },
+- { 0, 1, 0, 1, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=4", "avr4" },
+- { 0, 1, 1, 1, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=5", "avr5" },
+- { 0, 1, 1, 1, 1, 1, 0, 0, 0, 0x0060, "__AVR_ARCH__=51", "avr51" },
+- { 0, 1, 1, 1, 1, 1, 1, 0, 0, 0x0060, "__AVR_ARCH__=6", "avr6" },
+- { 0, 1, 0, 1, 0, 0, 0, 1, 0, 0x2000, "__AVR_ARCH__=101", "avrxmega1" },
+- { 0, 1, 1, 1, 0, 0, 0, 1, 0, 0x2000, "__AVR_ARCH__=102", "avrxmega2" },
+- { 0, 1, 1, 1, 0, 0, 0, 1, 1, 0x2000, "__AVR_ARCH__=103", "avrxmega3" },
+- { 0, 1, 1, 1, 1, 1, 0, 1, 0, 0x2000, "__AVR_ARCH__=104", "avrxmega4" },
+- { 0, 1, 1, 1, 1, 1, 0, 1, 1, 0x2000, "__AVR_ARCH__=105", "avrxmega5" },
+- { 0, 1, 1, 1, 1, 1, 1, 1, 0, 0x2000, "__AVR_ARCH__=106", "avrxmega6" },
+- { 0, 1, 1, 1, 1, 1, 1, 1, 1, 0x2000, "__AVR_ARCH__=107", "avrxmega7" }
++ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0x0060, NULL, "avr2" }, /* unknown device specified */
++ { 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=1", "avr1" },
++ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=2", "avr2" },
++ { 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=25", "avr25" },
++ { 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=3", "avr3" },
++ { 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=31", "avr31" },
++ { 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=35", "avr35" },
++ { 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=4", "avr4" },
++ { 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=5", "avr5" },
++ { 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=51", "avr51" },
++ { 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0x0060, "__AVR_ARCH__=6", "avr6" },
++ { 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0x2000, "__AVR_ARCH__=101", "avrxmega1" },
++ { 0, 1, 1, 1, 0, 0, 0, 1, 0, 0, 0x2000, "__AVR_ARCH__=102", "avrxmega2" },
++ { 0, 1, 1, 1, 0, 0, 0, 1, 1, 0, 0x2000, "__AVR_ARCH__=103", "avrxmega3" },
++ { 0, 1, 1, 1, 1, 1, 0, 1, 0, 0, 0x2000, "__AVR_ARCH__=104", "avrxmega4" },
++ { 0, 1, 1, 1, 1, 1, 0, 1, 1, 0, 0x2000, "__AVR_ARCH__=105", "avrxmega5" },
++ { 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0x2000, "__AVR_ARCH__=106", "avrxmega6" },
++ { 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0x2000, "__AVR_ARCH__=107", "avrxmega7" },
++ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0x0040, "__AVR_ARCH__=201", "avrtiny10" }
+ };
+
+ /* List of all known AVR MCU types - if updated, it has to be kept
+@@ -228,6 +229,14 @@ const struct mcu_type_s avr_mcu_types[]
+ { "avrxmega7", ARCH_AVRXMEGA7, NULL, 0, 0x2000, "x128a1" },
+ { "atxmega128a1", ARCH_AVRXMEGA7, "__AVR_ATxmega128A1__", 0, 0x2000, "x128a1" },
+ { "atxmega128a1u", ARCH_AVRXMEGA7, "__AVR_ATxmega128A1U__", 0, 0x2000, "x128a1u" },
++ /* tiny10 family */
++ { "avrtiny10", ARCH_AVRTINY10, NULL, 0, 0x0040, "tn10" },
++ { "attiny4", ARCH_AVRTINY10, "__AVR_ATtiny4__", 0, 0x0040, "tn4" },
++ { "attiny5", ARCH_AVRTINY10, "__AVR_ATtiny5__", 0, 0x0040, "tn5" },
++ { "attiny9", ARCH_AVRTINY10, "__AVR_ATtiny9__", 0, 0x0040, "tn9" },
++ { "attiny10", ARCH_AVRTINY10, "__AVR_ATtiny10__", 0, 0x0040, "tn10" },
++ { "attiny20", ARCH_AVRTINY10, "__AVR_ATtiny20__", 0, 0x0040, "tn20" },
++ { "attiny40", ARCH_AVRTINY10, "__AVR_ATtiny40__", 0, 0x0040, "tn40" },
+ /* Assembler only. */
+ { "avr1", ARCH_AVR1, NULL, 0, 0x0060, "s1200" },
+ { "at90s1200", ARCH_AVR1, "__AVR_AT90S1200__", 0, 0x0060, "s1200" },
+diff -Naurp gcc/config/avr/avr.h gcc/config/avr/avr.h
+--- gcc/config/avr/avr.h 2011-09-02 11:45:05.000000000 +0300
++++ gcc/config/avr/avr.h 2011-09-02 11:46:03.000000000 +0300
+@@ -51,6 +51,9 @@ struct base_arch_s {
+ /* Core have RAMPX, RAMPY and RAMPD registers. */
+ int have_rampx_y_d;
+
++ /* Core is in avrtiny10 family. */
++ int avrtiny;
++
+ /* Default start of data section address for architecture. */
+ int default_data_section_start;
+
+@@ -82,7 +85,8 @@ enum avr_arch
+ ARCH_AVRXMEGA4,
+ ARCH_AVRXMEGA5,
+ ARCH_AVRXMEGA6,
+- ARCH_AVRXMEGA7
++ ARCH_AVRXMEGA7,
++ ARCH_AVRTINY10
+ };
+
+ struct mcu_type_s {
+@@ -126,6 +130,7 @@ extern GTY(()) section *progmem_section;
+ #define AVR_HAVE_EIJMP_EICALL (avr_current_arch->have_eijmp_eicall)
+ #define AVR_HAVE_8BIT_SP (avr_current_device->short_sp || TARGET_TINY_STACK)
+ #define AVR_XMEGA (avr_current_arch->xmega)
++#define AVR_TINY (avr_current_arch->avrtiny)
+ #define AVR_HAVE_RAMPX_Y_D (avr_current_arch->have_rampx_y_d)
+
+ #define AVR_2_BYTE_PC (!AVR_HAVE_EIJMP_EICALL)
+@@ -249,7 +254,6 @@ extern GTY(()) section *progmem_section;
+
+ #define ORDER_REGS_FOR_LOCAL_ALLOC order_regs_for_local_alloc ()
+
+-
+ #define HARD_REGNO_NREGS(REGNO, MODE) ((GET_MODE_SIZE (MODE) + UNITS_PER_WORD - 1) / UNITS_PER_WORD)
+
+ #define HARD_REGNO_MODE_OK(REGNO, MODE) avr_hard_regno_mode_ok(REGNO, MODE)
+@@ -313,6 +317,41 @@ enum reg_class {
+ {0xffffffff,0x00000003} /* ALL_REGS */ \
+ }
+
++/* Zero or more C statements that may conditionally modify five variables
++ fixed_regs, call_used_regs, global_regs, reg_names, and reg_class_contents,
++ to take into account any dependence of these register sets on target flags.
++ The first three of these are of type char [] (interpreted as Boolean
++ vectors). global_regs is a const char *[], and reg_class_contents is a
++ HARD_REG_SET. Before the macro is called, fixed_regs, call_used_regs,
++ reg_class_contents, and reg_names have been initialized from
++ FIXED_REGISTERS, CALL_USED_REGISTERS, REG_CLASS_CONTENTS, and
++ REGISTER_NAMES, respectively. global_regs has been cleared, and any
++ \91-ffixed-reg\92, \91-fcall-used-reg\92 and \91-fcall-saved-reg\92 command options
++ have been applied.
++
++ You need not define this macro if it has no work to do.
++
++ If the usage of an entire class of registers depends on the target flags,
++ you may indicate this to GCC by using this macro to modify fixed_regs and
++ call_used_regs to 1 for each of the registers in the classes which should
++ not be used by GCC. Also define the macro REG_CLASS_FROM_LETTER /
++ REG_CLASS_FROM_CONSTRAINT to return NO_REGS if it is called with a letter
++ for a class that shouldn\92t be used. (However, if this class is not included
++ in GENERAL_REGS and all of the insn patterns whose constraints permit this
++ class are controlled by target switches, then GCC will automatically avoid
++ using these registers when the target switches are opposed to them.) */
++
++#define CONDITIONAL_REGISTER_USAGE \
++ if (AVR_TINY) { \
++ int i; \
++ for (i = 0; i <= 17; i++) { \
++ fixed_regs[i] = 1; \
++ call_used_regs[i] = 1; \
++ } \
++ CLEAR_HARD_REG_SET(reg_class_contents[(int)ADDW_REGS]); \
++ CLEAR_HARD_REG_SET(reg_class_contents[(int)NO_LD_REGS]); \
++ }
++
+ #define REGNO_REG_CLASS(R) avr_regno_reg_class(R)
+
+ /* The following macro defines cover classes for Integrated Register
+diff -Naurp gcc/config/avr/avr.md gcc/config/avr/avr.md
+--- gcc/config/avr/avr.md 2011-09-02 11:45:05.000000000 +0300
++++ gcc/config/avr/avr.md 2011-09-02 11:46:03.000000000 +0300
+@@ -186,6 +186,9 @@
+ DONE;
+ })
+
++(define_constants
++ [(TMP_REGNO_AVRTINY10 16) ; temporary register r16
++ (ZERO_REGNO_AVRTINY10 17)]) ; zero register r17
+
+ (define_insn "*push<ALLQ:mode>"
+ [(set (mem:ALLQ (post_dec (reg:HI REG_SP)))
+@@ -479,7 +482,7 @@
+ rtx addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
+
+ /* Create rtx for tmp register - we use this as scratch. */
+- rtx tmp_reg_rtx = gen_rtx_REG (QImode, TMP_REGNO);
++ rtx tmp_reg_rtx = gen_rtx_REG (QImode, AVR_TINY ? TMP_REGNO_AVRTINY10 : TMP_REGNO);
+
+ if (GET_CODE (operands[2]) != CONST_INT)
+ FAIL;
+@@ -2900,7 +2903,7 @@
+ UNSPEC_INDEX_JMP))
+ (use (label_ref (match_operand 1 "" "")))
+ (clobber (match_dup 0))]
+- "AVR_HAVE_JMP_CALL && !AVR_HAVE_EIJMP_EICALL"
++ "(AVR_HAVE_JMP_CALL && !AVR_HAVE_EIJMP_EICALL)"
+ "lsl r30
+ rol r31
+ lpm
+diff -Naurp gcc/config/avr/libgcc-fixed.S gcc/config/avr/libgcc-fixed.S
+--- gcc/config/avr/libgcc-fixed.S 2011-09-02 11:40:55.000000000 +0300
++++ gcc/config/avr/libgcc-fixed.S 2011-09-02 11:46:03.000000000 +0300
+@@ -29,13 +29,17 @@ Boston, MA 02110-1301, USA. */
+
+ /* Fixed point library routines for avr. */
+
++#if defined (__AVR_TINY__)
++#define __zero_reg__ r17
++#define __tmp_reg__ r16
++#else
+ #define __zero_reg__ r1
+ #define __tmp_reg__ r0
++#endif
+ #define __SREG__ 0x3f
+ #define __SP_H__ 0x3e
+ #define __SP_L__ 0x3d
+ #define __RAMPZ__ 0x3B
+-
+ /* Conversions to float. */
+ #if defined (L_fractqqsf)
+ .global __fractqqsf
+@@ -281,15 +285,15 @@ __muluqq3_exit:
+ .func __mulhq3
+ __mulhq3:
+ fmuls r_arg1H, r_arg2H
+- movw r_resL, r0
++ movw r_resL, __tmp_reg__
+ fmulsu r_arg2H, r_arg1L
+ clr r_arg1L
+ sbc r_resH, r_arg1L
+- add r_resL, r1
++ add r_resL, __zero_reg__
+ adc r_resH, r_arg1L
+ fmulsu r_arg1H, r_arg2L
+ sbc r_resH, r_arg1L
+- add r_resL, r1
++ add r_resL, __zero_reg__
+ adc r_resH, r_arg1L
+ clr __zero_reg__
+ ret
+@@ -301,13 +305,13 @@ __mulhq3:
+ .func __muluhq3
+ __muluhq3:
+ mul r_arg1H, r_arg2H
+- movw r_resL, r0
++ movw r_resL, __tmp_reg__
+ mul r_arg1H, r_arg2L
+- add r_resL, r1
++ add r_resL, __zero_reg__
+ clr __zero_reg__
+ adc r_resH, __zero_reg__
+ mul r_arg1L, r_arg2H
+- add r_resL, r1
++ add r_resL, __zero_reg__
+ clr __zero_reg__
+ adc r_resH, __zero_reg__
+ ret
+@@ -401,15 +405,15 @@ __muluhq3_skip:
+ .func __mulha3
+ __mulha3:
+ mul r_arg1L, r_arg2L
+- mov r_resL, r1
++ mov r_resL, __zero_reg__
+ muls r_arg1H, r_arg2H
+- mov r_resH, r0
++ mov r_resH, __tmp_reg__
+ mulsu r_arg1H, r_arg2L
+- add r_resL, r0
+- adc r_resH, r1
++ add r_resL, __tmp_reg__
++ adc r_resH, __zero_reg__
+ mulsu r_arg2H, r_arg1L
+- add r_resL, r0
+- adc r_resH, r1
++ add r_resL, __tmp_reg__
++ adc r_resH, __zero_reg__
+ clr __zero_reg__
+ ret
+ .endfunc
+@@ -420,15 +424,15 @@ __mulha3:
+ .func __muluha3
+ __muluha3:
+ mul r_arg1L, r_arg2L
+- mov r_resL, r1
++ mov r_resL, __zero_reg__
+ mul r_arg1H, r_arg2H
+- mov r_resH, r0
++ mov r_resH, __tmp_reg__
+ mul r_arg1H, r_arg2L
+- add r_resL, r0
+- adc r_resH, r1
++ add r_resL, __tmp_reg__
++ adc r_resH, __zero_reg__
+ mul r_arg1L, r_arg2H
+- add r_resL, r0
+- adc r_resH, r1
++ add r_resL, __tmp_reg__
++ adc r_resH, __zero_reg__
+ clr __zero_reg__
+ ret
+ .endfunc
+@@ -442,8 +446,8 @@ __muluha3:
+ #define r_arg2H r23 /* multiplicand High */
+ #define r_resL r18 /* result Low */
+ #define r_resH r19 /* result High */
+-#define r_scratchL r0 /* scratch Low */
+-#define r_scratchH r1
++#define r_scratchL __tmp_reg__ /* scratch Low */
++#define r_scratchH __zero_reg__
+
+ #if defined (L_mulha3)
+ .global __mulha3
+@@ -480,8 +484,8 @@ __mulha3_exit:
+ __muluha3:
+ clr r_resL ; clear result
+ clr r_resH
+- mov_l r0, r_arg1L ; save multiplicand
+- mov_h r1, r_arg1H
++ mov_l __tmp_reg__, r_arg1L ; save multiplicand
++ mov_h __zero_reg__, r_arg1H
+ __muluha3_loop1:
+ sbrs r_arg2H,0
+ rjmp __muluha3_skip1
+@@ -490,7 +494,12 @@ __muluha3_loop1:
+ __muluha3_skip1:
+ lsl r_arg1L ; shift multiplicand
+ rol r_arg1H
++#if defined (__AVR_TINY__)
++ subi r_arg1L, lo8(0)
++ sbci r_arg1L, hi8(0)
++#else
+ sbiw r_arg1L,0
++#endif
+ breq __muluha3_loop1_done ; exit multiplicand = 0
+ lsr r_arg2H
+ brne __muluha3_loop1 ; exit multiplier = 0
+@@ -500,7 +509,12 @@ __muluha3_loop1_done:
+ __muluha3_loop2:
+ lsr r_arg1H ; shift multiplicand
+ ror r_arg1L
++#if defined (__AVR_TINY__)
++ subi r_arg1L, lo8(0)
++ sbci r_arg1L, hi8(0)
++#else
+ sbiw r_arg1L,0
++#endif
+ breq __muluha3_exit ; exit if multiplicand = 0
+ sbrs r_arg2L,7
+ rjmp __muluha3_skip2
+@@ -556,53 +570,53 @@ __mulsa3:
+ clr r_resHL
+ clr r_resHH
+ mul r_arg1H, r_arg2L
+- mov r_resL, r1
++ mov r_resL, __zero_reg__
+ mul r_arg1L, r_arg2H
+- add r_resL, r1
++ add r_resL, __zero_reg__
+ adc r_resH, r_clr
+ mul r_arg1L, r_arg2HL
+- add r_resL, r0
+- adc r_resH, r1
++ add r_resL, __tmp_reg__
++ adc r_resH, __zero_reg__
+ adc r_resHL, r_clr
+ mul r_arg1H, r_arg2H
+- add r_resL, r0
+- adc r_resH, r1
++ add r_resL, __tmp_reg__
++ adc r_resH, __zero_reg__
+ adc r_resHL, r_clr
+ mul r_arg1HL, r_arg2L
+- add r_resL, r0
+- adc r_resH, r1
++ add r_resL, __tmp_reg__
++ adc r_resH, __zero_reg__
+ adc r_resHL, r_clr
+ mulsu r_arg2HH, r_arg1L
+ sbc r_resHH, r_clr
+- add r_resH, r0
+- adc r_resHL, r1
++ add r_resH, __tmp_reg__
++ adc r_resHL, __zero_reg__
+ adc r_resHH, r_clr
+ mul r_arg1H, r_arg2HL
+- add r_resH, r0
+- adc r_resHL, r1
++ add r_resH, __tmp_reg__
++ adc r_resHL, __zero_reg__
+ adc r_resHH, r_clr
+ mul r_arg1HL, r_arg2H
+- add r_resH, r0
+- adc r_resHL, r1
++ add r_resH, __tmp_reg__
++ adc r_resHL, __zero_reg__
+ adc r_resHH, r_clr
+ mulsu r_arg1HH, r_arg2L
+ sbc r_resHH, r_clr
+- add r_resH, r0
+- adc r_resHL, r1
++ add r_resH, __tmp_reg__
++ adc r_resHL, __zero_reg__
+ adc r_resHH, r_clr
+ mulsu r_arg2HH, r_arg1H
+- add r_resHL, r0
+- adc r_resHH, r1
++ add r_resHL, __tmp_reg__
++ adc r_resHH, __zero_reg__
+ mul r_arg1HL, r_arg2HL
+- add r_resHL, r0
+- adc r_resHH, r1
++ add r_resHL, __tmp_reg__
++ adc r_resHH, __zero_reg__
+ mulsu r_arg1HH, r_arg2H
+- add r_resHL, r0
+- adc r_resHH, r1
++ add r_resHL, __tmp_reg__
++ adc r_resHH, __zero_reg__
+ mulsu r_arg2HH, r_arg1HL
+- add r_resHH, r0
++ add r_resHH, __tmp_reg__
+ mulsu r_arg1HH, r_arg2HL
+- add r_resHH, r0
++ add r_resHH, __tmp_reg__
+ clr __zero_reg__
+ ret
+ .endfunc
+@@ -617,51 +631,51 @@ __mulusa3:
+ clr r_resHL
+ clr r_resHH
+ mul r_arg1H, r_arg2L
+- mov r_resL, r1
++ mov r_resL, __zero_reg__
+ mul r_arg1L, r_arg2H
+- add r_resL, r1
++ add r_resL, __zero_reg__
+ adc r_resH, r_clr
+ mul r_arg1L, r_arg2HL
+- add r_resL, r0
+- adc r_resH, r1
++ add r_resL, __tmp_reg__
++ adc r_resH, __zero_reg__
+ adc r_resHL, r_clr
+ mul r_arg1H, r_arg2H
+- add r_resL, r0
+- adc r_resH, r1
++ add r_resL, __tmp_reg__
++ adc r_resH, __zero_reg__
+ adc r_resHL, r_clr
+ mul r_arg1HL, r_arg2L
+- add r_resL, r0
+- adc r_resH, r1
++ add r_resL, __tmp_reg__
++ adc r_resH, __zero_reg__
+ adc r_resHL, r_clr
+ mul r_arg1L, r_arg2HH
+- add r_resH, r0
+- adc r_resHL, r1
++ add r_resH, __tmp_reg__
++ adc r_resHL, __zero_reg__
+ adc r_resHH, r_clr
+ mul r_arg1H, r_arg2HL
+- add r_resH, r0
+- adc r_resHL, r1
++ add r_resH, __tmp_reg__
++ adc r_resHL, __zero_reg__
+ adc r_resHH, r_clr
+ mul r_arg1HL, r_arg2H
+- add r_resH, r0
+- adc r_resHL, r1
++ add r_resH, __tmp_reg__
++ adc r_resHL, __zero_reg__
+ adc r_resHH, r_clr
+ mul r_arg1HH, r_arg2L
+- add r_resH, r0
+- adc r_resHL, r1
++ add r_resH, __tmp_reg__
++ adc r_resHL, __zero_reg__
+ adc r_resHH, r_clr
+ mul r_arg1H, r_arg2HH
+- add r_resHL, r0
+- adc r_resHH, r1
++ add r_resHL, __tmp_reg__
++ adc r_resHH, __zero_reg__
+ mul r_arg1HL, r_arg2HL
+- add r_resHL, r0
+- adc r_resHH, r1
++ add r_resHL, __tmp_reg__
++ adc r_resHH, __zero_reg__
+ mul r_arg1HH, r_arg2H
+- add r_resHL, r0
+- adc r_resHH, r1
++ add r_resHL, __tmp_reg__
++ adc r_resHH, __zero_reg__
+ mul r_arg1HL, r_arg2HH
+- add r_resHH, r0
++ add r_resHH, __tmp_reg__
+ mul r_arg1HH, r_arg2HL
+- add r_resHH, r0
++ add r_resHH, __tmp_reg__
+ clr __zero_reg__
+ ret
+ .endfunc
+@@ -680,13 +694,20 @@ __mulusa3:
+ #define r_arg2HL r26
+ #define r_arg2HH r27 /* multiplicand High */
+
++#if defined (__AVR_TINY__)
++#define r_resL r28 /* result Low */
++#define r_resH r29
++#define r_resHL r30
++#define r_resHH r31 /* result High */
++#else
+ #define r_resL r14 /* result Low */
+ #define r_resH r15
+ #define r_resHL r16
+ #define r_resHH r17 /* result High */
++#endif
+
+-#define r_scratchL r0 /* scratch Low */
+-#define r_scratchH r1
++#define r_scratchL __tmp_reg__ /* scratch Low */
++#define r_scratchH __zero_reg__
+ #define r_scratchHL r22
+ #define r_scratchHH r23 /* scratch High */
+
+@@ -758,7 +779,12 @@ __mulusa3_skip1:
+ rol r_arg1HH
+ lsr r_arg2HH
+ ror r_arg2HL
++#if defined (__AVR_TINY__)
++ subi r_arg2HL, lo8(0)
++ sbci r_arg2HL, hi8(0)
++#else
+ sbiw r_arg2HL,0
++#endif
+ brne __mulusa3_loop1 ; exit multiplier = 0
+ __mulusa3_loop1_done:
+ mov_l r_arg1L, r_scratchL ; restore multiplicand
+@@ -779,7 +805,12 @@ __mulusa3_loop2:
+ __mulusa3_skip2:
+ lsl r_arg2L
+ rol r_arg2H
++#if defined (__AVR_TINY__)
++ subi r_arg2L, lo8(0)
++ sbci r_arg2L, hi8(0)
++#else
+ sbiw r_arg2L,0
++#endif
+ brne __mulusa3_loop2 ; exit if multiplier = 0
+ __mulusa3_exit:
+ clr __zero_reg__ ; got clobbered
+@@ -791,9 +822,7 @@ __mulusa3_exit:
+ #undef r_scratchH
+ #undef r_scratchHL
+ #undef r_scratchHH
+-
+ #endif
+-
+ #undef r_arg1L
+ #undef r_arg1H
+ #undef r_arg1HL
+@@ -821,8 +850,8 @@ __mulusa3_exit:
+ .global __divqq3
+ .func __divqq3
+ __divqq3:
+- mov r0, r_divd
+- eor r0, r_div
++ mov __tmp_reg__, r_divd
++ eor __tmp_reg__, r_div
+ sbrc r_div, 7
+ neg r_div
+ sbrc r_divd, 7
+@@ -831,7 +860,7 @@ __divqq3:
+ breq __divqq3_minus1 ; if equal return -1
+ rcall __udivuqq3
+ lsr r_quo
+- sbrc r0, 7 ; negate result if needed
++ sbrc __tmp_reg__, 7 ; negate result if needed
+ neg r_quo
+ ret
+ __divqq3_minus1:
+@@ -886,8 +915,8 @@ __udivuqq3_cont:
+ .global __divhq3
+ .func __divhq3
+ __divhq3:
+- mov r0, r_divdH
+- eor r0, r_divH
++ mov __tmp_reg__, r_divdH
++ eor __tmp_reg__, r_divH
+ sbrs r_divH, 7
+ rjmp __divhq3_divpos
+ com r_divH
+@@ -906,7 +935,7 @@ __divhq3_divdpos:
+ rcall __udivuhq3
+ lsr r_quoH
+ ror r_quoL
+- sbrs r0, 7 ; negate result if needed
++ sbrs __tmp_reg__, 7 ; negate result if needed
+ ret
+ com r_quoH
+ neg r_quoL
+@@ -958,8 +987,8 @@ __udivuhq3_cont:
+ .global __divha3
+ .func __divha3
+ __divha3:
+- mov r0, r_divdH
+- eor r0, r_divH
++ mov __tmp_reg__, r_divdH
++ eor __tmp_reg__, r_divH
+ sbrs r_divH, 7
+ rjmp __divha3_divpos
+ com r_divH
+@@ -973,7 +1002,7 @@ __divha3_divpos:
+ sbci r_divdH,-1
+ __divha3_divdpos:
+ rcall __udivuha3
+- sbrs r0, 7 ; negate result if needed
++ sbrs __tmp_reg__, 7 ; negate result if needed
+ ret
+ com r_quoH
+ neg r_quoL
+@@ -1027,8 +1056,8 @@ __udivuha3:
+ .global __divsa3
+ .func __divsa3
+ __divsa3:
+- mov r0, r27
+- eor r0, r_divHH
++ mov __tmp_reg__, r27
++ eor __tmp_reg__, r_divHH
+ sbrs r_divHH, 7
+ rjmp __divsa3_divpos
+ com r_divHH
+@@ -1050,7 +1079,7 @@ __divsa3_divpos:
+ sbci r_arg1HH,-1
+ __divsa3_arg1pos:
+ rcall __udivusa3
+- sbrs r0, 7 ; negate result if needed
++ sbrs __tmp_reg__, 7 ; negate result if needed
+ ret
+ com r_quoHH
+ com r_quoHL
+diff -Naurp gcc/config/avr/libgcc.S gcc/config/avr/libgcc.S
+--- gcc/config/avr/libgcc.S 2011-09-02 11:45:05.000000000 +0300
++++ gcc/config/avr/libgcc.S 2011-09-02 11:46:03.000000000 +0300
+@@ -22,8 +22,13 @@ a copy of the GCC Runtime Library Except
+ see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
+ <http://www.gnu.org/licenses/>. */
+
++#if defined (__AVR_TINY__)
++#define __zero_reg__ r17
++#define __tmp_reg__ r16
++#else
+ #define __zero_reg__ r1
+ #define __tmp_reg__ r0
++#endif
+ #define __SREG__ 0x3f
+ #define __SP_H__ 0x3e
+ #define __SP_L__ 0x3d
+@@ -140,7 +145,12 @@ __mulhi3_skip1:
+
+ lsr r_arg1H ; gets LSB of multiplier
+ ror r_arg1L
++#if defined (__AVR_TINY__)
++ subi r_arg1L, lo8(0)
++ sbci r_arg1L, hi8(0)
++#else
+ sbiw r_arg1L,0
++#endif
+ brne __mulhi3_loop ; exit if multiplier = 0
+ __mulhi3_exit:
+ mov r_arg1H,r_resH ; result to return register
+@@ -304,7 +314,12 @@ __mulsi3_skip1:
+ ror r_arg1H
+ ror r_arg1L
+ brne __mulsi3_loop
++#if defined (__AVR_TINY__)
++ subi r_arg1HL, lo8(0)
++ sbci r_arg1HL, hi8(0)
++#else
+ sbiw r_arg1HL,0
++#endif
+ cpc r_arg1H,r_arg1L
+ brne __mulsi3_loop ; exit if multiplier = 0
+ __mulsi3_exit:
+@@ -610,6 +625,7 @@ __divmodsi4_neg1:
+ /**********************************
+ * This is a prologue subroutine
+ **********************************/
++#if !defined (__AVR_TINY__)
+ #if defined (L_prologue)
+
+ .global __prologue_saves__
+@@ -663,7 +679,6 @@ __prologue_saves__:
+ * This is an epilogue subroutine
+ */
+ #if defined (L_epilogue)
+-
+ .global __epilogue_restores__
+ .func __epilogue_restores__
+ __epilogue_restores__:
+@@ -704,6 +719,7 @@ __epilogue_restores__:
+ ret
+ .endfunc
+ #endif /* defined (L_epilogue) */
++#endif /* !defined (__AVR_TINY__) */
+
+ #ifdef L_exit
+ .section .fini9,"ax",@progbits
+@@ -730,6 +746,7 @@ _cleanup:
+ .endfunc
+ #endif /* defined (L_cleanup) */
+
++#if !defined(__AVR_TINY__)
+ #ifdef L_tablejump
+ .global __tablejump2__
+ .func __tablejump2__
+@@ -762,7 +779,9 @@ __tablejump__:
+ #endif
+ .endfunc
+ #endif /* defined (L_tablejump) */
++#endif
+
++#if !defined(__AVR_TINY__)
+ #ifdef L_copy_data
+ .section .init4,"ax",@progbits
+ .global __do_copy_data
+@@ -824,6 +843,7 @@ __do_copy_data:
+ brne .L__do_copy_data_loop
+ #endif /* !defined(__AVR_HAVE_ELPMX__) && !defined(__AVR_HAVE_ELPM__) */
+ #endif /* L_copy_data */
++#endif
+
+ /* __do_clear_bss is only necessary if there is anything in .bss section. */
+
+@@ -864,7 +884,12 @@ __do_global_ctors:
+ ldi r20, hh8(__ctors_end)
+ rjmp .L__do_global_ctors_start
+ .L__do_global_ctors_loop:
++#if defined (__AVR_TINY__)
++ subi r28, lo8(2)
++ sbci r29, hi8(2)
++#else
+ sbiw r28, 2
++#endif
+ sbc r20, __zero_reg__
+ mov_h r31, r29
+ mov_l r30, r28
+@@ -882,7 +907,12 @@ __do_global_ctors:
+ ldi r29, hi8(__ctors_end)
+ rjmp .L__do_global_ctors_start
+ .L__do_global_ctors_loop:
++#if defined (__AVR_TINY__)
++ subi r28, lo8(2)
++ sbci r29, hi8(2)
++#else
+ sbiw r28, 2
++#endif
+ mov_h r31, r29
+ mov_l r30, r28
+ XCALL __tablejump__
+@@ -905,7 +935,12 @@ __do_global_dtors:
+ ldi r20, hh8(__dtors_start)
+ rjmp .L__do_global_dtors_start
+ .L__do_global_dtors_loop:
++#if defined (__AVR_TINY__)
++ subi r28, lo8(2)
++ sbci r29, hi8(2)
++#else
+ sbiw r28, 2
++#endif
+ sbc r20, __zero_reg__
+ mov_h r31, r29
+ mov_l r30, r28
+@@ -926,7 +961,12 @@ __do_global_dtors:
+ mov_h r31, r29
+ mov_l r30, r28
+ XCALL __tablejump__
++#if defined (__AVR_TINY__)
++ subi r28, lo8(-2)
++ sbci r29, hi8(-2)
++#else
+ adiw r28, 2
++#endif
+ .L__do_global_dtors_start:
+ cpi r28, lo8(__dtors_end)
+ cpc r29, r17
+@@ -934,6 +974,7 @@ __do_global_dtors:
+ #endif /* defined(__AVR_HAVE_RAMPZ__) */
+ #endif /* L_dtors */
+
++#if !defined (__AVR_TINY__)
+ #ifdef L_tablejump_elpm
+ .global __tablejump_elpm__
+ .func __tablejump_elpm__
+@@ -963,5 +1004,6 @@ __tablejump_elpm__:
+ #endif /* defined (__AVR_HAVE_ELPM__) */
+ .endfunc
+ #endif /* defined (L_tablejump_elpm) */
++#endif /* !defined (__AVR_TINY__) */
+
+ #include "libgcc-fixed.S"
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-02 11:45:05.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-02 11:46:03.000000000 +0300
+@@ -107,8 +107,8 @@ fp-bit.c: $(srcdir)/config/fp-bit.c $(sr
+
+ FPBIT = fp-bit.c
+
+-MULTILIB_OPTIONS = mmcu=avr2/mmcu=avr25/mmcu=avr3/mmcu=avr31/mmcu=avr35/mmcu=avr4/mmcu=avr5/mmcu=avr51/mmcu=avr6/mmcu=avrxmega2/mmcu=avrxmega4/mmcu=avrxmega5/mmcu=avrxmega6/mmcu=avrxmega7
+-MULTILIB_DIRNAMES = avr2 avr25 avr3 avr31 avr35 avr4 avr5 avr51 avr6 avrxmega2 avrxmega4 avrxmega5 avrxmega6 avrxmega7
++MULTILIB_OPTIONS = mmcu=avr2/mmcu=avr25/mmcu=avr3/mmcu=avr31/mmcu=avr35/mmcu=avr4/mmcu=avr5/mmcu=avr51/mmcu=avr6/mmcu=avrxmega2/mmcu=avrxmega4/mmcu=avrxmega5/mmcu=avrxmega6/mmcu=avrxmega7/mmcu=avrtiny10
++MULTILIB_DIRNAMES = avr2 avr25 avr3 avr31 avr35 avr4 avr5 avr51 avr6 avrxmega2 avrxmega4 avrxmega5 avrxmega6 avrxmega7 avrtiny10
+
+ # The many avr2 matches are not listed here - this is the default.
+ MULTILIB_MATCHES = \
+@@ -241,7 +241,13 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega6=mmcu?atxmega256a3b \
+ mmcu?avrxmega6=mmcu?atxmega256d3 \
+ mmcu?avrxmega7=mmcu?atxmega128a1 \
+- mmcu?avrxmega7=mmcu?atxmega128a1u
++ mmcu?avrxmega7=mmcu?atxmega128a1u \
++ mmcu?avrtiny10=mmcu?attiny4 \
++ mmcu?avrtiny10=mmcu?attiny5 \
++ mmcu?avrtiny10=mmcu?attiny9 \
++ mmcu?avrtiny10=mmcu?attiny10 \
++ mmcu?avrtiny10=mmcu?attiny20 \
++ mmcu?avrtiny10=mmcu?attiny40
+
+ MULTILIB_EXCEPTIONS =
+
--- /dev/null
+diff -Naurp gcc/config/avr/avr.c gcc/config/avr/avr.c
+--- gcc/config/avr/avr.c 2011-01-19 13:45:00.000000000 -0600
++++ gcc/config/avr/avr.c 2011-01-19 13:45:47.000000000 -0600
+@@ -784,7 +784,8 @@ expand_prologue (void)
+ }
+ else if ((!AVR_XMEGA && TARGET_NO_INTERRUPTS)
+ || (!AVR_XMEGA && cfun->machine->is_signal)
+- || (!AVR_XMEGA && cfun->machine->is_OS_main))
++ || (!AVR_XMEGA && cfun->machine->is_OS_main)
++ || (AVR_XMEGA && cfun->machine->is_nmi))
+ {
+ insn =
+ emit_insn (gen_movhi_sp_r_irq_off (stack_pointer_rtx,
+@@ -963,7 +964,8 @@ expand_epilogue (void)
+ emit_move_insn (stack_pointer_rtx, frame_pointer_rtx);
+ }
+ else if ((!AVR_XMEGA && TARGET_NO_INTERRUPTS)
+- || (!AVR_XMEGA && cfun->machine->is_signal))
++ || (!AVR_XMEGA && cfun->machine->is_signal)
++ || (AVR_XMEGA && cfun->machine->is_nmi))
+ {
+ emit_insn (gen_movhi_sp_r_irq_off (stack_pointer_rtx,
+ frame_pointer_rtx));
+diff -Naurp gcc/function.c gcc/function.c
+--- gcc/function.c 2010-02-26 09:58:57.000000000 -0600
++++ gcc/function.c 2011-01-19 13:45:48.000000000 -0600
+@@ -4980,6 +4980,14 @@ contains (const_rtx insn, htab_t hash)
+ }
+
+ int
++prologue_contains (const_rtx insn)
++{
++ if (contains (insn, prologue_insn_hash))
++ return 1;
++ return 0;
++}
++
++int
+ prologue_epilogue_contains (const_rtx insn)
+ {
+ if (contains (insn, prologue_insn_hash))
+diff -Naurp gcc/rtl.h gcc/rtl.h
+--- gcc/rtl.h 2010-03-16 05:50:42.000000000 -0500
++++ gcc/rtl.h 2011-01-19 13:45:48.000000000 -0600
+@@ -2296,6 +2296,7 @@ extern void print_inline_rtx (FILE *, co
+
+ /* In function.c */
+ extern void reposition_prologue_and_epilogue_notes (void);
++extern int prologue_contains (const_rtx);
+ extern int prologue_epilogue_contains (const_rtx);
+ extern int sibcall_epilogue_contains (const_rtx);
+ extern void mark_temp_addr_taken (rtx);
---- ./gcc/config/avr/predicates.md.orig 2007-08-02 12:49:31.000000000 +0200
-+++ ./gcc/config/avr/predicates.md 2010-03-05 15:25:53.000000000 +0100
-@@ -27,6 +27,11 @@
- (and (match_code "reg")
- (match_test "REGNO (op) >= 16 && REGNO (op) <= 31")))
-
-+;; Registers from r16 to 24.
-+(define_predicate "a_register_operand"
-+ (and (match_code "reg")
-+ (match_test "REGNO (op) >= 16 && REGNO (op) <= 24")))
-+
- (define_predicate "even_register_operand"
- (and (match_code "reg")
- (and (match_test "REGNO (op) <= 31")
---- ./gcc/config/avr/avr.md.orig 2010-03-05 15:20:25.000000000 +0100
-+++ ./gcc/config/avr/avr.md 2010-03-05 15:25:53.000000000 +0100
-@@ -52,12 +52,26 @@
-
- (UNSPEC_STRLEN 0)
- (UNSPEC_INDEX_JMP 1)
-- (UNSPEC_SEI 2)
-- (UNSPEC_CLI 3)
-- (UNSPEC_SWAP 4)
--
-+ (UNSPEC_SWAP 2)
-+ (UNSPEC_FMUL 3)
-+ (UNSPEC_FMULS 4)
-+ (UNSPEC_FMULSU 5)
-+
- (UNSPECV_PROLOGUE_SAVES 0)
-- (UNSPECV_EPILOGUE_RESTORES 1)])
-+ (UNSPECV_EPILOGUE_RESTORES 1)
-+ (UNSPECV_SEI 2)
-+ (UNSPECV_CLI 3)
-+ (UNSPECV_NOP 4)
-+ (UNSPECV_NOP2 5)
-+ (UNSPECV_SLEEP 6)
-+ (UNSPECV_WDR 7)
-+
-+ (UNSPECV_DELAY_CYCLES 100)
-+ (UNSPECV_DELAY_CYCLES_1 101)
-+ (UNSPECV_DELAY_CYCLES_2 102)
-+ (UNSPECV_DELAY_CYCLES_3 103)
-+ (UNSPECV_DELAY_CYCLES_4 104)])
-+
-
- (include "predicates.md")
- (include "constraints.md")
-@@ -2541,13 +2555,6 @@
- (const_int 1))
- (const_int 3)])])
-
--(define_insn "nop"
-- [(const_int 0)]
-- ""
-- "nop"
-- [(set_attr "cc" "none")
-- (set_attr "length" "1")])
--
- ; indirect jump
- (define_insn "indirect_jump"
- [(set (pc) (match_operand:HI 0 "register_operand" "!z,*r"))]
-@@ -2925,7 +2932,7 @@
-
- ;; Enable Interrupts
- (define_insn "enable_interrupt"
-- [(unspec [(const_int 0)] UNSPEC_SEI)]
-+ [(unspec_volatile [(const_int 0)] UNSPECV_SEI)]
- ""
- "sei"
- [(set_attr "length" "1")
-@@ -2934,7 +2941,7 @@
-
- ;; Disable Interrupts
- (define_insn "disable_interrupt"
-- [(unspec [(const_int 0)] UNSPEC_CLI)]
-+ [(unspec_volatile [(const_int 0)] UNSPECV_CLI)]
- ""
- "cli"
- [(set_attr "length" "1")
-@@ -3034,3 +3041,219 @@
- expand_epilogue ();
- DONE;
- }")
-+
-+;;delay_cycles_delay_cycles_delay_cycles_delay_cycles_delay_cycles_delay
-+;; delay_cycles
-+
-+(define_expand "delay_cycles"
-+ [(unspec_volatile [(match_operand:SI 0 "const_int_operand" "i")]
-+ UNSPECV_DELAY_CYCLES)]
-+ ""
-+ "
-+ rtx loop_reg;
-+ unsigned int cycles = INTVAL (operands[0]);
-+ if (IN_RANGE(cycles, 83886082, 0xFFFFFFFF))
-+ {
-+ unsigned int loop_count = ((cycles - 9) / 6) + 1;
-+ unsigned int cycles_used = (((loop_count - 1) * 6) + 9);
-+ emit_insn (gen_delay_cycles_4 (gen_int_mode (loop_count, SImode)));
-+ cycles -= cycles_used;
-+ }
-+ if (IN_RANGE(cycles, 262145, 83886081))
-+ {
-+ unsigned int loop_count = ((cycles - 7) / 5) + 1;
-+ if (loop_count > 0xFFFFFF)
-+ loop_count = 0xFFFFFF;
-+ unsigned int cycles_used = (((loop_count - 1) * 5) + 7);
-+ emit_insn (gen_delay_cycles_3 (gen_int_mode (loop_count, SImode)));
-+ cycles -= cycles_used;
-+ }
-+ if (IN_RANGE(cycles, 768, 262144))
-+ {
-+ unsigned int loop_count = ((cycles - 5) / 4) + 1;
-+ if (loop_count > 0xFFFF)
-+ loop_count = 0xFFFF;
-+ unsigned int cycles_used = (((loop_count - 1) * 4) + 5);
-+ emit_insn (gen_delay_cycles_2 (gen_int_mode (loop_count, HImode)));
-+ cycles -= cycles_used;
-+ }
-+ if (IN_RANGE(cycles, 6, 767))
-+ {
-+ unsigned int loop_count = (cycles/ 3);
-+ if (loop_count > 255)
-+ loop_count = 255;
-+ unsigned int cycles_used = (loop_count * 3);
-+ emit_insn (gen_delay_cycles_1 (gen_int_mode (loop_count, QImode)));
-+ cycles -= cycles_used;
-+ }
-+ while (cycles >= 2)
-+ {
-+ emit_insn (gen_nop2 ());
-+ cycles -= 2;
-+ }
-+ if (cycles == 1)
-+ {
-+ emit_insn (gen_nop ());
-+ cycles--;
-+ }
-+ DONE;
-+ ")
-+
-+(define_insn "delay_cycles_1"
-+[(unspec_volatile [(const_int 0)] UNSPECV_DELAY_CYCLES_1)
-+ (match_operand:QI 0 "immediate_operand" "")
-+ (clobber (match_scratch:QI 1 "=&d"))]
-+ ""
-+ " ldi %1,lo8(%0)
-+ 1:dec %1
-+ brne 1b"
-+ [(set_attr "length" "3")
-+ (set_attr "cc" "clobber")])
-+
-+(define_insn "delay_cycles_2"
-+ [(unspec_volatile [(const_int 0)] UNSPECV_DELAY_CYCLES_2)
-+ (match_operand:HI 0 "immediate_operand" "")
-+ (clobber (match_scratch:HI 1 "=&w"))]
-+ ""
-+ " ldi %A1,lo8(%0)
-+ ldi %B1,hi8(%0)
-+ 1:sbiw %A1,1
-+ brne 1b"
-+ [(set_attr "length" "4")
-+ (set_attr "cc" "clobber")])
-+
-+(define_insn "delay_cycles_3"
-+ [(unspec_volatile [(const_int 0)] UNSPECV_DELAY_CYCLES_3)
-+ (match_operand:SI 0 "immediate_operand" "")
-+ (clobber (match_scratch:SI 1 "=&d"))]
-+ ""
-+ " ldi %A1,lo8(%0)
-+ ldi %B1,hi8(%0)
-+ ldi %C1,hlo8(%0)
-+ 1:subi %A1,1
-+ sbci %B1,0
-+ sbci %C1,0
-+ brne 1b"
-+ [(set_attr "length" "7")
-+ (set_attr "cc" "clobber")])
-+
-+(define_insn "delay_cycles_4"
-+ [(unspec_volatile [(const_int 0)] UNSPECV_DELAY_CYCLES_4)
-+ (match_operand:SI 0 "immediate_operand" "")
-+ (clobber (match_scratch:SI 1 "=&d"))]
-+ ""
-+ " ldi %A1,lo8(%0)
-+ ldi %B1,hi8(%0)
-+ ldi %C1,hlo8(%0)
-+ ldi %D1,hhi8(%0)
-+ 1:subi %A1,1
-+ sbci %B1,0
-+ sbci %C1,0
-+ sbci %D1,0
-+ brne 1b"
-+ [(set_attr "length" "9")
-+ (set_attr "cc" "clobber")])
-+
-+;; CPU instructions
-+
-+;; NOP
-+(define_insn "nop"
-+ [(unspec_volatile [(const_int 0)] UNSPECV_NOP)]
-+ ""
-+ "nop"
-+ [(set_attr "length" "1")
-+ (set_attr "cc" "none")])
-+
-+;; NOP2
-+(define_insn "nop2"
-+ [(unspec_volatile [(const_int 0)] UNSPECV_NOP2)]
-+ ""
-+ "rjmp ."
-+ [(set_attr "length" "1")
-+ (set_attr "cc" "none")])
-+
-+;; SEI, Enable Interrupts
-+;(define_insn "sei"
-+; [(unspec_volatile [(const_int 0)] UNSPECV_SEI)]
-+; ""
-+; "sei"
-+; [(set_attr "length" "1")
-+; (set_attr "cc" "none")
-+; ])
-+
-+;; CLI, Disable Interrupts
-+;(define_insn "cli"
-+; [(unspec_volatile [(const_int 0)] UNSPECV_CLI)]
-+; ""
-+; "cli"
-+; [(set_attr "length" "1")
-+; (set_attr "cc" "none")
-+; ])
-+
-+;; SLEEP
-+(define_insn "sleep"
-+ [(unspec_volatile [(const_int 0)] UNSPECV_SLEEP)]
-+ ""
-+ "sleep"
-+ [(set_attr "length" "1")
-+ (set_attr "cc" "none")
-+ ])
-+
-+;; WDR
-+(define_insn "wdr"
-+ [(unspec_volatile [(const_int 0)] UNSPECV_WDR)]
-+ ""
-+ "wdr"
-+ [(set_attr "length" "1")
-+ (set_attr "cc" "none")
-+ ])
-+
-+;; SWAP
-+(define_insn "swap"
-+ [(set (match_operand:QI 0 "register_operand" "=r")
-+ (unspec:QI [(match_operand:QI 1 "register_operand" "0")]
-+ UNSPEC_SWAP))]
-+ ""
-+ "swap %0"
-+ [(set_attr "length" "1")
-+ (set_attr "cc" "none")])
-+
-+;; FMUL
-+(define_insn "fmul"
-+ [(set (match_operand:HI 0 "a_register_operand" "=r")
-+ (unspec:HI [(match_operand:QI 1 "a_register_operand" "r")
-+ (match_operand:QI 2 "a_register_operand" "r")]
-+ UNSPEC_FMUL))]
-+ "AVR_HAVE_MUL"
-+ "fmul %1,%2
-+ movw %0,r0
-+ clr r1"
-+ [(set_attr "length" "3")
-+ (set_attr "cc" "clobber")])
-+
-+;; FMULS
-+(define_insn "fmuls"
-+ [(set (match_operand:HI 0 "a_register_operand" "=r")
-+ (unspec:HI [(match_operand:QI 1 "a_register_operand" "r")
-+ (match_operand:QI 2 "a_register_operand" "r")]
-+ UNSPEC_FMULS))]
-+ "AVR_HAVE_MUL"
-+ "fmuls %1,%2
-+ movw %0,r0
-+ clr r1"
-+ [(set_attr "length" "3")
-+ (set_attr "cc" "clobber")])
-+
-+;; FMULSU
-+(define_insn "fmulsu"
-+ [(set (match_operand:HI 0 "a_register_operand" "=r")
-+ (unspec:HI [(match_operand:QI 1 "a_register_operand" "r")
-+ (match_operand:QI 2 "a_register_operand" "r")]
-+ UNSPEC_FMULSU))]
-+ "AVR_HAVE_MUL"
-+ "fmulsu %1,%2
-+ movw %0,r0
-+ clr r1"
-+ [(set_attr "length" "3")
-+ (set_attr "cc" "clobber")])
-+
---- ./gcc/config/avr/avr.c.orig 2010-03-05 15:24:52.000000000 +0100
-+++ ./gcc/config/avr/avr.c 2010-03-05 15:25:53.000000000 +0100
+diff -Naurp gcc/config/avr/avr.c gcc/config/avr/avr.c
+--- gcc/config/avr/avr.c 2011-01-19 13:48:07.000000000 -0600
++++ gcc/config/avr/avr.c 2011-01-19 13:49:37.000000000 -0600
@@ -30,6 +30,7 @@
#include "insn-config.h"
#include "conditions.h"
#include "tm_p.h"
#include "target.h"
#include "target-def.h"
-@@ -87,6 +90,9 @@
- static int avr_address_cost (rtx);
+@@ -87,6 +90,8 @@ static bool avr_rtx_costs (rtx, int, int
+ static int avr_address_cost (rtx, bool);
static bool avr_return_in_memory (const_tree, const_tree);
static struct machine_function * avr_init_machine_status (void);
+static void avr_init_builtins (void);
+static rtx avr_expand_builtin (tree, rtx, rtx, enum machine_mode, int);
-+
- /* Allocate registers from r25 to r8 for parameters for function calls. */
- #define FIRST_CUM_REG 26
-
-@@ -340,6 +346,12 @@
- #undef TARGET_STRICT_ARGUMENT_NAMING
- #define TARGET_STRICT_ARGUMENT_NAMING hook_bool_CUMULATIVE_ARGS_true
+ static rtx avr_builtin_setjmp_frame_value (void);
+ static bool avr_hard_regno_scratch_ok (unsigned int);
+ static unsigned int avr_case_values_threshold (void);
+@@ -197,6 +202,13 @@ static const struct attribute_spec avr_a
+ #undef TARGET_SCALAR_MODE_SUPPORTED_P
+ #define TARGET_SCALAR_MODE_SUPPORTED_P avr_scalar_mode_supported_p
+#undef TARGET_INIT_BUILTINS
+#define TARGET_INIT_BUILTINS avr_init_builtins
-+
++
+#undef TARGET_EXPAND_BUILTIN
+#define TARGET_EXPAND_BUILTIN avr_expand_builtin
+
- struct gcc_target targetm = TARGET_INITIALIZER;
- \f
- void
-@@ -6079,4 +6091,237 @@
- return false;
++
+ /* Implement TARGET_SCALAR_MODE_SUPPORTED_P. */
+ static bool
+ avr_scalar_mode_supported_p (enum machine_mode mode)
+@@ -7286,4 +7298,237 @@ unsigned int avr_case_values_threshold (
+ return (!AVR_HAVE_JMP_CALL || TARGET_CALL_PROLOGUES) ? 8 : 17;
}
+/* Codes for all the AVR builtins. */
+
+ if ((op0mode == SImode || op0mode == VOIDmode) && mode0 == HImode)
+ {
-+ op0mode = HImode;
-+ op0 = gen_lowpart (HImode, op0);
++ op0mode = HImode;
++ op0 = gen_lowpart (HImode, op0);
++ }
++ if ((op1mode == SImode || op1mode == VOIDmode) && mode1 == HImode)
++ {
++ op1mode = HImode;
++ op1 = gen_lowpart (HImode, op1);
++ }
++ /* In case the insn wants input operands in modes different from
++ the result, abort. */
++ gcc_assert ((op0mode == mode0 || op0mode == VOIDmode)
++ && (op1mode == mode1 || op1mode == VOIDmode));
++
++ if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
++ op0 = copy_to_mode_reg (mode0, op0);
++ if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
++ op1 = copy_to_mode_reg (mode1, op1);
++
++ pat = GEN_FCN (icode) (target, op0, op1);
++ if (! pat)
++ return 0;
++
++ emit_insn (pat);
++ return target;
++}
++
++/* Expand an expression EXP that calls a built-in function,
++ with result going to TARGET if that's convenient
++ (and in mode MODE if that's convenient).
++ SUBTARGET may be used as the target for computing one of EXP's operands.
++ IGNORE is nonzero if the value is to be ignored. */
++
++static rtx
++avr_expand_builtin (tree exp, rtx target,
++ rtx subtarget ATTRIBUTE_UNUSED,
++ enum machine_mode mode ATTRIBUTE_UNUSED,
++ int ignore ATTRIBUTE_UNUSED)
++{
++ size_t i;
++ const struct builtin_description *d;
++ tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
++ unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
++ rtx pat;
++ tree arg0;
++ rtx op0;
++
++ switch (fcode)
++ {
++ case AVR_BUILTIN_SEI:
++ emit_insn (gen_enable_interrupt ());
++ return 0;
++ case AVR_BUILTIN_CLI:
++ emit_insn (gen_disable_interrupt ());
++ return 0;
++ case AVR_BUILTIN_WDR:
++ emit_insn (gen_wdr ());
++ return 0;
++ case AVR_BUILTIN_SLEEP:
++ emit_insn (gen_sleep ());
++ return 0;
++ case AVR_BUILTIN_DELAY_CYCLES:
++ {
++ arg0 = CALL_EXPR_ARG (exp, 0);
++ op0 = expand_expr (arg0, NULL_RTX, VOIDmode, 0);
++
++ if (!CONSTANT_P (op0))
++ error ("__builtin_avr_delay_cycles expects an integer constant.");
++
++ emit_insn (gen_delay_cycles (op0));
++ return 0;
++ }
++ }
++
++ for (i = 0, d = bdesc_1arg; i < ARRAY_SIZE (bdesc_1arg); i++, d++)
++ if (d->code == fcode)
++ return avr_expand_unop_builtin (d->icode, exp, target);
++
++ for (i = 0, d = bdesc_1arg; i < ARRAY_SIZE (bdesc_2arg); i++, d++)
++ if (d->code == fcode)
++ return avr_expand_binop_builtin (d->icode, exp, target);
++
++ gcc_unreachable ();
++}
++
+ #include "gt-avr.h"
+diff -Naurp gcc/config/avr/avr.md gcc/config/avr/avr.md
+--- gcc/config/avr/avr.md 2011-01-19 13:45:00.000000000 -0600
++++ gcc/config/avr/avr.md 2011-01-19 13:49:37.000000000 -0600
+@@ -51,14 +51,29 @@
+
+ (UNSPEC_STRLEN 0)
+ (UNSPEC_INDEX_JMP 1)
+- (UNSPEC_SEI 2)
+- (UNSPEC_CLI 3)
++ (UNSPEC_SWAP 2)
++ (UNSPEC_FMUL 3)
++ (UNSPEC_FMULS 4)
++ (UNSPEC_FMULSU 5)
++
+
+ (UNSPECV_PROLOGUE_SAVES 0)
+ (UNSPECV_EPILOGUE_RESTORES 1)
+ (UNSPECV_WRITE_SP_IRQ_ON 2)
+ (UNSPECV_WRITE_SP_IRQ_OFF 3)
+- (UNSPECV_GOTO_RECEIVER 4)])
++ (UNSPECV_GOTO_RECEIVER 4)
++ (UNSPECV_SEI 5)
++ (UNSPECV_CLI 6)
++ (UNSPECV_NOP 7)
++ (UNSPECV_NOP2 8)
++ (UNSPECV_SLEEP 9)
++ (UNSPECV_WDR 10)
++
++ (UNSPECV_DELAY_CYCLES 100)
++ (UNSPECV_DELAY_CYCLES_1 101)
++ (UNSPECV_DELAY_CYCLES_2 102)
++ (UNSPECV_DELAY_CYCLES_3 103)
++ (UNSPECV_DELAY_CYCLES_4 104)])
+
+ (include "predicates.md")
+ (include "constraints.md")
+@@ -2813,13 +2828,6 @@
+ (const_int 1))
+ (const_int 3)])])
+
+-(define_insn "nop"
+- [(const_int 0)]
+- ""
+- "nop"
+- [(set_attr "cc" "none")
+- (set_attr "length" "1")])
+-
+ ; indirect jump
+
+ (define_expand "indirect_jump"
+@@ -3221,7 +3229,7 @@
+
+ ;; Enable Interrupts
+ (define_insn "enable_interrupt"
+- [(unspec [(const_int 0)] UNSPEC_SEI)]
++ [(unspec_volatile [(const_int 0)] UNSPECV_SEI)]
+ ""
+ "sei"
+ [(set_attr "length" "1")
+@@ -3230,7 +3238,7 @@
+
+ ;; Disable Interrupts
+ (define_insn "disable_interrupt"
+- [(unspec [(const_int 0)] UNSPEC_CLI)]
++ [(unspec_volatile [(const_int 0)] UNSPECV_CLI)]
+ ""
+ "cli"
+ [(set_attr "length" "1")
+@@ -3330,3 +3338,219 @@
+ expand_epilogue ();
+ DONE;
+ }")
++
++;;delay_cycles_delay_cycles_delay_cycles_delay_cycles_delay_cycles_delay
++;; delay_cycles
++
++(define_expand "delay_cycles"
++ [(unspec_volatile [(match_operand:SI 0 "const_int_operand" "i")]
++ UNSPECV_DELAY_CYCLES)]
++ ""
++ "
++ rtx loop_reg;
++ unsigned int cycles = INTVAL (operands[0]);
++ if (IN_RANGE(cycles, 83886082, 0xFFFFFFFF))
++ {
++ unsigned int loop_count = ((cycles - 9) / 6) + 1;
++ unsigned int cycles_used = (((loop_count - 1) * 6) + 9);
++ emit_insn (gen_delay_cycles_4 (gen_int_mode (loop_count, SImode)));
++ cycles -= cycles_used;
++ }
++ if (IN_RANGE(cycles, 262145, 83886081))
++ {
++ unsigned int loop_count = ((cycles - 7) / 5) + 1;
++ if (loop_count > 0xFFFFFF)
++ loop_count = 0xFFFFFF;
++ unsigned int cycles_used = (((loop_count - 1) * 5) + 7);
++ emit_insn (gen_delay_cycles_3 (gen_int_mode (loop_count, SImode)));
++ cycles -= cycles_used;
++ }
++ if (IN_RANGE(cycles, 768, 262144))
++ {
++ unsigned int loop_count = ((cycles - 5) / 4) + 1;
++ if (loop_count > 0xFFFF)
++ loop_count = 0xFFFF;
++ unsigned int cycles_used = (((loop_count - 1) * 4) + 5);
++ emit_insn (gen_delay_cycles_2 (gen_int_mode (loop_count, HImode)));
++ cycles -= cycles_used;
+ }
-+ if ((op1mode == SImode || op1mode == VOIDmode) && mode1 == HImode)
++ if (IN_RANGE(cycles, 6, 767))
+ {
-+ op1mode = HImode;
-+ op1 = gen_lowpart (HImode, op1);
++ unsigned int loop_count = (cycles/ 3);
++ if (loop_count > 255)
++ loop_count = 255;
++ unsigned int cycles_used = (loop_count * 3);
++ emit_insn (gen_delay_cycles_1 (gen_int_mode (loop_count, QImode)));
++ cycles -= cycles_used;
+ }
-+ /* In case the insn wants input operands in modes different from
-+ the result, abort. */
-+ gcc_assert ((op0mode == mode0 || op0mode == VOIDmode)
-+ && (op1mode == mode1 || op1mode == VOIDmode));
++ while (cycles >= 2)
++ {
++ emit_insn (gen_nop2 ());
++ cycles -= 2;
++ }
++ if (cycles == 1)
++ {
++ emit_insn (gen_nop ());
++ cycles--;
++ }
++ DONE;
++ ")
+
-+ if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
-+ op0 = copy_to_mode_reg (mode0, op0);
-+ if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
-+ op1 = copy_to_mode_reg (mode1, op1);
++(define_insn "delay_cycles_1"
++[(unspec_volatile [(const_int 0)] UNSPECV_DELAY_CYCLES_1)
++ (match_operand:QI 0 "immediate_operand" "")
++ (clobber (match_scratch:QI 1 "=&d"))]
++ ""
++ " ldi %1,lo8(%0)
++ 1:dec %1
++ brne 1b"
++ [(set_attr "length" "3")
++ (set_attr "cc" "clobber")])
+
-+ pat = GEN_FCN (icode) (target, op0, op1);
-+ if (! pat)
-+ return 0;
++(define_insn "delay_cycles_2"
++ [(unspec_volatile [(const_int 0)] UNSPECV_DELAY_CYCLES_2)
++ (match_operand:HI 0 "immediate_operand" "")
++ (clobber (match_scratch:HI 1 "=&w"))]
++ ""
++ " ldi %A1,lo8(%0)
++ ldi %B1,hi8(%0)
++ 1:sbiw %A1,1
++ brne 1b"
++ [(set_attr "length" "4")
++ (set_attr "cc" "clobber")])
+
-+ emit_insn (pat);
-+ return target;
-+}
++(define_insn "delay_cycles_3"
++ [(unspec_volatile [(const_int 0)] UNSPECV_DELAY_CYCLES_3)
++ (match_operand:SI 0 "immediate_operand" "")
++ (clobber (match_scratch:SI 1 "=&d"))]
++ ""
++ " ldi %A1,lo8(%0)
++ ldi %B1,hi8(%0)
++ ldi %C1,hlo8(%0)
++ 1:subi %A1,1
++ sbci %B1,0
++ sbci %C1,0
++ brne 1b"
++ [(set_attr "length" "7")
++ (set_attr "cc" "clobber")])
+
-+/* Expand an expression EXP that calls a built-in function,
-+ with result going to TARGET if that's convenient
-+ (and in mode MODE if that's convenient).
-+ SUBTARGET may be used as the target for computing one of EXP's operands.
-+ IGNORE is nonzero if the value is to be ignored. */
++(define_insn "delay_cycles_4"
++ [(unspec_volatile [(const_int 0)] UNSPECV_DELAY_CYCLES_4)
++ (match_operand:SI 0 "immediate_operand" "")
++ (clobber (match_scratch:SI 1 "=&d"))]
++ ""
++ " ldi %A1,lo8(%0)
++ ldi %B1,hi8(%0)
++ ldi %C1,hlo8(%0)
++ ldi %D1,hhi8(%0)
++ 1:subi %A1,1
++ sbci %B1,0
++ sbci %C1,0
++ sbci %D1,0
++ brne 1b"
++ [(set_attr "length" "9")
++ (set_attr "cc" "clobber")])
+
-+static rtx
-+avr_expand_builtin (tree exp, rtx target,
-+ rtx subtarget ATTRIBUTE_UNUSED,
-+ enum machine_mode mode ATTRIBUTE_UNUSED,
-+ int ignore ATTRIBUTE_UNUSED)
-+{
-+ size_t i;
-+ const struct builtin_description *d;
-+ tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
-+ unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
-+ rtx pat;
-+ tree arg0;
-+ rtx op0;
++;; CPU instructions
+
-+ switch (fcode)
-+ {
-+ case AVR_BUILTIN_SEI:
-+ emit_insn (gen_enable_interrupt ());
-+ return 0;
-+ case AVR_BUILTIN_CLI:
-+ emit_insn (gen_disable_interrupt ());
-+ return 0;
-+ case AVR_BUILTIN_WDR:
-+ emit_insn (gen_wdr ());
-+ return 0;
-+ case AVR_BUILTIN_SLEEP:
-+ emit_insn (gen_sleep ());
-+ return 0;
-+ case AVR_BUILTIN_DELAY_CYCLES:
-+ {
-+ arg0 = CALL_EXPR_ARG (exp, 0);
-+ op0 = expand_expr (arg0, NULL_RTX, VOIDmode, 0);
++;; NOP
++(define_insn "nop"
++ [(unspec_volatile [(const_int 0)] UNSPECV_NOP)]
++ ""
++ "nop"
++ [(set_attr "length" "1")
++ (set_attr "cc" "none")])
+
-+ if (!CONSTANT_P (op0))
-+ error ("__builtin_avr_delay_cycles expects an integer constant.");
++;; NOP2
++(define_insn "nop2"
++ [(unspec_volatile [(const_int 0)] UNSPECV_NOP2)]
++ ""
++ "rjmp ."
++ [(set_attr "length" "1")
++ (set_attr "cc" "none")])
+
-+ emit_insn (gen_delay_cycles (op0));
-+ return 0;
-+ }
-+ }
++;; SEI, Enable Interrupts
++;(define_insn "sei"
++; [(unspec_volatile [(const_int 0)] UNSPECV_SEI)]
++; ""
++; "sei"
++; [(set_attr "length" "1")
++; (set_attr "cc" "none")
++; ])
+
-+ for (i = 0, d = bdesc_1arg; i < ARRAY_SIZE (bdesc_1arg); i++, d++)
-+ if (d->code == fcode)
-+ return avr_expand_unop_builtin (d->icode, exp, target);
++;; CLI, Disable Interrupts
++;(define_insn "cli"
++; [(unspec_volatile [(const_int 0)] UNSPECV_CLI)]
++; ""
++; "cli"
++; [(set_attr "length" "1")
++; (set_attr "cc" "none")
++; ])
+
-+ for (i = 0, d = bdesc_1arg; i < ARRAY_SIZE (bdesc_2arg); i++, d++)
-+ if (d->code == fcode)
-+ return avr_expand_binop_builtin (d->icode, exp, target);
++;; SLEEP
++(define_insn "sleep"
++ [(unspec_volatile [(const_int 0)] UNSPECV_SLEEP)]
++ ""
++ "sleep"
++ [(set_attr "length" "1")
++ (set_attr "cc" "none")
++ ])
++
++;; WDR
++(define_insn "wdr"
++ [(unspec_volatile [(const_int 0)] UNSPECV_WDR)]
++ ""
++ "wdr"
++ [(set_attr "length" "1")
++ (set_attr "cc" "none")
++ ])
++
++;; SWAP
++(define_insn "swap"
++ [(set (match_operand:QI 0 "register_operand" "=r")
++ (unspec:QI [(match_operand:QI 1 "register_operand" "0")]
++ UNSPEC_SWAP))]
++ ""
++ "swap %0"
++ [(set_attr "length" "1")
++ (set_attr "cc" "none")])
+
-+ gcc_unreachable ();
-+}
++;; FMUL
++(define_insn "fmul"
++ [(set (match_operand:HI 0 "a_register_operand" "=r")
++ (unspec:HI [(match_operand:QI 1 "a_register_operand" "r")
++ (match_operand:QI 2 "a_register_operand" "r")]
++ UNSPEC_FMUL))]
++ "AVR_HAVE_MUL"
++ "fmul %1,%2
++ movw %0,r0
++ clr r1"
++ [(set_attr "length" "3")
++ (set_attr "cc" "clobber")])
+
- #include "gt-avr.h"
++;; FMULS
++(define_insn "fmuls"
++ [(set (match_operand:HI 0 "a_register_operand" "=r")
++ (unspec:HI [(match_operand:QI 1 "a_register_operand" "r")
++ (match_operand:QI 2 "a_register_operand" "r")]
++ UNSPEC_FMULS))]
++ "AVR_HAVE_MUL"
++ "fmuls %1,%2
++ movw %0,r0
++ clr r1"
++ [(set_attr "length" "3")
++ (set_attr "cc" "clobber")])
++
++;; FMULSU
++(define_insn "fmulsu"
++ [(set (match_operand:HI 0 "a_register_operand" "=r")
++ (unspec:HI [(match_operand:QI 1 "a_register_operand" "r")
++ (match_operand:QI 2 "a_register_operand" "r")]
++ UNSPEC_FMULSU))]
++ "AVR_HAVE_MUL"
++ "fmulsu %1,%2
++ movw %0,r0
++ clr r1"
++ [(set_attr "length" "3")
++ (set_attr "cc" "clobber")])
++
+diff -Naurp gcc/config/avr/predicates.md gcc/config/avr/predicates.md
+--- gcc/config/avr/predicates.md 2011-01-19 13:03:59.000000000 -0600
++++ gcc/config/avr/predicates.md 2011-01-19 13:49:37.000000000 -0600
+@@ -27,6 +27,11 @@
+ (and (match_code "reg")
+ (match_test "REGNO (op) >= 16 && REGNO (op) <= 31")))
+
++;; Registers from r16 to 24.
++(define_predicate "a_register_operand"
++ (and (match_code "reg")
++ (match_test "REGNO (op) >= 16 && REGNO (op) <= 24")))
++
+ (define_predicate "even_register_operand"
+ (and (match_code "reg")
+ (and (match_test "REGNO (op) <= 31")
--- /dev/null
+diff -Naurp gcc/config/avr/avr.c gcc/config/avr/avr.c
+--- gcc/config/avr/avr.c 2011-02-07 16:17:20.000000000 -0600
++++ gcc/config/avr/avr.c 2011-02-07 16:12:53.000000000 -0600
+@@ -202,6 +202,9 @@ static const struct attribute_spec avr_a
+ #undef TARGET_SCALAR_MODE_SUPPORTED_P
+ #define TARGET_SCALAR_MODE_SUPPORTED_P avr_scalar_mode_supported_p
+
++#undef TARGET_FIXED_POINT_SUPPORTED_P
++#define TARGET_FIXED_POINT_SUPPORTED_P avr_fixed_point_supported_p
++
+ #undef TARGET_INIT_BUILTINS
+ #define TARGET_INIT_BUILTINS avr_init_builtins
+
+@@ -219,6 +222,17 @@ static const struct attribute_spec avr_a
+ return default_scalar_mode_supported_p (mode);
+ }
+
++ /* Implement TARGET_FIXED_POINT_SUPPORTED_P. */
++ static bool
++ avr_fixed_point_supported_p ()
++ {
++ if (AVR_TINY)
++ return false;
++
++ return default_fixed_point_supported_p ();
++ }
++
++
+ struct gcc_target targetm = TARGET_INITIALIZER;
+ \f
+ void
+diff -Naurp gcc/config/fixed-bit.c gcc/config/fixed-bit.c
+--- gcc/config/fixed-bit.c 2009-04-09 10:00:19.000000000 -0500
++++ gcc/config/fixed-bit.c 2011-02-07 16:12:53.000000000 -0600
+@@ -41,7 +41,7 @@ see the files COPYING3 and COPYING.RUNTI
+ Floating-point: SF, DF
+ Ex: If we define FROM_QQ and TO_SI, the conversion from QQ to SI is
+ generated. */
+-
++#if !defined (__AVR_TINY__)
+ #include "tconfig.h"
+ #include "tsystem.h"
+ #include "coretypes.h"
+@@ -1213,4 +1213,4 @@ SATFRACT (FROM_FLOAT_C_TYPE a)
+ return c;
+ }
+ #endif /* defined(SATFRACT) && FROM_TYPE == 3 && TO_TYPE == 4 */
+-
++#endif /* __AVR_TINY__ */
--- /dev/null
+diff -Naurp gcc/config/avr/avr.c gcc/config/avr/avr.c
+--- gcc/config/avr/avr.c 2011-02-11 14:56:08.000000000 -0600
++++ gcc/config/avr/avr.c 2011-02-11 14:54:05.000000000 -0600
+@@ -211,6 +211,8 @@ static const struct attribute_spec avr_a
+ #undef TARGET_EXPAND_BUILTIN
+ #define TARGET_EXPAND_BUILTIN avr_expand_builtin
+
++#undef TARGET_HELP
++#define TARGET_HELP avr_target_help
+
+ /* Implement TARGET_SCALAR_MODE_SUPPORTED_P. */
+ static bool
+@@ -232,7 +234,24 @@ static const struct attribute_spec avr_a
+ return default_fixed_point_supported_p ();
+ }
+
+-
++/* Implement TARGET_HELP. */
++void
++avr_target_help (void)
++{
++ if (avr_list_supported_parts)
++ {
++ const struct mcu_type_s *list_part;
++ fprintf (stdout, "List of parts supported by avr-gcc:\n");
++ for (list_part = &avr_mcu_types[0]; (list_part + 1)->name; list_part++)
++ {
++ if (!list_part->macro)
++ list_part++;
++ fprintf (stdout, "%-20s%s\n", list_part->name, list_part->macro);
++ }
++ fprintf (stdout, "\n");
++ }
++}
++
+ struct gcc_target targetm = TARGET_INITIALIZER;
+ \f
+ void
+diff -Naurp gcc/config/avr/avr.opt gcc/config/avr/avr.opt
+--- gcc/config/avr/avr.opt 2009-10-08 13:28:48.000000000 -0500
++++ gcc/config/avr/avr.opt 2011-02-11 14:53:20.000000000 -0600
+@@ -58,3 +58,7 @@ Relax branches
+ mpmem-wrap-around
+ Target Report
+ Make the linker relaxation machine assume that a program counter wrap-around occures.
++
++mlist-devices
++Target RejectNegative Var(avr_list_supported_parts)
++Print the list of parts supported while printing --target-help
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-02 11:47:23.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-02 11:49:57.000000000 +0300
+@@ -75,15 +75,23 @@ const struct mcu_type_s avr_mcu_types[]
+ { "attiny13", ARCH_AVR25, "__AVR_ATtiny13__", 1, 0x0060, "tn13" },
+ { "attiny13a", ARCH_AVR25, "__AVR_ATtiny13A__", 1, 0x0060, "tn13a" },
+ { "attiny2313", ARCH_AVR25, "__AVR_ATtiny2313__", 1, 0x0060, "tn2313" },
++ { "attiny2313a", ARCH_AVR25, "__AVR_ATtiny2313A__", 1, 0x0060, "tn2313a" },
+ { "attiny24", ARCH_AVR25, "__AVR_ATtiny24__", 1, 0x0060, "tn24" },
++ { "attiny24a", ARCH_AVR25, "__AVR_ATtiny24A__", 1, 0x0060, "tn24a" },
++ { "attiny4313", ARCH_AVR25, "__AVR_ATtiny4313__", 0, 0x0060, "tn4313" },
+ { "attiny44", ARCH_AVR25, "__AVR_ATtiny44__", 0, 0x0060, "tn44" },
++ { "attiny44a", ARCH_AVR25, "__AVR_ATtiny44A__", 0, 0x0060, "tn44a" },
+ { "attiny84", ARCH_AVR25, "__AVR_ATtiny84__", 0, 0x0060, "tn84" },
++ { "attiny84a", ARCH_AVR25, "__AVR_ATtiny84A__", 0, 0x0060, "tn84a" },
+ { "attiny25", ARCH_AVR25, "__AVR_ATtiny25__", 1, 0x0060, "tn25" },
+ { "attiny45", ARCH_AVR25, "__AVR_ATtiny45__", 0, 0x0060, "tn45" },
+ { "attiny85", ARCH_AVR25, "__AVR_ATtiny85__", 0, 0x0060, "tn85" },
+ { "attiny261", ARCH_AVR25, "__AVR_ATtiny261__", 1, 0x0060, "tn261" },
++ { "attiny261a", ARCH_AVR25, "__AVR_ATtiny261A__", 1, 0x0060, "tn261a" },
+ { "attiny461", ARCH_AVR25, "__AVR_ATtiny461__", 0, 0x0060, "tn461" },
++ { "attiny461a", ARCH_AVR25, "__AVR_ATtiny461A__", 0, 0x0060, "tn461a" },
+ { "attiny861", ARCH_AVR25, "__AVR_ATtiny861__", 0, 0x0060, "tn861" },
++ { "attiny861a", ARCH_AVR25, "__AVR_ATtiny861A__", 0, 0x0060, "tn861a" },
+ { "attiny43u", ARCH_AVR25, "__AVR_ATtiny43U__", 0, 0x0060, "tn43u" },
+ { "attiny87", ARCH_AVR25, "__AVR_ATtiny87__", 0, 0x0100, "tn87" },
+ { "attiny48", ARCH_AVR25, "__AVR_ATtiny48__", 0, 0x0100, "tn48" },
+@@ -105,21 +113,19 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega16u2", ARCH_AVR35, "__AVR_ATmega16U2__", 0, 0x0100, "m16u2" },
+ { "atmega32u2", ARCH_AVR35, "__AVR_ATmega32U2__", 0, 0x0100, "m32u2" },
+ { "attiny167", ARCH_AVR35, "__AVR_ATtiny167__", 0, 0x0100, "tn167" },
+- { "attiny327", ARCH_AVR35, "__AVR_ATtiny327__", 0, 0x0100, "tn327" },
+ /* Enhanced, <= 8K. */
+ { "avr4", ARCH_AVR4, NULL, 0, 0x0060, "m8" },
+ { "atmega8", ARCH_AVR4, "__AVR_ATmega8__", 0, 0x0060, "m8" },
+ { "atmega48", ARCH_AVR4, "__AVR_ATmega48__", 0, 0x0100, "m48" },
++ { "atmega48a", ARCH_AVR4, "__AVR_ATmega48A__", 0, 0x0100, "m48a" },
+ { "atmega48p", ARCH_AVR4, "__AVR_ATmega48P__", 0, 0x0100, "m48p" },
+ { "atmega88", ARCH_AVR4, "__AVR_ATmega88__", 0, 0x0100, "m88" },
++ { "atmega88a", ARCH_AVR4, "__AVR_ATmega88A__", 0, 0x0100, "m88a" },
+ { "atmega88p", ARCH_AVR4, "__AVR_ATmega88P__", 0, 0x0100, "m88p" },
++ { "atmega88pa", ARCH_AVR4, "__AVR_ATmega88PA__", 0, 0x0100, "m88pa" },
+ { "atmega8515", ARCH_AVR4, "__AVR_ATmega8515__", 0, 0x0060, "m8515" },
+ { "atmega8535", ARCH_AVR4, "__AVR_ATmega8535__", 0, 0x0060, "m8535" },
+- { "atmega8c1", ARCH_AVR4, "__AVR_ATmega8C1__", 0, 0x0100, "m8c1" },
+- { "atmega8m1", ARCH_AVR4, "__AVR_ATmega8M1__", 0, 0x0100, "m8m1" },
+ { "atmega8hva", ARCH_AVR4, "__AVR_ATmega8HVA__", 0, 0x0100, "m8hva" },
+- { "atmega4hvd", ARCH_AVR4, "__AVR_ATmega4HVD__", 0, 0x0100, "m4hvd" },
+- { "atmega8hvd", ARCH_AVR4, "__AVR_ATmega8HVD__", 0, 0x0100, "m8hvd" },
+ { "at90pwm1", ARCH_AVR4, "__AVR_AT90PWM1__", 0, 0x0100, "90pwm1" },
+ { "at90pwm2", ARCH_AVR4, "__AVR_AT90PWM2__", 0, 0x0100, "90pwm2" },
+ { "at90pwm2b", ARCH_AVR4, "__AVR_AT90PWM2B__", 0, 0x0100, "90pwm2b" },
+@@ -128,41 +134,78 @@ const struct mcu_type_s avr_mcu_types[]
+ { "at90pwm81", ARCH_AVR4, "__AVR_AT90PWM81__", 0, 0x0100, "90pwm81" },
+ /* Enhanced, > 8K, <= 64K. */
+ { "avr5", ARCH_AVR5, NULL, 0, 0x0060, "m16" },
++ { "at90pwm161", ARCH_AVR5, "__AVR_AT90PWM161__", 1, 0x0100, "90pwm161" },
+ { "atmega16", ARCH_AVR5, "__AVR_ATmega16__", 0, 0x0060, "m16" },
++ { "atmega16a", ARCH_AVR5, "__AVR_ATmega16A__", 0, 0x0060, "m16a" },
+ { "atmega161", ARCH_AVR5, "__AVR_ATmega161__", 0, 0x0060, "m161" },
+ { "atmega162", ARCH_AVR5, "__AVR_ATmega162__", 0, 0x0100, "m162" },
+ { "atmega163", ARCH_AVR5, "__AVR_ATmega163__", 0, 0x0060, "m163" },
++ { "atmega164a", ARCH_AVR5, "__AVR_ATmega164A__", 0, 0x0060, "m164a" },
+ { "atmega164p", ARCH_AVR5, "__AVR_ATmega164P__", 0, 0x0100, "m164p" },
+ { "atmega165", ARCH_AVR5, "__AVR_ATmega165__", 0, 0x0100, "m165" },
++ { "atmega165a", ARCH_AVR5, "__AVR_ATmega165A__", 0, 0x0100, "m165a" },
+ { "atmega165p", ARCH_AVR5, "__AVR_ATmega165P__", 0, 0x0100, "m165p" },
+ { "atmega168", ARCH_AVR5, "__AVR_ATmega168__", 0, 0x0100, "m168" },
++ { "atmega168a", ARCH_AVR5, "__AVR_ATmega168A__", 0, 0x0100, "m168a" },
+ { "atmega168p", ARCH_AVR5, "__AVR_ATmega168P__", 0, 0x0100, "m168p" },
+ { "atmega169", ARCH_AVR5, "__AVR_ATmega169__", 0, 0x0100, "m169" },
++ { "atmega169a", ARCH_AVR5, "__AVR_ATmega169A__", 0, 0x0100, "m169a" },
+ { "atmega169p", ARCH_AVR5, "__AVR_ATmega169P__", 0, 0x0100, "m169p" },
++ { "atmega169pa", ARCH_AVR5, "__AVR_ATmega169PA__", 0, 0x0100, "m169pa" },
++ { "atmega16hva", ARCH_AVR5, "__AVR_ATmega16HVA__", 0, 0x0100, "m16hva" },
++ { "atmega16hva2", ARCH_AVR5, "__AVR_ATmega16HVA2__", 0, 0x0100, "m16hva2" },
++ { "atmega16hvb", ARCH_AVR5, "__AVR_ATmega16HVB__", 0, 0x0100, "m16hvb" },
++ { "atmega16hvbrevb", ARCH_AVR5, "__AVR_ATmega16HVBREVB__", 1, 0x0100, "m16hvbrevb" },
++ { "atmega16m1", ARCH_AVR5, "__AVR_ATmega16M1__", 0, 0x0100, "m16m1" },
++ { "atmega16u4", ARCH_AVR5, "__AVR_ATmega16U4__", 0, 0x0100, "m16u4" },
+ { "atmega32", ARCH_AVR5, "__AVR_ATmega32__", 0, 0x0060, "m32" },
+ { "atmega323", ARCH_AVR5, "__AVR_ATmega323__", 0, 0x0060, "m323" },
++ { "atmega324a", ARCH_AVR5, "__AVR_ATmega324A__", 0, 0x0060, "m324a" },
+ { "atmega324p", ARCH_AVR5, "__AVR_ATmega324P__", 0, 0x0100, "m324p" },
++ { "atmega324pa", ARCH_AVR5, "__AVR_ATmega324PA__", 0, 0x0100, "m324pa" },
+ { "atmega325", ARCH_AVR5, "__AVR_ATmega325__", 0, 0x0100, "m325" },
++ { "atmega325a", ARCH_AVR5, "__AVR_ATmega325A__", 0, 0x0100, "m325a" },
+ { "atmega325p", ARCH_AVR5, "__AVR_ATmega325P__", 0, 0x0100, "m325p" },
+ { "atmega3250", ARCH_AVR5, "__AVR_ATmega3250__", 0, 0x0100, "m3250" },
++ { "atmega3250a", ARCH_AVR5, "__AVR_ATmega3250A__", 0, 0x0100, "m3250a" },
+ { "atmega3250p", ARCH_AVR5, "__AVR_ATmega3250P__", 0, 0x0100, "m3250p" },
++ { "atmega328", ARCH_AVR5, "__AVR_ATmega328__", 0, 0x0100, "m328" },
+ { "atmega328p", ARCH_AVR5, "__AVR_ATmega328P__", 0, 0x0100, "m328p" },
+ { "atmega329", ARCH_AVR5, "__AVR_ATmega329__", 0, 0x0100, "m329" },
++ { "atmega329a", ARCH_AVR5, "__AVR_ATmega329A__", 0, 0x0100, "m329a" },
+ { "atmega329p", ARCH_AVR5, "__AVR_ATmega329P__", 0, 0x0100, "m329p" },
++ { "atmega329pa", ARCH_AVR5, "__AVR_ATmega329PA__", 0, 0x0100, "m329pa" },
+ { "atmega3290", ARCH_AVR5, "__AVR_ATmega3290__", 0, 0x0100, "m3290" },
++ { "atmega3290a", ARCH_AVR5, "__AVR_ATmega3290A__", 0, 0x0100, "m3290a" },
+ { "atmega3290p", ARCH_AVR5, "__AVR_ATmega3290P__", 0, 0x0100, "m3290p" },
++ { "atmega32c1", ARCH_AVR5, "__AVR_ATmega32C1__", 0, 0x0100, "m32c1" },
++ { "atmega32m1", ARCH_AVR5, "__AVR_ATmega32M1__", 0, 0x0100, "m32m1" },
++ { "atmega32u4", ARCH_AVR5, "__AVR_ATmega32U4__", 0, 0x0100, "m32u4" },
++ { "atmega32u6", ARCH_AVR5, "__AVR_ATmega32U6__", 0, 0x0100, "m32u6" },
+ { "atmega406", ARCH_AVR5, "__AVR_ATmega406__", 0, 0x0100, "m406" },
+ { "atmega64", ARCH_AVR5, "__AVR_ATmega64__", 0, 0x0100, "m64" },
+ { "atmega640", ARCH_AVR5, "__AVR_ATmega640__", 0, 0x0200, "m640" },
+ { "atmega644", ARCH_AVR5, "__AVR_ATmega644__", 0, 0x0100, "m644" },
++ { "atmega644a", ARCH_AVR5, "__AVR_ATmega644A__", 0, 0x0100, "m644a" },
+ { "atmega644p", ARCH_AVR5, "__AVR_ATmega644P__", 0, 0x0100, "m644p" },
++ { "atmega644pa", ARCH_AVR5, "__AVR_ATmega644PA__", 0, 0x0100, "m644pa" },
++ { "atmega645a", ARCH_AVR5, "__AVR_ATmega645A__", 0, 0x0100, "m645a" },
++ { "atmega645p", ARCH_AVR5, "__AVR_ATmega645P__", 0, 0x0100, "m645p" },
+ { "atmega645", ARCH_AVR5, "__AVR_ATmega645__", 0, 0x0100, "m645" },
+ { "atmega6450", ARCH_AVR5, "__AVR_ATmega6450__", 0, 0x0100, "m6450" },
++ { "atmega6450a", ARCH_AVR5, "__AVR_ATmega6450A__", 0, 0x0100, "m6450a" },
++ { "atmega6450p", ARCH_AVR5, "__AVR_ATmega6450P__", 0, 0x0100, "m6450p" },
+ { "atmega649", ARCH_AVR5, "__AVR_ATmega649__", 0, 0x0100, "m649" },
++ { "atmega649a", ARCH_AVR5, "__AVR_ATmega649A__", 0, 0x0100, "m649a" },
++ { "atmega649p", ARCH_AVR5, "__AVR_ATmega649P__", 0, 0x0100, "m649p" },
+ { "atmega6490", ARCH_AVR5, "__AVR_ATmega6490__", 0, 0x0100, "m6490" },
+- { "atmega16hva", ARCH_AVR5, "__AVR_ATmega16HVA__", 0, 0x0100, "m16hva" },
+- { "atmega16hvb", ARCH_AVR5, "__AVR_ATmega16HVB__", 0, 0x0100, "m16hvb" },
+- { "atmega32hvb", ARCH_AVR5, "__AVR_ATmega32HVB__", 0, 0x0100, "m23hvb" },
++ { "atmega6490a", ARCH_AVR5, "__AVR_ATmega6490A__", 0, 0x0100, "m6490a" },
++ { "atmega6490p", ARCH_AVR5, "__AVR_ATmega6490P__", 0, 0x0100, "m6490p" },
++ { "atmega64c1", ARCH_AVR5, "__AVR_ATmega64C1__", 0, 0x0100, "m64c1" },
++ { "atmega64m1", ARCH_AVR5, "__AVR_ATmega64M1__", 0, 0x0100, "m64m1" },
++ { "atmega64hve", ARCH_AVR5, "__AVR_ATmega64HVE__", 0, 0x0100, "m64hve" },
++ { "atmega32hvb", ARCH_AVR5, "__AVR_ATmega32HVB__", 0, 0x0100, "m32hvb" },
++ { "atmega32hvbrevb", ARCH_AVR5, "__AVR_ATmega32HVBREVB__", 1, 0x0100, "m32hvbrevb" },
+ { "at90can32", ARCH_AVR5, "__AVR_AT90CAN32__", 0, 0x0100, "can32" },
+ { "at90can64", ARCH_AVR5, "__AVR_AT90CAN64__", 0, 0x0100, "can64" },
+ { "at90pwm216", ARCH_AVR5, "__AVR_AT90PWM216__", 0, 0x0100, "90pwm216" },
+@@ -180,6 +223,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "at90usb646", ARCH_AVR5, "__AVR_AT90USB646__", 0, 0x0100, "usb646" },
+ { "at90usb647", ARCH_AVR5, "__AVR_AT90USB647__", 0, 0x0100, "usb647" },
+ { "at94k", ARCH_AVR5, "__AVR_AT94K__", 0, 0x0060, "at94k" },
++ { "m3000", ARCH_AVR5, "__AVR_M3000__", 0, 0x1000, "m3000" },
+ /* Enhanced, == 128K. */
+ { "avr51", ARCH_AVR51, NULL, 0, 0x0100, "m128" },
+ { "atmega128", ARCH_AVR51, "__AVR_ATmega128__", 0, 0x0100, "m128" },
+@@ -190,9 +234,6 @@ const struct mcu_type_s avr_mcu_types[]
+ { "at90can128", ARCH_AVR51, "__AVR_AT90CAN128__", 0, 0x0100, "can128" },
+ { "at90usb1286", ARCH_AVR51, "__AVR_AT90USB1286__", 0, 0x0100, "usb1286" },
+ { "at90usb1287", ARCH_AVR51, "__AVR_AT90USB1287__", 0, 0x0100, "usb1286" },
+- { "m3000f", ARCH_AVR51, "__AVR_M3000F__", 0, 0x1000, "m3000f" },
+- { "m3000s", ARCH_AVR51, "__AVR_M3000S__", 0, 0x1000, "m3000f" },
+- { "m3001b", ARCH_AVR51, "__AVR_M3001B__", 0, 0x1000, "m3000f" },
+ /* 3-Byte PC. */
+ { "avr6", ARCH_AVR6, NULL, 0, 0x0200, "m2561" },
+ { "atmega2560", ARCH_AVR6, "__AVR_ATmega2560__", 0, 0x0200, "m2561" },
+@@ -219,11 +260,13 @@ const struct mcu_type_s avr_mcu_types[]
+ /* Xmega, > 128K, <= 256K FLASH, <= 64K RAM. */
+ { "avrxmega6", ARCH_AVRXMEGA6, NULL, 0, 0x2000, "x128a3" },
+ { "atxmega128a3", ARCH_AVRXMEGA6, "__AVR_ATxmega128A3__", 0, 0x2000, "x128a3" },
++ { "atxmega128b1", ARCH_AVRXMEGA6, "__AVR_ATxmega128B1__", 0, 0x2000, "x128b1" },
+ { "atxmega128d3", ARCH_AVRXMEGA6, "__AVR_ATxmega128D3__", 0, 0x2000, "x128d3" },
+ { "atxmega192a3", ARCH_AVRXMEGA6, "__AVR_ATxmega192A3__", 0, 0x2000, "x192a3" },
+ { "atxmega192d3", ARCH_AVRXMEGA6, "__AVR_ATxmega192D3__", 0, 0x2000, "x192d3" },
+ { "atxmega256a3", ARCH_AVRXMEGA6, "__AVR_ATxmega256A3__", 0, 0x2000, "x256a3" },
+ { "atxmega256a3b",ARCH_AVRXMEGA6, "__AVR_ATxmega256A3B__", 0, 0x2000, "x256a3b" },
++ { "atxmega256a3bu", ARCH_AVRXMEGA6, "__AVR_ATxmega256A3BU__", 0, 0x2000, "x256a3bu" },
+ { "atxmega256d3", ARCH_AVRXMEGA6, "__AVR_ATxmega256D3__", 0, 0x2000, "x256d3" },
+ /* Xmega, > 128K, <= 256K FLASH, > 64K RAM. */
+ { "avrxmega7", ARCH_AVRXMEGA7, NULL, 0, 0x2000, "x128a1" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-02 11:47:23.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-02 11:49:57.000000000 +0300
+@@ -116,16 +116,28 @@ MULTILIB_MATCHES = \
+ mmcu?avr25=mmcu?attiny13 \
+ mmcu?avr25=mmcu?attiny13a \
+ mmcu?avr25=mmcu?attiny2313 \
++ mmcu?avr25=mmcu?attiny2313a \
+ mmcu?avr25=mmcu?attiny24 \
++ mmcu?avr25=mmcu?attiny24a \
+ mmcu?avr25=mmcu?attiny44 \
++ mmcu?avr25=mmcu?attiny44a \
++ mmcu?avr25=mmcu?attiny45 \
+ mmcu?avr25=mmcu?attiny84 \
++ mmcu?avr25=mmcu?attiny84a \
+ mmcu?avr25=mmcu?attiny25 \
+ mmcu?avr25=mmcu?attiny45 \
+ mmcu?avr25=mmcu?attiny85 \
+ mmcu?avr25=mmcu?attiny261 \
++ mmcu?avr25=mmcu?attiny261a \
++ mmcu?avr25=mmcu?attiny4313 \
+ mmcu?avr25=mmcu?attiny461 \
++ mmcu?avr25=mmcu?attiny461a \
+ mmcu?avr25=mmcu?attiny861 \
+ mmcu?avr25=mmcu?attiny43u \
++ mmcu?avr25=mmcu?attiny84 \
++ mmcu?avr25=mmcu?attiny85 \
++ mmcu?avr25=mmcu?attiny861 \
++ mmcu?avr25=mmcu?attiny861a \
+ mmcu?avr25=mmcu?attiny87 \
+ mmcu?avr25=mmcu?attiny48 \
+ mmcu?avr25=mmcu?attiny88 \
+@@ -140,65 +152,90 @@ MULTILIB_MATCHES = \
+ mmcu?avr35=mmcu?atmega16u2 \
+ mmcu?avr35=mmcu?atmega32u2 \
+ mmcu?avr35=mmcu?attiny167 \
+- mmcu?avr35=mmcu?attiny327 \
+ mmcu?avr4=mmcu?atmega48 \
++ mmcu?avr4=mmcu?atmega48a \
+ mmcu?avr4=mmcu?atmega48p \
+ mmcu?avr4=mmcu?atmega8 \
+ mmcu?avr4=mmcu?atmega8515 \
+ mmcu?avr4=mmcu?atmega8535 \
+ mmcu?avr4=mmcu?atmega88 \
++ mmcu?avr4=mmcu?atmega88a \
+ mmcu?avr4=mmcu?atmega88p \
++ mmcu?avr4=mmcu?atmega88pa \
+ mmcu?avr4=mmcu?atmega8hva \
+- mmcu?avr4=mmcu?atmega4hvd \
+- mmcu?avr4=mmcu?atmega8hvd \
+- mmcu?avr4=mmcu?atmega8c1 \
+- mmcu?avr4=mmcu?atmega8m1 \
+ mmcu?avr4=mmcu?at90pwm1 \
+ mmcu?avr4=mmcu?at90pwm2 \
+ mmcu?avr4=mmcu?at90pwm2b \
+ mmcu?avr4=mmcu?at90pwm3 \
+ mmcu?avr4=mmcu?at90pwm3b \
+ mmcu?avr4=mmcu?at90pwm81 \
++ mmcu?avr5=mmcu?at90pwm161 \
+ mmcu?avr5=mmcu?atmega16 \
++ mmcu?avr5=mmcu?atmega16a \
+ mmcu?avr5=mmcu?atmega161 \
+ mmcu?avr5=mmcu?atmega162 \
+ mmcu?avr5=mmcu?atmega163 \
++ mmcu?avr5=mmcu?atmega164a \
+ mmcu?avr5=mmcu?atmega164p \
+ mmcu?avr5=mmcu?atmega165 \
++ mmcu?avr5=mmcu?atmega165a \
+ mmcu?avr5=mmcu?atmega165p \
+ mmcu?avr5=mmcu?atmega168 \
++ mmcu?avr5=mmcu?atmega168a \
+ mmcu?avr5=mmcu?atmega168p \
+ mmcu?avr5=mmcu?atmega169 \
++ mmcu?avr5=mmcu?atmega169a \
+ mmcu?avr5=mmcu?atmega169p \
++ mmcu?avr5=mmcu?atmega169pa \
+ mmcu?avr5=mmcu?atmega32 \
+ mmcu?avr5=mmcu?atmega323 \
++ mmcu?avr5=mmcu?atmega324a \
+ mmcu?avr5=mmcu?atmega324p \
++ mmcu?avr5=mmcu?atmega324pa \
+ mmcu?avr5=mmcu?atmega325 \
++ mmcu?avr5=mmcu?atmega325a \
+ mmcu?avr5=mmcu?atmega325p \
+ mmcu?avr5=mmcu?atmega3250 \
++ mmcu?avr5=mmcu?atmega3250a \
+ mmcu?avr5=mmcu?atmega3250p \
++ mmcu?avr5=mmcu?atmega328 \
+ mmcu?avr5=mmcu?atmega328p \
+ mmcu?avr5=mmcu?atmega329 \
++ mmcu?avr5=mmcu?atmega329a \
+ mmcu?avr5=mmcu?atmega329p \
++ mmcu?avr5=mmcu?atmega329pa \
+ mmcu?avr5=mmcu?atmega3290 \
++ mmcu?avr5=mmcu?atmega3290a \
+ mmcu?avr5=mmcu?atmega3290p \
+ mmcu?avr5=mmcu?atmega406 \
+ mmcu?avr5=mmcu?atmega64 \
+ mmcu?avr5=mmcu?atmega640 \
+ mmcu?avr5=mmcu?atmega644 \
++ mmcu?avr5=mmcu?atmega644a \
+ mmcu?avr5=mmcu?atmega644p \
++ mmcu?avr5=mmcu?atmega644pa \
+ mmcu?avr5=mmcu?atmega645 \
++ mmcu?avr5=mmcu?atmega645a \
++ mmcu?avr5=mmcu?atmega645p \
+ mmcu?avr5=mmcu?atmega6450 \
++ mmcu?avr5=mmcu?atmega6450a \
++ mmcu?avr5=mmcu?atmega6450p \
+ mmcu?avr5=mmcu?atmega649 \
++ mmcu?avr5=mmcu?atmega649a \
++ mmcu?avr5=mmcu?atmega649p \
+ mmcu?avr5=mmcu?atmega6490 \
++ mmcu?avr5=mmcu?atmega6490a \
++ mmcu?avr5=mmcu?atmega6490p \
+ mmcu?avr5=mmcu?atmega16hva \
++ mmcu?avr5=mmcu?atmega16hva2 \
+ mmcu?avr5=mmcu?atmega16hvb \
++ mmcu?avr5=mmcu?atmega16hvbrevb \
+ mmcu?avr5=mmcu?atmega32hvb \
++ mmcu?avr5=mmcu?atmega32hvbrevb \
+ mmcu?avr5=mmcu?at90can32 \
+ mmcu?avr5=mmcu?at90can64 \
+ mmcu?avr5=mmcu?at90pwm216 \
+ mmcu?avr5=mmcu?at90pwm316 \
+- mmcu?avr5=mmcu?atmega16c1 \
+ mmcu?avr5=mmcu?atmega32c1 \
+ mmcu?avr5=mmcu?atmega64c1 \
+ mmcu?avr5=mmcu?atmega16m1 \
+@@ -207,6 +244,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr5=mmcu?atmega16u4 \
+ mmcu?avr5=mmcu?atmega32u4 \
+ mmcu?avr5=mmcu?atmega32u6 \
++ mmcu?avr5=mmcu?atmega64hve \
+ mmcu?avr5=mmcu?at90scr100 \
+ mmcu?avr5=mmcu?at90usb646 \
+ mmcu?avr5=mmcu?at90usb647 \
+@@ -219,9 +257,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr51=mmcu?at90can128 \
+ mmcu?avr51=mmcu?at90usb1286 \
+ mmcu?avr51=mmcu?at90usb1287 \
+- mmcu?avr51=mmcu?m3000f \
+- mmcu?avr51=mmcu?m3000s \
+- mmcu?avr51=mmcu?m3001b \
++ mmcu?avr51=mmcu?m3000 \
+ mmcu?avr6=mmcu?atmega2560 \
+ mmcu?avr6=mmcu?atmega2561 \
+ mmcu?avrxmega2=mmcu?atxmega16a4 \
+@@ -234,11 +270,13 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega5=mmcu?atxmega64a1 \
+ mmcu?avrxmega5=mmcu?atxmega64a1u \
+ mmcu?avrxmega6=mmcu?atxmega128a3 \
++ mmcu?avrxmega6=mmcu?atxmega128b1 \
+ mmcu?avrxmega6=mmcu?atxmega128d3 \
+ mmcu?avrxmega6=mmcu?atxmega192a3 \
+ mmcu?avrxmega6=mmcu?atxmega192d3 \
+ mmcu?avrxmega6=mmcu?atxmega256a3 \
+ mmcu?avrxmega6=mmcu?atxmega256a3b \
++ mmcu?avrxmega6=mmcu?atxmega256a3bu \
+ mmcu?avrxmega6=mmcu?atxmega256d3 \
+ mmcu?avrxmega7=mmcu?atxmega128a1 \
+ mmcu?avrxmega7=mmcu?atxmega128a1u \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-02-17 12:04:53.000000000 -0600
++++ gcc/config/avr/avr-devices.c 2011-02-16 15:14:00.000000000 -0600
+@@ -166,9 +166,11 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega325", ARCH_AVR5, "__AVR_ATmega325__", 0, 0x0100, "m325" },
+ { "atmega325a", ARCH_AVR5, "__AVR_ATmega325A__", 0, 0x0100, "m325a" },
+ { "atmega325p", ARCH_AVR5, "__AVR_ATmega325P__", 0, 0x0100, "m325p" },
++ { "atmega325pa", ARCH_AVR5, "__AVR_ATmega325PA__", 0, 0x0100, "m325pa" },
+ { "atmega3250", ARCH_AVR5, "__AVR_ATmega3250__", 0, 0x0100, "m3250" },
+ { "atmega3250a", ARCH_AVR5, "__AVR_ATmega3250A__", 0, 0x0100, "m3250a" },
+ { "atmega3250p", ARCH_AVR5, "__AVR_ATmega3250P__", 0, 0x0100, "m3250p" },
++ { "atmega3250pa", ARCH_AVR5, "__AVR_ATmega3250PA__", 0, 0x0100, "m3250pa" },
+ { "atmega328", ARCH_AVR5, "__AVR_ATmega328__", 0, 0x0100, "m328" },
+ { "atmega328p", ARCH_AVR5, "__AVR_ATmega328P__", 0, 0x0100, "m328p" },
+ { "atmega329", ARCH_AVR5, "__AVR_ATmega329__", 0, 0x0100, "m329" },
+@@ -178,6 +180,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega3290", ARCH_AVR5, "__AVR_ATmega3290__", 0, 0x0100, "m3290" },
+ { "atmega3290a", ARCH_AVR5, "__AVR_ATmega3290A__", 0, 0x0100, "m3290a" },
+ { "atmega3290p", ARCH_AVR5, "__AVR_ATmega3290P__", 0, 0x0100, "m3290p" },
++ { "atmega3290pa", ARCH_AVR5, "__AVR_ATmega3290PA__", 0, 0x0100, "m3290pa" },
+ { "atmega32c1", ARCH_AVR5, "__AVR_ATmega32C1__", 0, 0x0100, "m32c1" },
+ { "atmega32m1", ARCH_AVR5, "__AVR_ATmega32M1__", 0, 0x0100, "m32m1" },
+ { "atmega32u4", ARCH_AVR5, "__AVR_ATmega32U4__", 0, 0x0100, "m32u4" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-02-17 12:04:53.000000000 -0600
++++ gcc/config/avr/t-avr 2011-02-16 15:15:18.000000000 -0600
+@@ -195,9 +195,11 @@ MULTILIB_MATCHES = \
+ mmcu?avr5=mmcu?atmega325 \
+ mmcu?avr5=mmcu?atmega325a \
+ mmcu?avr5=mmcu?atmega325p \
++ mmcu?avr5=mmcu?atmega325pa \
+ mmcu?avr5=mmcu?atmega3250 \
+ mmcu?avr5=mmcu?atmega3250a \
+ mmcu?avr5=mmcu?atmega3250p \
++ mmcu?avr5=mmcu?atmega3250pa \
+ mmcu?avr5=mmcu?atmega328 \
+ mmcu?avr5=mmcu?atmega328p \
+ mmcu?avr5=mmcu?atmega329 \
+@@ -207,6 +209,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr5=mmcu?atmega3290 \
+ mmcu?avr5=mmcu?atmega3290a \
+ mmcu?avr5=mmcu?atmega3290p \
++ mmcu?avr5=mmcu?atmega3290pa \
+ mmcu?avr5=mmcu?atmega406 \
+ mmcu?avr5=mmcu?atmega64 \
+ mmcu?avr5=mmcu?atmega640 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-05-13 17:35:31.000000000 -0500
++++ gcc/config/avr/avr-devices.c 2011-05-13 17:43:10.000000000 -0500
+@@ -113,6 +113,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega16u2", ARCH_AVR35, "__AVR_ATmega16U2__", 0, 0x0100, "m16u2" },
+ { "atmega32u2", ARCH_AVR35, "__AVR_ATmega32U2__", 0, 0x0100, "m32u2" },
+ { "attiny167", ARCH_AVR35, "__AVR_ATtiny167__", 0, 0x0100, "tn167" },
++ { "attiny1634", ARCH_AVR35, "__AVR_ATtiny1634__", 0, 0x0100, "tn1634" },
+ /* Enhanced, <= 8K. */
+ { "avr4", ARCH_AVR4, NULL, 0, 0x0060, "m8" },
+ { "atmega8", ARCH_AVR4, "__AVR_ATmega8__", 0, 0x0060, "m8" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-05-13 17:35:31.000000000 -0500
++++ gcc/config/avr/t-avr 2011-05-13 17:37:41.000000000 -0500
+@@ -152,6 +152,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr35=mmcu?atmega16u2 \
+ mmcu?avr35=mmcu?atmega32u2 \
+ mmcu?avr35=mmcu?attiny167 \
++ mmcu?avr35=mmcu?attiny1634 \
+ mmcu?avr4=mmcu?atmega48 \
+ mmcu?avr4=mmcu?atmega48a \
+ mmcu?avr4=mmcu?atmega48p \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-06-20 12:23:54.000000000 +0530
++++ gcc/config/avr/avr-devices.c 2011-06-20 12:11:26.000000000 +0530
+@@ -119,6 +119,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega8", ARCH_AVR4, "__AVR_ATmega8__", 0, 0x0060, "m8" },
+ { "atmega48", ARCH_AVR4, "__AVR_ATmega48__", 0, 0x0100, "m48" },
+ { "atmega48a", ARCH_AVR4, "__AVR_ATmega48A__", 0, 0x0100, "m48a" },
++ { "atmega48pa", ARCH_AVR4, "__AVR_ATmega48PA__", 0, 0x0100, "m48pa" },
+ { "atmega48p", ARCH_AVR4, "__AVR_ATmega48P__", 0, 0x0100, "m48p" },
+ { "atmega88", ARCH_AVR4, "__AVR_ATmega88__", 0, 0x0100, "m88" },
+ { "atmega88a", ARCH_AVR4, "__AVR_ATmega88A__", 0, 0x0100, "m88a" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-06-20 12:23:54.000000000 +0530
++++ gcc/config/avr/t-avr 2011-06-20 12:11:26.000000000 +0530
+@@ -155,6 +155,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr35=mmcu?attiny1634 \
+ mmcu?avr4=mmcu?atmega48 \
+ mmcu?avr4=mmcu?atmega48a \
++ mmcu?avr4=mmcu?atmega48pa \
+ mmcu?avr4=mmcu?atmega48p \
+ mmcu?avr4=mmcu?atmega8 \
+ mmcu?avr4=mmcu?atmega8515 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-02 12:01:05.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-02 12:10:44.000000000 +0300
+@@ -55,7 +55,7 @@ const struct base_arch_s avr_arch_types[
+ - avr-libc. */
+
+ const struct mcu_type_s avr_mcu_types[] = {
+- /* Classic, <= 8K. */
++ /* Classic, <= 8K, 2-byte PC. */
+ { "avr2", ARCH_AVR2, NULL, 0, 0x0060, "s8515" },
+ { "at90s2313", ARCH_AVR2, "__AVR_AT90S2313__", 1, 0x0060, "s2313" },
+ { "at90s2323", ARCH_AVR2, "__AVR_AT90S2323__", 1, 0x0060, "s2323" },
+@@ -69,7 +69,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "at90s8515", ARCH_AVR2, "__AVR_AT90S8515__", 0, 0x0060, "s8515" },
+ { "at90c8534", ARCH_AVR2, "__AVR_AT90C8534__", 0, 0x0060, "c8534" },
+ { "at90s8535", ARCH_AVR2, "__AVR_AT90S8535__", 0, 0x0060, "s8535" },
+- /* Classic + MOVW, <= 8K. */
++ /* Classic, <= 8K + 2-byte PC + { MOVW/LPMX }. */
+ { "avr25", ARCH_AVR25, NULL, 0, 0x0060, "tn85" },
+ { "ata6289", ARCH_AVR25, "__AVR_ATA6289__", 0, 0x0100, "a6289" },
+ { "attiny13", ARCH_AVR25, "__AVR_ATtiny13__", 1, 0x0060, "tn13" },
+@@ -97,15 +97,15 @@ const struct mcu_type_s avr_mcu_types[]
+ { "attiny48", ARCH_AVR25, "__AVR_ATtiny48__", 0, 0x0100, "tn48" },
+ { "attiny88", ARCH_AVR25, "__AVR_ATtiny88__", 0, 0x0100, "tn88" },
+ { "at86rf401", ARCH_AVR25, "__AVR_AT86RF401__", 1, 0x0060, "86401" },
+- /* Classic, > 8K, <= 64K. */
++ /* Classic, > 8K, <= 64K +2-byte PC + { JMP/CALL }. */
+ { "avr3", ARCH_AVR3, NULL, 0, 0x0060, "43355" },
+ { "at43usb355", ARCH_AVR3, "__AVR_AT43USB355__", 0, 0x0060, "43355" },
+ { "at76c711", ARCH_AVR3, "__AVR_AT76C711__", 0, 0x0060, "76711" },
+- /* Classic, == 128K. */
++ /* Classic, == 128K + 2-byte PC + { JMP/CALL, ELPM }. */
+ { "avr31", ARCH_AVR31, NULL, 0, 0x0060, "m103" },
+ { "atmega103", ARCH_AVR31, "__AVR_ATmega103__", 0, 0x0060, "m103" },
+ { "at43usb320", ARCH_AVR31, "__AVR_AT43USB320__", 0, 0x0060, "43320" },
+- /* Classic + MOVW + JMP/CALL. */
++ /* Classic, >=16K, <=64K + 2-byte PC + { MOVW/LPMX + JMP/CALL }. */
+ { "avr35", ARCH_AVR35, NULL, 0, 0x0100, "usb162" },
+ { "at90usb82", ARCH_AVR35, "__AVR_AT90USB82__", 0, 0x0100, "usb82" },
+ { "at90usb162", ARCH_AVR35, "__AVR_AT90USB162__", 0, 0x0100, "usb162" },
+@@ -114,7 +114,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega32u2", ARCH_AVR35, "__AVR_ATmega32U2__", 0, 0x0100, "m32u2" },
+ { "attiny167", ARCH_AVR35, "__AVR_ATtiny167__", 0, 0x0100, "tn167" },
+ { "attiny1634", ARCH_AVR35, "__AVR_ATtiny1634__", 0, 0x0100, "tn1634" },
+- /* Enhanced, <= 8K. */
++ /* Enhanced, <= 8K + 2-byte PC + { MOVW/LPMX, MUL }. */
+ { "avr4", ARCH_AVR4, NULL, 0, 0x0060, "m8" },
+ { "atmega8", ARCH_AVR4, "__AVR_ATmega8__", 0, 0x0060, "m8" },
+ { "atmega48", ARCH_AVR4, "__AVR_ATmega48__", 0, 0x0100, "m48" },
+@@ -134,7 +134,8 @@ const struct mcu_type_s avr_mcu_types[]
+ { "at90pwm3", ARCH_AVR4, "__AVR_AT90PWM3__", 0, 0x0100, "90pwm3" },
+ { "at90pwm3b", ARCH_AVR4, "__AVR_AT90PWM3B__", 0, 0x0100, "90pwm3b" },
+ { "at90pwm81", ARCH_AVR4, "__AVR_AT90PWM81__", 0, 0x0100, "90pwm81" },
+- /* Enhanced, > 8K, <= 64K. */
++ /* Enhanced, > 8K, <= 64K + 2-byte PC +
++ { MOVW/LPMX, JMP/CALL, MUL }. */
+ { "avr5", ARCH_AVR5, NULL, 0, 0x0060, "m16" },
+ { "at90pwm161", ARCH_AVR5, "__AVR_AT90PWM161__", 1, 0x0100, "90pwm161" },
+ { "atmega16", ARCH_AVR5, "__AVR_ATmega16__", 0, 0x0060, "m16" },
+@@ -229,7 +230,8 @@ const struct mcu_type_s avr_mcu_types[]
+ { "at90usb647", ARCH_AVR5, "__AVR_AT90USB647__", 0, 0x0100, "usb647" },
+ { "at94k", ARCH_AVR5, "__AVR_AT94K__", 0, 0x0060, "at94k" },
+ { "m3000", ARCH_AVR5, "__AVR_M3000__", 0, 0x1000, "m3000" },
+- /* Enhanced, == 128K. */
++ /* Enhanced, == 128K + 2-byte PC +
++ { MOVW/LPMX, JMP/CALL, MUL, ELPM, ELPMX }. */
+ { "avr51", ARCH_AVR51, NULL, 0, 0x0100, "m128" },
+ { "atmega128", ARCH_AVR51, "__AVR_ATmega128__", 0, 0x0100, "m128" },
+ { "atmega1280", ARCH_AVR51, "__AVR_ATmega1280__", 0, 0x0200, "m1280" },
+@@ -239,30 +241,33 @@ const struct mcu_type_s avr_mcu_types[]
+ { "at90can128", ARCH_AVR51, "__AVR_AT90CAN128__", 0, 0x0100, "can128" },
+ { "at90usb1286", ARCH_AVR51, "__AVR_AT90USB1286__", 0, 0x0100, "usb1286" },
+ { "at90usb1287", ARCH_AVR51, "__AVR_AT90USB1287__", 0, 0x0100, "usb1286" },
+- /* 3-Byte PC. */
++ /* Enhanced, ==256K + 3-Byte PC +
++ { MOVW/LPMX, JMP/CALL, MUL, ELPM, ELPMX }. */
+ { "avr6", ARCH_AVR6, NULL, 0, 0x0200, "m2561" },
+ { "atmega2560", ARCH_AVR6, "__AVR_ATmega2560__", 0, 0x0200, "m2561" },
+ { "atmega2561", ARCH_AVR6, "__AVR_ATmega2561__", 0, 0x0200, "m2561" },
+ /* Enhanced, == 256K. */
+ /* Xmega, <= 8K FLASH. */
+- /* Xmega, > 8K, <= 64K FLASH, <= 64K RAM. */
++ /* Xmega, > 8K, < 64K FLASH, <= 64K RAM. */
+ { "avrxmega2", ARCH_AVRXMEGA2, NULL, 0, 0x2000, "x32a4" },
+ { "atxmega16a4", ARCH_AVRXMEGA2, "__AVR_ATxmega16A4__", 0, 0x2000, "x16a4" },
++ { "atxmega16a4u", ARCH_AVRXMEGA2, "__AVR_ATxmega16A4U__", 0, 0x2000, "x16a4u" },
+ { "atxmega16d4", ARCH_AVRXMEGA2, "__AVR_ATxmega16D4__", 0, 0x2000, "x16d4" },
+ { "atxmega16x1", ARCH_AVRXMEGA2, "__AVR_ATxmega16X1__", 0, 0x2000, "x16x1" },
+ { "atxmega32a4", ARCH_AVRXMEGA2, "__AVR_ATxmega32A4__", 0, 0x2000, "x32a4" },
++ { "atxmega32a4u", ARCH_AVRXMEGA2, "__AVR_ATxmega32A4U__", 0, 0x2000, "x32a4u" },
+ { "atxmega32d4", ARCH_AVRXMEGA2, "__AVR_ATxmega32D4__", 0, 0x2000, "x32d4" },
+ /* Xmega, > 8K, <= 64K FLASH, > 64K RAM. */
+ /* { "avrxmega3", ARCH_AVRXMEGA3, NULL }, */
+- /* Xmega, > 64K, <= 128K FLASH, <= 64K RAM. */
++ /* Xmega, >= 64K, < 128K FLASH, <= 64K RAM. */
+ { "avrxmega4", ARCH_AVRXMEGA4, NULL, 0, 0x2000, "x64d3" },
+ { "atxmega64a3", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3__", 0, 0x2000, "x64a3" },
+ { "atxmega64d3", ARCH_AVRXMEGA4, "__AVR_ATxmega64D3__", 0, 0x2000, "x64d3" },
+- /* Xmega, > 64K, <= 128K FLASH, > 64K RAM. */
++ /* Xmega, >= 64K, < 128K FLASH, > 64K RAM. */
+ { "avrxmega5", ARCH_AVRXMEGA5, NULL, 0, 0x2000, "x64a1" },
+ { "atxmega64a1", ARCH_AVRXMEGA5, "__AVR_ATxmega64A1__", 0, 0x2000, "x64a1" },
+ { "atxmega64a1u", ARCH_AVRXMEGA5, "__AVR_ATxmega64A1U__", 0, 0x2000, "x64a1u" },
+- /* Xmega, > 128K, <= 256K FLASH, <= 64K RAM. */
++ /* Xmega, >= 128K, <= 256K FLASH, <= 64K RAM. */
+ { "avrxmega6", ARCH_AVRXMEGA6, NULL, 0, 0x2000, "x128a3" },
+ { "atxmega128a3", ARCH_AVRXMEGA6, "__AVR_ATxmega128A3__", 0, 0x2000, "x128a3" },
+ { "atxmega128b1", ARCH_AVRXMEGA6, "__AVR_ATxmega128B1__", 0, 0x2000, "x128b1" },
+@@ -273,7 +278,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atxmega256a3b",ARCH_AVRXMEGA6, "__AVR_ATxmega256A3B__", 0, 0x2000, "x256a3b" },
+ { "atxmega256a3bu", ARCH_AVRXMEGA6, "__AVR_ATxmega256A3BU__", 0, 0x2000, "x256a3bu" },
+ { "atxmega256d3", ARCH_AVRXMEGA6, "__AVR_ATxmega256D3__", 0, 0x2000, "x256d3" },
+- /* Xmega, > 128K, <= 256K FLASH, > 64K RAM. */
++ /* Xmega, >= 128K, <= 256K FLASH, > 64K RAM. */
+ { "avrxmega7", ARCH_AVRXMEGA7, NULL, 0, 0x2000, "x128a1" },
+ { "atxmega128a1", ARCH_AVRXMEGA7, "__AVR_ATxmega128A1__", 0, 0x2000, "x128a1" },
+ { "atxmega128a1u", ARCH_AVRXMEGA7, "__AVR_ATxmega128A1U__", 0, 0x2000, "x128a1u" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-02 12:01:05.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-02 12:12:37.000000000 +0300
+@@ -266,10 +266,12 @@ MULTILIB_MATCHES = \
+ mmcu?avr6=mmcu?atmega2560 \
+ mmcu?avr6=mmcu?atmega2561 \
+ mmcu?avrxmega2=mmcu?atxmega16a4 \
++ mmcu?avrxmega2=mmcu?atxmega16a4u \
+ mmcu?avrxmega2=mmcu?atxmega16d4 \
+ mmcu?avrxmega2=mmcu?atxmega16x1 \
+ mmcu?avrxmega2=mmcu?atxmega32d4 \
+ mmcu?avrxmega2=mmcu?atxmega32a4 \
++ mmcu?avrxmega2=mmcu?atxmega32a4u \
+ mmcu?avrxmega4=mmcu?atxmega64a3 \
+ mmcu?avrxmega4=mmcu?atxmega64d3 \
+ mmcu?avrxmega5=mmcu?atxmega64a1 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-02 12:18:00.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-02 12:20:38.000000000 +0300
+@@ -262,6 +262,7 @@ const struct mcu_type_s avr_mcu_types[]
+ /* Xmega, >= 64K, < 128K FLASH, <= 64K RAM. */
+ { "avrxmega4", ARCH_AVRXMEGA4, NULL, 0, 0x2000, "x64d3" },
+ { "atxmega64a3", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3__", 0, 0x2000, "x64a3" },
++ { "atxmega64a3u", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3U__", 0, 0x2000, "x64a3u"},
+ { "atxmega64d3", ARCH_AVRXMEGA4, "__AVR_ATxmega64D3__", 0, 0x2000, "x64d3" },
+ /* Xmega, >= 64K, < 128K FLASH, > 64K RAM. */
+ { "avrxmega5", ARCH_AVRXMEGA5, NULL, 0, 0x2000, "x64a1" },
+@@ -270,11 +271,14 @@ const struct mcu_type_s avr_mcu_types[]
+ /* Xmega, >= 128K, <= 256K FLASH, <= 64K RAM. */
+ { "avrxmega6", ARCH_AVRXMEGA6, NULL, 0, 0x2000, "x128a3" },
+ { "atxmega128a3", ARCH_AVRXMEGA6, "__AVR_ATxmega128A3__", 0, 0x2000, "x128a3" },
++ { "atxmega128a3u",ARCH_AVRXMEGA6, "__AVR_ATxmega128A3U__", 0, 0x2000, "x128a3u"},
+ { "atxmega128b1", ARCH_AVRXMEGA6, "__AVR_ATxmega128B1__", 0, 0x2000, "x128b1" },
+ { "atxmega128d3", ARCH_AVRXMEGA6, "__AVR_ATxmega128D3__", 0, 0x2000, "x128d3" },
+ { "atxmega192a3", ARCH_AVRXMEGA6, "__AVR_ATxmega192A3__", 0, 0x2000, "x192a3" },
++ { "atxmega192a3u",ARCH_AVRXMEGA6, "__AVR_ATxmega192A3U__", 0, 0x2000, "x192a3u"},
+ { "atxmega192d3", ARCH_AVRXMEGA6, "__AVR_ATxmega192D3__", 0, 0x2000, "x192d3" },
+ { "atxmega256a3", ARCH_AVRXMEGA6, "__AVR_ATxmega256A3__", 0, 0x2000, "x256a3" },
++ { "atxmega256a3u",ARCH_AVRXMEGA6, "__AVR_ATxmega256A3U__", 0, 0x2000, "x256a3u"},
+ { "atxmega256a3b",ARCH_AVRXMEGA6, "__AVR_ATxmega256A3B__", 0, 0x2000, "x256a3b" },
+ { "atxmega256a3bu", ARCH_AVRXMEGA6, "__AVR_ATxmega256A3BU__", 0, 0x2000, "x256a3bu" },
+ { "atxmega256d3", ARCH_AVRXMEGA6, "__AVR_ATxmega256D3__", 0, 0x2000, "x256d3" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-02 12:18:00.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-02 12:20:38.000000000 +0300
+@@ -273,15 +273,19 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega2=mmcu?atxmega32a4 \
+ mmcu?avrxmega2=mmcu?atxmega32a4u \
+ mmcu?avrxmega4=mmcu?atxmega64a3 \
++ mmcu?avrxmega4=mmcu?atxmega64a3u \
+ mmcu?avrxmega4=mmcu?atxmega64d3 \
+ mmcu?avrxmega5=mmcu?atxmega64a1 \
+ mmcu?avrxmega5=mmcu?atxmega64a1u \
+ mmcu?avrxmega6=mmcu?atxmega128a3 \
++ mmcu?avrxmega6=mmcu?atxmega128a3u \
+ mmcu?avrxmega6=mmcu?atxmega128b1 \
+ mmcu?avrxmega6=mmcu?atxmega128d3 \
+ mmcu?avrxmega6=mmcu?atxmega192a3 \
++ mmcu?avrxmega6=mmcu?atxmega192a3u \
+ mmcu?avrxmega6=mmcu?atxmega192d3 \
+ mmcu?avrxmega6=mmcu?atxmega256a3 \
++ mmcu?avrxmega6=mmcu?atxmega256a3u \
+ mmcu?avrxmega6=mmcu?atxmega256a3b \
+ mmcu?avrxmega6=mmcu?atxmega256a3bu \
+ mmcu?avrxmega6=mmcu?atxmega256d3 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-06-24 16:02:11.000000000 +0530
++++ gcc/config/avr/avr-devices.c 2011-06-24 15:45:54.000000000 +0530
+@@ -210,6 +210,8 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega64c1", ARCH_AVR5, "__AVR_ATmega64C1__", 0, 0x0100, "m64c1" },
+ { "atmega64m1", ARCH_AVR5, "__AVR_ATmega64M1__", 0, 0x0100, "m64m1" },
+ { "atmega64hve", ARCH_AVR5, "__AVR_ATmega64HVE__", 0, 0x0100, "m64hve" },
++ { "atmega64rfa2", ARCH_AVR5, "__AVR_ATmega64RFA2__", 0, 0x0200, "m64rfa2"},
++ { "atmega64rfr2", ARCH_AVR5, "__AVR_ATmega64RFR2__", 0, 0x0200, "m64rfr2"},
+ { "atmega32hvb", ARCH_AVR5, "__AVR_ATmega32HVB__", 0, 0x0100, "m32hvb" },
+ { "atmega32hvbrevb", ARCH_AVR5, "__AVR_ATmega32HVBREVB__", 1, 0x0100, "m32hvbrevb" },
+ { "at90can32", ARCH_AVR5, "__AVR_AT90CAN32__", 0, 0x0100, "can32" },
+@@ -238,14 +240,18 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega1281", ARCH_AVR51, "__AVR_ATmega1281__", 0, 0x0200, "m1281" },
+ { "atmega1284p", ARCH_AVR51, "__AVR_ATmega1284P__", 0, 0x0100, "m1284p" },
+ { "atmega128rfa1", ARCH_AVR51, "__AVR_ATmega128RFA1__", 0, 0x0200, "m128rfa1" },
++ { "atmega128rfa2", ARCH_AVR51, "__AVR_ATmega128RFA2__", 0, 0x0200, "m128rfa2" },
++ { "atmega128rfr2", ARCH_AVR51, "__AVR_ATmega128RFR2__", 0, 0x0200, "m128rfr2" },
+ { "at90can128", ARCH_AVR51, "__AVR_AT90CAN128__", 0, 0x0100, "can128" },
+ { "at90usb1286", ARCH_AVR51, "__AVR_AT90USB1286__", 0, 0x0100, "usb1286" },
+ { "at90usb1287", ARCH_AVR51, "__AVR_AT90USB1287__", 0, 0x0100, "usb1286" },
+ /* Enhanced, ==256K + 3-Byte PC +
+- { MOVW/LPMX, JMP/CALL, MUL, ELPM, ELPMX }. */
++ { MOVW/LPMX, JMP/CALL, MUL, ELPM, ELPMX, EIJMP/EICALL }. */
+ { "avr6", ARCH_AVR6, NULL, 0, 0x0200, "m2561" },
+ { "atmega2560", ARCH_AVR6, "__AVR_ATmega2560__", 0, 0x0200, "m2561" },
+ { "atmega2561", ARCH_AVR6, "__AVR_ATmega2561__", 0, 0x0200, "m2561" },
++ { "atmega256rfa2", ARCH_AVR6, "__AVR_ATmega256RFA2__", 0, 0x0200, "m256rfa2" },
++ { "atmega256rfr2", ARCH_AVR6, "__AVR_ATmega256RFR2__", 0, 0x0200, "m256rfr2" },
+ /* Enhanced, == 256K. */
+ /* Xmega, <= 8K FLASH. */
+ /* Xmega, > 8K, < 64K FLASH, <= 64K RAM. */
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-06-24 16:02:11.000000000 +0530
++++ gcc/config/avr/t-avr 2011-06-24 15:56:46.000000000 +0530
+@@ -213,6 +213,8 @@ MULTILIB_MATCHES = \
+ mmcu?avr5=mmcu?atmega3290p \
+ mmcu?avr5=mmcu?atmega3290pa \
+ mmcu?avr5=mmcu?atmega406 \
++ mmcu?avr5=mmcu?atmega64rfa2 \
++ mmcu?avr5=mmcu?atmega64rfr2 \
+ mmcu?avr5=mmcu?atmega64 \
+ mmcu?avr5=mmcu?atmega640 \
+ mmcu?avr5=mmcu?atmega644 \
+@@ -259,10 +261,14 @@ MULTILIB_MATCHES = \
+ mmcu?avr51=mmcu?atmega1281 \
+ mmcu?avr51=mmcu?atmega1284p \
+ mmcu?avr51=mmcu?atmega128rfa1 \
++ mmcu?avr51=mmcu?atmega128rfa2 \
++ mmcu?avr51=mmcu?atmega128rfr2 \
+ mmcu?avr51=mmcu?at90can128 \
+ mmcu?avr51=mmcu?at90usb1286 \
+ mmcu?avr51=mmcu?at90usb1287 \
+ mmcu?avr51=mmcu?m3000 \
++ mmcu?avr6=mmcu?atmega256rfa2 \
++ mmcu?avr6=mmcu?atmega256rfr2 \
+ mmcu?avr6=mmcu?atmega2560 \
+ mmcu?avr6=mmcu?atmega2561 \
+ mmcu?avrxmega2=mmcu?atxmega16a4 \
--- /dev/null
+diff -Naurp ./gcc/config/avr/avr-devices.c ./gcc/config/avr/avr-devices.c
+--- ./gcc/config/avr/avr-devices.c 2011-06-21 12:25:28.000000000 +0530
++++ ./gcc/config/avr/avr-devices.c 2011-06-21 12:30:08.000000000 +0530
+@@ -148,6 +148,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega165", ARCH_AVR5, "__AVR_ATmega165__", 0, 0x0100, "m165" },
+ { "atmega165a", ARCH_AVR5, "__AVR_ATmega165A__", 0, 0x0100, "m165a" },
+ { "atmega165p", ARCH_AVR5, "__AVR_ATmega165P__", 0, 0x0100, "m165p" },
++ { "atmega165pa", ARCH_AVR5, "__AVR_ATmega165PA__", 0, 0x0100, "m165pa" },
+ { "atmega168", ARCH_AVR5, "__AVR_ATmega168__", 0, 0x0100, "m168" },
+ { "atmega168a", ARCH_AVR5, "__AVR_ATmega168A__", 0, 0x0100, "m168a" },
+ { "atmega168p", ARCH_AVR5, "__AVR_ATmega168P__", 0, 0x0100, "m168p" },
+diff -Naurp ./gcc/config/avr/t-avr ./gcc/config/avr/t-avr
+--- ./gcc/config/avr/t-avr 2011-06-21 12:25:28.000000000 +0530
++++ ./gcc/config/avr/t-avr 2011-06-21 12:31:55.000000000 +0530
+@@ -182,6 +182,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr5=mmcu?atmega165 \
+ mmcu?avr5=mmcu?atmega165a \
+ mmcu?avr5=mmcu?atmega165p \
++ mmcu?avr5=mmcu?atmega165pa \
+ mmcu?avr5=mmcu?atmega168 \
+ mmcu?avr5=mmcu?atmega168a \
+ mmcu?avr5=mmcu?atmega168p \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-02 12:26:35.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-02 12:26:12.000000000 +0300
+@@ -275,7 +275,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "avrxmega5", ARCH_AVRXMEGA5, NULL, 0, 0x2000, "x64a1" },
+ { "atxmega64a1", ARCH_AVRXMEGA5, "__AVR_ATxmega64A1__", 0, 0x2000, "x64a1" },
+ { "atxmega64a1u", ARCH_AVRXMEGA5, "__AVR_ATxmega64A1U__", 0, 0x2000, "x64a1u" },
+- /* Xmega, >= 128K, <= 256K FLASH, <= 64K RAM. */
++ /* Xmega, >= 128K FLASH, <= 64K RAM. */
+ { "avrxmega6", ARCH_AVRXMEGA6, NULL, 0, 0x2000, "x128a3" },
+ { "atxmega128a3", ARCH_AVRXMEGA6, "__AVR_ATxmega128A3__", 0, 0x2000, "x128a3" },
+ { "atxmega128a3u",ARCH_AVRXMEGA6, "__AVR_ATxmega128A3U__", 0, 0x2000, "x128a3u"},
+@@ -289,7 +289,8 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atxmega256a3b",ARCH_AVRXMEGA6, "__AVR_ATxmega256A3B__", 0, 0x2000, "x256a3b" },
+ { "atxmega256a3bu", ARCH_AVRXMEGA6, "__AVR_ATxmega256A3BU__", 0, 0x2000, "x256a3bu" },
+ { "atxmega256d3", ARCH_AVRXMEGA6, "__AVR_ATxmega256D3__", 0, 0x2000, "x256d3" },
+- /* Xmega, >= 128K, <= 256K FLASH, > 64K RAM. */
++ { "atxmega384c3", ARCH_AVRXMEGA6, "__AVR_ATxmega384C3__", 0, 0x2000, "x384c3" },
++ /* Xmega, >= 128K FLASH, > 64K RAM. */
+ { "avrxmega7", ARCH_AVRXMEGA7, NULL, 0, 0x2000, "x128a1" },
+ { "atxmega128a1", ARCH_AVRXMEGA7, "__AVR_ATxmega128A1__", 0, 0x2000, "x128a1" },
+ { "atxmega128a1u", ARCH_AVRXMEGA7, "__AVR_ATxmega128A1U__", 0, 0x2000, "x128a1u" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-02 12:26:35.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-02 12:26:12.000000000 +0300
+@@ -296,6 +296,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega6=mmcu?atxmega256a3b \
+ mmcu?avrxmega6=mmcu?atxmega256a3bu \
+ mmcu?avrxmega6=mmcu?atxmega256d3 \
++ mmcu?avrxmega6=mmcu?atxmega384c3 \
+ mmcu?avrxmega7=mmcu?atxmega128a1 \
+ mmcu?avrxmega7=mmcu?atxmega128a1u \
+ mmcu?avrtiny10=mmcu?attiny4 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-06-10 16:21:40.000000000 -0500
++++ gcc/config/avr/avr-devices.c 2011-06-16 11:39:07.000000000 -0500
+@@ -96,6 +96,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "attiny87", ARCH_AVR25, "__AVR_ATtiny87__", 0, 0x0100, "tn87" },
+ { "attiny48", ARCH_AVR25, "__AVR_ATtiny48__", 0, 0x0100, "tn48" },
+ { "attiny88", ARCH_AVR25, "__AVR_ATtiny88__", 0, 0x0100, "tn88" },
++ { "attiny80", ARCH_AVR25, "__AVR_ATtiny80__", 0, 0x0100, "tn80" },
+ { "at86rf401", ARCH_AVR25, "__AVR_AT86RF401__", 1, 0x0060, "86401" },
+ /* Classic, > 8K, <= 64K +2-byte PC + { JMP/CALL }. */
+ { "avr3", ARCH_AVR3, NULL, 0, 0x0060, "43355" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-06-10 16:21:40.000000000 -0500
++++ gcc/config/avr/t-avr 2011-06-16 11:39:55.000000000 -0500
+@@ -141,6 +141,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr25=mmcu?attiny87 \
+ mmcu?avr25=mmcu?attiny48 \
+ mmcu?avr25=mmcu?attiny88 \
++ mmcu?avr25=mmcu?attiny80 \
+ mmcu?avr25=mmcu?at86rf401 \
+ mmcu?avr3=mmcu?at43usb355 \
+ mmcu?avr3=mmcu?at76c711 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-02 12:31:10.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-02 12:30:51.000000000 +0300
+@@ -295,6 +295,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "avrxmega7", ARCH_AVRXMEGA7, NULL, 0, 0x2000, "x128a1" },
+ { "atxmega128a1", ARCH_AVRXMEGA7, "__AVR_ATxmega128A1__", 0, 0x2000, "x128a1" },
+ { "atxmega128a1u", ARCH_AVRXMEGA7, "__AVR_ATxmega128A1U__", 0, 0x2000, "x128a1u" },
++ { "atxmega128a4u", ARCH_AVRXMEGA7, "__AVR_ATxmega128A4U__", 0, 0x2000, "x128a4u" },
+ /* tiny10 family */
+ { "avrtiny10", ARCH_AVRTINY10, NULL, 0, 0x0040, "tn10" },
+ { "attiny4", ARCH_AVRTINY10, "__AVR_ATtiny4__", 0, 0x0040, "tn4" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-02 12:31:10.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-02 12:30:51.000000000 +0300
+@@ -300,6 +300,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega6=mmcu?atxmega384c3 \
+ mmcu?avrxmega7=mmcu?atxmega128a1 \
+ mmcu?avrxmega7=mmcu?atxmega128a1u \
++ mmcu?avrxmega7=mmcu?atxmega128a4u \
+ mmcu?avrtiny10=mmcu?attiny4 \
+ mmcu?avrtiny10=mmcu?attiny5 \
+ mmcu?avrtiny10=mmcu?attiny9 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-02 12:37:07.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-02 12:37:47.000000000 +0300
+@@ -272,6 +272,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atxmega64a3", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3__", 0, 0x2000, "x64a3" },
+ { "atxmega64a3u", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3U__", 0, 0x2000, "x64a3u"},
+ { "atxmega64d3", ARCH_AVRXMEGA4, "__AVR_ATxmega64D3__", 0, 0x2000, "x64d3" },
++ { "atxmega64d4", ARCH_AVRXMEGA4, "__AVR_ATxmega64D4__", 0, 0x2000, "x64d4" },
+ /* Xmega, >= 64K, < 128K FLASH, > 64K RAM. */
+ { "avrxmega5", ARCH_AVRXMEGA5, NULL, 0, 0x2000, "x64a1" },
+ { "atxmega64a1", ARCH_AVRXMEGA5, "__AVR_ATxmega64A1__", 0, 0x2000, "x64a1" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-02 12:37:07.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-02 12:37:47.000000000 +0300
+@@ -283,6 +283,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega4=mmcu?atxmega64a3 \
+ mmcu?avrxmega4=mmcu?atxmega64a3u \
+ mmcu?avrxmega4=mmcu?atxmega64d3 \
++ mmcu?avrxmega4=mmcu?atxmega64d4 \
+ mmcu?avrxmega5=mmcu?atxmega64a1 \
+ mmcu?avrxmega5=mmcu?atxmega64a1u \
+ mmcu?avrxmega6=mmcu?atxmega128a3 \
--- /dev/null
+diff -Naurp ./gcc/config/avr/avr-devices.c ./gcc/config/avr/avr-devices.c
+--- ./gcc/config/avr/avr-devices.c 2011-08-30 14:41:43.000000000 +0300
++++ ./gcc/config/avr/avr-devices.c 2011-08-30 14:45:00.000000000 +0300
+@@ -146,6 +146,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega163", ARCH_AVR5, "__AVR_ATmega163__", 0, 0x0060, "m163" },
+ { "atmega164a", ARCH_AVR5, "__AVR_ATmega164A__", 0, 0x0060, "m164a" },
+ { "atmega164p", ARCH_AVR5, "__AVR_ATmega164P__", 0, 0x0100, "m164p" },
++ { "atmega164pa", ARCH_AVR5, "__AVR_ATmega164PA__", 0, 0x0100, "m164pa" },
+ { "atmega165", ARCH_AVR5, "__AVR_ATmega165__", 0, 0x0100, "m165" },
+ { "atmega165a", ARCH_AVR5, "__AVR_ATmega165A__", 0, 0x0100, "m165a" },
+ { "atmega165p", ARCH_AVR5, "__AVR_ATmega165P__", 0, 0x0100, "m165p" },
+@@ -153,6 +154,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega168", ARCH_AVR5, "__AVR_ATmega168__", 0, 0x0100, "m168" },
+ { "atmega168a", ARCH_AVR5, "__AVR_ATmega168A__", 0, 0x0100, "m168a" },
+ { "atmega168p", ARCH_AVR5, "__AVR_ATmega168P__", 0, 0x0100, "m168p" },
++ { "atmega168pa", ARCH_AVR5, "__AVR_ATmega168PA__", 0, 0x0100, "m168pa" },
+ { "atmega169", ARCH_AVR5, "__AVR_ATmega169__", 0, 0x0100, "m169" },
+ { "atmega169a", ARCH_AVR5, "__AVR_ATmega169A__", 0, 0x0100, "m169a" },
+ { "atmega169p", ARCH_AVR5, "__AVR_ATmega169P__", 0, 0x0100, "m169p" },
+@@ -164,6 +166,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega16m1", ARCH_AVR5, "__AVR_ATmega16M1__", 0, 0x0100, "m16m1" },
+ { "atmega16u4", ARCH_AVR5, "__AVR_ATmega16U4__", 0, 0x0100, "m16u4" },
+ { "atmega32", ARCH_AVR5, "__AVR_ATmega32__", 0, 0x0060, "m32" },
++ { "atmega32a", ARCH_AVR5, "__AVR_ATmega32A__", 0, 0x0060, "m32a" },
+ { "atmega323", ARCH_AVR5, "__AVR_ATmega323__", 0, 0x0060, "m323" },
+ { "atmega324a", ARCH_AVR5, "__AVR_ATmega324A__", 0, 0x0060, "m324a" },
+ { "atmega324p", ARCH_AVR5, "__AVR_ATmega324P__", 0, 0x0100, "m324p" },
+@@ -192,6 +195,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega32u6", ARCH_AVR5, "__AVR_ATmega32U6__", 0, 0x0100, "m32u6" },
+ { "atmega406", ARCH_AVR5, "__AVR_ATmega406__", 0, 0x0100, "m406" },
+ { "atmega64", ARCH_AVR5, "__AVR_ATmega64__", 0, 0x0100, "m64" },
++ { "atmega64a", ARCH_AVR5, "__AVR_ATmega64A__", 0, 0x0100, "m64a" },
+ { "atmega640", ARCH_AVR5, "__AVR_ATmega640__", 0, 0x0200, "m640" },
+ { "atmega644", ARCH_AVR5, "__AVR_ATmega644__", 0, 0x0100, "m644" },
+ { "atmega644a", ARCH_AVR5, "__AVR_ATmega644A__", 0, 0x0100, "m644a" },
+diff -Naurp ./gcc/config/avr/t-avr ./gcc/config/avr/t-avr
+--- ./gcc/config/avr/t-avr 2011-08-30 14:41:43.000000000 +0300
++++ ./gcc/config/avr/t-avr 2011-08-30 14:45:00.000000000 +0300
+@@ -180,6 +180,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr5=mmcu?atmega163 \
+ mmcu?avr5=mmcu?atmega164a \
+ mmcu?avr5=mmcu?atmega164p \
++ mmcu?avr5=mmcu?atmega164pa \
+ mmcu?avr5=mmcu?atmega165 \
+ mmcu?avr5=mmcu?atmega165a \
+ mmcu?avr5=mmcu?atmega165p \
+@@ -187,11 +188,13 @@ MULTILIB_MATCHES = \
+ mmcu?avr5=mmcu?atmega168 \
+ mmcu?avr5=mmcu?atmega168a \
+ mmcu?avr5=mmcu?atmega168p \
++ mmcu?avr5=mmcu?atmega168pa \
+ mmcu?avr5=mmcu?atmega169 \
+ mmcu?avr5=mmcu?atmega169a \
+ mmcu?avr5=mmcu?atmega169p \
+ mmcu?avr5=mmcu?atmega169pa \
+ mmcu?avr5=mmcu?atmega32 \
++ mmcu?avr5=mmcu?atmega32a \
+ mmcu?avr5=mmcu?atmega323 \
+ mmcu?avr5=mmcu?atmega324a \
+ mmcu?avr5=mmcu?atmega324p \
+@@ -218,6 +221,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr5=mmcu?atmega64rfa2 \
+ mmcu?avr5=mmcu?atmega64rfr2 \
+ mmcu?avr5=mmcu?atmega64 \
++ mmcu?avr5=mmcu?atmega64a \
+ mmcu?avr5=mmcu?atmega640 \
+ mmcu?avr5=mmcu?atmega644 \
+ mmcu?avr5=mmcu?atmega644a \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-02 12:44:50.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-02 12:55:09.000000000 +0300
+@@ -269,6 +269,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atxmega32a4", ARCH_AVRXMEGA2, "__AVR_ATxmega32A4__", 0, 0x2000, "x32a4" },
+ { "atxmega32a4u", ARCH_AVRXMEGA2, "__AVR_ATxmega32A4U__", 0, 0x2000, "x32a4u" },
+ { "atxmega32d4", ARCH_AVRXMEGA2, "__AVR_ATxmega32D4__", 0, 0x2000, "x32d4" },
++ { "atxmega32x1", ARCH_AVRXMEGA2, "__AVR_ATxmega32X1__", 0, 0x2000, "x32x1" },
+ /* Xmega, > 8K, <= 64K FLASH, > 64K RAM. */
+ /* { "avrxmega3", ARCH_AVRXMEGA3, NULL }, */
+ /* Xmega, >= 64K, < 128K FLASH, <= 64K RAM. */
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-02 12:43:34.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-02 12:55:52.000000000 +0300
+@@ -284,6 +284,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega2=mmcu?atxmega32d4 \
+ mmcu?avrxmega2=mmcu?atxmega32a4 \
+ mmcu?avrxmega2=mmcu?atxmega32a4u \
++ mmcu?avrxmega2=mmcu?atxmega32x1 \
+ mmcu?avrxmega4=mmcu?atxmega64a3 \
+ mmcu?avrxmega4=mmcu?atxmega64a3u \
+ mmcu?avrxmega4=mmcu?atxmega64d3 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-05 14:52:39.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-05 14:55:31.000000000 +0300
+@@ -276,6 +276,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "avrxmega4", ARCH_AVRXMEGA4, NULL, 0, 0x2000, "x64d3" },
+ { "atxmega64a3", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3__", 0, 0x2000, "x64a3" },
+ { "atxmega64a3u", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3U__", 0, 0x2000, "x64a3u"},
++ { "atxmega64b3", ARCH_AVRXMEGA4, "__AVR_ATxmega64B3__", 0, 0x2000, "x64b3"},
+ { "atxmega64d3", ARCH_AVRXMEGA4, "__AVR_ATxmega64D3__", 0, 0x2000, "x64d3" },
+ { "atxmega64d4", ARCH_AVRXMEGA4, "__AVR_ATxmega64D4__", 0, 0x2000, "x64d4" },
+ /* Xmega, >= 64K, < 128K FLASH, > 64K RAM. */
+@@ -287,6 +288,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atxmega128a3", ARCH_AVRXMEGA6, "__AVR_ATxmega128A3__", 0, 0x2000, "x128a3" },
+ { "atxmega128a3u",ARCH_AVRXMEGA6, "__AVR_ATxmega128A3U__", 0, 0x2000, "x128a3u"},
+ { "atxmega128b1", ARCH_AVRXMEGA6, "__AVR_ATxmega128B1__", 0, 0x2000, "x128b1" },
++ { "atxmega128b3", ARCH_AVRXMEGA6, "__AVR_ATxmega128B3__", 0, 0x2000, "x128b3" },
+ { "atxmega128d3", ARCH_AVRXMEGA6, "__AVR_ATxmega128D3__", 0, 0x2000, "x128d3" },
+ { "atxmega192a3", ARCH_AVRXMEGA6, "__AVR_ATxmega192A3__", 0, 0x2000, "x192a3" },
+ { "atxmega192a3u",ARCH_AVRXMEGA6, "__AVR_ATxmega192A3U__", 0, 0x2000, "x192a3u"},
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-05 14:52:39.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-05 14:56:06.000000000 +0300
+@@ -287,6 +287,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega2=mmcu?atxmega32x1 \
+ mmcu?avrxmega4=mmcu?atxmega64a3 \
+ mmcu?avrxmega4=mmcu?atxmega64a3u \
++ mmcu?avrxmega4=mmcu?atxmega64b3 \
+ mmcu?avrxmega4=mmcu?atxmega64d3 \
+ mmcu?avrxmega4=mmcu?atxmega64d4 \
+ mmcu?avrxmega5=mmcu?atxmega64a1 \
+@@ -294,6 +295,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega6=mmcu?atxmega128a3 \
+ mmcu?avrxmega6=mmcu?atxmega128a3u \
+ mmcu?avrxmega6=mmcu?atxmega128b1 \
++ mmcu?avrxmega6=mmcu?atxmega128b3 \
+ mmcu?avrxmega6=mmcu?atxmega128d3 \
+ mmcu?avrxmega6=mmcu?atxmega192a3 \
+ mmcu?avrxmega6=mmcu?atxmega192a3u \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-07 18:19:24.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-07 18:22:51.000000000 +0300
+@@ -276,6 +276,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "avrxmega4", ARCH_AVRXMEGA4, NULL, 0, 0x2000, "x64d3" },
+ { "atxmega64a3", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3__", 0, 0x2000, "x64a3" },
+ { "atxmega64a3u", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3U__", 0, 0x2000, "x64a3u"},
++ { "atxmega64b1", ARCH_AVRXMEGA4, "__AVR_ATxmega64B1__", 0, 0x2000, "x64b1" },
+ { "atxmega64b3", ARCH_AVRXMEGA4, "__AVR_ATxmega64B3__", 0, 0x2000, "x64b3"},
+ { "atxmega64d3", ARCH_AVRXMEGA4, "__AVR_ATxmega64D3__", 0, 0x2000, "x64d3" },
+ { "atxmega64d4", ARCH_AVRXMEGA4, "__AVR_ATxmega64D4__", 0, 0x2000, "x64d4" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-07 18:19:24.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-07 18:23:45.000000000 +0300
+@@ -287,6 +287,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega2=mmcu?atxmega32x1 \
+ mmcu?avrxmega4=mmcu?atxmega64a3 \
+ mmcu?avrxmega4=mmcu?atxmega64a3u \
++ mmcu?avrxmega4=mmcu?atxmega64b1 \
+ mmcu?avrxmega4=mmcu?atxmega64b3 \
+ mmcu?avrxmega4=mmcu?atxmega64d3 \
+ mmcu?avrxmega4=mmcu?atxmega64d4 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-08 17:29:28.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-08 17:34:31.000000000 +0300
+@@ -118,6 +118,7 @@ const struct mcu_type_s avr_mcu_types[]
+ /* Enhanced, <= 8K + 2-byte PC + { MOVW/LPMX, MUL }. */
+ { "avr4", ARCH_AVR4, NULL, 0, 0x0060, "m8" },
+ { "atmega8", ARCH_AVR4, "__AVR_ATmega8__", 0, 0x0060, "m8" },
++ { "atmega8a", ARCH_AVR4, "__AVR_ATmega8A__", 0, 0x0060, "m8a" },
+ { "atmega48", ARCH_AVR4, "__AVR_ATmega48__", 0, 0x0100, "m48" },
+ { "atmega48a", ARCH_AVR4, "__AVR_ATmega48A__", 0, 0x0100, "m48a" },
+ { "atmega48pa", ARCH_AVR4, "__AVR_ATmega48PA__", 0, 0x0100, "m48pa" },
+@@ -242,8 +243,10 @@ const struct mcu_type_s avr_mcu_types[]
+ { MOVW/LPMX, JMP/CALL, MUL, ELPM, ELPMX }. */
+ { "avr51", ARCH_AVR51, NULL, 0, 0x0100, "m128" },
+ { "atmega128", ARCH_AVR51, "__AVR_ATmega128__", 0, 0x0100, "m128" },
++ { "atmega128a", ARCH_AVR51, "__AVR_ATmega128A__", 0, 0x0100, "m128a" },
+ { "atmega1280", ARCH_AVR51, "__AVR_ATmega1280__", 0, 0x0200, "m1280" },
+ { "atmega1281", ARCH_AVR51, "__AVR_ATmega1281__", 0, 0x0200, "m1281" },
++ { "atmega1284", ARCH_AVR51, "__AVR_ATmega1284__", 0, 0x0100, "m1284" },
+ { "atmega1284p", ARCH_AVR51, "__AVR_ATmega1284P__", 0, 0x0100, "m1284p" },
+ { "atmega128rfa1", ARCH_AVR51, "__AVR_ATmega128RFA1__", 0, 0x0200, "m128rfa1" },
+ { "atmega128rfa2", ARCH_AVR51, "__AVR_ATmega128RFA2__", 0, 0x0200, "m128rfa2" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-08 17:29:28.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-08 17:37:19.000000000 +0300
+@@ -159,6 +159,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr4=mmcu?atmega48pa \
+ mmcu?avr4=mmcu?atmega48p \
+ mmcu?avr4=mmcu?atmega8 \
++ mmcu?avr4=mmcu?atmega8a \
+ mmcu?avr4=mmcu?atmega8515 \
+ mmcu?avr4=mmcu?atmega8535 \
+ mmcu?avr4=mmcu?atmega88 \
+@@ -263,8 +264,10 @@ MULTILIB_MATCHES = \
+ mmcu?avr5=mmcu?at90usb647 \
+ mmcu?avr5=mmcu?at94k \
+ mmcu?avr51=mmcu?atmega128 \
++ mmcu?avr51=mmcu?atmega128a \
+ mmcu?avr51=mmcu?atmega1280 \
+ mmcu?avr51=mmcu?atmega1281 \
++ mmcu?avr51=mmcu?atmega1284 \
+ mmcu?avr51=mmcu?atmega1284p \
+ mmcu?avr51=mmcu?atmega128rfa1 \
+ mmcu?avr51=mmcu?atmega128rfa2 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-12 14:07:28.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-12 14:29:05.000000000 +0300
+@@ -279,6 +279,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "avrxmega4", ARCH_AVRXMEGA4, NULL, 0, 0x2000, "x64d3" },
+ { "atxmega64a3", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3__", 0, 0x2000, "x64a3" },
+ { "atxmega64a3u", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3U__", 0, 0x2000, "x64a3u"},
++ { "atxmega64a4u", ARCH_AVRXMEGA4, "__AVR_ATxmega64A4U__", 0, 0x2000, "x64a4u"},
+ { "atxmega64b1", ARCH_AVRXMEGA4, "__AVR_ATxmega64B1__", 0, 0x2000, "x64b1" },
+ { "atxmega64b3", ARCH_AVRXMEGA4, "__AVR_ATxmega64B3__", 0, 0x2000, "x64b3"},
+ { "atxmega64d3", ARCH_AVRXMEGA4, "__AVR_ATxmega64D3__", 0, 0x2000, "x64d3" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-12 14:07:28.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-12 14:29:05.000000000 +0300
+@@ -290,6 +290,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega2=mmcu?atxmega32x1 \
+ mmcu?avrxmega4=mmcu?atxmega64a3 \
+ mmcu?avrxmega4=mmcu?atxmega64a3u \
++ mmcu?avrxmega4=mmcu?atxmega64a4u \
+ mmcu?avrxmega4=mmcu?atxmega64b1 \
+ mmcu?avrxmega4=mmcu?atxmega64b3 \
+ mmcu?avrxmega4=mmcu?atxmega64d3 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-15 11:58:29.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-15 12:01:45.000000000 +0300
+@@ -295,6 +295,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atxmega128b1", ARCH_AVRXMEGA6, "__AVR_ATxmega128B1__", 0, 0x2000, "x128b1" },
+ { "atxmega128b3", ARCH_AVRXMEGA6, "__AVR_ATxmega128B3__", 0, 0x2000, "x128b3" },
+ { "atxmega128d3", ARCH_AVRXMEGA6, "__AVR_ATxmega128D3__", 0, 0x2000, "x128d3" },
++ { "atxmega128d4", ARCH_AVRXMEGA6, "__AVR_ATxmega128D4__", 0, 0x2000, "x128d4" },
+ { "atxmega192a3", ARCH_AVRXMEGA6, "__AVR_ATxmega192A3__", 0, 0x2000, "x192a3" },
+ { "atxmega192a3u",ARCH_AVRXMEGA6, "__AVR_ATxmega192A3U__", 0, 0x2000, "x192a3u"},
+ { "atxmega192d3", ARCH_AVRXMEGA6, "__AVR_ATxmega192D3__", 0, 0x2000, "x192d3" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-15 11:58:29.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-15 12:01:45.000000000 +0300
+@@ -302,6 +302,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega6=mmcu?atxmega128b1 \
+ mmcu?avrxmega6=mmcu?atxmega128b3 \
+ mmcu?avrxmega6=mmcu?atxmega128d3 \
++ mmcu?avrxmega6=mmcu?atxmega128d4 \
+ mmcu?avrxmega6=mmcu?atxmega192a3 \
+ mmcu?avrxmega6=mmcu?atxmega192a3u \
+ mmcu?avrxmega6=mmcu?atxmega192d3 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-09-14 14:49:30.000000000 +0300
++++ gcc/config/avr/avr-devices.c 2011-09-14 15:26:55.000000000 +0300
+@@ -265,6 +265,7 @@ const struct mcu_type_s avr_mcu_types[]
+ /* Xmega, <= 8K FLASH. */
+ /* Xmega, > 8K, < 64K FLASH, <= 64K RAM. */
+ { "avrxmega2", ARCH_AVRXMEGA2, NULL, 0, 0x2000, "x32a4" },
++ { "atmxt336s", ARCH_AVRXMEGA2, "__AVR_ATMXT336S__", 0, 0x2000, "mxt336s"},
+ { "atxmega16a4", ARCH_AVRXMEGA2, "__AVR_ATxmega16A4__", 0, 0x2000, "x16a4" },
+ { "atxmega16a4u", ARCH_AVRXMEGA2, "__AVR_ATxmega16A4U__", 0, 0x2000, "x16a4u" },
+ { "atxmega16d4", ARCH_AVRXMEGA2, "__AVR_ATxmega16D4__", 0, 0x2000, "x16d4" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-09-14 14:49:30.000000000 +0300
++++ gcc/config/avr/t-avr 2011-09-14 15:30:42.000000000 +0300
+@@ -280,6 +280,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr6=mmcu?atmega256rfr2 \
+ mmcu?avr6=mmcu?atmega2560 \
+ mmcu?avr6=mmcu?atmega2561 \
++ mmcu?avrxmega2=mmcu?atmxt336s \
+ mmcu?avrxmega2=mmcu?atxmega16a4 \
+ mmcu?avrxmega2=mmcu?atxmega16a4u \
+ mmcu?avrxmega2=mmcu?atxmega16d4 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-11-02 16:39:32.000000000 +0530
++++ gcc/config/avr/avr-devices.c 2011-11-02 16:37:08.000000000 +0530
+@@ -268,10 +268,12 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmxt336s", ARCH_AVRXMEGA2, "__AVR_ATMXT336S__", 0, 0x2000, "mxt336s"},
+ { "atxmega16a4", ARCH_AVRXMEGA2, "__AVR_ATxmega16A4__", 0, 0x2000, "x16a4" },
+ { "atxmega16a4u", ARCH_AVRXMEGA2, "__AVR_ATxmega16A4U__", 0, 0x2000, "x16a4u" },
++ { "atxmega16c4", ARCH_AVRXMEGA2, "__AVR_ATxmega16C4__", 0, 0x2000, "x16c4" },
+ { "atxmega16d4", ARCH_AVRXMEGA2, "__AVR_ATxmega16D4__", 0, 0x2000, "x16d4" },
+ { "atxmega16x1", ARCH_AVRXMEGA2, "__AVR_ATxmega16X1__", 0, 0x2000, "x16x1" },
+ { "atxmega32a4", ARCH_AVRXMEGA2, "__AVR_ATxmega32A4__", 0, 0x2000, "x32a4" },
+ { "atxmega32a4u", ARCH_AVRXMEGA2, "__AVR_ATxmega32A4U__", 0, 0x2000, "x32a4u" },
++ { "atxmega32c4", ARCH_AVRXMEGA2, "__AVR_ATxmega32C4__", 0, 0x2000, "x32c4" },
+ { "atxmega32d4", ARCH_AVRXMEGA2, "__AVR_ATxmega32D4__", 0, 0x2000, "x32d4" },
+ { "atxmega32x1", ARCH_AVRXMEGA2, "__AVR_ATxmega32X1__", 0, 0x2000, "x32x1" },
+ /* Xmega, > 8K, <= 64K FLASH, > 64K RAM. */
+@@ -295,6 +297,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atxmega128a3u",ARCH_AVRXMEGA6, "__AVR_ATxmega128A3U__", 0, 0x2000, "x128a3u"},
+ { "atxmega128b1", ARCH_AVRXMEGA6, "__AVR_ATxmega128B1__", 0, 0x2000, "x128b1" },
+ { "atxmega128b3", ARCH_AVRXMEGA6, "__AVR_ATxmega128B3__", 0, 0x2000, "x128b3" },
++ { "atxmega128c3", ARCH_AVRXMEGA6, "__AVR_ATxmega128C3__", 0, 0x2000, "x128c3" },
+ { "atxmega128d3", ARCH_AVRXMEGA6, "__AVR_ATxmega128D3__", 0, 0x2000, "x128d3" },
+ { "atxmega128d4", ARCH_AVRXMEGA6, "__AVR_ATxmega128D4__", 0, 0x2000, "x128d4" },
+ { "atxmega192a3", ARCH_AVRXMEGA6, "__AVR_ATxmega192A3__", 0, 0x2000, "x192a3" },
+@@ -304,6 +307,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atxmega256a3u",ARCH_AVRXMEGA6, "__AVR_ATxmega256A3U__", 0, 0x2000, "x256a3u"},
+ { "atxmega256a3b",ARCH_AVRXMEGA6, "__AVR_ATxmega256A3B__", 0, 0x2000, "x256a3b" },
+ { "atxmega256a3bu", ARCH_AVRXMEGA6, "__AVR_ATxmega256A3BU__", 0, 0x2000, "x256a3bu" },
++ { "atxmega256c3", ARCH_AVRXMEGA6, "__AVR_ATxmega256C3__", 0, 0x2000, "x256c3" },
+ { "atxmega256d3", ARCH_AVRXMEGA6, "__AVR_ATxmega256D3__", 0, 0x2000, "x256d3" },
+ { "atxmega384c3", ARCH_AVRXMEGA6, "__AVR_ATxmega384C3__", 0, 0x2000, "x384c3" },
+ /* Xmega, >= 128K FLASH, > 64K RAM. */
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-11-02 16:39:32.000000000 +0530
++++ gcc/config/avr/t-avr 2011-11-02 16:37:08.000000000 +0530
+@@ -283,8 +283,10 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega2=mmcu?atmxt336s \
+ mmcu?avrxmega2=mmcu?atxmega16a4 \
+ mmcu?avrxmega2=mmcu?atxmega16a4u \
++ mmcu?avrxmega2=mmcu?atxmega16c4 \
+ mmcu?avrxmega2=mmcu?atxmega16d4 \
+ mmcu?avrxmega2=mmcu?atxmega16x1 \
++ mmcu?avrxmega2=mmcu?atxmega32c4 \
+ mmcu?avrxmega2=mmcu?atxmega32d4 \
+ mmcu?avrxmega2=mmcu?atxmega32a4 \
+ mmcu?avrxmega2=mmcu?atxmega32a4u \
+@@ -302,6 +304,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega6=mmcu?atxmega128a3u \
+ mmcu?avrxmega6=mmcu?atxmega128b1 \
+ mmcu?avrxmega6=mmcu?atxmega128b3 \
++ mmcu?avrxmega6=mmcu?atxmega128c3 \
+ mmcu?avrxmega6=mmcu?atxmega128d3 \
+ mmcu?avrxmega6=mmcu?atxmega128d4 \
+ mmcu?avrxmega6=mmcu?atxmega192a3 \
+@@ -311,6 +314,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega6=mmcu?atxmega256a3u \
+ mmcu?avrxmega6=mmcu?atxmega256a3b \
+ mmcu?avrxmega6=mmcu?atxmega256a3bu \
++ mmcu?avrxmega6=mmcu?atxmega256c3 \
+ mmcu?avrxmega6=mmcu?atxmega256d3 \
+ mmcu?avrxmega6=mmcu?atxmega384c3 \
+ mmcu?avrxmega7=mmcu?atxmega128a1 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-11-08 15:04:32.000000000 +0530
++++ gcc/config/avr/avr-devices.c 2011-11-08 15:06:12.000000000 +0530
+@@ -310,6 +310,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atxmega256c3", ARCH_AVRXMEGA6, "__AVR_ATxmega256C3__", 0, 0x2000, "x256c3" },
+ { "atxmega256d3", ARCH_AVRXMEGA6, "__AVR_ATxmega256D3__", 0, 0x2000, "x256d3" },
+ { "atxmega384c3", ARCH_AVRXMEGA6, "__AVR_ATxmega384C3__", 0, 0x2000, "x384c3" },
++ { "atxmega384d3", ARCH_AVRXMEGA6, "__AVR_ATxmega384D3__", 0, 0x2000, "x384d3" },
+ /* Xmega, >= 128K FLASH, > 64K RAM. */
+ { "avrxmega7", ARCH_AVRXMEGA7, NULL, 0, 0x2000, "x128a1" },
+ { "atxmega128a1", ARCH_AVRXMEGA7, "__AVR_ATxmega128A1__", 0, 0x2000, "x128a1" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-11-08 15:04:32.000000000 +0530
++++ gcc/config/avr/t-avr 2011-11-08 15:06:12.000000000 +0530
+@@ -317,6 +317,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega6=mmcu?atxmega256c3 \
+ mmcu?avrxmega6=mmcu?atxmega256d3 \
+ mmcu?avrxmega6=mmcu?atxmega384c3 \
++ mmcu?avrxmega6=mmcu?atxmega384d3 \
+ mmcu?avrxmega7=mmcu?atxmega128a1 \
+ mmcu?avrxmega7=mmcu?atxmega128a1u \
+ mmcu?avrxmega7=mmcu?atxmega128a4u \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-11-16 13:15:05.000000000 +0530
++++ gcc/config/avr/avr-devices.c 2011-11-16 18:19:13.000000000 +0530
+@@ -221,6 +221,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega64rfr2", ARCH_AVR5, "__AVR_ATmega64RFR2__", 0, 0x0200, "m64rfr2"},
+ { "atmega32hvb", ARCH_AVR5, "__AVR_ATmega32HVB__", 0, 0x0100, "m32hvb" },
+ { "atmega32hvbrevb", ARCH_AVR5, "__AVR_ATmega32HVBREVB__", 1, 0x0100, "m32hvbrevb" },
++ { "atmega48hvf", ARCH_AVR5, "__AVR_ATmega48HVF__", 0, 0x0100, "m48hvf" },
+ { "at90can32", ARCH_AVR5, "__AVR_AT90CAN32__", 0, 0x0100, "can32" },
+ { "at90can64", ARCH_AVR5, "__AVR_AT90CAN64__", 0, 0x0100, "can64" },
+ { "at90pwm216", ARCH_AVR5, "__AVR_AT90PWM216__", 0, 0x0100, "90pwm216" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-11-16 13:15:05.000000000 +0530
++++ gcc/config/avr/t-avr 2011-11-16 18:25:27.000000000 +0530
+@@ -246,6 +246,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr5=mmcu?atmega16hvbrevb \
+ mmcu?avr5=mmcu?atmega32hvb \
+ mmcu?avr5=mmcu?atmega32hvbrevb \
++ mmcu?avr5=mmcu?atmega48hvf \
+ mmcu?avr5=mmcu?at90can32 \
+ mmcu?avr5=mmcu?at90can64 \
+ mmcu?avr5=mmcu?at90pwm216 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-12-08 14:27:35.000000000 +0530
++++ gcc/config/avr/avr-devices.c 2011-12-08 14:44:38.000000000 +0530
+@@ -166,6 +166,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega16hvbrevb", ARCH_AVR5, "__AVR_ATmega16HVBREVB__", 1, 0x0100, "m16hvbrevb" },
+ { "atmega16m1", ARCH_AVR5, "__AVR_ATmega16M1__", 0, 0x0100, "m16m1" },
+ { "atmega16u4", ARCH_AVR5, "__AVR_ATmega16U4__", 0, 0x0100, "m16u4" },
++ { "atmega26hvg", ARCH_AVR5, "__AVR_ATmega26HVG__", 0, 0x0100, "m26hvg" },
+ { "atmega32", ARCH_AVR5, "__AVR_ATmega32__", 0, 0x0060, "m32" },
+ { "atmega32a", ARCH_AVR5, "__AVR_ATmega32A__", 0, 0x0060, "m32a" },
+ { "atmega323", ARCH_AVR5, "__AVR_ATmega323__", 0, 0x0060, "m323" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2011-12-08 14:27:35.000000000 +0530
++++ gcc/config/avr/t-avr 2011-12-08 14:44:38.000000000 +0530
+@@ -194,6 +194,7 @@ MULTILIB_MATCHES = \
+ mmcu?avr5=mmcu?atmega169a \
+ mmcu?avr5=mmcu?atmega169p \
+ mmcu?avr5=mmcu?atmega169pa \
++ mmcu?avr5=mmcu?atmega26hvg \
+ mmcu?avr5=mmcu?atmega32 \
+ mmcu?avr5=mmcu?atmega32a \
+ mmcu?avr5=mmcu?atmega323 \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2012-01-18 11:00:21.000000000 +0530
++++ gcc/config/avr/avr-devices.c 2012-01-18 11:35:04.000000000 +0530
+@@ -267,6 +267,8 @@ const struct mcu_type_s avr_mcu_types[]
+ /* Xmega, <= 8K FLASH. */
+ /* Xmega, > 8K, < 64K FLASH, <= 64K RAM. */
+ { "avrxmega2", ARCH_AVRXMEGA2, NULL, 0, 0x2000, "x32a4" },
++ { "atmxt224", ARCH_AVRXMEGA2, "__AVR_ATMXT224__", 0, 0x2000, "mxt224"},
++ { "atmxt224e", ARCH_AVRXMEGA2, "__AVR_ATMXT224E__", 0, 0x2000, "mxt224e"},
+ { "atmxt336s", ARCH_AVRXMEGA2, "__AVR_ATMXT336S__", 0, 0x2000, "mxt336s"},
+ { "atxmega16a4", ARCH_AVRXMEGA2, "__AVR_ATxmega16A4__", 0, 0x2000, "x16a4" },
+ { "atxmega16a4u", ARCH_AVRXMEGA2, "__AVR_ATxmega16A4U__", 0, 0x2000, "x16a4u" },
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2012-01-18 11:00:21.000000000 +0530
++++ gcc/config/avr/t-avr 2012-01-18 11:36:27.000000000 +0530
+@@ -282,6 +282,8 @@ MULTILIB_MATCHES = \
+ mmcu?avr6=mmcu?atmega256rfr2 \
+ mmcu?avr6=mmcu?atmega2560 \
+ mmcu?avr6=mmcu?atmega2561 \
++ mmcu?avrxmega2=mmcu?atmxt224 \
++ mmcu?avrxmega2=mmcu?atmxt224e \
+ mmcu?avrxmega2=mmcu?atmxt336s \
+ mmcu?avrxmega2=mmcu?atxmega16a4 \
+ mmcu?avrxmega2=mmcu?atxmega16a4u \
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2012-01-18 19:44:57.000000000 +0530
++++ gcc/config/avr/avr-devices.c 2012-01-18 18:48:36.000000000 +0530
+@@ -304,6 +304,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atxmega128d4", ARCH_AVRXMEGA6, "__AVR_ATxmega128D4__", 0, 0x2000, "x128d4" },
+ { "atxmega192a3", ARCH_AVRXMEGA6, "__AVR_ATxmega192A3__", 0, 0x2000, "x192a3" },
+ { "atxmega192a3u",ARCH_AVRXMEGA6, "__AVR_ATxmega192A3U__", 0, 0x2000, "x192a3u"},
++ { "atxmega192c3", ARCH_AVRXMEGA6, "__AVR_ATxmega192C3__", 0, 0x2000, "x192c3" },
+ { "atxmega192d3", ARCH_AVRXMEGA6, "__AVR_ATxmega192D3__", 0, 0x2000, "x192d3" },
+ { "atxmega256a3", ARCH_AVRXMEGA6, "__AVR_ATxmega256A3__", 0, 0x2000, "x256a3" },
+ { "atxmega256a3u",ARCH_AVRXMEGA6, "__AVR_ATxmega256A3U__", 0, 0x2000, "x256a3u"},
+diff -Naurp gcc/config/avr/t-avr gcc/config/avr/t-avr
+--- gcc/config/avr/t-avr 2012-01-18 19:44:57.000000000 +0530
++++ gcc/config/avr/t-avr 2012-01-18 18:50:16.000000000 +0530
+@@ -311,6 +311,7 @@ MULTILIB_MATCHES = \
+ mmcu?avrxmega6=mmcu?atxmega128d4 \
+ mmcu?avrxmega6=mmcu?atxmega192a3 \
+ mmcu?avrxmega6=mmcu?atxmega192a3u \
++ mmcu?avrxmega6=mmcu?atxmega192c3 \
+ mmcu?avrxmega6=mmcu?atxmega192d3 \
+ mmcu?avrxmega6=mmcu?atxmega256a3 \
+ mmcu?avrxmega6=mmcu?atxmega256a3u \
--- /dev/null
+diff -Naurp gcc/config/avr/avr.c gcc/config/avr/avr.c
+--- gcc/config/avr/avr.c 2011-06-09 14:30:33.000000000 -0500
++++ gcc/config/avr/avr.c 2011-06-09 15:33:10.000000000 -0500
+@@ -3350,8 +3350,8 @@ out_movhi_mr_r (rtx insn, rtx op[], int
+ AS2 (out,%m0-%2,%A1));
+ }
+ if (AVR_XMEGA)
+- return *l = 4, (AS2 (sts,%A0,%A1) CR_TAB
+- AS2 (sts,%B0,%B1));
++ return *l = 4, (AS2 (sts,%m0,%A1) CR_TAB
++ AS2 (sts,%m0+1,%B1));
+ else
+ return *l = 4, (AS2 (sts,%m0+1,%B1) CR_TAB
+ AS2 (sts,%m0,%A1));
--- /dev/null
+--- gcc/ipa-pure-const.c 2010-04-02 14:54:46.000000000 -0500
++++ gcc/ipa-pure-const.c 2011-02-24 16:10:26.000000000 -0600
+@@ -416,6 +416,14 @@ check_stmt (gimple_stmt_iterator *gsip,
+ print_gimple_stmt (dump_file, stmt, 0, 0);
+ }
+
++ if (gimple_has_volatile_ops (stmt))
++ {
++ local->pure_const_state = IPA_NEITHER;
++ if (dump_file)
++ fprintf (dump_file, " Volatile stmt is not const/pure\n");
++ }
++
++
+ /* Look for loads and stores. */
+ walk_stmt_load_store_ops (stmt, local, check_load, check_store);
+
---- ./gcc/config/avr/avr.c.orig 2010-03-05 15:10:10.000000000 +0100
-+++ ./gcc/config/avr/avr.c 2010-03-05 15:20:53.000000000 +0100
-@@ -72,6 +72,12 @@
+diff -Naurp gcc/config/avr/avr.c gcc/config/avr/avr.c
+--- gcc/config/avr/avr.c 2011-06-09 15:41:06.000000000 -0500
++++ gcc/config/avr/avr.c 2011-06-09 15:46:03.000000000 -0500
+@@ -81,6 +81,12 @@ static rtx avr_function_value (const_tre
static void avr_insert_attributes (tree, tree *);
static void avr_asm_init_sections (void);
static unsigned int avr_section_type_flags (tree, const char *, int);
static void avr_reorg (void);
static void avr_asm_out_ctor (rtx, int);
-@@ -4782,6 +4788,54 @@
+@@ -6102,6 +6108,54 @@ avr_output_progmem_section_asm_op (const
fprintf (asm_out_file, "\t.p2align 1\n");
}
/* Implement TARGET_ASM_INIT_SECTIONS. */
static void
-@@ -4791,6 +4845,27 @@
+@@ -6111,6 +6165,27 @@ avr_asm_init_sections (void)
avr_output_progmem_section_asm_op,
NULL);
readonly_data_section = data_section;
}
static unsigned int
-@@ -4829,12 +4904,6 @@
-
- fputs ("__tmp_reg__ = 0\n"
+@@ -6152,12 +6227,6 @@ avr_file_start (void)
+ AVR_TINY ? fputs ("__tmp_reg__ = 16\n"
+ "__zero_reg__ = 17\n", asm_out_file) : fputs ("__tmp_reg__ = 0\n"
"__zero_reg__ = 1\n", asm_out_file);
-
- /* FIXME: output these only if there is anything in the .data / .bss
}
/* Outputs to the stdio stream FILE some
-@@ -4843,6 +4912,16 @@
+@@ -6166,6 +6235,16 @@ avr_file_start (void)
static void
avr_file_end (void)
{
}
/* Choose the order in which to allocate hard registers for
---- ./gcc/config/avr/avr.h.orig 2010-03-05 15:10:10.000000000 +0100
-+++ ./gcc/config/avr/avr.h 2010-03-05 15:20:53.000000000 +0100
-@@ -533,29 +533,21 @@
+diff -Naurp gcc/config/avr/avr.h gcc/config/avr/avr.h
+--- gcc/config/avr/avr.h 2011-06-09 14:30:33.000000000 -0500
++++ gcc/config/avr/avr.h 2011-06-09 15:46:03.000000000 -0500
+@@ -562,7 +562,7 @@ do { \
#define ASM_APP_OFF "/* #NOAPP */\n"
/* Switch into a generic section. */
#define TARGET_ASM_INIT_SECTIONS avr_asm_init_sections
#define ASM_OUTPUT_ASCII(FILE, P, SIZE) gas_output_ascii (FILE,P,SIZE)
-
+@@ -570,21 +570,13 @@ do { \
#define IS_ASM_LOGICAL_LINE_SEPARATOR(C, STR) ((C) == '\n' || ((C) == '$'))
--#define ASM_OUTPUT_COMMON(STREAM, NAME, SIZE, ROUNDED) \
+ #define ASM_OUTPUT_COMMON(STREAM, NAME, SIZE, ROUNDED) \
-do { \
- fputs ("\t.comm ", (STREAM)); \
- assemble_name ((STREAM), (NAME)); \
- fprintf ((STREAM), ",%lu,1\n", (unsigned long)(SIZE)); \
-} while (0)
-+#define ASM_OUTPUT_COMMON(STREAM, NAME, SIZE, ROUNDED) \
+ avr_asm_output_common (STREAM, NAME, SIZE, ROUNDED)
--#define ASM_OUTPUT_BSS(FILE, DECL, NAME, SIZE, ROUNDED) \
-- asm_output_bss ((FILE), (DECL), (NAME), (SIZE), (ROUNDED))
-+#define ASM_OUTPUT_BSS(FILE, DECL, NAME, SIZE, ROUNDED) \
-+ asm_output_bss ((FILE), (DECL), (NAME), (SIZE), (ROUNDED))
+ #define ASM_OUTPUT_BSS(FILE, DECL, NAME, SIZE, ROUNDED) \
+ asm_output_bss ((FILE), (DECL), (NAME), (SIZE), (ROUNDED))
--#define ASM_OUTPUT_LOCAL(STREAM, NAME, SIZE, ROUNDED) \
+ #define ASM_OUTPUT_LOCAL(STREAM, NAME, SIZE, ROUNDED) \
-do { \
- fputs ("\t.lcomm ", (STREAM)); \
- assemble_name ((STREAM), (NAME)); \
- fprintf ((STREAM), ",%d\n", (int)(SIZE)); \
-} while (0)
-+#define ASM_OUTPUT_LOCAL(STREAM, NAME, SIZE, ROUNDED) \
+ avr_asm_output_local (STREAM, NAME, SIZE, ROUNDED)
#undef TYPE_ASM_OP
#undef SIZE_ASM_OP
---- ./gcc/config/avr/avr-protos.h.orig 2008-06-15 23:32:29.000000000 +0200
-+++ ./gcc/config/avr/avr-protos.h 2010-03-05 15:20:53.000000000 +0100
-@@ -38,6 +38,8 @@
+diff -Naurp gcc/config/avr/avr-protos.h gcc/config/avr/avr-protos.h
+--- gcc/config/avr/avr-protos.h 2011-06-09 14:30:33.000000000 -0500
++++ gcc/config/avr/avr-protos.h 2011-06-09 15:46:03.000000000 -0500
+@@ -35,6 +35,9 @@ extern int avr_simple_epilogue (void);
extern void gas_output_limited_string (FILE *file, const char *str);
extern void gas_output_ascii (FILE *file, const char *str, size_t length);
extern int avr_hard_regno_rename_ok (unsigned int, unsigned int);
+extern void avr_asm_output_common (FILE *stream, const char *name, unsigned HOST_WIDE_INT size, unsigned HOST_WIDE_INT rounded);
+extern void avr_asm_output_local (FILE *stream, const char *name, unsigned HOST_WIDE_INT size, unsigned HOST_WIDE_INT rounded);
++
+ extern rtx avr_return_addr_rtx (int count, const_rtx tem);
#ifdef TREE_CODE
- extern void asm_output_external (FILE *file, tree decl, char *name);
-@@ -123,6 +125,7 @@
- extern int compare_eq_p (rtx insn);
- extern void out_shift_with_cnt (const char *template, rtx insn,
- rtx operands[], int *len, int t_len);
-+extern rtx avr_return_addr_rtx (int count, rtx tem);
- extern int avr_io_address_p (rtx x, int size);
- extern int avr_peep2_scratch_safe (rtx reg_rtx);
- #endif /* RTX_CODE */
--- /dev/null
+diff -Naurp gcc/config/avr/avr.h gcc/config/avr/avr.h
+--- gcc/config/avr/avr.h 2011-06-09 15:53:13.000000000 -0500
++++ gcc/config/avr/avr.h 2011-06-09 15:55:45.000000000 -0500
+@@ -136,7 +136,7 @@ extern GTY(()) section *progmem_section;
+ #define AVR_2_BYTE_PC (!AVR_HAVE_EIJMP_EICALL)
+ #define AVR_3_BYTE_PC (AVR_HAVE_EIJMP_EICALL)
+
+-#define AVR_IO_OFFSET (AVR_XMEGA ? 0 : 0x20)
++#define AVR_IO_OFFSET ((AVR_XMEGA || AVR_TINY) ? 0 : 0x20)
+ #define AVR_RAMPD_ADDR (AVR_XMEGA ? 0x38 : 0)
+ #define AVR_RAMPX_ADDR (AVR_XMEGA ? 0x39 : 0)
+ #define AVR_RAMPY_ADDR (AVR_XMEGA ? 0x3A : 0)
+diff -Naurp gcc/config/avr/predicates.md gcc/config/avr/predicates.md
+--- gcc/config/avr/predicates.md 2011-06-09 14:30:33.000000000 -0500
++++ gcc/config/avr/predicates.md 2011-06-09 15:55:45.000000000 -0500
+@@ -50,21 +50,24 @@
+ ;; Return true if OP is a valid address for lower half of I/O space.
+ (define_predicate "low_io_address_operand"
+ (and (match_code "const_int")
+- (if_then_else (match_test "AVR_XMEGA")
++ (if_then_else (ior (match_test "AVR_XMEGA")
++ (match_test "AVR_TINY"))
+ (match_test "IN_RANGE((INTVAL (op)), 0x00, 0x1F)")
+ (match_test "IN_RANGE((INTVAL (op)), 0x20, 0x3F)"))))
+
+ ;; Return true if OP is a valid address for high half of I/O space.
+ (define_predicate "high_io_address_operand"
+ (and (match_code "const_int")
+- (if_then_else (match_test "AVR_XMEGA")
++ (if_then_else (ior (match_test "AVR_XMEGA")
++ (match_test "AVR_TINY"))
+ (match_test "IN_RANGE((INTVAL (op)), 0x20, 0x3F)")
+ (match_test "IN_RANGE((INTVAL (op)), 0x40, 0x5F)"))))
+
+ ;; Return true if OP is a valid address of I/O space.
+ (define_predicate "io_address_operand"
+ (and (match_code "const_int")
+- (if_then_else (match_test "AVR_XMEGA")
++ (if_then_else (ior (match_test "AVR_XMEGA")
++ (match_test "AVR_TINY"))
+ (match_test "IN_RANGE((INTVAL (op)), 0x0, (0x40 - GET_MODE_SIZE(mode)))")
+ (match_test "IN_RANGE((INTVAL (op)), 0x20, (0x60 - GET_MODE_SIZE(mode)))"))))
+
--- /dev/null
+diff -rupw gcc/config/avr/avr.md gcc/config/avr/avr.md
+--- gcc/config/avr/avr.md 2011-02-23 15:54:14.000000000 -0600
++++ gcc/config/avr/avr.md 2011-02-23 15:55:22.000000000 -0600
+@@ -1082,8 +1082,8 @@
+ (set_attr "cc" "clobber")])
+
+ (define_expand "<any_extend:u>mulhisi3"
+- [(set (reg:HI 18) (match_operand:SI 1 "register_operand" ""))
+- (set (reg:HI 20) (match_operand:SI 2 "register_operand" ""))
++ [(set (reg:HI 18) (match_operand:HI 1 "register_operand" ""))
++ (set (reg:HI 20) (match_operand:HI 2 "register_operand" ""))
+ (set (reg:SI 22)
+ (mult:SI (any_extend:SI (reg:HI 18))
+ (any_extend:SI (reg:HI 20))))
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-12-14 18:10:15.000000000 +0530
++++ gcc/config/avr/avr-devices.c 2011-12-14 18:12:49.000000000 +0530
+@@ -259,7 +259,7 @@ const struct mcu_type_s avr_mcu_types[]
+ /* Enhanced, ==256K + 3-Byte PC +
+ { MOVW/LPMX, JMP/CALL, MUL, ELPM, ELPMX, EIJMP/EICALL }. */
+ { "avr6", ARCH_AVR6, NULL, 0, 0x0200, "m2561" },
+- { "atmega2560", ARCH_AVR6, "__AVR_ATmega2560__", 0, 0x0200, "m2561" },
++ { "atmega2560", ARCH_AVR6, "__AVR_ATmega2560__", 0, 0x0200, "m2560" },
+ { "atmega2561", ARCH_AVR6, "__AVR_ATmega2561__", 0, 0x0200, "m2561" },
+ { "atmega256rfa2", ARCH_AVR6, "__AVR_ATmega256RFA2__", 0, 0x0200, "m256rfa2" },
+ { "atmega256rfr2", ARCH_AVR6, "__AVR_ATmega256RFR2__", 0, 0x0200, "m256rfr2" },
--- /dev/null
+diff -rup gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-04-27 12:24:24.000000000 -0500
++++ gcc/config/avr/avr-devices.c 2011-04-27 17:19:33.000000000 -0500
+@@ -37,14 +37,14 @@ const struct base_arch_s avr_arch_types[
+ { 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=5", "avr5" },
+ { 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0x0060, "__AVR_ARCH__=51", "avr51" },
+ { 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0x0060, "__AVR_ARCH__=6", "avr6" },
++ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0x0040, "__AVR_ARCH__=100", "avrtiny10" },
+ { 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0x2000, "__AVR_ARCH__=101", "avrxmega1" },
+ { 0, 1, 1, 1, 0, 0, 0, 1, 0, 0, 0x2000, "__AVR_ARCH__=102", "avrxmega2" },
+ { 0, 1, 1, 1, 0, 0, 0, 1, 1, 0, 0x2000, "__AVR_ARCH__=103", "avrxmega3" },
+ { 0, 1, 1, 1, 1, 1, 0, 1, 0, 0, 0x2000, "__AVR_ARCH__=104", "avrxmega4" },
+ { 0, 1, 1, 1, 1, 1, 0, 1, 1, 0, 0x2000, "__AVR_ARCH__=105", "avrxmega5" },
+ { 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0x2000, "__AVR_ARCH__=106", "avrxmega6" },
+- { 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0x2000, "__AVR_ARCH__=107", "avrxmega7" },
+- { 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0x0040, "__AVR_ARCH__=201", "avrtiny10" }
++ { 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0x2000, "__AVR_ARCH__=107", "avrxmega7" }
+ };
+
+ /* List of all known AVR MCU types - if updated, it has to be kept
+diff -rup gcc/config/avr/avr.h gcc/config/avr/avr.h
+--- gcc/config/avr/avr.h 2011-04-27 12:24:06.000000000 -0500
++++ gcc/config/avr/avr.h 2011-04-27 17:49:01.000000000 -0500
+@@ -79,14 +79,14 @@ enum avr_arch
+ ARCH_AVR5,
+ ARCH_AVR51,
+ ARCH_AVR6,
++ ARCH_AVRTINY10,
+ ARCH_AVRXMEGA1,
+ ARCH_AVRXMEGA2,
+ ARCH_AVRXMEGA3,
+ ARCH_AVRXMEGA4,
+ ARCH_AVRXMEGA5,
+ ARCH_AVRXMEGA6,
+- ARCH_AVRXMEGA7,
+- ARCH_AVRTINY10
++ ARCH_AVRXMEGA7
+ };
+
+ struct mcu_type_s {
--- /dev/null
+diff -Naurp gcc/config/avr/avr-devices.c gcc/config/avr/avr-devices.c
+--- gcc/config/avr/avr-devices.c 2011-12-14 18:16:56.000000000 +0530
++++ gcc/config/avr/avr-devices.c 2011-12-14 18:16:02.000000000 +0530
+@@ -170,7 +170,7 @@ const struct mcu_type_s avr_mcu_types[]
+ { "atmega32", ARCH_AVR5, "__AVR_ATmega32__", 0, 0x0060, "m32" },
+ { "atmega32a", ARCH_AVR5, "__AVR_ATmega32A__", 0, 0x0060, "m32a" },
+ { "atmega323", ARCH_AVR5, "__AVR_ATmega323__", 0, 0x0060, "m323" },
+- { "atmega324a", ARCH_AVR5, "__AVR_ATmega324A__", 0, 0x0060, "m324a" },
++ { "atmega324a", ARCH_AVR5, "__AVR_ATmega324A__", 0, 0x0100, "m324a" },
+ { "atmega324p", ARCH_AVR5, "__AVR_ATmega324P__", 0, 0x0100, "m324p" },
+ { "atmega324pa", ARCH_AVR5, "__AVR_ATmega324PA__", 0, 0x0100, "m324pa" },
+ { "atmega325", ARCH_AVR5, "__AVR_ATmega325__", 0, 0x0100, "m325" },
+++ /dev/null
---- gcc/config/avr/avr.c.old 2008-03-14 08:14:59.742194500 -0600
-+++ gcc/config/avr/avr.c 2008-03-14 08:26:24.509618500 -0600
-@@ -279,6 +279,7 @@ static const struct mcu_type_s avr_mcu_t
- { "at90pwm216", ARCH_AVR5, "__AVR_AT90PWM216__" },
- { "at90pwm316", ARCH_AVR5, "__AVR_AT90PWM316__" },
- { "atmega32m1", ARCH_AVR5, "__AVR_ATmega32M1__" },
-+ { "atmega32c1", ARCH_AVR5, "__AVR_ATmega32C1__" },
- { "at90usb646", ARCH_AVR5, "__AVR_AT90USB646__" },
- { "at90usb647", ARCH_AVR5, "__AVR_AT90USB647__" },
- { "at94k", ARCH_AVR5, "__AVR_AT94K__" },
---- gcc/config/avr/avr.h.old 2008-03-14 08:14:59.757858500 -0600
-+++ gcc/config/avr/avr.h 2008-03-14 08:27:51.946066500 -0600
-@@ -869,6 +869,7 @@ mmcu=*:-mmcu=%*}"
- mmcu=at90can*|\
- mmcu=at90pwm216|\
- mmcu=at90pwm316|\
-+ mmcu=atmega32c1|\
- mmcu=atmega32m1|\
- mmcu=at90usb64*|\
- mmcu=at90usb128*|\
-@@ -901,6 +902,7 @@ mmcu=*:-mmcu=%*}"
- mmcu=attiny88|\
- mmcu=at90can*|\
- mmcu=at90pwm*|\
-+ mmcu=atmega32c1|\
- mmcu=atmega32m1|\
- mmcu=at90usb*: -Tdata 0x800100}\
- %{mmcu=atmega640|\
-@@ -1011,6 +1013,7 @@ mmcu=*:-mmcu=%*}"
- %{mmcu=at90can64:crtcan64.o%s} \
- %{mmcu=at90pwm216:crt90pwm216.o%s} \
- %{mmcu=at90pwm316:crt90pwm316.o%s} \
-+%{mmcu=atmega32c1:crtm32c1.o%s} \
- %{mmcu=atmega32m1:crtm32m1.o%s} \
- %{mmcu=at90usb646:crtusb646.o%s} \
- %{mmcu=at90usb647:crtusb647.o%s} \
---- gcc/config/avr/t-avr.old 2008-03-14 08:14:59.757858500 -0600
-+++ gcc/config/avr/t-avr 2008-03-14 08:28:44.169842500 -0600
-@@ -114,6 +114,7 @@ MULTILIB_MATCHES = \
- mmcu?avr5=mmcu?at90can64 \
- mmcu?avr5=mmcu?at90pwm216 \
- mmcu?avr5=mmcu?at90pwm316 \
-+ mmcu?avr5=mmcu?atmega32c1 \
- mmcu?avr5=mmcu?atmega32m1 \
- mmcu?avr5=mmcu?at90usb646 \
- mmcu?avr5=mmcu?at90usb647 \
+++ /dev/null
---- gcc/config/avr/avr.c.old 2008-03-02 13:20:16.906250000 -0700
-+++ gcc/config/avr/avr.c 2008-03-02 13:22:31.953125000 -0700
-@@ -278,6 +278,7 @@ static const struct mcu_type_s avr_mcu_t
- { "at90can64", ARCH_AVR5, "__AVR_AT90CAN64__" },
- { "at90pwm216", ARCH_AVR5, "__AVR_AT90PWM216__" },
- { "at90pwm316", ARCH_AVR5, "__AVR_AT90PWM316__" },
-+ { "atmega32m1", ARCH_AVR5, "__AVR_ATmega32M1__" },
- { "at90usb646", ARCH_AVR5, "__AVR_AT90USB646__" },
- { "at90usb647", ARCH_AVR5, "__AVR_AT90USB647__" },
- { "at94k", ARCH_AVR5, "__AVR_AT94K__" },
---- gcc/config/avr/avr.h.old 2008-03-02 13:20:16.906250000 -0700
-+++ gcc/config/avr/avr.h 2008-03-02 13:23:36.593750000 -0700
-@@ -869,6 +869,7 @@ mmcu=*:-mmcu=%*}"
- mmcu=at90can*|\
- mmcu=at90pwm216|\
- mmcu=at90pwm316|\
-+ mmcu=atmega32m1|\
- mmcu=at90usb64*|\
- mmcu=at90usb128*|\
- mmcu=at94k: -m avr5}\
-@@ -900,6 +901,7 @@ mmcu=*:-mmcu=%*}"
- mmcu=attiny88|\
- mmcu=at90can*|\
- mmcu=at90pwm*|\
-+ mmcu=atmega32m1|\
- mmcu=at90usb*: -Tdata 0x800100}\
- %{mmcu=atmega640|\
- mmcu=atmega1280|\
-@@ -1009,6 +1011,7 @@ mmcu=*:-mmcu=%*}"
- %{mmcu=at90can64:crtcan64.o%s} \
- %{mmcu=at90pwm216:crt90pwm216.o%s} \
- %{mmcu=at90pwm316:crt90pwm316.o%s} \
-+%{mmcu=atmega32m1:crtm32m1.o%s} \
- %{mmcu=at90usb646:crtusb646.o%s} \
- %{mmcu=at90usb647:crtusb647.o%s} \
- %{mmcu=at94k:crtat94k.o%s} \
---- gcc/config/avr/t-avr.old 2008-03-02 13:20:16.906250000 -0700
-+++ gcc/config/avr/t-avr 2008-03-02 13:21:48.640625000 -0700
-@@ -114,6 +114,7 @@ MULTILIB_MATCHES = \
- mmcu?avr5=mmcu?at90can64 \
- mmcu?avr5=mmcu?at90pwm216 \
- mmcu?avr5=mmcu?at90pwm316 \
-+ mmcu?avr5=mmcu?atmega32m1 \
- mmcu?avr5=mmcu?at90usb646 \
- mmcu?avr5=mmcu?at90usb647 \
- mmcu?avr5=mmcu?at94k \
+++ /dev/null
---- gcc/config/avr/avr.c.old 2008-03-19 14:34:52.963111900 -0600
-+++ gcc/config/avr/avr.c 2008-03-22 07:53:54.900218600 -0600
-@@ -281,6 +281,7 @@ static const struct mcu_type_s avr_mcu_t
- { "at90pwm316", ARCH_AVR5, "__AVR_AT90PWM316__" },
- { "atmega32m1", ARCH_AVR5, "__AVR_ATmega32M1__" },
- { "atmega32c1", ARCH_AVR5, "__AVR_ATmega32C1__" },
-+ { "atmega32u4", ARCH_AVR5, "__AVR_ATmega32U4__" },
- { "at90usb646", ARCH_AVR5, "__AVR_AT90USB646__" },
- { "at90usb647", ARCH_AVR5, "__AVR_AT90USB647__" },
- { "at94k", ARCH_AVR5, "__AVR_AT94K__" },
---- gcc/config/avr/avr.h.old 2008-03-19 14:34:52.963111900 -0600
-+++ gcc/config/avr/avr.h 2008-03-22 07:56:04.463675600 -0600
-@@ -871,6 +871,7 @@ mmcu=*:-mmcu=%*}"
- mmcu=at90pwm316|\
- mmcu=atmega32c1|\
- mmcu=atmega32m1|\
-+ mmcu=atmega32u4|\
- mmcu=at90usb64*|\
- mmcu=at90usb128*|\
- mmcu=at94k: -m avr5}\
-@@ -904,6 +905,7 @@ mmcu=*:-mmcu=%*}"
- mmcu=at90pwm*|\
- mmcu=atmega32c1|\
- mmcu=atmega32m1|\
-+ mmcu=atmega32u4|\
- mmcu=at90usb*: -Tdata 0x800100}\
- %{mmcu=atmega640|\
- mmcu=atmega1280|\
-@@ -1015,6 +1017,7 @@ mmcu=*:-mmcu=%*}"
- %{mmcu=at90pwm316:crt90pwm316.o%s} \
- %{mmcu=atmega32c1:crtm32c1.o%s} \
- %{mmcu=atmega32m1:crtm32m1.o%s} \
-+%{mmcu=atmega32u4:crtm32u4.o%s} \
- %{mmcu=at90usb646:crtusb646.o%s} \
- %{mmcu=at90usb647:crtusb647.o%s} \
- %{mmcu=at94k:crtat94k.o%s} \
---- gcc/config/avr/t-avr.old 2008-03-19 14:34:52.963111900 -0600
-+++ gcc/config/avr/t-avr 2008-03-22 08:02:03.137164200 -0600
-@@ -116,6 +116,7 @@ MULTILIB_MATCHES = \
- mmcu?avr5=mmcu?at90pwm316 \
- mmcu?avr5=mmcu?atmega32c1 \
- mmcu?avr5=mmcu?atmega32m1 \
-+ mmcu?avr5=mmcu?atmega32u4 \
- mmcu?avr5=mmcu?at90usb646 \
- mmcu?avr5=mmcu?at90usb647 \
- mmcu?avr5=mmcu?at94k \
+++ /dev/null
---- gcc/config/avr/avr.c.old 2008-11-04 14:14:27.405669400 -0700
-+++ gcc/config/avr/avr.c 2008-11-04 14:14:55.772086800 -0700
-@@ -283,6 +283,7 @@ static const struct mcu_type_s avr_mcu_t
- { "atmega32m1", ARCH_AVR5, "__AVR_ATmega32M1__" },
- { "atmega32c1", ARCH_AVR5, "__AVR_ATmega32C1__" },
- { "atmega32u4", ARCH_AVR5, "__AVR_ATmega32U4__" },
-+ { "atmega32u6", ARCH_AVR5, "__AVR_ATmega32U6__" },
- { "at90usb646", ARCH_AVR5, "__AVR_AT90USB646__" },
- { "at90usb647", ARCH_AVR5, "__AVR_AT90USB647__" },
- { "at94k", ARCH_AVR5, "__AVR_AT94K__" },
---- gcc/config/avr/avr.h.old 2008-11-04 14:15:07.629280600 -0700
-+++ gcc/config/avr/avr.h 2008-11-04 14:16:11.692586600 -0700
-@@ -871,7 +871,7 @@ mmcu=*:-mmcu=%*}"
- mmcu=at90pwm316|\
- mmcu=atmega32c1|\
- mmcu=atmega32m1|\
-- mmcu=atmega32u4|\
-+ mmcu=atmega32u*|\
- mmcu=at90usb64*|\
- mmcu=at90usb128*|\
- mmcu=at94k: -m avr5}\
-@@ -908,7 +908,7 @@ mmcu=*:-mmcu=%*}"
- mmcu=at90pwm*|\
- mmcu=atmega32c1|\
- mmcu=atmega32m1|\
-- mmcu=atmega32u4|\
-+ mmcu=atmega32u*|\
- mmcu=at90usb*: -Tdata 0x800100}\
- %{mmcu=atmega640|\
- mmcu=atmega1280|\
---- gcc/config/avr/t-avr.old 2008-11-04 14:17:13.610006800 -0700
-+++ gcc/config/avr/t-avr 2008-11-04 14:17:24.793674400 -0700
-@@ -118,6 +118,7 @@ MULTILIB_MATCHES = \
- mmcu?avr5=mmcu?atmega32c1 \
- mmcu?avr5=mmcu?atmega32m1 \
- mmcu?avr5=mmcu?atmega32u4 \
-+ mmcu?avr5=mmcu?atmega32u6 \
- mmcu?avr5=mmcu?at90usb646 \
- mmcu?avr5=mmcu?at90usb647 \
- mmcu?avr5=mmcu?at94k \
+++ /dev/null
-Index: gcc/config/avr/avr.c
-===================================================================
---- gcc/config/avr/avr.c (revision 136946)
-+++ gcc/config/avr/avr.c (working copy)
-@@ -173,6 +174,7 @@
- /* Classic + MOVW, <= 8K. */
- { "avr25", ARCH_AVR25, NULL },
- { "attiny13", ARCH_AVR25, "__AVR_ATtiny13__" },
-+ { "attiny13a", ARCH_AVR25, "__AVR_ATtiny13A__" },
- { "attiny2313", ARCH_AVR25, "__AVR_ATtiny2313__" },
- { "attiny24", ARCH_AVR25, "__AVR_ATtiny24__" },
- { "attiny44", ARCH_AVR25, "__AVR_ATtiny44__" },
---- gcc/config/avr/t-avr.orig Wed Jun 25 18:36:00 2008
-+++ gcc/config/avr/t-avr Wed Jun 25 18:39:28 2008
-@@ -43,6 +43,7 @@ MULTILIB_DIRNAMES = avr2 avr25 avr3 avr3
- # The many avr2 matches are not listed here - this is the default.
- MULTILIB_MATCHES = \
- mmcu?avr25=mmcu?attiny13 \
-+ mmcu?avr25=mmcu?attiny13a \
- mmcu?avr25=mmcu?attiny2313 \
- mmcu?avr25=mmcu?attiny24 \
- mmcu?avr25=mmcu?attiny44 \
-Index: gcc/config/avr/avr.h
-===================================================================
---- gcc/config/avr/avr.h (revision 136946)
-+++ gcc/config/avr/avr.h (working copy)
-@@ -817,7 +817,7 @@
- mmcu=at90s8*|\
- mmcu=at90c8*|\
- mmcu=at86rf401|\
-- mmcu=attiny13|\
-+ mmcu=attiny13*|\
- mmcu=attiny2313|\
- mmcu=attiny24|\
- mmcu=attiny25|\
-@@ -916,6 +916,7 @@
- %{mmcu=at90s8535:crts8535.o%s} \
- %{mmcu=at86rf401:crt86401.o%s} \
- %{mmcu=attiny13:crttn13.o%s} \
-+%{mmcu=attiny13a:crttn13a.o%s} \
- %{mmcu=attiny2313|mmcu=avr25:crttn2313.o%s} \
- %{mmcu=attiny24:crttn24.o%s} \
- %{mmcu=attiny44:crttn44.o%s} \
+++ /dev/null
---- gcc/config/avr/avr.c.old 2008-03-24 08:03:54.091795900 -0600
-+++ gcc/config/avr/avr.c 2008-03-25 11:35:44.787369000 -0600
-@@ -224,6 +224,7 @@ static const struct mcu_type_s avr_mcu_t
- { "avr35", ARCH_AVR35, NULL },
- { "at90usb82", ARCH_AVR35, "__AVR_AT90USB82__" },
- { "at90usb162", ARCH_AVR35, "__AVR_AT90USB162__" },
-+ { "attiny167", ARCH_AVR35, "__AVR_ATtiny167__" },
- /* Enhanced, <= 8K. */
- { "avr4", ARCH_AVR4, NULL },
- { "atmega8", ARCH_AVR4, "__AVR_ATmega8__" },
---- gcc/config/avr/avr.h.old 2008-03-24 08:03:54.091795900 -0600
-+++ gcc/config/avr/avr.h 2008-03-25 12:23:56.468150200 -0600
-@@ -853,7 +853,8 @@ mmcu=*:-mmcu=%*}"
- mmcu=at43*|\
- mmcu=at76*|\
- mmcu=at90usb82|\
-- mmcu=at90usb162: -m avr3}\
-+ mmcu=at90usb162|\
-+ mmcu=attiny167: -m avr3}\
- %{mmcu=atmega8*|\
- mmcu=atmega48*|\
- mmcu=at90pwm1|\
-@@ -901,6 +902,7 @@ mmcu=*:-mmcu=%*}"
- mmcu=atmega32hvb|\
- mmcu=attiny48|\
- mmcu=attiny88|\
-+ mmcu=attiny167|\
- mmcu=at90can*|\
- mmcu=at90pwm*|\
- mmcu=atmega32c1|\
-@@ -958,6 +960,7 @@ mmcu=*:-mmcu=%*}"
- %{mmcu=attiny43u:crttn43u.o%s} \
- %{mmcu=attiny48:crttn48.o%s} \
- %{mmcu=attiny88:crttn88.o%s} \
-+%{mmcu=attiny167:crttn167.o%s} \
- %{mmcu=at43usb320|mmcu=avr3:crt43320.o%s} \
- %{mmcu=at43usb355:crt43355.o%s} \
- %{mmcu=at76c711:crt76711.o%s} \
---- gcc/config/avr/t-avr.old 2008-03-24 08:03:54.091795900 -0600
-+++ gcc/config/avr/t-avr 2008-03-25 12:24:35.371718000 -0600
-@@ -63,6 +63,7 @@ MULTILIB_MATCHES = \
- mmcu?avr31=mmcu?atmega103 \
- mmcu?avr35=mmcu?at90usb82 \
- mmcu?avr35=mmcu?at90usb162 \
-+ mmcu?avr35=mmcu?attiny167 \
- mmcu?avr4=mmcu?atmega48 \
- mmcu?avr4=mmcu?atmega48p \
- mmcu?avr4=mmcu?atmega8 \
+++ /dev/null
-diff -ur ../gcc-4.3.4.orig/gcc/config/avr/avr.md ./gcc/config/avr/avr.md
---- ../gcc-4.3.4.orig/gcc/config/avr/avr.md 2009-10-02 15:08:58.000000000 +0200
-+++ ./gcc/config/avr/avr.md 2009-10-02 15:09:26.000000000 +0200
-@@ -54,6 +54,7 @@
- (UNSPEC_INDEX_JMP 1)
- (UNSPEC_SEI 2)
- (UNSPEC_CLI 3)
-+ (UNSPEC_SWAP 4)
-
- (UNSPECV_PROLOGUE_SAVES 0)
- (UNSPECV_EPILOGUE_RESTORES 1)])
-@@ -1183,6 +1184,19 @@
- [(set_attr "length" "4,4")
- (set_attr "cc" "set_n,clobber")])
-
-+(define_peephole2 ; andi
-+ [(set (match_operand:QI 0 "d_register_operand" "")
-+ (and:QI (match_dup 0)
-+ (match_operand:QI 1 "const_int_operand" "")))
-+ (set (match_dup 0)
-+ (and:QI (match_dup 0)
-+ (match_operand:QI 2 "const_int_operand" "")))]
-+ ""
-+ [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))]
-+ {
-+ operands[1] = GEN_INT (INTVAL (operands[1]) & INTVAL (operands[2]));
-+ })
-+
- ;;|||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
- ;; ior
-
-@@ -1311,10 +1325,57 @@
- [(set_attr "length" "4")
- (set_attr "cc" "set_n")])
-
-+;; swap
-+
-+(define_insn "*swap"
-+ [(set (match_operand:QI 0 "register_operand" "=r")
-+ (unspec:QI [(match_operand:QI 1 "register_operand" "0")]
-+ UNSPEC_SWAP))]
-+ ""
-+ "swap %0"
-+ [(set_attr "length" "1")
-+ (set_attr "cc" "none")])
-+
- ;;<< << << << << << << << << << << << << << << << << << << << << << << << << <<
- ;; arithmetic shift left
-
--(define_insn "ashlqi3"
-+(define_expand "ashlqi3"
-+ [(set (match_operand:QI 0 "register_operand" "")
-+ (ashift:QI (match_operand:QI 1 "register_operand" "")
-+ (match_operand:QI 2 "general_operand" "")))]
-+ ""
-+ "")
-+
-+(define_split ; ashlqi3_const4
-+ [(set (match_operand:QI 0 "d_register_operand" "")
-+ (ashift:QI (match_operand:QI 1 "d_register_operand" "")
-+ (const_int 4)))]
-+ ""
-+ [(set (match_dup 0) (unspec:QI [(match_dup 0)] UNSPEC_SWAP))
-+ (set (match_dup 0) (and:QI (match_dup 0) (const_int -16)))]
-+ "")
-+
-+(define_split ; ashlqi3_const5
-+ [(set (match_operand:QI 0 "d_register_operand" "")
-+ (ashift:QI (match_operand:QI 1 "d_register_operand" "")
-+ (const_int 5)))]
-+ ""
-+ [(set (match_dup 0) (unspec:QI [(match_dup 0)] UNSPEC_SWAP))
-+ (set (match_dup 0) (ashift:QI (match_dup 0) (const_int 1)))
-+ (set (match_dup 0) (and:QI (match_dup 0) (const_int -32)))]
-+ "")
-+
-+(define_split ; ashlqi3_const6
-+ [(set (match_operand:QI 0 "d_register_operand" "")
-+ (ashift:QI (match_operand:QI 1 "d_register_operand" "")
-+ (const_int 6)))]
-+ ""
-+ [(set (match_dup 0) (unspec:QI [(match_dup 0)] UNSPEC_SWAP))
-+ (set (match_dup 0) (ashift:QI (match_dup 0) (const_int 2)))
-+ (set (match_dup 0) (and:QI (match_dup 0) (const_int -64)))]
-+ "")
-+
-+(define_insn "*ashlqi3"
- [(set (match_operand:QI 0 "register_operand" "=r,r,r,r,!d,r,r")
- (ashift:QI (match_operand:QI 1 "register_operand" "0,0,0,0,0,0,0")
- (match_operand:QI 2 "general_operand" "r,L,P,K,n,n,Qm")))]
-@@ -1344,6 +1405,47 @@
- ;; Optimize if a scratch register from LD_REGS happens to be available.
-
- (define_peephole2
-+ [(match_scratch:QI 2 "d")
-+ (set (match_operand:QI 0 "l_register_operand" "")
-+ (ashift:QI (match_operand:QI 1 "l_register_operand" "")
-+ (const_int 4)))]
-+ ""
-+ [(set (match_dup 0) (unspec:QI [(match_dup 0)] UNSPEC_SWAP))
-+ (set (match_dup 2) (const_int -16))
-+ (set (match_dup 0) (and:QI (match_dup 0) (match_dup 2)))
-+ (clobber (match_dup 2))]
-+ "if (!avr_peep2_scratch_safe (operands[2]))
-+ FAIL;")
-+
-+(define_peephole2
-+ [(match_scratch:QI 2 "d")
-+ (set (match_operand:QI 0 "l_register_operand" "")
-+ (ashift:QI (match_operand:QI 1 "l_register_operand" "")
-+ (const_int 5)))]
-+ ""
-+ [(set (match_dup 0) (unspec:QI [(match_dup 0)] UNSPEC_SWAP))
-+ (set (match_dup 0) (ashift:QI (match_dup 0) (const_int 1)))
-+ (set (match_dup 2) (const_int -32))
-+ (set (match_dup 0) (and:QI (match_dup 0) (match_dup 2)))
-+ (clobber (match_dup 2))]
-+ "if (!avr_peep2_scratch_safe (operands[2]))
-+ FAIL;")
-+
-+(define_peephole2
-+ [(match_scratch:QI 2 "d")
-+ (set (match_operand:QI 0 "l_register_operand" "")
-+ (ashift:QI (match_operand:QI 1 "l_register_operand" "")
-+ (const_int 6)))]
-+ ""
-+ [(set (match_dup 0) (unspec:QI [(match_dup 0)] UNSPEC_SWAP))
-+ (set (match_dup 0) (ashift:QI (match_dup 0) (const_int 2)))
-+ (set (match_dup 2) (const_int -64))
-+ (set (match_dup 0) (and:QI (match_dup 0) (match_dup 2)))
-+ (clobber (match_dup 2))]
-+ "if (!avr_peep2_scratch_safe (operands[2]))
-+ FAIL;")
-+
-+(define_peephole2
- [(match_scratch:QI 3 "d")
- (set (match_operand:HI 0 "register_operand" "")
- (ashift:HI (match_operand:HI 1 "register_operand" "")
-@@ -1462,7 +1564,49 @@
- ;; >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >> >>
- ;; logical shift right
-
--(define_insn "lshrqi3"
-+(define_expand "lshrqi3"
-+ [(set (match_operand:QI 0 "register_operand" "")
-+ (lshiftrt:QI (match_operand:QI 1 "register_operand" "")
-+ (match_operand:QI 2 "general_operand" "")))]
-+ ""
-+ "")
-+
-+(define_insn_and_split "*lshrqi3_const4"
-+ [(set (match_operand:QI 0 "d_register_operand" "=d")
-+ (lshiftrt:QI (match_operand:QI 1 "d_register_operand" "0")
-+ (const_int 4)))]
-+ ""
-+ "#"
-+ ""
-+ [(set (match_dup 0) (unspec:QI [(match_dup 0)] UNSPEC_SWAP))
-+ (set (match_dup 0) (and:QI (match_dup 0) (const_int 15)))]
-+ "")
-+
-+(define_insn_and_split "*lshrqi3_const5"
-+ [(set (match_operand:QI 0 "d_register_operand" "=d")
-+ (lshiftrt:QI (match_operand:QI 1 "d_register_operand" "0")
-+ (const_int 5)))]
-+ ""
-+ "#"
-+ ""
-+ [(set (match_dup 0) (unspec:QI [(match_dup 0)] UNSPEC_SWAP))
-+ (set (match_dup 0) (lshiftrt:QI (match_dup 0) (const_int 1)))
-+ (set (match_dup 0) (and:QI (match_dup 0) (const_int 7)))]
-+ "")
-+
-+(define_insn_and_split "*lshrqi3_const6"
-+ [(set (match_operand:QI 0 "d_register_operand" "=d")
-+ (lshiftrt:QI (match_operand:QI 1 "d_register_operand" "0")
-+ (const_int 6)))]
-+ ""
-+ "#"
-+ ""
-+ [(set (match_dup 0) (unspec:QI [(match_dup 0)] UNSPEC_SWAP))
-+ (set (match_dup 0) (lshiftrt:QI (match_dup 0) (const_int 2)))
-+ (set (match_dup 0) (and:QI (match_dup 0) (const_int 3)))]
-+ "")
-+
-+(define_insn "*lshrqi3"
- [(set (match_operand:QI 0 "register_operand" "=r,r,r,r,!d,r,r")
- (lshiftrt:QI (match_operand:QI 1 "register_operand" "0,0,0,0,0,0,0")
- (match_operand:QI 2 "general_operand" "r,L,P,K,n,n,Qm")))]
-@@ -1492,6 +1636,47 @@
- ;; Optimize if a scratch register from LD_REGS happens to be available.
-
- (define_peephole2
-+ [(match_scratch:QI 2 "d")
-+ (set (match_operand:QI 0 "l_register_operand" "")
-+ (lshiftrt:QI (match_operand:QI 1 "l_register_operand" "")
-+ (const_int 4)))]
-+ ""
-+ [(set (match_dup 0) (unspec:QI [(match_dup 0)] UNSPEC_SWAP))
-+ (set (match_dup 2) (const_int 15))
-+ (set (match_dup 0) (and:QI (match_dup 0) (match_dup 2)))
-+ (clobber (match_dup 2))]
-+ "if (!avr_peep2_scratch_safe (operands[2]))
-+ FAIL;")
-+
-+(define_peephole2
-+ [(match_scratch:QI 2 "d")
-+ (set (match_operand:QI 0 "l_register_operand" "")
-+ (lshiftrt:QI (match_operand:QI 1 "l_register_operand" "")
-+ (const_int 5)))]
-+ ""
-+ [(set (match_dup 0) (unspec:QI [(match_dup 0)] UNSPEC_SWAP))
-+ (set (match_dup 0) (lshiftrt:QI (match_dup 0) (const_int 1)))
-+ (set (match_dup 2) (const_int 7))
-+ (set (match_dup 0) (and:QI (match_dup 0) (match_dup 2)))
-+ (clobber (match_dup 2))]
-+ "if (!avr_peep2_scratch_safe (operands[2]))
-+ FAIL;")
-+
-+(define_peephole2
-+ [(match_scratch:QI 2 "d")
-+ (set (match_operand:QI 0 "l_register_operand" "")
-+ (lshiftrt:QI (match_operand:QI 1 "l_register_operand" "")
-+ (const_int 6)))]
-+ ""
-+ [(set (match_dup 0) (unspec:QI [(match_dup 0)] UNSPEC_SWAP))
-+ (set (match_dup 0) (lshiftrt:QI (match_dup 0) (const_int 2)))
-+ (set (match_dup 2) (const_int 3))
-+ (set (match_dup 0) (and:QI (match_dup 0) (match_dup 2)))
-+ (clobber (match_dup 2))]
-+ "if (!avr_peep2_scratch_safe (operands[2]))
-+ FAIL;")
-+
-+(define_peephole2
- [(match_scratch:QI 3 "d")
- (set (match_operand:HI 0 "register_operand" "")
- (lshiftrt:HI (match_operand:HI 1 "register_operand" "")
-Only in ./gcc/config/avr: avr.md.orig
+++ /dev/null
---- gcc/config/avr/avr.h.orig 2010-03-05 15:20:53.000000000 +0100
-+++ gcc/config/avr/avr.h 2010-03-05 15:22:53.000000000 +0100
-@@ -470,10 +470,6 @@
- OPNUM, TYPE); \
- goto WIN; \
- } \
-- push_reload (XEXP (X, 0), NULL_RTX, &XEXP (X, 0), NULL, \
-- BASE_POINTER_REGS, GET_MODE (X), VOIDmode, 0, 0, \
-- OPNUM, TYPE); \
-- goto WIN; \
- } \
- else if (! (frame_pointer_needed && XEXP (X,0) == frame_pointer_rtx)) \
- { \
---- gcc/config/avr/avr.c.orig 2010-03-05 15:20:53.000000000 +0100
-+++ gcc/config/avr/avr.c 2010-03-05 15:22:53.000000000 +0100
-@@ -993,6 +993,8 @@
- true_regnum (XEXP (x, 0)));
- debug_rtx (x);
- }
-+ if (!strict && GET_CODE (x) == SUBREG)
-+ x = SUBREG_REG (x);
- if (REG_P (x) && (strict ? REG_OK_FOR_BASE_STRICT_P (x)
- : REG_OK_FOR_BASE_NOSTRICT_P (x)))
- r = POINTER_REGS;
-@@ -1007,6 +1009,7 @@
- if (fit)
- {
- if (! strict
-+ || REGNO (XEXP (x,0)) == REG_X
- || REGNO (XEXP (x,0)) == REG_Y
- || REGNO (XEXP (x,0)) == REG_Z)
- r = BASE_POINTER_REGS;
+++ /dev/null
-Index: gcc/rtl-factoring.c
-===================================================================
---- gcc/rtl-factoring.c (revision 132522)
-+++ gcc/rtl-factoring.c (working copy)
-@@ -551,8 +551,8 @@
- df_simulate_artificial_refs_at_end (bb, &live);
-
- /* Propagate until INSN if found. */
-- for (x = BB_END (bb); x != insn;)
-- df_simulate_one_insn_backwards (bb, insn, &live);
-+ for (x = BB_END (bb); x != insn; x = PREV_INSN(x))
-+ df_simulate_one_insn_backwards (bb, x, &live);
-
- /* Clear registers live after INSN. */
- renumbered_reg_set_to_hard_reg_set (&hlive, &live);
-@@ -562,7 +562,7 @@
- for (i = 0; i < length;)
- {
- rtx prev = PREV_INSN (x);
-- df_simulate_one_insn_backwards (bb, insn, &live);
-+ df_simulate_one_insn_backwards (bb, x, &live);
-
- if (INSN_P (x))
- {
-@@ -949,6 +949,17 @@
- return sym;
- }
-
-+/* Splits basic block at the requested insn and rebuilds dataflow. */
-+
-+static basic_block
-+asplit_block(basic_block bb, rtx insn)
-+{
-+ basic_block next;
-+ next = split_block (bb, insn)->dest;
-+ df_analyze ();
-+ return next;
-+}
-+
- /* Ensures that INSN is the last insn in its block and returns the block label
- of the next block. */
-
-@@ -959,7 +970,7 @@
- if ((insn == BB_END (bb)) && (bb->next_bb != EXIT_BLOCK_PTR))
- return block_label (bb->next_bb);
- else
-- return block_label (split_block (bb, insn)->dest);
-+ return block_label (asplit_block (bb, insn));
- }
-
- /* Ensures that the last insns of the best pattern and its matching sequences
-@@ -1008,8 +1019,9 @@
-
- /* Emit an indirect jump via the link register after the sequence acting
- as the return insn. Also emit a barrier and update the basic block. */
-- retjmp = emit_jump_insn_after (gen_indirect_jump (pattern_seqs->link_reg),
-- BB_END (bb));
-+ if (!find_reg_note (BB_END(bb), REG_NORETURN, NULL))
-+ retjmp = emit_jump_insn_after (gen_indirect_jump (pattern_seqs->link_reg),
-+ BB_END (bb));
- emit_barrier_after (BB_END (bb));
-
- /* Replace all outgoing edges with a new one to the block of RETLABEL. */
-@@ -1025,7 +1037,7 @@
- for (; i < sb->length; i++)
- insn = prev_insn_in_block (insn);
-
-- sb->label = block_label (split_block (bb, insn)->dest);
-+ sb->label = block_label (asplit_block (bb, insn));
- }
-
- /* Emit an insn saving the return address to the link register before the
-@@ -1067,7 +1079,7 @@
- /* Delete the insns of the sequence. */
- for (i = 0; i < sb->length; i++)
- insn = prev_insn_in_block (insn);
-- delete_basic_block (split_block (bb, insn)->dest);
-+ delete_basic_block (asplit_block (bb, insn));
-
- /* Emit an insn saving the return address to the link register
- before the deleted sequence. */
+++ /dev/null
-Fix for bugs #34210, #35508.
-
-===================================================================
---- libgcc/config.host.orig 2008-01-25 13:49:04.000000000 -0700
-+++ libgcc/config.host 2008-03-22 22:04:25.965018200 -0600
-@@ -77,6 +77,9 @@ strongarm*-*-*)
- arm*-*-*)
- cpu_type=arm
- ;;
-+avr-*-*)
-+ cpu_type=avr
-+ ;;
- bfin*-*)
- cpu_type=bfin
- ;;
-@@ -243,6 +246,8 @@ arm*-*-kaos*)
- avr-*-rtems*)
- ;;
- avr-*-*)
-+ # Make HImode functions for AVR
-+ tmake_file=${cpu_type}/t-avr
- ;;
- bfin*-elf*)
- ;;
-Index: config/avr/t-avr
-===================================================================
---- libgcc/config/avr/t-avr (revision 0)
-+++ libgcc/config/avr/t-avr (revision 0)
-@@ -0,0 +1,19 @@
-+# Extra 16-bit integer functions.
-+intfuncs16 = _absvXX2 _addvXX3 _subvXX3 _mulvXX3 _negvXX2 _ffsXX2 _clzXX2 \
-+ _ctzXX2 _popcountXX2 _parityXX2
-+hiintfuncs16 = $(subst XX,hi,$(intfuncs16))
-+siintfuncs16 = $(subst XX,si,$(intfuncs16))
-+
-+iter-items := $(hiintfuncs16)
-+iter-labels := $(siintfuncs16)
-+iter-sizes := $(patsubst %,2,$(siintfuncs16)) $(patsubst %,2,$(hiintfuncs16))
-+
-+
-+include $(srcdir)/empty.mk $(patsubst %,$(srcdir)/siditi-object.mk,$(iter-items))
-+libgcc-objects += $(patsubst %,%$(objext),$(hiintfuncs16))
-+
-+ifeq ($(enable_shared),yes)
-+libgcc-s-objects += $(patsubst %,%_s$(objext),$(hiintfuncs16))
-+endif
-+
-+
+++ /dev/null
---- ./gcc/config/avr/avr-protos.h.orig 2010-03-05 15:20:53.000000000 +0100
-+++ ./gcc/config/avr/avr-protos.h 2010-03-05 15:24:52.000000000 +0100
-@@ -114,6 +114,7 @@
- extern int _reg_unused_after (rtx insn, rtx reg);
- extern int avr_jump_mode (rtx x, rtx insn);
- extern int byte_immediate_operand (rtx op, enum machine_mode mode);
-+extern int text_segment_operand (rtx op, enum machine_mode mode);
- extern int test_hard_reg_class (enum reg_class class, rtx x);
- extern int jump_over_one_insn_p (rtx insn, rtx dest);
-
---- ./gcc/config/avr/avr.c.orig 2010-03-05 15:22:53.000000000 +0100
-+++ ./gcc/config/avr/avr.c 2010-03-05 15:24:52.000000000 +0100
-@@ -1136,8 +1136,7 @@
-
- default:
- if (CONSTANT_ADDRESS_P (addr)
-- && ((GET_CODE (addr) == SYMBOL_REF && SYMBOL_REF_FUNCTION_P (addr))
-- || GET_CODE (addr) == LABEL_REF))
-+ && text_segment_operand (addr, VOIDmode))
- {
- fprintf (file, "gs(");
- output_addr_const (file,addr);
-@@ -1453,6 +1452,26 @@
- && INTVAL (op) <= 0xff && INTVAL (op) >= 0);
- }
-
-+/* Return true if OP is a program memory reference.*/
-+int
-+text_segment_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED)
-+{
-+ switch (GET_CODE (op))
-+ {
-+ case LABEL_REF :
-+ return true;
-+ case SYMBOL_REF :
-+ return SYMBOL_REF_FUNCTION_P (op);
-+ case PLUS :
-+ /* Assume canonical format of symbol + constant.
-+ Fall through. */
-+ case CONST :
-+ return text_segment_operand (XEXP (op, 0), VOIDmode);
-+ default :
-+ return false;
-+ }
-+}
-+
- /* Output all insn addresses and their sizes into the assembly language
- output file. This is helpful for debugging whether the length attributes
- in the md file are correct.
-@@ -4490,8 +4509,7 @@
- avr_assemble_integer (rtx x, unsigned int size, int aligned_p)
- {
- if (size == POINTER_SIZE / BITS_PER_UNIT && aligned_p
-- && ((GET_CODE (x) == SYMBOL_REF && SYMBOL_REF_FUNCTION_P (x))
-- || GET_CODE (x) == LABEL_REF))
-+ && text_segment_operand (x, VOIDmode) )
- {
- fputs ("\t.word\tgs(", asm_out_file);
- output_addr_const (asm_out_file, x);
+++ /dev/null
-diff -ur ../gcc-4.3.4.orig/gcc/config/avr/avr.c ./gcc/config/avr/avr.c
---- ../gcc-4.3.4.orig/gcc/config/avr/avr.c 2008-06-15 23:32:29.000000000 +0200
-+++ ./gcc/config/avr/avr.c 2009-10-02 14:27:56.000000000 +0200
-@@ -127,7 +127,8 @@
- { 0, 0, 1, 1, 0, 0, 0, 0, "__AVR_ARCH__=35" },
- { 0, 1, 0, 1, 0, 0, 0, 0, "__AVR_ARCH__=4" },
- { 0, 1, 1, 1, 0, 0, 0, 0, "__AVR_ARCH__=5" },
-- { 0, 1, 1, 1, 1, 1, 0, 0, "__AVR_ARCH__=51" }
-+ { 0, 1, 1, 1, 1, 1, 0, 0, "__AVR_ARCH__=51" },
-+ { 0, 1, 1, 1, 1, 1, 1, 0, "__AVR_ARCH__=6" }
- };
-
- /* These names are used as the index into the avr_arch_types[] table
-@@ -144,7 +145,8 @@
- ARCH_AVR35,
- ARCH_AVR4,
- ARCH_AVR5,
-- ARCH_AVR51
-+ ARCH_AVR51,
-+ ARCH_AVR6
- };
-
- struct mcu_type_s {
-@@ -273,6 +275,10 @@
- { "at90can128", ARCH_AVR51, "__AVR_AT90CAN128__" },
- { "at90usb1286", ARCH_AVR51, "__AVR_AT90USB1286__" },
- { "at90usb1287", ARCH_AVR51, "__AVR_AT90USB1287__" },
-+ /* 3-Byte PC. */
-+ { "avr6", ARCH_AVR6, NULL },
-+ { "atmega2560", ARCH_AVR6, "__AVR_ATmega2560__" },
-+ { "atmega2561", ARCH_AVR6, "__AVR_ATmega2561__" },
- /* Assembler only. */
- { "avr1", ARCH_AVR1, NULL },
- { "at90s1200", ARCH_AVR1, "__AVR_AT90S1200__" },
-@@ -513,9 +519,10 @@
- else
- {
- int offset = frame_pointer_needed ? 2 : 0;
-+ int avr_pc_size = AVR_HAVE_EIJMP_EICALL ? 3 : 2;
-
- offset += avr_regs_to_save (NULL);
-- return get_frame_size () + 2 + 1 + offset;
-+ return get_frame_size () + (avr_pc_size) + 1 + offset;
- }
- }
-
-@@ -662,7 +669,9 @@
- /* Prevent any attempt to delete the setting of ZERO_REG! */
- emit_insn (gen_rtx_USE (VOIDmode, zero_reg_rtx));
- }
-- if (minimize && (frame_pointer_needed || live_seq > 6))
-+ if (minimize && (frame_pointer_needed
-+ || (AVR_2_BYTE_PC && live_seq > 6)
-+ || live_seq > 7))
- {
- insn = emit_move_insn (gen_rtx_REG (HImode, REG_X),
- gen_int_mode (size, HImode));
-@@ -1121,7 +1130,7 @@
- && ((GET_CODE (addr) == SYMBOL_REF && SYMBOL_REF_FUNCTION_P (addr))
- || GET_CODE (addr) == LABEL_REF))
- {
-- fprintf (file, "pm(");
-+ fprintf (file, "gs(");
- output_addr_const (file,addr);
- fprintf (file ,")");
- }
-@@ -1146,6 +1155,11 @@
- if (!AVR_MEGA)
- fputc ('r', file);
- }
-+ else if (code == '!')
-+ {
-+ if (AVR_HAVE_EIJMP_EICALL)
-+ fputc ('e', file);
-+ }
- else if (REG_P (x))
- {
- if (x == zero_reg_rtx)
-@@ -4470,7 +4484,7 @@
- && ((GET_CODE (x) == SYMBOL_REF && SYMBOL_REF_FUNCTION_P (x))
- || GET_CODE (x) == LABEL_REF))
- {
-- fputs ("\t.word\tpm(", asm_out_file);
-+ fputs ("\t.word\tgs(", asm_out_file);
- output_addr_const (asm_out_file, x);
- fputs (")\n", asm_out_file);
- return true;
-@@ -5817,7 +5831,7 @@
- {
- switch_to_section (progmem_section);
- if (AVR_MEGA)
-- fprintf (stream, "\t.word pm(.L%d)\n", value);
-+ fprintf (stream, "\t.word gs(.L%d)\n", value);
- else
- fprintf (stream, "\trjmp .L%d\n", value);
- }
-Only in ./gcc/config/avr: avr.c.orig
-diff -ur ../gcc-4.3.4.orig/gcc/config/avr/avr.h ./gcc/config/avr/avr.h
---- ../gcc-4.3.4.orig/gcc/config/avr/avr.h 2008-06-15 23:32:29.000000000 +0200
-+++ ./gcc/config/avr/avr.h 2009-10-02 14:27:56.000000000 +0200
-@@ -80,6 +80,12 @@
- builtin_define ("__AVR_MEGA__"); \
- if (avr_current_arch->have_jmp_call) \
- builtin_define ("__AVR_HAVE_JMP_CALL__"); \
-+ if (!avr_current_arch->have_eijmp_eicall) \
-+ builtin_define ("__AVR_2_BYTE_PC__"); \
-+ if (avr_current_arch->have_eijmp_eicall) \
-+ builtin_define ("__AVR_3_BYTE_PC__"); \
-+ if (avr_current_arch->have_eijmp_eicall) \
-+ builtin_define ("__AVR_HAVE_EIJMP_EICALL__"); \
- if (TARGET_NO_INTERRUPTS) \
- builtin_define ("__NO_INTERRUPTS__"); \
- } \
-@@ -100,9 +106,10 @@
- #define AVR_HAVE_MOVW (avr_have_movw_lpmx_p)
- #define AVR_HAVE_LPMX (avr_have_movw_lpmx_p)
- #define AVR_HAVE_RAMPZ (avr_current_arch->have_elpm)
-+#define AVR_HAVE_EIJMP_EICALL (avr_current_arch->have_eijmp_eicall)
-
--#define AVR_2_BYTE_PC 1
--#define AVR_3_BYTE_PC 0
-+#define AVR_2_BYTE_PC (!AVR_HAVE_EIJMP_EICALL)
-+#define AVR_3_BYTE_PC (AVR_HAVE_EIJMP_EICALL)
-
- #define TARGET_VERSION fprintf (stderr, " (GNU assembler syntax)");
-
-@@ -681,7 +688,7 @@
-
- #define PRINT_OPERAND(STREAM, X, CODE) print_operand (STREAM, X, CODE)
-
--#define PRINT_OPERAND_PUNCT_VALID_P(CODE) ((CODE) == '~')
-+#define PRINT_OPERAND_PUNCT_VALID_P(CODE) ((CODE) == '~' || (CODE) == '!')
-
- #define PRINT_OPERAND_ADDRESS(STREAM, X) print_operand_address(STREAM, X)
-
-@@ -838,6 +845,7 @@
- mmcu=at90usb64*|\
- mmcu=at90usb128*|\
- mmcu=at94k: -m avr5}\
-+%{mmcu=atmega256*:-m avr6}\
- %{mmcu=atmega324*|\
- mmcu=atmega325*|\
- mmcu=atmega328p|\
-@@ -866,7 +874,8 @@
- mmcu=at90usb*: -Tdata 0x800100}\
- %{mmcu=atmega640|\
- mmcu=atmega1280|\
-- mmcu=atmega1281: -Tdata 0x800200} "
-+ mmcu=atmega1281|\
-+ mmcu=atmega256*: -Tdata 0x800200} "
-
- #define LIB_SPEC \
- "%{!mmcu=at90s1*:%{!mmcu=attiny11:%{!mmcu=attiny12:%{!mmcu=attiny15:%{!mmcu=attiny28: -lc }}}}}"
-@@ -978,6 +987,8 @@
- %{mmcu=atmega1280:crtm1280.o%s} \
- %{mmcu=atmega1281:crtm1281.o%s} \
- %{mmcu=atmega1284p:crtm1284p.o%s} \
-+%{mmcu=atmega2560:crtm2560.o%s} \
-+%{mmcu=atmega2561:crtm2561.o%s} \
- %{mmcu=at90can128:crtcan128.o%s} \
- %{mmcu=at90usb1286:crtusb1286.o%s} \
- %{mmcu=at90usb1287:crtusb1287.o%s}"
-Only in ./gcc/config/avr: avr.h.orig
-diff -ur ../gcc-4.3.4.orig/gcc/config/avr/avr.md ./gcc/config/avr/avr.md
---- ../gcc-4.3.4.orig/gcc/config/avr/avr.md 2009-03-09 21:49:28.000000000 +0100
-+++ ./gcc/config/avr/avr.md 2009-10-02 14:27:56.000000000 +0200
-@@ -32,6 +32,7 @@
- ;; p POST_INC or PRE_DEC address as a pointer (X, Y, Z)
- ;; r POST_INC or PRE_DEC address as a register (r26, r28, r30)
- ;; ~ Output 'r' if not AVR_MEGA.
-+;; ! Output 'e' if AVR_HAVE_EIJMP_EICALL.
-
- ;; UNSPEC usage:
- ;; 0 Length of a string, see "strlenhi".
-@@ -2290,22 +2291,22 @@
- "(register_operand (operands[0], HImode) || CONSTANT_P (operands[0]))"
- "*{
- if (which_alternative==0)
-- return \"icall\";
-+ return \"%!icall\";
- else if (which_alternative==1)
- {
- if (AVR_HAVE_MOVW)
- return (AS2 (movw, r30, %0) CR_TAB
-- \"icall\");
-+ \"%!icall\");
- else
- return (AS2 (mov, r30, %A0) CR_TAB
- AS2 (mov, r31, %B0) CR_TAB
-- \"icall\");
-+ \"%!icall\");
- }
- else if (which_alternative==2)
- return AS1(%~call,%c0);
- return (AS2 (ldi,r30,lo8(%0)) CR_TAB
- AS2 (ldi,r31,hi8(%0)) CR_TAB
-- \"icall\");
-+ \"%!icall\");
- }"
- [(set_attr "cc" "clobber,clobber,clobber,clobber")
- (set_attr_alternative "length"
-@@ -2327,22 +2328,22 @@
- "(register_operand (operands[0], VOIDmode) || CONSTANT_P (operands[0]))"
- "*{
- if (which_alternative==0)
-- return \"icall\";
-+ return \"%!icall\";
- else if (which_alternative==1)
- {
- if (AVR_HAVE_MOVW)
- return (AS2 (movw, r30, %1) CR_TAB
-- \"icall\");
-+ \"%!icall\");
- else
- return (AS2 (mov, r30, %A1) CR_TAB
- AS2 (mov, r31, %B1) CR_TAB
-- \"icall\");
-+ \"%!icall\");
- }
- else if (which_alternative==2)
- return AS1(%~call,%c1);
- return (AS2 (ldi, r30, lo8(%1)) CR_TAB
- AS2 (ldi, r31, hi8(%1)) CR_TAB
-- \"icall\");
-+ \"%!icall\");
- }"
- [(set_attr "cc" "clobber,clobber,clobber,clobber")
- (set_attr_alternative "length"
-@@ -2365,13 +2366,20 @@
- ; indirect jump
- (define_insn "indirect_jump"
- [(set (pc) (match_operand:HI 0 "register_operand" "!z,*r"))]
-- ""
-+ "!AVR_HAVE_EIJMP_EICALL"
- "@
- ijmp
- push %A0\;push %B0\;ret"
- [(set_attr "length" "1,3")
- (set_attr "cc" "none,none")])
-
-+(define_insn "*indirect_jump_avr6"
-+ [(set (pc) (match_operand:HI 0 "register_operand" "z"))]
-+ "AVR_HAVE_EIJMP_EICALL"
-+ "eijmp"
-+ [(set_attr "length" "1")
-+ (set_attr "cc" "none")])
-+
- ;; table jump
-
- ;; Table made from "rjmp" instructions for <=8K devices.
-@@ -2380,7 +2388,7 @@
- UNSPEC_INDEX_JMP))
- (use (label_ref (match_operand 1 "" "")))
- (clobber (match_dup 0))]
-- "!AVR_MEGA"
-+ "(!AVR_MEGA) && (!AVR_HAVE_EIJMP_EICALL)"
- "@
- ijmp
- push %A0\;push %B0\;ret"
-@@ -2409,7 +2417,7 @@
- lpm __tmp_reg__,Z+
- lpm r31,Z
- mov r30,__tmp_reg__
-- ijmp"
-+ %!ijmp"
- [(set_attr "length" "6")
- (set_attr "cc" "clobber")])
-
-@@ -2418,7 +2426,7 @@
- UNSPEC_INDEX_JMP))
- (use (label_ref (match_operand 1 "" "")))
- (clobber (match_dup 0))]
-- "AVR_MEGA"
-+ "AVR_MEGA && !AVR_HAVE_EIJMP_EICALL"
- "lsl r30
- rol r31
- lpm
-@@ -2758,8 +2766,8 @@
- (use (reg:HI REG_X))
- (clobber (reg:HI REG_Z))]
- ""
-- "ldi r30,pm_lo8(1f)
-- ldi r31,pm_hi8(1f)
-+ "ldi r30,lo8(gs(1f))
-+ ldi r31,hi8(gs(1f))
- %~jmp __prologue_saves__+((18 - %0) * 2)
- 1:"
- [(set_attr_alternative "length"
-Only in ./gcc/config/avr: avr.md.orig
-diff -ur ../gcc-4.3.4.orig/gcc/config/avr/libgcc.S ./gcc/config/avr/libgcc.S
---- ../gcc-4.3.4.orig/gcc/config/avr/libgcc.S 2008-01-19 13:15:02.000000000 +0100
-+++ ./gcc/config/avr/libgcc.S 2009-10-02 14:27:56.000000000 +0200
-@@ -594,7 +594,12 @@
- out __SP_H__,r29
- out __SREG__,__tmp_reg__
- out __SP_L__,r28
-+#if defined (__AVR_HAVE_EIJMP_EICALL__)
-+ eijmp
-+#else
- ijmp
-+#endif
-+
- .endfunc
- #endif /* defined (L_prologue) */
-
-@@ -674,13 +679,22 @@
- lpm __tmp_reg__, Z+
- lpm r31, Z
- mov r30, __tmp_reg__
-+
-+#if defined (__AVR_HAVE_EIJMP_EICALL__)
-+ eijmp
-+#else
- ijmp
-+#endif
-+
- #else
- lpm
- adiw r30, 1
- push r0
- lpm
- push r0
-+#if defined (__AVR_HAVE_EIJMP_EICALL__)
-+ push __zero_reg__
-+#endif
- ret
- #endif
- .endfunc
-diff -ur ../gcc-4.3.4.orig/gcc/config/avr/t-avr ./gcc/config/avr/t-avr
---- ../gcc-4.3.4.orig/gcc/config/avr/t-avr 2008-01-23 16:07:09.000000000 +0100
-+++ ./gcc/config/avr/t-avr 2009-10-02 14:27:56.000000000 +0200
-@@ -37,8 +37,8 @@
-
- FPBIT = fp-bit.c
-
--MULTILIB_OPTIONS = mmcu=avr2/mmcu=avr25/mmcu=avr3/mmcu=avr31/mmcu=avr35/mmcu=avr4/mmcu=avr5/mmcu=avr51
--MULTILIB_DIRNAMES = avr2 avr25 avr3 avr31 avr35 avr4 avr5 avr51
-+MULTILIB_OPTIONS = mmcu=avr2/mmcu=avr25/mmcu=avr3/mmcu=avr31/mmcu=avr35/mmcu=avr4/mmcu=avr5/mmcu=avr51/mmcu=avr6
-+MULTILIB_DIRNAMES = avr2 avr25 avr3 avr31 avr35 avr4 avr5 avr51 avr6
-
- # The many avr2 matches are not listed here - this is the default.
- MULTILIB_MATCHES = \
-@@ -123,7 +123,9 @@
- mmcu?avr51=mmcu?atmega1284p \
- mmcu?avr51=mmcu?at90can128 \
- mmcu?avr51=mmcu?at90usb1286 \
-- mmcu?avr51=mmcu?at90usb1287
-+ mmcu?avr51=mmcu?at90usb1287 \
-+ mmcu?avr6=mmcu?atmega2560 \
-+ mmcu?avr6=mmcu?atmega2561
-
- MULTILIB_EXCEPTIONS =
-
+++ /dev/null
-Fix for bugs #34210, #35508.
-
-===================================================================
---- libgcc/config.host.orig 2008-01-25 13:49:04.000000000 -0700
-+++ libgcc/config.host 2008-03-22 22:04:25.965018200 -0600
-@@ -77,6 +77,9 @@ strongarm*-*-*)
- arm*-*-*)
- cpu_type=arm
- ;;
-+avr-*-*)
-+ cpu_type=avr
-+ ;;
- bfin*-*)
- cpu_type=bfin
- ;;
-@@ -243,6 +246,8 @@ arm*-*-kaos*)
- avr-*-rtems*)
- ;;
- avr-*-*)
-+ # Make HImode functions for AVR
-+ tmake_file=${cpu_type}/t-avr
- ;;
- bfin*-elf*)
- ;;
-Index: config/avr/t-avr
-===================================================================
---- libgcc/config/avr/t-avr (revision 0)
-+++ libgcc/config/avr/t-avr (revision 0)
-@@ -0,0 +1,19 @@
-+# Extra 16-bit integer functions.
-+intfuncs16 = _absvXX2 _addvXX3 _subvXX3 _mulvXX3 _negvXX2 _ffsXX2 _clzXX2 \
-+ _ctzXX2 _popcountXX2 _parityXX2
-+hiintfuncs16 = $(subst XX,hi,$(intfuncs16))
-+siintfuncs16 = $(subst XX,si,$(intfuncs16))
-+
-+iter-items := $(hiintfuncs16)
-+iter-labels := $(siintfuncs16)
-+iter-sizes := $(patsubst %,2,$(siintfuncs16)) $(patsubst %,2,$(hiintfuncs16))
-+
-+
-+include $(srcdir)/empty.mk $(patsubst %,$(srcdir)/siditi-object.mk,$(iter-items))
-+libgcc-objects += $(patsubst %,%$(objext),$(hiintfuncs16))
-+
-+ifeq ($(enable_shared),yes)
-+libgcc-s-objects += $(patsubst %,%_s$(objext),$(hiintfuncs16))
-+endif
-+
-+
+++ /dev/null
-2008-05-26 Tristan Gingold <gingold@adacore.com>
- Anatoly Sokolov <aesok@post.ru>
-
- * config/avr/avr.md ("call_prologue_saves"): Use hi8(gs())/lo8(gs())
- instead of pm_lo8/pm_hi8 to makes this call working on avr6.
- * config/avr/avr.c (expand_prologue): Tune "call_prologue"
- optimization for 'avr6' architecture.
-
-Index: gcc/config/avr/avr.c
-===================================================================
---- gcc/config/avr/avr.c (revision 135845)
-+++ gcc/config/avr/avr.c (working copy)
-@@ -682,7 +694,9 @@
- /* Prevent any attempt to delete the setting of ZERO_REG! */
- emit_insn (gen_rtx_USE (VOIDmode, zero_reg_rtx));
- }
-- if (minimize && (frame_pointer_needed || live_seq > 6))
-+ if (minimize && (frame_pointer_needed
-+ || (AVR_2_BYTE_PC && live_seq > 6)
-+ || live_seq > 7))
- {
- insn = emit_move_insn (gen_rtx_REG (HImode, REG_X),
- gen_int_mode (size, HImode));
---- gcc/config/avr/avr.md.orig Wed Aug 20 16:55:20 2008
-+++ gcc/config/avr/avr.md Wed Aug 20 16:59:52 2008
-@@ -2764,8 +2764,8 @@
- (use (reg:HI REG_X))
- (clobber (reg:HI REG_Z))]
- ""
-- "ldi r30,pm_lo8(1f)
-- ldi r31,pm_hi8(1f)
-+ "ldi r30,lo8(gs(1f))
-+ ldi r31,hi8(gs(1f))
- %~jmp __prologue_saves__+((18 - %0) * 2)
- 1:"
- [(set_attr_alternative "length"
+++ /dev/null
-Index: gcc/config/avr/libgcc.S
-===================================================================
---- gcc/config/avr/libgcc.S (revision 132252)
-+++ gcc/config/avr/libgcc.S (working copy)
-@@ -594,7 +594,12 @@
- out __SP_H__,r29
- out __SREG__,__tmp_reg__
- out __SP_L__,r28
-+#if defined (__AVR_HAVE_EIJMP_EICALL__)
-+ eijmp
-+#else
- ijmp
-+#endif
-+
- .endfunc
- #endif /* defined (L_prologue) */
-
-@@ -674,13 +679,22 @@
- lpm __tmp_reg__, Z+
- lpm r31, Z
- mov r30, __tmp_reg__
-+
-+#if defined (__AVR_HAVE_EIJMP_EICALL__)
-+ eijmp
-+#else
- ijmp
-+#endif
-+
- #else
- lpm
- adiw r30, 1
- push r0
- lpm
- push r0
-+#if defined (__AVR_HAVE_EIJMP_EICALL__)
-+ push __zero_reg__
-+#endif
- ret
- #endif
- .endfunc
-Index: gcc/config/avr/avr.md
-===================================================================
---- gcc/config/avr/avr.md (revision 132252)
-+++ gcc/config/avr/avr.md (working copy)
-@@ -32,6 +32,7 @@
- ;; p POST_INC or PRE_DEC address as a pointer (X, Y, Z)
- ;; r POST_INC or PRE_DEC address as a register (r26, r28, r30)
- ;; ~ Output 'r' if not AVR_MEGA.
-+;; ! Output 'e' if AVR_HAVE_EIJMP_EICALL.
-
- ;; UNSPEC usage:
- ;; 0 Length of a string, see "strlenhi".
-@@ -2301,22 +2302,22 @@
- "(register_operand (operands[0], HImode) || CONSTANT_P (operands[0]))"
- "*{
- if (which_alternative==0)
-- return \"icall\";
-+ return \"%!icall\";
- else if (which_alternative==1)
- {
- if (AVR_HAVE_MOVW)
- return (AS2 (movw, r30, %0) CR_TAB
-- \"icall\");
-+ \"%!icall\");
- else
- return (AS2 (mov, r30, %A0) CR_TAB
- AS2 (mov, r31, %B0) CR_TAB
-- \"icall\");
-+ \"%!icall\");
- }
- else if (which_alternative==2)
- return AS1(%~call,%c0);
- return (AS2 (ldi,r30,lo8(%0)) CR_TAB
- AS2 (ldi,r31,hi8(%0)) CR_TAB
-- \"icall\");
-+ \"%!icall\");
- }"
- [(set_attr "cc" "clobber,clobber,clobber,clobber")
- (set_attr_alternative "length"
-@@ -2338,22 +2339,22 @@
- "(register_operand (operands[0], VOIDmode) || CONSTANT_P (operands[0]))"
- "*{
- if (which_alternative==0)
-- return \"icall\";
-+ return \"%!icall\";
- else if (which_alternative==1)
- {
- if (AVR_HAVE_MOVW)
- return (AS2 (movw, r30, %1) CR_TAB
-- \"icall\");
-+ \"%!icall\");
- else
- return (AS2 (mov, r30, %A1) CR_TAB
- AS2 (mov, r31, %B1) CR_TAB
-- \"icall\");
-+ \"%!icall\");
- }
- else if (which_alternative==2)
- return AS1(%~call,%c1);
- return (AS2 (ldi, r30, lo8(%1)) CR_TAB
- AS2 (ldi, r31, hi8(%1)) CR_TAB
-- \"icall\");
-+ \"%!icall\");
- }"
- [(set_attr "cc" "clobber,clobber,clobber,clobber")
- (set_attr_alternative "length"
-@@ -2376,13 +2377,20 @@
- ; indirect jump
- (define_insn "indirect_jump"
- [(set (pc) (match_operand:HI 0 "register_operand" "!z,*r"))]
-- ""
-+ "!AVR_HAVE_EIJMP_EICALL"
- "@
- ijmp
- push %A0\;push %B0\;ret"
- [(set_attr "length" "1,3")
- (set_attr "cc" "none,none")])
-
-+(define_insn "*indirect_jump_avr6"
-+ [(set (pc) (match_operand:HI 0 "register_operand" "z"))]
-+ "AVR_HAVE_EIJMP_EICALL"
-+ "eijmp"
-+ [(set_attr "length" "1")
-+ (set_attr "cc" "none")])
-+
- ;; table jump
-
- ;; Table made from "rjmp" instructions for <=8K devices.
-@@ -2391,7 +2399,7 @@
- UNSPEC_INDEX_JMP))
- (use (label_ref (match_operand 1 "" "")))
- (clobber (match_dup 0))]
-- "!AVR_MEGA"
-+ "(!AVR_MEGA) && (!AVR_HAVE_EIJMP_EICALL)"
- "@
- ijmp
- push %A0\;push %B0\;ret"
-@@ -2420,7 +2428,7 @@
- lpm __tmp_reg__,Z+
- lpm r31,Z
- mov r30,__tmp_reg__
-- ijmp"
-+ %!ijmp"
- [(set_attr "length" "6")
- (set_attr "cc" "clobber")])
-
-@@ -2429,7 +2437,7 @@
- UNSPEC_INDEX_JMP))
- (use (label_ref (match_operand 1 "" "")))
- (clobber (match_dup 0))]
-- "AVR_MEGA"
-+ "AVR_MEGA && !AVR_HAVE_EIJMP_EICALL"
- "lsl r30
- rol r31
- lpm
-Index: gcc/config/avr/avr.c
-===================================================================
---- gcc/config/avr/avr.c (revision 132252)
-+++ gcc/config/avr/avr.c (working copy)
-@@ -127,7 +127,8 @@
- { 0, 0, 1, 1, 0, 0, 0, 0, "__AVR_ARCH__=35" },
- { 0, 1, 0, 1, 0, 0, 0, 0, "__AVR_ARCH__=4" },
- { 0, 1, 1, 1, 0, 0, 0, 0, "__AVR_ARCH__=5" },
-- { 0, 1, 1, 1, 1, 1, 0, 0, "__AVR_ARCH__=51" }
-+ { 0, 1, 1, 1, 1, 1, 0, 0, "__AVR_ARCH__=51" },
-+ { 0, 1, 1, 1, 1, 1, 1, 0, "__AVR_ARCH__=6" }
- };
-
- /* These names are used as the index into the avr_arch_types[] table
-@@ -144,7 +145,8 @@
- ARCH_AVR35,
- ARCH_AVR4,
- ARCH_AVR5,
-- ARCH_AVR51
-+ ARCH_AVR51,
-+ ARCH_AVR6
- };
-
- struct mcu_type_s {
-@@ -273,6 +275,10 @@
- { "at90can128", ARCH_AVR51, "__AVR_AT90CAN128__" },
- { "at90usb1286", ARCH_AVR51, "__AVR_AT90USB1286__" },
- { "at90usb1287", ARCH_AVR51, "__AVR_AT90USB1287__" },
-+ /* 3-Byte PC. */
-+ { "avr6", ARCH_AVR6, NULL },
-+ { "atmega2560", ARCH_AVR6, "__AVR_ATmega2560__" },
-+ { "atmega2561", ARCH_AVR6, "__AVR_ATmega2561__" },
- /* Assembler only. */
- { "avr1", ARCH_AVR1, NULL },
- { "at90s1200", ARCH_AVR1, "__AVR_AT90S1200__" },
-@@ -511,9 +517,10 @@
- else
- {
- int offset = frame_pointer_needed ? 2 : 0;
-+ int avr_pc_size = AVR_HAVE_EIJMP_EICALL ? 3 : 2;
-
- offset += avr_regs_to_save (NULL);
-- return get_frame_size () + 2 + 1 + offset;
-+ return get_frame_size () + (avr_pc_size) + 1 + offset;
- }
- }
-
-@@ -1119,7 +1126,7 @@
- && ((GET_CODE (addr) == SYMBOL_REF && SYMBOL_REF_FUNCTION_P (addr))
- || GET_CODE (addr) == LABEL_REF))
- {
-- fprintf (file, "pm(");
-+ fprintf (file, "gs(");
- output_addr_const (file,addr);
- fprintf (file ,")");
- }
-@@ -1144,6 +1151,11 @@
- if (!AVR_MEGA)
- fputc ('r', file);
- }
-+ else if (code == '!')
-+ {
-+ if (AVR_HAVE_EIJMP_EICALL)
-+ fputc ('e', file);
-+ }
- else if (REG_P (x))
- {
- if (x == zero_reg_rtx)
-@@ -4468,7 +4480,7 @@
- && ((GET_CODE (x) == SYMBOL_REF && SYMBOL_REF_FUNCTION_P (x))
- || GET_CODE (x) == LABEL_REF))
- {
-- fputs ("\t.word\tpm(", asm_out_file);
-+ fputs ("\t.word\tgs(", asm_out_file);
- output_addr_const (asm_out_file, x);
- fputs (")\n", asm_out_file);
- return true;
-@@ -5815,7 +5827,7 @@
- {
- switch_to_section (progmem_section);
- if (AVR_MEGA)
-- fprintf (stream, "\t.word pm(.L%d)\n", value);
-+ fprintf (stream, "\t.word gs(.L%d)\n", value);
- else
- fprintf (stream, "\trjmp .L%d\n", value);
- }
-Index: gcc/config/avr/t-avr
-===================================================================
---- gcc/config/avr/t-avr (revision 132252)
-+++ gcc/config/avr/t-avr (working copy)
-@@ -37,8 +37,8 @@
-
- FPBIT = fp-bit.c
-
--MULTILIB_OPTIONS = mmcu=avr2/mmcu=avr25/mmcu=avr3/mmcu=avr31/mmcu=avr35/mmcu=avr4/mmcu=avr5/mmcu=avr51
--MULTILIB_DIRNAMES = avr2 avr25 avr3 avr31 avr35 avr4 avr5 avr51
-+MULTILIB_OPTIONS = mmcu=avr2/mmcu=avr25/mmcu=avr3/mmcu=avr31/mmcu=avr35/mmcu=avr4/mmcu=avr5/mmcu=avr51/mmcu=avr6
-+MULTILIB_DIRNAMES = avr2 avr25 avr3 avr31 avr35 avr4 avr5 avr51 avr6
-
- # The many avr2 matches are not listed here - this is the default.
- MULTILIB_MATCHES = \
-@@ -123,7 +123,9 @@
- mmcu?avr51=mmcu?atmega1284p \
- mmcu?avr51=mmcu?at90can128 \
- mmcu?avr51=mmcu?at90usb1286 \
-- mmcu?avr51=mmcu?at90usb1287
-+ mmcu?avr51=mmcu?at90usb1287 \
-+ mmcu?avr6=mmcu?atmega2560 \
-+ mmcu?avr6=mmcu?atmega2561
-
- MULTILIB_EXCEPTIONS =
-
-Index: gcc/config/avr/avr.h
-===================================================================
---- gcc/config/avr/avr.h (revision 132252)
-+++ gcc/config/avr/avr.h (working copy)
-@@ -80,6 +80,12 @@
- builtin_define ("__AVR_MEGA__"); \
- if (avr_current_arch->have_jmp_call) \
- builtin_define ("__AVR_HAVE_JMP_CALL__"); \
-+ if (!avr_current_arch->have_eijmp_eicall) \
-+ builtin_define ("__AVR_2_BYTE_PC__"); \
-+ if (avr_current_arch->have_eijmp_eicall) \
-+ builtin_define ("__AVR_3_BYTE_PC__"); \
-+ if (avr_current_arch->have_eijmp_eicall) \
-+ builtin_define ("__AVR_HAVE_EIJMP_EICALL__"); \
- if (TARGET_NO_INTERRUPTS) \
- builtin_define ("__NO_INTERRUPTS__"); \
- } \
-@@ -100,9 +106,10 @@
- #define AVR_HAVE_MOVW (avr_have_movw_lpmx_p)
- #define AVR_HAVE_LPMX (avr_have_movw_lpmx_p)
- #define AVR_HAVE_RAMPZ (avr_current_arch->have_elpm)
-+#define AVR_HAVE_EIJMP_EICALL (avr_current_arch->have_eijmp_eicall)
-
--#define AVR_2_BYTE_PC 1
--#define AVR_3_BYTE_PC 0
-+#define AVR_2_BYTE_PC (!AVR_HAVE_EIJMP_EICALL)
-+#define AVR_3_BYTE_PC (AVR_HAVE_EIJMP_EICALL)
-
- #define TARGET_VERSION fprintf (stderr, " (GNU assembler syntax)");
-
-@@ -671,7 +678,7 @@
-
- #define PRINT_OPERAND(STREAM, X, CODE) print_operand (STREAM, X, CODE)
-
--#define PRINT_OPERAND_PUNCT_VALID_P(CODE) ((CODE) == '~')
-+#define PRINT_OPERAND_PUNCT_VALID_P(CODE) ((CODE) == '~' || (CODE) == '!')
-
- #define PRINT_OPERAND_ADDRESS(STREAM, X) print_operand_address(STREAM, X)
-
-@@ -828,6 +835,7 @@
- mmcu=at90usb64*|\
- mmcu=at90usb128*|\
- mmcu=at94k: -m avr5}\
-+%{mmcu=atmega256*:-m avr6}\
- %{mmcu=atmega324*|\
- mmcu=atmega325*|\
- mmcu=atmega328p|\
-@@ -856,7 +864,8 @@
- mmcu=at90usb*: -Tdata 0x800100}\
- %{mmcu=atmega640|\
- mmcu=atmega1280|\
-- mmcu=atmega1281: -Tdata 0x800200} "
-+ mmcu=atmega1281|\
-+ mmcu=atmega256*: -Tdata 0x800200} "
-
- #define LIB_SPEC \
- "%{!mmcu=at90s1*:%{!mmcu=attiny11:%{!mmcu=attiny12:%{!mmcu=attiny15:%{!mmcu=attiny28: -lc }}}}}"
-@@ -968,6 +977,8 @@
- %{mmcu=atmega1280:crtm1280.o%s} \
- %{mmcu=atmega1281:crtm1281.o%s} \
- %{mmcu=atmega1284p:crtm1284p.o%s} \
-+%{mmcu=atmega2560:crtm2560.o%s} \
-+%{mmcu=atmega2561:crtm2561.o%s} \
- %{mmcu=at90can128:crtcan128.o%s} \
- %{mmcu=at90usb1286:crtusb1286.o%s} \
- %{mmcu=at90usb1287:crtusb1287.o%s}"
+++ /dev/null
---- ./gcc/config/avr/avr.c~ 2010-03-05 17:16:20.000000000 +0100
-+++ ./gcc/config/avr/avr.c 2010-03-05 17:19:30.000000000 +0100
-@@ -193,18 +193,28 @@
- { "at90s8535", ARCH_AVR2, "__AVR_AT90S8535__" },
- /* Classic + MOVW, <= 8K. */
- { "avr25", ARCH_AVR25, NULL },
-+ { "ata6289", ARCH_AVR25, "__AVR_ATA6289__" },
- { "attiny13", ARCH_AVR25, "__AVR_ATtiny13__" },
-+ { "attiny13a", ARCH_AVR25, "__AVR_ATtiny13A__" },
- { "attiny2313", ARCH_AVR25, "__AVR_ATtiny2313__" },
-+ { "attiny2313a", ARCH_AVR25, "__AVR_ATtiny2313A__" },
- { "attiny24", ARCH_AVR25, "__AVR_ATtiny24__" },
-+ { "attiny24a", ARCH_AVR25, "__AVR_ATtiny24A__" },
-+ { "attiny4313", ARCH_AVR25, "__AVR_ATtiny4313__" },
- { "attiny44", ARCH_AVR25, "__AVR_ATtiny44__" },
-+ { "attiny44a", ARCH_AVR25, "__AVR_ATtiny44A__" },
- { "attiny84", ARCH_AVR25, "__AVR_ATtiny84__" },
- { "attiny25", ARCH_AVR25, "__AVR_ATtiny25__" },
- { "attiny45", ARCH_AVR25, "__AVR_ATtiny45__" },
- { "attiny85", ARCH_AVR25, "__AVR_ATtiny85__" },
- { "attiny261", ARCH_AVR25, "__AVR_ATtiny261__" },
-+ { "attiny261a", ARCH_AVR25, "__AVR_ATtiny261A__" },
- { "attiny461", ARCH_AVR25, "__AVR_ATtiny461__" },
-+ { "attiny461a", ARCH_AVR25, "__AVR_ATtiny461A__" },
- { "attiny861", ARCH_AVR25, "__AVR_ATtiny861__" },
-+ { "attiny861a", ARCH_AVR25, "__AVR_ATtiny861A__" },
- { "attiny43u", ARCH_AVR25, "__AVR_ATtiny43U__" },
-+ { "attiny87", ARCH_AVR25, "__AVR_ATtiny87__" },
- { "attiny48", ARCH_AVR25, "__AVR_ATtiny48__" },
- { "attiny88", ARCH_AVR25, "__AVR_ATtiny88__" },
- { "at86rf401", ARCH_AVR25, "__AVR_AT86RF401__" },
-@@ -220,61 +230,104 @@
- { "avr35", ARCH_AVR35, NULL },
- { "at90usb82", ARCH_AVR35, "__AVR_AT90USB82__" },
- { "at90usb162", ARCH_AVR35, "__AVR_AT90USB162__" },
-+ { "atmega8u2", ARCH_AVR35, "__AVR_ATmega8U2__" },
-+ { "atmega16u2", ARCH_AVR35, "__AVR_ATmega16U2__" },
-+ { "atmega32u2", ARCH_AVR35, "__AVR_ATmega32U2__" },
-+ { "attiny167", ARCH_AVR35, "__AVR_ATtiny167__" },
- /* Enhanced, <= 8K. */
- { "avr4", ARCH_AVR4, NULL },
- { "atmega8", ARCH_AVR4, "__AVR_ATmega8__" },
- { "atmega48", ARCH_AVR4, "__AVR_ATmega48__" },
-+ { "atmega48a", ARCH_AVR4, "__AVR_ATmega48A__" },
- { "atmega48p", ARCH_AVR4, "__AVR_ATmega48P__" },
- { "atmega88", ARCH_AVR4, "__AVR_ATmega88__" },
-+ { "atmega88a", ARCH_AVR4, "__AVR_ATmega88A__" },
- { "atmega88p", ARCH_AVR4, "__AVR_ATmega88P__" },
-+ { "atmega88pa", ARCH_AVR4, "__AVR_ATmega88PA__" },
- { "atmega8515", ARCH_AVR4, "__AVR_ATmega8515__" },
- { "atmega8535", ARCH_AVR4, "__AVR_ATmega8535__" },
- { "atmega8hva", ARCH_AVR4, "__AVR_ATmega8HVA__" },
-+ { "atmega4hvd", ARCH_AVR4, "__AVR_ATmega4HVD__" },
-+ { "atmega8hvd", ARCH_AVR4, "__AVR_ATmega8HVD__" },
- { "at90pwm1", ARCH_AVR4, "__AVR_AT90PWM1__" },
- { "at90pwm2", ARCH_AVR4, "__AVR_AT90PWM2__" },
- { "at90pwm2b", ARCH_AVR4, "__AVR_AT90PWM2B__" },
- { "at90pwm3", ARCH_AVR4, "__AVR_AT90PWM3__" },
- { "at90pwm3b", ARCH_AVR4, "__AVR_AT90PWM3B__" },
-+ { "at90pwm81", ARCH_AVR4, "__AVR_AT90PWM81__" },
- /* Enhanced, > 8K, <= 64K. */
- { "avr5", ARCH_AVR5, NULL },
- { "atmega16", ARCH_AVR5, "__AVR_ATmega16__" },
-+ { "atmega16a", ARCH_AVR5, "__AVR_ATmega16A__" },
- { "atmega161", ARCH_AVR5, "__AVR_ATmega161__" },
- { "atmega162", ARCH_AVR5, "__AVR_ATmega162__" },
- { "atmega163", ARCH_AVR5, "__AVR_ATmega163__" },
-+ { "atmega164a", ARCH_AVR5, "__AVR_ATmega164A__" },
- { "atmega164p", ARCH_AVR5, "__AVR_ATmega164P__" },
- { "atmega165", ARCH_AVR5, "__AVR_ATmega165__" },
-+ { "atmega165a", ARCH_AVR5, "__AVR_ATmega165A__" },
- { "atmega165p", ARCH_AVR5, "__AVR_ATmega165P__" },
- { "atmega168", ARCH_AVR5, "__AVR_ATmega168__" },
-+ { "atmega168a", ARCH_AVR5, "__AVR_ATmega168A__" },
- { "atmega168p", ARCH_AVR5, "__AVR_ATmega168P__" },
- { "atmega169", ARCH_AVR5, "__AVR_ATmega169__" },
-+ { "atmega169a", ARCH_AVR5, "__AVR_ATmega169A__" },
- { "atmega169p", ARCH_AVR5, "__AVR_ATmega169P__" },
-+ { "atmega169pa", ARCH_AVR5, "__AVR_ATmega169PA__" },
-+ { "atmega16c1", ARCH_AVR5, "__AVR_ATmega16C1__" },
-+ { "atmega16hva", ARCH_AVR5, "__AVR_ATmega16HVA__" },
-+ { "atmega16hva2", ARCH_AVR5, "__AVR_ATmega16HVA2__" },
-+ { "atmega16hvb", ARCH_AVR5, "__AVR_ATmega16HVB__" },
-+ { "atmega16m1", ARCH_AVR5, "__AVR_ATmega16M1__" },
-+ { "atmega16u4", ARCH_AVR5, "__AVR_ATmega16U4__" },
- { "atmega32", ARCH_AVR5, "__AVR_ATmega32__" },
- { "atmega323", ARCH_AVR5, "__AVR_ATmega323__" },
-+ { "atmega324a", ARCH_AVR5, "__AVR_ATmega324A__" },
- { "atmega324p", ARCH_AVR5, "__AVR_ATmega324P__" },
-+ { "atmega324pa", ARCH_AVR5, "__AVR_ATmega324PA__" },
- { "atmega325", ARCH_AVR5, "__AVR_ATmega325__" },
- { "atmega325p", ARCH_AVR5, "__AVR_ATmega325P__" },
- { "atmega3250", ARCH_AVR5, "__AVR_ATmega3250__" },
- { "atmega3250p", ARCH_AVR5, "__AVR_ATmega3250P__" },
-+ { "atmega328", ARCH_AVR5, "__AVR_ATmega328__" },
- { "atmega328p", ARCH_AVR5, "__AVR_ATmega328P__" },
- { "atmega329", ARCH_AVR5, "__AVR_ATmega329__" },
- { "atmega329p", ARCH_AVR5, "__AVR_ATmega329P__" },
-+ { "atmega329pa", ARCH_AVR5, "__AVR_ATmega329PA__" },
- { "atmega3290", ARCH_AVR5, "__AVR_ATmega3290__" },
- { "atmega3290p", ARCH_AVR5, "__AVR_ATmega3290P__" },
-+ { "atmega32c1", ARCH_AVR5, "__AVR_ATmega32C1__" },
- { "atmega32hvb", ARCH_AVR5, "__AVR_ATmega32HVB__" },
-+ { "atmega32m1", ARCH_AVR5, "__AVR_ATmega32M1__" },
-+ { "atmega32u4", ARCH_AVR5, "__AVR_ATmega32U4__" },
-+ { "atmega32u6", ARCH_AVR5, "__AVR_ATmega32U6__" },
- { "atmega406", ARCH_AVR5, "__AVR_ATmega406__" },
- { "atmega64", ARCH_AVR5, "__AVR_ATmega64__" },
- { "atmega640", ARCH_AVR5, "__AVR_ATmega640__" },
- { "atmega644", ARCH_AVR5, "__AVR_ATmega644__" },
-+ { "atmega644a", ARCH_AVR5, "__AVR_ATmega644A__" },
- { "atmega644p", ARCH_AVR5, "__AVR_ATmega644P__" },
-+ { "atmega644pa", ARCH_AVR5, "__AVR_ATmega644PA__" },
- { "atmega645", ARCH_AVR5, "__AVR_ATmega645__" },
-+ { "atmega645a", ARCH_AVR5, "__AVR_ATmega645A__" },
-+ { "atmega645p", ARCH_AVR5, "__AVR_ATmega645P__" },
- { "atmega6450", ARCH_AVR5, "__AVR_ATmega6450__" },
-+ { "atmega6450a", ARCH_AVR5, "__AVR_ATmega6450A__" },
-+ { "atmega6450p", ARCH_AVR5, "__AVR_ATmega6450P__" },
- { "atmega649", ARCH_AVR5, "__AVR_ATmega649__" },
-+ { "atmega649a", ARCH_AVR5, "__AVR_ATmega649A__" },
-+ { "atmega649p", ARCH_AVR5, "__AVR_ATmega649P__" },
- { "atmega6490", ARCH_AVR5, "__AVR_ATmega6490__" },
-- { "atmega16hva", ARCH_AVR5, "__AVR_ATmega16HVA__" },
-+ { "atmega6490a", ARCH_AVR5, "__AVR_ATmega6490A__" },
-+ { "atmega6490p", ARCH_AVR5, "__AVR_ATmega6490P__" },
-+ { "atmega64c1", ARCH_AVR5, "__AVR_ATmega64C1__" },
-+ { "atmega64m1", ARCH_AVR5, "__AVR_ATmega64M1__" },
-+ { "atmega64hve", ARCH_AVR5, "__AVR_ATmega64HVE__" },
- { "at90can32", ARCH_AVR5, "__AVR_AT90CAN32__" },
- { "at90can64", ARCH_AVR5, "__AVR_AT90CAN64__" },
- { "at90pwm216", ARCH_AVR5, "__AVR_AT90PWM216__" },
- { "at90pwm316", ARCH_AVR5, "__AVR_AT90PWM316__" },
-+ { "at90scr100", ARCH_AVR5, "__AVR_AT90SCR100__" },
- { "at90usb646", ARCH_AVR5, "__AVR_AT90USB646__" },
- { "at90usb647", ARCH_AVR5, "__AVR_AT90USB647__" },
- { "at94k", ARCH_AVR5, "__AVR_AT94K__" },
-@@ -284,9 +337,13 @@
- { "atmega1280", ARCH_AVR51, "__AVR_ATmega1280__" },
- { "atmega1281", ARCH_AVR51, "__AVR_ATmega1281__" },
- { "atmega1284p", ARCH_AVR51, "__AVR_ATmega1284P__" },
-+ { "atmega128rfa1", ARCH_AVR51, "__AVR_ATmega128RFA1__" },
- { "at90can128", ARCH_AVR51, "__AVR_AT90CAN128__" },
- { "at90usb1286", ARCH_AVR51, "__AVR_AT90USB1286__" },
- { "at90usb1287", ARCH_AVR51, "__AVR_AT90USB1287__" },
-+ { "m3000f", ARCH_AVR51, "__AVR_M3000F__" },
-+ { "m3000s", ARCH_AVR51, "__AVR_M3000S__" },
-+ { "m3001b", ARCH_AVR51, "__AVR_M3001B__" },
- /* 3-Byte PC. */
- { "avr6", ARCH_AVR6, NULL },
- { "atmega2560", ARCH_AVR6, "__AVR_ATmega2560__" },
---- ./gcc/config/avr/avr.h~ 2010-03-05 17:15:55.000000000 +0100
-+++ ./gcc/config/avr/avr.h 2010-03-05 17:19:53.000000000 +0100
-@@ -803,67 +803,221 @@
- mmcu=at90s8*|\
- mmcu=at90c8*|\
- mmcu=at86rf401|\
-- mmcu=attiny13|\
-+ mmcu=ata6289|\
-+ mmcu=attiny13*|\
- mmcu=attiny2313|\
-+ mmcu=attiny2313a|\
- mmcu=attiny24|\
-+ mmcu=attiny24a|\
- mmcu=attiny25|\
- mmcu=attiny261|\
-- mmcu=attiny4*|\
-- mmcu=attiny8*: -m avr2}\
-+ mmcu=attiny261a|\
-+ mmcu=attiny4313|\
-+ mmcu=attiny43u|\
-+ mmcu=attiny44|\
-+ mmcu=attiny44a|\
-+ mmcu=attiny45|\
-+ mmcu=attiny461|\
-+ mmcu=attiny461a|\
-+ mmcu=attiny48|\
-+ mmcu=attiny84|\
-+ mmcu=attiny85|\
-+ mmcu=attiny861|\
-+ mmcu=attiny861a|\
-+ mmcu=attiny87|\
-+ mmcu=attiny88: -m avr2}\
- %{mmcu=atmega103|\
-- mmcu=at43*|\
-- mmcu=at76*|\
-+ mmcu=at43usb320|\
-+ mmcu=at43usb355|\
-+ mmcu=at76c711|\
- mmcu=at90usb82|\
-- mmcu=at90usb162: -m avr3}\
--%{mmcu=atmega8*|\
-- mmcu=atmega48*|\
-+ mmcu=at90usb162|\
-+ mmcu=atmega8u2|\
-+ mmcu=atmega16u2|\
-+ mmcu=atmega32u2|\
-+ mmcu=attiny167: -m avr3}\
-+%{mmcu=atmega8|\
-+ mmcu=atmega88|\
-+ mmcu=atmega88a|\
-+ mmcu=atmega88p|\
-+ mmcu=atmega88pa|\
-+ mmcu=atmega8515|\
-+ mmcu=atmega8535|\
-+ mmcu=atmega8hva|\
-+ mmcu=atmega8hvd|\
-+ mmcu=atmega48|\
-+ mmcu=atmega48a|\
-+ mmcu=atmega48p|\
-+ mmcu=atmega4hvd|\
- mmcu=at90pwm1|\
- mmcu=at90pwm2|\
- mmcu=at90pwm2b|\
- mmcu=at90pwm3|\
-- mmcu=at90pwm3b: -m avr4}\
--%{mmcu=atmega16*|\
-- mmcu=atmega32*|\
-+ mmcu=at90pwm3b|\
-+ mmcu=at90pwm81: -m avr4}\
-+%{mmcu=atmega16|\
-+ mmcu=atmega16a|\
-+ mmcu=atmega161|\
-+ mmcu=atmega162|\
-+ mmcu=atmega163|\
-+ mmcu=atmega164a|\
-+ mmcu=atmega164p|\
-+ mmcu=atmega165|\
-+ mmcu=atmega165a|\
-+ mmcu=atmega165p|\
-+ mmcu=atmega168|\
-+ mmcu=atmega168a|\
-+ mmcu=atmega168p|\
-+ mmcu=atmega169|\
-+ mmcu=atmega169a|\
-+ mmcu=atmega169p|\
-+ mmcu=atmega169pa|\
-+ mmcu=atmega16c1|\
-+ mmcu=atmega16hva|\
-+ mmcu=atmega16hva2|\
-+ mmcu=atmega16hvb|\
-+ mmcu=atmega16m1|\
-+ mmcu=atmega16u4|\
-+ mmcu=atmega32|\
-+ mmcu=atmega323|\
-+ mmcu=atmega324a|\
-+ mmcu=atmega324p|\
-+ mmcu=atmega324pa|\
-+ mmcu=atmega325|\
-+ mmcu=atmega325p|\
-+ mmcu=atmega3250|\
-+ mmcu=atmega3250p|\
-+ mmcu=atmega328|\
-+ mmcu=atmega328p|\
-+ mmcu=atmega329|\
-+ mmcu=atmega329p|\
-+ mmcu=atmega329pa|\
-+ mmcu=atmega3290|\
-+ mmcu=atmega3290p|\
-+ mmcu=atmega32c1|\
-+ mmcu=atmega32hvb|\
-+ mmcu=atmega32m1|\
-+ mmcu=atmega32u4|\
-+ mmcu=atmega32u6|\
- mmcu=atmega406|\
-- mmcu=atmega64*|\
-+ mmcu=atmega64|\
-+ mmcu=atmega640|\
-+ mmcu=atmega644|\
-+ mmcu=atmega644a|\
-+ mmcu=atmega644p|\
-+ mmcu=atmega644pa|\
-+ mmcu=atmega645|\
-+ mmcu=atmega645a|\
-+ mmcu=atmega645p|\
-+ mmcu=atmega6450|\
-+ mmcu=atmega6450a|\
-+ mmcu=atmega6450p|\
-+ mmcu=atmega649|\
-+ mmcu=atmega649a|\
-+ mmcu=atmega649p|\
-+ mmcu=atmega6490|\
-+ mmcu=atmega6490a|\
-+ mmcu=atmega6490p|\
-+ mmcu=atmega64c1|\
-+ mmcu=atmega64m1|\
-+ mmcu=atmega64hve|\
- mmcu=atmega128*|\
- mmcu=at90can*|\
- mmcu=at90pwm216|\
- mmcu=at90pwm316|\
-+ mmcu=atmega32c1|\
-+ mmcu=atmega32m1|\
-+ mmcu=atmega32u4|\
-+ mmcu=at90scr100|\
- mmcu=at90usb64*|\
- mmcu=at90usb128*|\
-- mmcu=at94k: -m avr5}\
-+ mmcu=at94k|\
-+ mmcu=m3000*|\
-+ mmcu=m3001*: -m avr5}\
- %{mmcu=atmega256*:-m avr6}\
--%{mmcu=atmega324*|\
-+%{mmcu=atmega324a|\
-+ mmcu=atmega324p|\
-+ mmcu=atmega324pa|\
- mmcu=atmega325*|\
-+ mmcu=atmega328|\
- mmcu=atmega328p|\
-- mmcu=atmega329*|\
-+ mmcu=atmega329|\
-+ mmcu=atmega329p|\
-+ mmcu=atmega329pa|\
-+ mmcu=atmega3290|\
-+ mmcu=atmega3290p|\
- mmcu=atmega406|\
-- mmcu=atmega48*|\
-- mmcu=atmega88*|\
-+ mmcu=atmega48|\
-+ mmcu=atmega48a|\
-+ mmcu=atmega48p|\
-+ mmcu=atmega88|\
-+ mmcu=atmega88a|\
-+ mmcu=atmega88p|\
-+ mmcu=atmega88pa|\
- mmcu=atmega64|\
-- mmcu=atmega644*|\
-- mmcu=atmega645*|\
-- mmcu=atmega649*|\
-+ mmcu=atmega644|\
-+ mmcu=atmega644a|\
-+ mmcu=atmega644p|\
-+ mmcu=atmega644pa|\
-+ mmcu=atmega645|\
-+ mmcu=atmega645p|\
-+ mmcu=atmega645a|\
-+ mmcu=atmega6450|\
-+ mmcu=atmega6450a|\
-+ mmcu=atmega6450p|\
-+ mmcu=atmega649|\
-+ mmcu=atmega649a|\
-+ mmcu=atmega649p|\
-+ mmcu=atmega6490|\
-+ mmcu=atmega6490a|\
-+ mmcu=atmega6490p|\
- mmcu=atmega128|\
- mmcu=atmega1284p|\
- mmcu=atmega162|\
-- mmcu=atmega164*|\
-- mmcu=atmega165*|\
-- mmcu=atmega168*|\
-- mmcu=atmega169*|\
-- mmcu=atmega8hva|\
-- mmcu=atmega16hva|\
-- mmcu=atmega32hvb|\
-+ mmcu=atmega164a|\
-+ mmcu=atmega164p|\
-+ mmcu=atmega165|\
-+ mmcu=atmega165a|\
-+ mmcu=atmega165p|\
-+ mmcu=atmega168|\
-+ mmcu=atmega168a|\
-+ mmcu=atmega168p|\
-+ mmcu=atmega169|\
-+ mmcu=atmega169a|\
-+ mmcu=atmega169p|\
-+ mmcu=atmega169pa|\
-+ mmcu=atmega4hv*|\
-+ mmcu=atmega8hv*|\
-+ mmcu=atmega16hv*|\
-+ mmcu=atmega32hv*|\
- mmcu=attiny48|\
- mmcu=attiny88|\
-+ mmcu=attiny87|\
-+ mmcu=attiny167|\
- mmcu=at90can*|\
- mmcu=at90pwm*|\
-+ mmcu=atmega16c1|\
-+ mmcu=atmega16m1|\
-+ mmcu=atmega32c1|\
-+ mmcu=atmega32m1|\
-+ mmcu=atmega64c1|\
-+ mmcu=atmega64m1|\
-+ mmcu=atmega16u4|\
-+ mmcu=atmega32u*|\
-+ mmcu=at90scr100|\
-+ mmcu=ata6289|\
-+ mmcu=atmega64hve|\
-+ mmcu=atmega8u2|\
-+ mmcu=atmega16u2|\
-+ mmcu=atmega32u2|\
- mmcu=at90usb*: -Tdata 0x800100}\
- %{mmcu=atmega640|\
- mmcu=atmega1280|\
- mmcu=atmega1281|\
-- mmcu=atmega256*: -Tdata 0x800200} "
-+ mmcu=atmega128rfa1|\
-+ mmcu=atmega256*: -Tdata 0x800200}\
-+%{mmcu=m3000*|\
-+ mmcu=m3001*: -Tdata 0x801000}"
-
- #define LIB_SPEC \
- "%{!mmcu=at90s1*:%{!mmcu=attiny11:%{!mmcu=attiny12:%{!mmcu=attiny15:%{!mmcu=attiny28: -lc }}}}}"
-@@ -898,30 +1052,47 @@
- %{mmcu=at90s8535:crts8535.o%s} \
- %{mmcu=at86rf401:crt86401.o%s} \
- %{mmcu=attiny13:crttn13.o%s} \
-+%{mmcu=attiny13a:crttn13a.o%s} \
- %{mmcu=attiny2313|mmcu=avr25:crttn2313.o%s} \
-+%{mmcu=attiny2313a:crttn2313a.o%s} \
- %{mmcu=attiny24:crttn24.o%s} \
-+%{mmcu=attiny24a:crttn24a.o%s} \
-+%{mmcu=attiny4313:crttn4313.o%s} \
- %{mmcu=attiny44:crttn44.o%s} \
-+%{mmcu=attiny44a:crttn44a.o%s} \
- %{mmcu=attiny84:crttn84.o%s} \
- %{mmcu=attiny25:crttn25.o%s} \
- %{mmcu=attiny45:crttn45.o%s} \
- %{mmcu=attiny85:crttn85.o%s} \
- %{mmcu=attiny261:crttn261.o%s} \
-+%{mmcu=attiny261a:crttn261a.o%s} \
- %{mmcu=attiny461:crttn461.o%s} \
-+%{mmcu=attiny461a:crttn461a.o%s} \
- %{mmcu=attiny861:crttn861.o%s} \
-+%{mmcu=attiny861a:crttn861a.o%s} \
- %{mmcu=attiny43u:crttn43u.o%s} \
- %{mmcu=attiny48:crttn48.o%s} \
- %{mmcu=attiny88:crttn88.o%s} \
-+%{mmcu=attiny87:crttn87.o%s} \
-+%{mmcu=ata6289:crta6289.o%s} \
- %{mmcu=at43usb320|mmcu=avr3:crt43320.o%s} \
- %{mmcu=at43usb355:crt43355.o%s} \
- %{mmcu=at76c711:crt76711.o%s} \
- %{mmcu=atmega103|mmcu=avr31:crtm103.o%s} \
- %{mmcu=at90usb162|mmcu=avr35:crtusb162.o%s} \
- %{mmcu=at90usb82:crtusb82.o%s} \
-+%{mmcu=atmega8u2:crtm8u2.o%s} \
-+%{mmcu=atmega16u2:crtm16u2.o%s} \
-+%{mmcu=atmega32u2:crtm32u2.o%s} \
-+%{mmcu=attiny167:crttn167.o%s} \
- %{mmcu=atmega8|mmcu=avr4:crtm8.o%s} \
- %{mmcu=atmega48:crtm48.o%s} \
-+%{mmcu=atmega48a:crtm48a.o%s} \
- %{mmcu=atmega48p:crtm48p.o%s} \
- %{mmcu=atmega88:crtm88.o%s} \
-+%{mmcu=atmega88a:crtm88a.o%s} \
- %{mmcu=atmega88p:crtm88p.o%s} \
-+%{mmcu=atmega88pa:crtm88pa.o%s} \
- %{mmcu=atmega8515:crtm8515.o%s} \
- %{mmcu=atmega8535:crtm8535.o%s} \
- %{mmcu=at90pwm1:crt90pwm1.o%s} \
-@@ -929,45 +1100,81 @@
- %{mmcu=at90pwm2b:crt90pwm2b.o%s} \
- %{mmcu=at90pwm3:crt90pwm3.o%s} \
- %{mmcu=at90pwm3b:crt90pwm3b.o%s} \
-+%{mmcu=at90pwm81:crt90pwm81.o%s} \
- %{mmcu=atmega16:crtm16.o%s} \
-+%{mmcu=atmega16a:crtm16a.o%s} \
- %{mmcu=atmega161|mmcu=avr5:crtm161.o%s} \
- %{mmcu=atmega162:crtm162.o%s} \
- %{mmcu=atmega163:crtm163.o%s} \
-+%{mmcu=atmega164a:crtm164a.o%s} \
- %{mmcu=atmega164p:crtm164p.o%s} \
- %{mmcu=atmega165:crtm165.o%s} \
-+%{mmcu=atmega165a:crtm165a.o%s} \
- %{mmcu=atmega165p:crtm165p.o%s} \
- %{mmcu=atmega168:crtm168.o%s} \
-+%{mmcu=atmega168a:crtm168a.o%s} \
- %{mmcu=atmega168p:crtm168p.o%s} \
- %{mmcu=atmega169:crtm169.o%s} \
-+%{mmcu=atmega169a:crtm169a.o%s} \
- %{mmcu=atmega169p:crtm169p.o%s} \
-+%{mmcu=atmega169pa:crtm169pa.o%s} \
- %{mmcu=atmega32:crtm32.o%s} \
- %{mmcu=atmega323:crtm323.o%s} \
-+%{mmcu=atmega324a:crtm324a.o%s} \
- %{mmcu=atmega324p:crtm324p.o%s} \
-+%{mmcu=atmega324pa:crtm324pa.o%s} \
- %{mmcu=atmega325:crtm325.o%s} \
- %{mmcu=atmega325p:crtm325p.o%s} \
- %{mmcu=atmega3250:crtm3250.o%s} \
- %{mmcu=atmega3250p:crtm3250p.o%s} \
-+%{mmcu=atmega328:crtm328.o%s} \
- %{mmcu=atmega328p:crtm328p.o%s} \
- %{mmcu=atmega329:crtm329.o%s} \
- %{mmcu=atmega329p:crtm329p.o%s} \
-+%{mmcu=atmega329pa:crtm329pa.o%s} \
- %{mmcu=atmega3290:crtm3290.o%s} \
- %{mmcu=atmega3290p:crtm3290p.o%s} \
--%{mmcu=atmega32hvb:crtm32hvb.o%s} \
- %{mmcu=atmega406:crtm406.o%s} \
- %{mmcu=atmega64:crtm64.o%s} \
- %{mmcu=atmega640:crtm640.o%s} \
- %{mmcu=atmega644:crtm644.o%s} \
-+%{mmcu=atmega644a:crtm644a.o%s} \
- %{mmcu=atmega644p:crtm644p.o%s} \
-+%{mmcu=atmega644pa:crtm644pa.o%s} \
- %{mmcu=atmega645:crtm645.o%s} \
-+%{mmcu=atmega645a:crtm645a.o%s} \
-+%{mmcu=atmega645p:crtm645p.o%s} \
- %{mmcu=atmega6450:crtm6450.o%s} \
-+%{mmcu=atmega6450a:crtm6450a.o%s} \
-+%{mmcu=atmega6450p:crtm6450p.o%s} \
- %{mmcu=atmega649:crtm649.o%s} \
-+%{mmcu=atmega649a:crtm649a.o%s} \
-+%{mmcu=atmega649p:crtm649p.o%s} \
- %{mmcu=atmega6490:crtm6490.o%s} \
-+%{mmcu=atmega6490a:crtm6490a.o%s} \
-+%{mmcu=atmega6490p:crtm6490p.o%s} \
-+%{mmcu=atmega64hve:crtm64hve.o%s} \
- %{mmcu=atmega8hva:crtm8hva.o%s} \
- %{mmcu=atmega16hva:crtm16hva.o%s} \
-+%{mmcu=atmega16hva2:crtm16hva2.o%s} \
-+%{mmcu=atmega16hvb:crtm16hvb.o%s} \
-+%{mmcu=atmega32hvb:crtm32hvb.o%s} \
-+%{mmcu=atmega4hvd:crtm4hvd.o%s} \
-+%{mmcu=atmega8hvd:crtm8hvd.o%s} \
- %{mmcu=at90can32:crtcan32.o%s} \
- %{mmcu=at90can64:crtcan64.o%s} \
- %{mmcu=at90pwm216:crt90pwm216.o%s} \
- %{mmcu=at90pwm316:crt90pwm316.o%s} \
-+%{mmcu=atmega16c1:crtm16c1.o%s} \
-+%{mmcu=atmega16m1:crtm16m1.o%s} \
-+%{mmcu=atmega16u4:crtm16u4.o%s} \
-+%{mmcu=atmega32c1:crtm32c1.o%s} \
-+%{mmcu=atmega32m1:crtm32m1.o%s} \
-+%{mmcu=atmega32u4:crtm32u4.o%s} \
-+%{mmcu=atmega32u6:crtm32u6.o%s} \
-+%{mmcu=atmega64c1:crtm64c1.o%s} \
-+%{mmcu=atmega64m1:crtm64m1.o%s} \
-+%{mmcu=at90scr100:crt90scr100.o%s} \
- %{mmcu=at90usb646:crtusb646.o%s} \
- %{mmcu=at90usb647:crtusb647.o%s} \
- %{mmcu=at94k:crtat94k.o%s} \
-@@ -975,11 +1182,15 @@
- %{mmcu=atmega1280:crtm1280.o%s} \
- %{mmcu=atmega1281:crtm1281.o%s} \
- %{mmcu=atmega1284p:crtm1284p.o%s} \
--%{mmcu=atmega2560:crtm2560.o%s} \
--%{mmcu=atmega2561:crtm2561.o%s} \
-+%{mmcu=atmega128rfa1:crtm128rfa1.o%s} \
- %{mmcu=at90can128:crtcan128.o%s} \
- %{mmcu=at90usb1286:crtusb1286.o%s} \
--%{mmcu=at90usb1287:crtusb1287.o%s}"
-+%{mmcu=at90usb1287:crtusb1287.o%s} \
-+%{mmcu=m3000f:crtm3000f.o%s} \
-+%{mmcu=m3000s:crtm3000s.o%s} \
-+%{mmcu=m3001b:crtm3001b.o%s} \
-+%{mmcu=atmega2560|mmcu=avr6:crtm2560.o%s} \
-+%{mmcu=atmega2561:crtm2561.o%s}"
-
- #define EXTRA_SPECS {"crt_binutils", CRT_BINUTILS_SPECS},
-
---- ./gcc/config/avr/t-avr~ 2010-03-05 17:15:38.000000000 +0100
-+++ ./gcc/config/avr/t-avr 2010-03-05 17:20:12.000000000 +0100
-@@ -42,19 +42,29 @@
-
- # The many avr2 matches are not listed here - this is the default.
- MULTILIB_MATCHES = \
-+ mmcu?avr25=mmcu?ata6289 \
- mmcu?avr25=mmcu?attiny13 \
-+ mmcu?avr25=mmcu?attiny13a \
- mmcu?avr25=mmcu?attiny2313 \
-+ mmcu?avr25=mmcu?attiny2313a \
- mmcu?avr25=mmcu?attiny24 \
-- mmcu?avr25=mmcu?attiny44 \
-- mmcu?avr25=mmcu?attiny84 \
-+ mmcu?avr25=mmcu?attiny24a \
- mmcu?avr25=mmcu?attiny25 \
-- mmcu?avr25=mmcu?attiny45 \
-- mmcu?avr25=mmcu?attiny85 \
- mmcu?avr25=mmcu?attiny261 \
-- mmcu?avr25=mmcu?attiny461 \
-- mmcu?avr25=mmcu?attiny861 \
-+ mmcu?avr25=mmcu?attiny261a \
-+ mmcu?avr25=mmcu?attiny4313 \
- mmcu?avr25=mmcu?attiny43u \
-+ mmcu?avr25=mmcu?attiny44 \
-+ mmcu?avr25=mmcu?attiny44a \
-+ mmcu?avr25=mmcu?attiny45 \
-+ mmcu?avr25=mmcu?attiny461 \
-+ mmcu?avr25=mmcu?attiny461a \
- mmcu?avr25=mmcu?attiny48 \
-+ mmcu?avr25=mmcu?attiny84 \
-+ mmcu?avr25=mmcu?attiny85 \
-+ mmcu?avr25=mmcu?attiny861 \
-+ mmcu?avr25=mmcu?attiny861a \
-+ mmcu?avr25=mmcu?attiny87 \
- mmcu?avr25=mmcu?attiny88 \
- mmcu?avr25=mmcu?at86rf401 \
- mmcu?avr3=mmcu?at43usb320 \
-@@ -63,57 +73,100 @@
- mmcu?avr31=mmcu?atmega103 \
- mmcu?avr35=mmcu?at90usb82 \
- mmcu?avr35=mmcu?at90usb162 \
-+ mmcu?avr35=mmcu?atmega8u2 \
-+ mmcu?avr35=mmcu?atmega16u2 \
-+ mmcu?avr35=mmcu?atmega32u2 \
-+ mmcu?avr35=mmcu?attiny167 \
- mmcu?avr4=mmcu?atmega48 \
-+ mmcu?avr4=mmcu?atmega48a \
- mmcu?avr4=mmcu?atmega48p \
- mmcu?avr4=mmcu?atmega8 \
- mmcu?avr4=mmcu?atmega8515 \
- mmcu?avr4=mmcu?atmega8535 \
- mmcu?avr4=mmcu?atmega88 \
-+ mmcu?avr4=mmcu?atmega88a \
- mmcu?avr4=mmcu?atmega88p \
-+ mmcu?avr4=mmcu?atmega88pa \
- mmcu?avr4=mmcu?atmega8hva \
-+ mmcu?avr4=mmcu?atmega4hvd \
-+ mmcu?avr4=mmcu?atmega8hvd \
- mmcu?avr4=mmcu?at90pwm1 \
- mmcu?avr4=mmcu?at90pwm2 \
- mmcu?avr4=mmcu?at90pwm2b \
- mmcu?avr4=mmcu?at90pwm3 \
- mmcu?avr4=mmcu?at90pwm3b \
-+ mmcu?avr4=mmcu?at90pwm81 \
- mmcu?avr5=mmcu?atmega16 \
-+ mmcu?avr5=mmcu?atmega16a \
- mmcu?avr5=mmcu?atmega161 \
- mmcu?avr5=mmcu?atmega162 \
- mmcu?avr5=mmcu?atmega163 \
-+ mmcu?avr5=mmcu?atmega164a \
- mmcu?avr5=mmcu?atmega164p \
- mmcu?avr5=mmcu?atmega165 \
-+ mmcu?avr5=mmcu?atmega165a \
- mmcu?avr5=mmcu?atmega165p \
- mmcu?avr5=mmcu?atmega168 \
-+ mmcu?avr5=mmcu?atmega168a \
- mmcu?avr5=mmcu?atmega168p \
- mmcu?avr5=mmcu?atmega169 \
-+ mmcu?avr5=mmcu?atmega169a \
- mmcu?avr5=mmcu?atmega169p \
-+ mmcu?avr5=mmcu?atmega169pa \
- mmcu?avr5=mmcu?atmega32 \
- mmcu?avr5=mmcu?atmega323 \
-+ mmcu?avr5=mmcu?atmega324a \
- mmcu?avr5=mmcu?atmega324p \
-+ mmcu?avr5=mmcu?atmega324pa \
- mmcu?avr5=mmcu?atmega325 \
- mmcu?avr5=mmcu?atmega325p \
- mmcu?avr5=mmcu?atmega3250 \
- mmcu?avr5=mmcu?atmega3250p \
-+ mmcu?avr5=mmcu?atmega328 \
- mmcu?avr5=mmcu?atmega328p \
- mmcu?avr5=mmcu?atmega329 \
- mmcu?avr5=mmcu?atmega329p \
-+ mmcu?avr5=mmcu?atmega329pa \
- mmcu?avr5=mmcu?atmega3290 \
- mmcu?avr5=mmcu?atmega3290p \
-- mmcu?avr5=mmcu?atmega32hvb \
- mmcu?avr5=mmcu?atmega406 \
- mmcu?avr5=mmcu?atmega64 \
- mmcu?avr5=mmcu?atmega640 \
- mmcu?avr5=mmcu?atmega644 \
-+ mmcu?avr5=mmcu?atmega644a \
- mmcu?avr5=mmcu?atmega644p \
-+ mmcu?avr5=mmcu?atmega644pa \
- mmcu?avr5=mmcu?atmega645 \
-+ mmcu?avr5=mmcu?atmega645a \
-+ mmcu?avr5=mmcu?atmega645p \
- mmcu?avr5=mmcu?atmega6450 \
-+ mmcu?avr5=mmcu?atmega6450a \
-+ mmcu?avr5=mmcu?atmega6450p \
- mmcu?avr5=mmcu?atmega649 \
-+ mmcu?avr5=mmcu?atmega649a \
-+ mmcu?avr5=mmcu?atmega649p \
- mmcu?avr5=mmcu?atmega6490 \
-+ mmcu?avr5=mmcu?atmega6490a \
-+ mmcu?avr5=mmcu?atmega6490p \
- mmcu?avr5=mmcu?atmega16hva \
-+ mmcu?avr5=mmcu?atmega16hva2 \
-+ mmcu?avr5=mmcu?atmega16hvb \
-+ mmcu?avr5=mmcu?atmega32hvb \
- mmcu?avr5=mmcu?at90can32 \
- mmcu?avr5=mmcu?at90can64 \
- mmcu?avr5=mmcu?at90pwm216 \
- mmcu?avr5=mmcu?at90pwm316 \
-+ mmcu?avr5=mmcu?atmega16c1 \
-+ mmcu?avr5=mmcu?atmega16m1 \
-+ mmcu?avr5=mmcu?atmega16u4 \
-+ mmcu?avr5=mmcu?atmega32c1 \
-+ mmcu?avr5=mmcu?atmega32m1 \
-+ mmcu?avr5=mmcu?atmega32u4 \
-+ mmcu?avr5=mmcu?atmega32u6 \
-+ mmcu?avr5=mmcu?atmega64c1 \
-+ mmcu?avr5=mmcu?atmega64m1 \
-+ mmcu?avr5=mmcu?atmega64hve \
-+ mmcu?avr5=mmcu?at90scr100 \
- mmcu?avr5=mmcu?at90usb646 \
- mmcu?avr5=mmcu?at90usb647 \
- mmcu?avr5=mmcu?at94k \
-@@ -121,12 +174,15 @@
- mmcu?avr51=mmcu?atmega1280 \
- mmcu?avr51=mmcu?atmega1281 \
- mmcu?avr51=mmcu?atmega1284p \
-+ mmcu?avr51=mmcu?atmega128rfa1 \
- mmcu?avr51=mmcu?at90can128 \
- mmcu?avr51=mmcu?at90usb1286 \
- mmcu?avr51=mmcu?at90usb1287 \
-- mmcu?avr6=mmcu?atmega2560 \
-- mmcu?avr6=mmcu?atmega2561
--
-+ mmcu?avr51=mmcu?m3000f \
-+ mmcu?avr51=mmcu?m3000s \
-+ mmcu?avr51=mmcu?m3001b \
-+ mmcu?avr6=mmcu?atmega2560 \
-+ mmcu?avr6=mmcu?atmega2561
- MULTILIB_EXCEPTIONS =
-
- LIBGCC = stmp-multilib
+++ /dev/null
---- ./gcc/config/avr/avr.c.orig 2010-03-05 18:01:20.000000000 +0100
-+++ ./gcc/config/avr/avr.c 2010-03-05 18:01:51.000000000 +0100
-@@ -57,6 +57,7 @@
- static int signal_function_p (tree);
- static int nmi_function_p (tree);
- static int avr_OS_task_function_p (tree);
-+static int avr_OS_main_function_p (tree);
- static int avr_regs_to_save (HARD_REG_SET *);
- static int sequent_regs_live (void);
- static const char *ptrreg_to_str (int);
-@@ -603,6 +604,19 @@
- return a != NULL_TREE;
- }
-
-+/* Return nonzero if FUNC is a OS_main function. */
-+
-+static int
-+avr_OS_main_function_p (tree func)
-+{
-+ tree a;
-+
-+ gcc_assert (TREE_CODE (func) == FUNCTION_DECL);
-+
-+ a = lookup_attribute ("OS_main", TYPE_ATTRIBUTES (TREE_TYPE (func)));
-+ return a != NULL_TREE;
-+}
-+
- /* Return the number of hard registers to push/pop in the prologue/epilogue
- of the current function, and optionally store these registers in SET. */
-
-@@ -621,9 +635,10 @@
- count = 0;
-
- /* No need to save any registers if the function never returns or
-- is have "OS_task" attribute. */
-+ is have "OS_task" or "OS_main" attribute. */
- if (TREE_THIS_VOLATILE (current_function_decl)
-- || cfun->machine->is_OS_task)
-+ || cfun->machine->is_OS_task
-+ || cfun->machine->is_OS_main)
- return 0;
-
- for (reg = 0; reg < 32; reg++)
-@@ -742,6 +757,8 @@
- rtx pushword = gen_rtx_MEM (HImode,
- gen_rtx_POST_DEC (HImode, stack_pointer_rtx));
- rtx insn;
-+ int method1_length;
-+ int sp_plus_length;
-
- last_insn_address = 0;
-
-@@ -751,6 +768,7 @@
- cfun->machine->is_signal = signal_function_p (current_function_decl);
- cfun->machine->is_nmi = nmi_function_p (current_function_decl);
- cfun->machine->is_OS_task = avr_OS_task_function_p (current_function_decl);
-+ cfun->machine->is_OS_main = avr_OS_main_function_p (current_function_decl);
-
- /* Prologue: naked. */
- if (cfun->machine->is_naked)
-@@ -764,6 +782,7 @@
- && !cfun->machine->is_interrupt
- && !cfun->machine->is_signal
- && !cfun->machine->is_OS_task
-+ && !cfun->machine->is_OS_main
- && live_seq);
-
- if (cfun->machine->is_interrupt || cfun->machine->is_signal)
-@@ -903,7 +922,7 @@
- }
- if (frame_pointer_needed)
- {
-- if(!cfun->machine->is_OS_task)
-+ if (!(cfun->machine->is_OS_task || cfun->machine->is_OS_main))
- {
- /* Push frame pointer. */
- insn = emit_move_insn (pushword, frame_pointer_rtx);
-@@ -933,7 +952,7 @@
- if (TARGET_TINY_STACK)
- {
- if (size < -63 || size > 63)
-- warning (0, "large frame pointer change (%d) with -mtiny-stack", size);
-+ warning (0, "large frame pointer change (%ld) with -mtiny-stack", size);
-
- /* The high byte (r29) doesn't change - prefer 'subi' (1 cycle)
- over 'sbiw' (2 cycles, same size). */
-@@ -945,7 +964,6 @@
- myfp = frame_pointer_rtx;
- }
- /* Calculate length. */
-- int method1_length;
- method1_length =
- get_attr_length (gen_move_insn (frame_pointer_rtx, stack_pointer_rtx));
- method1_length +=
-@@ -1043,6 +1061,7 @@
- HARD_REG_SET set;
- int minimize;
- HOST_WIDE_INT size = get_frame_size();
-+ int sp_plus_length;
-
- /* epilogue: naked */
- if (cfun->machine->is_naked)
-@@ -1057,6 +1076,7 @@
- && !cfun->machine->is_interrupt
- && !cfun->machine->is_signal
- && !cfun->machine->is_OS_task
-+ && !cfun->machine->is_OS_main
- && live_seq);
-
- if (minimize && (frame_pointer_needed || live_seq > 4))
-@@ -1119,7 +1139,7 @@
- emit_move_insn (stack_pointer_rtx, frame_pointer_rtx);
- }
- }
-- if(!cfun->machine->is_OS_task)
-+ if (!(cfun->machine->is_OS_task || cfun->machine->is_OS_main))
- {
- /* Restore previous frame_pointer. */
- emit_insn (gen_pophi (frame_pointer_rtx));
-@@ -1939,10 +1959,18 @@
- }
- /* Use simple load of stack pointer if no interrupts are used
- or inside main or signal function prologue where they disabled. */
-- else if (TARGET_NO_INTERRUPTS
-+ else if ((!AVR_XMEGA && TARGET_NO_INTERRUPTS)
- || (!AVR_XMEGA
-- && reload_completed
-+ && reload_completed
- && cfun->machine->is_signal
-+ && prologue_epilogue_contains (insn))
-+ || (!AVR_XMEGA
-+ && reload_completed
-+ && cfun->machine->is_OS_main
-+ && prologue_contains (insn))
-+ || (AVR_XMEGA
-+ && reload_completed
-+ && cfun->machine->is_nmi
- && prologue_epilogue_contains (insn)))
- {
- *l = 2;
-@@ -4969,6 +4997,7 @@
- { "nmi", 0, 0, true, false, false, avr_handle_fndecl_attribute },
- { "naked", 0, 0, false, true, true, avr_handle_fntype_attribute },
- { "OS_task", 0, 0, false, true, true, avr_handle_fntype_attribute },
-+ { "OS_main", 0, 0, false, true, true, avr_handle_fntype_attribute },
- { NULL, 0, 0, false, false, false, NULL }
- };
-
---- ./gcc/config/avr/avr.h.orig 2010-03-05 18:01:20.000000000 +0100
-+++ ./gcc/config/avr/avr.h 2010-03-05 18:01:51.000000000 +0100
-@@ -1320,4 +1320,8 @@
- /* 'true' - if current function is a task function
- as specified by the "OS_task" attribute. */
- int is_OS_task;
-+
-+ /* 'true' - if current function is a 'main' function
-+ as specified by the "OS_main" attribute. */
-+ int is_OS_main;
- };
---- ./gcc/function.c.orig 2009-06-19 23:44:24.000000000 +0200
-+++ ./gcc/function.c 2010-03-05 18:01:51.000000000 +0100
-@@ -4757,6 +4757,14 @@
- }
-
- int
-+prologue_contains (const_rtx insn)
-+{
-+ if (contains (insn, &prologue))
-+ return 1;
-+ return 0;
-+}
-+
-+int
- prologue_epilogue_contains (const_rtx insn)
- {
- if (contains (insn, &prologue))
---- ./gcc/rtl.h.orig 2009-07-14 11:32:55.000000000 +0200
-+++ ./gcc/rtl.h 2010-03-05 18:01:51.000000000 +0100
-@@ -2145,6 +2145,7 @@
-
- /* In function.c */
- extern void reposition_prologue_and_epilogue_notes (void);
-+extern int prologue_contains (const_rtx);
- extern int prologue_epilogue_contains (const_rtx);
- extern int sibcall_epilogue_contains (const_rtx);
- extern void mark_temp_addr_taken (rtx);
+++ /dev/null
---- gcc/config/avr/avr.c.orig 2010-03-05 17:21:19.000000000 +0100
-+++ gcc/config/avr/avr.c 2010-03-05 17:22:02.000000000 +0100
-@@ -46,6 +46,7 @@
- #include "tm_p.h"
- #include "target.h"
- #include "target-def.h"
-+#include "params.h"
- #include "df.h"
-
- /* Maximal allowed offset for an address in the LD command */
-@@ -419,6 +420,9 @@
-
- flag_delete_null_pointer_checks = 0;
-
-+ if (!PARAM_SET_P (PARAM_INLINE_CALL_COST))
-+ set_param_value ("inline-call-cost", 5);
-+
- for (t = avr_mcu_types; t->name; t++)
- if (strcmp (t->name, avr_mcu_name) == 0)
- break;
+++ /dev/null
---- ./gcc/config/avr/avr.c.orig 2010-03-08 12:55:13.000000000 +0100
-+++ ./gcc/config/avr/avr.c 2010-03-08 12:55:36.000000000 +0100
-@@ -55,6 +55,7 @@
- static int avr_naked_function_p (tree);
- static int interrupt_function_p (tree);
- static int signal_function_p (tree);
-+static int nmi_function_p (tree);
- static int avr_OS_task_function_p (tree);
- static int avr_regs_to_save (HARD_REG_SET *);
- static int sequent_regs_live (void);
-@@ -131,17 +132,24 @@
- int avr_have_movw_lpmx_p = 0;
-
- static const struct base_arch_s avr_arch_types[] = {
-- { 1, 0, 0, 0, 0, 0, 0, 0, NULL }, /* unknown device specified */
-- { 1, 0, 0, 0, 0, 0, 0, 0, "__AVR_ARCH__=1" },
-- { 0, 0, 0, 0, 0, 0, 0, 0, "__AVR_ARCH__=2" },
-- { 0, 0, 0, 1, 0, 0, 0, 0, "__AVR_ARCH__=25" },
-- { 0, 0, 1, 0, 0, 0, 0, 0, "__AVR_ARCH__=3" },
-- { 0, 0, 1, 0, 1, 0, 0, 0, "__AVR_ARCH__=31" },
-- { 0, 0, 1, 1, 0, 0, 0, 0, "__AVR_ARCH__=35" },
-- { 0, 1, 0, 1, 0, 0, 0, 0, "__AVR_ARCH__=4" },
-- { 0, 1, 1, 1, 0, 0, 0, 0, "__AVR_ARCH__=5" },
-- { 0, 1, 1, 1, 1, 1, 0, 0, "__AVR_ARCH__=51" },
-- { 0, 1, 1, 1, 1, 1, 1, 0, "__AVR_ARCH__=6" }
-+ { 1, 0, 0, 0, 0, 0, 0, 0, 0, NULL }, /* Unknown device specified. */
-+ { 1, 0, 0, 0, 0, 0, 0, 0, 0, "__AVR_ARCH__=1" },
-+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, "__AVR_ARCH__=2" },
-+ { 0, 0, 0, 1, 0, 0, 0, 0, 0, "__AVR_ARCH__=25" },
-+ { 0, 0, 1, 0, 0, 0, 0, 0, 0, "__AVR_ARCH__=3" },
-+ { 0, 0, 1, 0, 1, 0, 0, 0, 0, "__AVR_ARCH__=31" },
-+ { 0, 0, 1, 1, 0, 0, 0, 0, 0, "__AVR_ARCH__=35" },
-+ { 0, 1, 0, 1, 0, 0, 0, 0, 0, "__AVR_ARCH__=4" },
-+ { 0, 1, 1, 1, 0, 0, 0, 0, 0, "__AVR_ARCH__=5" },
-+ { 0, 1, 1, 1, 1, 1, 0, 0, 0, "__AVR_ARCH__=51" },
-+ { 0, 1, 1, 1, 1, 1, 1, 0, 0, "__AVR_ARCH__=6" },
-+ { 0, 1, 0, 1, 0, 0, 0, 1, 0, "__AVR_ARCH__=101" },
-+ { 0, 1, 1, 1, 0, 0, 0, 1, 0, "__AVR_ARCH__=102" },
-+ { 0, 1, 1, 1, 0, 0, 0, 1, 1, "__AVR_ARCH__=103" },
-+ { 0, 1, 1, 1, 1, 1, 0, 1, 0, "__AVR_ARCH__=104" },
-+ { 0, 1, 1, 1, 1, 1, 0, 1, 1, "__AVR_ARCH__=105" },
-+ { 0, 1, 1, 1, 1, 1, 1, 1, 0, "__AVR_ARCH__=106" },
-+ { 0, 1, 1, 1, 1, 1, 1, 1, 1, "__AVR_ARCH__=107" }
- };
-
- /* These names are used as the index into the avr_arch_types[] table
-@@ -159,7 +167,14 @@
- ARCH_AVR4,
- ARCH_AVR5,
- ARCH_AVR51,
-- ARCH_AVR6
-+ ARCH_AVR6,
-+ ARCH_AVRXMEGA1,
-+ ARCH_AVRXMEGA2,
-+ ARCH_AVRXMEGA3,
-+ ARCH_AVRXMEGA4,
-+ ARCH_AVRXMEGA5,
-+ ARCH_AVRXMEGA6,
-+ ARCH_AVRXMEGA7
- };
-
- struct mcu_type_s {
-@@ -349,6 +364,35 @@
- { "avr6", ARCH_AVR6, NULL },
- { "atmega2560", ARCH_AVR6, "__AVR_ATmega2560__" },
- { "atmega2561", ARCH_AVR6, "__AVR_ATmega2561__" },
-+ /* Enhanced, == 256K. */
-+ /* Xmega, <= 8K FLASH. */
-+ /* Xmega, > 8K, <= 64K FLASH, <= 64K RAM. */
-+ { "avrxmega2", ARCH_AVRXMEGA2, NULL },
-+ { "atxmega16a4", ARCH_AVRXMEGA2, "__AVR_ATxmega16A4__" },
-+ { "atxmega16d4", ARCH_AVRXMEGA2, "__AVR_ATxmega16D4__" },
-+ { "atxmega32d4", ARCH_AVRXMEGA2, "__AVR_ATxmega32D4__" },
-+ /* Xmega, > 8K, <= 64K FLASH, > 64K RAM. */
-+ { "avrxmega3", ARCH_AVRXMEGA3, NULL },
-+ { "atxmega32a4", ARCH_AVRXMEGA3, "__AVR_ATxmega32A4__" },
-+ /* Xmega, > 64K, <= 128K FLASH, <= 64K RAM. */
-+ { "avrxmega4", ARCH_AVRXMEGA4, NULL },
-+ { "atxmega64a3", ARCH_AVRXMEGA4, "__AVR_ATxmega64A3__" },
-+ { "atxmega64d3", ARCH_AVRXMEGA4, "__AVR_ATxmega64D3__" },
-+ /* Xmega, > 64K, <= 128K FLASH, > 64K RAM. */
-+ { "avrxmega5", ARCH_AVRXMEGA5, NULL },
-+ { "atxmega64a1", ARCH_AVRXMEGA5, "__AVR_ATxmega64A1__" },
-+ /* Xmega, > 128K, <= 256K FLASH, <= 64K RAM. */
-+ { "avrxmega6", ARCH_AVRXMEGA6, NULL },
-+ { "atxmega128a3", ARCH_AVRXMEGA6, "__AVR_ATxmega128A3__" },
-+ { "atxmega128d3", ARCH_AVRXMEGA6, "__AVR_ATxmega128D3__" },
-+ { "atxmega192a3", ARCH_AVRXMEGA6, "__AVR_ATxmega192A3__" },
-+ { "atxmega192d3", ARCH_AVRXMEGA6, "__AVR_ATxmega192D3__" },
-+ { "atxmega256a3", ARCH_AVRXMEGA6, "__AVR_ATxmega256A3__" },
-+ { "atxmega256a3b",ARCH_AVRXMEGA6, "__AVR_ATxmega256A3B__" },
-+ { "atxmega256d3", ARCH_AVRXMEGA6, "__AVR_ATxmega256D3__" },
-+ /* Xmega, > 128K, <= 256K FLASH, > 64K RAM. */
-+ { "avrxmega7", ARCH_AVRXMEGA7, NULL },
-+ { "atxmega128a1", ARCH_AVRXMEGA7, "__AVR_ATxmega128A1__" },
- /* Assembler only. */
- { "avr1", ARCH_AVR1, NULL },
- { "at90s1200", ARCH_AVR1, "__AVR_AT90S1200__" },
-@@ -531,6 +575,21 @@
- return a != NULL_TREE;
- }
-
-+/* Return nonzero if FUNC is a nmi function as specified
-+ by the "nmi" attribute. */
-+
-+static int
-+nmi_function_p (tree func)
-+{
-+ tree a;
-+
-+ if (TREE_CODE (func) != FUNCTION_DECL)
-+ return 0;
-+
-+ a = lookup_attribute ("nmi", DECL_ATTRIBUTES (func));
-+ return a != NULL_TREE;
-+}
-+
- /* Return nonzero if FUNC is a OS_task function. */
-
- static int
-@@ -690,6 +749,7 @@
- cfun->machine->is_naked = avr_naked_function_p (current_function_decl);
- cfun->machine->is_interrupt = interrupt_function_p (current_function_decl);
- cfun->machine->is_signal = signal_function_p (current_function_decl);
-+ cfun->machine->is_nmi = nmi_function_p (current_function_decl);
- cfun->machine->is_OS_task = avr_OS_task_function_p (current_function_decl);
-
- /* Prologue: naked. */
-@@ -725,17 +785,48 @@
-
- /* Push SREG. */
- insn = emit_move_insn (tmp_reg_rtx,
-- gen_rtx_MEM (QImode, GEN_INT (SREG_ADDR)));
-+ gen_rtx_MEM (QImode, GEN_INT (AVR_SREG_ADDR)));
- RTX_FRAME_RELATED_P (insn) = 1;
- insn = emit_move_insn (pushbyte, tmp_reg_rtx);
- RTX_FRAME_RELATED_P (insn) = 1;
-
-+ /* Push RAMPD, RAMPX, RAMPY. */
-+ if (AVR_HAVE_RAMPX_Y_D)
-+ {
-+ /* Push RAMPD. */
-+ insn = emit_move_insn (tmp_reg_rtx,
-+ gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPD_ADDR)));
-+ RTX_FRAME_RELATED_P (insn) = 1;
-+ insn = emit_move_insn (pushbyte, tmp_reg_rtx);
-+ RTX_FRAME_RELATED_P (insn) = 1;
-+
-+ /* Push RAMPX. */
-+ if (TEST_HARD_REG_BIT (set, REG_X) && TEST_HARD_REG_BIT (set, REG_X + 1))
-+ {
-+ insn = emit_move_insn (tmp_reg_rtx,
-+ gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPX_ADDR)));
-+ RTX_FRAME_RELATED_P (insn) = 1;
-+ insn = emit_move_insn (pushbyte, tmp_reg_rtx);
-+ RTX_FRAME_RELATED_P (insn) = 1;
-+ }
-+
-+ /* Push RAMPY. */
-+ if (TEST_HARD_REG_BIT (set, REG_Y) && TEST_HARD_REG_BIT (set, REG_Y + 1))
-+ {
-+ insn = emit_move_insn (tmp_reg_rtx,
-+ gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPY_ADDR)));
-+ RTX_FRAME_RELATED_P (insn) = 1;
-+ insn = emit_move_insn (pushbyte, tmp_reg_rtx);
-+ RTX_FRAME_RELATED_P (insn) = 1;
-+ }
-+ }
-+
- /* Push RAMPZ. */
- if(AVR_HAVE_RAMPZ
- && (TEST_HARD_REG_BIT (set, REG_Z) && TEST_HARD_REG_BIT (set, REG_Z + 1)))
- {
- insn = emit_move_insn (tmp_reg_rtx,
-- gen_rtx_MEM (QImode, GEN_INT (RAMPZ_ADDR)));
-+ gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPZ_ADDR)));
- RTX_FRAME_RELATED_P (insn) = 1;
- insn = emit_move_insn (pushbyte, tmp_reg_rtx);
- RTX_FRAME_RELATED_P (insn) = 1;
-@@ -744,9 +835,46 @@
- /* Clear zero reg. */
- insn = emit_move_insn (zero_reg_rtx, const0_rtx);
- RTX_FRAME_RELATED_P (insn) = 1;
--
-+
- /* Prevent any attempt to delete the setting of ZERO_REG! */
- emit_insn (gen_rtx_USE (VOIDmode, zero_reg_rtx));
-+
-+ /*
-+ Clear RAMP? registers if used for data access in the interrupt/signal
-+ context. Do this after the zero register has been explictly cleared.
-+ */
-+ if (AVR_HAVE_RAMPX_Y_D)
-+ {
-+ /* Set RAMPD to 0. */
-+ insn = emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPD_ADDR)),
-+ const0_rtx);
-+ RTX_FRAME_RELATED_P (insn) = 1;
-+
-+ if (TEST_HARD_REG_BIT (set, REG_X) && TEST_HARD_REG_BIT (set, REG_X + 1))
-+ {
-+ /* Set RAMPX to 0. */
-+ insn = emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPX_ADDR)),
-+ const0_rtx);
-+ RTX_FRAME_RELATED_P (insn) = 1;
-+ }
-+
-+ if (TEST_HARD_REG_BIT (set, REG_Y) && TEST_HARD_REG_BIT (set, REG_Y + 1))
-+ {
-+ /* Set RAMPY to 0. */
-+ insn = emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPY_ADDR)),
-+ const0_rtx);
-+ RTX_FRAME_RELATED_P (insn) = 1;
-+ }
-+
-+ if(AVR_HAVE_RAMPZ
-+ && (TEST_HARD_REG_BIT (set, REG_Z) && TEST_HARD_REG_BIT (set, REG_Z + 1)))
-+ {
-+ /* Set RAMPZ to 0. */
-+ insn = emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPZ_ADDR)),
-+ const0_rtx);
-+ RTX_FRAME_RELATED_P (insn) = 1;
-+ }
-+ }
- }
- if (minimize && (frame_pointer_needed
- || (AVR_2_BYTE_PC && live_seq > 6)
-@@ -1010,14 +1138,39 @@
- && (TEST_HARD_REG_BIT (set, REG_Z) && TEST_HARD_REG_BIT (set, REG_Z + 1)))
- {
- emit_insn (gen_popqi (tmp_reg_rtx));
-- emit_move_insn (gen_rtx_MEM(QImode, GEN_INT(RAMPZ_ADDR)),
-+ emit_move_insn (gen_rtx_MEM(QImode, GEN_INT(AVR_RAMPZ_ADDR)),
- tmp_reg_rtx);
- }
-
-+ /* Restore RAMPY, RAMPX, RAMPD using tmp reg as scratch. */
-+ if (AVR_HAVE_RAMPX_Y_D)
-+ {
-+ /* Pop RAMPY. */
-+ if (TEST_HARD_REG_BIT (set, REG_Y) && TEST_HARD_REG_BIT (set, REG_Y + 1))
-+ {
-+ emit_insn (gen_popqi (tmp_reg_rtx));
-+ emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPY_ADDR)),
-+ tmp_reg_rtx);
-+ }
-+
-+ /* Pop RAMPX. */
-+ if (TEST_HARD_REG_BIT (set, REG_X) && TEST_HARD_REG_BIT (set, REG_X + 1))
-+ {
-+ emit_insn (gen_popqi (tmp_reg_rtx));
-+ emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPX_ADDR)),
-+ tmp_reg_rtx);
-+ }
-+
-+ /* Pop RAMPD. */
-+ emit_insn (gen_popqi (tmp_reg_rtx));
-+ emit_move_insn (gen_rtx_MEM (QImode, GEN_INT (AVR_RAMPD_ADDR)),
-+ tmp_reg_rtx);
-+ }
-+
- /* Restore SREG using tmp reg as scratch. */
- emit_insn (gen_popqi (tmp_reg_rtx));
-
-- emit_move_insn (gen_rtx_MEM(QImode, GEN_INT(SREG_ADDR)),
-+ emit_move_insn (gen_rtx_MEM(QImode, GEN_INT(AVR_SREG_ADDR)),
- tmp_reg_rtx);
-
- /* Restore tmp REG. */
-@@ -1786,8 +1939,9 @@
- }
- /* Use simple load of stack pointer if no interrupts are used
- or inside main or signal function prologue where they disabled. */
-- else if (TARGET_NO_INTERRUPTS
-- || (reload_completed
-+ else if (TARGET_NO_INTERRUPTS
-+ || (!AVR_XMEGA
-+ && reload_completed
- && cfun->machine->is_signal
- && prologue_epilogue_contains (insn)))
- {
-@@ -1796,7 +1950,8 @@
- AS2 (out,__SP_L__,%A1));
- }
- /* In interrupt prolog we know interrupts are enabled. */
-- else if (reload_completed
-+ else if (!AVR_XMEGA
-+ && reload_completed
- && cfun->machine->is_interrupt
- && prologue_epilogue_contains (insn))
- {
-@@ -1806,12 +1961,21 @@
- "sei" CR_TAB
- AS2 (out,__SP_L__,%A1));
- }
-- *l = 5;
-- return (AS2 (in,__tmp_reg__,__SREG__) CR_TAB
-- "cli" CR_TAB
-- AS2 (out,__SP_H__,%B1) CR_TAB
-- AS2 (out,__SREG__,__tmp_reg__) CR_TAB
-- AS2 (out,__SP_L__,%A1));
-+ if(AVR_XMEGA)
-+ {
-+ *l = 2;
-+ return (AS2 (out,__SP_L__,%A1) CR_TAB
-+ AS2 (out,__SP_H__,%B1));
-+ }
-+ else
-+ {
-+ *l = 5;
-+ return (AS2 (in,__tmp_reg__,__SREG__) CR_TAB
-+ "cli" CR_TAB
-+ AS2 (out,__SP_H__,%B1) CR_TAB
-+ AS2 (out,__SREG__,__tmp_reg__) CR_TAB
-+ AS2 (out,__SP_L__,%A1));
-+ }
- }
- else if (test_hard_reg_class (STACK_REG, src))
- {
-@@ -1946,7 +2110,7 @@
-
- if (CONSTANT_ADDRESS_P (x))
- {
-- if (CONST_INT_P (x) && INTVAL (x) == SREG_ADDR)
-+ if (CONST_INT_P (x) && INTVAL (x) == AVR_SREG_ADDR)
- {
- *l = 1;
- return AS2 (in,%0,__SREG__);
-@@ -1954,7 +2118,8 @@
- if (avr_io_address_p (x, 1))
- {
- *l = 1;
-- return AS2 (in,%0,%1-0x20);
-+ op[2] = GEN_INT(AVR_IO_OFFSET);
-+ return AS2 (in,%0,%1-%2);
- }
- *l = 2;
- return AS2 (lds,%0,%1);
-@@ -2142,8 +2307,9 @@
- if (avr_io_address_p (base, 2))
- {
- *l = 2;
-- return (AS2 (in,%A0,%A1-0x20) CR_TAB
-- AS2 (in,%B0,%B1-0x20));
-+ op[2] = GEN_INT(AVR_IO_OFFSET);
-+ return (AS2 (in,%A0,%A1-%2) CR_TAB
-+ AS2 (in,%B0,%B1-%2));
- }
- *l = 4;
- return (AS2 (lds,%A0,%A1) CR_TAB
-@@ -2634,7 +2800,7 @@
-
- if (CONSTANT_ADDRESS_P (x))
- {
-- if (CONST_INT_P (x) && INTVAL (x) == SREG_ADDR)
-+ if (CONST_INT_P (x) && INTVAL (x) == AVR_SREG_ADDR)
- {
- *l = 1;
- return AS2 (out,__SREG__,%1);
-@@ -2642,7 +2808,8 @@
- if (avr_io_address_p (x, 1))
- {
- *l = 1;
-- return AS2 (out,%0-0x20,%1);
-+ op[2] = GEN_INT(AVR_IO_OFFSET);
-+ return AS2 (out,%0-%2,%1);
- }
- *l = 2;
- return AS2 (sts,%0,%1);
-@@ -2721,11 +2888,20 @@
- if (avr_io_address_p (base, 2))
- {
- *l = 2;
-- return (AS2 (out,%B0-0x20,%B1) CR_TAB
-- AS2 (out,%A0-0x20,%A1));
-+ op[2] = GEN_INT(AVR_IO_OFFSET);
-+ if (AVR_XMEGA)
-+ return (AS2 (out,%A0-%2,%A1) CR_TAB
-+ AS2 (out,%B0-%2,%B1));
-+ else
-+ return (AS2 (out,%B0-%2,%B1) CR_TAB
-+ AS2 (out,%A0-%2,%A1));
- }
-- return *l = 4, (AS2 (sts,%B0,%B1) CR_TAB
-- AS2 (sts,%A0,%A1));
-+ if (AVR_XMEGA)
-+ return *l = 4, (AS2 (sts,%A0,%A1) CR_TAB
-+ AS2 (sts,%B0,%B1));
-+ else
-+ return *l = 4, (AS2 (sts,%B0,%B1) CR_TAB
-+ AS2 (sts,%A0,%A1));
- }
- if (reg_base > 0)
- {
-@@ -2740,11 +2916,20 @@
- AS2 (adiw,r26,1) CR_TAB
- AS2 (st,X,__tmp_reg__));
- else
-- return *l=5, (AS2 (mov,__tmp_reg__,r27) CR_TAB
-- AS2 (adiw,r26,1) CR_TAB
-- AS2 (st,X,__tmp_reg__) CR_TAB
-- AS2 (sbiw,r26,1) CR_TAB
-- AS2 (st,X,r26));
-+ {
-+ if (!AVR_XMEGA)
-+ return *l=5, (AS2 (mov,__tmp_reg__,r27) CR_TAB
-+ AS2 (adiw,r26,1) CR_TAB
-+ AS2 (st,X,__tmp_reg__) CR_TAB
-+ AS2 (sbiw,r26,1) CR_TAB
-+ AS2 (st,X,r26));
-+ else
-+ return *l=5, (AS2 (mov,__tmp_reg__,r27) CR_TAB
-+ AS2 (st,X,r26) CR_TAB
-+ AS2 (adiw,r26,1) CR_TAB
-+ AS2 (st,X,__tmp_reg__) CR_TAB
-+ AS2 (sbiw,r26,1));
-+ }
- }
- else
- {
-@@ -2752,14 +2937,27 @@
- return *l=2, (AS2 (st,X+,%A1) CR_TAB
- AS2 (st,X,%B1));
- else
-- return *l=3, (AS2 (adiw,r26,1) CR_TAB
-- AS2 (st,X,%B1) CR_TAB
-- AS2 (st,-X,%A1));
-+ {
-+ if (!AVR_XMEGA)
-+ return *l=3, (AS2 (adiw,r26,1) CR_TAB
-+ AS2 (st,X,%B1) CR_TAB
-+ AS2 (st,-X,%A1));
-+ else
-+ return *l=3, (AS2 (st,X+,%A1) CR_TAB
-+ AS2 (st,X,%B1) CR_TAB
-+ AS2 (sbiw,r26,1));
-+ }
- }
- }
- else
-- return *l=2, (AS2 (std,%0+1,%B1) CR_TAB
-- AS2 (st,%0,%A1));
-+ {
-+ if (!AVR_XMEGA)
-+ return *l=2, (AS2 (std,%0+1,%B1) CR_TAB
-+ AS2 (st,%0,%A1));
-+ else
-+ return *l=2, (AS2 (st,%0,%A1) CR_TAB
-+ AS2 (std,%0+1,%B1));
-+ }
- }
- else if (GET_CODE (base) == PLUS)
- {
-@@ -2770,48 +2968,104 @@
- if (reg_base != REG_Y)
- fatal_insn ("incorrect insn:",insn);
-
-- if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest)))
-- return *l = 4, (AS2 (adiw,r28,%o0-62) CR_TAB
-- AS2 (std,Y+63,%B1) CR_TAB
-- AS2 (std,Y+62,%A1) CR_TAB
-- AS2 (sbiw,r28,%o0-62));
--
-- return *l = 6, (AS2 (subi,r28,lo8(-%o0)) CR_TAB
-- AS2 (sbci,r29,hi8(-%o0)) CR_TAB
-- AS2 (std,Y+1,%B1) CR_TAB
-- AS2 (st,Y,%A1) CR_TAB
-- AS2 (subi,r28,lo8(%o0)) CR_TAB
-- AS2 (sbci,r29,hi8(%o0)));
-+ if (!AVR_XMEGA)
-+ {
-+ if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest)))
-+ return *l = 4, (AS2 (adiw,r28,%o0-62) CR_TAB
-+ AS2 (std,Y+63,%B1) CR_TAB
-+ AS2 (std,Y+62,%A1) CR_TAB
-+ AS2 (sbiw,r28,%o0-62));
-+
-+ return *l = 6, (AS2 (subi,r28,lo8(-%o0)) CR_TAB
-+ AS2 (sbci,r29,hi8(-%o0)) CR_TAB
-+ AS2 (std,Y+1,%B1) CR_TAB
-+ AS2 (st,Y,%A1) CR_TAB
-+ AS2 (subi,r28,lo8(%o0)) CR_TAB
-+ AS2 (sbci,r29,hi8(%o0)));
-+ }
-+ else
-+ {
-+ if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest)))
-+ return *l = 4, (AS2 (adiw,r28,%o0-62) CR_TAB
-+ AS2 (std,Y+62,%A1) CR_TAB
-+ AS2 (std,Y+63,%B1) CR_TAB
-+ AS2 (sbiw,r28,%o0-62));
-+
-+ return *l = 6, (AS2 (subi,r28,lo8(-%o0)) CR_TAB
-+ AS2 (sbci,r29,hi8(-%o0)) CR_TAB
-+ AS2 (st,Y,%A1) CR_TAB
-+ AS2 (std,Y+1,%B1) CR_TAB
-+ AS2 (subi,r28,lo8(%o0)) CR_TAB
-+ AS2 (sbci,r29,hi8(%o0)));
-+ }
- }
- if (reg_base == REG_X)
- {
- /* (X + d) = R */
- if (reg_src == REG_X)
- {
-- *l = 7;
-- return (AS2 (mov,__tmp_reg__,r26) CR_TAB
-- AS2 (mov,__zero_reg__,r27) CR_TAB
-- AS2 (adiw,r26,%o0+1) CR_TAB
-- AS2 (st,X,__zero_reg__) CR_TAB
-- AS2 (st,-X,__tmp_reg__) CR_TAB
-- AS1 (clr,__zero_reg__) CR_TAB
-+ if (!AVR_XMEGA)
-+ {
-+ *l = 7;
-+ return (AS2 (mov,__tmp_reg__,r26) CR_TAB
-+ AS2 (mov,__zero_reg__,r27) CR_TAB
-+ AS2 (adiw,r26,%o0+1) CR_TAB
-+ AS2 (st,X,__zero_reg__) CR_TAB
-+ AS2 (st,-X,__tmp_reg__) CR_TAB
-+ AS1 (clr,__zero_reg__) CR_TAB
-+ AS2 (sbiw,r26,%o0));
-+ }
-+ else
-+ {
-+ *l = 7;
-+ return (AS2 (mov,__tmp_reg__,r26) CR_TAB
-+ AS2 (mov,__zero_reg__,r27) CR_TAB
-+ AS2 (adiw,r26,%o0) CR_TAB
-+ AS2 (st,X+,__tmp_reg__) CR_TAB
-+ AS2 (st,X,__zero_reg__) CR_TAB
-+ AS1 (clr,__zero_reg__) CR_TAB
-+ AS2 (sbiw,r26,%o0+1));
-+ }
-+ }
-+ if (!AVR_XMEGA)
-+ {
-+ *l = 4;
-+ return (AS2 (adiw,r26,%o0+1) CR_TAB
-+ AS2 (st,X,%B1) CR_TAB
-+ AS2 (st,-X,%A1) CR_TAB
- AS2 (sbiw,r26,%o0));
- }
-- *l = 4;
-- return (AS2 (adiw,r26,%o0+1) CR_TAB
-- AS2 (st,X,%B1) CR_TAB
-- AS2 (st,-X,%A1) CR_TAB
-- AS2 (sbiw,r26,%o0));
-+ else
-+ {
-+ *l = 4;
-+ return (AS2 (adiw,r26,%o0) CR_TAB
-+ AS2 (st,X+,%A1) CR_TAB
-+ AS2 (st,X,%B1) CR_TAB
-+ AS2 (sbiw,r26,%o0+1));
-+ }
- }
-- return *l=2, (AS2 (std,%B0,%B1) CR_TAB
-- AS2 (std,%A0,%A1));
-+
-+ if (!AVR_XMEGA)
-+ return *l=2, (AS2 (std,%B0,%B1) CR_TAB
-+ AS2 (std,%A0,%A1));
-+ else
-+ return *l=2, (AS2 (std,%A0,%A1) CR_TAB
-+ AS2 (std,%B0,%B1));
- }
- else if (GET_CODE (base) == PRE_DEC) /* (--R) */
-- return *l=2, (AS2 (st,%0,%B1) CR_TAB
-- AS2 (st,%0,%A1));
-+ {
-+ if (mem_volatile_p && AVR_XMEGA)
-+ return *l = 4, (AS2 (sbiw,%r0,1) CR_TAB
-+ AS2 (st,%p0+,%A1) CR_TAB
-+ AS2 (st,%p0,%B1) CR_TAB
-+ AS2 (sbiw,%r0,2));
-+ else
-+ return *l=2, (AS2 (st,%0,%B1) CR_TAB
-+ AS2 (st,%0,%A1));
-+ }
- else if (GET_CODE (base) == POST_INC) /* (R++) */
- {
-- if (mem_volatile_p)
-+ if (mem_volatile_p && !AVR_XMEGA)
- {
- if (REGNO (XEXP (base, 0)) == REG_X)
- {
-@@ -2832,7 +3086,7 @@
-
- *l = 2;
- return (AS2 (st,%0,%A1) CR_TAB
-- AS2 (st,%0,%B1));
-+ AS2 (st,%0,%B1));
- }
- fatal_insn ("unknown move insn:",insn);
- return "";
-@@ -4712,6 +4966,7 @@
- { "progmem", 0, 0, false, false, false, avr_handle_progmem_attribute },
- { "signal", 0, 0, true, false, false, avr_handle_fndecl_attribute },
- { "interrupt", 0, 0, true, false, false, avr_handle_fndecl_attribute },
-+ { "nmi", 0, 0, true, false, false, avr_handle_fndecl_attribute },
- { "naked", 0, 0, false, true, true, avr_handle_fntype_attribute },
- { "OS_task", 0, 0, false, true, true, avr_handle_fntype_attribute },
- { NULL, 0, 0, false, false, false, NULL }
-@@ -4800,6 +5055,14 @@
- func_name);
- }
- }
-+ else if (strncmp (attr, "nmi", strlen ("nmi")) == 0)
-+ {
-+ if (strncmp (func_name, "__vector", strlen ("__vector")) != 0)
-+ {
-+ warning (0, "%qs appears to be a misspelled nmi handler",
-+ func_name);
-+ }
-+ }
- }
-
- return NULL_TREE;
-@@ -4994,7 +5257,8 @@
- /* fprintf (asm_out_file, "\t.arch %s\n", avr_mcu_name);*/
- fputs ("__SREG__ = 0x3f\n"
- "__SP_H__ = 0x3e\n"
-- "__SP_L__ = 0x3d\n", asm_out_file);
-+ "__SP_L__ = 0x3d\n"
-+ "__CCP__ = 0x34\n", asm_out_file);
-
- fputs ("__tmp_reg__ = 0\n"
- "__zero_reg__ = 1\n", asm_out_file);
-@@ -5888,15 +6152,18 @@
- return !(regno & 1);
- }
-
--/* Returns 1 if X is a valid address for an I/O register of size SIZE
-- (1 or 2). Used for lds/sts -> in/out optimization. Add 0x20 to SIZE
-- to check for the lower half of I/O space (for cbi/sbi/sbic/sbis). */
-+/* Returns 1 if X is a valid address for an I/O register of size SIZE
-+ (1 or 2). Used for lds/sts -> in/out optimization. */
-
- int
- avr_io_address_p (rtx x, int size)
- {
-- return (optimize > 0 && GET_CODE (x) == CONST_INT
-- && INTVAL (x) >= 0x20 && INTVAL (x) <= 0x60 - size);
-+ if(AVR_XMEGA)
-+ return (optimize > 0 && GET_CODE (x) == CONST_INT
-+ && INTVAL (x) >= 0 && INTVAL (x) <= 0x40 - size);
-+ else
-+ return (optimize > 0 && GET_CODE (x) == CONST_INT
-+ && INTVAL (x) >= 0x20 && INTVAL (x) <= 0x60 - size);
- }
-
- const char *
-@@ -6074,16 +6341,17 @@
-
- if (GET_CODE (operands[1]) == CONST_INT)
- {
-- if (INTVAL (operands[1]) < 0x40)
-+ operands[4] = GEN_INT(AVR_IO_OFFSET); /* operands[3] is for the jump */
-+ if (low_io_address_operand (operands[1], VOIDmode))
- {
- if (comp == EQ)
-- output_asm_insn (AS2 (sbis,%1-0x20,%2), operands);
-+ output_asm_insn (AS2 (sbis,%1-%4,%2), operands);
- else
-- output_asm_insn (AS2 (sbic,%1-0x20,%2), operands);
-+ output_asm_insn (AS2 (sbic,%1-%4,%2), operands);
- }
- else
- {
-- output_asm_insn (AS2 (in,__tmp_reg__,%1-0x20), operands);
-+ output_asm_insn (AS2 (in,__tmp_reg__,%1-%4), operands);
- if (comp == EQ)
- output_asm_insn (AS2 (sbrs,__tmp_reg__,%2), operands);
- else
---- ./gcc/config/avr/avr.h.orig 2010-03-08 12:55:09.000000000 +0100
-+++ ./gcc/config/avr/avr.h 2010-03-08 12:55:36.000000000 +0100
-@@ -44,8 +44,11 @@
- /* Core have 'EICALL' and 'EIJMP' instructions. */
- int have_eijmp_eicall;
-
-- /* Reserved. */
-- int reserved;
-+ /* Core is in Xmega family. */
-+ int xmega;
-+
-+ /* Core have RAMPX, RAMPY and RAMPD registers. */
-+ int have_rampx_y_d;
-
- const char *const macro;
- };
-@@ -68,6 +71,13 @@
- builtin_define ("__AVR_HAVE_ELPMX__"); \
- if (avr_have_movw_lpmx_p) \
- builtin_define ("__AVR_HAVE_MOVW__"); \
-+ if (avr_current_arch->have_elpm) \
-+ { \
-+ builtin_define ("__AVR_HAVE_RAMPZ__");\
-+ builtin_define ("__AVR_HAVE_ELPM__"); \
-+ } \
-+ if (avr_current_arch->have_elpmx) \
-+ builtin_define ("__AVR_HAVE_ELPMX__"); \
- if (avr_have_movw_lpmx_p) \
- builtin_define ("__AVR_HAVE_LPMX__"); \
- if (avr_asm_only_p) \
-@@ -88,6 +98,17 @@
- builtin_define ("__AVR_HAVE_EIJMP_EICALL__"); \
- if (TARGET_NO_INTERRUPTS) \
- builtin_define ("__NO_INTERRUPTS__"); \
-+ if (avr_current_arch->xmega) \
-+ { \
-+ builtin_define ("__AVR_XMEGA__"); \
-+ builtin_define ("__AVR_HAVE_SPMX__"); \
-+ } \
-+ if (avr_current_arch->have_rampx_y_d) \
-+ { \
-+ builtin_define ("__AVR_HAVE_RAMPX__");\
-+ builtin_define ("__AVR_HAVE_RAMPY__");\
-+ builtin_define ("__AVR_HAVE_RAMPD__");\
-+ } \
- } \
- while (0)
-
-@@ -107,10 +128,19 @@
- #define AVR_HAVE_LPMX (avr_have_movw_lpmx_p)
- #define AVR_HAVE_RAMPZ (avr_current_arch->have_elpm)
- #define AVR_HAVE_EIJMP_EICALL (avr_current_arch->have_eijmp_eicall)
-+#define AVR_XMEGA (avr_current_arch->xmega)
-+#define AVR_HAVE_RAMPX_Y_D (avr_current_arch->have_rampx_y_d)
-
- #define AVR_2_BYTE_PC (!AVR_HAVE_EIJMP_EICALL)
- #define AVR_3_BYTE_PC (AVR_HAVE_EIJMP_EICALL)
-
-+#define AVR_IO_OFFSET (AVR_XMEGA ? 0 : 0x20)
-+#define AVR_RAMPD_ADDR (AVR_XMEGA ? 0x38 : 0)
-+#define AVR_RAMPX_ADDR (AVR_XMEGA ? 0x39 : 0)
-+#define AVR_RAMPY_ADDR (AVR_XMEGA ? 0x3A : 0)
-+#define AVR_RAMPZ_ADDR (AVR_XMEGA ? 0x3B : 0x5B)
-+#define AVR_SREG_ADDR (AVR_XMEGA ? 0x3F: 0x5F)
-+
- #define TARGET_VERSION fprintf (stderr, " (GNU assembler syntax)");
-
- #define OVERRIDE_OPTIONS avr_override_options ()
-@@ -935,6 +965,20 @@
- mmcu=m3000*|\
- mmcu=m3001*: -m avr5}\
- %{mmcu=atmega256*:-m avr6}\
-+%{mmcu=atxmega16a4|\
-+ mmcu=atxmega16d4|\
-+ mmcu=atxmega32d4:-m avrxmega2}\
-+%{mmcu=atxmega32a4:-m avrxmega3} \
-+%{mmcu=atxmega64a3|\
-+ mmcu=atxmega64d3:-m avrxmega4} \
-+%{mmcu=atxmega64a1:-m avrxmega5} \
-+%{mmcu=atxmega128a3|\
-+ mmcu=atxmega128d3|\
-+ mmcu=atxmega192a3|\
-+ mmcu=atxmega192d3|\
-+ mmcu=atxmega256a3*|\
-+ mmcu=atxmega256d3:-m avrxmega6} \
-+%{mmcu=atxmega128a1:-m avrxmega7} \
- %{mmcu=atmega324a|\
- mmcu=atmega324p|\
- mmcu=atmega324pa|\
-@@ -1190,7 +1234,22 @@
- %{mmcu=m3000s:crtm3000s.o%s} \
- %{mmcu=m3001b:crtm3001b.o%s} \
- %{mmcu=atmega2560|mmcu=avr6:crtm2560.o%s} \
--%{mmcu=atmega2561:crtm2561.o%s}"
-+%{mmcu=atmega2561:crtm2561.o%s} \
-+%{mmcu=avrxmega2|mmcu=atxmega32d4:crtx32d4.o%s} \
-+%{mmcu=atxmega16a4:crtx16a4.o%s} \
-+%{mmcu=atxmega16d4:crtx16d4.o%s} \
-+%{mmcu=atxmega3|mmcu=atxmega32a4:crtx32a4.o%s} \
-+%{mmcu=atxmega4|mmcu=atxmega64a3:crtx64a3.o%s} \
-+%{mmcu=atxmega64d3:crtx64d3.o%s} \
-+%{mmcu=atxmega5|mmcu=atxmega64a1:crtx64a1.o%s} \
-+%{mmcu=atxmega6|mmcu=atxmega128a3:crtx128a3.o%s} \
-+%{mmcu=atxmega128d3:crtx128d3.o%s}\
-+%{mmcu=atxmega192a3:crtx192a3.o%s}\
-+%{mmcu=atxmega192d3:crtx192d3.o%s}\
-+%{mmcu=atxmega256a3:crtx256a3.o%s} \
-+%{mmcu=atxmega256a3b:crtx256a3b.o%s} \
-+%{mmcu=atxmega256d3:crtx256d3.o%s} \
-+%{mmcu=atxmega7|mmcu=atxmega128a1:crtx128a1.o%s}"
-
- #define EXTRA_SPECS {"crt_binutils", CRT_BINUTILS_SPECS},
-
-@@ -1252,8 +1311,12 @@
- /* 'true' - if current function is a signal function
- as specified by the "signal" attribute. */
- int is_signal;
--
-+
- /* 'true' - if current function is a signal function
-+ as specified by the "nmi" attribute. */
-+ int is_nmi;
-+
-+ /* 'true' - if current function is a task function
- as specified by the "OS_task" attribute. */
- int is_OS_task;
- };
---- ./gcc/config/avr/t-avr.orig 2010-03-08 12:55:09.000000000 +0100
-+++ ./gcc/config/avr/t-avr 2010-03-08 12:55:36.000000000 +0100
-@@ -37,8 +37,8 @@
-
- FPBIT = fp-bit.c
-
--MULTILIB_OPTIONS = mmcu=avr2/mmcu=avr25/mmcu=avr3/mmcu=avr31/mmcu=avr35/mmcu=avr4/mmcu=avr5/mmcu=avr51/mmcu=avr6
--MULTILIB_DIRNAMES = avr2 avr25 avr3 avr31 avr35 avr4 avr5 avr51 avr6
-+MULTILIB_OPTIONS = mmcu=avr2/mmcu=avr25/mmcu=avr3/mmcu=avr31/mmcu=avr35/mmcu=avr4/mmcu=avr5/mmcu=avr51/mmcu=avr6/mmcu=avrxmega2/mmcu=avrxmega3/mmcu=avrxmega4/mmcu=avrxmega5/mmcu=avrxmega6/mmcu=avrxmega7
-+MULTILIB_DIRNAMES = avr2 avr25 avr3 avr31 avr35 avr4 avr5 avr51 avr6 avrxmega2 avrxmega3 avrxmega4 avrxmega5 avrxmega6 avrxmega7
-
- # The many avr2 matches are not listed here - this is the default.
- MULTILIB_MATCHES = \
-@@ -182,7 +182,22 @@
- mmcu?avr51=mmcu?m3000s \
- mmcu?avr51=mmcu?m3001b \
- mmcu?avr6=mmcu?atmega2560 \
-- mmcu?avr6=mmcu?atmega2561
-+ mmcu?avr6=mmcu?atmega2561 \
-+ mmcu?avrxmega2=mmcu?atxmega16a4 \
-+ mmcu?avrxmega2=mmcu?atxmega16d4 \
-+ mmcu?avrxmega2=mmcu?atxmega32d4 \
-+ mmcu?avrxmega3=mmcu?atxmega32a4 \
-+ mmcu?avrxmega4=mmcu?atxmega64a3 \
-+ mmcu?avrxmega4=mmcu?atxmega64d3 \
-+ mmcu?avrxmega5=mmcu?atxmega64a1 \
-+ mmcu?avrxmega6=mmcu?atxmega128a3 \
-+ mmcu?avrxmega6=mmcu?atxmega128d3 \
-+ mmcu?avrxmega6=mmcu?atxmega192a3 \
-+ mmcu?avrxmega6=mmcu?atxmega192d3 \
-+ mmcu?avrxmega6=mmcu?atxmega256a3 \
-+ mmcu?avrxmega6=mmcu?atxmega256a3b \
-+ mmcu?avrxmega6=mmcu?atxmega256d3 \
-+ mmcu?avrxmega7=mmcu?atxmega128a1
- MULTILIB_EXCEPTIONS =
-
- LIBGCC = stmp-multilib
---- ./gcc/config/avr/avr.md.orig 2010-03-08 12:54:57.000000000 +0100
-+++ ./gcc/config/avr/avr.md 2010-03-08 12:55:36.000000000 +0100
-@@ -47,9 +47,6 @@
- (TMP_REGNO 0) ; temporary register r0
- (ZERO_REGNO 1) ; zero register r1
-
-- (SREG_ADDR 0x5F)
-- (RAMPZ_ADDR 0x5B)
--
- (UNSPEC_STRLEN 0)
- (UNSPEC_INDEX_JMP 1)
- (UNSPEC_SWAP 2)
-@@ -2677,7 +2674,8 @@
- "(optimize > 0)"
- {
- operands[2] = GEN_INT (exact_log2 (~INTVAL (operands[1]) & 0xff));
-- return AS2 (cbi,%0-0x20,%2);
-+ operands[3] = GEN_INT(AVR_IO_OFFSET);
-+ return AS2 (cbi,%0-%3,%2);
- }
- [(set_attr "length" "1")
- (set_attr "cc" "none")])
-@@ -2689,7 +2687,8 @@
- "(optimize > 0)"
- {
- operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1]) & 0xff));
-- return AS2 (sbi,%0-0x20,%2);
-+ operands[3] = GEN_INT(AVR_IO_OFFSET);
-+ return AS2 (sbi,%0-%3,%2);
- }
- [(set_attr "length" "1")
- (set_attr "cc" "none")])
---- ./gcc/config/avr/predicates.md.orig 2010-03-08 12:54:57.000000000 +0100
-+++ ./gcc/config/avr/predicates.md 2010-03-08 12:55:36.000000000 +0100
-@@ -50,12 +50,16 @@
- ;; Return true if OP is a valid address for lower half of I/O space.
- (define_predicate "low_io_address_operand"
- (and (match_code "const_int")
-- (match_test "IN_RANGE((INTVAL (op)), 0x20, 0x3F)")))
-+ (if_then_else (match_test "AVR_XMEGA")
-+ (match_test "IN_RANGE((INTVAL (op)), 0x00, 0x1F)")
-+ (match_test "IN_RANGE((INTVAL (op)), 0x20, 0x3F)"))))
-
- ;; Return true if OP is a valid address for high half of I/O space.
- (define_predicate "high_io_address_operand"
- (and (match_code "const_int")
-- (match_test "IN_RANGE((INTVAL (op)), 0x40, 0x5F)")))
-+ (if_then_else (match_test "AVR_XMEGA")
-+ (match_test "IN_RANGE((INTVAL (op)), 0x20, 0x3F)")
-+ (match_test "IN_RANGE((INTVAL (op)), 0x40, 0x5F)"))))
-
- ;; Return 1 if OP is the zero constant for MODE.
- (define_predicate "const0_operand"
Summary(pt_BR.UTF-8): Utilitários para desenvolvimento de binários da GNU - AVR gcc
Summary(tr.UTF-8): GNU geliştirme araçları - AVR gcc
Name: crossavr-gcc
-Version: 4.3.5
-Release: 2
-Patch0: crossavr-gcc-bug-11259-v3.patch
-Patch1: crossavr-gcc-bug-18145.patch
-Patch2: crossavr-gcc-bug-19636-24894-31644-31786.patch
-Patch3: crossavr-gcc-bug-33009.patch
-Patch4: crossavr-gcc-bug-34210-35508.patch
-Patch5: crossavr-gcc-bug-35013.patch
-Patch6: crossavr-gcc-builtins-v6.patch
-Patch7: crossavr-gcc-libgcc.patch
-Patch8: crossavr-gcc-libiberty-Makefile.in.patch
-Patch9: crossavr-gcc-new-devices.patch
-Patch10: crossavr-gcc-param-inline-call-cost.patch
-Patch11: crossavr-gcc-xmega.patch
-Patch12: crossavr-gcc-osmain.patch
+Version: 4.5.3
+Release: 1
Epoch: 1
+# Patches 1xx are taken form Atmel official AVR8-GNU toolchain version 3.3.1.481.
+Patch100: 200-gcc-4.5.1-libiberty-Makefile.in.patch
+Patch101: 300-gcc-4.5.1-fixedpoint-3-4-2010.patch
+Patch102: 301-gcc-4.5.1-xmega-v14.patch
+Patch103: 302-gcc-4.5.1-avrtiny10.patch
+Patch104: 303-gcc-4.5.1-osmain.patch
+Patch105: 304-gcc-4.5.1-builtins-v6.patch
+Patch106: 305-gcc-4.5.1-avrtiny10-non-fixedpoint.patch
+Patch107: 306-gcc-4.5.1-option-list-devices.patch
+Patch108: 400-gcc-4.5.1-new-devices.patch
+Patch109: 401-gcc-4.5.1-atmega32_5_50_90_pa.patch
+Patch110: 402-gcc-4.5.1-attiny1634.patch
+Patch111: 403-gcc-4.5.1-atmega48pa.patch
+Patch112: 404-gcc-4.5.1-atxmega_16_32_a4u.patch
+Patch113: 405-gcc-4.5.1-atxmega64_128_192_256a3u.patch
+Patch114: 406-gcc-4.5.1-atmegarfr2_a2.patch
+Patch115: 407-gcc-4.5.1-atmega165pa.patch
+Patch116: 408-gcc-4.5.1-atxmega384c3.patch
+Patch117: 409-gcc-4.5.1-attiny80.patch
+Patch118: 410-gcc-4.5.1-atxmega128a4u.patch
+Patch119: 411-gcc-4.5.1-atxmega64d4.patch
+Patch120: 412-gcc-4.5.1-atmega164pa_168pa_32a_64a.patch
+Patch121: 413-gcc-4.5.1-atxmega32x1.patch
+Patch122: 414-gcc-4.5.1-atxmega64_128_b3.patch
+Patch123: 415-gcc-4.5.1-atxmega64b1.patch
+Patch124: 416-gcc-4.5.1-atmega_8a_128a_1284.patch
+Patch125: 417-gcc-4.5.1-atxmega64a4u.patch
+Patch126: 418-gcc-4.5.1-atxmega128d4.patch
+Patch127: 419-gcc-4.5.1-atmxt336s.patch
+Patch128: 420-gcc-4.5.1-atxmega16c4_32c4_128c3_256c3.patch
+Patch129: 421-gcc-4.5.1-atxmega384d3.patch
+Patch130: 422-gcc-4.5.1-atmega48hvf.patch
+Patch131: 423-gcc-4.5.1-atmega26hvg.patch
+Patch132: 424-gcc-4.5.1-atmxt224_224e.patch
+Patch133: 424-gcc-4.5.1-atxmega192c3.patch
+Patch134: 500-gcc-4.5.1-bug13473.patch
+Patch135: 501-gcc-4.5.1-bug13579.patch
+Patch136: 502-gcc-4.5.1-bug-18145-v4.patch
+Patch137: 503-gcc-4.5.1-avrtiny10-bug-12510.patch
+Patch138: 504-gcc-4.5.1-bug12915.patch
+Patch139: 505-gcc-4.5.1-bug13932.patch
+Patch140: 506-gcc-4.5.1-bug13789.patch
+Patch141: 507-gcc-4.5.1-bug14415.patch
License: GPL
Group: Development/Languages
Source0: ftp://gcc.gnu.org/pub/gcc/releases/gcc-%{version}/gcc-%{version}.tar.bz2
-# Source0-md5: e588cfde3bf323f82918589b94f14a15
+# Source0-md5: 8e0b5c12212e185f3e4383106bfa9cc6
BuildRequires: /bin/bash
BuildRequires: autoconf
BuildRequires: bison
BuildRequires: crossavr-binutils
+BuildRequires: elfutils-devel >= 0.145-1
BuildRequires: flex
BuildRequires: gmp-devel >= 4.1
+BuildRequires: libmpc-devel
BuildRequires: mpfr-devel >= 2.3.0
BuildRequires: perl-tools-pod
Requires: crossavr-binutils >= 2.15.91.0.2
%prep
%setup -q -n gcc-%{version}
-%patch0 -p0
-%patch1 -p0
-%patch2 -p0
-%patch3 -p0
-%patch4 -p0
-%patch5 -p0
-%patch6 -p0
-%patch7 -p0
-%patch8 -p0
-%patch9 -p0
-%patch10 -p0
-%patch11 -p0
-%patch12 -p0
+%patch100 -p0
+%patch101 -p0
+%patch102 -p0
+%patch103 -p0
+%patch104 -p0
+%patch105 -p0
+%patch106 -p0
+%patch107 -p0
+%patch108 -p0
+%patch109 -p0
+%patch110 -p0
+%patch111 -p0
+%patch112 -p0
+%patch113 -p0
+%patch114 -p0
+%patch115 -p0
+%patch116 -p0
+%patch117 -p0
+%patch118 -p0
+%patch119 -p0
+%patch120 -p0
+%patch121 -p0
+%patch122 -p0
+%patch123 -p0
+%patch124 -p0
+%patch125 -p0
+%patch126 -p0
+%patch127 -p0
+%patch128 -p0
+%patch129 -p0
+%patch130 -p0
+%patch131 -p0
+%patch132 -p0
+%patch133 -p0
+%patch134 -p0
+%patch135 -p0
+%patch136 -p0
+%patch137 -p0
+%patch138 -p0
+%patch139 -p0
+%patch140 -p0
+%patch141 -p0
%build
rm -rf obj-%{target}
--bindir=%{_bindir} \
--libdir=%{_libdir} \
--libexecdir=%{_libdir} \
+ --enable-c99 \
+ --enable-languages="c,c++" \
+ --enable-long-long \
+ --enable-lto \
--disable-shared \
--disable-libssp \
- --enable-languages="c,c++" \
--with-dwarf2 \
--with-gnu-as \
--with-gnu-ld \
%dir %{gcclib}
%attr(755,root,root) %{gcclib}/cc1
%attr(755,root,root) %{gcclib}/collect2
+%attr(755,root,root) %{gcclib}/lto-wrapper
+%attr(755,root,root) %{gcclib}/lto1
%{gcclib}/libg*.a
%{gcclib}/%{target}*
+%{gcclib}/plugin
%dir %{gcclib}/include
%{gcclib}/include/*.h
%{_mandir}/man1/%{target}-cpp.1*