re PR target/27067 (Compile errors with multiple inheritance where the stdcall attribute is applied to virtual functions.)
ChangeLog PR target/27067 * doc/tm.texi (TARGET_MANGLE_DECL_ASSEMBLER_NAME): Document. * targhooks.h (default_mangle_decl_assembler_name): Declare default hook. * targhooks.c (default_mangle_decl_assembler_name): Define default hook. * target-def.h (TARGET_MANGLE_DECL_ASSEMBLER_NAME) New. Set to default hook. * target.h (struct gcc_target): Add mangle_decl_assembler_name field. * langhooks.c (lhd_set_decl_assembler_name): Call targetm.mangle_decl_assembler_name for names with global scope. * config/i386/cygming.h (TARGET_MANGLE_DECL_ASSEMBLER_NAME) Override default. (ASM_OUTPUT_DEF_FROM_DECLS): Simplify to use DECL_ASSEMBLER_NAME. * config/i386/i386-protos.h (i386_pe_mangle_decl_assembler_name): Declare. * config/i386/winnt.c (i386_pe_maybe_mangle_decl_assembler_name): New. Factored out of i386_pe_encode_section_info. (gen_stdcall_or_fastcall_suffix): Get name identifier as argument. Move check for prior decoration of stdcall symbols to i386_pe_encode_section_info. (i386_pe_encode_section_info): Adjust call to gen_stdcall_or_fastcall_suffix. Use i386_pe_maybe_mangle_decl_assembler_name, if needed. (i386_pe_mangle_decl_assembler_name): New. Wrap i386_pe_maybe_mangle_decl_assembler_name. cp/ChangeLog * mangle.c (mangle_decl): Call targetm.mangle_decl_assembler_name. From-SVN: r125020
This commit is contained in:
parent
4f5497a924
commit
5234b8f573
12 changed files with 146 additions and 42 deletions
|
@ -1,3 +1,33 @@
|
|||
2007-05-24 Danny Smith <dannysmith@users.sourceforge.net>
|
||||
|
||||
PR target/27067
|
||||
* doc/tm.texi (TARGET_MANGLE_DECL_ASSEMBLER_NAME): Document.
|
||||
* targhooks.h (default_mangle_decl_assembler_name): Declare
|
||||
default hook.
|
||||
* targhooks.c (default_mangle_decl_assembler_name): Define
|
||||
default hook.
|
||||
* target-def.h (TARGET_MANGLE_DECL_ASSEMBLER_NAME) New. Set to
|
||||
default hook.
|
||||
* target.h (struct gcc_target): Add mangle_decl_assembler_name field.
|
||||
* langhooks.c (lhd_set_decl_assembler_name): Call
|
||||
targetm.mangle_decl_assembler_name for names with global scope.
|
||||
|
||||
* config/i386/cygming.h (TARGET_MANGLE_DECL_ASSEMBLER_NAME) Override
|
||||
default.
|
||||
(ASM_OUTPUT_DEF_FROM_DECLS): Simplify to use DECL_ASSEMBLER_NAME.
|
||||
* config/i386/i386-protos.h (i386_pe_mangle_decl_assembler_name):
|
||||
Declare.
|
||||
* config/i386/winnt.c (i386_pe_maybe_mangle_decl_assembler_name):
|
||||
New. Factored out of i386_pe_encode_section_info.
|
||||
(gen_stdcall_or_fastcall_suffix): Get name identifier as argument.
|
||||
Move check for prior decoration of stdcall
|
||||
symbols to i386_pe_encode_section_info.
|
||||
(i386_pe_encode_section_info): Adjust call to
|
||||
gen_stdcall_or_fastcall_suffix. Use
|
||||
i386_pe_maybe_mangle_decl_assembler_name, if needed.
|
||||
(i386_pe_mangle_decl_assembler_name): New. Wrap
|
||||
i386_pe_maybe_mangle_decl_assembler_name.
|
||||
|
||||
2007-05-16 Rafael Avila de Espindola <espindola@google.com>
|
||||
|
||||
* c-common.c (c_common_signed_or_unsigned_type): Delay the check for
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
/* Operating system specific defines to be used when targeting GCC for
|
||||
hosting on Windows32, using a Unix style C library and tools.
|
||||
Copyright (C) 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003,
|
||||
2004, 2005
|
||||
2004, 2005, 2007
|
||||
Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GCC.
|
||||
|
@ -347,15 +347,11 @@ do { \
|
|||
/* This implements the `alias' attribute, keeping any stdcall or
|
||||
fastcall decoration. */
|
||||
#undef ASM_OUTPUT_DEF_FROM_DECLS
|
||||
#define ASM_OUTPUT_DEF_FROM_DECLS(STREAM, DECL, TARGET) \
|
||||
#define ASM_OUTPUT_DEF_FROM_DECLS(STREAM, DECL, TARGET) \
|
||||
do \
|
||||
{ \
|
||||
const char *alias; \
|
||||
rtx rtlname = XEXP (DECL_RTL (DECL), 0); \
|
||||
if (GET_CODE (rtlname) == SYMBOL_REF) \
|
||||
alias = XSTR (rtlname, 0); \
|
||||
else \
|
||||
abort (); \
|
||||
const char *alias \
|
||||
= IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (DECL)); \
|
||||
if (TREE_CODE (DECL) == FUNCTION_DECL) \
|
||||
i386_pe_declare_function_type (STREAM, alias, \
|
||||
TREE_PUBLIC (DECL)); \
|
||||
|
@ -394,6 +390,7 @@ do { \
|
|||
|
||||
#define TARGET_VALID_DLLIMPORT_ATTRIBUTE_P i386_pe_valid_dllimport_attribute_p
|
||||
#define TARGET_CXX_ADJUST_CLASS_AT_DEFINITION i386_pe_adjust_class_at_definition
|
||||
#define TARGET_MANGLE_DECL_ASSEMBLER_NAME i386_pe_mangle_decl_assembler_name
|
||||
|
||||
#undef TREE
|
||||
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/* Definitions of target machine for GCC for IA-32.
|
||||
Copyright (C) 1988, 1992, 1994, 1995, 1996, 1996, 1997, 1998, 1999,
|
||||
2000, 2001, 2002, 2003, 2004, 2005, 2006
|
||||
2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007
|
||||
Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GCC.
|
||||
|
@ -220,6 +220,7 @@ extern void i386_pe_asm_output_aligned_decl_common (FILE *, tree,
|
|||
HOST_WIDE_INT,
|
||||
HOST_WIDE_INT);
|
||||
extern void i386_pe_file_end (void);
|
||||
extern tree i386_pe_mangle_decl_assembler_name (tree, tree);
|
||||
|
||||
/* In winnt-cxx.c and winnt-stubs.c */
|
||||
extern void i386_pe_adjust_class_at_definition (tree);
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
/* Subroutines for insn-output.c for Windows NT.
|
||||
Contributed by Douglas Rupp (drupp@cs.washington.edu)
|
||||
Copyright (C) 1995, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004,
|
||||
2005, 2006 Free Software Foundation, Inc.
|
||||
2005, 2006, 2007 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GCC.
|
||||
|
||||
|
@ -75,7 +75,7 @@ ix86_handle_selectany_attribute (tree *node, tree name,
|
|||
/* The attribute applies only to objects that are initialized and have
|
||||
external linkage. However, we may not know about initialization
|
||||
until the language frontend has processed the decl. We'll check for
|
||||
initialization later in encode_section_info. */
|
||||
initialization later in encode_section_info. */
|
||||
if (TREE_CODE (*node) != VAR_DECL || !TREE_PUBLIC (*node))
|
||||
{
|
||||
error ("%qs attribute applies only to initialized variables"
|
||||
|
@ -154,22 +154,21 @@ i386_pe_valid_dllimport_attribute_p (tree decl)
|
|||
return true;
|
||||
}
|
||||
|
||||
/* Return string which is the former assembler name modified with a
|
||||
suffix consisting of an atsign (@) followed by the number of bytes of
|
||||
arguments. If FASTCALL is true, also add the FASTCALL_PREFIX.
|
||||
/* Return string which is the function name, identified by ID, modified
|
||||
with a suffix consisting of an atsign (@) followed by the number of
|
||||
bytes of arguments. If ID is NULL use the DECL_NAME as base. If
|
||||
FASTCALL is true, also add the FASTCALL_PREFIX.
|
||||
Return NULL if no change required. */
|
||||
|
||||
static tree
|
||||
gen_stdcall_or_fastcall_suffix (tree decl, bool fastcall)
|
||||
gen_stdcall_or_fastcall_suffix (tree decl, tree id, bool fastcall)
|
||||
{
|
||||
HOST_WIDE_INT total = 0;
|
||||
const char *asm_str = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl));
|
||||
const char *old_str = IDENTIFIER_POINTER (id != NULL_TREE ? id : DECL_NAME (decl));
|
||||
char *new_str, *p;
|
||||
tree formal_type;
|
||||
|
||||
/* Do not change the identifier if a verbatim asmspec or already done. */
|
||||
if (*asm_str == '*' || strchr (asm_str, '@'))
|
||||
return NULL_TREE;
|
||||
gcc_assert (TREE_CODE (decl) == FUNCTION_DECL);
|
||||
|
||||
formal_type = TYPE_ARG_TYPES (TREE_TYPE (decl));
|
||||
if (formal_type != NULL_TREE)
|
||||
|
@ -202,16 +201,47 @@ gen_stdcall_or_fastcall_suffix (tree decl, bool fastcall)
|
|||
|
||||
formal_type = TREE_CHAIN (formal_type);
|
||||
}
|
||||
|
||||
/* Assume max of 8 base 10 digits in the suffix. */
|
||||
p = new_str = alloca (1 + strlen (asm_str) + 1 + 8 + 1);
|
||||
p = new_str = alloca (1 + strlen (old_str) + 1 + 8 + 1);
|
||||
if (fastcall)
|
||||
*p++ = FASTCALL_PREFIX;
|
||||
sprintf (p, "%s@" HOST_WIDE_INT_PRINT_DEC, asm_str, total);
|
||||
sprintf (p, "%s@" HOST_WIDE_INT_PRINT_DEC, old_str, total);
|
||||
|
||||
return get_identifier (new_str);
|
||||
}
|
||||
|
||||
/* Maybe decorate and get a new identifier for the DECL of a stdcall or
|
||||
fastcall function. The original identifier is supplied in ID. */
|
||||
|
||||
static tree
|
||||
i386_pe_maybe_mangle_decl_assembler_name (tree decl, tree id)
|
||||
{
|
||||
tree new_id = NULL_TREE;
|
||||
|
||||
if (TREE_CODE (decl) == FUNCTION_DECL)
|
||||
{
|
||||
tree type_attributes = TYPE_ATTRIBUTES (TREE_TYPE (decl));
|
||||
if (lookup_attribute ("stdcall", type_attributes))
|
||||
new_id = gen_stdcall_or_fastcall_suffix (decl, id, false);
|
||||
else if (lookup_attribute ("fastcall", type_attributes))
|
||||
new_id = gen_stdcall_or_fastcall_suffix (decl, id, true);
|
||||
}
|
||||
|
||||
return new_id;
|
||||
}
|
||||
|
||||
/* This is used as a target hook to modify the DECL_ASSEMBLER_NAME
|
||||
in the language-independent default hook
|
||||
langhooks,c:lhd_set_decl_assembler_name ()
|
||||
and in cp/mangle,c:mangle_decl (). */
|
||||
tree
|
||||
i386_pe_mangle_decl_assembler_name (tree decl, tree id)
|
||||
{
|
||||
tree new_id = i386_pe_maybe_mangle_decl_assembler_name (decl, id);
|
||||
|
||||
return (new_id ? new_id : id);
|
||||
}
|
||||
|
||||
void
|
||||
i386_pe_encode_section_info (tree decl, rtx rtl, int first)
|
||||
{
|
||||
|
@ -233,21 +263,24 @@ i386_pe_encode_section_info (tree decl, rtx rtl, int first)
|
|||
case FUNCTION_DECL:
|
||||
if (first)
|
||||
{
|
||||
tree type_attributes = TYPE_ATTRIBUTES (TREE_TYPE (decl));
|
||||
tree newid = NULL_TREE;
|
||||
|
||||
if (lookup_attribute ("stdcall", type_attributes))
|
||||
newid = gen_stdcall_or_fastcall_suffix (decl, false);
|
||||
else if (lookup_attribute ("fastcall", type_attributes))
|
||||
newid = gen_stdcall_or_fastcall_suffix (decl, true);
|
||||
if (newid != NULL_TREE)
|
||||
/* FIXME: In Ada, and perhaps other language frontends,
|
||||
imported stdcall names may not yet have been modified.
|
||||
Check and do it know. */
|
||||
tree new_id;
|
||||
tree old_id = DECL_ASSEMBLER_NAME (decl);
|
||||
const char* asm_str = IDENTIFIER_POINTER (old_id);
|
||||
/* Do not change the identifier if a verbatim asmspec
|
||||
or if stdcall suffix already added. */
|
||||
if (*asm_str == '*' || strchr (asm_str, '@'))
|
||||
break;
|
||||
if ((new_id = i386_pe_maybe_mangle_decl_assembler_name (decl, old_id)))
|
||||
{
|
||||
XSTR (symbol, 0) = IDENTIFIER_POINTER (newid);
|
||||
/* These attributes must be present on first declaration,
|
||||
change_decl_assembler_name will warn if they are added
|
||||
later and the decl has been referenced, but duplicate_decls
|
||||
should catch the mismatch before this is called. */
|
||||
change_decl_assembler_name (decl, newid);
|
||||
change_decl_assembler_name will warn if they are added
|
||||
later and the decl has been referenced, but duplicate_decls
|
||||
should catch the mismatch first. */
|
||||
change_decl_assembler_name (decl, new_id);
|
||||
XSTR (symbol, 0) = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl));
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
|
|
@ -1,3 +1,8 @@
|
|||
2007-05-24 Danny Smith <dannysmith@users.sourceforge.net>
|
||||
|
||||
PR target/27067
|
||||
* mangle.c (mangle_decl): Call targetm.mangle_decl_assembler_name.
|
||||
|
||||
2007-05-22 Ollie Wild <aaw@google.com>
|
||||
|
||||
* name-lookup.c (ambiguous_decl): Adds check for hidden types.
|
||||
|
|
|
@ -2621,8 +2621,9 @@ get_identifier_nocopy (const char *name)
|
|||
void
|
||||
mangle_decl (const tree decl)
|
||||
{
|
||||
SET_DECL_ASSEMBLER_NAME (decl,
|
||||
get_identifier_nocopy (mangle_decl_string (decl)));
|
||||
tree id = get_identifier_nocopy (mangle_decl_string (decl));
|
||||
id = targetm.mangle_decl_assembler_name (decl, id);
|
||||
SET_DECL_ASSEMBLER_NAME (decl, id);
|
||||
}
|
||||
|
||||
/* Generate the mangled representation of TYPE. */
|
||||
|
|
|
@ -6462,6 +6462,16 @@ constants in @code{flag_pic} mode in @code{data_section} and everything
|
|||
else in @code{readonly_data_section}.
|
||||
@end deftypefn
|
||||
|
||||
@deftypefn {Target Hook} void TARGET_MANGLE_DECL_ASSEMBLER_NAME (tree @var{decl}, tree @var{id})
|
||||
Define this hook if you need to postprocess the assembler name generated
|
||||
by target-independent code. The @var{id} provided to this hook will be
|
||||
the computed name (e.g., the macro @code{DECL_NAME} of the @var{decl} in C,
|
||||
or the mangled name of the @var{decl} in C++). The return value of the
|
||||
hook is an @code{IDENTIFIER_NODE} for the appropriate mangled name on
|
||||
your target system. The default implementation of this hook just
|
||||
returns the @var{id} provided.
|
||||
@end deftypefn
|
||||
|
||||
@deftypefn {Target Hook} void TARGET_ENCODE_SECTION_INFO (tree @var{decl}, rtx @var{rtl}, int @var{new_decl_p})
|
||||
Define this hook if references to a symbol or a constant must be
|
||||
treated differently depending on something about the variable or
|
||||
|
|
|
@ -34,6 +34,7 @@ Boston, MA 02110-1301, USA. */
|
|||
#include "integrate.h"
|
||||
#include "flags.h"
|
||||
#include "langhooks.h"
|
||||
#include "target.h"
|
||||
#include "langhooks-def.h"
|
||||
#include "ggc.h"
|
||||
#include "diagnostic.h"
|
||||
|
@ -147,6 +148,8 @@ lhd_warn_unused_global_decl (tree decl)
|
|||
void
|
||||
lhd_set_decl_assembler_name (tree decl)
|
||||
{
|
||||
tree id;
|
||||
|
||||
/* The language-independent code should never use the
|
||||
DECL_ASSEMBLER_NAME for lots of DECLs. Only FUNCTION_DECLs and
|
||||
VAR_DECLs for variables with static storage duration need a real
|
||||
|
@ -161,21 +164,26 @@ lhd_set_decl_assembler_name (tree decl)
|
|||
as that used in the source language. (That's correct for C, and
|
||||
GCC used to set DECL_ASSEMBLER_NAME to the same value as
|
||||
DECL_NAME in build_decl, so this choice provides backwards
|
||||
compatibility with existing front-ends.
|
||||
|
||||
compatibility with existing front-ends. This assumption is wrapped
|
||||
in a target hook, to allow for target-specific modification of the
|
||||
identifier.
|
||||
|
||||
Can't use just the variable's own name for a variable whose scope
|
||||
is less than the whole compilation. Concatenate a distinguishing
|
||||
number - we use the DECL_UID. */
|
||||
|
||||
if (TREE_PUBLIC (decl) || DECL_CONTEXT (decl) == NULL_TREE)
|
||||
SET_DECL_ASSEMBLER_NAME (decl, DECL_NAME (decl));
|
||||
id = targetm.mangle_decl_assembler_name (decl, DECL_NAME (decl));
|
||||
else
|
||||
{
|
||||
const char *name = IDENTIFIER_POINTER (DECL_NAME (decl));
|
||||
char *label;
|
||||
|
||||
ASM_FORMAT_PRIVATE_NAME (label, name, DECL_UID (decl));
|
||||
SET_DECL_ASSEMBLER_NAME (decl, get_identifier (label));
|
||||
id = get_identifier (label);
|
||||
}
|
||||
SET_DECL_ASSEMBLER_NAME (decl, id);
|
||||
|
||||
}
|
||||
|
||||
/* Type promotion for variable arguments. */
|
||||
|
|
|
@ -464,6 +464,10 @@ Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|||
#define TARGET_IN_SMALL_DATA_P hook_bool_tree_false
|
||||
#endif
|
||||
|
||||
#ifndef TARGET_MANGLE_DECL_ASSEMBLER_NAME
|
||||
#define TARGET_MANGLE_DECL_ASSEMBLER_NAME mangle_decl_assembler_name
|
||||
#endif
|
||||
|
||||
#ifndef TARGET_ENCODE_SECTION_INFO
|
||||
#define TARGET_ENCODE_SECTION_INFO default_encode_section_info
|
||||
#endif
|
||||
|
@ -681,6 +685,7 @@ Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|||
TARGET_FUNCTION_OK_FOR_SIBCALL, \
|
||||
TARGET_IN_SMALL_DATA_P, \
|
||||
TARGET_BINDS_LOCAL_P, \
|
||||
TARGET_MANGLE_DECL_ASSEMBLER_NAME, \
|
||||
TARGET_ENCODE_SECTION_INFO, \
|
||||
TARGET_STRIP_NAME_ENCODING, \
|
||||
TARGET_SHIFT_TRUNCATION_MASK, \
|
||||
|
|
|
@ -544,6 +544,12 @@ struct gcc_target
|
|||
to the current module. */
|
||||
bool (* binds_local_p) (tree);
|
||||
|
||||
/* Modify and return the identifier of a DECL's external name,
|
||||
originally identified by ID, as required by the target,
|
||||
(eg, append @nn to windows32 stdcall function names).
|
||||
The default is to return ID without modification. */
|
||||
tree (* mangle_decl_assembler_name) (tree decl, tree id);
|
||||
|
||||
/* Do something target-specific to record properties of the DECL into
|
||||
the associated SYMBOL_REF. */
|
||||
void (* encode_section_info) (tree, rtx, int);
|
||||
|
|
|
@ -631,4 +631,11 @@ default_reloc_rw_mask (void)
|
|||
return flag_pic ? 3 : 0;
|
||||
}
|
||||
|
||||
/* By default, do no modification. */
|
||||
tree default_mangle_decl_assembler_name (tree decl ATTRIBUTE_UNUSED,
|
||||
tree id)
|
||||
{
|
||||
return id;
|
||||
}
|
||||
|
||||
#include "gt-targhooks.h"
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/* Default target hook functions.
|
||||
Copyright (C) 2003, 2004, 2005 Free Software Foundation, Inc.
|
||||
Copyright (C) 2003, 2004, 2005, 2007 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GCC.
|
||||
|
||||
|
@ -84,3 +84,4 @@ extern enum reg_class default_secondary_reload (bool, rtx, enum reg_class,
|
|||
extern void hook_void_bitmap (bitmap);
|
||||
extern bool default_handle_c_option (size_t, const char *, int);
|
||||
extern int default_reloc_rw_mask (void);
|
||||
extern tree default_mangle_decl_assembler_name (tree, tree);
|
||||
|
|
Loading…
Add table
Reference in a new issue