Commit 9a6dfb47 by Richard Sandiford Committed by Richard Sandiford

mips.h (SYMBOL_FLAG_MIPS16_FUNC): Delete.

gcc/
2007-09-13  Richard Sandiford  <richard@codesourcery.com>
	    Sandra Loosemore <sandra@codesourcery.com>

	* config/mips/mips.h (SYMBOL_FLAG_MIPS16_FUNC): Delete.
	(SYMBOL_REF_MIPS16_FUNC_P): Delete.
	* config/mips/mips.c (mips_attribute_table): Turn mips16 and
	nomips16 into decl attributes.
	(TARGET_INSERT_ATTRIBUTES): Override.
	(TARGET_MERGE_DECL_ATTRIBUTES): Likewise.
	(TARGET_FUNCTION_ATTRIBUTE_INLINABLE_P): Always return true.
	(mips_mips16_type_p, mips_nomips16_type_p): Delete in favor of...
	(mips_mips16_decl_p, mips_nomips16_decl_p): ...these new functions.
	(mips_comp_type_attributes): Remove mips16 and nomips16 handling.
	(mips_use_mips16_mode_p): Reimplement as a function that takes
	a decl and considers only decl attributes.  If the decl is nested
	function, use its parent attributes.
	(mips_function_ok_for_sibcall): Use mips_use_mips16_mode_p
	instead of SYMBOL_REF_MIPS16_FUNC_P.
	(mips_set_mips16_mode): Move call to sorry here from old
	mips_use_mips16_mode_p.
	(mflip_mips16_entry): New structure.
	(mflip_mips16_htab): New variable.
	(mflip_mips16_htab_hash, mflip_mips16_htab_eq): New functions.
	(mflip_mips16_use_mips16_p, mips_insert_attributes): Likewise.
	(mips_merge_decl_attributes): New function.
	(mips_set_current_function): Reinstate call to mips_set_mips16_mode.
	Use mips_use_mips16_mode_p.
	(mips_output_mi_thunk): Use mips_use_mips16_mode_p instead of
	SYMBOL_REF_MIPS16_FUNC_P.
	(mips_encode_section_info): Don't set SYMBOL_FLAG_MIPS16_FUNC.

gcc/testsuite/
	* gcc.dg/gcc-have-sync-compare-and-swap.c: Skip for -mflip-mips16.
	* gcc.target/mips/mips16-attributes-2.c: New test.
	* gcc.target/mips/mips16-attributes-3.c: Likewise.
	* gcc.target/mips/args-3.c: Skip for -mflip-mips16.  Do not use the
	hard-float asm when __mips16 is defined.
	* gcc.target/mips/atomic-memory-1.c (main): Add a nomips16 attribute.
	* gcc.target/mips/atomic-memory-2.c (main): Likewise.
	* gcc.target/mips/fpcmp-1.c (f1, f2): Likewise.
	* gcc.target/mips/fpcmp-2.c (f1, f2): Likewise.
	* gcc.target/mips/neg-abs-1.c (f1, f2, d1, f2): Likewise.
	* gcc.target/mips/pr26765.c (foo): Likewise.
	* gcc.target/mips/gcc-have-sync-compare-and-swap-1.c: Run for all
	targets, use dg-mips-options instead of dg-options, and use -mgp32
	to force 32-bit mode.
	* gcc.target/mips/gcc-have-sync-compare-and-swap-2.c: Likewise -mgp64
	and 64-bit mode.
	* gcc.target/mips/mips.exp (is_gp32_flag): Return true for -mips32*.

Co-Authored-By: Sandra Loosemore <sandra@codesourcery.com>

From-SVN: r128460
parent 0ad7e054
2007-09-13 Richard Sandiford <richard@codesourcery.com>
Sandra Loosemore <sandra@codesourcery.com>
* config/mips/mips.h (SYMBOL_FLAG_MIPS16_FUNC): Delete.
(SYMBOL_REF_MIPS16_FUNC_P): Delete.
* config/mips/mips.c (mips_attribute_table): Turn mips16 and
nomips16 into decl attributes.
(TARGET_INSERT_ATTRIBUTES): Override.
(TARGET_MERGE_DECL_ATTRIBUTES): Likewise.
(TARGET_FUNCTION_ATTRIBUTE_INLINABLE_P): Always return true.
(mips_mips16_type_p, mips_nomips16_type_p): Delete in favor of...
(mips_mips16_decl_p, mips_nomips16_decl_p): ...these new functions.
(mips_comp_type_attributes): Remove mips16 and nomips16 handling.
(mips_use_mips16_mode_p): Reimplement as a function that takes
a decl and considers only decl attributes. If the decl is nested
function, use its parent attributes.
(mips_function_ok_for_sibcall): Use mips_use_mips16_mode_p
instead of SYMBOL_REF_MIPS16_FUNC_P.
(mips_set_mips16_mode): Move call to sorry here from old
mips_use_mips16_mode_p.
(mflip_mips16_entry): New structure.
(mflip_mips16_htab): New variable.
(mflip_mips16_htab_hash, mflip_mips16_htab_eq): New functions.
(mflip_mips16_use_mips16_p, mips_insert_attributes): Likewise.
(mips_merge_decl_attributes): New function.
(mips_set_current_function): Reinstate call to mips_set_mips16_mode.
Use mips_use_mips16_mode_p.
(mips_output_mi_thunk): Use mips_use_mips16_mode_p instead of
SYMBOL_REF_MIPS16_FUNC_P.
(mips_encode_section_info): Don't set SYMBOL_FLAG_MIPS16_FUNC.
2007-09-13 Richard Sandiford <richard@codesourcery.com>
* c-parser.c (c_parser_struct_declaration): Check for a null return.
......@@ -426,6 +426,8 @@ static void mips_encode_section_info (tree, rtx, int);
static void mips_extra_live_on_entry (bitmap);
static int mips_comp_type_attributes (const_tree, const_tree);
static void mips_set_mips16_mode (int);
static void mips_insert_attributes (tree, tree *);
static tree mips_merge_decl_attributes (tree, tree);
static void mips_set_current_function (tree);
static int mips_mode_rep_extended (enum machine_mode, enum machine_mode);
static bool mips_offset_within_alignment_p (rtx, HOST_WIDE_INT);
......@@ -734,9 +736,13 @@ const struct attribute_spec mips_attribute_table[] =
{ "long_call", 0, 0, false, true, true, NULL },
{ "far", 0, 0, false, true, true, NULL },
{ "near", 0, 0, false, true, true, NULL },
/* Switch MIPS16 ASE on and off per-function. */
{ "mips16", 0, 0, false, true, true, NULL },
{ "nomips16", 0, 0, false, true, true, NULL },
/* Switch MIPS16 ASE on and off per-function. We would really like
to make these type attributes, but GCC doesn't provide the hooks
we need to support the right conversion rules. As declaration
attributes, they affect code generation but don't carry other
semantics. */
{ "mips16", 0, 0, true, false, false, NULL },
{ "nomips16", 0, 0, true, false, false, NULL },
{ NULL, 0, 0, false, false, false, NULL }
};
......@@ -1268,6 +1274,10 @@ static const unsigned char mips16e_save_restore_regs[] = {
#undef TARGET_FUNCTION_OK_FOR_SIBCALL
#define TARGET_FUNCTION_OK_FOR_SIBCALL mips_function_ok_for_sibcall
#undef TARGET_INSERT_ATTRIBUTES
#define TARGET_INSERT_ATTRIBUTES mips_insert_attributes
#undef TARGET_MERGE_DECL_ATTRIBUTES
#define TARGET_MERGE_DECL_ATTRIBUTES mips_merge_decl_attributes
#undef TARGET_SET_CURRENT_FUNCTION
#define TARGET_SET_CURRENT_FUNCTION mips_set_current_function
......@@ -1352,6 +1362,10 @@ static const unsigned char mips16e_save_restore_regs[] = {
#undef TARGET_ATTRIBUTE_TABLE
#define TARGET_ATTRIBUTE_TABLE mips_attribute_table
/* All our function attributes are related to how out-of-line copies should
be compiled or called. They don't in themselves prevent inlining. */
#undef TARGET_FUNCTION_ATTRIBUTE_INLINABLE_P
#define TARGET_FUNCTION_ATTRIBUTE_INLINABLE_P hook_bool_const_tree_true
#undef TARGET_EXTRA_LIVE_ON_ENTRY
#define TARGET_EXTRA_LIVE_ON_ENTRY mips_extra_live_on_entry
......@@ -1395,15 +1409,15 @@ mips_far_type_p (const_tree type)
/* Similar predicates for "mips16"/"nomips16" attributes. */
static bool
mips_mips16_type_p (const_tree type)
mips_mips16_decl_p (const_tree decl)
{
return lookup_attribute ("mips16", TYPE_ATTRIBUTES (type)) != NULL;
return lookup_attribute ("mips16", DECL_ATTRIBUTES (decl)) != NULL;
}
static bool
mips_nomips16_type_p (const_tree type)
mips_nomips16_decl_p (const_tree decl)
{
return lookup_attribute ("nomips16", TYPE_ATTRIBUTES (type)) != NULL;
return lookup_attribute ("nomips16", DECL_ATTRIBUTES (decl)) != NULL;
}
/* Return 0 if the attributes for two types are incompatible, 1 if they
......@@ -1423,11 +1437,6 @@ mips_comp_type_attributes (const_tree type1, const_tree type2)
if (mips_near_type_p (type1) && mips_far_type_p (type2))
return 0;
/* Mips16/nomips16 attributes must match exactly. */
if (mips_nomips16_type_p (type1) != mips_nomips16_type_p (type2)
|| mips_mips16_type_p (type1) != mips_mips16_type_p (type2))
return 0;
return 1;
}
......@@ -4120,6 +4129,27 @@ mips_gen_conditional_trap (rtx *operands)
operands[1]));
}
/* Return true if function DECL is a MIPS16 function. Return the ambient
setting if DECL is null. */
static bool
mips_use_mips16_mode_p (tree decl)
{
if (decl)
{
/* Nested functions must use the same frame pointer as their
parent and must therefore use the same ISA mode. */
tree parent = decl_function_context (decl);
if (parent)
decl = parent;
if (mips_mips16_decl_p (decl))
return true;
if (mips_nomips16_decl_p (decl))
return false;
}
return mips_base_mips16;
}
/* Return true if calls to X can use R_MIPS_CALL* relocations. */
static bool
......@@ -4223,7 +4253,7 @@ mips_function_ok_for_sibcall (tree decl, tree exp ATTRIBUTE_UNUSED)
/* We can't do a sibcall if the called function is a MIPS16 function
because there is no direct "jx" instruction equivalent to "jalx" to
switch the ISA mode. */
if (decl && SYMBOL_REF_MIPS16_FUNC_P (XEXP (DECL_RTL (decl), 0)))
if (mips_use_mips16_mode_p (decl))
return false;
/* Otherwise OK. */
......@@ -5666,6 +5696,9 @@ mips_set_mips16_mode (int mips16_p)
of lw and sw instead. */
targetm.min_anchor_offset = 0;
targetm.max_anchor_offset = 127;
if (flag_pic || TARGET_ABICALLS)
sorry ("MIPS16 PIC");
}
else
{
......@@ -5703,12 +5736,130 @@ mips_set_mips16_mode (int mips16_p)
was_mips16_p = TARGET_MIPS16;
}
/* Use a hash table to keep track of implicit mips16/nomips16 attributes
for -mflip_mips16. It maps decl names onto a boolean mode setting. */
struct mflip_mips16_entry GTY (()) {
const char *name;
bool mips16_p;
};
static GTY ((param_is (struct mflip_mips16_entry))) htab_t mflip_mips16_htab;
/* Hash table callbacks for mflip_mips16_htab. */
static hashval_t
mflip_mips16_htab_hash (const void *entry)
{
return htab_hash_string (((const struct mflip_mips16_entry *) entry)->name);
}
static int
mflip_mips16_htab_eq (const void *entry, const void *name)
{
return strcmp (((const struct mflip_mips16_entry *) entry)->name,
(const char *) name) == 0;
}
/* DECL is a function that needs a default "mips16" or "nomips16" attribute
for -mflip-mips16. Return true if it should use "mips16" and false if
it should use "nomips16". */
static bool
mflip_mips16_use_mips16_p (tree decl)
{
struct mflip_mips16_entry *entry;
const char *name;
hashval_t hash;
void **slot;
/* Use the opposite of the command-line setting for anonymous decls. */
if (!DECL_NAME (decl))
return !mips_base_mips16;
if (!mflip_mips16_htab)
mflip_mips16_htab = htab_create_ggc (37, mflip_mips16_htab_hash,
mflip_mips16_htab_eq, NULL);
name = IDENTIFIER_POINTER (DECL_NAME (decl));
hash = htab_hash_string (name);
slot = htab_find_slot_with_hash (mflip_mips16_htab, name, hash, INSERT);
entry = (struct mflip_mips16_entry *) *slot;
if (!entry)
{
mips16_flipper = !mips16_flipper;
entry = GGC_NEW (struct mflip_mips16_entry);
entry->name = name;
entry->mips16_p = mips16_flipper ? !mips_base_mips16 : mips_base_mips16;
*slot = entry;
}
return entry->mips16_p;
}
/* Implement TARGET_INSERT_ATTRIBUTES. */
static void
mips_insert_attributes (tree decl, tree *attributes)
{
const char *name;
bool mips16_p, nomips16_p;
/* Check for "mips16" and "nomips16" attributes. */
mips16_p = lookup_attribute ("mips16", *attributes) != NULL;
nomips16_p = lookup_attribute ("nomips16", *attributes) != NULL;
if (TREE_CODE (decl) != FUNCTION_DECL)
{
if (mips16_p)
error ("%qs attribute only applies to functions", "mips16");
if (nomips16_p)
error ("%qs attribute only applies to functions", "nomips16");
}
else
{
mips16_p |= mips_mips16_decl_p (decl);
nomips16_p |= mips_nomips16_decl_p (decl);
if (mips16_p || nomips16_p)
{
/* DECL cannot be simultaneously mips16 and nomips16. */
if (mips16_p && nomips16_p)
error ("%qs cannot have both %<mips16%> and "
"%<nomips16%> attributes",
IDENTIFIER_POINTER (DECL_NAME (decl)));
}
else if (TARGET_FLIP_MIPS16 && !DECL_ARTIFICIAL (decl))
{
/* Implement -mflip-mips16. If DECL has neither a "nomips16" nor a
"mips16" attribute, arbitrarily pick one. We must pick the same
setting for duplicate declarations of a function. */
name = mflip_mips16_use_mips16_p (decl) ? "mips16" : "nomips16";
*attributes = tree_cons (get_identifier (name), NULL, *attributes);
}
}
}
/* Implement TARGET_MERGE_DECL_ATTRIBUTES. */
static tree
mips_merge_decl_attributes (tree olddecl, tree newdecl)
{
/* The decls' "mips16" and "nomips16" attributes must match exactly. */
if (mips_mips16_decl_p (olddecl) != mips_mips16_decl_p (newdecl))
error ("%qs redeclared with conflicting %qs attributes",
IDENTIFIER_POINTER (DECL_NAME (newdecl)), "mips16");
if (mips_nomips16_decl_p (olddecl) != mips_nomips16_decl_p (newdecl))
error ("%qs redeclared with conflicting %qs attributes",
IDENTIFIER_POINTER (DECL_NAME (newdecl)), "nomips16");
return merge_attributes (DECL_ATTRIBUTES (olddecl),
DECL_ATTRIBUTES (newdecl));
}
/* Implement TARGET_SET_CURRENT_FUNCTION. Decide whether the current
function should use the MIPS16 ISA and switch modes accordingly. */
static void
mips_set_current_function (tree fndecl ATTRIBUTE_UNUSED)
mips_set_current_function (tree fndecl)
{
mips_set_mips16_mode (mips_use_mips16_mode_p (fndecl));
}
/* Implement TARGET_HANDLE_OPTION. */
......@@ -8783,7 +8934,7 @@ mips_output_mi_thunk (FILE *file, tree thunk_fndecl ATTRIBUTE_UNUSED,
allowed, otherwise load the address into a register first. */
fnaddr = XEXP (DECL_RTL (function), 0);
if (TARGET_MIPS16 || TARGET_USE_GOT || SYMBOL_REF_LONG_CALL_P (fnaddr)
|| SYMBOL_REF_MIPS16_FUNC_P (fnaddr))
|| mips_use_mips16_mode_p (function))
{
/* This is messy. gas treats "la $25,foo" as part of a call
sequence and may allow a global "foo" to be lazily bound.
......@@ -12724,43 +12875,6 @@ mips_expand_builtin_bposge (enum mips_builtin_type builtin_type, rtx target)
const1_rtx, const0_rtx);
}
/* Return true if we should force MIPS16 mode for the function named by
the SYMBOL_REF SYMBOL, which belongs to DECL and has type TYPE.
FIRST is true if this is the first time handling this decl. */
static bool
mips_use_mips16_mode_p (rtx symbol, tree decl, int first, tree type)
{
tree parent;
/* Explicit function attributes take precedence. */
if (mips_mips16_type_p (type))
return true;
if (mips_nomips16_type_p (type))
return false;
/* A nested function should inherit the MIPS16 setting from its parent. */
parent = decl_function_context (decl);
if (parent)
return SYMBOL_REF_MIPS16_FUNC_P (XEXP (DECL_RTL (parent), 0));
/* Handle -mflip-mips16. */
if (TARGET_FLIP_MIPS16
&& !DECL_BUILT_IN (decl)
&& !DECL_ARTIFICIAL (decl))
{
if (!first)
/* Use the setting we picked first time around. */
return SYMBOL_REF_MIPS16_FUNC_P (symbol);
mips16_flipper = !mips16_flipper;
if (mips16_flipper)
return !mips_base_mips16;
}
return mips_base_mips16;
}
/* Set SYMBOL_REF_FLAGS for the SYMBOL_REF inside RTL, which belongs to DECL.
FIRST is true if this is the first time handling this decl. */
......@@ -12777,14 +12891,6 @@ mips_encode_section_info (tree decl, rtx rtl, int first)
if ((TARGET_LONG_CALLS && !mips_near_type_p (type))
|| mips_far_type_p (type))
SYMBOL_REF_FLAGS (symbol) |= SYMBOL_FLAG_LONG_CALL;
if (mips_use_mips16_mode_p (symbol, decl, first, type))
{
if (flag_pic || TARGET_ABICALLS)
sorry ("MIPS16 PIC");
else
SYMBOL_REF_FLAGS (symbol) |= SYMBOL_FLAG_MIPS16_FUNC;
}
}
}
......
......@@ -2338,11 +2338,6 @@ typedef struct mips_args {
#define SYMBOL_REF_LONG_CALL_P(X) \
((SYMBOL_REF_FLAGS (X) & SYMBOL_FLAG_LONG_CALL) != 0)
/* Flag to mark a function decl symbol a "mips16" function. */
#define SYMBOL_FLAG_MIPS16_FUNC (SYMBOL_FLAG_MACH_DEP << 1)
#define SYMBOL_REF_MIPS16_FUNC_P(RTX) \
((SYMBOL_REF_FLAGS (RTX) & SYMBOL_FLAG_MIPS16_FUNC) != 0)
/* True if we're generating a form of MIPS16 code in which jump tables
are stored in the text section and encoded as 16-bit PC-relative
offsets. This is only possible when general text loads are allowed,
......
2007-09-13 Richard Sandiford <richard@codesourcery.com>
* gcc.dg/gcc-have-sync-compare-and-swap.c: Skip for -mflip-mips16.
* gcc.target/mips/mips16-attributes-2.c: New test.
* gcc.target/mips/mips16-attributes-3.c: Likewise.
* gcc.target/mips/args-3.c: Skip for -mflip-mips16. Do not use the
hard-float asm when __mips16 is defined.
* gcc.target/mips/atomic-memory-1.c (main): Add a nomips16 attribute.
* gcc.target/mips/atomic-memory-2.c (main): Likewise.
* gcc.target/mips/fpcmp-1.c (f1, f2): Likewise.
* gcc.target/mips/fpcmp-2.c (f1, f2): Likewise.
* gcc.target/mips/neg-abs-1.c (f1, f2, d1, f2): Likewise.
* gcc.target/mips/pr26765.c (foo): Likewise.
* gcc.target/mips/gcc-have-sync-compare-and-swap-1.c: Run for all
targets, use dg-mips-options instead of dg-options, and use -mgp32
to force 32-bit mode.
* gcc.target/mips/gcc-have-sync-compare-and-swap-2.c: Likewise -mgp64
and 64-bit mode.
* gcc.target/mips/mips.exp (is_gp32_flag): Return true for -mips32*.
2007-09-12 Dwarakanath Rajagopal <dwarak.rajagopal@amd.com>
Michael Meissner <michael.meissner@amd.com>
/* { dg-do link } */
/* MIPS only supports these built-in functions for non-MIPS16 mode, and
-mflip-mips16 will change the mode of some functions to be different
from the command-line setting. */
/* { dg-skip-if "" { mips*-*-* } { "-mflip-mips16" } { "" } } */
void f1()
{
......
/* __mips, and related defines, guarantee that certain assembly
instructions can be used. Check a few examples. */
/* { dg-do run } */
/* { dg-skip-if "" { *-*-* } { "-mflip-mips16" } { "" } } */
extern void abort (void);
extern void exit (int);
......@@ -11,7 +12,7 @@ int foo (float inf, int64 in64, int32 in32)
int64 res64;
int32 res32;
#if __mips != 1 && defined (__mips_hard_float)
#if __mips != 1 && defined (__mips_hard_float) && !defined (__mips16)
__asm__ ("trunc.w.s %0, %1" : "=f" (res32) : "f" (inf));
if (res32 != 11)
abort ();
......
......@@ -2,7 +2,9 @@
extern void abort (void);
extern void exit (int);
int main ()
#define NOMIPS16 __attribute__ ((nomips16))
NOMIPS16 int main ()
{
#ifdef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_4
unsigned v = 0;
......
......@@ -3,7 +3,9 @@
/* { dg-final { scan-assembler "addiu" } } */
/* { dg-final { scan-assembler-not "subu" } } */
unsigned long
#define NOMIPS16 __attribute__ ((nomips16))
NOMIPS16 unsigned long
f(unsigned long *p)
{
return __sync_fetch_and_sub (p, 5);
......
/* We used to use c.lt.fmt instead of c.ule.fmt here. */
/* { dg-mips-options "-mhard-float -O2" } */
int f1 (float x, float y) { return __builtin_isless (x, y); }
int f2 (double x, double y) { return __builtin_isless (x, y); }
#define NOMIPS16 __attribute__ ((nomips16))
NOMIPS16 int f1 (float x, float y) { return __builtin_isless (x, y); }
NOMIPS16 int f2 (double x, double y) { return __builtin_isless (x, y); }
/* { dg-final { scan-assembler "c\\.ule\\.s" } } */
/* { dg-final { scan-assembler "c\\.ule\\.d" } } */
/* We used to use c.le.fmt instead of c.ult.fmt here. */
/* { dg-mips-options "-mhard-float -O2" } */
int f1 (float x, float y) { return __builtin_islessequal (x, y); }
int f2 (double x, double y) { return __builtin_islessequal (x, y); }
#define NOMIPS16 __attribute__ ((nomips16))
NOMIPS16 int f1 (float x, float y) { return __builtin_islessequal (x, y); }
NOMIPS16 int f2 (double x, double y) { return __builtin_islessequal (x, y); }
/* { dg-final { scan-assembler "c\\.ult\\.s" } } */
/* { dg-final { scan-assembler "c\\.ult\\.d" } } */
/* { dg-do preprocess } */
/* { dg-options "-mips32 -mabi=32" } */
/* { dg-mips-options "-mips2" } */
#ifdef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_1
#error nonono
......
/* { dg-do preprocess { target { mips64*-*-* } } } */
/* { dg-options "-mips64 -mabi=64" } */
/* { dg-do preprocess } */
/* { dg-mips-options "-mgp64" } */
#ifdef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_1
#error nonono
......
......@@ -103,6 +103,7 @@ proc is_gp32_flag {flag} {
switch -glob -- $flag {
-msmartmips -
-mips[12] -
-mips32* -
-march=mips32* -
-mgp32 { return 1 }
default { return 0 }
......
/* { dg-skip-if "" { *-*-* } { "-mflip-mips16" } { "" } } */
void f1 (void);
void __attribute__((mips16)) f1 (void) {} /* { dg-error "conflicting" } */
void __attribute__((mips16)) f2 (void);
void f2 (void) {} /* { dg-error "conflicting" } */
void f3 (void);
void __attribute__((nomips16)) f3 (void) {} /* { dg-error "conflicting" } */
void __attribute__((nomips16)) f4 (void);
void f4 (void) {} /* { dg-error "conflicting" } */
void __attribute__((mips16, nomips16)) f5 (void) {} /* { dg-error "cannot have both" } */
/* We should be able to assign mips16 and nomips16 functions to a pointer. */
void __attribute__((mips16)) f1 (void);
void (*ptr1) (void) = f1;
void __attribute__((nomips16)) f2 (void);
void (*ptr2) (void) = f2;
......@@ -7,7 +7,9 @@
/* { dg-final { scan-assembler "abs.s" } } */
/* { dg-final { scan-assembler "abs.d" } } */
float f1 (float f) { return -f; }
float f2 (float f) { return __builtin_fabsf (f); }
double d1 (double d) { return -d; }
double d2 (double d) { return __builtin_fabs (d); }
#define NOMIPS16 __attribute__ ((nomips16))
NOMIPS16 float f1 (float f) { return -f; }
NOMIPS16 float f2 (float f) { return __builtin_fabsf (f); }
NOMIPS16 double d1 (double d) { return -d; }
NOMIPS16 double d2 (double d) { return __builtin_fabs (d); }
......@@ -6,7 +6,9 @@
__thread int *a = 0;
void foo (void)
#define NOMIPS16 __attribute__ ((nomips16))
NOMIPS16 void foo (void)
{
extern int *b;
b = (int *) ((*a));
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment