From: John David Anglin Date: Tue, 28 Dec 2004 04:51:33 +0000 (+0000) Subject: re PR c++/14607 (Duplicate symbol "vtable for node" in files div.o and env.o) X-Git-Tag: releases/gcc-3.4.4~362 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=c24ae4f66c20152c6b01a05b036a0ef3bda2c507;p=thirdparty%2Fgcc.git re PR c++/14607 (Duplicate symbol "vtable for node" in files div.o and env.o) PR c++/14607. Backported from main. * configure.ac (HAVE_GAS_NSUBSPA_COMDAT): Add check for .NSUBSPA COMDAT support. * configure. config.in: Rebuilt. * config/pa/pa-protos.h (som_text_section_asm_op, som_readonly_data_section, som_one_only_readonly_data_section, som_one_only_data_section, forget_section): Declare. * pa.c (override_options): Set init_machine_status to pa_init_machine_status. (pa_init_machine_status): New function. (pa_output_function_epilogue): Call forget_section if TARGET_SOM and TARGET_GAS. (pa_asm_output_mi_thunk): Likewise. (som_text_section_asm_op): New function. (pa_select_section): Call som_one_only_readonly_data_section and som_one_only_data_section when appropriate. * pa.h (struct machine_function): Define. (EXTRA_SECTIONS, EXTRA_SECTION_FUNCTIONS, SOM_READONLY_DATA_SECTION_FUNCTION, SOM_ONE_ONLY_READONLY_DATA_SECTION_FUNCTION SOM_ONE_ONLY_DATA_SECTION_FUNCTION, FORGET_SECTION_FUNCTION): New macros. * som.h (ASM_OUTPUT_FUNCTION_PREFIX): Delete. (TEXT_SECTION_ASM_OP): Call som_text_section_asm_op. (READONLY_DATA_ASM_OP, EXTRA_SECTIONS, EXTRA_SECTION_FUNCTIONS): Delete. (READONLY_DATA_SECTION): Call som_readonly_data_section when not PIC. (SUPPORTS_SOM_COMDAT): New define. (SUPPORTS_ONE_ONLY): True if SUPPORTS_WEAK or SUPPORTS_SOM_COMDAT. (MAKE_DECL_ONE_ONLY): Rework common support. From-SVN: r92660 --- diff --git a/gcc/ChangeLog b/gcc/ChangeLog index d4dff7786b45..888a66781c10 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,36 @@ +2004-12-27 John David Anglin + + PR c++/14607. + Backported from main. + * configure.ac (HAVE_GAS_NSUBSPA_COMDAT): Add check for .NSUBSPA + COMDAT support. + * configure. config.in: Rebuilt. + * config/pa/pa-protos.h (som_text_section_asm_op, + som_readonly_data_section, som_one_only_readonly_data_section, + som_one_only_data_section, forget_section): Declare. + * pa.c (override_options): Set init_machine_status to + pa_init_machine_status. + (pa_init_machine_status): New function. + (pa_output_function_epilogue): Call forget_section if TARGET_SOM and + TARGET_GAS. + (pa_asm_output_mi_thunk): Likewise. + (som_text_section_asm_op): New function. + (pa_select_section): Call som_one_only_readonly_data_section and + som_one_only_data_section when appropriate. + * pa.h (struct machine_function): Define. + (EXTRA_SECTIONS, EXTRA_SECTION_FUNCTIONS, + SOM_READONLY_DATA_SECTION_FUNCTION, + SOM_ONE_ONLY_READONLY_DATA_SECTION_FUNCTION + SOM_ONE_ONLY_DATA_SECTION_FUNCTION, FORGET_SECTION_FUNCTION): New + macros. + * som.h (ASM_OUTPUT_FUNCTION_PREFIX): Delete. + (TEXT_SECTION_ASM_OP): Call som_text_section_asm_op. + (READONLY_DATA_ASM_OP, EXTRA_SECTIONS, EXTRA_SECTION_FUNCTIONS): Delete. + (READONLY_DATA_SECTION): Call som_readonly_data_section when not PIC. + (SUPPORTS_SOM_COMDAT): New define. + (SUPPORTS_ONE_ONLY): True if SUPPORTS_WEAK or SUPPORTS_SOM_COMDAT. + (MAKE_DECL_ONE_ONLY): Rework common support. + 2004-12-26 John David Anglin PR target/17643 diff --git a/gcc/config.in b/gcc/config.in index 4d47fbea162a..547dda029454 100644 --- a/gcc/config.in +++ b/gcc/config.in @@ -262,6 +262,9 @@ skip when using the GAS .p2align command. */ #undef HAVE_GAS_MAX_SKIP_P2ALIGN +/* Define if your assembler supports .nsubspa comdat option. */ +#undef HAVE_GAS_NSUBSPA_COMDAT + /* Define 0/1 if your assembler supports marking sections with SHF_MERGE flag. */ #undef HAVE_GAS_SHF_MERGE @@ -549,9 +552,11 @@ /* Define to `int' if doesn't define. */ #undef gid_t -/* Define as `__inline' if that's what the C compiler calls it, or to nothing - if it is not supported. */ +/* Define to `__inline__' or `__inline' if that's what the C compiler + calls it, or to nothing if 'inline' is not supported under any name. */ +#ifndef __cplusplus #undef inline +#endif /* Define to `int' if does not define. */ #undef pid_t diff --git a/gcc/config/pa/pa-protos.h b/gcc/config/pa/pa-protos.h index 848997e4d3ee..6d6dcc8e50e1 100644 --- a/gcc/config/pa/pa-protos.h +++ b/gcc/config/pa/pa-protos.h @@ -137,6 +137,7 @@ extern struct rtx_def *hppa_builtin_saveregs (void); extern void override_options (void); extern void output_ascii (FILE *, const char *, int); +extern const char * som_text_section_asm_op (void); extern HOST_WIDE_INT compute_frame_size (HOST_WIDE_INT, int *); extern int and_mask_p (unsigned HOST_WIDE_INT); extern int cint_ok_for_move (HOST_WIDE_INT); @@ -153,7 +154,6 @@ extern int cmpib_comparison_operator (rtx, enum machine_mode); #endif - #ifdef TREE_CODE extern int reloc_needed (tree); #ifdef RTX_CODE @@ -165,3 +165,9 @@ extern int function_arg_partial_nregs (CUMULATIVE_ARGS *, enum machine_mode, tree, int); #endif /* TREE_CODE */ + +/* Functions in varasm.c used by pa.c. */ +extern void som_readonly_data_section (void); +extern void som_one_only_readonly_data_section (void); +extern void som_one_only_data_section (void); +extern void forget_section (void); diff --git a/gcc/config/pa/pa.c b/gcc/config/pa/pa.c index 8864cee7bc38..661eff59cca9 100644 --- a/gcc/config/pa/pa.c +++ b/gcc/config/pa/pa.c @@ -148,6 +148,7 @@ static void output_deferred_plabels (void); #ifdef HPUX_LONG_DOUBLE_LIBRARY static void pa_hpux_init_libfuncs (void); #endif +static struct machine_function * pa_init_machine_status (void); /* Save the operands last given to a compare for use when we generate a scc or bcc insn. */ @@ -370,6 +371,8 @@ override_options (void) targetm.asm_out.unaligned_op.si = NULL; targetm.asm_out.unaligned_op.di = NULL; } + + init_machine_status = pa_init_machine_status; } static void @@ -381,6 +384,16 @@ pa_init_builtins (void) #endif } +/* Function to init struct machine_function. + This will be called, via a pointer variable, + from push_function_context. */ + +static struct machine_function * +pa_init_machine_status (void) +{ + return ggc_alloc_cleared (sizeof (machine_function)); +} + /* If FROM is a probable pointer register, mark TO as a probable pointer register with the same pointer alignment as FROM. */ @@ -4098,6 +4111,14 @@ pa_output_function_epilogue (FILE *file, HOST_WIDE_INT size ATTRIBUTE_UNUSED) fputs ("\t.EXIT\n\t.PROCEND\n", file); + if (TARGET_SOM && TARGET_GAS) + { + /* We done with this subspace except possibly for some additional + debug information. Forget that we are in this subspace to ensure + that the next function is output in its own subspace. */ + forget_section (); + } + if (INSN_ADDRESSES_SET_P ()) { insn = get_last_nonnote_insn (); @@ -7897,8 +7918,9 @@ pa_asm_output_mi_thunk (FILE *file, tree thunk_fndecl, HOST_WIDE_INT delta, fprintf (file, "\t.align 4\n"); ASM_OUTPUT_LABEL (file, label); fprintf (file, "\t.word P'%s\n", fname); - function_section (thunk_fndecl); } + else if (TARGET_SOM && TARGET_GAS) + forget_section (); current_thunk_number++; nbytes = ((nbytes + FUNCTION_BOUNDARY / BITS_PER_UNIT - 1) @@ -9060,6 +9082,50 @@ cmpib_comparison_operator (rtx op, enum machine_mode mode) || GET_CODE (op) == LEU)); } +/* Return a string to output before text in the current function. + + This function is only used with SOM. Because we don't support + named subspaces, we can only create a new subspace or switch back + to the default text subspace. */ +const char * +som_text_section_asm_op (void) +{ + if (!TARGET_SOM) + return ""; + + if (TARGET_GAS) + { + if (cfun && !cfun->machine->in_nsubspa) + { + /* We only want to emit a .nsubspa directive once at the + start of the function. */ + cfun->machine->in_nsubspa = 1; + + /* Create a new subspace for the text. This provides + better stub placement and one-only functions. */ + if (cfun->decl + && DECL_ONE_ONLY (cfun->decl) + && !DECL_WEAK (cfun->decl)) + return + "\t.SPACE $TEXT$\n\t.NSUBSPA $CODE$,QUAD=0,ALIGN=8,ACCESS=44,SORT=24,COMDAT"; + + return "\t.SPACE $TEXT$\n\t.NSUBSPA $CODE$"; + } + else + { + /* There isn't a current function or the body of the current + function has been completed. So, we are changing to the + text section to output debugging information. Do this in + the default text section. We need to forget that we are + in the text section so that the function text_section in + varasm.c will call us the next time around. */ + forget_section (); + } + } + + return "\t.SPACE $TEXT$\n\t.SUBSPA $CODE$"; +} + /* On hpux10, the linker will give an error if we have a reference in the read-only data section to a symbol defined in a shared library. Therefore, expressions that might require a reloc can @@ -9076,11 +9142,23 @@ pa_select_section (tree exp, int reloc, && (DECL_INITIAL (exp) == error_mark_node || TREE_CONSTANT (DECL_INITIAL (exp))) && !reloc) - readonly_data_section (); + { + if (TARGET_SOM + && DECL_ONE_ONLY (exp) + && !DECL_WEAK (exp)) + som_one_only_readonly_data_section (); + else + readonly_data_section (); + } else if (TREE_CODE_CLASS (TREE_CODE (exp)) == 'c' && !(TREE_CODE (exp) == STRING_CST && flag_writable_strings) && !reloc) readonly_data_section (); + else if (TARGET_SOM + && TREE_CODE (exp) == VAR_DECL + && DECL_ONE_ONLY (exp) + && !DECL_WEAK (exp)) + som_one_only_data_section (); else data_section (); } diff --git a/gcc/config/pa/pa.h b/gcc/config/pa/pa.h index 15aeccda388c..1dc2806d2ee6 100644 --- a/gcc/config/pa/pa.h +++ b/gcc/config/pa/pa.h @@ -424,6 +424,12 @@ do { \ #define CAN_DEBUG_WITHOUT_FP /* target machine storage layout */ +typedef struct machine_function GTY(()) +{ + /* Flag indicating that a .NSUBSPA directive has been output for + this function. */ + int in_nsubspa; +} machine_function; /* Define this macro if it is advisable to hold scalars in registers in a wider mode than that declared by the program. In such cases, @@ -1682,12 +1688,78 @@ do { \ goto LABEL #define TARGET_ASM_SELECT_SECTION pa_select_section - + /* Return a nonzero value if DECL has a section attribute. */ #define IN_NAMED_SECTION_P(DECL) \ ((TREE_CODE (DECL) == FUNCTION_DECL || TREE_CODE (DECL) == VAR_DECL) \ && DECL_SECTION_NAME (DECL) != NULL_TREE) +/* The following extra sections and extra section functions are only used + for SOM, but they must be provided unconditionally because pa.c's calls + to the functions might not get optimized out when other object formats + are in use. */ + +#define EXTRA_SECTIONS \ + in_som_readonly_data, \ + in_som_one_only_readonly_data, \ + in_som_one_only_data + +#define EXTRA_SECTION_FUNCTIONS \ + SOM_READONLY_DATA_SECTION_FUNCTION \ + SOM_ONE_ONLY_READONLY_DATA_SECTION_FUNCTION \ + SOM_ONE_ONLY_DATA_SECTION_FUNCTION \ + FORGET_SECTION_FUNCTION + +/* SOM puts readonly data in the default $LIT$ subspace when PIC code + is not being generated. */ +#define SOM_READONLY_DATA_SECTION_FUNCTION \ +void \ +som_readonly_data_section (void) \ +{ \ + if (!TARGET_SOM) \ + return; \ + if (in_section != in_som_readonly_data) \ + { \ + in_section = in_som_readonly_data; \ + fputs ("\t.SPACE $TEXT$\n\t.SUBSPA $LIT$\n", asm_out_file); \ + } \ +} + +/* When secondary definitions are not supported, SOM makes readonly data one + only by creating a new $LIT$ subspace in $TEXT$ with the comdat flag. */ +#define SOM_ONE_ONLY_READONLY_DATA_SECTION_FUNCTION \ +void \ +som_one_only_readonly_data_section (void) \ +{ \ + if (!TARGET_SOM) \ + return; \ + in_section = in_som_one_only_readonly_data; \ + fputs ("\t.SPACE $TEXT$\n" \ + "\t.NSUBSPA $LIT$,QUAD=0,ALIGN=8,ACCESS=0x2c,SORT=16,COMDAT\n",\ + asm_out_file); \ +} + +/* When secondary definitions are not supported, SOM makes data one only by + creating a new $DATA$ subspace in $PRIVATE$ with the comdat flag. */ +#define SOM_ONE_ONLY_DATA_SECTION_FUNCTION \ +void \ +som_one_only_data_section (void) \ +{ \ + if (!TARGET_SOM) \ + return; \ + in_section = in_som_one_only_data; \ + fputs ("\t.SPACE $PRIVATE$\n" \ + "\t.NSUBSPA $DATA$,QUAD=1,ALIGN=8,ACCESS=31,SORT=24,COMDAT\n", \ + asm_out_file); \ +} + +#define FORGET_SECTION_FUNCTION \ +void \ +forget_section (void) \ +{ \ + in_section = no_section; \ +} + /* Define this macro if references to a symbol must be treated differently depending on something about the variable or function named by the symbol (such as what section it is in). diff --git a/gcc/config/pa/som.h b/gcc/config/pa/som.h index ae52cd0a30e2..1680ecbcba3f 100644 --- a/gcc/config/pa/som.h +++ b/gcc/config/pa/som.h @@ -1,5 +1,5 @@ /* Definitions for SOM assembler support. - Copyright (C) 1999, 2001, 2002, 2003 Free Software Foundation, Inc. + Copyright (C) 1999, 2001, 2002, 2003, 2004 Free Software Foundation, Inc. This file is part of GCC. @@ -129,19 +129,6 @@ do { \ #endif -/* NAME refers to the function's name. If we are placing each function into - its own section, we need to switch to the section for this function. Note - that the section name will have a "." prefix. */ -#define ASM_OUTPUT_FUNCTION_PREFIX(FILE, NAME) \ - { \ - const char *name = (*targetm.strip_name_encoding) (NAME); \ - if (TARGET_GAS && in_section == in_text) \ - fputs ("\t.NSUBSPA $CODE$,QUAD=0,ALIGN=8,ACCESS=44,CODE_ONLY\n", FILE); \ - else if (TARGET_GAS) \ - fprintf (FILE, \ - "\t.SUBSPA .%s\n", name); \ - } - #define ASM_DECLARE_FUNCTION_NAME(FILE, NAME, DECL) \ do { tree fntype = TREE_TYPE (TREE_TYPE (DECL)); \ tree tree_type = TREE_TYPE (DECL); \ @@ -219,29 +206,14 @@ do { \ #define TARGET_ASM_FILE_START pa_som_file_start -/* Output before code. */ - -/* Supposedly the assembler rejects the command if there is no tab! */ -#define TEXT_SECTION_ASM_OP "\t.SPACE $TEXT$\n\t.SUBSPA $CODE$\n" - -/* Output before read-only data. */ - -/* Supposedly the assembler rejects the command if there is no tab! */ -#define READONLY_DATA_ASM_OP "\t.SPACE $TEXT$\n\t.SUBSPA $LIT$\n" +/* String to output before text. */ +#define TEXT_SECTION_ASM_OP som_text_section_asm_op () -#define EXTRA_SECTIONS in_readonly_data +/* String to output before writable data. */ +#define DATA_SECTION_ASM_OP "\t.SPACE $PRIVATE$\n\t.SUBSPA $DATA$\n" -#define EXTRA_SECTION_FUNCTIONS \ -extern void readonly_data (void); \ -void \ -readonly_data (void) \ -{ \ - if (in_section != in_readonly_data) \ - { \ - in_section = in_readonly_data; \ - fprintf (asm_out_file, "%s\n", READONLY_DATA_ASM_OP); \ - } \ -} +/* String to output before uninitialized data. */ +#define BSS_SECTION_ASM_OP "\t.SPACE $PRIVATE$\n\t.SUBSPA $BSS$\n" /* FIXME: HPUX ld generates incorrect GOT entries for "T" fixups which reference data within the $TEXT$ space (for example constant @@ -255,17 +227,8 @@ readonly_data (void) \ $TEXT$ space during PIC generation. Instead place all constant data into the $PRIVATE$ subspace (this reduces sharing, but it works correctly). */ - -#define READONLY_DATA_SECTION (flag_pic ? data_section : readonly_data) - -/* Output before writable data. */ - -/* Supposedly the assembler rejects the command if there is no tab! */ -#define DATA_SECTION_ASM_OP "\t.SPACE $PRIVATE$\n\t.SUBSPA $DATA$\n" - -/* Output before uninitialized data. */ - -#define BSS_SECTION_ASM_OP "\t.SPACE $PRIVATE$\n\t.SUBSPA $BSS$\n" +#define READONLY_DATA_SECTION \ + (flag_pic ? data_section : som_readonly_data_section) /* We must not have a reference to an external symbol defined in a shared library in a readonly section, else the SOM linker will @@ -361,11 +324,30 @@ do { \ #define SUPPORTS_WEAK 0 #endif -/* We can support one only if we support weak. */ -#define SUPPORTS_ONE_ONLY SUPPORTS_WEAK +/* CVS GAS as of 4/28/04 supports a comdat parameter for the .nsubspa + directive. This provides one-only linkage semantics even though we + don't have weak support. */ +#ifdef HAVE_GAS_NSUBSPA_COMDAT +#define SUPPORTS_SOM_COMDAT (TARGET_GAS) +#else +#define SUPPORTS_SOM_COMDAT 0 +#endif -/* Use weak (secondary definitions) to make one only declarations. */ -#define MAKE_DECL_ONE_ONLY(DECL) (DECL_WEAK (DECL) = 1) +/* We can support one only if we support weak or comdat. */ +#define SUPPORTS_ONE_ONLY (SUPPORTS_WEAK || SUPPORTS_SOM_COMDAT) + +/* We use DECL_COMMON for uninitialized one-only variables as we don't + have linkonce .bss. We use SOM secondary definitions or comdat for + initialized variables and functions. */ +#define MAKE_DECL_ONE_ONLY(DECL) \ + do { \ + if (TREE_CODE (DECL) == VAR_DECL \ + && (DECL_INITIAL (DECL) == 0 \ + || DECL_INITIAL (DECL) == error_mark_node)) \ + DECL_COMMON (DECL) = 1; \ + else if (SUPPORTS_WEAK) \ + DECL_WEAK (DECL) = 1; \ + } while (0) /* This is how we tell the assembler that a symbol is weak. The SOM weak implementation uses the secondary definition (sdef) flag. diff --git a/gcc/configure b/gcc/configure index 0232ac075660..1d3cc0e51334 100755 --- a/gcc/configure +++ b/gcc/configure @@ -10397,6 +10397,44 @@ _ACEOF fi +echo "$as_me:$LINENO: checking assembler for .nsubspa comdat" >&5 +echo $ECHO_N "checking assembler for .nsubspa comdat... $ECHO_C" >&6 +if test "${gcc_cv_as_nsubspa_comdat+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + gcc_cv_as_nsubspa_comdat=no + if test $in_tree_gas = yes; then + if test $gcc_cv_gas_vers -ge `expr \( \( 2 \* 1000 \) + 15 \) \* 1000 + 91` + then gcc_cv_as_nsubspa_comdat=yes +fi + elif test x$gcc_cv_as != x; then + echo ' .SPACE $TEXT$ + .NSUBSPA $CODE$,COMDAT' > conftest.s + if { ac_try='$gcc_cv_as -o conftest.o conftest.s >&5' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } + then + gcc_cv_as_nsubspa_comdat=yes + else + echo "configure: failed program was" >&5 + cat conftest.s >&5 + fi + rm -f conftest.o conftest.s + fi +fi +echo "$as_me:$LINENO: result: $gcc_cv_as_nsubspa_comdat" >&5 +echo "${ECHO_T}$gcc_cv_as_nsubspa_comdat" >&6 +if test $gcc_cv_as_nsubspa_comdat = yes; then + +cat >>confdefs.h <<\_ACEOF +#define HAVE_GAS_NSUBSPA_COMDAT 1 +_ACEOF + +fi + # .hidden needs to be supported in both the assembler and the linker, # because GNU LD versions before 2.12.1 have buggy support for STV_HIDDEN. # This is irritatingly difficult to feature test for; we have to check the diff --git a/gcc/configure.ac b/gcc/configure.ac index ec6942b43ec4..89edf64bc01f 100644 --- a/gcc/configure.ac +++ b/gcc/configure.ac @@ -1855,6 +1855,12 @@ gcc_GAS_CHECK_FEATURE([.weak], gcc_cv_as_weak, [ .weak foobar],, [AC_DEFINE(HAVE_GAS_WEAK, 1, [Define if your assembler supports .weak.])]) +gcc_GAS_CHECK_FEATURE([.nsubspa comdat], gcc_cv_as_nsubspa_comdat, + [2,15,91],, + [ .SPACE $TEXT$ + .NSUBSPA $CODE$,COMDAT],, +[AC_DEFINE(HAVE_GAS_NSUBSPA_COMDAT, 1, [Define if your assembler supports .nsubspa comdat option.])]) + # .hidden needs to be supported in both the assembler and the linker, # because GNU LD versions before 2.12.1 have buggy support for STV_HIDDEN. # This is irritatingly difficult to feature test for; we have to check the