Index: docs/DesignDocs/VisibilityMacros.rst =================================================================== --- docs/DesignDocs/VisibilityMacros.rst +++ docs/DesignDocs/VisibilityMacros.rst @@ -22,11 +22,11 @@ Mark a symbol as being exported by the libc++ library. This attribute must be applied to the declaration of all functions exported by the libc++ dylib. -**_LIBCPP_EXTERN_VIS** +**_LIBCPP_EXPORTED_FROM_ABI** Mark a symbol as being exported by the libc++ library. This attribute may - only be applied to objects defined in the libc++ library. On Windows this - macro applies `dllimport`/`dllexport` to the symbol. On all other platforms - this macro has no effect. + only be applied to objects defined in the libc++ runtime library. On Windows, + this macro applies `dllimport`/`dllexport` to the symbol, and on other + platforms it gives the symbol default visibility. **_LIBCPP_OVERRIDABLE_FUNC_VIS** Mark a symbol as being exported by the libc++ library, but allow it to be Index: include/__config =================================================================== --- include/__config +++ include/__config @@ -675,21 +675,23 @@ # define _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS # define _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS # define _LIBCPP_OVERRIDABLE_FUNC_VIS +# define _LIBCPP_EXPORTED_FROM_ABI #elif defined(_LIBCPP_BUILDING_LIBRARY) # define _LIBCPP_DLL_VIS __declspec(dllexport) # define _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS # define _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS _LIBCPP_DLL_VIS # define _LIBCPP_OVERRIDABLE_FUNC_VIS _LIBCPP_DLL_VIS +# define _LIBCPP_EXPORTED_FROM_ABI __declspec(dllexport) #else # define _LIBCPP_DLL_VIS __declspec(dllimport) # define _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS _LIBCPP_DLL_VIS # define _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS # define _LIBCPP_OVERRIDABLE_FUNC_VIS +# define _LIBCPP_EXPORTED_FROM_ABI __declspec(dllimport) #endif #define _LIBCPP_TYPE_VIS _LIBCPP_DLL_VIS #define _LIBCPP_FUNC_VIS _LIBCPP_DLL_VIS -#define _LIBCPP_EXTERN_VIS _LIBCPP_DLL_VIS #define _LIBCPP_EXCEPTION_ABI _LIBCPP_DLL_VIS #define _LIBCPP_HIDDEN #define _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS @@ -743,8 +745,8 @@ # endif #endif -#ifndef _LIBCPP_EXTERN_VIS -#define _LIBCPP_EXTERN_VIS +#ifndef _LIBCPP_EXPORTED_FROM_ABI +# define _LIBCPP_EXPORTED_FROM_ABI __attribute__((__visibility__("default"))) #endif #ifndef _LIBCPP_OVERRIDABLE_FUNC_VIS Index: include/__debug =================================================================== --- include/__debug +++ include/__debug @@ -74,7 +74,7 @@ /// __libcpp_debug_function - The handler function called when a _LIBCPP_ASSERT /// fails. -extern _LIBCPP_EXTERN_VIS __libcpp_debug_function_type __libcpp_debug_function; +extern _LIBCPP_EXPORTED_FROM_ABI __libcpp_debug_function_type __libcpp_debug_function; /// __libcpp_abort_debug_function - A debug handler that aborts when called. _LIBCPP_NORETURN _LIBCPP_FUNC_VIS Index: include/__functional_base =================================================================== --- include/__functional_base +++ include/__functional_base @@ -562,7 +562,7 @@ struct _LIBCPP_TEMPLATE_VIS allocator_arg_t { }; #if defined(_LIBCPP_CXX03_LANG) || defined(_LIBCPP_BUILDING_LIBRARY) -extern const allocator_arg_t allocator_arg; +extern _LIBCPP_EXPORTED_FROM_ABI const allocator_arg_t allocator_arg; #else /* _LIBCPP_INLINE_VAR */ constexpr allocator_arg_t allocator_arg = allocator_arg_t(); #endif Index: include/__locale =================================================================== --- include/__locale +++ include/__locale @@ -1255,13 +1255,13 @@ }; template <> -struct __narrow_to_utf8<16> +struct _LIBCPP_TEMPLATE_VIS __narrow_to_utf8<16> : public codecvt { _LIBCPP_INLINE_VISIBILITY __narrow_to_utf8() : codecvt(1) {} - ~__narrow_to_utf8(); + _LIBCPP_EXPORTED_FROM_ABI ~__narrow_to_utf8(); template _LIBCPP_INLINE_VISIBILITY @@ -1289,13 +1289,13 @@ }; template <> -struct __narrow_to_utf8<32> +struct _LIBCPP_TEMPLATE_VIS __narrow_to_utf8<32> : public codecvt { _LIBCPP_INLINE_VISIBILITY __narrow_to_utf8() : codecvt(1) {} - ~__narrow_to_utf8(); + _LIBCPP_EXPORTED_FROM_ABI ~__narrow_to_utf8(); template _LIBCPP_INLINE_VISIBILITY @@ -1345,13 +1345,13 @@ }; template <> -struct __widen_from_utf8<16> +struct _LIBCPP_TEMPLATE_VIS __widen_from_utf8<16> : public codecvt { _LIBCPP_INLINE_VISIBILITY __widen_from_utf8() : codecvt(1) {} - ~__widen_from_utf8(); + _LIBCPP_EXPORTED_FROM_ABI ~__widen_from_utf8(); template _LIBCPP_INLINE_VISIBILITY @@ -1379,13 +1379,13 @@ }; template <> -struct __widen_from_utf8<32> +struct _LIBCPP_TEMPLATE_VIS __widen_from_utf8<32> : public codecvt { _LIBCPP_INLINE_VISIBILITY __widen_from_utf8() : codecvt(1) {} - ~__widen_from_utf8(); + _LIBCPP_EXPORTED_FROM_ABI ~__widen_from_utf8(); template _LIBCPP_INLINE_VISIBILITY Index: include/__mutex_base =================================================================== --- include/__mutex_base +++ include/__mutex_base @@ -76,9 +76,9 @@ #if defined(_LIBCPP_CXX03_LANG) || defined(_LIBCPP_BUILDING_LIBRARY) -extern const defer_lock_t defer_lock; -extern const try_to_lock_t try_to_lock; -extern const adopt_lock_t adopt_lock; +extern _LIBCPP_EXPORTED_FROM_ABI const defer_lock_t defer_lock; +extern _LIBCPP_EXPORTED_FROM_ABI const try_to_lock_t try_to_lock; +extern _LIBCPP_EXPORTED_FROM_ABI const adopt_lock_t adopt_lock; #else Index: include/charconv =================================================================== --- include/charconv +++ include/charconv @@ -89,6 +89,11 @@ _LIBCPP_BEGIN_NAMESPACE_STD +namespace __itoa { +_LIBCPP_FUNC_VIS char* __u64toa(uint64_t __value, char* __buffer); +_LIBCPP_FUNC_VIS char* __u32toa(uint32_t __value, char* __buffer); +} + #if _LIBCPP_STD_VER > 11 enum class _LIBCPP_ENUM_VIS chars_format @@ -147,9 +152,6 @@ UINT32_C(1000000000), }; -_LIBCPP_FUNC_VIS char* __u64toa(uint64_t __value, char* __buffer); -_LIBCPP_FUNC_VIS char* __u32toa(uint32_t __value, char* __buffer); - template struct _LIBCPP_HIDDEN __traits_base { Index: include/locale =================================================================== --- include/locale +++ include/locale @@ -2408,6 +2408,23 @@ string_type __analyze(char __fmt, const ctype<_CharT>&); }; +#define _LIBCPP_TIME_GET_STORAGE_EXPLICIT_INSTANTIATION(_CharT) \ +template <> _LIBCPP_FUNC_VIS time_base::dateorder __time_get_storage<_CharT>::__do_date_order() const; \ +template <> _LIBCPP_FUNC_VIS __time_get_storage<_CharT>::__time_get_storage(const char*); \ +template <> _LIBCPP_FUNC_VIS __time_get_storage<_CharT>::__time_get_storage(const string&); \ +template <> _LIBCPP_FUNC_VIS void __time_get_storage<_CharT>::init(const ctype<_CharT>&); \ +template <> _LIBCPP_FUNC_VIS __time_get_storage<_CharT>::string_type __time_get_storage<_CharT>::__analyze(char, const ctype<_CharT>&); \ +extern template _LIBCPP_FUNC_VIS time_base::dateorder __time_get_storage<_CharT>::__do_date_order() const; \ +extern template _LIBCPP_FUNC_VIS __time_get_storage<_CharT>::__time_get_storage(const char*); \ +extern template _LIBCPP_FUNC_VIS __time_get_storage<_CharT>::__time_get_storage(const string&); \ +extern template _LIBCPP_FUNC_VIS void __time_get_storage<_CharT>::init(const ctype<_CharT>&); \ +extern template _LIBCPP_FUNC_VIS __time_get_storage<_CharT>::string_type __time_get_storage<_CharT>::__analyze(char, const ctype<_CharT>&); \ +/**/ + +_LIBCPP_TIME_GET_STORAGE_EXPLICIT_INSTANTIATION(char) +_LIBCPP_TIME_GET_STORAGE_EXPLICIT_INSTANTIATION(wchar_t) +#undef _LIBCPP_TIME_GET_STORAGE_EXPLICIT_INSTANTIATION + template > class _LIBCPP_TEMPLATE_VIS time_get_byname : public time_get<_CharT, _InputIterator>, Index: include/thread =================================================================== --- include/thread +++ include/thread @@ -151,7 +151,7 @@ __thread_specific_ptr(const __thread_specific_ptr&); __thread_specific_ptr& operator=(const __thread_specific_ptr&); - static void _LIBCPP_TLS_DESTRUCTOR_CC __at_thread_exit(void*); + _LIBCPP_HIDDEN static void _LIBCPP_TLS_DESTRUCTOR_CC __at_thread_exit(void*); public: typedef _Tp* pointer; Index: include/utility =================================================================== --- include/utility +++ include/utility @@ -297,7 +297,7 @@ struct _LIBCPP_TEMPLATE_VIS piecewise_construct_t { }; #if defined(_LIBCPP_CXX03_LANG) || defined(_LIBCPP_BUILDING_LIBRARY) -extern const piecewise_construct_t piecewise_construct;// = piecewise_construct_t(); +extern _LIBCPP_EXPORTED_FROM_ABI const piecewise_construct_t piecewise_construct;// = piecewise_construct_t(); #else /* _LIBCPP_INLINE_VAR */ constexpr piecewise_construct_t piecewise_construct = piecewise_construct_t(); #endif Index: lib/abi/CHANGELOG.TXT =================================================================== --- lib/abi/CHANGELOG.TXT +++ lib/abi/CHANGELOG.TXT @@ -16,6 +16,34 @@ Version 7.0 ----------- +* rXXXXX - Making libc++ build under -fvisibility=hidden + + The change marks __thread_specific_ptr<__thread_struct>::__at_thread_exit(void*) + with hidden visibility. This removes a symbol from the shared libraries, + however this is not an ABI break because it's impossible for programs linking + against libc++.dylib to actually depend on that symbol. The reason is that + the symbol is exported from the shared library through an implicit + instantiation present in the dylib itself only. Furthermore, if a user's + dylib was implicitly instantiating __thread_specific_ptr::__at_thread_exit + (because it's defined in the headers), marking that symbol as hidden would + not be an ABI break for them because none of their users could actually be + using the symbol in their dylib (because it's an implicit instantiation). + + This change also marks __start_std_streams as hidden -- this variable is + only required to initialize the streams, and nobody should depend on it + from outside the dylib. + + x86_64-linux-gnu + ---------------- + Symbol removed: _ZNSt3__121__thread_specific_ptrINS_15__thread_structEE16__at_thread_exitEPv + Symbol removed: _ZNSt3__119__start_std_streamsE + + x86_64-apple-darwin16.0 + ----------------------- + Symbol removed: __ZNSt3__221__thread_specific_ptrINS_15__thread_structEE16__at_thread_exitEPv + Symbol removed: __ZNSt3__119__start_std_streamsE + + * r338479 - Elementary string conversions for integral types The change emits __u64toa and __u32toa under std::__1::__itoa. Index: lib/abi/x86_64-apple-darwin.v1.abilist =================================================================== --- lib/abi/x86_64-apple-darwin.v1.abilist +++ lib/abi/x86_64-apple-darwin.v1.abilist @@ -1197,13 +1197,11 @@ {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__119__shared_weak_countD0Ev'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__119__shared_weak_countD1Ev'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__119__shared_weak_countD2Ev'} -{'type': 'OBJECT', 'is_defined': True, 'name': '__ZNSt3__119__start_std_streamsE', 'size': 0} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__119__thread_local_dataEv'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__119declare_no_pointersEPcm'} {'type': 'OBJECT', 'is_defined': True, 'name': '__ZNSt3__119piecewise_constructE', 'size': 0} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__120__get_collation_nameEPKc'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__120__throw_system_errorEiPKc'} -{'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__121__thread_specific_ptrINS_15__thread_structEE16__at_thread_exitEPv'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__121__throw_runtime_errorEPKc'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__121__undeclare_reachableEPv'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__121recursive_timed_mutex4lockEv'} Index: lib/abi/x86_64-apple-darwin.v2.abilist =================================================================== --- lib/abi/x86_64-apple-darwin.v2.abilist +++ lib/abi/x86_64-apple-darwin.v2.abilist @@ -1119,13 +1119,11 @@ {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__219__shared_weak_countD0Ev'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__219__shared_weak_countD1Ev'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__219__shared_weak_countD2Ev'} -{'type': 'OBJECT', 'is_defined': True, 'name': '__ZNSt3__219__start_std_streamsE', 'size': 0} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__219__thread_local_dataEv'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__219declare_no_pointersEPcm'} {'type': 'OBJECT', 'is_defined': True, 'name': '__ZNSt3__219piecewise_constructE', 'size': 0} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__220__get_collation_nameEPKc'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__220__throw_system_errorEiPKc'} -{'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__221__thread_specific_ptrINS_15__thread_structEE16__at_thread_exitEPv'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__221__throw_runtime_errorEPKc'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__221__undeclare_reachableEPv'} {'type': 'FUNC', 'is_defined': True, 'name': '__ZNSt3__221recursive_timed_mutex4lockEv'} Index: lib/abi/x86_64-unknown-linux-gnu.v1.abilist =================================================================== --- lib/abi/x86_64-unknown-linux-gnu.v1.abilist +++ lib/abi/x86_64-unknown-linux-gnu.v1.abilist @@ -1098,13 +1098,11 @@ {'name': '_ZNSt3__119__shared_weak_countD0Ev', 'is_defined': True, 'type': 'FUNC'} {'name': '_ZNSt3__119__shared_weak_countD1Ev', 'is_defined': True, 'type': 'FUNC'} {'name': '_ZNSt3__119__shared_weak_countD2Ev', 'is_defined': True, 'type': 'FUNC'} -{'name': '_ZNSt3__119__start_std_streamsE', 'is_defined': True, 'type': 'OBJECT', 'size': 1} {'name': '_ZNSt3__119__thread_local_dataEv', 'is_defined': True, 'type': 'FUNC'} {'name': '_ZNSt3__119declare_no_pointersEPcm', 'is_defined': True, 'type': 'FUNC'} {'name': '_ZNSt3__119piecewise_constructE', 'is_defined': True, 'type': 'OBJECT', 'size': 1} {'name': '_ZNSt3__120__get_collation_nameEPKc', 'is_defined': True, 'type': 'FUNC'} {'name': '_ZNSt3__120__throw_system_errorEiPKc', 'is_defined': True, 'type': 'FUNC'} -{'name': '_ZNSt3__121__thread_specific_ptrINS_15__thread_structEE16__at_thread_exitEPv', 'is_defined': True, 'type': 'FUNC'} {'name': '_ZNSt3__121__throw_runtime_errorEPKc', 'is_defined': True, 'type': 'FUNC'} {'name': '_ZNSt3__121__undeclare_reachableEPv', 'is_defined': True, 'type': 'FUNC'} {'name': '_ZNSt3__121recursive_timed_mutex4lockEv', 'is_defined': True, 'type': 'FUNC'} Index: src/iostream.cpp =================================================================== --- src/iostream.cpp +++ src/iostream.cpp @@ -77,7 +77,7 @@ #endif ; -ios_base::Init __start_std_streams; +_LIBCPP_HIDDEN ios_base::Init __start_std_streams; ios_base::Init::Init() {