/* Default target hook functions.
   Copyright (C) 2003-2022 Free Software Foundation, Inc.

This file is part of GCC.

GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.

GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
for more details.

You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3.  If not see
<http://www.gnu.org/licenses/>.  */

/* The migration of target macros to target hooks works as follows:

   1. Create a target hook that uses the existing target macros to
      implement the same functionality.

   2. Convert all the MI files to use the hook instead of the macro.

   3. Repeat for a majority of the remaining target macros.  This will
      take some time.

   4. Tell target maintainers to start migrating.

   5. Eventually convert the backends to override the hook instead of
      defining the macros.  This will take some time too.

   6. TBD when, poison the macros.  Unmigrated targets will break at
      this point.

   Note that we expect steps 1-3 to be done by the people that
   understand what the MI does with each macro, and step 5 to be done
   by the target maintainers for their respective targets.

   Note that steps 1 and 2 don't have to be done together, but no
   target can override the new hook until step 2 is complete for it.

   Once the macros are poisoned, we will revert to the old migration
   rules - migrate the macro, callers, and targets all at once.  This
   comment can thus be removed at that point.  */

#include "config.h"
#include "system.h"
#include "coretypes.h"
#include "target.h"
#include "function.h"
#include "rtl.h"
#include "tree.h"
#include "tree-ssa-alias.h"
#include "gimple-expr.h"
#include "memmodel.h"
#include "backend.h"
#include "emit-rtl.h"
#include "df.h"
#include "tm_p.h"
#include "stringpool.h"
#include "tree-vrp.h"
#include "tree-ssanames.h"
#include "profile-count.h"
#include "optabs.h"
#include "regs.h"
#include "recog.h"
#include "diagnostic-core.h"
#include "fold-const.h"
#include "stor-layout.h"
#include "varasm.h"
#include "flags.h"
#include "explow.h"
#include "expmed.h"
#include "calls.h"
#include "expr.h"
#include "output.h"
#include "common/common-target.h"
#include "reload.h"
#include "intl.h"
#include "opts.h"
#include "gimplify.h"
#include "predict.h"
#include "real.h"
#include "langhooks.h"
#include "sbitmap.h"
#include "function-abi.h"
#include "attribs.h"
#include "asan.h"
#include "emit-rtl.h"
#include "gimple.h"
#include "cfgloop.h"
#include "tree-vectorizer.h"

bool
default_legitimate_address_p (machine_mode mode ATTRIBUTE_UNUSED,
			      rtx addr ATTRIBUTE_UNUSED,
			      bool strict ATTRIBUTE_UNUSED)
{
#ifdef GO_IF_LEGITIMATE_ADDRESS
  /* Defer to the old implementation using a goto.  */
  if (strict)
    return strict_memory_address_p (mode, addr);
  else
    return memory_address_p (mode, addr);
#else
  gcc_unreachable ();
#endif
}

void
default_external_libcall (rtx fun ATTRIBUTE_UNUSED)
{
#ifdef ASM_OUTPUT_EXTERNAL_LIBCALL
  ASM_OUTPUT_EXTERNAL_LIBCALL (asm_out_file, fun);
#endif
}

int
default_unspec_may_trap_p (const_rtx x, unsigned flags)
{
  int i;

  /* Any floating arithmetic may trap.  */
  if ((SCALAR_FLOAT_MODE_P (GET_MODE (x)) && flag_trapping_math))
    return 1;

  for (i = 0; i < XVECLEN (x, 0); ++i)
    {
      if (may_trap_p_1 (XVECEXP (x, 0, i), flags))
	return 1;
    }

  return 0;
}

machine_mode
default_promote_function_mode (const_tree type ATTRIBUTE_UNUSED,
			       machine_mode mode,
			       int *punsignedp ATTRIBUTE_UNUSED,
			       const_tree funtype ATTRIBUTE_UNUSED,
			       int for_return ATTRIBUTE_UNUSED)
{
  if (type != NULL_TREE && for_return == 2)
    return promote_mode (type, mode, punsignedp);
  return mode;
}

machine_mode
default_promote_function_mode_always_promote (const_tree type,
					      machine_mode mode,
					      int *punsignedp,
					      const_tree funtype ATTRIBUTE_UNUSED,
					      int for_return ATTRIBUTE_UNUSED)
{
  return promote_mode (type, mode, punsignedp);
}

machine_mode
default_cc_modes_compatible (machine_mode m1, machine_mode m2)
{
  if (m1 == m2)
    return m1;
  return VOIDmode;
}

bool
default_return_in_memory (const_tree type,
			  const_tree fntype ATTRIBUTE_UNUSED)
{
  return (TYPE_MODE (type) == BLKmode);
}

rtx
default_legitimize_address (rtx x, rtx orig_x ATTRIBUTE_UNUSED,
			    machine_mode mode ATTRIBUTE_UNUSED)
{
  return x;
}

bool
default_legitimize_address_displacement (rtx *, rtx *, poly_int64,
					 machine_mode)
{
  return false;
}

bool
default_const_not_ok_for_debug_p (rtx x)
{
  if (GET_CODE (x) == UNSPEC)
    return true;
  return false;
}

rtx
default_expand_builtin_saveregs (void)
{
  error ("%<__builtin_saveregs%> not supported by this target");
  return const0_rtx;
}

void
default_setup_incoming_varargs (cumulative_args_t,
				const function_arg_info &, int *, int)
{
}

/* The default implementation of TARGET_BUILTIN_SETJMP_FRAME_VALUE.  */

rtx
default_builtin_setjmp_frame_value (void)
{
  return virtual_stack_vars_rtx;
}

/* Generic hook that takes a CUMULATIVE_ARGS pointer and returns false.  */

bool
hook_bool_CUMULATIVE_ARGS_false (cumulative_args_t ca ATTRIBUTE_UNUSED)
{
  return false;
}

bool
default_pretend_outgoing_varargs_named (cumulative_args_t ca ATTRIBUTE_UNUSED)
{
  return (targetm.calls.setup_incoming_varargs
	  != default_setup_incoming_varargs);
}

scalar_int_mode
default_eh_return_filter_mode (void)
{
  return targetm.unwind_word_mode ();
}

scalar_int_mode
default_libgcc_cmp_return_mode (void)
{
  return word_mode;
}

scalar_int_mode
default_libgcc_shift_count_mode (void)
{
  return word_mode;
}

scalar_int_mode
default_unwind_word_mode (void)
{
  return word_mode;
}

/* The default implementation of TARGET_SHIFT_TRUNCATION_MASK.  */

unsigned HOST_WIDE_INT
default_shift_truncation_mask (machine_mode mode)
{
  return SHIFT_COUNT_TRUNCATED ? GET_MODE_UNIT_BITSIZE (mode) - 1 : 0;
}

/* The default implementation of TARGET_MIN_DIVISIONS_FOR_RECIP_MUL.  */

unsigned int
default_min_divisions_for_recip_mul (machine_mode mode ATTRIBUTE_UNUSED)
{
  return have_insn_for (DIV, mode) ? 3 : 2;
}

/* The default implementation of TARGET_MODE_REP_EXTENDED.  */

int
default_mode_rep_extended (scalar_int_mode, scalar_int_mode)
{
  return UNKNOWN;
}

/* Generic hook that takes a CUMULATIVE_ARGS pointer and returns true.  */

bool
hook_bool_CUMULATIVE_ARGS_true (cumulative_args_t a ATTRIBUTE_UNUSED)
{
  return true;
}

/* Return machine mode for non-standard suffix
   or VOIDmode if non-standard suffixes are unsupported.  */
machine_mode
default_mode_for_suffix (char suffix ATTRIBUTE_UNUSED)
{
  return VOIDmode;
}

/* The generic C++ ABI specifies this is a 64-bit value.  */
tree
default_cxx_guard_type (void)
{
  return long_long_integer_type_node;
}

/* Returns the size of the cookie to use when allocating an array
   whose elements have the indicated TYPE.  Assumes that it is already
   known that a cookie is needed.  */

tree
default_cxx_get_cookie_size (tree type)
{
  tree cookie_size;

  /* We need to allocate an additional max (sizeof (size_t), alignof
     (true_type)) bytes.  */
  tree sizetype_size;
  tree type_align;

  sizetype_size = size_in_bytes (sizetype);
  type_align = size_int (TYPE_ALIGN_UNIT (type));
  if (tree_int_cst_lt (type_align, sizetype_size))
    cookie_size = sizetype_size;
  else
    cookie_size = type_align;

  return cookie_size;
}

/* Return true if a parameter must be passed by reference.  This version
   of the TARGET_PASS_BY_REFERENCE hook uses just MUST_PASS_IN_STACK.  */

bool
hook_pass_by_reference_must_pass_in_stack (cumulative_args_t,
					   const function_arg_info &arg)
{
  return targetm.calls.must_pass_in_stack (arg);
}

/* Return true if a parameter follows callee copies conventions.  This
   version of the hook is true for all named arguments.  */

bool
hook_callee_copies_named (cumulative_args_t, const function_arg_info &arg)
{
  return arg.named;
}

/* Emit to STREAM the assembler syntax for insn operand X.  */

void
default_print_operand (FILE *stream ATTRIBUTE_UNUSED, rtx x ATTRIBUTE_UNUSED,
		       int code ATTRIBUTE_UNUSED)
{
#ifdef PRINT_OPERAND
  PRINT_OPERAND (stream, x, code);
#else
  gcc_unreachable ();
#endif
}

/* Emit to STREAM the assembler syntax for an insn operand whose memory
   address is X.  */

void
default_print_operand_address (FILE *stream ATTRIBUTE_UNUSED,
			       machine_mode /*mode*/,
			       rtx x ATTRIBUTE_UNUSED)
{
#ifdef PRINT_OPERAND_ADDRESS
  PRINT_OPERAND_ADDRESS (stream, x);
#else
  gcc_unreachable ();
#endif
}

/* Return true if CODE is a valid punctuation character for the
   `print_operand' hook.  */

bool
default_print_operand_punct_valid_p (unsigned char code ATTRIBUTE_UNUSED)
{
#ifdef PRINT_OPERAND_PUNCT_VALID_P
  return PRINT_OPERAND_PUNCT_VALID_P (code);
#else
  return false;
#endif
}

/* The default implementation of TARGET_MANGLE_ASSEMBLER_NAME.  */
tree
default_mangle_assembler_name (const char *name ATTRIBUTE_UNUSED)
{
  const char *skipped = name + (*name == '*' ? 1 : 0);
  const char *stripped = targetm.strip_name_encoding (skipped);
  if (*name != '*' && user_label_prefix[0])
    stripped = ACONCAT ((user_label_prefix, stripped, NULL));
  return get_identifier (stripped);
}

/* The default implementation of TARGET_TRANSLATE_MODE_ATTRIBUTE.  */

machine_mode
default_translate_mode_attribute (machine_mode mode)
{
  return mode;
}

/* True if MODE is valid for the target.  By "valid", we mean able to
   be manipulated in non-trivial ways.  In particular, this means all
   the arithmetic is supported.

   By default we guess this means that any C type is supported.  If
   we can't map the mode back to a type that would be available in C,
   then reject it.  Special case, here, is the double-word arithmetic
   supported by optabs.cc.  */

bool
default_scalar_mode_supported_p (scalar_mode mode)
{
  int precision = GET_MODE_PRECISION (mode);

  switch (GET_MODE_CLASS (mode))
    {
    case MODE_PARTIAL_INT:
    case MODE_INT:
      if (precision == CHAR_TYPE_SIZE)
	return true;
      if (precision == SHORT_TYPE_SIZE)
	return true;
      if (precision == INT_TYPE_SIZE)
	return true;
      if (precision == LONG_TYPE_SIZE)
	return true;
      if (precision == LONG_LONG_TYPE_SIZE)
	return true;
      if (precision == 2 * BITS_PER_WORD)
	return true;
      return false;

    case MODE_FLOAT:
      if (precision == FLOAT_TYPE_SIZE)
	return true;
      if (precision == DOUBLE_TYPE_SIZE)
	return true;
      if (precision == LONG_DOUBLE_TYPE_SIZE)
	return true;
      return false;

    case MODE_DECIMAL_FLOAT:
    case MODE_FRACT:
    case MODE_UFRACT:
    case MODE_ACCUM:
    case MODE_UACCUM:
      return false;

    default:
      gcc_unreachable ();
    }
}

/* Return true if libgcc supports floating-point mode MODE (known to
   be supported as a scalar mode).  */

bool
default_libgcc_floating_mode_supported_p (scalar_float_mode mode)
{
  switch (mode)
    {
#ifdef HAVE_SFmode
    case E_SFmode:
#endif
#ifdef HAVE_DFmode
    case E_DFmode:
#endif
#ifdef HAVE_XFmode
    case E_XFmode:
#endif
#ifdef HAVE_TFmode
    case E_TFmode:
#endif
      return true;

    default:
      return false;
    }
}

/* Return the machine mode to use for the type _FloatN, if EXTENDED is
   false, or _FloatNx, if EXTENDED is true, or VOIDmode if not
   supported.  */
opt_scalar_float_mode
default_floatn_mode (int n, bool extended)
{
  if (extended)
    {
      opt_scalar_float_mode cand1, cand2;
      scalar_float_mode mode;
      switch (n)
	{
	case 32:
#ifdef HAVE_DFmode
	  cand1 = DFmode;
#endif
	  break;

	case 64:
#ifdef HAVE_XFmode
	  cand1 = XFmode;
#endif
#ifdef HAVE_TFmode
	  cand2 = TFmode;
#endif
	  break;

	case 128:
	  break;

	default:
	  /* Those are the only valid _FloatNx types.  */
	  gcc_unreachable ();
	}
      if (cand1.exists (&mode)
	  && REAL_MODE_FORMAT (mode)->ieee_bits > n
	  && targetm.scalar_mode_supported_p (mode)
	  && targetm.libgcc_floating_mode_supported_p (mode))
	return cand1;
      if (cand2.exists (&mode)
	  && REAL_MODE_FORMAT (mode)->ieee_bits > n
	  && targetm.scalar_mode_supported_p (mode)
	  && targetm.libgcc_floating_mode_supported_p (mode))
	return cand2;
    }
  else
    {
      opt_scalar_float_mode cand;
      scalar_float_mode mode;
      switch (n)
	{
	case 16:
	  /* Always enable _Float16 if we have basic support for the mode.
	     Targets can control the range and precision of operations on
	     the _Float16 type using TARGET_C_EXCESS_PRECISION.  */
#ifdef HAVE_HFmode
	  cand = HFmode;
#endif
	  break;

	case 32:
#ifdef HAVE_SFmode
	  cand = SFmode;
#endif
	  break;

	case 64:
#ifdef HAVE_DFmode
	  cand = DFmode;
#endif
	  break;

	case 128:
#ifdef HAVE_TFmode
	  cand = TFmode;
#endif
	  break;

	default:
	  break;
	}
      if (cand.exists (&mode)
	  && REAL_MODE_FORMAT (mode)->ieee_bits == n
	  && targetm.scalar_mode_supported_p (mode)
	  && targetm.libgcc_floating_mode_supported_p (mode))
	return cand;
    }
  return opt_scalar_float_mode ();
}

/* Define this to return true if the _Floatn and _Floatnx built-in functions
   should implicitly enable the built-in function without the __builtin_ prefix
   in addition to the normal built-in function with the __builtin_ prefix.  The
   default is to only enable built-in functions without the __builtin_ prefix
   for the GNU C langauge.  The argument FUNC is the enum builtin_in_function
   id of the function to be enabled.  */

bool
default_floatn_builtin_p (int func ATTRIBUTE_UNUSED)
{
  static bool first_time_p = true;
  static bool c_or_objective_c;

  if (first_time_p)
    {
      first_time_p = false;
      c_or_objective_c = lang_GNU_C () || lang_GNU_OBJC ();
    }

  return c_or_objective_c;
}

/* Make some target macros useable by target-independent code.  */
bool
targhook_words_big_endian (void)
{
  return !!WORDS_BIG_ENDIAN;
}

bool
targhook_float_words_big_endian (void)
{
  return !!FLOAT_WORDS_BIG_ENDIAN;
}

/* True if the target supports floating-point exceptions and rounding
   modes.  */

bool
default_float_exceptions_rounding_supported_p (void)
{
#ifdef HAVE_adddf3
  return HAVE_adddf3;
#else
  return false;
#endif
}

/* True if the target supports decimal floating point.  */

bool
default_decimal_float_supported_p (void)
{
  return ENABLE_DECIMAL_FLOAT;
}

/* True if the target supports fixed-point arithmetic.  */

bool
default_fixed_point_supported_p (void)
{
  return ENABLE_FIXED_POINT;
}

/* True if the target supports GNU indirect functions.  */

bool
default_has_ifunc_p (void)
{
  return HAVE_GNU_INDIRECT_FUNCTION;
}

/* Return true if we predict the loop LOOP will be transformed to a
   low-overhead loop, otherwise return false.

   By default, false is returned, as this hook's applicability should be
   verified for each target.  Target maintainers should re-define the hook
   if the target can take advantage of it.  */

bool
default_predict_doloop_p (class loop *loop ATTRIBUTE_UNUSED)
{
  return false;
}

/* By default, just use the input MODE itself.  */

machine_mode
default_preferred_doloop_mode (machine_mode mode)
{
  return mode;
}

/* NULL if INSN insn is valid within a low-overhead loop, otherwise returns
   an error message.

   This function checks whether a given INSN is valid within a low-overhead
   loop.  If INSN is invalid it returns the reason for that, otherwise it
   returns NULL. A called function may clobber any special registers required
   for low-overhead looping. Additionally, some targets (eg, PPC) use the count
   register for branch on table instructions. We reject the doloop pattern in
   these cases.  */

const char *
default_invalid_within_doloop (const rtx_insn *insn)
{
  if (CALL_P (insn))
    return "Function call in loop.";

  if (tablejump_p (insn, NULL, NULL) || computed_jump_p (insn))
    return "Computed branch in the loop.";

  return NULL;
}

/* Mapping of builtin functions to vectorized variants.  */

tree
default_builtin_vectorized_function (unsigned int, tree, tree)
{
  return NULL_TREE;
}

/* Mapping of target builtin functions to vectorized variants.  */

tree
default_builtin_md_vectorized_function (tree, tree, tree)
{
  return NULL_TREE;
}

/* Default vectorizer cost model values.  */

int
default_builtin_vectorization_cost (enum vect_cost_for_stmt type_of_cost,
                                    tree vectype,
                                    int misalign ATTRIBUTE_UNUSED)
{
  switch (type_of_cost)
    {
      case scalar_stmt:
      case scalar_load:
      case scalar_store:
      case vector_stmt:
      case vector_load:
      case vector_store:
      case vec_to_scalar:
      case scalar_to_vec:
      case cond_branch_not_taken:
      case vec_perm:
      case vec_promote_demote:
        return 1;

      case unaligned_load:
      case unaligned_store:
        return 2;

      case cond_branch_taken:
        return 3;

      case vec_construct:
	return estimated_poly_value (TYPE_VECTOR_SUBPARTS (vectype)) - 1;

      default:
        gcc_unreachable ();
    }
}

/* Reciprocal.  */

tree
default_builtin_reciprocal (tree)
{
  return NULL_TREE;
}

bool
hook_bool_CUMULATIVE_ARGS_arg_info_false (cumulative_args_t,
					  const function_arg_info &)
{
  return false;
}

bool
hook_bool_CUMULATIVE_ARGS_arg_info_true (cumulative_args_t,
					 const function_arg_info &)
{
  return true;
}

int
hook_int_CUMULATIVE_ARGS_arg_info_0 (cumulative_args_t,
				     const function_arg_info &)
{
  return 0;
}

void
hook_void_CUMULATIVE_ARGS_tree (cumulative_args_t ca ATTRIBUTE_UNUSED,
				tree ATTRIBUTE_UNUSED)
{
}

/* Default implementation of TARGET_PUSH_ARGUMENT.  */

bool
default_push_argument (unsigned int)
{
#ifdef PUSH_ROUNDING
  return !ACCUMULATE_OUTGOING_ARGS;
#else
  return false;
#endif
}

void
default_function_arg_advance (cumulative_args_t, const function_arg_info &)
{
  gcc_unreachable ();
}

/* Default implementation of TARGET_FUNCTION_ARG_OFFSET.  */

HOST_WIDE_INT
default_function_arg_offset (machine_mode, const_tree)
{
  return 0;
}

/* Default implementation of TARGET_FUNCTION_ARG_PADDING: usually pad
   upward, but pad short args downward on big-endian machines.  */

pad_direction
default_function_arg_padding (machine_mode mode, const_tree type)
{
  if (!BYTES_BIG_ENDIAN)
    return PAD_UPWARD;

  unsigned HOST_WIDE_INT size;
  if (mode == BLKmode)
    {
      if (!type || TREE_CODE (TYPE_SIZE (type)) != INTEGER_CST)
	return PAD_UPWARD;
      size = int_size_in_bytes (type);
    }
  else
    /* Targets with variable-sized modes must override this hook
       and handle variable-sized modes explicitly.  */
    size = GET_MODE_SIZE (mode).to_constant ();

  if (size < (PARM_BOUNDARY / BITS_PER_UNIT))
    return PAD_DOWNWARD;

  return PAD_UPWARD;
}

rtx
default_function_arg (cumulative_args_t, const function_arg_info &)
{
  gcc_unreachable ();
}

rtx
default_function_incoming_arg (cumulative_args_t, const function_arg_info &)
{
  gcc_unreachable ();
}

unsigned int
default_function_arg_boundary (machine_mode mode ATTRIBUTE_UNUSED,
			       const_tree type ATTRIBUTE_UNUSED)
{
  return PARM_BOUNDARY;
}

unsigned int
default_function_arg_round_boundary (machine_mode mode ATTRIBUTE_UNUSED,
				     const_tree type ATTRIBUTE_UNUSED)
{
  return PARM_BOUNDARY;
}

void
hook_void_bitmap (bitmap regs ATTRIBUTE_UNUSED)
{
}

const char *
hook_invalid_arg_for_unprototyped_fn (
	const_tree typelist ATTRIBUTE_UNUSED,
	const_tree funcdecl ATTRIBUTE_UNUSED,
	const_tree val ATTRIBUTE_UNUSED)
{
  return NULL;
}

/* Initialize the stack protection decls.  */

/* Stack protection related decls living in libgcc.  */
static GTY(()) tree stack_chk_guard_decl;

tree
default_stack_protect_guard (void)
{
  tree t = stack_chk_guard_decl;

  if (t == NULL)
    {
      rtx x;

      t = build_decl (UNKNOWN_LOCATION,
		      VAR_DECL, get_identifier ("__stack_chk_guard"),
		      ptr_type_node);
      TREE_STATIC (t) = 1;
      TREE_PUBLIC (t) = 1;
      DECL_EXTERNAL (t) = 1;
      TREE_USED (t) = 1;
      TREE_THIS_VOLATILE (t) = 1;
      DECL_ARTIFICIAL (t) = 1;
      DECL_IGNORED_P (t) = 1;

      /* Do not share RTL as the declaration is visible outside of
	 current function.  */
      x = DECL_RTL (t);
      RTX_FLAG (x, used) = 1;

      stack_chk_guard_decl = t;
    }

  return t;
}

static GTY(()) tree stack_chk_fail_decl;

tree
default_external_stack_protect_fail (void)
{
  tree t = stack_chk_fail_decl;

  if (t == NULL_TREE)
    {
      t = build_function_type_list (void_type_node, NULL_TREE);
      t = build_decl (UNKNOWN_LOCATION,
		      FUNCTION_DECL, get_identifier ("__stack_chk_fail"), t);
      TREE_STATIC (t) = 1;
      TREE_PUBLIC (t) = 1;
      DECL_EXTERNAL (t) = 1;
      TREE_USED (t) = 1;
      TREE_THIS_VOLATILE (t) = 1;
      TREE_NOTHROW (t) = 1;
      DECL_ARTIFICIAL (t) = 1;
      DECL_IGNORED_P (t) = 1;
      DECL_VISIBILITY (t) = VISIBILITY_DEFAULT;
      DECL_VISIBILITY_SPECIFIED (t) = 1;

      stack_chk_fail_decl = t;
    }

  return build_call_expr (t, 0);
}

tree
default_hidden_stack_protect_fail (void)
{
#ifndef HAVE_GAS_HIDDEN
  return default_external_stack_protect_fail ();
#else
  tree t = stack_chk_fail_decl;

  if (!flag_pic)
    return default_external_stack_protect_fail ();

  if (t == NULL_TREE)
    {
      t = build_function_type_list (void_type_node, NULL_TREE);
      t = build_decl (UNKNOWN_LOCATION, FUNCTION_DECL,
		      get_identifier ("__stack_chk_fail_local"), t);
      TREE_STATIC (t) = 1;
      TREE_PUBLIC (t) = 1;
      DECL_EXTERNAL (t) = 1;
      TREE_USED (t) = 1;
      TREE_THIS_VOLATILE (t) = 1;
      TREE_NOTHROW (t) = 1;
      DECL_ARTIFICIAL (t) = 1;
      DECL_IGNORED_P (t) = 1;
      DECL_VISIBILITY_SPECIFIED (t) = 1;
      DECL_VISIBILITY (t) = VISIBILITY_HIDDEN;

      stack_chk_fail_decl = t;
    }

  return build_call_expr (t, 0);
#endif
}

bool
hook_bool_const_rtx_commutative_p (const_rtx x,
				   int outer_code ATTRIBUTE_UNUSED)
{
  return COMMUTATIVE_P (x);
}

rtx
default_function_value (const_tree ret_type ATTRIBUTE_UNUSED,
			const_tree fn_decl_or_type,
			bool outgoing ATTRIBUTE_UNUSED)
{
  /* The old interface doesn't handle receiving the function type.  */
  if (fn_decl_or_type
      && !DECL_P (fn_decl_or_type))
    fn_decl_or_type = NULL;

#ifdef FUNCTION_VALUE
  return FUNCTION_VALUE (ret_type, fn_decl_or_type);
#else
  gcc_unreachable ();
#endif
}

rtx
default_libcall_value (machine_mode mode ATTRIBUTE_UNUSED,
		       const_rtx fun ATTRIBUTE_UNUSED)
{
#ifdef LIBCALL_VALUE
  return LIBCALL_VALUE (MACRO_MODE (mode));
#else
  gcc_unreachable ();
#endif
}

/* The default hook for TARGET_FUNCTION_VALUE_REGNO_P.  */

bool
default_function_value_regno_p (const unsigned int regno ATTRIBUTE_UNUSED)
{
#ifdef FUNCTION_VALUE_REGNO_P
  return FUNCTION_VALUE_REGNO_P (regno);
#else
  gcc_unreachable ();
#endif
}

/* Choose the mode and rtx to use to zero REGNO, storing tem in PMODE and
   PREGNO_RTX and returning TRUE if successful, otherwise returning FALSE.  If
   the natural mode for REGNO doesn't work, attempt to group it with subsequent
   adjacent registers set in TOZERO.  */

static inline bool
zcur_select_mode_rtx (unsigned int regno, machine_mode *pmode,
		      rtx *pregno_rtx, HARD_REG_SET tozero)
{
  rtx regno_rtx = regno_reg_rtx[regno];
  machine_mode mode = GET_MODE (regno_rtx);

  /* If the natural mode doesn't work, try some wider mode.  */
  if (!targetm.hard_regno_mode_ok (regno, mode))
    {
      bool found = false;
      for (int nregs = 2;
	   !found && nregs <= hard_regno_max_nregs
	     && regno + nregs <= FIRST_PSEUDO_REGISTER
	     && TEST_HARD_REG_BIT (tozero,
				   regno + nregs - 1);
	   nregs++)
	{
	  mode = choose_hard_reg_mode (regno, nregs, 0);
	  if (mode == E_VOIDmode)
	    continue;
	  gcc_checking_assert (targetm.hard_regno_mode_ok (regno, mode));
	  regno_rtx = gen_rtx_REG (mode, regno);
	  found = true;
	}
      if (!found)
	return false;
    }

  *pmode = mode;
  *pregno_rtx = regno_rtx;
  return true;
}

/* The default hook for TARGET_ZERO_CALL_USED_REGS.  */

HARD_REG_SET
default_zero_call_used_regs (HARD_REG_SET need_zeroed_hardregs)
{
  gcc_assert (!hard_reg_set_empty_p (need_zeroed_hardregs));

  HARD_REG_SET failed;
  CLEAR_HARD_REG_SET (failed);
  bool progress = false;

  /* First, try to zero each register in need_zeroed_hardregs by
     loading a zero into it, taking note of any failures in
     FAILED.  */
  for (unsigned int regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
    if (TEST_HARD_REG_BIT (need_zeroed_hardregs, regno))
      {
	rtx_insn *last_insn = get_last_insn ();
	rtx regno_rtx;
	machine_mode mode;

	if (!zcur_select_mode_rtx (regno, &mode, &regno_rtx,
				   need_zeroed_hardregs))
	  {
	    SET_HARD_REG_BIT (failed, regno);
	    continue;
	  }

	rtx zero = CONST0_RTX (mode);
	rtx_insn *insn = emit_move_insn (regno_rtx, zero);
	if (!valid_insn_p (insn))
	  {
	    SET_HARD_REG_BIT (failed, regno);
	    delete_insns_since (last_insn);
	  }
	else
	  {
	    progress = true;
	    regno += hard_regno_nregs (regno, mode) - 1;
	  }
      }

  /* Now retry with copies from zeroed registers, as long as we've
     made some PROGRESS, and registers remain to be zeroed in
     FAILED.  */
  while (progress && !hard_reg_set_empty_p (failed))
    {
      HARD_REG_SET retrying = failed;

      CLEAR_HARD_REG_SET (failed);
      progress = false;

      for (unsigned int regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
	if (TEST_HARD_REG_BIT (retrying, regno))
	  {
	    rtx regno_rtx;
	    machine_mode mode;

	    /* This might select registers we've already zeroed.  If grouping
	       with them is what it takes to get regno zeroed, so be it.  */
	    if (!zcur_select_mode_rtx (regno, &mode, &regno_rtx,
				       need_zeroed_hardregs))
	      {
		SET_HARD_REG_BIT (failed, regno);
		continue;
	      }

	    bool success = false;
	    /* Look for a source.  */
	    for (unsigned int src = 0; src < FIRST_PSEUDO_REGISTER; src++)
	      {
		/* If SRC hasn't been zeroed (yet?), skip it.  */
		if (! TEST_HARD_REG_BIT (need_zeroed_hardregs, src))
		  continue;
		if (TEST_HARD_REG_BIT (retrying, src))
		  continue;

		/* Check that SRC can hold MODE, and that any other
		   registers needed to hold MODE in SRC have also been
		   zeroed.  */
		if (!targetm.hard_regno_mode_ok (src, mode))
		  continue;
		unsigned n = targetm.hard_regno_nregs (src, mode);
		bool ok = true;
		for (unsigned i = 1; ok && i < n; i++)
		  ok = (TEST_HARD_REG_BIT (need_zeroed_hardregs, src + i)
			&& !TEST_HARD_REG_BIT (retrying, src + i));
		if (!ok)
		  continue;

		/* SRC is usable, try to copy from it.  */
		rtx_insn *last_insn = get_last_insn ();
		rtx src_rtx = gen_rtx_REG (mode, src);
		rtx_insn *insn = emit_move_insn (regno_rtx, src_rtx);
		if (!valid_insn_p (insn))
		  /* It didn't work, remove any inserts.  We'll look
		     for another SRC.  */
		  delete_insns_since (last_insn);
		else
		  {
		    /* We're done for REGNO.  */
		    success = true;
		    break;
		  }
	      }

	    /* If nothing worked for REGNO this round, mark it to be
	       retried if we get another round.  */
	    if (!success)
	      SET_HARD_REG_BIT (failed, regno);
	    else
	      {
		/* Take note so as to enable another round if needed.  */
		progress = true;
		regno += hard_regno_nregs (regno, mode) - 1;
	      }
	  }
    }

  /* If any register remained, report it.  */
  if (!progress)
    {
      static bool issued_error;
      if (!issued_error)
	{
	  issued_error = true;
	  sorry ("%qs not supported on this target",
		 "-fzero-call-used-regs");
	}
    }

  return need_zeroed_hardregs;
}

rtx
default_internal_arg_pointer (void)
{
  /* If the reg that the virtual arg pointer will be translated into is
     not a fixed reg or is the stack pointer, make a copy of the virtual
     arg pointer, and address parms via the copy.  The frame pointer is
     considered fixed even though it is not marked as such.  */
  if ((ARG_POINTER_REGNUM == STACK_POINTER_REGNUM
       || ! (fixed_regs[ARG_POINTER_REGNUM]
	     || ARG_POINTER_REGNUM == FRAME_POINTER_REGNUM)))
    return copy_to_reg (virtual_incoming_args_rtx);
  else
    return virtual_incoming_args_rtx;
}

rtx
default_static_chain (const_tree ARG_UNUSED (fndecl_or_type), bool incoming_p)
{
  if (incoming_p)
    {
#ifdef STATIC_CHAIN_INCOMING_REGNUM
      return gen_rtx_REG (Pmode, STATIC_CHAIN_INCOMING_REGNUM);
#endif
    }

#ifdef STATIC_CHAIN_REGNUM
  return gen_rtx_REG (Pmode, STATIC_CHAIN_REGNUM);
#endif

  {
    static bool issued_error;
    if (!issued_error)
      {
	issued_error = true;
	sorry ("nested functions not supported on this target");
      }

    /* It really doesn't matter what we return here, so long at it
       doesn't cause the rest of the compiler to crash.  */
    return gen_rtx_MEM (Pmode, stack_pointer_rtx);
  }
}

void
default_trampoline_init (rtx ARG_UNUSED (m_tramp), tree ARG_UNUSED (t_func),
			 rtx ARG_UNUSED (r_chain))
{
  sorry ("nested function trampolines not supported on this target");
}

poly_int64
default_return_pops_args (tree, tree, poly_int64)
{
  return 0;
}

reg_class_t
default_ira_change_pseudo_allocno_class (int regno ATTRIBUTE_UNUSED,
					 reg_class_t cl,
					 reg_class_t best_cl ATTRIBUTE_UNUSED)
{
  return cl;
}

extern bool
default_lra_p (void)
{
  return true;
}

int
default_register_priority (int hard_regno ATTRIBUTE_UNUSED)
{
  return 0;
}

extern bool
default_register_usage_leveling_p (void)
{
  return false;
}

extern bool
default_different_addr_displacement_p (void)
{
  return false;
}

reg_class_t
default_secondary_reload (bool in_p ATTRIBUTE_UNUSED, rtx x ATTRIBUTE_UNUSED,
			  reg_class_t reload_class_i ATTRIBUTE_UNUSED,
			  machine_mode reload_mode ATTRIBUTE_UNUSED,
			  secondary_reload_info *sri)
{
  enum reg_class rclass = NO_REGS;
  enum reg_class reload_class = (enum reg_class) reload_class_i;

  if (sri->prev_sri && sri->prev_sri->t_icode != CODE_FOR_nothing)
    {
      sri->icode = sri->prev_sri->t_icode;
      return NO_REGS;
    }
#ifdef SECONDARY_INPUT_RELOAD_CLASS
  if (in_p)
    rclass = SECONDARY_INPUT_RELOAD_CLASS (reload_class,
					   MACRO_MODE (reload_mode), x);
#endif
#ifdef SECONDARY_OUTPUT_RELOAD_CLASS
  if (! in_p)
    rclass = SECONDARY_OUTPUT_RELOAD_CLASS (reload_class,
					    MACRO_MODE (reload_mode), x);
#endif
  if (rclass != NO_REGS)
    {
      enum insn_code icode
	= direct_optab_handler (in_p ? reload_in_optab : reload_out_optab,
				reload_mode);

      if (icode != CODE_FOR_nothing
	  && !insn_operand_matches (icode, in_p, x))
	icode = CODE_FOR_nothing;
      else if (icode != CODE_FOR_nothing)
	{
	  const char *insn_constraint, *scratch_constraint;
	  enum reg_class insn_class, scratch_class;

	  gcc_assert (insn_data[(int) icode].n_operands == 3);
	  insn_constraint = insn_data[(int) icode].operand[!in_p].constraint;
	  if (!*insn_constraint)
	    insn_class = ALL_REGS;
	  else
	    {
	      if (in_p)
		{
		  gcc_assert (*insn_constraint == '=');
		  insn_constraint++;
		}
	      insn_class = (reg_class_for_constraint
			    (lookup_constraint (insn_constraint)));
	      gcc_assert (insn_class != NO_REGS);
	    }

	  scratch_constraint = insn_data[(int) icode].operand[2].constraint;
	  /* The scratch register's constraint must start with "=&",
	     except for an input reload, where only "=" is necessary,
	     and where it might be beneficial to re-use registers from
	     the input.  */
	  gcc_assert (scratch_constraint[0] == '='
		      && (in_p || scratch_constraint[1] == '&'));
	  scratch_constraint++;
	  if (*scratch_constraint == '&')
	    scratch_constraint++;
	  scratch_class = (reg_class_for_constraint
			   (lookup_constraint (scratch_constraint)));

	  if (reg_class_subset_p (reload_class, insn_class))
	    {
	      gcc_assert (scratch_class == rclass);
	      rclass = NO_REGS;
	    }
	  else
	    rclass = insn_class;

        }
      if (rclass == NO_REGS)
	sri->icode = icode;
      else
	sri->t_icode = icode;
    }
  return rclass;
}

/* The default implementation of TARGET_SECONDARY_MEMORY_NEEDED_MODE.  */

machine_mode
default_secondary_memory_needed_mode (machine_mode mode)
{
  if (!targetm.lra_p ()
      && known_lt (GET_MODE_BITSIZE (mode), BITS_PER_WORD)
      && INTEGRAL_MODE_P (mode))
    return mode_for_size (BITS_PER_WORD, GET_MODE_CLASS (mode), 0).require ();
  return mode;
}

/* By default, if flag_pic is true, then neither local nor global relocs
   should be placed in readonly memory.  */

int
default_reloc_rw_mask (void)
{
  return flag_pic ? 3 : 0;
}

/* By default, address diff vectors are generated
for jump tables when flag_pic is true.  */

bool
default_generate_pic_addr_diff_vec (void)
{
  return flag_pic;
}

/* By default, do no modification. */
tree default_mangle_decl_assembler_name (tree decl ATTRIBUTE_UNUSED,
					 tree id)
{
   return id;
}

/* The default implementation of TARGET_STATIC_RTX_ALIGNMENT.  */

HOST_WIDE_INT
default_static_rtx_alignment (machine_mode mode)
{
  return GET_MODE_ALIGNMENT (mode);
}

/* The default implementation of TARGET_CONSTANT_ALIGNMENT.  */

HOST_WIDE_INT
default_constant_alignment (const_tree, HOST_WIDE_INT align)
{
  return align;
}

/* An implementation of TARGET_CONSTANT_ALIGNMENT that aligns strings
   to at least BITS_PER_WORD but otherwise makes no changes.  */

HOST_WIDE_INT
constant_alignment_word_strings (const_tree exp, HOST_WIDE_INT align)
{
  if (TREE_CODE (exp) == STRING_CST)
    return MAX (align, BITS_PER_WORD);
  return align;
}

/* Default to natural alignment for vector types, bounded by
   MAX_OFILE_ALIGNMENT.  */

HOST_WIDE_INT
default_vector_alignment (const_tree type)
{
  unsigned HOST_WIDE_INT align = MAX_OFILE_ALIGNMENT;
  tree size = TYPE_SIZE (type);
  if (tree_fits_uhwi_p (size))
    align = tree_to_uhwi (size);
  if (align >= MAX_OFILE_ALIGNMENT)
    return MAX_OFILE_ALIGNMENT;
  return MAX (align, GET_MODE_ALIGNMENT (TYPE_MODE (type)));
}

/* The default implementation of
   TARGET_VECTORIZE_PREFERRED_VECTOR_ALIGNMENT.  */

poly_uint64
default_preferred_vector_alignment (const_tree type)
{
  return TYPE_ALIGN (type);
}

/* By default assume vectors of element TYPE require a multiple of the natural
   alignment of TYPE.  TYPE is naturally aligned if IS_PACKED is false.  */
bool
default_builtin_vector_alignment_reachable (const_tree /*type*/, bool is_packed)
{
  return ! is_packed;
}

/* By default, assume that a target supports any factor of misalignment
   memory access if it supports movmisalign patten.
   is_packed is true if the memory access is defined in a packed struct.  */
bool
default_builtin_support_vector_misalignment (machine_mode mode,
					     const_tree type
					     ATTRIBUTE_UNUSED,
					     int misalignment
					     ATTRIBUTE_UNUSED,
					     bool is_packed
					     ATTRIBUTE_UNUSED)
{
  if (optab_handler (movmisalign_optab, mode) != CODE_FOR_nothing)
    return true;
  return false;
}

/* By default, only attempt to parallelize bitwise operations, and
   possibly adds/subtracts using bit-twiddling.  */

machine_mode
default_preferred_simd_mode (scalar_mode)
{
  return word_mode;
}

/* By default do not split reductions further.  */

machine_mode
default_split_reduction (machine_mode mode)
{
  return mode;
}

/* By default only the preferred vector mode is tried.  */

unsigned int
default_autovectorize_vector_modes (vector_modes *, bool)
{
  return 0;
}

/* The default implementation of TARGET_VECTORIZE_RELATED_MODE.  */

opt_machine_mode
default_vectorize_related_mode (machine_mode vector_mode,
				scalar_mode element_mode,
				poly_uint64 nunits)
{
  machine_mode result_mode;
  if ((maybe_ne (nunits, 0U)
       || multiple_p (GET_MODE_SIZE (vector_mode),
		      GET_MODE_SIZE (element_mode), &nunits))
      && mode_for_vector (element_mode, nunits).exists (&result_mode)
      && VECTOR_MODE_P (result_mode)
      && targetm.vector_mode_supported_p (result_mode))
    return result_mode;

  return opt_machine_mode ();
}

/* By default a vector of integers is used as a mask.  */

opt_machine_mode
default_get_mask_mode (machine_mode mode)
{
  return related_int_vector_mode (mode);
}

/* By default consider masked stores to be expensive.  */

bool
default_empty_mask_is_expensive (unsigned ifn)
{
  return ifn == IFN_MASK_STORE;
}

/* By default, the cost model accumulates three separate costs (prologue,
   loop body, and epilogue) for a vectorized loop or block.  So allocate an
   array of three unsigned ints, set it to zero, and return its address.  */

vector_costs *
default_vectorize_create_costs (vec_info *vinfo, bool costing_for_scalar)
{
  return new vector_costs (vinfo, costing_for_scalar);
}

/* Determine whether or not a pointer mode is valid. Assume defaults
   of ptr_mode or Pmode - can be overridden.  */
bool
default_valid_pointer_mode (scalar_int_mode mode)
{
  return (mode == ptr_mode || mode == Pmode);
}

/* Determine whether the memory reference specified by REF may alias
   the C libraries errno location.  */
bool
default_ref_may_alias_errno (ao_ref *ref)
{
  tree base = ao_ref_base (ref);
  /* The default implementation assumes the errno location is
     a declaration of type int or is always accessed via a
     pointer to int.  We assume that accesses to errno are
     not deliberately obfuscated (even in conforming ways).  */
  if (TYPE_UNSIGNED (TREE_TYPE (base))
      || TYPE_MODE (TREE_TYPE (base)) != TYPE_MODE (integer_type_node))
    return false;
  /* The default implementation assumes an errno location declaration
     is never defined in the current compilation unit and may not be
     aliased by a local variable.  */
  if (DECL_P (base)
      && DECL_EXTERNAL (base)
      && !TREE_STATIC (base))
    return true;
  else if (TREE_CODE (base) == MEM_REF
	   && TREE_CODE (TREE_OPERAND (base, 0)) == SSA_NAME)
    {
      struct ptr_info_def *pi = SSA_NAME_PTR_INFO (TREE_OPERAND (base, 0));
      return !pi || pi->pt.anything || pi->pt.nonlocal;
    }
  return false;
}

/* Return the mode for a pointer to a given ADDRSPACE,
   defaulting to ptr_mode for all address spaces.  */

scalar_int_mode
default_addr_space_pointer_mode (addr_space_t addrspace ATTRIBUTE_UNUSED)
{
  return ptr_mode;
}

/* Return the mode for an address in a given ADDRSPACE,
   defaulting to Pmode for all address spaces.  */

scalar_int_mode
default_addr_space_address_mode (addr_space_t addrspace ATTRIBUTE_UNUSED)
{
  return Pmode;
}

/* Named address space version of valid_pointer_mode.
   To match the above, the same modes apply to all address spaces.  */

bool
default_addr_space_valid_pointer_mode (scalar_int_mode mode,
				       addr_space_t as ATTRIBUTE_UNUSED)
{
  return targetm.valid_pointer_mode (mode);
}

/* Some places still assume that all pointer or address modes are the
   standard Pmode and ptr_mode.  These optimizations become invalid if
   the target actually supports multiple different modes.  For now,
   we disable such optimizations on such targets, using this function.  */

bool
target_default_pointer_address_modes_p (void)
{
  if (targetm.addr_space.address_mode != default_addr_space_address_mode)
    return false;
  if (targetm.addr_space.pointer_mode != default_addr_space_pointer_mode)
    return false;

  return true;
}

/* Named address space version of legitimate_address_p.
   By default, all address spaces have the same form.  */

bool
default_addr_space_legitimate_address_p (machine_mode mode, rtx mem,
					 bool strict,
					 addr_space_t as ATTRIBUTE_UNUSED)
{
  return targetm.legitimate_address_p (mode, mem, strict);
}

/* Named address space version of LEGITIMIZE_ADDRESS.
   By default, all address spaces have the same form.  */

rtx
default_addr_space_legitimize_address (rtx x, rtx oldx, machine_mode mode,
				       addr_space_t as ATTRIBUTE_UNUSED)
{
  return targetm.legitimize_address (x, oldx, mode);
}

/* The default hook for determining if one named address space is a subset of
   another and to return which address space to use as the common address
   space.  */

bool
default_addr_space_subset_p (addr_space_t subset, addr_space_t superset)
{
  return (subset == superset);
}

/* The default hook for determining if 0 within a named address
   space is a valid address.  */

bool
default_addr_space_zero_address_valid (addr_space_t as ATTRIBUTE_UNUSED)
{
  return false;
}

/* The default hook for debugging the address space is to return the
   address space number to indicate DW_AT_address_class.  */
int
default_addr_space_debug (addr_space_t as)
{
  return as;
}

/* The default hook implementation for TARGET_ADDR_SPACE_DIAGNOSE_USAGE.
   Don't complain about any address space.  */

void
default_addr_space_diagnose_usage (addr_space_t, location_t)
{
}
	 

/* The default hook for TARGET_ADDR_SPACE_CONVERT. This hook should never be
   called for targets with only a generic address space.  */

rtx
default_addr_space_convert (rtx op ATTRIBUTE_UNUSED,
			    tree from_type ATTRIBUTE_UNUSED,
			    tree to_type ATTRIBUTE_UNUSED)
{
  gcc_unreachable ();
}

/* The defualt implementation of TARGET_HARD_REGNO_NREGS.  */

unsigned int
default_hard_regno_nregs (unsigned int, machine_mode mode)
{
  /* Targets with variable-sized modes must provide their own definition
     of this hook.  */
  return CEIL (GET_MODE_SIZE (mode).to_constant (), UNITS_PER_WORD);
}

bool
default_hard_regno_scratch_ok (unsigned int regno ATTRIBUTE_UNUSED)
{
  return true;
}

/* The default implementation of TARGET_MODE_DEPENDENT_ADDRESS_P.  */

bool
default_mode_dependent_address_p (const_rtx addr ATTRIBUTE_UNUSED,
				  addr_space_t addrspace ATTRIBUTE_UNUSED)
{
  return false;
}

extern bool default_new_address_profitable_p (rtx, rtx);


/* The default implementation of TARGET_NEW_ADDRESS_PROFITABLE_P.  */

bool
default_new_address_profitable_p (rtx memref ATTRIBUTE_UNUSED,
				  rtx_insn *insn ATTRIBUTE_UNUSED,
				  rtx new_addr ATTRIBUTE_UNUSED)
{
  return true;
}

bool
default_target_option_valid_attribute_p (tree ARG_UNUSED (fndecl),
					 tree ARG_UNUSED (name),
					 tree ARG_UNUSED (args),
					 int ARG_UNUSED (flags))
{
  warning (OPT_Wattributes,
	   "target attribute is not supported on this machine");

  return false;
}

bool
default_target_option_pragma_parse (tree ARG_UNUSED (args),
				    tree ARG_UNUSED (pop_target))
{
  /* If args is NULL the caller is handle_pragma_pop_options ().  In that case,
     emit no warning because "#pragma GCC pop_target" is valid on targets that
     do not have the "target" pragma.  */
  if (args)
    warning (OPT_Wpragmas,
	     "%<#pragma GCC target%> is not supported for this machine");

  return false;
}

bool
default_target_can_inline_p (tree caller, tree callee)
{
  tree callee_opts = DECL_FUNCTION_SPECIFIC_TARGET (callee);
  tree caller_opts = DECL_FUNCTION_SPECIFIC_TARGET (caller);
  if (! callee_opts)
    callee_opts = target_option_default_node;
  if (! caller_opts)
    caller_opts = target_option_default_node;

  /* If both caller and callee have attributes, assume that if the
     pointer is different, the two functions have different target
     options since build_target_option_node uses a hash table for the
     options.  */
  return callee_opts == caller_opts;
}

/* By default, return false to not need to collect any target information
   for inlining.  Target maintainer should re-define the hook if the
   target want to take advantage of it.  */

bool
default_need_ipa_fn_target_info (const_tree, unsigned int &)
{
  return false;
}

bool
default_update_ipa_fn_target_info (unsigned int &, const gimple *)
{
  return false;
}

/* If the machine does not have a case insn that compares the bounds,
   this means extra overhead for dispatch tables, which raises the
   threshold for using them.  */

unsigned int
default_case_values_threshold (void)
{
  return (targetm.have_casesi () ? 4 : 5);
}

bool
default_have_conditional_execution (void)
{
  return HAVE_conditional_execution;
}

/* By default we assume that c99 functions are present at the runtime,
   but sincos is not.  */
bool
default_libc_has_function (enum function_class fn_class,
			   tree type ATTRIBUTE_UNUSED)
{
  if (fn_class == function_c94
      || fn_class == function_c99_misc
      || fn_class == function_c99_math_complex)
    return true;

  return false;
}

/* By default assume that libc has not a fast implementation.  */

bool
default_libc_has_fast_function (int fcode ATTRIBUTE_UNUSED)
{
  return false;
}

bool
gnu_libc_has_function (enum function_class fn_class ATTRIBUTE_UNUSED,
		       tree type ATTRIBUTE_UNUSED)
{
  return true;
}

bool
no_c99_libc_has_function (enum function_class fn_class ATTRIBUTE_UNUSED,
			  tree type ATTRIBUTE_UNUSED)
{
  return false;
}

/* Assume some c99 functions are present at the runtime including sincos.  */
bool
bsd_libc_has_function (enum function_class fn_class,
		       tree type ATTRIBUTE_UNUSED)
{
  if (fn_class == function_c94
      || fn_class == function_c99_misc
      || fn_class == function_sincos)
    return true;

  return false;
}


tree
default_builtin_tm_load_store (tree ARG_UNUSED (type))
{
  return NULL_TREE;
}

/* Compute cost of moving registers to/from memory.  */

int
default_memory_move_cost (machine_mode mode ATTRIBUTE_UNUSED,
			  reg_class_t rclass ATTRIBUTE_UNUSED,
			  bool in ATTRIBUTE_UNUSED)
{
#ifndef MEMORY_MOVE_COST
    return (4 + memory_move_secondary_cost (mode, (enum reg_class) rclass, in));
#else
    return MEMORY_MOVE_COST (MACRO_MODE (mode), (enum reg_class) rclass, in);
#endif
}

/* Compute cost of moving data from a register of class FROM to one of
   TO, using MODE.  */

int
default_register_move_cost (machine_mode mode ATTRIBUTE_UNUSED,
                            reg_class_t from ATTRIBUTE_UNUSED,
                            reg_class_t to ATTRIBUTE_UNUSED)
{
#ifndef REGISTER_MOVE_COST
  return 2;
#else
  return REGISTER_MOVE_COST (MACRO_MODE (mode),
			     (enum reg_class) from, (enum reg_class) to);
#endif
}

/* The default implementation of TARGET_SLOW_UNALIGNED_ACCESS.  */

bool
default_slow_unaligned_access (machine_mode, unsigned int)
{
  return STRICT_ALIGNMENT;
}

/* The default implementation of TARGET_ESTIMATED_POLY_VALUE.  */

HOST_WIDE_INT
default_estimated_poly_value (poly_int64 x, poly_value_estimate_kind)
{
  return x.coeffs[0];
}

/* For hooks which use the MOVE_RATIO macro, this gives the legacy default
   behavior.  SPEED_P is true if we are compiling for speed.  */

unsigned int
get_move_ratio (bool speed_p ATTRIBUTE_UNUSED)
{
  unsigned int move_ratio;
#ifdef MOVE_RATIO
  move_ratio = (unsigned int) MOVE_RATIO (speed_p);
#else
#if defined (HAVE_cpymemqi) || defined (HAVE_cpymemhi) || defined (HAVE_cpymemsi) || defined (HAVE_cpymemdi) || defined (HAVE_cpymemti)
  move_ratio = 2;
#else /* No cpymem patterns, pick a default.  */
  move_ratio = ((speed_p) ? 15 : 3);
#endif
#endif
  return move_ratio;
}

/* Return TRUE if the move_by_pieces/set_by_pieces infrastructure should be
   used; return FALSE if the cpymem/setmem optab should be expanded, or
   a call to memcpy emitted.  */

bool
default_use_by_pieces_infrastructure_p (unsigned HOST_WIDE_INT size,
					unsigned int alignment,
					enum by_pieces_operation op,
					bool speed_p)
{
  unsigned int max_size = 0;
  unsigned int ratio = 0;

  switch (op)
    {
    case CLEAR_BY_PIECES:
      max_size = STORE_MAX_PIECES;
      ratio = CLEAR_RATIO (speed_p);
      break;
    case MOVE_BY_PIECES:
      max_size = MOVE_MAX_PIECES;
      ratio = get_move_ratio (speed_p);
      break;
    case SET_BY_PIECES:
      max_size = STORE_MAX_PIECES;
      ratio = SET_RATIO (speed_p);
      break;
    case STORE_BY_PIECES:
      max_size = STORE_MAX_PIECES;
      ratio = get_move_ratio (speed_p);
      break;
    case COMPARE_BY_PIECES:
      max_size = COMPARE_MAX_PIECES;
      /* Pick a likely default, just as in get_move_ratio.  */
      ratio = speed_p ? 15 : 3;
      break;
    }

  return by_pieces_ninsns (size, alignment, max_size + 1, op) < ratio;
}

/* This hook controls code generation for expanding a memcmp operation by
   pieces.  Return 1 for the normal pattern of compare/jump after each pair
   of loads, or a higher number to reduce the number of branches.  */

int
default_compare_by_pieces_branch_ratio (machine_mode)
{
  return 1;
}

/* Helper for default_print_patchable_function_entry and other
   print_patchable_function_entry hook implementations.  */

void
default_print_patchable_function_entry_1 (FILE *file,
					  unsigned HOST_WIDE_INT
					  patch_area_size,
					  bool record_p,
					  unsigned int flags)
{
  const char *nop_templ = 0;
  int code_num;
  rtx_insn *my_nop = make_insn_raw (gen_nop ());

  /* We use the template alone, relying on the (currently sane) assumption
     that the NOP template does not have variable operands.  */
  code_num = recog_memoized (my_nop);
  nop_templ = get_insn_template (code_num, my_nop);

  if (record_p && targetm_common.have_named_sections)
    {
      char buf[256];
      static int patch_area_number;
      section *previous_section = in_section;
      const char *asm_op = integer_asm_op (POINTER_SIZE_UNITS, false);

      gcc_assert (asm_op != NULL);
      patch_area_number++;
      ASM_GENERATE_INTERNAL_LABEL (buf, "LPFE", patch_area_number);

      section *sect = get_section ("__patchable_function_entries",
				  flags, current_function_decl);
      if (HAVE_COMDAT_GROUP && DECL_COMDAT_GROUP (current_function_decl))
	switch_to_comdat_section (sect, current_function_decl);
      else
	switch_to_section (sect);
      assemble_align (POINTER_SIZE);
      fputs (asm_op, file);
      assemble_name_raw (file, buf);
      fputc ('\n', file);

      switch_to_section (previous_section);
      ASM_OUTPUT_LABEL (file, buf);
    }

  unsigned i;
  for (i = 0; i < patch_area_size; ++i)
    output_asm_insn (nop_templ, NULL);
}

/* Write PATCH_AREA_SIZE NOPs into the asm outfile FILE around a function
   entry.  If RECORD_P is true and the target supports named sections,
   the location of the NOPs will be recorded in a special object section
   called "__patchable_function_entries".  This routine may be called
   twice per function to put NOPs before and after the function
   entry.  */

void
default_print_patchable_function_entry (FILE *file,
					unsigned HOST_WIDE_INT patch_area_size,
					bool record_p)
{
  unsigned int flags = SECTION_WRITE | SECTION_RELRO;
  if (HAVE_GAS_SECTION_LINK_ORDER)
    flags |= SECTION_LINK_ORDER;
  default_print_patchable_function_entry_1 (file, patch_area_size, record_p,
					    flags);
}

bool
default_profile_before_prologue (void)
{
#ifdef PROFILE_BEFORE_PROLOGUE
  return true;
#else
  return false;
#endif
}

/* The default implementation of TARGET_PREFERRED_RELOAD_CLASS.  */

reg_class_t
default_preferred_reload_class (rtx x ATTRIBUTE_UNUSED,
			        reg_class_t rclass)
{
#ifdef PREFERRED_RELOAD_CLASS 
  return (reg_class_t) PREFERRED_RELOAD_CLASS (x, (enum reg_class) rclass);
#else
  return rclass;
#endif
}

/* The default implementation of TARGET_OUTPUT_PREFERRED_RELOAD_CLASS.  */

reg_class_t
default_preferred_output_reload_class (rtx x ATTRIBUTE_UNUSED,
				       reg_class_t rclass)
{
  return rclass;
}

/* The default implementation of TARGET_PREFERRED_RENAME_CLASS.  */
reg_class_t
default_preferred_rename_class (reg_class_t rclass ATTRIBUTE_UNUSED)
{
  return NO_REGS;
}

/* The default implementation of TARGET_CLASS_LIKELY_SPILLED_P.  */

bool
default_class_likely_spilled_p (reg_class_t rclass)
{
  return (reg_class_size[(int) rclass] == 1);
}

/* The default implementation of TARGET_CLASS_MAX_NREGS.  */

unsigned char
default_class_max_nregs (reg_class_t rclass ATTRIBUTE_UNUSED,
			 machine_mode mode ATTRIBUTE_UNUSED)
{
#ifdef CLASS_MAX_NREGS
  return (unsigned char) CLASS_MAX_NREGS ((enum reg_class) rclass,
					  MACRO_MODE (mode));
#else
  /* Targets with variable-sized modes must provide their own definition
     of this hook.  */
  unsigned int size = GET_MODE_SIZE (mode).to_constant ();
  return (size + UNITS_PER_WORD - 1) / UNITS_PER_WORD;
#endif
}

/* Determine the debugging unwind mechanism for the target.  */

enum unwind_info_type
default_debug_unwind_info (void)
{
  /* If the target wants to force the use of dwarf2 unwind info, let it.  */
  /* ??? Change all users to the hook, then poison this.  */
#ifdef DWARF2_FRAME_INFO
  if (DWARF2_FRAME_INFO)
    return UI_DWARF2;
#endif

  /* Otherwise, only turn it on if dwarf2 debugging is enabled.  */
#ifdef DWARF2_DEBUGGING_INFO
  if (dwarf_debuginfo_p ())
    return UI_DWARF2;
#endif

  return UI_NONE;
}

/* Targets that set NUM_POLY_INT_COEFFS to something greater than 1
   must define this hook.  */

unsigned int
default_dwarf_poly_indeterminate_value (unsigned int, unsigned int *, int *)
{
  gcc_unreachable ();
}

/* Determine the correct mode for a Dwarf frame register that represents
   register REGNO.  */

machine_mode
default_dwarf_frame_reg_mode (int regno)
{
  machine_mode save_mode = reg_raw_mode[regno];

  if (targetm.hard_regno_call_part_clobbered (eh_edge_abi.id (),
					      regno, save_mode))
    save_mode = choose_hard_reg_mode (regno, 1, &eh_edge_abi);
  return save_mode;
}

/* To be used by targets where reg_raw_mode doesn't return the right
   mode for registers used in apply_builtin_return and apply_builtin_arg.  */

fixed_size_mode
default_get_reg_raw_mode (int regno)
{
  /* Targets must override this hook if the underlying register is
     variable-sized.  */
  return as_a <fixed_size_mode> (reg_raw_mode[regno]);
}

/* Return true if a leaf function should stay leaf even with profiling
   enabled.  */

bool
default_keep_leaf_when_profiled ()
{
  return false;
}

/* Return true if the state of option OPTION should be stored in PCH files
   and checked by default_pch_valid_p.  Store the option's current state
   in STATE if so.  */

static inline bool
option_affects_pch_p (int option, struct cl_option_state *state)
{
  if ((cl_options[option].flags & CL_TARGET) == 0)
    return false;
  if ((cl_options[option].flags & CL_PCH_IGNORE) != 0)
    return false;
  if (option_flag_var (option, &global_options) == &target_flags)
    if (targetm.check_pch_target_flags)
      return false;
  return get_option_state (&global_options, option, state);
}

/* Default version of get_pch_validity.
   By default, every flag difference is fatal; that will be mostly right for
   most targets, but completely right for very few.  */

void *
default_get_pch_validity (size_t *sz)
{
  struct cl_option_state state;
  size_t i;
  char *result, *r;

  *sz = 2;
  if (targetm.check_pch_target_flags)
    *sz += sizeof (target_flags);
  for (i = 0; i < cl_options_count; i++)
    if (option_affects_pch_p (i, &state))
      *sz += state.size;

  result = r = XNEWVEC (char, *sz);
  r[0] = flag_pic;
  r[1] = flag_pie;
  r += 2;
  if (targetm.check_pch_target_flags)
    {
      memcpy (r, &target_flags, sizeof (target_flags));
      r += sizeof (target_flags);
    }

  for (i = 0; i < cl_options_count; i++)
    if (option_affects_pch_p (i, &state))
      {
	memcpy (r, state.data, state.size);
	r += state.size;
      }

  return result;
}

/* Return a message which says that a PCH file was created with a different
   setting of OPTION.  */

static const char *
pch_option_mismatch (const char *option)
{
  return xasprintf (_("created and used with differing settings of '%s'"),
		    option);
}

/* Default version of pch_valid_p.  */

const char *
default_pch_valid_p (const void *data_p, size_t len ATTRIBUTE_UNUSED)
{
  struct cl_option_state state;
  const char *data = (const char *)data_p;
  size_t i;

  /* -fpic and -fpie also usually make a PCH invalid.  */
  if (data[0] != flag_pic)
    return _("created and used with different settings of %<-fpic%>");
  if (data[1] != flag_pie)
    return _("created and used with different settings of %<-fpie%>");
  data += 2;

  /* Check target_flags.  */
  if (targetm.check_pch_target_flags)
    {
      int tf;
      const char *r;

      memcpy (&tf, data, sizeof (target_flags));
      data += sizeof (target_flags);
      r = targetm.check_pch_target_flags (tf);
      if (r != NULL)
	return r;
    }

  for (i = 0; i < cl_options_count; i++)
    if (option_affects_pch_p (i, &state))
      {
	if (memcmp (data, state.data, state.size) != 0)
	  return pch_option_mismatch (cl_options[i].opt_text);
	data += state.size;
      }

  return NULL;
}

/* Default version of cstore_mode.  */

scalar_int_mode
default_cstore_mode (enum insn_code icode)
{
  return as_a <scalar_int_mode> (insn_data[(int) icode].operand[0].mode);
}

/* Default version of member_type_forces_blk.  */

bool
default_member_type_forces_blk (const_tree, machine_mode)
{
  return false;
}

/* Default version of canonicalize_comparison.  */

void
default_canonicalize_comparison (int *, rtx *, rtx *, bool)
{
}

/* Default implementation of TARGET_ATOMIC_ASSIGN_EXPAND_FENV.  */

void
default_atomic_assign_expand_fenv (tree *, tree *, tree *)
{
}

#ifndef PAD_VARARGS_DOWN
#define PAD_VARARGS_DOWN BYTES_BIG_ENDIAN
#endif

/* Build an indirect-ref expression over the given TREE, which represents a
   piece of a va_arg() expansion.  */
tree
build_va_arg_indirect_ref (tree addr)
{
  addr = build_simple_mem_ref_loc (EXPR_LOCATION (addr), addr);
  return addr;
}

/* The "standard" implementation of va_arg: read the value from the
   current (padded) address and increment by the (padded) size.  */

tree
std_gimplify_va_arg_expr (tree valist, tree type, gimple_seq *pre_p,
			  gimple_seq *post_p)
{
  tree addr, t, type_size, rounded_size, valist_tmp;
  unsigned HOST_WIDE_INT align, boundary;
  bool indirect;

  /* All of the alignment and movement below is for args-grow-up machines.
     As of 2004, there are only 3 ARGS_GROW_DOWNWARD targets, and they all
     implement their own specialized gimplify_va_arg_expr routines.  */
  if (ARGS_GROW_DOWNWARD)
    gcc_unreachable ();

  indirect = pass_va_arg_by_reference (type);
  if (indirect)
    type = build_pointer_type (type);

  if (targetm.calls.split_complex_arg
      && TREE_CODE (type) == COMPLEX_TYPE
      && targetm.calls.split_complex_arg (type))
    {
      tree real_part, imag_part;

      real_part = std_gimplify_va_arg_expr (valist,
					    TREE_TYPE (type), pre_p, NULL);
      real_part = get_initialized_tmp_var (real_part, pre_p);

      imag_part = std_gimplify_va_arg_expr (unshare_expr (valist),
					    TREE_TYPE (type), pre_p, NULL);
      imag_part = get_initialized_tmp_var (imag_part, pre_p);

      return build2 (COMPLEX_EXPR, type, real_part, imag_part);
   }

  align = PARM_BOUNDARY / BITS_PER_UNIT;
  boundary = targetm.calls.function_arg_boundary (TYPE_MODE (type), type);

  /* When we align parameter on stack for caller, if the parameter
     alignment is beyond MAX_SUPPORTED_STACK_ALIGNMENT, it will be
     aligned at MAX_SUPPORTED_STACK_ALIGNMENT.  We will match callee
     here with caller.  */
  if (boundary > MAX_SUPPORTED_STACK_ALIGNMENT)
    boundary = MAX_SUPPORTED_STACK_ALIGNMENT;

  boundary /= BITS_PER_UNIT;

  /* Hoist the valist value into a temporary for the moment.  */
  valist_tmp = get_initialized_tmp_var (valist, pre_p);

  /* va_list pointer is aligned to PARM_BOUNDARY.  If argument actually
     requires greater alignment, we must perform dynamic alignment.  */
  if (boundary > align
      && !TYPE_EMPTY_P (type)
      && !integer_zerop (TYPE_SIZE (type)))
    {
      t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist_tmp,
		  fold_build_pointer_plus_hwi (valist_tmp, boundary - 1));
      gimplify_and_add (t, pre_p);

      t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist_tmp,
		  fold_build2 (BIT_AND_EXPR, TREE_TYPE (valist),
			       valist_tmp,
			       build_int_cst (TREE_TYPE (valist), -boundary)));
      gimplify_and_add (t, pre_p);
    }
  else
    boundary = align;

  /* If the actual alignment is less than the alignment of the type,
     adjust the type accordingly so that we don't assume strict alignment
     when dereferencing the pointer.  */
  boundary *= BITS_PER_UNIT;
  if (boundary < TYPE_ALIGN (type))
    {
      type = build_variant_type_copy (type);
      SET_TYPE_ALIGN (type, boundary);
    }

  /* Compute the rounded size of the type.  */
  type_size = arg_size_in_bytes (type);
  rounded_size = round_up (type_size, align);

  /* Reduce rounded_size so it's sharable with the postqueue.  */
  gimplify_expr (&rounded_size, pre_p, post_p, is_gimple_val, fb_rvalue);

  /* Get AP.  */
  addr = valist_tmp;
  if (PAD_VARARGS_DOWN && !integer_zerop (rounded_size))
    {
      /* Small args are padded downward.  */
      t = fold_build2_loc (input_location, GT_EXPR, sizetype,
		       rounded_size, size_int (align));
      t = fold_build3 (COND_EXPR, sizetype, t, size_zero_node,
		       size_binop (MINUS_EXPR, rounded_size, type_size));
      addr = fold_build_pointer_plus (addr, t);
    }

  /* Compute new value for AP.  */
  t = fold_build_pointer_plus (valist_tmp, rounded_size);
  t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist, t);
  gimplify_and_add (t, pre_p);

  addr = fold_convert (build_pointer_type (type), addr);

  if (indirect)
    addr = build_va_arg_indirect_ref (addr);

  return build_va_arg_indirect_ref (addr);
}

/* An implementation of TARGET_CAN_USE_DOLOOP_P for targets that do
   not support nested low-overhead loops.  */

bool
can_use_doloop_if_innermost (const widest_int &, const widest_int &,
			     unsigned int loop_depth, bool)
{
  return loop_depth == 1;
}

/* Default implementation of TARGET_OPTAB_SUPPORTED_P.  */

bool
default_optab_supported_p (int, machine_mode, machine_mode, optimization_type)
{
  return true;
}

/* Default implementation of TARGET_MAX_NOCE_IFCVT_SEQ_COST.  */

unsigned int
default_max_noce_ifcvt_seq_cost (edge e)
{
  bool predictable_p = predictable_edge_p (e);

  if (predictable_p)
    {
      if (OPTION_SET_P (param_max_rtl_if_conversion_predictable_cost))
	return param_max_rtl_if_conversion_predictable_cost;
    }
  else
    {
      if (OPTION_SET_P (param_max_rtl_if_conversion_unpredictable_cost))
	return param_max_rtl_if_conversion_unpredictable_cost;
    }

  return BRANCH_COST (true, predictable_p) * COSTS_N_INSNS (3);
}

/* Default implementation of TARGET_MIN_ARITHMETIC_PRECISION.  */

unsigned int
default_min_arithmetic_precision (void)
{
  return WORD_REGISTER_OPERATIONS ? BITS_PER_WORD : BITS_PER_UNIT;
}

/* Default implementation of TARGET_C_EXCESS_PRECISION.  */

enum flt_eval_method
default_excess_precision (enum excess_precision_type ATTRIBUTE_UNUSED)
{
  return FLT_EVAL_METHOD_PROMOTE_TO_FLOAT;
}

/* Default implementation for
  TARGET_STACK_CLASH_PROTECTION_ALLOCA_PROBE_RANGE.  */
HOST_WIDE_INT
default_stack_clash_protection_alloca_probe_range (void)
{
  return 0;
}

/* The default implementation of TARGET_EARLY_REMAT_MODES.  */

void
default_select_early_remat_modes (sbitmap)
{
}

/* The default implementation of TARGET_PREFERRED_ELSE_VALUE.  */

tree
default_preferred_else_value (unsigned, tree type, unsigned, tree *)
{
  return build_zero_cst (type);
}

/* Default implementation of TARGET_HAVE_SPECULATION_SAFE_VALUE.  */
bool
default_have_speculation_safe_value (bool active ATTRIBUTE_UNUSED)
{
#ifdef HAVE_speculation_barrier
  return active ? HAVE_speculation_barrier : true;
#else
  return false;
#endif
}
/* Alternative implementation of TARGET_HAVE_SPECULATION_SAFE_VALUE
   that can be used on targets that never have speculative execution.  */
bool
speculation_safe_value_not_needed (bool active)
{
  return !active;
}

/* Default implementation of the speculation-safe-load builtin.  This
   implementation simply copies val to result and generates a
   speculation_barrier insn, if such a pattern is defined.  */
rtx
default_speculation_safe_value (machine_mode mode ATTRIBUTE_UNUSED,
				rtx result, rtx val,
				rtx failval ATTRIBUTE_UNUSED)
{
  emit_move_insn (result, val);

#ifdef HAVE_speculation_barrier
  /* Assume the target knows what it is doing: if it defines a
     speculation barrier, but it is not enabled, then assume that one
     isn't needed.  */
  if (HAVE_speculation_barrier)
    emit_insn (gen_speculation_barrier ());
#endif

  return result;
}

/* How many bits to shift in order to access the tag bits.
   The default is to store the tag in the top 8 bits of a 64 bit pointer, hence
   shifting 56 bits will leave just the tag.  */
#define HWASAN_SHIFT (GET_MODE_PRECISION (Pmode) - 8)
#define HWASAN_SHIFT_RTX GEN_INT (HWASAN_SHIFT)

bool
default_memtag_can_tag_addresses ()
{
  return false;
}

uint8_t
default_memtag_tag_size ()
{
  return 8;
}

uint8_t
default_memtag_granule_size ()
{
  return 16;
}

/* The default implementation of TARGET_MEMTAG_INSERT_RANDOM_TAG.  */
rtx
default_memtag_insert_random_tag (rtx untagged, rtx target)
{
  gcc_assert (param_hwasan_instrument_stack);
  if (param_hwasan_random_frame_tag)
    {
      rtx fn = init_one_libfunc ("__hwasan_generate_tag");
      rtx new_tag = emit_library_call_value (fn, NULL_RTX, LCT_NORMAL, QImode);
      return targetm.memtag.set_tag (untagged, new_tag, target);
    }
  else
    {
      /* NOTE: The kernel API does not have __hwasan_generate_tag exposed.
	 In the future we may add the option emit random tags with inline
	 instrumentation instead of function calls.  This would be the same
	 between the kernel and userland.  */
      return untagged;
    }
}

/* The default implementation of TARGET_MEMTAG_ADD_TAG.  */
rtx
default_memtag_add_tag (rtx base, poly_int64 offset, uint8_t tag_offset)
{
  /* Need to look into what the most efficient code sequence is.
     This is a code sequence that would be emitted *many* times, so we
     want it as small as possible.

     There are two places where tag overflow is a question:
       - Tagging the shadow stack.
	  (both tagging and untagging).
       - Tagging addressable pointers.

     We need to ensure both behaviors are the same (i.e. that the tag that
     ends up in a pointer after "overflowing" the tag bits with a tag addition
     is the same that ends up in the shadow space).

     The aim is that the behavior of tag addition should follow modulo
     wrapping in both instances.

     The libhwasan code doesn't have any path that increments a pointer's tag,
     which means it has no opinion on what happens when a tag increment
     overflows (and hence we can choose our own behavior).  */

  offset += ((uint64_t)tag_offset << HWASAN_SHIFT);
  return plus_constant (Pmode, base, offset);
}

/* The default implementation of TARGET_MEMTAG_SET_TAG.  */
rtx
default_memtag_set_tag (rtx untagged, rtx tag, rtx target)
{
  gcc_assert (GET_MODE (untagged) == Pmode && GET_MODE (tag) == QImode);
  tag = expand_simple_binop (Pmode, ASHIFT, tag, HWASAN_SHIFT_RTX, NULL_RTX,
			     /* unsignedp = */1, OPTAB_WIDEN);
  rtx ret = expand_simple_binop (Pmode, IOR, untagged, tag, target,
				 /* unsignedp = */1, OPTAB_DIRECT);
  gcc_assert (ret);
  return ret;
}

/* The default implementation of TARGET_MEMTAG_EXTRACT_TAG.  */
rtx
default_memtag_extract_tag (rtx tagged_pointer, rtx target)
{
  rtx tag = expand_simple_binop (Pmode, LSHIFTRT, tagged_pointer,
				 HWASAN_SHIFT_RTX, target,
				 /* unsignedp = */0,
				 OPTAB_DIRECT);
  rtx ret = gen_lowpart (QImode, tag);
  gcc_assert (ret);
  return ret;
}

/* The default implementation of TARGET_MEMTAG_UNTAGGED_POINTER.  */
rtx
default_memtag_untagged_pointer (rtx tagged_pointer, rtx target)
{
  rtx tag_mask = gen_int_mode ((HOST_WIDE_INT_1U << HWASAN_SHIFT) - 1, Pmode);
  rtx untagged_base = expand_simple_binop (Pmode, AND, tagged_pointer,
					   tag_mask, target, true,
					   OPTAB_DIRECT);
  gcc_assert (untagged_base);
  return untagged_base;
}

/* The default implementation of TARGET_GCOV_TYPE_SIZE.  */
HOST_WIDE_INT
default_gcov_type_size (void)
{
  return TYPE_PRECISION (long_long_integer_type_node) > 32 ? 64 : 32;
}

#include "gt-targhooks.h"
