Add markup for libc++ dylib availability

Libc++ is used as a system library on macOS and iOS (amongst others). In order
for users to be able to compile a binary that is intended to be deployed to an
older version of the platform, clang provides the
availability attribute <https://clang.llvm.org/docs/AttributeReference.html#availability>_
that can be placed on declarations to describe the lifecycle of a symbol in the
library.

See docs/DesignDocs/AvailabilityMarkup.rst for more information.

Differential Revision: https://reviews.llvm.org/D31739

git-svn-id: https://llvm.org/svn/llvm-project/libcxx/trunk@302172 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/include/__config b/include/__config
index 598015c..05622a4 100644
--- a/include/__config
+++ b/include/__config
@@ -1113,4 +1113,77 @@
 
 #endif // __cplusplus
 
+// Decide whether to use availability macros.
+#if !defined(_LIBCPP_BUILDING_LIBRARY) &&                                      \
+    !defined(_LIBCPP_DISABLE_AVAILABILITY) &&                                  \
+    __has_feature(attribute_availability_with_strict) &&                       \
+    __has_feature(attribute_availability_in_templates)
+#ifdef __APPLE__
+#define _LIBCPP_USE_AVAILABILITY_APPLE
+#endif
+#endif
+
+// Define availability macros.
+#if defined(_LIBCPP_USE_AVAILABILITY_APPLE)
+#define _LIBCPP_AVAILABILITY_SHARED_MUTEX                                      \
+  __attribute__((availability(macosx,strict,introduced=10.12)))                \
+  __attribute__((availability(ios,strict,introduced=10.0)))                    \
+  __attribute__((availability(tvos,strict,introduced=10.0)))                   \
+  __attribute__((availability(watchos,strict,introduced=3.0)))
+#define _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS __attribute__((unavailable))
+#define _LIBCPP_AVAILABILITY_BAD_ARRAY_LENGTH __attribute__((unavailable))
+#define _LIBCPP_AVAILABILITY_UNCAUGHT_EXCEPTIONS                               \
+  __attribute__((availability(macosx,strict,introduced=10.12)))                \
+  __attribute__((availability(ios,strict,introduced=10.0)))                    \
+  __attribute__((availability(tvos,strict,introduced=10.0)))                   \
+  __attribute__((availability(watchos,strict,introduced=3.0)))
+#define _LIBCPP_AVAILABILITY_SIZED_NEW_DELETE                                  \
+  __attribute__((availability(macosx,strict,introduced=10.12)))                \
+  __attribute__((availability(ios,strict,introduced=10.0)))                    \
+  __attribute__((availability(tvos,strict,introduced=10.0)))                   \
+  __attribute__((availability(watchos,strict,introduced=3.0)))
+#define _LIBCPP_AVAILABILITY_FUTURE_ERROR                                      \
+  __attribute__((availability(ios,strict,introduced=6.0)))
+#define _LIBCPP_AVAILABILITY_TYPEINFO_VTABLE                                   \
+  __attribute__((availability(macosx,strict,introduced=10.9)))                 \
+  __attribute__((availability(ios,strict,introduced=7.0)))
+#define _LIBCPP_AVAILABILITY_LOCALE_CATEGORY                                   \
+  __attribute__((availability(macosx,strict,introduced=10.9)))                 \
+  __attribute__((availability(ios,strict,introduced=7.0)))
+#define _LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR                                 \
+  __attribute__((availability(macosx,strict,introduced=10.9)))                 \
+  __attribute__((availability(ios,strict,introduced=7.0)))
+#else
+#define _LIBCPP_AVAILABILITY_SHARED_MUTEX
+#define _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS
+#define _LIBCPP_AVAILABILITY_BAD_ARRAY_LENGTH
+#define _LIBCPP_AVAILABILITY_UNCAUGHT_EXCEPTIONS
+#define _LIBCPP_AVAILABILITY_SIZED_NEW_DELETE
+#define _LIBCPP_AVAILABILITY_FUTURE_ERROR
+#define _LIBCPP_AVAILABILITY_TYPEINFO_VTABLE
+#define _LIBCPP_AVAILABILITY_LOCALE_CATEGORY
+#define _LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR
+#endif
+
+// Define availability that depends on _LIBCPP_NO_EXCEPTIONS.
+#ifdef _LIBCPP_NO_EXCEPTIONS
+#define _LIBCPP_AVAILABILITY_DYNARRAY
+#define _LIBCPP_AVAILABILITY_FUTURE
+#else
+#define _LIBCPP_AVAILABILITY_DYNARRAY _LIBCPP_AVAILABILITY_BAD_ARRAY_LENGTH
+#define _LIBCPP_AVAILABILITY_FUTURE _LIBCPP_AVAILABILITY_FUTURE_ERROR
+#endif
+
+// Availability of stream API in the dylib got dropped and re-added.  The
+// extern template should effectively be available at:
+//    availability(macosx,introduced=10.9)
+//    availability(ios,introduced=7.0)
+#if defined(_LIBCPP_USE_AVAILABILITY_APPLE) &&                                 \
+    ((defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) &&                \
+      __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ <= 1090) ||                \
+     (defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) &&               \
+      __ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ <= 70000))
+#define _LIBCPP_AVAILABILITY_NO_STREAMS_EXTERN_TEMPLATE
+#endif
+
 #endif // _LIBCPP_CONFIG
diff --git a/include/__locale b/include/__locale
index 918cd1d..4184e7e 100644
--- a/include/__locale
+++ b/include/__locale
@@ -69,6 +69,7 @@
     class _LIBCPP_TYPE_VIS id;
 
     typedef int category;
+    _LIBCPP_AVAILABILITY_LOCALE_CATEGORY
     static const category // values assigned here are for exposition only
         none     = 0,
         collate  = LC_COLLATE_MASK,
diff --git a/include/exception b/include/exception
index f12ae42..9999ca0 100644
--- a/include/exception
+++ b/include/exception
@@ -127,7 +127,7 @@
 _LIBCPP_NORETURN _LIBCPP_FUNC_VIS void terminate() _NOEXCEPT;
 
 _LIBCPP_FUNC_VIS bool uncaught_exception() _NOEXCEPT;
-_LIBCPP_FUNC_VIS int uncaught_exceptions() _NOEXCEPT;
+_LIBCPP_FUNC_VIS _LIBCPP_AVAILABILITY_UNCAUGHT_EXCEPTIONS int uncaught_exceptions() _NOEXCEPT;
 
 class _LIBCPP_TYPE_VIS exception_ptr;
 
diff --git a/include/experimental/dynarray b/include/experimental/dynarray
index 8c97337..f96a0e5 100644
--- a/include/experimental/dynarray
+++ b/include/experimental/dynarray
@@ -110,7 +110,7 @@
 namespace std { namespace experimental { inline namespace __array_extensions_v1 {
 
 template <class _Tp>
-struct _LIBCPP_TEMPLATE_VIS dynarray
+struct _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_DYNARRAY dynarray
 {
 public:
     // types:
diff --git a/include/experimental/optional b/include/experimental/optional
index f32941b..48adfba 100644
--- a/include/experimental/optional
+++ b/include/experimental/optional
@@ -145,7 +145,7 @@
 #include <stdexcept>
 
 _LIBCPP_BEGIN_NAMESPACE_EXPERIMENTAL
-class _LIBCPP_EXCEPTION_ABI bad_optional_access
+class _LIBCPP_EXCEPTION_ABI _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS bad_optional_access
     : public std::logic_error
 {
 public:
@@ -523,6 +523,9 @@
     constexpr explicit operator bool() const noexcept {return this->__engaged_;}
 
 	_LIBCPP_NORETURN _LIBCPP_INLINE_VISIBILITY 
+#ifndef _LIBCPP_NO_EXCEPTIONS
+_LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS
+#endif
 	constexpr void __throw_bad_optional_access() const
 	{
 #ifndef _LIBCPP_NO_EXCEPTIONS
@@ -532,7 +535,7 @@
 #endif
 	}
 	
-    _LIBCPP_INLINE_VISIBILITY
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS
     constexpr value_type const& value() const
     {
         if (!this->__engaged_)
@@ -540,7 +543,7 @@
         return this->__val_;
     }
 
-    _LIBCPP_INLINE_VISIBILITY
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS
     value_type& value()
     {
         if (!this->__engaged_)
diff --git a/include/future b/include/future
index 1ceedf9..e388767 100644
--- a/include/future
+++ b/include/future
@@ -499,7 +499,7 @@
     return error_condition(static_cast<int>(__e), future_category());
 }
 
-class _LIBCPP_EXCEPTION_ABI future_error
+class _LIBCPP_EXCEPTION_ABI _LIBCPP_AVAILABILITY_FUTURE_ERROR future_error
     : public logic_error
 {
     error_code __ec_;
@@ -515,6 +515,9 @@
 };
 
 _LIBCPP_NORETURN inline _LIBCPP_ALWAYS_INLINE
+#ifndef _LIBCPP_NO_EXCEPTIONS
+_LIBCPP_AVAILABILITY_FUTURE_ERROR
+#endif
 void __throw_future_error(future_errc _Ev)
 {
 #ifndef _LIBCPP_NO_EXCEPTIONS
@@ -525,7 +528,7 @@
 #endif
 }
 
-class _LIBCPP_TYPE_VIS __assoc_sub_state
+class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_FUTURE __assoc_sub_state
     : public __shared_count
 {
 protected:
@@ -612,7 +615,7 @@
 }
 
 template <class _Rp>
-class __assoc_state
+class _LIBCPP_AVAILABILITY_FUTURE __assoc_state
     : public __assoc_sub_state
 {
     typedef __assoc_sub_state base;
@@ -652,6 +655,7 @@
 
 template <class _Rp>
 template <class _Arg>
+_LIBCPP_AVAILABILITY_FUTURE
 void
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 __assoc_state<_Rp>::set_value(_Arg&& __arg)
@@ -707,7 +711,7 @@
 }
 
 template <class _Rp>
-class __assoc_state<_Rp&>
+class _LIBCPP_AVAILABILITY_FUTURE __assoc_state<_Rp&>
     : public __assoc_sub_state
 {
     typedef __assoc_sub_state base;
@@ -767,7 +771,7 @@
 }
 
 template <class _Rp, class _Alloc>
-class __assoc_state_alloc
+class _LIBCPP_AVAILABILITY_FUTURE __assoc_state_alloc
     : public __assoc_state<_Rp>
 {
     typedef __assoc_state<_Rp> base;
@@ -795,7 +799,7 @@
 }
 
 template <class _Rp, class _Alloc>
-class __assoc_state_alloc<_Rp&, _Alloc>
+class _LIBCPP_AVAILABILITY_FUTURE __assoc_state_alloc<_Rp&, _Alloc>
     : public __assoc_state<_Rp&>
 {
     typedef __assoc_state<_Rp&> base;
@@ -821,7 +825,7 @@
 }
 
 template <class _Alloc>
-class __assoc_sub_state_alloc
+class _LIBCPP_AVAILABILITY_FUTURE __assoc_sub_state_alloc
     : public __assoc_sub_state
 {
     typedef __assoc_sub_state base;
@@ -847,7 +851,7 @@
 }
 
 template <class _Rp, class _Fp>
-class __deferred_assoc_state
+class _LIBCPP_AVAILABILITY_FUTURE __deferred_assoc_state
     : public __assoc_state<_Rp>
 {
     typedef __assoc_state<_Rp> base;
@@ -894,7 +898,7 @@
 }
 
 template <class _Fp>
-class __deferred_assoc_state<void, _Fp>
+class _LIBCPP_AVAILABILITY_FUTURE __deferred_assoc_state<void, _Fp>
     : public __assoc_sub_state
 {
     typedef __assoc_sub_state base;
@@ -942,7 +946,7 @@
 }
 
 template <class _Rp, class _Fp>
-class __async_assoc_state
+class _LIBCPP_AVAILABILITY_FUTURE __async_assoc_state
     : public __assoc_state<_Rp>
 {
     typedef __assoc_state<_Rp> base;
@@ -997,7 +1001,7 @@
 }
 
 template <class _Fp>
-class __async_assoc_state<void, _Fp>
+class _LIBCPP_AVAILABILITY_FUTURE __async_assoc_state<void, _Fp>
     : public __assoc_sub_state
 {
     typedef __assoc_sub_state base;
@@ -1076,7 +1080,7 @@
 #endif
 
 template <class _Rp>
-class _LIBCPP_TEMPLATE_VIS future
+class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE future
 {
     __assoc_state<_Rp>* __state_;
 
@@ -1179,7 +1183,7 @@
 }
 
 template <class _Rp>
-class _LIBCPP_TEMPLATE_VIS future<_Rp&>
+class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE future<_Rp&>
 {
     __assoc_state<_Rp&>* __state_;
 
@@ -1277,7 +1281,7 @@
 }
 
 template <>
-class _LIBCPP_TYPE_VIS future<void>
+class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_FUTURE future<void>
 {
     __assoc_sub_state* __state_;
 
@@ -1360,7 +1364,7 @@
 template <class _Callable> class packaged_task;
 
 template <class _Rp>
-class _LIBCPP_TEMPLATE_VIS promise
+class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE promise
 {
     __assoc_state<_Rp>* __state_;
 
@@ -1527,7 +1531,7 @@
 // promise<R&>
 
 template <class _Rp>
-class _LIBCPP_TEMPLATE_VIS promise<_Rp&>
+class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE promise<_Rp&>
 {
     __assoc_state<_Rp&>* __state_;
 
@@ -1663,7 +1667,7 @@
 // promise<void>
 
 template <>
-class _LIBCPP_TYPE_VIS promise<void>
+class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_FUTURE promise<void>
 {
     __assoc_sub_state* __state_;
 
@@ -1749,7 +1753,7 @@
 template<class _Fp> class __packaged_task_base;
 
 template<class _Rp, class ..._ArgTypes>
-class __packaged_task_base<_Rp(_ArgTypes...)>
+class _LIBCPP_AVAILABILITY_FUTURE __packaged_task_base<_Rp(_ArgTypes...)>
 {
     __packaged_task_base(const __packaged_task_base&);
     __packaged_task_base& operator=(const __packaged_task_base&);
@@ -1767,7 +1771,7 @@
 template<class _FD, class _Alloc, class _FB> class __packaged_task_func;
 
 template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes>
-class __packaged_task_func<_Fp, _Alloc, _Rp(_ArgTypes...)>
+class _LIBCPP_AVAILABILITY_FUTURE __packaged_task_func<_Fp, _Alloc, _Rp(_ArgTypes...)>
     : public  __packaged_task_base<_Rp(_ArgTypes...)>
 {
     __compressed_pair<_Fp, _Alloc> __f_;
@@ -1825,7 +1829,7 @@
 template <class _Callable> class __packaged_task_function;
 
 template<class _Rp, class ..._ArgTypes>
-class __packaged_task_function<_Rp(_ArgTypes...)>
+class _LIBCPP_AVAILABILITY_FUTURE __packaged_task_function<_Rp(_ArgTypes...)>
 {
     typedef __packaged_task_base<_Rp(_ArgTypes...)> __base;
     typename aligned_storage<3*sizeof(void*)>::type __buf_;
@@ -2000,7 +2004,7 @@
 }
 
 template<class _Rp, class ..._ArgTypes>
-class _LIBCPP_TEMPLATE_VIS packaged_task<_Rp(_ArgTypes...)>
+class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE packaged_task<_Rp(_ArgTypes...)>
 {
 public:
     typedef _Rp result_type; // extension
@@ -2129,7 +2133,7 @@
 }
 
 template<class ..._ArgTypes>
-class _LIBCPP_TEMPLATE_VIS packaged_task<void(_ArgTypes...)>
+class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE packaged_task<void(_ArgTypes...)>
 {
 public:
     typedef void result_type; // extension
@@ -2517,7 +2521,7 @@
 }
 
 template <>
-class _LIBCPP_TYPE_VIS shared_future<void>
+class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_FUTURE shared_future<void>
 {
     __assoc_sub_state* __state_;
 
diff --git a/include/istream b/include/istream
index 9a8bb44..530f204 100644
--- a/include/istream
+++ b/include/istream
@@ -1675,9 +1675,11 @@
     return __is;
 }
 
+#ifndef _LIBCPP_AVAILABILITY_NO_STREAMS_EXTERN_TEMPLATE
 _LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS basic_istream<char>)
 _LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS basic_istream<wchar_t>)
 _LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS basic_iostream<char>)
+#endif
 
 _LIBCPP_END_NAMESPACE_STD
 
diff --git a/include/memory b/include/memory
index a02d61c..41ab01b 100644
--- a/include/memory
+++ b/include/memory
@@ -5293,7 +5293,8 @@
     friend _LIBCPP_FUNC_VIS __sp_mut& __get_sp_mut(const void*);
 };
 
-_LIBCPP_FUNC_VIS __sp_mut& __get_sp_mut(const void*);
+_LIBCPP_FUNC_VIS _LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR
+__sp_mut& __get_sp_mut(const void*);
 
 template <class _Tp>
 inline _LIBCPP_INLINE_VISIBILITY
@@ -5304,6 +5305,7 @@
 }
 
 template <class _Tp>
+_LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR
 shared_ptr<_Tp>
 atomic_load(const shared_ptr<_Tp>* __p)
 {
@@ -5316,6 +5318,7 @@
   
 template <class _Tp>
 inline _LIBCPP_INLINE_VISIBILITY
+_LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR
 shared_ptr<_Tp>
 atomic_load_explicit(const shared_ptr<_Tp>* __p, memory_order)
 {
@@ -5323,6 +5326,7 @@
 }
 
 template <class _Tp>
+_LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR
 void
 atomic_store(shared_ptr<_Tp>* __p, shared_ptr<_Tp> __r)
 {
@@ -5334,6 +5338,7 @@
 
 template <class _Tp>
 inline _LIBCPP_INLINE_VISIBILITY
+_LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR
 void
 atomic_store_explicit(shared_ptr<_Tp>* __p, shared_ptr<_Tp> __r, memory_order)
 {
@@ -5341,6 +5346,7 @@
 }
 
 template <class _Tp>
+_LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR
 shared_ptr<_Tp>
 atomic_exchange(shared_ptr<_Tp>* __p, shared_ptr<_Tp> __r)
 {
@@ -5353,6 +5359,7 @@
   
 template <class _Tp>
 inline _LIBCPP_INLINE_VISIBILITY
+_LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR
 shared_ptr<_Tp>
 atomic_exchange_explicit(shared_ptr<_Tp>* __p, shared_ptr<_Tp> __r, memory_order)
 {
@@ -5360,6 +5367,7 @@
 }
 
 template <class _Tp>
+_LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR
 bool
 atomic_compare_exchange_strong(shared_ptr<_Tp>* __p, shared_ptr<_Tp>* __v, shared_ptr<_Tp> __w)
 {
@@ -5381,6 +5389,7 @@
 
 template <class _Tp>
 inline _LIBCPP_INLINE_VISIBILITY
+_LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR
 bool
 atomic_compare_exchange_weak(shared_ptr<_Tp>* __p, shared_ptr<_Tp>* __v, shared_ptr<_Tp> __w)
 {
@@ -5389,6 +5398,7 @@
 
 template <class _Tp>
 inline _LIBCPP_INLINE_VISIBILITY
+_LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR
 bool
 atomic_compare_exchange_strong_explicit(shared_ptr<_Tp>* __p, shared_ptr<_Tp>* __v,
                                         shared_ptr<_Tp> __w, memory_order, memory_order)
@@ -5398,6 +5408,7 @@
 
 template <class _Tp>
 inline _LIBCPP_INLINE_VISIBILITY
+_LIBCPP_AVAILABILITY_ATOMIC_SHARED_PTR
 bool
 atomic_compare_exchange_weak_explicit(shared_ptr<_Tp>* __p, shared_ptr<_Tp>* __v,
                                       shared_ptr<_Tp> __w, memory_order, memory_order)
diff --git a/include/new b/include/new
index c0e7b2d..34df2ef 100644
--- a/include/new
+++ b/include/new
@@ -146,9 +146,8 @@
 
 #if defined(_LIBCPP_BUILDING_LIBRARY) || (_LIBCPP_STD_VER > 11)
 
-class _LIBCPP_EXCEPTION_ABI bad_array_length
-    : public bad_alloc
-{
+class _LIBCPP_EXCEPTION_ABI _LIBCPP_AVAILABILITY_BAD_ARRAY_LENGTH
+    bad_array_length : public bad_alloc {
 public:
     bad_array_length() _NOEXCEPT;
     virtual ~bad_array_length() _NOEXCEPT;
@@ -182,7 +181,7 @@
 _LIBCPP_OVERRIDABLE_FUNC_VIS void  operator delete(void* __p) _NOEXCEPT;
 _LIBCPP_OVERRIDABLE_FUNC_VIS void  operator delete(void* __p, const std::nothrow_t&) _NOEXCEPT;
 #ifndef _LIBCPP_HAS_NO_SIZED_DEALLOCATION
-_LIBCPP_OVERRIDABLE_FUNC_VIS void  operator delete(void* __p, std::size_t __sz) _NOEXCEPT;
+_LIBCPP_OVERRIDABLE_FUNC_VIS _LIBCPP_AVAILABILITY_SIZED_NEW_DELETE void  operator delete(void* __p, std::size_t __sz) _NOEXCEPT;
 #endif
 
 _LIBCPP_OVERRIDABLE_FUNC_VIS void* operator new[](std::size_t __sz) _THROW_BAD_ALLOC;
@@ -190,7 +189,7 @@
 _LIBCPP_OVERRIDABLE_FUNC_VIS void  operator delete[](void* __p) _NOEXCEPT;
 _LIBCPP_OVERRIDABLE_FUNC_VIS void  operator delete[](void* __p, const std::nothrow_t&) _NOEXCEPT;
 #ifndef _LIBCPP_HAS_NO_SIZED_DEALLOCATION
-_LIBCPP_OVERRIDABLE_FUNC_VIS void  operator delete[](void* __p, std::size_t __sz) _NOEXCEPT;
+_LIBCPP_OVERRIDABLE_FUNC_VIS _LIBCPP_AVAILABILITY_SIZED_NEW_DELETE void  operator delete[](void* __p, std::size_t __sz) _NOEXCEPT;
 #endif
 
 #ifndef _LIBCPP_HAS_NO_ALIGNED_ALLOCATION
@@ -199,7 +198,7 @@
 _LIBCPP_OVERRIDABLE_FUNC_VIS void  operator delete(void* __p, std::align_val_t) _NOEXCEPT;
 _LIBCPP_OVERRIDABLE_FUNC_VIS void  operator delete(void* __p, std::align_val_t, const std::nothrow_t&) _NOEXCEPT;
 #ifndef _LIBCPP_HAS_NO_SIZED_DEALLOCATION
-_LIBCPP_OVERRIDABLE_FUNC_VIS void  operator delete(void* __p, std::size_t __sz, std::align_val_t) _NOEXCEPT;
+_LIBCPP_OVERRIDABLE_FUNC_VIS _LIBCPP_AVAILABILITY_SIZED_NEW_DELETE void  operator delete(void* __p, std::size_t __sz, std::align_val_t) _NOEXCEPT;
 #endif
 
 _LIBCPP_OVERRIDABLE_FUNC_VIS void* operator new[](std::size_t __sz, std::align_val_t) _THROW_BAD_ALLOC;
@@ -207,7 +206,7 @@
 _LIBCPP_OVERRIDABLE_FUNC_VIS void  operator delete[](void* __p, std::align_val_t) _NOEXCEPT;
 _LIBCPP_OVERRIDABLE_FUNC_VIS void  operator delete[](void* __p, std::align_val_t, const std::nothrow_t&) _NOEXCEPT;
 #ifndef _LIBCPP_HAS_NO_SIZED_DEALLOCATION
-_LIBCPP_OVERRIDABLE_FUNC_VIS void  operator delete[](void* __p, std::size_t __sz, std::align_val_t) _NOEXCEPT;
+_LIBCPP_OVERRIDABLE_FUNC_VIS _LIBCPP_AVAILABILITY_SIZED_NEW_DELETE void  operator delete[](void* __p, std::size_t __sz, std::align_val_t) _NOEXCEPT;
 #endif
 #endif
 
@@ -238,6 +237,9 @@
 
 #ifdef _LIBCPP_BAD_ARRAY_LENGTH_DEFINED
 _LIBCPP_NORETURN inline _LIBCPP_ALWAYS_INLINE
+#ifndef _LIBCPP_NO_EXCEPTIONS
+_LIBCPP_AVAILABILITY_BAD_ARRAY_LENGTH
+#endif
 void __throw_bad_array_length()
 {
 #ifndef _LIBCPP_NO_EXCEPTIONS
diff --git a/include/ostream b/include/ostream
index ca2c83f..9bf8d3c 100644
--- a/include/ostream
+++ b/include/ostream
@@ -1080,8 +1080,10 @@
                          use_facet<ctype<_CharT> >(__os.getloc()).widen('1'));
 }
 
+#ifndef _LIBCPP_AVAILABILITY_NO_STREAMS_EXTERN_TEMPLATE
 _LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS basic_ostream<char>)
 _LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS basic_ostream<wchar_t>)
+#endif
 
 _LIBCPP_END_NAMESPACE_STD
 
diff --git a/include/shared_mutex b/include/shared_mutex
index f2fd667..b0802ae 100644
--- a/include/shared_mutex
+++ b/include/shared_mutex
@@ -141,7 +141,7 @@
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
-struct _LIBCPP_TYPE_VIS __shared_mutex_base
+struct _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_SHARED_MUTEX __shared_mutex_base
 {
     mutex               __mut_;
     condition_variable  __gate1_;
@@ -173,7 +173,7 @@
 
 
 #if _LIBCPP_STD_VER > 14
-class _LIBCPP_TYPE_VIS shared_mutex
+class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_SHARED_MUTEX shared_mutex
 {
     __shared_mutex_base __base;
 public:
@@ -199,7 +199,7 @@
 #endif
 
 
-class _LIBCPP_TYPE_VIS shared_timed_mutex
+class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_SHARED_MUTEX shared_timed_mutex
 {
     __shared_mutex_base __base;
 public:
diff --git a/include/streambuf b/include/streambuf
index 8607065..12eded5 100644
--- a/include/streambuf
+++ b/include/streambuf
@@ -476,11 +476,13 @@
     return traits_type::eof();
 }
 
+#ifndef _LIBCPP_AVAILABILITY_NO_STREAMS_EXTERN_TEMPLATE
 _LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS basic_streambuf<char>)
 _LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS basic_streambuf<wchar_t>)
 
 _LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS basic_ios<char>)
 _LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS basic_ios<wchar_t>)
+#endif
 
 _LIBCPP_END_NAMESPACE_STD
 
diff --git a/include/typeinfo b/include/typeinfo
index 4145ac1..8624b34 100644
--- a/include/typeinfo
+++ b/include/typeinfo
@@ -108,6 +108,7 @@
 #endif
 
 public:
+    _LIBCPP_AVAILABILITY_TYPEINFO_VTABLE
     virtual ~type_info();
 
 #if defined(_LIBCPP_HAS_NONUNIQUE_TYPEINFO)