This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

-fvisibility-inlines-hidden correction


The key property of -fvisibility-inlines-hidden is that if your
program doesn't compare method addresses across shared objects,
switching the flag on or off should have no effect (other than
performance).

So, this patch ensures it has no effect on the visibility of static
variables, and adds a testcase.  (This is a regression, the testcase
passed in 4.1.)

The logic behind the patch is that if a method has a local variable,
and neither the variable nor the method has an explicit visibility
attribute (or pragma), then either both the variable and the method
get their visibility from the enclosing class, or the method
gets its visibility from -fvisibility-inlines-hidden... and the
variable should still get its visibility from the enclosing class.

Bootstrapped & tested on powerpc-darwin8.
-- 
- Geoffrey Keating <geoffk@apple.com>

===File ~/patches/gcc-cp-visinlhdnstatic.patch==============
Index: ChangeLog
2006-07-12  Geoffrey Keating  <geoffk@apple.com>

	* doc/invoke.texi (C++ Dialect Options): Explain difference
	between -fvisibility-inlines-hidden and setting hidden
	visibility explicitly.

Index: cp/ChangeLog
2006-07-12  Geoffrey Keating  <geoffk@apple.com>

	* decl2.c (determine_visibility): Don't change visibility of
	function locals because of -fvisibility-inlines-hidden.

Index: testsuite/ChangeLog
2006-07-12  Geoffrey Keating  <geoffk@apple.com>

	* g++.dg/ext/visibility/fvisibility-inlines-hidden-2.C: New.

Index: doc/invoke.texi
===================================================================
--- doc/invoke.texi	(revision 115379)
+++ doc/invoke.texi	(working copy)
@@ -1618,10 +1618,15 @@
 on load and link times of a DSO as it massively reduces the size of the
 dynamic export table when the library makes heavy use of templates.
 
+The behaviour of this switch is not quite the same as marking the
+methods as hidden directly, because it does not affect static variables
+local to the function or cause the compiler to deduce that
+the function is defined in only one shared object.
+
 You may mark a method as having a visibility explicitly to negate the
 effect of the switch for that method.  For example, if you do want to
-compare pointers to a particular inline method, or the method has
-local static data, you might mark it as having default visibility.
+compare pointers to a particular inline method, you might mark it as
+having default visibility.
 
 @item -fno-weak
 @opindex fno-weak
Index: testsuite/g++.dg/ext/visibility/fvisibility-inlines-hidden-2.C
===================================================================
--- testsuite/g++.dg/ext/visibility/fvisibility-inlines-hidden-2.C	(revision 0)
+++ testsuite/g++.dg/ext/visibility/fvisibility-inlines-hidden-2.C	(revision 0)
@@ -0,0 +1,19 @@
+/* Test that -fvisibility-inlines-hidden doesn't affect static variables. */
+/* { dg-do compile } */
+/* { dg-require-visibility "" } */
+/* { dg-options "-fvisibility-inlines-hidden" } */
+/* { dg-final { scan-not-hidden "_ZZN3foo7my_funcEvE1x" } } */
+
+struct foo 
+{
+  int my_func() {
+    static int x;
+    return x++;
+  }
+};
+
+int t() 
+{
+  foo f;
+  return f.my_func();
+}
Index: cp/decl2.c
===================================================================
--- cp/decl2.c	(revision 115379)
+++ cp/decl2.c	(working copy)
@@ -1712,13 +1712,20 @@
       gcc_assert (TREE_CODE (decl) != VAR_DECL
 		  || !DECL_VTABLE_OR_VTT_P (decl));
 
-      if (DECL_FUNCTION_SCOPE_P (decl))
+      if (DECL_FUNCTION_SCOPE_P (decl) && ! DECL_VISIBILITY_SPECIFIED (decl))
 	{
 	  /* Local statics and classes get the visibility of their
-	     containing function.  */
+	     containing function by default, except that
+	     -fvisibility-inlines-hidden doesn't affect them.  */
 	  tree fn = DECL_CONTEXT (decl);
-	  DECL_VISIBILITY (decl) = DECL_VISIBILITY (fn);
-	  DECL_VISIBILITY_SPECIFIED (decl) = DECL_VISIBILITY_SPECIFIED (fn);
+	  if (DECL_VISIBILITY_SPECIFIED (fn) || ! DECL_CLASS_SCOPE_P (fn))
+	    {
+	      DECL_VISIBILITY (decl) = DECL_VISIBILITY (fn);
+	      DECL_VISIBILITY_SPECIFIED (decl) = 
+		DECL_VISIBILITY_SPECIFIED (fn);
+	    }
+	  else
+	    determine_visibility_from_class (decl, DECL_CONTEXT (fn));
 
 	  /* Local classes in templates have CLASSTYPE_USE_TEMPLATE set,
 	     but have no TEMPLATE_INFO, so don't try to check it.  */
============================================================


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]