re PR c++/30066 (option to make inline functions hidden)
PR c++/30066 gcc/c-family: * c.opt (fvisibility-inlines-hidden): Description change. gcc/cp: * decl2.c (determine_hidden_inline): New function. (determine_visibility): fvisibility-inlines-hidden affects inline functions. From-SVN: r180589
This commit is contained in:
parent
2bea3d9195
commit
fb9120e3b1
|
@ -1,3 +1,8 @@
|
|||
2011-10-27 Roberto Agostino Vitillo <ravitillo@lbl.gov>
|
||||
|
||||
PR c++/30066
|
||||
* c.opt (fvisibility-inlines-hidden): Description change.
|
||||
|
||||
2011-10-26 Ed Smith-Rowland <3dw4rd@verizon.net>
|
||||
|
||||
Implement C++11 user-defined literals.
|
||||
|
|
|
@ -1043,7 +1043,7 @@ Use __cxa_get_exception_ptr in exception handling
|
|||
|
||||
fvisibility-inlines-hidden
|
||||
C++ ObjC++
|
||||
Marks all inlined methods as having hidden visibility
|
||||
Marks all inlined functions and methods as having hidden visibility
|
||||
|
||||
fvisibility-ms-compat
|
||||
C++ ObjC++ Var(flag_visibility_ms_compat)
|
||||
|
|
|
@ -1,3 +1,10 @@
|
|||
2011-10-27 Roberto Agostino Vitillo <ravitillo@lbl.gov>
|
||||
|
||||
PR c++/30066
|
||||
* decl2.c (determine_hidden_inline): New function.
|
||||
(determine_visibility): fvisibility-inlines-hidden affects inline
|
||||
functions.
|
||||
|
||||
2011-10-27 Dodji Seketeli <dodji@redhat.com>
|
||||
|
||||
* cp-tree.h (DECL_DECLARES_TYPE_P): Fix comment.
|
||||
|
|
|
@ -86,6 +86,7 @@ static void write_out_vars (tree);
|
|||
static void import_export_class (tree);
|
||||
static tree get_guard_bits (tree);
|
||||
static void determine_visibility_from_class (tree, tree);
|
||||
static bool determine_hidden_inline (tree);
|
||||
static bool decl_defined_p (tree);
|
||||
|
||||
/* A list of static class variables. This is needed, because a
|
||||
|
@ -2088,14 +2089,29 @@ determine_visibility (tree decl)
|
|||
containing function by default, except that
|
||||
-fvisibility-inlines-hidden doesn't affect them. */
|
||||
tree fn = DECL_CONTEXT (decl);
|
||||
if (DECL_VISIBILITY_SPECIFIED (fn) || ! DECL_CLASS_SCOPE_P (fn))
|
||||
if (DECL_VISIBILITY_SPECIFIED (fn))
|
||||
{
|
||||
DECL_VISIBILITY (decl) = DECL_VISIBILITY (fn);
|
||||
DECL_VISIBILITY_SPECIFIED (decl) =
|
||||
DECL_VISIBILITY_SPECIFIED (fn);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (DECL_CLASS_SCOPE_P (fn))
|
||||
determine_visibility_from_class (decl, DECL_CONTEXT (fn));
|
||||
else if (determine_hidden_inline (fn))
|
||||
{
|
||||
DECL_VISIBILITY (decl) = default_visibility;
|
||||
DECL_VISIBILITY_SPECIFIED (decl) =
|
||||
visibility_options.inpragma;
|
||||
}
|
||||
else
|
||||
{
|
||||
DECL_VISIBILITY (decl) = DECL_VISIBILITY (fn);
|
||||
DECL_VISIBILITY_SPECIFIED (decl) =
|
||||
DECL_VISIBILITY_SPECIFIED (fn);
|
||||
}
|
||||
}
|
||||
|
||||
/* Local classes in templates have CLASSTYPE_USE_TEMPLATE set,
|
||||
but have no TEMPLATE_INFO, so don't try to check it. */
|
||||
|
@ -2133,6 +2149,10 @@ determine_visibility (tree decl)
|
|||
/* Template instantiations and specializations get visibility based
|
||||
on their template unless they override it with an attribute. */;
|
||||
else if (! DECL_VISIBILITY_SPECIFIED (decl))
|
||||
{
|
||||
if (determine_hidden_inline (decl))
|
||||
DECL_VISIBILITY (decl) = VISIBILITY_HIDDEN;
|
||||
else
|
||||
{
|
||||
/* Set default visibility to whatever the user supplied with
|
||||
#pragma GCC visibility or a namespace visibility attribute. */
|
||||
|
@ -2140,6 +2160,7 @@ determine_visibility (tree decl)
|
|||
DECL_VISIBILITY_SPECIFIED (decl) = visibility_options.inpragma;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (use_template)
|
||||
{
|
||||
|
@ -2156,11 +2177,17 @@ determine_visibility (tree decl)
|
|||
tree pattern = DECL_TEMPLATE_RESULT (TI_TEMPLATE (tinfo));
|
||||
|
||||
if (!DECL_VISIBILITY_SPECIFIED (decl))
|
||||
{
|
||||
if (!DECL_VISIBILITY_SPECIFIED (pattern)
|
||||
&& determine_hidden_inline (decl))
|
||||
DECL_VISIBILITY (decl) = VISIBILITY_HIDDEN;
|
||||
else
|
||||
{
|
||||
DECL_VISIBILITY (decl) = DECL_VISIBILITY (pattern);
|
||||
DECL_VISIBILITY_SPECIFIED (decl)
|
||||
= DECL_VISIBILITY_SPECIFIED (pattern);
|
||||
}
|
||||
}
|
||||
|
||||
/* FIXME should TMPL_ARGS_DEPTH really return 1 for null input? */
|
||||
if (args && depth > template_class_depth (class_type))
|
||||
|
@ -2214,15 +2241,7 @@ determine_visibility_from_class (tree decl, tree class_type)
|
|||
if (DECL_VISIBILITY_SPECIFIED (decl))
|
||||
return;
|
||||
|
||||
if (visibility_options.inlines_hidden
|
||||
/* Don't do this for inline templates; specializations might not be
|
||||
inline, and we don't want them to inherit the hidden
|
||||
visibility. We'll set it here for all inline instantiations. */
|
||||
&& !processing_template_decl
|
||||
&& TREE_CODE (decl) == FUNCTION_DECL
|
||||
&& DECL_DECLARED_INLINE_P (decl)
|
||||
&& (! DECL_LANG_SPECIFIC (decl)
|
||||
|| ! DECL_EXPLICIT_INSTANTIATION (decl)))
|
||||
if (determine_hidden_inline (decl))
|
||||
DECL_VISIBILITY (decl) = VISIBILITY_HIDDEN;
|
||||
else
|
||||
{
|
||||
|
@ -2247,6 +2266,23 @@ determine_visibility_from_class (tree decl, tree class_type)
|
|||
targetm.cxx.determine_class_data_visibility (decl);
|
||||
}
|
||||
|
||||
/* Returns true iff DECL is an inline that should get hidden visibility
|
||||
because of -fvisibility-inlines-hidden. */
|
||||
|
||||
static bool
|
||||
determine_hidden_inline (tree decl)
|
||||
{
|
||||
return (visibility_options.inlines_hidden
|
||||
/* Don't do this for inline templates; specializations might not be
|
||||
inline, and we don't want them to inherit the hidden
|
||||
visibility. We'll set it here for all inline instantiations. */
|
||||
&& !processing_template_decl
|
||||
&& TREE_CODE (decl) == FUNCTION_DECL
|
||||
&& DECL_DECLARED_INLINE_P (decl)
|
||||
&& (! DECL_LANG_SPECIFIC (decl)
|
||||
|| ! DECL_EXPLICIT_INSTANTIATION (decl)));
|
||||
}
|
||||
|
||||
/* Constrain the visibility of a class TYPE based on the visibility of its
|
||||
field types. Warn if any fields require lesser visibility. */
|
||||
|
||||
|
|
|
@ -2120,7 +2120,7 @@ if the runtime routine is not available.
|
|||
@item -fvisibility-inlines-hidden
|
||||
@opindex fvisibility-inlines-hidden
|
||||
This switch declares that the user does not attempt to compare
|
||||
pointers to inline methods where the addresses of the two functions
|
||||
pointers to inline functions or methods where the addresses of the two functions
|
||||
were taken in different shared objects.
|
||||
|
||||
The effect of this is that GCC may, effectively, mark inline methods with
|
||||
|
|
|
@ -1,3 +1,8 @@
|
|||
2011-10-27 Roberto Agostino Vitillo <ravitillo@lbl.gov>
|
||||
|
||||
PR c++/30066
|
||||
* g++.dg/ext/visibility/fvisibility-inlines-hidden-4.C: New test.
|
||||
|
||||
2011-10-27 Jakub Jelinek <jakub@redhat.com>
|
||||
|
||||
* gcc.target/i386/sse2-cvt-1.c: New test.
|
||||
|
|
|
@ -0,0 +1,37 @@
|
|||
/* PR c++/30066: Test that -fvisibility-inlines-hidden affects functions. */
|
||||
/* { dg-do compile } */
|
||||
/* { dg-require-visibility "" } */
|
||||
/* { dg-options "-fvisibility-inlines-hidden" } */
|
||||
/* { dg-final { scan-hidden "_Z3barv" } } */
|
||||
/* { dg-final { scan-not-hidden "_ZZ3barvE1n" } } */
|
||||
/* { dg-final { scan-not-hidden "_Z3fooIiEvv" } } */
|
||||
/* { dg-final { scan-hidden "_Z3fooIvEvv" } } */
|
||||
/* { dg-final { scan-hidden "_ZZN1A5innerEvE1n" } } */
|
||||
|
||||
inline int * bar()
|
||||
{
|
||||
static int n;
|
||||
return &n;
|
||||
}
|
||||
|
||||
template <class T>
|
||||
inline void foo() { }
|
||||
|
||||
template void foo<int>();
|
||||
|
||||
namespace A __attribute__ ((visibility ("hidden")))
|
||||
{
|
||||
inline int * inner()
|
||||
{
|
||||
static int n;
|
||||
return &n;
|
||||
}
|
||||
}
|
||||
|
||||
int main(void)
|
||||
{
|
||||
bar();
|
||||
foo<void>();
|
||||
A::inner();
|
||||
return 0;
|
||||
}
|
Loading…
Reference in New Issue