]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
re PR c/6343 (attribute((weak)) not working on second declaration)
authorFranz Sirl <Franz.Sirl-kernel@lauterbach.com>
Sun, 28 Apr 2002 18:43:58 +0000 (18:43 +0000)
committerFranz Sirl <sirl@gcc.gnu.org>
Sun, 28 Apr 2002 18:43:58 +0000 (18:43 +0000)
2002-04-28  Franz Sirl  <Franz.Sirl-kernel@lauterbach.com>

PR c/6343
* c-decl.c (duplicate_decls): Call merge_weak.
* c-pragma.c (apply_pragma_weak): Warn about misuse.
* output.h (merge_weak): Prototype merge_weak.
* varasm.c (merge_weak): New function.
(declare_weak): Make sure we don't give an error on VAR_DECLs.
Mark RTL with SYMBOL_REF_WEAK.

cp:
* decl.c (duplicate_decls): Call merge_weak.

testsuite:
* gcc.dg/weak-[2-7].c: New tests.

From-SVN: r52848

gcc/ChangeLog
gcc/c-decl.c
gcc/c-pragma.c
gcc/cp/ChangeLog
gcc/cp/decl.c
gcc/output.h
gcc/testsuite/ChangeLog
gcc/varasm.c

index 682b8098f37820d65136f145161780e0721e25c0..431490c4830cb39c92522a2e5f5327faae6ec43b 100644 (file)
@@ -1,3 +1,13 @@
+2002-04-28  Franz Sirl  <Franz.Sirl-kernel@lauterbach.com>
+
+       PR c/6343
+       * c-decl.c (duplicate_decls): Call merge_weak.
+       * c-pragma.c (apply_pragma_weak): Warn about misuse.
+       * output.h (merge_weak): Prototype merge_weak.
+       * varasm.c (merge_weak): New function.
+       (declare_weak): Make sure we don't give an error on VAR_DECLs.
+       Mark RTL with SYMBOL_REF_WEAK.
+
 2002-04-25  David S. Miller  <davem@redhat.com>
 
        PR target/6422
index dca3b646050672ffc6348aefbc4c3ff805e4550f..59ef4d4e8a9d52d930ce3c6bae84d1e3f208d821 100644 (file)
@@ -1955,7 +1955,8 @@ duplicate_decls (newdecl, olddecl, different_binding_level)
     }
 
   /* Merge the storage class information.  */
-  DECL_WEAK (newdecl) |= DECL_WEAK (olddecl);
+  merge_weak (newdecl, olddecl);
+
   /* For functions, static overrides non-static.  */
   if (TREE_CODE (newdecl) == FUNCTION_DECL)
     {
index 4bf7ce205ac21214a8ad9916201bba80473191b9..d5df35595975e07d7b593e5f25710825c2f35c9d 100644 (file)
@@ -287,6 +287,10 @@ apply_pragma_weak (decl, value)
     decl_attributes (&decl, build_tree_list (get_identifier ("alias"),
                                             build_tree_list (NULL, value)),
                     0);
+  if (SUPPORTS_WEAK && DECL_EXTERNAL (decl) && TREE_USED (decl)
+      && TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl)))
+    warning_with_decl (decl, "applying #pragma weak `%s' after first use results in unspecified behavior");
+
   declare_weak (decl);
 }
 
index 82710c5d3005f9152ab073283c6c3693bc4ff578..d280e08ff6387b00f0f023b7deaa35764e984434 100644 (file)
@@ -1,3 +1,8 @@
+2002-04-28  Franz Sirl  <Franz.Sirl-kernel@lauterbach.com>
+
+       PR c/6343
+       * decl.c (duplicate_decls): Call merge_weak.
+
 2002-04-26  Mark Mitchell  <mark@codesourcery.com>
 
        PR c++/6497
index bb74515daa7f0ec79f296dc294e579820c969417..4ba1511c20282b076faa29c931cc02dbc648cf6d 100644 (file)
@@ -3645,7 +3645,8 @@ duplicate_decls (newdecl, olddecl)
     }
 
   /* Merge the storage class information.  */
-  DECL_WEAK (newdecl) |= DECL_WEAK (olddecl);
+  merge_weak (newdecl, olddecl);
+
   DECL_ONE_ONLY (newdecl) |= DECL_ONE_ONLY (olddecl);
   DECL_DEFER_OUTPUT (newdecl) |= DECL_DEFER_OUTPUT (olddecl);
   TREE_PUBLIC (newdecl) = TREE_PUBLIC (olddecl);
index b6e460442efa52ec6b8a323b0c91f89e3df4375d..0e11df3c833f5c7a6d0a161d93fd3a4f5bcb73fa 100644 (file)
@@ -231,6 +231,8 @@ extern void mergeable_constant_section      PARAMS ((enum machine_mode,
 
 /* Declare DECL to be a weak symbol.  */
 extern void declare_weak               PARAMS ((tree));
+/* Merge weak status.  */
+extern void merge_weak                 PARAMS ((tree, tree));
 #endif /* TREE_CODE */
 
 /* Emit any pending weak declarations.  */
index b7a7a9460e2bdc9bf457e5ffd5239737c6ec4598..3b98fd942163527f434d3fa8a7bfb0ec4734a45d 100644 (file)
@@ -1,3 +1,8 @@
+2002-04-28  Franz Sirl  <Franz.Sirl-kernel@lauterbach.com>
+
+       PR c/6343
+       * gcc.dg/weak-[2-7].c: New tests.
+
 2002-04-26  Mark Mitchell  <mark@codesourcery.com>
 
        PR c++/6497
index 8f8641f4a495debcc5ef03b62a26868f1bf3037a..77f00d9c1c9a77868c8d113105f850b9b86c58e3 100644 (file)
@@ -4990,6 +4990,31 @@ output_constructor (exp, size, align)
    to be emitted.  */
 static tree weak_decls;
 
+/* Merge weak status between NEWDECL and OLDDECL.  */
+
+void
+merge_weak (newdecl, olddecl)
+     tree newdecl;
+     tree olddecl;
+{
+  tree decl;
+
+  if (DECL_WEAK (newdecl) == DECL_WEAK (olddecl))
+    return;
+
+  decl = DECL_WEAK (olddecl) ? newdecl : olddecl;
+
+  if (SUPPORTS_WEAK
+      && DECL_EXTERNAL (newdecl) && DECL_EXTERNAL (olddecl)
+      && (TREE_CODE (decl) != VAR_DECL
+         || ! TREE_STATIC (decl))
+      && TREE_USED (decl)
+      && TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl)))
+    warning_with_decl (decl, "weak declaration of `%s' after first use results in unspecified behavior");
+
+  declare_weak (decl);
+}
+
 /* Declare DECL to be a weak symbol.  */
 
 void
@@ -4998,7 +5023,7 @@ declare_weak (decl)
 {
   if (! TREE_PUBLIC (decl))
     error_with_decl (decl, "weak declaration of `%s' must be public");
-  else if (TREE_ASM_WRITTEN (decl))
+  else if (TREE_CODE (decl) == FUNCTION_DECL && TREE_ASM_WRITTEN (decl))
     error_with_decl (decl, "weak declaration of `%s' must precede definition");
   else if (SUPPORTS_WEAK)
     {
@@ -5009,6 +5034,12 @@ declare_weak (decl)
     warning_with_decl (decl, "weak declaration of `%s' not supported");
 
   DECL_WEAK (decl) = 1;
+
+  if (DECL_RTL_SET_P (decl)
+      && GET_CODE (DECL_RTL (decl)) == MEM
+      && XEXP (DECL_RTL (decl), 0)
+      && GET_CODE (XEXP (DECL_RTL (decl), 0)) == SYMBOL_REF)
+    SYMBOL_REF_WEAK (XEXP (DECL_RTL (decl), 0)) = 1;
 }
 
 /* Emit any pending weak declarations.  */