/* Subroutines for insn-output.c for ATMEL AVR micro controllers
   Copyright (C) 1998-2021 Free Software Foundation, Inc.
   Contributed by Denis Chertykov (chertykov@gmail.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 IN_TARGET_CODE 1

#include "config.h"
#include "system.h"
#include "intl.h"
#include "coretypes.h"
#include "backend.h"
#include "target.h"
#include "rtl.h"
#include "tree.h"
#include "stringpool.h"
#include "attribs.h"
#include "cgraph.h"
#include "c-family/c-common.h"
#include "cfghooks.h"
#include "df.h"
#include "memmodel.h"
#include "tm_p.h"
#include "optabs.h"
#include "regs.h"
#include "emit-rtl.h"
#include "recog.h"
#include "conditions.h"
#include "insn-attr.h"
#include "reload.h"
#include "varasm.h"
#include "calls.h"
#include "stor-layout.h"
#include "output.h"
#include "explow.h"
#include "expr.h"
#include "langhooks.h"
#include "cfgrtl.h"
#include "builtins.h"
#include "context.h"
#include "tree-pass.h"
#include "print-rtl.h"
#include "rtl-iter.h"

/* This file should be included last.  */
#include "target-def.h"

/* Maximal allowed offset for an address in the LD command */
#define MAX_LD_OFFSET(MODE) (64 - (signed)GET_MODE_SIZE (MODE))

/* The 4 bits starting at SECTION_MACH_DEP are reserved to store the
   address space where data is to be located.
   As the only non-generic address spaces are all located in flash,
   this can be used to test if data shall go into some .progmem* section.
   This must be the rightmost field of machine dependent section flags.  */
#define AVR_SECTION_PROGMEM (0xf * SECTION_MACH_DEP)

/* Similar 4-bit region for SYMBOL_REF_FLAGS.  */
#define AVR_SYMBOL_FLAG_PROGMEM (0xf * SYMBOL_FLAG_MACH_DEP)

/* Similar 4-bit region in SYMBOL_REF_FLAGS:
   Set address-space AS in SYMBOL_REF_FLAGS of SYM  */
#define AVR_SYMBOL_SET_ADDR_SPACE(SYM,AS)                       \
  do {                                                          \
    SYMBOL_REF_FLAGS (sym) &= ~AVR_SYMBOL_FLAG_PROGMEM;         \
    SYMBOL_REF_FLAGS (sym) |= (AS) * SYMBOL_FLAG_MACH_DEP;      \
  } while (0)

/* Read address-space from SYMBOL_REF_FLAGS of SYM  */
#define AVR_SYMBOL_GET_ADDR_SPACE(SYM)                          \
  ((SYMBOL_REF_FLAGS (sym) & AVR_SYMBOL_FLAG_PROGMEM)           \
   / SYMBOL_FLAG_MACH_DEP)

/* (AVR_TINY only): Symbol has attribute progmem */
#define AVR_SYMBOL_FLAG_TINY_PM \
  (SYMBOL_FLAG_MACH_DEP << 7)

/* (AVR_TINY only): Symbol has attribute absdata */
#define AVR_SYMBOL_FLAG_TINY_ABSDATA \
  (SYMBOL_FLAG_MACH_DEP << 8)

#define TINY_ADIW(REG1, REG2, I)                                \
    "subi " #REG1 ",lo8(-(" #I "))" CR_TAB                      \
    "sbci " #REG2 ",hi8(-(" #I "))"

#define TINY_SBIW(REG1, REG2, I)                                \
    "subi " #REG1 ",lo8((" #I "))" CR_TAB                       \
    "sbci " #REG2 ",hi8((" #I "))"

#define AVR_TMP_REGNO (AVR_TINY ? TMP_REGNO_TINY : TMP_REGNO)
#define AVR_ZERO_REGNO (AVR_TINY ? ZERO_REGNO_TINY : ZERO_REGNO)

/* Known address spaces.  The order must be the same as in the respective
   enum from avr.h (or designated initialized must be used).  */
const avr_addrspace_t avr_addrspace[ADDR_SPACE_COUNT] =
{
  { ADDR_SPACE_RAM,  0, 2, "", 0, NULL },
  { ADDR_SPACE_FLASH,  1, 2, "__flash",   0, ".progmem.data" },
  { ADDR_SPACE_FLASH1, 1, 2, "__flash1",  1, ".progmem1.data" },
  { ADDR_SPACE_FLASH2, 1, 2, "__flash2",  2, ".progmem2.data" },
  { ADDR_SPACE_FLASH3, 1, 2, "__flash3",  3, ".progmem3.data" },
  { ADDR_SPACE_FLASH4, 1, 2, "__flash4",  4, ".progmem4.data" },
  { ADDR_SPACE_FLASH5, 1, 2, "__flash5",  5, ".progmem5.data" },
  { ADDR_SPACE_MEMX, 1, 3, "__memx",  0, ".progmemx.data" },
};


/* Holding RAM addresses of some SFRs used by the compiler and that
   are unique over all devices in an architecture like 'avr4'.  */

typedef struct
{
  /* SREG: The processor status */
  int sreg;

  /* RAMPX, RAMPY, RAMPD and CCP of XMEGA */
  int ccp;
  int rampd;
  int rampx;
  int rampy;

  /* RAMPZ: The high byte of 24-bit address used with ELPM */
  int rampz;

  /* SP: The stack pointer and its low and high byte */
  int sp_l;
  int sp_h;
} avr_addr_t;

static avr_addr_t avr_addr;


/* Prototypes for local helper functions.  */

static const char* out_movqi_r_mr (rtx_insn *, rtx[], int*);
static const char* out_movhi_r_mr (rtx_insn *, rtx[], int*);
static const char* out_movsi_r_mr (rtx_insn *, rtx[], int*);
static const char* out_movqi_mr_r (rtx_insn *, rtx[], int*);
static const char* out_movhi_mr_r (rtx_insn *, rtx[], int*);
static const char* out_movsi_mr_r (rtx_insn *, rtx[], int*);

static int get_sequence_length (rtx_insn *insns);
static int sequent_regs_live (void);
static const char *ptrreg_to_str (int);
static const char *cond_string (enum rtx_code);
static int avr_num_arg_regs (machine_mode, const_tree);
static int avr_operand_rtx_cost (rtx, machine_mode, enum rtx_code,
                                 int, bool);
static void output_reload_in_const (rtx*, rtx, int*, bool);
static struct machine_function * avr_init_machine_status (void);


/* Prototypes for hook implementors if needed before their implementation.  */

static bool avr_rtx_costs (rtx, machine_mode, int, int, int*, bool);


/* Allocate registers from r25 to r8 for parameters for function calls.  */
#define FIRST_CUM_REG 26

/* Last call saved register */
#define LAST_CALLEE_SAVED_REG (AVR_TINY ? 19 : 17)

/* Implicit target register of LPM instruction (R0) */
extern GTY(()) rtx lpm_reg_rtx;
rtx lpm_reg_rtx;

/* (Implicit) address register of LPM instruction (R31:R30 = Z) */
extern GTY(()) rtx lpm_addr_reg_rtx;
rtx lpm_addr_reg_rtx;

/* Temporary register RTX (reg:QI TMP_REGNO) */
extern GTY(()) rtx tmp_reg_rtx;
rtx tmp_reg_rtx;

/* Zeroed register RTX (reg:QI ZERO_REGNO) */
extern GTY(()) rtx zero_reg_rtx;
rtx zero_reg_rtx;

/* Condition Code register RTX (reg:CC REG_CC) */
extern GTY(()) rtx cc_reg_rtx;
rtx cc_reg_rtx;

/* RTXs for all general purpose registers as QImode */
extern GTY(()) rtx all_regs_rtx[32];
rtx all_regs_rtx[32];

/* SREG, the processor status */
extern GTY(()) rtx sreg_rtx;
rtx sreg_rtx;

/* RAMP* special function registers */
extern GTY(()) rtx rampd_rtx;
extern GTY(()) rtx rampx_rtx;
extern GTY(()) rtx rampy_rtx;
extern GTY(()) rtx rampz_rtx;
rtx rampd_rtx;
rtx rampx_rtx;
rtx rampy_rtx;
rtx rampz_rtx;

/* RTX containing the strings "" and "e", respectively */
static GTY(()) rtx xstring_empty;
static GTY(()) rtx xstring_e;

/* Current architecture.  */
const avr_arch_t *avr_arch;

/* Unnamed sections associated to __attribute__((progmem)) aka. PROGMEM
   or to address space __flash* or __memx.  Only used as singletons inside
   avr_asm_select_section, but it must not be local there because of GTY.  */
static GTY(()) section *progmem_section[ADDR_SPACE_COUNT];

/* Condition for insns/expanders from avr-dimode.md.  */
bool avr_have_dimode = true;

/* To track if code will use .bss and/or .data.  */
bool avr_need_clear_bss_p = false;
bool avr_need_copy_data_p = false;


/* Transform UP into lowercase and write the result to LO.
   You must provide enough space for LO.  Return LO.  */

static char*
avr_tolower (char *lo, const char *up)
{
  char *lo0 = lo;

  for (; *up; up++, lo++)
    *lo = TOLOWER (*up);

  *lo = '\0';

  return lo0;
}


/* Constraint helper function.  XVAL is a CONST_INT or a CONST_DOUBLE.
   Return true if the least significant N_BYTES bytes of XVAL all have a
   popcount in POP_MASK and false, otherwise.  POP_MASK represents a subset
   of integers which contains an integer N iff bit N of POP_MASK is set.  */

bool
avr_popcount_each_byte (rtx xval, int n_bytes, int pop_mask)
{
  machine_mode mode = GET_MODE (xval);

  if (VOIDmode == mode)
    mode = SImode;

  for (int i = 0; i < n_bytes; i++)
    {
      rtx xval8 = simplify_gen_subreg (QImode, xval, mode, i);
      unsigned int val8 = UINTVAL (xval8) & GET_MODE_MASK (QImode);

      if ((pop_mask & (1 << popcount_hwi (val8))) == 0)
        return false;
    }

  return true;
}


/* Access some RTX as INT_MODE.  If X is a CONST_FIXED we can get
   the bit representation of X by "casting" it to CONST_INT.  */

rtx
avr_to_int_mode (rtx x)
{
  machine_mode mode = GET_MODE (x);

  return VOIDmode == mode
    ? x
    : simplify_gen_subreg (int_mode_for_mode (mode).require (), x, mode, 0);
}

namespace {

static const pass_data avr_pass_data_recompute_notes =
{
  RTL_PASS,      // type
  "",            // name (will be patched)
  OPTGROUP_NONE, // optinfo_flags
  TV_DF_SCAN,    // tv_id
  0,             // properties_required
  0,             // properties_provided
  0,             // properties_destroyed
  0,             // todo_flags_start
  TODO_df_finish | TODO_df_verify // todo_flags_finish
};


class avr_pass_recompute_notes : public rtl_opt_pass
{
public:
  avr_pass_recompute_notes (gcc::context *ctxt, const char *name)
    : rtl_opt_pass (avr_pass_data_recompute_notes, ctxt)
  {
    this->name = name;
  }

  virtual unsigned int execute (function*)
  {
    df_note_add_problem ();
    df_analyze ();

    return 0;
  }
}; // avr_pass_recompute_notes

static const pass_data avr_pass_data_casesi =
{
  RTL_PASS,      // type
  "",            // name (will be patched)
  OPTGROUP_NONE, // optinfo_flags
  TV_DF_SCAN,    // tv_id
  0,             // properties_required
  0,             // properties_provided
  0,             // properties_destroyed
  0,             // todo_flags_start
  0              // todo_flags_finish
};


class avr_pass_casesi : public rtl_opt_pass
{
public:
  avr_pass_casesi (gcc::context *ctxt, const char *name)
    : rtl_opt_pass (avr_pass_data_casesi, ctxt)
  {
    this->name = name;
  }

  void avr_rest_of_handle_casesi (function*);

  virtual bool gate (function*) { return optimize > 0; }

  virtual unsigned int execute (function *func)
  {
    avr_rest_of_handle_casesi (func);

    return 0;
  }
}; // avr_pass_casesi

} // anon namespace

rtl_opt_pass*
make_avr_pass_recompute_notes (gcc::context *ctxt)
{
  return new avr_pass_recompute_notes (ctxt, "avr-notes-free-cfg");
}

rtl_opt_pass*
make_avr_pass_casesi (gcc::context *ctxt)
{
  return new avr_pass_casesi (ctxt, "avr-casesi");
}


/* Make one parallel insn with all the patterns from insns i[0]..i[5].  */

static rtx_insn*
avr_parallel_insn_from_insns (rtx_insn *i[5])
{
  rtvec vec = gen_rtvec (5, PATTERN (i[0]), PATTERN (i[1]), PATTERN (i[2]),
                         PATTERN (i[3]), PATTERN (i[4]));
  start_sequence();
  emit (gen_rtx_PARALLEL (VOIDmode, vec));
  rtx_insn *insn = get_insns();
  end_sequence();

  return insn;
}


/* Return true if we see an insn stream generated by casesi expander together
   with an extension to SImode of the switch value.

   If this is the case, fill in the insns from casesi to INSNS[1..5] and
   the SImode extension to INSNS[0].  Moreover, extract the operands of
   pattern casesi_<mode>_sequence forged from the sequence to recog_data.  */

static bool
avr_is_casesi_sequence (basic_block bb, rtx_insn *insn, rtx_insn *insns[5])
{
  rtx set_4, set_0;

  /* A first and quick test for a casesi sequences.  As a side effect of
     the test, harvest respective insns to INSNS[0..4].  */

  if (!(JUMP_P (insns[4] = insn)
        // casesi is the only insn that comes up with UNSPEC_INDEX_JMP,
        // hence the following test ensures that we are actually dealing
        // with code from casesi.
        && (set_4 = single_set (insns[4]))
        && UNSPEC == GET_CODE (SET_SRC (set_4))
        && UNSPEC_INDEX_JMP == XINT (SET_SRC (set_4), 1)

        && (insns[3] = prev_real_insn (insns[4]))
        && (insns[2] = prev_real_insn (insns[3]))
        && (insns[1] = prev_real_insn (insns[2]))

        // Insn prior to casesi.
        && (insns[0] = prev_real_insn (insns[1]))
        && (set_0 = single_set (insns[0]))
        && extend_operator (SET_SRC (set_0), SImode)))
    {
      return false;
    }

  if (dump_file)
    {
      fprintf (dump_file, ";; Sequence from casesi in "
               "[bb %d]:\n\n", bb->index);
      for (int i = 0; i < 5; i++)
        print_rtl_single (dump_file, insns[i]);
    }

  /* We have to deal with quite some operands.  Extracting them by hand
     would be tedious, therefore wrap the insn patterns into a parallel,
     run recog against it and then use insn extract to get the operands. */

  rtx_insn *xinsn = avr_parallel_insn_from_insns (insns);

  INSN_CODE (xinsn) = recog (PATTERN (xinsn), xinsn, NULL /* num_clobbers */);

  /* Failing to recognize means that someone changed the casesi expander or
     that some passes prior to this one performed some unexpected changes.
     Gracefully drop such situations instead of aborting.  */

  if (INSN_CODE (xinsn) < 0)
    {
      if (dump_file)
        fprintf (dump_file, ";; Sequence not recognized, giving up.\n\n");

      return false;
    }

  gcc_assert (CODE_FOR_casesi_qi_sequence == INSN_CODE (xinsn)
              || CODE_FOR_casesi_hi_sequence == INSN_CODE (xinsn));

  extract_insn (xinsn);

  // Assert on the anatomy of xinsn's operands we are going to work with.

  gcc_assert (recog_data.n_operands == 11);
  gcc_assert (recog_data.n_dups == 4);

  if (dump_file)
    {
      fprintf (dump_file, ";; Operands extracted:\n");
      for (int i = 0; i < recog_data.n_operands; i++)
        avr_fdump (dump_file, ";; $%d = %r\n", i, recog_data.operand[i]);
      fprintf (dump_file, "\n");
    }

  return true;
}


/* Perform some extra checks on operands of casesi_<mode>_sequence.
   Not all operand dependencies can be described by means of predicates.
   This function performs left over checks and should always return true.
   Returning false means that someone changed the casesi expander but did
   not adjust casesi_<mode>_sequence.  */

bool
avr_casei_sequence_check_operands (rtx *xop)
{
  rtx sub_5 = NULL_RTX;

  if (AVR_HAVE_EIJMP_EICALL
      // The last clobber op of the tablejump.
      && xop[8] == all_regs_rtx[24])
    {
      // $6 is: (subreg:SI ($5) 0)
      sub_5 = xop[6];
    }

  if (!AVR_HAVE_EIJMP_EICALL
      // $6 is: (plus:HI (subreg:SI ($5) 0)
      //                 (label_ref ($3)))
      && PLUS == GET_CODE (xop[6])
      && LABEL_REF == GET_CODE (XEXP (xop[6], 1))
      && rtx_equal_p (xop[3], XEXP (XEXP (xop[6], 1), 0))
      // The last clobber op of the tablejump.
      && xop[8] == const0_rtx)
    {
      sub_5 = XEXP (xop[6], 0);
    }

  if (sub_5
      && SUBREG_P (sub_5)
      && SUBREG_BYTE (sub_5) == 0
      && rtx_equal_p (xop[5], SUBREG_REG (sub_5)))
    return true;

  if (dump_file)
    fprintf (dump_file, "\n;; Failed condition for casesi_<mode>_sequence\n\n");

  return false;
}


/* INSNS[1..4] is a sequence as generated by casesi and INSNS[0] is an
   extension of an 8-bit or 16-bit integer to SImode.  XOP contains the
   operands of INSNS as extracted by insn_extract from pattern
   casesi_<mode>_sequence:

      $0: SImode reg switch value as result of $9.
      $1: Negative of smallest index in switch.
      $2: Number of entries in switch.
      $3: Label to table.
      $4: Label if out-of-bounds.
      $5: $0 + $1.
      $6: 3-byte PC: subreg:HI ($5) + label_ref ($3)
          2-byte PC: subreg:HI ($5)
      $7: HI reg index into table (Z or pseudo)
      $8: R24 or const0_rtx (to be clobbered)
      $9: Extension to SImode of an 8-bit or 16-bit integer register $10.
      $10: QImode or HImode register input of $9.

   Try to optimize this sequence, i.e. use the original HImode / QImode
   switch value instead of SImode.  */

static void
avr_optimize_casesi (rtx_insn *insns[5], rtx *xop)
{
  // Original mode of the switch value; this is QImode or HImode.
  machine_mode mode = GET_MODE (xop[10]);

  // How the original switch value was extended to SImode; this is
  // SIGN_EXTEND or ZERO_EXTEND.
  enum rtx_code code = GET_CODE (xop[9]);

  // Lower index, upper index (plus one) and range of case calues.
  HOST_WIDE_INT low_idx = -INTVAL (xop[1]);
  HOST_WIDE_INT num_idx = INTVAL (xop[2]);
  HOST_WIDE_INT hig_idx = low_idx + num_idx;

  // Maximum ranges of (un)signed QImode resp. HImode.
  unsigned umax = QImode == mode ? 0xff : 0xffff;
  int imax = QImode == mode ? 0x7f : 0x7fff;
  int imin = -imax - 1;

  // Testing the case range and whether it fits into the range of the
  // (un)signed mode.  This test should actually always pass because it
  // makes no sense to have case values outside the mode range.  Notice
  // that case labels which are unreachable because they are outside the
  // mode of the switch value (e.g. "case -1" for uint8_t) have already
  // been thrown away by the middle-end.

  if (SIGN_EXTEND == code
      && low_idx >= imin
      && hig_idx <= imax)
    {
      // ok
    }
  else if (ZERO_EXTEND == code
           && low_idx >= 0
           && (unsigned) hig_idx <= umax)
    {
      // ok
    }
  else
    {
      if (dump_file)
        fprintf (dump_file, ";; Case ranges too big, giving up.\n\n");
      return;
    }

  // Do normalization of switch value $10 and out-of-bound check in its
  // original mode instead of in SImode.  Use a newly created pseudo.
  // This will replace insns[1..2].

  start_sequence();

  rtx_insn *seq1, *seq2, *last1, *last2;

  rtx reg = copy_to_mode_reg (mode, xop[10]);

  rtx (*gen_add)(rtx,rtx,rtx) = QImode == mode ? gen_addqi3 : gen_addhi3;
  rtx (*gen_cbranch)(rtx,rtx,rtx,rtx)
    = QImode == mode ? gen_cbranchqi4 : gen_cbranchhi4;

  emit_insn (gen_add (reg, reg, gen_int_mode (-low_idx, mode)));
  rtx op0 = reg; rtx op1 = gen_int_mode (num_idx, mode);
  rtx labelref = copy_rtx (xop[4]);
  emit_jump_insn (gen_cbranch (gen_rtx_fmt_ee (GTU, VOIDmode, op0, op1),
                               op0, op1,
                               labelref));

  seq1 = get_insns();
  last1 = get_last_insn();
  end_sequence();

  emit_insn_after (seq1, insns[2]);

  // After the out-of-bounds test and corresponding branch, use a
  // 16-bit index.  If QImode is used, extend it to HImode first.
  // This will replace insns[4].

  start_sequence();

  if (QImode == mode)
    reg = force_reg (HImode, gen_rtx_fmt_e (code, HImode, reg));

  rtx pat_4 = AVR_3_BYTE_PC
    ? gen_movhi (xop[7], reg)
    : gen_addhi3 (xop[7], reg, gen_rtx_LABEL_REF (VOIDmode, xop[3]));

  emit_insn (pat_4);

  seq2 = get_insns();
  last2 = get_last_insn();
  end_sequence();

  emit_insn_after (seq2, insns[3]);

  if (dump_file)
    {
      fprintf (dump_file, ";; New insns: ");

      for (rtx_insn *insn = seq1; ; insn = NEXT_INSN (insn))
        {
          fprintf (dump_file, "%d, ", INSN_UID (insn));
          if (insn == last1)
            break;
        }
      for (rtx_insn *insn = seq2; ; insn = NEXT_INSN (insn))
        {
          fprintf (dump_file, "%d%s", INSN_UID (insn),
                   insn == last2 ? ".\n\n" : ", ");
          if (insn == last2)
            break;
        }

      fprintf (dump_file, ";; Deleting insns: %d, %d, %d.\n\n",
               INSN_UID (insns[1]), INSN_UID (insns[2]), INSN_UID (insns[3]));
    }

  // Pseudodelete the SImode and subreg of SImode insns.  We don't care
  // about the extension insns[0]: Its result is now unused and other
  // passes will clean it up.

  SET_INSN_DELETED (insns[1]);
  SET_INSN_DELETED (insns[2]);
  SET_INSN_DELETED (insns[3]);
}


void
avr_pass_casesi::avr_rest_of_handle_casesi (function *func)
{
  basic_block bb;

  FOR_EACH_BB_FN (bb, func)
    {
      rtx_insn *insn, *insns[5];

      FOR_BB_INSNS (bb, insn)
        {
          if (avr_is_casesi_sequence (bb, insn, insns))
            {
              avr_optimize_casesi (insns, recog_data.operand);
            }
        }
    }
}


/* Set `avr_arch' as specified by `-mmcu='.
   Return true on success.  */

static bool
avr_set_core_architecture (void)
{
  /* Search for mcu core architecture.  */

  if (!avr_mmcu)
    avr_mmcu = AVR_MMCU_DEFAULT;

  avr_arch = &avr_arch_types[0];

  for (const avr_mcu_t *mcu = avr_mcu_types; ; mcu++)
    {
      if (mcu->name == NULL)
        {
          /* Reached the end of `avr_mcu_types'.  This should actually never
             happen as options are provided by device-specs.  It could be a
             typo in a device-specs or calling the compiler proper directly
             with -mmcu=<device>. */

          error ("unknown core architecture %qs specified with %qs",
                 avr_mmcu, "-mmcu=");
          avr_inform_core_architectures ();
          break;
        }
      else if (strcmp (mcu->name, avr_mmcu) == 0
               // Is this a proper architecture ?
	       && mcu->macro == NULL)
        {
          avr_arch = &avr_arch_types[mcu->arch_id];
          if (avr_n_flash < 0)
            avr_n_flash = 1 + (mcu->flash_size - 1) / 0x10000;

          return true;
        }
    }

  return false;
}


/* Implement `TARGET_OPTION_OVERRIDE'.  */

static void
avr_option_override (void)
{
  /* caller-save.c looks for call-clobbered hard registers that are assigned
     to pseudos that cross calls and tries so save-restore them around calls
     in order to reduce the number of stack slots needed.

     This might lead to situations where reload is no more able to cope
     with the challenge of AVR's very few address registers and fails to
     perform the requested spills.  */

  if (avr_strict_X)
    flag_caller_saves = 0;

  /* Unwind tables currently require a frame pointer for correctness,
     see toplev.c:process_options().  */

  if ((flag_unwind_tables
       || flag_non_call_exceptions
       || flag_asynchronous_unwind_tables)
      && !ACCUMULATE_OUTGOING_ARGS)
    {
      flag_omit_frame_pointer = 0;
    }

  if (flag_pic == 1)
    warning (OPT_fpic, "%<-fpic%> is not supported");
  if (flag_pic == 2)
    warning (OPT_fPIC, "%<-fPIC%> is not supported");
  if (flag_pie == 1)
    warning (OPT_fpie, "%<-fpie%> is not supported");
  if (flag_pie == 2)
    warning (OPT_fPIE, "%<-fPIE%> is not supported");

#if !defined (HAVE_AS_AVR_MGCCISR_OPTION)
  avr_gasisr_prologues = 0;
#endif

  if (!avr_set_core_architecture())
    return;

  /* Sould be set by avr-common.c */
  gcc_assert (avr_long_double >= avr_double && avr_double >= 32);

  /* RAM addresses of some SFRs common to all devices in respective arch. */

  /* SREG: Status Register containing flags like I (global IRQ) */
  avr_addr.sreg = 0x3F + avr_arch->sfr_offset;

  /* RAMPZ: Address' high part when loading via ELPM */
  avr_addr.rampz = 0x3B + avr_arch->sfr_offset;

  avr_addr.rampy = 0x3A + avr_arch->sfr_offset;
  avr_addr.rampx = 0x39 + avr_arch->sfr_offset;
  avr_addr.rampd = 0x38 + avr_arch->sfr_offset;
  avr_addr.ccp = (AVR_TINY ? 0x3C : 0x34) + avr_arch->sfr_offset;

  /* SP: Stack Pointer (SP_H:SP_L) */
  avr_addr.sp_l = 0x3D + avr_arch->sfr_offset;
  avr_addr.sp_h = avr_addr.sp_l + 1;

  init_machine_status = avr_init_machine_status;

  avr_log_set_avr_log();
}

/* Function to set up the backend function structure.  */

static struct machine_function *
avr_init_machine_status (void)
{
  return ggc_cleared_alloc<machine_function> ();
}


/* Implement `INIT_EXPANDERS'.  */
/* The function works like a singleton.  */

void
avr_init_expanders (void)
{
  for (int regno = 0; regno < 32; regno ++)
    all_regs_rtx[regno] = gen_rtx_REG (QImode, regno);

  lpm_reg_rtx  = all_regs_rtx[LPM_REGNO];
  tmp_reg_rtx  = all_regs_rtx[AVR_TMP_REGNO];
  zero_reg_rtx = all_regs_rtx[AVR_ZERO_REGNO];

  cc_reg_rtx  = gen_rtx_REG (CCmode, REG_CC);

  lpm_addr_reg_rtx = gen_rtx_REG (HImode, REG_Z);

  sreg_rtx = gen_rtx_MEM (QImode, GEN_INT (avr_addr.sreg));
  rampd_rtx = gen_rtx_MEM (QImode, GEN_INT (avr_addr.rampd));
  rampx_rtx = gen_rtx_MEM (QImode, GEN_INT (avr_addr.rampx));
  rampy_rtx = gen_rtx_MEM (QImode, GEN_INT (avr_addr.rampy));
  rampz_rtx = gen_rtx_MEM (QImode, GEN_INT (avr_addr.rampz));

  xstring_empty = gen_rtx_CONST_STRING (VOIDmode, "");
  xstring_e = gen_rtx_CONST_STRING (VOIDmode, "e");

  /* TINY core does not have regs r10-r16, but avr-dimode.md expects them
     to be present */
  if (AVR_TINY)
    avr_have_dimode = false;
}


/* Implement `REGNO_REG_CLASS'.  */
/* Return register class for register R.  */

enum reg_class
avr_regno_reg_class (int r)
{
  static const enum reg_class reg_class_tab[] =
    {
      R0_REG,
      /* r1 - r15 */
      NO_LD_REGS, NO_LD_REGS, NO_LD_REGS,
      NO_LD_REGS, NO_LD_REGS, NO_LD_REGS, NO_LD_REGS,
      NO_LD_REGS, NO_LD_REGS, NO_LD_REGS, NO_LD_REGS,
      NO_LD_REGS, NO_LD_REGS, NO_LD_REGS, NO_LD_REGS,
      /* r16 - r23 */
      SIMPLE_LD_REGS, SIMPLE_LD_REGS, SIMPLE_LD_REGS, SIMPLE_LD_REGS,
      SIMPLE_LD_REGS, SIMPLE_LD_REGS, SIMPLE_LD_REGS, SIMPLE_LD_REGS,
      /* r24, r25 */
      ADDW_REGS, ADDW_REGS,
      /* X: r26, 27 */
      POINTER_X_REGS, POINTER_X_REGS,
      /* Y: r28, r29 */
      POINTER_Y_REGS, POINTER_Y_REGS,
      /* Z: r30, r31 */
      POINTER_Z_REGS, POINTER_Z_REGS,
      /* SP: SPL, SPH */
      STACK_REG, STACK_REG
    };

  if (r <= 33)
    return reg_class_tab[r];

  if (r == REG_CC)
    return CC_REG;

  return ALL_REGS;
}


/* Implement `TARGET_SCALAR_MODE_SUPPORTED_P'.  */

static bool
avr_scalar_mode_supported_p (scalar_mode mode)
{
  if (ALL_FIXED_POINT_MODE_P (mode))
    return true;

  if (PSImode == mode)
    return true;

  return default_scalar_mode_supported_p (mode);
}


/* Return TRUE if DECL is a VAR_DECL located in flash and FALSE, otherwise.  */

static bool
avr_decl_flash_p (tree decl)
{
  if (TREE_CODE (decl) != VAR_DECL
      || TREE_TYPE (decl) == error_mark_node)
    {
      return false;
    }

  return !ADDR_SPACE_GENERIC_P (TYPE_ADDR_SPACE (TREE_TYPE (decl)));
}


/* Return TRUE if DECL is a VAR_DECL located in the 24-bit flash
   address space and FALSE, otherwise.  */

static bool
avr_decl_memx_p (tree decl)
{
  if (TREE_CODE (decl) != VAR_DECL
      || TREE_TYPE (decl) == error_mark_node)
    {
      return false;
    }

  return (ADDR_SPACE_MEMX == TYPE_ADDR_SPACE (TREE_TYPE (decl)));
}


/* Return TRUE if X is a MEM rtx located in flash and FALSE, otherwise.  */

bool
avr_mem_flash_p (rtx x)
{
  return (MEM_P (x)
          && !ADDR_SPACE_GENERIC_P (MEM_ADDR_SPACE (x)));
}


/* Return TRUE if X is a MEM rtx located in the 24-bit flash
   address space and FALSE, otherwise.  */

bool
avr_mem_memx_p (rtx x)
{
  return (MEM_P (x)
          && ADDR_SPACE_MEMX == MEM_ADDR_SPACE (x));
}


/* A helper for the subsequent function attribute used to dig for
   attribute 'name' in a FUNCTION_DECL or FUNCTION_TYPE */

static inline int
avr_lookup_function_attribute1 (const_tree func, const char *name)
{
  if (FUNCTION_DECL == TREE_CODE (func))
    {
      if (NULL_TREE != lookup_attribute (name, DECL_ATTRIBUTES (func)))
        {
          return true;
        }

      func = TREE_TYPE (func);
    }

  gcc_assert (TREE_CODE (func) == FUNCTION_TYPE
              || TREE_CODE (func) == METHOD_TYPE);

  return NULL_TREE != lookup_attribute (name, TYPE_ATTRIBUTES (func));
}

/* Return nonzero if FUNC is a naked function.  */

static int
avr_naked_function_p (tree func)
{
  return avr_lookup_function_attribute1 (func, "naked");
}

/* Return nonzero if FUNC is an interrupt function as specified
   by the "interrupt" attribute.  */

static int
avr_interrupt_function_p (tree func)
{
  return avr_lookup_function_attribute1 (func, "interrupt");
}

/* Return nonzero if FUNC is a signal function as specified
   by the "signal" attribute.  */

static int
avr_signal_function_p (tree func)
{
  return avr_lookup_function_attribute1 (func, "signal");
}

/* Return nonzero if FUNC is an OS_task function.  */

static int
avr_OS_task_function_p (tree func)
{
  return avr_lookup_function_attribute1 (func, "OS_task");
}

/* Return nonzero if FUNC is an OS_main function.  */

static int
avr_OS_main_function_p (tree func)
{
  return avr_lookup_function_attribute1 (func, "OS_main");
}


/* Return nonzero if FUNC is a no_gccisr function as specified
   by the "no_gccisr" attribute.  */

static int
avr_no_gccisr_function_p (tree func)
{
  return avr_lookup_function_attribute1 (func, "no_gccisr");
}

/* Implement `TARGET_SET_CURRENT_FUNCTION'.  */
/* Sanity cheching for above function attributes.  */

static void
avr_set_current_function (tree decl)
{
  if (decl == NULL_TREE
      || current_function_decl == NULL_TREE
      || current_function_decl == error_mark_node
      || ! cfun->machine
      || cfun->machine->attributes_checked_p)
    return;

  location_t loc = DECL_SOURCE_LOCATION (decl);

  cfun->machine->is_naked = avr_naked_function_p (decl);
  cfun->machine->is_signal = avr_signal_function_p (decl);
  cfun->machine->is_interrupt = avr_interrupt_function_p (decl);
  cfun->machine->is_OS_task = avr_OS_task_function_p (decl);
  cfun->machine->is_OS_main = avr_OS_main_function_p (decl);
  cfun->machine->is_no_gccisr = avr_no_gccisr_function_p (decl);

  const char *isr = cfun->machine->is_interrupt ? "interrupt" : "signal";

  /* Too much attributes make no sense as they request conflicting features. */

  if (cfun->machine->is_OS_task
      && (cfun->machine->is_signal || cfun->machine->is_interrupt))
    error_at (loc, "function attributes %qs and %qs are mutually exclusive",
              "OS_task", isr);

  if (cfun->machine->is_OS_main
      && (cfun->machine->is_signal || cfun->machine->is_interrupt))
    error_at (loc, "function attributes %qs and %qs are mutually exclusive",
              "OS_main", isr);

  if (cfun->machine->is_interrupt || cfun->machine->is_signal)
    {
      tree args = TYPE_ARG_TYPES (TREE_TYPE (decl));
      tree ret = TREE_TYPE (TREE_TYPE (decl));
      const char *name;

      name = DECL_ASSEMBLER_NAME_SET_P (decl)
        ? IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl))
        : IDENTIFIER_POINTER (DECL_NAME (decl));

      /* Skip a leading '*' that might still prefix the assembler name,
         e.g. in non-LTO runs.  */

      name = default_strip_name_encoding (name);

      /* Interrupt handlers must be  void __vector (void)  functions.  */

      if (args && TREE_CODE (TREE_VALUE (args)) != VOID_TYPE)
        error_at (loc, "%qs function cannot have arguments", isr);

      if (TREE_CODE (ret) != VOID_TYPE)
        error_at (loc, "%qs function cannot return a value", isr);

#if defined WITH_AVRLIBC
      /* Silently ignore 'signal' if 'interrupt' is present.  AVR-LibC startet
         using this when it switched from SIGNAL and INTERRUPT to ISR.  */

      if (cfun->machine->is_interrupt)
        cfun->machine->is_signal = 0;

      /* If the function has the 'signal' or 'interrupt' attribute, ensure
         that the name of the function is "__vector_NN" so as to catch
         when the user misspells the vector name.  */

      if (!startswith (name, "__vector"))
        warning_at (loc, OPT_Wmisspelled_isr, "%qs appears to be a misspelled "
                    "%qs handler, missing %<__vector%> prefix", name, isr);
#endif // AVR-LibC naming conventions
    }

#if defined WITH_AVRLIBC
  // Common problem is using "ISR" without first including avr/interrupt.h.
  const char *name = IDENTIFIER_POINTER (DECL_NAME (decl));
  name = default_strip_name_encoding (name);
  if (strcmp ("ISR", name) == 0
      || strcmp ("INTERRUPT", name) == 0
      || strcmp ("SIGNAL", name) == 0)
    {
      warning_at (loc, OPT_Wmisspelled_isr, "%qs is a reserved identifier"
                  " in AVR-LibC.  Consider %<#include <avr/interrupt.h>%>"
                  " before using the %qs macro", name, name);
    }
#endif // AVR-LibC naming conventions

  /* Don't print the above diagnostics more than once.  */

  cfun->machine->attributes_checked_p = 1;
}


/* Implement `ACCUMULATE_OUTGOING_ARGS'.  */

int
avr_accumulate_outgoing_args (void)
{
  if (!cfun)
    return TARGET_ACCUMULATE_OUTGOING_ARGS;

  /* FIXME: For setjmp and in avr_builtin_setjmp_frame_value we don't know
        what offset is correct.  In some cases it is relative to
        virtual_outgoing_args_rtx and in others it is relative to
        virtual_stack_vars_rtx.  For example code see
            gcc.c-torture/execute/built-in-setjmp.c
            gcc.c-torture/execute/builtins/sprintf-chk.c   */

  return (TARGET_ACCUMULATE_OUTGOING_ARGS
          && !(cfun->calls_setjmp
               || cfun->has_nonlocal_label));
}


/* Report contribution of accumulated outgoing arguments to stack size.  */

static inline int
avr_outgoing_args_size (void)
{
  return (ACCUMULATE_OUTGOING_ARGS
	  ? (HOST_WIDE_INT) crtl->outgoing_args_size : 0);
}


/* Implement TARGET_STARTING_FRAME_OFFSET.  */
/* This is the offset from the frame pointer register to the first stack slot
   that contains a variable living in the frame.  */

static HOST_WIDE_INT
avr_starting_frame_offset (void)
{
  return 1 + avr_outgoing_args_size ();
}


/* Return the number of hard registers to push/pop in the prologue/epilogue
   of the current function, and optionally store these registers in SET.  */

static int
avr_regs_to_save (HARD_REG_SET *set)
{
  int count;
  int int_or_sig_p = cfun->machine->is_interrupt || cfun->machine->is_signal;

  if (set)
    CLEAR_HARD_REG_SET (*set);
  count = 0;

  /* No need to save any registers if the function never returns or
     has the "OS_task" or "OS_main" attribute.  */

  if (TREE_THIS_VOLATILE (current_function_decl)
      || cfun->machine->is_OS_task
      || cfun->machine->is_OS_main)
    return 0;

  for (int reg = 0; reg < 32; reg++)
    {
      /* Do not push/pop __tmp_reg__, __zero_reg__, as well as
         any global register variables.  */

      if (fixed_regs[reg])
        continue;

      if ((int_or_sig_p && !crtl->is_leaf && call_used_or_fixed_reg_p (reg))
          || (df_regs_ever_live_p (reg)
              && (int_or_sig_p || !call_used_or_fixed_reg_p (reg))
              /* Don't record frame pointer registers here.  They are treated
                 indivitually in prologue.  */
              && !(frame_pointer_needed
                   && (reg == REG_Y || reg == REG_Y + 1))))
        {
          if (set)
            SET_HARD_REG_BIT (*set, reg);
          count++;
        }
    }
  return count;
}


/* Implement `TARGET_ALLOCATE_STACK_SLOTS_FOR_ARGS' */

static bool
avr_allocate_stack_slots_for_args (void)
{
  return !cfun->machine->is_naked;
}


/* Return true if register FROM can be eliminated via register TO.  */

static bool
avr_can_eliminate (const int from ATTRIBUTE_UNUSED, const int to)
{
  return ((frame_pointer_needed && to == FRAME_POINTER_REGNUM)
          || !frame_pointer_needed);
}


/* Implement `TARGET_WARN_FUNC_RETURN'.  */

static bool
avr_warn_func_return (tree decl)
{
  /* Naked functions are implemented entirely in assembly, including the
     return sequence, so suppress warnings about this.  */

  return !avr_naked_function_p (decl);
}

/* Compute offset between arg_pointer and frame_pointer.  */

int
avr_initial_elimination_offset (int from, int to)
{
  if (from == FRAME_POINTER_REGNUM && to == STACK_POINTER_REGNUM)
    return 0;
  else
    {
      int offset = frame_pointer_needed ? 2 : 0;
      int avr_pc_size = AVR_HAVE_EIJMP_EICALL ? 3 : 2;

      // If FROM is ARG_POINTER_REGNUM, we are not in an ISR as ISRs
      // might not have arguments.  Hence the following is not affected
      // by gasisr prologues.
      offset += avr_regs_to_save (NULL);
      return (get_frame_size () + avr_outgoing_args_size()
              + avr_pc_size + 1 + offset);
    }
}


/* Helper for the function below.  */

static void
avr_adjust_type_node (tree *node, machine_mode mode, int sat_p)
{
  *node = make_node (FIXED_POINT_TYPE);
  TYPE_SATURATING (*node) = sat_p;
  TYPE_UNSIGNED (*node) = UNSIGNED_FIXED_POINT_MODE_P (mode);
  TYPE_IBIT (*node) = GET_MODE_IBIT (mode);
  TYPE_FBIT (*node) = GET_MODE_FBIT (mode);
  TYPE_PRECISION (*node) = GET_MODE_BITSIZE (mode);
  SET_TYPE_ALIGN (*node, 8);
  SET_TYPE_MODE (*node, mode);

  layout_type (*node);
}


/* Implement `TARGET_BUILD_BUILTIN_VA_LIST'.  */

static tree
avr_build_builtin_va_list (void)
{
  /* avr-modes.def adjusts [U]TA to be 64-bit modes with 48 fractional bits.
     This is more appropriate for the 8-bit machine AVR than 128-bit modes.
     The ADJUST_IBIT/FBIT are handled in toplev:init_adjust_machine_modes()
     which is auto-generated by genmodes, but the compiler assigns [U]DAmode
     to the long long accum modes instead of the desired [U]TAmode.

     Fix this now, right after node setup in tree.c:build_common_tree_nodes().
     This must run before c-cppbuiltin.c:builtin_define_fixed_point_constants()
     which built-in defines macros like __ULLACCUM_FBIT__ that are used by
     libgcc to detect IBIT and FBIT.  */

  avr_adjust_type_node (&ta_type_node, TAmode, 0);
  avr_adjust_type_node (&uta_type_node, UTAmode, 0);
  avr_adjust_type_node (&sat_ta_type_node, TAmode, 1);
  avr_adjust_type_node (&sat_uta_type_node, UTAmode, 1);

  unsigned_long_long_accum_type_node = uta_type_node;
  long_long_accum_type_node = ta_type_node;
  sat_unsigned_long_long_accum_type_node = sat_uta_type_node;
  sat_long_long_accum_type_node = sat_ta_type_node;

  /* Dispatch to the default handler.  */

  return std_build_builtin_va_list ();
}


/* Return contents of MEM at frame pointer + stack size + 1 (+2 if 3-byte PC).
   This is return address of function.  */

rtx
avr_return_addr_rtx (int count, rtx tem)
{
  rtx r;

  /* Can only return this function's return address. Others not supported.  */
  if (count)
    return NULL;

  if (AVR_3_BYTE_PC)
    {
      r = gen_rtx_SYMBOL_REF (Pmode, ".L__stack_usage+2");
      warning (0, "%<builtin_return_address%> contains only 2 bytes"
               " of address");
    }
  else
    r = gen_rtx_SYMBOL_REF (Pmode, ".L__stack_usage+1");

  cfun->machine->use_L__stack_usage = 1;

  r = gen_rtx_PLUS (Pmode, tem, r);
  r = gen_frame_mem (Pmode, memory_address (Pmode, r));
  r = gen_rtx_ROTATE (HImode, r, GEN_INT (8));
  return r;
}

/* Return 1 if the function epilogue is just a single "ret".  */

int
avr_simple_epilogue (void)
{
  return (! frame_pointer_needed
          && get_frame_size () == 0
          && avr_outgoing_args_size() == 0
          && avr_regs_to_save (NULL) == 0
          && ! cfun->machine->is_interrupt
          && ! cfun->machine->is_signal
          && ! cfun->machine->is_naked
          && ! TREE_THIS_VOLATILE (current_function_decl));
}

/* This function checks sequence of live registers.  */

static int
sequent_regs_live (void)
{
  int live_seq = 0;
  int cur_seq = 0;

  for (int reg = 0; reg <= LAST_CALLEE_SAVED_REG; ++reg)
    {
      if (fixed_regs[reg])
        {
          /* Don't recognize sequences that contain global register
             variables.  */

          if (live_seq != 0)
            return 0;
          else
            continue;
        }

      if (!call_used_or_fixed_reg_p (reg))
        {
          if (df_regs_ever_live_p (reg))
            {
              ++live_seq;
              ++cur_seq;
            }
          else
            cur_seq = 0;
        }
    }

  if (!frame_pointer_needed)
    {
      if (df_regs_ever_live_p (REG_Y))
        {
          ++live_seq;
          ++cur_seq;
        }
      else
        cur_seq = 0;

      if (df_regs_ever_live_p (REG_Y + 1))
        {
          ++live_seq;
          ++cur_seq;
        }
      else
        cur_seq = 0;
    }
  else
    {
      cur_seq += 2;
      live_seq += 2;
    }
  return (cur_seq == live_seq) ? live_seq : 0;
}

namespace {
static const pass_data avr_pass_data_pre_proep =
{
  RTL_PASS,      // type
  "",            // name (will be patched)
  OPTGROUP_NONE, // optinfo_flags
  TV_DF_SCAN,    // tv_id
  0,             // properties_required
  0,             // properties_provided
  0,             // properties_destroyed
  0,             // todo_flags_start
  0              // todo_flags_finish
};


class avr_pass_pre_proep : public rtl_opt_pass
{
public:
  avr_pass_pre_proep (gcc::context *ctxt, const char *name)
    : rtl_opt_pass (avr_pass_data_pre_proep, ctxt)
  {
    this->name = name;
  }

  void compute_maybe_gasisr (function*);

  virtual unsigned int execute (function *fun)
  {
    if (avr_gasisr_prologues
        // Whether this function is an ISR worth scanning at all.
        && !fun->machine->is_no_gccisr
        && (fun->machine->is_interrupt
            || fun->machine->is_signal)
        && !cfun->machine->is_naked
        // Paranoia: Non-local gotos and labels that might escape.
        && !cfun->calls_setjmp
        && !cfun->has_nonlocal_label
        && !cfun->has_forced_label_in_static)
      {
        compute_maybe_gasisr (fun);
      }

    return 0;
  }

}; // avr_pass_pre_proep

} // anon namespace

rtl_opt_pass*
make_avr_pass_pre_proep (gcc::context *ctxt)
{
  return new avr_pass_pre_proep (ctxt, "avr-pre-proep");
}


/* Set fun->machine->gasisr.maybe provided we don't find anything that
   prohibits GAS generating parts of ISR prologues / epilogues for us.  */

void
avr_pass_pre_proep::compute_maybe_gasisr (function *fun)
{
  // Don't use BB iterators so that we see JUMP_TABLE_DATA.

  for (rtx_insn *insn = get_insns (); insn; insn = NEXT_INSN (insn))
    {
      // Transparent calls always use [R]CALL and are filtered out by GAS.
      // ISRs don't use -mcall-prologues, hence what remains to be filtered
      // out are open coded (tail) calls.

      if (CALL_P (insn))
        return;

      // __tablejump2__ clobbers something and is targeted by JMP so
      // that GAS won't see its usage.

      if (AVR_HAVE_JMP_CALL
          && JUMP_TABLE_DATA_P (insn))
        return;

      // Non-local gotos not seen in *FUN.

      if (JUMP_P (insn)
          && find_reg_note (insn, REG_NON_LOCAL_GOTO, NULL_RTX))
        return;
    }

  fun->machine->gasisr.maybe = 1;
}


/* Obtain the length sequence of insns.  */

int
get_sequence_length (rtx_insn *insns)
{
  int length = 0;

  for (rtx_insn *insn = insns; insn; insn = NEXT_INSN (insn))
    length += get_attr_length (insn);

  return length;
}


/*  Implement `INCOMING_RETURN_ADDR_RTX'.  */

rtx
avr_incoming_return_addr_rtx (void)
{
  /* The return address is at the top of the stack.  Note that the push
     was via post-decrement, which means the actual address is off by one.  */
  return gen_frame_mem (HImode, plus_constant (Pmode, stack_pointer_rtx, 1));
}


/* Unset a bit in *SET.  If successful, return the respective bit number.
   Otherwise, return -1 and *SET is unaltered.  */

static int
avr_hregs_split_reg (HARD_REG_SET *set)
{
  for (int regno = 0; regno < 32; regno++)
    if (TEST_HARD_REG_BIT (*set, regno))
      {
        // Don't remove a register from *SET which might indicate that
        // some RAMP* register might need ISR prologue / epilogue treatment.

        if (AVR_HAVE_RAMPX
            && (REG_X == regno || REG_X + 1 == regno)
            && TEST_HARD_REG_BIT (*set, REG_X)
            && TEST_HARD_REG_BIT (*set, REG_X + 1))
          continue;

        if (AVR_HAVE_RAMPY
            && !frame_pointer_needed
            && (REG_Y == regno || REG_Y + 1 == regno)
            && TEST_HARD_REG_BIT (*set, REG_Y)
            && TEST_HARD_REG_BIT (*set, REG_Y + 1))
          continue;

        if (AVR_HAVE_RAMPZ
            && (REG_Z == regno || REG_Z + 1 == regno)
            && TEST_HARD_REG_BIT (*set, REG_Z)
            && TEST_HARD_REG_BIT (*set, REG_Z + 1))
          continue;
            
        CLEAR_HARD_REG_BIT (*set, regno);
        return regno;
      }

  return -1;
}


/*  Helper for expand_prologue.  Emit a push of a byte register.  */

static void
emit_push_byte (unsigned regno, bool frame_related_p)
{
  rtx mem, reg;
  rtx_insn *insn;

  mem = gen_rtx_POST_DEC (HImode, stack_pointer_rtx);
  mem = gen_frame_mem (QImode, mem);
  reg = gen_rtx_REG (QImode, regno);

  insn = emit_insn (gen_rtx_SET (mem, reg));
  if (frame_related_p)
    RTX_FRAME_RELATED_P (insn) = 1;

  cfun->machine->stack_usage++;
}


/*  Helper for expand_prologue.  Emit a push of a SFR via register TREG.
    SFR is a MEM representing the memory location of the SFR.
    If CLR_P then clear the SFR after the push using zero_reg.  */

static void
emit_push_sfr (rtx sfr, bool frame_related_p, bool clr_p, int treg)
{
  rtx_insn *insn;

  gcc_assert (MEM_P (sfr));

  /* IN treg, IO(SFR) */
  insn = emit_move_insn (all_regs_rtx[treg], sfr);
  if (frame_related_p)
    RTX_FRAME_RELATED_P (insn) = 1;

  /* PUSH treg */
  emit_push_byte (treg, frame_related_p);

  if (clr_p)
    {
      /* OUT IO(SFR), __zero_reg__ */
      insn = emit_move_insn (sfr, const0_rtx);
      if (frame_related_p)
        RTX_FRAME_RELATED_P (insn) = 1;
    }
}

static void
avr_prologue_setup_frame (HOST_WIDE_INT size, HARD_REG_SET set)
{
  rtx_insn *insn;
  bool isr_p = cfun->machine->is_interrupt || cfun->machine->is_signal;
  int live_seq = sequent_regs_live ();

  HOST_WIDE_INT size_max
    = (HOST_WIDE_INT) GET_MODE_MASK (AVR_HAVE_8BIT_SP ? QImode : Pmode);

  bool minimize = (TARGET_CALL_PROLOGUES
                   && size < size_max
                   && live_seq
                   && !isr_p
                   && !cfun->machine->is_OS_task
                   && !cfun->machine->is_OS_main
                   && !AVR_TINY);

  if (minimize
      && (frame_pointer_needed
          || avr_outgoing_args_size() > 8
          || (AVR_2_BYTE_PC && live_seq > 6)
          || live_seq > 7))
    {
      rtx pattern;
      int first_reg, reg, offset;

      emit_move_insn (gen_rtx_REG (HImode, REG_X),
                      gen_int_mode (size, HImode));

      pattern = gen_call_prologue_saves (gen_int_mode (live_seq, HImode),
                                         gen_int_mode (live_seq+size, HImode));
      insn = emit_insn (pattern);
      RTX_FRAME_RELATED_P (insn) = 1;

      /* Describe the effect of the unspec_volatile call to prologue_saves.
         Note that this formulation assumes that add_reg_note pushes the
         notes to the front.  Thus we build them in the reverse order of
         how we want dwarf2out to process them.  */

      /* The function does always set frame_pointer_rtx, but whether that
         is going to be permanent in the function is frame_pointer_needed.  */

      add_reg_note (insn, REG_CFA_ADJUST_CFA,
                    gen_rtx_SET ((frame_pointer_needed
				  ? frame_pointer_rtx
				  : stack_pointer_rtx),
                                 plus_constant (Pmode, stack_pointer_rtx,
                                                -(size + live_seq))));

      /* Note that live_seq always contains r28+r29, but the other
         registers to be saved are all below 18.  */

      first_reg = (LAST_CALLEE_SAVED_REG + 1) - (live_seq - 2);

      for (reg = 29, offset = -live_seq + 1;
           reg >= first_reg;
           reg = (reg == 28 ? LAST_CALLEE_SAVED_REG : reg - 1), ++offset)
        {
          rtx m, r;

          m = gen_rtx_MEM (QImode, plus_constant (Pmode, stack_pointer_rtx,
                                                  offset));
          r = gen_rtx_REG (QImode, reg);
          add_reg_note (insn, REG_CFA_OFFSET, gen_rtx_SET (m, r));
        }

      cfun->machine->stack_usage += size + live_seq;
    }
  else /* !minimize */
    {
      for (int reg = 0; reg < 32; ++reg)
        if (TEST_HARD_REG_BIT (set, reg))
          emit_push_byte (reg, true);

      if (frame_pointer_needed
          && (!(cfun->machine->is_OS_task || cfun->machine->is_OS_main)))
        {
          /* Push frame pointer.  Always be consistent about the
             ordering of pushes -- epilogue_restores expects the
             register pair to be pushed low byte first.  */

          emit_push_byte (REG_Y, true);
          emit_push_byte (REG_Y + 1, true);
        }

      if (frame_pointer_needed
          && size == 0)
        {
          insn = emit_move_insn (frame_pointer_rtx, stack_pointer_rtx);
          RTX_FRAME_RELATED_P (insn) = 1;
        }

      if (size != 0)
        {
          /*  Creating a frame can be done by direct manipulation of the
              stack or via the frame pointer. These two methods are:
                  fp =  sp
                  fp -= size
                  sp =  fp
              or
                  sp -= size
                  fp =  sp    (*)
              the optimum method depends on function type, stack and
              frame size.  To avoid a complex logic, both methods are
              tested and shortest is selected.

              There is also the case where SIZE != 0 and no frame pointer is
              needed; this can occur if ACCUMULATE_OUTGOING_ARGS is on.
              In that case, insn (*) is not needed in that case.
              We use the X register as scratch. This is save because in X
              is call-clobbered.
                 In an interrupt routine, the case of SIZE != 0 together with
              !frame_pointer_needed can only occur if the function is not a
              leaf function and thus X has already been saved.  */

          int irq_state = -1;
          HOST_WIDE_INT size_cfa = size, neg_size;
          rtx_insn *fp_plus_insns;
          rtx fp, my_fp;

          gcc_assert (frame_pointer_needed
                      || !isr_p
                      || !crtl->is_leaf);

          fp = my_fp = (frame_pointer_needed
                        ? frame_pointer_rtx
                        : gen_rtx_REG (Pmode, REG_X));

          if (AVR_HAVE_8BIT_SP)
            {
              /* The high byte (r29) does not change:
                 Prefer SUBI (1 cycle) over SBIW (2 cycles, same size).  */

              my_fp = all_regs_rtx[FRAME_POINTER_REGNUM];
            }

          /* Cut down size and avoid size = 0 so that we don't run
             into ICE like PR52488 in the remainder.  */

          if (size > size_max)
            {
              /* Don't error so that insane code from newlib still compiles
                 and does not break building newlib.  As PR51345 is implemented
                 now, there are multilib variants with -msp8.

                 If user wants sanity checks he can use -Wstack-usage=
                 or similar options.

                 For CFA we emit the original, non-saturated size so that
                 the generic machinery is aware of the real stack usage and
                 will print the above diagnostic as expected.  */

              size = size_max;
            }

          size = trunc_int_for_mode (size, GET_MODE (my_fp));
          neg_size = trunc_int_for_mode (-size, GET_MODE (my_fp));

          /************  Method 1: Adjust frame pointer  ************/

          start_sequence ();

          /* Normally, the dwarf2out frame-related-expr interpreter does
             not expect to have the CFA change once the frame pointer is
             set up.  Thus, we avoid marking the move insn below and
             instead indicate that the entire operation is complete after
             the frame pointer subtraction is done.  */

          insn = emit_move_insn (fp, stack_pointer_rtx);
          if (frame_pointer_needed)
            {
              RTX_FRAME_RELATED_P (insn) = 1;
              add_reg_note (insn, REG_CFA_ADJUST_CFA,
                            gen_rtx_SET (fp, stack_pointer_rtx));
            }

          insn = emit_move_insn (my_fp, plus_constant (GET_MODE (my_fp),
                                                       my_fp, neg_size));

          if (frame_pointer_needed)
            {
              RTX_FRAME_RELATED_P (insn) = 1;
              add_reg_note (insn, REG_CFA_ADJUST_CFA,
                            gen_rtx_SET (fp, plus_constant (Pmode, fp,
							    -size_cfa)));
            }

          /* Copy to stack pointer.  Note that since we've already
             changed the CFA to the frame pointer this operation
             need not be annotated if frame pointer is needed.
             Always move through unspec, see PR50063.
             For meaning of irq_state see movhi_sp_r insn.  */

          if (cfun->machine->is_interrupt)
            irq_state = 1;

          if (TARGET_NO_INTERRUPTS
              || cfun->machine->is_signal
              || cfun->machine->is_OS_main)
            irq_state = 0;

          if (AVR_HAVE_8BIT_SP)
            irq_state = 2;

          insn = emit_insn (gen_movhi_sp_r (stack_pointer_rtx,
                                            fp, GEN_INT (irq_state)));
          if (!frame_pointer_needed)
            {
              RTX_FRAME_RELATED_P (insn) = 1;
              add_reg_note (insn, REG_CFA_ADJUST_CFA,
                            gen_rtx_SET (stack_pointer_rtx,
                                         plus_constant (Pmode,
                                                        stack_pointer_rtx,
                                                        -size_cfa)));
            }

          fp_plus_insns = get_insns ();
          end_sequence ();

          /************  Method 2: Adjust Stack pointer  ************/

          /* Stack adjustment by means of RCALL . and/or PUSH __TMP_REG__
             can only handle specific offsets.  */

          int n_rcall = size / (AVR_3_BYTE_PC ? 3 : 2);

          if (avr_sp_immediate_operand (gen_int_mode (-size, HImode), HImode)
              // Don't use more than 3 RCALLs.
              && n_rcall <= 3)
            {
              rtx_insn *sp_plus_insns;

              start_sequence ();

              insn = emit_move_insn (stack_pointer_rtx,
                                     plus_constant (Pmode, stack_pointer_rtx,
                                                    -size));
              RTX_FRAME_RELATED_P (insn) = 1;
              add_reg_note (insn, REG_CFA_ADJUST_CFA,
                            gen_rtx_SET (stack_pointer_rtx,
                                         plus_constant (Pmode,
                                                        stack_pointer_rtx,
                                                        -size_cfa)));
              if (frame_pointer_needed)
                {
                  insn = emit_move_insn (fp, stack_pointer_rtx);
                  RTX_FRAME_RELATED_P (insn) = 1;
                }

              sp_plus_insns = get_insns ();
              end_sequence ();

              /************ Use shortest method  ************/

              emit_insn (get_sequence_length (sp_plus_insns)
                         < get_sequence_length (fp_plus_insns)
                         ? sp_plus_insns
                         : fp_plus_insns);
            }
          else
            {
              emit_insn (fp_plus_insns);
            }

          cfun->machine->stack_usage += size_cfa;
        } /* !minimize && size != 0 */
    } /* !minimize */
}


/*  Output function prologue.  */

void
avr_expand_prologue (void)
{
  HARD_REG_SET set;
  HOST_WIDE_INT size;

  size = get_frame_size() + avr_outgoing_args_size();

  cfun->machine->stack_usage = 0;

  /* Prologue: naked.  */
  if (cfun->machine->is_naked)
    {
      return;
    }

  avr_regs_to_save (&set);

  if (cfun->machine->is_interrupt || cfun->machine->is_signal)
    {
      int treg = AVR_TMP_REGNO;
      /* Enable interrupts.  */
      if (cfun->machine->is_interrupt)
        emit_insn (gen_enable_interrupt ());

      if (cfun->machine->gasisr.maybe)
        {
          /* Let GAS PR21472 emit prologue preamble for us which handles SREG,
             ZERO_REG and TMP_REG and one additional, optional register for
             us in an optimal way.  This even scans through inline asm.  */

          cfun->machine->gasisr.yes = 1;

          // The optional reg or TMP_REG if we don't need one.  If we need one,
          // remove that reg from SET so that it's not puhed / popped twice.
          // We also use it below instead of TMP_REG in some places.

          treg = avr_hregs_split_reg (&set);
          if (treg < 0)
            treg = AVR_TMP_REGNO;
          cfun->machine->gasisr.regno = treg;

          // The worst case of pushes.  The exact number can be inferred
          // at assembly time by magic expression __gcc_isr.n_pushed.
          cfun->machine->stack_usage += 3 + (treg != AVR_TMP_REGNO);

          // Emit a Prologue chunk.  Epilogue chunk(s) might follow.
          // The final Done chunk is emit by final postscan.
          emit_insn (gen_gasisr (GEN_INT (GASISR_Prologue), GEN_INT (treg)));
        }
      else // !TARGET_GASISR_PROLOGUES: Classic, dumb prologue preamble.
        {
          /* Push zero reg.  */
          emit_push_byte (AVR_ZERO_REGNO, true);

          /* Push tmp reg.  */
          emit_push_byte (AVR_TMP_REGNO, true);

          /* Push SREG.  */
          /* ??? There's no dwarf2 column reserved for SREG.  */
          emit_push_sfr (sreg_rtx, false, false /* clr */, AVR_TMP_REGNO);

          /* Clear zero reg.  */
          emit_move_insn (zero_reg_rtx, const0_rtx);

          /* Prevent any attempt to delete the setting of ZERO_REG!  */
          emit_use (zero_reg_rtx);
        }

      /* Push and clear RAMPD/X/Y/Z if present and low-part register is used.
         ??? There are no dwarf2 columns reserved for RAMPD/X/Y/Z.  */

      if (AVR_HAVE_RAMPD)
        emit_push_sfr (rampd_rtx, false /* frame */, true /* clr */, treg);

      if (AVR_HAVE_RAMPX
          && TEST_HARD_REG_BIT (set, REG_X)
          && TEST_HARD_REG_BIT (set, REG_X + 1))
        {
          emit_push_sfr (rampx_rtx, false /* frame */, true /* clr */, treg);
        }

      if (AVR_HAVE_RAMPY
          && (frame_pointer_needed
              || (TEST_HARD_REG_BIT (set, REG_Y)
                  && TEST_HARD_REG_BIT (set, REG_Y + 1))))
        {
          emit_push_sfr (rampy_rtx, false /* frame */, true /* clr */, treg);
        }

      if (AVR_HAVE_RAMPZ
          && TEST_HARD_REG_BIT (set, REG_Z)
          && TEST_HARD_REG_BIT (set, REG_Z + 1))
        {
          emit_push_sfr (rampz_rtx, false /* frame */, AVR_HAVE_RAMPD, treg);
        }
    }  /* is_interrupt is_signal */

  avr_prologue_setup_frame (size, set);

  if (flag_stack_usage_info)
    current_function_static_stack_size
      = cfun->machine->stack_usage + INCOMING_FRAME_SP_OFFSET;
}


/* Implement `TARGET_ASM_FUNCTION_END_PROLOGUE'.  */
/* Output summary at end of function prologue.  */

static void
avr_asm_function_end_prologue (FILE *file)
{
  if (cfun->machine->is_naked)
    {
      fputs ("/* prologue: naked */\n", file);
    }
  else
    {
      if (cfun->machine->is_interrupt)
        {
          fputs ("/* prologue: Interrupt */\n", file);
        }
      else if (cfun->machine->is_signal)
        {
          fputs ("/* prologue: Signal */\n", file);
        }
      else
        fputs ("/* prologue: function */\n", file);
    }

  if (ACCUMULATE_OUTGOING_ARGS)
    fprintf (file, "/* outgoing args size = %d */\n",
             avr_outgoing_args_size());

  fprintf (file, "/* frame size = " HOST_WIDE_INT_PRINT_DEC " */\n",
           (HOST_WIDE_INT) get_frame_size());

  if (!cfun->machine->gasisr.yes)
    {
      fprintf (file, "/* stack size = %d */\n", cfun->machine->stack_usage);
      // Create symbol stack offset so all functions have it. Add 1 to stack
      // usage for offset so that SP + .L__stack_offset = return address.
      fprintf (file, ".L__stack_usage = %d\n", cfun->machine->stack_usage);
    }
  else
    {
      int used_by_gasisr = 3 + (cfun->machine->gasisr.regno != AVR_TMP_REGNO);
      int to = cfun->machine->stack_usage;
      int from = to - used_by_gasisr;
      // Number of pushed regs is only known at assembly-time.
      fprintf (file, "/* stack size = %d...%d */\n", from , to);
      fprintf (file, ".L__stack_usage = %d + __gcc_isr.n_pushed\n", from);
    }
}


/* Implement `EPILOGUE_USES'.  */

int
avr_epilogue_uses (int regno ATTRIBUTE_UNUSED)
{
  if (reload_completed
      && cfun->machine
      && (cfun->machine->is_interrupt || cfun->machine->is_signal))
    return 1;
  return 0;
}

/*  Helper for avr_expand_epilogue.  Emit a pop of a byte register.  */

static void
emit_pop_byte (unsigned regno)
{
  rtx mem, reg;

  mem = gen_rtx_PRE_INC (HImode, stack_pointer_rtx);
  mem = gen_frame_mem (QImode, mem);
  reg = gen_rtx_REG (QImode, regno);

  emit_insn (gen_rtx_SET (reg, mem));
}

/*  Output RTL epilogue.  */

void
avr_expand_epilogue (bool sibcall_p)
{
  int live_seq;
  HARD_REG_SET set;
  int minimize;
  HOST_WIDE_INT size;
  bool isr_p = cfun->machine->is_interrupt || cfun->machine->is_signal;

  size = get_frame_size() + avr_outgoing_args_size();

  /* epilogue: naked  */
  if (cfun->machine->is_naked)
    {
      gcc_assert (!sibcall_p);

      emit_jump_insn (gen_return ());
      return;
    }

  avr_regs_to_save (&set);
  live_seq = sequent_regs_live ();

  minimize = (TARGET_CALL_PROLOGUES
              && live_seq
              && !isr_p
              && !cfun->machine->is_OS_task
              && !cfun->machine->is_OS_main
              && !AVR_TINY);

  if (minimize
      && (live_seq > 4
          || frame_pointer_needed
          || size))
    {
      /*  Get rid of frame.  */

      if (!frame_pointer_needed)
        {
          emit_move_insn (frame_pointer_rtx, stack_pointer_rtx);
        }

      if (size)
        {
          emit_move_insn (frame_pointer_rtx,
                          plus_constant (Pmode, frame_pointer_rtx, size));
        }

      emit_insn (gen_epilogue_restores (gen_int_mode (live_seq, HImode)));
      return;
    }

  if (size)
    {
      /* Try two methods to adjust stack and select shortest.  */

      int irq_state = -1;
      rtx fp, my_fp;
      rtx_insn *fp_plus_insns;
      HOST_WIDE_INT size_max;

      gcc_assert (frame_pointer_needed
                  || !isr_p
                  || !crtl->is_leaf);

      fp = my_fp = (frame_pointer_needed
                    ? frame_pointer_rtx
                    : gen_rtx_REG (Pmode, REG_X));

      if (AVR_HAVE_8BIT_SP)
        {
          /* The high byte (r29) does not change:
             Prefer SUBI (1 cycle) over SBIW (2 cycles).  */

          my_fp = all_regs_rtx[FRAME_POINTER_REGNUM];
        }

      /* For rationale see comment in prologue generation.  */

      size_max = (HOST_WIDE_INT) GET_MODE_MASK (GET_MODE (my_fp));
      if (size > size_max)
        size = size_max;
      size = trunc_int_for_mode (size, GET_MODE (my_fp));

      /********** Method 1: Adjust fp register  **********/

      start_sequence ();

      if (!frame_pointer_needed)
        emit_move_insn (fp, stack_pointer_rtx);

      emit_move_insn (my_fp, plus_constant (GET_MODE (my_fp), my_fp, size));

      /* Copy to stack pointer.  */

      if (TARGET_NO_INTERRUPTS)
        irq_state = 0;

      if (AVR_HAVE_8BIT_SP)
        irq_state = 2;

      emit_insn (gen_movhi_sp_r (stack_pointer_rtx, fp,
                                 GEN_INT (irq_state)));

      fp_plus_insns = get_insns ();
      end_sequence ();

      /********** Method 2: Adjust Stack pointer  **********/

      if (avr_sp_immediate_operand (gen_int_mode (size, HImode), HImode))
        {
          rtx_insn *sp_plus_insns;

          start_sequence ();

          emit_move_insn (stack_pointer_rtx,
                          plus_constant (Pmode, stack_pointer_rtx, size));

          sp_plus_insns = get_insns ();
          end_sequence ();

          /************ Use shortest method  ************/

          emit_insn (get_sequence_length (sp_plus_insns)
                     < get_sequence_length (fp_plus_insns)
                     ? sp_plus_insns
                     : fp_plus_insns);
        }
      else
        emit_insn (fp_plus_insns);
    } /* size != 0 */

  if (frame_pointer_needed
      && !(cfun->machine->is_OS_task || cfun->machine->is_OS_main))
    {
      /* Restore previous frame_pointer.  See avr_expand_prologue for
         rationale for not using pophi.  */

      emit_pop_byte (REG_Y + 1);
      emit_pop_byte (REG_Y);
    }

  /* Restore used registers.  */

  int treg = AVR_TMP_REGNO;

  if (isr_p
      && cfun->machine->gasisr.yes)
    {
      treg = cfun->machine->gasisr.regno;
      CLEAR_HARD_REG_BIT (set, treg);
    }

  for (int reg = 31; reg >= 0; --reg)
    if (TEST_HARD_REG_BIT (set, reg))
      emit_pop_byte (reg);

  if (isr_p)
    {
      /* Restore RAMPZ/Y/X/D using tmp_reg as scratch.
         The conditions to restore them must be tha same as in prologue.  */

      if (AVR_HAVE_RAMPZ
          && TEST_HARD_REG_BIT (set, REG_Z)
          && TEST_HARD_REG_BIT (set, REG_Z + 1))
        {
          emit_pop_byte (treg);
          emit_move_insn (rampz_rtx, all_regs_rtx[treg]);
        }

      if (AVR_HAVE_RAMPY
          && (frame_pointer_needed
              || (TEST_HARD_REG_BIT (set, REG_Y)
                  && TEST_HARD_REG_BIT (set, REG_Y + 1))))
        {
          emit_pop_byte (treg);
          emit_move_insn (rampy_rtx, all_regs_rtx[treg]);
        }

      if (AVR_HAVE_RAMPX
          && TEST_HARD_REG_BIT (set, REG_X)
          && TEST_HARD_REG_BIT (set, REG_X + 1))
        {
          emit_pop_byte (treg);
          emit_move_insn (rampx_rtx, all_regs_rtx[treg]);
        }

      if (AVR_HAVE_RAMPD)
        {
          emit_pop_byte (treg);
          emit_move_insn (rampd_rtx, all_regs_rtx[treg]);
        }

      if (cfun->machine->gasisr.yes)
        {
          // Emit an Epilogue chunk.
          emit_insn (gen_gasisr (GEN_INT (GASISR_Epilogue),
                                 GEN_INT (cfun->machine->gasisr.regno)));
        }
      else // !TARGET_GASISR_PROLOGUES
        {
          /* Restore SREG using tmp_reg as scratch.  */

          emit_pop_byte (AVR_TMP_REGNO);
          emit_move_insn (sreg_rtx, tmp_reg_rtx);

          /* Restore tmp REG.  */
          emit_pop_byte (AVR_TMP_REGNO);

          /* Restore zero REG.  */
          emit_pop_byte (AVR_ZERO_REGNO);
        }
    }

  if (!sibcall_p)
    emit_jump_insn (gen_return ());
}


/* Implement `TARGET_ASM_FUNCTION_BEGIN_EPILOGUE'.  */

static void
avr_asm_function_begin_epilogue (FILE *file)
{
  app_disable();
  fprintf (file, "/* epilogue start */\n");
}


/* Implement `TARGET_CANNOT_MODITY_JUMPS_P'.  */

static bool
avr_cannot_modify_jumps_p (void)
{
  /* Naked Functions must not have any instructions after
     their epilogue, see PR42240 */

  if (reload_completed
      && cfun->machine
      && cfun->machine->is_naked)
    {
      return true;
    }

  return false;
}


/* Implement `TARGET_MODE_DEPENDENT_ADDRESS_P'.  */

static bool
avr_mode_dependent_address_p (const_rtx addr ATTRIBUTE_UNUSED, addr_space_t as)
{
  /* FIXME:  Non-generic addresses are not mode-dependent in themselves.
       This hook just serves to hack around PR rtl-optimization/52543 by
       claiming that non-generic addresses were mode-dependent so that
       lower-subreg.c will skip these addresses.  lower-subreg.c sets up fake
       RTXes to probe SET and MEM costs and assumes that MEM is always in the
       generic address space which is not true.  */

  return !ADDR_SPACE_GENERIC_P (as);
}


/* Return true if rtx X is a CONST_INT, CONST or SYMBOL_REF
   address with the `absdata' variable attribute, i.e. respective
   data can be read / written by LDS / STS instruction.
   This is used only for AVR_TINY.  */

static bool
avr_address_tiny_absdata_p (rtx x, machine_mode mode)
{
  if (CONST == GET_CODE (x))
    x = XEXP (XEXP (x, 0), 0);

  if (SYMBOL_REF_P (x))
    return SYMBOL_REF_FLAGS (x) & AVR_SYMBOL_FLAG_TINY_ABSDATA;

  if (CONST_INT_P (x)
      && IN_RANGE (INTVAL (x), 0, 0xc0 - GET_MODE_SIZE (mode)))
    return true;

  return false;
}


/* Helper function for `avr_legitimate_address_p'.  */

static inline bool
avr_reg_ok_for_addr_p (rtx reg, addr_space_t as,
                       RTX_CODE outer_code, bool strict)
{
  return (REG_P (reg)
          && (avr_regno_mode_code_ok_for_base_p (REGNO (reg), QImode,
                                                 as, outer_code, UNKNOWN)
              || (!strict
                  && REGNO (reg) >= FIRST_PSEUDO_REGISTER)));
}


/* Return nonzero if X (an RTX) is a legitimate memory address on the target
   machine for a memory operand of mode MODE.  */

static bool
avr_legitimate_address_p (machine_mode mode, rtx x, bool strict)
{
  bool ok = CONSTANT_ADDRESS_P (x);

  switch (GET_CODE (x))
    {
    case REG:
      ok = avr_reg_ok_for_addr_p (x, ADDR_SPACE_GENERIC,
                                  MEM, strict);

      if (strict
          && GET_MODE_SIZE (mode) > 4
          && REG_X == REGNO (x))
        {
          ok = false;
        }
      break;

    case POST_INC:
    case PRE_DEC:
      ok = avr_reg_ok_for_addr_p (XEXP (x, 0), ADDR_SPACE_GENERIC,
                                  GET_CODE (x), strict);
      break;

    case PLUS:
      {
        rtx reg = XEXP (x, 0);
        rtx op1 = XEXP (x, 1);

        if (REG_P (reg)
            && CONST_INT_P (op1)
            && INTVAL (op1) >= 0)
          {
            bool fit = IN_RANGE (INTVAL (op1), 0, MAX_LD_OFFSET (mode));

            if (fit)
              {
                ok = (! strict
                      || avr_reg_ok_for_addr_p (reg, ADDR_SPACE_GENERIC,
                                                PLUS, strict));

                if (reg == frame_pointer_rtx
                    || reg == arg_pointer_rtx)
                  {
                    ok = true;
                  }
              }
            else if (frame_pointer_needed
                     && reg == frame_pointer_rtx)
              {
                ok = true;
              }
          }
      }
      break;

    default:
      break;
    }

  if (AVR_TINY
      && CONSTANT_ADDRESS_P (x))
    {
      /* avrtiny's load / store instructions only cover addresses 0..0xbf:
         IN / OUT range is 0..0x3f and LDS / STS can access 0x40..0xbf.  */

      ok = avr_address_tiny_absdata_p (x, mode);
    }

  if (avr_log.legitimate_address_p)
    {
      avr_edump ("\n%?: ret=%d, mode=%m strict=%d "
                 "reload_completed=%d reload_in_progress=%d %s:",
                 ok, mode, strict, reload_completed, reload_in_progress,
                 reg_renumber ? "(reg_renumber)" : "");

      if (GET_CODE (x) == PLUS
          && REG_P (XEXP (x, 0))
          && CONST_INT_P (XEXP (x, 1))
          && IN_RANGE (INTVAL (XEXP (x, 1)), 0, MAX_LD_OFFSET (mode))
          && reg_renumber)
        {
          avr_edump ("(r%d ---> r%d)", REGNO (XEXP (x, 0)),
                     true_regnum (XEXP (x, 0)));
        }

      avr_edump ("\n%r\n", x);
    }

  return ok;
}


/* Former implementation of TARGET_LEGITIMIZE_ADDRESS,
   now only a helper for avr_addr_space_legitimize_address.  */
/* Attempts to replace X with a valid
   memory address for an operand of mode MODE  */

static rtx
avr_legitimize_address (rtx x, rtx oldx, machine_mode mode)
{
  bool big_offset_p = false;

  x = oldx;

  if (AVR_TINY)
    {
      if (CONSTANT_ADDRESS_P (x)
          && ! avr_address_tiny_absdata_p (x, mode))
        {
          x = force_reg (Pmode, x);
        }
    }

  if (GET_CODE (oldx) == PLUS
      && REG_P (XEXP (oldx, 0)))
    {
      if (REG_P (XEXP (oldx, 1)))
        x = force_reg (GET_MODE (oldx), oldx);
      else if (CONST_INT_P (XEXP (oldx, 1)))
        {
          int offs = INTVAL (XEXP (oldx, 1));
          if (frame_pointer_rtx != XEXP (oldx, 0)
              && offs > MAX_LD_OFFSET (mode))
            {
              big_offset_p = true;
              x = force_reg (GET_MODE (oldx), oldx);
            }
        }
    }

  if (avr_log.legitimize_address)
    {
      avr_edump ("\n%?: mode=%m\n %r\n", mode, oldx);

      if (x != oldx)
        avr_edump (" %s --> %r\n", big_offset_p ? "(big offset)" : "", x);
    }

  return x;
}


/* Implement `LEGITIMIZE_RELOAD_ADDRESS'.  */
/* This will allow register R26/27 to be used where it is no worse than normal
   base pointers R28/29 or R30/31.  For example, if base offset is greater
   than 63 bytes or for R++ or --R addressing.  */

rtx
avr_legitimize_reload_address (rtx *px, machine_mode mode,
                               int opnum, int type, int addr_type,
                               int ind_levels ATTRIBUTE_UNUSED,
                               rtx (*mk_memloc)(rtx,int))
{
  rtx x = *px;

  if (avr_log.legitimize_reload_address)
    avr_edump ("\n%?:%m %r\n", mode, x);

  if (1 && (GET_CODE (x) == POST_INC
            || GET_CODE (x) == PRE_DEC))
    {
      push_reload (XEXP (x, 0), XEXP (x, 0), &XEXP (x, 0), &XEXP (x, 0),
                   POINTER_REGS, GET_MODE (x), GET_MODE (x), 0, 0,
                   opnum, RELOAD_OTHER);

      if (avr_log.legitimize_reload_address)
        avr_edump (" RCLASS.1 = %R\n IN = %r\n OUT = %r\n",
                   POINTER_REGS, XEXP (x, 0), XEXP (x, 0));

      return x;
    }

  if (GET_CODE (x) == PLUS
      && REG_P (XEXP (x, 0))
      && reg_equiv_constant (REGNO (XEXP (x, 0))) == 0
      && CONST_INT_P (XEXP (x, 1))
      && INTVAL (XEXP (x, 1)) >= 1)
    {
      bool fit = INTVAL (XEXP (x, 1)) <= MAX_LD_OFFSET (mode);

      if (fit)
        {
          if (reg_equiv_address (REGNO (XEXP (x, 0))) != 0)
            {
              int regno = REGNO (XEXP (x, 0));
              rtx mem = mk_memloc (x, regno);

              push_reload (XEXP (mem, 0), NULL_RTX, &XEXP (mem, 0), NULL,
                           POINTER_REGS, Pmode, VOIDmode, 0, 0,
                           1, (enum reload_type) addr_type);

              if (avr_log.legitimize_reload_address)
                avr_edump (" RCLASS.2 = %R\n IN = %r\n OUT = %r\n",
                           POINTER_REGS, XEXP (mem, 0), NULL_RTX);

              push_reload (mem, NULL_RTX, &XEXP (x, 0), NULL,
                           BASE_POINTER_REGS, GET_MODE (x), VOIDmode, 0, 0,
                           opnum, (enum reload_type) type);

              if (avr_log.legitimize_reload_address)
                avr_edump (" RCLASS.2 = %R\n IN = %r\n OUT = %r\n",
                           BASE_POINTER_REGS, mem, NULL_RTX);

              return x;
            }
        }
      else if (! (frame_pointer_needed
                  && XEXP (x, 0) == frame_pointer_rtx))
        {
          push_reload (x, NULL_RTX, px, NULL,
                       POINTER_REGS, GET_MODE (x), VOIDmode, 0, 0,
                       opnum, (enum reload_type) type);

          if (avr_log.legitimize_reload_address)
            avr_edump (" RCLASS.3 = %R\n IN = %r\n OUT = %r\n",
                       POINTER_REGS, x, NULL_RTX);

          return x;
        }
    }

  return NULL_RTX;
}


/* Helper function to print assembler resp. track instruction
   sequence lengths.  Always return "".

   If PLEN == NULL:
       Output assembler code from template TPL with operands supplied
       by OPERANDS.  This is just forwarding to output_asm_insn.

   If PLEN != NULL:
       If N_WORDS >= 0  Add N_WORDS to *PLEN.
       If N_WORDS < 0   Set *PLEN to -N_WORDS.
       Don't output anything.
*/

static const char*
avr_asm_len (const char* tpl, rtx* operands, int* plen, int n_words)
{
  if (plen == NULL)
    output_asm_insn (tpl, operands);
  else
    {
      if (n_words < 0)
        *plen = -n_words;
      else
        *plen += n_words;
    }

  return "";
}


/* Return a pointer register name as a string.  */

static const char*
ptrreg_to_str (int regno)
{
  switch (regno)
    {
    case REG_X: return "X";
    case REG_Y: return "Y";
    case REG_Z: return "Z";
    default:
      output_operand_lossage ("address operand requires constraint for"
                              " X, Y, or Z register");
    }
  return NULL;
}

/* Return the condition name as a string.
   Used in conditional jump constructing  */

static const char*
cond_string (enum rtx_code code)
{
  bool cc_overflow_unusable = false;

  switch (code)
    {
    case NE:
      return "ne";
    case EQ:
      return "eq";
    case GE:
      if (cc_overflow_unusable)
        return "pl";
      else
        return "ge";
    case LT:
      if (cc_overflow_unusable)
        return "mi";
      else
        return "lt";
    case GEU:
      return "sh";
    case LTU:
      return "lo";
    default:
      gcc_unreachable ();
    }

  return "";
}


/* Return true if rtx X is a CONST or SYMBOL_REF with progmem.
   This must be used for AVR_TINY only because on other cores
   the flash memory is not visible in the RAM address range and
   cannot be read by, say,  LD instruction.  */

static bool
avr_address_tiny_pm_p (rtx x)
{
  if (CONST == GET_CODE (x))
    x = XEXP (XEXP (x, 0), 0);

  if (SYMBOL_REF_P (x))
    return SYMBOL_REF_FLAGS (x) & AVR_SYMBOL_FLAG_TINY_PM;

  return false;
}

/* Implement `TARGET_PRINT_OPERAND_ADDRESS'.  */
/* Output ADDR to FILE as address.  */

static void
avr_print_operand_address (FILE *file, machine_mode /*mode*/, rtx addr)
{
  if (AVR_TINY
      && avr_address_tiny_pm_p (addr))
    {
      addr = plus_constant (Pmode, addr, avr_arch->flash_pm_offset);
    }

  switch (GET_CODE (addr))
    {
    case REG:
      fprintf (file, "%s", ptrreg_to_str (REGNO (addr)));
      break;

    case PRE_DEC:
      fprintf (file, "-%s", ptrreg_to_str (REGNO (XEXP (addr, 0))));
      break;

    case POST_INC:
      fprintf (file, "%s+", ptrreg_to_str (REGNO (XEXP (addr, 0))));
      break;

    default:
      if (CONSTANT_ADDRESS_P (addr)
          && text_segment_operand (addr, VOIDmode))
        {
          rtx x = addr;
          if (GET_CODE (x) == CONST)
            x = XEXP (x, 0);
          if (GET_CODE (x) == PLUS && CONST_INT_P (XEXP (x, 1)))
            {
              /* Assembler gs() will implant word address.  Make offset
                 a byte offset inside gs() for assembler.  This is
                 needed because the more logical (constant+gs(sym)) is not
                 accepted by gas.  For 128K and smaller devices this is ok.
                 For large devices it will create a trampoline to offset
                 from symbol which may not be what the user really wanted.  */

              fprintf (file, "gs(");
              output_addr_const (file, XEXP (x, 0));
              fprintf (file, "+" HOST_WIDE_INT_PRINT_DEC ")",
                       2 * INTVAL (XEXP (x, 1)));
              if (AVR_3_BYTE_PC)
                if (warning (0, "pointer offset from symbol maybe incorrect"))
                  {
                    output_addr_const (stderr, addr);
                    fprintf (stderr, "\n");
                  }
            }
          else
            {
              fprintf (file, "gs(");
              output_addr_const (file, addr);
              fprintf (file, ")");
            }
        }
      else
        output_addr_const (file, addr);
    }
}


/* Implement `TARGET_PRINT_OPERAND_PUNCT_VALID_P'.  */

static bool
avr_print_operand_punct_valid_p (unsigned char code)
{
  return code == '~' || code == '!';
}


/* Implement `TARGET_PRINT_OPERAND'.  */
/* Output X as assembler operand to file FILE.
   For a description of supported %-codes, see top of avr.md.  */

static void
avr_print_operand (FILE *file, rtx x, int code)
{
  int abcd = 0, ef = 0, ij = 0;

  if (code >= 'A' && code <= 'D')
    abcd = code - 'A';
  else if (code == 'E' || code == 'F')
    ef = code - 'E';
  else if (code == 'I' || code == 'J')
    ij = code - 'I';

  if (code == '~')
    {
      if (!AVR_HAVE_JMP_CALL)
        fputc ('r', file);
    }
  else if (code == '!')
    {
      if (AVR_HAVE_EIJMP_EICALL)
        fputc ('e', file);
    }
  else if (code == 't'
           || code == 'T')
    {
      static int t_regno = -1;
      static int t_nbits = -1;

      if (REG_P (x) && t_regno < 0 && code == 'T')
        {
          t_regno = REGNO (x);
          t_nbits = GET_MODE_BITSIZE (GET_MODE (x));
        }
      else if (CONST_INT_P (x) && t_regno >= 0
               && IN_RANGE (INTVAL (x), 0, t_nbits - 1))
        {
          int bpos = INTVAL (x);

          fprintf (file, "%s", reg_names[t_regno + bpos / 8]);
          if (code == 'T')
            fprintf (file, ",%d", bpos % 8);

          t_regno = -1;
        }
      else
        fatal_insn ("operands to %T/%t must be reg + const_int:", x);
    }
  else if (code == 'E' || code == 'F')
    {
      rtx op = XEXP (x, 0);
      fprintf (file, "%s", reg_names[REGNO (op) + ef]);
    }
  else if (code == 'I' || code == 'J')
    {
      rtx op = XEXP (XEXP (x, 0), 0);
      fprintf (file, "%s", reg_names[REGNO (op) + ij]);
    }
  else if (REG_P (x))
    {
      if (x == zero_reg_rtx)
        fprintf (file, "__zero_reg__");
      else if (code == 'r' && REGNO (x) < 32)
        fprintf (file, "%d", (int) REGNO (x));
      else
        fprintf (file, "%s", reg_names[REGNO (x) + abcd]);
    }
  else if (CONST_INT_P (x))
    {
      HOST_WIDE_INT ival = INTVAL (x);

      if ('i' != code)
        fprintf (file, HOST_WIDE_INT_PRINT_DEC, ival + abcd);
      else if (low_io_address_operand (x, VOIDmode)
               || high_io_address_operand (x, VOIDmode))
        {
          if (AVR_HAVE_RAMPZ && ival == avr_addr.rampz)
            fprintf (file, "__RAMPZ__");
          else if (AVR_HAVE_RAMPY && ival == avr_addr.rampy)
            fprintf (file, "__RAMPY__");
          else if (AVR_HAVE_RAMPX && ival == avr_addr.rampx)
            fprintf (file, "__RAMPX__");
          else if (AVR_HAVE_RAMPD && ival == avr_addr.rampd)
            fprintf (file, "__RAMPD__");
          else if ((AVR_XMEGA || AVR_TINY) && ival == avr_addr.ccp)
            fprintf (file, "__CCP__");
          else if (ival == avr_addr.sreg)   fprintf (file, "__SREG__");
          else if (ival == avr_addr.sp_l)   fprintf (file, "__SP_L__");
          else if (ival == avr_addr.sp_h)   fprintf (file, "__SP_H__");
          else
            {
              fprintf (file, HOST_WIDE_INT_PRINT_HEX,
                       ival - avr_arch->sfr_offset);
            }
        }
      else
        fatal_insn ("bad address, not an I/O address:", x);
    }
  else if (MEM_P (x))
    {
      rtx addr = XEXP (x, 0);

      if (code == 'm')
        {
          if (!CONSTANT_P (addr))
            fatal_insn ("bad address, not a constant:", addr);
          /* Assembler template with m-code is data - not progmem section */
          if (text_segment_operand (addr, VOIDmode))
            if (warning (0, "accessing data memory with"
                         " program memory address"))
              {
                output_addr_const (stderr, addr);
                fprintf(stderr,"\n");
              }
          output_addr_const (file, addr);
        }
      else if (code == 'i')
        {
          avr_print_operand (file, addr, 'i');
        }
      else if (code == 'o')
        {
          if (GET_CODE (addr) != PLUS)
            fatal_insn ("bad address, not (reg+disp):", addr);

          avr_print_operand (file, XEXP (addr, 1), 0);
        }
      else if (code == 'b')
        {
          if (GET_CODE (addr) != PLUS)
            fatal_insn ("bad address, not (reg+disp):", addr);

          avr_print_operand_address (file, VOIDmode, XEXP (addr, 0));
        }
      else if (code == 'p' || code == 'r')
        {
          if (GET_CODE (addr) != POST_INC && GET_CODE (addr) != PRE_DEC)
            fatal_insn ("bad address, not post_inc or pre_dec:", addr);

          if (code == 'p')
            /* X, Y, Z */
            avr_print_operand_address (file, VOIDmode, XEXP (addr, 0));
          else
            avr_print_operand (file, XEXP (addr, 0), 0);  /* r26, r28, r30 */
        }
      else if (GET_CODE (addr) == PLUS)
        {
          avr_print_operand_address (file, VOIDmode, XEXP (addr, 0));
          if (REGNO (XEXP (addr, 0)) == REG_X)
            fatal_insn ("internal compiler error.  Bad address:"
                        ,addr);
          fputc ('+', file);
          avr_print_operand (file, XEXP (addr, 1), code);
        }
      else
        avr_print_operand_address (file, VOIDmode, addr);
    }
  else if (code == 'i')
    {
      if (SYMBOL_REF_P (x) && (SYMBOL_REF_FLAGS (x) & SYMBOL_FLAG_IO))
	avr_print_operand_address
	  (file, VOIDmode, plus_constant (HImode, x, -avr_arch->sfr_offset));
      else
	fatal_insn ("bad address, not an I/O address:", x);
    }
  else if (code == 'x')
    {
      /* Constant progmem address - like used in jmp or call */
      if (text_segment_operand (x, VOIDmode) == 0)
        if (warning (0, "accessing program memory"
                     " with data memory address"))
          {
            output_addr_const (stderr, x);
            fprintf(stderr,"\n");
          }
      /* Use normal symbol for direct address no linker trampoline needed */
      output_addr_const (file, x);
    }
  else if (CONST_FIXED_P (x))
    {
      HOST_WIDE_INT ival = INTVAL (avr_to_int_mode (x));
      if (code != 0)
        output_operand_lossage ("Unsupported code '%c' for fixed-point:",
                                code);
      fprintf (file, HOST_WIDE_INT_PRINT_DEC, ival);
    }
  else if (CONST_DOUBLE_P (x))
    {
      long val;
      if (GET_MODE (x) != SFmode)
        fatal_insn ("internal compiler error.  Unknown mode:", x);
      REAL_VALUE_TO_TARGET_SINGLE (*CONST_DOUBLE_REAL_VALUE (x), val);
      fprintf (file, "0x%lx", val);
    }
  else if (GET_CODE (x) == CONST_STRING)
    fputs (XSTR (x, 0), file);
  else if (code == 'j')
    fputs (cond_string (GET_CODE (x)), file);
  else if (code == 'k')
    fputs (cond_string (reverse_condition (GET_CODE (x))), file);
  else
    avr_print_operand_address (file, VOIDmode, x);
}


/* Implement TARGET_USE_BY_PIECES_INFRASTRUCTURE_P.  */

/* Prefer sequence of loads/stores for moves of size upto
   two - two pairs of load/store instructions are always better
   than the 5 instruction sequence for a loop (1 instruction
   for loop counter setup, and 4 for the body of the loop). */

static bool
avr_use_by_pieces_infrastructure_p (unsigned HOST_WIDE_INT size,
                                    unsigned int align ATTRIBUTE_UNUSED,
                                    enum by_pieces_operation op,
                                    bool speed_p)
{
  if (op != MOVE_BY_PIECES
      || (speed_p && size > MOVE_MAX_PIECES))
    return default_use_by_pieces_infrastructure_p (size, align, op, speed_p);

  return size <= MOVE_MAX_PIECES;
}

/* Choose mode for jump insn:
   1 - relative jump in range -63 <= x <= 62 ;
   2 - relative jump in range -2046 <= x <= 2045 ;
   3 - absolute jump (only for ATmega[16]03).  */

int
avr_jump_mode (rtx x, rtx_insn *insn)
{
  int dest_addr = INSN_ADDRESSES (INSN_UID (GET_CODE (x) == LABEL_REF
                                            ? XEXP (x, 0) : x));
  int cur_addr = INSN_ADDRESSES (INSN_UID (insn));
  int jump_distance = cur_addr - dest_addr;

  if (IN_RANGE (jump_distance, -63, 62))
    return 1;
  else if (IN_RANGE (jump_distance, -2046, 2045))
    return 2;
  else if (AVR_HAVE_JMP_CALL)
    return 3;

  return 2;
}

/* Return an AVR condition jump commands.
   X is a comparison RTX.
   LEN is a number returned by avr_jump_mode function.
   If REVERSE nonzero then condition code in X must be reversed.  */

const char*
ret_cond_branch (rtx x, int len, int reverse)
{
  RTX_CODE cond = reverse ? reverse_condition (GET_CODE (x)) : GET_CODE (x);
  bool cc_overflow_unusable = false;

  switch (cond)
    {
    case GT:
      if (cc_overflow_unusable)
	return (len == 1 ? ("breq .+2" CR_TAB
			    "brpl %0") :
		len == 2 ? ("breq .+4" CR_TAB
			    "brmi .+2" CR_TAB
			    "rjmp %0") :
		("breq .+6" CR_TAB
		 "brmi .+4" CR_TAB
		 "jmp %0"));

      else
	return (len == 1 ? ("breq .+2" CR_TAB
			    "brge %0") :
		len == 2 ? ("breq .+4" CR_TAB
			    "brlt .+2" CR_TAB
			    "rjmp %0") :
		("breq .+6" CR_TAB
		 "brlt .+4" CR_TAB
		 "jmp %0"));
    case GTU:
      return (len == 1 ? ("breq .+2" CR_TAB
                          "brsh %0") :
              len == 2 ? ("breq .+4" CR_TAB
                          "brlo .+2" CR_TAB
                          "rjmp %0") :
              ("breq .+6" CR_TAB
               "brlo .+4" CR_TAB
               "jmp %0"));
    case LE:
      if (cc_overflow_unusable)
	return (len == 1 ? ("breq %0" CR_TAB
			    "brmi %0") :
		len == 2 ? ("breq .+2" CR_TAB
			    "brpl .+2" CR_TAB
			    "rjmp %0") :
		("breq .+2" CR_TAB
		 "brpl .+4" CR_TAB
		 "jmp %0"));
      else
	return (len == 1 ? ("breq %0" CR_TAB
			    "brlt %0") :
		len == 2 ? ("breq .+2" CR_TAB
			    "brge .+2" CR_TAB
			    "rjmp %0") :
		("breq .+2" CR_TAB
		 "brge .+4" CR_TAB
		 "jmp %0"));
    case LEU:
      return (len == 1 ? ("breq %0" CR_TAB
                          "brlo %0") :
              len == 2 ? ("breq .+2" CR_TAB
                          "brsh .+2" CR_TAB
			  "rjmp %0") :
              ("breq .+2" CR_TAB
               "brsh .+4" CR_TAB
	       "jmp %0"));
    default:
      if (reverse)
	{
	  switch (len)
	    {
	    case 1:
	      return "br%k1 %0";
	    case 2:
	      return ("br%j1 .+2" CR_TAB
		      "rjmp %0");
	    default:
	      return ("br%j1 .+4" CR_TAB
		      "jmp %0");
	    }
	}
      else
        {
          switch (len)
            {
            case 1:
              return "br%j1 %0";
            case 2:
              return ("br%k1 .+2" CR_TAB
                      "rjmp %0");
            default:
              return ("br%k1 .+4" CR_TAB
                      "jmp %0");
            }
        }
    }
  return "";
}


/* Worker function for `FINAL_PRESCAN_INSN'.  */
/* Output insn cost for next insn.  */

void
avr_final_prescan_insn (rtx_insn *insn, rtx *operand ATTRIBUTE_UNUSED,
                        int num_operands ATTRIBUTE_UNUSED)
{
  if (avr_log.rtx_costs)
    {
      rtx set = single_set (insn);

      if (set)
        fprintf (asm_out_file, "/* DEBUG: cost = %d.  */\n",
                 set_src_cost (SET_SRC (set), GET_MODE (SET_DEST (set)),
			       optimize_insn_for_speed_p ()));
      else
        fprintf (asm_out_file, "/* DEBUG: pattern-cost = %d.  */\n",
                 rtx_cost (PATTERN (insn), VOIDmode, INSN, 0,
                           optimize_insn_for_speed_p()));
    }

  if (avr_log.insn_addresses)
    fprintf (asm_out_file, ";; ADDR = %d\n",
             (int) INSN_ADDRESSES (INSN_UID (insn)));
}


/* Implement `TARGET_ASM_FINAL_POSTSCAN_INSN'.  */
/* When GAS generates (parts of) ISR prologue / epilogue for us, we must
   hint GAS about the end of the code to scan.  There migh be code located
   after the last epilogue.  */

static void
avr_asm_final_postscan_insn (FILE *stream, rtx_insn *insn, rtx*, int)
{
  if (cfun->machine->gasisr.yes
      && !next_real_insn (insn))
    {
      app_disable();
      fprintf (stream, "\t__gcc_isr %d,r%d\n", GASISR_Done,
               cfun->machine->gasisr.regno);
    }
}


/* Return 0 if undefined, 1 if always true or always false.  */

int
avr_simplify_comparison_p (machine_mode mode, RTX_CODE op, rtx x)
{
  unsigned int max = (mode == QImode ? 0xff :
                      mode == HImode ? 0xffff :
                      mode == PSImode ? 0xffffff :
                      mode == SImode ? 0xffffffff : 0);
  if (max && op && CONST_INT_P (x))
    {
      if (unsigned_condition (op) != op)
        max >>= 1;

      if (max != (INTVAL (x) & max)
          && INTVAL (x) != 0xff)
        return 1;
    }
  return 0;
}


/* Worker function for `FUNCTION_ARG_REGNO_P'.  */
/* Returns nonzero if REGNO is the number of a hard
   register in which function arguments are sometimes passed.  */

int
avr_function_arg_regno_p (int r)
{
  return AVR_TINY ? IN_RANGE (r, 20, 25) : IN_RANGE (r, 8, 25);
}


/* Worker function for `INIT_CUMULATIVE_ARGS'.  */
/* Initializing the variable cum for the state at the beginning
   of the argument list.  */

void
avr_init_cumulative_args (CUMULATIVE_ARGS *cum, tree fntype, rtx libname,
                          tree fndecl ATTRIBUTE_UNUSED)
{
  cum->nregs = AVR_TINY ? 6 : 18;
  cum->regno = FIRST_CUM_REG;
  if (!libname && stdarg_p (fntype))
    cum->nregs = 0;

  /* Assume the calle may be tail called */

  cfun->machine->sibcall_fails = 0;
}

/* Returns the number of registers to allocate for a function argument.  */

static int
avr_num_arg_regs (machine_mode mode, const_tree type)
{
  int size;

  if (mode == BLKmode)
    size = int_size_in_bytes (type);
  else
    size = GET_MODE_SIZE (mode);

  /* Align all function arguments to start in even-numbered registers.
     Odd-sized arguments leave holes above them.  */

  return (size + 1) & ~1;
}


/* Implement `TARGET_FUNCTION_ARG'.  */
/* Controls whether a function argument is passed
   in a register, and which register.  */

static rtx
avr_function_arg (cumulative_args_t cum_v, const function_arg_info &arg)
{
  CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);
  int bytes = avr_num_arg_regs (arg.mode, arg.type);

  if (cum->nregs && bytes <= cum->nregs)
    return gen_rtx_REG (arg.mode, cum->regno - bytes);

  return NULL_RTX;
}


/* Implement `TARGET_FUNCTION_ARG_ADVANCE'.  */
/* Update the summarizer variable CUM to advance past an argument
   in the argument list.  */

static void
avr_function_arg_advance (cumulative_args_t cum_v,
			  const function_arg_info &arg)
{
  CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);
  int bytes = avr_num_arg_regs (arg.mode, arg.type);

  cum->nregs -= bytes;
  cum->regno -= bytes;

  /* A parameter is being passed in a call-saved register.  As the original
     contents of these regs has to be restored before leaving the function,
     a function must not pass arguments in call-saved regs in order to get
     tail-called.  */

  if (cum->regno >= 8
      && cum->nregs >= 0
      && !call_used_or_fixed_reg_p (cum->regno))
    {
      /* FIXME: We ship info on failing tail-call in struct machine_function.
         This uses internals of calls.c:expand_call() and the way args_so_far
         is used.  targetm.function_ok_for_sibcall() needs to be extended to
         pass &args_so_far, too.  At present, CUMULATIVE_ARGS is target
         dependent so that such an extension is not wanted.  */

      cfun->machine->sibcall_fails = 1;
    }

  /* Test if all registers needed by the ABI are actually available.  If the
     user has fixed a GPR needed to pass an argument, an (implicit) function
     call will clobber that fixed register.  See PR45099 for an example.  */

  if (cum->regno >= 8
      && cum->nregs >= 0)
    {
      for (int regno = cum->regno; regno < cum->regno + bytes; regno++)
        if (fixed_regs[regno])
          warning (0, "fixed register %s used to pass parameter to function",
                   reg_names[regno]);
    }

  if (cum->nregs <= 0)
    {
      cum->nregs = 0;
      cum->regno = FIRST_CUM_REG;
    }
}

/* Implement `TARGET_FUNCTION_OK_FOR_SIBCALL' */
/* Decide whether we can make a sibling call to a function.  DECL is the
   declaration of the function being targeted by the call and EXP is the
   CALL_EXPR representing the call.  */

static bool
avr_function_ok_for_sibcall (tree decl_callee, tree exp_callee)
{
  tree fntype_callee;

  /* Tail-calling must fail if callee-saved regs are used to pass
     function args.  We must not tail-call when `epilogue_restores'
     is used.  Unfortunately, we cannot tell at this point if that
     actually will happen or not, and we cannot step back from
     tail-calling.  Thus, we inhibit tail-calling with -mcall-prologues.  */

  if (cfun->machine->sibcall_fails
      || TARGET_CALL_PROLOGUES)
    {
      return false;
    }

  fntype_callee = TREE_TYPE (CALL_EXPR_FN (exp_callee));

  if (decl_callee)
    {
      decl_callee = TREE_TYPE (decl_callee);
    }
  else
    {
      decl_callee = fntype_callee;

      while (FUNCTION_TYPE != TREE_CODE (decl_callee)
             && METHOD_TYPE != TREE_CODE (decl_callee))
        {
          decl_callee = TREE_TYPE (decl_callee);
        }
    }

  /* Ensure that caller and callee have compatible epilogues */

  if (cfun->machine->is_interrupt
      || cfun->machine->is_signal
      || cfun->machine->is_naked
      || avr_naked_function_p (decl_callee))
    {
      return false;
    }

  return true;
}

/***********************************************************************
  Functions for outputting various mov's for a various modes
************************************************************************/

/* Return true if a value of mode MODE is read from flash by
   __load_* function from libgcc.  */

bool
avr_load_libgcc_p (rtx op)
{
  machine_mode mode = GET_MODE (op);
  int n_bytes = GET_MODE_SIZE (mode);

  return (n_bytes > 2
          && !AVR_HAVE_LPMX
          && avr_mem_flash_p (op));
}

/* Return true if a value of mode MODE is read by __xload_* function.  */

bool
avr_xload_libgcc_p (machine_mode mode)
{
  int n_bytes = GET_MODE_SIZE (mode);

  return (n_bytes > 1
          || avr_n_flash > 1);
}


/* Fixme: This is a hack because secondary reloads don't works as expected.

   Find an unused d-register to be used as scratch in INSN.
   EXCLUDE is either NULL_RTX or some register. In the case where EXCLUDE
   is a register, skip all possible return values that overlap EXCLUDE.
   The policy for the returned register is similar to that of
   `reg_unused_after', i.e. the returned register may overlap the SET_DEST
   of INSN.

   Return a QImode d-register or NULL_RTX if nothing found.  */

static rtx
avr_find_unused_d_reg (rtx_insn *insn, rtx exclude)
{
  bool isr_p = (avr_interrupt_function_p (current_function_decl)
                || avr_signal_function_p (current_function_decl));

  for (int regno = 16; regno < 32; regno++)
    {
      rtx reg = all_regs_rtx[regno];

      if ((exclude
           && reg_overlap_mentioned_p (exclude, reg))
          || fixed_regs[regno])
        {
          continue;
        }

      /* Try non-live register */

      if (!df_regs_ever_live_p (regno)
          && (TREE_THIS_VOLATILE (current_function_decl)
              || cfun->machine->is_OS_task
              || cfun->machine->is_OS_main
              || (!isr_p && call_used_or_fixed_reg_p (regno))))
        {
          return reg;
        }

      /* Any live register can be used if it is unused after.
         Prologue/epilogue will care for it as needed.  */

      if (df_regs_ever_live_p (regno)
          && reg_unused_after (insn, reg))
        {
          return reg;
        }
    }

  return NULL_RTX;
}


/* Helper function for the next function in the case where only restricted
   version of LPM instruction is available.  */

static const char*
avr_out_lpm_no_lpmx (rtx_insn *insn, rtx *xop, int *plen)
{
  rtx dest = xop[0];
  rtx addr = xop[1];
  int n_bytes = GET_MODE_SIZE (GET_MODE (dest));
  int regno_dest;

  regno_dest = REGNO (dest);

  /* The implicit target register of LPM.  */
  xop[3] = lpm_reg_rtx;

  switch (GET_CODE (addr))
    {
    default:
      gcc_unreachable();

    case REG:

      gcc_assert (REG_Z == REGNO (addr));

      switch (n_bytes)
        {
        default:
          gcc_unreachable();

        case 1:
          avr_asm_len ("%4lpm", xop, plen, 1);

          if (regno_dest != LPM_REGNO)
            avr_asm_len ("mov %0,%3", xop, plen, 1);

          return "";

        case 2:
          if (REGNO (dest) == REG_Z)
            return avr_asm_len ("%4lpm"      CR_TAB
                                "push %3"    CR_TAB
                                "adiw %2,1"  CR_TAB
                                "%4lpm"      CR_TAB
                                "mov %B0,%3" CR_TAB
                                "pop %A0", xop, plen, 6);

          avr_asm_len ("%4lpm"      CR_TAB
                       "mov %A0,%3" CR_TAB
                       "adiw %2,1"  CR_TAB
                       "%4lpm"      CR_TAB
                       "mov %B0,%3", xop, plen, 5);

          if (!reg_unused_after (insn, addr))
            avr_asm_len ("sbiw %2,1", xop, plen, 1);

          break; /* 2 */
        }

      break; /* REG */

    case POST_INC:

      gcc_assert (REG_Z == REGNO (XEXP (addr, 0))
                  && n_bytes <= 4);

      if (regno_dest == LPM_REGNO)
        avr_asm_len ("%4lpm"      CR_TAB
                     "adiw %2,1", xop, plen, 2);
      else
        avr_asm_len ("%4lpm"      CR_TAB
                     "mov %A0,%3" CR_TAB
                     "adiw %2,1", xop, plen, 3);

      if (n_bytes >= 2)
        avr_asm_len ("%4lpm"      CR_TAB
                     "mov %B0,%3" CR_TAB
                     "adiw %2,1", xop, plen, 3);

      if (n_bytes >= 3)
        avr_asm_len ("%4lpm"      CR_TAB
                     "mov %C0,%3" CR_TAB
                     "adiw %2,1", xop, plen, 3);

      if (n_bytes >= 4)
        avr_asm_len ("%4lpm"      CR_TAB
                     "mov %D0,%3" CR_TAB
                     "adiw %2,1", xop, plen, 3);

      break; /* POST_INC */

    } /* switch CODE (addr) */

  return "";
}


/* If PLEN == NULL: Ouput instructions to load a value from a memory location
   OP[1] in AS1 to register OP[0].
   If PLEN != 0 set *PLEN to the length in words of the instruction sequence.
   Return "".  */

const char*
avr_out_lpm (rtx_insn *insn, rtx *op, int *plen)
{
  rtx xop[7];
  rtx dest = op[0];
  rtx src = SET_SRC (single_set (insn));
  rtx addr;
  int n_bytes = GET_MODE_SIZE (GET_MODE (dest));
  int segment;
  RTX_CODE code;
  addr_space_t as = MEM_ADDR_SPACE (src);

  if (plen)
    *plen = 0;

  if (MEM_P (dest))
    {
      warning (0, "writing to address space %qs not supported",
               avr_addrspace[MEM_ADDR_SPACE (dest)].name);

      return "";
    }

  addr = XEXP (src, 0);
  code = GET_CODE (addr);

  gcc_assert (REG_P (dest));
  gcc_assert (REG == code || POST_INC == code);

  xop[0] = dest;
  xop[1] = addr;
  xop[2] = lpm_addr_reg_rtx;
  xop[4] = xstring_empty;
  xop[5] = tmp_reg_rtx;
  xop[6] = XEXP (rampz_rtx, 0);

  segment = avr_addrspace[as].segment;

  /* Set RAMPZ as needed.  */

  if (segment)
    {
      xop[4] = GEN_INT (segment);
      xop[3] = avr_find_unused_d_reg (insn, lpm_addr_reg_rtx);

      if (xop[3] != NULL_RTX)
        {
          avr_asm_len ("ldi %3,%4" CR_TAB
                       "out %i6,%3", xop, plen, 2);
        }
      else if (segment == 1)
        {
          avr_asm_len ("clr %5" CR_TAB
                       "inc %5" CR_TAB
                       "out %i6,%5", xop, plen, 3);
        }
      else
        {
          avr_asm_len ("mov %5,%2"   CR_TAB
                       "ldi %2,%4"   CR_TAB
                       "out %i6,%2"  CR_TAB
                       "mov %2,%5", xop, plen, 4);
        }

      xop[4] = xstring_e;

      if (!AVR_HAVE_ELPMX)
        return avr_out_lpm_no_lpmx (insn, xop, plen);
    }
  else if (!AVR_HAVE_LPMX)
    {
      return avr_out_lpm_no_lpmx (insn, xop, plen);
    }

  /* We have [E]LPMX: Output reading from Flash the comfortable way.  */

  switch (GET_CODE (addr))
    {
    default:
      gcc_unreachable();

    case REG:

      gcc_assert (REG_Z == REGNO (addr));

      switch (n_bytes)
        {
        default:
          gcc_unreachable();

        case 1:
          avr_asm_len ("%4lpm %0,%a2", xop, plen, 1);
          break;

        case 2:
          if (REGNO (dest) == REG_Z)
            avr_asm_len ("%4lpm %5,%a2+" CR_TAB
                         "%4lpm %B0,%a2" CR_TAB
                         "mov %A0,%5", xop, plen, 3);
          else
            {
              avr_asm_len ("%4lpm %A0,%a2+" CR_TAB
                           "%4lpm %B0,%a2", xop, plen, 2);

              if (!reg_unused_after (insn, addr))
                avr_asm_len ("sbiw %2,1", xop, plen, 1);
            }

          break; /* 2 */

        case 3:

          avr_asm_len ("%4lpm %A0,%a2+" CR_TAB
                       "%4lpm %B0,%a2+" CR_TAB
                       "%4lpm %C0,%a2", xop, plen, 3);

          if (!reg_unused_after (insn, addr))
            avr_asm_len ("sbiw %2,2", xop, plen, 1);

          break; /* 3 */

        case 4:

          avr_asm_len ("%4lpm %A0,%a2+" CR_TAB
                       "%4lpm %B0,%a2+", xop, plen, 2);

          if (REGNO (dest) == REG_Z - 2)
            avr_asm_len ("%4lpm %5,%a2+" CR_TAB
                         "%4lpm %C0,%a2" CR_TAB
                         "mov %D0,%5", xop, plen, 3);
          else
            {
              avr_asm_len ("%4lpm %C0,%a2+" CR_TAB
                           "%4lpm %D0,%a2", xop, plen, 2);

              if (!reg_unused_after (insn, addr))
                avr_asm_len ("sbiw %2,3", xop, plen, 1);
            }

          break; /* 4 */
        } /* n_bytes */

      break; /* REG */

    case POST_INC:

      gcc_assert (REG_Z == REGNO (XEXP (addr, 0))
                  && n_bytes <= 4);

      avr_asm_len                    ("%4lpm %A0,%a2+", xop, plen, 1);
      if (n_bytes >= 2)  avr_asm_len ("%4lpm %B0,%a2+", xop, plen, 1);
      if (n_bytes >= 3)  avr_asm_len ("%4lpm %C0,%a2+", xop, plen, 1);
      if (n_bytes >= 4)  avr_asm_len ("%4lpm %D0,%a2+", xop, plen, 1);

      break; /* POST_INC */

    } /* switch CODE (addr) */

  if (xop[4] == xstring_e && AVR_HAVE_RAMPD)
    {
      /* Reset RAMPZ to 0 so that EBI devices don't read garbage from RAM.  */

      xop[0] = zero_reg_rtx;
      avr_asm_len ("out %i6,%0", xop, plen, 1);
    }

  return "";
}


/* Worker function for xload_8 insn.  */

const char*
avr_out_xload (rtx_insn *insn ATTRIBUTE_UNUSED, rtx *op, int *plen)
{
  rtx xop[4];

  xop[0] = op[0];
  xop[1] = op[1];
  xop[2] = lpm_addr_reg_rtx;
  xop[3] = AVR_HAVE_LPMX ? op[0] : lpm_reg_rtx;

  avr_asm_len (AVR_HAVE_LPMX ? "lpm %3,%a2" : "lpm", xop, plen, -1);

  avr_asm_len ("sbrc %1,7" CR_TAB
               "ld %3,%a2", xop, plen, 2);

  if (REGNO (xop[0]) != REGNO (xop[3]))
    avr_asm_len ("mov %0,%3", xop, plen, 1);

  return "";
}


const char*
output_movqi (rtx_insn *insn, rtx operands[], int *plen)
{
  rtx dest = operands[0];
  rtx src = operands[1];

  if (avr_mem_flash_p (src)
      || avr_mem_flash_p (dest))
    {
      return avr_out_lpm (insn, operands, plen);
    }

  gcc_assert (GET_MODE_SIZE (GET_MODE (dest)) == 1);

  if (REG_P (dest))
    {
      if (REG_P (src)) /* mov r,r */
        {
          if (test_hard_reg_class (STACK_REG, dest))
            return avr_asm_len ("out %0,%1", operands, plen, -1);
          else if (test_hard_reg_class (STACK_REG, src))
            return avr_asm_len ("in %0,%1", operands, plen, -1);

          return avr_asm_len ("mov %0,%1", operands, plen, -1);
        }
      else if (CONSTANT_P (src))
        {
          output_reload_in_const (operands, NULL_RTX, plen, false);
          return "";
        }
      else if (MEM_P (src))
        return out_movqi_r_mr (insn, operands, plen); /* mov r,m */
    }
  else if (MEM_P (dest))
    {
      rtx xop[2];

      xop[0] = dest;
      xop[1] = src == CONST0_RTX (GET_MODE (dest)) ? zero_reg_rtx : src;

      return out_movqi_mr_r (insn, xop, plen);
    }

  return "";
}


const char *
output_movhi (rtx_insn *insn, rtx xop[], int *plen)
{
  rtx dest = xop[0];
  rtx src = xop[1];

  gcc_assert (GET_MODE_SIZE (GET_MODE (dest)) == 2);

  if (avr_mem_flash_p (src)
      || avr_mem_flash_p (dest))
    {
      return avr_out_lpm (insn, xop, plen);
    }

  if (REG_P (dest))
    {
      if (REG_P (src)) /* mov r,r */
        {
          if (test_hard_reg_class (STACK_REG, dest))
            {
              if (AVR_HAVE_8BIT_SP)
                return avr_asm_len ("out __SP_L__,%A1", xop, plen, -1);

              if (AVR_XMEGA)
                return avr_asm_len ("out __SP_L__,%A1" CR_TAB
                                    "out __SP_H__,%B1", xop, plen, -2);

              /* Use simple load of SP if no interrupts are  used.  */

              return TARGET_NO_INTERRUPTS
                ? avr_asm_len ("out __SP_H__,%B1" CR_TAB
                               "out __SP_L__,%A1", xop, plen, -2)
                : avr_asm_len ("in __tmp_reg__,__SREG__"  CR_TAB
                               "cli"                      CR_TAB
                               "out __SP_H__,%B1"         CR_TAB
                               "out __SREG__,__tmp_reg__" CR_TAB
                               "out __SP_L__,%A1", xop, plen, -5);
            }
          else if (test_hard_reg_class (STACK_REG, src))
            {
              return !AVR_HAVE_SPH
                ? avr_asm_len ("in %A0,__SP_L__" CR_TAB
                               "clr %B0", xop, plen, -2)

                : avr_asm_len ("in %A0,__SP_L__" CR_TAB
                               "in %B0,__SP_H__", xop, plen, -2);
            }

          return AVR_HAVE_MOVW
            ? avr_asm_len ("movw %0,%1", xop, plen, -1)

            : avr_asm_len ("mov %A0,%A1" CR_TAB
                           "mov %B0,%B1", xop, plen, -2);
        } /* REG_P (src) */
      else if (CONSTANT_P (src))
        {
          return output_reload_inhi (xop, NULL, plen);
        }
      else if (MEM_P (src))
        {
          return out_movhi_r_mr (insn, xop, plen); /* mov r,m */
        }
    }
  else if (MEM_P (dest))
    {
      rtx xop[2];

      xop[0] = dest;
      xop[1] = src == CONST0_RTX (GET_MODE (dest)) ? zero_reg_rtx : src;

      return out_movhi_mr_r (insn, xop, plen);
    }

  fatal_insn ("invalid insn:", insn);

  return "";
}


/* Same as out_movqi_r_mr, but TINY does not have ADIW or SBIW */

static const char*
avr_out_movqi_r_mr_reg_disp_tiny (rtx_insn *insn, rtx op[], int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx x = XEXP (src, 0);

  avr_asm_len (TINY_ADIW (%I1, %J1, %o1) CR_TAB
               "ld %0,%b1" , op, plen, -3);

  if (!reg_overlap_mentioned_p (dest, XEXP (x, 0))
      && !reg_unused_after (insn, XEXP (x, 0)))
    avr_asm_len (TINY_SBIW (%I1, %J1, %o1), op, plen, 2);

  return "";
}

static const char*
out_movqi_r_mr (rtx_insn *insn, rtx op[], int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx x = XEXP (src, 0);

  if (CONSTANT_ADDRESS_P (x))
    {
      int n_words = AVR_TINY ? 1 : 2;
      return io_address_operand (x, QImode)
        ? avr_asm_len ("in %0,%i1", op, plen, -1)
        : avr_asm_len ("lds %0,%m1", op, plen, -n_words);
    }

  if (GET_CODE (x) == PLUS
      && REG_P (XEXP (x, 0))
      && CONST_INT_P (XEXP (x, 1)))
    {
      /* memory access by reg+disp */

      int disp = INTVAL (XEXP (x, 1));

      if (AVR_TINY)
        return avr_out_movqi_r_mr_reg_disp_tiny (insn, op, plen);

      if (disp - GET_MODE_SIZE (GET_MODE (src)) >= 63)
        {
          if (REGNO (XEXP (x, 0)) != REG_Y)
            fatal_insn ("incorrect insn:",insn);

          if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (src)))
            return avr_asm_len ("adiw r28,%o1-63" CR_TAB
                                "ldd %0,Y+63"     CR_TAB
                                "sbiw r28,%o1-63", op, plen, -3);

          return avr_asm_len ("subi r28,lo8(-%o1)" CR_TAB
                              "sbci r29,hi8(-%o1)" CR_TAB
                              "ld %0,Y"            CR_TAB
                              "subi r28,lo8(%o1)"  CR_TAB
                              "sbci r29,hi8(%o1)", op, plen, -5);
        }
      else if (REGNO (XEXP (x, 0)) == REG_X)
        {
          /* This is a paranoid case LEGITIMIZE_RELOAD_ADDRESS must exclude
             it but I have this situation with extremal optimizing options.  */

          avr_asm_len ("adiw r26,%o1" CR_TAB
                       "ld %0,X", op, plen, -2);

          if (!reg_overlap_mentioned_p (dest, XEXP (x, 0))
              && !reg_unused_after (insn, XEXP (x, 0)))
            {
              avr_asm_len ("sbiw r26,%o1", op, plen, 1);
            }

          return "";
        }

      return avr_asm_len ("ldd %0,%1", op, plen, -1);
    }

  return avr_asm_len ("ld %0,%1", op, plen, -1);
}


/* Same as movhi_r_mr, but TINY does not have ADIW, SBIW and LDD */

static const char*
avr_out_movhi_r_mr_reg_no_disp_tiny (rtx_insn *insn, rtx op[], int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (src, 0);

  int reg_dest = true_regnum (dest);
  int reg_base = true_regnum (base);

  if (reg_dest == reg_base)         /* R = (R) */
    return avr_asm_len ("ld __tmp_reg__,%1+" CR_TAB
			"ld %B0,%1"          CR_TAB
			"mov %A0,__tmp_reg__", op, plen, -3);

  avr_asm_len ("ld %A0,%1+" CR_TAB
               "ld %B0,%1", op, plen, -2);

  if (!reg_unused_after (insn, base))
    avr_asm_len (TINY_SBIW (%E1, %F1, 1), op, plen, 2);

  return "";
}


/* Same as movhi_r_mr, but TINY does not have ADIW, SBIW and LDD */

static const char*
avr_out_movhi_r_mr_reg_disp_tiny (rtx_insn *insn, rtx op[], int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (src, 0);

  int reg_dest = true_regnum (dest);
  int reg_base = true_regnum (XEXP (base, 0));

  if (reg_base == reg_dest)
    {
      return avr_asm_len (TINY_ADIW (%I1, %J1, %o1) CR_TAB
                          "ld __tmp_reg__,%b1+"     CR_TAB
                          "ld %B0,%b1"              CR_TAB
                          "mov %A0,__tmp_reg__", op, plen, -5);
    }
  else
    {
      avr_asm_len (TINY_ADIW (%I1, %J1, %o1) CR_TAB
                   "ld %A0,%b1+"             CR_TAB
                   "ld %B0,%b1", op, plen, -4);

      if (!reg_unused_after (insn, XEXP (base, 0)))
        avr_asm_len (TINY_SBIW (%I1, %J1, %o1+1), op, plen, 2);

      return "";
    }
}


/* Same as movhi_r_mr, but TINY does not have ADIW, SBIW and LDD */

static const char*
avr_out_movhi_r_mr_pre_dec_tiny (rtx_insn *insn, rtx op[], int *plen)
{
  int mem_volatile_p = 0;
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (src, 0);

  /* "volatile" forces reading low byte first, even if less efficient,
     for correct operation with 16-bit I/O registers.  */
  mem_volatile_p = MEM_VOLATILE_P (src);

  if (reg_overlap_mentioned_p (dest, XEXP (base, 0)))
    fatal_insn ("incorrect insn:", insn);

  if (!mem_volatile_p)
    return avr_asm_len ("ld %B0,%1" CR_TAB
                        "ld %A0,%1", op, plen, -2);

  return avr_asm_len (TINY_SBIW (%I1, %J1, 2)  CR_TAB
                      "ld %A0,%p1+"            CR_TAB
                      "ld %B0,%p1"             CR_TAB
                      TINY_SBIW (%I1, %J1, 1), op, plen, -6);
}


static const char*
out_movhi_r_mr (rtx_insn *insn, rtx op[], int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (src, 0);
  int reg_dest = true_regnum (dest);
  int reg_base = true_regnum (base);
  /* "volatile" forces reading low byte first, even if less efficient,
     for correct operation with 16-bit I/O registers.  */
  int mem_volatile_p = MEM_VOLATILE_P (src);

  if (reg_base > 0)
    {
      if (AVR_TINY)
        return avr_out_movhi_r_mr_reg_no_disp_tiny (insn, op, plen);

      if (reg_dest == reg_base)         /* R = (R) */
        return avr_asm_len ("ld __tmp_reg__,%1+" CR_TAB
                            "ld %B0,%1"          CR_TAB
                            "mov %A0,__tmp_reg__", op, plen, -3);

      if (reg_base != REG_X)
        return avr_asm_len ("ld %A0,%1" CR_TAB
                            "ldd %B0,%1+1", op, plen, -2);

      avr_asm_len ("ld %A0,X+" CR_TAB
                   "ld %B0,X", op, plen, -2);

      if (!reg_unused_after (insn, base))
        avr_asm_len ("sbiw r26,1", op, plen, 1);

      return "";
    }
  else if (GET_CODE (base) == PLUS) /* (R + i) */
    {
      int disp = INTVAL (XEXP (base, 1));
      int reg_base = true_regnum (XEXP (base, 0));

      if (AVR_TINY)
        return avr_out_movhi_r_mr_reg_disp_tiny (insn, op, plen);

      if (disp > MAX_LD_OFFSET (GET_MODE (src)))
        {
          if (REGNO (XEXP (base, 0)) != REG_Y)
            fatal_insn ("incorrect insn:",insn);

          return disp <= 63 + MAX_LD_OFFSET (GET_MODE (src))
            ? avr_asm_len ("adiw r28,%o1-62" CR_TAB
                           "ldd %A0,Y+62"    CR_TAB
                           "ldd %B0,Y+63"    CR_TAB
                           "sbiw r28,%o1-62", op, plen, -4)

            : avr_asm_len ("subi r28,lo8(-%o1)" CR_TAB
                           "sbci r29,hi8(-%o1)" CR_TAB
                           "ld %A0,Y"           CR_TAB
                           "ldd %B0,Y+1"        CR_TAB
                           "subi r28,lo8(%o1)"  CR_TAB
                           "sbci r29,hi8(%o1)", op, plen, -6);
        }

      /* This is a paranoid case. LEGITIMIZE_RELOAD_ADDRESS must exclude
         it but I have this situation with extremal
         optimization options.  */

      if (reg_base == REG_X)
        {
          if (reg_base == reg_dest)
            return avr_asm_len ("adiw r26,%o1"      CR_TAB
                                "ld __tmp_reg__,X+" CR_TAB
                                "ld %B0,X"          CR_TAB
                                "mov %A0,__tmp_reg__", op, plen, -4);

          avr_asm_len ("adiw r26,%o1" CR_TAB
                       "ld %A0,X+"    CR_TAB
                       "ld %B0,X", op, plen, -3);

          if (!reg_unused_after (insn, XEXP (base, 0)))
            avr_asm_len ("sbiw r26,%o1+1", op, plen, 1);

          return "";
        }

      return reg_base == reg_dest
        ? avr_asm_len ("ldd __tmp_reg__,%A1" CR_TAB
                       "ldd %B0,%B1"         CR_TAB
                       "mov %A0,__tmp_reg__", op, plen, -3)

        : avr_asm_len ("ldd %A0,%A1" CR_TAB
                       "ldd %B0,%B1", op, plen, -2);
    }
  else if (GET_CODE (base) == PRE_DEC) /* (--R) */
    {
      if (AVR_TINY)
	return avr_out_movhi_r_mr_pre_dec_tiny (insn, op, plen);

      if (reg_overlap_mentioned_p (dest, XEXP (base, 0)))
        fatal_insn ("incorrect insn:", insn);

      if (!mem_volatile_p)
        return avr_asm_len ("ld %B0,%1" CR_TAB
                            "ld %A0,%1", op, plen, -2);

      return REGNO (XEXP (base, 0)) == REG_X
        ? avr_asm_len ("sbiw r26,2"  CR_TAB
                       "ld %A0,X+"   CR_TAB
                       "ld %B0,X"    CR_TAB
                       "sbiw r26,1", op, plen, -4)

        : avr_asm_len ("sbiw %r1,2"  CR_TAB
                       "ld %A0,%p1"  CR_TAB
                       "ldd %B0,%p1+1", op, plen, -3);
    }
  else if (GET_CODE (base) == POST_INC) /* (R++) */
    {
      if (reg_overlap_mentioned_p (dest, XEXP (base, 0)))
        fatal_insn ("incorrect insn:", insn);

      return avr_asm_len ("ld %A0,%1"  CR_TAB
                          "ld %B0,%1", op, plen, -2);
    }
  else if (CONSTANT_ADDRESS_P (base))
    {
      int n_words = AVR_TINY ? 2 : 4;
      return io_address_operand (base, HImode)
        ? avr_asm_len ("in %A0,%i1" CR_TAB
                       "in %B0,%i1+1", op, plen, -2)

        : avr_asm_len ("lds %A0,%m1" CR_TAB
                       "lds %B0,%m1+1", op, plen, -n_words);
    }

  fatal_insn ("unknown move insn:",insn);
  return "";
}

static const char*
avr_out_movsi_r_mr_reg_no_disp_tiny (rtx_insn *insn, rtx op[], int *l)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (src, 0);
  int reg_dest = true_regnum (dest);
  int reg_base = true_regnum (base);

  if (reg_dest == reg_base)
    {
      /* "ld r26,-X" is undefined */
      return *l = 9, (TINY_ADIW (%E1, %F1, 3) CR_TAB
		      "ld %D0,%1"             CR_TAB
		      "ld %C0,-%1"            CR_TAB
		      "ld __tmp_reg__,-%1"    CR_TAB
		      TINY_SBIW (%E1, %F1, 1) CR_TAB
		      "ld %A0,%1"             CR_TAB
		      "mov %B0,__tmp_reg__");
    }
  else if (reg_dest == reg_base - 2)
    {
      return *l = 5, ("ld %A0,%1+"            CR_TAB
		      "ld %B0,%1+"            CR_TAB
		      "ld __tmp_reg__,%1+"    CR_TAB
		      "ld %D0,%1"             CR_TAB
		      "mov %C0,__tmp_reg__");
    }
  else if (reg_unused_after (insn, base))
    {
      return *l = 4, ("ld %A0,%1+"    CR_TAB
		      "ld %B0,%1+"    CR_TAB
		      "ld %C0,%1+"    CR_TAB
		      "ld %D0,%1");
    }
  else
    {
      return *l = 6, ("ld %A0,%1+"    CR_TAB
		      "ld %B0,%1+"    CR_TAB
		      "ld %C0,%1+"    CR_TAB
		      "ld %D0,%1"     CR_TAB
		      TINY_SBIW (%E1, %F1, 3));
    }
}


static const char*
avr_out_movsi_r_mr_reg_disp_tiny (rtx_insn *insn, rtx op[], int *l)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (src, 0);
  int reg_dest = true_regnum (dest);
  int reg_base = true_regnum (XEXP (base, 0));

  if (reg_dest == reg_base)
    {
      /* "ld r26,-X" is undefined */
      return *l = 9, (TINY_ADIW (%I1, %J1, %o1+3) CR_TAB
                      "ld %D0,%b1"                CR_TAB
                      "ld %C0,-%b1"               CR_TAB
                      "ld __tmp_reg__,-%b1"       CR_TAB
                      TINY_SBIW (%I1, %J1, 1)     CR_TAB
                      "ld %A0,%b1"                CR_TAB
                      "mov %B0,__tmp_reg__");
    }
  else if (reg_dest == reg_base - 2)
    {
      return *l = 7, (TINY_ADIW (%I1, %J1, %o1) CR_TAB
                      "ld %A0,%b1+"             CR_TAB
                      "ld %B0,%b1+"             CR_TAB
                      "ld __tmp_reg__,%b1+"     CR_TAB
                      "ld %D0,%b1"              CR_TAB
                      "mov %C0,__tmp_reg__");
    }
  else if (reg_unused_after (insn, XEXP (base, 0)))
    {
      return *l = 6, (TINY_ADIW (%I1, %J1, %o1) CR_TAB
                      "ld %A0,%b1+"             CR_TAB
                      "ld %B0,%b1+"             CR_TAB
                      "ld %C0,%b1+"             CR_TAB
                      "ld %D0,%b1");
    }
  else
    {
      return *l = 8, (TINY_ADIW (%I1, %J1, %o1)  CR_TAB
                      "ld %A0,%b1+"              CR_TAB
                      "ld %B0,%b1+"              CR_TAB
                      "ld %C0,%b1+"              CR_TAB
                      "ld %D0,%b1"               CR_TAB
                      TINY_SBIW (%I1, %J1, %o1+3));
    }
}

static const char*
out_movsi_r_mr (rtx_insn *insn, rtx op[], int *l)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (src, 0);
  int reg_dest = true_regnum (dest);
  int reg_base = true_regnum (base);
  int tmp;

  if (!l)
    l = &tmp;

  if (reg_base > 0)
    {
      if (AVR_TINY)
        return avr_out_movsi_r_mr_reg_no_disp_tiny (insn, op, l);

      if (reg_base == REG_X)        /* (R26) */
        {
          if (reg_dest == REG_X)
	    /* "ld r26,-X" is undefined */
	    return *l=7, ("adiw r26,3"        CR_TAB
			  "ld r29,X"          CR_TAB
			  "ld r28,-X"         CR_TAB
			  "ld __tmp_reg__,-X" CR_TAB
			  "sbiw r26,1"        CR_TAB
			  "ld r26,X"          CR_TAB
			  "mov r27,__tmp_reg__");
          else if (reg_dest == REG_X - 2)
            return *l=5, ("ld %A0,X+"          CR_TAB
                          "ld %B0,X+"          CR_TAB
                          "ld __tmp_reg__,X+"  CR_TAB
                          "ld %D0,X"           CR_TAB
                          "mov %C0,__tmp_reg__");
          else if (reg_unused_after (insn, base))
            return  *l=4, ("ld %A0,X+" CR_TAB
                           "ld %B0,X+" CR_TAB
                           "ld %C0,X+" CR_TAB
                           "ld %D0,X");
          else
            return  *l=5, ("ld %A0,X+" CR_TAB
                           "ld %B0,X+" CR_TAB
                           "ld %C0,X+" CR_TAB
                           "ld %D0,X"  CR_TAB
                           "sbiw r26,3");
        }
      else
        {
          if (reg_dest == reg_base)
            return *l=5, ("ldd %D0,%1+3" CR_TAB
                          "ldd %C0,%1+2" CR_TAB
                          "ldd __tmp_reg__,%1+1"  CR_TAB
                          "ld %A0,%1"  CR_TAB
                          "mov %B0,__tmp_reg__");
          else if (reg_base == reg_dest + 2)
            return *l=5, ("ld %A0,%1"             CR_TAB
                          "ldd %B0,%1+1"          CR_TAB
                          "ldd __tmp_reg__,%1+2"  CR_TAB
                          "ldd %D0,%1+3"          CR_TAB
                          "mov %C0,__tmp_reg__");
          else
            return *l=4, ("ld %A0,%1"    CR_TAB
                          "ldd %B0,%1+1" CR_TAB
                          "ldd %C0,%1+2" CR_TAB
                          "ldd %D0,%1+3");
        }
    }
  else if (GET_CODE (base) == PLUS) /* (R + i) */
    {
      int disp = INTVAL (XEXP (base, 1));

      if (AVR_TINY)
        return avr_out_movsi_r_mr_reg_disp_tiny (insn, op, l);

      if (disp > MAX_LD_OFFSET (GET_MODE (src)))
	{
	  if (REGNO (XEXP (base, 0)) != REG_Y)
	    fatal_insn ("incorrect insn:",insn);

	  if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (src)))
	    return *l = 6, ("adiw r28,%o1-60" CR_TAB
			    "ldd %A0,Y+60"    CR_TAB
			    "ldd %B0,Y+61"    CR_TAB
			    "ldd %C0,Y+62"    CR_TAB
			    "ldd %D0,Y+63"    CR_TAB
			    "sbiw r28,%o1-60");

	  return *l = 8, ("subi r28,lo8(-%o1)" CR_TAB
			  "sbci r29,hi8(-%o1)" CR_TAB
			  "ld %A0,Y"           CR_TAB
			  "ldd %B0,Y+1"        CR_TAB
			  "ldd %C0,Y+2"        CR_TAB
			  "ldd %D0,Y+3"        CR_TAB
			  "subi r28,lo8(%o1)"  CR_TAB
			  "sbci r29,hi8(%o1)");
	}

      reg_base = true_regnum (XEXP (base, 0));
      if (reg_base == REG_X)
	{
	  /* R = (X + d) */
	  if (reg_dest == REG_X)
	    {
	      *l = 7;
	      /* "ld r26,-X" is undefined */
	      return ("adiw r26,%o1+3"    CR_TAB
		      "ld r29,X"          CR_TAB
		      "ld r28,-X"         CR_TAB
		      "ld __tmp_reg__,-X" CR_TAB
		      "sbiw r26,1"        CR_TAB
		      "ld r26,X"          CR_TAB
		      "mov r27,__tmp_reg__");
	    }
	  *l = 6;
	  if (reg_dest == REG_X - 2)
	    return ("adiw r26,%o1"      CR_TAB
		    "ld r24,X+"         CR_TAB
		    "ld r25,X+"         CR_TAB
		    "ld __tmp_reg__,X+" CR_TAB
		    "ld r27,X"          CR_TAB
		    "mov r26,__tmp_reg__");

	  return ("adiw r26,%o1" CR_TAB
		  "ld %A0,X+"    CR_TAB
		  "ld %B0,X+"    CR_TAB
		  "ld %C0,X+"    CR_TAB
		  "ld %D0,X"     CR_TAB
		  "sbiw r26,%o1+3");
	}
      if (reg_dest == reg_base)
        return *l=5, ("ldd %D0,%D1"          CR_TAB
                      "ldd %C0,%C1"          CR_TAB
                      "ldd __tmp_reg__,%B1"  CR_TAB
                      "ldd %A0,%A1"          CR_TAB
                      "mov %B0,__tmp_reg__");
      else if (reg_dest == reg_base - 2)
        return *l=5, ("ldd %A0,%A1"          CR_TAB
                      "ldd %B0,%B1"          CR_TAB
                      "ldd __tmp_reg__,%C1"  CR_TAB
                      "ldd %D0,%D1"          CR_TAB
                      "mov %C0,__tmp_reg__");
      return *l=4, ("ldd %A0,%A1" CR_TAB
                    "ldd %B0,%B1" CR_TAB
                    "ldd %C0,%C1" CR_TAB
                    "ldd %D0,%D1");
    }
  else if (GET_CODE (base) == PRE_DEC) /* (--R) */
    return *l=4, ("ld %D0,%1" CR_TAB
		  "ld %C0,%1" CR_TAB
		  "ld %B0,%1" CR_TAB
		  "ld %A0,%1");
  else if (GET_CODE (base) == POST_INC) /* (R++) */
    return *l=4, ("ld %A0,%1" CR_TAB
		  "ld %B0,%1" CR_TAB
		  "ld %C0,%1" CR_TAB
		  "ld %D0,%1");
  else if (CONSTANT_ADDRESS_P (base))
    {
      if (io_address_operand (base, SImode))
        {
          *l = 4;
          return ("in %A0,%i1"   CR_TAB
                  "in %B0,%i1+1" CR_TAB
                  "in %C0,%i1+2" CR_TAB
                  "in %D0,%i1+3");
        }
      else
        {
          *l = AVR_TINY ? 4 : 8;
          return ("lds %A0,%m1"   CR_TAB
                  "lds %B0,%m1+1" CR_TAB
                  "lds %C0,%m1+2" CR_TAB
                  "lds %D0,%m1+3");
        }
    }

  fatal_insn ("unknown move insn:",insn);
  return "";
}

static const char*
avr_out_movsi_mr_r_reg_no_disp_tiny (rtx_insn *insn, rtx op[], int *l)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (dest, 0);
  int reg_base = true_regnum (base);
  int reg_src = true_regnum (src);

  if (reg_base == reg_src)
    {
      /* "ld r26,-X" is undefined */
      if (reg_unused_after (insn, base))
        {
          return *l = 7, ("mov __tmp_reg__, %B1"  CR_TAB
			  "st %0,%A1"             CR_TAB
			  TINY_ADIW (%E0, %F0, 1) CR_TAB
			  "st %0+,__tmp_reg__"    CR_TAB
			  "st %0+,%C1"            CR_TAB
			  "st %0+,%D1");
        }
      else
        {
          return *l = 9, ("mov __tmp_reg__, %B1"  CR_TAB
			  "st %0,%A1"             CR_TAB
			  TINY_ADIW (%E0, %F0, 1) CR_TAB
			  "st %0+,__tmp_reg__"    CR_TAB
			  "st %0+,%C1"            CR_TAB
			  "st %0+,%D1"            CR_TAB
			  TINY_SBIW (%E0, %F0, 3));
        }
    }
  else if (reg_base == reg_src + 2)
    {
      if (reg_unused_after (insn, base))
	return *l = 7, ("mov __zero_reg__,%C1" CR_TAB
                        "mov __tmp_reg__,%D1"  CR_TAB
                        "st %0+,%A1"           CR_TAB
                        "st %0+,%B1"           CR_TAB
                        "st %0+,__zero_reg__"  CR_TAB
                        "st %0,__tmp_reg__"    CR_TAB
                        "clr __zero_reg__");
      else
	return *l = 9, ("mov __zero_reg__,%C1" CR_TAB
			"mov __tmp_reg__,%D1"  CR_TAB
			"st %0+,%A1"           CR_TAB
			"st %0+,%B1"           CR_TAB
			"st %0+,__zero_reg__"  CR_TAB
			"st %0,__tmp_reg__"    CR_TAB
			"clr __zero_reg__"     CR_TAB
			TINY_SBIW (%E0, %F0, 3));
    }

  return *l = 6, ("st %0+,%A1" CR_TAB
		  "st %0+,%B1" CR_TAB
		  "st %0+,%C1" CR_TAB
		  "st %0,%D1"  CR_TAB
		  TINY_SBIW (%E0, %F0, 3));
}

static const char*
avr_out_movsi_mr_r_reg_disp_tiny (rtx op[], int *l)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (dest, 0);
  int reg_base = REGNO (XEXP (base, 0));
  int reg_src =true_regnum (src);

  if (reg_base == reg_src)
    {
      *l = 11;
      return ("mov __tmp_reg__,%A2"        CR_TAB
              "mov __zero_reg__,%B2"       CR_TAB
              TINY_ADIW (%I0, %J0, %o0)    CR_TAB
              "st %b0+,__tmp_reg__"        CR_TAB
              "st %b0+,__zero_reg__"       CR_TAB
              "st %b0+,%C2"                CR_TAB
              "st %b0,%D2"                 CR_TAB
              "clr __zero_reg__"           CR_TAB
              TINY_SBIW (%I0, %J0, %o0+3));
    }
  else if (reg_src == reg_base - 2)
    {
      *l = 11;
      return ("mov __tmp_reg__,%C2"         CR_TAB
              "mov __zero_reg__,%D2"        CR_TAB
              TINY_ADIW (%I0, %J0, %o0)     CR_TAB
              "st %b0+,%A0"                 CR_TAB
              "st %b0+,%B0"                 CR_TAB
              "st %b0+,__tmp_reg__"         CR_TAB
              "st %b0,__zero_reg__"         CR_TAB
              "clr __zero_reg__"            CR_TAB
              TINY_SBIW (%I0, %J0, %o0+3));
    }
  *l = 8;
  return (TINY_ADIW (%I0, %J0, %o0)     CR_TAB
          "st %b0+,%A1"                 CR_TAB
          "st %b0+,%B1"                 CR_TAB
          "st %b0+,%C1"                 CR_TAB
          "st %b0,%D1"                  CR_TAB
          TINY_SBIW (%I0, %J0, %o0+3));
}

static const char*
out_movsi_mr_r (rtx_insn *insn, rtx op[], int *l)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (dest, 0);
  int reg_base = true_regnum (base);
  int reg_src = true_regnum (src);
  int tmp;

  if (!l)
    l = &tmp;

  if (CONSTANT_ADDRESS_P (base))
    {
      if (io_address_operand (base, SImode))
        {
          return *l=4,("out %i0, %A1"  CR_TAB
                       "out %i0+1,%B1" CR_TAB
                       "out %i0+2,%C1" CR_TAB
                       "out %i0+3,%D1");
        }
      else
        {
          *l = AVR_TINY ? 4 : 8;
          return ("sts %m0,%A1"   CR_TAB
                  "sts %m0+1,%B1" CR_TAB
                  "sts %m0+2,%C1" CR_TAB
                  "sts %m0+3,%D1");
        }
    }

  if (reg_base > 0)                 /* (r) */
    {
      if (AVR_TINY)
        return avr_out_movsi_mr_r_reg_no_disp_tiny (insn, op, l);

      if (reg_base == REG_X)                /* (R26) */
        {
          if (reg_src == REG_X)
            {
	      /* "st X+,r26" is undefined */
              if (reg_unused_after (insn, base))
		return *l=6, ("mov __tmp_reg__,r27" CR_TAB
			      "st X,r26"            CR_TAB
			      "adiw r26,1"          CR_TAB
			      "st X+,__tmp_reg__"   CR_TAB
			      "st X+,r28"           CR_TAB
			      "st X,r29");
              else
                return *l=7, ("mov __tmp_reg__,r27" CR_TAB
			      "st X,r26"            CR_TAB
			      "adiw r26,1"          CR_TAB
			      "st X+,__tmp_reg__"   CR_TAB
			      "st X+,r28"           CR_TAB
			      "st X,r29"            CR_TAB
			      "sbiw r26,3");
            }
          else if (reg_base == reg_src + 2)
            {
              if (reg_unused_after (insn, base))
                return *l=7, ("mov __zero_reg__,%C1" CR_TAB
                              "mov __tmp_reg__,%D1"  CR_TAB
                              "st %0+,%A1"           CR_TAB
                              "st %0+,%B1"           CR_TAB
                              "st %0+,__zero_reg__"  CR_TAB
                              "st %0,__tmp_reg__"    CR_TAB
                              "clr __zero_reg__");
              else
                return *l=8, ("mov __zero_reg__,%C1" CR_TAB
                              "mov __tmp_reg__,%D1"  CR_TAB
                              "st %0+,%A1"           CR_TAB
                              "st %0+,%B1"           CR_TAB
                              "st %0+,__zero_reg__"  CR_TAB
                              "st %0,__tmp_reg__"    CR_TAB
                              "clr __zero_reg__"     CR_TAB
                              "sbiw r26,3");
            }
          return *l=5, ("st %0+,%A1" CR_TAB
                        "st %0+,%B1" CR_TAB
                        "st %0+,%C1" CR_TAB
                        "st %0,%D1"  CR_TAB
                        "sbiw r26,3");
        }
      else
        return *l=4, ("st %0,%A1"    CR_TAB
		      "std %0+1,%B1" CR_TAB
		      "std %0+2,%C1" CR_TAB
		      "std %0+3,%D1");
    }
  else if (GET_CODE (base) == PLUS) /* (R + i) */
    {
      int disp = INTVAL (XEXP (base, 1));

      if (AVR_TINY)
        return avr_out_movsi_mr_r_reg_disp_tiny (op, l);

      reg_base = REGNO (XEXP (base, 0));
      if (disp > MAX_LD_OFFSET (GET_MODE (dest)))
	{
	  if (reg_base != REG_Y)
	    fatal_insn ("incorrect insn:",insn);

	  if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest)))
	    return *l = 6, ("adiw r28,%o0-60" CR_TAB
			    "std Y+60,%A1"    CR_TAB
			    "std Y+61,%B1"    CR_TAB
			    "std Y+62,%C1"    CR_TAB
			    "std Y+63,%D1"    CR_TAB
			    "sbiw r28,%o0-60");

	  return *l = 8, ("subi r28,lo8(-%o0)" CR_TAB
			  "sbci r29,hi8(-%o0)" CR_TAB
			  "st Y,%A1"           CR_TAB
			  "std Y+1,%B1"        CR_TAB
			  "std Y+2,%C1"        CR_TAB
			  "std Y+3,%D1"        CR_TAB
			  "subi r28,lo8(%o0)"  CR_TAB
			  "sbci r29,hi8(%o0)");
	}
      if (reg_base == REG_X)
	{
	  /* (X + d) = R */
	  if (reg_src == REG_X)
	    {
	      *l = 9;
	      return ("mov __tmp_reg__,r26"  CR_TAB
		      "mov __zero_reg__,r27" CR_TAB
		      "adiw r26,%o0"         CR_TAB
		      "st X+,__tmp_reg__"    CR_TAB
		      "st X+,__zero_reg__"   CR_TAB
		      "st X+,r28"            CR_TAB
		      "st X,r29"             CR_TAB
		      "clr __zero_reg__"     CR_TAB
		      "sbiw r26,%o0+3");
	    }
	  else if (reg_src == REG_X - 2)
	    {
	      *l = 9;
	      return ("mov __tmp_reg__,r26"  CR_TAB
		      "mov __zero_reg__,r27" CR_TAB
		      "adiw r26,%o0"         CR_TAB
		      "st X+,r24"            CR_TAB
		      "st X+,r25"            CR_TAB
		      "st X+,__tmp_reg__"    CR_TAB
		      "st X,__zero_reg__"    CR_TAB
		      "clr __zero_reg__"     CR_TAB
		      "sbiw r26,%o0+3");
	    }
	  *l = 6;
	  return ("adiw r26,%o0" CR_TAB
		  "st X+,%A1"    CR_TAB
		  "st X+,%B1"    CR_TAB
		  "st X+,%C1"    CR_TAB
		  "st X,%D1"     CR_TAB
		  "sbiw r26,%o0+3");
	}
      return *l=4, ("std %A0,%A1" CR_TAB
		    "std %B0,%B1" CR_TAB
		    "std %C0,%C1" CR_TAB
		    "std %D0,%D1");
    }
  else if (GET_CODE (base) == PRE_DEC) /* (--R) */
    return *l=4, ("st %0,%D1" CR_TAB
		  "st %0,%C1" CR_TAB
		  "st %0,%B1" CR_TAB
		  "st %0,%A1");
  else if (GET_CODE (base) == POST_INC) /* (R++) */
    return *l=4, ("st %0,%A1" CR_TAB
		  "st %0,%B1" CR_TAB
		  "st %0,%C1" CR_TAB
		  "st %0,%D1");
  fatal_insn ("unknown move insn:",insn);
  return "";
}

const char *
output_movsisf (rtx_insn *insn, rtx operands[], int *l)
{
  int dummy;
  rtx dest = operands[0];
  rtx src = operands[1];
  int *real_l = l;

  if (avr_mem_flash_p (src)
      || avr_mem_flash_p (dest))
    {
      return avr_out_lpm (insn, operands, real_l);
    }

  if (!l)
    l = &dummy;

  gcc_assert (GET_MODE_SIZE (GET_MODE (dest)) == 4);

  if (REG_P (dest))
    {
      if (REG_P (src)) /* mov r,r */
	{
	  if (true_regnum (dest) > true_regnum (src))
	    {
	      if (AVR_HAVE_MOVW)
		{
		  *l = 2;
		  return ("movw %C0,%C1" CR_TAB
			  "movw %A0,%A1");
		}
	      *l = 4;
	      return ("mov %D0,%D1" CR_TAB
		      "mov %C0,%C1" CR_TAB
		      "mov %B0,%B1" CR_TAB
		      "mov %A0,%A1");
	    }
	  else
	    {
	      if (AVR_HAVE_MOVW)
		{
		  *l = 2;
		  return ("movw %A0,%A1" CR_TAB
			  "movw %C0,%C1");
		}
	      *l = 4;
	      return ("mov %A0,%A1" CR_TAB
		      "mov %B0,%B1" CR_TAB
		      "mov %C0,%C1" CR_TAB
		      "mov %D0,%D1");
	    }
	}
      else if (CONSTANT_P (src))
	{
          return output_reload_insisf (operands, NULL_RTX, real_l);
        }
      else if (MEM_P (src))
	return out_movsi_r_mr (insn, operands, real_l); /* mov r,m */
    }
  else if (MEM_P (dest))
    {
      const char *templ;

      if (src == CONST0_RTX (GET_MODE (dest)))
        operands[1] = zero_reg_rtx;

      templ = out_movsi_mr_r (insn, operands, real_l);

      if (!real_l)
	output_asm_insn (templ, operands);

      operands[1] = src;
      return "";
    }
  fatal_insn ("invalid insn:", insn);
  return "";
}


/* Handle loads of 24-bit types from memory to register.  */

static const char*
avr_out_load_psi_reg_no_disp_tiny (rtx_insn *insn, rtx *op, int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (src, 0);
  int reg_dest = true_regnum (dest);
  int reg_base = true_regnum (base);

  if (reg_base == reg_dest)
    {
      return avr_asm_len (TINY_ADIW (%E1, %F1, 2)   CR_TAB
                          "ld %C0,%1"               CR_TAB
                          "ld __tmp_reg__,-%1"      CR_TAB
                          TINY_SBIW (%E1, %F1, 1)   CR_TAB
                          "ld %A0,%1"               CR_TAB
                          "mov %B0,__tmp_reg__", op, plen, -8);
    }
  else
    {
      avr_asm_len ("ld %A0,%1+"  CR_TAB
		   "ld %B0,%1+"  CR_TAB
		   "ld %C0,%1", op, plen, -3);

      if (reg_dest != reg_base - 2
          && !reg_unused_after (insn, base))
        {
          avr_asm_len (TINY_SBIW (%E1, %F1, 2), op, plen, 2);
        }
      return "";
    }
}

static const char*
avr_out_load_psi_reg_disp_tiny (rtx_insn *insn, rtx *op, int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (src, 0);
  int reg_dest = true_regnum (dest);
  int reg_base = true_regnum (base);

  reg_base = true_regnum (XEXP (base, 0));
  if (reg_base == reg_dest)
    {
      return avr_asm_len (TINY_ADIW (%I1, %J1, %o1+2) CR_TAB
                          "ld %C0,%b1"                CR_TAB
                          "ld __tmp_reg__,-%b1"       CR_TAB
                          TINY_SBIW (%I1, %J1, 1)     CR_TAB
                          "ld %A0,%b1"                CR_TAB
                          "mov %B0,__tmp_reg__", op, plen, -8);
    }
  else
    {
      avr_asm_len (TINY_ADIW (%I1, %J1, %o1)   CR_TAB
                   "ld %A0,%b1+"               CR_TAB
                   "ld %B0,%b1+"               CR_TAB
                   "ld %C0,%b1", op, plen, -5);

      if (reg_dest != reg_base - 2
          && !reg_unused_after (insn, XEXP (base, 0)))
        avr_asm_len (TINY_SBIW (%I1, %J1, %o1+2), op, plen, 2);

      return "";
    }
}

static const char*
avr_out_load_psi (rtx_insn *insn, rtx *op, int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (src, 0);
  int reg_dest = true_regnum (dest);
  int reg_base = true_regnum (base);

  if (reg_base > 0)
    {
      if (AVR_TINY)
        return avr_out_load_psi_reg_no_disp_tiny (insn, op, plen);

      if (reg_base == REG_X)        /* (R26) */
        {
          if (reg_dest == REG_X)
            /* "ld r26,-X" is undefined */
            return avr_asm_len ("adiw r26,2"        CR_TAB
                                "ld r28,X"          CR_TAB
                                "ld __tmp_reg__,-X" CR_TAB
                                "sbiw r26,1"        CR_TAB
                                "ld r26,X"          CR_TAB
                                "mov r27,__tmp_reg__", op, plen, -6);
          else
            {
              avr_asm_len ("ld %A0,X+" CR_TAB
                           "ld %B0,X+" CR_TAB
                           "ld %C0,X", op, plen, -3);

              if (reg_dest != REG_X - 2
                  && !reg_unused_after (insn, base))
                {
                  avr_asm_len ("sbiw r26,2", op, plen, 1);
                }

              return "";
            }
        }
      else /* reg_base != REG_X */
        {
          if (reg_dest == reg_base)
            return avr_asm_len ("ldd %C0,%1+2"          CR_TAB
                                "ldd __tmp_reg__,%1+1"  CR_TAB
                                "ld  %A0,%1"            CR_TAB
                                "mov %B0,__tmp_reg__", op, plen, -4);
          else
            return avr_asm_len ("ld  %A0,%1"    CR_TAB
                                "ldd %B0,%1+1"  CR_TAB
                                "ldd %C0,%1+2", op, plen, -3);
        }
    }
  else if (GET_CODE (base) == PLUS) /* (R + i) */
    {
      int disp = INTVAL (XEXP (base, 1));

      if (AVR_TINY)
        return avr_out_load_psi_reg_disp_tiny (insn, op, plen);

      if (disp > MAX_LD_OFFSET (GET_MODE (src)))
        {
          if (REGNO (XEXP (base, 0)) != REG_Y)
            fatal_insn ("incorrect insn:",insn);

          if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (src)))
            return avr_asm_len ("adiw r28,%o1-61" CR_TAB
                                "ldd %A0,Y+61"    CR_TAB
                                "ldd %B0,Y+62"    CR_TAB
                                "ldd %C0,Y+63"    CR_TAB
                                "sbiw r28,%o1-61", op, plen, -5);

          return avr_asm_len ("subi r28,lo8(-%o1)" CR_TAB
                              "sbci r29,hi8(-%o1)" CR_TAB
                              "ld  %A0,Y"          CR_TAB
                              "ldd %B0,Y+1"        CR_TAB
                              "ldd %C0,Y+2"        CR_TAB
                              "subi r28,lo8(%o1)"  CR_TAB
                              "sbci r29,hi8(%o1)", op, plen, -7);
        }

      reg_base = true_regnum (XEXP (base, 0));
      if (reg_base == REG_X)
        {
          /* R = (X + d) */
          if (reg_dest == REG_X)
            {
              /* "ld r26,-X" is undefined */
              return avr_asm_len ("adiw r26,%o1+2"     CR_TAB
                                  "ld  r28,X"          CR_TAB
                                  "ld  __tmp_reg__,-X" CR_TAB
                                  "sbiw r26,1"         CR_TAB
                                  "ld  r26,X"          CR_TAB
                                  "mov r27,__tmp_reg__", op, plen, -6);
            }

          avr_asm_len ("adiw r26,%o1" CR_TAB
                       "ld %A0,X+"    CR_TAB
                       "ld %B0,X+"    CR_TAB
                       "ld %C0,X", op, plen, -4);

          if (reg_dest != REG_W
              && !reg_unused_after (insn, XEXP (base, 0)))
            avr_asm_len ("sbiw r26,%o1+2", op, plen, 1);

          return "";
        }

      if (reg_dest == reg_base)
        return avr_asm_len ("ldd %C0,%C1" CR_TAB
                            "ldd __tmp_reg__,%B1"  CR_TAB
                            "ldd %A0,%A1" CR_TAB
                            "mov %B0,__tmp_reg__", op, plen, -4);

      return avr_asm_len ("ldd %A0,%A1" CR_TAB
                          "ldd %B0,%B1" CR_TAB
                          "ldd %C0,%C1", op, plen, -3);
    }
  else if (GET_CODE (base) == PRE_DEC) /* (--R) */
    return avr_asm_len ("ld %C0,%1" CR_TAB
                        "ld %B0,%1" CR_TAB
                        "ld %A0,%1", op, plen, -3);
  else if (GET_CODE (base) == POST_INC) /* (R++) */
    return avr_asm_len ("ld %A0,%1" CR_TAB
                        "ld %B0,%1" CR_TAB
                        "ld %C0,%1", op, plen, -3);

  else if (CONSTANT_ADDRESS_P (base))
    {
      int n_words = AVR_TINY ? 3 : 6;
      return avr_asm_len ("lds %A0,%m1" CR_TAB
                          "lds %B0,%m1+1" CR_TAB
                          "lds %C0,%m1+2", op, plen , -n_words);
    }

  fatal_insn ("unknown move insn:",insn);
  return "";
}


static const char*
avr_out_store_psi_reg_no_disp_tiny (rtx_insn *insn, rtx *op, int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (dest, 0);
  int reg_base = true_regnum (base);
  int reg_src = true_regnum (src);

  if (reg_base == reg_src)
    {
      avr_asm_len ("st %0,%A1"              CR_TAB
                   "mov __tmp_reg__,%B1"    CR_TAB
                   TINY_ADIW (%E0, %F0, 1)  CR_TAB /* st X+, r27 is undefined */
                   "st %0+,__tmp_reg__"     CR_TAB
                   "st %0,%C1", op, plen, -6);

    }
  else if (reg_src == reg_base - 2)
    {
      avr_asm_len ("st %0,%A1"              CR_TAB
                   "mov __tmp_reg__,%C1"    CR_TAB
                   TINY_ADIW (%E0, %F0, 1)  CR_TAB
                   "st %0+,%B1"             CR_TAB
                   "st %0,__tmp_reg__", op, plen, 6);
    }
  else
    {
      avr_asm_len ("st %0+,%A1"  CR_TAB
                   "st %0+,%B1" CR_TAB
                   "st %0,%C1", op, plen, -3);
    }

  if (!reg_unused_after (insn, base))
    avr_asm_len (TINY_SBIW (%E0, %F0, 2), op, plen, 2);

  return "";
}

static const char*
avr_out_store_psi_reg_disp_tiny (rtx_insn *insn, rtx *op, int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (dest, 0);
  int reg_base = REGNO (XEXP (base, 0));
  int reg_src = true_regnum (src);

  if (reg_src == reg_base)
    avr_asm_len ("mov __tmp_reg__,%A1"          CR_TAB
                 "mov __zero_reg__,%B1"         CR_TAB
                 TINY_ADIW (%I0, %J0, %o0)      CR_TAB
                 "st %b0+,__tmp_reg__"          CR_TAB
                 "st %b0+,__zero_reg__"         CR_TAB
                 "st %b0,%C1"                   CR_TAB
                 "clr __zero_reg__", op, plen, -8);
  else if (reg_src == reg_base - 2)
    avr_asm_len ("mov __tmp_reg__,%C1"          CR_TAB
                 TINY_ADIW (%I0, %J0, %o0)      CR_TAB
                 "st %b0+,%A1"                  CR_TAB
                 "st %b0+,%B1"                  CR_TAB
                 "st %b0,__tmp_reg__", op, plen, -6);
  else
    avr_asm_len (TINY_ADIW (%I0, %J0, %o0)      CR_TAB
                 "st %b0+,%A1"                  CR_TAB
                 "st %b0+,%B1"                  CR_TAB
                 "st %b0,%C1", op, plen, -5);

  if (!reg_unused_after (insn, XEXP (base, 0)))
    avr_asm_len (TINY_SBIW (%I0, %J0, %o0+2), op, plen, 2);

  return "";
}

/* Handle store of 24-bit type from register or zero to memory.  */

static const char*
avr_out_store_psi (rtx_insn *insn, rtx *op, int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (dest, 0);
  int reg_base = true_regnum (base);

  if (CONSTANT_ADDRESS_P (base))
    {
      int n_words = AVR_TINY ? 3 : 6;
      return avr_asm_len ("sts %m0,%A1"   CR_TAB
                          "sts %m0+1,%B1" CR_TAB
                          "sts %m0+2,%C1", op, plen, -n_words);
    }

  if (reg_base > 0)                 /* (r) */
    {
      if (AVR_TINY)
        return avr_out_store_psi_reg_no_disp_tiny (insn, op, plen);

      if (reg_base == REG_X)        /* (R26) */
        {
          gcc_assert (!reg_overlap_mentioned_p (base, src));

          avr_asm_len ("st %0+,%A1"  CR_TAB
                       "st %0+,%B1" CR_TAB
                       "st %0,%C1", op, plen, -3);

          if (!reg_unused_after (insn, base))
            avr_asm_len ("sbiw r26,2", op, plen, 1);

          return "";
        }
      else
        return avr_asm_len ("st %0,%A1"    CR_TAB
                            "std %0+1,%B1" CR_TAB
                            "std %0+2,%C1", op, plen, -3);
    }
  else if (GET_CODE (base) == PLUS) /* (R + i) */
    {
      int disp = INTVAL (XEXP (base, 1));

      if (AVR_TINY)
        return avr_out_store_psi_reg_disp_tiny (insn, op, plen);

      reg_base = REGNO (XEXP (base, 0));

      if (disp > MAX_LD_OFFSET (GET_MODE (dest)))
        {
          if (reg_base != REG_Y)
            fatal_insn ("incorrect insn:",insn);

          if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest)))
            return avr_asm_len ("adiw r28,%o0-61" CR_TAB
                                "std Y+61,%A1"    CR_TAB
                                "std Y+62,%B1"    CR_TAB
                                "std Y+63,%C1"    CR_TAB
                                "sbiw r28,%o0-61", op, plen, -5);

          return avr_asm_len ("subi r28,lo8(-%o0)" CR_TAB
                              "sbci r29,hi8(-%o0)" CR_TAB
                              "st Y,%A1"           CR_TAB
                              "std Y+1,%B1"        CR_TAB
                              "std Y+2,%C1"        CR_TAB
                              "subi r28,lo8(%o0)"  CR_TAB
                              "sbci r29,hi8(%o0)", op, plen, -7);
        }
      if (reg_base == REG_X)
        {
          /* (X + d) = R */
          gcc_assert (!reg_overlap_mentioned_p (XEXP (base, 0), src));

          avr_asm_len ("adiw r26,%o0" CR_TAB
                       "st X+,%A1"    CR_TAB
                       "st X+,%B1"    CR_TAB
                       "st X,%C1", op, plen, -4);

          if (!reg_unused_after (insn, XEXP (base, 0)))
            avr_asm_len ("sbiw r26,%o0+2", op, plen, 1);

          return "";
        }

      return avr_asm_len ("std %A0,%A1" CR_TAB
                          "std %B0,%B1" CR_TAB
                          "std %C0,%C1", op, plen, -3);
    }
  else if (GET_CODE (base) == PRE_DEC) /* (--R) */
    return avr_asm_len ("st %0,%C1" CR_TAB
                        "st %0,%B1" CR_TAB
                        "st %0,%A1", op, plen, -3);
  else if (GET_CODE (base) == POST_INC) /* (R++) */
    return avr_asm_len ("st %0,%A1" CR_TAB
                        "st %0,%B1" CR_TAB
                        "st %0,%C1", op, plen, -3);

  fatal_insn ("unknown move insn:",insn);
  return "";
}


/* Move around 24-bit stuff.  */

const char *
avr_out_movpsi (rtx_insn *insn, rtx *op, int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];

  if (avr_mem_flash_p (src)
      || avr_mem_flash_p (dest))
    {
      return avr_out_lpm (insn, op, plen);
    }

  if (register_operand (dest, VOIDmode))
    {
      if (register_operand (src, VOIDmode)) /* mov r,r */
        {
          if (true_regnum (dest) > true_regnum (src))
            {
              avr_asm_len ("mov %C0,%C1", op, plen, -1);

              if (AVR_HAVE_MOVW)
                return avr_asm_len ("movw %A0,%A1", op, plen, 1);
              else
                return avr_asm_len ("mov %B0,%B1"  CR_TAB
                                    "mov %A0,%A1", op, plen, 2);
            }
          else
            {
              if (AVR_HAVE_MOVW)
                avr_asm_len ("movw %A0,%A1", op, plen, -1);
              else
                avr_asm_len ("mov %A0,%A1"  CR_TAB
                             "mov %B0,%B1", op, plen, -2);

              return avr_asm_len ("mov %C0,%C1", op, plen, 1);
            }
        }
      else if (CONSTANT_P (src))
        {
          return avr_out_reload_inpsi (op, NULL_RTX, plen);
        }
      else if (MEM_P (src))
        return avr_out_load_psi (insn, op, plen); /* mov r,m */
    }
  else if (MEM_P (dest))
    {
      rtx xop[2];

      xop[0] = dest;
      xop[1] = src == CONST0_RTX (GET_MODE (dest)) ? zero_reg_rtx : src;

      return avr_out_store_psi (insn, xop, plen);
    }

  fatal_insn ("invalid insn:", insn);
  return "";
}

static const char*
avr_out_movqi_mr_r_reg_disp_tiny (rtx_insn *insn, rtx op[], int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx x = XEXP (dest, 0);

  if (reg_overlap_mentioned_p (src, XEXP (x, 0)))
    {
      avr_asm_len ("mov __tmp_reg__,%1"      CR_TAB
                   TINY_ADIW (%I0, %J0, %o0) CR_TAB
                   "st %b0,__tmp_reg__", op, plen, -4);
    }
  else
    {
      avr_asm_len (TINY_ADIW (%I0, %J0, %o0) CR_TAB
                   "st %b0,%1", op, plen, -3);
    }

  if (!reg_unused_after (insn, XEXP (x, 0)))
    avr_asm_len (TINY_SBIW (%I0, %J0, %o0), op, plen, 2);

  return "";
}

static const char*
out_movqi_mr_r (rtx_insn *insn, rtx op[], int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx x = XEXP (dest, 0);

  if (CONSTANT_ADDRESS_P (x))
    {
      int n_words = AVR_TINY ? 1 : 2;
      return io_address_operand (x, QImode)
        ? avr_asm_len ("out %i0,%1", op, plen, -1)
        : avr_asm_len ("sts %m0,%1", op, plen, -n_words);
    }
  else if (GET_CODE (x) == PLUS
           && REG_P (XEXP (x, 0))
           && CONST_INT_P (XEXP (x, 1)))
    {
      /* memory access by reg+disp */

      int disp = INTVAL (XEXP (x, 1));

      if (AVR_TINY)
        return avr_out_movqi_mr_r_reg_disp_tiny (insn, op, plen);

      if (disp - GET_MODE_SIZE (GET_MODE (dest)) >= 63)
        {
          if (REGNO (XEXP (x, 0)) != REG_Y)
            fatal_insn ("incorrect insn:",insn);

          if (disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest)))
            return avr_asm_len ("adiw r28,%o0-63" CR_TAB
                                "std Y+63,%1"     CR_TAB
                                "sbiw r28,%o0-63", op, plen, -3);

          return avr_asm_len ("subi r28,lo8(-%o0)" CR_TAB
                              "sbci r29,hi8(-%o0)" CR_TAB
                              "st Y,%1"            CR_TAB
                              "subi r28,lo8(%o0)"  CR_TAB
                              "sbci r29,hi8(%o0)", op, plen, -5);
        }
      else if (REGNO (XEXP (x, 0)) == REG_X)
        {
          if (reg_overlap_mentioned_p (src, XEXP (x, 0)))
            {
              avr_asm_len ("mov __tmp_reg__,%1" CR_TAB
                           "adiw r26,%o0"       CR_TAB
                           "st X,__tmp_reg__", op, plen, -3);
            }
          else
            {
              avr_asm_len ("adiw r26,%o0" CR_TAB
                           "st X,%1", op, plen, -2);
            }

          if (!reg_unused_after (insn, XEXP (x, 0)))
            avr_asm_len ("sbiw r26,%o0", op, plen, 1);

          return "";
        }

      return avr_asm_len ("std %0,%1", op, plen, -1);
    }

  return avr_asm_len ("st %0,%1", op, plen, -1);
}


/* Helper for the next function for XMEGA.  It does the same
   but with low byte first.  */

static const char*
avr_out_movhi_mr_r_xmega (rtx_insn *insn, rtx op[], int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (dest, 0);
  int reg_base = true_regnum (base);
  int reg_src = true_regnum (src);

  /* "volatile" forces writing low byte first, even if less efficient,
     for correct operation with 16-bit I/O registers like SP.  */
  int mem_volatile_p = MEM_VOLATILE_P (dest);

  if (CONSTANT_ADDRESS_P (base))
    {
      return io_address_operand (base, HImode)
        ? avr_asm_len ("out %i0,%A1" CR_TAB
                       "out %i0+1,%B1", op, plen, -2)

        : avr_asm_len ("sts %m0,%A1" CR_TAB
                       "sts %m0+1,%B1", op, plen, -4);
    }

  if (reg_base > 0)
    {
      if (reg_base != REG_X)
        return avr_asm_len ("st %0,%A1" CR_TAB
                            "std %0+1,%B1", op, plen, -2);

      if (reg_src == REG_X)
        /* "st X+,r26" and "st -X,r26" are undefined.  */
        avr_asm_len ("mov __tmp_reg__,r27" CR_TAB
                     "st X,r26"            CR_TAB
                     "adiw r26,1"          CR_TAB
                     "st X,__tmp_reg__", op, plen, -4);
      else
        avr_asm_len ("st X+,%A1" CR_TAB
                     "st X,%B1", op, plen, -2);

      return reg_unused_after (insn, base)
        ? ""
        : avr_asm_len ("sbiw r26,1", op, plen, 1);
    }
  else if (GET_CODE (base) == PLUS)
    {
      int disp = INTVAL (XEXP (base, 1));
      reg_base = REGNO (XEXP (base, 0));
      if (disp > MAX_LD_OFFSET (GET_MODE (dest)))
        {
          if (reg_base != REG_Y)
            fatal_insn ("incorrect insn:",insn);

          return disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest))
            ? avr_asm_len ("adiw r28,%o0-62" CR_TAB
                           "std Y+62,%A1"    CR_TAB
                           "std Y+63,%B1"    CR_TAB
                           "sbiw r28,%o0-62", op, plen, -4)

            : avr_asm_len ("subi r28,lo8(-%o0)" CR_TAB
                           "sbci r29,hi8(-%o0)" CR_TAB
                           "st Y,%A1"           CR_TAB
                           "std Y+1,%B1"        CR_TAB
                           "subi r28,lo8(%o0)"  CR_TAB
                           "sbci r29,hi8(%o0)", op, plen, -6);
        }

      if (reg_base != REG_X)
        return avr_asm_len ("std %A0,%A1" CR_TAB
                            "std %B0,%B1", op, plen, -2);
      /* (X + d) = R */
      return reg_src == REG_X
        ? avr_asm_len ("mov __tmp_reg__,r26"  CR_TAB
                       "mov __zero_reg__,r27" CR_TAB
                       "adiw r26,%o0"         CR_TAB
                       "st X+,__tmp_reg__"    CR_TAB
                       "st X,__zero_reg__"    CR_TAB
                       "clr __zero_reg__"     CR_TAB
                       "sbiw r26,%o0+1", op, plen, -7)

        : avr_asm_len ("adiw r26,%o0" CR_TAB
                       "st X+,%A1"    CR_TAB
                       "st X,%B1"     CR_TAB
                       "sbiw r26,%o0+1", op, plen, -4);
    }
  else if (GET_CODE (base) == PRE_DEC) /* (--R) */
    {
      if (!mem_volatile_p)
        return avr_asm_len ("st %0,%B1" CR_TAB
                            "st %0,%A1", op, plen, -2);

      return REGNO (XEXP (base, 0)) == REG_X
        ? avr_asm_len ("sbiw r26,2"  CR_TAB
                       "st X+,%A1"   CR_TAB
                       "st X,%B1"    CR_TAB
                       "sbiw r26,1", op, plen, -4)

        : avr_asm_len ("sbiw %r0,2"  CR_TAB
                       "st %p0,%A1"  CR_TAB
                       "std %p0+1,%B1", op, plen, -3);
    }
  else if (GET_CODE (base) == POST_INC) /* (R++) */
    {
      return avr_asm_len ("st %0,%A1"  CR_TAB
                          "st %0,%B1", op, plen, -2);

    }
  fatal_insn ("unknown move insn:",insn);
  return "";
}

static const char*
avr_out_movhi_mr_r_reg_no_disp_tiny (rtx_insn *insn, rtx op[], int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (dest, 0);
  int reg_base = true_regnum (base);
  int reg_src = true_regnum (src);
  int mem_volatile_p = MEM_VOLATILE_P (dest);

  if (reg_base == reg_src)
    {
      return !mem_volatile_p && reg_unused_after (insn, src)
        ? avr_asm_len ("mov __tmp_reg__,%B1"   CR_TAB
                       "st %0,%A1"             CR_TAB
                       TINY_ADIW (%E0, %F0, 1) CR_TAB
                       "st %0,__tmp_reg__", op, plen, -5)
        : avr_asm_len ("mov __tmp_reg__,%B1"   CR_TAB
                       TINY_ADIW (%E0, %F0, 1) CR_TAB
                       "st %0,__tmp_reg__"     CR_TAB
                       TINY_SBIW (%E0, %F0, 1) CR_TAB
                       "st %0, %A1", op, plen, -7);
    }

  return !mem_volatile_p && reg_unused_after (insn, base)
    ? avr_asm_len ("st %0+,%A1" CR_TAB
                   "st %0,%B1", op, plen, -2)
    : avr_asm_len (TINY_ADIW (%E0, %F0, 1) CR_TAB
                   "st %0,%B1"             CR_TAB
                   "st -%0,%A1", op, plen, -4);
}

static const char*
avr_out_movhi_mr_r_reg_disp_tiny (rtx_insn *insn, rtx op[], int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (dest, 0);
  int reg_base = REGNO (XEXP (base, 0));
  int reg_src = true_regnum (src);

  if (reg_src == reg_base)
    avr_asm_len ("mov __tmp_reg__,%A1"          CR_TAB
                 "mov __zero_reg__,%B1"         CR_TAB
                 TINY_ADIW (%I0, %J0, %o0+1)    CR_TAB
                 "st %b0,__zero_reg__"          CR_TAB
                 "st -%b0,__tmp_reg__"          CR_TAB
                 "clr __zero_reg__", op, plen, -7);
  else
    avr_asm_len (TINY_ADIW (%I0, %J0, %o0+1) CR_TAB
                 "st %b0,%B1"                CR_TAB
                 "st -%b0,%A1", op, plen, -4);

  if (!reg_unused_after (insn, XEXP (base, 0)))
    avr_asm_len (TINY_SBIW (%I0, %J0, %o0), op, plen, 2);

  return "";
}

static const char*
avr_out_movhi_mr_r_post_inc_tiny (rtx op[], int *plen)
{
  return avr_asm_len (TINY_ADIW (%I0, %J0, 1)  CR_TAB
                      "st %p0,%B1"    CR_TAB
                      "st -%p0,%A1"   CR_TAB
                      TINY_ADIW (%I0, %J0, 2), op, plen, -6);
}

static const char*
out_movhi_mr_r (rtx_insn *insn, rtx op[], int *plen)
{
  rtx dest = op[0];
  rtx src = op[1];
  rtx base = XEXP (dest, 0);
  int reg_base = true_regnum (base);
  int reg_src = true_regnum (src);
  int mem_volatile_p;

  /* "volatile" forces writing high-byte first (no-xmega) resp.
     low-byte first (xmega) even if less efficient, for correct
     operation with 16-bit I/O registers like.  */

  if (AVR_XMEGA)
    return avr_out_movhi_mr_r_xmega (insn, op, plen);

  mem_volatile_p = MEM_VOLATILE_P (dest);

  if (CONSTANT_ADDRESS_P (base))
    {
      int n_words = AVR_TINY ? 2 : 4;
      return io_address_operand (base, HImode)
        ? avr_asm_len ("out %i0+1,%B1" CR_TAB
                       "out %i0,%A1", op, plen, -2)

        : avr_asm_len ("sts %m0+1,%B1" CR_TAB
                       "sts %m0,%A1", op, plen, -n_words);
    }

  if (reg_base > 0)
    {
      if (AVR_TINY)
        return avr_out_movhi_mr_r_reg_no_disp_tiny (insn, op, plen);

      if (reg_base != REG_X)
        return avr_asm_len ("std %0+1,%B1" CR_TAB
                            "st %0,%A1", op, plen, -2);

      if (reg_src == REG_X)
        /* "st X+,r26" and "st -X,r26" are undefined.  */
        return !mem_volatile_p && reg_unused_after (insn, src)
          ? avr_asm_len ("mov __tmp_reg__,r27" CR_TAB
                         "st X,r26"            CR_TAB
                         "adiw r26,1"          CR_TAB
                         "st X,__tmp_reg__", op, plen, -4)

          : avr_asm_len ("mov __tmp_reg__,r27" CR_TAB
                         "adiw r26,1"          CR_TAB
                         "st X,__tmp_reg__"    CR_TAB
                         "sbiw r26,1"          CR_TAB
                         "st X,r26", op, plen, -5);

      return !mem_volatile_p && reg_unused_after (insn, base)
        ? avr_asm_len ("st X+,%A1" CR_TAB
                       "st X,%B1", op, plen, -2)
        : avr_asm_len ("adiw r26,1" CR_TAB
                       "st X,%B1"   CR_TAB
                       "st -X,%A1", op, plen, -3);
    }
  else if (GET_CODE (base) == PLUS)
    {
      int disp = INTVAL (XEXP (base, 1));

      if (AVR_TINY)
        return avr_out_movhi_mr_r_reg_disp_tiny (insn, op, plen);

      reg_base = REGNO (XEXP (base, 0));
      if (disp > MAX_LD_OFFSET (GET_MODE (dest)))
        {
          if (reg_base != REG_Y)
            fatal_insn ("incorrect insn:",insn);

          return disp <= 63 + MAX_LD_OFFSET (GET_MODE (dest))
            ? avr_asm_len ("adiw r28,%o0-62" CR_TAB
                           "std Y+63,%B1"    CR_TAB
                           "std Y+62,%A1"    CR_TAB
                           "sbiw r28,%o0-62", op, plen, -4)

            : avr_asm_len ("subi r28,lo8(-%o0)" CR_TAB
                           "sbci r29,hi8(-%o0)" CR_TAB
                           "std Y+1,%B1"        CR_TAB
                           "st Y,%A1"           CR_TAB
                           "subi r28,lo8(%o0)"  CR_TAB
                           "sbci r29,hi8(%o0)", op, plen, -6);
        }

      if (reg_base != REG_X)
        return avr_asm_len ("std %B0,%B1" CR_TAB
                            "std %A0,%A1", op, plen, -2);
      /* (X + d) = R */
      return reg_src == REG_X
        ? avr_asm_len ("mov __tmp_reg__,r26"  CR_TAB
                       "mov __zero_reg__,r27" CR_TAB
                       "adiw r26,%o0+1"       CR_TAB
                       "st X,__zero_reg__"    CR_TAB
                       "st -X,__tmp_reg__"    CR_TAB
                       "clr __zero_reg__"     CR_TAB
                       "sbiw r26,%o0", op, plen, -7)

        : avr_asm_len ("adiw r26,%o0+1" CR_TAB
                       "st X,%B1"       CR_TAB
                       "st -X,%A1"      CR_TAB
                       "sbiw r26,%o0", op, plen, -4);
    }
  else if (GET_CODE (base) == PRE_DEC) /* (--R) */
    {
      return avr_asm_len ("st %0,%B1" CR_TAB
                          "st %0,%A1", op, plen, -2);
    }
  else if (GET_CODE (base) == POST_INC) /* (R++) */
    {
      if (!mem_volatile_p)
        return avr_asm_len ("st %0,%A1"  CR_TAB
                            "st %0,%B1", op, plen, -2);

      if (AVR_TINY)
        return avr_out_movhi_mr_r_post_inc_tiny (op, plen);

      return REGNO (XEXP (base, 0)) == REG_X
        ? avr_asm_len ("adiw r26,1"  CR_TAB
                       "st X,%B1"    CR_TAB
                       "st -X,%A1"   CR_TAB
                       "adiw r26,2", op, plen, -4)

        : avr_asm_len ("std %p0+1,%B1" CR_TAB
                       "st %p0,%A1"    CR_TAB
                       "adiw %r0,2", op, plen, -3);
    }
  fatal_insn ("unknown move insn:",insn);
  return "";
}

/* Return 1 if frame pointer for current function required.  */

static bool
avr_frame_pointer_required_p (void)
{
  return (cfun->calls_alloca
          || cfun->calls_setjmp
          || cfun->has_nonlocal_label
          || crtl->args.info.nregs == 0
          || get_frame_size () > 0);
}

/* Returns the condition of compare insn INSN, or UNKNOWN.  */

static RTX_CODE
compare_condition (rtx_insn *insn)
{
  rtx_insn *next = next_real_insn (insn);

  if (next && JUMP_P (next))
    {
      rtx pat = PATTERN (next);
      if (GET_CODE (pat) == PARALLEL)
        pat = XVECEXP (pat, 0, 0);
      rtx src = SET_SRC (pat);

      if (IF_THEN_ELSE == GET_CODE (src))
        return GET_CODE (XEXP (src, 0));
    }

  return UNKNOWN;
}


/* Returns true iff INSN is a tst insn that only tests the sign.  */

static bool
compare_sign_p (rtx_insn *insn)
{
  RTX_CODE cond = compare_condition (insn);
  return (cond == GE || cond == LT);
}


/* Returns true iff the next insn is a JUMP_INSN with a condition
   that needs to be swapped (GT, GTU, LE, LEU).  */

static bool
compare_diff_p (rtx_insn *insn)
{
  RTX_CODE cond = compare_condition (insn);
  return (cond == GT || cond == GTU || cond == LE || cond == LEU) ? cond : 0;
}

/* Returns true iff INSN is a compare insn with the EQ or NE condition.  */

static bool
compare_eq_p (rtx_insn *insn)
{
  RTX_CODE cond = compare_condition (insn);
  return (cond == EQ || cond == NE);
}


/* Output compare instruction

      compare (XOP[0], XOP[1])

   for a register XOP[0] and a compile-time constant XOP[1].  Return "".
   XOP[2] is an 8-bit scratch register as needed.

   PLEN == NULL:  Output instructions.
   PLEN != NULL:  Set *PLEN to the length (in words) of the sequence.
                  Don't output anything.  */

const char*
avr_out_compare (rtx_insn *insn, rtx *xop, int *plen)
{
  /* Register to compare and value to compare against. */
  rtx xreg = xop[0];
  rtx xval = xop[1];

  /* MODE of the comparison.  */
  machine_mode mode;

  /* Number of bytes to operate on.  */
  int n_bytes = GET_MODE_SIZE (GET_MODE (xreg));

  /* Value (0..0xff) held in clobber register xop[2] or -1 if unknown.  */
  int clobber_val = -1;

  /* Map fixed mode operands to integer operands with the same binary
     representation.  They are easier to handle in the remainder.  */

  if (CONST_FIXED_P (xval))
    {
      xreg = avr_to_int_mode (xop[0]);
      xval = avr_to_int_mode (xop[1]);
    }

  mode = GET_MODE (xreg);

  gcc_assert (REG_P (xreg));
  gcc_assert ((CONST_INT_P (xval) && n_bytes <= 4)
              || (const_double_operand (xval, VOIDmode) && n_bytes == 8));

  if (plen)
    *plen = 0;

  /* Comparisons == +/-1 and != +/-1 can be done similar to camparing
     against 0 by ORing the bytes.  This is one instruction shorter.
     Notice that 64-bit comparisons are always against reg:ALL8 18 (ACC_A)
     and therefore don't use this.  */

  if (!test_hard_reg_class (LD_REGS, xreg)
      && compare_eq_p (insn)
      && reg_unused_after (insn, xreg))
    {
      if (xval == const1_rtx)
        {
          avr_asm_len ("dec %A0" CR_TAB
                       "or %A0,%B0", xop, plen, 2);

          if (n_bytes >= 3)
            avr_asm_len ("or %A0,%C0", xop, plen, 1);

          if (n_bytes >= 4)
            avr_asm_len ("or %A0,%D0", xop, plen, 1);

          return "";
        }
      else if (xval == constm1_rtx)
        {
          if (n_bytes >= 4)
            avr_asm_len ("and %A0,%D0", xop, plen, 1);

          if (n_bytes >= 3)
            avr_asm_len ("and %A0,%C0", xop, plen, 1);

          return avr_asm_len ("and %A0,%B0" CR_TAB
                              "com %A0", xop, plen, 2);
        }
    }

  /* Comparisons == -1 and != -1 of a d-register that's used after the
     comparison.  (If it's unused after we use CPI / SBCI or ADIW sequence
     from below.)  Instead of  CPI Rlo,-1 / LDI Rx,-1 / CPC Rhi,Rx  we can
     use  CPI Rlo,-1 / CPC Rhi,Rlo  which is 1 instruction shorter:
     If CPI is true then Rlo contains -1 and we can use Rlo instead of Rx
     when CPC'ing the high part.  If CPI is false then CPC cannot render
     the result to true.  This also works for the more generic case where
     the constant is of the form 0xabab.  */

  if (n_bytes == 2
      && xval != const0_rtx
      && test_hard_reg_class (LD_REGS, xreg)
      && compare_eq_p (insn)
      && !reg_unused_after (insn, xreg))
    {
      rtx xlo8 = simplify_gen_subreg (QImode, xval, mode, 0);
      rtx xhi8 = simplify_gen_subreg (QImode, xval, mode, 1);

      if (INTVAL (xlo8) == INTVAL (xhi8))
        {
          xop[0] = xreg;
          xop[1] = xlo8;

          return avr_asm_len ("cpi %A0,%1"  CR_TAB
                              "cpc %B0,%A0", xop, plen, 2);
        }
    }

  for (int i = 0; i < n_bytes; i++)
    {
      /* We compare byte-wise.  */
      rtx reg8 = simplify_gen_subreg (QImode, xreg, mode, i);
      rtx xval8 = simplify_gen_subreg (QImode, xval, mode, i);

      /* 8-bit value to compare with this byte.  */
      unsigned int val8 = UINTVAL (xval8) & GET_MODE_MASK (QImode);

      /* Registers R16..R31 can operate with immediate.  */
      bool ld_reg_p = test_hard_reg_class (LD_REGS, reg8);

      xop[0] = reg8;
      xop[1] = gen_int_mode (val8, QImode);

      /* Word registers >= R24 can use SBIW/ADIW with 0..63.  */

      if (i == 0
          && test_hard_reg_class (ADDW_REGS, reg8))
        {
          int val16 = trunc_int_for_mode (INTVAL (xval), HImode);

          if (IN_RANGE (val16, 0, 63)
              && (val8 == 0
                  || reg_unused_after (insn, xreg)))
            {
              if (AVR_TINY)
                avr_asm_len (TINY_SBIW (%A0, %B0, %1), xop, plen, 2);
              else
                avr_asm_len ("sbiw %0,%1", xop, plen, 1);

              i++;
              continue;
            }

          if (n_bytes == 2
              && IN_RANGE (val16, -63, -1)
              && compare_eq_p (insn)
              && reg_unused_after (insn, xreg))
            {
              return AVR_TINY
                ? avr_asm_len (TINY_ADIW (%A0, %B0, %n1), xop, plen, 2)
                : avr_asm_len ("adiw %0,%n1", xop, plen, 1);
            }
        }

      /* Comparing against 0 is easy.  */

      if (val8 == 0)
        {
          avr_asm_len (i == 0
                       ? "cp %0,__zero_reg__"
                       : "cpc %0,__zero_reg__", xop, plen, 1);
          continue;
        }

      /* Upper registers can compare and subtract-with-carry immediates.
         Notice that compare instructions do the same as respective subtract
         instruction; the only difference is that comparisons don't write
         the result back to the target register.  */

      if (ld_reg_p)
        {
          if (i == 0)
            {
              avr_asm_len ("cpi %0,%1", xop, plen, 1);
              continue;
            }
          else if (reg_unused_after (insn, xreg))
            {
              avr_asm_len ("sbci %0,%1", xop, plen, 1);
              continue;
            }
        }

      /* Must load the value into the scratch register.  */

      gcc_assert (REG_P (xop[2]));

      if (clobber_val != (int) val8)
        avr_asm_len ("ldi %2,%1", xop, plen, 1);
      clobber_val = (int) val8;

      avr_asm_len (i == 0
                   ? "cp %0,%2"
                   : "cpc %0,%2", xop, plen, 1);
    }

  return "";
}


/* Prepare operands of compare_const_di2 to be used with avr_out_compare.  */

const char*
avr_out_compare64 (rtx_insn *insn, rtx *op, int *plen)
{
  rtx xop[3];

  xop[0] = gen_rtx_REG (DImode, 18);
  xop[1] = op[0];
  xop[2] = op[1];

  return avr_out_compare (insn, xop, plen);
}

/* Output test instruction for HImode.  */

const char*
avr_out_tsthi (rtx_insn *insn, rtx *op, int *plen)
{
  if (compare_sign_p (insn))
    {
      avr_asm_len ("tst %B0", op, plen, -1);
    }
  else if (reg_unused_after (insn, op[0])
           && compare_eq_p (insn))
    {
      /* Faster than sbiw if we can clobber the operand.  */
      avr_asm_len ("or %A0,%B0", op, plen, -1);
    }
  else
    {
      avr_out_compare (insn, op, plen);
    }

  return "";
}


/* Output test instruction for PSImode.  */

const char*
avr_out_tstpsi (rtx_insn *insn, rtx *op, int *plen)
{
  if (compare_sign_p (insn))
    {
      avr_asm_len ("tst %C0", op, plen, -1);
    }
  else if (reg_unused_after (insn, op[0])
           && compare_eq_p (insn))
    {
      /* Faster than sbiw if we can clobber the operand.  */
      avr_asm_len ("or %A0,%B0" CR_TAB
                   "or %A0,%C0", op, plen, -2);
    }
  else
    {
      avr_out_compare (insn, op, plen);
    }

  return "";
}


/* Output test instruction for SImode.  */

const char*
avr_out_tstsi (rtx_insn *insn, rtx *op, int *plen)
{
  if (compare_sign_p (insn))
    {
      avr_asm_len ("tst %D0", op, plen, -1);
    }
  else if (reg_unused_after (insn, op[0])
           && compare_eq_p (insn))
    {
      /* Faster than sbiw if we can clobber the operand.  */
      avr_asm_len ("or %A0,%B0" CR_TAB
                   "or %A0,%C0" CR_TAB
                   "or %A0,%D0", op, plen, -3);
    }
  else
    {
      avr_out_compare (insn, op, plen);
    }

  return "";
}


/* Generate asm equivalent for various shifts.  This only handles cases
   that are not already carefully hand-optimized in ?sh??i3_out.

   OPERANDS[0] resp. %0 in TEMPL is the operand to be shifted.
   OPERANDS[2] is the shift count as CONST_INT, MEM or REG.
   OPERANDS[3] is a QImode scratch register from LD regs if
               available and SCRATCH, otherwise (no scratch available)

   TEMPL is an assembler template that shifts by one position.
   T_LEN is the length of this template.  */

void
out_shift_with_cnt (const char *templ, rtx_insn *insn, rtx operands[],
		    int *plen, int t_len)
{
  bool second_label = true;
  bool saved_in_tmp = false;
  bool use_zero_reg = false;
  rtx op[5];

  op[0] = operands[0];
  op[1] = operands[1];
  op[2] = operands[2];
  op[3] = operands[3];

  if (plen)
    *plen = 0;

  if (CONST_INT_P (operands[2]))
    {
      /* Operand 3 is a scratch register if this is a
         parallel with three elements i.e. a set,
         a clobber of a scratch, and clobber of REG_CC.
         If a scratch reg is not available, then the parallel
         will contain only a set and clobber of REG_CC. */
      bool scratch = (GET_CODE (PATTERN (insn)) == PARALLEL
                      && XVECLEN (PATTERN (insn), 0) == 3
                      && REG_P (operands[3]));
      int count = INTVAL (operands[2]);
      int max_len = 10;  /* If larger than this, always use a loop.  */

      if (count <= 0)
        return;

      if (count < 8 && !scratch)
        use_zero_reg = true;

      if (optimize_size)
        max_len = t_len + (scratch ? 3 : (use_zero_reg ? 4 : 5));

      if (t_len * count <= max_len)
        {
          /* Output shifts inline with no loop - faster.  */

          while (count-- > 0)
            avr_asm_len (templ, op, plen, t_len);

          return;
        }

      if (scratch)
        {
          avr_asm_len ("ldi %3,%2", op, plen, 1);
        }
      else if (use_zero_reg)
        {
          /* Hack to save one word: use __zero_reg__ as loop counter.
             Set one bit, then shift in a loop until it is 0 again.  */

          op[3] = zero_reg_rtx;

          avr_asm_len ("set" CR_TAB
                       "bld %3,%2-1", op, plen, 2);
        }
      else
        {
          /* No scratch register available, use one from LD_REGS (saved in
             __tmp_reg__) that doesn't overlap with registers to shift.  */

          op[3] = all_regs_rtx[((REGNO (op[0]) - 1) & 15) + 16];
          op[4] = tmp_reg_rtx;
          saved_in_tmp = true;

          avr_asm_len ("mov %4,%3" CR_TAB
                       "ldi %3,%2", op, plen, 2);
        }

      second_label = false;
    }
  else if (MEM_P (op[2]))
    {
      rtx op_mov[2];

      op_mov[0] = op[3] = tmp_reg_rtx;
      op_mov[1] = op[2];

      out_movqi_r_mr (insn, op_mov, plen);
    }
  else if (register_operand (op[2], QImode))
    {
      op[3] = op[2];

      if (!reg_unused_after (insn, op[2])
          || reg_overlap_mentioned_p (op[0], op[2]))
        {
          op[3] = tmp_reg_rtx;
          avr_asm_len ("mov %3,%2", op, plen, 1);
        }
    }
  else
    fatal_insn ("bad shift insn:", insn);

  if (second_label)
    avr_asm_len ("rjmp 2f", op, plen, 1);

  avr_asm_len ("1:", op, plen, 0);
  avr_asm_len (templ, op, plen, t_len);

  if (second_label)
    avr_asm_len ("2:", op, plen, 0);

  avr_asm_len (use_zero_reg ? "lsr %3" : "dec %3", op, plen, 1);
  avr_asm_len (second_label ? "brpl 1b" : "brne 1b", op, plen, 1);

  if (saved_in_tmp)
    avr_asm_len ("mov %3,%4", op, plen, 1);
}


/* 8bit shift left ((char)x << i)   */

const char *
ashlqi3_out (rtx_insn *insn, rtx operands[], int *len)
{
  if (CONST_INT_P (operands[2]))
    {
      int k;

      if (!len)
	len = &k;

      switch (INTVAL (operands[2]))
	{
	default:
	  if (INTVAL (operands[2]) < 8)
	    break;

	  *len = 1;
	  return "clr %0";

	case 1:
	  *len = 1;
	  return "lsl %0";

	case 2:
	  *len = 2;
	  return ("lsl %0" CR_TAB
		  "lsl %0");

	case 3:
	  *len = 3;
	  return ("lsl %0" CR_TAB
		  "lsl %0" CR_TAB
		  "lsl %0");

	case 4:
	  if (test_hard_reg_class (LD_REGS, operands[0]))
	    {
	      *len = 2;
	      return ("swap %0" CR_TAB
		      "andi %0,0xf0");
	    }
	  *len = 4;
	  return ("lsl %0" CR_TAB
		  "lsl %0" CR_TAB
		  "lsl %0" CR_TAB
		  "lsl %0");

	case 5:
	  if (test_hard_reg_class (LD_REGS, operands[0]))
	    {
	      *len = 3;
	      return ("swap %0" CR_TAB
		      "lsl %0"  CR_TAB
		      "andi %0,0xe0");
	    }
	  *len = 5;
	  return ("lsl %0" CR_TAB
		  "lsl %0" CR_TAB
		  "lsl %0" CR_TAB
		  "lsl %0" CR_TAB
		  "lsl %0");

	case 6:
	  if (test_hard_reg_class (LD_REGS, operands[0]))
	    {
	      *len = 4;
	      return ("swap %0" CR_TAB
		      "lsl %0"  CR_TAB
		      "lsl %0"  CR_TAB
		      "andi %0,0xc0");
	    }
	  *len = 6;
	  return ("lsl %0" CR_TAB
		  "lsl %0" CR_TAB
		  "lsl %0" CR_TAB
		  "lsl %0" CR_TAB
		  "lsl %0" CR_TAB
		  "lsl %0");

	case 7:
	  *len = 3;
	  return ("ror %0" CR_TAB
		  "clr %0" CR_TAB
		  "ror %0");
	}
    }
  else if (CONSTANT_P (operands[2]))
    fatal_insn ("internal compiler error.  Incorrect shift:", insn);

  out_shift_with_cnt ("lsl %0",
                      insn, operands, len, 1);
  return "";
}


/* 16bit shift left ((short)x << i)   */

const char *
ashlhi3_out (rtx_insn *insn, rtx operands[], int *len)
{
  if (CONST_INT_P (operands[2]))
    {
      int scratch = (GET_CODE (PATTERN (insn)) == PARALLEL
                     && XVECLEN (PATTERN (insn), 0) == 3
                     && REG_P (operands[3]));
      int ldi_ok = test_hard_reg_class (LD_REGS, operands[0]);
      int k;
      int *t = len;

      if (!len)
	len = &k;

      switch (INTVAL (operands[2]))
	{
	default:
	  if (INTVAL (operands[2]) < 16)
	    break;

	  *len = 2;
	  return ("clr %B0" CR_TAB
		  "clr %A0");

	case 4:
	  if (optimize_size && scratch)
	    break;  /* 5 */
	  if (ldi_ok)
	    {
	      *len = 6;
	      return ("swap %A0"      CR_TAB
		      "swap %B0"      CR_TAB
		      "andi %B0,0xf0" CR_TAB
		      "eor %B0,%A0"   CR_TAB
		      "andi %A0,0xf0" CR_TAB
		      "eor %B0,%A0");
	    }
	  if (scratch)
	    {
	      *len = 7;
	      return ("swap %A0"    CR_TAB
		      "swap %B0"    CR_TAB
		      "ldi %3,0xf0" CR_TAB
		      "and %B0,%3"  CR_TAB
		      "eor %B0,%A0" CR_TAB
		      "and %A0,%3"  CR_TAB
		      "eor %B0,%A0");
	    }
	  break;  /* optimize_size ? 6 : 8 */

	case 5:
	  if (optimize_size)
	    break;  /* scratch ? 5 : 6 */
	  if (ldi_ok)
	    {
	      *len = 8;
	      return ("lsl %A0"       CR_TAB
		      "rol %B0"       CR_TAB
		      "swap %A0"      CR_TAB
		      "swap %B0"      CR_TAB
		      "andi %B0,0xf0" CR_TAB
		      "eor %B0,%A0"   CR_TAB
		      "andi %A0,0xf0" CR_TAB
		      "eor %B0,%A0");
	    }
	  if (scratch)
	    {
	      *len = 9;
	      return ("lsl %A0"     CR_TAB
		      "rol %B0"     CR_TAB
		      "swap %A0"    CR_TAB
		      "swap %B0"    CR_TAB
		      "ldi %3,0xf0" CR_TAB
		      "and %B0,%3"  CR_TAB
		      "eor %B0,%A0" CR_TAB
		      "and %A0,%3"  CR_TAB
		      "eor %B0,%A0");
	    }
	  break;  /* 10 */

	case 6:
	  if (optimize_size)
	    break;  /* scratch ? 5 : 6 */
	  *len = 9;
	  return ("clr __tmp_reg__" CR_TAB
		  "lsr %B0"         CR_TAB
		  "ror %A0"         CR_TAB
		  "ror __tmp_reg__" CR_TAB
		  "lsr %B0"         CR_TAB
		  "ror %A0"         CR_TAB
		  "ror __tmp_reg__" CR_TAB
		  "mov %B0,%A0"     CR_TAB
		  "mov %A0,__tmp_reg__");

	case 7:
	  *len = 5;
	  return ("lsr %B0"     CR_TAB
		  "mov %B0,%A0" CR_TAB
		  "clr %A0"     CR_TAB
		  "ror %B0"     CR_TAB
		  "ror %A0");

	case 8:
	  return *len = 2, ("mov %B0,%A1" CR_TAB
			    "clr %A0");

	case 9:
	  *len = 3;
	  return ("mov %B0,%A0" CR_TAB
		  "clr %A0"     CR_TAB
		  "lsl %B0");

	case 10:
	  *len = 4;
	  return ("mov %B0,%A0" CR_TAB
		  "clr %A0"     CR_TAB
		  "lsl %B0"     CR_TAB
		  "lsl %B0");

	case 11:
	  *len = 5;
	  return ("mov %B0,%A0" CR_TAB
		  "clr %A0"     CR_TAB
		  "lsl %B0"     CR_TAB
		  "lsl %B0"     CR_TAB
		  "lsl %B0");

	case 12:
	  if (ldi_ok)
	    {
	      *len = 4;
	      return ("mov %B0,%A0" CR_TAB
		      "clr %A0"     CR_TAB
		      "swap %B0"    CR_TAB
		      "andi %B0,0xf0");
	    }
	  if (scratch)
	    {
	      *len = 5;
	      return ("mov %B0,%A0" CR_TAB
		      "clr %A0"     CR_TAB
		      "swap %B0"    CR_TAB
		      "ldi %3,0xf0" CR_TAB
		      "and %B0,%3");
	    }
	  *len = 6;
	  return ("mov %B0,%A0" CR_TAB
		  "clr %A0"     CR_TAB
		  "lsl %B0"     CR_TAB
		  "lsl %B0"     CR_TAB
		  "lsl %B0"     CR_TAB
		  "lsl %B0");

	case 13:
	  if (ldi_ok)
	    {
	      *len = 5;
	      return ("mov %B0,%A0" CR_TAB
		      "clr %A0"     CR_TAB
		      "swap %B0"    CR_TAB
		      "lsl %B0"     CR_TAB
		      "andi %B0,0xe0");
	    }
	  if (AVR_HAVE_MUL && scratch)
	    {
	      *len = 5;
	      return ("ldi %3,0x20" CR_TAB
		      "mul %A0,%3"  CR_TAB
		      "mov %B0,r0"  CR_TAB
		      "clr %A0"     CR_TAB
		      "clr __zero_reg__");
	    }
	  if (optimize_size && scratch)
	    break;  /* 5 */
	  if (scratch)
	    {
	      *len = 6;
	      return ("mov %B0,%A0" CR_TAB
		      "clr %A0"     CR_TAB
		      "swap %B0"    CR_TAB
		      "lsl %B0"     CR_TAB
		      "ldi %3,0xe0" CR_TAB
		      "and %B0,%3");
	    }
	  if (AVR_HAVE_MUL)
	    {
	      *len = 6;
	      return ("set"        CR_TAB
		      "bld r1,5"   CR_TAB
		      "mul %A0,r1" CR_TAB
		      "mov %B0,r0" CR_TAB
		      "clr %A0"    CR_TAB
		      "clr __zero_reg__");
	    }
	  *len = 7;
	  return ("mov %B0,%A0" CR_TAB
		  "clr %A0"     CR_TAB
		  "lsl %B0"     CR_TAB
		  "lsl %B0"     CR_TAB
		  "lsl %B0"     CR_TAB
		  "lsl %B0"     CR_TAB
		  "lsl %B0");

	case 14:
	  if (AVR_HAVE_MUL && ldi_ok)
	    {
	      *len = 5;
	      return ("ldi %B0,0x40" CR_TAB
		      "mul %A0,%B0"  CR_TAB
		      "mov %B0,r0"   CR_TAB
		      "clr %A0"      CR_TAB
		      "clr __zero_reg__");
	    }
	  if (AVR_HAVE_MUL && scratch)
	    {
	      *len = 5;
	      return ("ldi %3,0x40" CR_TAB
		      "mul %A0,%3"  CR_TAB
		      "mov %B0,r0"  CR_TAB
		      "clr %A0"     CR_TAB
		      "clr __zero_reg__");
	    }
	  if (optimize_size && ldi_ok)
	    {
	      *len = 5;
	      return ("mov %B0,%A0" CR_TAB
		      "ldi %A0,6" "\n1:\t"
		      "lsl %B0"     CR_TAB
		      "dec %A0"     CR_TAB
		      "brne 1b");
	    }
	  if (optimize_size && scratch)
	    break;  /* 5 */
	  *len = 6;
	  return ("clr %B0" CR_TAB
		  "lsr %A0" CR_TAB
		  "ror %B0" CR_TAB
		  "lsr %A0" CR_TAB
		  "ror %B0" CR_TAB
		  "clr %A0");

	case 15:
	  *len = 4;
	  return ("clr %B0" CR_TAB
		  "lsr %A0" CR_TAB
		  "ror %B0" CR_TAB
		  "clr %A0");
	}
      len = t;
    }
  out_shift_with_cnt ("lsl %A0" CR_TAB
                      "rol %B0", insn, operands, len, 2);
  return "";
}


/* 24-bit shift left */

const char*
avr_out_ashlpsi3 (rtx_insn *insn, rtx *op, int *plen)
{
  if (plen)
    *plen = 0;

  if (CONST_INT_P (op[2]))
    {
      switch (INTVAL (op[2]))
        {
        default:
          if (INTVAL (op[2]) < 24)
            break;

          return avr_asm_len ("clr %A0" CR_TAB
                              "clr %B0" CR_TAB
                              "clr %C0", op, plen, 3);

        case 8:
          {
            int reg0 = REGNO (op[0]);
            int reg1 = REGNO (op[1]);

            if (reg0 >= reg1)
              return avr_asm_len ("mov %C0,%B1"  CR_TAB
                                  "mov %B0,%A1"  CR_TAB
                                  "clr %A0", op, plen, 3);
            else
              return avr_asm_len ("clr %A0"      CR_TAB
                                  "mov %B0,%A1"  CR_TAB
                                  "mov %C0,%B1", op, plen, 3);
          }

        case 16:
          {
            int reg0 = REGNO (op[0]);
            int reg1 = REGNO (op[1]);

            if (reg0 + 2 != reg1)
              avr_asm_len ("mov %C0,%A0", op, plen, 1);

            return avr_asm_len ("clr %B0"  CR_TAB
                                "clr %A0", op, plen, 2);
          }

        case 23:
          return avr_asm_len ("clr %C0" CR_TAB
                              "lsr %A0" CR_TAB
                              "ror %C0" CR_TAB
                              "clr %B0" CR_TAB
                              "clr %A0", op, plen, 5);
        }
    }

  out_shift_with_cnt ("lsl %A0" CR_TAB
                      "rol %B0" CR_TAB
                      "rol %C0", insn, op, plen, 3);
  return "";
}


/* 32bit shift left ((long)x << i)   */

const char *
ashlsi3_out (rtx_insn *insn, rtx operands[], int *len)
{
  if (CONST_INT_P (operands[2]))
    {
      int k;
      int *t = len;

      if (!len)
	len = &k;

      switch (INTVAL (operands[2]))
	{
	default:
	  if (INTVAL (operands[2]) < 32)
	    break;

	  if (AVR_HAVE_MOVW)
	    return *len = 3, ("clr %D0" CR_TAB
			      "clr %C0" CR_TAB
			      "movw %A0,%C0");
	  *len = 4;
	  return ("clr %D0" CR_TAB
		  "clr %C0" CR_TAB
		  "clr %B0" CR_TAB
		  "clr %A0");

	case 8:
	  {
	    int reg0 = true_regnum (operands[0]);
	    int reg1 = true_regnum (operands[1]);
	    *len = 4;
	    if (reg0 >= reg1)
	      return ("mov %D0,%C1"  CR_TAB
		      "mov %C0,%B1"  CR_TAB
		      "mov %B0,%A1"  CR_TAB
		      "clr %A0");
	    else
	      return ("clr %A0"      CR_TAB
		      "mov %B0,%A1"  CR_TAB
		      "mov %C0,%B1"  CR_TAB
		      "mov %D0,%C1");
	  }

	case 16:
	  {
	    int reg0 = true_regnum (operands[0]);
	    int reg1 = true_regnum (operands[1]);
	    if (reg0 + 2 == reg1)
	      return *len = 2, ("clr %B0"      CR_TAB
				"clr %A0");
	    if (AVR_HAVE_MOVW)
	      return *len = 3, ("movw %C0,%A1" CR_TAB
				"clr %B0"      CR_TAB
				"clr %A0");
	    else
	      return *len = 4, ("mov %C0,%A1"  CR_TAB
				"mov %D0,%B1"  CR_TAB
				"clr %B0"      CR_TAB
				"clr %A0");
	  }

	case 24:
	  *len = 4;
	  return ("mov %D0,%A1"  CR_TAB
		  "clr %C0"      CR_TAB
		  "clr %B0"      CR_TAB
		  "clr %A0");

	case 31:
	  *len = 6;
	  return ("clr %D0" CR_TAB
		  "lsr %A0" CR_TAB
		  "ror %D0" CR_TAB
		  "clr %C0" CR_TAB
		  "clr %B0" CR_TAB
		  "clr %A0");
	}
      len = t;
    }
  out_shift_with_cnt ("lsl %A0" CR_TAB
                      "rol %B0" CR_TAB
                      "rol %C0" CR_TAB
                      "rol %D0", insn, operands, len, 4);
  return "";
}

/* 8bit arithmetic shift right  ((signed char)x >> i) */

const char *
ashrqi3_out (rtx_insn *insn, rtx operands[], int *len)
{
  if (CONST_INT_P (operands[2]))
    {
      int k;

      if (!len)
	len = &k;

      switch (INTVAL (operands[2]))
	{
	case 1:
	  *len = 1;
	  return "asr %0";

	case 2:
	  *len = 2;
	  return ("asr %0" CR_TAB
		  "asr %0");

	case 3:
	  *len = 3;
	  return ("asr %0" CR_TAB
		  "asr %0" CR_TAB
		  "asr %0");

	case 4:
	  *len = 4;
	  return ("asr %0" CR_TAB
		  "asr %0" CR_TAB
		  "asr %0" CR_TAB
		  "asr %0");

	case 5:
	  *len = 5;
	  return ("asr %0" CR_TAB
		  "asr %0" CR_TAB
		  "asr %0" CR_TAB
		  "asr %0" CR_TAB
		  "asr %0");

	case 6:
	  *len = 4;
	  return ("bst %0,6"  CR_TAB
		  "lsl %0"    CR_TAB
		  "sbc %0,%0" CR_TAB
		  "bld %0,0");

	default:
	  if (INTVAL (operands[2]) < 8)
	    break;

	  /* fall through */

	case 7:
	  *len = 2;
	  return ("lsl %0" CR_TAB
		  "sbc %0,%0");
	}
    }
  else if (CONSTANT_P (operands[2]))
    fatal_insn ("internal compiler error.  Incorrect shift:", insn);

  out_shift_with_cnt ("asr %0",
                      insn, operands, len, 1);
  return "";
}


/* 16bit arithmetic shift right  ((signed short)x >> i) */

const char *
ashrhi3_out (rtx_insn *insn, rtx operands[], int *len)
{
  if (CONST_INT_P (operands[2]))
    {
      int scratch = (GET_CODE (PATTERN (insn)) == PARALLEL
                     && XVECLEN (PATTERN (insn), 0) == 3
                     && REG_P (operands[3]));
      int ldi_ok = test_hard_reg_class (LD_REGS, operands[0]);
      int k;
      int *t = len;

      if (!len)
	len = &k;

      switch (INTVAL (operands[2]))
	{
	case 4:
	case 5:
	  /* XXX try to optimize this too? */
	  break;

	case 6:
	  if (optimize_size)
	    break;  /* scratch ? 5 : 6 */
	  *len = 8;
	  return ("mov __tmp_reg__,%A0" CR_TAB
		  "mov %A0,%B0"         CR_TAB
		  "lsl __tmp_reg__"     CR_TAB
		  "rol %A0"             CR_TAB
		  "sbc %B0,%B0"         CR_TAB
		  "lsl __tmp_reg__"     CR_TAB
		  "rol %A0"             CR_TAB
		  "rol %B0");

	case 7:
	  *len = 4;
	  return ("lsl %A0"     CR_TAB
		  "mov %A0,%B0" CR_TAB
		  "rol %A0"     CR_TAB
		  "sbc %B0,%B0");

	case 8:
	  {
	    int reg0 = true_regnum (operands[0]);
	    int reg1 = true_regnum (operands[1]);

	    if (reg0 == reg1)
	      return *len = 3, ("mov %A0,%B0" CR_TAB
				"lsl %B0"     CR_TAB
				"sbc %B0,%B0");
	    else
	      return *len = 4, ("mov %A0,%B1" CR_TAB
			        "clr %B0"     CR_TAB
			        "sbrc %A0,7"  CR_TAB
			        "dec %B0");
	  }

	case 9:
	  *len = 4;
	  return ("mov %A0,%B0" CR_TAB
		  "lsl %B0"      CR_TAB
		  "sbc %B0,%B0" CR_TAB
		  "asr %A0");

	case 10:
	  *len = 5;
	  return ("mov %A0,%B0" CR_TAB
		  "lsl %B0"     CR_TAB
		  "sbc %B0,%B0" CR_TAB
		  "asr %A0"     CR_TAB
		  "asr %A0");

	case 11:
	  if (AVR_HAVE_MUL && ldi_ok)
	    {
	      *len = 5;
	      return ("ldi %A0,0x20" CR_TAB
		      "muls %B0,%A0" CR_TAB
		      "mov %A0,r1"   CR_TAB
		      "sbc %B0,%B0"  CR_TAB
		      "clr __zero_reg__");
	    }
	  if (optimize_size && scratch)
	    break;  /* 5 */
	  *len = 6;
	  return ("mov %A0,%B0" CR_TAB
		  "lsl %B0"     CR_TAB
		  "sbc %B0,%B0" CR_TAB
		  "asr %A0"     CR_TAB
		  "asr %A0"     CR_TAB
		  "asr %A0");

	case 12:
	  if (AVR_HAVE_MUL && ldi_ok)
	    {
	      *len = 5;
	      return ("ldi %A0,0x10" CR_TAB
		      "muls %B0,%A0" CR_TAB
		      "mov %A0,r1"   CR_TAB
		      "sbc %B0,%B0"  CR_TAB
		      "clr __zero_reg__");
	    }
	  if (optimize_size && scratch)
	    break;  /* 5 */
	  *len = 7;
	  return ("mov %A0,%B0" CR_TAB
		  "lsl %B0"     CR_TAB
		  "sbc %B0,%B0" CR_TAB
		  "asr %A0"     CR_TAB
		  "asr %A0"     CR_TAB
		  "asr %A0"     CR_TAB
		  "asr %A0");

	case 13:
	  if (AVR_HAVE_MUL && ldi_ok)
	    {
	      *len = 5;
	      return ("ldi %A0,0x08" CR_TAB
		      "muls %B0,%A0" CR_TAB
		      "mov %A0,r1"   CR_TAB
		      "sbc %B0,%B0"  CR_TAB
		      "clr __zero_reg__");
	    }
	  if (optimize_size)
	    break;  /* scratch ? 5 : 7 */
	  *len = 8;
	  return ("mov %A0,%B0" CR_TAB
		  "lsl %B0"     CR_TAB
		  "sbc %B0,%B0" CR_TAB
		  "asr %A0"     CR_TAB
		  "asr %A0"     CR_TAB
		  "asr %A0"     CR_TAB
		  "asr %A0"     CR_TAB
		  "asr %A0");

	case 14:
	  *len = 5;
	  return ("lsl %B0"     CR_TAB
		  "sbc %A0,%A0" CR_TAB
		  "lsl %B0"     CR_TAB
		  "mov %B0,%A0" CR_TAB
		  "rol %A0");

	default:
	  if (INTVAL (operands[2]) < 16)
	    break;

	  /* fall through */

	case 15:
	  return *len = 3, ("lsl %B0"     CR_TAB
			    "sbc %A0,%A0" CR_TAB
			    "mov %B0,%A0");
	}
      len = t;
    }
  out_shift_with_cnt ("asr %B0" CR_TAB
                      "ror %A0", insn, operands, len, 2);
  return "";
}


/* 24-bit arithmetic shift right */

const char*
avr_out_ashrpsi3 (rtx_insn *insn, rtx *op, int *plen)
{
  int dest = REGNO (op[0]);
  int src = REGNO (op[1]);

  if (CONST_INT_P (op[2]))
    {
      if (plen)
        *plen = 0;

      switch (INTVAL (op[2]))
        {
        case 8:
          if (dest <= src)
            return avr_asm_len ("mov %A0,%B1" CR_TAB
                                "mov %B0,%C1" CR_TAB
                                "clr %C0"     CR_TAB
                                "sbrc %B0,7"  CR_TAB
                                "dec %C0", op, plen, 5);
          else
            return avr_asm_len ("clr %C0"     CR_TAB
                                "sbrc %C1,7"  CR_TAB
                                "dec %C0"     CR_TAB
                                "mov %B0,%C1" CR_TAB
                                "mov %A0,%B1", op, plen, 5);

        case 16:
          if (dest != src + 2)
            avr_asm_len ("mov %A0,%C1", op, plen, 1);

          return avr_asm_len ("clr %B0"     CR_TAB
                              "sbrc %A0,7"  CR_TAB
                              "com %B0"     CR_TAB
                              "mov %C0,%B0", op, plen, 4);

        default:
          if (INTVAL (op[2]) < 24)
            break;

          /* fall through */

        case 23:
          return avr_asm_len ("lsl %C0"     CR_TAB
                              "sbc %A0,%A0" CR_TAB
                              "mov %B0,%A0" CR_TAB
                              "mov %C0,%A0", op, plen, 4);
        } /* switch */
    }

  out_shift_with_cnt ("asr %C0" CR_TAB
                      "ror %B0" CR_TAB
                      "ror %A0", insn, op, plen, 3);
  return "";
}


/* 32-bit arithmetic shift right  ((signed long)x >> i) */

const char *
ashrsi3_out (rtx_insn *insn, rtx operands[], int *len)
{
  if (CONST_INT_P (operands[2]))
    {
      int k;
      int *t = len;

      if (!len)
	len = &k;

      switch (INTVAL (operands[2]))
	{
	case 8:
	  {
	    int reg0 = true_regnum (operands[0]);
	    int reg1 = true_regnum (operands[1]);
	    *len=6;
	    if (reg0 <= reg1)
	      return ("mov %A0,%B1" CR_TAB
		      "mov %B0,%C1" CR_TAB
		      "mov %C0,%D1" CR_TAB
		      "clr %D0"     CR_TAB
		      "sbrc %C0,7"  CR_TAB
		      "dec %D0");
	    else
	      return ("clr %D0"     CR_TAB
		      "sbrc %D1,7"  CR_TAB
		      "dec %D0"     CR_TAB
		      "mov %C0,%D1" CR_TAB
		      "mov %B0,%C1" CR_TAB
		      "mov %A0,%B1");
	  }

	case 16:
	  {
	    int reg0 = true_regnum (operands[0]);
	    int reg1 = true_regnum (operands[1]);

	    if (reg0 == reg1 + 2)
	      return *len = 4, ("clr %D0"     CR_TAB
				"sbrc %B0,7"  CR_TAB
				"com %D0"     CR_TAB
				"mov %C0,%D0");
	    if (AVR_HAVE_MOVW)
	      return *len = 5, ("movw %A0,%C1" CR_TAB
				"clr %D0"      CR_TAB
				"sbrc %B0,7"   CR_TAB
				"com %D0"      CR_TAB
				"mov %C0,%D0");
	    else
	      return *len = 6, ("mov %B0,%D1" CR_TAB
				"mov %A0,%C1" CR_TAB
				"clr %D0"     CR_TAB
				"sbrc %B0,7"  CR_TAB
				"com %D0"     CR_TAB
				"mov %C0,%D0");
	  }

	case 24:
	  return *len = 6, ("mov %A0,%D1" CR_TAB
			    "clr %D0"     CR_TAB
			    "sbrc %A0,7"  CR_TAB
			    "com %D0"     CR_TAB
			    "mov %B0,%D0" CR_TAB
			    "mov %C0,%D0");

	default:
	  if (INTVAL (operands[2]) < 32)
	    break;

	  /* fall through */

	case 31:
	  if (AVR_HAVE_MOVW)
	    return *len = 4, ("lsl %D0"     CR_TAB
			      "sbc %A0,%A0" CR_TAB
			      "mov %B0,%A0" CR_TAB
			      "movw %C0,%A0");
	  else
	    return *len = 5, ("lsl %D0"     CR_TAB
			      "sbc %A0,%A0" CR_TAB
			      "mov %B0,%A0" CR_TAB
			      "mov %C0,%A0" CR_TAB
			      "mov %D0,%A0");
	}
      len = t;
    }
  out_shift_with_cnt ("asr %D0" CR_TAB
                      "ror %C0" CR_TAB
                      "ror %B0" CR_TAB
                      "ror %A0", insn, operands, len, 4);
  return "";
}

/* 8-bit logic shift right ((unsigned char)x >> i) */

const char *
lshrqi3_out (rtx_insn *insn, rtx operands[], int *len)
{
  if (CONST_INT_P (operands[2]))
    {
      int k;

      if (!len)
	len = &k;

      switch (INTVAL (operands[2]))
	{
	default:
	  if (INTVAL (operands[2]) < 8)
	    break;

	  *len = 1;
	  return "clr %0";

	case 1:
	  *len = 1;
	  return "lsr %0";

	case 2:
	  *len = 2;
	  return ("lsr %0" CR_TAB
		  "lsr %0");
	case 3:
	  *len = 3;
	  return ("lsr %0" CR_TAB
		  "lsr %0" CR_TAB
		  "lsr %0");

	case 4:
	  if (test_hard_reg_class (LD_REGS, operands[0]))
	    {
	      *len=2;
	      return ("swap %0" CR_TAB
		      "andi %0,0x0f");
	    }
	  *len = 4;
	  return ("lsr %0" CR_TAB
		  "lsr %0" CR_TAB
		  "lsr %0" CR_TAB
		  "lsr %0");

	case 5:
	  if (test_hard_reg_class (LD_REGS, operands[0]))
	    {
	      *len = 3;
	      return ("swap %0" CR_TAB
		      "lsr %0"  CR_TAB
		      "andi %0,0x7");
	    }
	  *len = 5;
	  return ("lsr %0" CR_TAB
		  "lsr %0" CR_TAB
		  "lsr %0" CR_TAB
		  "lsr %0" CR_TAB
		  "lsr %0");

	case 6:
	  if (test_hard_reg_class (LD_REGS, operands[0]))
	    {
	      *len = 4;
	      return ("swap %0" CR_TAB
		      "lsr %0"  CR_TAB
		      "lsr %0"  CR_TAB
		      "andi %0,0x3");
	    }
	  *len = 6;
	  return ("lsr %0" CR_TAB
		  "lsr %0" CR_TAB
		  "lsr %0" CR_TAB
		  "lsr %0" CR_TAB
		  "lsr %0" CR_TAB
		  "lsr %0");

	case 7:
	  *len = 3;
	  return ("rol %0" CR_TAB
		  "clr %0" CR_TAB
		  "rol %0");
	}
    }
  else if (CONSTANT_P (operands[2]))
    fatal_insn ("internal compiler error.  Incorrect shift:", insn);

  out_shift_with_cnt ("lsr %0",
                      insn, operands, len, 1);
  return "";
}

/* 16-bit logic shift right ((unsigned short)x >> i) */

const char *
lshrhi3_out (rtx_insn *insn, rtx operands[], int *len)
{
  if (CONST_INT_P (operands[2]))
    {
      int scratch = (GET_CODE (PATTERN (insn)) == PARALLEL
                     && XVECLEN (PATTERN (insn), 0) == 3
                     && REG_P (operands[3]));
      int ldi_ok = test_hard_reg_class (LD_REGS, operands[0]);
      int k;
      int *t = len;

      if (!len)
	len = &k;

      switch (INTVAL (operands[2]))
	{
	default:
	  if (INTVAL (operands[2]) < 16)
	    break;

	  *len = 2;
	  return ("clr %B0" CR_TAB
		  "clr %A0");

	case 4:
	  if (optimize_size && scratch)
	    break;  /* 5 */
	  if (ldi_ok)
	    {
	      *len = 6;
	      return ("swap %B0"      CR_TAB
		      "swap %A0"      CR_TAB
		      "andi %A0,0x0f" CR_TAB
		      "eor %A0,%B0"   CR_TAB
		      "andi %B0,0x0f" CR_TAB
		      "eor %A0,%B0");
	    }
	  if (scratch)
	    {
	      *len = 7;
	      return ("swap %B0"    CR_TAB
		      "swap %A0"    CR_TAB
		      "ldi %3,0x0f" CR_TAB
		      "and %A0,%3"  CR_TAB
		      "eor %A0,%B0" CR_TAB
		      "and %B0,%3"  CR_TAB
		      "eor %A0,%B0");
	    }
	  break;  /* optimize_size ? 6 : 8 */

	case 5:
	  if (optimize_size)
	    break;  /* scratch ? 5 : 6 */
	  if (ldi_ok)
	    {
	      *len = 8;
	      return ("lsr %B0"       CR_TAB
		      "ror %A0"       CR_TAB
		      "swap %B0"      CR_TAB
		      "swap %A0"      CR_TAB
		      "andi %A0,0x0f" CR_TAB
		      "eor %A0,%B0"   CR_TAB
		      "andi %B0,0x0f" CR_TAB
		      "eor %A0,%B0");
	    }
	  if (scratch)
	    {
	      *len = 9;
	      return ("lsr %B0"     CR_TAB
		      "ror %A0"     CR_TAB
		      "swap %B0"    CR_TAB
		      "swap %A0"    CR_TAB
		      "ldi %3,0x0f" CR_TAB
		      "and %A0,%3"  CR_TAB
		      "eor %A0,%B0" CR_TAB
		      "and %B0,%3"  CR_TAB
		      "eor %A0,%B0");
	    }
	  break;  /* 10 */

	case 6:
	  if (optimize_size)
	    break;  /* scratch ? 5 : 6 */
	  *len = 9;
	  return ("clr __tmp_reg__" CR_TAB
		  "lsl %A0"         CR_TAB
		  "rol %B0"         CR_TAB
		  "rol __tmp_reg__" CR_TAB
		  "lsl %A0"         CR_TAB
		  "rol %B0"         CR_TAB
		  "rol __tmp_reg__" CR_TAB
		  "mov %A0,%B0"     CR_TAB
		  "mov %B0,__tmp_reg__");

	case 7:
	  *len = 5;
	  return ("lsl %A0"     CR_TAB
		  "mov %A0,%B0" CR_TAB
		  "rol %A0"     CR_TAB
		  "sbc %B0,%B0" CR_TAB
		  "neg %B0");

	case 8:
	  return *len = 2, ("mov %A0,%B1" CR_TAB
			    "clr %B0");

	case 9:
	  *len = 3;
	  return ("mov %A0,%B0" CR_TAB
		  "clr %B0"     CR_TAB
		  "lsr %A0");

	case 10:
	  *len = 4;
	  return ("mov %A0,%B0" CR_TAB
		  "clr %B0"     CR_TAB
		  "lsr %A0"     CR_TAB
		  "lsr %A0");

	case 11:
	  *len = 5;
	  return ("mov %A0,%B0" CR_TAB
		  "clr %B0"     CR_TAB
		  "lsr %A0"     CR_TAB
		  "lsr %A0"     CR_TAB
		  "lsr %A0");

	case 12:
	  if (ldi_ok)
	    {
	      *len = 4;
	      return ("mov %A0,%B0" CR_TAB
		      "clr %B0"     CR_TAB
		      "swap %A0"    CR_TAB
		      "andi %A0,0x0f");
	    }
	  if (scratch)
	    {
	      *len = 5;
	      return ("mov %A0,%B0" CR_TAB
		      "clr %B0"     CR_TAB
		      "swap %A0"    CR_TAB
		      "ldi %3,0x0f" CR_TAB
		      "and %A0,%3");
	    }
	  *len = 6;
	  return ("mov %A0,%B0" CR_TAB
		  "clr %B0"     CR_TAB
		  "lsr %A0"     CR_TAB
		  "lsr %A0"     CR_TAB
		  "lsr %A0"     CR_TAB
		  "lsr %A0");

	case 13:
	  if (ldi_ok)
	    {
	      *len = 5;
	      return ("mov %A0,%B0" CR_TAB
		      "clr %B0"     CR_TAB
		      "swap %A0"    CR_TAB
		      "lsr %A0"     CR_TAB
		      "andi %A0,0x07");
	    }
	  if (AVR_HAVE_MUL && scratch)
	    {
	      *len = 5;
	      return ("ldi %3,0x08" CR_TAB
		      "mul %B0,%3"  CR_TAB
		      "mov %A0,r1"  CR_TAB
		      "clr %B0"     CR_TAB
		      "clr __zero_reg__");
	    }
	  if (optimize_size && scratch)
	    break;  /* 5 */
	  if (scratch)
	    {
	      *len = 6;
	      return ("mov %A0,%B0" CR_TAB
		      "clr %B0"     CR_TAB
		      "swap %A0"    CR_TAB
		      "lsr %A0"     CR_TAB
		      "ldi %3,0x07" CR_TAB
		      "and %A0,%3");
	    }
	  if (AVR_HAVE_MUL)
	    {
	      *len = 6;
	      return ("set"        CR_TAB
		      "bld r1,3"   CR_TAB
		      "mul %B0,r1" CR_TAB
		      "mov %A0,r1" CR_TAB
		      "clr %B0"    CR_TAB
		      "clr __zero_reg__");
	    }
	  *len = 7;
	  return ("mov %A0,%B0" CR_TAB
		  "clr %B0"     CR_TAB
		  "lsr %A0"     CR_TAB
		  "lsr %A0"     CR_TAB
		  "lsr %A0"     CR_TAB
		  "lsr %A0"     CR_TAB
		  "lsr %A0");

	case 14:
	  if (AVR_HAVE_MUL && ldi_ok)
	    {
	      *len = 5;
	      return ("ldi %A0,0x04" CR_TAB
		      "mul %B0,%A0"  CR_TAB
		      "mov %A0,r1"   CR_TAB
		      "clr %B0"      CR_TAB
		      "clr __zero_reg__");
	    }
	  if (AVR_HAVE_MUL && scratch)
	    {
	      *len = 5;
	      return ("ldi %3,0x04" CR_TAB
		      "mul %B0,%3"  CR_TAB
		      "mov %A0,r1"  CR_TAB
		      "clr %B0"     CR_TAB
		      "clr __zero_reg__");
	    }
	  if (optimize_size && ldi_ok)
	    {
	      *len = 5;
	      return ("mov %A0,%B0" CR_TAB
		      "ldi %B0,6" "\n1:\t"
		      "lsr %A0"     CR_TAB
		      "dec %B0"     CR_TAB
		      "brne 1b");
	    }
	  if (optimize_size && scratch)
	    break;  /* 5 */
	  *len = 6;
	  return ("clr %A0" CR_TAB
		  "lsl %B0" CR_TAB
		  "rol %A0" CR_TAB
		  "lsl %B0" CR_TAB
		  "rol %A0" CR_TAB
		  "clr %B0");

	case 15:
	  *len = 4;
	  return ("clr %A0" CR_TAB
		  "lsl %B0" CR_TAB
		  "rol %A0" CR_TAB
		  "clr %B0");
	}
      len = t;
    }
  out_shift_with_cnt ("lsr %B0" CR_TAB
                      "ror %A0", insn, operands, len, 2);
  return "";
}


/* 24-bit logic shift right */

const char*
avr_out_lshrpsi3 (rtx_insn *insn, rtx *op, int *plen)
{
  int dest = REGNO (op[0]);
  int src = REGNO (op[1]);

  if (CONST_INT_P (op[2]))
    {
      if (plen)
        *plen = 0;

      switch (INTVAL (op[2]))
        {
        case 8:
          if (dest <= src)
            return avr_asm_len ("mov %A0,%B1" CR_TAB
                                "mov %B0,%C1" CR_TAB
                                "clr %C0", op, plen, 3);
          else
            return avr_asm_len ("clr %C0"     CR_TAB
                                "mov %B0,%C1" CR_TAB
                                "mov %A0,%B1", op, plen, 3);

        case 16:
          if (dest != src + 2)
            avr_asm_len ("mov %A0,%C1", op, plen, 1);

          return avr_asm_len ("clr %B0"  CR_TAB
                              "clr %C0", op, plen, 2);

        default:
          if (INTVAL (op[2]) < 24)
            break;

          /* fall through */

        case 23:
          return avr_asm_len ("clr %A0"    CR_TAB
                              "sbrc %C0,7" CR_TAB
                              "inc %A0"    CR_TAB
                              "clr %B0"    CR_TAB
                              "clr %C0", op, plen, 5);
        } /* switch */
    }

  out_shift_with_cnt ("lsr %C0" CR_TAB
                      "ror %B0" CR_TAB
                      "ror %A0", insn, op, plen, 3);
  return "";
}


/* 32-bit logic shift right ((unsigned int)x >> i) */

const char *
lshrsi3_out (rtx_insn *insn, rtx operands[], int *len)
{
  if (CONST_INT_P (operands[2]))
    {
      int k;
      int *t = len;

      if (!len)
	len = &k;

      switch (INTVAL (operands[2]))
	{
	default:
	  if (INTVAL (operands[2]) < 32)
	    break;

	  if (AVR_HAVE_MOVW)
	    return *len = 3, ("clr %D0" CR_TAB
			      "clr %C0" CR_TAB
			      "movw %A0,%C0");
	  *len = 4;
	  return ("clr %D0" CR_TAB
		  "clr %C0" CR_TAB
		  "clr %B0" CR_TAB
		  "clr %A0");

	case 8:
	  {
	    int reg0 = true_regnum (operands[0]);
	    int reg1 = true_regnum (operands[1]);
	    *len = 4;
	    if (reg0 <= reg1)
	      return ("mov %A0,%B1" CR_TAB
		      "mov %B0,%C1" CR_TAB
		      "mov %C0,%D1" CR_TAB
		      "clr %D0");
	    else
	      return ("clr %D0"     CR_TAB
		      "mov %C0,%D1" CR_TAB
		      "mov %B0,%C1" CR_TAB
		      "mov %A0,%B1");
	  }

	case 16:
	  {
	    int reg0 = true_regnum (operands[0]);
	    int reg1 = true_regnum (operands[1]);

	    if (reg0 == reg1 + 2)
	      return *len = 2, ("clr %C0"     CR_TAB
				"clr %D0");
	    if (AVR_HAVE_MOVW)
	      return *len = 3, ("movw %A0,%C1" CR_TAB
				"clr %C0"      CR_TAB
				"clr %D0");
	    else
	      return *len = 4, ("mov %B0,%D1" CR_TAB
				"mov %A0,%C1" CR_TAB
				"clr %C0"     CR_TAB
				"clr %D0");
	  }

	case 24:
	  return *len = 4, ("mov %A0,%D1" CR_TAB
			    "clr %B0"     CR_TAB
			    "clr %C0"     CR_TAB
			    "clr %D0");

	case 31:
	  *len = 6;
	  return ("clr %A0"    CR_TAB
		  "sbrc %D0,7" CR_TAB
		  "inc %A0"    CR_TAB
		  "clr %B0"    CR_TAB
		  "clr %C0"    CR_TAB
		  "clr %D0");
	}
      len = t;
    }
  out_shift_with_cnt ("lsr %D0" CR_TAB
                      "ror %C0" CR_TAB
                      "ror %B0" CR_TAB
                      "ror %A0", insn, operands, len, 4);
  return "";
}


/* Output addition of register XOP[0] and compile time constant XOP[2].
   CODE == PLUS:  perform addition by using ADD instructions or
   CODE == MINUS: perform addition by using SUB instructions:

      XOP[0] = XOP[0] + XOP[2]

   Or perform addition/subtraction with register XOP[2] depending on CODE:

      XOP[0] = XOP[0] +/- XOP[2]

   If PLEN == NULL, print assembler instructions to perform the operation;
   otherwise, set *PLEN to the length of the instruction sequence (in words)
   printed with PLEN == NULL.  XOP[3] is an 8-bit scratch register or NULL_RTX.
   Set *PCC to effect on cc0 according to respective CC_* insn attribute.

   CODE_SAT == UNKNOWN: Perform ordinary, non-saturating operation.
   CODE_SAT != UNKNOWN: Perform operation and saturate according to CODE_SAT.
   If  CODE_SAT != UNKNOWN  then SIGN contains the sign of the summand resp.
   the subtrahend in the original insn, provided it is a compile time constant.
   In all other cases, SIGN is 0.

   If OUT_LABEL is true, print the final 0: label which is needed for
   saturated addition / subtraction.  The only case where OUT_LABEL = false
   is useful is for saturated addition / subtraction performed during
   fixed-point rounding, cf. `avr_out_round'.  */

static void
avr_out_plus_1 (rtx *xop, int *plen, enum rtx_code code, int *pcc,
                enum rtx_code code_sat, int sign, bool out_label)
{
  /* MODE of the operation.  */
  machine_mode mode = GET_MODE (xop[0]);

  /* INT_MODE of the same size.  */
  scalar_int_mode imode = int_mode_for_mode (mode).require ();

  /* Number of bytes to operate on.  */
  int n_bytes = GET_MODE_SIZE (mode);

  /* Value (0..0xff) held in clobber register op[3] or -1 if unknown.  */
  int clobber_val = -1;

  /* op[0]: 8-bit destination register
     op[1]: 8-bit const int
     op[2]: 8-bit scratch register */
  rtx op[3];

  /* Started the operation?  Before starting the operation we may skip
     adding 0.  This is no more true after the operation started because
     carry must be taken into account.  */
  bool started = false;

  /* Value to add.  There are two ways to add VAL: R += VAL and R -= -VAL.  */
  rtx xval = xop[2];

  /* Output a BRVC instruction.  Only needed with saturation.  */
  bool out_brvc = true;

  if (plen)
    *plen = 0;

  if (REG_P (xop[2]))
    {
      *pcc = MINUS == code ? (int) CC_SET_CZN : (int) CC_CLOBBER;

      for (int i = 0; i < n_bytes; i++)
        {
          /* We operate byte-wise on the destination.  */
          op[0] = simplify_gen_subreg (QImode, xop[0], mode, i);
          op[1] = simplify_gen_subreg (QImode, xop[2], mode, i);

          if (i == 0)
            avr_asm_len (code == PLUS ? "add %0,%1" : "sub %0,%1",
                         op, plen, 1);
          else
            avr_asm_len (code == PLUS ? "adc %0,%1" : "sbc %0,%1",
                         op, plen, 1);
        }

      if (reg_overlap_mentioned_p (xop[0], xop[2]))
        {
          gcc_assert (REGNO (xop[0]) == REGNO (xop[2]));

          if (MINUS == code)
            return;
        }

      goto saturate;
    }

  /* Except in the case of ADIW with 16-bit register (see below)
     addition does not set cc0 in a usable way.  */

  *pcc = (MINUS == code) ? CC_SET_CZN : CC_CLOBBER;

  if (CONST_FIXED_P (xval))
    xval = avr_to_int_mode (xval);

  /* Adding/Subtracting zero is a no-op.  */

  if (xval == const0_rtx)
    {
      *pcc = CC_NONE;
      return;
    }

  if (MINUS == code)
    xval = simplify_unary_operation (NEG, imode, xval, imode);

  op[2] = xop[3];

  if (SS_PLUS == code_sat && MINUS == code
      && sign < 0
      && 0x80 == (INTVAL (simplify_gen_subreg (QImode, xval, imode, n_bytes-1))
                  & GET_MODE_MASK (QImode)))
    {
      /* We compute x + 0x80 by means of SUB instructions.  We negated the
         constant subtrahend above and are left with  x - (-128)  so that we
         need something like SUBI r,128 which does not exist because SUBI sets
         V according to the sign of the subtrahend.  Notice the only case
         where this must be done is when NEG overflowed in case [2s] because
         the V computation needs the right sign of the subtrahend.  */

      rtx msb = simplify_gen_subreg (QImode, xop[0], mode, n_bytes - 1);

      avr_asm_len ("subi %0,128" CR_TAB
                   "brmi 0f", &msb, plen, 2);
      out_brvc = false;

      goto saturate;
    }

  for (int i = 0; i < n_bytes; i++)
    {
      /* We operate byte-wise on the destination.  */
      rtx reg8 = simplify_gen_subreg (QImode, xop[0], mode, i);
      rtx xval8 = simplify_gen_subreg (QImode, xval, imode, i);

      /* 8-bit value to operate with this byte. */
      unsigned int val8 = UINTVAL (xval8) & GET_MODE_MASK (QImode);

      /* Registers R16..R31 can operate with immediate.  */
      bool ld_reg_p = test_hard_reg_class (LD_REGS, reg8);

      op[0] = reg8;
      op[1] = gen_int_mode (val8, QImode);

      /* To get usable cc0 no low-bytes must have been skipped.  */

      if (i && !started)
        *pcc = CC_CLOBBER;

      if (!started
          && i % 2 == 0
          && i + 2 <= n_bytes
          && test_hard_reg_class (ADDW_REGS, reg8))
        {
          rtx xval16 = simplify_gen_subreg (HImode, xval, imode, i);
          unsigned int val16 = UINTVAL (xval16) & GET_MODE_MASK (HImode);

          /* Registers R24, X, Y, Z can use ADIW/SBIW with constants < 64
             i.e. operate word-wise.  */

          if (val16 < 64)
            {
              if (val16 != 0)
                {
                  started = true;
                  avr_asm_len (code == PLUS ? "adiw %0,%1" : "sbiw %0,%1",
                               op, plen, 1);

                  if (n_bytes == 2 && PLUS == code)
                    *pcc = CC_SET_CZN;
                }

              i++;
              continue;
            }
        }

      if (val8 == 0)
        {
          if (started)
            avr_asm_len (code == PLUS
                         ? "adc %0,__zero_reg__" : "sbc %0,__zero_reg__",
                         op, plen, 1);
          continue;
        }
      else if ((val8 == 1 || val8 == 0xff)
               && UNKNOWN == code_sat
               && !started
               && i == n_bytes - 1)
        {
          avr_asm_len ((code == PLUS) ^ (val8 == 1) ? "dec %0" : "inc %0",
                       op, plen, 1);
          *pcc = CC_CLOBBER;
          break;
        }

      switch (code)
        {
        case PLUS:

          gcc_assert (plen != NULL || (op[2] && REG_P (op[2])));

          if (plen != NULL && UNKNOWN != code_sat)
            {
              /* This belongs to the x + 0x80 corner case.  The code with
                 ADD instruction is not smaller, thus make this case
                 expensive so that the caller won't pick it.  */

              *plen += 10;
              break;
            }

          if (clobber_val != (int) val8)
            avr_asm_len ("ldi %2,%1", op, plen, 1);
          clobber_val = (int) val8;

          avr_asm_len (started ? "adc %0,%2" : "add %0,%2", op, plen, 1);

          break; /* PLUS */

        case MINUS:

          if (ld_reg_p)
            avr_asm_len (started ? "sbci %0,%1" : "subi %0,%1", op, plen, 1);
          else
            {
              gcc_assert (plen != NULL || REG_P (op[2]));

              if (clobber_val != (int) val8)
                avr_asm_len ("ldi %2,%1", op, plen, 1);
              clobber_val = (int) val8;

              avr_asm_len (started ? "sbc %0,%2" : "sub %0,%2", op, plen, 1);
            }

          break; /* MINUS */

        default:
          /* Unknown code */
          gcc_unreachable();
        }

      started = true;

    } /* for all sub-bytes */

 saturate:

  if (UNKNOWN == code_sat)
    return;

  *pcc = (int) CC_CLOBBER;

  /* Vanilla addition/subtraction is done.  We are left with saturation.

     We have to compute  A = A <op> B  where  A  is a register and
     B is a register or a non-zero compile time constant CONST.
     A is register class "r" if unsigned && B is REG.  Otherwise, A is in "d".
     B stands for the original operand $2 in INSN.  In the case of B = CONST,
     SIGN in { -1, 1 } is the sign of B.  Otherwise, SIGN is 0.

     CODE is the instruction flavor we use in the asm sequence to perform <op>.


     unsigned
     operation        |  code |  sat if  |    b is      | sat value |  case
     -----------------+-------+----------+--------------+-----------+-------
     +  as  a + b     |  add  |  C == 1  |  const, reg  | u+ = 0xff |  [1u]
     +  as  a - (-b)  |  sub  |  C == 0  |  const       | u+ = 0xff |  [2u]
     -  as  a - b     |  sub  |  C == 1  |  const, reg  | u- = 0    |  [3u]
     -  as  a + (-b)  |  add  |  C == 0  |  const       | u- = 0    |  [4u]


     signed
     operation        |  code |  sat if  |    b is      | sat value |  case
     -----------------+-------+----------+--------------+-----------+-------
     +  as  a + b     |  add  |  V == 1  |  const, reg  | s+        |  [1s]
     +  as  a - (-b)  |  sub  |  V == 1  |  const       | s+        |  [2s]
     -  as  a - b     |  sub  |  V == 1  |  const, reg  | s-        |  [3s]
     -  as  a + (-b)  |  add  |  V == 1  |  const       | s-        |  [4s]

     s+  =  b < 0  ?  -0x80 :  0x7f
     s-  =  b < 0  ?   0x7f : -0x80

     The cases a - b actually perform  a - (-(-b))  if B is CONST.
  */

  op[0] = simplify_gen_subreg (QImode, xop[0], mode, n_bytes-1);
  op[1] = n_bytes > 1
    ? simplify_gen_subreg (QImode, xop[0], mode, n_bytes-2)
    : NULL_RTX;

  bool need_copy = true;
  int len_call = 1 + AVR_HAVE_JMP_CALL;

  switch (code_sat)
    {
    default:
      gcc_unreachable();

    case SS_PLUS:
    case SS_MINUS:

      if (out_brvc)
        avr_asm_len ("brvc 0f", op, plen, 1);

      if (reg_overlap_mentioned_p (xop[0], xop[2]))
        {
          /* [1s,reg] */

          if (n_bytes == 1)
            avr_asm_len ("ldi %0,0x7f" CR_TAB
                         "adc %0,__zero_reg__", op, plen, 2);
          else
            avr_asm_len ("ldi %0,0x7f" CR_TAB
                         "ldi %1,0xff" CR_TAB
                         "adc %1,__zero_reg__" CR_TAB
                         "adc %0,__zero_reg__", op, plen, 4);
        }
      else if (sign == 0 && PLUS == code)
        {
          /* [1s,reg] */

          op[2] = simplify_gen_subreg (QImode, xop[2], mode, n_bytes-1);

          if (n_bytes == 1)
            avr_asm_len ("ldi %0,0x80" CR_TAB
                         "sbrs %2,7"   CR_TAB
                         "dec %0", op, plen, 3);
          else
            avr_asm_len ("ldi %0,0x80" CR_TAB
                         "cp %2,%0"    CR_TAB
                         "sbc %1,%1"   CR_TAB
                         "sbci %0,0", op, plen, 4);
        }
      else if (sign == 0 && MINUS == code)
        {
          /* [3s,reg] */

          op[2] = simplify_gen_subreg (QImode, xop[2], mode, n_bytes-1);

          if (n_bytes == 1)
            avr_asm_len ("ldi %0,0x7f" CR_TAB
                         "sbrs %2,7"   CR_TAB
                         "inc %0", op, plen, 3);
          else
            avr_asm_len ("ldi %0,0x7f" CR_TAB
                         "cp %0,%2"    CR_TAB
                         "sbc %1,%1"   CR_TAB
                         "sbci %0,-1", op, plen, 4);
        }
      else if ((sign < 0) ^ (SS_MINUS == code_sat))
        {
          /* [1s,const,B < 0] [2s,B < 0] */
          /* [3s,const,B > 0] [4s,B > 0] */

          if (n_bytes == 8)
            {
              avr_asm_len ("%~call __clr_8", op, plen, len_call);
              need_copy = false;
            }

          avr_asm_len ("ldi %0,0x80", op, plen, 1);
          if (n_bytes > 1 && need_copy)
            avr_asm_len ("clr %1", op, plen, 1);
        }
      else if ((sign > 0) ^ (SS_MINUS == code_sat))
        {
          /* [1s,const,B > 0] [2s,B > 0] */
          /* [3s,const,B < 0] [4s,B < 0] */

          if (n_bytes == 8)
            {
              avr_asm_len ("sec" CR_TAB
                           "%~call __sbc_8", op, plen, 1 + len_call);
              need_copy = false;
            }

          avr_asm_len ("ldi %0,0x7f", op, plen, 1);
          if (n_bytes > 1 && need_copy)
            avr_asm_len ("ldi %1,0xff", op, plen, 1);
        }
      else
        gcc_unreachable();

      break;

    case US_PLUS:
      /* [1u] : [2u] */

      avr_asm_len (PLUS == code ? "brcc 0f" : "brcs 0f", op, plen, 1);

      if (n_bytes == 8)
        {
          if (MINUS == code)
            avr_asm_len ("sec", op, plen, 1);
          avr_asm_len ("%~call __sbc_8", op, plen, len_call);

          need_copy = false;
        }
      else
        {
          if (MINUS == code && !test_hard_reg_class (LD_REGS, op[0]))
            avr_asm_len ("sec" CR_TAB
                         "sbc %0,%0", op, plen, 2);
          else
            avr_asm_len (PLUS == code ? "sbc %0,%0" : "ldi %0,0xff",
                         op, plen, 1);
        }
      break; /* US_PLUS */

    case US_MINUS:
      /* [4u] : [3u] */

      avr_asm_len (PLUS == code ? "brcs 0f" : "brcc 0f", op, plen, 1);

      if (n_bytes == 8)
        {
          avr_asm_len ("%~call __clr_8", op, plen, len_call);
          need_copy = false;
        }
      else
        avr_asm_len ("clr %0", op, plen, 1);

      break;
    }

  /* We set the MSB in the unsigned case and the 2 MSBs in the signed case.
     Now copy the right value to the LSBs.  */

  if (need_copy && n_bytes > 1)
    {
      if (US_MINUS == code_sat || US_PLUS == code_sat)
        {
          avr_asm_len ("mov %1,%0", op, plen, 1);

          if (n_bytes > 2)
            {
              op[0] = xop[0];
              if (AVR_HAVE_MOVW)
                avr_asm_len ("movw %0,%1", op, plen, 1);
              else
                avr_asm_len ("mov %A0,%1" CR_TAB
                             "mov %B0,%1", op, plen, 2);
            }
        }
      else if (n_bytes > 2)
        {
          op[0] = xop[0];
          avr_asm_len ("mov %A0,%1" CR_TAB
                       "mov %B0,%1", op, plen, 2);
        }
    }

  if (need_copy && n_bytes == 8)
    {
      if (AVR_HAVE_MOVW)
        avr_asm_len ("movw %r0+2,%0" CR_TAB
                     "movw %r0+4,%0", xop, plen, 2);
      else
        avr_asm_len ("mov %r0+2,%0" CR_TAB
                     "mov %r0+3,%0" CR_TAB
                     "mov %r0+4,%0" CR_TAB
                     "mov %r0+5,%0", xop, plen, 4);
    }

  if (out_label)
    avr_asm_len ("0:", op, plen, 0);
}


/* Output addition/subtraction of register XOP[0] and a constant XOP[2] that
   is ont a compile-time constant:

      XOP[0] = XOP[0] +/- XOP[2]

   This is a helper for the function below.  The only insns that need this
   are additions/subtraction for pointer modes, i.e. HImode and PSImode.  */

static const char*
avr_out_plus_symbol (rtx *xop, enum rtx_code code, int *plen, int *pcc)
{
  machine_mode mode = GET_MODE (xop[0]);

  /* Only pointer modes want to add symbols.  */

  gcc_assert (mode == HImode || mode == PSImode);

  *pcc = MINUS == code ? (int) CC_SET_CZN : (int) CC_SET_N;

  avr_asm_len (PLUS == code
               ? "subi %A0,lo8(-(%2))" CR_TAB "sbci %B0,hi8(-(%2))"
               : "subi %A0,lo8(%2)"    CR_TAB "sbci %B0,hi8(%2)",
               xop, plen, -2);

  if (PSImode == mode)
    avr_asm_len (PLUS == code
                 ? "sbci %C0,hlo8(-(%2))"
                 : "sbci %C0,hlo8(%2)", xop, plen, 1);
  return "";
}


/* Prepare operands of addition/subtraction to be used with avr_out_plus_1.

   INSN is a single_set insn or an insn pattern with a binary operation as
   SET_SRC that is one of: PLUS, SS_PLUS, US_PLUS, MINUS, SS_MINUS, US_MINUS.

   XOP are the operands of INSN.  In the case of 64-bit operations with
   constant XOP[] has just one element:  The summand/subtrahend in XOP[0].
   The non-saturating insns up to 32 bits may or may not supply a "d" class
   scratch as XOP[3].

   If PLEN == NULL output the instructions.
   If PLEN != NULL set *PLEN to the length of the sequence in words.

   PCC is a pointer to store the instructions' effect on cc0.
   PCC may be NULL.

   PLEN and PCC default to NULL.

   OUT_LABEL defaults to TRUE.  For a description, see AVR_OUT_PLUS_1.

   Return ""  */

const char*
avr_out_plus (rtx insn, rtx *xop, int *plen, int *pcc, bool out_label)
{
  int cc_plus, cc_minus, cc_dummy;
  int len_plus, len_minus;
  rtx op[4];
  rtx xpattern = INSN_P (insn) ? single_set (as_a <rtx_insn *> (insn)) : insn;
  rtx xdest = SET_DEST (xpattern);
  machine_mode mode = GET_MODE (xdest);
  scalar_int_mode imode = int_mode_for_mode (mode).require ();
  int n_bytes = GET_MODE_SIZE (mode);
  enum rtx_code code_sat = GET_CODE (SET_SRC (xpattern));
  enum rtx_code code
    = (PLUS == code_sat || SS_PLUS == code_sat || US_PLUS == code_sat
       ? PLUS : MINUS);

  if (!pcc)
    pcc = &cc_dummy;

  /* PLUS and MINUS don't saturate:  Use modular wrap-around.  */

  if (PLUS == code_sat || MINUS == code_sat)
    code_sat = UNKNOWN;

  if (n_bytes <= 4 && REG_P (xop[2]))
    {
      avr_out_plus_1 (xop, plen, code, pcc, code_sat, 0, out_label);
      return "";
    }

  if (n_bytes == 8)
    {
      op[0] = gen_rtx_REG (DImode, ACC_A);
      op[1] = gen_rtx_REG (DImode, ACC_A);
      op[2] = avr_to_int_mode (xop[0]);
    }
  else
    {
      if (!REG_P (xop[2])
          && !CONST_INT_P (xop[2])
          && !CONST_FIXED_P (xop[2]))
        {
          return avr_out_plus_symbol (xop, code, plen, pcc);
        }

      op[0] = avr_to_int_mode (xop[0]);
      op[1] = avr_to_int_mode (xop[1]);
      op[2] = avr_to_int_mode (xop[2]);
    }

  /* Saturations and 64-bit operations don't have a clobber operand.
     For the other cases, the caller will provide a proper XOP[3].  */

  xpattern = INSN_P (insn) ? PATTERN (insn) : insn;
  op[3] = PARALLEL == GET_CODE (xpattern) ? xop[3] : NULL_RTX;

  /* Saturation will need the sign of the original operand.  */

  rtx xmsb = simplify_gen_subreg (QImode, op[2], imode, n_bytes-1);
  int sign = INTVAL (xmsb) < 0 ? -1 : 1;

  /* If we subtract and the subtrahend is a constant, then negate it
     so that avr_out_plus_1 can be used.  */

  if (MINUS == code)
    op[2] = simplify_unary_operation (NEG, imode, op[2], imode);

  /* Work out the shortest sequence.  */

  avr_out_plus_1 (op, &len_minus, MINUS, &cc_minus, code_sat, sign, out_label);
  avr_out_plus_1 (op, &len_plus, PLUS, &cc_plus, code_sat, sign, out_label);

  if (plen)
    {
      *plen = (len_minus <= len_plus) ? len_minus : len_plus;
      *pcc  = (len_minus <= len_plus) ? cc_minus : cc_plus;
    }
  else if (len_minus <= len_plus)
    avr_out_plus_1 (op, NULL, MINUS, pcc, code_sat, sign, out_label);
  else
    avr_out_plus_1 (op, NULL, PLUS, pcc, code_sat, sign, out_label);

  return "";
}


/* Output bit operation (IOR, AND, XOR) with register XOP[0] and compile
   time constant XOP[2]:

      XOP[0] = XOP[0] <op> XOP[2]

   and return "".  If PLEN == NULL, print assembler instructions to perform the
   operation; otherwise, set *PLEN to the length of the instruction sequence
   (in words) printed with PLEN == NULL.  XOP[3] is either an 8-bit clobber
   register or SCRATCH if no clobber register is needed for the operation.
   INSN is an INSN_P or a pattern of an insn.  */

const char*
avr_out_bitop (rtx insn, rtx *xop, int *plen)
{
  /* CODE and MODE of the operation.  */
  rtx xpattern = INSN_P (insn) ? single_set (as_a <rtx_insn *> (insn)) : insn;
  enum rtx_code code = GET_CODE (SET_SRC (xpattern));
  machine_mode mode = GET_MODE (xop[0]);

  /* Number of bytes to operate on.  */
  int n_bytes = GET_MODE_SIZE (mode);

  /* Value of T-flag (0 or 1) or -1 if unknow.  */
  int set_t = -1;

  /* Value (0..0xff) held in clobber register op[3] or -1 if unknown.  */
  int clobber_val = -1;

  /* op[0]: 8-bit destination register
     op[1]: 8-bit const int
     op[2]: 8-bit clobber register, SCRATCH or NULL_RTX.
     op[3]: 8-bit register containing 0xff or NULL_RTX  */
  rtx op[4];

  op[2] = QImode == mode ? NULL_RTX : xop[3];
  op[3] = NULL_RTX;

  if (plen)
    *plen = 0;

  for (int i = 0; i < n_bytes; i++)
    {
      /* We operate byte-wise on the destination.  */
      rtx reg8 = simplify_gen_subreg (QImode, xop[0], mode, i);
      rtx xval8 = simplify_gen_subreg (QImode, xop[2], mode, i);

      /* 8-bit value to operate with this byte. */
      unsigned int val8 = UINTVAL (xval8) & GET_MODE_MASK (QImode);

      /* Number of bits set in the current byte of the constant.  */
      int pop8 = popcount_hwi (val8);

      /* Registers R16..R31 can operate with immediate.  */
      bool ld_reg_p = test_hard_reg_class (LD_REGS, reg8);

      op[0] = reg8;
      op[1] = GEN_INT (val8);

      switch (code)
        {
        case IOR:

	  if (pop8 == 0)
            continue;
          else if (ld_reg_p)
            avr_asm_len ("ori %0,%1", op, plen, 1);
	  else if (pop8 == 1)
            {
              if (set_t != 1)
                avr_asm_len ("set", op, plen, 1);
              set_t = 1;

              op[1] = GEN_INT (exact_log2 (val8));
              avr_asm_len ("bld %0,%1", op, plen, 1);
            }
	  else if (pop8 == 8)
            {
              if (op[3] != NULL_RTX)
                avr_asm_len ("mov %0,%3", op, plen, 1);
              else
                avr_asm_len ("clr %0" CR_TAB
                             "dec %0", op, plen, 2);

              op[3] = op[0];
            }
          else
            {
              if (clobber_val != (int) val8)
                avr_asm_len ("ldi %2,%1", op, plen, 1);
              clobber_val = (int) val8;

              avr_asm_len ("or %0,%2", op, plen, 1);
            }

          continue; /* IOR */

        case AND:

	  if (pop8 == 8)
            continue;
	  else if (pop8 == 0)
            avr_asm_len ("clr %0", op, plen, 1);
          else if (ld_reg_p)
            avr_asm_len ("andi %0,%1", op, plen, 1);
	  else if (pop8 == 7)
            {
              if (set_t != 0)
                avr_asm_len ("clt", op, plen, 1);
              set_t = 0;

              op[1] = GEN_INT (exact_log2 (GET_MODE_MASK (QImode) & ~val8));
              avr_asm_len ("bld %0,%1", op, plen, 1);
            }
          else
            {
              if (clobber_val != (int) val8)
                avr_asm_len ("ldi %2,%1", op, plen, 1);
              clobber_val = (int) val8;

              avr_asm_len ("and %0,%2", op, plen, 1);
            }

          continue; /* AND */

        case XOR:

	  if (pop8 == 0)
            continue;
	  else if (pop8 == 8)
            avr_asm_len ("com %0", op, plen, 1);
          else if (ld_reg_p && val8 == (1 << 7))
            avr_asm_len ("subi %0,%1", op, plen, 1);
          else
            {
              if (clobber_val != (int) val8)
                avr_asm_len ("ldi %2,%1", op, plen, 1);
              clobber_val = (int) val8;

              avr_asm_len ("eor %0,%2", op, plen, 1);
            }

          continue; /* XOR */

        default:
          /* Unknown rtx_code */
          gcc_unreachable();
        }
    } /* for all sub-bytes */

  return "";
}


/* Output sign extension from XOP[1] to XOP[0] and return "".
   If PLEN == NULL, print assembler instructions to perform the operation;
   otherwise, set *PLEN to the length of the instruction sequence (in words)
   as printed with PLEN == NULL.  */

const char*
avr_out_sign_extend (rtx_insn *insn, rtx *xop, int *plen)
{
  // Size in bytes of source resp. destination operand.
  unsigned n_src = GET_MODE_SIZE (GET_MODE (xop[1]));
  unsigned n_dest = GET_MODE_SIZE (GET_MODE (xop[0]));
  rtx r_msb = all_regs_rtx[REGNO (xop[1]) + n_src - 1];

  if (plen)
    *plen = 0;

  // Copy destination to source

  if (REGNO (xop[0]) != REGNO (xop[1]))
    {
      gcc_assert (n_src <= 2);

      if (n_src == 2)
        avr_asm_len (AVR_HAVE_MOVW
                     ? "movw %0,%1"
                     : "mov %B0,%B1", xop, plen, 1);
      if (n_src == 1 || !AVR_HAVE_MOVW)
        avr_asm_len ("mov %A0,%A1", xop, plen, 1);
    }

  // Set Carry to the sign bit MSB.7...

  if (REGNO (xop[0]) == REGNO (xop[1])
      || !reg_unused_after (insn, r_msb))
    {
      avr_asm_len ("mov __tmp_reg__,%0", &r_msb, plen, 1);
      r_msb = tmp_reg_rtx;
    }

  avr_asm_len ("lsl %0", &r_msb, plen, 1);

  // ...and propagate it to all the new sign bits

  for (unsigned n = n_src; n < n_dest; n++)
    avr_asm_len ("sbc %0,%0", &all_regs_rtx[REGNO (xop[0]) + n], plen, 1);

  return "";
}


/* PLEN == NULL: Output code to add CONST_INT OP[0] to SP.
   PLEN != NULL: Set *PLEN to the length of that sequence.
   Return "".  */

const char*
avr_out_addto_sp (rtx *op, int *plen)
{
  int pc_len = AVR_2_BYTE_PC ? 2 : 3;
  int addend = INTVAL (op[0]);

  if (plen)
    *plen = 0;

  if (addend < 0)
    {
      if (flag_verbose_asm || flag_print_asm_name)
        avr_asm_len (ASM_COMMENT_START "SP -= %n0", op, plen, 0);

      while (addend <= -pc_len)
        {
          addend += pc_len;
          avr_asm_len ("rcall .", op, plen, 1);
        }

      while (addend++ < 0)
        avr_asm_len ("push __tmp_reg__", op, plen, 1);
    }
  else if (addend > 0)
    {
      if (flag_verbose_asm || flag_print_asm_name)
        avr_asm_len (ASM_COMMENT_START "SP += %0", op, plen, 0);

      while (addend-- > 0)
        avr_asm_len ("pop __tmp_reg__", op, plen, 1);
    }

  return "";
}


/* Output instructions to insert an inverted bit into OPERANDS[0]:
   $0.$1 = ~$2.$3      if XBITNO = NULL
   $0.$1 = ~$2.XBITNO  if XBITNO != NULL.
   If PLEN = NULL then output the respective instruction sequence which
   is a combination of BST / BLD and some instruction(s) to invert the bit.
   If PLEN != NULL then store the length of the sequence (in words) in *PLEN.
   Return "".  */

const char*
avr_out_insert_notbit (rtx_insn *insn, rtx operands[], rtx xbitno, int *plen)
{
  rtx op[4] = { operands[0], operands[1], operands[2],
                xbitno == NULL_RTX ? operands [3] : xbitno };

  if (INTVAL (op[1]) == 7
      && test_hard_reg_class (LD_REGS, op[0]))
    {
      /* If the inserted bit number is 7 and we have a d-reg, then invert
         the bit after the insertion by means of SUBI *,0x80.  */

      if (INTVAL (op[3]) == 7
          && REGNO (op[0]) == REGNO (op[2]))
        {
          avr_asm_len ("subi %0,0x80", op, plen, -1);
        }
      else
        {
          avr_asm_len ("bst %2,%3" CR_TAB
                       "bld %0,%1" CR_TAB
                       "subi %0,0x80", op, plen, -3);
        }
    }
  else if (test_hard_reg_class (LD_REGS, op[0])
           && (INTVAL (op[1]) != INTVAL (op[3])
               || !reg_overlap_mentioned_p (op[0], op[2])))
    {
      /* If the destination bit is in a d-reg we can jump depending
         on the source bit and use ANDI / ORI.  This just applies if we
         have not an early-clobber situation with the bit.  */

      avr_asm_len ("andi %0,~(1<<%1)" CR_TAB
                   "sbrs %2,%3"       CR_TAB
                   "ori %0,1<<%1", op, plen, -3);
    }
  else
    {
      /* Otherwise, invert the bit by means of COM before we store it with
         BST and then undo the COM if needed.  */

      avr_asm_len ("com %2" CR_TAB
                   "bst %2,%3", op, plen, -2);

      if (!reg_unused_after (insn, op[2])
          // A simple 'reg_unused_after' is not enough because that function
          // assumes that the destination register is overwritten completely
          // and hence is in order for our purpose.  This is not the case
          // with BLD which just changes one bit of the destination.
          || reg_overlap_mentioned_p (op[0], op[2]))
        {
          /* Undo the COM from above.  */
          avr_asm_len ("com %2", op, plen, 1);
        }

      avr_asm_len ("bld %0,%1", op, plen, 1);
    }

  return "";
}


/* Outputs instructions needed for fixed point type conversion.
   This includes converting between any fixed point type, as well
   as converting to any integer type.  Conversion between integer
   types is not supported.

   Converting signed fractional types requires a bit shift if converting
   to or from any unsigned fractional type because the decimal place is
   shifted by 1 bit.  When the destination is a signed fractional, the sign
   is stored in either the carry or T bit.  */

const char*
avr_out_fract (rtx_insn *insn, rtx operands[], bool intsigned, int *plen)
{
  rtx xop[6];
  RTX_CODE shift = UNKNOWN;
  bool sign_in_carry = false;
  bool msb_in_carry = false;
  bool lsb_in_tmp_reg = false;
  bool lsb_in_carry = false;
  bool frac_rounded = false;
  const char *code_ashift = "lsl %0";


#define MAY_CLOBBER(RR)                                                 \
  /* Shorthand used below.  */                                          \
  ((sign_bytes                                                          \
    && IN_RANGE (RR, dest.regno_msb - sign_bytes + 1, dest.regno_msb))  \
   || (offset && IN_RANGE (RR, dest.regno, dest.regno_msb))		\
   || (reg_unused_after (insn, all_regs_rtx[RR])                        \
       && !IN_RANGE (RR, dest.regno, dest.regno_msb)))

  struct
  {
    /* bytes       : Length of operand in bytes.
       ibyte       : Length of integral part in bytes.
       fbyte, fbit : Length of fractional part in bytes, bits.  */

    bool sbit;
    unsigned fbit, bytes, ibyte, fbyte;
    unsigned regno, regno_msb;
  } dest, src, *val[2] = { &dest, &src };

  if (plen)
    *plen = 0;

  /* Step 0:  Determine information on source and destination operand we
     ======   will need in the remainder.  */

  for (size_t i = 0; i < ARRAY_SIZE (val); i++)
    {
      machine_mode mode;

      xop[i] = operands[i];

      mode = GET_MODE (xop[i]);

      val[i]->bytes = GET_MODE_SIZE (mode);
      val[i]->regno = REGNO (xop[i]);
      val[i]->regno_msb = REGNO (xop[i]) + val[i]->bytes - 1;

      if (SCALAR_INT_MODE_P (mode))
        {
          val[i]->sbit = intsigned;
          val[i]->fbit = 0;
        }
      else if (ALL_SCALAR_FIXED_POINT_MODE_P (mode))
        {
          val[i]->sbit = SIGNED_SCALAR_FIXED_POINT_MODE_P (mode);
          val[i]->fbit = GET_MODE_FBIT (mode);
        }
      else
        fatal_insn ("unsupported fixed-point conversion", insn);

      val[i]->fbyte = (1 + val[i]->fbit) / BITS_PER_UNIT;
      val[i]->ibyte = val[i]->bytes - val[i]->fbyte;
    }

  // Byte offset of the decimal point taking into account different place
  // of the decimal point in input and output and different register numbers
  // of input and output.
  int offset = dest.regno - src.regno + dest.fbyte - src.fbyte;

  // Number of destination bytes that will come from sign / zero extension.
  int sign_bytes = (dest.ibyte - src.ibyte) * (dest.ibyte > src.ibyte);

  // Number of bytes at the low end to be filled with zeros.
  int zero_bytes = (dest.fbyte - src.fbyte) * (dest.fbyte > src.fbyte);

  // Do we have a 16-Bit register that is cleared?
  rtx clrw = NULL_RTX;

  bool sign_extend = src.sbit && sign_bytes;

  if (dest.fbit % 8 == 0 && src.fbit % 8 == 7)
    shift = ASHIFT;
  else if (dest.fbit % 8 == 7 && src.fbit % 8 == 0)
    shift = ASHIFTRT;
  else if (dest.fbit % 8 == src.fbit % 8)
    shift = UNKNOWN;
  else
    gcc_unreachable();

  /* If we need to round the fraction part, we might need to save/round it
     before clobbering any of it in Step 1.  Also, we might want to do
     the rounding now to make use of LD_REGS.  */
  if (SCALAR_INT_MODE_P (GET_MODE (xop[0]))
      && SCALAR_ACCUM_MODE_P (GET_MODE (xop[1]))
      && !TARGET_FRACT_CONV_TRUNC)
    {
      bool overlap
        = (src.regno <=
           (offset ? dest.regno_msb - sign_bytes : dest.regno + zero_bytes - 1)
           && dest.regno - offset -1 >= dest.regno);
      unsigned s0 = dest.regno - offset -1;
      bool use_src = true;
      unsigned sn;
      unsigned copied_msb = src.regno_msb;
      bool have_carry = false;

      if (src.ibyte > dest.ibyte)
        copied_msb -= src.ibyte - dest.ibyte;

      for (sn = s0; sn <= copied_msb; sn++)
        if (!IN_RANGE (sn, dest.regno, dest.regno_msb)
            && !reg_unused_after (insn, all_regs_rtx[sn]))
          use_src = false;
      if (use_src && TEST_HARD_REG_BIT (reg_class_contents[LD_REGS], s0))
        {
          avr_asm_len ("tst %0" CR_TAB "brpl 0f",
                       &all_regs_rtx[src.regno_msb], plen, 2);
          sn = src.regno;
          if (sn < s0)
            {
              if (TEST_HARD_REG_BIT (reg_class_contents[LD_REGS], sn))
                avr_asm_len ("cpi %0,1", &all_regs_rtx[sn], plen, 1);
              else
                avr_asm_len ("sec" CR_TAB
                             "cpc %0,__zero_reg__",
                             &all_regs_rtx[sn], plen, 2);
              have_carry = true;
            }
          while (++sn < s0)
            avr_asm_len ("cpc %0,__zero_reg__", &all_regs_rtx[sn], plen, 1);

          avr_asm_len (have_carry ? "sbci %0,128" : "subi %0,129",
                       &all_regs_rtx[s0], plen, 1);
          for (sn = src.regno + src.fbyte; sn <= copied_msb; sn++)
            avr_asm_len ("sbci %0,255", &all_regs_rtx[sn], plen, 1);
          avr_asm_len ("\n0:", NULL, plen, 0);
          frac_rounded = true;
        }
      else if (use_src && overlap)
        {
          avr_asm_len ("clr __tmp_reg__" CR_TAB
                       "sbrc %1,0"       CR_TAB
                       "dec __tmp_reg__", xop, plen, 1);
          sn = src.regno;
          if (sn < s0)
            {
              avr_asm_len ("add %0,__tmp_reg__", &all_regs_rtx[sn], plen, 1);
              have_carry = true;
            }

          while (++sn < s0)
            avr_asm_len ("adc %0,__tmp_reg__", &all_regs_rtx[sn], plen, 1);

          if (have_carry)
            avr_asm_len ("clt"                CR_TAB
                         "bld __tmp_reg__,7"  CR_TAB
                         "adc %0,__tmp_reg__",
                         &all_regs_rtx[s0], plen, 1);
          else
            avr_asm_len ("lsr __tmp_reg" CR_TAB
                         "add %0,__tmp_reg__",
                         &all_regs_rtx[s0], plen, 2);
          for (sn = src.regno + src.fbyte; sn <= copied_msb; sn++)
            avr_asm_len ("adc %0,__zero_reg__", &all_regs_rtx[sn], plen, 1);
          frac_rounded = true;
        }
      else if (overlap)
        {
          bool use_src
            = (TEST_HARD_REG_BIT (reg_class_contents[LD_REGS], s0)
               && (IN_RANGE (s0, dest.regno, dest.regno_msb)
                   || reg_unused_after (insn, all_regs_rtx[s0])));
          xop[2] = all_regs_rtx[s0];
          unsigned sn = src.regno;
          if (!use_src || sn == s0)
            avr_asm_len ("mov __tmp_reg__,%2", xop, plen, 1);
          /* We need to consider to-be-discarded bits
             if the value is negative.  */
          if (sn < s0)
            {
              avr_asm_len ("tst %0" CR_TAB
                           "brpl 0f",
                           &all_regs_rtx[src.regno_msb], plen, 2);
              /* Test to-be-discarded bytes for any nozero bits.
                 ??? Could use OR or SBIW to test two registers at once.  */
              if (sn < s0)
                avr_asm_len ("cp %0,__zero_reg__", &all_regs_rtx[sn], plen, 1);

              while (++sn < s0)
                avr_asm_len ("cpc %0,__zero_reg__", &all_regs_rtx[sn], plen, 1);
              /* Set bit 0 in __tmp_reg__ if any of the lower bits was set.  */
              if (use_src)
                avr_asm_len ("breq 0f" CR_TAB
                             "ori %2,1"
                             "\n0:\t" "mov __tmp_reg__,%2",
                             xop, plen, 3);
              else
                avr_asm_len ("breq 0f" CR_TAB
                             "set"     CR_TAB
                             "bld __tmp_reg__,0\n0:",
                             xop, plen, 3);
            }
          lsb_in_tmp_reg = true;
        }
    }

  /* Step 1:  Clear bytes at the low end and copy payload bits from source
     ======   to destination.  */

  int step = offset < 0 ? 1 : -1;
  unsigned d0 = offset < 0 ? dest.regno : dest.regno_msb;

  // We cleared at least that number of registers.
  int clr_n = 0;

  for (; d0 >= dest.regno && d0 <= dest.regno_msb; d0 += step)
    {
      // Next regno of destination is needed for MOVW
      unsigned d1 = d0 + step;

      // Current and next regno of source
      signed s0 = d0 - offset;
      signed s1 = s0 + step;

      // Must current resp. next regno be CLRed?  This applies to the low
      // bytes of the destination that have no associated source bytes.
      bool clr0 = s0 < (signed) src.regno;
      bool clr1 = s1 < (signed) src.regno && d1 >= dest.regno;

      // First gather what code to emit (if any) and additional step to
      // apply if a MOVW is in use.  xop[2] is destination rtx and xop[3]
      // is the source rtx for the current loop iteration.
      const char *code = NULL;
      int stepw = 0;

      if (clr0)
        {
          if (AVR_HAVE_MOVW && clr1 && clrw)
            {
              xop[2] = all_regs_rtx[d0 & ~1];
              xop[3] = clrw;
              code = "movw %2,%3";
              stepw = step;
            }
          else
            {
              xop[2] = all_regs_rtx[d0];
              code = "clr %2";

              if (++clr_n >= 2
                  && !clrw
                  && d0 % 2 == (step > 0))
                {
                  clrw = all_regs_rtx[d0 & ~1];
                }
            }
        }
      else if (offset && s0 <= (signed) src.regno_msb)
        {
          int movw = AVR_HAVE_MOVW && offset % 2 == 0
            && d0 % 2 == (offset > 0)
            && d1 <= dest.regno_msb && d1 >= dest.regno
            && s1 <= (signed) src.regno_msb  && s1 >= (signed) src.regno;

          xop[2] = all_regs_rtx[d0 & ~movw];
          xop[3] = all_regs_rtx[s0 & ~movw];
          code = movw ? "movw %2,%3" : "mov %2,%3";
          stepw = step * movw;
        }

      if (code)
        {
          if (sign_extend && shift != ASHIFT && !sign_in_carry
              && (d0 == src.regno_msb || d0 + stepw == src.regno_msb))
            {
              /* We are going to override the sign bit.  If we sign-extend,
                 store the sign in the Carry flag.  This is not needed if
                 the destination will be ASHIFT in the remainder because
                 the ASHIFT will set Carry without extra instruction.  */

              avr_asm_len ("lsl %0", &all_regs_rtx[src.regno_msb], plen, 1);
              sign_in_carry = true;
            }

          unsigned src_msb = dest.regno_msb - sign_bytes - offset + 1;

          if (!sign_extend && shift == ASHIFTRT && !msb_in_carry
              && src.ibyte > dest.ibyte
              && (d0 == src_msb || d0 + stepw == src_msb))
            {
              /* We are going to override the MSB.  If we shift right,
                 store the MSB in the Carry flag.  This is only needed if
                 we don't sign-extend becaue with sign-extension the MSB
                 (the sign) will be produced by the sign extension.  */

              avr_asm_len ("lsr %0", &all_regs_rtx[src_msb], plen, 1);
              msb_in_carry = true;
            }

          unsigned src_lsb = dest.regno - offset -1;

          if (shift == ASHIFT && src.fbyte > dest.fbyte && !lsb_in_carry
	      && !lsb_in_tmp_reg
              && (d0 == src_lsb || d0 + stepw == src_lsb))
            {
              /* We are going to override the new LSB; store it into carry.  */

              avr_asm_len ("lsl %0", &all_regs_rtx[src_lsb], plen, 1);
              code_ashift = "rol %0";
              lsb_in_carry = true;
            }

          avr_asm_len (code, xop, plen, 1);
          d0 += stepw;
        }
    }

  /* Step 2:  Shift destination left by 1 bit position.  This might be needed
     ======   for signed input and unsigned output.  */

  if (shift == ASHIFT && src.fbyte > dest.fbyte && !lsb_in_carry)
    {
      unsigned s0 = dest.regno - offset -1;

      /* n1169 4.1.4 says:
	 "Conversions from a fixed-point to an integer type round toward zero."
	 Hence, converting a fract type to integer only gives a non-zero result
	 for -1.  */
      if (SCALAR_INT_MODE_P (GET_MODE (xop[0]))
	  && SCALAR_FRACT_MODE_P (GET_MODE (xop[1]))
	  && !TARGET_FRACT_CONV_TRUNC)
	{
	  gcc_assert (s0 == src.regno_msb);
	  /* Check if the input is -1.  We do that by checking if negating
	     the input causes an integer overflow.  */
	  unsigned sn = src.regno;
	  avr_asm_len ("cp __zero_reg__,%0", &all_regs_rtx[sn++], plen, 1);
	  while (sn <= s0)
	    avr_asm_len ("cpc __zero_reg__,%0", &all_regs_rtx[sn++], plen, 1);

	  /* Overflow goes with set carry.  Clear carry otherwise.  */
	  avr_asm_len ("brvs 0f" CR_TAB
                       "clc\n0:", NULL, plen, 2);
	}
      /* Likewise, when converting from accumulator types to integer, we
	 need to round up negative values.  */
      else if (SCALAR_INT_MODE_P (GET_MODE (xop[0]))
	       && SCALAR_ACCUM_MODE_P (GET_MODE (xop[1]))
	       && !TARGET_FRACT_CONV_TRUNC
	       && !frac_rounded)
	{
	  bool have_carry = false;

	  xop[2] = all_regs_rtx[s0];
	  if (!lsb_in_tmp_reg && !MAY_CLOBBER (s0))
	    avr_asm_len ("mov __tmp_reg__,%2", xop, plen, 1);
	  avr_asm_len ("tst %0" CR_TAB "brpl 0f",
		       &all_regs_rtx[src.regno_msb], plen, 2);
	  if (!lsb_in_tmp_reg)
	    {
	      unsigned sn = src.regno;
	      if (sn < s0)
		{
		  avr_asm_len ("cp __zero_reg__,%0", &all_regs_rtx[sn],
			       plen, 1);
		  have_carry = true;
		}
	      while (++sn < s0)
		avr_asm_len ("cpc __zero_reg__,%0", &all_regs_rtx[sn], plen, 1);
	      lsb_in_tmp_reg = !MAY_CLOBBER (s0);
	    }
	  /* Add in C and the rounding value 127.  */
	  /* If the destination msb is a sign byte, and in LD_REGS,
	     grab it as a temporary.  */
	  if (sign_bytes
	      && TEST_HARD_REG_BIT (reg_class_contents[LD_REGS],
				    dest.regno_msb))
	    {
	      xop[3] = all_regs_rtx[dest.regno_msb];
	      avr_asm_len ("ldi %3,127", xop, plen, 1);
	      avr_asm_len ((have_carry && lsb_in_tmp_reg ? "adc __tmp_reg__,%3"
			    : have_carry ? "adc %2,%3"
			    : lsb_in_tmp_reg ? "add __tmp_reg__,%3"
			    : "add %2,%3"),
			   xop, plen, 1);
	    }
	  else
	    {
	      /* Fall back to use __zero_reg__ as a temporary.  */
	      avr_asm_len ("dec __zero_reg__", NULL, plen, 1);
	      if (have_carry)
		avr_asm_len ("clt" CR_TAB
                             "bld __zero_reg__,7", NULL, plen, 2);
	      else
		avr_asm_len ("lsr __zero_reg__", NULL, plen, 1);
	      avr_asm_len (have_carry && lsb_in_tmp_reg
                           ? "adc __tmp_reg__,__zero_reg__"
                           : have_carry ? "adc %2,__zero_reg__"
                           : lsb_in_tmp_reg ? "add __tmp_reg__,__zero_reg__"
                           : "add %2,__zero_reg__",
			   xop, plen, 1);
	      avr_asm_len ("eor __zero_reg__,__zero_reg__", NULL, plen, 1);
	    }

          for (d0 = dest.regno + zero_bytes;
	       d0 <= dest.regno_msb - sign_bytes; d0++)
	    avr_asm_len ("adc %0,__zero_reg__", &all_regs_rtx[d0], plen, 1);

          avr_asm_len (lsb_in_tmp_reg
		       ? "\n0:\t" "lsl __tmp_reg__"
                       : "\n0:\t" "lsl %2",
		       xop, plen, 1);
	}
      else if (MAY_CLOBBER (s0))
        avr_asm_len ("lsl %0", &all_regs_rtx[s0], plen, 1);
      else
        avr_asm_len ("mov __tmp_reg__,%0" CR_TAB
                     "lsl __tmp_reg__", &all_regs_rtx[s0], plen, 2);

      code_ashift = "rol %0";
      lsb_in_carry = true;
    }

  if (shift == ASHIFT)
    {
      for (d0 = dest.regno + zero_bytes;
           d0 <= dest.regno_msb - sign_bytes; d0++)
        {
          avr_asm_len (code_ashift, &all_regs_rtx[d0], plen, 1);
          code_ashift = "rol %0";
        }

      lsb_in_carry = false;
      sign_in_carry = true;
    }

  /* Step 4a:  Store MSB in carry if we don't already have it or will produce
     =======   it in sign-extension below.  */

  if (!sign_extend && shift == ASHIFTRT && !msb_in_carry
      && src.ibyte > dest.ibyte)
    {
      unsigned s0 = dest.regno_msb - sign_bytes - offset + 1;

      if (MAY_CLOBBER (s0))
        avr_asm_len ("lsr %0", &all_regs_rtx[s0], plen, 1);
      else
        avr_asm_len ("mov __tmp_reg__,%0" CR_TAB
                     "lsr __tmp_reg__", &all_regs_rtx[s0], plen, 2);

      msb_in_carry = true;
    }

  /* Step 3:  Sign-extend or zero-extend the destination as needed.
     ======   */

  if (sign_extend && !sign_in_carry)
    {
      unsigned s0 = src.regno_msb;

      if (MAY_CLOBBER (s0))
        avr_asm_len ("lsl %0", &all_regs_rtx[s0], plen, 1);
      else
        avr_asm_len ("mov __tmp_reg__,%0" CR_TAB
                     "lsl __tmp_reg__", &all_regs_rtx[s0], plen, 2);

      sign_in_carry = true;
    }

  gcc_assert (sign_in_carry + msb_in_carry + lsb_in_carry <= 1);

  unsigned copies = 0;
  rtx movw = sign_extend ? NULL_RTX : clrw;

  for (d0 = dest.regno_msb - sign_bytes + 1; d0 <= dest.regno_msb; d0++)
    {
      if (AVR_HAVE_MOVW && movw
          && d0 % 2 == 0 && d0 + 1 <= dest.regno_msb)
        {
          xop[2] = all_regs_rtx[d0];
          xop[3] = movw;
          avr_asm_len ("movw %2,%3", xop, plen, 1);
          d0++;
        }
      else
        {
          avr_asm_len (sign_extend ? "sbc %0,%0" : "clr %0",
                       &all_regs_rtx[d0], plen, 1);

          if (++copies >= 2 && !movw && d0 % 2 == 1)
            movw = all_regs_rtx[d0-1];
        }
    } /* for */


  /* Step 4:  Right shift the destination.  This might be needed for
     ======   conversions from unsigned to signed.  */

  if (shift == ASHIFTRT)
    {
      const char *code_ashiftrt = "lsr %0";

      if (sign_extend || msb_in_carry)
        code_ashiftrt = "ror %0";

      if (src.sbit && src.ibyte == dest.ibyte)
        code_ashiftrt = "asr %0";

      for (d0 = dest.regno_msb - sign_bytes;
           d0 >= dest.regno + zero_bytes - 1 && d0 >= dest.regno; d0--)
        {
          avr_asm_len (code_ashiftrt, &all_regs_rtx[d0], plen, 1);
          code_ashiftrt = "ror %0";
        }
    }

#undef MAY_CLOBBER

  return "";
}


/* Output fixed-point rounding.  XOP[0] = XOP[1] is the operand to round.
   XOP[2] is the rounding point, a CONST_INT.  The function prints the
   instruction sequence if PLEN = NULL and computes the length in words
   of the sequence if PLEN != NULL.  Most of this function deals with
   preparing operands for calls to `avr_out_plus' and `avr_out_bitop'.  */

const char*
avr_out_round (rtx_insn *insn ATTRIBUTE_UNUSED, rtx *xop, int *plen)
{
  scalar_mode mode = as_a <scalar_mode> (GET_MODE (xop[0]));
  scalar_int_mode imode = int_mode_for_mode (mode).require ();
  // The smallest fractional bit not cleared by the rounding is 2^(-RP).
  int fbit = (int) GET_MODE_FBIT (mode);
  double_int i_add = double_int_zero.set_bit (fbit-1 - INTVAL (xop[2]));
  wide_int wi_add = wi::set_bit_in_zero (fbit-1 - INTVAL (xop[2]),
					 GET_MODE_PRECISION (imode));
  // Lengths of PLUS and AND parts.
  int len_add = 0, *plen_add = plen ? &len_add : NULL;
  int len_and = 0, *plen_and = plen ? &len_and : NULL;

  // Add-Saturate  1/2 * 2^(-RP).  Don't print the label "0:" when printing
  // the saturated addition so that we can emit the "rjmp 1f" before the
  // "0:" below.

  rtx xadd = const_fixed_from_double_int (i_add, mode);
  rtx xpattern, xsrc, op[4];

  xsrc = SIGNED_FIXED_POINT_MODE_P (mode)
    ? gen_rtx_SS_PLUS (mode, xop[1], xadd)
    : gen_rtx_US_PLUS (mode, xop[1], xadd);
  xpattern = gen_rtx_SET (xop[0], xsrc);

  op[0] = xop[0];
  op[1] = xop[1];
  op[2] = xadd;
  avr_out_plus (xpattern, op, plen_add, NULL, false /* Don't print "0:" */);

  avr_asm_len ("rjmp 1f" CR_TAB
               "0:", NULL, plen_add, 1);

  // Keep  all bits from RP and higher:   ... 2^(-RP)
  // Clear all bits from RP+1 and lower:              2^(-RP-1) ...
  // Rounding point                           ^^^^^^^
  // Added above                                      ^^^^^^^^^
  rtx xreg = simplify_gen_subreg (imode, xop[0], mode, 0);
  rtx xmask = immed_wide_int_const (-wi_add - wi_add, imode);

  xpattern = gen_rtx_SET (xreg, gen_rtx_AND (imode, xreg, xmask));

  op[0] = xreg;
  op[1] = xreg;
  op[2] = xmask;
  op[3] = gen_rtx_SCRATCH (QImode);
  avr_out_bitop (xpattern, op, plen_and);
  avr_asm_len ("1:", NULL, plen, 0);

  if (plen)
    *plen = len_add + len_and;

  return "";
}


/* Create RTL split patterns for byte sized rotate expressions.  This
   produces a series of move instructions and considers overlap situations.
   Overlapping non-HImode operands need a scratch register.  */

bool
avr_rotate_bytes (rtx operands[])
{
  machine_mode mode = GET_MODE (operands[0]);
  bool overlapped = reg_overlap_mentioned_p (operands[0], operands[1]);
  bool same_reg = rtx_equal_p (operands[0], operands[1]);
  int num = INTVAL (operands[2]);
  rtx scratch = operands[3];
  /* Work out if byte or word move is needed.  Odd byte rotates need QImode.
     Word move if no scratch is needed, otherwise use size of scratch.  */
  machine_mode move_mode = QImode;
  int move_size, offset, size;

  if (num & 0xf)
    move_mode = QImode;
  else if ((mode == SImode && !same_reg) || !overlapped)
    move_mode = HImode;
  else
    move_mode = GET_MODE (scratch);

  /* Force DI rotate to use QI moves since other DI moves are currently split
     into QI moves so forward propagation works better.  */
  if (mode == DImode)
    move_mode = QImode;
  /* Make scratch smaller if needed.  */
  if (SCRATCH != GET_CODE (scratch)
      && HImode == GET_MODE (scratch)
      && QImode == move_mode)
    scratch = simplify_gen_subreg (move_mode, scratch, HImode, 0);

  move_size = GET_MODE_SIZE (move_mode);
  /* Number of bytes/words to rotate.  */
  offset = (num  >> 3) / move_size;
  /* Number of moves needed.  */
  size = GET_MODE_SIZE (mode) / move_size;
  /* Himode byte swap is special case to avoid a scratch register.  */
  if (mode == HImode && same_reg)
    {
      /* HImode byte swap, using xor.  This is as quick as using scratch.  */
      rtx src, dst;
      src = simplify_gen_subreg (move_mode, operands[1], mode, 0);
      dst = simplify_gen_subreg (move_mode, operands[0], mode, 1);
      if (!rtx_equal_p (dst, src))
        {
          emit_move_insn (dst, gen_rtx_XOR (QImode, dst, src));
          emit_move_insn (src, gen_rtx_XOR (QImode, src, dst));
          emit_move_insn (dst, gen_rtx_XOR (QImode, dst, src));
        }
    }
  else
    {
#define MAX_SIZE 8 /* GET_MODE_SIZE (DImode) / GET_MODE_SIZE (QImode)  */
      /* Create linked list of moves to determine move order.  */
      struct {
        rtx src, dst;
        int links;
      } move[MAX_SIZE + 8];
      int blocked, moves;

      gcc_assert (size <= MAX_SIZE);
      /* Generate list of subreg moves.  */
      for (int i = 0; i < size; i++)
        {
          int from = i;
          int to = (from + offset) % size;
          move[i].src = simplify_gen_subreg (move_mode, operands[1],
                                             mode, from * move_size);
          move[i].dst = simplify_gen_subreg (move_mode, operands[0],
                                             mode, to * move_size);
          move[i].links = -1;
        }
      /* Mark dependence where a dst of one move is the src of another move.
         The first move is a conflict as it must wait until second is
         performed.  We ignore moves to self - we catch this later.  */
      if (overlapped)
        for (int i = 0; i < size; i++)
          if (reg_overlap_mentioned_p (move[i].dst, operands[1]))
            for (int j = 0; j < size; j++)
              if (j != i && rtx_equal_p (move[j].src, move[i].dst))
                {
                  /* The dst of move i is the src of move j.  */
                  move[i].links = j;
                  break;
                }

      blocked = -1;
      moves = 0;
      /* Go through move list and perform non-conflicting moves.  As each
         non-overlapping move is made, it may remove other conflicts
         so the process is repeated until no conflicts remain.  */
      do
        {
          blocked = -1;
          moves = 0;
          /* Emit move where dst is not also a src or we have used that
             src already.  */
          for (int i = 0; i < size; i++)
            if (move[i].src != NULL_RTX)
              {
                if (move[i].links == -1
                    || move[move[i].links].src == NULL_RTX)
                  {
                    moves++;
                    /* Ignore NOP moves to self.  */
                    if (!rtx_equal_p (move[i].dst, move[i].src))
                      emit_move_insn (move[i].dst, move[i].src);

                    /* Remove  conflict from list.  */
                    move[i].src = NULL_RTX;
                  }
                else
                  blocked = i;
              }

          /* Check for deadlock. This is when no moves occurred and we have
             at least one blocked move.  */
          if (moves == 0 && blocked != -1)
            {
              /* Need to use scratch register to break deadlock.
                 Add move to put dst of blocked move into scratch.
                 When this move occurs, it will break chain deadlock.
                 The scratch register is substituted for real move.  */

              gcc_assert (SCRATCH != GET_CODE (scratch));

              move[size].src = move[blocked].dst;
              move[size].dst =  scratch;
              /* Scratch move is never blocked.  */
              move[size].links = -1;
              /* Make sure we have valid link.  */
              gcc_assert (move[blocked].links != -1);
              /* Replace src of  blocking move with scratch reg.  */
              move[move[blocked].links].src = scratch;
              /* Make dependent on scratch move occurring.  */
              move[blocked].links = size;
              size=size+1;
            }
        }
      while (blocked != -1);
    }
  return true;
}


/* Worker function for `ADJUST_INSN_LENGTH'.  */
/* Modifies the length assigned to instruction INSN
   LEN is the initially computed length of the insn.  */

int
avr_adjust_insn_length (rtx_insn *insn, int len)
{
  rtx *op = recog_data.operand;
  enum attr_adjust_len adjust_len;

  /* As we pretend jump tables in .text, fix branch offsets crossing jump
     tables now.  */

  if (JUMP_TABLE_DATA_P (insn))
    return 0;

  /* Some complex insns don't need length adjustment and therefore
     the length need not/must not be adjusted for these insns.
     It is easier to state this in an insn attribute "adjust_len" than
     to clutter up code here...  */

  if (!NONDEBUG_INSN_P (insn) || recog_memoized (insn) == -1)
    {
      return len;
    }

  /* Read from insn attribute "adjust_len" if/how length is to be adjusted.  */

  adjust_len = get_attr_adjust_len (insn);

  if (adjust_len == ADJUST_LEN_NO)
    {
      /* Nothing to adjust: The length from attribute "length" is fine.
         This is the default.  */

      return len;
    }

  /* Extract insn's operands.  */

  extract_constrain_insn_cached (insn);

  /* Dispatch to right function.  */

  switch (adjust_len)
    {
    case ADJUST_LEN_RELOAD_IN16: output_reload_inhi (op, op[2], &len); break;
    case ADJUST_LEN_RELOAD_IN24: avr_out_reload_inpsi (op, op[2], &len); break;
    case ADJUST_LEN_RELOAD_IN32: output_reload_insisf (op, op[2], &len); break;

    case ADJUST_LEN_OUT_BITOP: avr_out_bitop (insn, op, &len); break;

    case ADJUST_LEN_PLUS: avr_out_plus (insn, op, &len); break;
    case ADJUST_LEN_ADDTO_SP: avr_out_addto_sp (op, &len); break;

    case ADJUST_LEN_MOV8:  output_movqi (insn, op, &len); break;
    case ADJUST_LEN_MOV16: output_movhi (insn, op, &len); break;
    case ADJUST_LEN_MOV24: avr_out_movpsi (insn, op, &len); break;
    case ADJUST_LEN_MOV32: output_movsisf (insn, op, &len); break;
    case ADJUST_LEN_CPYMEM: avr_out_cpymem (insn, op, &len); break;
    case ADJUST_LEN_XLOAD: avr_out_xload (insn, op, &len); break;
    case ADJUST_LEN_SEXT: avr_out_sign_extend (insn, op, &len); break;

    case ADJUST_LEN_SFRACT: avr_out_fract (insn, op, true, &len); break;
    case ADJUST_LEN_UFRACT: avr_out_fract (insn, op, false, &len); break;
    case ADJUST_LEN_ROUND: avr_out_round (insn, op, &len); break;

    case ADJUST_LEN_TSTHI: avr_out_tsthi (insn, op, &len); break;
    case ADJUST_LEN_TSTPSI: avr_out_tstpsi (insn, op, &len); break;
    case ADJUST_LEN_TSTSI: avr_out_tstsi (insn, op, &len); break;
    case ADJUST_LEN_COMPARE: avr_out_compare (insn, op, &len); break;
    case ADJUST_LEN_COMPARE64: avr_out_compare64 (insn, op, &len); break;

    case ADJUST_LEN_LSHRQI: lshrqi3_out (insn, op, &len); break;
    case ADJUST_LEN_LSHRHI: lshrhi3_out (insn, op, &len); break;
    case ADJUST_LEN_LSHRSI: lshrsi3_out (insn, op, &len); break;

    case ADJUST_LEN_ASHRQI: ashrqi3_out (insn, op, &len); break;
    case ADJUST_LEN_ASHRHI: ashrhi3_out (insn, op, &len); break;
    case ADJUST_LEN_ASHRSI: ashrsi3_out (insn, op, &len); break;

    case ADJUST_LEN_ASHLQI: ashlqi3_out (insn, op, &len); break;
    case ADJUST_LEN_ASHLHI: ashlhi3_out (insn, op, &len); break;
    case ADJUST_LEN_ASHLSI: ashlsi3_out (insn, op, &len); break;

    case ADJUST_LEN_ASHLPSI: avr_out_ashlpsi3 (insn, op, &len); break;
    case ADJUST_LEN_ASHRPSI: avr_out_ashrpsi3 (insn, op, &len); break;
    case ADJUST_LEN_LSHRPSI: avr_out_lshrpsi3 (insn, op, &len); break;

    case ADJUST_LEN_CALL: len = AVR_HAVE_JMP_CALL ? 2 : 1; break;

    case ADJUST_LEN_INSERT_BITS: avr_out_insert_bits (op, &len); break;

    case ADJUST_LEN_INSV_NOTBIT:
      avr_out_insert_notbit (insn, op, NULL_RTX, &len);
      break;
    case ADJUST_LEN_INSV_NOTBIT_0:
      avr_out_insert_notbit (insn, op, const0_rtx, &len);
      break;
    case ADJUST_LEN_INSV_NOTBIT_7:
      avr_out_insert_notbit (insn, op, GEN_INT (7), &len);
      break;

    default:
      gcc_unreachable();
    }

  return len;
}

/* Return nonzero if register REG dead after INSN.  */

int
reg_unused_after (rtx_insn *insn, rtx reg)
{
  return (dead_or_set_p (insn, reg)
	  || (REG_P (reg) && _reg_unused_after (insn, reg)));
}

/* Return nonzero if REG is not used after INSN.
   We assume REG is a reload reg, and therefore does
   not live past labels.  It may live past calls or jumps though.  */

int
_reg_unused_after (rtx_insn *insn, rtx reg)
{
  enum rtx_code code;
  rtx set;

  /* If the reg is set by this instruction, then it is safe for our
     case.  Disregard the case where this is a store to memory, since
     we are checking a register used in the store address.  */
  set = single_set (insn);
  if (set && !MEM_P (SET_DEST (set))
      && reg_overlap_mentioned_p (reg, SET_DEST (set)))
    return 1;

  while ((insn = NEXT_INSN (insn)))
    {
      rtx set;
      code = GET_CODE (insn);

#if 0
      /* If this is a label that existed before reload, then the register
	 if dead here.  However, if this is a label added by reorg, then
	 the register may still be live here.  We can't tell the difference,
	 so we just ignore labels completely.  */
      if (code == CODE_LABEL)
	return 1;
      /* else */
#endif

      if (!INSN_P (insn))
	continue;

      if (code == JUMP_INSN)
	return 0;

      /* If this is a sequence, we must handle them all at once.
	 We could have for instance a call that sets the target register,
	 and an insn in a delay slot that uses the register.  In this case,
	 we must return 0.  */
      else if (code == INSN && GET_CODE (PATTERN (insn)) == SEQUENCE)
	{
	  rtx_sequence *seq = as_a <rtx_sequence *> (PATTERN (insn));
	  int retval = 0;

	  for (int i = 0; i < seq->len (); i++)
	    {
	      rtx_insn *this_insn = seq->insn (i);
	      rtx set = single_set (this_insn);

	      if (CALL_P (this_insn))
		code = CALL_INSN;
	      else if (JUMP_P (this_insn))
		{
		  if (INSN_ANNULLED_BRANCH_P (this_insn))
		    return 0;
		  code = JUMP_INSN;
		}

	      if (set && reg_overlap_mentioned_p (reg, SET_SRC (set)))
		return 0;
	      if (set && reg_overlap_mentioned_p (reg, SET_DEST (set)))
		{
		  if (!MEM_P (SET_DEST (set)))
		    retval = 1;
		  else
		    return 0;
		}
	      if (set == 0
		  && reg_overlap_mentioned_p (reg, PATTERN (this_insn)))
		return 0;
	    }
	  if (retval == 1)
	    return 1;
	  else if (code == JUMP_INSN)
	    return 0;
	}

      if (code == CALL_INSN)
	{
	  rtx tem;
	  for (tem = CALL_INSN_FUNCTION_USAGE (insn); tem; tem = XEXP (tem, 1))
	    if (GET_CODE (XEXP (tem, 0)) == USE
		&& REG_P (XEXP (XEXP (tem, 0), 0))
		&& reg_overlap_mentioned_p (reg, XEXP (XEXP (tem, 0), 0)))
	      return 0;
	  if (call_used_or_fixed_reg_p (REGNO (reg)))
	    return 1;
	}

      set = single_set (insn);

      if (set && reg_overlap_mentioned_p (reg, SET_SRC (set)))
	return 0;
      if (set && reg_overlap_mentioned_p (reg, SET_DEST (set)))
	return !MEM_P (SET_DEST (set));
      if (set == 0 && reg_overlap_mentioned_p (reg, PATTERN (insn)))
	return 0;
    }
  return 1;
}


/* Implement `TARGET_ASM_INTEGER'.  */
/* Target hook for assembling integer objects.  The AVR version needs
   special handling for references to certain labels.  */

static bool
avr_assemble_integer (rtx x, unsigned int size, int aligned_p)
{
  if (size == POINTER_SIZE / BITS_PER_UNIT && aligned_p
      && text_segment_operand (x, VOIDmode))
    {
      fputs ("\t.word\tgs(", asm_out_file);
      output_addr_const (asm_out_file, x);
      fputs (")\n", asm_out_file);

      return true;
    }
  else if (GET_MODE (x) == PSImode)
    {
      /* This needs binutils 2.23+, see PR binutils/13503  */

      fputs ("\t.byte\tlo8(", asm_out_file);
      output_addr_const (asm_out_file, x);
      fputs (")" ASM_COMMENT_START "need binutils PR13503\n", asm_out_file);

      fputs ("\t.byte\thi8(", asm_out_file);
      output_addr_const (asm_out_file, x);
      fputs (")" ASM_COMMENT_START "need binutils PR13503\n", asm_out_file);

      fputs ("\t.byte\thh8(", asm_out_file);
      output_addr_const (asm_out_file, x);
      fputs (")" ASM_COMMENT_START "need binutils PR13503\n", asm_out_file);

      return true;
    }
  else if (CONST_FIXED_P (x))
    {
      /* varasm fails to handle big fixed modes that don't fit in hwi.  */

      for (unsigned n = 0; n < size; n++)
        {
          rtx xn = simplify_gen_subreg (QImode, x, GET_MODE (x), n);
          default_assemble_integer (xn, 1, aligned_p);
        }

      return true;
    }

  if (AVR_TINY
      && avr_address_tiny_pm_p (x))
    {
      x = plus_constant (Pmode, x, avr_arch->flash_pm_offset);
    }

  return default_assemble_integer (x, size, aligned_p);
}

/* Implement TARGET_CLASS_MAX_NREGS. Reasons described in comments for
   avr_hard_regno_nregs. */

static unsigned char
avr_class_max_nregs (reg_class_t rclass, machine_mode mode)
{
  if (rclass == CC_REG && mode == CCmode)
	return 1;

  return CEIL (GET_MODE_SIZE (mode), UNITS_PER_WORD);
}


/* Implement `TARGET_CLASS_LIKELY_SPILLED_P'.  */
/* Return value is nonzero if pseudos that have been
   assigned to registers of class CLASS would likely be spilled
   because registers of CLASS are needed for spill registers.  */

static bool
avr_class_likely_spilled_p (reg_class_t c)
{
  return (c != ALL_REGS &&
           (AVR_TINY ? 1 : c != ADDW_REGS));
}


/* Valid attributes:
   progmem   -  Put data to program memory.
   signal    -  Make a function to be hardware interrupt.
                After function prologue interrupts remain disabled.
   interrupt -  Make a function to be hardware interrupt. Before function
                prologue interrupts are enabled by means of SEI.
   naked     -  Don't generate function prologue/epilogue and RET
                instruction.  */

/* Handle a "progmem" attribute; arguments as in
   struct attribute_spec.handler.  */

static tree
avr_handle_progmem_attribute (tree *node, tree name,
			      tree args ATTRIBUTE_UNUSED,
			      int flags ATTRIBUTE_UNUSED,
			      bool *no_add_attrs)
{
  if (DECL_P (*node))
    {
      if (TREE_CODE (*node) == TYPE_DECL)
	{
	  /* This is really a decl attribute, not a type attribute,
	     but try to handle it for GCC 3.0 backwards compatibility.  */

	  tree type = TREE_TYPE (*node);
	  tree attr = tree_cons (name, args, TYPE_ATTRIBUTES (type));
	  tree newtype = build_type_attribute_variant (type, attr);

	  TYPE_MAIN_VARIANT (newtype) = TYPE_MAIN_VARIANT (type);
	  TREE_TYPE (*node) = newtype;
	  *no_add_attrs = true;
	}
      else if (TREE_STATIC (*node) || DECL_EXTERNAL (*node))
	{
          *no_add_attrs = false;
	}
      else
	{
	  warning (OPT_Wattributes, "%qE attribute ignored",
		   name);
	  *no_add_attrs = true;
	}
    }

  return NULL_TREE;
}

/* Handle an attribute requiring a FUNCTION_DECL; arguments as in
   struct attribute_spec.handler.  */

static tree
avr_handle_fndecl_attribute (tree *node, tree name,
			     tree args ATTRIBUTE_UNUSED,
			     int flags ATTRIBUTE_UNUSED,
			     bool *no_add_attrs)
{
  if (TREE_CODE (*node) != FUNCTION_DECL)
    {
      warning (OPT_Wattributes, "%qE attribute only applies to functions",
	       name);
      *no_add_attrs = true;
    }

  return NULL_TREE;
}

static tree
avr_handle_fntype_attribute (tree *node, tree name,
                             tree args ATTRIBUTE_UNUSED,
                             int flags ATTRIBUTE_UNUSED,
                             bool *no_add_attrs)
{
  if (TREE_CODE (*node) != FUNCTION_TYPE)
    {
      warning (OPT_Wattributes, "%qE attribute only applies to functions",
	       name);
      *no_add_attrs = true;
    }

  return NULL_TREE;
}

static tree
avr_handle_absdata_attribute (tree *node, tree name, tree /* args */,
                              int /* flags */, bool *no_add)
{
  location_t loc = DECL_SOURCE_LOCATION (*node);

  if (AVR_TINY)
    {
      if (TREE_CODE (*node) != VAR_DECL
          || (!TREE_STATIC (*node) && !DECL_EXTERNAL (*node)))
        {
          warning_at (loc, OPT_Wattributes, "%qE attribute only applies to"
                      " variables in static storage", name);
          *no_add = true;
        }
    }
  else
    {
      warning_at (loc, OPT_Wattributes, "%qE attribute only supported"
                  " for reduced Tiny cores", name);
      *no_add = true;
    }

  return NULL_TREE;
}

static tree
avr_handle_addr_attribute (tree *node, tree name, tree args,
			   int flags ATTRIBUTE_UNUSED, bool *no_add)
{
  bool io_p = startswith (IDENTIFIER_POINTER (name), "io");
  location_t loc = DECL_SOURCE_LOCATION (*node);

  if (!VAR_P (*node))
    {
      warning_at (loc, OPT_Wattributes, "%qE attribute only applies to "
		  "variables", name);
      *no_add = true;
      return NULL_TREE;
    }

  if (args != NULL_TREE)
    {
      if (TREE_CODE (TREE_VALUE (args)) == NON_LVALUE_EXPR)
	TREE_VALUE (args) = TREE_OPERAND (TREE_VALUE (args), 0);
      tree arg = TREE_VALUE (args);
      if (TREE_CODE (arg) != INTEGER_CST)
	{
	  warning_at (loc, OPT_Wattributes, "%qE attribute allows only an "
		      "integer constant argument", name);
	  *no_add = true;
	}
      else if (io_p
	       && (!tree_fits_shwi_p (arg)
		   || !(strcmp (IDENTIFIER_POINTER (name), "io_low") == 0
			? low_io_address_operand : io_address_operand)
			 (GEN_INT (TREE_INT_CST_LOW (arg)), QImode)))
	{
	  warning_at (loc, OPT_Wattributes, "%qE attribute address "
		      "out of range", name);
	  *no_add = true;
	}
      else
	{
	  tree attribs = DECL_ATTRIBUTES (*node);
	  const char *names[] = { "io", "io_low", "address", NULL };
	  for (const char **p = names; *p; p++)
	    {
	      tree other = lookup_attribute (*p, attribs);
	      if (other && TREE_VALUE (other))
		{
		  warning_at (loc, OPT_Wattributes,
			      "both %s and %qE attribute provide address",
			      *p, name);
		  *no_add = true;
		  break;
		}
	    }
	}
    }

  if (*no_add == false && io_p && !TREE_THIS_VOLATILE (*node))
    warning_at (loc, OPT_Wattributes, "%qE attribute on non-volatile variable",
		name);

  return NULL_TREE;
}

rtx
avr_eval_addr_attrib (rtx x)
{
  if (SYMBOL_REF_P (x)
      && (SYMBOL_REF_FLAGS (x) & SYMBOL_FLAG_ADDRESS))
    {
      tree decl = SYMBOL_REF_DECL (x);
      tree attr = NULL_TREE;

      if (SYMBOL_REF_FLAGS (x) & SYMBOL_FLAG_IO)
	{
	  attr = lookup_attribute ("io", DECL_ATTRIBUTES (decl));
          if (!attr || !TREE_VALUE (attr))
            attr = lookup_attribute ("io_low", DECL_ATTRIBUTES (decl));
	  gcc_assert (attr);
	}
      if (!attr || !TREE_VALUE (attr))
	attr = lookup_attribute ("address", DECL_ATTRIBUTES (decl));
      gcc_assert (attr && TREE_VALUE (attr) && TREE_VALUE (TREE_VALUE (attr)));
      return GEN_INT (TREE_INT_CST_LOW (TREE_VALUE (TREE_VALUE (attr))));
    }
  return x;
}


/* AVR attributes.  */
static const struct attribute_spec avr_attribute_table[] =
{
  /* { name, min_len, max_len, decl_req, type_req, fn_type_req,
       affects_type_identity, handler, exclude } */
  { "progmem",   0, 0, false, false, false, false,
    avr_handle_progmem_attribute, NULL },
  { "signal",    0, 0, true,  false, false, false,
    avr_handle_fndecl_attribute, NULL },
  { "interrupt", 0, 0, true,  false, false, false,
    avr_handle_fndecl_attribute, NULL },
  { "no_gccisr", 0, 0, true,  false, false, false,
    avr_handle_fndecl_attribute, NULL },
  { "naked",     0, 0, false, true,  true,  false,
    avr_handle_fntype_attribute, NULL },
  { "OS_task",   0, 0, false, true,  true,  false,
    avr_handle_fntype_attribute, NULL },
  { "OS_main",   0, 0, false, true,  true,  false,
    avr_handle_fntype_attribute, NULL },
  { "io",        0, 1, true, false, false,  false,
    avr_handle_addr_attribute, NULL },
  { "io_low",    0, 1, true, false, false,  false,
    avr_handle_addr_attribute, NULL },
  { "address",   1, 1, true, false, false,  false,
    avr_handle_addr_attribute, NULL },
  { "absdata",   0, 0, true, false, false,  false,
    avr_handle_absdata_attribute, NULL },
  { NULL,        0, 0, false, false, false, false, NULL, NULL }
};


/* Return true if we support address space AS for the architecture in effect
   and false, otherwise.  If LOC is not UNKNOWN_LOCATION then also issue
   a respective error.  */

bool
avr_addr_space_supported_p (addr_space_t as, location_t loc)
{
  if (AVR_TINY)
    {
      if (loc != UNKNOWN_LOCATION)
        error_at (loc, "address spaces are not supported for reduced "
                  "Tiny devices");
      return false;
    }
  else if (avr_addrspace[as].segment >= avr_n_flash)
    {
      if (loc != UNKNOWN_LOCATION)
        error_at (loc, "address space %qs not supported for devices with "
                  "flash size up to %d KiB", avr_addrspace[as].name,
                  64 * avr_n_flash);
      return false;
    }

  return true;
}


/* Implement `TARGET_ADDR_SPACE_DIAGNOSE_USAGE'.  */

static void
avr_addr_space_diagnose_usage (addr_space_t as, location_t loc)
{
  (void) avr_addr_space_supported_p (as, loc);
}


/* Look if DECL shall be placed in program memory space by
   means of attribute `progmem' or some address-space qualifier.
   Return non-zero if DECL is data that must end up in Flash and
   zero if the data lives in RAM (.bss, .data, .rodata, ...).

   Return 2   if DECL is located in 24-bit flash address-space
   Return 1   if DECL is located in 16-bit flash address-space
   Return -1  if attribute `progmem' occurs in DECL or ATTRIBUTES
   Return 0   otherwise  */

int
avr_progmem_p (tree decl, tree attributes)
{
  tree a;

  if (TREE_CODE (decl) != VAR_DECL)
    return 0;

  if (avr_decl_memx_p (decl))
    return 2;

  if (avr_decl_flash_p (decl))
    return 1;

  if (NULL_TREE
      != lookup_attribute ("progmem", attributes))
    return -1;

  a = decl;

  do
    a = TREE_TYPE(a);
  while (TREE_CODE (a) == ARRAY_TYPE);

  if (a == error_mark_node)
    return 0;

  if (NULL_TREE != lookup_attribute ("progmem", TYPE_ATTRIBUTES (a)))
    return -1;

  return 0;
}


/* Return true if DECL has attribute `absdata' set.  This function should
   only be used for AVR_TINY.  */

static bool
avr_decl_absdata_p (tree decl, tree attributes)
{
  return (TREE_CODE (decl) == VAR_DECL
          && NULL_TREE != lookup_attribute ("absdata", attributes));
}


/* Scan type TYP for pointer references to address space ASn.
   Return ADDR_SPACE_GENERIC (i.e. 0) if all pointers targeting
   the AS are also declared to be CONST.
   Otherwise, return the respective address space, i.e. a value != 0.  */

static addr_space_t
avr_nonconst_pointer_addrspace (tree typ)
{
  while (ARRAY_TYPE == TREE_CODE (typ))
    typ = TREE_TYPE (typ);

  if (POINTER_TYPE_P (typ))
    {
      addr_space_t as;
      tree target = TREE_TYPE (typ);

      /* Pointer to function: Test the function's return type.  */

      if (FUNCTION_TYPE == TREE_CODE (target))
        return avr_nonconst_pointer_addrspace (TREE_TYPE (target));

      /* "Ordinary" pointers... */

      while (TREE_CODE (target) == ARRAY_TYPE)
        target = TREE_TYPE (target);

      /* Pointers to non-generic address space must be const.  */

      as = TYPE_ADDR_SPACE (target);

      if (!ADDR_SPACE_GENERIC_P (as)
          && !TYPE_READONLY (target)
          && avr_addr_space_supported_p (as))
        {
          return as;
        }

      /* Scan pointer's target type.  */

      return avr_nonconst_pointer_addrspace (target);
    }

  return ADDR_SPACE_GENERIC;
}


/* Sanity check NODE so that all pointers targeting non-generic address spaces
   go along with CONST qualifier.  Writing to these address spaces should
   be detected and complained about as early as possible.  */

static bool
avr_pgm_check_var_decl (tree node)
{
  const char *reason = NULL;

  addr_space_t as = ADDR_SPACE_GENERIC;

  gcc_assert (as == 0);

  if (avr_log.progmem)
    avr_edump ("%?: %t\n", node);

  switch (TREE_CODE (node))
    {
    default:
      break;

    case VAR_DECL:
      if (as = avr_nonconst_pointer_addrspace (TREE_TYPE (node)), as)
        reason = _("variable");
      break;

    case PARM_DECL:
      if (as = avr_nonconst_pointer_addrspace (TREE_TYPE (node)), as)
        reason = _("function parameter");
      break;

    case FIELD_DECL:
      if (as = avr_nonconst_pointer_addrspace (TREE_TYPE (node)), as)
        reason = _("structure field");
      break;

    case FUNCTION_DECL:
      if (as = avr_nonconst_pointer_addrspace (TREE_TYPE (TREE_TYPE (node))),
          as)
        reason = _("return type of function");
      break;

    case POINTER_TYPE:
      if (as = avr_nonconst_pointer_addrspace (node), as)
        reason = _("pointer");
      break;
    }

  if (reason)
    {
      if (TYPE_P (node))
        error ("pointer targeting address space %qs must be const in %qT",
               avr_addrspace[as].name, node);
      else
        error ("pointer targeting address space %qs must be const"
               " in %s %q+D",
               avr_addrspace[as].name, reason, node);
    }

  return reason == NULL;
}


/* Implement `TARGET_INSERT_ATTRIBUTES'.  */

static void
avr_insert_attributes (tree node, tree *attributes)
{
  avr_pgm_check_var_decl (node);

  if (TARGET_MAIN_IS_OS_TASK
      && TREE_CODE (node) == FUNCTION_DECL
      && MAIN_NAME_P (DECL_NAME (node))
      // FIXME:  We'd like to also test `flag_hosted' which is only
      // available in the C-ish fronts, hence no such test for now.
      // Instead, we test the return type of "main" which is not exactly
      // the same but good enough.
      && INTEGRAL_TYPE_P (TREE_TYPE (TREE_TYPE (node)))
      && NULL == lookup_attribute ("OS_task", *attributes))
    {
      *attributes = tree_cons (get_identifier ("OS_task"),
                               NULL, *attributes);
    }

  /* Add the section attribute if the variable is in progmem.  */

  if (TREE_CODE (node) == VAR_DECL
      && (TREE_STATIC (node) || DECL_EXTERNAL (node))
      && avr_progmem_p (node, *attributes))
    {
      addr_space_t as;
      tree node0 = node;

      /* For C++, we have to peel arrays in order to get correct
         determination of readonlyness.  */

      do
        node0 = TREE_TYPE (node0);
      while (TREE_CODE (node0) == ARRAY_TYPE);

      if (error_mark_node == node0)
        return;

      as = TYPE_ADDR_SPACE (TREE_TYPE (node));

      if (!TYPE_READONLY (node0)
          && !TREE_READONLY (node))
        {
          const char *reason = "__attribute__((progmem))";

          if (!ADDR_SPACE_GENERIC_P (as))
            reason = avr_addrspace[as].name;

          if (avr_log.progmem)
            avr_edump ("\n%?: %t\n%t\n", node, node0);

          error ("variable %q+D must be const in order to be put into"
                 " read-only section by means of %qs", node, reason);
        }
    }
}


/* Implement `ASM_OUTPUT_ALIGNED_DECL_LOCAL'.  */
/* Implement `ASM_OUTPUT_ALIGNED_DECL_COMMON'.  */
/* Track need of __do_clear_bss.  */

void
avr_asm_output_aligned_decl_common (FILE * stream,
                                    tree decl,
                                    const char *name,
                                    unsigned HOST_WIDE_INT size,
                                    unsigned int align, bool local_p)
{
  rtx mem = decl == NULL_TREE ? NULL_RTX : DECL_RTL (decl);
  rtx symbol;

  if (mem != NULL_RTX && MEM_P (mem)
      && SYMBOL_REF_P ((symbol = XEXP (mem, 0)))
      && (SYMBOL_REF_FLAGS (symbol) & (SYMBOL_FLAG_IO | SYMBOL_FLAG_ADDRESS)))
    {
      if (!local_p)
	{
	  fprintf (stream, "\t.globl\t");
	  assemble_name (stream, name);
	  fprintf (stream, "\n");
	}
      if (SYMBOL_REF_FLAGS (symbol) & SYMBOL_FLAG_ADDRESS)
	{
	  assemble_name (stream, name);
	  fprintf (stream, " = %ld\n",
		   (long) INTVAL (avr_eval_addr_attrib (symbol)));
	}
      else if (local_p)
	error_at (DECL_SOURCE_LOCATION (decl),
		  "static IO declaration for %q+D needs an address", decl);
      return;
    }

  /* __gnu_lto_slim is just a marker for the linker injected by toplev.c.
     There is no need to trigger __do_clear_bss code for them.  */

  if (!startswith (name, "__gnu_lto"))
    avr_need_clear_bss_p = true;

  if (local_p)
    ASM_OUTPUT_ALIGNED_LOCAL (stream, name, size, align);
  else
    ASM_OUTPUT_ALIGNED_COMMON (stream, name, size, align);
}

void
avr_asm_asm_output_aligned_bss (FILE *file, tree decl, const char *name,
				unsigned HOST_WIDE_INT size, int align,
				void (*default_func)
				  (FILE *, tree, const char *,
				   unsigned HOST_WIDE_INT, int))
{
  rtx mem = decl == NULL_TREE ? NULL_RTX : DECL_RTL (decl);
  rtx symbol;

  if (mem != NULL_RTX && MEM_P (mem)
      && SYMBOL_REF_P ((symbol = XEXP (mem, 0)))
      && (SYMBOL_REF_FLAGS (symbol) & (SYMBOL_FLAG_IO | SYMBOL_FLAG_ADDRESS)))
    {
      if (!(SYMBOL_REF_FLAGS (symbol) & SYMBOL_FLAG_ADDRESS))
	error_at (DECL_SOURCE_LOCATION (decl),
		  "IO definition for %q+D needs an address", decl);
      avr_asm_output_aligned_decl_common (file, decl, name, size, align, false);
    }
  else
    default_func (file, decl, name, size, align);
}


/* Unnamed section callback for data_section
   to track need of __do_copy_data.  */

static void
avr_output_data_section_asm_op (const void *data)
{
  avr_need_copy_data_p = true;

  /* Dispatch to default.  */
  output_section_asm_op (data);
}


/* Unnamed section callback for bss_section
   to track need of __do_clear_bss.  */

static void
avr_output_bss_section_asm_op (const void *data)
{
  avr_need_clear_bss_p = true;

  /* Dispatch to default.  */
  output_section_asm_op (data);
}


/* Unnamed section callback for progmem*.data sections.  */

static void
avr_output_progmem_section_asm_op (const void *data)
{
  fprintf (asm_out_file, "\t.section\t%s,\"a\",@progbits\n",
           (const char*) data);
}


/* Implement `TARGET_ASM_INIT_SECTIONS'.  */

static void
avr_asm_init_sections (void)
{
  /* Override section callbacks to keep track of `avr_need_clear_bss_p'
     resp. `avr_need_copy_data_p'.  If flash is not mapped to RAM then
     we have also to track .rodata because it is located in RAM then.  */

#if defined HAVE_LD_AVR_AVRXMEGA3_RODATA_IN_FLASH
  if (avr_arch->flash_pm_offset == 0)
#endif
    readonly_data_section->unnamed.callback = avr_output_data_section_asm_op;
  data_section->unnamed.callback = avr_output_data_section_asm_op;
  bss_section->unnamed.callback = avr_output_bss_section_asm_op;
}


/* Implement `TARGET_ASM_NAMED_SECTION'.  */
/* Track need of __do_clear_bss, __do_copy_data for named sections.  */

static void
avr_asm_named_section (const char *name, unsigned int flags, tree decl)
{
  if (flags & AVR_SECTION_PROGMEM)
    {
      addr_space_t as = (flags & AVR_SECTION_PROGMEM) / SECTION_MACH_DEP;
      const char *old_prefix = ".rodata";
      const char *new_prefix = avr_addrspace[as].section_name;

      if (startswith (name, old_prefix))
        {
          const char *sname = ACONCAT ((new_prefix,
                                        name + strlen (old_prefix), NULL));
          default_elf_asm_named_section (sname, flags, decl);
          return;
        }

      default_elf_asm_named_section (new_prefix, flags, decl);
      return;
    }

  if (!avr_need_copy_data_p)
    avr_need_copy_data_p = (startswith (name, ".data")
			    || startswith (name, ".gnu.linkonce.d"));

  if (!avr_need_copy_data_p
#if defined HAVE_LD_AVR_AVRXMEGA3_RODATA_IN_FLASH
      && avr_arch->flash_pm_offset == 0
#endif
      )
    avr_need_copy_data_p = (startswith (name, ".rodata")
			    || startswith (name, ".gnu.linkonce.r"));

  if (!avr_need_clear_bss_p)
    avr_need_clear_bss_p = startswith (name, ".bss");

  default_elf_asm_named_section (name, flags, decl);
}


/* Implement `TARGET_SECTION_TYPE_FLAGS'.  */

static unsigned int
avr_section_type_flags (tree decl, const char *name, int reloc)
{
  unsigned int flags = default_section_type_flags (decl, name, reloc);

  if (startswith (name, ".noinit"))
    {
      if (decl && TREE_CODE (decl) == VAR_DECL
	  && DECL_INITIAL (decl) == NULL_TREE)
	flags |= SECTION_BSS;  /* @nobits */
      else
	warning (0, "only uninitialized variables can be placed in the "
		 ".noinit section");
    }

  if (decl && DECL_P (decl)
      && avr_progmem_p (decl, DECL_ATTRIBUTES (decl)))
    {
      addr_space_t as = TYPE_ADDR_SPACE (TREE_TYPE (decl));

      /* Attribute progmem puts data in generic address space.
         Set section flags as if it was in __flash to get the right
         section prefix in the remainder.  */

      if (ADDR_SPACE_GENERIC_P (as))
        as = ADDR_SPACE_FLASH;

      flags |= as * SECTION_MACH_DEP;
      flags &= ~SECTION_WRITE;
      flags &= ~SECTION_BSS;
    }

  return flags;
}


/* A helper for the next function.  NODE is a decl that is associated with
   a symbol.  Return TRUE if the respective object may be accessed by LDS.
   There might still be other reasons for why LDS is not appropriate.
   This function is only appropriate for AVR_TINY.  */

static bool
avr_decl_maybe_lds_p (tree node)
{
  if (!node
      || TREE_CODE (node) != VAR_DECL
      || DECL_SECTION_NAME (node) != NULL)
    return false;

  /* Don't use LDS for objects that go to .rodata.  The current default
     linker description file still locates .rodata in RAM, but this is not
     a must.  A better linker script would just keep .rodata in flash and
     add an offset of 0x4000 to the VMA.  Hence avoid LDS for such data.  */

  if (TREE_READONLY (node))
    return false;

  // C++ requires peeling arrays.

  do
    node = TREE_TYPE (node);
  while (ARRAY_TYPE == TREE_CODE (node));

  return (node != error_mark_node
          && !TYPE_READONLY (node));
}


/* Implement `TARGET_ENCODE_SECTION_INFO'.  */

static void
avr_encode_section_info (tree decl, rtx rtl, int new_decl_p)
{
  tree addr_attr = NULL_TREE;

  /* In avr_handle_progmem_attribute, DECL_INITIAL is not yet
     readily available, see PR34734.  So we postpone the warning
     about uninitialized data in program memory section until here.  */

  if (new_decl_p
      && decl && DECL_P (decl)
      && !DECL_EXTERNAL (decl)
      && avr_progmem_p (decl, DECL_ATTRIBUTES (decl)))
    {
      if (!TREE_READONLY (decl))
        {
          // This might happen with C++ if stuff needs constructing.
          error ("variable %q+D with dynamic initialization put "
                 "into program memory area", decl);
        }
      else if (NULL_TREE == DECL_INITIAL (decl))
        {
          // Don't warn for (implicit) aliases like in PR80462.
          tree asmname = DECL_ASSEMBLER_NAME (decl);
          varpool_node *node = varpool_node::get_for_asmname (asmname);
          bool alias_p = node && node->alias;

          if (!alias_p)
            warning (OPT_Wuninitialized, "uninitialized variable %q+D put "
                     "into program memory area", decl);
        }
    }

  default_encode_section_info (decl, rtl, new_decl_p);

  if (decl && DECL_P (decl)
      && TREE_CODE (decl) != FUNCTION_DECL
      && MEM_P (rtl)
      && SYMBOL_REF_P (XEXP (rtl, 0)))
    {
      rtx sym = XEXP (rtl, 0);
      tree type = TREE_TYPE (decl);
      tree attr = DECL_ATTRIBUTES (decl);
      if (type == error_mark_node)
	return;

      addr_space_t as = TYPE_ADDR_SPACE (type);

      /* PSTR strings are in generic space but located in flash:
         patch address space.  */

      if (!AVR_TINY && avr_progmem_p (decl, attr) == -1)
        as = ADDR_SPACE_FLASH;

      AVR_SYMBOL_SET_ADDR_SPACE (sym, as);

      tree io_low_attr = lookup_attribute ("io_low", attr);
      tree io_attr = lookup_attribute ("io", attr);

      if (io_low_attr
	  && TREE_VALUE (io_low_attr) && TREE_VALUE (TREE_VALUE (io_low_attr)))
	addr_attr = io_attr;
      else if (io_attr
	       && TREE_VALUE (io_attr) && TREE_VALUE (TREE_VALUE (io_attr)))
	addr_attr = io_attr;
      else
	addr_attr = lookup_attribute ("address", attr);
      if (io_low_attr
	  || (io_attr && addr_attr
              && low_io_address_operand
                  (GEN_INT (TREE_INT_CST_LOW
                            (TREE_VALUE (TREE_VALUE (addr_attr)))), QImode)))
	SYMBOL_REF_FLAGS (sym) |= SYMBOL_FLAG_IO_LOW;
      if (io_attr || io_low_attr)
	SYMBOL_REF_FLAGS (sym) |= SYMBOL_FLAG_IO;
      /* If we have an (io) address attribute specification, but the variable
	 is external, treat the address as only a tentative definition
	 to be used to determine if an io port is in the lower range, but
	 don't use the exact value for constant propagation.  */
      if (addr_attr && !DECL_EXTERNAL (decl))
	SYMBOL_REF_FLAGS (sym) |= SYMBOL_FLAG_ADDRESS;
    }

  if (AVR_TINY
      && decl
      && VAR_DECL == TREE_CODE (decl)
      && MEM_P (rtl)
      && SYMBOL_REF_P (XEXP (rtl, 0)))
    {
      rtx sym = XEXP (rtl, 0);
      bool progmem_p = avr_progmem_p (decl, DECL_ATTRIBUTES (decl)) == -1;

      if (progmem_p)
        {
          // Tag symbols for addition of 0x4000 (avr_arch->flash_pm_offset).
          SYMBOL_REF_FLAGS (sym) |= AVR_SYMBOL_FLAG_TINY_PM;
        }

      if (avr_decl_absdata_p (decl, DECL_ATTRIBUTES (decl))
          || (TARGET_ABSDATA
              && !progmem_p
              && !addr_attr
              && avr_decl_maybe_lds_p (decl))
          || (addr_attr
              // If addr_attr is non-null, it has an argument.  Peek into it.
              && TREE_INT_CST_LOW (TREE_VALUE (TREE_VALUE (addr_attr))) < 0xc0))
        {
          // May be accessed by LDS / STS.
          SYMBOL_REF_FLAGS (sym) |= AVR_SYMBOL_FLAG_TINY_ABSDATA;
        }

      if (progmem_p
          && avr_decl_absdata_p (decl, DECL_ATTRIBUTES (decl)))
        {
          error ("%q+D has incompatible attributes %qs and %qs",
                 decl, "progmem", "absdata");
        }
    }
}


/* Implement `TARGET_ASM_SELECT_SECTION' */

static section *
avr_asm_select_section (tree decl, int reloc, unsigned HOST_WIDE_INT align)
{
  section * sect = default_elf_select_section (decl, reloc, align);

  if (decl && DECL_P (decl)
      && avr_progmem_p (decl, DECL_ATTRIBUTES (decl)))
    {
      addr_space_t as = TYPE_ADDR_SPACE (TREE_TYPE (decl));

      /* __progmem__ goes in generic space but shall be allocated to
         .progmem.data  */

      if (ADDR_SPACE_GENERIC_P (as))
        as = ADDR_SPACE_FLASH;

      if (sect->common.flags & SECTION_NAMED)
        {
          const char * name = sect->named.name;
          const char * old_prefix = ".rodata";
          const char * new_prefix = avr_addrspace[as].section_name;

	  if (startswith (name, old_prefix))
            {
              const char *sname = ACONCAT ((new_prefix,
                                            name + strlen (old_prefix), NULL));
              return get_section (sname,
                                  sect->common.flags & ~SECTION_DECLARED,
                                  sect->named.decl);
            }
        }

      if (!progmem_section[as])
        {
          progmem_section[as]
            = get_unnamed_section (0, avr_output_progmem_section_asm_op,
                                   avr_addrspace[as].section_name);
        }

      return progmem_section[as];
    }

  return sect;
}

/* Implement `TARGET_ASM_FILE_START'.  */
/* Outputs some text at the start of each assembler file.  */

static void
avr_file_start (void)
{
  int sfr_offset = avr_arch->sfr_offset;

  if (avr_arch->asm_only)
    error ("architecture %qs supported for assembler only", avr_mmcu);

  default_file_start ();

  /* Print I/O addresses of some SFRs used with IN and OUT.  */

  if (AVR_HAVE_SPH)
    fprintf (asm_out_file, "__SP_H__ = 0x%02x\n", avr_addr.sp_h - sfr_offset);

  fprintf (asm_out_file, "__SP_L__ = 0x%02x\n", avr_addr.sp_l - sfr_offset);
  fprintf (asm_out_file, "__SREG__ = 0x%02x\n", avr_addr.sreg - sfr_offset);
  if (AVR_HAVE_RAMPZ)
    fprintf (asm_out_file, "__RAMPZ__ = 0x%02x\n", avr_addr.rampz - sfr_offset);
  if (AVR_HAVE_RAMPY)
    fprintf (asm_out_file, "__RAMPY__ = 0x%02x\n", avr_addr.rampy - sfr_offset);
  if (AVR_HAVE_RAMPX)
    fprintf (asm_out_file, "__RAMPX__ = 0x%02x\n", avr_addr.rampx - sfr_offset);
  if (AVR_HAVE_RAMPD)
    fprintf (asm_out_file, "__RAMPD__ = 0x%02x\n", avr_addr.rampd - sfr_offset);
  if (AVR_XMEGA || AVR_TINY)
    fprintf (asm_out_file, "__CCP__ = 0x%02x\n", avr_addr.ccp - sfr_offset);
  fprintf (asm_out_file, "__tmp_reg__ = %d\n", AVR_TMP_REGNO);
  fprintf (asm_out_file, "__zero_reg__ = %d\n", AVR_ZERO_REGNO);
}


/* Implement `TARGET_ASM_FILE_END'.  */
/* Outputs to the stdio stream FILE some
   appropriate text to go at the end of an assembler file.  */

static void
avr_file_end (void)
{
  /* Output these only if there is anything in the
     .data* / .rodata* / .gnu.linkonce.* resp. .bss* or COMMON
     input section(s) - some code size can be saved by not
     linking in the initialization code from libgcc if resp.
     sections are empty, see PR18145.  */

  if (avr_need_copy_data_p)
    fputs (".global __do_copy_data\n", asm_out_file);

  if (avr_need_clear_bss_p)
    fputs (".global __do_clear_bss\n", asm_out_file);
}


/* Worker function for `ADJUST_REG_ALLOC_ORDER'.  */
/* Choose the order in which to allocate hard registers for
   pseudo-registers local to a basic block.

   Store the desired register order in the array `reg_alloc_order'.
   Element 0 should be the register to allocate first; element 1, the
   next register; and so on.  */

void
avr_adjust_reg_alloc_order (void)
{
  static const int order_0[] =
    {
      24, 25,
      18, 19, 20, 21, 22, 23,
      30, 31,
      26, 27, 28, 29,
      17, 16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2,
      0, 1,
      32, 33, 34, 35
    };
  static const int tiny_order_0[] = {
    20, 21,
    22, 23,
    24, 25,
    30, 31,
    26, 27,
    28, 29,
    19, 18,
    16, 17,
    32, 33, 34, 35,
    15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0
  };
  static const int order_1[] =
    {
      18, 19, 20, 21, 22, 23, 24, 25,
      30, 31,
      26, 27, 28, 29,
      17, 16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2,
      0, 1,
      32, 33, 34, 35
    };
  static const int tiny_order_1[] = {
    22, 23,
    24, 25,
    30, 31,
    26, 27,
    28, 29,
    21, 20, 19, 18,
    16, 17,
    32, 33, 34, 35,
    15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0
  };
  static const int order_2[] =
    {
      25, 24, 23, 22, 21, 20, 19, 18,
      30, 31,
      26, 27, 28, 29,
      17, 16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2,
      1, 0,
      32, 33, 34, 35
    };

  /* Select specific register allocation order.
     Tiny Core (ATtiny4/5/9/10/20/40) devices have only 16 registers,
     so different allocation order should be used.  */

  const int *order = (TARGET_ORDER_1 ? (AVR_TINY ? tiny_order_1 : order_1)
                      : TARGET_ORDER_2 ? (AVR_TINY ? tiny_order_0 : order_2)
                      : (AVR_TINY ? tiny_order_0 : order_0));

  for (size_t i = 0; i < ARRAY_SIZE (order_0); ++i)
    reg_alloc_order[i] = order[i];
}


/* Implement `TARGET_REGISTER_MOVE_COST' */

static int
avr_register_move_cost (machine_mode mode ATTRIBUTE_UNUSED,
                        reg_class_t from, reg_class_t to)
{
  return (from == STACK_REG ? 6
          : to == STACK_REG ? 12
          : 2);
}


/* Implement `TARGET_MEMORY_MOVE_COST' */

static int
avr_memory_move_cost (machine_mode mode,
                      reg_class_t rclass ATTRIBUTE_UNUSED,
                      bool in ATTRIBUTE_UNUSED)
{
  return (mode == QImode ? 2
          : mode == HImode ? 4
          : mode == SImode ? 8
          : mode == SFmode ? 8
          : 16);
}


/* Cost for mul highpart.  X is a LSHIFTRT, i.e. the outer TRUNCATE is
   already stripped off.  */

static int
avr_mul_highpart_cost (rtx x, int)
{
  if (AVR_HAVE_MUL
      && LSHIFTRT == GET_CODE (x)
      && MULT == GET_CODE (XEXP (x, 0))
      && CONST_INT_P (XEXP (x, 1)))
    {
      // This is the wider mode.
      machine_mode mode = GET_MODE (x);
  
      // The middle-end might still have PR81444, i.e. it is calling the cost
      // functions with strange modes.  Fix this now by also considering
      // PSImode (should actually be SImode instead).
      if (HImode == mode || PSImode == mode || SImode == mode)
        {
          return COSTS_N_INSNS (2);
        }
    }

  return 10000;
}


/* Mutually recursive subroutine of avr_rtx_cost for calculating the
   cost of an RTX operand given its context.  X is the rtx of the
   operand, MODE is its mode, and OUTER is the rtx_code of this
   operand's parent operator.  */

static int
avr_operand_rtx_cost (rtx x, machine_mode mode, enum rtx_code outer,
		      int opno, bool speed)
{
  enum rtx_code code = GET_CODE (x);
  int total;

  switch (code)
    {
    case REG:
    case SUBREG:
      return 0;

    case CONST_INT:
    case CONST_FIXED:
    case CONST_DOUBLE:
      return COSTS_N_INSNS (GET_MODE_SIZE (mode));

    default:
      break;
    }

  total = 0;
  avr_rtx_costs (x, mode, outer, opno, &total, speed);
  return total;
}

/* Worker function for AVR backend's rtx_cost function.
   X is rtx expression whose cost is to be calculated.
   Return true if the complete cost has been computed.
   Return false if subexpressions should be scanned.
   In either case, *TOTAL contains the cost result.  */

static bool
avr_rtx_costs_1 (rtx x, machine_mode mode, int outer_code,
                 int opno ATTRIBUTE_UNUSED, int *total, bool speed)
{
  enum rtx_code code = GET_CODE (x);
  HOST_WIDE_INT val;

  switch (code)
    {
    case CONST_INT:
    case CONST_FIXED:
    case CONST_DOUBLE:
    case SYMBOL_REF:
    case CONST:
    case LABEL_REF:
      /* Immediate constants are as cheap as registers.  */
      *total = 0;
      return true;

    case MEM:
      *total = COSTS_N_INSNS (GET_MODE_SIZE (mode));
      return true;

    case NEG:
      switch (mode)
	{
	case E_QImode:
	case E_SFmode:
	  *total = COSTS_N_INSNS (1);
	  break;

        case E_HImode:
        case E_PSImode:
        case E_SImode:
          *total = COSTS_N_INSNS (2 * GET_MODE_SIZE (mode) - 1);
          break;

	default:
	  return false;
	}
      *total += avr_operand_rtx_cost (XEXP (x, 0), mode, code, 0, speed);
      return true;

    case ABS:
      switch (mode)
	{
	case E_QImode:
	case E_SFmode:
	  *total = COSTS_N_INSNS (1);
	  break;

	default:
	  return false;
	}
      *total += avr_operand_rtx_cost (XEXP (x, 0), mode, code, 0, speed);
      return true;

    case NOT:
      *total = COSTS_N_INSNS (GET_MODE_SIZE (mode));
      *total += avr_operand_rtx_cost (XEXP (x, 0), mode, code, 0, speed);
      return true;

    case ZERO_EXTEND:
      *total = COSTS_N_INSNS (GET_MODE_SIZE (mode)
			      - GET_MODE_SIZE (GET_MODE (XEXP (x, 0))));
      *total += avr_operand_rtx_cost (XEXP (x, 0), GET_MODE (XEXP (x, 0)),
				      code, 0, speed);
      return true;

    case SIGN_EXTEND:
      *total = COSTS_N_INSNS (GET_MODE_SIZE (mode) + 2
			      - GET_MODE_SIZE (GET_MODE (XEXP (x, 0))));
      *total += avr_operand_rtx_cost (XEXP (x, 0), GET_MODE (XEXP (x, 0)),
				      code, 0, speed);
      return true;

    case PLUS:
      switch (mode)
	{
	case E_QImode:
          if (AVR_HAVE_MUL
              && MULT == GET_CODE (XEXP (x, 0))
              && register_operand (XEXP (x, 1), QImode))
            {
              /* multiply-add */
              *total = COSTS_N_INSNS (speed ? 4 : 3);
              /* multiply-add with constant: will be split and load constant. */
              if (CONST_INT_P (XEXP (XEXP (x, 0), 1)))
                *total = COSTS_N_INSNS (1) + *total;
              return true;
            }
	  *total = COSTS_N_INSNS (1);
	  if (!CONST_INT_P (XEXP (x, 1)))
	    *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1, speed);
	  break;

	case E_HImode:
          if (AVR_HAVE_MUL
              && (MULT == GET_CODE (XEXP (x, 0))
                  || ASHIFT == GET_CODE (XEXP (x, 0)))
              && register_operand (XEXP (x, 1), HImode)
              && (ZERO_EXTEND == GET_CODE (XEXP (XEXP (x, 0), 0))
                  || SIGN_EXTEND == GET_CODE (XEXP (XEXP (x, 0), 0))))
            {
              /* multiply-add */
              *total = COSTS_N_INSNS (speed ? 5 : 4);
              /* multiply-add with constant: will be split and load constant. */
              if (CONST_INT_P (XEXP (XEXP (x, 0), 1)))
                *total = COSTS_N_INSNS (1) + *total;
              return true;
            }
	  if (!CONST_INT_P (XEXP (x, 1)))
	    {
	      *total = COSTS_N_INSNS (2);
	      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
					      speed);
	    }
	  else if (IN_RANGE (INTVAL (XEXP (x, 1)), -63, 63))
	    *total = COSTS_N_INSNS (1);
	  else
	    *total = COSTS_N_INSNS (2);
	  break;

        case E_PSImode:
          if (!CONST_INT_P (XEXP (x, 1)))
            {
              *total = COSTS_N_INSNS (3);
              *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
                                              speed);
            }
          else if (IN_RANGE (INTVAL (XEXP (x, 1)), -63, 63))
            *total = COSTS_N_INSNS (2);
          else
            *total = COSTS_N_INSNS (3);
          break;

	case E_SImode:
	  if (!CONST_INT_P (XEXP (x, 1)))
	    {
	      *total = COSTS_N_INSNS (4);
	      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
					      speed);
	    }
	  else if (IN_RANGE (INTVAL (XEXP (x, 1)), -63, 63))
	    *total = COSTS_N_INSNS (1);
	  else
	    *total = COSTS_N_INSNS (4);
	  break;

	default:
	  return false;
	}
      *total += avr_operand_rtx_cost (XEXP (x, 0), mode, code, 0, speed);
      return true;

    case MINUS:
      if (AVR_HAVE_MUL
          && QImode == mode
          && register_operand (XEXP (x, 0), QImode)
          && MULT == GET_CODE (XEXP (x, 1)))
        {
          /* multiply-sub */
          *total = COSTS_N_INSNS (speed ? 4 : 3);
          /* multiply-sub with constant: will be split and load constant. */
          if (CONST_INT_P (XEXP (XEXP (x, 1), 1)))
            *total = COSTS_N_INSNS (1) + *total;
          return true;
        }
      if (AVR_HAVE_MUL
          && HImode == mode
          && register_operand (XEXP (x, 0), HImode)
          && (MULT == GET_CODE (XEXP (x, 1))
              || ASHIFT == GET_CODE (XEXP (x, 1)))
          && (ZERO_EXTEND == GET_CODE (XEXP (XEXP (x, 1), 0))
              || SIGN_EXTEND == GET_CODE (XEXP (XEXP (x, 1), 0))))
        {
          /* multiply-sub */
          *total = COSTS_N_INSNS (speed ? 5 : 4);
          /* multiply-sub with constant: will be split and load constant. */
          if (CONST_INT_P (XEXP (XEXP (x, 1), 1)))
            *total = COSTS_N_INSNS (1) + *total;
          return true;
        }
      /* FALLTHRU */
    case AND:
    case IOR:
      if (IOR == code
          && HImode == mode
          && ASHIFT == GET_CODE (XEXP (x, 0)))
        {
          *total = COSTS_N_INSNS (2);
          // Just a rough estimate.  If we see no sign- or zero-extend,
          // then increase the cost a little bit.
          if (REG_P (XEXP (XEXP (x, 0), 0)))
            *total += COSTS_N_INSNS (1);
          if (REG_P (XEXP (x, 1)))
            *total += COSTS_N_INSNS (1);
          return true;
        }
      *total = COSTS_N_INSNS (GET_MODE_SIZE (mode));
      *total += avr_operand_rtx_cost (XEXP (x, 0), mode, code, 0, speed);
      if (!CONST_INT_P (XEXP (x, 1)))
	*total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1, speed);
      return true;

    case XOR:
      *total = COSTS_N_INSNS (GET_MODE_SIZE (mode));
      *total += avr_operand_rtx_cost (XEXP (x, 0), mode, code, 0, speed);
      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1, speed);
      return true;

    case MULT:
      switch (mode)
	{
	case E_QImode:
	  if (AVR_HAVE_MUL)
	    *total = COSTS_N_INSNS (!speed ? 3 : 4);
	  else if (!speed)
	    *total = COSTS_N_INSNS (AVR_HAVE_JMP_CALL ? 2 : 1);
	  else
	    return false;
	  break;

	case E_HImode:
	  if (AVR_HAVE_MUL)
            {
              rtx op0 = XEXP (x, 0);
              rtx op1 = XEXP (x, 1);
              enum rtx_code code0 = GET_CODE (op0);
              enum rtx_code code1 = GET_CODE (op1);
              bool ex0 = SIGN_EXTEND == code0 || ZERO_EXTEND == code0;
              bool ex1 = SIGN_EXTEND == code1 || ZERO_EXTEND == code1;

              if (ex0
                  && (u8_operand (op1, HImode)
                      || s8_operand (op1, HImode)))
                {
                  *total = COSTS_N_INSNS (!speed ? 4 : 6);
                  return true;
                }
              if (ex0
                  && register_operand (op1, HImode))
                {
                  *total = COSTS_N_INSNS (!speed ? 5 : 8);
                  return true;
                }
              else if (ex0 || ex1)
                {
                  *total = COSTS_N_INSNS (!speed ? 3 : 5);
                  return true;
                }
              else if (register_operand (op0, HImode)
                       && (u8_operand (op1, HImode)
                           || s8_operand (op1, HImode)))
                {
                  *total = COSTS_N_INSNS (!speed ? 6 : 9);
                  return true;
                }
              else
                *total = COSTS_N_INSNS (!speed ? 7 : 10);
            }
	  else if (!speed)
	    *total = COSTS_N_INSNS (AVR_HAVE_JMP_CALL ? 2 : 1);
	  else
	    return false;
	  break;

        case E_PSImode:
          if (!speed)
            *total = COSTS_N_INSNS (AVR_HAVE_JMP_CALL ? 2 : 1);
          else
            *total = 10;
          break;

	case E_SImode:
	case E_DImode:
	  if (AVR_HAVE_MUL)
            {
              if (!speed)
                {
                  /* Add some additional costs besides CALL like moves etc.  */

                  *total = COSTS_N_INSNS (AVR_HAVE_JMP_CALL ? 5 : 4);
                }
              else
                {
                  /* Just a rough estimate.  Even with -O2 we don't want bulky
                     code expanded inline.  */

                  *total = COSTS_N_INSNS (25);
                }
            }
          else
            {
              if (speed)
                *total = COSTS_N_INSNS (300);
              else
                /* Add some additional costs besides CALL like moves etc.  */
                *total = COSTS_N_INSNS (AVR_HAVE_JMP_CALL ? 5 : 4);
            }

	  if (mode == DImode)
	    *total *= 2;

	  return true;

	default:
	  return false;
	}
      *total += avr_operand_rtx_cost (XEXP (x, 0), mode, code, 0, speed);
      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1, speed);
      return true;

    case DIV:
    case MOD:
    case UDIV:
    case UMOD:
      if (!speed)
        *total = COSTS_N_INSNS (AVR_HAVE_JMP_CALL ? 2 : 1);
      else
        *total = COSTS_N_INSNS (15 * GET_MODE_SIZE (mode));
      *total += avr_operand_rtx_cost (XEXP (x, 0), mode, code, 0, speed);
      /* For div/mod with const-int divisor we have at least the cost of
         loading the divisor. */
      if (CONST_INT_P (XEXP (x, 1)))
        *total += COSTS_N_INSNS (GET_MODE_SIZE (mode));
      /* Add some overall penaly for clobbering and moving around registers */
      *total += COSTS_N_INSNS (2);
      return true;

    case ROTATE:
      switch (mode)
	{
	case E_QImode:
	  if (CONST_INT_P (XEXP (x, 1)) && INTVAL (XEXP (x, 1)) == 4)
	    *total = COSTS_N_INSNS (1);

	  break;

	case E_HImode:
	  if (CONST_INT_P (XEXP (x, 1)) && INTVAL (XEXP (x, 1)) == 8)
	    *total = COSTS_N_INSNS (3);

	  break;

	case E_SImode:
	  if (CONST_INT_P (XEXP (x, 1)))
	    switch (INTVAL (XEXP (x, 1)))
	      {
	      case 8:
	      case 24:
		*total = COSTS_N_INSNS (5);
		break;
	      case 16:
		*total = COSTS_N_INSNS (AVR_HAVE_MOVW ? 4 : 6);
		break;
	      }
	  break;

	default:
	  return false;
	}
      *total += avr_operand_rtx_cost (XEXP (x, 0), mode, code, 0, speed);
      return true;

    case ASHIFT:
      switch (mode)
	{
	case E_QImode:
	  if (!CONST_INT_P (XEXP (x, 1)))
	    {
	      *total = COSTS_N_INSNS (!speed ? 4 : 17);
	      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
					      speed);
	    }
	  else
	    {
	      val = INTVAL (XEXP (x, 1));
	      if (val == 7)
		*total = COSTS_N_INSNS (3);
	      else if (val >= 0 && val <= 7)
		*total = COSTS_N_INSNS (val);
	      else
		*total = COSTS_N_INSNS (1);
	    }
	  break;

	case E_HImode:
          if (AVR_HAVE_MUL)
            {
              if (const_2_to_7_operand (XEXP (x, 1), HImode)
                  && (SIGN_EXTEND == GET_CODE (XEXP (x, 0))
                      || ZERO_EXTEND == GET_CODE (XEXP (x, 0))))
                {
                  *total = COSTS_N_INSNS (!speed ? 4 : 6);
                  return true;
                }
            }

          if (const1_rtx == (XEXP (x, 1))
              && SIGN_EXTEND == GET_CODE (XEXP (x, 0)))
            {
              *total = COSTS_N_INSNS (2);
              return true;
            }

	  if (!CONST_INT_P (XEXP (x, 1)))
	    {
	      *total = COSTS_N_INSNS (!speed ? 5 : 41);
	      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
					      speed);
	    }
	  else
	    switch (INTVAL (XEXP (x, 1)))
	      {
	      case 0:
		*total = 0;
		break;
	      case 1:
	      case 8:
		*total = COSTS_N_INSNS (2);
		break;
	      case 9:
		*total = COSTS_N_INSNS (3);
		break;
	      case 2:
	      case 3:
	      case 10:
	      case 15:
		*total = COSTS_N_INSNS (4);
		break;
	      case 7:
	      case 11:
	      case 12:
		*total = COSTS_N_INSNS (5);
		break;
	      case 4:
		*total = COSTS_N_INSNS (!speed ? 5 : 8);
		break;
	      case 6:
		*total = COSTS_N_INSNS (!speed ? 5 : 9);
		break;
	      case 5:
		*total = COSTS_N_INSNS (!speed ? 5 : 10);
		break;
	      default:
	        *total = COSTS_N_INSNS (!speed ? 5 : 41);
	        *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
						speed);
	      }
	  break;

        case E_PSImode:
          if (!CONST_INT_P (XEXP (x, 1)))
            {
              *total = COSTS_N_INSNS (!speed ? 6 : 73);
            }
          else
            switch (INTVAL (XEXP (x, 1)))
              {
              case 0:
                *total = 0;
                break;
              case 1:
              case 8:
              case 16:
                *total = COSTS_N_INSNS (3);
                break;
              case 23:
                *total = COSTS_N_INSNS (5);
                break;
              default:
                *total = COSTS_N_INSNS (!speed ? 5 : 3 * INTVAL (XEXP (x, 1)));
                break;
              }
          break;

	case E_SImode:
	  if (!CONST_INT_P (XEXP (x, 1)))
	    {
	      *total = COSTS_N_INSNS (!speed ? 7 : 113);
	      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
					      speed);
	    }
	  else
	    switch (INTVAL (XEXP (x, 1)))
	      {
	      case 0:
		*total = 0;
		break;
	      case 24:
		*total = COSTS_N_INSNS (3);
		break;
	      case 1:
	      case 8:
	      case 16:
		*total = COSTS_N_INSNS (4);
		break;
	      case 31:
		*total = COSTS_N_INSNS (6);
		break;
	      case 2:
		*total = COSTS_N_INSNS (!speed ? 7 : 8);
		break;
	      default:
		*total = COSTS_N_INSNS (!speed ? 7 : 113);
		*total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
						speed);
	      }
	  break;

	default:
	  return false;
	}
      *total += avr_operand_rtx_cost (XEXP (x, 0), mode, code, 0, speed);
      return true;

    case ASHIFTRT:
      switch (mode)
	{
	case E_QImode:
	  if (!CONST_INT_P (XEXP (x, 1)))
	    {
	      *total = COSTS_N_INSNS (!speed ? 4 : 17);
	      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
					      speed);
	    }
	  else
	    {
	      val = INTVAL (XEXP (x, 1));
	      if (val == 6)
		*total = COSTS_N_INSNS (4);
	      else if (val == 7)
		*total = COSTS_N_INSNS (2);
	      else if (val >= 0 && val <= 7)
		*total = COSTS_N_INSNS (val);
	      else
		*total = COSTS_N_INSNS (1);
	    }
	  break;

	case E_HImode:
	  if (!CONST_INT_P (XEXP (x, 1)))
	    {
	      *total = COSTS_N_INSNS (!speed ? 5 : 41);
	      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
					      speed);
	    }
	  else
	    switch (INTVAL (XEXP (x, 1)))
	      {
	      case 0:
		*total = 0;
		break;
	      case 1:
		*total = COSTS_N_INSNS (2);
		break;
	      case 15:
		*total = COSTS_N_INSNS (3);
		break;
	      case 2:
	      case 7:
              case 8:
              case 9:
		*total = COSTS_N_INSNS (4);
		break;
              case 10:
	      case 14:
		*total = COSTS_N_INSNS (5);
		break;
              case 11:
                *total = COSTS_N_INSNS (!speed ? 5 : 6);
		break;
              case 12:
                *total = COSTS_N_INSNS (!speed ? 5 : 7);
		break;
              case 6:
	      case 13:
                *total = COSTS_N_INSNS (!speed ? 5 : 8);
		break;
	      default:
	        *total = COSTS_N_INSNS (!speed ? 5 : 41);
	        *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
						speed);
	      }
	  break;

        case E_PSImode:
          if (!CONST_INT_P (XEXP (x, 1)))
            {
              *total = COSTS_N_INSNS (!speed ? 6 : 73);
            }
          else
            switch (INTVAL (XEXP (x, 1)))
              {
              case 0:
                *total = 0;
                break;
              case 1:
                *total = COSTS_N_INSNS (3);
                break;
              case 16:
              case 8:
                *total = COSTS_N_INSNS (5);
                break;
              case 23:
                *total = COSTS_N_INSNS (4);
                break;
              default:
                *total = COSTS_N_INSNS (!speed ? 5 : 3 * INTVAL (XEXP (x, 1)));
                break;
              }
          break;

	case E_SImode:
	  if (!CONST_INT_P (XEXP (x, 1)))
	    {
	      *total = COSTS_N_INSNS (!speed ? 7 : 113);
	      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
					      speed);
	    }
	  else
	    switch (INTVAL (XEXP (x, 1)))
	      {
	      case 0:
		*total = 0;
		break;
	      case 1:
		*total = COSTS_N_INSNS (4);
		break;
	      case 8:
	      case 16:
	      case 24:
		*total = COSTS_N_INSNS (6);
		break;
	      case 2:
		*total = COSTS_N_INSNS (!speed ? 7 : 8);
		break;
	      case 31:
		*total = COSTS_N_INSNS (AVR_HAVE_MOVW ? 4 : 5);
		break;
	      default:
		*total = COSTS_N_INSNS (!speed ? 7 : 113);
		*total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
						speed);
	      }
	  break;

	default:
	  return false;
	}
      *total += avr_operand_rtx_cost (XEXP (x, 0), mode, code, 0, speed);
      return true;

    case LSHIFTRT:
      if (outer_code == TRUNCATE)
        {
          *total = avr_mul_highpart_cost (x, speed);
          return true;
        }

      switch (mode)
	{
	case E_QImode:
	  if (!CONST_INT_P (XEXP (x, 1)))
	    {
	      *total = COSTS_N_INSNS (!speed ? 4 : 17);
	      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
					      speed);
	    }
	  else
	    {
	      val = INTVAL (XEXP (x, 1));
	      if (val == 7)
		*total = COSTS_N_INSNS (3);
	      else if (val >= 0 && val <= 7)
		*total = COSTS_N_INSNS (val);
	      else
		*total = COSTS_N_INSNS (1);
	    }
	  break;

	case E_HImode:
	  if (!CONST_INT_P (XEXP (x, 1)))
	    {
	      *total = COSTS_N_INSNS (!speed ? 5 : 41);
	      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
					      speed);
	    }
	  else
	    switch (INTVAL (XEXP (x, 1)))
	      {
	      case 0:
		*total = 0;
		break;
	      case 1:
	      case 8:
		*total = COSTS_N_INSNS (2);
		break;
	      case 9:
		*total = COSTS_N_INSNS (3);
		break;
	      case 2:
	      case 10:
	      case 15:
		*total = COSTS_N_INSNS (4);
		break;
	      case 7:
              case 11:
		*total = COSTS_N_INSNS (5);
		break;
	      case 3:
	      case 12:
	      case 13:
	      case 14:
		*total = COSTS_N_INSNS (!speed ? 5 : 6);
		break;
	      case 4:
		*total = COSTS_N_INSNS (!speed ? 5 : 7);
		break;
	      case 5:
	      case 6:
		*total = COSTS_N_INSNS (!speed ? 5 : 9);
		break;
	      default:
	        *total = COSTS_N_INSNS (!speed ? 5 : 41);
	        *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
						speed);
	      }
	  break;

        case E_PSImode:
          if (!CONST_INT_P (XEXP (x, 1)))
            {
              *total = COSTS_N_INSNS (!speed ? 6 : 73);
            }
          else
            switch (INTVAL (XEXP (x, 1)))
              {
              case 0:
                *total = 0;
                break;
              case 1:
              case 8:
              case 16:
                *total = COSTS_N_INSNS (3);
                break;
              case 23:
                *total = COSTS_N_INSNS (5);
                break;
              default:
                *total = COSTS_N_INSNS (!speed ? 5 : 3 * INTVAL (XEXP (x, 1)));
                break;
              }
          break;

	case E_SImode:
	  if (!CONST_INT_P (XEXP (x, 1)))
	    {
	      *total = COSTS_N_INSNS (!speed ? 7 : 113);
	      *total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
					      speed);
	    }
	  else
	    switch (INTVAL (XEXP (x, 1)))
	      {
	      case 0:
		*total = 0;
		break;
	      case 1:
		*total = COSTS_N_INSNS (4);
		break;
	      case 2:
		*total = COSTS_N_INSNS (!speed ? 7 : 8);
		break;
	      case 8:
	      case 16:
	      case 24:
		*total = COSTS_N_INSNS (4);
		break;
	      case 31:
		*total = COSTS_N_INSNS (6);
		break;
	      default:
		*total = COSTS_N_INSNS (!speed ? 7 : 113);
		*total += avr_operand_rtx_cost (XEXP (x, 1), mode, code, 1,
						speed);
	      }
	  break;

	default:
	  return false;
	}
      *total += avr_operand_rtx_cost (XEXP (x, 0), mode, code, 0, speed);
      return true;

    case COMPARE:
      switch (GET_MODE (XEXP (x, 0)))
	{
	case E_QImode:
	  *total = COSTS_N_INSNS (1);
	  if (!CONST_INT_P (XEXP (x, 1)))
	    *total += avr_operand_rtx_cost (XEXP (x, 1), QImode, code,
					    1, speed);
	  break;

        case E_HImode:
	  *total = COSTS_N_INSNS (2);
	  if (!CONST_INT_P (XEXP (x, 1)))
            *total += avr_operand_rtx_cost (XEXP (x, 1), HImode, code,
					    1, speed);
	  else if (INTVAL (XEXP (x, 1)) != 0)
	    *total += COSTS_N_INSNS (1);
          break;

        case E_PSImode:
          *total = COSTS_N_INSNS (3);
          if (CONST_INT_P (XEXP (x, 1)) && INTVAL (XEXP (x, 1)) != 0)
            *total += COSTS_N_INSNS (2);
          break;

        case E_SImode:
          *total = COSTS_N_INSNS (4);
          if (!CONST_INT_P (XEXP (x, 1)))
            *total += avr_operand_rtx_cost (XEXP (x, 1), SImode, code,
					    1, speed);
	  else if (INTVAL (XEXP (x, 1)) != 0)
	    *total += COSTS_N_INSNS (3);
          break;

	default:
	  return false;
	}
      *total += avr_operand_rtx_cost (XEXP (x, 0), GET_MODE (XEXP (x, 0)),
				      code, 0, speed);
      return true;

    case TRUNCATE:
      if (LSHIFTRT == GET_CODE (XEXP (x, 0)))
        {
          *total = avr_mul_highpart_cost (XEXP (x, 0), speed);
          return true;
        }
      break;

    default:
      break;
    }
  return false;
}


/* Implement `TARGET_RTX_COSTS'.  */

static bool
avr_rtx_costs (rtx x, machine_mode mode, int outer_code,
	       int opno, int *total, bool speed)
{
  bool done = avr_rtx_costs_1 (x, mode, outer_code, opno, total, speed);

  if (avr_log.rtx_costs)
    {
      avr_edump ("\n%?=%b (%s) total=%d, outer=%C:\n%r\n",
                 done, speed ? "speed" : "size", *total, outer_code, x);
    }

  return done;
}


/* Implement `TARGET_ADDRESS_COST'.  */

static int
avr_address_cost (rtx x, machine_mode mode ATTRIBUTE_UNUSED,
                  addr_space_t as ATTRIBUTE_UNUSED,
                  bool speed ATTRIBUTE_UNUSED)
{
  int cost = 4;

  if (GET_CODE (x) == PLUS
      && CONST_INT_P (XEXP (x, 1))
      && (REG_P (XEXP (x, 0))
          || SUBREG_P (XEXP (x, 0))))
    {
      if (INTVAL (XEXP (x, 1)) > MAX_LD_OFFSET(mode))
        cost = 18;
    }
  else if (CONSTANT_ADDRESS_P (x))
    {
      if (io_address_operand (x, QImode))
        cost = 2;

      if (AVR_TINY
          && avr_address_tiny_absdata_p (x, QImode))
        cost = 2;
    }

  if (avr_log.address_cost)
    avr_edump ("\n%?: %d = %r\n", cost, x);

  return cost;
}

/* Test for extra memory constraint 'Q'.
   It's a memory address based on Y or Z pointer with valid displacement.  */

int
extra_constraint_Q (rtx x)
{
  int ok = 0;
  rtx plus = XEXP (x, 0);

  if (GET_CODE (plus) == PLUS
      && REG_P (XEXP (plus, 0))
      && CONST_INT_P (XEXP (plus, 1))
      && (INTVAL (XEXP (plus, 1))
	  <= MAX_LD_OFFSET (GET_MODE (x))))
    {
      rtx xx = XEXP (plus, 0);
      int regno = REGNO (xx);

      ok = (/* allocate pseudos */
            regno >= FIRST_PSEUDO_REGISTER
            /* strictly check */
            || regno == REG_Z || regno == REG_Y
            /* XXX frame & arg pointer checks */
            || xx == frame_pointer_rtx
            || xx == arg_pointer_rtx);

      if (avr_log.constraints)
        avr_edump ("\n%?=%d reload_completed=%d reload_in_progress=%d\n %r\n",
                   ok, reload_completed, reload_in_progress, x);
    }

  return ok;
}

/* Convert condition code CONDITION to the valid AVR condition code.  */

RTX_CODE
avr_normalize_condition (RTX_CODE condition)
{
  switch (condition)
    {
    case GT:
      return GE;
    case GTU:
      return GEU;
    case LE:
      return LT;
    case LEU:
      return LTU;
    default:
      gcc_unreachable ();
    }
}

/* Helper function for `avr_reorg'.  */

static rtx
avr_compare_pattern (rtx_insn *insn)
{
  rtx pattern = single_set (insn);

  if (pattern
      && NONJUMP_INSN_P (insn)
      && REG_P (SET_DEST (pattern))
      && REGNO (SET_DEST (pattern)) == REG_CC
      && GET_CODE (SET_SRC (pattern)) == COMPARE)
    {
      machine_mode mode0 = GET_MODE (XEXP (SET_SRC (pattern), 0));
      machine_mode mode1 = GET_MODE (XEXP (SET_SRC (pattern), 1));

      /* The 64-bit comparisons have fixed operands ACC_A and ACC_B.
         They must not be swapped, thus skip them.  */

      if ((mode0 == VOIDmode || GET_MODE_SIZE (mode0) <= 4)
          && (mode1 == VOIDmode || GET_MODE_SIZE (mode1) <= 4))
        return pattern;
    }

  return NULL_RTX;
}

/* Helper function for `avr_reorg'.  */

/* Expansion of switch/case decision trees leads to code like

       REG_CC = compare (Reg, Num)
       if (REG_CC == 0)
         goto L1

       REG_CC = compare (Reg, Num)
       if (REG_CC > 0)
         goto L2

   The second comparison is superfluous and can be deleted.
   The second jump condition can be transformed from a
   "difficult" one to a "simple" one because "REG_CC > 0" and
   "REG_CC >= 0" will have the same effect here.

   This function relies on the way switch/case is being expaned
   as binary decision tree.  For example code see PR 49903.

   Return TRUE if optimization performed.
   Return FALSE if nothing changed.

   INSN1 is a comparison, i.e. avr_compare_pattern != 0.

   We don't want to do this in text peephole because it is
   tedious to work out jump offsets there and the second comparison
   might have been transormed by `avr_reorg'.

   RTL peephole won't do because peephole2 does not scan across
   basic blocks.  */

static bool
avr_reorg_remove_redundant_compare (rtx_insn *insn1)
{
  rtx comp1, ifelse1, xcond1;
  rtx_insn *branch1;
  rtx comp2, ifelse2, xcond2;
  rtx_insn *branch2, *insn2;
  enum rtx_code code;
  rtx_insn *jump;
  rtx target, cond;

  /* Look out for:  compare1 - branch1 - compare2 - branch2  */

  branch1 = next_nonnote_nondebug_insn (insn1);
  if (!branch1 || !JUMP_P (branch1))
    return false;

  insn2 = next_nonnote_nondebug_insn (branch1);
  if (!insn2 || !avr_compare_pattern (insn2))
    return false;

  branch2 = next_nonnote_nondebug_insn (insn2);
  if (!branch2 || !JUMP_P (branch2))
    return false;

  comp1 = avr_compare_pattern (insn1);
  comp2 = avr_compare_pattern (insn2);
  xcond1 = single_set (branch1);
  xcond2 = single_set (branch2);

  if (!comp1 || !comp2
      || !rtx_equal_p (comp1, comp2)
      || !xcond1 || SET_DEST (xcond1) != pc_rtx
      || !xcond2 || SET_DEST (xcond2) != pc_rtx
      || IF_THEN_ELSE != GET_CODE (SET_SRC (xcond1))
      || IF_THEN_ELSE != GET_CODE (SET_SRC (xcond2)))
    {
      return false;
    }

  comp1 = SET_SRC (comp1);
  ifelse1 = SET_SRC (xcond1);
  ifelse2 = SET_SRC (xcond2);

  /* comp<n> is COMPARE now and ifelse<n> is IF_THEN_ELSE.  */

  if (EQ != GET_CODE (XEXP (ifelse1, 0))
      || !REG_P (XEXP (comp1, 0))
      || !CONST_INT_P (XEXP (comp1, 1))
      || XEXP (ifelse1, 2) != pc_rtx
      || XEXP (ifelse2, 2) != pc_rtx
      || LABEL_REF != GET_CODE (XEXP (ifelse1, 1))
      || LABEL_REF != GET_CODE (XEXP (ifelse2, 1))
      || !COMPARISON_P (XEXP (ifelse2, 0))
      || REG_CC != REGNO (XEXP (XEXP (ifelse1, 0), 0))
      || REG_CC != REGNO (XEXP (XEXP (ifelse2, 0), 0))
      || const0_rtx != XEXP (XEXP (ifelse1, 0), 1)
      || const0_rtx != XEXP (XEXP (ifelse2, 0), 1))
    {
      return false;
    }

  /* We filtered the insn sequence to look like

        (set (reg:CC cc)
             (compare (reg:M N)
                      (const_int VAL)))
        (set (pc)
             (if_then_else (eq (reg:CC cc)
                               (const_int 0))
                           (label_ref L1)
                           (pc)))

        (set (reg:CC cc)
             (compare (reg:M N)
                      (const_int VAL)))
        (set (pc)
             (if_then_else (CODE (reg:CC cc)
                                 (const_int 0))
                           (label_ref L2)
                           (pc)))
  */

  code = GET_CODE (XEXP (ifelse2, 0));

  /* Map GT/GTU to GE/GEU which is easier for AVR.
     The first two instructions compare/branch on EQ
     so we may replace the difficult

        if (x == VAL)   goto L1;
        if (x > VAL)    goto L2;

     with easy

         if (x == VAL)   goto L1;
         if (x >= VAL)   goto L2;

     Similarly, replace LE/LEU by LT/LTU.  */

  switch (code)
    {
    case EQ:
    case LT:  case LTU:
    case GE:  case GEU:
      break;

    case LE:  case LEU:
    case GT:  case GTU:
      code = avr_normalize_condition (code);
      break;

    default:
      return false;
    }

  /* Wrap the branches into UNSPECs so they won't be changed or
     optimized in the remainder.  */

  target = XEXP (XEXP (ifelse1, 1), 0);
  cond = XEXP (ifelse1, 0);
  jump = emit_jump_insn_after (gen_branch_unspec (target, cond), insn1);

  JUMP_LABEL (jump) = JUMP_LABEL (branch1);

  target = XEXP (XEXP (ifelse2, 1), 0);
  cond = gen_rtx_fmt_ee (code, VOIDmode, cc_reg_rtx, const0_rtx);
  jump = emit_jump_insn_after (gen_branch_unspec (target, cond), insn2);

  JUMP_LABEL (jump) = JUMP_LABEL (branch2);

  /* The comparisons in insn1 and insn2 are exactly the same;
     insn2 is superfluous so delete it.  */

  delete_insn (insn2);
  delete_insn (branch1);
  delete_insn (branch2);

  return true;
}


/* Implement `TARGET_MACHINE_DEPENDENT_REORG'.  */
/* Optimize conditional jumps.  */

static void
avr_reorg (void)
{
  rtx_insn *insn = get_insns();

  for (insn = next_real_insn (insn); insn; insn = next_real_insn (insn))
    {
      rtx pattern = avr_compare_pattern (insn);

      if (!pattern)
        continue;

      if (optimize
          && avr_reorg_remove_redundant_compare (insn))
        {
          continue;
        }

      if (compare_diff_p (insn))
	{
          /* Now we work under compare insn with difficult branch.  */

	  rtx_insn *next = next_real_insn (insn);
          rtx pat = PATTERN (next);
          if (GET_CODE (pat) == PARALLEL)
            pat = XVECEXP (pat, 0, 0);

          pattern = SET_SRC (pattern);

          if (true_regnum (XEXP (pattern, 0)) >= 0
              && true_regnum (XEXP (pattern, 1)) >= 0)
            {
              rtx x = XEXP (pattern, 0);
              rtx src = SET_SRC (pat);
              rtx t = XEXP (src, 0);
              PUT_CODE (t, swap_condition (GET_CODE (t)));
              XEXP (pattern, 0) = XEXP (pattern, 1);
              XEXP (pattern, 1) = x;
              INSN_CODE (next) = -1;
            }
          else if (true_regnum (XEXP (pattern, 0)) >= 0
                   && XEXP (pattern, 1) == const0_rtx)
            {
              /* This is a tst insn, we can reverse it.  */
              rtx src = SET_SRC (pat);
              rtx t = XEXP (src, 0);

              PUT_CODE (t, swap_condition (GET_CODE (t)));
              XEXP (pattern, 1) = XEXP (pattern, 0);
              XEXP (pattern, 0) = const0_rtx;
              INSN_CODE (next) = -1;
              INSN_CODE (insn) = -1;
            }
          else if (true_regnum (XEXP (pattern, 0)) >= 0
                   && CONST_INT_P (XEXP (pattern, 1)))
            {
              rtx x = XEXP (pattern, 1);
              rtx src = SET_SRC (pat);
              rtx t = XEXP (src, 0);
              machine_mode mode = GET_MODE (XEXP (pattern, 0));

              if (avr_simplify_comparison_p (mode, GET_CODE (t), x))
                {
                  XEXP (pattern, 1) = gen_int_mode (INTVAL (x) + 1, mode);
                  PUT_CODE (t, avr_normalize_condition (GET_CODE (t)));
                  INSN_CODE (next) = -1;
                  INSN_CODE (insn) = -1;
                }
            }
        }
    }
}

/* Returns register number for function return value.*/

static inline unsigned int
avr_ret_register (void)
{
  return 24;
}


/* Implement `TARGET_FUNCTION_VALUE_REGNO_P'.  */

static bool
avr_function_value_regno_p (const unsigned int regno)
{
  return (regno == avr_ret_register ());
}


/* Implement `TARGET_LIBCALL_VALUE'.  */
/* Create an RTX representing the place where a
   library function returns a value of mode MODE.  */

static rtx
avr_libcall_value (machine_mode mode,
		   const_rtx func ATTRIBUTE_UNUSED)
{
  int offs = GET_MODE_SIZE (mode);

  if (offs <= 4)
    offs = (offs + 1) & ~1;

  return gen_rtx_REG (mode, avr_ret_register () + 2 - offs);
}


/* Implement `TARGET_FUNCTION_VALUE'.  */
/* Create an RTX representing the place where a
   function returns a value of data type VALTYPE.  */

static rtx
avr_function_value (const_tree type,
                    const_tree fn_decl_or_type ATTRIBUTE_UNUSED,
                    bool outgoing ATTRIBUTE_UNUSED)
{
  unsigned int offs;

  if (TYPE_MODE (type) != BLKmode)
    return avr_libcall_value (TYPE_MODE (type), NULL_RTX);

  offs = int_size_in_bytes (type);
  if (offs < 2)
    offs = 2;
  if (offs > 2 && offs < GET_MODE_SIZE (SImode))
    offs = GET_MODE_SIZE (SImode);
  else if (offs > GET_MODE_SIZE (SImode) && offs < GET_MODE_SIZE (DImode))
    offs = GET_MODE_SIZE (DImode);

  return gen_rtx_REG (BLKmode, avr_ret_register () + 2 - offs);
}

int
test_hard_reg_class (enum reg_class rclass, rtx x)
{
  int regno = true_regnum (x);
  if (regno < 0)
    return 0;

  if (TEST_HARD_REG_CLASS (rclass, regno))
    return 1;

  return 0;
}


/* Helper for jump_over_one_insn_p:  Test if INSN is a 2-word instruction
   and thus is suitable to be skipped by CPSE, SBRC, etc.  */

static bool
avr_2word_insn_p (rtx_insn *insn)
{
  if (TARGET_SKIP_BUG || !insn || get_attr_length (insn) != 2)
    {
      return false;
    }

  switch (INSN_CODE (insn))
    {
    default:
      return false;

    case CODE_FOR_movqi_insn:
    case CODE_FOR_movuqq_insn:
    case CODE_FOR_movqq_insn:
      {
        rtx set  = single_set (insn);
        rtx src  = SET_SRC (set);
        rtx dest = SET_DEST (set);

        /* Factor out LDS and STS from movqi_insn.  */

        if (MEM_P (dest)
            && (REG_P (src) || src == CONST0_RTX (GET_MODE (dest))))
          {
            return CONSTANT_ADDRESS_P (XEXP (dest, 0));
          }
        else if (REG_P (dest)
                 && MEM_P (src))
          {
            return CONSTANT_ADDRESS_P (XEXP (src, 0));
          }

        return false;
      }

    case CODE_FOR_call_insn:
    case CODE_FOR_call_value_insn:
      return true;
    }
}


int
jump_over_one_insn_p (rtx_insn *insn, rtx dest)
{
  int uid = INSN_UID (GET_CODE (dest) == LABEL_REF
		      ? XEXP (dest, 0)
		      : dest);
  int jump_addr = INSN_ADDRESSES (INSN_UID (insn));
  int dest_addr = INSN_ADDRESSES (uid);
  int jump_offset = dest_addr - jump_addr - get_attr_length (insn);

  return (jump_offset == 1
          || (jump_offset == 2
              && avr_2word_insn_p (next_active_insn (insn))));
}

/* Implement TARGET_HARD_REGNO_NREGS. CCmode is four units for historical
   reasons. If this hook is not defined, TARGET_HARD_REGNO_NREGS
   reports that CCmode requires four registers.
   Define this hook to allow CCmode to fit in a single REG_CC. For
   other modes and regs, return the number of words in mode (i.e whatever
   the default implementation of the hook returned). */

static unsigned int
avr_hard_regno_nregs (unsigned int regno, machine_mode mode)
{
  if (regno == REG_CC && mode == CCmode)
    return 1;

  return CEIL (GET_MODE_SIZE (mode), UNITS_PER_WORD);
}


/* Implement TARGET_HARD_REGNO_MODE_OK.  On the enhanced core, anything
   larger than 1 byte must start in even numbered register for "movw" to
   work (this way we don't have to check for odd registers everywhere).  */

static bool
avr_hard_regno_mode_ok (unsigned int regno, machine_mode mode)
{
  if (regno == REG_CC)
    return mode == CCmode;

  /* NOTE: 8-bit values must not be disallowed for R28 or R29.
        Disallowing QI et al. in these regs might lead to code like
            (set (subreg:QI (reg:HI 28) n) ...)
        which will result in wrong code because reload does not
        handle SUBREGs of hard regsisters like this.
        This could be fixed in reload.  However, it appears
        that fixing reload is not wanted by reload people.  */

  /* Any GENERAL_REGS register can hold 8-bit values.  */

  if (GET_MODE_SIZE (mode) == 1)
    return true;

  /* FIXME: Ideally, the following test is not needed.
        However, it turned out that it can reduce the number
        of spill fails.  AVR and it's poor endowment with
        address registers is extreme stress test for reload.  */

  if (GET_MODE_SIZE (mode) >= 4
      && regno >= REG_X)
    return false;

  /* All modes larger than 8 bits should start in an even register.  */

  return !(regno & 1);
}


/* Implement TARGET_HARD_REGNO_CALL_PART_CLOBBERED.  */

static bool
avr_hard_regno_call_part_clobbered (unsigned, unsigned regno,
				    machine_mode mode)
{
  /* FIXME: This hook gets called with MODE:REGNO combinations that don't
        represent valid hard registers like, e.g. HI:29.  Returning TRUE
        for such registers can lead to performance degradation as mentioned
        in PR53595.  Thus, report invalid hard registers as FALSE.  */

  if (!avr_hard_regno_mode_ok (regno, mode))
    return 0;

  /* Return true if any of the following boundaries is crossed:
     17/18 or 19/20 (if AVR_TINY), 27/28 and 29/30.  */

  return ((regno <= LAST_CALLEE_SAVED_REG
           && regno + GET_MODE_SIZE (mode) > 1 + LAST_CALLEE_SAVED_REG)
          || (regno < REG_Y && regno + GET_MODE_SIZE (mode) > REG_Y)
          || (regno < REG_Z && regno + GET_MODE_SIZE (mode) > REG_Z));
}


/* Implement `MODE_CODE_BASE_REG_CLASS'.  */

enum reg_class
avr_mode_code_base_reg_class (machine_mode mode ATTRIBUTE_UNUSED,
                              addr_space_t as, RTX_CODE outer_code,
                              RTX_CODE index_code ATTRIBUTE_UNUSED)
{
  if (!ADDR_SPACE_GENERIC_P (as))
    {
      return POINTER_Z_REGS;
    }

  if (!avr_strict_X)
    return reload_completed ? BASE_POINTER_REGS : POINTER_REGS;

  return PLUS == outer_code ? BASE_POINTER_REGS : POINTER_REGS;
}


/* Implement `REGNO_MODE_CODE_OK_FOR_BASE_P'.  */

bool
avr_regno_mode_code_ok_for_base_p (int regno,
                                   machine_mode mode ATTRIBUTE_UNUSED,
                                   addr_space_t as ATTRIBUTE_UNUSED,
                                   RTX_CODE outer_code,
                                   RTX_CODE index_code ATTRIBUTE_UNUSED)
{
  bool ok = false;

  if (!ADDR_SPACE_GENERIC_P (as))
    {
      if (regno < FIRST_PSEUDO_REGISTER
          && regno == REG_Z)
        {
          return true;
        }

      if (reg_renumber)
        {
          regno = reg_renumber[regno];

          if (regno == REG_Z)
            {
              return true;
            }
        }

      return false;
    }

  if (regno < FIRST_PSEUDO_REGISTER
      && (regno == REG_X
          || regno == REG_Y
          || regno == REG_Z
          || regno == ARG_POINTER_REGNUM))
    {
      ok = true;
    }
  else if (reg_renumber)
    {
      regno = reg_renumber[regno];

      if (regno == REG_X
          || regno == REG_Y
          || regno == REG_Z
          || regno == ARG_POINTER_REGNUM)
        {
          ok = true;
        }
    }

  if (avr_strict_X
      && PLUS == outer_code
      && regno == REG_X)
    {
      ok = false;
    }

  return ok;
}


/* A helper for `output_reload_insisf' and `output_reload_inhi'.  */
/* Set 32-bit register OP[0] to compile-time constant OP[1].
   CLOBBER_REG is a QI clobber register or NULL_RTX.
   LEN == NULL: output instructions.
   LEN != NULL: set *LEN to the length of the instruction sequence
                (in words) printed with LEN = NULL.
   If CLEAR_P is true, OP[0] had been cleard to Zero already.
   If CLEAR_P is false, nothing is known about OP[0].

   The effect on cc0 is as follows:

   Load 0 to any register except ZERO_REG : NONE
   Load ld register with any value        : NONE
   Anything else:                         : CLOBBER  */

static void
output_reload_in_const (rtx *op, rtx clobber_reg, int *len, bool clear_p)
{
  rtx src = op[1];
  rtx dest = op[0];
  rtx xval, xdest[4];
  int ival[4];
  int clobber_val = 1234;
  bool cooked_clobber_p = false;
  bool set_p = false;
  machine_mode mode = GET_MODE (dest);
  int n_bytes = GET_MODE_SIZE (mode);

  gcc_assert (REG_P (dest)
              && CONSTANT_P (src));

  if (len)
    *len = 0;

  /* (REG:SI 14) is special: It's neither in LD_REGS nor in NO_LD_REGS
     but has some subregs that are in LD_REGS.  Use the MSB (REG:QI 17).  */

  if (REGNO (dest) < 16
      && REGNO (dest) + GET_MODE_SIZE (mode) > 16)
    {
      clobber_reg = all_regs_rtx[REGNO (dest) + n_bytes - 1];
    }

  /* We might need a clobber reg but don't have one.  Look at the value to
     be loaded more closely.  A clobber is only needed if it is a symbol
     or contains a byte that is neither 0, -1 or a power of 2.  */

  if (NULL_RTX == clobber_reg
      && !test_hard_reg_class (LD_REGS, dest)
      && (! (CONST_INT_P (src) || CONST_FIXED_P (src) || CONST_DOUBLE_P (src))
          || !avr_popcount_each_byte (src, n_bytes,
                                      (1 << 0) | (1 << 1) | (1 << 8))))
    {
      /* We have no clobber register but need one.  Cook one up.
         That's cheaper than loading from constant pool.  */

      cooked_clobber_p = true;
      clobber_reg = all_regs_rtx[REG_Z + 1];
      avr_asm_len ("mov __tmp_reg__,%0", &clobber_reg, len, 1);
    }

  /* Now start filling DEST from LSB to MSB.  */

  for (int n = 0; n < n_bytes; n++)
    {
      int ldreg_p;
      bool done_byte = false;
      rtx xop[3];

      /* Crop the n-th destination byte.  */

      xdest[n] = simplify_gen_subreg (QImode, dest, mode, n);
      ldreg_p = test_hard_reg_class (LD_REGS, xdest[n]);

      if (!CONST_INT_P (src)
          && !CONST_FIXED_P (src)
          && !CONST_DOUBLE_P (src))
        {
          static const char* const asm_code[][2] =
            {
              { "ldi %2,lo8(%1)"  CR_TAB "mov %0,%2",    "ldi %0,lo8(%1)"  },
              { "ldi %2,hi8(%1)"  CR_TAB "mov %0,%2",    "ldi %0,hi8(%1)"  },
              { "ldi %2,hlo8(%1)" CR_TAB "mov %0,%2",    "ldi %0,hlo8(%1)" },
              { "ldi %2,hhi8(%1)" CR_TAB "mov %0,%2",    "ldi %0,hhi8(%1)" }
            };

          xop[0] = xdest[n];
          xop[1] = src;
          xop[2] = clobber_reg;

          avr_asm_len (asm_code[n][ldreg_p], xop, len, ldreg_p ? 1 : 2);

          continue;
        }

      /* Crop the n-th source byte.  */

      xval = simplify_gen_subreg (QImode, src, mode, n);
      ival[n] = INTVAL (xval);

      /* Look if we can reuse the low word by means of MOVW.  */

      if (n == 2
          && n_bytes >= 4
          && AVR_HAVE_MOVW)
        {
          rtx lo16 = simplify_gen_subreg (HImode, src, mode, 0);
          rtx hi16 = simplify_gen_subreg (HImode, src, mode, 2);

          if (INTVAL (lo16) == INTVAL (hi16))
            {
	      if (INTVAL (lo16) != 0 || !clear_p)
		avr_asm_len ("movw %C0,%A0", &op[0], len, 1);

              break;
            }
        }

      /* Don't use CLR so that cc0 is set as expected.  */

      if (ival[n] == 0)
        {
          if (!clear_p)
            avr_asm_len (ldreg_p ? "ldi %0,0"
                         : AVR_ZERO_REGNO == REGNO (xdest[n]) ? "clr %0"
                         : "mov %0,__zero_reg__",
                         &xdest[n], len, 1);
          continue;
        }

      if (clobber_val == ival[n]
          && REGNO (clobber_reg) == REGNO (xdest[n]))
        {
          continue;
        }

      /* LD_REGS can use LDI to move a constant value */

      if (ldreg_p)
        {
          xop[0] = xdest[n];
          xop[1] = xval;
          avr_asm_len ("ldi %0,lo8(%1)", xop, len, 1);
          continue;
        }

      /* Try to reuse value already loaded in some lower byte. */

      for (int j = 0; j < n; j++)
        if (ival[j] == ival[n])
          {
            xop[0] = xdest[n];
            xop[1] = xdest[j];

            avr_asm_len ("mov %0,%1", xop, len, 1);
            done_byte = true;
            break;
          }

      if (done_byte)
        continue;

      /* Need no clobber reg for -1: Use CLR/DEC */

      if (ival[n] == -1)
        {
          if (!clear_p)
            avr_asm_len ("clr %0", &xdest[n], len, 1);

          avr_asm_len ("dec %0", &xdest[n], len, 1);
          continue;
        }
      else if (ival[n] == 1)
        {
          if (!clear_p)
            avr_asm_len ("clr %0", &xdest[n], len, 1);

          avr_asm_len ("inc %0", &xdest[n], len, 1);
          continue;
        }

      /* Use T flag or INC to manage powers of 2 if we have
         no clobber reg.  */

      if (NULL_RTX == clobber_reg
          && single_one_operand (xval, QImode))
        {
          xop[0] = xdest[n];
          xop[1] = GEN_INT (exact_log2 (ival[n] & GET_MODE_MASK (QImode)));

          gcc_assert (constm1_rtx != xop[1]);

          if (!set_p)
            {
              set_p = true;
              avr_asm_len ("set", xop, len, 1);
            }

          if (!clear_p)
            avr_asm_len ("clr %0", xop, len, 1);

          avr_asm_len ("bld %0,%1", xop, len, 1);
          continue;
        }

      /* We actually need the LD_REGS clobber reg.  */

      gcc_assert (NULL_RTX != clobber_reg);

      xop[0] = xdest[n];
      xop[1] = xval;
      xop[2] = clobber_reg;
      clobber_val = ival[n];

      avr_asm_len ("ldi %2,lo8(%1)" CR_TAB
                   "mov %0,%2", xop, len, 2);
    }

  /* If we cooked up a clobber reg above, restore it.  */

  if (cooked_clobber_p)
    {
      avr_asm_len ("mov %0,__tmp_reg__", &clobber_reg, len, 1);
    }
}


/* Reload the constant OP[1] into the HI register OP[0].
   CLOBBER_REG is a QI clobber reg needed to move vast majority of consts
   into a NO_LD_REGS register.  If CLOBBER_REG is NULL_RTX we either don't
   need a clobber reg or have to cook one up.

   PLEN == NULL: Output instructions.
   PLEN != NULL: Output nothing.  Set *PLEN to number of words occupied
                 by the insns printed.

   Return "".  */

const char*
output_reload_inhi (rtx *op, rtx clobber_reg, int *plen)
{
  output_reload_in_const (op, clobber_reg, plen, false);
  return "";
}


/* Reload a SI or SF compile time constant OP[1] into the register OP[0].
   CLOBBER_REG is a QI clobber reg needed to move vast majority of consts
   into a NO_LD_REGS register.  If CLOBBER_REG is NULL_RTX we either don't
   need a clobber reg or have to cook one up.

   LEN == NULL: Output instructions.

   LEN != NULL: Output nothing.  Set *LEN to number of words occupied
                by the insns printed.

   Return "".  */

const char *
output_reload_insisf (rtx *op, rtx clobber_reg, int *len)
{
  if (AVR_HAVE_MOVW
      && !test_hard_reg_class (LD_REGS, op[0])
      && (CONST_INT_P (op[1])
          || CONST_FIXED_P (op[1])
          || CONST_DOUBLE_P (op[1])))
    {
      int len_clr, len_noclr;

      /* In some cases it is better to clear the destination beforehand, e.g.

             CLR R2   CLR R3   MOVW R4,R2   INC R2

         is shorther than

             CLR R2   INC R2   CLR  R3      CLR R4   CLR R5

         We find it too tedious to work that out in the print function.
         Instead, we call the print function twice to get the lengths of
         both methods and use the shortest one.  */

      output_reload_in_const (op, clobber_reg, &len_clr, true);
      output_reload_in_const (op, clobber_reg, &len_noclr, false);

      if (len_noclr - len_clr == 4)
        {
          /* Default needs 4 CLR instructions: clear register beforehand.  */

          avr_asm_len ("mov %A0,__zero_reg__" CR_TAB
                       "mov %B0,__zero_reg__" CR_TAB
                       "movw %C0,%A0", &op[0], len, 3);

          output_reload_in_const (op, clobber_reg, len, true);

          if (len)
            *len += 3;

          return "";
        }
    }

  /* Default: destination not pre-cleared.  */

  output_reload_in_const (op, clobber_reg, len, false);
  return "";
}

const char*
avr_out_reload_inpsi (rtx *op, rtx clobber_reg, int *len)
{
  output_reload_in_const (op, clobber_reg, len, false);
  return "";
}


/* Worker function for `ASM_OUTPUT_ADDR_VEC'.  */
/* Emit jump tables out-of-line so that branches crossing the table
   get shorter offsets.  If we have JUMP + CALL, then put the tables
   in a dedicated non-.text section so that CALLs get better chance to
   be relaxed to RCALLs.

   We emit the tables by hand because `function_rodata_section' does not
   work as expected, cf. PR71151, and we do *NOT* want the table to be
   in .rodata, hence setting JUMP_TABLES_IN_TEXT_SECTION = 0 is of limited
   use; and setting it to 1 attributes table lengths to branch offsets...
   Moreover, fincal.c keeps switching section before each table entry
   which we find too fragile as to rely on section caching.  */

void
avr_output_addr_vec (rtx_insn *labl, rtx table)
{
  FILE *stream = asm_out_file;

  app_disable();

  // Switch to appropriate (sub)section.

  if (DECL_SECTION_NAME (current_function_decl)
      && symtab_node::get (current_function_decl)
      && ! symtab_node::get (current_function_decl)->implicit_section)
    {
      // .subsection will emit the code after the function and in the
      // section as chosen by the user.

      switch_to_section (current_function_section ());
      fprintf (stream, "\t.subsection\t1\n");
    }
  else
    {
      // Since PR63223 there is no restriction where to put the table; it
      // may even reside above 128 KiB.  We put it in a section as high as
      // possible and avoid progmem in order not to waste flash <= 64 KiB.

      const char *sec_name = ".jumptables.gcc";

      // The table belongs to its host function, therefore use fine
      // grained sections so that, if that function is removed by
      // --gc-sections, the child table(s) may also be removed.  */

      tree asm_name = DECL_ASSEMBLER_NAME (current_function_decl);
      const char *fname = IDENTIFIER_POINTER (asm_name);
      fname = targetm.strip_name_encoding (fname);
      sec_name = ACONCAT ((sec_name, ".", fname, NULL));

      fprintf (stream, "\t.section\t%s,\"%s\",@progbits\n", sec_name,
               AVR_HAVE_JMP_CALL ? "a" : "ax");
    }

  // Output the label that preceeds the table.

  ASM_OUTPUT_ALIGN (stream, 1);
  targetm.asm_out.internal_label (stream, "L", CODE_LABEL_NUMBER (labl));

  // Output the table's content.

  int vlen = XVECLEN (table, 0);

  for (int idx = 0; idx < vlen; idx++)
    {
      int value = CODE_LABEL_NUMBER (XEXP (XVECEXP (table, 0, idx), 0));

      if (AVR_HAVE_JMP_CALL)
        fprintf (stream, "\t.word gs(.L%d)\n", value);
      else
        fprintf (stream, "\trjmp .L%d\n", value);
    }

  // Switch back to original section.  As we clobbered the section above,
  // forget the current section before switching back.

  in_section = NULL;
  switch_to_section (current_function_section ());
}


/* Implement `TARGET_CONDITIONAL_REGISTER_USAGE'.  */

static void
avr_conditional_register_usage (void)
{
  if (AVR_TINY)
    {
      const int tiny_reg_alloc_order[] = {
        24, 25,
        22, 23,
        30, 31,
        26, 27,
        28, 29,
        21, 20, 19, 18,
        16, 17,
        32, 33, 34, 35,
        15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0
      };

      /* Set R0-R17 as fixed registers. Reset R0-R17 in call used register list
         - R0-R15 are not available in Tiny Core devices
         - R16 and R17 are fixed registers.  */

      for (size_t i = 0; i <= 17;  i++)
        {
          fixed_regs[i] = 1;
          call_used_regs[i] = 1;
        }

      /* Set R18 to R21 as callee saved registers
         - R18, R19, R20 and R21 are the callee saved registers in
           Tiny Core devices  */

      for (size_t i = 18; i <= LAST_CALLEE_SAVED_REG; i++)
        {
          call_used_regs[i] = 0;
        }

      /* Update register allocation order for Tiny Core devices */

      for (size_t i = 0; i < ARRAY_SIZE (tiny_reg_alloc_order); i++)
        {
          reg_alloc_order[i] = tiny_reg_alloc_order[i];
        }

      CLEAR_HARD_REG_SET (reg_class_contents[(int) ADDW_REGS]);
      CLEAR_HARD_REG_SET (reg_class_contents[(int) NO_LD_REGS]);
    }
}

/* Implement `TARGET_HARD_REGNO_SCRATCH_OK'.  */
/* Returns true if SCRATCH are safe to be allocated as a scratch
   registers (for a define_peephole2) in the current function.  */

static bool
avr_hard_regno_scratch_ok (unsigned int regno)
{
  /* Interrupt functions can only use registers that have already been saved
     by the prologue, even if they would normally be call-clobbered.  */

  if ((cfun->machine->is_interrupt || cfun->machine->is_signal)
      && !df_regs_ever_live_p (regno))
    return false;

  /* Don't allow hard registers that might be part of the frame pointer.
     Some places in the compiler just test for [HARD_]FRAME_POINTER_REGNUM
     and don't care for a frame pointer that spans more than one register.  */

  if ((!reload_completed || frame_pointer_needed)
      && (regno == REG_Y || regno == REG_Y + 1))
    {
      return false;
    }

  return true;
}


/* Worker function for `HARD_REGNO_RENAME_OK'.  */
/* Return nonzero if register OLD_REG can be renamed to register NEW_REG.  */

int
avr_hard_regno_rename_ok (unsigned int old_reg,
			  unsigned int new_reg)
{
  /* Interrupt functions can only use registers that have already been
     saved by the prologue, even if they would normally be
     call-clobbered.  */

  if ((cfun->machine->is_interrupt || cfun->machine->is_signal)
      && !df_regs_ever_live_p (new_reg))
    return 0;

  /* Don't allow hard registers that might be part of the frame pointer.
     Some places in the compiler just test for [HARD_]FRAME_POINTER_REGNUM
     and don't care for a frame pointer that spans more than one register.  */

  if ((!reload_completed || frame_pointer_needed)
      && (old_reg == REG_Y || old_reg == REG_Y + 1
          || new_reg == REG_Y || new_reg == REG_Y + 1))
    {
      return 0;
    }

  return 1;
}

/* Output a branch that tests a single bit of a register (QI, HI, SI or DImode)
   or memory location in the I/O space (QImode only).

   Operand 0: comparison operator (must be EQ or NE, compare bit to zero).
   Operand 1: register operand to test, or CONST_INT memory address.
   Operand 2: bit number.
   Operand 3: label to jump to if the test is true.  */

const char*
avr_out_sbxx_branch (rtx_insn *insn, rtx operands[])
{
  enum rtx_code comp = GET_CODE (operands[0]);
  bool long_jump = get_attr_length (insn) >= 4;
  bool reverse = long_jump || jump_over_one_insn_p (insn, operands[3]);

  if (comp == GE)
    comp = EQ;
  else if (comp == LT)
    comp = NE;

  if (reverse)
    comp = reverse_condition (comp);

  switch (GET_CODE (operands[1]))
    {
    default:
      gcc_unreachable();

    case CONST_INT:
    case CONST:
    case SYMBOL_REF:

      if (low_io_address_operand (operands[1], QImode))
        {
          if (comp == EQ)
            output_asm_insn ("sbis %i1,%2", operands);
          else
            output_asm_insn ("sbic %i1,%2", operands);
        }
      else
        {
	  gcc_assert (io_address_operand (operands[1], QImode));
          output_asm_insn ("in __tmp_reg__,%i1", operands);
          if (comp == EQ)
            output_asm_insn ("sbrs __tmp_reg__,%2", operands);
          else
            output_asm_insn ("sbrc __tmp_reg__,%2", operands);
        }

      break; /* CONST_INT */

    case REG:

      if (comp == EQ)
        output_asm_insn ("sbrs %T1%T2", operands);
      else
        output_asm_insn ("sbrc %T1%T2", operands);

      break; /* REG */
    }        /* switch */

  if (long_jump)
    return ("rjmp .+4" CR_TAB
            "jmp %x3");

  if (!reverse)
    return "rjmp %x3";

  return "";
}

/* Worker function for `TARGET_ASM_CONSTRUCTOR'.  */

static void
avr_asm_out_ctor (rtx symbol, int priority)
{
  fputs ("\t.global __do_global_ctors\n", asm_out_file);
  default_ctor_section_asm_out_constructor (symbol, priority);
}


/* Worker function for `TARGET_ASM_DESTRUCTOR'.  */

static void
avr_asm_out_dtor (rtx symbol, int priority)
{
  fputs ("\t.global __do_global_dtors\n", asm_out_file);
  default_dtor_section_asm_out_destructor (symbol, priority);
}


/* Worker function for `TARGET_RETURN_IN_MEMORY'.  */

static bool
avr_return_in_memory (const_tree type, const_tree fntype ATTRIBUTE_UNUSED)
{
  HOST_WIDE_INT size = int_size_in_bytes (type);
  HOST_WIDE_INT ret_size_limit = AVR_TINY ? 4 : 8;

  /* In avr, there are 8 return registers. But, for Tiny Core
     (ATtiny4/5/9/10/20/40) devices, only 4 registers are available.
     Return true if size is unknown or greater than the limit.  */

  if (size == -1 || size > ret_size_limit)
    {
      return true;
    }
  else
    {
      return false;
    }
}


/* Implement `CASE_VALUES_THRESHOLD'.  */
/* Supply the default for --param case-values-threshold=0  */

static unsigned int
avr_case_values_threshold (void)
{
  /* The exact break-even point between a jump table and an if-else tree
     depends on several factors not available here like, e.g. if 8-bit
     comparisons can be used in the if-else tree or not, on the
     range of the case values, if the case value can be reused, on the
     register allocation, etc.  '7' appears to be a good choice.  */

  return 7;
}


/* Implement `TARGET_ADDR_SPACE_ADDRESS_MODE'.  */

static scalar_int_mode
avr_addr_space_address_mode (addr_space_t as)
{
  return avr_addrspace[as].pointer_size == 3 ? PSImode : HImode;
}


/* Implement `TARGET_ADDR_SPACE_POINTER_MODE'.  */

static scalar_int_mode
avr_addr_space_pointer_mode (addr_space_t as)
{
  return avr_addr_space_address_mode (as);
}


/* Helper for following function.  */

static bool
avr_reg_ok_for_pgm_addr (rtx reg, bool strict)
{
  gcc_assert (REG_P (reg));

  if (strict)
    {
      return REGNO (reg) == REG_Z;
    }

  /* Avoid combine to propagate hard regs.  */

  if (can_create_pseudo_p()
      && REGNO (reg) < REG_Z)
    {
      return false;
    }

  return true;
}


/* Implement `TARGET_ADDR_SPACE_LEGITIMATE_ADDRESS_P'.  */

static bool
avr_addr_space_legitimate_address_p (machine_mode mode, rtx x,
                                     bool strict, addr_space_t as)
{
  bool ok = false;

  switch (as)
    {
    default:
      gcc_unreachable();

    case ADDR_SPACE_GENERIC:
      return avr_legitimate_address_p (mode, x, strict);

    case ADDR_SPACE_FLASH:
    case ADDR_SPACE_FLASH1:
    case ADDR_SPACE_FLASH2:
    case ADDR_SPACE_FLASH3:
    case ADDR_SPACE_FLASH4:
    case ADDR_SPACE_FLASH5:

      switch (GET_CODE (x))
        {
        case REG:
          ok = avr_reg_ok_for_pgm_addr (x, strict);
          break;

        case POST_INC:
          ok = avr_reg_ok_for_pgm_addr (XEXP (x, 0), strict);
          break;

        default:
          break;
        }

      break; /* FLASH */

    case ADDR_SPACE_MEMX:
      if (REG_P (x))
        ok = (!strict
              && can_create_pseudo_p());

      if (LO_SUM == GET_CODE (x))
        {
          rtx hi = XEXP (x, 0);
          rtx lo = XEXP (x, 1);

          ok = (REG_P (hi)
                && (!strict || REGNO (hi) < FIRST_PSEUDO_REGISTER)
                && REG_P (lo)
                && REGNO (lo) == REG_Z);
        }

      break; /* MEMX */
    }

  if (avr_log.legitimate_address_p)
    {
      avr_edump ("\n%?: ret=%b, mode=%m strict=%d "
                 "reload_completed=%d reload_in_progress=%d %s:",
                 ok, mode, strict, reload_completed, reload_in_progress,
                 reg_renumber ? "(reg_renumber)" : "");

      if (GET_CODE (x) == PLUS
          && REG_P (XEXP (x, 0))
          && CONST_INT_P (XEXP (x, 1))
          && IN_RANGE (INTVAL (XEXP (x, 1)), 0, MAX_LD_OFFSET (mode))
          && reg_renumber)
        {
          avr_edump ("(r%d ---> r%d)", REGNO (XEXP (x, 0)),
                     true_regnum (XEXP (x, 0)));
        }

      avr_edump ("\n%r\n", x);
    }

  return ok;
}


/* Implement `TARGET_ADDR_SPACE_LEGITIMIZE_ADDRESS'.  */

static rtx
avr_addr_space_legitimize_address (rtx x, rtx old_x,
                                   machine_mode mode, addr_space_t as)
{
  if (ADDR_SPACE_GENERIC_P (as))
    return avr_legitimize_address (x, old_x, mode);

  if (avr_log.legitimize_address)
    {
      avr_edump ("\n%?: mode=%m\n %r\n", mode, old_x);
    }

  return old_x;
}


/* Implement `TARGET_ADDR_SPACE_CONVERT'.  */

static rtx
avr_addr_space_convert (rtx src, tree type_from, tree type_to)
{
  addr_space_t as_from = TYPE_ADDR_SPACE (TREE_TYPE (type_from));
  addr_space_t as_to = TYPE_ADDR_SPACE (TREE_TYPE (type_to));

  if (avr_log.progmem)
    avr_edump ("\n%!: op = %r\nfrom = %t\nto = %t\n",
               src, type_from, type_to);

  /* Up-casting from 16-bit to 24-bit pointer.  */

  if (as_from != ADDR_SPACE_MEMX
      && as_to == ADDR_SPACE_MEMX)
    {
      int msb;
      rtx sym = src;
      rtx reg = gen_reg_rtx (PSImode);

      while (CONST == GET_CODE (sym) || PLUS == GET_CODE (sym))
        sym = XEXP (sym, 0);

      /* Look at symbol flags:  avr_encode_section_info set the flags
         also if attribute progmem was seen so that we get the right
         promotion for, e.g. PSTR-like strings that reside in generic space
         but are located in flash.  In that case we patch the incoming
         address space.  */

      if (SYMBOL_REF_P (sym)
          && ADDR_SPACE_FLASH == AVR_SYMBOL_GET_ADDR_SPACE (sym))
        {
          as_from = ADDR_SPACE_FLASH;
        }

      /* Linearize memory: RAM has bit 23 set.  */

      msb = ADDR_SPACE_GENERIC_P (as_from)
        ? 0x80
        : avr_addrspace[as_from].segment;

      src = force_reg (Pmode, src);

      emit_insn (msb == 0
                 ? gen_zero_extendhipsi2 (reg, src)
                 : gen_n_extendhipsi2 (reg, gen_int_mode (msb, QImode), src));

      return reg;
    }

  /* Down-casting from 24-bit to 16-bit throws away the high byte.  */

  if (as_from == ADDR_SPACE_MEMX
      && as_to != ADDR_SPACE_MEMX)
    {
      rtx new_src = gen_reg_rtx (Pmode);

      src = force_reg (PSImode, src);

      emit_move_insn (new_src,
                      simplify_gen_subreg (Pmode, src, PSImode, 0));
      return new_src;
    }

  return src;
}


/* Implement `TARGET_ADDR_SPACE_SUBSET_P'.  */

static bool
avr_addr_space_subset_p (addr_space_t subset ATTRIBUTE_UNUSED,
                         addr_space_t superset ATTRIBUTE_UNUSED)
{
  /* Allow any kind of pointer mess.  */

  return true;
}


/* Implement `TARGET_CONVERT_TO_TYPE'.  */

static tree
avr_convert_to_type (tree type, tree expr)
{
  /* Print a diagnose for pointer conversion that changes the address
     space of the pointer target to a non-enclosing address space,
     provided -Waddr-space-convert is on.

     FIXME: Filter out cases where the target object is known to
            be located in the right memory, like in

                (const __flash*) PSTR ("text")

            Also try to distinguish between explicit casts requested by
            the user and implicit casts like

                void f (const __flash char*);

                void g (const char *p)
                {
                    f ((const __flash*) p);
                }

            under the assumption that an explicit casts means that the user
            knows what he is doing, e.g. interface with PSTR or old style
            code with progmem and pgm_read_xxx.
  */

  if (avr_warn_addr_space_convert
      && expr != error_mark_node
      && POINTER_TYPE_P (type)
      && POINTER_TYPE_P (TREE_TYPE (expr)))
    {
      addr_space_t as_old = TYPE_ADDR_SPACE (TREE_TYPE (TREE_TYPE (expr)));
      addr_space_t as_new = TYPE_ADDR_SPACE (TREE_TYPE (type));

      if (avr_log.progmem)
        avr_edump ("%?: type = %t\nexpr = %t\n\n", type, expr);

      if (as_new != ADDR_SPACE_MEMX
          && as_new != as_old)
        {
          location_t loc = EXPR_LOCATION (expr);
          const char *name_old = avr_addrspace[as_old].name;
          const char *name_new = avr_addrspace[as_new].name;

          warning (OPT_Waddr_space_convert,
                   "conversion from address space %qs to address space %qs",
                   ADDR_SPACE_GENERIC_P (as_old) ? "generic" : name_old,
                   ADDR_SPACE_GENERIC_P (as_new) ? "generic" : name_new);

          return fold_build1_loc (loc, ADDR_SPACE_CONVERT_EXPR, type, expr);
        }
    }

  return NULL_TREE;
}


/* Implement `TARGET_LEGITIMATE_COMBINED_INSN'.  */

/* PR78883: Filter out paradoxical SUBREGs of MEM which are not handled
   properly by following passes.  As INSN_SCHEDULING is off and hence
   general_operand accepts such expressions, ditch them now.  */

static bool
avr_legitimate_combined_insn (rtx_insn *insn)
{
  subrtx_iterator::array_type array;

  FOR_EACH_SUBRTX (iter, array, PATTERN (insn), NONCONST)
    {
      const_rtx op = *iter;

      if (SUBREG_P (op)
          && MEM_P (SUBREG_REG (op))
          && (GET_MODE_SIZE (GET_MODE (op))
              > GET_MODE_SIZE (GET_MODE (SUBREG_REG (op)))))
        {
          return false;
        }
    }

  return true;
}


/* PR63633: The middle-end might come up with hard regs as input operands.

   RMASK is a bit mask representing a subset of hard registers R0...R31:
   Rn is an element of that set iff bit n of RMASK is set.
   OPMASK describes a subset of OP[]:  If bit n of OPMASK is 1 then
   OP[n] has to be fixed; otherwise OP[n] is left alone.

   For each element of OPMASK which is a hard register overlapping RMASK,
   replace OP[n] with a newly created pseudo register

   HREG == 0:  Also emit a move insn that copies the contents of that
               hard register into the new pseudo.

   HREG != 0:  Also set HREG[n] to the hard register.  */

static void
avr_fix_operands (rtx *op, rtx *hreg, unsigned opmask, unsigned rmask)
{
  for (; opmask; opmask >>= 1, op++)
    {
      rtx reg = *op;

      if (hreg)
        *hreg = NULL_RTX;

      if ((opmask & 1)
          && REG_P (reg)
          && REGNO (reg) < FIRST_PSEUDO_REGISTER
          // This hard-reg overlaps other prohibited hard regs?
          && (rmask & regmask (GET_MODE (reg), REGNO (reg))))
        {
          *op = gen_reg_rtx (GET_MODE (reg));
          if (hreg == NULL)
            emit_move_insn (*op, reg);
          else
            *hreg = reg;
        }

      if (hreg)
        hreg++;
    }
}


void
avr_fix_inputs (rtx *op, unsigned opmask, unsigned rmask)
{
  avr_fix_operands (op, NULL, opmask, rmask);
}


/* Helper for the function below:  If bit n of MASK is set and
   HREG[n] != NULL, then emit a move insn to copy OP[n] to HREG[n].
   Otherwise do nothing for that n.  Return TRUE.  */

static bool
avr_move_fixed_operands (rtx *op, rtx *hreg, unsigned mask)
{
  for (; mask; mask >>= 1, op++, hreg++)
    if ((mask & 1)
        && *hreg)
      emit_move_insn (*hreg, *op);

  return true;
}


/* PR63633: The middle-end might come up with hard regs as output operands.

   GEN is a sequence generating function like gen_mulsi3 with 3 operands OP[].
   RMASK is a bit mask representing a subset of hard registers R0...R31:
   Rn is an element of that set iff bit n of RMASK is set.
   OPMASK describes a subset of OP[]:  If bit n of OPMASK is 1 then
   OP[n] has to be fixed; otherwise OP[n] is left alone.

   Emit the insn sequence as generated by GEN() with all elements of OPMASK
   which are hard registers overlapping RMASK replaced by newly created
   pseudo registers.  After the sequence has been emitted, emit insns that
   move the contents of respective pseudos to their hard regs.  */

bool
avr_emit3_fix_outputs (rtx (*gen)(rtx,rtx,rtx), rtx *op,
                       unsigned opmask, unsigned rmask)
{
  const int n = 3;
  rtx hreg[n];

  /* It is letigimate for GEN to call this function, and in order not to
     get self-recursive we use the following static kludge.  This is the
     only way not to duplicate all expanders and to avoid ugly and
     hard-to-maintain C-code instead of the much more appreciated RTL
     representation as supplied by define_expand.  */
  static bool lock = false;

  gcc_assert (opmask < (1u << n));

  if (lock)
    return false;

  avr_fix_operands (op, hreg, opmask, rmask);

  lock = true;
  emit_insn (gen (op[0], op[1], op[2]));
  lock = false;

  return avr_move_fixed_operands (op, hreg, opmask);
}


/* Worker function for cpymemhi expander.
   XOP[0]  Destination as MEM:BLK
   XOP[1]  Source      "     "
   XOP[2]  # Bytes to copy

   Return TRUE  if the expansion is accomplished.
   Return FALSE if the operand compination is not supported.  */

bool
avr_emit_cpymemhi (rtx *xop)
{
  HOST_WIDE_INT count;
  machine_mode loop_mode;
  addr_space_t as = MEM_ADDR_SPACE (xop[1]);
  rtx loop_reg, addr1, a_src, a_dest, insn, xas;
  rtx a_hi8 = NULL_RTX;

  if (avr_mem_flash_p (xop[0]))
    return false;

  if (!CONST_INT_P (xop[2]))
    return false;

  count = INTVAL (xop[2]);
  if (count <= 0)
    return false;

  a_src  = XEXP (xop[1], 0);
  a_dest = XEXP (xop[0], 0);

  if (PSImode == GET_MODE (a_src))
    {
      gcc_assert (as == ADDR_SPACE_MEMX);

      loop_mode = (count < 0x100) ? QImode : HImode;
      loop_reg = gen_rtx_REG (loop_mode, 24);
      emit_move_insn (loop_reg, gen_int_mode (count, loop_mode));

      addr1 = simplify_gen_subreg (HImode, a_src, PSImode, 0);
      a_hi8 = simplify_gen_subreg (QImode, a_src, PSImode, 2);
    }
  else
    {
      int segment = avr_addrspace[as].segment;

      if (segment
          && avr_n_flash > 1)
        {
          a_hi8 = GEN_INT (segment);
          emit_move_insn (rampz_rtx, a_hi8 = copy_to_mode_reg (QImode, a_hi8));
        }
      else if (!ADDR_SPACE_GENERIC_P (as))
        {
          as = ADDR_SPACE_FLASH;
        }

      addr1 = a_src;

      loop_mode = (count <= 0x100) ? QImode : HImode;
      loop_reg = copy_to_mode_reg (loop_mode, gen_int_mode (count, loop_mode));
    }

  xas = GEN_INT (as);

  /* FIXME: Register allocator might come up with spill fails if it is left
        on its own.  Thus, we allocate the pointer registers by hand:
        Z = source address
        X = destination address  */

  emit_move_insn (lpm_addr_reg_rtx, addr1);
  emit_move_insn (gen_rtx_REG (HImode, REG_X), a_dest);

  /* FIXME: Register allocator does a bad job and might spill address
        register(s) inside the loop leading to additional move instruction
        to/from stack which could clobber tmp_reg.  Thus, do *not* emit
        load and store as separate insns.  Instead, we perform the copy
        by means of one monolithic insn.  */

  gcc_assert (TMP_REGNO == LPM_REGNO);

  if (as != ADDR_SPACE_MEMX)
    {
      /* Load instruction ([E]LPM or LD) is known at compile time:
         Do the copy-loop inline.  */

      rtx (*fun) (rtx, rtx, rtx)
        = QImode == loop_mode ? gen_cpymem_qi : gen_cpymem_hi;

      insn = fun (xas, loop_reg, loop_reg);
    }
  else
    {
      rtx (*fun) (rtx, rtx)
        = QImode == loop_mode ? gen_cpymemx_qi : gen_cpymemx_hi;

      emit_move_insn (gen_rtx_REG (QImode, 23), a_hi8);

      insn = fun (xas, GEN_INT (avr_addr.rampz));
    }

  set_mem_addr_space (SET_SRC (XVECEXP (insn, 0, 0)), as);
  emit_insn (insn);

  return true;
}


/* Print assembler for cpymem_qi, cpymem_hi insns...
       $0     : Address Space
       $1, $2 : Loop register
       Z      : Source address
       X      : Destination address
*/

const char*
avr_out_cpymem (rtx_insn *insn ATTRIBUTE_UNUSED, rtx *op, int *plen)
{
  addr_space_t as = (addr_space_t) INTVAL (op[0]);
  machine_mode loop_mode = GET_MODE (op[1]);
  bool sbiw_p = test_hard_reg_class (ADDW_REGS, op[1]);
  rtx xop[3];

  if (plen)
    *plen = 0;

  xop[0] = op[0];
  xop[1] = op[1];
  xop[2] = tmp_reg_rtx;

  /* Loop label */

  avr_asm_len ("0:", xop, plen, 0);

  /* Load with post-increment */

  switch (as)
    {
    default:
      gcc_unreachable();

    case ADDR_SPACE_GENERIC:

      avr_asm_len ("ld %2,Z+", xop, plen, 1);
      break;

    case ADDR_SPACE_FLASH:

      if (AVR_HAVE_LPMX)
        avr_asm_len ("lpm %2,Z+", xop, plen, 1);
      else
        avr_asm_len ("lpm" CR_TAB
                     "adiw r30,1", xop, plen, 2);
      break;

    case ADDR_SPACE_FLASH1:
    case ADDR_SPACE_FLASH2:
    case ADDR_SPACE_FLASH3:
    case ADDR_SPACE_FLASH4:
    case ADDR_SPACE_FLASH5:

      if (AVR_HAVE_ELPMX)
        avr_asm_len ("elpm %2,Z+", xop, plen, 1);
      else
        avr_asm_len ("elpm" CR_TAB
                     "adiw r30,1", xop, plen, 2);
      break;
    }

  /* Store with post-increment */

  avr_asm_len ("st X+,%2", xop, plen, 1);

  /* Decrement loop-counter and set Z-flag */

  if (QImode == loop_mode)
    {
      avr_asm_len ("dec %1", xop, plen, 1);
    }
  else if (sbiw_p)
    {
      avr_asm_len ("sbiw %1,1", xop, plen, 1);
    }
  else
    {
      avr_asm_len ("subi %A1,1" CR_TAB
                   "sbci %B1,0", xop, plen, 2);
    }

  /* Loop until zero */

  return avr_asm_len ("brne 0b", xop, plen, 1);
}



/* Helper for __builtin_avr_delay_cycles */

static rtx
avr_mem_clobber (void)
{
  rtx mem = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
  MEM_VOLATILE_P (mem) = 1;
  return mem;
}

static void
avr_expand_delay_cycles (rtx operands0)
{
  unsigned HOST_WIDE_INT cycles = UINTVAL (operands0) & GET_MODE_MASK (SImode);
  unsigned HOST_WIDE_INT cycles_used;
  unsigned HOST_WIDE_INT loop_count;

  if (IN_RANGE (cycles, 83886082, 0xFFFFFFFF))
    {
      loop_count = ((cycles - 9) / 6) + 1;
      cycles_used = ((loop_count - 1) * 6) + 9;
      emit_insn (gen_delay_cycles_4 (gen_int_mode (loop_count, SImode),
                                     avr_mem_clobber()));
      cycles -= cycles_used;
    }

  if (IN_RANGE (cycles, 262145, 83886081))
    {
      loop_count = ((cycles - 7) / 5) + 1;
      if (loop_count > 0xFFFFFF)
        loop_count = 0xFFFFFF;
      cycles_used = ((loop_count - 1) * 5) + 7;
      emit_insn (gen_delay_cycles_3 (gen_int_mode (loop_count, SImode),
                                     avr_mem_clobber()));
      cycles -= cycles_used;
    }

  if (IN_RANGE (cycles, 768, 262144))
    {
      loop_count = ((cycles - 5) / 4) + 1;
      if (loop_count > 0xFFFF)
        loop_count = 0xFFFF;
      cycles_used = ((loop_count - 1) * 4) + 5;
      emit_insn (gen_delay_cycles_2 (gen_int_mode (loop_count, HImode),
                                     avr_mem_clobber()));
      cycles -= cycles_used;
    }

  if (IN_RANGE (cycles, 6, 767))
    {
      loop_count = cycles / 3;
      if (loop_count > 255)
        loop_count = 255;
      cycles_used = loop_count * 3;
      emit_insn (gen_delay_cycles_1 (gen_int_mode (loop_count, QImode),
                                     avr_mem_clobber()));
      cycles -= cycles_used;
    }

  while (cycles >= 2)
    {
      emit_insn (gen_nopv (GEN_INT (2)));
      cycles -= 2;
    }

  if (cycles == 1)
    {
      emit_insn (gen_nopv (GEN_INT (1)));
      cycles--;
    }
}


static void
avr_expand_nops (rtx operands0)
{
  unsigned HOST_WIDE_INT n_nops = UINTVAL (operands0) & GET_MODE_MASK (HImode);

  while (n_nops--)
    {
      emit_insn (gen_nopv (const1_rtx));
    }
}


/* Compute the image of x under f, i.e. perform   x --> f(x)    */

static int
avr_map (unsigned int f, int x)
{
  return x < 8 ? (f >> (4 * x)) & 0xf : 0;
}


/* Return some metrics of map A.  */

enum
  {
    /* Number of fixed points in { 0 ... 7 } */
    MAP_FIXED_0_7,

    /* Size of preimage of non-fixed points in { 0 ... 7 } */
    MAP_NONFIXED_0_7,

    /* Mask representing the fixed points in { 0 ... 7 } */
    MAP_MASK_FIXED_0_7,

    /* Size of the preimage of { 0 ... 7 } */
    MAP_PREIMAGE_0_7,

    /* Mask that represents the preimage of { f } */
    MAP_MASK_PREIMAGE_F
  };

static unsigned
avr_map_metric (unsigned int a, int mode)
{
  unsigned metric = 0;

  for (unsigned i = 0; i < 8; i++)
    {
      unsigned ai = avr_map (a, i);

      if (mode == MAP_FIXED_0_7)
        metric += ai == i;
      else if (mode == MAP_NONFIXED_0_7)
        metric += ai < 8 && ai != i;
      else if (mode == MAP_MASK_FIXED_0_7)
        metric |= ((unsigned) (ai == i)) << i;
      else if (mode == MAP_PREIMAGE_0_7)
        metric += ai < 8;
      else if (mode == MAP_MASK_PREIMAGE_F)
        metric |= ((unsigned) (ai == 0xf)) << i;
      else
        gcc_unreachable();
    }

  return metric;
}


/* Return true if IVAL has a 0xf in its hexadecimal representation
   and false, otherwise.  Only nibbles 0..7 are taken into account.
   Used as constraint helper for C0f and Cxf.  */

bool
avr_has_nibble_0xf (rtx ival)
{
  unsigned int map = UINTVAL (ival) & GET_MODE_MASK (SImode);
  return avr_map_metric (map, MAP_MASK_PREIMAGE_F) != 0;
}


/* We have a set of bits that are mapped by a function F.
   Try to decompose F by means of a second function G so that

      F = F o G^-1 o G

   and

      cost (F o G^-1) + cost (G)  <  cost (F)

   Example:  Suppose builtin insert_bits supplies us with the map
   F = 0x3210ffff.  Instead of doing 4 bit insertions to get the high
   nibble of the result, we can just as well rotate the bits before inserting
   them and use the map 0x7654ffff which is cheaper than the original map.
   For this example G = G^-1 = 0x32107654 and F o G^-1 = 0x7654ffff.  */

typedef struct
{
  /* tree code of binary function G */
  enum tree_code code;

  /* The constant second argument of G */
  int arg;

  /* G^-1, the inverse of G (*, arg) */
  unsigned ginv;

  /* The cost of applying G (*, arg) */
  int cost;

  /* The composition F o G^-1 (*, arg) for some function F */
  unsigned int map;

  /* For debug purpose only */
  const char *str;
} avr_map_op_t;

static const avr_map_op_t avr_map_op[] =
  {
    { LROTATE_EXPR, 0, 0x76543210, 0, 0, "id" },
    { LROTATE_EXPR, 1, 0x07654321, 2, 0, "<<<" },
    { LROTATE_EXPR, 2, 0x10765432, 4, 0, "<<<" },
    { LROTATE_EXPR, 3, 0x21076543, 4, 0, "<<<" },
    { LROTATE_EXPR, 4, 0x32107654, 1, 0, "<<<" },
    { LROTATE_EXPR, 5, 0x43210765, 3, 0, "<<<" },
    { LROTATE_EXPR, 6, 0x54321076, 5, 0, "<<<" },
    { LROTATE_EXPR, 7, 0x65432107, 3, 0, "<<<" },
    { RSHIFT_EXPR, 1, 0x6543210c, 1, 0, ">>" },
    { RSHIFT_EXPR, 1, 0x7543210c, 1, 0, ">>" },
    { RSHIFT_EXPR, 2, 0x543210cc, 2, 0, ">>" },
    { RSHIFT_EXPR, 2, 0x643210cc, 2, 0, ">>" },
    { RSHIFT_EXPR, 2, 0x743210cc, 2, 0, ">>" },
    { LSHIFT_EXPR, 1, 0xc7654321, 1, 0, "<<" },
    { LSHIFT_EXPR, 2, 0xcc765432, 2, 0, "<<" }
  };


/* Try to decompose F as F = (F o G^-1) o G as described above.
   The result is a struct representing F o G^-1 and G.
   If result.cost < 0 then such a decomposition does not exist.  */

static avr_map_op_t
avr_map_decompose (unsigned int f, const avr_map_op_t *g, bool val_const_p)
{
  bool val_used_p = avr_map_metric (f, MAP_MASK_PREIMAGE_F) != 0;
  avr_map_op_t f_ginv = *g;
  unsigned int ginv = g->ginv;

  f_ginv.cost = -1;

  /* Step 1:  Computing F o G^-1  */

  for (int i = 7; i >= 0; i--)
    {
      int x = avr_map (f, i);

      if (x <= 7)
        {
          x = avr_map (ginv, x);

          /* The bit is no element of the image of G: no avail (cost = -1)  */

          if (x > 7)
            return f_ginv;
        }

      f_ginv.map = (f_ginv.map << 4) + x;
    }

  /* Step 2:  Compute the cost of the operations.
     The overall cost of doing an operation prior to the insertion is
      the cost of the insertion plus the cost of the operation.  */

  /* Step 2a:  Compute cost of F o G^-1  */

  if (avr_map_metric (f_ginv.map, MAP_NONFIXED_0_7) == 0)
    /* The mapping consists only of fixed points and can be folded
       to AND/OR logic in the remainder.  Reasonable cost is 3. */
    f_ginv.cost = 2 + (val_used_p && !val_const_p);
  else
    {
      rtx xop[4];

      /* Get the cost of the insn by calling the output worker with some
         fake values.  Mimic effect of reloading xop[3]: Unused operands
         are mapped to 0 and used operands are reloaded to xop[0].  */

      xop[0] = all_regs_rtx[24];
      xop[1] = gen_int_mode (f_ginv.map, SImode);
      xop[2] = all_regs_rtx[25];
      xop[3] = val_used_p ? xop[0] : const0_rtx;

      avr_out_insert_bits (xop, &f_ginv.cost);

      f_ginv.cost += val_const_p && val_used_p ? 1 : 0;
    }

  /* Step 2b:  Add cost of G  */

  f_ginv.cost += g->cost;

  if (avr_log.builtin)
    avr_edump (" %s%d=%d", g->str, g->arg, f_ginv.cost);

  return f_ginv;
}


/* Insert bits from XOP[1] into XOP[0] according to MAP.
   XOP[0] and XOP[1] don't overlap.
   If FIXP_P = true:  Move all bits according to MAP using BLD/BST sequences.
   If FIXP_P = false: Just move the bit if its position in the destination
   is different to its source position.  */

static void
avr_move_bits (rtx *xop, unsigned int map, bool fixp_p, int *plen)
{
  /* T-flag contains this bit of the source, i.e. of XOP[1]  */
  int t_bit_src = -1;

  /* We order the operations according to the requested source bit b.  */

  for (int b = 0; b < 8; b++)
    for (int bit_dest = 0; bit_dest < 8; bit_dest++)
      {
        int bit_src = avr_map (map, bit_dest);

        if (b != bit_src
            || bit_src >= 8
            /* Same position: No need to copy as requested by FIXP_P.  */
            || (bit_dest == bit_src && !fixp_p))
          continue;

        if (t_bit_src != bit_src)
          {
            /* Source bit is not yet in T: Store it to T.  */

            t_bit_src = bit_src;

            xop[3] = GEN_INT (bit_src);
            avr_asm_len ("bst %T1%T3", xop, plen, 1);
          }

        /* Load destination bit with T.  */

        xop[3] = GEN_INT (bit_dest);
        avr_asm_len ("bld %T0%T3", xop, plen, 1);
      }
}


/* PLEN == 0: Print assembler code for `insert_bits'.
   PLEN != 0: Compute code length in bytes.

   OP[0]:  Result
   OP[1]:  The mapping composed of nibbles. If nibble no. N is
           0:   Bit N of result is copied from bit OP[2].0
           ...  ...
           7:   Bit N of result is copied from bit OP[2].7
           0xf: Bit N of result is copied from bit OP[3].N
   OP[2]:  Bits to be inserted
   OP[3]:  Target value  */

const char*
avr_out_insert_bits (rtx *op, int *plen)
{
  unsigned int map = UINTVAL (op[1]) & GET_MODE_MASK (SImode);
  unsigned mask_fixed;
  bool fixp_p = true;
  rtx xop[4];

  xop[0] = op[0];
  xop[1] = op[2];
  xop[2] = op[3];

  gcc_assert (REG_P (xop[2]) || CONST_INT_P (xop[2]));

  if (plen)
    *plen = 0;
  else if (flag_print_asm_name)
    fprintf (asm_out_file, ASM_COMMENT_START "map = 0x%08x\n", map);

  /* If MAP has fixed points it might be better to initialize the result
     with the bits to be inserted instead of moving all bits by hand.  */

  mask_fixed = avr_map_metric (map, MAP_MASK_FIXED_0_7);

  if (REGNO (xop[0]) == REGNO (xop[1]))
    {
      /* Avoid early-clobber conflicts */

      avr_asm_len ("mov __tmp_reg__,%1", xop, plen, 1);
      xop[1] = tmp_reg_rtx;
      fixp_p = false;
    }

  if (avr_map_metric (map, MAP_MASK_PREIMAGE_F))
    {
      /* XOP[2] is used and reloaded to XOP[0] already */

      int n_fix = 0, n_nofix = 0;

      gcc_assert (REG_P (xop[2]));

      /* Get the code size of the bit insertions; once with all bits
         moved and once with fixed points omitted.  */

      avr_move_bits (xop, map, true, &n_fix);
      avr_move_bits (xop, map, false, &n_nofix);

      if (fixp_p && n_fix - n_nofix > 3)
        {
          xop[3] = gen_int_mode (~mask_fixed, QImode);

          avr_asm_len ("eor %0,%1"   CR_TAB
                       "andi %0,%3"  CR_TAB
                       "eor %0,%1", xop, plen, 3);
          fixp_p = false;
        }
    }
  else
    {
      /* XOP[2] is unused */

      if (fixp_p && mask_fixed)
        {
          avr_asm_len ("mov %0,%1", xop, plen, 1);
          fixp_p = false;
        }
    }

  /* Move/insert remaining bits.  */

  avr_move_bits (xop, map, fixp_p, plen);

  return "";
}


/* IDs for all the AVR builtins.  */

enum avr_builtin_id
  {
#define DEF_BUILTIN(NAME, N_ARGS, TYPE, CODE, LIBNAME)  \
    AVR_BUILTIN_ ## NAME,
#include "builtins.def"
#undef DEF_BUILTIN

    AVR_BUILTIN_COUNT
  };

struct GTY(()) avr_builtin_description
{
  enum insn_code icode;
  int n_args;
  tree fndecl;
};


/* Notice that avr_bdesc[] and avr_builtin_id are initialized in such a way
   that a built-in's ID can be used to access the built-in by means of
   avr_bdesc[ID]  */

static GTY(()) struct avr_builtin_description
avr_bdesc[AVR_BUILTIN_COUNT] =
  {
#define DEF_BUILTIN(NAME, N_ARGS, TYPE, ICODE, LIBNAME)         \
    { (enum insn_code) CODE_FOR_ ## ICODE, N_ARGS, NULL_TREE },
#include "builtins.def"
#undef DEF_BUILTIN
  };


/* Implement `TARGET_BUILTIN_DECL'.  */

static tree
avr_builtin_decl (unsigned id, bool initialize_p ATTRIBUTE_UNUSED)
{
  if (id < AVR_BUILTIN_COUNT)
    return avr_bdesc[id].fndecl;

  return error_mark_node;
}


static void
avr_init_builtin_int24 (void)
{
  tree int24_type  = make_signed_type (GET_MODE_BITSIZE (PSImode));
  tree uint24_type = make_unsigned_type (GET_MODE_BITSIZE (PSImode));

  lang_hooks.types.register_builtin_type (int24_type, "__int24");
  lang_hooks.types.register_builtin_type (uint24_type, "__uint24");
}


/* Implement `TARGET_INIT_BUILTINS' */
/* Set up all builtin functions for this target.  */

static void
avr_init_builtins (void)
{
  tree void_ftype_void
    = build_function_type_list (void_type_node, NULL_TREE);
  tree uchar_ftype_uchar
    = build_function_type_list (unsigned_char_type_node,
                                unsigned_char_type_node,
                                NULL_TREE);
  tree uint_ftype_uchar_uchar
    = build_function_type_list (unsigned_type_node,
                                unsigned_char_type_node,
                                unsigned_char_type_node,
                                NULL_TREE);
  tree int_ftype_char_char
    = build_function_type_list (integer_type_node,
                                char_type_node,
                                char_type_node,
                                NULL_TREE);
  tree int_ftype_char_uchar
    = build_function_type_list (integer_type_node,
                                char_type_node,
                                unsigned_char_type_node,
                                NULL_TREE);
  tree void_ftype_ulong
    = build_function_type_list (void_type_node,
                                long_unsigned_type_node,
                                NULL_TREE);

  tree uchar_ftype_ulong_uchar_uchar
    = build_function_type_list (unsigned_char_type_node,
                                long_unsigned_type_node,
                                unsigned_char_type_node,
                                unsigned_char_type_node,
                                NULL_TREE);

  tree const_memx_void_node
    = build_qualified_type (void_type_node,
                            TYPE_QUAL_CONST
                            | ENCODE_QUAL_ADDR_SPACE (ADDR_SPACE_MEMX));

  tree const_memx_ptr_type_node
    = build_pointer_type_for_mode (const_memx_void_node, PSImode, false);

  tree char_ftype_const_memx_ptr
    = build_function_type_list (char_type_node,
                                const_memx_ptr_type_node,
                                NULL);

#define ITYP(T)                                                         \
  lang_hooks.types.type_for_size (TYPE_PRECISION (T), TYPE_UNSIGNED (T))

#define FX_FTYPE_FX(fx)                                                 \
  tree fx##r_ftype_##fx##r                                              \
    = build_function_type_list (node_##fx##r, node_##fx##r, NULL);      \
  tree fx##k_ftype_##fx##k                                              \
    = build_function_type_list (node_##fx##k, node_##fx##k, NULL)

#define FX_FTYPE_FX_INT(fx)                                             \
  tree fx##r_ftype_##fx##r_int                                          \
    = build_function_type_list (node_##fx##r, node_##fx##r,             \
                                integer_type_node, NULL);               \
  tree fx##k_ftype_##fx##k_int                                          \
    = build_function_type_list (node_##fx##k, node_##fx##k,             \
                                integer_type_node, NULL)

#define INT_FTYPE_FX(fx)                                                \
  tree int_ftype_##fx##r                                                \
    = build_function_type_list (integer_type_node, node_##fx##r, NULL); \
  tree int_ftype_##fx##k                                                \
    = build_function_type_list (integer_type_node, node_##fx##k, NULL)

#define INTX_FTYPE_FX(fx)                                               \
  tree int##fx##r_ftype_##fx##r                                         \
    = build_function_type_list (ITYP (node_##fx##r), node_##fx##r, NULL); \
  tree int##fx##k_ftype_##fx##k                                         \
    = build_function_type_list (ITYP (node_##fx##k), node_##fx##k, NULL)

#define FX_FTYPE_INTX(fx)                                               \
  tree fx##r_ftype_int##fx##r                                           \
    = build_function_type_list (node_##fx##r, ITYP (node_##fx##r), NULL); \
  tree fx##k_ftype_int##fx##k                                           \
    = build_function_type_list (node_##fx##k, ITYP (node_##fx##k), NULL)

  tree node_hr = short_fract_type_node;
  tree node_nr = fract_type_node;
  tree node_lr = long_fract_type_node;
  tree node_llr = long_long_fract_type_node;

  tree node_uhr = unsigned_short_fract_type_node;
  tree node_unr = unsigned_fract_type_node;
  tree node_ulr = unsigned_long_fract_type_node;
  tree node_ullr = unsigned_long_long_fract_type_node;

  tree node_hk = short_accum_type_node;
  tree node_nk = accum_type_node;
  tree node_lk = long_accum_type_node;
  tree node_llk = long_long_accum_type_node;

  tree node_uhk = unsigned_short_accum_type_node;
  tree node_unk = unsigned_accum_type_node;
  tree node_ulk = unsigned_long_accum_type_node;
  tree node_ullk = unsigned_long_long_accum_type_node;


  /* For absfx builtins.  */

  FX_FTYPE_FX (h);
  FX_FTYPE_FX (n);
  FX_FTYPE_FX (l);
  FX_FTYPE_FX (ll);

  /* For roundfx builtins.  */

  FX_FTYPE_FX_INT (h);
  FX_FTYPE_FX_INT (n);
  FX_FTYPE_FX_INT (l);
  FX_FTYPE_FX_INT (ll);

  FX_FTYPE_FX_INT (uh);
  FX_FTYPE_FX_INT (un);
  FX_FTYPE_FX_INT (ul);
  FX_FTYPE_FX_INT (ull);

  /* For countlsfx builtins.  */

  INT_FTYPE_FX (h);
  INT_FTYPE_FX (n);
  INT_FTYPE_FX (l);
  INT_FTYPE_FX (ll);

  INT_FTYPE_FX (uh);
  INT_FTYPE_FX (un);
  INT_FTYPE_FX (ul);
  INT_FTYPE_FX (ull);

  /* For bitsfx builtins.  */

  INTX_FTYPE_FX (h);
  INTX_FTYPE_FX (n);
  INTX_FTYPE_FX (l);
  INTX_FTYPE_FX (ll);

  INTX_FTYPE_FX (uh);
  INTX_FTYPE_FX (un);
  INTX_FTYPE_FX (ul);
  INTX_FTYPE_FX (ull);

  /* For fxbits builtins.  */

  FX_FTYPE_INTX (h);
  FX_FTYPE_INTX (n);
  FX_FTYPE_INTX (l);
  FX_FTYPE_INTX (ll);

  FX_FTYPE_INTX (uh);
  FX_FTYPE_INTX (un);
  FX_FTYPE_INTX (ul);
  FX_FTYPE_INTX (ull);


#define DEF_BUILTIN(NAME, N_ARGS, TYPE, CODE, LIBNAME)                  \
  {                                                                     \
    int id = AVR_BUILTIN_ ## NAME;                                      \
    const char *Name = "__builtin_avr_" #NAME;                          \
    char *name = (char*) alloca (1 + strlen (Name));                    \
                                                                        \
    gcc_assert (id < AVR_BUILTIN_COUNT);                                \
    avr_bdesc[id].fndecl                                                \
      = add_builtin_function (avr_tolower (name, Name), TYPE, id,       \
                              BUILT_IN_MD, LIBNAME, NULL_TREE);         \
  }
#include "builtins.def"
#undef DEF_BUILTIN

  avr_init_builtin_int24 ();
}


/* Subroutine of avr_expand_builtin to expand vanilla builtins
   with non-void result and 1 ... 3 arguments.  */

static rtx
avr_default_expand_builtin (enum insn_code icode, tree exp, rtx target)
{
  rtx pat, xop[3];
  int n_args = call_expr_nargs (exp);
  machine_mode tmode = insn_data[icode].operand[0].mode;

  gcc_assert (n_args >= 1 && n_args <= 3);

  if (target == NULL_RTX
      || GET_MODE (target) != tmode
      || !insn_data[icode].operand[0].predicate (target, tmode))
    {
      target = gen_reg_rtx (tmode);
    }

  for (int n = 0; n < n_args; n++)
    {
      tree arg = CALL_EXPR_ARG (exp, n);
      rtx op = expand_expr (arg, NULL_RTX, VOIDmode, EXPAND_NORMAL);
      machine_mode opmode = GET_MODE (op);
      machine_mode mode = insn_data[icode].operand[n + 1].mode;

      if ((opmode == SImode || opmode == VOIDmode) && mode == HImode)
        {
          opmode = HImode;
          op = gen_lowpart (HImode, op);
        }

      /* In case the insn wants input operands in modes different from
         the result, abort.  */

      gcc_assert (opmode == mode || opmode == VOIDmode);

      if (!insn_data[icode].operand[n + 1].predicate (op, mode))
        op = copy_to_mode_reg (mode, op);

      xop[n] = op;
    }

  switch (n_args)
    {
    case 1: pat = GEN_FCN (icode) (target, xop[0]); break;
    case 2: pat = GEN_FCN (icode) (target, xop[0], xop[1]); break;
    case 3: pat = GEN_FCN (icode) (target, xop[0], xop[1], xop[2]); break;

    default:
      gcc_unreachable();
    }

  if (pat == NULL_RTX)
    return NULL_RTX;

  emit_insn (pat);

  return target;
}


/* Implement `TARGET_EXPAND_BUILTIN'.  */
/* 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,
                    machine_mode mode ATTRIBUTE_UNUSED,
                    int ignore)
{
  tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
  const char *bname = IDENTIFIER_POINTER (DECL_NAME (fndecl));
  unsigned int id = DECL_MD_FUNCTION_CODE (fndecl);
  const struct avr_builtin_description *d = &avr_bdesc[id];
  tree arg0;
  rtx op0;

  gcc_assert (id < AVR_BUILTIN_COUNT);

  switch (id)
    {
    case AVR_BUILTIN_NOP:
      emit_insn (gen_nopv (GEN_INT (1)));
      return 0;

    case AVR_BUILTIN_DELAY_CYCLES:
      {
        arg0 = CALL_EXPR_ARG (exp, 0);
        op0 = expand_expr (arg0, NULL_RTX, VOIDmode, EXPAND_NORMAL);

        if (!CONST_INT_P (op0))
          error ("%s expects a compile time integer constant", bname);
        else
          avr_expand_delay_cycles (op0);

        return NULL_RTX;
      }

    case AVR_BUILTIN_NOPS:
      {
        arg0 = CALL_EXPR_ARG (exp, 0);
        op0 = expand_expr (arg0, NULL_RTX, VOIDmode, EXPAND_NORMAL);

        if (!CONST_INT_P (op0))
          error ("%s expects a compile time integer constant", bname);
        else
          avr_expand_nops (op0);

        return NULL_RTX;
      }

    case AVR_BUILTIN_INSERT_BITS:
      {
        arg0 = CALL_EXPR_ARG (exp, 0);
        op0 = expand_expr (arg0, NULL_RTX, VOIDmode, EXPAND_NORMAL);

        if (!CONST_INT_P (op0))
          {
            error ("%s expects a compile time long integer constant"
                   " as first argument", bname);
            return target;
          }

        break;
      }

    case AVR_BUILTIN_ROUNDHR:   case AVR_BUILTIN_ROUNDUHR:
    case AVR_BUILTIN_ROUNDR:    case AVR_BUILTIN_ROUNDUR:
    case AVR_BUILTIN_ROUNDLR:   case AVR_BUILTIN_ROUNDULR:
    case AVR_BUILTIN_ROUNDLLR:  case AVR_BUILTIN_ROUNDULLR:

    case AVR_BUILTIN_ROUNDHK:   case AVR_BUILTIN_ROUNDUHK:
    case AVR_BUILTIN_ROUNDK:    case AVR_BUILTIN_ROUNDUK:
    case AVR_BUILTIN_ROUNDLK:   case AVR_BUILTIN_ROUNDULK:
    case AVR_BUILTIN_ROUNDLLK:  case AVR_BUILTIN_ROUNDULLK:

      /* Warn about odd rounding.  Rounding points >= FBIT will have
         no effect.  */

      if (TREE_CODE (CALL_EXPR_ARG (exp, 1)) != INTEGER_CST)
        break;

      int rbit = (int) TREE_INT_CST_LOW (CALL_EXPR_ARG (exp, 1));

      if (rbit >= (int) GET_MODE_FBIT (mode))
        {
          warning (OPT_Wextra, "rounding to %d bits has no effect for "
                   "fixed-point value with %d fractional bits",
                   rbit, GET_MODE_FBIT (mode));

          return expand_expr (CALL_EXPR_ARG (exp, 0), NULL_RTX, mode,
                              EXPAND_NORMAL);
        }
      else if (rbit <= - (int) GET_MODE_IBIT (mode))
        {
          warning (0, "rounding result will always be 0");
          return CONST0_RTX (mode);
        }

      /* The rounding points RP satisfies now:  -IBIT < RP < FBIT.

         TR 18037 only specifies results for  RP > 0.  However, the
         remaining cases of  -IBIT < RP <= 0  can easily be supported
         without any additional overhead.  */

      break; /* round */
    }

  /* No fold found and no insn:  Call support function from libgcc.  */

  if (d->icode == CODE_FOR_nothing
      && DECL_ASSEMBLER_NAME (get_callee_fndecl (exp)) != NULL_TREE)
    {
      return expand_call (exp, target, ignore);
    }

  /* No special treatment needed: vanilla expand.  */

  gcc_assert (d->icode != CODE_FOR_nothing);
  gcc_assert (d->n_args == call_expr_nargs (exp));

  if (d->n_args == 0)
    {
      emit_insn ((GEN_FCN (d->icode)) (target));
      return NULL_RTX;
    }

  return avr_default_expand_builtin (d->icode, exp, target);
}


/* Helper for `avr_fold_builtin' that folds  absfx (FIXED_CST).  */

static tree
avr_fold_absfx (tree tval)
{
  if (FIXED_CST != TREE_CODE (tval))
    return NULL_TREE;

  /* Our fixed-points have no padding:  Use double_int payload directly.  */

  FIXED_VALUE_TYPE fval = TREE_FIXED_CST (tval);
  unsigned int bits = GET_MODE_BITSIZE (fval.mode);
  double_int ival = fval.data.sext (bits);

  if (!ival.is_negative())
    return tval;

  /* ISO/IEC TR 18037, 7.18a.6.2:  The absfx functions are saturating.  */

  fval.data = (ival == double_int::min_value (bits, false).sext (bits))
    ? double_int::max_value (bits, false)
    : -ival;

  return build_fixed (TREE_TYPE (tval), fval);
}


/* Implement `TARGET_FOLD_BUILTIN'.  */

static tree
avr_fold_builtin (tree fndecl, int n_args ATTRIBUTE_UNUSED, tree *arg,
                  bool ignore ATTRIBUTE_UNUSED)
{
  unsigned int fcode = DECL_MD_FUNCTION_CODE (fndecl);
  tree val_type = TREE_TYPE (TREE_TYPE (fndecl));

  if (!optimize)
    return NULL_TREE;

  switch (fcode)
    {
    default:
      break;

    case AVR_BUILTIN_SWAP:
      {
        return fold_build2 (LROTATE_EXPR, val_type, arg[0],
                            build_int_cst (val_type, 4));
      }

    case AVR_BUILTIN_ABSHR:
    case AVR_BUILTIN_ABSR:
    case AVR_BUILTIN_ABSLR:
    case AVR_BUILTIN_ABSLLR:

    case AVR_BUILTIN_ABSHK:
    case AVR_BUILTIN_ABSK:
    case AVR_BUILTIN_ABSLK:
    case AVR_BUILTIN_ABSLLK:
      /* GCC is not good with folding ABS for fixed-point.  Do it by hand.  */

      return avr_fold_absfx (arg[0]);

    case AVR_BUILTIN_BITSHR:    case AVR_BUILTIN_HRBITS:
    case AVR_BUILTIN_BITSHK:    case AVR_BUILTIN_HKBITS:
    case AVR_BUILTIN_BITSUHR:   case AVR_BUILTIN_UHRBITS:
    case AVR_BUILTIN_BITSUHK:   case AVR_BUILTIN_UHKBITS:

    case AVR_BUILTIN_BITSR:     case AVR_BUILTIN_RBITS:
    case AVR_BUILTIN_BITSK:     case AVR_BUILTIN_KBITS:
    case AVR_BUILTIN_BITSUR:    case AVR_BUILTIN_URBITS:
    case AVR_BUILTIN_BITSUK:    case AVR_BUILTIN_UKBITS:

    case AVR_BUILTIN_BITSLR:    case AVR_BUILTIN_LRBITS:
    case AVR_BUILTIN_BITSLK:    case AVR_BUILTIN_LKBITS:
    case AVR_BUILTIN_BITSULR:   case AVR_BUILTIN_ULRBITS:
    case AVR_BUILTIN_BITSULK:   case AVR_BUILTIN_ULKBITS:

    case AVR_BUILTIN_BITSLLR:   case AVR_BUILTIN_LLRBITS:
    case AVR_BUILTIN_BITSLLK:   case AVR_BUILTIN_LLKBITS:
    case AVR_BUILTIN_BITSULLR:  case AVR_BUILTIN_ULLRBITS:
    case AVR_BUILTIN_BITSULLK:  case AVR_BUILTIN_ULLKBITS:

      gcc_assert (TYPE_PRECISION (val_type)
                  == TYPE_PRECISION (TREE_TYPE (arg[0])));

      return build1 (VIEW_CONVERT_EXPR, val_type, arg[0]);

    case AVR_BUILTIN_INSERT_BITS:
      {
        tree tbits = arg[1];
        tree tval = arg[2];
        tree tmap;
        tree map_type = TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (fndecl)));
        unsigned int map;
        bool changed = false;
        avr_map_op_t best_g;

        if (TREE_CODE (arg[0]) != INTEGER_CST)
          {
            /* No constant as first argument: Don't fold this and run into
               error in avr_expand_builtin.  */

            break;
          }

        tmap = wide_int_to_tree (map_type, wi::to_wide (arg[0]));
        map = TREE_INT_CST_LOW (tmap);

        if (TREE_CODE (tval) != INTEGER_CST
	    && avr_map_metric (map, MAP_MASK_PREIMAGE_F) == 0)
          {
            /* There are no F in the map, i.e. 3rd operand is unused.
               Replace that argument with some constant to render
               respective input unused.  */

            tval = build_int_cst (val_type, 0);
            changed = true;
          }

        if (TREE_CODE (tbits) != INTEGER_CST
	    && avr_map_metric (map, MAP_PREIMAGE_0_7) == 0)
          {
            /* Similar for the bits to be inserted. If they are unused,
               we can just as well pass 0.  */

            tbits = build_int_cst (val_type, 0);
          }

        if (TREE_CODE (tbits) == INTEGER_CST)
          {
            /* Inserting bits known at compile time is easy and can be
               performed by AND and OR with appropriate masks.  */

            int bits = TREE_INT_CST_LOW (tbits);
            int mask_ior = 0, mask_and = 0xff;

            for (size_t i = 0; i < 8; i++)
              {
                int mi = avr_map (map, i);

                if (mi < 8)
                  {
                    if (bits & (1 << mi))     mask_ior |=  (1 << i);
                    else                      mask_and &= ~(1 << i);
                  }
              }

            tval = fold_build2 (BIT_IOR_EXPR, val_type, tval,
                                build_int_cst (val_type, mask_ior));
            return fold_build2 (BIT_AND_EXPR, val_type, tval,
                                build_int_cst (val_type, mask_and));
          }

        if (changed)
          return build_call_expr (fndecl, 3, tmap, tbits, tval);

        /* If bits don't change their position we can use vanilla logic
           to merge the two arguments.  */

	if (avr_map_metric (map, MAP_NONFIXED_0_7) == 0)
          {
            int mask_f = avr_map_metric (map, MAP_MASK_PREIMAGE_F);
            tree tres, tmask = build_int_cst (val_type, mask_f ^ 0xff);

            tres = fold_build2 (BIT_XOR_EXPR, val_type, tbits, tval);
            tres = fold_build2 (BIT_AND_EXPR, val_type, tres, tmask);
            return fold_build2 (BIT_XOR_EXPR, val_type, tres, tval);
          }

        /* Try to decomposing map to reduce overall cost.  */

        if (avr_log.builtin)
          avr_edump ("\n%?: %x\n%?: ROL cost: ", map);

        best_g = avr_map_op[0];
        best_g.cost = 1000;

        for (size_t i = 0; i < ARRAY_SIZE (avr_map_op); i++)
          {
            avr_map_op_t g
              = avr_map_decompose (map, avr_map_op + i,
                                   TREE_CODE (tval) == INTEGER_CST);

            if (g.cost >= 0 && g.cost < best_g.cost)
              best_g = g;
          }

        if (avr_log.builtin)
          avr_edump ("\n");

        if (best_g.arg == 0)
          /* No optimization found */
          break;

        /* Apply operation G to the 2nd argument.  */

        if (avr_log.builtin)
          avr_edump ("%?: using OP(%s%d, %x) cost %d\n",
                     best_g.str, best_g.arg, best_g.map, best_g.cost);

        /* Do right-shifts arithmetically: They copy the MSB instead of
           shifting in a non-usable value (0) as with logic right-shift.  */

        tbits = fold_convert (signed_char_type_node, tbits);
        tbits = fold_build2 (best_g.code, signed_char_type_node, tbits,
                             build_int_cst (val_type, best_g.arg));
        tbits = fold_convert (val_type, tbits);

        /* Use map o G^-1 instead of original map to undo the effect of G.  */

        tmap = wide_int_to_tree (map_type, best_g.map);

        return build_call_expr (fndecl, 3, tmap, tbits, tval);
      } /* AVR_BUILTIN_INSERT_BITS */
    }

  return NULL_TREE;
}

/* Prepend to CLOBBERS hard registers that are automatically clobbered
   for an asm. We do this for CC_REGNUM to maintain source compatibility
   with the original cc0-based compiler.  */

static rtx_insn *
avr_md_asm_adjust (vec<rtx> &/*outputs*/, vec<rtx> &/*inputs*/,
                   vec<machine_mode> & /*input_modes*/,
                   vec<const char *> &/*constraints*/,
                   vec<rtx> &clobbers, HARD_REG_SET &clobbered_regs,
		   location_t /*loc*/)
{
  clobbers.safe_push (cc_reg_rtx);
  SET_HARD_REG_BIT (clobbered_regs, REG_CC);
  return NULL;
}


/* Worker function for `FLOAT_LIB_COMPARE_RETURNS_BOOL'.  */

bool
avr_float_lib_compare_returns_bool (machine_mode mode, enum rtx_code)
{
  if (mode == DFmode)
    {
#if WITH_DOUBLE_COMPARISON == 2
      return true;
#endif
    }

  // This is the GCC default and also what AVR-LibC implements.
  return false;
}



/* Initialize the GCC target structure.  */

#undef  TARGET_ASM_ALIGNED_HI_OP
#define TARGET_ASM_ALIGNED_HI_OP "\t.word\t"
#undef  TARGET_ASM_ALIGNED_SI_OP
#define TARGET_ASM_ALIGNED_SI_OP "\t.long\t"
#undef  TARGET_ASM_UNALIGNED_HI_OP
#define TARGET_ASM_UNALIGNED_HI_OP "\t.word\t"
#undef  TARGET_ASM_UNALIGNED_SI_OP
#define TARGET_ASM_UNALIGNED_SI_OP "\t.long\t"
#undef  TARGET_ASM_INTEGER
#define TARGET_ASM_INTEGER avr_assemble_integer
#undef  TARGET_ASM_FILE_START
#define TARGET_ASM_FILE_START avr_file_start
#undef  TARGET_ASM_FILE_END
#define TARGET_ASM_FILE_END avr_file_end

#undef  TARGET_ASM_FUNCTION_END_PROLOGUE
#define TARGET_ASM_FUNCTION_END_PROLOGUE avr_asm_function_end_prologue
#undef  TARGET_ASM_FUNCTION_BEGIN_EPILOGUE
#define TARGET_ASM_FUNCTION_BEGIN_EPILOGUE avr_asm_function_begin_epilogue

#undef  TARGET_FUNCTION_VALUE
#define TARGET_FUNCTION_VALUE avr_function_value
#undef  TARGET_LIBCALL_VALUE
#define TARGET_LIBCALL_VALUE avr_libcall_value
#undef  TARGET_FUNCTION_VALUE_REGNO_P
#define TARGET_FUNCTION_VALUE_REGNO_P avr_function_value_regno_p

#undef  TARGET_ATTRIBUTE_TABLE
#define TARGET_ATTRIBUTE_TABLE avr_attribute_table
#undef  TARGET_INSERT_ATTRIBUTES
#define TARGET_INSERT_ATTRIBUTES avr_insert_attributes
#undef  TARGET_SECTION_TYPE_FLAGS
#define TARGET_SECTION_TYPE_FLAGS avr_section_type_flags

#undef  TARGET_ASM_NAMED_SECTION
#define TARGET_ASM_NAMED_SECTION avr_asm_named_section
#undef  TARGET_ASM_INIT_SECTIONS
#define TARGET_ASM_INIT_SECTIONS avr_asm_init_sections
#undef  TARGET_ENCODE_SECTION_INFO
#define TARGET_ENCODE_SECTION_INFO avr_encode_section_info
#undef  TARGET_ASM_SELECT_SECTION
#define TARGET_ASM_SELECT_SECTION avr_asm_select_section

#undef  TARGET_ASM_FINAL_POSTSCAN_INSN
#define TARGET_ASM_FINAL_POSTSCAN_INSN avr_asm_final_postscan_insn

#undef  TARGET_REGISTER_MOVE_COST
#define TARGET_REGISTER_MOVE_COST avr_register_move_cost
#undef  TARGET_MEMORY_MOVE_COST
#define TARGET_MEMORY_MOVE_COST avr_memory_move_cost
#undef  TARGET_RTX_COSTS
#define TARGET_RTX_COSTS avr_rtx_costs
#undef  TARGET_ADDRESS_COST
#define TARGET_ADDRESS_COST avr_address_cost
#undef  TARGET_MACHINE_DEPENDENT_REORG
#define TARGET_MACHINE_DEPENDENT_REORG avr_reorg
#undef  TARGET_FUNCTION_ARG
#define TARGET_FUNCTION_ARG avr_function_arg
#undef  TARGET_FUNCTION_ARG_ADVANCE
#define TARGET_FUNCTION_ARG_ADVANCE avr_function_arg_advance

#undef  TARGET_SET_CURRENT_FUNCTION
#define TARGET_SET_CURRENT_FUNCTION avr_set_current_function

#undef  TARGET_RETURN_IN_MEMORY
#define TARGET_RETURN_IN_MEMORY avr_return_in_memory

#undef  TARGET_STRICT_ARGUMENT_NAMING
#define TARGET_STRICT_ARGUMENT_NAMING hook_bool_CUMULATIVE_ARGS_true

#undef TARGET_CONDITIONAL_REGISTER_USAGE
#define TARGET_CONDITIONAL_REGISTER_USAGE avr_conditional_register_usage

#undef TARGET_HARD_REGNO_NREGS
#define TARGET_HARD_REGNO_NREGS avr_hard_regno_nregs

#undef  TARGET_HARD_REGNO_MODE_OK
#define TARGET_HARD_REGNO_MODE_OK avr_hard_regno_mode_ok
#undef  TARGET_HARD_REGNO_SCRATCH_OK
#define TARGET_HARD_REGNO_SCRATCH_OK avr_hard_regno_scratch_ok
#undef  TARGET_HARD_REGNO_CALL_PART_CLOBBERED
#define TARGET_HARD_REGNO_CALL_PART_CLOBBERED \
  avr_hard_regno_call_part_clobbered

#undef  TARGET_CASE_VALUES_THRESHOLD
#define TARGET_CASE_VALUES_THRESHOLD avr_case_values_threshold

#undef  TARGET_FRAME_POINTER_REQUIRED
#define TARGET_FRAME_POINTER_REQUIRED avr_frame_pointer_required_p
#undef  TARGET_CAN_ELIMINATE
#define TARGET_CAN_ELIMINATE avr_can_eliminate

#undef  TARGET_ALLOCATE_STACK_SLOTS_FOR_ARGS
#define TARGET_ALLOCATE_STACK_SLOTS_FOR_ARGS avr_allocate_stack_slots_for_args

#undef TARGET_WARN_FUNC_RETURN
#define TARGET_WARN_FUNC_RETURN avr_warn_func_return

#undef  TARGET_CLASS_LIKELY_SPILLED_P
#define TARGET_CLASS_LIKELY_SPILLED_P avr_class_likely_spilled_p

#undef  TARGET_CLASS_MAX_NREGS
#define TARGET_CLASS_MAX_NREGS avr_class_max_nregs

#undef  TARGET_OPTION_OVERRIDE
#define TARGET_OPTION_OVERRIDE avr_option_override

#undef  TARGET_CANNOT_MODIFY_JUMPS_P
#define TARGET_CANNOT_MODIFY_JUMPS_P avr_cannot_modify_jumps_p

#undef  TARGET_FUNCTION_OK_FOR_SIBCALL
#define TARGET_FUNCTION_OK_FOR_SIBCALL avr_function_ok_for_sibcall

#undef  TARGET_INIT_BUILTINS
#define TARGET_INIT_BUILTINS avr_init_builtins

#undef  TARGET_BUILTIN_DECL
#define TARGET_BUILTIN_DECL avr_builtin_decl

#undef  TARGET_EXPAND_BUILTIN
#define TARGET_EXPAND_BUILTIN avr_expand_builtin

#undef  TARGET_FOLD_BUILTIN
#define TARGET_FOLD_BUILTIN avr_fold_builtin

#undef  TARGET_SCALAR_MODE_SUPPORTED_P
#define TARGET_SCALAR_MODE_SUPPORTED_P avr_scalar_mode_supported_p

#undef  TARGET_BUILD_BUILTIN_VA_LIST
#define TARGET_BUILD_BUILTIN_VA_LIST avr_build_builtin_va_list

#undef  TARGET_FIXED_POINT_SUPPORTED_P
#define TARGET_FIXED_POINT_SUPPORTED_P hook_bool_void_true

#undef  TARGET_CONVERT_TO_TYPE
#define TARGET_CONVERT_TO_TYPE avr_convert_to_type

#undef TARGET_LRA_P
#define TARGET_LRA_P hook_bool_void_false

#undef  TARGET_ADDR_SPACE_SUBSET_P
#define TARGET_ADDR_SPACE_SUBSET_P avr_addr_space_subset_p

#undef  TARGET_ADDR_SPACE_CONVERT
#define TARGET_ADDR_SPACE_CONVERT avr_addr_space_convert

#undef  TARGET_ADDR_SPACE_ADDRESS_MODE
#define TARGET_ADDR_SPACE_ADDRESS_MODE avr_addr_space_address_mode

#undef  TARGET_ADDR_SPACE_POINTER_MODE
#define TARGET_ADDR_SPACE_POINTER_MODE avr_addr_space_pointer_mode

#undef  TARGET_ADDR_SPACE_LEGITIMATE_ADDRESS_P
#define TARGET_ADDR_SPACE_LEGITIMATE_ADDRESS_P  \
  avr_addr_space_legitimate_address_p

#undef  TARGET_ADDR_SPACE_LEGITIMIZE_ADDRESS
#define TARGET_ADDR_SPACE_LEGITIMIZE_ADDRESS avr_addr_space_legitimize_address

#undef  TARGET_ADDR_SPACE_DIAGNOSE_USAGE
#define TARGET_ADDR_SPACE_DIAGNOSE_USAGE avr_addr_space_diagnose_usage

#undef  TARGET_MODE_DEPENDENT_ADDRESS_P
#define TARGET_MODE_DEPENDENT_ADDRESS_P avr_mode_dependent_address_p

#undef  TARGET_PRINT_OPERAND
#define TARGET_PRINT_OPERAND avr_print_operand
#undef  TARGET_PRINT_OPERAND_ADDRESS
#define TARGET_PRINT_OPERAND_ADDRESS avr_print_operand_address
#undef  TARGET_PRINT_OPERAND_PUNCT_VALID_P
#define TARGET_PRINT_OPERAND_PUNCT_VALID_P avr_print_operand_punct_valid_p

#undef TARGET_USE_BY_PIECES_INFRASTRUCTURE_P
#define TARGET_USE_BY_PIECES_INFRASTRUCTURE_P \
  avr_use_by_pieces_infrastructure_p

#undef  TARGET_LEGITIMATE_COMBINED_INSN
#define TARGET_LEGITIMATE_COMBINED_INSN avr_legitimate_combined_insn

#undef  TARGET_STARTING_FRAME_OFFSET
#define TARGET_STARTING_FRAME_OFFSET avr_starting_frame_offset

#undef  TARGET_MD_ASM_ADJUST
#define TARGET_MD_ASM_ADJUST avr_md_asm_adjust

struct gcc_target targetm = TARGET_INITIALIZER;


#include "gt-avr.h"
