Merge to upstream r244462.

Change-Id: I97e4a2e1d843ad20a9225a31bacc7b1a6e9d8f4f
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 230a3c6..be6fbbe 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -3,18 +3,21 @@
 #===============================================================================
 # Setup Project
 #===============================================================================
-
-project(libcxx CXX C)
 cmake_minimum_required(VERSION 2.8)
 
 if(POLICY CMP0042)
   cmake_policy(SET CMP0042 NEW) # Set MACOSX_RPATH=YES by default
 endif()
+if(POLICY CMP0022)
+  cmake_policy(SET CMP0022 NEW) # Required when interacting with LLVM and Clang
+endif()
+
+project(libcxx CXX C)
 
 set(PACKAGE_NAME libcxx)
 set(PACKAGE_VERSION trunk-svn)
 set(PACKAGE_STRING "${PACKAGE_NAME} ${PACKAGE_VERSION}")
-set(PACKAGE_BUGREPORT "llvmbugs@cs.uiuc.edu")
+set(PACKAGE_BUGREPORT "llvm-bugs@lists.llvm.org")
 
 # Add path for custom modules
 set(CMAKE_MODULE_PATH
@@ -30,45 +33,95 @@
  build directory and run 'cmake /path/to/${PROJECT_NAME} [options]' there."
  )
 
-if(CMAKE_SOURCE_DIR STREQUAL CMAKE_CURRENT_SOURCE_DIR)
-  set(LIBCXX_LIBDIR_SUFFIX "" CACHE STRING
-      "Define suffix of library directory name (32/64)")
-
-  set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib${LIBCXX_LIBDIR_SUFFIX})
-  set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib${LIBCXX_LIBDIR_SUFFIX})
-
-  set(LIBCXX_BUILT_STANDALONE 1)
-else()
-  set(LIBCXX_LIBDIR_SUFFIX ${LLVM_LIBDIR_SUFFIX})
+# Find the LLVM sources and simulate LLVM CMake options.
+include(HandleOutOfTreeLLVM)
+if (LIBCXX_BUILT_STANDALONE AND NOT LLVM_FOUND)
+  message(WARNING "UNSUPPORTED LIBCXX CONFIGURATION DETECTED: "
+                  "llvm-config not found and LLVM_PATH not defined.\n"
+                  "Reconfigure with -DLLVM_CONFIG=path/to/llvm-config "
+                  "or -DLLVM_PATH=path/to/llvm-source-root.")
 endif()
 
+
 #===============================================================================
 # Setup CMake Options
 #===============================================================================
 
-# Define options.
+# Basic options ---------------------------------------------------------------
+option(LIBCXX_ENABLE_ASSERTIONS "Enable assertions independent of build mode." ON)
+option(LIBCXX_ENABLE_SHARED "Build libc++ as a shared library." ON)
+
+option(LIBCXX_INCLUDE_TESTS "Build the libc++ tests." ${LLVM_INCLUDE_TESTS})
+set(LIBCXX_LIBDIR_SUFFIX "${LLVM_LIBDIR_SUFFIX}" CACHE STRING
+    "Define suffix of library directory name (32/64)")
+option(LIBCXX_INSTALL_HEADERS "Install the libc++ headers." ON)
+option(LIBCXX_INSTALL_SUPPORT_HEADERS "Install libc++ support headers." ON)
+
+# ABI Library options ---------------------------------------------------------
+set(LIBCXX_CXX_ABI "${LIBCXX_CXX_ABI}" CACHE STRING
+    "Specify C++ ABI library to use." FORCE)
+set(CXXABIS none libcxxabi libcxxrt libstdc++ libsupc++)
+set_property(CACHE LIBCXX_CXX_ABI PROPERTY STRINGS ;${CXXABIS})
+
+option(LIBCXX_ENABLE_STATIC_ABI_LIBRARY "Statically link the ABI library" OFF)
+
+# Build libc++abi with libunwind. We need this option to determine whether to
+# link with libunwind or libgcc_s while running the test cases.
+option(LIBCXXABI_USE_LLVM_UNWINDER "Build and use the LLVM unwinder." OFF)
+
+# Target options --------------------------------------------------------------
+option(LIBCXX_BUILD_32_BITS "Build 32 bit libc++." ${LLVM_BUILD_32_BITS})
+set(LIBCXX_SYSROOT "" CACHE STRING "Use alternate sysroot.")
+set(LIBCXX_GCC_TOOLCHAIN "" CACHE STRING "Use alternate GCC toolchain.")
+
+# Feature options -------------------------------------------------------------
 option(LIBCXX_ENABLE_EXCEPTIONS "Use exceptions." ON)
 option(LIBCXX_ENABLE_RTTI "Use run time type information." ON)
-option(LIBCXX_ENABLE_ASSERTIONS "Enable assertions independent of build mode." ON)
-option(LIBCXX_ENABLE_PEDANTIC "Compile with pedantic enabled." ON)
-option(LIBCXX_ENABLE_WERROR "Fail and stop if a warning is triggered." OFF)
-option(LIBCXX_ENABLE_CXX1Y "Enable -std=c++1y and use of c++1y language features if the compiler supports it." OFF)
-option(LIBCXX_ENABLE_SHARED "Build libc++ as a shared library." ON)
+option(LIBCXX_ENABLE_GLOBAL_FILESYSTEM_NAMESPACE "Build libc++ with support for the global filesystem namespace." ON)
+option(LIBCXX_ENABLE_STDIN "Build libc++ with support for stdin/std::cin." ON)
+option(LIBCXX_ENABLE_STDOUT "Build libc++ with support for stdout/std::cout." ON)
 option(LIBCXX_ENABLE_THREADS "Build libc++ with support for threads." ON)
-option(LIBCXX_BUILD_32_BITS "Build 32 bit libc++" OFF)
+option(LIBCXX_ENABLE_THREAD_UNSAFE_C_FUNCTIONS "Build libc++ with support for thread-unsafe C functions" ON)
 option(LIBCXX_ENABLE_MONOTONIC_CLOCK
   "Build libc++ with support for a monotonic clock.
    This option may only be used when LIBCXX_ENABLE_THREADS=OFF." ON)
-option(LIBCXX_INSTALL_HEADERS "Install the libc++ headers." ON)
-option(LIBCXX_INSTALL_SUPPORT_HEADERS "Install libc++ support headers." ON)
-option(LIBCXX_ENABLE_STATIC_ABI_LIBRARY "Statically link the ABI library" OFF)
-set(LIBCXX_SYSROOT "" CACHE STRING "Use alternate sysroot.")
-set(LIBCXX_GCC_TOOLCHAIN "" CACHE STRING "Use alternate GCC toolchain.")
-if (LIBCXX_BUILT_STANDALONE)
-  set(LLVM_USE_SANITIZER "" CACHE STRING
-      "Define the sanitizer used to build the library and tests")
+
+# Misc options ----------------------------------------------------------------
+option(LIBCXX_ENABLE_PEDANTIC "Compile with pedantic enabled." ON)
+option(LIBCXX_ENABLE_WERROR "Fail and stop if a warning is triggered." OFF)
+
+option(LIBCXX_GENERATE_COVERAGE "Enable generating code coverage." OFF)
+set(LIBCXX_COVERAGE_LIBRARY "" CACHE STRING
+    "The Profile-rt library used to build with code coverage")
+
+#===============================================================================
+# Check option configurations
+#===============================================================================
+
+# Ensure LIBCXX_ENABLE_MONOTONIC_CLOCK is set to ON only when
+# LIBCXX_ENABLE_THREADS is on.
+if(LIBCXX_ENABLE_THREADS AND NOT LIBCXX_ENABLE_MONOTONIC_CLOCK)
+  message(FATAL_ERROR "LIBCXX_ENABLE_MONOTONIC_CLOCK can only be set to OFF"
+                      " when LIBCXX_ENABLE_THREADS is also set to OFF.")
 endif()
 
+# Ensure LLVM_USE_SANITIZER is not specified when LIBCXX_GENERATE_COVERAGE
+# is ON.
+if (LLVM_USE_SANITIZER AND LIBCXX_GENERATE_COVERAGE)
+  message(FATAL_ERROR "LLVM_USE_SANITIZER cannot be used with LIBCXX_GENERATE_COVERAGE")
+endif()
+
+# Set LIBCXX_BUILD_32_BITS to (LIBCXX_BUILD_32_BITS OR LLVM_BUILD_32_BITS)
+# and check that we can build with 32 bits if requested.
+if (CMAKE_SIZEOF_VOID_P EQUAL 8 AND NOT WIN32)
+  if (LIBCXX_BUILD_32_BITS AND NOT LLVM_BUILD_32_BITS) # Don't duplicate the output from LLVM
+    message(STATUS "Building 32 bits executables and libraries.")
+  endif()
+elseif(LIBCXX_BUILD_32_BITS)
+  message(FATAL_ERROR "LIBCXX_BUILD_32_BITS=ON is not supported on this platform.")
+endif()
+
+# Check that this option is not enabled on Apple and emit a usage warning.
 if (LIBCXX_ENABLE_STATIC_ABI_LIBRARY)
   if (APPLE)
     message(FATAL_ERROR "LIBCXX_ENABLE_STATIC_ABI_LIBRARY is not supported on OS X")
@@ -77,23 +130,6 @@
   endif()
 endif()
 
-set(CXXABIS none libcxxabi libcxxrt libstdc++ libsupc++)
-if (NOT LIBCXX_CXX_ABI)
-  if (NOT DEFINED LIBCXX_BUILT_STANDALONE AND
-      IS_DIRECTORY "${CMAKE_SOURCE_DIR}/projects/libcxxabi")
-    set(LIBCXX_CXX_ABI_LIBNAME "libcxxabi")
-    set(LIBCXX_LIBCXXABI_INCLUDE_PATHS "${CMAKE_SOURCE_DIR}/projects/libcxxabi/include")
-    set(LIBCXX_CXX_ABI_INTREE 1)
-  else ()
-    set(LIBCXX_CXX_ABI_LIBNAME "none")
-  endif ()
-else ()
-  set(LIBCXX_CXX_ABI_LIBNAME "${LIBCXX_CXX_ABI}")
-endif ()
-set(LIBCXX_CXX_ABI "${LIBCXX_CXX_ABI}" CACHE STRING
-    "Specify C++ ABI library to use." FORCE)
-set_property(CACHE LIBCXX_CXX_ABI PROPERTY STRINGS ;${CXXABIS})
-
 #===============================================================================
 # Configure System
 #===============================================================================
@@ -103,202 +139,155 @@
 set(LIBCXX_BINARY_DIR  ${CMAKE_CURRENT_BINARY_DIR})
 set(LIBCXX_LIBRARY_DIR ${CMAKE_BINARY_DIR}/lib${LIBCXX_LIBDIR_SUFFIX})
 
+set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${LIBCXX_LIBRARY_DIR})
+set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${LIBCXX_LIBRARY_DIR})
+
 # Declare libc++ configuration variables.
 # They are intended for use as follows:
 # LIBCXX_CXX_FLAGS: General flags for both the compiler and linker.
 # LIBCXX_COMPILE_FLAGS: Compile only flags.
 # LIBCXX_LINK_FLAGS: Linker only flags.
-set(LIBCXX_CXX_FLAGS "")
 set(LIBCXX_COMPILE_FLAGS "")
 set(LIBCXX_LINK_FLAGS "")
+set(LIBCXX_LIBRARIES "")
 
 # Configure compiler.
 include(config-ix)
-# Configure ABI library
-include(HandleLibCXXABI)
+
+# Configure coverage options.
+if (LIBCXX_GENERATE_COVERAGE)
+  include(CodeCoverage)
+  set(CMAKE_BUILD_TYPE "COVERAGE" CACHE STRING "" FORCE)
+endif()
+
+string(TOUPPER "${CMAKE_BUILD_TYPE}" uppercase_CMAKE_BUILD_TYPE)
 
 #===============================================================================
 # Setup Compiler Flags
 #===============================================================================
 
-# Get required flags.
+include(HandleLibCXXABI) # Steup the ABI library flags
+
+# Include macros for adding and removing libc++ flags.
+include(HandleLibcxxFlags)
+
+# Remove flags that may have snuck in.
+remove_flags(-DNDEBUG -UNDEBUG -D_DEBUG
+             -stdlib=libc++ -stdlib=libstdc++ -lc++abi -m32)
+
+# Required flags ==============================================================
+add_compile_flags_if_supported(-std=c++11)
+if (NOT MSVC AND NOT LIBCXX_SUPPORTS_STD_EQ_CXX11_FLAG)
+  message(FATAL_ERROR "C++11 is required but the compiler does not support -std=c++11")
+endif()
+
 # On all systems the system c++ standard library headers need to be excluded.
-if (MSVC)
-  # MSVC only has -X, which disables all default includes; including the crt.
-  # Thus, we do nothing and hope we don't accidentally include any of the C++
-  # headers.
-else()
-  if (LIBCXX_HAS_NOSTDINCXX_FLAG)
-    list(APPEND LIBCXX_COMPILE_FLAGS -nostdinc++)
-    string(REPLACE "-stdlib=libc++" "" CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS}")
-    string(REPLACE "-stdlib=libstdc++" "" CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS}")
-  endif()
-  # If c++1y has been enabled then attempt to use it. Fail if it is no supported
-  # by the compiler. Otherwise choose c++11 and ensure the compiler supports it.
-  if (LIBCXX_ENABLE_CXX1Y)
-    if (LIBCXX_HAS_STDCXX1Y_FLAG)
-      set(LIBCXX_STD_VERSION c++1y)
-    else()
-      message(FATAL_ERROR "c++1y was enabled but the compiler does not support it.")
-    endif()
-  else()
-    if (LIBCXX_HAS_STDCXX11_FLAG)
-      set(LIBCXX_STD_VERSION c++11)
-    else()
-      message(FATAL_ERROR "c++11 is required by libc++ but is not supported by the compiler")
-    endif()
-  endif()
-  # LIBCXX_STD_VERSION should always be set at this point.
-  list(APPEND LIBCXX_CXX_FLAGS "-std=${LIBCXX_STD_VERSION}")
-endif()
+# MSVC only has -X, which disables all default includes; including the crt.
+# Thus, we do nothing and hope we don't accidentally include any of the C++
+# headers
+add_compile_flags_if_supported(-nostdinc++)
 
-macro(append_if list condition var)
-  if (${condition})
-    list(APPEND ${list} ${var})
-  endif()
-endmacro()
+# Target flags ================================================================
+add_flags_if(LIBCXX_BUILD_32_BITS -m32)
+add_flags_if(LIBCXX_TARGET_TRIPLE "-target ${LIBCXX_TARGET_TRIPLE}")
+add_flags_if(LIBCXX_SYSROOT "--sysroot ${LIBCXX_SYSROOT}")
+add_flags_if(LIBCXX_GCC_TOOLCHAIN "-gcc-toolchain ${LIBCXX_GCC_TOOLCHAIN}")
 
-# Get warning flags
-if (NOT MSVC)
-  append_if(LIBCXX_COMPILE_FLAGS LIBCXX_HAS_WALL_FLAG -Wall)
-  list(APPEND LIBCXX_COMPILE_FLAGS -Werror=return-type)
-endif()
-
-append_if(LIBCXX_COMPILE_FLAGS LIBCXX_HAS_W_FLAG -W)
-append_if(LIBCXX_COMPILE_FLAGS LIBCXX_HAS_WNO_UNUSED_PARAMETER_FLAG -Wno-unused-parameter)
-append_if(LIBCXX_COMPILE_FLAGS LIBCXX_HAS_WWRITE_STRINGS_FLAG -Wwrite-strings)
-append_if(LIBCXX_COMPILE_FLAGS LIBCXX_HAS_WNO_LONG_LONG_FLAG -Wno-long-long)
+# Warning flags ===============================================================
+add_definitions(-D_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+add_compile_flags_if_supported(
+    -Wall -W -Wwrite-strings
+    -Wno-unused-parameter -Wno-long-long
+    -Werror=return-type)
 if (LIBCXX_ENABLE_WERROR)
-  append_if(LIBCXX_COMPILE_FLAGS LIBCXX_HAS_WERROR_FLAG -Werror)
-  append_if(LIBCXX_COMPILE_FLAGS LIBCXX_HAS_WX_FLAG -WX)
+  add_compile_flags_if_supported(-Werror)
+  add_compile_flags_if_supported(-WX)
 else()
-  append_if(LIBCXX_COMPILE_FLAGS LIBCXX_HAS_WNO_ERROR_FLAG -Wno-error)
-  append_if(LIBCXX_COMPILE_FLAGS LIBCXX_HAS_NO_WX_FLAG -WX-)
+  # TODO(EricWF) Remove this. We shouldn't be suppressing errors when -Werror is
+  # added elsewhere.
+  add_compile_flags_if_supported(-Wno-error)
 endif()
 if (LIBCXX_ENABLE_PEDANTIC)
-  append_if(LIBCXX_COMPILE_FLAGS LIBCXX_HAS_PEDANTIC_FLAG -pedantic)
+  add_compile_flags_if_supported(-pedantic)
 endif()
 
-# Get feature flags.
-# Exceptions
+# Exception flags =============================================================
 if (LIBCXX_ENABLE_EXCEPTIONS)
   # Catches C++ exceptions only and tells the compiler to assume that extern C
   # functions never throw a C++ exception.
-  append_if(LIBCXX_CXX_FLAGS LIBCXX_HAS_EHSC_FLAG -EHsc)
+  add_compile_flags_if_supported(-EHsc)
 else()
-  list(APPEND LIBCXX_CXX_FLAGS -D_LIBCPP_NO_EXCEPTIONS)
-  append_if(LIBCXX_CXX_FLAGS LIBCXX_HAS_NO_EHS_FLAG -EHs-)
-  append_if(LIBCXX_CXX_FLAGS LIBCXX_HAS_NO_EHA_FLAG -EHa-)
-  append_if(LIBCXX_CXX_FLAGS LIBCXX_HAS_FNO_EXCEPTIONS_FLAG -fno-exceptions)
+  add_definitions(-D_LIBCPP_NO_EXCEPTIONS)
+  add_compile_flags_if_supported(-EHs- -EHa-)
+  add_compile_flags_if_supported(-fno-exceptions)
 endif()
-# RTTI
+
+# RTTI flags ==================================================================
 if (NOT LIBCXX_ENABLE_RTTI)
-  list(APPEND LIBCXX_CXX_FLAGS -D_LIBCPP_NO_RTTI)
-  append_if(LIBCXX_CXX_FLAGS LIBCXX_HAS_NO_GR_FLAG -GR-)
-  append_if(LIBCXX_CXX_FLAGS LIBCXX_HAS_FNO_RTTI_FLAG -fno-rtti)
+  add_definitions(-D_LIBCPP_NO_RTTI)
+  add_compile_flags_if_supported(-GR-)
+  add_compile_flags_if_supported(-fno-rtti)
 endif()
-# Assert
-string(TOUPPER "${CMAKE_BUILD_TYPE}" uppercase_CMAKE_BUILD_TYPE)
+
+# Assertion flags =============================================================
+define_if(LIBCXX_ENABLE_ASSERTIONS -UNDEBUG)
+define_if_not(LIBCXX_ENABLE_ASSERTIONS -DNDEBUG)
 if (LIBCXX_ENABLE_ASSERTIONS)
   # MSVC doesn't like _DEBUG on release builds. See PR 4379.
-  if (NOT MSVC)
-    list(APPEND LIBCXX_COMPILE_FLAGS -D_DEBUG)
-  endif()
-  # On Release builds cmake automatically defines NDEBUG, so we
-  # explicitly undefine it:
-  if (uppercase_CMAKE_BUILD_TYPE STREQUAL "RELEASE")
-    list(APPEND LIBCXX_COMPILE_FLAGS -UNDEBUG)
-  endif()
-else()
-  if (NOT uppercase_CMAKE_BUILD_TYPE STREQUAL "RELEASE")
-    list(APPEND LIBCXX_COMPILE_FLAGS -DNDEBUG)
-  endif()
-endif()
-# Static library
-if (NOT LIBCXX_ENABLE_SHARED)
-  list(APPEND LIBCXX_COMPILE_FLAGS -D_LIBCPP_BUILD_STATIC)
+  define_if_not(MSVC -D_DEBUG)
 endif()
 
-if (CMAKE_SIZEOF_VOID_P EQUAL 8 AND NOT WIN32)
-  if (LIBCXX_BUILD_32_BITS)
-    message(STATUS "Building 32 bits executables and libraries.")
-    list(APPEND LIBCXX_CXX_FLAGS "-m32")
-  endif()
-elseif(LIBCXX_BUILD_32_BITS)
-  message(FATAL_ERROR "LIBCXX_BUILD_32_BITS=ON is not supported on this platform.")
-endif()
-# This is the _ONLY_ place where add_definitions is called.
-if (MSVC)
-  add_definitions(-D_CRT_SECURE_NO_WARNINGS)
-endif()
+# Feature flags ===============================================================
+define_if(MSVC -D_CRT_SECURE_NO_WARNINGS)
+define_if_not(LIBCXX_ENABLE_GLOBAL_FILESYSTEM_NAMESPACE -D_LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE)
+define_if_not(LIBCXX_ENABLE_STDIN -D_LIBCPP_HAS_NO_STDIN)
+define_if_not(LIBCXX_ENABLE_STDOUT -D_LIBCPP_HAS_NO_STDOUT)
+define_if_not(LIBCXX_ENABLE_THREADS -D_LIBCPP_HAS_NO_THREADS)
+define_if_not(LIBCXX_ENABLE_MONOTONIC_CLOCK -D_LIBCPP_HAS_NO_MONOTONIC_CLOCK)
+define_if_not(LIBCXX_ENABLE_THREAD_UNSAFE_C_FUNCTIONS -D_LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS)
 
-# LIBCXX_ENABLE_THREADS configuration
-if (NOT LIBCXX_ENABLE_THREADS)
-  add_definitions(-D_LIBCPP_HAS_NO_THREADS)
-  if (NOT LIBCXX_ENABLE_MONOTONIC_CLOCK)
-    add_definitions(-D_LIBCPP_HAS_NO_MONOTONIC_CLOCK)
-  endif()
-# Ensure LIBCXX_ENABLE_MONOTONIC_CLOCK is set to ON.
-elseif(NOT LIBCXX_ENABLE_MONOTONIC_CLOCK)
-  message(FATAL_ERROR "LIBCXX_ENABLE_MONOTONIC_CLOCK can only be set to OFF"
-                      " when LIBCXX_ENABLE_THREADS is also set to OFF.")
-endif()
+
+# Sanitizer flags
 
 # Configure for sanitizers. If LIBCXX_BUILT_STANDALONE then we have to do
 # the flag translation ourselves. Othewise LLVM's CMakeList.txt will handle it.
 if (LIBCXX_BUILT_STANDALONE)
+  set(LLVM_USE_SANITIZER "" CACHE STRING
+      "Define the sanitizer used to build the library and tests")
   # NOTE: LLVM_USE_SANITIZER checks for a UNIX like system instead of MSVC.
   # But we don't have LLVM_ON_UNIX so checking for MSVC is the best we can do.
   if (LLVM_USE_SANITIZER AND NOT MSVC)
-    append_if(LIBCXX_CXX_FLAGS LIBCXX_HAS_FNO_OMIT_FRAME_POINTER_FLAG
-              "-fno-omit-frame-pointer")
+    add_flags_if_supported("-fno-omit-frame-pointer")
+    add_flags_if_supported("-gline-tables-only")
+
     if (NOT uppercase_CMAKE_BUILD_TYPE STREQUAL "DEBUG" AND
         NOT uppercase_CMAKE_BUILD_TYPE STREQUAL "RELWITHDEBINFO")
-      append_if(LIBCXX_CXX_FLAGS LIBCXX_HAS_GLINE_TABLES_ONLY_FLAG
-                "-gline-tables-only")
+        add_flags_if_supported("-gline-tables-only")
     endif()
     if (LLVM_USE_SANITIZER STREQUAL "Address")
-      list(APPEND LIBCXX_CXX_FLAGS "-fsanitize=address")
+      add_flags("-fsanitize=address")
     elseif (LLVM_USE_SANITIZER MATCHES "Memory(WithOrigins)?")
-      list(APPEND LIBCXX_CXX_FLAGS "-fsanitize=memory")
+      add_flags(-fsanitize=memory)
       if (LLVM_USE_SANITIZER STREQUAL "MemoryWithOrigins")
-        list(APPEND LIBCXX_CXX_FLAGS "-fsanitize-memory-track-origins")
+        add_flags("-fsanitize-memory-track-origins")
       endif()
     elseif (LLVM_USE_SANITIZER STREQUAL "Undefined")
-      list(APPEND LIBCXX_CXX_FLAGS
-          "-fsanitize=undefined -fno-sanitize=vptr,function -fno-sanitize-recover")
+      add_flags("-fsanitize=undefined -fno-sanitize=vptr,function -fno-sanitize-recover=all")
     elseif (LLVM_USE_SANITIZER STREQUAL "Thread")
-      list(APPEND LIBCXX_CXX_FLAGS "-fsanitize=thread")
+      add_flags(-fsanitize=thread)
     else()
       message(WARNING "Unsupported value of LLVM_USE_SANITIZER: ${LLVM_USE_SANITIZER}")
     endif()
-  elseif(MSVC)
-    message(WARNING "LLVM_USE_SANITIZER is not supported with MSVC")
+  elseif(LLVM_USE_SANITIZER AND MSVC)
+    message(WARNING "LLVM_USE_SANITIZER is not supported on this platform.")
   endif()
 endif()
-
-append_if(LIBCXX_CXX_FLAGS LIBCXX_TARGET_TRIPLE
-          "-target ${LIBCXX_TARGET_TRIPLE}")
-append_if(LIBCXX_CXX_FLAGS LIBCXX_SYSROOT "--sysroot ${LIBCXX_SYSROOT}")
-append_if(LIBCXX_CXX_FLAGS LIBCXX_GCC_TOOLCHAIN
-          "-gcc-toolchain ${LIBCXX_GCC_TOOLCHAIN}")
-
-string(REPLACE ";" " " LIBCXX_CXX_FLAGS "${LIBCXX_CXX_FLAGS}")
-set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${LIBCXX_CXX_FLAGS}")
-
 #===============================================================================
-# Setup Source Code
+# Setup Source Code And Tests
 #===============================================================================
-
 include_directories(include)
 add_subdirectory(include)
-
-# Add source code. This also contains all of the logic for deciding linker flags
-# soname, etc...
 add_subdirectory(lib)
-
-#===============================================================================
-# Setup Tests
-#===============================================================================
-
-add_subdirectory(test)
+if (LIBCXX_INCLUDE_TESTS)
+  add_subdirectory(test)
+endif()
diff --git a/LICENSE.TXT b/LICENSE.TXT
index 41ca5d1..53352e4 100644
--- a/LICENSE.TXT
+++ b/LICENSE.TXT
@@ -14,7 +14,7 @@
 University of Illinois/NCSA
 Open Source License
 
-Copyright (c) 2009-2014 by the contributors listed in CREDITS.TXT
+Copyright (c) 2009-2015 by the contributors listed in CREDITS.TXT
 
 All rights reserved.
 
diff --git a/TODO.TXT b/TODO.TXT
new file mode 100644
index 0000000..513b863
--- /dev/null
+++ b/TODO.TXT
@@ -0,0 +1,49 @@
+This is meant to be a general place to list things that should be done "someday"
+
+ABI Related Tasks
+=================
+* Explicitly manage and verify symbols exported from the dylib.
+* Explore using namespaces for managing symbol visibility.
+* Introduce and document ABI versioning/evolution policy.
+
+CXX Runtime Library Tasks
+=========================
+* Cleanup #ifdef hell in sources files that supports the different ABI libraries.
+* Fix that CMake always link to /usr/lib/libc++abi.dylib on OS X.
+* Fix selection of ABI symbol list on OS X.
+* Have CMake generate linker scripts for libc++.so that it properly links the
+  runtime library.
+* Look into mirroring libsupc++'s typeinfo vtable layout when libsupc++/libstdc++
+  is used as the runtime library.
+* Audit libraries that CMake links into libc++. Are they all required?
+* Investigate and document interoperability between libc++ and libstdc++ on
+  linux. Do this for every supported c++ runtime library.
+
+Atomic Related Tasks
+====================
+* Support <atomic> in C++03 (needed for internal use).
+* Audit use of libatomic builtins in <atomic> with GCC.
+* future should use <atomic> for synchronization.
+* call_once should use <atomic> for synchronization.
+* Audit shared_ptr use of <atomic>
+
+Test Suite Tasks
+================
+* Get test suite passing in C++03.
+* Move all libc++ specific tests from test/std into test/libcxx.
+* Improve how LIT handles compiler warnings.
+* Improve the quality and portability of the locale test data.
+
+Misc Tasks
+==========
+* Find all sequences of >2 underscores and eradicate them.
+* run clang-tidy on libc++
+* Document the "conditionally-supported" bits of libc++
+* Look at basic_string's move assignment operator, re LWG 2063 and POCMA
+* libc++ is missing try_emplace
+* Put a static_assert in std::allocator to deny const/volatile types (LWG 2447)
+* Investigate the effect of using __decltype instead of __typeof__ to provide
+  decltype in C++03. What code could be broken by this change?
+* Convert failure tests to use Clang Verify.
+* Document support (or lack of) for C++11 libraries in C++03.
+* Document supported compilers.
diff --git a/cmake/Modules/CodeCoverage.cmake b/cmake/Modules/CodeCoverage.cmake
new file mode 100644
index 0000000..addd10a
--- /dev/null
+++ b/cmake/Modules/CodeCoverage.cmake
@@ -0,0 +1,36 @@
+find_program(CODE_COVERAGE_LCOV lcov)
+if (NOT CODE_COVERAGE_LCOV)
+  message(FATAL_ERROR "Cannot find lcov...")
+endif()
+
+find_program(CODE_COVERAGE_GENHTML genhtml)
+if (NOT CODE_COVERAGE_GENHTML)
+  message(FATAL_ERROR "Cannot find genhtml...")
+endif()
+
+set(CMAKE_CXX_FLAGS_COVERAGE "-g -O0 --coverage")
+
+function(setup_lcov_test_target_coverage target_name output_dir capture_dirs source_dirs)
+  file(MAKE_DIRECTORY ${output_dir})
+
+  set(CAPTURE_DIRS "")
+  foreach(cdir ${capture_dirs})
+    list(APPEND CAPTURE_DIRS "-d;${cdir}")
+  endforeach()
+
+  set(EXTRACT_DIRS "")
+  foreach(sdir ${source_dirs})
+    list(APPEND EXTRACT_DIRS "'${sdir}/*'")
+  endforeach()
+
+  message(STATUS "Capture Directories: ${CAPTURE_DIRS}")
+  message(STATUS "Extract Directories: ${EXTRACT_DIRS}")
+
+  add_custom_target(generate-lib${target_name}-coverage
+        COMMAND ${CODE_COVERAGE_LCOV} --capture ${CAPTURE_DIRS} -o test_coverage.info
+        COMMAND ${CODE_COVERAGE_LCOV} --extract test_coverage.info ${EXTRACT_DIRS} -o test_coverage.info
+        COMMAND ${CODE_COVERAGE_GENHTML} --demangle-cpp test_coverage.info -o test_coverage
+        COMMAND ${CMAKE_COMMAND} -E remove test_coverage.info
+        WORKING_DIRECTORY ${output_dir}
+        COMMENT "Generating coverage results")
+endfunction()
diff --git a/cmake/Modules/HandleLibCXXABI.cmake b/cmake/Modules/HandleLibCXXABI.cmake
index 960df9e..4224882 100644
--- a/cmake/Modules/HandleLibCXXABI.cmake
+++ b/cmake/Modules/HandleLibCXXABI.cmake
@@ -15,9 +15,9 @@
 #   abidirs   : A list of relative paths to create under an include directory
 #               in the libc++ build directory.
 #
-macro(setup_abi_lib abipathvar abidefines abilib abifiles abidirs)
+macro(setup_abi_lib abidefines abilib abifiles abidirs)
   list(APPEND LIBCXX_COMPILE_FLAGS ${abidefines})
-  set(${abipathvar} "${${abipathvar}}"
+  set(LIBCXX_CXX_ABI_INCLUDE_PATHS "${LIBCXX_CXX_ABI_INCLUDE_PATHS}"
     CACHE PATH
     "Paths to C++ ABI header directories separated by ';'." FORCE
     )
@@ -33,7 +33,7 @@
 
   foreach(fpath ${LIBCXX_ABILIB_FILES})
     set(found FALSE)
-    foreach(incpath ${${abipathvar}})
+    foreach(incpath ${LIBCXX_CXX_ABI_INCLUDE_PATHS})
       if (EXISTS "${incpath}/${fpath}")
         set(found TRUE)
         get_filename_component(dstdir ${fpath} PATH)
@@ -58,6 +58,21 @@
 
 endmacro()
 
+# Setup the default options if LIBCXX_CXX_ABI is not specified.
+if (NOT LIBCXX_CXX_ABI)
+  if (NOT DEFINED LIBCXX_BUILT_STANDALONE AND
+      IS_DIRECTORY "${CMAKE_SOURCE_DIR}/projects/libcxxabi")
+    set(LIBCXX_CXX_ABI_LIBNAME "libcxxabi")
+    set(LIBCXX_CXX_ABI_INCLUDE_PATHS "${CMAKE_SOURCE_DIR}/projects/libcxxabi/include")
+    set(LIBCXX_CXX_ABI_INTREE 1)
+  else ()
+    set(LIBCXX_CXX_ABI_LIBNAME "none")
+  endif ()
+else ()
+  set(LIBCXX_CXX_ABI_LIBNAME "${LIBCXX_CXX_ABI}")
+endif ()
+
+# Configure based on the selected ABI library.
 if ("${LIBCXX_CXX_ABI_LIBNAME}" STREQUAL "libstdc++" OR
     "${LIBCXX_CXX_ABI_LIBNAME}" STREQUAL "libsupc++")
   set(_LIBSUPCXX_INCLUDE_FILES
@@ -71,7 +86,7 @@
     set(_LIBSUPCXX_DEFINES "")
     set(_LIBSUPCXX_LIBNAME supc++)
   endif()
-  setup_abi_lib("LIBCXX_LIBSUPCXX_INCLUDE_PATHS"
+  setup_abi_lib(
     "-D__GLIBCXX__ ${_LIBSUPCXX_DEFINES}"
     "${_LIBSUPCXX_LIBNAME}" "${_LIBSUPCXX_INCLUDE_FILES}" "bits"
     )
@@ -88,11 +103,11 @@
     # Assume c++abi is installed in the system, rely on -lc++abi link flag.
     set(CXXABI_LIBNAME "c++abi")
   endif()
-  setup_abi_lib("LIBCXX_LIBCXXABI_INCLUDE_PATHS" ""
+  setup_abi_lib("-DLIBCXX_BUILDING_LIBCXXABI"
     ${CXXABI_LIBNAME} "cxxabi.h;__cxxabi_config.h" ""
     )
 elseif ("${LIBCXX_CXX_ABI_LIBNAME}" STREQUAL "libcxxrt")
-  setup_abi_lib("LIBCXX_LIBCXXRT_INCLUDE_PATHS" "-DLIBCXXRT"
+  setup_abi_lib("-DLIBCXXRT"
     "cxxrt" "cxxabi.h;unwind.h;unwind-arm.h;unwind-itanium.h" ""
     )
 elseif (NOT "${LIBCXX_CXX_ABI_LIBNAME}" STREQUAL "none")
diff --git a/cmake/Modules/HandleLibcxxFlags.cmake b/cmake/Modules/HandleLibcxxFlags.cmake
new file mode 100644
index 0000000..223b7b7
--- /dev/null
+++ b/cmake/Modules/HandleLibcxxFlags.cmake
@@ -0,0 +1,147 @@
+# HandleLibcxxFlags - A set of macros used to setup the flags used to compile
+# and link libc++. These macros add flags to the following CMake variables.
+# - LIBCXX_COMPILE_FLAGS: flags used to compile libc++
+# - LIBCXX_LINK_FLAGS: flags used to link libc++
+# - LIBCXX_LIBRARIES: libraries to link libc++ to.
+
+include(CheckCXXCompilerFlag)
+
+unset(add_flag_if_supported)
+
+# Mangle the name of a compiler flag into a valid CMake identifier.
+# Ex: --std=c++11 -> STD_EQ_CXX11
+macro(mangle_name str output)
+  string(STRIP "${str}" strippedStr)
+  string(REGEX REPLACE "^/" "" strippedStr "${strippedStr}")
+  string(REGEX REPLACE "^-+" "" strippedStr "${strippedStr}")
+  string(REGEX REPLACE "-+$" "" strippedStr "${strippedStr}")
+  string(REPLACE "-" "_" strippedStr "${strippedStr}")
+  string(REPLACE "=" "_EQ_" strippedStr "${strippedStr}")
+  string(REPLACE "+" "X" strippedStr "${strippedStr}")
+  string(TOUPPER "${strippedStr}" ${output})
+endmacro()
+
+# Remove a list of flags from all CMake variables that affect compile flags.
+# This can be used to remove unwanted flags specified on the command line
+# or added in other parts of LLVM's cmake configuration.
+macro(remove_flags)
+  foreach(var ${ARGN})
+    string(REPLACE "${var}" "" CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS}")
+    string(REPLACE "${var}" "" CMAKE_C_FLAGS "${CMAKE_C_FLAGS}")
+    string(REPLACE "${var}" "" CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS}")
+    string(REPLACE "${var}" "" CMAKE_SHARED_LINKER_FLAGS "${CMAKE_SHARED_LINKER_FLAGS}")
+    string(REPLACE "${var}" "" CMAKE_SHARED_MODULE_FLAGS "${CMAKE_SHARED_MODULE_FLAGS}")
+    remove_definitions(${var})
+  endforeach()
+endmacro(remove_flags)
+
+# Add a macro definition if condition is true.
+macro(define_if condition def)
+  if (${condition})
+    add_definitions(${def})
+  endif()
+endmacro()
+
+# Add a macro definition if condition is not true.
+macro(define_if_not condition def)
+  if (NOT ${condition})
+    add_definitions(${def})
+  endif()
+endmacro()
+
+# Add a specified list of flags to both 'LIBCXX_COMPILE_FLAGS' and
+# 'LIBCXX_LINK_FLAGS'.
+macro(add_flags)
+  foreach(value ${ARGN})
+    list(APPEND LIBCXX_COMPILE_FLAGS ${value})
+    list(APPEND LIBCXX_LINK_FLAGS ${value})
+  endforeach()
+endmacro()
+
+# If the specified 'condition' is true then add a list of flags to both
+# 'LIBCXX_COMPILE_FLAGS' and 'LIBCXX_LINK_FLAGS'.
+macro(add_flags_if condition)
+  if (${condition})
+    add_flags(${ARGN})
+  endif()
+endmacro()
+
+# Add each flag in the list to LIBCXX_COMPILE_FLAGS and LIBCXX_LINK_FLAGS
+# if that flag is supported by the current compiler.
+macro(add_flags_if_supported)
+  foreach(flag ${ARGN})
+      mangle_name("${flag}" flagname)
+      check_cxx_compiler_flag("${flag}" "LIBCXX_SUPPORTS_${flagname}_FLAG")
+      add_flags_if(LIBCXX_SUPPORTS_${flagname}_FLAG ${flag})
+  endforeach()
+endmacro()
+
+# Add a list of flags to 'LIBCXX_COMPILE_FLAGS'.
+macro(add_compile_flags)
+  foreach(f ${ARGN})
+    list(APPEND LIBCXX_COMPILE_FLAGS ${f})
+  endforeach()
+endmacro()
+
+# If 'condition' is true then add the specified list of flags to
+# 'LIBCXX_COMPILE_FLAGS'
+macro(add_compile_flags_if condition)
+  if (${condition})
+    add_compile_flags(${ARGN})
+  endif()
+endmacro()
+
+# For each specified flag, add that flag to 'LIBCXX_COMPILE_FLAGS' if the
+# flag is supported by the C++ compiler.
+macro(add_compile_flags_if_supported)
+  foreach(flag ${ARGN})
+      mangle_name("${flag}" flagname)
+      check_cxx_compiler_flag("${flag}" "LIBCXX_SUPPORTS_${flagname}_FLAG")
+      add_compile_flags_if(LIBCXX_SUPPORTS_${flagname}_FLAG ${flag})
+  endforeach()
+endmacro()
+
+# Add a list of flags to 'LIBCXX_LINK_FLAGS'.
+macro(add_link_flags)
+  foreach(f ${ARGN})
+    list(APPEND LIBCXX_LINK_FLAGS ${f})
+  endforeach()
+endmacro()
+
+# If 'condition' is true then add the specified list of flags to
+# 'LIBCXX_LINK_FLAGS'
+macro(add_link_flags_if condition)
+  if (${condition})
+    add_link_flags(${ARGN})
+  endif()
+endmacro()
+
+# For each specified flag, add that flag to 'LIBCXX_LINK_FLAGS' if the
+# flag is supported by the C++ compiler.
+macro(add_link_flags_if_supported)
+  foreach(flag ${ARGN})
+    mangle_name("${flag}" flagname)
+    check_cxx_compiler_flag("${flag}" "LIBCXX_SUPPORTS_${flagname}_FLAG")
+    add_link_flags_if(LIBCXX_SUPPORTS_${flagname}_FLAG ${flag})
+  endforeach()
+endmacro()
+
+# Add a list of libraries or link flags to 'LIBCXX_LIBRARIES'.
+macro(add_library_flags)
+  foreach(lib ${ARGN})
+    list(APPEND LIBCXX_LIBRARIES ${lib})
+  endforeach()
+endmacro()
+
+# if 'condition' is true then add the specified list of libraries and flags
+# to 'LIBCXX_LIBRARIES'.
+macro(add_library_flags_if condition)
+  if(${condition})
+    add_library_flags(${ARGN})
+  endif()
+endmacro()
+
+# Turn a comma separated CMake list into a space separated string.
+macro(split_list listname)
+  string(REPLACE ";" " " ${listname} "${${listname}}")
+endmacro()
diff --git a/cmake/Modules/HandleOutOfTreeLLVM.cmake b/cmake/Modules/HandleOutOfTreeLLVM.cmake
new file mode 100644
index 0000000..bf629a9
--- /dev/null
+++ b/cmake/Modules/HandleOutOfTreeLLVM.cmake
@@ -0,0 +1,96 @@
+macro(find_llvm_parts)
+# Rely on llvm-config.
+  set(CONFIG_OUTPUT)
+  find_program(LLVM_CONFIG "llvm-config")
+  if(DEFINED LLVM_PATH)
+    set(LLVM_INCLUDE_DIR ${LLVM_INCLUDE_DIR} CACHE PATH "Path to llvm/include")
+    set(LLVM_PATH ${LLVM_PATH} CACHE PATH "Path to LLVM source tree")
+    set(LLVM_MAIN_SRC_DIR ${LLVM_PATH})
+    set(LLVM_CMAKE_PATH "${LLVM_PATH}/cmake/modules")
+  elseif(LLVM_CONFIG)
+    message(STATUS "Found LLVM_CONFIG as ${LLVM_CONFIG}")
+    set(CONFIG_COMMAND ${LLVM_CONFIG}
+      "--includedir"
+      "--prefix"
+      "--src-root")
+    execute_process(
+      COMMAND ${CONFIG_COMMAND}
+      RESULT_VARIABLE HAD_ERROR
+      OUTPUT_VARIABLE CONFIG_OUTPUT
+    )
+    if(NOT HAD_ERROR)
+      string(REGEX REPLACE
+        "[ \t]*[\r\n]+[ \t]*" ";"
+        CONFIG_OUTPUT ${CONFIG_OUTPUT})
+    else()
+      string(REPLACE ";" " " CONFIG_COMMAND_STR "${CONFIG_COMMAND}")
+      message(STATUS "${CONFIG_COMMAND_STR}")
+      message(FATAL_ERROR "llvm-config failed with status ${HAD_ERROR}")
+    endif()
+
+    list(GET CONFIG_OUTPUT 0 INCLUDE_DIR)
+    list(GET CONFIG_OUTPUT 1 LLVM_OBJ_ROOT)
+    list(GET CONFIG_OUTPUT 2 MAIN_SRC_DIR)
+
+    set(LLVM_INCLUDE_DIR ${INCLUDE_DIR} CACHE PATH "Path to llvm/include")
+    set(LLVM_BINARY_DIR ${LLVM_OBJ_ROOT} CACHE PATH "Path to LLVM build tree")
+    set(LLVM_MAIN_SRC_DIR ${MAIN_SRC_DIR} CACHE PATH "Path to LLVM source tree")
+    set(LLVM_CMAKE_PATH "${LLVM_BINARY_DIR}/share/llvm/cmake")
+  else()
+    set(LLVM_FOUND OFF)
+    return()
+  endif()
+
+  if (NOT EXISTS ${LLVM_MAIN_SRC_DIR})
+    message(FATAL_ERROR "Not found: ${LLVM_MAIN_SRC_DIR}")
+  endif()
+
+  if(NOT EXISTS ${LLVM_CMAKE_PATH})
+    message(FATAL_ERROR "Not found: ${LLVM_CMAKE_PATH}")
+  endif()
+
+  list(APPEND CMAKE_MODULE_PATH "${LLVM_CMAKE_PATH}")
+  list(APPEND CMAKE_MODULE_PATH "${LLVM_MAIN_SRC_DIR}/cmake/modules")
+
+  set(LLVM_FOUND ON)
+endmacro(find_llvm_parts)
+
+
+if (CMAKE_SOURCE_DIR STREQUAL CMAKE_CURRENT_SOURCE_DIR)
+  set(LIBCXX_BUILT_STANDALONE 1)
+  message(STATUS "Configuring for standalone build.")
+
+  find_llvm_parts()
+
+  # LLVM Options --------------------------------------------------------------
+  include(FindPythonInterp)
+  if( NOT PYTHONINTERP_FOUND )
+    message(WARNING "Failed to find python interpreter. "
+                    "The libc++ test suite will be disabled.")
+    set(LLVM_INCLUDE_TESTS OFF)
+  endif()
+
+  if (NOT DEFINED LLVM_INCLUDE_TESTS)
+    set(LLVM_INCLUDE_TESTS ${LLVM_FOUND})
+  endif()
+
+  # Required LIT Configuration ------------------------------------------------
+  # Define the default arguments to use with 'lit', and an option for the user
+  # to override.
+  set(LIT_ARGS_DEFAULT "-sv --show-xfail --show-unsupported")
+  if (MSVC OR XCODE)
+    set(LIT_ARGS_DEFAULT "${LIT_ARGS_DEFAULT} --no-progress-bar")
+  endif()
+  set(LLVM_LIT_ARGS "${LIT_ARGS_DEFAULT}" CACHE STRING "Default options for lit")
+
+  # Make sure we can use the console pool for recent cmake and ninja > 1.5
+  # Needed for add_lit_testsuite
+  if(CMAKE_VERSION VERSION_LESS 3.1.20141117)
+    set(cmake_3_2_USES_TERMINAL)
+  else()
+    set(cmake_3_2_USES_TERMINAL USES_TERMINAL)
+  endif()
+
+  # Add LLVM Functions --------------------------------------------------------
+  include(AddLLVM OPTIONAL)
+endif()
diff --git a/cmake/config-ix.cmake b/cmake/config-ix.cmake
index 428d737..ace7aca 100644
--- a/cmake/config-ix.cmake
+++ b/cmake/config-ix.cmake
@@ -2,23 +2,7 @@
 include(CheckCXXCompilerFlag)
 
 # Check compiler flags
-check_cxx_compiler_flag(-std=c++11              LIBCXX_HAS_STDCXX11_FLAG)
-check_cxx_compiler_flag(-std=c++1y              LIBCXX_HAS_STDCXX1Y_FLAG)
-check_cxx_compiler_flag(-fPIC                   LIBCXX_HAS_FPIC_FLAG)
-check_cxx_compiler_flag(-fno-omit-frame-pointer LIBCXX_HAS_FNO_OMIT_FRAME_POINTER_FLAG)
-check_cxx_compiler_flag(-nodefaultlibs          LIBCXX_HAS_NODEFAULTLIBS_FLAG)
-check_cxx_compiler_flag(-nostdinc++             LIBCXX_HAS_NOSTDINCXX_FLAG)
-check_cxx_compiler_flag(-Wall                   LIBCXX_HAS_WALL_FLAG)
-check_cxx_compiler_flag(-W                      LIBCXX_HAS_W_FLAG)
-check_cxx_compiler_flag(-Wno-unused-parameter   LIBCXX_HAS_WNO_UNUSED_PARAMETER_FLAG)
-check_cxx_compiler_flag(-Wwrite-strings         LIBCXX_HAS_WWRITE_STRINGS_FLAG)
-check_cxx_compiler_flag(-Wno-long-long          LIBCXX_HAS_WNO_LONG_LONG_FLAG)
-check_cxx_compiler_flag(-pedantic               LIBCXX_HAS_PEDANTIC_FLAG)
-check_cxx_compiler_flag(-Werror                 LIBCXX_HAS_WERROR_FLAG)
-check_cxx_compiler_flag(-Wno-error              LIBCXX_HAS_WNO_ERROR_FLAG)
-check_cxx_compiler_flag(-fno-exceptions         LIBCXX_HAS_FNO_EXCEPTIONS_FLAG)
-check_cxx_compiler_flag(-fno-rtti               LIBCXX_HAS_FNO_RTTI_FLAG)
-check_cxx_compiler_flag(-gline-tables-only      LIBCXX_HAS_GLINE_TABLES_ONLY_FLAG)
+
 check_cxx_compiler_flag(/WX                     LIBCXX_HAS_WX_FLAG)
 check_cxx_compiler_flag(/WX-                    LIBCXX_HAS_NO_WX_FLAG)
 check_cxx_compiler_flag(/EHsc                   LIBCXX_HAS_EHSC_FLAG)
@@ -26,6 +10,7 @@
 check_cxx_compiler_flag(/EHa-                   LIBCXX_HAS_NO_EHA_FLAG)
 check_cxx_compiler_flag(/GR-                    LIBCXX_HAS_NO_GR_FLAG)
 
+
 # Check libraries
 check_library_exists(pthread pthread_create "" LIBCXX_HAS_PTHREAD_LIB)
 check_library_exists(c printf "" LIBCXX_HAS_C_LIB)
diff --git a/include/__config b/include/__config
index d89025f..600f0fb 100644
--- a/include/__config
+++ b/include/__config
@@ -17,13 +17,11 @@
 
 #ifdef __GNUC__
 #define _GNUC_VER (__GNUC__ * 100 + __GNUC_MINOR__)
+#else
+#define _GNUC_VER 0
 #endif
 
-#if !_WIN32
-#include <unistd.h>
-#endif
-
-#define _LIBCPP_VERSION 1101
+#define _LIBCPP_VERSION 3800
 
 #define _LIBCPP_ABI_VERSION 1
 
@@ -32,6 +30,23 @@
 
 #define _LIBCPP_NAMESPACE _LIBCPP_CONCAT(__,_LIBCPP_ABI_VERSION)
 
+
+#ifndef __has_attribute
+#define __has_attribute(__x) 0
+#endif
+#ifndef __has_builtin
+#define __has_builtin(__x) 0
+#endif
+#ifndef __has_feature
+#define __has_feature(__x) 0
+#endif
+// '__is_identifier' returns '0' if '__x' is a reserved identifier provided by
+// the compiler and '1' otherwise.
+#ifndef __is_identifier
+#define __is_identifier(__x) 1
+#endif
+
+
 #ifdef __LITTLE_ENDIAN__
 #if __LITTLE_ENDIAN__
 #define _LIBCPP_LITTLE_ENDIAN 1
@@ -75,10 +90,8 @@
 #ifdef _WIN32
 #  define _LIBCPP_LITTLE_ENDIAN 1
 #  define _LIBCPP_BIG_ENDIAN    0
-// Compiler intrinsics (GCC or MSVC)
-#  if defined(__clang__) \
-   || (defined(_MSC_VER) && _MSC_VER >= 1400) \
-   || (defined(__GNUC__) && _GNUC_VER > 403)
+// Compiler intrinsics (MSVC)
+#if defined(_MSC_VER) && _MSC_VER >= 1400
 #    define _LIBCPP_HAS_IS_BASE_OF
 #  endif
 #  if defined(_MSC_VER) && !defined(__clang__)
@@ -93,12 +106,6 @@
 #  endif
 #endif  // _WIN32
 
-#ifdef __linux__
-#  if defined(__GNUC__) && _GNUC_VER >= 403
-#    define _LIBCPP_HAS_IS_BASE_OF
-#  endif
-#endif
-
 #ifdef __sun__
 # include <sys/isa_defs.h>
 # ifdef _LITTLE_ENDIAN
@@ -110,12 +117,22 @@
 # endif
 #endif // __sun__
 
-#if defined(__native_client__)
+#if defined(__CloudABI__)
+  // Certain architectures provide arc4random(). Prefer using
+  // arc4random() over /dev/{u,}random to make it possible to obtain
+  // random data even when using sandboxing mechanisms such as chroots,
+  // Capsicum, etc.
+# define _LIBCPP_USING_ARC4_RANDOM
+#elif defined(__native_client__)
   // NaCl's sandbox (which PNaCl also runs in) doesn't allow filesystem access,
   // including accesses to the special files under /dev. C++11's
   // std::random_device is instead exposed through a NaCl syscall.
 # define _LIBCPP_USING_NACL_RANDOM
-#endif // defined(__native_client__)
+#elif defined(_WIN32)
+# define _LIBCPP_USING_WIN32_RANDOM
+#else
+# define _LIBCPP_USING_DEV_RANDOM
+#endif
 
 #if !defined(_LIBCPP_LITTLE_ENDIAN) || !defined(_LIBCPP_BIG_ENDIAN)
 # include <endian.h>
@@ -172,10 +189,6 @@
 
 #endif // _WIN32
 
-#ifndef __has_attribute
-#define __has_attribute(__x) 0
-#endif
-
 #ifndef _LIBCPP_HIDDEN
 #define _LIBCPP_HIDDEN __attribute__ ((__visibility__("hidden")))
 #endif
@@ -308,6 +321,10 @@
 #  define _LIBCPP_HAS_IS_BASE_OF
 #endif
 
+#if __has_feature(is_final)
+#  define _LIBCPP_HAS_IS_FINAL
+#endif
+
 // Objective-C++ features (opt-in)
 #if __has_feature(objc_arc)
 #define _LIBCPP_HAS_OBJC_ARC
@@ -326,6 +343,10 @@
 #define _LIBCPP_HAS_NO_CXX14_CONSTEXPR
 #endif
 
+#if !(__has_feature(cxx_variable_templates))
+#define _LIBCPP_HAS_NO_VARIABLE_TEMPLATES
+#endif
+
 #if __ISO_C_VISIBLE >= 2011 || __cplusplus >= 201103L
 #if defined(__FreeBSD__)
 #define _LIBCPP_HAS_QUICK_EXIT
@@ -387,6 +408,11 @@
 #if _GNUC_VER >= 407
 #define _LIBCPP_UNDERLYING_TYPE(T) __underlying_type(T)
 #define _LIBCPP_IS_LITERAL(T) __is_literal_type(T)
+#define _LIBCPP_HAS_IS_FINAL
+#endif
+
+#if defined(__GNUC__) && _GNUC_VER >= 403
+#  define _LIBCPP_HAS_IS_BASE_OF
 #endif
 
 #if !__EXCEPTIONS
@@ -405,6 +431,8 @@
 
 // No version of GCC supports relaxed constexpr rules
 #define _LIBCPP_HAS_NO_CXX14_CONSTEXPR
+// GCC 5 will support variable templates
+#define _LIBCPP_HAS_NO_VARIABLE_TEMPLATES
 
 #define _NOEXCEPT throw()
 #define _NOEXCEPT_(x)
@@ -476,6 +504,7 @@
 #define _LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER
 #define _LIBCPP_HAS_NO_CONSTEXPR
 #define _LIBCPP_HAS_NO_CXX14_CONSTEXPR
+#define _LIBCPP_HAS_NO_VARIABLE_TEMPLATES
 #define _LIBCPP_HAS_NO_UNICODE_CHARS
 #define _LIBCPP_HAS_NO_DELETED_FUNCTIONS
 #define _LIBCPP_HAS_NO_DEFAULTED_FUNCTIONS
@@ -518,6 +547,8 @@
 #define _LIBCPP_HAS_NO_NULLPTR
 #define _LIBCPP_HAS_NO_UNICODE_CHARS
 #define _LIBCPP_HAS_IS_BASE_OF
+#define _LIBCPP_HAS_IS_FINAL
+#define _LIBCPP_HAS_NO_VARIABLE_TEMPLATES
 
 #if defined(_AIX)
 #define __MULTILOCALE_API
@@ -557,7 +588,12 @@
 #endif  // _LIBCPP_HAS_NO_STATIC_ASSERT
 
 #ifdef _LIBCPP_HAS_NO_DECLTYPE
-#define decltype(x) __typeof__(x)
+// GCC 4.6 provides __decltype in all standard modes.
+#if !__is_identifier(__decltype) || _GNUC_VER >= 406
+#  define decltype(__x) __decltype(__x)
+#else
+#  define decltype(__x) __typeof__(__x)
+#endif
 #endif
 
 #ifdef _LIBCPP_HAS_NO_CONSTEXPR
@@ -578,14 +614,6 @@
 #define _NOALIAS
 #endif
 
-#ifndef __has_feature
-#define __has_feature(__x) 0
-#endif
-
-#ifndef __has_builtin
-#define __has_builtin(__x) 0
-#endif
-
 #if __has_feature(cxx_explicit_conversions) || defined(__IBMCPP__)
 #   define _LIBCPP_EXPLICIT explicit
 #else
@@ -621,7 +649,7 @@
 #endif
 
 #ifndef _LIBCPP_EXTERN_TEMPLATE
-#define _LIBCPP_EXTERN_TEMPLATE(...)
+#define _LIBCPP_EXTERN_TEMPLATE(...) extern template __VA_ARGS__;
 #endif
 
 #ifndef _LIBCPP_EXTERN_TEMPLATE2
@@ -632,10 +660,16 @@
 #define _LIBCPP_NONUNIQUE_RTTI_BIT (1ULL << 63)
 #endif
 
-#if defined(__APPLE__) || defined(__FreeBSD__) || defined(_WIN32) || defined(__sun__) || defined(__NetBSD__)
+#if defined(__APPLE__) || defined(__FreeBSD__) || defined(_WIN32) || \
+    defined(__sun__) || defined(__NetBSD__) || defined(__CloudABI__)
 #define _LIBCPP_LOCALE__L_EXTENSIONS 1
 #endif
 
+#if !defined(_WIN32) && !defined(__ANDROID__) && !defined(_NEWLIB_VERSION) && \
+    !defined(__CloudABI__)
+#define _LIBCPP_HAS_CATOPEN 1
+#endif
+
 #ifdef __FreeBSD__
 #define _DECLARE_C99_LDBL_MATH 1
 #endif
@@ -708,8 +742,29 @@
          _LIBCPP_HAS_NO_THREADS is defined.
 #endif
 
-#if defined(__ANDROID__)
+// Systems that use capability-based security (FreeBSD with Capsicum,
+// Nuxi CloudABI) may only provide local filesystem access (using *at()).
+// Functions like open(), rename(), unlink() and stat() should not be
+// used, as they attempt to access the global filesystem namespace.
+#ifdef __CloudABI__
+#define _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
+#endif
+
+// CloudABI is intended for running networked services. Processes do not
+// have standard input and output channels.
+#ifdef __CloudABI__
+#define _LIBCPP_HAS_NO_STDIN
+#define _LIBCPP_HAS_NO_STDOUT
+#endif
+
+#if defined(__ANDROID__) || defined(__CloudABI__)
 #define _LIBCPP_PROVIDES_DEFAULT_RUNE_TABLE
 #endif
 
+// Thread-unsafe functions such as strtok(), mbtowc() and localtime()
+// are not available.
+#ifdef __CloudABI__
+#define _LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
+#endif
+
 #endif  // _LIBCPP_CONFIG
diff --git a/include/__debug b/include/__debug
index c151224..a21f9a8 100644
--- a/include/__debug
+++ b/include/__debug
@@ -22,7 +22,7 @@
 #   include <cstdio>
 #   include <cstddef>
 #   ifndef _LIBCPP_ASSERT
-#      define _LIBCPP_ASSERT(x, m) ((x) ? (void)0 : (_VSTD::printf("%s\n", m), _VSTD::abort()))
+#      define _LIBCPP_ASSERT(x, m) ((x) ? (void)0 : (_VSTD::fprintf(stderr, "%s\n", m), _VSTD::abort()))
 #   endif
 #endif
 
diff --git a/include/__functional_03 b/include/__functional_03
index 157d6bf..56a8475 100644
--- a/include/__functional_03
+++ b/include/__functional_03
@@ -17,218 +17,7 @@
 #pragma GCC system_header
 #endif
 
-template <class _Tp>
-class __mem_fn
-    : public __weak_result_type<_Tp>
-{
-public:
-    // types
-    typedef _Tp type;
-private:
-    type __f_;
-
-public:
-    _LIBCPP_INLINE_VISIBILITY __mem_fn(type __f) : __f_(__f) {}
-
-    // invoke
-
-    typename __invoke_return<type>::type
-       operator() () const
-       {
-           return __invoke(__f_);
-       }
-
-    template <class _A0>
-       typename __invoke_return0<type, _A0>::type
-          operator() (_A0& __a0) const
-          {
-              return __invoke(__f_, __a0);
-          }
-
-    template <class _A0, class _A1>
-       typename __invoke_return1<type, _A0, _A1>::type
-          operator() (_A0& __a0, _A1& __a1) const
-          {
-              return __invoke(__f_, __a0, __a1);
-          }
-
-    template <class _A0, class _A1, class _A2>
-       typename __invoke_return2<type, _A0, _A1, _A2>::type
-          operator() (_A0& __a0, _A1& __a1, _A2& __a2) const
-          {
-              return __invoke(__f_, __a0, __a1, __a2);
-          }
-};
-
-template<class _Rp, class _Tp>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp _Tp::*>
-mem_fn(_Rp _Tp::* __pm)
-{
-    return __mem_fn<_Rp _Tp::*>(__pm);
-}
-
-template<class _Rp, class _Tp>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)()>
-mem_fn(_Rp (_Tp::* __pm)())
-{
-    return __mem_fn<_Rp (_Tp::*)()>(__pm);
-}
-
-template<class _Rp, class _Tp, class _A0>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)(_A0)>
-mem_fn(_Rp (_Tp::* __pm)(_A0))
-{
-    return __mem_fn<_Rp (_Tp::*)(_A0)>(__pm);
-}
-
-template<class _Rp, class _Tp, class _A0, class _A1>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)(_A0, _A1)>
-mem_fn(_Rp (_Tp::* __pm)(_A0, _A1))
-{
-    return __mem_fn<_Rp (_Tp::*)(_A0, _A1)>(__pm);
-}
-
-template<class _Rp, class _Tp, class _A0, class _A1, class _A2>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)(_A0, _A1, _A2)>
-mem_fn(_Rp (_Tp::* __pm)(_A0, _A1, _A2))
-{
-    return __mem_fn<_Rp (_Tp::*)(_A0, _A1, _A2)>(__pm);
-}
-
-template<class _Rp, class _Tp>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)() const>
-mem_fn(_Rp (_Tp::* __pm)() const)
-{
-    return __mem_fn<_Rp (_Tp::*)() const>(__pm);
-}
-
-template<class _Rp, class _Tp, class _A0>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)(_A0) const>
-mem_fn(_Rp (_Tp::* __pm)(_A0) const)
-{
-    return __mem_fn<_Rp (_Tp::*)(_A0) const>(__pm);
-}
-
-template<class _Rp, class _Tp, class _A0, class _A1>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)(_A0, _A1) const>
-mem_fn(_Rp (_Tp::* __pm)(_A0, _A1) const)
-{
-    return __mem_fn<_Rp (_Tp::*)(_A0, _A1) const>(__pm);
-}
-
-template<class _Rp, class _Tp, class _A0, class _A1, class _A2>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)(_A0, _A1, _A2) const>
-mem_fn(_Rp (_Tp::* __pm)(_A0, _A1, _A2) const)
-{
-    return __mem_fn<_Rp (_Tp::*)(_A0, _A1, _A2) const>(__pm);
-}
-
-template<class _Rp, class _Tp>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)() volatile>
-mem_fn(_Rp (_Tp::* __pm)() volatile)
-{
-    return __mem_fn<_Rp (_Tp::*)() volatile>(__pm);
-}
-
-template<class _Rp, class _Tp, class _A0>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)(_A0) volatile>
-mem_fn(_Rp (_Tp::* __pm)(_A0) volatile)
-{
-    return __mem_fn<_Rp (_Tp::*)(_A0) volatile>(__pm);
-}
-
-template<class _Rp, class _Tp, class _A0, class _A1>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)(_A0, _A1) volatile>
-mem_fn(_Rp (_Tp::* __pm)(_A0, _A1) volatile)
-{
-    return __mem_fn<_Rp (_Tp::*)(_A0, _A1) volatile>(__pm);
-}
-
-template<class _Rp, class _Tp, class _A0, class _A1, class _A2>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)(_A0, _A1, _A2) volatile>
-mem_fn(_Rp (_Tp::* __pm)(_A0, _A1, _A2) volatile)
-{
-    return __mem_fn<_Rp (_Tp::*)(_A0, _A1, _A2) volatile>(__pm);
-}
-
-template<class _Rp, class _Tp>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)() const volatile>
-mem_fn(_Rp (_Tp::* __pm)() const volatile)
-{
-    return __mem_fn<_Rp (_Tp::*)() const volatile>(__pm);
-}
-
-template<class _Rp, class _Tp, class _A0>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)(_A0) const volatile>
-mem_fn(_Rp (_Tp::* __pm)(_A0) const volatile)
-{
-    return __mem_fn<_Rp (_Tp::*)(_A0) const volatile>(__pm);
-}
-
-template<class _Rp, class _Tp, class _A0, class _A1>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)(_A0, _A1) const volatile>
-mem_fn(_Rp (_Tp::* __pm)(_A0, _A1) const volatile)
-{
-    return __mem_fn<_Rp (_Tp::*)(_A0, _A1) const volatile>(__pm);
-}
-
-template<class _Rp, class _Tp, class _A0, class _A1, class _A2>
-inline _LIBCPP_INLINE_VISIBILITY
-__mem_fn<_Rp (_Tp::*)(_A0, _A1, _A2) const volatile>
-mem_fn(_Rp (_Tp::* __pm)(_A0, _A1, _A2) const volatile)
-{
-    return __mem_fn<_Rp (_Tp::*)(_A0, _A1, _A2) const volatile>(__pm);
-}
-
-// bad_function_call
-
-class _LIBCPP_EXCEPTION_ABI bad_function_call
-    : public exception
-{
-};
-
-template<class _Fp> class _LIBCPP_TYPE_VIS_ONLY function; // undefined
-
-namespace __function
-{
-
-template<class _Fp>
-struct __maybe_derive_from_unary_function
-{
-};
-
-template<class _Rp, class _A1>
-struct __maybe_derive_from_unary_function<_Rp(_A1)>
-    : public unary_function<_A1, _Rp>
-{
-};
-
-template<class _Fp>
-struct __maybe_derive_from_binary_function
-{
-};
-
-template<class _Rp, class _A1, class _A2>
-struct __maybe_derive_from_binary_function<_Rp(_A1, _A2)>
-    : public binary_function<_A1, _A2, _Rp>
-{
-};
+namespace __function {
 
 template<class _Fp> class __base;
 
@@ -333,7 +122,8 @@
 __base<_Rp()>*
 __func<_Fp, _Alloc, _Rp()>::__clone() const
 {
-    typedef typename _Alloc::template rebind<__func>::other _Ap;
+    typedef allocator_traits<_Alloc> __alloc_traits;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap;
     _Ap __a(__f_.second());
     typedef __allocator_destructor<_Ap> _Dp;
     unique_ptr<__func, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
@@ -359,7 +149,8 @@
 void
 __func<_Fp, _Alloc, _Rp()>::destroy_deallocate()
 {
-    typedef typename _Alloc::template rebind<__func>::other _Ap;
+    typedef allocator_traits<_Alloc> __alloc_traits;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap;
     _Ap __a(__f_.second());
     __f_.~__compressed_pair<_Fp, _Alloc>();
     __a.deallocate(this, 1);
@@ -417,7 +208,8 @@
 __base<_Rp(_A0)>*
 __func<_Fp, _Alloc, _Rp(_A0)>::__clone() const
 {
-    typedef typename _Alloc::template rebind<__func>::other _Ap;
+    typedef allocator_traits<_Alloc> __alloc_traits;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap;
     _Ap __a(__f_.second());
     typedef __allocator_destructor<_Ap> _Dp;
     unique_ptr<__func, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
@@ -443,7 +235,8 @@
 void
 __func<_Fp, _Alloc, _Rp(_A0)>::destroy_deallocate()
 {
-    typedef typename _Alloc::template rebind<__func>::other _Ap;
+    typedef allocator_traits<_Alloc> __alloc_traits;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap;
     _Ap __a(__f_.second());
     __f_.~__compressed_pair<_Fp, _Alloc>();
     __a.deallocate(this, 1);
@@ -501,7 +294,8 @@
 __base<_Rp(_A0, _A1)>*
 __func<_Fp, _Alloc, _Rp(_A0, _A1)>::__clone() const
 {
-    typedef typename _Alloc::template rebind<__func>::other _Ap;
+    typedef allocator_traits<_Alloc> __alloc_traits;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap;
     _Ap __a(__f_.second());
     typedef __allocator_destructor<_Ap> _Dp;
     unique_ptr<__func, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
@@ -527,7 +321,8 @@
 void
 __func<_Fp, _Alloc, _Rp(_A0, _A1)>::destroy_deallocate()
 {
-    typedef typename _Alloc::template rebind<__func>::other _Ap;
+    typedef allocator_traits<_Alloc> __alloc_traits;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap;
     _Ap __a(__f_.second());
     __f_.~__compressed_pair<_Fp, _Alloc>();
     __a.deallocate(this, 1);
@@ -585,7 +380,8 @@
 __base<_Rp(_A0, _A1, _A2)>*
 __func<_Fp, _Alloc, _Rp(_A0, _A1, _A2)>::__clone() const
 {
-    typedef typename _Alloc::template rebind<__func>::other _Ap;
+    typedef allocator_traits<_Alloc> __alloc_traits;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap;
     _Ap __a(__f_.second());
     typedef __allocator_destructor<_Ap> _Dp;
     unique_ptr<__func, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
@@ -611,7 +407,8 @@
 void
 __func<_Fp, _Alloc, _Rp(_A0, _A1, _A2)>::destroy_deallocate()
 {
-    typedef typename _Alloc::template rebind<__func>::other _Ap;
+    typedef allocator_traits<_Alloc> __alloc_traits;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap;
     _Ap __a(__f_.second());
     __f_.~__compressed_pair<_Fp, _Alloc>();
     __a.deallocate(this, 1);
@@ -794,17 +591,11 @@
         if (sizeof(_FF) <= sizeof(__buf_))
         {
             __f_ = (__base*)&__buf_;
-            ::new (__f_) _FF(__f);
+            ::new (__f_) _FF(__f, __a0);
         }
         else
         {
-            typedef typename __alloc_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-                rebind_alloc<_FF>
-#else
-                rebind_alloc<_FF>::other
-#endif
-                                                         _Ap;
+            typedef typename __rebind_alloc_helper<__alloc_traits, _FF>::type _Ap;
             _Ap __a(__a0);
             typedef __allocator_destructor<_Ap> _Dp;
             unique_ptr<__base, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
@@ -831,6 +622,7 @@
     else if (__f_)
         __f_->destroy_deallocate();
     __f_ = 0;
+    return *this;
 }
 
 template<class _Rp>
@@ -1096,17 +888,11 @@
         if (sizeof(_FF) <= sizeof(__buf_))
         {
             __f_ = (__base*)&__buf_;
-            ::new (__f_) _FF(__f);
+            ::new (__f_) _FF(__f, __a0);
         }
         else
         {
-            typedef typename __alloc_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-                rebind_alloc<_FF>
-#else
-                rebind_alloc<_FF>::other
-#endif
-                                                         _Ap;
+            typedef typename __rebind_alloc_helper<__alloc_traits, _FF>::type _Ap;
             _Ap __a(__a0);
             typedef __allocator_destructor<_Ap> _Dp;
             unique_ptr<__base, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
@@ -1133,6 +919,7 @@
     else if (__f_)
         __f_->destroy_deallocate();
     __f_ = 0;
+    return *this;
 }
 
 template<class _Rp, class _A0>
@@ -1398,17 +1185,11 @@
         if (sizeof(_FF) <= sizeof(__buf_))
         {
             __f_ = (__base*)&__buf_;
-            ::new (__f_) _FF(__f);
+            ::new (__f_) _FF(__f, __a0);
         }
         else
         {
-            typedef typename __alloc_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-                rebind_alloc<_FF>
-#else
-                rebind_alloc<_FF>::other
-#endif
-                                                         _Ap;
+            typedef typename __rebind_alloc_helper<__alloc_traits, _FF>::type _Ap;
             _Ap __a(__a0);
             typedef __allocator_destructor<_Ap> _Dp;
             unique_ptr<__base, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
@@ -1435,6 +1216,7 @@
     else if (__f_)
         __f_->destroy_deallocate();
     __f_ = 0;
+    return *this;
 }
 
 template<class _Rp, class _A0, class _A1>
@@ -1700,17 +1482,11 @@
         if (sizeof(_FF) <= sizeof(__buf_))
         {
             __f_ = (__base*)&__buf_;
-            ::new (__f_) _FF(__f);
+            ::new (__f_) _FF(__f, __a0);
         }
         else
         {
-            typedef typename __alloc_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-                rebind_alloc<_FF>
-#else
-                rebind_alloc<_FF>::other
-#endif
-                                                         _Ap;
+            typedef typename __rebind_alloc_helper<__alloc_traits, _FF>::type _Ap;
             _Ap __a(__a0);
             typedef __allocator_destructor<_Ap> _Dp;
             unique_ptr<__base, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
@@ -1737,6 +1513,7 @@
     else if (__f_)
         __f_->destroy_deallocate();
     __f_ = 0;
+    return *this;
 }
 
 template<class _Rp, class _A0, class _A1, class _A2>
@@ -1868,272 +1645,4 @@
 swap(function<_Fp>& __x, function<_Fp>& __y)
 {return __x.swap(__y);}
 
-template<class _Tp> struct __is_bind_expression : public false_type {};
-template<class _Tp> struct _LIBCPP_TYPE_VIS_ONLY is_bind_expression
-    : public __is_bind_expression<typename remove_cv<_Tp>::type> {};
-
-template<class _Tp> struct __is_placeholder : public integral_constant<int, 0> {};
-template<class _Tp> struct _LIBCPP_TYPE_VIS_ONLY is_placeholder
-    : public __is_placeholder<typename remove_cv<_Tp>::type> {};
-
-namespace placeholders
-{
-
-template <int _Np> struct __ph {};
-
-extern __ph<1>   _1;
-extern __ph<2>   _2;
-extern __ph<3>   _3;
-extern __ph<4>   _4;
-extern __ph<5>   _5;
-extern __ph<6>   _6;
-extern __ph<7>   _7;
-extern __ph<8>   _8;
-extern __ph<9>   _9;
-extern __ph<10> _10;
-
-}  // placeholders
-
-template<int _Np>
-struct __is_placeholder<placeholders::__ph<_Np> >
-    : public integral_constant<int, _Np> {};
-
-template <class _Tp, class _Uj>
-inline _LIBCPP_INLINE_VISIBILITY
-_Tp&
-__mu(reference_wrapper<_Tp> __t, _Uj&)
-{
-    return __t.get();
-}
-/*
-template <bool _IsBindExpr, class _Ti, class ..._Uj>
-struct __mu_return1 {};
-
-template <class _Ti, class ..._Uj>
-struct __mu_return1<true, _Ti, _Uj...>
-{
-    typedef typename result_of<_Ti(_Uj...)>::type type;
-};
-
-template <class _Ti, class ..._Uj, size_t ..._Indx>
-inline _LIBCPP_INLINE_VISIBILITY
-typename __mu_return1<true, _Ti, _Uj...>::type
-__mu_expand(_Ti& __ti, tuple<_Uj...>&& __uj, __tuple_indices<_Indx...>)
-{
-    __ti(_VSTD::forward<typename tuple_element<_Indx, _Uj>::type>(_VSTD::get<_Indx>(__uj))...);
-}
-
-template <class _Ti, class ..._Uj>
-inline _LIBCPP_INLINE_VISIBILITY
-typename enable_if
-<
-    is_bind_expression<_Ti>::value,
-    typename __mu_return1<is_bind_expression<_Ti>::value, _Ti, _Uj...>::type
->::type
-__mu(_Ti& __ti, tuple<_Uj...>& __uj)
-{
-    typedef typename __make_tuple_indices<sizeof...(_Uj)>::type __indices;
-    return  __mu_expand(__ti, __uj, __indices());
-}
-
-template <bool IsPh, class _Ti, class _Uj>
-struct __mu_return2 {};
-
-template <class _Ti, class _Uj>
-struct __mu_return2<true, _Ti, _Uj>
-{
-    typedef typename tuple_element<is_placeholder<_Ti>::value - 1, _Uj>::type type;
-};
-
-template <class _Ti, class _Uj>
-inline _LIBCPP_INLINE_VISIBILITY
-typename enable_if
-<
-    0 < is_placeholder<_Ti>::value,
-    typename __mu_return2<0 < is_placeholder<_Ti>::value, _Ti, _Uj>::type
->::type
-__mu(_Ti&, _Uj& __uj)
-{
-    const size_t _Indx = is_placeholder<_Ti>::value - 1;
-    // compiler bug workaround
-    typename tuple_element<_Indx, _Uj>::type __t = _VSTD::get<_Indx>(__uj);
-    return __t;
-//    return _VSTD::forward<typename tuple_element<_Indx, _Uj>::type>(_VSTD::get<_Indx>(__uj));
-}
-
-template <class _Ti, class _Uj>
-inline _LIBCPP_INLINE_VISIBILITY
-typename enable_if
-<
-    !is_bind_expression<_Ti>::value &&
-    is_placeholder<_Ti>::value == 0 &&
-    !__is_reference_wrapper<_Ti>::value,
-    _Ti&
->::type
-__mu(_Ti& __ti, _Uj& __uj)
-{
-    return __ti;
-}
-
-template <class _Ti, bool IsBindEx, bool IsPh, class _TupleUj>
-struct ____mu_return;
-
-template <class _Ti, class ..._Uj>
-struct ____mu_return<_Ti, true, false, tuple<_Uj...> >
-{
-    typedef typename result_of<_Ti(_Uj...)>::type type;
-};
-
-template <class _Ti, class _TupleUj>
-struct ____mu_return<_Ti, false, true, _TupleUj>
-{
-    typedef typename tuple_element<is_placeholder<_Ti>::value - 1,
-                                   _TupleUj>::type&& type;
-};
-
-template <class _Ti, class _TupleUj>
-struct ____mu_return<_Ti, false, false, _TupleUj>
-{
-    typedef _Ti& type;
-};
-
-template <class _Ti, class _TupleUj>
-struct __mu_return
-    : public ____mu_return<_Ti,
-                           is_bind_expression<_Ti>::value,
-                           0 < is_placeholder<_Ti>::value,
-                           _TupleUj>
-{
-};
-
-template <class _Ti, class _TupleUj>
-struct __mu_return<reference_wrapper<_Ti>, _TupleUj>
-{
-    typedef _Ti& type;
-};
-
-template <class _Fp, class _BoundArgs, class _TupleUj>
-struct __bind_return;
-
-template <class _Fp, class ..._BoundArgs, class _TupleUj>
-struct __bind_return<_Fp, tuple<_BoundArgs...>, _TupleUj>
-{
-    typedef typename __ref_return
-    <
-        _Fp&,
-        typename __mu_return
-        <
-            _BoundArgs,
-            _TupleUj
-        >::type...
-    >::type type;
-};
-
-template <class _Fp, class ..._BoundArgs, class _TupleUj>
-struct __bind_return<_Fp, const tuple<_BoundArgs...>, _TupleUj>
-{
-    typedef typename __ref_return
-    <
-        _Fp&,
-        typename __mu_return
-        <
-            const _BoundArgs,
-            _TupleUj
-        >::type...
-    >::type type;
-};
-
-template <class _Fp, class _BoundArgs, size_t ..._Indx, class _Args>
-inline _LIBCPP_INLINE_VISIBILITY
-typename __bind_return<_Fp, _BoundArgs, _Args>::type
-__apply_functor(_Fp& __f, _BoundArgs& __bound_args, __tuple_indices<_Indx...>,
-                _Args&& __args)
-{
-    return __invoke(__f, __mu(_VSTD::get<_Indx>(__bound_args), __args)...);
-}
-
-template<class _Fp, class ..._BoundArgs>
-class __bind
-{
-    _Fp __f_;
-    tuple<_BoundArgs...> __bound_args_;
-
-    typedef typename __make_tuple_indices<sizeof...(_BoundArgs)>::type __indices;
-public:
-    template <class _Gp, class ..._BA>
-      explicit __bind(_Gp&& __f, _BA&& ...__bound_args)
-        : __f_(_VSTD::forward<_Gp>(__f)),
-          __bound_args_(_VSTD::forward<_BA>(__bound_args)...) {}
-
-    template <class ..._Args>
-        typename __bind_return<_Fp, tuple<_BoundArgs...>, tuple<_Args&&...> >::type
-        operator()(_Args&& ...__args)
-        {
-            // compiler bug workaround
-            return __apply_functor(__f_, __bound_args_, __indices(),
-                                  tuple<_Args&&...>(__args...));
-        }
-
-    template <class ..._Args>
-        typename __bind_return<_Fp, tuple<_BoundArgs...>, tuple<_Args&&...> >::type
-        operator()(_Args&& ...__args) const
-        {
-            return __apply_functor(__f_, __bound_args_, __indices(),
-                                   tuple<_Args&&...>(__args...));
-        }
-};
-
-template<class _Fp, class ..._BoundArgs>
-struct __is_bind_expression<__bind<_Fp, _BoundArgs...> > : public true_type {};
-
-template<class _Rp, class _Fp, class ..._BoundArgs>
-class __bind_r
-    : public __bind<_Fp, _BoundArgs...>
-{
-    typedef __bind<_Fp, _BoundArgs...> base;
-public:
-    typedef _Rp result_type;
-
-    template <class _Gp, class ..._BA>
-      explicit __bind_r(_Gp&& __f, _BA&& ...__bound_args)
-        : base(_VSTD::forward<_Gp>(__f),
-               _VSTD::forward<_BA>(__bound_args)...) {}
-
-    template <class ..._Args>
-        result_type
-        operator()(_Args&& ...__args)
-        {
-            return base::operator()(_VSTD::forward<_Args>(__args)...);
-        }
-
-    template <class ..._Args>
-        result_type
-        operator()(_Args&& ...__args) const
-        {
-            return base::operator()(_VSTD::forward<_Args>(__args)...);
-        }
-};
-
-template<class _Rp, class _Fp, class ..._BoundArgs>
-struct __is_bind_expression<__bind_r<_Rp, _Fp, _BoundArgs...> > : public true_type {};
-
-template<class _Fp, class ..._BoundArgs>
-inline _LIBCPP_INLINE_VISIBILITY
-__bind<typename decay<_Fp>::type, typename decay<_BoundArgs>::type...>
-bind(_Fp&& __f, _BoundArgs&&... __bound_args)
-{
-    typedef __bind<typename decay<_Fp>::type, typename decay<_BoundArgs>::type...> type;
-    return type(_VSTD::forward<_Fp>(__f), _VSTD::forward<_BoundArgs>(__bound_args)...);
-}
-
-template<class _Rp, class _Fp, class ..._BoundArgs>
-inline _LIBCPP_INLINE_VISIBILITY
-__bind_r<_Rp, typename decay<_Fp>::type, typename decay<_BoundArgs>::type...>
-bind(_Fp&& __f, _BoundArgs&&... __bound_args)
-{
-    typedef __bind_r<_Rp, typename decay<_Fp>::type, typename decay<_BoundArgs>::type...> type;
-    return type(_VSTD::forward<_Fp>(__f), _VSTD::forward<_BoundArgs>(__bound_args)...);
-}
-*/
-
 #endif  // _LIBCPP_FUNCTIONAL_03
diff --git a/include/__functional_base b/include/__functional_base
index 09424bc..3ff2e35 100644
--- a/include/__functional_base
+++ b/include/__functional_base
@@ -127,11 +127,6 @@
 }
 #endif
 
-#ifdef _LIBCPP_HAS_NO_VARIADICS
-
-#include <__functional_base_03>
-
-#else  // _LIBCPP_HAS_NO_VARIADICS
 
 // __weak_result_type
 
@@ -314,6 +309,8 @@
 {
 };
 
+
+#ifndef _LIBCPP_HAS_NO_VARIADICS
 // 3 or more arguments
 
 template <class _Rp, class _A1, class _A2, class _A3, class ..._A4>
@@ -358,8 +355,12 @@
     typedef _Rp result_type;
 };
 
+#endif // _LIBCPP_HAS_NO_VARIADICS
+
 // __invoke
 
+#ifndef _LIBCPP_HAS_NO_VARIADICS
+
 // bullets 1 and 2
 
 template <class _Fp, class _A0, class ..._Args,
@@ -414,31 +415,79 @@
 {
     return _VSTD::forward<_Fp>(__f)(_VSTD::forward<_Args>(__args)...);
 }
-
 template <class _Tp, class ..._Args>
 struct __invoke_return
 {
     typedef decltype(__invoke(_VSTD::declval<_Tp>(), _VSTD::declval<_Args>()...)) type;
 };
 
+#else // _LIBCPP_HAS_NO_VARIADICS
+
+#include <__functional_base_03>
+
+#endif  // _LIBCPP_HAS_NO_VARIADICS
+
+
 template <class _Ret>
 struct __invoke_void_return_wrapper
 {
+#ifndef _LIBCPP_HAS_NO_VARIADICS
     template <class ..._Args>
-    static _Ret __call(_Args&&... __args)
-    {
+    static _Ret __call(_Args&&... __args) {
         return __invoke(_VSTD::forward<_Args>(__args)...);
     }
+#else
+    template <class _Fn>
+    static _Ret __call(_Fn __f) {
+        return __invoke(__f);
+    }
+
+    template <class _Fn, class _A0>
+    static _Ret __call(_Fn __f, _A0& __a0) {
+        return __invoke(__f, __a0);
+    }
+
+    template <class _Fn, class _A0, class _A1>
+    static _Ret __call(_Fn __f, _A0& __a0, _A1& __a1) {
+        return __invoke(__f, __a0, __a1);
+    }
+
+    template <class _Fn, class _A0, class _A1, class _A2>
+    static _Ret __call(_Fn __f, _A0& __a0, _A1& __a1, _A2& __a2){
+        return __invoke(__f, __a0, __a1, __a2);
+    }
+#endif
 };
 
 template <>
 struct __invoke_void_return_wrapper<void>
 {
+#ifndef _LIBCPP_HAS_NO_VARIADICS
     template <class ..._Args>
-    static void __call(_Args&&... __args)
-    {
+    static void __call(_Args&&... __args) {
         __invoke(_VSTD::forward<_Args>(__args)...);
     }
+#else
+    template <class _Fn>
+    static void __call(_Fn __f) {
+        __invoke(__f);
+    }
+
+    template <class _Fn, class _A0>
+    static void __call(_Fn __f, _A0& __a0) {
+        __invoke(__f, __a0);
+    }
+
+    template <class _Fn, class _A0, class _A1>
+    static void __call(_Fn __f, _A0& __a0, _A1& __a1) {
+        __invoke(__f, __a0, __a1);
+    }
+
+    template <class _Fn, class _A0, class _A1, class _A2>
+    static void __call(_Fn __f, _A0& __a0, _A1& __a1, _A2& __a2) {
+        __invoke(__f, __a0, __a1, __a2);
+    }
+#endif
 };
 
 template <class _Tp>
@@ -463,6 +512,7 @@
     _LIBCPP_INLINE_VISIBILITY operator type&    () const _NOEXCEPT {return *__f_;}
     _LIBCPP_INLINE_VISIBILITY          type& get() const _NOEXCEPT {return *__f_;}
 
+#ifndef _LIBCPP_HAS_NO_VARIADICS
     // invoke
     template <class... _ArgTypes>
        _LIBCPP_INLINE_VISIBILITY
@@ -471,6 +521,39 @@
           {
               return __invoke(get(), _VSTD::forward<_ArgTypes>(__args)...);
           }
+#else
+
+    _LIBCPP_INLINE_VISIBILITY
+    typename __invoke_return<type>::type
+       operator() () const
+       {
+           return __invoke(get());
+       }
+
+    template <class _A0>
+       _LIBCPP_INLINE_VISIBILITY
+       typename __invoke_return0<type&, _A0>::type
+          operator() (_A0& __a0) const
+          {
+              return __invoke<type&, _A0>(get(), __a0);
+          }
+
+    template <class _A0, class _A1>
+       _LIBCPP_INLINE_VISIBILITY
+       typename __invoke_return1<type&, _A0, _A1>::type
+          operator() (_A0& __a0, _A1& __a1) const
+          {
+              return __invoke<type&, _A0, _A1>(get(), __a0, __a1);
+          }
+
+    template <class _A0, class _A1, class _A2>
+       _LIBCPP_INLINE_VISIBILITY
+       typename __invoke_return2<type&, _A0, _A1, _A2>::type
+          operator() (_A0& __a0, _A1& __a1, _A2& __a2) const
+          {
+              return __invoke<type&, _A0, _A1, _A2>(get(), __a0, __a1, __a2);
+          }
+#endif // _LIBCPP_HAS_NO_VARIADICS
 };
 
 template <class _Tp> struct __is_reference_wrapper_impl : public false_type {};
@@ -510,6 +593,7 @@
     return cref(__t.get());
 }
 
+#ifndef _LIBCPP_HAS_NO_VARIADICS
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 #ifndef _LIBCPP_HAS_NO_DELETED_FUNCTIONS
 
diff --git a/include/__functional_base_03 b/include/__functional_base_03
index 6550277..0a7ff62 100644
--- a/include/__functional_base_03
+++ b/include/__functional_base_03
@@ -13,404 +13,7 @@
 
 // manual variadic expansion for <functional>
 
-// __weak_result_type
-
-template <class _Tp>
-struct __derives_from_unary_function
-{
-private:
-    struct __two {char __lx; char __lxx;};
-    static __two __test(...);
-    template <class _Ap, class _Rp>
-        static unary_function<_Ap, _Rp>
-        __test(const volatile unary_function<_Ap, _Rp>*);
-public:
-    static const bool value = !is_same<decltype(__test((_Tp*)0)), __two>::value;
-    typedef decltype(__test((_Tp*)0)) type;
-};
-
-template <class _Tp>
-struct __derives_from_binary_function
-{
-private:
-    struct __two {char __lx; char __lxx;};
-    static __two __test(...);
-    template <class _A1, class _A2, class _Rp>
-        static binary_function<_A1, _A2, _Rp>
-        __test(const volatile binary_function<_A1, _A2, _Rp>*);
-public:
-    static const bool value = !is_same<decltype(__test((_Tp*)0)), __two>::value;
-    typedef decltype(__test((_Tp*)0)) type;
-};
-
-template <class _Tp, bool = __derives_from_unary_function<_Tp>::value>
-struct __maybe_derive_from_unary_function  // bool is true
-    : public __derives_from_unary_function<_Tp>::type
-{
-};
-
-template <class _Tp>
-struct __maybe_derive_from_unary_function<_Tp, false>
-{
-};
-
-template <class _Tp, bool = __derives_from_binary_function<_Tp>::value>
-struct __maybe_derive_from_binary_function  // bool is true
-    : public __derives_from_binary_function<_Tp>::type
-{
-};
-
-template <class _Tp>
-struct __maybe_derive_from_binary_function<_Tp, false>
-{
-};
-
-template <class _Tp, bool = __has_result_type<_Tp>::value>
-struct __weak_result_type_imp // bool is true
-    : public __maybe_derive_from_unary_function<_Tp>,
-      public __maybe_derive_from_binary_function<_Tp>
-{
-    typedef typename _Tp::result_type result_type;
-};
-
-template <class _Tp>
-struct __weak_result_type_imp<_Tp, false>
-    : public __maybe_derive_from_unary_function<_Tp>,
-      public __maybe_derive_from_binary_function<_Tp>
-{
-};
-
-template <class _Tp>
-struct __weak_result_type
-    : public __weak_result_type_imp<typename remove_reference<_Tp>::type>
-{
-};
-
-// 0 argument case
-
-template <class _Rp>
-struct __weak_result_type<_Rp ()>
-{
-    typedef _Rp result_type;
-};
-
-template <class _Rp>
-struct __weak_result_type<_Rp (&)()>
-{
-    typedef _Rp result_type;
-};
-
-template <class _Rp>
-struct __weak_result_type<_Rp (*)()>
-{
-    typedef _Rp result_type;
-};
-
-// 1 argument case
-
-template <class _Rp, class _A1>
-struct __weak_result_type<_Rp (_A1)>
-    : public unary_function<_A1, _Rp>
-{
-};
-
-template <class _Rp, class _A1>
-struct __weak_result_type<_Rp (&)(_A1)>
-    : public unary_function<_A1, _Rp>
-{
-};
-
-template <class _Rp, class _A1>
-struct __weak_result_type<_Rp (*)(_A1)>
-    : public unary_function<_A1, _Rp>
-{
-};
-
-template <class _Rp, class _Cp>
-struct __weak_result_type<_Rp (_Cp::*)()>
-    : public unary_function<_Cp*, _Rp>
-{
-};
-
-template <class _Rp, class _Cp>
-struct __weak_result_type<_Rp (_Cp::*)() const>
-    : public unary_function<const _Cp*, _Rp>
-{
-};
-
-template <class _Rp, class _Cp>
-struct __weak_result_type<_Rp (_Cp::*)() volatile>
-    : public unary_function<volatile _Cp*, _Rp>
-{
-};
-
-template <class _Rp, class _Cp>
-struct __weak_result_type<_Rp (_Cp::*)() const volatile>
-    : public unary_function<const volatile _Cp*, _Rp>
-{
-};
-
-// 2 argument case
-
-template <class _Rp, class _A1, class _A2>
-struct __weak_result_type<_Rp (_A1, _A2)>
-    : public binary_function<_A1, _A2, _Rp>
-{
-};
-
-template <class _Rp, class _A1, class _A2>
-struct __weak_result_type<_Rp (*)(_A1, _A2)>
-    : public binary_function<_A1, _A2, _Rp>
-{
-};
-
-template <class _Rp, class _A1, class _A2>
-struct __weak_result_type<_Rp (&)(_A1, _A2)>
-    : public binary_function<_A1, _A2, _Rp>
-{
-};
-
-template <class _Rp, class _Cp, class _A1>
-struct __weak_result_type<_Rp (_Cp::*)(_A1)>
-    : public binary_function<_Cp*, _A1, _Rp>
-{
-};
-
-template <class _Rp, class _Cp, class _A1>
-struct __weak_result_type<_Rp (_Cp::*)(_A1) const>
-    : public binary_function<const _Cp*, _A1, _Rp>
-{
-};
-
-template <class _Rp, class _Cp, class _A1>
-struct __weak_result_type<_Rp (_Cp::*)(_A1) volatile>
-    : public binary_function<volatile _Cp*, _A1, _Rp>
-{
-};
-
-template <class _Rp, class _Cp, class _A1>
-struct __weak_result_type<_Rp (_Cp::*)(_A1) const volatile>
-    : public binary_function<const volatile _Cp*, _A1, _Rp>
-{
-};
-
-// 3 or more arguments
-
-template <class _Rp, class _A1, class _A2, class _A3>
-struct __weak_result_type<_Rp (_A1, _A2, _A3)>
-{
-    typedef _Rp result_type;
-};
-
-template <class _Rp, class _A1, class _A2, class _A3>
-struct __weak_result_type<_Rp (&)(_A1, _A2, _A3)>
-{
-    typedef _Rp result_type;
-};
-
-template <class _Rp, class _A1, class _A2, class _A3>
-struct __weak_result_type<_Rp (*)(_A1, _A2, _A3)>
-{
-    typedef _Rp result_type;
-};
-
-template <class _Rp, class _Cp, class _A1, class _A2>
-struct __weak_result_type<_Rp (_Cp::*)(_A1, _A2)>
-{
-    typedef _Rp result_type;
-};
-
-template <class _Rp, class _Cp, class _A1, class _A2>
-struct __weak_result_type<_Rp (_Cp::*)(_A1, _A2) const>
-{
-    typedef _Rp result_type;
-};
-
-template <class _Rp, class _Cp, class _A1, class _A2>
-struct __weak_result_type<_Rp (_Cp::*)(_A1, _A2) volatile>
-{
-    typedef _Rp result_type;
-};
-
 // __invoke
-
-// __ref_return0
-//
-// template <class _Tp, bool _HasResultType>
-// struct ________ref_return0  // _HasResultType is true
-// {
-//     typedef typename _Tp::result_type type;
-// };
-//
-// template <class _Tp>
-// struct ________ref_return0<_Tp, false>
-// {
-//     typedef void type;
-// };
-//
-// template <class _Tp, bool _IsClass>
-// struct ____ref_return0  // _IsClass is true
-//     : public ________ref_return0<_Tp, __has_result_type<typename remove_cv<_Tp>::type>::value>
-// {
-// };
-//
-// template <class _Tp, bool _HasResultType>
-// struct ______ref_return0  // _HasResultType is true
-// {
-//     typedef typename __callable_type<_Tp>::result_type type;
-// };
-//
-// template <class _Tp>
-// struct ______ref_return0<_Tp, false>  // pointer to member data
-// {
-//     typedef void type;
-// };
-//
-// template <class _Tp>
-// struct ____ref_return0<_Tp, false>
-//     : public ______ref_return0<typename remove_cv<_Tp>::type,
-//                  __has_result_type<__callable_type<typename remove_cv<_Tp>::type> >::value>
-// {
-// };
-//
-// template <class _Tp>
-// struct __ref_return0
-//     : public ____ref_return0<typename remove_reference<_Tp>::type,
-//                    is_class<typename remove_reference<_Tp>::type>::value>
-// {
-// };
-//
-// __ref_return1
-//
-// template <class _Tp, bool _IsClass, class _A0>
-// struct ____ref_return1  // _IsClass is true
-// {
-//     typedef typename result_of<_Tp(_A0)>::type type;
-// };
-//
-// template <class _Tp, bool _HasResultType, class _A0>
-// struct ______ref_return1  // _HasResultType is true
-// {
-//     typedef typename __callable_type<_Tp>::result_type type;
-// };
-//
-// template <class _Tp, class _A0, bool>
-// struct __ref_return1_member_data1;
-//
-// template <class _Rp, class _Cp, class _A0>
-// struct __ref_return1_member_data1<_Rp _Cp::*, _A0, true>
-// {
-//     typedef typename __apply_cv<_A0, _Rp>::type& type;
-// };
-//
-// template <class _Rp, class _Cp, class _A0>
-// struct __ref_return1_member_data1<_Rp _Cp::*, _A0, false>
-// {
-//     static _A0 __a;
-//     typedef typename __apply_cv<decltype(*__a), _Rp>::type& type;
-// };
-//
-// template <class _Tp, class _A0>
-// struct __ref_return1_member_data;
-//
-// template <class _Rp, class _Cp, class _A0>
-// struct __ref_return1_member_data<_Rp _Cp::*, _A0>
-//     : public __ref_return1_member_data1<_Rp _Cp::*, _A0,
-//                 is_same<typename remove_cv<_Cp>::type,
-//                         typename remove_cv<typename remove_reference<_A0>::type>::type>::value>
-// {
-// };
-//
-// template <class _Tp, class _A0>
-// struct ______ref_return1<_Tp, false, _A0>  // pointer to member data
-//     : public __ref_return1_member_data<typename remove_cv<_Tp>::type, _A0>
-// {
-// };
-//
-// template <class _Tp, class _A0>
-// struct ____ref_return1<_Tp, false, _A0>
-//     : public ______ref_return1<typename remove_cv<_Tp>::type,
-//                  __has_result_type<__callable_type<typename remove_cv<_Tp>::type> >::value, _A0>
-// {
-// };
-//
-// template <class _Tp, class _A0>
-// struct __ref_return1
-//     : public ____ref_return1<typename remove_reference<_Tp>::type,
-//                    is_class<typename remove_reference<_Tp>::type>::value, _A0>
-// {
-// };
-//
-// __ref_return2
-//
-// template <class _Tp, bool _IsClass, class _A0, class _A1>
-// struct ____ref_return2  // _IsClass is true
-// {
-//     typedef typename result_of<_Tp(_A0, _A1)>::type type;
-// };
-//
-// template <class _Tp, bool _HasResultType, class _A0, class _A1>
-// struct ______ref_return2  // _HasResultType is true
-// {
-//     typedef typename __callable_type<_Tp>::result_type type;
-// };
-//
-// template <class _Tp>
-// struct ______ref_return2<_Tp, false, class _A0, class _A1>  // pointer to member data
-// {
-//     static_assert(sizeof(_Tp) == 0, "An attempt has been made to `call` a pointer"
-//                          " to member data with too many arguments.");
-// };
-//
-// template <class _Tp, class _A0, class _A1>
-// struct ____ref_return2<_Tp, false, _A0, _A1>
-//     : public ______ref_return2<typename remove_cv<_Tp>::type,
-//                  __has_result_type<__callable_type<typename remove_cv<_Tp>::type> >::value, _A0, _A1>
-// {
-// };
-//
-// template <class _Tp, class _A0, class _A1>
-// struct __ref_return2
-//     : public ____ref_return2<typename remove_reference<_Tp>::type,
-//                    is_class<typename remove_reference<_Tp>::type>::value, _A0, _A1>
-// {
-// };
-//
-// __ref_return3
-//
-// template <class _Tp, bool _IsClass, class _A0, class _A1, class _A2>
-// struct ____ref_return3  // _IsClass is true
-// {
-//     typedef typename result_of<_Tp(_A0, _A1, _A2)>::type type;
-// };
-//
-// template <class _Tp, bool _HasResultType, class _A0, class _A1, class _A2>
-// struct ______ref_return3  // _HasResultType is true
-// {
-//     typedef typename __callable_type<_Tp>::result_type type;
-// };
-//
-// template <class _Tp>
-// struct ______ref_return3<_Tp, false, class _A0, class _A1, class _A2>  // pointer to member data
-// {
-//     static_assert(sizeof(_Tp) == 0, "An attempt has been made to `call` a pointer"
-//                          " to member data with too many arguments.");
-// };
-//
-// template <class _Tp, class _A0, class _A1, class _A2>
-// struct ____ref_return3<_Tp, false, _A0, _A1, _A2>
-//     : public ______ref_return3<typename remove_cv<_Tp>::type,
-//                  __has_result_type<__callable_type<typename remove_cv<_Tp>::type> >::value, _A0, _A1, _A2>
-// {
-// };
-//
-// template <class _Tp, class _A0, class _A1, class _A2>
-// struct __ref_return3
-//     : public ____ref_return3<typename remove_reference<_Tp>::type,
-//                    is_class<typename remove_reference<_Tp>::type>::value, _A0, _A1, _A2>
-// {
-// };
-
 // first bullet
 
 template <class _Rp, class _Tp, class _T1>
@@ -805,32 +408,15 @@
 inline _LIBCPP_INLINE_VISIBILITY
 typename enable_if
 <
+    is_member_object_pointer<_Rp _Tp::*>::value &&
     is_base_of<_Tp, typename remove_reference<_T1>::type>::value,
-    typename __apply_cv<_T1, _Rp>::type&
->::type
+   __apply_cv<_T1, _Rp>
+>::type::type&
 __invoke(_Rp _Tp::* __f, _T1& __t1)
 {
     return __t1.*__f;
 }
 
-template <class _Rp, class _Tp>
-inline _LIBCPP_INLINE_VISIBILITY
-void
-__invoke(_Rp _Tp::*)
-{
-}
-
-// template <class _Dp, class _Rp, class _Tp, class _T1>
-// inline _LIBCPP_INLINE_VISIBILITY
-// typename enable_if
-// <
-//     is_base_of<_Tp, typename remove_reference<_T1>::type>::value,
-//     typename __ref_return1<_Rp _Tp::*, _T1>::type
-// >::type
-// __invoke(_Rp _Tp::* __f, _T1& __t1)
-// {
-//     return __t1.*__f;
-// }
 
 // forth bullet
 
@@ -842,114 +428,54 @@
 template <class _T1, class _Rp>
 struct __4th_helper<_T1, _Rp, true>
 {
-    typedef typename __apply_cv<decltype(*_VSTD::declval<_T1>()), _Rp>::type type;
+    typedef typename __apply_cv<decltype(*_VSTD::declval<_T1&>()), _Rp>::type type;
 };
 
 template <class _Rp, class _Tp, class _T1>
 inline _LIBCPP_INLINE_VISIBILITY
 typename __4th_helper<_T1, _Rp,
-                      !is_base_of<_Tp,
-                                  typename remove_reference<_T1>::type
-                                 >::value
-                     >::type&
+    is_member_object_pointer<_Rp _Tp::*>::value &&
+    !is_base_of<_Tp, typename remove_reference<_T1>::type>::value
+>::type&
 __invoke(_Rp _Tp::* __f, _T1& __t1)
 {
     return (*__t1).*__f;
 }
 
-// template <class _Dp, class _Rp, class _Tp, class _T1>
-// inline _LIBCPP_INLINE_VISIBILITY
-// typename enable_if
-// <
-//     !is_base_of<_Tp, typename remove_reference<_T1>::type>::value,
-//     typename __ref_return1<_Rp _Tp::*, _T1>::type
-// >::type
-// __invoke(_Rp _Tp::* __f, _T1 __t1)
-// {
-//     return (*__t1).*__f;
-// }
-
 // fifth bullet
 
 template <class _Fp>
 inline _LIBCPP_INLINE_VISIBILITY
-decltype(declval<_Fp>()())
-__invoke(_Fp __f)
+decltype(_VSTD::declval<_Fp&>()())
+__invoke(_Fp& __f)
 {
     return __f();
 }
 
 template <class _Fp, class _A0>
 inline _LIBCPP_INLINE_VISIBILITY
-decltype(declval<_Fp>()(declval<_A0&>()))
-__invoke(_Fp __f, _A0& __a0)
+decltype(_VSTD::declval<_Fp&>()(_VSTD::declval<_A0&>()))
+__invoke(_Fp& __f, _A0& __a0)
 {
     return __f(__a0);
 }
 
 template <class _Fp, class _A0, class _A1>
 inline _LIBCPP_INLINE_VISIBILITY
-decltype(declval<_Fp>()(declval<_A0&>(), declval<_A1&>()))
-__invoke(_Fp __f, _A0& __a0, _A1& __a1)
+decltype(_VSTD::declval<_Fp&>()(_VSTD::declval<_A0&>(), _VSTD::declval<_A1&>()))
+__invoke(_Fp& __f, _A0& __a0, _A1& __a1)
 {
     return __f(__a0, __a1);
 }
 
 template <class _Fp, class _A0, class _A1, class _A2>
 inline _LIBCPP_INLINE_VISIBILITY
-decltype(declval<_Fp>()(declval<_A0&>(), declval<_A1&>(), declval<_A2&>()))
-__invoke(_Fp __f, _A0& __a0, _A1& __a1, _A2& __a2)
+decltype(_VSTD::declval<_Fp&>()(_VSTD::declval<_A0&>(), _VSTD::declval<_A1&>(), _VSTD::declval<_A2&>()))
+__invoke(_Fp& __f, _A0& __a0, _A1& __a1, _A2& __a2)
 {
     return __f(__a0, __a1, __a2);
 }
 
-// template <class _Rp, class _Fp>
-// inline _LIBCPP_INLINE_VISIBILITY
-// _Rp
-// __invoke(_Fp& __f)
-// {
-//     return __f();
-// }
-//
-// template <class _Rp, class _Fp, class _A0>
-// inline _LIBCPP_INLINE_VISIBILITY
-// typename enable_if
-// <
-//     !is_member_pointer<_Fp>::value,
-//     _Rp
-// >::type
-// __invoke(_Fp& __f, _A0& __a0)
-// {
-//     return __f(__a0);
-// }
-//
-// template <class _Rp, class _Fp, class _A0, class _A1>
-// inline _LIBCPP_INLINE_VISIBILITY
-// _Rp
-// __invoke(_Fp& __f, _A0& __a0, _A1& __a1)
-// {
-//     return __f(__a0, __a1);
-// }
-//
-// template <class _Rp, class _Fp, class _A0, class _A1, class _A2>
-// inline _LIBCPP_INLINE_VISIBILITY
-// _Rp
-// __invoke(_Fp& __f, _A0& __a0, _A1& __a1, _A2& __a2)
-// {
-//     return __f(__a0, __a1, __a2);
-// }
-
-template <class _Tp>
-struct __has_type
-{
-private:
-    struct __two {char __lx; char __lxx;};
-    template <class _Up> static __two __test(...);
-    template <class _Up> static char __test(typename _Up::type* = 0);
-public:
-    static const bool value = sizeof(__test<_Tp>(0)) == 1;
-};
-
 template <class _Fp, bool = __has_result_type<__weak_result_type<_Fp> >::value>
 struct __invoke_return
 {
@@ -959,23 +485,23 @@
 template <class _Fp>
 struct __invoke_return<_Fp, false>
 {
-    typedef decltype(__invoke(_VSTD::declval<_Fp>())) type;
+    typedef decltype(__invoke(_VSTD::declval<_Fp&>())) type;
 };
 
-template <class _Tp, class _A0>
+template <class _Tp, class _A0, bool = is_member_object_pointer<_Tp>::value>
 struct __invoke_return0
 {
-    typedef decltype(__invoke(_VSTD::declval<_Tp>(), _VSTD::declval<_A0>())) type;
+    typedef decltype(__invoke(_VSTD::declval<_Tp&>(), _VSTD::declval<_A0&>())) type;
 };
 
 template <class _Rp, class _Tp, class _A0>
-struct __invoke_return0<_Rp _Tp::*, _A0>
+struct __invoke_return0<_Rp _Tp::*, _A0, true>
 {
     typedef typename __apply_cv<_A0, _Rp>::type& type;
 };
 
 template <class _Rp, class _Tp, class _A0>
-struct __invoke_return0<_Rp _Tp::*, _A0*>
+struct __invoke_return0<_Rp _Tp::*, _A0*, true>
 {
     typedef typename __apply_cv<_A0, _Rp>::type& type;
 };
@@ -983,162 +509,16 @@
 template <class _Tp, class _A0, class _A1>
 struct __invoke_return1
 {
-    typedef decltype(__invoke(_VSTD::declval<_Tp>(), _VSTD::declval<_A0>(),
-                                                    _VSTD::declval<_A1>())) type;
+    typedef decltype(__invoke(_VSTD::declval<_Tp&>(), _VSTD::declval<_A0&>(),
+                                                     _VSTD::declval<_A1&>())) type;
 };
 
 template <class _Tp, class _A0, class _A1, class _A2>
 struct __invoke_return2
 {
-    typedef decltype(__invoke(_VSTD::declval<_Tp>(), _VSTD::declval<_A0>(),
-                                                    _VSTD::declval<_A1>(),
-                                                    _VSTD::declval<_A2>())) type;
+    typedef decltype(__invoke(_VSTD::declval<_Tp&>(), _VSTD::declval<_A0&>(),
+                                                      _VSTD::declval<_A1&>(),
+                                                      _VSTD::declval<_A2&>())) type;
 };
 
-template <class _Ret>
-struct __invoke_void_return_wrapper
-{
-    template <class _Fn>
-    static _Ret __call(_Fn __f)
-    {
-        return __invoke(__f);
-    }
-
-    template <class _Fn, class _A0>
-    static _Ret __call(_Fn __f, _A0& __a0)
-    {
-        return __invoke(__f, __a0);
-    }
-
-    template <class _Fn, class _A0, class _A1>
-    static _Ret __call(_Fn __f, _A0& __a0, _A1& __a1)
-    {
-        return __invoke(__f, __a0, __a1);
-    }
-
-    template <class _Fn, class _A0, class _A1, class _A2>
-    static _Ret __call(_Fn __f, _A0& __a0, _A1& __a1, _A2& __a2)
-    {
-        return __invoke(__f, __a0, __a1, __a2);
-    }
-};
-
-
-template <>
-struct __invoke_void_return_wrapper<void>
-{
-    template <class _Fn>
-    static void __call(_Fn __f)
-    {
-        __invoke(__f);
-    }
-
-    template <class _Fn, class _A0>
-    static void __call(_Fn __f, _A0& __a0)
-    {
-        __invoke(__f, __a0);
-    }
-
-    template <class _Fn, class _A0, class _A1>
-    static void __call(_Fn __f, _A0& __a0, _A1& __a1)
-    {
-        __invoke(__f, __a0, __a1);
-    }
-
-    template <class _Fn, class _A0, class _A1, class _A2>
-    static void __call(_Fn __f, _A0& __a0, _A1& __a1, _A2& __a2)
-    {
-        __invoke(__f, __a0, __a1, __a2);
-    }
-};
-
-template <class _Tp>
-class _LIBCPP_TYPE_VIS_ONLY reference_wrapper
-    : public __weak_result_type<_Tp>
-{
-public:
-    // types
-    typedef _Tp type;
-private:
-    type* __f_;
-
-public:
-    // construct/copy/destroy
-    _LIBCPP_INLINE_VISIBILITY reference_wrapper(type& __f) : __f_(&__f) {}
-
-    // access
-    _LIBCPP_INLINE_VISIBILITY operator type&    () const {return *__f_;}
-    _LIBCPP_INLINE_VISIBILITY          type& get() const {return *__f_;}
-
-    // invoke
-
-    _LIBCPP_INLINE_VISIBILITY
-    typename __invoke_return<type&>::type
-       operator() () const
-       {
-           return __invoke(get());
-       }
-
-    template <class _A0>
-       _LIBCPP_INLINE_VISIBILITY
-       typename __invoke_return0<type&, _A0>::type
-          operator() (_A0& __a0) const
-          {
-              return __invoke<type&, _A0>(get(), __a0);
-          }
-
-    template <class _A0, class _A1>
-       _LIBCPP_INLINE_VISIBILITY
-       typename __invoke_return1<type&, _A0, _A1>::type
-          operator() (_A0& __a0, _A1& __a1) const
-          {
-              return __invoke<type&, _A0, _A1>(get(), __a0, __a1);
-          }
-
-    template <class _A0, class _A1, class _A2>
-       _LIBCPP_INLINE_VISIBILITY
-       typename __invoke_return2<type&, _A0, _A1, _A2>::type
-          operator() (_A0& __a0, _A1& __a1, _A2& __a2) const
-          {
-              return __invoke<type&, _A0, _A1, _A2>(get(), __a0, __a1, __a2);
-          }
-};
-
-template <class _Tp> struct __is_reference_wrapper_impl : public false_type {};
-template <class _Tp> struct __is_reference_wrapper_impl<reference_wrapper<_Tp> > : public true_type {};
-template <class _Tp> struct __is_reference_wrapper
-    : public __is_reference_wrapper_impl<typename remove_cv<_Tp>::type> {};
-
-template <class _Tp>
-inline _LIBCPP_INLINE_VISIBILITY
-reference_wrapper<_Tp>
-ref(_Tp& __t)
-{
-    return reference_wrapper<_Tp>(__t);
-}
-
-template <class _Tp>
-inline _LIBCPP_INLINE_VISIBILITY
-reference_wrapper<_Tp>
-ref(reference_wrapper<_Tp> __t)
-{
-    return ref(__t.get());
-}
-
-template <class _Tp>
-inline _LIBCPP_INLINE_VISIBILITY
-reference_wrapper<const _Tp>
-cref(const _Tp& __t)
-{
-    return reference_wrapper<const _Tp>(__t);
-}
-
-template <class _Tp>
-inline _LIBCPP_INLINE_VISIBILITY
-reference_wrapper<const _Tp>
-cref(reference_wrapper<_Tp> __t)
-{
-    return cref(__t.get());
-}
-
 #endif  // _LIBCPP_FUNCTIONAL_BASE_03
diff --git a/include/__hash_table b/include/__hash_table
index 71cf5fb..ec20e10 100644
--- a/include/__hash_table
+++ b/include/__hash_table
@@ -85,8 +85,6 @@
 template <class _ConstNodePtr> class _LIBCPP_TYPE_VIS_ONLY __hash_const_iterator;
 template <class _HashIterator> class _LIBCPP_TYPE_VIS_ONLY __hash_map_iterator;
 template <class _HashIterator> class _LIBCPP_TYPE_VIS_ONLY __hash_map_const_iterator;
-template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
-    class _LIBCPP_TYPE_VIS_ONLY unordered_map;
 
 template <class _NodePtr>
 class _LIBCPP_TYPE_VIS_ONLY __hash_iterator
@@ -777,13 +775,7 @@
 public:
     // Create __node
     typedef __hash_node<value_type, typename __alloc_traits::void_pointer> __node;
-    typedef typename __alloc_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-            rebind_alloc<__node>
-#else
-            rebind_alloc<__node>::other
-#endif
-                                                     __node_allocator;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __node>::type __node_allocator;
     typedef allocator_traits<__node_allocator>       __node_traits;
     typedef typename __node_traits::pointer          __node_pointer;
     typedef typename __node_traits::pointer          __node_const_pointer;
@@ -798,13 +790,7 @@
 
 private:
 
-    typedef typename __node_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-            rebind_alloc<__node_pointer>
-#else
-            rebind_alloc<__node_pointer>::other
-#endif
-                                                            __pointer_allocator;
+    typedef typename __rebind_alloc_helper<__node_traits, __node_pointer>::type __pointer_allocator;
     typedef __bucket_list_deallocator<__pointer_allocator> __bucket_list_deleter;
     typedef unique_ptr<__node_pointer[], __bucket_list_deleter> __bucket_list;
     typedef allocator_traits<__pointer_allocator>          __pointer_alloc_traits;
@@ -910,11 +896,21 @@
         iterator __emplace_hint_multi(const_iterator __p, _Args&&... __args);
 #endif  // !defined(_LIBCPP_HAS_NO_RVALUE_REFERENCES) && !defined(_LIBCPP_HAS_NO_VARIADICS)
 
+#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+    template <class _ValueTp>
+    _LIBCPP_INLINE_VISIBILITY
+    pair<iterator, bool> __insert_unique_value(_ValueTp&& __x);
+#else
+    _LIBCPP_INLINE_VISIBILITY
+    pair<iterator, bool> __insert_unique_value(const value_type& __x);
+#endif
+
     pair<iterator, bool> __insert_unique(const value_type& __x);
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+    pair<iterator, bool> __insert_unique(value_type&& __x);
     template <class _Pp>
-        pair<iterator, bool> __insert_unique(_Pp&& __x);
+    pair<iterator, bool> __insert_unique(_Pp&& __x);
 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
@@ -988,13 +984,17 @@
         __equal_range_multi(const _Key& __k) const;
 
     void swap(__hash_table& __u)
+#if _LIBCPP_STD_VER <= 11
         _NOEXCEPT_(
-            (!allocator_traits<__pointer_allocator>::propagate_on_container_swap::value ||
-             __is_nothrow_swappable<__pointer_allocator>::value) &&
-            (!__node_traits::propagate_on_container_swap::value ||
-             __is_nothrow_swappable<__node_allocator>::value) &&
-            __is_nothrow_swappable<hasher>::value &&
-            __is_nothrow_swappable<key_equal>::value);
+            __is_nothrow_swappable<hasher>::value && __is_nothrow_swappable<key_equal>::value
+            && (!allocator_traits<__pointer_allocator>::propagate_on_container_swap::value
+                  || __is_nothrow_swappable<__pointer_allocator>::value)
+            && (!__node_traits::propagate_on_container_swap::value
+                  || __is_nothrow_swappable<__node_allocator>::value)
+            );
+#else
+     _NOEXCEPT_(__is_nothrow_swappable<hasher>::value && __is_nothrow_swappable<key_equal>::value);
+#endif
 
     _LIBCPP_INLINE_VISIBILITY
     size_type max_bucket_count() const _NOEXCEPT
@@ -1122,38 +1122,6 @@
     _LIBCPP_INLINE_VISIBILITY
         void __move_assign_alloc(__hash_table&, false_type) _NOEXCEPT {}
 
-    template <class _Ap>
-    _LIBCPP_INLINE_VISIBILITY
-    static
-    void
-    __swap_alloc(_Ap& __x, _Ap& __y)
-        _NOEXCEPT_(
-            !allocator_traits<_Ap>::propagate_on_container_swap::value ||
-            __is_nothrow_swappable<_Ap>::value)
-    {
-        __swap_alloc(__x, __y,
-                     integral_constant<bool,
-                        allocator_traits<_Ap>::propagate_on_container_swap::value
-                                      >());
-    }
-
-    template <class _Ap>
-    _LIBCPP_INLINE_VISIBILITY
-    static
-    void
-    __swap_alloc(_Ap& __x, _Ap& __y, true_type)
-        _NOEXCEPT_(__is_nothrow_swappable<_Ap>::value)
-    {
-        using _VSTD::swap;
-        swap(__x, __y);
-    }
-
-    template <class _Ap>
-    _LIBCPP_INLINE_VISIBILITY
-    static
-    void
-    __swap_alloc(_Ap&, _Ap&, false_type) _NOEXCEPT {}
-
     void __deallocate(__node_pointer __np) _NOEXCEPT;
     __node_pointer __detach() _NOEXCEPT;
 
@@ -1753,6 +1721,26 @@
 pair<typename __hash_table<_Tp, _Hash, _Equal, _Alloc>::iterator, bool>
 __hash_table<_Tp, _Hash, _Equal, _Alloc>::__insert_unique(const value_type& __x)
 {
+    return __insert_unique_value(__x);
+}
+
+
+#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+template <class _Tp, class _Hash, class _Equal, class _Alloc>
+template <class _ValueTp>
+_LIBCPP_INLINE_VISIBILITY
+pair<typename __hash_table<_Tp, _Hash, _Equal, _Alloc>::iterator, bool>
+__hash_table<_Tp, _Hash, _Equal, _Alloc>::__insert_unique_value(_ValueTp&& __x)
+#else
+template <class _Tp, class _Hash, class _Equal, class _Alloc>
+_LIBCPP_INLINE_VISIBILITY
+pair<typename __hash_table<_Tp, _Hash, _Equal, _Alloc>::iterator, bool>
+__hash_table<_Tp, _Hash, _Equal, _Alloc>::__insert_unique_value(const value_type& __x)
+#endif
+{
+#if defined(_LIBCPP_HAS_NO_RVALUE_REFERENCES)
+    typedef const value_type& _ValueTp;
+#endif
     size_t __hash = hash_function()(__x);
     size_type __bc = bucket_count();
     bool __inserted = false;
@@ -1774,7 +1762,7 @@
         }
     }
     {
-        __node_holder __h = __construct_node(__x, __hash);
+        __node_holder __h = __construct_node(_VSTD::forward<_ValueTp>(__x), __hash);
         if (size()+1 > __bc * max_load_factor() || __bc == 0)
         {
             rehash(_VSTD::max<size_type>(2 * __bc + !__is_hash_power2(__bc),
@@ -1858,6 +1846,13 @@
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 
 template <class _Tp, class _Hash, class _Equal, class _Alloc>
+pair<typename __hash_table<_Tp, _Hash, _Equal, _Alloc>::iterator, bool>
+__hash_table<_Tp, _Hash, _Equal, _Alloc>::__insert_unique(value_type&& __x)
+{
+    return __insert_unique_value(_VSTD::move(__x));
+}
+
+template <class _Tp, class _Hash, class _Equal, class _Alloc>
 template <class _Pp>
 pair<typename __hash_table<_Tp, _Hash, _Equal, _Alloc>::iterator, bool>
 __hash_table<_Tp, _Hash, _Equal, _Alloc>::__insert_unique(_Pp&& __x)
@@ -2358,13 +2353,17 @@
 template <class _Tp, class _Hash, class _Equal, class _Alloc>
 void
 __hash_table<_Tp, _Hash, _Equal, _Alloc>::swap(__hash_table& __u)
+#if _LIBCPP_STD_VER <= 11
     _NOEXCEPT_(
-        (!allocator_traits<__pointer_allocator>::propagate_on_container_swap::value ||
-         __is_nothrow_swappable<__pointer_allocator>::value) &&
-        (!__node_traits::propagate_on_container_swap::value ||
-         __is_nothrow_swappable<__node_allocator>::value) &&
-        __is_nothrow_swappable<hasher>::value &&
-        __is_nothrow_swappable<key_equal>::value)
+        __is_nothrow_swappable<hasher>::value && __is_nothrow_swappable<key_equal>::value
+        && (!allocator_traits<__pointer_allocator>::propagate_on_container_swap::value
+              || __is_nothrow_swappable<__pointer_allocator>::value)
+        && (!__node_traits::propagate_on_container_swap::value
+              || __is_nothrow_swappable<__node_allocator>::value)
+            )
+#else
+  _NOEXCEPT_(__is_nothrow_swappable<hasher>::value && __is_nothrow_swappable<key_equal>::value)
+#endif
 {
     {
     __node_pointer_pointer __npp = __bucket_list_.release();
@@ -2372,9 +2371,9 @@
     __u.__bucket_list_.reset(__npp);
     }
     _VSTD::swap(__bucket_list_.get_deleter().size(), __u.__bucket_list_.get_deleter().size());
-    __swap_alloc(__bucket_list_.get_deleter().__alloc(),
+    __swap_allocator(__bucket_list_.get_deleter().__alloc(),
              __u.__bucket_list_.get_deleter().__alloc());
-    __swap_alloc(__node_alloc(), __u.__node_alloc());
+    __swap_allocator(__node_alloc(), __u.__node_alloc());
     _VSTD::swap(__p1_.first().__next_, __u.__p1_.first().__next_);
     __p2_.swap(__u.__p2_);
     __p3_.swap(__u.__p3_);
diff --git a/include/__locale b/include/__locale
index 625d0f8..1989558 100644
--- a/include/__locale
+++ b/include/__locale
@@ -353,6 +353,7 @@
     static const mask punct  = _PUNCT;
     static const mask xdigit = _HEX;
     static const mask blank  = _BLANK;
+# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_PRINT
 #elif defined(__APPLE__) || defined(__FreeBSD__) || defined(__EMSCRIPTEN__) || defined(__NetBSD__)
 # ifdef __APPLE__
     typedef __uint32_t mask;
@@ -401,6 +402,9 @@
     static const mask punct  = _P;
     static const mask xdigit = _X | _N;
     static const mask blank  = _B;
+# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_PRINT
+# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_ALPHA
+# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_XDIGIT
 #else
     typedef unsigned long mask;
     static const mask space  = 1<<0;
diff --git a/include/__split_buffer b/include/__split_buffer
index 1d529cb..727b1b6 100644
--- a/include/__split_buffer
+++ b/include/__split_buffer
@@ -156,25 +156,6 @@
     _LIBCPP_INLINE_VISIBILITY
     void __move_assign_alloc(__split_buffer&, false_type) _NOEXCEPT
         {}
-
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__alloc_rr& __x, __alloc_rr& __y)
-        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value||
-                   __is_nothrow_swappable<__alloc_rr>::value)
-        {__swap_alloc(__x, __y, integral_constant<bool,
-                      __alloc_traits::propagate_on_container_swap::value>());}
-
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__alloc_rr& __x, __alloc_rr& __y, true_type)
-        _NOEXCEPT_(__is_nothrow_swappable<__alloc_rr>::value)
-        {
-            using _VSTD::swap;
-            swap(__x, __y);
-        }
-
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__alloc_rr&, __alloc_rr&, false_type) _NOEXCEPT
-        {}
 };
 
 template <class _Tp, class _Allocator>
@@ -431,7 +412,7 @@
     _VSTD::swap(__begin_, __x.__begin_);
     _VSTD::swap(__end_, __x.__end_);
     _VSTD::swap(__end_cap(), __x.__end_cap());
-    __swap_alloc(__alloc(), __x.__alloc());
+    __swap_allocator(__alloc(), __x.__alloc());
 }
 
 template <class _Tp, class _Allocator>
diff --git a/include/__std_stream b/include/__std_stream
index 5403ada..f867cd2 100644
--- a/include/__std_stream
+++ b/include/__std_stream
@@ -276,7 +276,6 @@
             codecvt_base::result __r;
             char_type* pbase = &__1buf;
             char_type* pptr = pbase + 1;
-            char_type* epptr = pptr;
             do
             {
                 const char_type* __e;
diff --git a/include/__tree b/include/__tree
index 2aa9c1f..3ad5794 100644
--- a/include/__tree
+++ b/include/__tree
@@ -28,14 +28,6 @@
     class _LIBCPP_TYPE_VIS_ONLY __tree_iterator;
 template <class _Tp, class _ConstNodePtr, class _DiffType>
     class _LIBCPP_TYPE_VIS_ONLY __tree_const_iterator;
-template <class _Key, class _Tp, class _Compare, class _Allocator>
-    class _LIBCPP_TYPE_VIS_ONLY map;
-template <class _Key, class _Tp, class _Compare, class _Allocator>
-    class _LIBCPP_TYPE_VIS_ONLY multimap;
-template <class _Key, class _Compare, class _Allocator>
-    class _LIBCPP_TYPE_VIS_ONLY set;
-template <class _Key, class _Compare, class _Allocator>
-    class _LIBCPP_TYPE_VIS_ONLY multiset;
 
 /*
 
@@ -810,13 +802,7 @@
 
     typedef __tree_node<value_type, __void_pointer> __node;
     typedef __tree_node_base<__void_pointer>        __node_base;
-    typedef typename __alloc_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-            rebind_alloc<__node>
-#else
-            rebind_alloc<__node>::other
-#endif
-                                                     __node_allocator;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __node>::type __node_allocator;
     typedef allocator_traits<__node_allocator>       __node_traits;
     typedef typename __node_traits::pointer          __node_pointer;
     typedef typename __node_traits::pointer          __node_const_pointer;
@@ -940,9 +926,12 @@
 
     void swap(__tree& __t)
         _NOEXCEPT_(
-            __is_nothrow_swappable<value_compare>::value &&
-            (!__node_traits::propagate_on_container_swap::value ||
-             __is_nothrow_swappable<__node_allocator>::value));
+            __is_nothrow_swappable<value_compare>::value
+#if _LIBCPP_STD_VER <= 11
+            && (!__node_traits::propagate_on_container_swap::value ||
+                 __is_nothrow_swappable<__node_allocator>::value)
+#endif
+            );
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 #ifndef _LIBCPP_HAS_NO_VARIADICS
@@ -1110,25 +1099,6 @@
     _LIBCPP_INLINE_VISIBILITY
     void __move_assign_alloc(__tree& __t, false_type) _NOEXCEPT {}
 
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__node_allocator& __x, __node_allocator& __y)
-        _NOEXCEPT_(
-            !__node_traits::propagate_on_container_swap::value ||
-            __is_nothrow_swappable<__node_allocator>::value)
-        {__swap_alloc(__x, __y, integral_constant<bool,
-                      __node_traits::propagate_on_container_swap::value>());}
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__node_allocator& __x, __node_allocator& __y, true_type)
-        _NOEXCEPT_(__is_nothrow_swappable<__node_allocator>::value)
-        {
-            using _VSTD::swap;
-            swap(__x, __y);
-        }
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__node_allocator& __x, __node_allocator& __y, false_type)
-        _NOEXCEPT
-        {}
-
     __node_pointer __detach();
     static __node_pointer __detach(__node_pointer);
 
@@ -1148,8 +1118,8 @@
 
 template <class _Tp, class _Compare, class _Allocator>
 __tree<_Tp, _Compare, _Allocator>::__tree(const allocator_type& __a)
-    : __pair1_(__node_allocator(__a)),
-      __begin_node_(__node_pointer()),
+    : __begin_node_(__node_pointer()),
+      __pair1_(__node_allocator(__a)),
       __pair3_(0)
 {
     __begin_node() = __end_node();
@@ -1158,8 +1128,8 @@
 template <class _Tp, class _Compare, class _Allocator>
 __tree<_Tp, _Compare, _Allocator>::__tree(const value_compare& __comp,
                                            const allocator_type& __a)
-    : __pair1_(__node_allocator(__a)),
-      __begin_node_(__node_pointer()),
+    : __begin_node_(__node_pointer()),
+      __pair1_(__node_allocator(__a)),
       __pair3_(0, __comp)
 {
     __begin_node() = __end_node();
@@ -1466,15 +1436,18 @@
 template <class _Tp, class _Compare, class _Allocator>
 void
 __tree<_Tp, _Compare, _Allocator>::swap(__tree& __t)
-    _NOEXCEPT_(
-        __is_nothrow_swappable<value_compare>::value &&
-        (!__node_traits::propagate_on_container_swap::value ||
-         __is_nothrow_swappable<__node_allocator>::value))
+        _NOEXCEPT_(
+            __is_nothrow_swappable<value_compare>::value
+#if _LIBCPP_STD_VER <= 11
+            && (!__node_traits::propagate_on_container_swap::value ||
+                 __is_nothrow_swappable<__node_allocator>::value)
+#endif
+            )
 {
     using _VSTD::swap;
     swap(__begin_node_, __t.__begin_node_);
     swap(__pair1_.first(), __t.__pair1_.first());
-    __swap_alloc(__node_alloc(), __t.__node_alloc());
+    __swap_allocator(__node_alloc(), __t.__node_alloc());
     __pair3_.swap(__t.__pair3_);
     if (size() == 0)
         __begin_node() = __end_node();
@@ -2085,7 +2058,6 @@
 typename __tree<_Tp, _Compare, _Allocator>::size_type
 __tree<_Tp, _Compare, _Allocator>::__count_multi(const _Key& __k) const
 {
-    typedef pair<const_iterator, const_iterator> _Pp;
     __node_const_pointer __result = __end_node();
     __node_const_pointer __rt = __root();
     while (__rt != nullptr)
diff --git a/include/__tuple b/include/__tuple
index bffb95c..2837ce7 100644
--- a/include/__tuple
+++ b/include/__tuple
@@ -19,40 +19,9 @@
 #pragma GCC system_header
 #endif
 
-#ifdef _LIBCPP_HAS_NO_VARIADICS
-
-#include <__tuple_03>
-
-#else  // _LIBCPP_HAS_NO_VARIADICS
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
-// __lazy_and
-
-template <bool _Last, class ..._Preds>
-struct __lazy_and_impl;
-
-template <class ..._Preds>
-struct __lazy_and_impl<false, _Preds...> : false_type {};
-
-template <>
-struct __lazy_and_impl<true> : true_type {};
-
-template <class _Pred>
-struct __lazy_and_impl<true, _Pred> : integral_constant<bool, _Pred::type::value> {};
-
-template <class _Hp, class ..._Tp>
-struct __lazy_and_impl<true, _Hp, _Tp...> : __lazy_and_impl<_Hp::type::value, _Tp...> {};
-
-template <class _P1, class ..._Pr>
-struct __lazy_and : __lazy_and_impl<_P1::type::value, _Pr...> {};
-
-// __lazy_not
-
-template <class _Pred>
-struct __lazy_not : integral_constant<bool, !_Pred::type::value> {};
-
-
 template <class _Tp> class _LIBCPP_TYPE_VIS_ONLY tuple_size;
 
 template <class _Tp>
@@ -90,19 +59,18 @@
     typedef typename add_cv<typename tuple_element<_Ip, _Tp>::type>::type type;
 };
 
-template <class ..._Tp> class _LIBCPP_TYPE_VIS_ONLY tuple;
-template <class _T1, class _T2> struct _LIBCPP_TYPE_VIS_ONLY pair;
-template <class _Tp, size_t _Size> struct _LIBCPP_TYPE_VIS_ONLY array;
-
 template <class _Tp> struct __tuple_like : false_type {};
 
 template <class _Tp> struct __tuple_like<const _Tp> : public __tuple_like<_Tp> {};
 template <class _Tp> struct __tuple_like<volatile _Tp> : public __tuple_like<_Tp> {};
 template <class _Tp> struct __tuple_like<const volatile _Tp> : public __tuple_like<_Tp> {};
 
+// tuple specializations
+
+#if !defined(_LIBCPP_HAS_NO_VARIADICS)
+template <class ..._Tp> class _LIBCPP_TYPE_VIS_ONLY tuple;
+
 template <class... _Tp> struct __tuple_like<tuple<_Tp...> > : true_type {};
-template <class _T1, class _T2> struct __tuple_like<pair<_T1, _T2> > : true_type {};
-template <class _Tp, size_t _Size> struct __tuple_like<array<_Tp, _Size> > : true_type {};
 
 template <size_t _Ip, class ..._Tp>
 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
@@ -118,6 +86,13 @@
 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
 typename tuple_element<_Ip, tuple<_Tp...> >::type&&
 get(tuple<_Tp...>&&) _NOEXCEPT;
+#endif
+
+// pair specializations
+
+template <class _T1, class _T2> struct _LIBCPP_TYPE_VIS_ONLY pair;
+
+template <class _T1, class _T2> struct __tuple_like<pair<_T1, _T2> > : true_type {};
 
 template <size_t _Ip, class _T1, class _T2>
 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
@@ -129,10 +104,18 @@
 const typename tuple_element<_Ip, pair<_T1, _T2> >::type&
 get(const pair<_T1, _T2>&) _NOEXCEPT;
 
+#if !defined(_LIBCPP_HAS_NO_RVALUE_REFERENCES)
 template <size_t _Ip, class _T1, class _T2>
 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
 typename tuple_element<_Ip, pair<_T1, _T2> >::type&&
 get(pair<_T1, _T2>&&) _NOEXCEPT;
+#endif
+
+// array specializations
+
+template <class _Tp, size_t _Size> struct _LIBCPP_TYPE_VIS_ONLY array;
+
+template <class _Tp, size_t _Size> struct __tuple_like<array<_Tp, _Size> > : true_type {};
 
 template <size_t _Ip, class _Tp, size_t _Size>
 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
@@ -144,10 +127,39 @@
 const _Tp&
 get(const array<_Tp, _Size>&) _NOEXCEPT;
 
+#if !defined(_LIBCPP_HAS_NO_RVALUE_REFERENCES)
 template <size_t _Ip, class _Tp, size_t _Size>
 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
 _Tp&&
 get(array<_Tp, _Size>&&) _NOEXCEPT;
+#endif
+
+#if !defined(_LIBCPP_HAS_NO_VARIADICS)
+
+// __lazy_and
+
+template <bool _Last, class ..._Preds>
+struct __lazy_and_impl;
+
+template <class ..._Preds>
+struct __lazy_and_impl<false, _Preds...> : false_type {};
+
+template <>
+struct __lazy_and_impl<true> : true_type {};
+
+template <class _Pred>
+struct __lazy_and_impl<true, _Pred> : integral_constant<bool, _Pred::type::value> {};
+
+template <class _Hp, class ..._Tp>
+struct __lazy_and_impl<true, _Hp, _Tp...> : __lazy_and_impl<_Hp::type::value, _Tp...> {};
+
+template <class _P1, class ..._Pr>
+struct __lazy_and : __lazy_and_impl<_P1::type::value, _Pr...> {};
+
+// __lazy_not
+
+template <class _Pred>
+struct __lazy_not : integral_constant<bool, !_Pred::type::value> {};
 
 // __make_tuple_indices
 
@@ -354,8 +366,8 @@
                                     tuple_size<_Up>::value, _Tp, _Up>
 {};
 
-_LIBCPP_END_NAMESPACE_STD
-
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 
+_LIBCPP_END_NAMESPACE_STD
+
 #endif  // _LIBCPP___TUPLE
diff --git a/include/__tuple_03 b/include/__tuple_03
deleted file mode 100644
index b91c2cd..0000000
--- a/include/__tuple_03
+++ /dev/null
@@ -1,27 +0,0 @@
-// -*- C++ -*-
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-#ifndef _LIBCPP___TUPLE_03
-#define _LIBCPP___TUPLE_03
-
-#include <__config>
-
-#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
-#pragma GCC system_header
-#endif
-
-_LIBCPP_BEGIN_NAMESPACE_STD
-
-template <class _Tp> class _LIBCPP_TYPE_VIS_ONLY tuple_size;
-template <size_t _Ip, class _Tp> class _LIBCPP_TYPE_VIS_ONLY tuple_element;
-
-_LIBCPP_END_NAMESPACE_STD
-
-#endif  // _LIBCPP___TUPLE_03
diff --git a/include/algorithm b/include/algorithm
index 415059d..c1635fc 100644
--- a/include/algorithm
+++ b/include/algorithm
@@ -521,11 +521,11 @@
 
 template <class ForwardIterator>
     ForwardIterator
-    min_element(ForwardIterator first, ForwardIterator last);
+    min_element(ForwardIterator first, ForwardIterator last);  // constexpr in C++14
 
 template <class ForwardIterator, class Compare>
     ForwardIterator
-    min_element(ForwardIterator first, ForwardIterator last, Compare comp);
+    min_element(ForwardIterator first, ForwardIterator last, Compare comp);  // constexpr in C++14
 
 template <class T>
     const T&
@@ -545,11 +545,11 @@
 
 template <class ForwardIterator>
     ForwardIterator
-    max_element(ForwardIterator first, ForwardIterator last);
+    max_element(ForwardIterator first, ForwardIterator last);  // constexpr in C++14
 
 template <class ForwardIterator, class Compare>
     ForwardIterator
-    max_element(ForwardIterator first, ForwardIterator last, Compare comp);
+    max_element(ForwardIterator first, ForwardIterator last, Compare comp);  // constexpr in C++14
 
 template <class T>
     const T&
@@ -569,11 +569,11 @@
 
 template<class ForwardIterator>
     pair<ForwardIterator, ForwardIterator>
-    minmax_element(ForwardIterator first, ForwardIterator last);
+    minmax_element(ForwardIterator first, ForwardIterator last);   // constexpr in C++14
 
 template<class ForwardIterator, class Compare>
     pair<ForwardIterator, ForwardIterator>
-    minmax_element(ForwardIterator first, ForwardIterator last, Compare comp);
+    minmax_element(ForwardIterator first, ForwardIterator last, Compare comp);   // constexpr in C++14
 
 template<class T>
     pair<const T&, const T&>
@@ -1763,7 +1763,8 @@
 __copy(_Tp* __first, _Tp* __last, _Up* __result)
 {
     const size_t __n = static_cast<size_t>(__last - __first);
-    _VSTD::memmove(__result, __first, __n * sizeof(_Up));
+    if (__n > 0)
+        _VSTD::memmove(__result, __first, __n * sizeof(_Up));
     return __result + __n;
 }
 
@@ -1798,8 +1799,11 @@
 __copy_backward(_Tp* __first, _Tp* __last, _Up* __result)
 {
     const size_t __n = static_cast<size_t>(__last - __first);
-    __result -= __n;
-    _VSTD::memmove(__result, __first, __n * sizeof(_Up));
+    if (__n > 0)
+    {
+        __result -= __n;
+        _VSTD::memmove(__result, __first, __n * sizeof(_Up));
+    }
     return __result;
 }
 
@@ -1896,7 +1900,8 @@
 __move(_Tp* __first, _Tp* __last, _Up* __result)
 {
     const size_t __n = static_cast<size_t>(__last - __first);
-    _VSTD::memmove(__result, __first, __n * sizeof(_Up));
+    if (__n > 0)
+        _VSTD::memmove(__result, __first, __n * sizeof(_Up));
     return __result + __n;
 }
 
@@ -1931,8 +1936,11 @@
 __move_backward(_Tp* __first, _Tp* __last, _Up* __result)
 {
     const size_t __n = static_cast<size_t>(__last - __first);
-    __result -= __n;
-    _VSTD::memmove(__result, __first, __n * sizeof(_Up));
+    if (__n > 0)
+    {
+        __result -= __n;
+        _VSTD::memmove(__result, __first, __n * sizeof(_Up));
+    }
     return __result;
 }
 
@@ -2544,7 +2552,7 @@
 template <class _ForwardIterator, class _Compare>
 inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
 _ForwardIterator
-__min_element(_ForwardIterator __first, _ForwardIterator __last, _Compare __comp)
+min_element(_ForwardIterator __first, _ForwardIterator __last, _Compare __comp)
 {
     if (__first != __last)
     {
@@ -2556,20 +2564,12 @@
     return __first;
 }
 
-template <class _ForwardIterator, class _Compare>
-inline _LIBCPP_INLINE_VISIBILITY
-_ForwardIterator
-min_element(_ForwardIterator __first, _ForwardIterator __last, _Compare __comp)
-{
-    return __min_element(__first, __last, __comp);
-}
-
 template <class _ForwardIterator>
-inline _LIBCPP_INLINE_VISIBILITY
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
 _ForwardIterator
 min_element(_ForwardIterator __first, _ForwardIterator __last)
 {
-    return __min_element(__first, __last,
+    return _VSTD::min_element(__first, __last,
               __less<typename iterator_traits<_ForwardIterator>::value_type>());
 }
 
@@ -2598,7 +2598,7 @@
 _Tp
 min(initializer_list<_Tp> __t, _Compare __comp)
 {
-    return *__min_element(__t.begin(), __t.end(), __comp);
+    return *_VSTD::min_element(__t.begin(), __t.end(), __comp);
 }
 
 template<class _Tp>
@@ -2606,7 +2606,7 @@
 _Tp
 min(initializer_list<_Tp> __t)
 {
-    return *__min_element(__t.begin(), __t.end(), __less<_Tp>());
+    return *_VSTD::min_element(__t.begin(), __t.end(), __less<_Tp>());
 }
 
 #endif  // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
@@ -2616,7 +2616,7 @@
 template <class _ForwardIterator, class _Compare>
 inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
 _ForwardIterator
-__max_element(_ForwardIterator __first, _ForwardIterator __last, _Compare __comp)
+max_element(_ForwardIterator __first, _ForwardIterator __last, _Compare __comp)
 {
     if (__first != __last)
     {
@@ -2629,20 +2629,12 @@
 }
 
 
-template <class _ForwardIterator, class _Compare>
-inline _LIBCPP_INLINE_VISIBILITY
-_ForwardIterator
-max_element(_ForwardIterator __first, _ForwardIterator __last, _Compare __comp)
-{
-    return __max_element(__first, __last, __comp);
-}
-
 template <class _ForwardIterator>
-inline _LIBCPP_INLINE_VISIBILITY
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
 _ForwardIterator
 max_element(_ForwardIterator __first, _ForwardIterator __last)
 {
-    return __max_element(__first, __last,
+    return _VSTD::max_element(__first, __last,
               __less<typename iterator_traits<_ForwardIterator>::value_type>());
 }
 
@@ -2671,7 +2663,7 @@
 _Tp
 max(initializer_list<_Tp> __t, _Compare __comp)
 {
-    return *__max_element(__t.begin(), __t.end(), __comp);
+    return *_VSTD::max_element(__t.begin(), __t.end(), __comp);
 }
 
 template<class _Tp>
@@ -2679,7 +2671,7 @@
 _Tp
 max(initializer_list<_Tp> __t)
 {
-    return *__max_element(__t.begin(), __t.end(), __less<_Tp>());
+    return *_VSTD::max_element(__t.begin(), __t.end(), __less<_Tp>());
 }
 
 #endif  // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
@@ -2687,6 +2679,7 @@
 // minmax_element
 
 template <class _ForwardIterator, class _Compare>
+_LIBCPP_CONSTEXPR_AFTER_CXX11
 std::pair<_ForwardIterator, _ForwardIterator>
 minmax_element(_ForwardIterator __first, _ForwardIterator __last, _Compare __comp)
 {
@@ -2734,7 +2727,7 @@
 }
 
 template <class _ForwardIterator>
-inline _LIBCPP_INLINE_VISIBILITY
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
 std::pair<_ForwardIterator, _ForwardIterator>
 minmax_element(_ForwardIterator __first, _ForwardIterator __last)
 {
@@ -3044,7 +3037,7 @@
     if (_Rp == 0)
         return static_cast<result_type>(_Eng(__g, _Dt)());
     size_t __w = _Dt - __clz(_Rp) - 1;
-    if ((_Rp & (_UIntType(~0) >> (_Dt - __w))) != 0)
+    if ((_Rp & (std::numeric_limits<_UIntType>::max() >> (_Dt - __w))) != 0)
         ++__w;
     _Eng __e(__g, __w);
     _UIntType __u;
@@ -4368,6 +4361,34 @@
 
 // inplace_merge
 
+template <class _Compare, class _InputIterator1, class _InputIterator2,
+          class _OutputIterator>
+void __half_inplace_merge(_InputIterator1 __first1, _InputIterator1 __last1,
+                          _InputIterator2 __first2, _InputIterator2 __last2,
+                          _OutputIterator __result, _Compare __comp)
+{
+    for (; __first1 != __last1; ++__result)
+    {
+        if (__first2 == __last2)
+        {
+            _VSTD::move(__first1, __last1, __result);
+            return;
+        }
+
+        if (__comp(*__first2, *__first1))
+        {
+            *__result = _VSTD::move(*__first2);
+            ++__first2;
+        }
+        else
+        {
+            *__result = _VSTD::move(*__first1);
+            ++__first1;
+        }
+    }
+    // __first2 through __last2 are already in the right spot.
+}
+
 template <class _Compare, class _BidirectionalIterator>
 void
 __buffered_inplace_merge(_BidirectionalIterator __first, _BidirectionalIterator __middle, _BidirectionalIterator __last,
@@ -4383,11 +4404,7 @@
         value_type* __p = __buff;
         for (_BidirectionalIterator __i = __first; __i != __middle; __d.__incr((value_type*)0), (void) ++__i, ++__p)
             ::new(__p) value_type(_VSTD::move(*__i));
-        __merge<_Compare>(move_iterator<value_type*>(__buff),
-                          move_iterator<value_type*>(__p),
-                          move_iterator<_BidirectionalIterator>(__middle),
-                          move_iterator<_BidirectionalIterator>(__last),
-                          __first, __comp);
+        __half_inplace_merge(__buff, __p, __middle, __last, __first, __comp);
     }
     else
     {
@@ -4396,9 +4413,9 @@
             ::new(__p) value_type(_VSTD::move(*__i));
         typedef reverse_iterator<_BidirectionalIterator> _RBi;
         typedef reverse_iterator<value_type*> _Rv;
-        __merge(move_iterator<_RBi>(_RBi(__middle)), move_iterator<_RBi>(_RBi(__first)),
-                move_iterator<_Rv>(_Rv(__p)), move_iterator<_Rv>(_Rv(__buff)),
-                _RBi(__last), __negate<_Compare>(__comp));
+        __half_inplace_merge(_Rv(__p), _Rv(__buff), 
+                             _RBi(__middle), _RBi(__first),
+                             _RBi(__last), __negate<_Compare>(__comp));
     }
 }
 
diff --git a/include/array b/include/array
index d37075d..2e02a43 100644
--- a/include/array
+++ b/include/array
@@ -288,10 +288,6 @@
 class _LIBCPP_TYPE_VIS_ONLY tuple_size<array<_Tp, _Size> >
     : public integral_constant<size_t, _Size> {};
 
-template <class _Tp, size_t _Size>
-class _LIBCPP_TYPE_VIS_ONLY tuple_size<const array<_Tp, _Size> >
-    : public integral_constant<size_t, _Size> {};
-
 template <size_t _Ip, class _Tp, size_t _Size>
 class _LIBCPP_TYPE_VIS_ONLY tuple_element<_Ip, array<_Tp, _Size> >
 {
@@ -300,13 +296,6 @@
 };
 
 template <size_t _Ip, class _Tp, size_t _Size>
-class _LIBCPP_TYPE_VIS_ONLY tuple_element<_Ip, const array<_Tp, _Size> >
-{
-public:
-    typedef const _Tp type;
-};
-
-template <size_t _Ip, class _Tp, size_t _Size>
 inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
 _Tp&
 get(array<_Tp, _Size>& __a) _NOEXCEPT
diff --git a/include/atomic b/include/atomic
index 0427a91..97a998d 100644
--- a/include/atomic
+++ b/include/atomic
@@ -554,7 +554,8 @@
 template <typename _Tp>
 struct __gcc_atomic_t {
   __gcc_atomic_t() _NOEXCEPT {}
-  explicit __gcc_atomic_t(_Tp value) _NOEXCEPT : __a_value(value) {}
+  _LIBCPP_CONSTEXPR explicit __gcc_atomic_t(_Tp value) _NOEXCEPT
+    : __a_value(value) {}
   _Tp __a_value;
 };
 #define _Atomic(x) __gcc_atomic::__gcc_atomic_t<x>
@@ -633,10 +634,6 @@
   __atomic_signal_fence(__gcc_atomic::__to_gcc_order(__order));
 }
 
-static inline bool __c11_atomic_is_lock_free(size_t __size) {
-  return __atomic_is_lock_free(__size, 0);
-}
-
 template <typename _Tp>
 static inline void __c11_atomic_store(volatile _Atomic(_Tp)* __a,  _Tp __val,
                                       memory_order __order) {
@@ -827,10 +824,16 @@
 
     _LIBCPP_INLINE_VISIBILITY
     bool is_lock_free() const volatile _NOEXCEPT
-        {return __c11_atomic_is_lock_free(sizeof(_Tp));}
+    {
+#if __has_feature(cxx_atomic)
+    return __c11_atomic_is_lock_free(sizeof(_Tp));
+#else
+    return __atomic_is_lock_free(sizeof(_Tp), 0);
+#endif
+    }
     _LIBCPP_INLINE_VISIBILITY
     bool is_lock_free() const _NOEXCEPT
-        {return __c11_atomic_is_lock_free(sizeof(_Tp));}
+        {return static_cast<__atomic_base const volatile*>(this)->is_lock_free();}
     _LIBCPP_INLINE_VISIBILITY
     void store(_Tp __d, memory_order __m = memory_order_seq_cst) volatile _NOEXCEPT
         {__c11_atomic_store(&__a_, __d, __m);}
diff --git a/include/cinttypes b/include/cinttypes
index 786692b..cfd763c 100644
--- a/include/cinttypes
+++ b/include/cinttypes
@@ -247,7 +247,9 @@
 
 using::imaxdiv_t;
 
+#undef imaxabs
 using::imaxabs;
+#undef imaxdiv
 using::imaxdiv;
 using::strtoimax;
 using::strtoumax;
diff --git a/include/clocale b/include/clocale
index f8b8f0d..05fa9c6 100644
--- a/include/clocale
+++ b/include/clocale
@@ -45,7 +45,9 @@
 _LIBCPP_BEGIN_NAMESPACE_STD
 
 using ::lconv;
+#ifndef _LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
 using ::setlocale;
+#endif
 using ::localeconv;
 
 _LIBCPP_END_NAMESPACE_STD
diff --git a/include/cmath b/include/cmath
index b340b4d..5f9aaed 100644
--- a/include/cmath
+++ b/include/cmath
@@ -654,6 +654,10 @@
 
 // abs
 
+#if defined(__sun__)
+using ::abs;
+#endif
+
 #if !defined(_AIX) && !defined(__sun__)
 inline _LIBCPP_INLINE_VISIBILITY
 float
diff --git a/include/cstdio b/include/cstdio
index 37814ef..d8ba6c2 100644
--- a/include/cstdio
+++ b/include/cstdio
@@ -144,30 +144,20 @@
 using ::fpos_t;
 using ::size_t;
 
-using ::remove;
-using ::rename;
-using ::tmpfile;
-using ::tmpnam;
 using ::fclose;
 using ::fflush;
-using ::fopen;
-using ::freopen;
 using ::setbuf;
 using ::setvbuf;
 using ::fprintf;
 using ::fscanf;
-using ::printf;
-using ::scanf;
 using ::snprintf;
 using ::sprintf;
 using ::sscanf;
 #ifndef _LIBCPP_MSVCRT
 using ::vfprintf;
 using ::vfscanf;
-using ::vscanf;
 using ::vsscanf;
 #endif // _LIBCPP_MSVCRT
-using ::vprintf;
 using ::vsnprintf;
 using ::vsprintf;
 using ::fgetc;
@@ -175,13 +165,7 @@
 using ::fputc;
 using ::fputs;
 using ::getc;
-using ::getchar;
-#if _LIBCPP_STD_VER <= 11
-using ::gets;
-#endif
 using ::putc;
-using ::putchar;
-using ::puts;
 using ::ungetc;
 using ::fread;
 using ::fwrite;
@@ -195,6 +179,31 @@
 using ::ferror;
 using ::perror;
 
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
+using ::fopen;
+using ::freopen;
+using ::remove;
+using ::rename;
+using ::tmpfile;
+using ::tmpnam;
+#endif
+
+#ifndef _LIBCPP_HAS_NO_STDIN
+using ::getchar;
+#if _LIBCPP_STD_VER <= 11
+using ::gets;
+#endif
+using ::scanf;
+using ::vscanf;
+#endif
+
+#ifndef _LIBCPP_HAS_NO_STDOUT
+using ::printf;
+using ::putchar;
+using ::puts;
+using ::vprintf;
+#endif
+
 _LIBCPP_END_NAMESPACE_STD
 
 #endif  // _LIBCPP_CSTDIO
diff --git a/include/cstdlib b/include/cstdlib
index 152b891..55e15c8 100644
--- a/include/cstdlib
+++ b/include/cstdlib
@@ -131,19 +131,27 @@
 using ::system;
 using ::bsearch;
 using ::qsort;
+#undef abs
 using ::abs;
+#undef labs
 using ::labs;
 #ifndef _LIBCPP_HAS_NO_LONG_LONG
+#undef llabs
 using ::llabs;
 #endif // _LIBCPP_HAS_NO_LONG_LONG
+#undef div
 using ::div;
+#undef ldiv
 using ::ldiv;
 #ifndef _LIBCPP_HAS_NO_LONG_LONG
+#undef lldiv
 using ::lldiv;
 #endif // _LIBCPP_HAS_NO_LONG_LONG
+#ifndef _LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
 using ::mblen;
 using ::mbtowc;
 using ::wctomb;
+#endif
 using ::mbstowcs;
 using ::wcstombs;
 #ifdef _LIBCPP_HAS_QUICK_EXIT
diff --git a/include/cstring b/include/cstring
index 21c9155..d60b992 100644
--- a/include/cstring
+++ b/include/cstring
@@ -102,7 +102,9 @@
 inline _LIBCPP_INLINE_VISIBILITY       char* strstr(      char* __s1, const char* __s2) {return ::strstr(__s1, __s2);}
 #endif
 
+#ifndef _LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
 using ::strtok;
+#endif
 using ::memset;
 using ::strerror;
 using ::strlen;
diff --git a/include/ctime b/include/ctime
index fc4eb26..da9e329 100644
--- a/include/ctime
+++ b/include/ctime
@@ -61,10 +61,12 @@
 using ::difftime;
 using ::mktime;
 using ::time;
+#ifndef _LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
 using ::asctime;
 using ::ctime;
 using ::gmtime;
 using ::localtime;
+#endif
 using ::strftime;
 
 _LIBCPP_END_NAMESPACE_STD
diff --git a/include/cwchar b/include/cwchar
index 9f51587..797a177 100644
--- a/include/cwchar
+++ b/include/cwchar
@@ -126,24 +126,18 @@
 using ::swprintf;
 using ::vfwprintf;
 using ::vswprintf;
-using ::vwprintf;
 #ifndef _LIBCPP_MSVCRT
 using ::swscanf;
 using ::vfwscanf;
 using ::vswscanf;
-using ::vwscanf;
 #endif // _LIBCPP_MSVCRT
-using ::wprintf;
-using ::wscanf;
 using ::fgetwc;
 using ::fgetws;
 using ::fputwc;
 using ::fputws;
 using ::fwide;
 using ::getwc;
-using ::getwchar;
 using ::putwc;
-using ::putwchar;
 using ::ungetwc;
 using ::wcstod;
 #ifndef _LIBCPP_MSVCRT
@@ -212,6 +206,20 @@
 using ::mbsrtowcs;
 using ::wcsrtombs;
 
+#ifndef _LIBCPP_HAS_NO_STDIN
+using ::getwchar;
+#ifndef _LIBCPP_MSVCRT
+using ::vwscanf;
+#endif // _LIBCPP_MSVCRT
+using ::wscanf;
+#endif
+
+#ifndef _LIBCPP_HAS_NO_STDOUT
+using ::putwchar;
+using ::vwprintf;
+using ::wprintf;
+#endif
+
 _LIBCPP_END_NAMESPACE_STD
 
 #endif  // _LIBCPP_CWCHAR
diff --git a/include/deque b/include/deque
index 6b419c5..87ff8bf 100644
--- a/include/deque
+++ b/include/deque
@@ -124,8 +124,7 @@
     iterator erase(const_iterator p);
     iterator erase(const_iterator f, const_iterator l);
     void swap(deque& c)
-        noexcept(!allocator_type::propagate_on_container_swap::value ||
-                 __is_nothrow_swappable<allocator_type>::value);
+        noexcept(allocator_traits<allocator_type>::is_always_equal::value);  // C++17
     void clear() noexcept;
 };
 
@@ -912,22 +911,10 @@
 
     static const difference_type __block_size = sizeof(value_type) < 256 ? 4096 / sizeof(value_type) : 16;
 
-    typedef typename __alloc_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-                rebind_alloc<pointer>
-#else
-                rebind_alloc<pointer>::other
-#endif
-                                                         __pointer_allocator;
+    typedef typename __rebind_alloc_helper<__alloc_traits, pointer>::type __pointer_allocator;
     typedef allocator_traits<__pointer_allocator>        __map_traits;
     typedef typename __map_traits::pointer               __map_pointer;
-    typedef typename __alloc_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-                rebind_alloc<const_pointer>
-#else
-                rebind_alloc<const_pointer>::other
-#endif
-                                                         __const_pointer_allocator;
+    typedef typename __rebind_alloc_helper<__alloc_traits, const_pointer>::type __const_pointer_allocator;
     typedef typename allocator_traits<__const_pointer_allocator>::const_pointer __map_const_pointer;
     typedef __split_buffer<pointer, __pointer_allocator> __map;
 
@@ -966,8 +953,12 @@
 
 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
     void swap(__deque_base& __c)
-        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<allocator_type>::value);
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT;
+#else
+        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 
+                    __is_nothrow_swappable<allocator_type>::value);
+#endif
 protected:
     void clear() _NOEXCEPT;
 
@@ -1003,26 +994,6 @@
     _LIBCPP_INLINE_VISIBILITY
     void __move_assign_alloc(__deque_base&, false_type) _NOEXCEPT
         {}
-
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(allocator_type& __x, allocator_type& __y)
-        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<allocator_type>::value)
-        {__swap_alloc(__x, __y, integral_constant<bool,
-                      __alloc_traits::propagate_on_container_swap::value>());}
-
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(allocator_type& __x, allocator_type& __y, true_type)
-        _NOEXCEPT_(__is_nothrow_swappable<allocator_type>::value)
-        {
-            using _VSTD::swap;
-            swap(__x, __y);
-        }
-
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(allocator_type&, allocator_type&, false_type)
-        _NOEXCEPT
-        {}
 };
 
 template <class _Tp, class _Allocator>
@@ -1146,13 +1117,17 @@
 template <class _Tp, class _Allocator>
 void
 __deque_base<_Tp, _Allocator>::swap(__deque_base& __c)
-        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value||
-                   __is_nothrow_swappable<allocator_type>::value)
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT
+#else
+        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 
+                    __is_nothrow_swappable<allocator_type>::value)
+#endif
 {
     __map_.swap(__c.__map_);
     _VSTD::swap(__start_, __c.__start_);
     _VSTD::swap(size(), __c.size());
-    __swap_alloc(__alloc(), __c.__alloc());
+    __swap_allocator(__alloc(), __c.__alloc());
 }
 
 template <class _Tp, class _Allocator>
@@ -1354,8 +1329,12 @@
     iterator erase(const_iterator __f, const_iterator __l);
 
     void swap(deque& __c)
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT;
+#else
         _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
                    __is_nothrow_swappable<allocator_type>::value);
+#endif
     void clear() _NOEXCEPT;
 
     _LIBCPP_INLINE_VISIBILITY
@@ -2050,7 +2029,6 @@
         if (__n > __front_spare())
             __add_front_capacity(__n - __front_spare());
         // __n <= __front_spare()
-        size_type __old_n = __n;
         iterator __old_begin = __base::begin();
         iterator __i = __old_begin;
         if (__n > __pos)
@@ -2075,7 +2053,6 @@
         if (__n > __back_capacity)
             __add_back_capacity(__n - __back_capacity);
         // __n <= __back_capacity
-        size_type __old_n = __n;
         iterator __old_end = __base::end();
         iterator __i = __old_end;
         size_type __de = __base::size() - __pos;
@@ -2140,7 +2117,6 @@
         if (__n > __front_spare())
             __add_front_capacity(__n - __front_spare());
         // __n <= __front_spare()
-        size_type __old_n = __n;
         iterator __old_begin = __base::begin();
         iterator __i = __old_begin;
         _BiIter __m = __f;
@@ -2171,7 +2147,6 @@
         if (__n > __back_capacity)
             __add_back_capacity(__n - __back_capacity);
         // __n <= __back_capacity
-        size_type __old_n = __n;
         iterator __old_end = __base::end();
         iterator __i = __old_end;
         _BiIter __m = __l;
@@ -2288,19 +2263,14 @@
         __split_buffer<pointer, typename __base::__pointer_allocator&>
             __buf(max<size_type>(2 * __base::__map_.capacity(), 1),
                   0, __base::__map_.__alloc());
-#ifndef _LIBCPP_NO_EXCEPTIONS
-        try
-        {
-#endif  // _LIBCPP_NO_EXCEPTIONS
-            __buf.push_back(__alloc_traits::allocate(__a, __base::__block_size));
-#ifndef _LIBCPP_NO_EXCEPTIONS
-        }
-        catch (...)
-        {
-            __alloc_traits::deallocate(__a, __buf.front(), __base::__block_size);
-            throw;
-        }
-#endif  // _LIBCPP_NO_EXCEPTIONS
+
+        typedef __allocator_destructor<_Allocator> _Dp;
+        unique_ptr<pointer, _Dp> __hold(
+            __alloc_traits::allocate(__a, __base::__block_size),
+                _Dp(__a, __base::__block_size));
+        __buf.push_back(__hold.get());
+        __hold.release();
+    
         for (typename __base::__map_pointer __i = __base::__map_.begin();
                 __i != __base::__map_.end(); ++__i)
             __buf.push_back(*__i);
@@ -2436,19 +2406,14 @@
             __buf(max<size_type>(2* __base::__map_.capacity(), 1),
                   __base::__map_.size(),
                   __base::__map_.__alloc());
-#ifndef _LIBCPP_NO_EXCEPTIONS
-        try
-        {
-#endif  // _LIBCPP_NO_EXCEPTIONS
-            __buf.push_back(__alloc_traits::allocate(__a, __base::__block_size));
-#ifndef _LIBCPP_NO_EXCEPTIONS
-        }
-        catch (...)
-        {
-            __alloc_traits::deallocate(__a, __buf.back(), __base::__block_size);
-            throw;
-        }
-#endif  // _LIBCPP_NO_EXCEPTIONS
+
+        typedef __allocator_destructor<_Allocator> _Dp;
+        unique_ptr<pointer, _Dp> __hold(
+            __alloc_traits::allocate(__a, __base::__block_size),
+                _Dp(__a, __base::__block_size));
+        __buf.push_back(__hold.get());
+        __hold.release();
+
         for (typename __base::__map_pointer __i = __base::__map_.end();
                 __i != __base::__map_.begin();)
             __buf.push_front(*--__i);
@@ -2716,12 +2681,11 @@
 typename deque<_Tp, _Allocator>::iterator
 deque<_Tp, _Allocator>::erase(const_iterator __f)
 {
-    difference_type __n = 1;
     iterator __b = __base::begin();
     difference_type __pos = __f - __b;
     iterator __p = __b + __pos;
     allocator_type& __a = __base::__alloc();
-    if (__pos < (__base::size() - 1) / 2)
+    if (__pos <= (__base::size() - 1) / 2)
     {   // erase from front
         _VSTD::move_backward(__b, __p, _VSTD::next(__p));
         __alloc_traits::destroy(__a, _VSTD::addressof(*__b));
@@ -2759,7 +2723,7 @@
     if (__n > 0)
     {
         allocator_type& __a = __base::__alloc();
-        if (__pos < (__base::size() - __n) / 2)
+        if (__pos <= (__base::size() - __n) / 2)
         {   // erase from front
             iterator __i = _VSTD::move_backward(__b, __p, __p + __n);
             for (; __b != __i; ++__b)
@@ -2815,8 +2779,12 @@
 inline _LIBCPP_INLINE_VISIBILITY
 void
 deque<_Tp, _Allocator>::swap(deque& __c)
-        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<allocator_type>::value)
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT
+#else
+        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 
+                    __is_nothrow_swappable<allocator_type>::value)
+#endif
 {
     __base::swap(__c);
 }
diff --git a/include/exception b/include/exception
index cad802e..5a905e7 100644
--- a/include/exception
+++ b/include/exception
@@ -48,7 +48,8 @@
 terminate_handler get_terminate() noexcept;
 [[noreturn]] void terminate() noexcept;
 
-bool uncaught_exception() noexcept;
+bool uncaught_exception()  noexcept;
+int  uncaught_exceptions() noexcept;  // C++17
 
 typedef unspecified exception_ptr;
 
@@ -115,6 +116,7 @@
 _LIBCPP_NORETURN _LIBCPP_FUNC_VIS void terminate() _NOEXCEPT;
 
 _LIBCPP_FUNC_VIS bool uncaught_exception() _NOEXCEPT;
+_LIBCPP_FUNC_VIS int uncaught_exceptions() _NOEXCEPT;
 
 class _LIBCPP_TYPE_VIS exception_ptr;
 
@@ -193,6 +195,7 @@
 throw_with_nested(_Tp&& __t, typename enable_if<
                   is_class<typename remove_reference<_Tp>::type>::value &&
                   !is_base_of<nested_exception, typename remove_reference<_Tp>::type>::value
+                  && !__libcpp_is_final<typename remove_reference<_Tp>::type>::value
                                     >::type* = 0)
 #else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 throw_with_nested (_Tp& __t, typename enable_if<
@@ -212,6 +215,7 @@
 throw_with_nested(_Tp&& __t, typename enable_if<
                   !is_class<typename remove_reference<_Tp>::type>::value ||
                   is_base_of<nested_exception, typename remove_reference<_Tp>::type>::value
+                  || __libcpp_is_final<typename remove_reference<_Tp>::type>::value
                                     >::type* = 0)
 #else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 throw_with_nested (_Tp& __t, typename enable_if<
diff --git a/include/experimental/algorithm b/include/experimental/algorithm
new file mode 100644
index 0000000..ffaa793
--- /dev/null
+++ b/include/experimental/algorithm
@@ -0,0 +1,120 @@
+// -*- C++ -*-
+//===-------------------------- algorithm ---------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP_EXPERIMENTAL_ALGORITHM
+#define _LIBCPP_EXPERIMENTAL_ALGORITHM
+
+/*
+   experimental/algorithm synopsis
+
+#include <algorithm>
+
+namespace std {
+namespace experimental {
+inline namespace fundamentals_v1 {
+
+template <class ForwardIterator, class Searcher>
+ForwardIterator search(ForwardIterator first, ForwardIterator last,
+                       const Searcher &searcher);
+template <class PopulationIterator, class SampleIterator, class Distance,
+          class UniformRandomNumberGenerator>
+SampleIterator sample(PopulationIterator first, PopulationIterator last,
+                      SampleIterator out, Distance n,
+                      UniformRandomNumberGenerator &&g);
+
+} // namespace fundamentals_v1
+} // namespace experimental
+} // namespace std
+
+*/
+
+#include <experimental/__config>
+#include <algorithm>
+#include <type_traits>
+
+#include <__undef_min_max>
+
+#include <__debug>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_BEGIN_NAMESPACE_LFTS
+
+
+template <class _ForwardIterator, class _Searcher>
+_LIBCPP_INLINE_VISIBILITY
+_ForwardIterator search(_ForwardIterator __f, _ForwardIterator __l, const _Searcher &__s)
+{ return __s(__f, __l); }
+
+
+template <class _PopulationIterator, class _SampleIterator, class _Distance,
+          class _UniformRandomNumberGenerator>
+_LIBCPP_INLINE_VISIBILITY
+_SampleIterator __sample(_PopulationIterator __first,
+                         _PopulationIterator __last, _SampleIterator __out,
+                         _Distance __n,
+                         _UniformRandomNumberGenerator &&__g,
+                         input_iterator_tag) {
+
+  _Distance __k = 0;
+  for (; __first != __last && __k < __n; ++__first, (void)++__k)
+    __out[__k] = *__first;
+  _Distance __sz = __k;
+  for (; __first != __last; ++__first, (void)++__k) {
+    _Distance __r = _VSTD::uniform_int_distribution<_Distance>(0, __k)(__g);
+    if (__r < __sz)
+      __out[__r] = *__first;
+  }
+  return __out + _VSTD::min(__n, __k);
+}
+
+template <class _PopulationIterator, class _SampleIterator, class _Distance,
+          class _UniformRandomNumberGenerator>
+_LIBCPP_INLINE_VISIBILITY
+_SampleIterator __sample(_PopulationIterator __first,
+                         _PopulationIterator __last, _SampleIterator __out,
+                         _Distance __n,
+                         _UniformRandomNumberGenerator &&__g,
+                         forward_iterator_tag) {
+  _Distance __unsampled_sz = _VSTD::distance(__first, __last);
+  for (__n = _VSTD::min(__n, __unsampled_sz); __n != 0; ++__first) {
+    _Distance __r =
+        _VSTD::uniform_int_distribution<_Distance>(0, --__unsampled_sz)(__g);
+    if (__r < __n) {
+      *__out++ = *__first;
+      --__n;
+    }
+  }
+  return __out;
+}
+
+template <class _PopulationIterator, class _SampleIterator, class _Distance,
+          class _UniformRandomNumberGenerator>
+_LIBCPP_INLINE_VISIBILITY
+_SampleIterator sample(_PopulationIterator __first,
+                         _PopulationIterator __last, _SampleIterator __out,
+                         _Distance __n, _UniformRandomNumberGenerator &&__g) {
+  typedef typename iterator_traits<_PopulationIterator>::iterator_category
+        _PopCategory;
+  typedef typename iterator_traits<_PopulationIterator>::difference_type
+        _Difference;
+  typedef typename common_type<_Distance, _Difference>::type _CommonType;
+  _LIBCPP_ASSERT(__n >= 0, "N must be a positive number.");
+  return _VSTD_LFTS::__sample(
+      __first, __last, __out, _CommonType(__n),
+      _VSTD::forward<_UniformRandomNumberGenerator>(__g),
+      _PopCategory());
+}
+
+_LIBCPP_END_NAMESPACE_LFTS
+
+#endif /* _LIBCPP_EXPERIMENTAL_ALGORITHM */
diff --git a/include/experimental/any b/include/experimental/any
new file mode 100644
index 0000000..a38397a
--- /dev/null
+++ b/include/experimental/any
@@ -0,0 +1,592 @@
+// -*- C++ -*-
+//===------------------------------ any -----------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP_EXPERIMENTAL_ANY
+#define _LIBCPP_EXPERIMENTAL_ANY
+
+/*
+   experimental/any synopsis
+
+namespace std {
+namespace experimental {
+inline namespace fundamentals_v1 {
+
+  class bad_any_cast : public bad_cast
+  {
+  public:
+    virtual const char* what() const noexcept;
+  };
+
+  class any
+  {
+  public:
+
+    // 6.3.1 any construct/destruct
+    any() noexcept;
+
+    any(const any& other);
+    any(any&& other) noexcept;
+
+    template <class ValueType>
+      any(ValueType&& value);
+
+    ~any();
+
+    // 6.3.2 any assignments
+    any& operator=(const any& rhs);
+    any& operator=(any&& rhs) noexcept;
+
+    template <class ValueType>
+      any& operator=(ValueType&& rhs);
+
+    // 6.3.3 any modifiers
+    void clear() noexcept;
+    void swap(any& rhs) noexcept;
+
+    // 6.3.4 any observers
+    bool empty() const noexcept;
+    const type_info& type() const noexcept;
+  };
+
+   // 6.4 Non-member functions
+  void swap(any& x, any& y) noexcept;
+
+  template<class ValueType>
+    ValueType any_cast(const any& operand);
+  template<class ValueType>
+    ValueType any_cast(any& operand);
+  template<class ValueType>
+    ValueType any_cast(any&& operand);
+
+  template<class ValueType>
+    const ValueType* any_cast(const any* operand) noexcept;
+  template<class ValueType>
+    ValueType* any_cast(any* operand) noexcept;
+
+} // namespace fundamentals_v1
+} // namespace experimental
+} // namespace std
+
+*/
+
+#include <experimental/__config>
+#include <memory>
+#include <new>
+#include <typeinfo>
+#include <type_traits>
+#include <cstdlib>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_BEGIN_NAMESPACE_LFTS
+
+class _LIBCPP_EXCEPTION_ABI bad_any_cast : public bad_cast
+{
+public:
+     //TODO(EricWF) Enable or delete these.
+    //bad_any_cast() _NOEXCEPT;
+    //virtual ~bad_any_cast() _NOEXCEPT;
+    virtual const char* what() const _NOEXCEPT;
+};
+
+#if _LIBCPP_STD_VER > 11                                            // C++ > 11
+
+_LIBCPP_NORETURN _LIBCPP_INLINE_VISIBILITY
+inline void __throw_bad_any_cast()
+{
+#ifndef _LIBCPP_NO_EXCEPTIONS
+    throw bad_any_cast();
+#else
+    _VSTD::abort();
+#endif
+}
+
+// Forward declarations
+class any;
+
+template <class _ValueType>
+typename add_pointer<typename add_const<_ValueType>::type>::type
+any_cast(any const *) _NOEXCEPT;
+
+template <class _ValueType>
+typename add_pointer<_ValueType>::type
+any_cast(any *) _NOEXCEPT;
+
+namespace __any_imp
+{
+  typedef typename aligned_storage<3*sizeof(void*), alignment_of<void*>::value>::type
+    _Buffer;
+
+  template <class _Tp>
+  struct _IsSmallObject
+    : public integral_constant<bool
+        , sizeof(_Tp) <= sizeof(_Buffer)
+          && alignment_of<_Buffer>::value
+             % alignment_of<_Tp>::value == 0
+          && is_nothrow_move_constructible<_Tp>::value
+        >
+  {};
+
+  enum class _Action
+  {
+    _Destroy,
+    _Copy,
+    _Move,
+    _Get,
+    _TypeInfo
+  };
+
+  template <class _Tp>
+  struct _SmallHandler;
+
+  template <class _Tp>
+  struct _LargeHandler;
+
+  template <class _Tp>
+  using _Handler = typename conditional<_IsSmallObject<_Tp>::value
+                                      , _SmallHandler<_Tp>
+                                      , _LargeHandler<_Tp>
+                                    >::type;
+  template <class _ValueType>
+  using _EnableIfNotAny = typename
+    enable_if<
+      !is_same<typename decay<_ValueType>::type, any>::value
+    >::type;
+
+} // namespace __any_imp
+
+class any
+{
+public:
+  // 6.3.1 any construct/destruct
+  _LIBCPP_INLINE_VISIBILITY
+  any() _NOEXCEPT : __h(nullptr) {}
+
+  _LIBCPP_INLINE_VISIBILITY
+  any(any const & __other) : __h(nullptr)
+  {
+    if (__other.__h) __other.__call(_Action::_Copy, this);
+  }
+
+  _LIBCPP_INLINE_VISIBILITY
+  any(any && __other) _NOEXCEPT : __h(nullptr)
+  {
+    if (__other.__h) __other.__call(_Action::_Move, this);
+  }
+
+  template <
+      class _ValueType
+    , class = __any_imp::_EnableIfNotAny<_ValueType>
+    >
+  any(_ValueType && __value);
+
+  _LIBCPP_INLINE_VISIBILITY
+  ~any()
+  {
+    this->clear();
+  }
+
+  // 6.3.2 any assignments
+  _LIBCPP_INLINE_VISIBILITY
+  any & operator=(any const & __rhs)
+  {
+    any(__rhs).swap(*this);
+    return *this;
+  }
+
+  _LIBCPP_INLINE_VISIBILITY
+  any & operator=(any && __rhs) _NOEXCEPT
+  {
+    any(_VSTD::move(__rhs)).swap(*this);
+    return *this;
+  }
+
+  template <
+      class _ValueType
+    , class = __any_imp::_EnableIfNotAny<_ValueType>
+    >
+  any & operator=(_ValueType && __rhs);
+
+  // 6.3.3 any modifiers
+  _LIBCPP_INLINE_VISIBILITY
+  void clear() _NOEXCEPT
+  {
+    if (__h) this->__call(_Action::_Destroy);
+  }
+
+  void swap(any & __rhs) _NOEXCEPT;
+
+  // 6.3.4 any observers
+  _LIBCPP_INLINE_VISIBILITY
+  bool empty() const _NOEXCEPT
+  {
+    return __h == nullptr;
+  }
+
+#if !defined(_LIBCPP_NO_RTTI)
+  _LIBCPP_INLINE_VISIBILITY
+  const type_info & type() const _NOEXCEPT
+  {
+    if (__h) {
+        return *static_cast<type_info const *>(this->__call(_Action::_TypeInfo));
+    } else {
+        return typeid(void);
+    }
+  }
+#endif
+
+private:
+    typedef __any_imp::_Action _Action;
+
+    typedef void* (*_HandleFuncPtr)(_Action, any const *, any *, const type_info *);
+
+    union _Storage
+    {
+        void *  __ptr;
+        __any_imp::_Buffer __buf;
+    };
+
+    _LIBCPP_ALWAYS_INLINE
+    void * __call(_Action __a, any * __other = nullptr,
+                  type_info const * __info = nullptr) const
+    {
+        return __h(__a, this, __other, __info);
+    }
+
+    _LIBCPP_ALWAYS_INLINE
+    void * __call(_Action __a, any * __other = nullptr,
+                  type_info const * __info = nullptr)
+    {
+        return __h(__a, this, __other, __info);
+    }
+
+    template <class>
+    friend struct __any_imp::_SmallHandler;
+    template <class>
+    friend struct __any_imp::_LargeHandler;
+
+    template <class _ValueType>
+    friend typename add_pointer<typename add_const<_ValueType>::type>::type
+    any_cast(any const *) _NOEXCEPT;
+
+    template <class _ValueType>
+    friend typename add_pointer<_ValueType>::type
+    any_cast(any *) _NOEXCEPT;
+
+    _HandleFuncPtr __h;
+    _Storage __s;
+};
+
+namespace __any_imp
+{
+
+  template <class _Tp>
+  struct _LIBCPP_TYPE_VIS_ONLY _SmallHandler
+  {
+     _LIBCPP_INLINE_VISIBILITY
+     static void* __handle(_Action __act, any const * __this, any * __other,
+                           type_info const * __info)
+     {
+        switch (__act)
+        {
+        case _Action::_Destroy:
+          __destroy(const_cast<any &>(*__this));
+          return nullptr;
+        case _Action::_Copy:
+            __copy(*__this, *__other);
+            return nullptr;
+        case _Action::_Move:
+          __move(const_cast<any &>(*__this), *__other);
+          return nullptr;
+        case _Action::_Get:
+            return __get(const_cast<any &>(*__this), __info);
+        case _Action::_TypeInfo:
+          return __type_info();
+        }
+    }
+
+    template <class _Up>
+    _LIBCPP_INLINE_VISIBILITY
+    static void __create(any & __dest, _Up && __v)
+    {
+        ::new (static_cast<void*>(&__dest.__s.__buf)) _Tp(_VSTD::forward<_Up>(__v));
+        __dest.__h = &_SmallHandler::__handle;
+    }
+
+  private:
+    _LIBCPP_ALWAYS_INLINE _LIBCPP_INLINE_VISIBILITY
+    static void __destroy(any & __this)
+    {
+        _Tp & __value = *static_cast<_Tp *>(static_cast<void*>(&__this.__s.__buf));
+        __value.~_Tp();
+        __this.__h = nullptr;
+    }
+
+    _LIBCPP_ALWAYS_INLINE _LIBCPP_INLINE_VISIBILITY
+    static void __copy(any const & __this, any & __dest)
+    {
+        _SmallHandler::__create(__dest, *static_cast<_Tp const *>(
+            static_cast<void const *>(&__this.__s.__buf)));
+    }
+
+    _LIBCPP_ALWAYS_INLINE _LIBCPP_INLINE_VISIBILITY
+    static void __move(any & __this, any & __dest)
+    {
+        _SmallHandler::__create(__dest, _VSTD::move(
+            *static_cast<_Tp*>(static_cast<void*>(&__this.__s.__buf))));
+        __destroy(__this);
+    }
+
+    _LIBCPP_ALWAYS_INLINE _LIBCPP_INLINE_VISIBILITY
+    static void* __get(any & __this, type_info const * __info)
+    {
+#if !defined(_LIBCPP_NO_RTTI)
+        if (typeid(_Tp) == *__info) {
+            return static_cast<void*>(&__this.__s.__buf);
+        }
+        return nullptr;
+#else
+        return static_cast<void*>(&__this.__s.__buf);
+#endif
+    }
+
+    _LIBCPP_ALWAYS_INLINE _LIBCPP_INLINE_VISIBILITY
+    static void* __type_info()
+    {
+#if !defined(_LIBCPP_NO_RTTI)
+        return const_cast<void*>(static_cast<void const *>(&typeid(_Tp)));
+#else
+        return nullptr;
+#endif
+    }
+  };
+
+  template <class _Tp>
+  struct _LIBCPP_TYPE_VIS_ONLY _LargeHandler
+  {
+    _LIBCPP_INLINE_VISIBILITY
+    static void* __handle(_Action __act, any const * __this, any * __other,
+                          type_info const * __info)
+    {
+        switch (__act)
+        {
+        case _Action::_Destroy:
+          __destroy(const_cast<any &>(*__this));
+          return nullptr;
+        case _Action::_Copy:
+          __copy(*__this, *__other);
+          return nullptr;
+        case _Action::_Move:
+          __move(const_cast<any &>(*__this), *__other);
+          return nullptr;
+        case _Action::_Get:
+            return __get(const_cast<any &>(*__this), __info);
+        case _Action::_TypeInfo:
+          return __type_info();
+        }
+    }
+
+    template <class _Up>
+    _LIBCPP_INLINE_VISIBILITY
+    static void __create(any & __dest, _Up && __v)
+    {
+        typedef allocator<_Tp> _Alloc;
+        typedef __allocator_destructor<_Alloc> _Dp;
+        _Alloc __a;
+        unique_ptr<_Tp, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
+        ::new ((void*)__hold.get()) _Tp(_VSTD::forward<_Up>(__v));
+        __dest.__s.__ptr = __hold.release();
+        __dest.__h = &_LargeHandler::__handle;
+    }
+
+  private:
+
+    _LIBCPP_ALWAYS_INLINE _LIBCPP_INLINE_VISIBILITY
+    static void __destroy(any & __this)
+    {
+        delete static_cast<_Tp*>(__this.__s.__ptr);
+        __this.__h = nullptr;
+    }
+
+    _LIBCPP_ALWAYS_INLINE _LIBCPP_INLINE_VISIBILITY
+    static void __copy(any const & __this, any & __dest)
+    {
+        _LargeHandler::__create(__dest, *static_cast<_Tp const *>(__this.__s.__ptr));
+    }
+
+    _LIBCPP_ALWAYS_INLINE _LIBCPP_INLINE_VISIBILITY
+    static void __move(any & __this, any & __dest)
+    {
+      __dest.__s.__ptr = __this.__s.__ptr;
+      __dest.__h = &_LargeHandler::__handle;
+      __this.__h = nullptr;
+    }
+
+    _LIBCPP_ALWAYS_INLINE _LIBCPP_INLINE_VISIBILITY
+    static void* __get(any & __this, type_info const * __info)
+    {
+#if !defined(_LIBCPP_NO_RTTI)
+        if (typeid(_Tp) == *__info) {
+            return static_cast<void*>(__this.__s.__ptr);
+        }
+        return nullptr;
+#else
+        return static_cast<void*>(__this.__s.__ptr);
+#endif
+    }
+
+    _LIBCPP_ALWAYS_INLINE _LIBCPP_INLINE_VISIBILITY
+    static void* __type_info()
+    {
+#if !defined(_LIBCPP_NO_RTTI)
+        return const_cast<void*>(static_cast<void const *>(&typeid(_Tp)));
+#else
+        return nullptr;
+#endif
+    }
+  };
+
+} // namespace __any_imp
+
+
+template <class _ValueType, class>
+_LIBCPP_INLINE_VISIBILITY
+any::any(_ValueType && __v) : __h(nullptr)
+{
+  typedef typename decay<_ValueType>::type _Tp;
+  static_assert(is_copy_constructible<_Tp>::value,
+                "_ValueType must be CopyConstructible.");
+  typedef __any_imp::_Handler<_Tp> _HandlerType;
+  _HandlerType::__create(*this, _VSTD::forward<_ValueType>(__v));
+}
+
+template <class _ValueType, class>
+_LIBCPP_INLINE_VISIBILITY
+any & any::operator=(_ValueType && __v)
+{
+  typedef typename decay<_ValueType>::type _Tp;
+  static_assert(is_copy_constructible<_Tp>::value,
+                "_ValueType must be CopyConstructible.");
+  any(_VSTD::forward<_ValueType>(__v)).swap(*this);
+  return *this;
+}
+
+inline _LIBCPP_INLINE_VISIBILITY
+void any::swap(any & __rhs) _NOEXCEPT
+{
+    if (__h && __rhs.__h) {
+        any __tmp;
+        __rhs.__call(_Action::_Move, &__tmp);
+        this->__call(_Action::_Move, &__rhs);
+        __tmp.__call(_Action::_Move, this);
+    }
+    else if (__h) {
+        this->__call(_Action::_Move, &__rhs);
+    }
+    else if (__rhs.__h) {
+        __rhs.__call(_Action::_Move, this);
+    }
+}
+
+// 6.4 Non-member functions
+
+inline _LIBCPP_INLINE_VISIBILITY
+void swap(any & __lhs, any & __rhs) _NOEXCEPT
+{
+    __lhs.swap(__rhs);
+}
+
+template <class _ValueType>
+_LIBCPP_INLINE_VISIBILITY
+_ValueType any_cast(any const & __v)
+{
+    static_assert(
+        is_reference<_ValueType>::value
+        || is_copy_constructible<_ValueType>::value,
+        "_ValueType is required to be a reference or a CopyConstructible type.");
+    typedef typename add_const<typename remove_reference<_ValueType>::type>::type
+            _Tp;
+    _Tp * __tmp = any_cast<_Tp>(&__v);
+    if (__tmp == nullptr)
+        __throw_bad_any_cast();
+    return *__tmp;
+}
+
+template <class _ValueType>
+_LIBCPP_INLINE_VISIBILITY
+_ValueType any_cast(any & __v)
+{
+    static_assert(
+        is_reference<_ValueType>::value
+        || is_copy_constructible<_ValueType>::value,
+        "_ValueType is required to be a reference or a CopyConstructible type.");
+    typedef typename remove_reference<_ValueType>::type _Tp;
+    _Tp * __tmp = any_cast<_Tp>(&__v);
+    if (__tmp == nullptr)
+        __throw_bad_any_cast();
+    return *__tmp;
+}
+
+template <class _ValueType>
+_LIBCPP_INLINE_VISIBILITY
+_ValueType any_cast(any && __v)
+{
+    static_assert(
+        is_reference<_ValueType>::value
+        || is_copy_constructible<_ValueType>::value,
+        "_ValueType is required to be a reference or a CopyConstructible type.");
+    typedef typename remove_reference<_ValueType>::type _Tp;
+    _Tp * __tmp = any_cast<_Tp>(&__v);
+    if (__tmp == nullptr)
+        __throw_bad_any_cast();
+    return *__tmp;
+}
+
+template <class _ValueType>
+inline _LIBCPP_INLINE_VISIBILITY
+typename add_pointer<typename add_const<_ValueType>::type>::type
+any_cast(any const * __any) _NOEXCEPT
+{
+    static_assert(!is_reference<_ValueType>::value,
+                  "_ValueType may not be a reference.");
+    return any_cast<_ValueType>(const_cast<any *>(__any));
+}
+
+template <class _ValueType>
+_LIBCPP_INLINE_VISIBILITY
+typename add_pointer<_ValueType>::type
+any_cast(any * __any) _NOEXCEPT
+{
+    using __any_imp::_Action;
+    static_assert(!is_reference<_ValueType>::value,
+                  "_ValueType may not be a reference.");
+    typedef typename add_pointer<_ValueType>::type _ReturnType;
+    if (__any && __any->__h) {
+
+        return static_cast<_ReturnType>(
+            __any->__call(_Action::_Get, nullptr,
+#if !defined(_LIBCPP_NO_RTTI)
+                &typeid(_ValueType)
+#else
+                nullptr
+#endif
+        ));
+
+    }
+    return nullptr;
+}
+
+#endif // _LIBCPP_STD_VER > 11
+
+_LIBCPP_END_NAMESPACE_LFTS
+
+#endif // _LIBCPP_EXPERIMENTAL_ANY
diff --git a/include/experimental/chrono b/include/experimental/chrono
index 738ded8..ca9e5f8 100644
--- a/include/experimental/chrono
+++ b/include/experimental/chrono
@@ -45,12 +45,12 @@
 
 _LIBCPP_BEGIN_NAMESPACE_CHRONO_LFTS
 
-#if __has_feature(cxx_variable_templates)
+#ifndef _LIBCPP_HAS_NO_VARIABLE_TEMPLATES
 
 template <class _Rep> _LIBCPP_CONSTEXPR bool treat_as_floating_point_v
     = treat_as_floating_point<_Rep>::value;
 
-#endif /* __has_feature(cxx_variable_templates) */
+#endif /* _LIBCPP_HAS_NO_VARIABLE_TEMPLATES */
 
 _LIBCPP_END_NAMESPACE_CHRONO_LFTS
 
diff --git a/include/experimental/functional b/include/experimental/functional
new file mode 100644
index 0000000..f5a905f
--- /dev/null
+++ b/include/experimental/functional
@@ -0,0 +1,133 @@
+// -*- C++ -*-
+//===-------------------------- functional --------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP_EXPERIMENTAL_FUNCTIONAL
+#define _LIBCPP_EXPERIMENTAL_FUNCTIONAL
+
+/*
+   experimental/functional synopsis
+
+#include <algorithm>
+
+namespace std {
+namespace experimental {
+inline namespace fundamentals_v1 {
+
+    // See C++14 §20.9.9, Function object binders
+    template <class T> constexpr bool is_bind_expression_v
+      = is_bind_expression<T>::value;
+    template <class T> constexpr int is_placeholder_v
+      = is_placeholder<T>::value;
+
+    // 4.2, Class template function
+    template<class> class function; // undefined
+    template<class R, class... ArgTypes> class function<R(ArgTypes...)>;
+
+    template<class R, class... ArgTypes>
+    void swap(function<R(ArgTypes...)>&, function<R(ArgTypes...)>&);
+
+    template<class R, class... ArgTypes>
+    bool operator==(const function<R(ArgTypes...)>&, nullptr_t) noexcept;
+    template<class R, class... ArgTypes>
+    bool operator==(nullptr_t, const function<R(ArgTypes...)>&) noexcept;
+    template<class R, class... ArgTypes>
+    bool operator!=(const function<R(ArgTypes...)>&, nullptr_t) noexcept;
+    template<class R, class... ArgTypes>
+    bool operator!=(nullptr_t, const function<R(ArgTypes...)>&) noexcept;
+
+    // 4.3, Searchers
+    template<class ForwardIterator, class BinaryPredicate = equal_to<>>
+      class default_searcher;
+
+    template<class RandomAccessIterator,
+             class Hash = hash<typename iterator_traits<RandomAccessIterator>::value_type>,
+             class BinaryPredicate = equal_to<>>
+      class boyer_moore_searcher;
+
+    template<class RandomAccessIterator,
+             class Hash = hash<typename iterator_traits<RandomAccessIterator>::value_type>,
+             class BinaryPredicate = equal_to<>>
+      class boyer_moore_horspool_searcher;
+
+    template<class ForwardIterator, class BinaryPredicate = equal_to<>>
+    default_searcher<ForwardIterator, BinaryPredicate>
+    make_default_searcher(ForwardIterator pat_first, ForwardIterator pat_last,
+                          BinaryPredicate pred = BinaryPredicate());
+
+    template<class RandomAccessIterator,
+             class Hash = hash<typename iterator_traits<RandomAccessIterator>::value_type>,
+             class BinaryPredicate = equal_to<>>
+    boyer_moore_searcher<RandomAccessIterator, Hash, BinaryPredicate>
+    make_boyer_moore_searcher(
+        RandomAccessIterator pat_first, RandomAccessIterator pat_last,
+        Hash hf = Hash(), BinaryPredicate pred = BinaryPredicate());
+
+    template<class RandomAccessIterator,
+             class Hash = hash<typename iterator_traits<RandomAccessIterator>::value_type>,
+             class BinaryPredicate = equal_to<>>
+    boyer_moore_horspool_searcher<RandomAccessIterator, Hash, BinaryPredicate>
+    make_boyer_moore_horspool_searcher(
+        RandomAccessIterator pat_first, RandomAccessIterator pat_last,
+        Hash hf = Hash(), BinaryPredicate pred = BinaryPredicate());
+
+  } // namespace fundamentals_v1
+  } // namespace experimental
+
+  template<class R, class... ArgTypes, class Alloc>
+  struct uses_allocator<experimental::function<R(ArgTypes...)>, Alloc>;
+
+} // namespace std
+
+*/
+
+#include <experimental/__config>
+#include <functional>
+#include <algorithm>
+
+#include <__undef_min_max>
+
+#include <__debug>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_BEGIN_NAMESPACE_LFTS
+
+// default searcher
+template<class _ForwardIterator, class _BinaryPredicate = equal_to<>>
+class default_searcher {
+public:
+    default_searcher(_ForwardIterator __f, _ForwardIterator __l, 
+                       _BinaryPredicate __p = _BinaryPredicate())
+        : __first_(__f), __last_(__l), __pred_(__p) {}
+
+    template <typename _ForwardIterator2>
+    _ForwardIterator2 operator () (_ForwardIterator2 __f, _ForwardIterator2 __l) const {
+        return _VSTD::search(__f, __l, __first_, __last_, __pred_);
+        }
+
+private:
+    _ForwardIterator __first_;
+    _ForwardIterator __last_;
+    _BinaryPredicate __pred_;
+    };
+
+template<class _ForwardIterator, class _BinaryPredicate = equal_to<>>
+default_searcher<_ForwardIterator, _BinaryPredicate>
+make_default_searcher( _ForwardIterator __f, _ForwardIterator __l, _BinaryPredicate __p = _BinaryPredicate ())
+{
+    return default_searcher<_ForwardIterator, _BinaryPredicate>(__f, __l, __p);
+}
+
+
+_LIBCPP_END_NAMESPACE_LFTS
+
+#endif /* _LIBCPP_EXPERIMENTAL_FUNCTIONAL */
diff --git a/include/experimental/ratio b/include/experimental/ratio
index a393cef..757f24e 100644
--- a/include/experimental/ratio
+++ b/include/experimental/ratio
@@ -48,7 +48,7 @@
 
 _LIBCPP_BEGIN_NAMESPACE_LFTS
 
-#if __has_feature(cxx_variable_templates)
+#ifndef _LIBCPP_HAS_NO_VARIABLE_TEMPLATES
 
 template <class _R1, class _R2> _LIBCPP_CONSTEXPR bool ratio_equal_v
     = ratio_equal<_R1, _R2>::value;
@@ -68,10 +68,10 @@
 template <class _R1, class _R2> _LIBCPP_CONSTEXPR bool ratio_greater_equal_v
     = ratio_greater_equal<_R1, _R2>::value;
 
-#endif /* __has_feature(cxx_variable_templates) */
+#endif /* _LIBCPP_HAS_NO_VARIABLE_TEMPLATES */
 
 _LIBCPP_END_NAMESPACE_LFTS
 
 #endif /* _LIBCPP_STD_VER > 11 */
 
-#endif _LIBCPP_EXPERIMENTAL_RATIO
\ No newline at end of file
+#endif // _LIBCPP_EXPERIMENTAL_RATIO
diff --git a/include/experimental/system_error b/include/experimental/system_error
index 9b9ab33..2ec2385 100644
--- a/include/experimental/system_error
+++ b/include/experimental/system_error
@@ -46,7 +46,7 @@
 
 _LIBCPP_BEGIN_NAMESPACE_LFTS
 
-#if __has_feature(cxx_variable_templates)
+#ifndef _LIBCPP_HAS_NO_VARIABLE_TEMPLATES
 
 template <class _Tp> _LIBCPP_CONSTEXPR bool is_error_code_enum_v
     = is_error_code_enum<_Tp>::value;
@@ -54,7 +54,7 @@
 template <class _Tp> _LIBCPP_CONSTEXPR bool is_error_condition_enum_v
     = is_error_condition_enum<_Tp>::value;
 
-#endif /* __has_feature(cxx_variable_templates) */
+#endif /* _LIBCPP_HAS_NO_VARIABLE_TEMPLATES */
 
 _LIBCPP_END_NAMESPACE_LFTS
 
diff --git a/include/experimental/tuple b/include/experimental/tuple
new file mode 100644
index 0000000..50d1e05
--- /dev/null
+++ b/include/experimental/tuple
@@ -0,0 +1,81 @@
+// -*- C++ -*-
+//===----------------------------- tuple ----------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP_EXPERIMENTAL_TUPLE
+#define _LIBCPP_EXPERIMENTAL_TUPLE
+
+/*
+    experimental/tuple synopsis
+
+// C++1y
+
+#include <tuple>
+
+namespace std {
+namespace experimental {
+inline namespace fundamentals_v1 {
+
+  // See C++14 20.4.2.5, tuple helper classes
+  template <class T> constexpr size_t tuple_size_v
+    = tuple_size<T>::value;
+
+  // 3.2.2, Calling a function with a tuple of arguments
+  template <class F, class Tuple>
+  constexpr decltype(auto) apply(F&& f, Tuple&& t);
+
+} // namespace fundamentals_v1
+} // namespace experimental
+} // namespace std
+
+ */
+
+# include <experimental/__config>
+
+#if _LIBCPP_STD_VER > 11
+
+# include <tuple>
+# include <utility>
+# include <__functional_base>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_BEGIN_NAMESPACE_LFTS
+
+#ifndef _LIBCPP_HAS_NO_VARIABLE_TEMPLATES
+template <class _Tp>
+_LIBCPP_CONSTEXPR size_t tuple_size_v = tuple_size<_Tp>::value;
+#endif
+
+template <class _Fn, class _Tuple, size_t ..._Id>
+inline _LIBCPP_INLINE_VISIBILITY
+decltype(auto) __apply_tuple_impl(_Fn && __f, _Tuple && __t,
+                                  integer_sequence<size_t, _Id...>) {
+    return _VSTD::__invoke(
+        _VSTD::forward<_Fn>(__f),
+        _VSTD::get<_Id>(_VSTD::forward<_Tuple>(__t))...
+    );
+}
+
+template <class _Fn, class _Tuple>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
+decltype(auto) apply(_Fn && __f, _Tuple && __t) {
+    return _VSTD_LFTS::__apply_tuple_impl(
+        _VSTD::forward<_Fn>(__f), _VSTD::forward<_Tuple>(__t),
+        make_index_sequence<tuple_size<typename decay<_Tuple>::type>::value>()
+    );
+}
+
+_LIBCPP_END_NAMESPACE_LFTS
+
+#endif /* _LIBCPP_STD_VER > 11 */
+
+#endif /* _LIBCPP_EXPERIMENTAL_TUPLE */
diff --git a/include/experimental/type_traits b/include/experimental/type_traits
index 35cdada..ae49fc1 100644
--- a/include/experimental/type_traits
+++ b/include/experimental/type_traits
@@ -190,7 +190,7 @@
 
 _LIBCPP_BEGIN_NAMESPACE_LFTS
 
-#if __has_feature(cxx_variable_templates)
+#ifndef _LIBCPP_HAS_NO_VARIABLE_TEMPLATES
 
 // C++14 20.10.4.1, primary type categories
 
@@ -397,7 +397,7 @@
 template <class _Tp, class _Up> _LIBCPP_CONSTEXPR bool is_convertible_v
     = is_convertible<_Tp, _Up>::value;
 
-#endif /* __has_feature(cxx_variable_templates) */
+#endif /* _LIBCPP_HAS_NO_VARIABLE_TEMPLATES */
 
 // 3.3.2, Other type transformations
 /*
diff --git a/include/ext/hash_map b/include/ext/hash_map
index 36cd595..31fcedf 100644
--- a/include/ext/hash_map
+++ b/include/ext/hash_map
@@ -203,6 +203,7 @@
 #include <__hash_table>
 #include <functional>
 #include <stdexcept>
+#include <type_traits>
 #include <ext/__hash>
 
 #if __DEPRECATED
@@ -213,16 +214,16 @@
 #endif
 #endif
 
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
 #pragma GCC system_header
+#endif
 
 namespace __gnu_cxx {
 
 using namespace std;
 
-template <class _Tp, class _Hash, bool = is_empty<_Hash>::value
-#if __has_feature(is_final)
-                                         && !__is_final(_Hash)
-#endif
+template <class _Tp, class _Hash,
+          bool = is_empty<_Hash>::value && !__libcpp_is_final<_Hash>::value
         >
 class __hash_map_hasher
     : private _Hash
@@ -255,10 +256,8 @@
         {return __hash_(__x);}
 };
 
-template <class _Tp, class _Pred, bool = is_empty<_Pred>::value
-#if __has_feature(is_final)
-                                         && !__is_final(_Pred)
-#endif
+template <class _Tp, class _Pred,
+          bool = is_empty<_Pred>::value && !__libcpp_is_final<_Pred>::value
          >
 class __hash_map_equal
     : private _Pred
@@ -493,13 +492,7 @@
     typedef pair<key_type, mapped_type>                    __value_type;
     typedef __hash_map_hasher<__value_type, hasher>   __hasher;
     typedef __hash_map_equal<__value_type, key_equal> __key_equal;
-    typedef typename allocator_traits<allocator_type>::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-            rebind_alloc<__value_type>
-#else
-            rebind_alloc<__value_type>::other
-#endif
-                                                           __allocator_type;
+    typedef typename __rebind_alloc_helper<allocator_traits<allocator_type>, __value_type>::type __allocator_type;
 
     typedef __hash_table<__value_type, __hasher,
                          __key_equal,  __allocator_type>   __table;
@@ -772,13 +765,7 @@
     typedef pair<key_type, mapped_type>                    __value_type;
     typedef __hash_map_hasher<__value_type, hasher>   __hasher;
     typedef __hash_map_equal<__value_type, key_equal> __key_equal;
-    typedef typename allocator_traits<allocator_type>::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-            rebind_alloc<__value_type>
-#else
-            rebind_alloc<__value_type>::other
-#endif
-                                                           __allocator_type;
+    typedef typename __rebind_alloc_helper<allocator_traits<allocator_type>, __value_type>::type __allocator_type;
 
     typedef __hash_table<__value_type, __hasher,
                          __key_equal,  __allocator_type>   __table;
diff --git a/include/forward_list b/include/forward_list
index a442a9b..8a87fc5 100644
--- a/include/forward_list
+++ b/include/forward_list
@@ -107,8 +107,7 @@
     iterator erase_after(const_iterator first, const_iterator last);
 
     void swap(forward_list& x)
-        noexcept(!allocator_type::propagate_on_container_swap::value ||
-                 __is_nothrow_swappable<allocator_type>::value);
+        noexcept(allocator_traits<allocator_type>::is_always_equal::value);  // C++17
 
     void resize(size_type n);
     void resize(size_type n, const value_type& v);
@@ -365,24 +364,12 @@
     typedef typename allocator_traits<allocator_type>::void_pointer  void_pointer;
     typedef __forward_list_node<value_type, void_pointer>            __node;
     typedef typename __begin_node_of<value_type, void_pointer>::type __begin_node;
-    typedef typename allocator_traits<allocator_type>::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-                rebind_alloc<__node>
-#else
-                rebind_alloc<__node>::other
-#endif
-                                                      __node_allocator;
+    typedef typename __rebind_alloc_helper<allocator_traits<allocator_type>, __node>::type __node_allocator;
     typedef allocator_traits<__node_allocator>        __node_traits;
     typedef typename __node_traits::pointer           __node_pointer;
     typedef typename __node_traits::pointer           __node_const_pointer;
 
-    typedef typename allocator_traits<allocator_type>::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-                rebind_alloc<__begin_node>
-#else
-                rebind_alloc<__begin_node>::other
-#endif
-                                                      __begin_node_allocator;
+    typedef typename __rebind_alloc_helper<allocator_traits<allocator_type>, __begin_node>::type __begin_node_allocator;
     typedef typename allocator_traits<__begin_node_allocator>::pointer __begin_node_pointer;
 
     __compressed_pair<__begin_node, __node_allocator> __before_begin_;
@@ -443,8 +430,12 @@
 
 public:
     void swap(__forward_list_base& __x)
-        _NOEXCEPT_(!__node_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<__node_allocator>::value);
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT;
+#else
+        _NOEXCEPT_(!__node_traits::propagate_on_container_move_assignment::value || 
+                    __is_nothrow_swappable<__node_allocator>::value);
+#endif
 protected:
     void clear() _NOEXCEPT;
 
@@ -466,26 +457,6 @@
     void __move_assign_alloc(__forward_list_base& __x, true_type)
         _NOEXCEPT_(is_nothrow_move_assignable<__node_allocator>::value)
         {__alloc() = _VSTD::move(__x.__alloc());}
-
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__node_allocator& __x, __node_allocator& __y)
-        _NOEXCEPT_(!__node_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<__node_allocator>::value)
-        {__swap_alloc(__x, __y, integral_constant<bool,
-                         __node_traits::propagate_on_container_swap::value>());}
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__node_allocator& __x, __node_allocator& __y,
-                                                                     false_type)
-        _NOEXCEPT
-        {}
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__node_allocator& __x, __node_allocator& __y,
-                                                                      true_type)
-        _NOEXCEPT_(__is_nothrow_swappable<__node_allocator>::value)
-        {
-            using _VSTD::swap;
-            swap(__x, __y);
-        }
 };
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
@@ -524,10 +495,15 @@
 inline _LIBCPP_INLINE_VISIBILITY
 void
 __forward_list_base<_Tp, _Alloc>::swap(__forward_list_base& __x)
-        _NOEXCEPT_(!__node_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<__node_allocator>::value)
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT
+#else
+        _NOEXCEPT_(!__node_traits::propagate_on_container_move_assignment::value || 
+                    __is_nothrow_swappable<__node_allocator>::value)
+#endif
 {
-    __swap_alloc(__alloc(), __x.__alloc());
+    __swap_allocator(__alloc(), __x.__alloc(), 
+            integral_constant<bool, __node_traits::propagate_on_container_swap::value>());
     using _VSTD::swap;
     swap(__before_begin()->__next_, __x.__before_begin()->__next_);
 }
@@ -715,8 +691,12 @@
 
     _LIBCPP_INLINE_VISIBILITY
     void swap(forward_list& __x)
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT
+#else
         _NOEXCEPT_(!__node_traits::propagate_on_container_swap::value ||
                    __is_nothrow_swappable<__node_allocator>::value)
+#endif
         {base::swap(__x);}
 
     void resize(size_type __n);
diff --git a/include/fstream b/include/fstream
index ace5eb9..1f289ed 100644
--- a/include/fstream
+++ b/include/fstream
@@ -206,8 +206,10 @@
 
     // 27.9.1.4 Members:
     bool is_open() const;
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
     basic_filebuf* open(const char* __s, ios_base::openmode __mode);
     basic_filebuf* open(const string& __s, ios_base::openmode __mode);
+#endif
     basic_filebuf* close();
 
 protected:
@@ -463,6 +465,7 @@
     return __file_ != 0;
 }
 
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
 template <class _CharT, class _Traits>
 basic_filebuf<_CharT, _Traits>*
 basic_filebuf<_CharT, _Traits>::open(const char* __s, ios_base::openmode __mode)
@@ -550,6 +553,7 @@
 {
     return open(__s.c_str(), __mode);
 }
+#endif
 
 template <class _CharT, class _Traits>
 basic_filebuf<_CharT, _Traits>*
@@ -1005,8 +1009,10 @@
     typedef typename traits_type::off_type off_type;
 
     basic_ifstream();
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
     explicit basic_ifstream(const char* __s, ios_base::openmode __mode = ios_base::in);
     explicit basic_ifstream(const string& __s, ios_base::openmode __mode = ios_base::in);
+#endif
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     basic_ifstream(basic_ifstream&& __rhs);
 #endif
@@ -1018,8 +1024,10 @@
 
     basic_filebuf<char_type, traits_type>* rdbuf() const;
     bool is_open() const;
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
     void open(const char* __s, ios_base::openmode __mode = ios_base::in);
     void open(const string& __s, ios_base::openmode __mode = ios_base::in);
+#endif
     void close();
 
 private:
@@ -1033,6 +1041,7 @@
 {
 }
 
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
 template <class _CharT, class _Traits>
 inline _LIBCPP_INLINE_VISIBILITY
 basic_ifstream<_CharT, _Traits>::basic_ifstream(const char* __s, ios_base::openmode __mode)
@@ -1050,6 +1059,7 @@
     if (__sb_.open(__s, __mode | ios_base::in) == 0)
         this->setstate(ios_base::failbit);
 }
+#endif
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
@@ -1107,6 +1117,7 @@
     return __sb_.is_open();
 }
 
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
 template <class _CharT, class _Traits>
 void
 basic_ifstream<_CharT, _Traits>::open(const char* __s, ios_base::openmode __mode)
@@ -1126,6 +1137,7 @@
     else
         this->setstate(ios_base::failbit);
 }
+#endif
 
 template <class _CharT, class _Traits>
 inline _LIBCPP_INLINE_VISIBILITY
@@ -1163,8 +1175,10 @@
 
     basic_filebuf<char_type, traits_type>* rdbuf() const;
     bool is_open() const;
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
     void open(const char* __s, ios_base::openmode __mode = ios_base::out);
     void open(const string& __s, ios_base::openmode __mode = ios_base::out);
+#endif
     void close();
 
 private:
@@ -1178,6 +1192,7 @@
 {
 }
 
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
 template <class _CharT, class _Traits>
 inline _LIBCPP_INLINE_VISIBILITY
 basic_ofstream<_CharT, _Traits>::basic_ofstream(const char* __s, ios_base::openmode __mode)
@@ -1195,6 +1210,7 @@
     if (__sb_.open(__s, __mode | ios_base::out) == 0)
         this->setstate(ios_base::failbit);
 }
+#endif
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
@@ -1252,6 +1268,7 @@
     return __sb_.is_open();
 }
 
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
 template <class _CharT, class _Traits>
 void
 basic_ofstream<_CharT, _Traits>::open(const char* __s, ios_base::openmode __mode)
@@ -1271,6 +1288,7 @@
     else
         this->setstate(ios_base::failbit);
 }
+#endif
 
 template <class _CharT, class _Traits>
 inline _LIBCPP_INLINE_VISIBILITY
@@ -1295,8 +1313,10 @@
     typedef typename traits_type::off_type off_type;
 
     basic_fstream();
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
     explicit basic_fstream(const char* __s, ios_base::openmode __mode = ios_base::in | ios_base::out);
     explicit basic_fstream(const string& __s, ios_base::openmode __mode = ios_base::in | ios_base::out);
+#endif
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     basic_fstream(basic_fstream&& __rhs);
 #endif
@@ -1308,8 +1328,10 @@
 
     basic_filebuf<char_type, traits_type>* rdbuf() const;
     bool is_open() const;
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
     void open(const char* __s, ios_base::openmode __mode = ios_base::in | ios_base::out);
     void open(const string& __s, ios_base::openmode __mode = ios_base::in | ios_base::out);
+#endif
     void close();
 
 private:
@@ -1323,6 +1345,7 @@
 {
 }
 
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
 template <class _CharT, class _Traits>
 inline _LIBCPP_INLINE_VISIBILITY
 basic_fstream<_CharT, _Traits>::basic_fstream(const char* __s, ios_base::openmode __mode)
@@ -1340,6 +1363,7 @@
     if (__sb_.open(__s, __mode) == 0)
         this->setstate(ios_base::failbit);
 }
+#endif
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
@@ -1397,6 +1421,7 @@
     return __sb_.is_open();
 }
 
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
 template <class _CharT, class _Traits>
 void
 basic_fstream<_CharT, _Traits>::open(const char* __s, ios_base::openmode __mode)
@@ -1416,6 +1441,7 @@
     else
         this->setstate(ios_base::failbit);
 }
+#endif
 
 template <class _CharT, class _Traits>
 inline _LIBCPP_INLINE_VISIBILITY
diff --git a/include/functional b/include/functional
index 070347a..6c57de0 100644
--- a/include/functional
+++ b/include/functional
@@ -1234,11 +1234,9 @@
 mem_fun_ref(_Sp (_Tp::*__f)(_Ap) const)
     {return const_mem_fun1_ref_t<_Sp,_Tp,_Ap>(__f);}
 
-#ifdef _LIBCPP_HAS_NO_VARIADICS
-
-#include <__functional_03>
-
-#else  // _LIBCPP_HAS_NO_VARIADICS
+////////////////////////////////////////////////////////////////////////////////
+//                                MEMFUN
+//==============================================================================
 
 template <class _Tp>
 class __mem_fn
@@ -1253,14 +1251,34 @@
 public:
     _LIBCPP_INLINE_VISIBILITY __mem_fn(type __f) : __f_(__f) {}
 
+#ifndef _LIBCPP_HAS_NO_VARIADICS
     // invoke
     template <class... _ArgTypes>
-       _LIBCPP_INLINE_VISIBILITY
-       typename __invoke_return<type, _ArgTypes...>::type
-          operator() (_ArgTypes&&... __args) const
-          {
-              return __invoke(__f_, _VSTD::forward<_ArgTypes>(__args)...);
-          }
+    _LIBCPP_INLINE_VISIBILITY
+    typename __invoke_return<type, _ArgTypes...>::type
+    operator() (_ArgTypes&&... __args) const {
+        return __invoke(__f_, _VSTD::forward<_ArgTypes>(__args)...);
+    }
+#else
+
+    template <class _A0>
+    typename __invoke_return0<type, _A0>::type
+    operator() (_A0& __a0) const {
+        return __invoke(__f_, __a0);
+    }
+
+    template <class _A0, class _A1>
+    typename __invoke_return1<type, _A0, _A1>::type
+    operator() (_A0& __a0, _A1& __a1) const {
+        return __invoke(__f_, __a0, __a1);
+    }
+
+    template <class _A0, class _A1, class _A2>
+    typename __invoke_return2<type, _A0, _A1, _A2>::type
+    operator() (_A0& __a0, _A1& __a1, _A2& __a2) const {
+        return __invoke(__f_, __a0, __a1, __a2);
+    }
+#endif
 };
 
 template<class _Rp, class _Tp>
@@ -1271,6 +1289,10 @@
     return __mem_fn<_Rp _Tp::*>(__pm);
 }
 
+////////////////////////////////////////////////////////////////////////////////
+//                                FUNCTION
+//==============================================================================
+
 // bad_function_call
 
 class _LIBCPP_EXCEPTION_ABI bad_function_call
@@ -1283,7 +1305,7 @@
 namespace __function
 {
 
-template<class _Rp, class ..._ArgTypes>
+template<class _Rp>
 struct __maybe_derive_from_unary_function
 {
 };
@@ -1294,7 +1316,7 @@
 {
 };
 
-template<class _Rp, class ..._ArgTypes>
+template<class _Rp>
 struct __maybe_derive_from_binary_function
 {
 };
@@ -1305,6 +1327,12 @@
 {
 };
 
+} // namespace __function
+
+#ifndef _LIBCPP_HAS_NO_VARIADICS
+
+namespace __function {
+
 template<class _Fp> class __base;
 
 template<class _Rp, class ..._ArgTypes>
@@ -1367,7 +1395,8 @@
 __base<_Rp(_ArgTypes...)>*
 __func<_Fp, _Alloc, _Rp(_ArgTypes...)>::__clone() const
 {
-    typedef typename _Alloc::template rebind<__func>::other _Ap;
+    typedef allocator_traits<_Alloc> __alloc_traits;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap;
     _Ap __a(__f_.second());
     typedef __allocator_destructor<_Ap> _Dp;
     unique_ptr<__func, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
@@ -1393,7 +1422,8 @@
 void
 __func<_Fp, _Alloc, _Rp(_ArgTypes...)>::destroy_deallocate() _NOEXCEPT
 {
-    typedef typename _Alloc::template rebind<__func>::other _Ap;
+    typedef allocator_traits<_Alloc> __alloc_traits;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __func>::type _Ap;
     _Ap __a(__f_.second());
     __f_.~__compressed_pair<_Fp, _Alloc>();
     __a.deallocate(this, 1);
@@ -1654,13 +1684,7 @@
     if (__not_null(__f))
     {
         typedef __function::__func<_Fp, _Alloc, _Rp(_ArgTypes...)> _FF;
-        typedef typename __alloc_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-            rebind_alloc<_FF>
-#else
-            rebind_alloc<_FF>::other
-#endif
-            _Ap;
+        typedef typename __rebind_alloc_helper<__alloc_traits, _FF>::type _Ap;
         _Ap __a(__a0);
         if (sizeof(_FF) <= sizeof(__buf_) && 
             is_nothrow_copy_constructible<_Fp>::value && is_nothrow_copy_constructible<_Ap>::value)
@@ -1852,6 +1876,16 @@
 swap(function<_Rp(_ArgTypes...)>& __x, function<_Rp(_ArgTypes...)>& __y) _NOEXCEPT
 {return __x.swap(__y);}
 
+#else // _LIBCPP_HAS_NO_VARIADICS
+
+#include <__functional_03>
+
+#endif
+
+////////////////////////////////////////////////////////////////////////////////
+//                                  BIND
+//==============================================================================
+
 template<class _Tp> struct __is_bind_expression : public false_type {};
 template<class _Tp> struct _LIBCPP_TYPE_VIS_ONLY is_bind_expression
     : public __is_bind_expression<typename remove_cv<_Tp>::type> {};
@@ -1882,6 +1916,9 @@
 struct __is_placeholder<placeholders::__ph<_Np> >
     : public integral_constant<int, _Np> {};
 
+
+#ifndef _LIBCPP_HAS_NO_VARIADICS
+
 template <class _Tp, class _Uj>
 inline _LIBCPP_INLINE_VISIBILITY
 _Tp&
@@ -2000,27 +2037,27 @@
 };
 
 template <class _Fp, class _BoundArgs, class _TupleUj>
-struct _is_valid_bind_return
+struct __is_valid_bind_return
 {
     static const bool value = false;
 };
 
 template <class _Fp, class ..._BoundArgs, class _TupleUj>
-struct _is_valid_bind_return<_Fp, tuple<_BoundArgs...>, _TupleUj>
+struct __is_valid_bind_return<_Fp, tuple<_BoundArgs...>, _TupleUj>
 {
     static const bool value = __invokable<_Fp,
                     typename __mu_return<_BoundArgs, _TupleUj>::type...>::value;
 };
 
 template <class _Fp, class ..._BoundArgs, class _TupleUj>
-struct _is_valid_bind_return<_Fp, const tuple<_BoundArgs...>, _TupleUj>
+struct __is_valid_bind_return<_Fp, const tuple<_BoundArgs...>, _TupleUj>
 {
     static const bool value = __invokable<_Fp,
                     typename __mu_return<const _BoundArgs, _TupleUj>::type...>::value;
 };
 
 template <class _Fp, class _BoundArgs, class _TupleUj,
-          bool = _is_valid_bind_return<_Fp, _BoundArgs, _TupleUj>::value>
+          bool = __is_valid_bind_return<_Fp, _BoundArgs, _TupleUj>::value>
 struct __bind_return;
 
 template <class _Fp, class ..._BoundArgs, class _TupleUj>
@@ -2190,12 +2227,13 @@
         typename enable_if
         <
             is_convertible<typename __bind_return<_Fd, _Td, tuple<_Args&&...> >::type,
-                           result_type>::value,
+                           result_type>::value || is_void<_Rp>::value,
             result_type
         >::type
         operator()(_Args&& ...__args)
         {
-            return base::operator()(_VSTD::forward<_Args>(__args)...);
+            typedef __invoke_void_return_wrapper<_Rp> _Invoker;
+            return _Invoker::__call(static_cast<base&>(*this), _VSTD::forward<_Args>(__args)...);
         }
 
     template <class ..._Args>
@@ -2203,12 +2241,13 @@
         typename enable_if
         <
             is_convertible<typename __bind_return<const _Fd, const _Td, tuple<_Args&&...> >::type,
-                           result_type>::value,
+                           result_type>::value || is_void<_Rp>::value,
             result_type
         >::type
         operator()(_Args&& ...__args) const
         {
-            return base::operator()(_VSTD::forward<_Args>(__args)...);
+            typedef __invoke_void_return_wrapper<_Rp> _Invoker;
+            return _Invoker::__call(static_cast<base const&>(*this), _VSTD::forward<_Args>(__args)...);
         }
 };
 
@@ -2404,14 +2443,14 @@
                 size_t __b;
                 size_t __c;
                 size_t __d;
-            };
+            } __s;
         } __u;
-        __u.__a = 0;
-        __u.__b = 0;
-        __u.__c = 0;
-        __u.__d = 0;
+        __u.__s.__a = 0;
+        __u.__s.__b = 0;
+        __u.__s.__c = 0;
+        __u.__s.__d = 0;
         __u.__t = __v;
-        return __u.__a ^ __u.__b ^ __u.__c ^ __u.__d;
+        return __u.__s.__a ^ __u.__s.__b ^ __u.__s.__c ^ __u.__s.__d;
 #elif defined(__x86_64__)
         // Zero out padding bits
         union
@@ -2421,12 +2460,12 @@
             {
                 size_t __a;
                 size_t __b;
-            };
+            } __s;
         } __u;
-        __u.__a = 0;
-        __u.__b = 0;
+        __u.__s.__a = 0;
+        __u.__s.__b = 0;
         __u.__t = __v;
-        return __u.__a ^ __u.__b;
+        return __u.__s.__a ^ __u.__s.__b;
 #else
         return __scalar_hash<long double>::operator()(__v);
 #endif
@@ -2449,6 +2488,15 @@
 };
 #endif
 
+
+#if _LIBCPP_STD_VER > 14
+template <class _Fn, class ..._Args>
+result_of_t<_Fn&&(_Args&&...)>
+invoke(_Fn&& __f, _Args&&... __args) {
+    return __invoke(_VSTD::forward<_Fn>(__f), _VSTD::forward<_Args>(__args)...);
+}
+#endif
+
 // struct hash<T*> in <memory>
 
 _LIBCPP_END_NAMESPACE_STD
diff --git a/include/future b/include/future
index ad7af72..5b5afe6 100644
--- a/include/future
+++ b/include/future
@@ -329,7 +329,7 @@
     template <class F>
         explicit packaged_task(F&& f);
     template <class F, class Allocator>
-        explicit packaged_task(allocator_arg_t, const Allocator& a, F&& f);
+        packaged_task(allocator_arg_t, const Allocator& a, F&& f);
     ~packaged_task();
 
     // no copy
@@ -651,7 +651,6 @@
 #endif
     ::new(&__value_) _Rp(_VSTD::forward<_Arg>(__arg));
     this->__state_ |= base::__constructed | base::ready;
-    __lk.unlock();
     __cv_.notify_all();
 }
 
@@ -672,7 +671,6 @@
     ::new(&__value_) _Rp(_VSTD::forward<_Arg>(__arg));
     this->__state_ |= base::__constructed;
     __thread_local_data()->__make_ready_at_thread_exit(this);
-    __lk.unlock();
 }
 
 template <class _Rp>
@@ -733,7 +731,6 @@
 #endif
     __value_ = _VSTD::addressof(__arg);
     this->__state_ |= base::__constructed | base::ready;
-    __lk.unlock();
     __cv_.notify_all();
 }
 
@@ -749,7 +746,6 @@
     __value_ = _VSTD::addressof(__arg);
     this->__state_ |= base::__constructed;
     __thread_local_data()->__make_ready_at_thread_exit(this);
-    __lk.unlock();
 }
 
 template <class _Rp>
@@ -2046,7 +2042,7 @@
                   >::type
               >
         _LIBCPP_INLINE_VISIBILITY
-        explicit packaged_task(allocator_arg_t, const _Allocator& __a, _Fp&& __f)
+        packaged_task(allocator_arg_t, const _Allocator& __a, _Fp&& __f)
              : __f_(allocator_arg, __a, _VSTD::forward<_Fp>(__f)),
                __p_(allocator_arg, __a) {}
     // ~packaged_task() = default;
@@ -2177,7 +2173,7 @@
                   >::type
               >    
         _LIBCPP_INLINE_VISIBILITY
-        explicit packaged_task(allocator_arg_t, const _Allocator& __a, _Fp&& __f)
+        packaged_task(allocator_arg_t, const _Allocator& __a, _Fp&& __f)
              : __f_(allocator_arg, __a, _VSTD::forward<_Fp>(__f)),
                __p_(allocator_arg, __a) {}
     // ~packaged_task() = default;
diff --git a/include/iostream b/include/iostream
index ddf2484..136a849 100644
--- a/include/iostream
+++ b/include/iostream
@@ -46,13 +46,17 @@
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
+#ifndef _LIBCPP_HAS_NO_STDIN
 extern _LIBCPP_FUNC_VIS istream cin;
-extern _LIBCPP_FUNC_VIS ostream cout;
-extern _LIBCPP_FUNC_VIS ostream cerr;
-extern _LIBCPP_FUNC_VIS ostream clog;
 extern _LIBCPP_FUNC_VIS wistream wcin;
+#endif
+#ifndef _LIBCPP_HAS_NO_STDOUT
+extern _LIBCPP_FUNC_VIS ostream cout;
 extern _LIBCPP_FUNC_VIS wostream wcout;
+#endif
+extern _LIBCPP_FUNC_VIS ostream cerr;
 extern _LIBCPP_FUNC_VIS wostream wcerr;
+extern _LIBCPP_FUNC_VIS ostream clog;
 extern _LIBCPP_FUNC_VIS wostream wclog;
 
 _LIBCPP_END_NAMESPACE_STD
diff --git a/include/iterator b/include/iterator
index 05d7412..c06ef8f 100644
--- a/include/iterator
+++ b/include/iterator
@@ -214,7 +214,7 @@
     typedef traits traits_type;
     typedef basic_istream<charT,traits> istream_type;
 
-    istream_iterator();
+    constexpr istream_iterator();
     istream_iterator(istream_type& s);
     istream_iterator(const istream_iterator& x);
     ~istream_iterator();
@@ -575,7 +575,7 @@
     _LIBCPP_INLINE_VISIBILITY reverse_iterator& operator-=(difference_type __n)
         {current += __n; return *this;}
     _LIBCPP_INLINE_VISIBILITY reference         operator[](difference_type __n) const
-        {return current[-__n-1];}
+        {return *(*this + __n);}
 };
 
 template <class _Iter1, class _Iter2>
@@ -765,7 +765,7 @@
     istream_type* __in_stream_;
     _Tp __value_;
 public:
-    _LIBCPP_INLINE_VISIBILITY istream_iterator() : __in_stream_(0) {}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR istream_iterator() : __in_stream_(0), __value_() {}
     _LIBCPP_INLINE_VISIBILITY istream_iterator(istream_type& __s) : __in_stream_(&__s)
         {
             if (!(*__in_stream_ >> __value_))
@@ -1112,8 +1112,6 @@
 >::type
 __unwrap_iter(__wrap_iter<_Tp*>);
 
-template <class _Tp, class _Alloc> class _LIBCPP_TYPE_VIS_ONLY vector;
-
 template <class _Iter>
 class __wrap_iter
 {
@@ -1243,7 +1241,7 @@
 
     template <class _Up> friend class __wrap_iter;
     template <class _CharT, class _Traits, class _Alloc> friend class basic_string;
-    template <class _Tp, class _Alloc> friend class vector;
+    template <class _Tp, class _Alloc> friend class _LIBCPP_TYPE_VIS_ONLY vector;
 
     template <class _Iter1, class _Iter2>
     friend
diff --git a/include/list b/include/list
index 13e1199..14201a8 100644
--- a/include/list
+++ b/include/list
@@ -118,8 +118,7 @@
     void resize(size_type sz, const value_type& c);
 
     void swap(list&)
-        noexcept(!allocator_type::propagate_on_container_swap::value ||
-                 __is_nothrow_swappable<allocator_type>::value);
+        noexcept(allocator_traits<allocator_type>::is_always_equal::value);  // C++17
     void clear() noexcept;
 
     void splice(const_iterator position, list& x);
@@ -515,13 +514,7 @@
     typedef __list_const_iterator<value_type, __void_pointer>       const_iterator;
     typedef __list_node_base<value_type, __void_pointer>            __node_base;
     typedef __list_node<value_type, __void_pointer>                 __node;
-    typedef typename __alloc_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-                rebind_alloc<__node>
-#else
-                rebind_alloc<__node>::other
-#endif
-                                                                     __node_allocator;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __node>::type __node_allocator;
     typedef allocator_traits<__node_allocator>                       __node_alloc_traits;
     typedef typename __node_alloc_traits::pointer                    __node_pointer;
     typedef typename __node_alloc_traits::pointer                    __node_const_pointer;
@@ -529,13 +522,7 @@
     typedef typename __alloc_traits::const_pointer                   const_pointer;
     typedef typename __alloc_traits::difference_type                 difference_type;
 
-    typedef typename __alloc_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-                rebind_alloc<__node_base>
-#else
-                rebind_alloc<__node_base>::other
-#endif
-                                                                     __node_base_allocator;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __node_base>::type __node_base_allocator;
     typedef typename allocator_traits<__node_base_allocator>::pointer __node_base_pointer;
 
     __node_base __end_;
@@ -605,8 +592,12 @@
     }
 
     void swap(__list_imp& __c)
-        _NOEXCEPT_(!__node_alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<__node_allocator>::value);
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT;
+#else
+        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 
+                    __is_nothrow_swappable<allocator_type>::value);
+#endif
 
     _LIBCPP_INLINE_VISIBILITY
     void __copy_assign_alloc(const __list_imp& __c)
@@ -623,24 +614,6 @@
 
 private:
     _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__node_allocator& __x, __node_allocator& __y)
-        _NOEXCEPT_(!__node_alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<__node_allocator>::value)
-        {__swap_alloc(__x, __y, integral_constant<bool,
-                      __node_alloc_traits::propagate_on_container_swap::value>());}
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__node_allocator& __x, __node_allocator& __y, true_type)
-        _NOEXCEPT_(__is_nothrow_swappable<__node_allocator>::value)
-        {
-            using _VSTD::swap;
-            swap(__x, __y);
-        }
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__node_allocator& __x, __node_allocator& __y, false_type)
-        _NOEXCEPT
-        {}
-
-    _LIBCPP_INLINE_VISIBILITY
     void __copy_assign_alloc(const __list_imp& __c, true_type)
         {
             if (__node_alloc() != __c.__node_alloc())
@@ -740,15 +713,19 @@
 template <class _Tp, class _Alloc>
 void
 __list_imp<_Tp, _Alloc>::swap(__list_imp& __c)
-        _NOEXCEPT_(!__node_alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<__node_allocator>::value)
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT
+#else
+        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 
+                    __is_nothrow_swappable<allocator_type>::value)
+#endif
 {
     _LIBCPP_ASSERT(__alloc_traits::propagate_on_container_swap::value ||
                    this->__node_alloc() == __c.__node_alloc(),
                    "list::swap: Either propagate_on_container_swap must be true"
                    " or the allocators must compare equal");
     using _VSTD::swap;
-    __swap_alloc(__node_alloc(), __c.__node_alloc());
+    __swap_allocator(__node_alloc(), __c.__node_alloc());
     swap(__sz(), __c.__sz());
     swap(__end_, __c.__end_);
     if (__sz() == 0)
@@ -984,8 +961,12 @@
 
     _LIBCPP_INLINE_VISIBILITY
     void swap(list& __c)
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT
+#else
         _NOEXCEPT_(!__node_alloc_traits::propagate_on_container_swap::value ||
                    __is_nothrow_swappable<__node_allocator>::value)
+#endif
         {base::swap(__c);}
     _LIBCPP_INLINE_VISIBILITY
     void clear() _NOEXCEPT {base::clear();}
@@ -1480,7 +1461,7 @@
         try
         {
 #endif  // _LIBCPP_NO_EXCEPTIONS
-            for (++__f; __f != __l; ++__f, ++__e, ++__ds)
+            for (++__f; __f != __l; ++__f, (void) ++__e, (void) ++__ds)
             {
                 __hold.reset(__node_alloc_traits::allocate(__na, 1));
                 __node_alloc_traits::construct(__na, _VSTD::addressof(__hold->__value_), *__f);
diff --git a/include/locale b/include/locale
index 38c68ec..e683ba3 100644
--- a/include/locale
+++ b/include/locale
@@ -198,7 +198,8 @@
 // include of <sys/cdefs.h> once https://sourceware.org/ml/newlib-cvs/2014-q3/msg00038.html
 // has had a chance to bake for a bit
 #include <support/newlib/xlocale.h>
-#elif !defined(__ANDROID__)
+#endif
+#ifdef _LIBCPP_HAS_CATOPEN
 #include <nl_types.h>
 #endif
 
@@ -216,7 +217,7 @@
 
 #if defined(__APPLE__) || defined(__FreeBSD__)
 #  define _LIBCPP_GET_C_LOCALE 0
-#elif defined(__NetBSD__)
+#elif defined(__CloudABI__) || defined(__NetBSD__)
 #  define _LIBCPP_GET_C_LOCALE LC_C_LOCALE
 #else
 #  define _LIBCPP_GET_C_LOCALE __cloc()
@@ -235,7 +236,7 @@
 // locale.  Linux, not so much.  The following functions avoid the locale when
 // that's possible and otherwise do the wrong thing.  FIXME.
 #if defined(__linux__) || defined(__EMSCRIPTEN__) || defined(_AIX) || \
-    defined(_NEWLIB_VERSION)
+    defined(_NEWLIB_VERSION) || defined(__GLIBC__)
 
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
 decltype(MB_CUR_MAX_L(_VSTD::declval<locale_t>()))
@@ -1190,7 +1191,7 @@
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
     if (sscanf_l(__buf.c_str(), _LIBCPP_GET_C_LOCALE, "%p", &__v) != 1)
 #else
-    if (__sscanf_l(__buf.c_str(), __cloc(), "%p", &__v) != 1)
+    if (__sscanf_l(__buf.c_str(), _LIBCPP_GET_C_LOCALE, "%p", &__v) != 1)
 #endif
         __err = ios_base::failbit;
     // EOF checked
@@ -1560,7 +1561,7 @@
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
     int __nc = snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #else
-    int __nc = __snprintf_l(__nar, sizeof(__nar), __cloc(), __fmt, __v);
+    int __nc = __snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #endif
     char* __ne = __nar + __nc;
     char* __np = this->__identify_padding(__nar, __ne, __iob);
@@ -1590,7 +1591,7 @@
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
     int __nc = snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #else
-    int __nc = __snprintf_l(__nar, sizeof(__nar), __cloc(), __fmt, __v);
+    int __nc = __snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #endif
     char* __ne = __nar + __nc;
     char* __np = this->__identify_padding(__nar, __ne, __iob);
@@ -1620,7 +1621,7 @@
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
     int __nc = snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #else
-    int __nc = __snprintf_l(__nar, sizeof(__nar), __cloc(), __fmt, __v);
+    int __nc = __snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #endif
     char* __ne = __nar + __nc;
     char* __np = this->__identify_padding(__nar, __ne, __iob);
@@ -1650,7 +1651,7 @@
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
     int __nc = snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #else
-    int __nc = __snprintf_l(__nar, sizeof(__nar), __cloc(), __fmt, __v);
+    int __nc = __snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #endif
     char* __ne = __nar + __nc;
     char* __np = this->__identify_padding(__nar, __ne, __iob);
@@ -1682,14 +1683,14 @@
         __nc = snprintf_l(__nb, __nbuf, _LIBCPP_GET_C_LOCALE, __fmt,
                                    (int)__iob.precision(), __v);
 #else
-        __nc = __snprintf_l(__nb, __nbuf, __cloc(), __fmt,
-                            (int)__iob.precision(), __v);
+        __nc = __snprintf_l(__nb, __nbuf, _LIBCPP_GET_C_LOCALE, __fmt,
+                                   (int)__iob.precision(), __v);
 #endif
     else
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
         __nc = snprintf_l(__nb, __nbuf, _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #else
-        __nc = __snprintf_l(__nb, __nbuf, __cloc(), __fmt, __v);
+        __nc = __snprintf_l(__nb, __nbuf, _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #endif
     unique_ptr<char, void(*)(void*)> __nbh(0, free);
     if (__nc > static_cast<int>(__nbuf-1))
@@ -1698,14 +1699,13 @@
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
             __nc = asprintf_l(&__nb, _LIBCPP_GET_C_LOCALE, __fmt, (int)__iob.precision(), __v);
 #else
-            __nc = __asprintf_l(&__nb, __cloc(), __fmt,
-                              (int)__iob.precision(), __v);
+            __nc = __asprintf_l(&__nb, _LIBCPP_GET_C_LOCALE, __fmt, (int)__iob.precision(), __v);
 #endif
         else
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
             __nc = asprintf_l(&__nb, _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #else
-            __nc = __asprintf_l(&__nb, __cloc(), __fmt, (int)__iob.precision(), __v);
+            __nc = __asprintf_l(&__nb, _LIBCPP_GET_C_LOCALE, __fmt, (int)__iob.precision(), __v);
 #endif
         if (__nb == 0)
             __throw_bad_alloc();
@@ -1751,14 +1751,14 @@
         __nc = snprintf_l(__nb, __nbuf, _LIBCPP_GET_C_LOCALE, __fmt,
                                    (int)__iob.precision(), __v);
 #else
-        __nc = __snprintf_l(__nb, __nbuf, __cloc(), __fmt,
-                            (int)__iob.precision(), __v);
+        __nc = __snprintf_l(__nb, __nbuf, _LIBCPP_GET_C_LOCALE, __fmt,
+                                   (int)__iob.precision(), __v);
 #endif
     else
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
         __nc = snprintf_l(__nb, __nbuf, _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #else
-        __nc = __snprintf_l(__nb, __nbuf, __cloc(), __fmt, __v);
+        __nc = __snprintf_l(__nb, __nbuf, _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #endif
     unique_ptr<char, void(*)(void*)> __nbh(0, free);
     if (__nc > static_cast<int>(__nbuf-1))
@@ -1767,14 +1767,13 @@
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
             __nc = asprintf_l(&__nb, _LIBCPP_GET_C_LOCALE, __fmt, (int)__iob.precision(), __v);
 #else
-            __nc = __asprintf_l(&__nb, __cloc(), __fmt,
-                              (int)__iob.precision(), __v);
+            __nc = __asprintf_l(&__nb, _LIBCPP_GET_C_LOCALE, __fmt, (int)__iob.precision(), __v);
 #endif
         else
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
             __nc = asprintf_l(&__nb, _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #else
-            __nc = __asprintf_l(&__nb, __cloc(), __fmt, __v);
+            __nc = __asprintf_l(&__nb, _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #endif
         if (__nb == 0)
             __throw_bad_alloc();
@@ -1814,7 +1813,7 @@
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
     int __nc = snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #else
-    int __nc = __snprintf_l(__nar, sizeof(__nar), __cloc(), __fmt, __v);
+    int __nc = __snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
 #endif
     char* __ne = __nar + __nc;
     char* __np = this->__identify_padding(__nar, __ne, __iob);
@@ -3527,7 +3526,7 @@
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
         __n = static_cast<size_t>(asprintf_l(&__bb, _LIBCPP_GET_C_LOCALE, "%.0Lf", __units));
 #else
-        __n = __asprintf_l(&__bb, __cloc(), "%.0Lf", __units);
+        __n = __asprintf_l(&__bb, _LIBCPP_GET_C_LOCALE, "%.0Lf", __units);
 #endif
         if (__bb == 0)
             __throw_bad_alloc();
@@ -3681,14 +3680,14 @@
 typename messages<_CharT>::catalog
 messages<_CharT>::do_open(const basic_string<char>& __nm, const locale&) const
 {
-#if defined(_WIN32) || defined(__ANDROID__) || defined(_NEWLIB_VERSION)
-    return -1;
-#else // _WIN32 || __ANDROID__
+#ifdef _LIBCPP_HAS_CATOPEN
     catalog __cat = (catalog)catopen(__nm.c_str(), NL_CAT_LOCALE);
     if (__cat != -1)
         __cat = static_cast<catalog>((static_cast<size_t>(__cat) >> 1));
     return __cat;
-#endif // _WIN32 || __ANDROID__
+#else // !_LIBCPP_HAS_CATOPEN
+    return -1;
+#endif // _LIBCPP_HAS_CATOPEN
 }
 
 template <class _CharT>
@@ -3696,9 +3695,7 @@
 messages<_CharT>::do_get(catalog __c, int __set, int __msgid,
                          const string_type& __dflt) const
 {
-#if defined(_WIN32) || defined(__ANDROID__) || defined(_NEWLIB_VERSION)
-    return __dflt;
-#else // _WIN32
+#ifdef _LIBCPP_HAS_CATOPEN
     string __ndflt;
     __narrow_to_utf8<sizeof(char_type)*__CHAR_BIT__>()(back_inserter(__ndflt),
                                                        __dflt.c_str(),
@@ -3711,19 +3708,21 @@
     __widen_from_utf8<sizeof(char_type)*__CHAR_BIT__>()(back_inserter(__w),
                                                         __n, __n + strlen(__n));
     return __w;
-#endif // _WIN32
+#else // !_LIBCPP_HAS_CATOPEN
+    return __dflt;
+#endif // _LIBCPP_HAS_CATOPEN
 }
 
 template <class _CharT>
 void
 messages<_CharT>::do_close(catalog __c) const
 {
-#if !defined(_WIN32) && !defined(__ANDROID__) && !defined(_NEWLIB_VERSION)
+#ifdef _LIBCPP_HAS_CATOPEN
     if (__c != -1)
         __c <<= 1;
     nl_catd __cat = (nl_catd)__c;
     catclose(__cat);
-#endif // !_WIN32
+#endif // _LIBCPP_HAS_CATOPEN
 }
 
 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS messages<char>)
diff --git a/include/map b/include/map
index 0b5eb20..eb6b8ed 100644
--- a/include/map
+++ b/include/map
@@ -135,16 +135,32 @@
         void insert(InputIterator first, InputIterator last);
     void insert(initializer_list<value_type> il);
 
+    template <class... Args>
+        pair<iterator, bool> try_emplace(const key_type& k, Args&&... args);          // C++17
+    template <class... Args>
+        pair<iterator, bool> try_emplace(key_type&& k, Args&&... args);               // C++17
+    template <class... Args>
+        iterator try_emplace(const_iterator hint, const key_type& k, Args&&... args); // C++17
+    template <class... Args>
+        iterator try_emplace(const_iterator hint, key_type&& k, Args&&... args);      // C++17
+    template <class M>
+        pair<iterator, bool> insert_or_assign(const key_type& k, M&& obj);            // C++17
+    template <class M>
+        pair<iterator, bool> insert_or_assign(key_type&& k, M&& obj);                 // C++17
+    template <class M>
+        iterator insert_or_assign(const_iterator hint, const key_type& k, M&& obj);   // C++17
+    template <class M>
+        iterator insert_or_assign(const_iterator hint, key_type&& k, M&& obj);        // C++17
+
     iterator  erase(const_iterator position);
+    iterator  erase(iterator position); // C++14
     size_type erase(const key_type& k);
     iterator  erase(const_iterator first, const_iterator last);
     void clear() noexcept;
 
     void swap(map& m)
-        noexcept(
-            __is_nothrow_swappable<key_compare>::value &&
-            (!allocator_type::propagate_on_container_swap::value ||
-             __is_nothrow_swappable<allocator_type>::value));
+        noexcept(allocator_traits<allocator_type>::is_always_equal::value &&
+            __is_nothrow_swappable<key_compare>::value); // C++17
 
     // observers:
     allocator_type get_allocator() const noexcept;
@@ -330,15 +346,14 @@
     void insert(initializer_list<value_type> il);
 
     iterator  erase(const_iterator position);
+    iterator  erase(iterator position); // C++14
     size_type erase(const key_type& k);
     iterator  erase(const_iterator first, const_iterator last);
     void clear() noexcept;
 
     void swap(multimap& m)
-        noexcept(
-            __is_nothrow_swappable<key_compare>::value &&
-            (!allocator_type::propagate_on_container_swap::value ||
-             __is_nothrow_swappable<allocator_type>::value));
+        noexcept(allocator_traits<allocator_type>::is_always_equal::value &&
+            __is_nothrow_swappable<key_compare>::value); // C++17
 
     // observers:
     allocator_type get_allocator() const noexcept;
@@ -426,6 +441,7 @@
 #include <utility>
 #include <functional>
 #include <initializer_list>
+#include <type_traits>
 
 #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
 #pragma GCC system_header
@@ -433,10 +449,8 @@
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
-template <class _Key, class _CP, class _Compare, bool = is_empty<_Compare>::value
-#if __has_feature(is_final)
-                                                        && !__is_final(_Compare)
-#endif
+template <class _Key, class _CP, class _Compare,
+          bool = is_empty<_Compare>::value && !__libcpp_is_final<_Compare>::value
          >
 class __map_value_compare
     : private _Compare
@@ -461,6 +475,12 @@
     _LIBCPP_INLINE_VISIBILITY
     bool operator()(const _Key& __x, const _CP& __y) const
         {return static_cast<const _Compare&>(*this)(__x, __y.__cc.first);}
+    void swap(__map_value_compare&__y)
+        _NOEXCEPT_(__is_nothrow_swappable<_Compare>::value)
+    {
+        using _VSTD::swap;
+        swap(static_cast<const _Compare&>(*this), static_cast<const _Compare&>(__y));
+    }
 
 #if _LIBCPP_STD_VER > 11
     template <typename _K2>
@@ -503,7 +523,13 @@
     _LIBCPP_INLINE_VISIBILITY
     bool operator()(const _Key& __x, const _CP& __y) const
         {return comp(__x, __y.__cc.first);}
-
+    void swap(__map_value_compare&__y)
+        _NOEXCEPT_(__is_nothrow_swappable<_Compare>::value)
+    {
+        using _VSTD::swap;
+        swap(comp, __y.comp);
+    }
+    
 #if _LIBCPP_STD_VER > 11
     template <typename _K2>
     _LIBCPP_INLINE_VISIBILITY
@@ -519,6 +545,16 @@
 #endif
 };
 
+template <class _Key, class _CP, class _Compare, bool __b>
+inline _LIBCPP_INLINE_VISIBILITY
+void
+swap(__map_value_compare<_Key, _CP, _Compare, __b>& __x,
+     __map_value_compare<_Key, _CP, _Compare, __b>& __y)
+    _NOEXCEPT_(_NOEXCEPT_(__x.swap(__y)))
+{
+    __x.swap(__y);
+}
+
 template <class _Allocator>
 class __map_node_destructor
 {
@@ -822,13 +858,8 @@
 
     typedef _VSTD::__value_type<key_type, mapped_type>             __value_type;
     typedef __map_value_compare<key_type, __value_type, key_compare> __vc;
-    typedef typename allocator_traits<allocator_type>::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-            rebind_alloc<__value_type>
-#else
-            rebind_alloc<__value_type>::other
-#endif
-                                                           __allocator_type;
+    typedef typename __rebind_alloc_helper<allocator_traits<allocator_type>,
+                                                 __value_type>::type __allocator_type;
     typedef __tree<__value_type, __vc, __allocator_type>   __base;
     typedef typename __base::__node_traits                 __node_traits;
     typedef allocator_traits<allocator_type>               __alloc_traits;
@@ -1081,9 +1112,125 @@
 
 #endif  // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
 
+#if _LIBCPP_STD_VER > 14
+#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#ifndef _LIBCPP_HAS_NO_VARIADICS
+    template <class... _Args>
+        _LIBCPP_INLINE_VISIBILITY
+        pair<iterator, bool> try_emplace(const key_type& __k, _Args&&... __args)
+    {
+        iterator __p = lower_bound(__k);
+        if ( __p != end() && !key_comp()(__k, __p->first))
+            return _VSTD::make_pair(__p, false);
+        else
+            return _VSTD::make_pair(
+                      emplace_hint(__p, 
+                        _VSTD::piecewise_construct, _VSTD::forward_as_tuple(__k), 
+                        _VSTD::forward_as_tuple(_VSTD::forward<_Args>(__args)...)),
+                      true);
+    }
+
+    template <class... _Args>
+        _LIBCPP_INLINE_VISIBILITY
+        pair<iterator, bool> try_emplace(key_type&& __k, _Args&&... __args)
+    {
+        iterator __p = lower_bound(__k);
+        if ( __p != end() && !key_comp()(__k, __p->first))
+            return _VSTD::make_pair(__p, false);
+        else
+            return _VSTD::make_pair(
+                      emplace_hint(__p, 
+                        _VSTD::piecewise_construct, _VSTD::forward_as_tuple(_VSTD::move(__k)), 
+                        _VSTD::forward_as_tuple(_VSTD::forward<_Args>(__args)...)),
+                      true);
+    }
+
+    template <class... _Args>
+        _LIBCPP_INLINE_VISIBILITY
+        iterator try_emplace(const_iterator __h, const key_type& __k, _Args&&... __args)
+    {
+        iterator __p = lower_bound(__k);
+        if ( __p != end() && !key_comp()(__k, __p->first))
+            return __p;
+        else
+            return emplace_hint(__p, 
+                      _VSTD::piecewise_construct, _VSTD::forward_as_tuple(__k), 
+                      _VSTD::forward_as_tuple(_VSTD::forward<_Args>(__args)...));
+    }
+
+    template <class... _Args>
+        _LIBCPP_INLINE_VISIBILITY
+        iterator try_emplace(const_iterator __h, key_type&& __k, _Args&&... __args)
+    {
+        iterator __p = lower_bound(__k);
+        if ( __p != end() && !key_comp()(__k, __p->first))
+            return __p;
+        else
+            return emplace_hint(__p, 
+                      _VSTD::piecewise_construct, _VSTD::forward_as_tuple(_VSTD::move(__k)), 
+                      _VSTD::forward_as_tuple(_VSTD::forward<_Args>(__args)...));
+    }
+
+    template <class _Vp>
+        _LIBCPP_INLINE_VISIBILITY
+        pair<iterator, bool> insert_or_assign(const key_type& __k, _Vp&& __v)
+    {
+        iterator __p = lower_bound(__k);
+        if ( __p != end() && !key_comp()(__k, __p->first))
+        {
+            __p->second = _VSTD::forward<_Vp>(__v);
+            return _VSTD::make_pair(__p, false);
+        }
+        return _VSTD::make_pair(emplace_hint(__p, __k, _VSTD::forward<_Vp>(__v)), true);
+    }
+        
+    template <class _Vp>
+        _LIBCPP_INLINE_VISIBILITY
+        pair<iterator, bool> insert_or_assign(key_type&& __k, _Vp&& __v)
+    {
+        iterator __p = lower_bound(__k);
+        if ( __p != end() && !key_comp()(__k, __p->first))
+        {
+            __p->second = _VSTD::forward<_Vp>(__v);
+            return _VSTD::make_pair(__p, false);
+        }
+        return _VSTD::make_pair(emplace_hint(__p, _VSTD::move(__k), _VSTD::forward<_Vp>(__v)), true);
+    }
+
+    template <class _Vp>
+        _LIBCPP_INLINE_VISIBILITY
+        iterator insert_or_assign(const_iterator __h, const key_type& __k, _Vp&& __v)
+     {
+        iterator __p = lower_bound(__k);
+        if ( __p != end() && !key_comp()(__k, __p->first))
+        {
+            __p->second = _VSTD::forward<_Vp>(__v);
+            return __p;
+        }
+        return emplace_hint(__h, __k, _VSTD::forward<_Vp>(__v));
+     }
+
+    template <class _Vp>
+        _LIBCPP_INLINE_VISIBILITY
+        iterator insert_or_assign(const_iterator __h, key_type&& __k, _Vp&& __v)
+     {
+        iterator __p = lower_bound(__k);
+        if ( __p != end() && !key_comp()(__k, __p->first))
+        {
+            __p->second = _VSTD::forward<_Vp>(__v);
+            return __p;
+        }
+        return emplace_hint(__h, _VSTD::move(__k), _VSTD::forward<_Vp>(__v));
+     }
+#endif
+#endif
+#endif
+
     _LIBCPP_INLINE_VISIBILITY
     iterator erase(const_iterator __p) {return __tree_.erase(__p.__i_);}
     _LIBCPP_INLINE_VISIBILITY
+    iterator erase(iterator __p)       {return __tree_.erase(__p.__i_);}
+    _LIBCPP_INLINE_VISIBILITY
     size_type erase(const key_type& __k)
         {return __tree_.__erase_unique(__k);}
     _LIBCPP_INLINE_VISIBILITY
@@ -1119,7 +1266,7 @@
     template <typename _K2>
     _LIBCPP_INLINE_VISIBILITY
     typename enable_if<__is_transparent<_Compare, _K2>::value,size_type>::type
-    count(const _K2& __k)                  {return __tree_.__count_unique(__k);}
+    count(const _K2& __k) const {return __tree_.__count_unique(__k);}
 #endif
     _LIBCPP_INLINE_VISIBILITY
     iterator lower_bound(const key_type& __k)
@@ -1568,13 +1715,8 @@
 
     typedef _VSTD::__value_type<key_type, mapped_type>             __value_type;
     typedef __map_value_compare<key_type, __value_type, key_compare> __vc;
-    typedef typename allocator_traits<allocator_type>::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-            rebind_alloc<__value_type>
-#else
-            rebind_alloc<__value_type>::other
-#endif
-                                                                    __allocator_type;
+    typedef typename __rebind_alloc_helper<allocator_traits<allocator_type>,
+                                                 __value_type>::type __allocator_type;
     typedef __tree<__value_type, __vc, __allocator_type>            __base;
     typedef typename __base::__node_traits                          __node_traits;
     typedef allocator_traits<allocator_type>                        __alloc_traits;
@@ -1821,6 +1963,8 @@
     _LIBCPP_INLINE_VISIBILITY
     iterator erase(const_iterator __p) {return __tree_.erase(__p.__i_);}
     _LIBCPP_INLINE_VISIBILITY
+    iterator erase(iterator __p)       {return __tree_.erase(__p.__i_);}
+    _LIBCPP_INLINE_VISIBILITY
     size_type erase(const key_type& __k) {return __tree_.__erase_multi(__k);}
     _LIBCPP_INLINE_VISIBILITY
     iterator  erase(const_iterator __f, const_iterator __l)
@@ -1855,7 +1999,7 @@
     template <typename _K2>
     _LIBCPP_INLINE_VISIBILITY
     typename enable_if<__is_transparent<_Compare, _K2>::value,size_type>::type
-    count(const _K2& __k)                   {return __tree_.__count_multi(__k);}
+    count(const _K2& __k) const {return __tree_.__count_multi(__k);}
 #endif
     _LIBCPP_INLINE_VISIBILITY
     iterator lower_bound(const key_type& __k)
diff --git a/include/memory b/include/memory
index 7085ced..df35a07 100644
--- a/include/memory
+++ b/include/memory
@@ -75,6 +75,8 @@
           | false_type                   propagate_on_container_move_assignment;
     typedef Alloc::propagate_on_container_swap
           | false_type                   propagate_on_container_swap;
+    typedef Alloc::is_always_equal
+          | is_empty                     is_always_equal;
 
     template <class T> using rebind_alloc  = Alloc::rebind<U>::other | Alloc<T, Args...>;
     template <class T> using rebind_traits = allocator_traits<rebind_alloc<T>>;
@@ -623,6 +625,18 @@
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
+template <class _ValueType>
+inline _LIBCPP_ALWAYS_INLINE
+_ValueType __libcpp_relaxed_load(_ValueType const* __value) {
+#if !defined(_LIBCPP_HAS_NO_THREADS) && \
+    defined(__ATOMIC_RELAXED) &&        \
+    (__has_builtin(__atomic_load_n) || _GNUC_VER >= 407)
+    return __atomic_load_n(__value, __ATOMIC_RELAXED);
+#else
+    return *__value;
+#endif
+}
+
 // addressof moved to <__functional_base>
 
 template <class _Tp> class allocator;
@@ -1144,6 +1158,29 @@
     typedef typename _Alloc::propagate_on_container_swap type;
 };
 
+template <class _Tp>
+struct __has_is_always_equal
+{
+private:
+    struct __two {char __lx; char __lxx;};
+    template <class _Up> static __two __test(...);
+    template <class _Up> static char __test(typename _Up::is_always_equal* = 0);
+public:
+    static const bool value = sizeof(__test<_Tp>(0)) == 1;
+};
+
+template <class _Alloc, bool = __has_is_always_equal<_Alloc>::value>
+struct __is_always_equal
+{
+    typedef typename _VSTD::is_empty<_Alloc>::type type;
+};
+
+template <class _Alloc>
+struct __is_always_equal<_Alloc, true>
+{
+    typedef typename _Alloc::is_always_equal type;
+};
+
 template <class _Tp, class _Up, bool = __has_rebind<_Tp, _Up>::value>
 struct __has_rebind_other
 {
@@ -1423,6 +1460,8 @@
                      propagate_on_container_move_assignment;
     typedef typename __propagate_on_container_swap<allocator_type>::type
                      propagate_on_container_swap;
+    typedef typename __is_always_equal<allocator_type>::type
+                     is_always_equal;
 
 #ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
     template <class _Tp> using rebind_alloc =
@@ -1521,8 +1560,42 @@
         __construct_forward(allocator_type& __a, _Tp* __begin1, _Tp* __end1, _Tp*& __begin2)
         {
             ptrdiff_t _Np = __end1 - __begin1;
-            _VSTD::memcpy(__begin2, __begin1, _Np * sizeof(_Tp));
-            __begin2 += _Np;
+            if (_Np > 0)
+            {
+                _VSTD::memcpy(__begin2, __begin1, _Np * sizeof(_Tp));
+                __begin2 += _Np;
+            }
+        }
+
+    template <class _Iter, class _Ptr>
+        _LIBCPP_INLINE_VISIBILITY
+        static
+        void
+        __construct_range_forward(allocator_type& __a, _Iter __begin1, _Iter __end1, _Ptr& __begin2)
+        {
+            for (; __begin1 != __end1; ++__begin1, (void) ++__begin2)
+                construct(__a, _VSTD::__to_raw_pointer(__begin2), *__begin1);
+        }
+
+    template <class _Tp>
+        _LIBCPP_INLINE_VISIBILITY
+        static
+        typename enable_if
+        <
+            (is_same<allocator_type, allocator<_Tp> >::value
+                || !__has_construct<allocator_type, _Tp*, _Tp>::value) &&
+             is_trivially_move_constructible<_Tp>::value,
+            void
+        >::type
+        __construct_range_forward(allocator_type& __a, _Tp* __begin1, _Tp* __end1, _Tp*& __begin2)
+        {
+            typedef typename remove_const<_Tp>::type _Vp;
+            ptrdiff_t _Np = __end1 - __begin1;
+            if (_Np > 0)
+            {
+                _VSTD::memcpy(const_cast<_Vp*>(__begin2), __begin1, _Np * sizeof(_Tp));
+                __begin2 += _Np;
+            }
         }
 
     template <class _Ptr>
@@ -1552,7 +1625,8 @@
         {
             ptrdiff_t _Np = __end1 - __begin1;
             __end2 -= _Np;
-            _VSTD::memcpy(__end2, __begin1, _Np * sizeof(_Tp));
+            if (_Np > 0)
+                _VSTD::memcpy(__end2, __begin1, _Np * sizeof(_Tp));
         }
 
 private:
@@ -1607,6 +1681,16 @@
             {return __a;}
 };
 
+template <class _Traits, class _Tp>
+struct __rebind_alloc_helper
+{
+#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
+    typedef typename _Traits::template rebind_alloc<_Tp>        type;
+#else
+    typedef typename _Traits::template rebind_alloc<_Tp>::other type;
+#endif
+};
+
 // allocator
 
 template <class _Tp>
@@ -1622,6 +1706,7 @@
     typedef _Tp               value_type;
 
     typedef true_type propagate_on_container_move_assignment;
+    typedef true_type is_always_equal;
 
     template <class _Up> struct rebind {typedef allocator<_Up> other;};
 
@@ -1714,6 +1799,7 @@
     typedef const _Tp         value_type;
 
     typedef true_type propagate_on_container_move_assignment;
+    typedef true_type is_always_equal;
 
     template <class _Up> struct rebind {typedef allocator<_Up> other;};
 
@@ -1817,6 +1903,9 @@
     _LIBCPP_INLINE_VISIBILITY raw_storage_iterator& operator++() {++__x_; return *this;}
     _LIBCPP_INLINE_VISIBILITY raw_storage_iterator  operator++(int)
         {raw_storage_iterator __t(*this); ++__x_; return __t;}
+#if _LIBCPP_STD_VER >= 14
+    _LIBCPP_INLINE_VISIBILITY _OutputIterator base() const { return __x_; } 
+#endif
 };
 
 template <class _Tp>
@@ -1906,14 +1995,9 @@
 template <class _T1, class _T2, bool = is_same<typename remove_cv<_T1>::type,
                                                      typename remove_cv<_T2>::type>::value,
                                 bool = is_empty<_T1>::value
-#if __has_feature(is_final)
-                                       && !__is_final(_T1)
-#endif
-                                ,
+                                       && !__libcpp_is_final<_T1>::value,
                                 bool = is_empty<_T2>::value
-#if __has_feature(is_final)
-                                       && !__is_final(_T2)
-#endif
+                                       && !__libcpp_is_final<_T2>::value
          >
 struct __libcpp_compressed_pair_switch;
 
@@ -1951,11 +2035,11 @@
     typedef const typename remove_reference<_T1>::type& _T1_const_reference;
     typedef const typename remove_reference<_T2>::type& _T2_const_reference;
 
-    _LIBCPP_INLINE_VISIBILITY __libcpp_compressed_pair_imp() {}
+    _LIBCPP_INLINE_VISIBILITY __libcpp_compressed_pair_imp() : __first_(), __second_() {}
     _LIBCPP_INLINE_VISIBILITY explicit __libcpp_compressed_pair_imp(_T1_param __t1)
-        : __first_(_VSTD::forward<_T1_param>(__t1)) {}
+        : __first_(_VSTD::forward<_T1_param>(__t1)), __second_() {}
     _LIBCPP_INLINE_VISIBILITY explicit __libcpp_compressed_pair_imp(_T2_param __t2)
-        : __second_(_VSTD::forward<_T2_param>(__t2)) {}
+        : __first_(), __second_(_VSTD::forward<_T2_param>(__t2)) {}
     _LIBCPP_INLINE_VISIBILITY __libcpp_compressed_pair_imp(_T1_param __t1, _T2_param __t2)
         : __first_(_VSTD::forward<_T1_param>(__t1)), __second_(_VSTD::forward<_T2_param>(__t2)) {}
 
@@ -2044,9 +2128,9 @@
     typedef const _T1&                                        _T1_const_reference;
     typedef const typename remove_reference<_T2>::type& _T2_const_reference;
 
-    _LIBCPP_INLINE_VISIBILITY __libcpp_compressed_pair_imp() {}
+    _LIBCPP_INLINE_VISIBILITY __libcpp_compressed_pair_imp() : __second_() {}
     _LIBCPP_INLINE_VISIBILITY explicit __libcpp_compressed_pair_imp(_T1_param __t1)
-        : _T1(_VSTD::forward<_T1_param>(__t1)) {}
+        : _T1(_VSTD::forward<_T1_param>(__t1)), __second_() {}
     _LIBCPP_INLINE_VISIBILITY explicit __libcpp_compressed_pair_imp(_T2_param __t2)
         : __second_(_VSTD::forward<_T2_param>(__t2)) {}
     _LIBCPP_INLINE_VISIBILITY __libcpp_compressed_pair_imp(_T1_param __t1, _T2_param __t2)
@@ -2134,11 +2218,11 @@
     typedef const typename remove_reference<_T1>::type& _T1_const_reference;
     typedef const _T2&                                        _T2_const_reference;
 
-    _LIBCPP_INLINE_VISIBILITY __libcpp_compressed_pair_imp() {}
+    _LIBCPP_INLINE_VISIBILITY __libcpp_compressed_pair_imp() : __first_() {}
     _LIBCPP_INLINE_VISIBILITY explicit __libcpp_compressed_pair_imp(_T1_param __t1)
         : __first_(_VSTD::forward<_T1_param>(__t1)) {}
     _LIBCPP_INLINE_VISIBILITY explicit __libcpp_compressed_pair_imp(_T2_param __t2)
-        : _T2(_VSTD::forward<_T2_param>(__t2)) {}
+        : _T2(_VSTD::forward<_T2_param>(__t2)), __first_() {}
     _LIBCPP_INLINE_VISIBILITY __libcpp_compressed_pair_imp(_T1_param __t1, _T2_param __t2)
         _NOEXCEPT_(is_nothrow_move_constructible<_T1>::value &&
                    is_nothrow_move_constructible<_T2>::value)
@@ -3336,7 +3420,7 @@
             {
                 size_t __a;
                 size_t __b;
-            };
+            } __s;
         } __u;
         __u.__t = __v;
         return __murmur2_or_cityhash<size_t>()(&__u, sizeof(__u));
@@ -3358,7 +3442,7 @@
                 size_t __a;
                 size_t __b;
                 size_t __c;
-            };
+            } __s;
         } __u;
         __u.__t = __v;
         return __murmur2_or_cityhash<size_t>()(&__u, sizeof(__u));
@@ -3381,7 +3465,7 @@
                 size_t __b;
                 size_t __c;
                 size_t __d;
-            };
+            } __s;
         } __u;
         __u.__t = __v;
         return __murmur2_or_cityhash<size_t>()(&__u, sizeof(__u));
@@ -3486,8 +3570,8 @@
     try
     {
 #endif
-        for (; __f != __l; ++__f, ++__r)
-            ::new(&*__r) value_type(*__f);
+        for (; __f != __l; ++__f, (void) ++__r)
+            ::new (static_cast<void*>(_VSTD::addressof(*__r))) value_type(*__f);
 #ifndef _LIBCPP_NO_EXCEPTIONS
     }
     catch (...)
@@ -3510,8 +3594,8 @@
     try
     {
 #endif
-        for (; __n > 0; ++__f, ++__r, --__n)
-            ::new(&*__r) value_type(*__f);
+        for (; __n > 0; ++__f, (void) ++__r, (void) --__n)
+            ::new (static_cast<void*>(_VSTD::addressof(*__r))) value_type(*__f);
 #ifndef _LIBCPP_NO_EXCEPTIONS
     }
     catch (...)
@@ -3535,7 +3619,7 @@
     {
 #endif
         for (; __f != __l; ++__f)
-            ::new(&*__f) value_type(__x);
+            ::new (static_cast<void*>(_VSTD::addressof(*__f))) value_type(__x);
 #ifndef _LIBCPP_NO_EXCEPTIONS
     }
     catch (...)
@@ -3557,8 +3641,8 @@
     try
     {
 #endif
-        for (; __n > 0; ++__f, --__n)
-            ::new(&*__f) value_type(__x);
+        for (; __n > 0; ++__f, (void) --__n)
+            ::new (static_cast<void*>(_VSTD::addressof(*__f))) value_type(__x);
 #ifndef _LIBCPP_NO_EXCEPTIONS
     }
     catch (...)
@@ -3600,7 +3684,9 @@
     void __add_shared() _NOEXCEPT;
     bool __release_shared() _NOEXCEPT;
     _LIBCPP_INLINE_VISIBILITY
-    long use_count() const _NOEXCEPT {return __shared_owners_ + 1;}
+    long use_count() const _NOEXCEPT {
+        return __libcpp_relaxed_load(&__shared_owners_) + 1;
+    }
 };
 
 class _LIBCPP_TYPE_VIS __shared_weak_count
@@ -4002,11 +4088,15 @@
         __enable_weak_this(const enable_shared_from_this<_Yp>* __e) _NOEXCEPT
         {
             if (__e)
-                __e->__weak_this_ = *this;
+            {
+                __e->__weak_this_.__ptr_ = const_cast<_Yp*>(static_cast<const _Yp*>(__e));
+                __e->__weak_this_.__cntrl_ = __cntrl_;
+                __cntrl_->__add_weak();
+            }
         }
 
     _LIBCPP_INLINE_VISIBILITY
-    void __enable_weak_this(const void*) _NOEXCEPT {}
+    void __enable_weak_this(const volatile void*) _NOEXCEPT {}
 
     template <class _Up> friend class _LIBCPP_TYPE_VIS_ONLY shared_ptr;
     template <class _Up> friend class _LIBCPP_TYPE_VIS_ONLY weak_ptr;
@@ -4236,9 +4326,16 @@
                             >::type)
     : __ptr_(__r.get())
 {
-    typedef __shared_ptr_pointer<_Yp*, _Dp, allocator<_Yp> > _CntrlBlk;
-    __cntrl_ = new _CntrlBlk(__r.get(), __r.get_deleter(), allocator<_Yp>());
-    __enable_weak_this(__r.get());
+#if _LIBCPP_STD_VER > 11
+    if (__ptr_ == nullptr)
+        __cntrl_ = nullptr;
+    else
+#endif
+    {
+        typedef __shared_ptr_pointer<_Yp*, _Dp, allocator<_Yp> > _CntrlBlk;
+        __cntrl_ = new _CntrlBlk(__r.get(), __r.get_deleter(), allocator<_Yp>());
+        __enable_weak_this(__r.get());
+    }
     __r.release();
 }
 
@@ -4258,11 +4355,18 @@
                             >::type)
     : __ptr_(__r.get())
 {
-    typedef __shared_ptr_pointer<_Yp*,
-                                 reference_wrapper<typename remove_reference<_Dp>::type>,
-                                 allocator<_Yp> > _CntrlBlk;
-    __cntrl_ = new _CntrlBlk(__r.get(), ref(__r.get_deleter()), allocator<_Yp>());
-    __enable_weak_this(__r.get());
+#if _LIBCPP_STD_VER > 11
+    if (__ptr_ == nullptr)
+        __cntrl_ = nullptr;
+    else
+#endif
+    {
+        typedef __shared_ptr_pointer<_Yp*,
+                                     reference_wrapper<typename remove_reference<_Dp>::type>,
+                                     allocator<_Yp> > _CntrlBlk;
+        __cntrl_ = new _CntrlBlk(__r.get(), ref(__r.get_deleter()), allocator<_Yp>());
+        __enable_weak_this(__r.get());
+    }
     __r.release();
 }
 
@@ -5439,6 +5543,38 @@
 
 _LIBCPP_FUNC_VIS void* align(size_t __align, size_t __sz, void*& __ptr, size_t& __space);
 
+// --- Helper for container swap --
+template <typename _Alloc>
+_LIBCPP_INLINE_VISIBILITY
+void __swap_allocator(_Alloc & __a1, _Alloc & __a2)
+#if _LIBCPP_STD_VER >= 14
+    _NOEXCEPT
+#else
+    _NOEXCEPT_(__is_nothrow_swappable<_Alloc>::value)
+#endif
+{
+    __swap_allocator(__a1, __a2, 
+      integral_constant<bool, _VSTD::allocator_traits<_Alloc>::propagate_on_container_swap::value>());
+}
+
+template <typename _Alloc>
+_LIBCPP_INLINE_VISIBILITY
+void __swap_allocator(_Alloc & __a1, _Alloc & __a2, true_type)
+#if _LIBCPP_STD_VER >= 14
+    _NOEXCEPT
+#else
+    _NOEXCEPT_(__is_nothrow_swappable<_Alloc>::value)
+#endif
+{
+    using _VSTD::swap;
+    swap(__a1, __a2);
+}
+
+template <typename _Alloc>
+_LIBCPP_INLINE_VISIBILITY
+void __swap_allocator(_Alloc &, _Alloc &, false_type) _NOEXCEPT {}
+
+
 _LIBCPP_END_NAMESPACE_STD
 
 #endif  // _LIBCPP_MEMORY
diff --git a/include/mutex b/include/mutex
index e2a0daa..373d75b 100644
--- a/include/mutex
+++ b/include/mutex
@@ -175,6 +175,7 @@
 #include <__config>
 #include <__mutex_base>
 #include <functional>
+#include <memory>
 #ifndef _LIBCPP_HAS_NO_VARIADICS
 #include <tuple>
 #endif
@@ -442,7 +443,11 @@
 
 template<class _Callable>
 _LIBCPP_INLINE_VISIBILITY
-void call_once(once_flag&, _Callable);
+void call_once(once_flag&, _Callable&);
+
+template<class _Callable>
+_LIBCPP_INLINE_VISIBILITY
+void call_once(once_flag&, const _Callable&);
 
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 
@@ -465,7 +470,11 @@
 #else  // _LIBCPP_HAS_NO_VARIADICS
     template<class _Callable>
     friend
-    void call_once(once_flag&, _Callable);
+    void call_once(once_flag&, _Callable&);
+
+    template<class _Callable>
+    friend
+    void call_once(once_flag&, const _Callable&);
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 };
 
@@ -474,15 +483,10 @@
 template <class _Fp>
 class __call_once_param
 {
-    _Fp __f_;
+    _Fp& __f_;
 public:
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     _LIBCPP_INLINE_VISIBILITY
-    explicit __call_once_param(_Fp&& __f) : __f_(_VSTD::move(__f)) {}
-#else
-    _LIBCPP_INLINE_VISIBILITY
-    explicit __call_once_param(const _Fp& __f) : __f_(__f) {}
-#endif
+    explicit __call_once_param(_Fp& __f) : __f_(__f) {}
 
     _LIBCPP_INLINE_VISIBILITY
     void operator()()
@@ -496,7 +500,7 @@
     _LIBCPP_INLINE_VISIBILITY
     void __execute(__tuple_indices<_Indices...>)
     {
-        __invoke(_VSTD::move(_VSTD::get<0>(__f_)), _VSTD::move(_VSTD::get<_Indices>(__f_))...);
+        __invoke(_VSTD::get<0>(_VSTD::move(__f_)), _VSTD::get<_Indices>(_VSTD::move(__f_))...);
     }
 };
 
@@ -505,15 +509,10 @@
 template <class _Fp>
 class __call_once_param
 {
-    _Fp __f_;
+    _Fp& __f_;
 public:
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     _LIBCPP_INLINE_VISIBILITY
-    explicit __call_once_param(_Fp&& __f) : __f_(_VSTD::move(__f)) {}
-#else
-    _LIBCPP_INLINE_VISIBILITY
-    explicit __call_once_param(const _Fp& __f) : __f_(__f) {}
-#endif
+    explicit __call_once_param(_Fp& __f) : __f_(__f) {}
 
     _LIBCPP_INLINE_VISIBILITY
     void operator()()
@@ -541,11 +540,11 @@
 void
 call_once(once_flag& __flag, _Callable&& __func, _Args&&... __args)
 {
-    if (__flag.__state_ != ~0ul)
+    if (__libcpp_relaxed_load(&__flag.__state_) != ~0ul)
     {
-        typedef tuple<typename decay<_Callable>::type, typename decay<_Args>::type...> _Gp;
-        __call_once_param<_Gp> __p(_Gp(__decay_copy(_VSTD::forward<_Callable>(__func)),
-                                __decay_copy(_VSTD::forward<_Args>(__args))...));
+        typedef tuple<_Callable&&, _Args&&...> _Gp;
+        _Gp __f(_VSTD::forward<_Callable>(__func), _VSTD::forward<_Args>(__args)...);
+        __call_once_param<_Gp> __p(__f);
         __call_once(__flag.__state_, &__p, &__call_once_proxy<_Gp>);
     }
 }
@@ -555,15 +554,27 @@
 template<class _Callable>
 inline _LIBCPP_INLINE_VISIBILITY
 void
-call_once(once_flag& __flag, _Callable __func)
+call_once(once_flag& __flag, _Callable& __func)
 {
-    if (__flag.__state_ != ~0ul)
+    if (__libcpp_relaxed_load(&__flag.__state_) != ~0ul)
     {
         __call_once_param<_Callable> __p(__func);
         __call_once(__flag.__state_, &__p, &__call_once_proxy<_Callable>);
     }
 }
 
+template<class _Callable>
+inline _LIBCPP_INLINE_VISIBILITY
+void
+call_once(once_flag& __flag, const _Callable& __func)
+{
+    if (__flag.__state_ != ~0ul)
+    {
+        __call_once_param<const _Callable> __p(__func);
+        __call_once(__flag.__state_, &__p, &__call_once_proxy<const _Callable>);
+    }
+}
+
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 
 _LIBCPP_END_NAMESPACE_STD
diff --git a/include/new b/include/new
index 29c1a83..d2b2ae6 100644
--- a/include/new
+++ b/include/new
@@ -52,16 +52,12 @@
 void  operator delete(void* ptr) noexcept;                              // replaceable
 void  operator delete(void* ptr, std::size_t size) noexcept;            // replaceable, C++14
 void  operator delete(void* ptr, const std::nothrow_t&) noexcept;       // replaceable
-void  operator delete(void* ptr, std::size_t size,
-                      const std::nothrow_t&) noexcept;                  // replaceable, C++14
 
 void* operator new[](std::size_t size);                                 // replaceable
 void* operator new[](std::size_t size, const std::nothrow_t&) noexcept; // replaceable
 void  operator delete[](void* ptr) noexcept;                            // replaceable
 void  operator delete[](void* ptr, std::size_t size) noexcept;          // replaceable, C++14
 void  operator delete[](void* ptr, const std::nothrow_t&) noexcept;     // replaceable
-void  operator delete[](void* ptr, std::size_t size,
-                        const std::nothrow_t&) noexcept;                // replaceable, C++14
 
 void* operator new  (std::size_t size, void* ptr) noexcept;
 void* operator new[](std::size_t size, void* ptr) noexcept;
@@ -140,9 +136,9 @@
 _LIBCPP_NEW_DELETE_VIS void* operator new(std::size_t __sz, const std::nothrow_t&) _NOEXCEPT _NOALIAS;
 _LIBCPP_NEW_DELETE_VIS void  operator delete(void* __p) _NOEXCEPT;
 _LIBCPP_NEW_DELETE_VIS void  operator delete(void* __p, const std::nothrow_t&) _NOEXCEPT;
-#if defined(_LIBCPP_BUILDING_NEW) || _LIBCPP_STD_VER >= 14
+#if defined(_LIBCPP_BUILDING_NEW) || _LIBCPP_STD_VER >= 14 || \
+    (defined(__cpp_sized_deallocation) && __cpp_sized_deallocation >= 201309)
 _LIBCPP_NEW_DELETE_VIS void  operator delete(void* __p, std::size_t __sz) _NOEXCEPT;
-_LIBCPP_NEW_DELETE_VIS void  operator delete(void* __p, std::size_t __sz, const std::nothrow_t&) _NOEXCEPT;
 #endif
 
 _LIBCPP_NEW_DELETE_VIS void* operator new[](std::size_t __sz)
@@ -153,9 +149,9 @@
 _LIBCPP_NEW_DELETE_VIS void* operator new[](std::size_t __sz, const std::nothrow_t&) _NOEXCEPT _NOALIAS;
 _LIBCPP_NEW_DELETE_VIS void  operator delete[](void* __p) _NOEXCEPT;
 _LIBCPP_NEW_DELETE_VIS void  operator delete[](void* __p, const std::nothrow_t&) _NOEXCEPT;
-#if defined(_LIBCPP_BUILDING_NEW) || _LIBCPP_STD_VER >= 14
+#if defined(_LIBCPP_BUILDING_NEW) || _LIBCPP_STD_VER >= 14 || \
+    (defined(__cpp_sized_deallocation) && __cpp_sized_deallocation >= 201309)
 _LIBCPP_NEW_DELETE_VIS void  operator delete[](void* __p, std::size_t __sz) _NOEXCEPT;
-_LIBCPP_NEW_DELETE_VIS void  operator delete[](void* __p, std::size_t __sz, const std::nothrow_t&) _NOEXCEPT;
 #endif
 
 inline _LIBCPP_INLINE_VISIBILITY void* operator new  (std::size_t, void* __p) _NOEXCEPT {return __p;}
diff --git a/include/ostream b/include/ostream
index a7af299..f55fd40 100644
--- a/include/ostream
+++ b/include/ostream
@@ -1004,7 +1004,7 @@
 basic_ostream<_CharT, _Traits>::seekp(pos_type __pos)
 {
     sentry __s(*this);
-    if (__s)
+    if (!this->fail())
     {
         if (this->rdbuf()->pubseekpos(__pos, ios_base::out) == pos_type(-1))
             this->setstate(ios_base::failbit);
@@ -1018,7 +1018,7 @@
 basic_ostream<_CharT, _Traits>::seekp(off_type __off, ios_base::seekdir __dir)
 {
     sentry __s(*this);
-    if (__s)
+    if (!this->fail())
     {
         if (this->rdbuf()->pubseekoff(__off, __dir, ios_base::out) == pos_type(-1))
             this->setstate(ios_base::failbit);
diff --git a/include/random b/include/random
index bccf92a..c8341ef 100644
--- a/include/random
+++ b/include/random
@@ -3475,9 +3475,9 @@
 
 class _LIBCPP_TYPE_VIS random_device
 {
-#if !(defined(_WIN32) || defined(_LIBCPP_USING_NACL_RANDOM))
+#ifdef _LIBCPP_USING_DEV_RANDOM
     int __f_;
-#endif // !(defined(_WIN32) || defined(_LIBCPP_USING_NACL_RANDOM))
+#endif // defined(_LIBCPP_USING_DEV_RANDOM)
 public:
     // types
     typedef unsigned result_type;
@@ -6044,9 +6044,6 @@
 operator>>(basic_istream<_CharT, _Traits>& __is,
            discrete_distribution<_IT>& __x)
 {
-    typedef discrete_distribution<_IT> _Eng;
-    typedef typename _Eng::result_type result_type;
-    typedef typename _Eng::param_type param_type;
     __save_flags<_CharT, _Traits> __lx(__is);
     __is.flags(ios_base::dec | ios_base::skipws);
     size_t __n;
@@ -6358,7 +6355,6 @@
 {
     typedef piecewise_constant_distribution<_RT> _Eng;
     typedef typename _Eng::result_type result_type;
-    typedef typename _Eng::param_type param_type;
     __save_flags<_CharT, _Traits> __lx(__is);
     __is.flags(ios_base::dec | ios_base::skipws);
     size_t __n;
@@ -6698,7 +6694,6 @@
 {
     typedef piecewise_linear_distribution<_RT> _Eng;
     typedef typename _Eng::result_type result_type;
-    typedef typename _Eng::param_type param_type;
     __save_flags<_CharT, _Traits> __lx(__is);
     __is.flags(ios_base::dec | ios_base::skipws);
     size_t __n;
diff --git a/include/ratio b/include/ratio
index 48dcd81..f623a06 100644
--- a/include/ratio
+++ b/include/ratio
@@ -21,8 +21,8 @@
 class ratio
 {
 public:
-    static const intmax_t num;
-    static const intmax_t den;
+    static constexpr intmax_t num;
+    static constexpr intmax_t den;
     typedef ratio<num, den> type;
 };
 
@@ -236,19 +236,22 @@
     static_assert(__static_abs<_Num>::value >= 0, "ratio numerator is out of range");
     static_assert(_Den != 0, "ratio divide by 0");
     static_assert(__static_abs<_Den>::value >  0, "ratio denominator is out of range");
-    static const intmax_t __na = __static_abs<_Num>::value;
-    static const intmax_t __da = __static_abs<_Den>::value;
-    static const intmax_t __s = __static_sign<_Num>::value * __static_sign<_Den>::value;
-    static const intmax_t __gcd = __static_gcd<__na, __da>::value;
+    static _LIBCPP_CONSTEXPR const intmax_t __na = __static_abs<_Num>::value;
+    static _LIBCPP_CONSTEXPR const intmax_t __da = __static_abs<_Den>::value;
+    static _LIBCPP_CONSTEXPR const intmax_t __s = __static_sign<_Num>::value * __static_sign<_Den>::value;
+    static _LIBCPP_CONSTEXPR const intmax_t __gcd = __static_gcd<__na, __da>::value;
 public:
-    static const intmax_t num = __s * __na / __gcd;
-    static const intmax_t den = __da / __gcd;
+    static _LIBCPP_CONSTEXPR const intmax_t num = __s * __na / __gcd;
+    static _LIBCPP_CONSTEXPR const intmax_t den = __da / __gcd;
 
     typedef ratio<num, den> type;
 };
 
-template <intmax_t _Num, intmax_t _Den> const intmax_t ratio<_Num, _Den>::num;
-template <intmax_t _Num, intmax_t _Den> const intmax_t ratio<_Num, _Den>::den;
+template <intmax_t _Num, intmax_t _Den>
+_LIBCPP_CONSTEXPR const intmax_t ratio<_Num, _Den>::num;
+
+template <intmax_t _Num, intmax_t _Den>
+_LIBCPP_CONSTEXPR const intmax_t ratio<_Num, _Den>::den;
 
 template <class _Tp>                    struct __is_ratio                     : false_type {};
 template <intmax_t _Num, intmax_t _Den> struct __is_ratio<ratio<_Num, _Den> > : true_type  {};
@@ -398,11 +401,11 @@
 
 template <class _R1, class _R2>
 struct _LIBCPP_TYPE_VIS_ONLY ratio_equal
-    : public integral_constant<bool, _R1::num == _R2::num && _R1::den == _R2::den> {};
+    : public _LIBCPP_BOOL_CONSTANT((_R1::num == _R2::num && _R1::den == _R2::den)) {};
 
 template <class _R1, class _R2>
 struct _LIBCPP_TYPE_VIS_ONLY ratio_not_equal
-    : public integral_constant<bool, !ratio_equal<_R1, _R2>::value> {};
+    : public _LIBCPP_BOOL_CONSTANT((!ratio_equal<_R1, _R2>::value)) {};
 
 // ratio_less
 
@@ -461,19 +464,19 @@
 
 template <class _R1, class _R2>
 struct _LIBCPP_TYPE_VIS_ONLY ratio_less
-    : public integral_constant<bool, __ratio_less<_R1, _R2>::value> {};
+    : public _LIBCPP_BOOL_CONSTANT((__ratio_less<_R1, _R2>::value)) {};
 
 template <class _R1, class _R2>
 struct _LIBCPP_TYPE_VIS_ONLY ratio_less_equal
-    : public integral_constant<bool, !ratio_less<_R2, _R1>::value> {};
+    : public _LIBCPP_BOOL_CONSTANT((!ratio_less<_R2, _R1>::value)) {};
 
 template <class _R1, class _R2>
 struct _LIBCPP_TYPE_VIS_ONLY ratio_greater
-    : public integral_constant<bool, ratio_less<_R2, _R1>::value> {};
+    : public _LIBCPP_BOOL_CONSTANT((ratio_less<_R2, _R1>::value)) {};
 
 template <class _R1, class _R2>
 struct _LIBCPP_TYPE_VIS_ONLY ratio_greater_equal
-    : public integral_constant<bool, !ratio_less<_R1, _R2>::value> {};
+    : public _LIBCPP_BOOL_CONSTANT((!ratio_less<_R1, _R2>::value)) {};
 
 template <class _R1, class _R2>
 struct __ratio_gcd
diff --git a/include/regex b/include/regex
index e1a7f46..c270cab 100644
--- a/include/regex
+++ b/include/regex
@@ -955,6 +955,15 @@
     regex_constants::error_type code() const {return __code_;}
 };
 
+template <regex_constants::error_type _Ev>
+_LIBCPP_ALWAYS_INLINE
+void __throw_regex_error()
+{
+#ifndef _LIBCPP_NO_EXCEPTIONS
+	throw regex_error(_Ev);
+#endif
+}
+
 template <class _CharT>
 struct _LIBCPP_TYPE_VIS_ONLY regex_traits
 {
@@ -1956,7 +1965,8 @@
 void
 __l_anchor<_CharT>::__exec(__state& __s) const
 {
-    if (__s.__at_first_ && __s.__current_ == __s.__first_)
+    if (__s.__at_first_ && __s.__current_ == __s.__first_ &&
+        !(__s.__flags_ & regex_constants::match_not_bol))
     {
         __s.__do_ = __state::__accept_but_not_consume;
         __s.__node_ = this->first();
@@ -1990,7 +2000,8 @@
 void
 __r_anchor<_CharT>::__exec(__state& __s) const
 {
-    if (__s.__current_ == __s.__last_)
+    if (__s.__current_ == __s.__last_ &&
+        !(__s.__flags_ & regex_constants::match_not_eol))
     {
         __s.__do_ = __state::__accept_but_not_consume;
         __s.__node_ = this->first();
@@ -2263,10 +2274,8 @@
             }
             else
             {
-#ifndef _LIBCPP_NO_EXCEPTIONS
                 if (__b.size() != 1 || __e.size() != 1)
-                    throw regex_error(regex_constants::error_collate);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                    __throw_regex_error<regex_constants::error_collate>();
                 if (__icase_)
                 {
                     __b[0] = __traits_.translate_nocase(__b[0]);
@@ -2959,7 +2968,7 @@
 
     _LIBCPP_INLINE_VISIBILITY
     __lookahead(const basic_regex<_CharT, _Traits>& __exp, bool __invert, __node<_CharT>* __s, unsigned __mexp)
-        : base(__s), __exp_(__exp), __invert_(__invert), __mexp_(__mexp) {}
+        : base(__s), __exp_(__exp), __mexp_(__mexp), __invert_(__invert) {}
 
     virtual void __exec(__state&) const;
 };
@@ -3019,10 +3028,8 @@
     case egrep:
         __first = __parse_egrep(__first, __last);
         break;
-#ifndef _LIBCPP_NO_EXCEPTIONS
     default:
-        throw regex_error(regex_constants::__re_err_grammar);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+        __throw_regex_error<regex_constants::__re_err_grammar>();
     }
     return __first;
 }
@@ -3053,10 +3060,8 @@
                 }
             }
         }
-#ifndef _LIBCPP_NO_EXCEPTIONS
         if (__first != __last)
-            throw regex_error(regex_constants::__re_err_empty);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+            __throw_regex_error<regex_constants::__re_err_empty>();
     }
     return __first;
 }
@@ -3069,19 +3074,15 @@
 {
     __owns_one_state<_CharT>* __sa = __end_;
     _ForwardIterator __temp = __parse_ERE_branch(__first, __last);
-#ifndef _LIBCPP_NO_EXCEPTIONS
     if (__temp == __first)
-        throw regex_error(regex_constants::__re_err_empty);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+        __throw_regex_error<regex_constants::__re_err_empty>();
     __first = __temp;
     while (__first != __last && *__first == '|')
     {
         __owns_one_state<_CharT>* __sb = __end_;
         __temp = __parse_ERE_branch(++__first, __last);
-#ifndef _LIBCPP_NO_EXCEPTIONS
         if (__temp == __first)
-            throw regex_error(regex_constants::__re_err_empty);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+            __throw_regex_error<regex_constants::__re_err_empty>();
         __push_alternation(__sa, __sb);
         __first = __temp;
     }
@@ -3095,10 +3096,8 @@
                                                  _ForwardIterator __last)
 {
     _ForwardIterator __temp = __parse_ERE_expression(__first, __last);
-#ifndef _LIBCPP_NO_EXCEPTIONS
     if (__temp == __first)
-        throw regex_error(regex_constants::__re_err_empty);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+        __throw_regex_error<regex_constants::__re_err_empty>();
     do
     {
         __first = __temp;
@@ -3133,10 +3132,8 @@
             unsigned __temp_count = __marked_count_;
             ++__open_count_;
             __temp = __parse_extended_reg_exp(++__temp, __last);
-#ifndef _LIBCPP_NO_EXCEPTIONS
             if (__temp == __last || *__temp != ')')
-                throw regex_error(regex_constants::error_paren);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_paren>();
             __push_end_marked_subexpression(__temp_count);
             --__open_count_;
             ++__temp;
@@ -3201,10 +3198,8 @@
             unsigned __temp_count = __marked_count_;
             __first = __parse_RE_expression(__temp, __last);
             __temp = __parse_Back_close_paren(__first, __last);
-#ifndef _LIBCPP_NO_EXCEPTIONS
             if (__temp == __first)
-                throw regex_error(regex_constants::error_paren);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_paren>();
             __push_end_marked_subexpression(__temp_count);
             __first = __temp;
         }
@@ -3518,22 +3513,16 @@
                 int __min = 0;
                 __first = __temp;
                 __temp = __parse_DUP_COUNT(__first, __last, __min);
-#ifndef _LIBCPP_NO_EXCEPTIONS
                 if (__temp == __first)
-                    throw regex_error(regex_constants::error_badbrace);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                    __throw_regex_error<regex_constants::error_badbrace>();
                 __first = __temp;
-#ifndef _LIBCPP_NO_EXCEPTIONS
                 if (__first == __last)
-                    throw regex_error(regex_constants::error_brace);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                    __throw_regex_error<regex_constants::error_brace>();
                 if (*__first != ',')
                 {
                     __temp = __parse_Back_close_brace(__first, __last);
-#ifndef _LIBCPP_NO_EXCEPTIONS
                     if (__temp == __first)
-                        throw regex_error(regex_constants::error_brace);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                        __throw_regex_error<regex_constants::error_brace>();
                     __push_loop(__min, __min, __s, __mexp_begin, __mexp_end,
                                     true);
                     __first = __temp;
@@ -3544,18 +3533,14 @@
                     int __max = -1;
                     __first = __parse_DUP_COUNT(__first, __last, __max);
                     __temp = __parse_Back_close_brace(__first, __last);
-#ifndef _LIBCPP_NO_EXCEPTIONS
                     if (__temp == __first)
-                        throw regex_error(regex_constants::error_brace);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                        __throw_regex_error<regex_constants::error_brace>();
                     if (__max == -1)
                         __push_greedy_inf_repeat(__min, __s, __mexp_begin, __mexp_end);
                     else
                     {
-#ifndef _LIBCPP_NO_EXCEPTIONS
                         if (__max < __min)
-                            throw regex_error(regex_constants::error_badbrace);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                            __throw_regex_error<regex_constants::error_badbrace>();
                         __push_loop(__min, __max, __s, __mexp_begin, __mexp_end,
                                     true);
                     }
@@ -3615,15 +3600,11 @@
             {
                 int __min;
                 _ForwardIterator __temp = __parse_DUP_COUNT(++__first, __last, __min);
-#ifndef _LIBCPP_NO_EXCEPTIONS
                 if (__temp == __first)
-                    throw regex_error(regex_constants::error_badbrace);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                    __throw_regex_error<regex_constants::error_badbrace>();
                 __first = __temp;
-#ifndef _LIBCPP_NO_EXCEPTIONS
                 if (__first == __last)
-                    throw regex_error(regex_constants::error_brace);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                    __throw_regex_error<regex_constants::error_brace>();
                 switch (*__first)
                 {
                 case '}':
@@ -3638,10 +3619,8 @@
                     break;
                 case ',':
                     ++__first;
-#ifndef _LIBCPP_NO_EXCEPTIONS
                     if (__first == __last)
-                        throw regex_error(regex_constants::error_badbrace);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                        __throw_regex_error<regex_constants::error_badbrace>();
                     if (*__first == '}')
                     {
                         ++__first;
@@ -3657,20 +3636,14 @@
                     {
                         int __max = -1;
                         __temp = __parse_DUP_COUNT(__first, __last, __max);
-#ifndef _LIBCPP_NO_EXCEPTIONS
                         if (__temp == __first)
-                            throw regex_error(regex_constants::error_brace);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                            __throw_regex_error<regex_constants::error_brace>();
                         __first = __temp;
-#ifndef _LIBCPP_NO_EXCEPTIONS
                         if (__first == __last || *__first != '}')
-                            throw regex_error(regex_constants::error_brace);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                            __throw_regex_error<regex_constants::error_brace>();
                         ++__first;
-#ifndef _LIBCPP_NO_EXCEPTIONS
                         if (__max < __min)
-                            throw regex_error(regex_constants::error_badbrace);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                            __throw_regex_error<regex_constants::error_badbrace>();
                         if (__grammar == ECMAScript && __first != __last && *__first == '?')
                         {
                             ++__first;
@@ -3680,10 +3653,8 @@
                             __push_loop(__min, __max, __s, __mexp_begin, __mexp_end);
                     }
                     break;
-#ifndef _LIBCPP_NO_EXCEPTIONS
                 default:
-                    throw regex_error(regex_constants::error_badbrace);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                    __throw_regex_error<regex_constants::error_badbrace>();
                 }
             }
             break;
@@ -3701,10 +3672,8 @@
     if (__first != __last && *__first == '[')
     {
         ++__first;
-#ifndef _LIBCPP_NO_EXCEPTIONS
         if (__first == __last)
-            throw regex_error(regex_constants::error_brack);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+            __throw_regex_error<regex_constants::error_brack>();
         bool __negate = false;
         if (*__first == '^')
         {
@@ -3713,29 +3682,23 @@
         }
         __bracket_expression<_CharT, _Traits>* __ml = __start_matching_list(__negate);
         // __ml owned by *this
-#ifndef _LIBCPP_NO_EXCEPTIONS
         if (__first == __last)
-            throw regex_error(regex_constants::error_brack);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+            __throw_regex_error<regex_constants::error_brack>();
         if ((__flags_ & 0x1F0) != ECMAScript && *__first == ']')
         {
             __ml->__add_char(']');
             ++__first;
         }
         __first = __parse_follow_list(__first, __last, __ml);
-#ifndef _LIBCPP_NO_EXCEPTIONS
         if (__first == __last)
-            throw regex_error(regex_constants::error_brack);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+            __throw_regex_error<regex_constants::error_brack>();
         if (*__first == '-')
         {
             __ml->__add_char('-');
             ++__first;
         }
-#ifndef _LIBCPP_NO_EXCEPTIONS
         if (__first == __last || *__first != ']')
-            throw regex_error(regex_constants::error_brack);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+            __throw_regex_error<regex_constants::error_brack>();
         ++__first;
     }
     return __first;
@@ -3855,10 +3818,8 @@
                           basic_string<_CharT>& __str,
                           __bracket_expression<_CharT, _Traits>* __ml)
 {
-#ifndef _LIBCPP_NO_EXCEPTIONS
     if (__first == __last)
-        throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+        __throw_regex_error<regex_constants::error_escape>();
     switch (*__first)
     {
     case 0:
@@ -3899,10 +3860,8 @@
                           _ForwardIterator __last,
                           basic_string<_CharT>* __str)
 {
-#ifndef _LIBCPP_NO_EXCEPTIONS
     if (__first == __last)
-        throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+        __throw_regex_error<regex_constants::error_escape>();
     switch (*__first)
     {
     case '\\':
@@ -3970,10 +3929,8 @@
         else
             __push_char(_CharT(__val));
     }
-#ifndef _LIBCPP_NO_EXCEPTIONS
     else
-        throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+        __throw_regex_error<regex_constants::error_escape>();
     return __first;
 }
 
@@ -3989,18 +3946,14 @@
     value_type _Equal_close[2] = {'=', ']'};
     _ForwardIterator __temp = _VSTD::search(__first, __last, _Equal_close,
                                                             _Equal_close+2);
-#ifndef _LIBCPP_NO_EXCEPTIONS
     if (__temp == __last)
-        throw regex_error(regex_constants::error_brack);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+        __throw_regex_error<regex_constants::error_brack>();
     // [__first, __temp) contains all text in [= ... =]
     typedef typename _Traits::string_type string_type;
     string_type __collate_name =
         __traits_.lookup_collatename(__first, __temp);
-#ifndef _LIBCPP_NO_EXCEPTIONS
     if (__collate_name.empty())
-        throw regex_error(regex_constants::error_collate);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+        __throw_regex_error<regex_constants::error_collate>();
     string_type __equiv_name =
         __traits_.transform_primary(__collate_name.begin(),
                                     __collate_name.end());
@@ -4016,10 +3969,8 @@
         case 2:
             __ml->__add_digraph(__collate_name[0], __collate_name[1]);
             break;
-#ifndef _LIBCPP_NO_EXCEPTIONS
         default:
-            throw regex_error(regex_constants::error_collate);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+            __throw_regex_error<regex_constants::error_collate>();
         }
     }
     __first = _VSTD::next(__temp, 2);
@@ -4038,18 +3989,14 @@
     value_type _Colon_close[2] = {':', ']'};
     _ForwardIterator __temp = _VSTD::search(__first, __last, _Colon_close,
                                                             _Colon_close+2);
-#ifndef _LIBCPP_NO_EXCEPTIONS
     if (__temp == __last)
-        throw regex_error(regex_constants::error_brack);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+        __throw_regex_error<regex_constants::error_brack>();
     // [__first, __temp) contains all text in [: ... :]
     typedef typename _Traits::char_class_type char_class_type;
     char_class_type __class_type =
         __traits_.lookup_classname(__first, __temp, __flags_ & icase);
-#ifndef _LIBCPP_NO_EXCEPTIONS
     if (__class_type == 0)
-        throw regex_error(regex_constants::error_brack);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+        __throw_regex_error<regex_constants::error_brack>();
     __ml->__add_class(__class_type);
     __first = _VSTD::next(__temp, 2);
     return __first;
@@ -4067,22 +4014,17 @@
     value_type _Dot_close[2] = {'.', ']'};
     _ForwardIterator __temp = _VSTD::search(__first, __last, _Dot_close,
                                                             _Dot_close+2);
-#ifndef _LIBCPP_NO_EXCEPTIONS
     if (__temp == __last)
-        throw regex_error(regex_constants::error_brack);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+        __throw_regex_error<regex_constants::error_brack>();
     // [__first, __temp) contains all text in [. ... .]
-    typedef typename _Traits::string_type string_type;
     __col_sym = __traits_.lookup_collatename(__first, __temp);
     switch (__col_sym.size())
     {
     case 1:
     case 2:
         break;
-#ifndef _LIBCPP_NO_EXCEPTIONS
     default:
-        throw regex_error(regex_constants::error_collate);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+        __throw_regex_error<regex_constants::error_collate>();
     }
     __first = _VSTD::next(__temp, 2);
     return __first;
@@ -4226,10 +4168,8 @@
                                 unsigned __mexp = __exp.__marked_count_;
                                 __push_lookahead(_VSTD::move(__exp), false, __marked_count_);
                                 __marked_count_ += __mexp;
-#ifndef _LIBCPP_NO_EXCEPTIONS
                                 if (__temp == __last || *__temp != ')')
-                                    throw regex_error(regex_constants::error_paren);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                                    __throw_regex_error<regex_constants::error_paren>();
                                 __first = ++__temp;
                             }
                             break;
@@ -4241,10 +4181,8 @@
                                 unsigned __mexp = __exp.__marked_count_;
                                 __push_lookahead(_VSTD::move(__exp), true, __marked_count_);
                                 __marked_count_ += __mexp;
-#ifndef _LIBCPP_NO_EXCEPTIONS
                                 if (__temp == __last || *__temp != ')')
-                                    throw regex_error(regex_constants::error_paren);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                                    __throw_regex_error<regex_constants::error_paren>();
                                 __first = ++__temp;
                             }
                             break;
@@ -4281,19 +4219,15 @@
         case '(':
             {
                 ++__first;
-#ifndef _LIBCPP_NO_EXCEPTIONS
                 if (__first == __last)
-                    throw regex_error(regex_constants::error_paren);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                    __throw_regex_error<regex_constants::error_paren>();
                 _ForwardIterator __temp = _VSTD::next(__first);
                 if (__temp != __last && *__first == '?' && *__temp == ':')
                 {
                     ++__open_count_;
                     __first = __parse_ecma_exp(++__temp, __last);
-#ifndef _LIBCPP_NO_EXCEPTIONS
                     if (__first == __last || *__first != ')')
-                        throw regex_error(regex_constants::error_paren);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                        __throw_regex_error<regex_constants::error_paren>();
                     --__open_count_;
                     ++__first;
                 }
@@ -4303,16 +4237,20 @@
                     unsigned __temp_count = __marked_count_;
                     ++__open_count_;
                     __first = __parse_ecma_exp(__first, __last);
-#ifndef _LIBCPP_NO_EXCEPTIONS
                     if (__first == __last || *__first != ')')
-                        throw regex_error(regex_constants::error_paren);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                        __throw_regex_error<regex_constants::error_paren>();
                     __push_end_marked_subexpression(__temp_count);
                     --__open_count_;
                     ++__first;
                 }
             }
             break;
+        case '*':
+        case '+':
+        case '?':
+        case '{':
+            __throw_regex_error<regex_constants::error_badrepeat>();
+            break;
         default:
             __first = __parse_pattern_character(__first, __last);
             break;
@@ -4367,10 +4305,8 @@
             unsigned __v = *__first - '0';
             for (++__first; '0' <= *__first && *__first <= '9'; ++__first)
                 __v = 10 * __v + *__first - '0';
-#ifndef _LIBCPP_NO_EXCEPTIONS
             if (__v > mark_count())
-                throw regex_error(regex_constants::error_backref);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_backref>();
             __push_back_ref(__v);
         }
     }
@@ -4486,62 +4422,42 @@
                         __push_char(_CharT(*__t % 32));
                     __first = ++__t;
                 }
-#ifndef _LIBCPP_NO_EXCEPTIONS
                 else 
-                    throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                    __throw_regex_error<regex_constants::error_escape>();
             }
-#ifndef _LIBCPP_NO_EXCEPTIONS
             else
-                throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_escape>();
             break;
         case 'u':
             ++__first;
-#ifndef _LIBCPP_NO_EXCEPTIONS
             if (__first == __last)
-                throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_escape>();
             __hd = __traits_.value(*__first, 16);
-#ifndef _LIBCPP_NO_EXCEPTIONS
             if (__hd == -1)
-                throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_escape>();
             __sum = 16 * __sum + static_cast<unsigned>(__hd);
             ++__first;
-#ifndef _LIBCPP_NO_EXCEPTIONS
             if (__first == __last)
-                throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_escape>();
             __hd = __traits_.value(*__first, 16);
-#ifndef _LIBCPP_NO_EXCEPTIONS
             if (__hd == -1)
-                throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_escape>();
             __sum = 16 * __sum + static_cast<unsigned>(__hd);
             // drop through
         case 'x':
             ++__first;
-#ifndef _LIBCPP_NO_EXCEPTIONS
             if (__first == __last)
-                throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_escape>();
             __hd = __traits_.value(*__first, 16);
-#ifndef _LIBCPP_NO_EXCEPTIONS
             if (__hd == -1)
-                throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_escape>();
             __sum = 16 * __sum + static_cast<unsigned>(__hd);
             ++__first;
-#ifndef _LIBCPP_NO_EXCEPTIONS
             if (__first == __last)
-                throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_escape>();
             __hd = __traits_.value(*__first, 16);
-#ifndef _LIBCPP_NO_EXCEPTIONS
             if (__hd == -1)
-                throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_escape>();
             __sum = 16 * __sum + static_cast<unsigned>(__hd);
             if (__str)
                 *__str = _CharT(__sum);
@@ -4565,10 +4481,8 @@
                     __push_char(*__first);
                 ++__first;
             }
-#ifndef _LIBCPP_NO_EXCEPTIONS
             else
-                throw regex_error(regex_constants::error_escape);
-#endif  // _LIBCPP_NO_EXCEPTIONS
+                __throw_regex_error<regex_constants::error_escape>();
             break;
         }
     }
@@ -5429,8 +5343,8 @@
       __unmatched_(),
       __prefix_(),
       __suffix_(),
-      __position_start_(),
-      __ready_(false)
+      __ready_(false),
+      __position_start_()
 {
 }
 
@@ -5655,9 +5569,7 @@
                 __states.pop_back();
                 break;
             default:
-#ifndef _LIBCPP_NO_EXCEPTIONS
-                throw regex_error(regex_constants::__re_err_unknown);
-#endif
+                __throw_regex_error<regex_constants::__re_err_unknown>();
                 break;
 
             }
@@ -5727,9 +5639,7 @@
                 __states.pop_back();
                 break;
             default:
-#ifndef _LIBCPP_NO_EXCEPTIONS
-                throw regex_error(regex_constants::__re_err_unknown);
-#endif
+                __throw_regex_error<regex_constants::__re_err_unknown>();
                 break;
             }
         } while (!__states.empty());
@@ -5815,9 +5725,7 @@
                 __states.pop_back();
                 break;
             default:
-#ifndef _LIBCPP_NO_EXCEPTIONS
-                throw regex_error(regex_constants::__re_err_unknown);
-#endif
+                __throw_regex_error<regex_constants::__re_err_unknown>();
                 break;
             }
         } while (!__states.empty());
diff --git a/include/scoped_allocator b/include/scoped_allocator
index aa8bece..cd4987a 100644
--- a/include/scoped_allocator
+++ b/include/scoped_allocator
@@ -38,6 +38,7 @@
     typedef see below propagate_on_container_copy_assignment;
     typedef see below propagate_on_container_move_assignment;
     typedef see below propagate_on_container_swap;
+    typedef see below is_always_equal;
 
     template <class Tp>
         struct rebind
@@ -170,6 +171,22 @@
         __get_poc_swap<_Allocs...>::value;
 };
 
+template <class ..._Allocs> struct __get_is_always_equal;
+
+template <class _A0>
+struct __get_is_always_equal<_A0>
+{
+    static const bool value = allocator_traits<_A0>::is_always_equal::value;
+};
+
+template <class _A0, class ..._Allocs>
+struct __get_is_always_equal<_A0, _Allocs...>
+{
+    static const bool value =
+        allocator_traits<_A0>::is_always_equal::value &&
+        __get_is_always_equal<_Allocs...>::value;
+};
+
 template <class ..._Allocs>
 class __scoped_allocator_storage;
 
@@ -397,6 +414,11 @@
                 bool,
                 __get_poc_swap<outer_allocator_type, _InnerAllocs...>::value
             > propagate_on_container_swap;
+    typedef integral_constant
+            <
+                bool,
+                __get_is_always_equal<outer_allocator_type, _InnerAllocs...>::value
+            > is_always_equal;
 
     template <class _Tp>
     struct rebind
diff --git a/include/set b/include/set
index 22d794d..9d64a52 100644
--- a/include/set
+++ b/include/set
@@ -116,6 +116,7 @@
     void insert(initializer_list<value_type> il);
 
     iterator  erase(const_iterator position);
+    iterator  erase(iterator position);  // C++14
     size_type erase(const key_type& k);
     iterator  erase(const_iterator first, const_iterator last);
     void clear() noexcept;
@@ -297,6 +298,7 @@
     void insert(initializer_list<value_type> il);
 
     iterator  erase(const_iterator position);
+    iterator  erase(iterator position);  // C++14
     size_type erase(const key_type& k);
     iterator  erase(const_iterator first, const_iterator last);
     void clear() noexcept;
diff --git a/include/shared_mutex b/include/shared_mutex
index 9b7f0bf..dcb9394 100644
--- a/include/shared_mutex
+++ b/include/shared_mutex
@@ -19,6 +19,29 @@
 namespace std
 {
 
+class shared_mutex      // C++17
+{
+public:
+    shared_mutex();
+    ~shared_mutex();
+
+    shared_mutex(const shared_mutex&) = delete;
+    shared_mutex& operator=(const shared_mutex&) = delete;
+
+    // Exclusive ownership
+    void lock(); // blocking
+    bool try_lock();
+    void unlock();
+
+    // Shared ownership
+    void lock_shared(); // blocking
+    bool try_lock_shared();
+    void unlock_shared();
+
+    typedef implementation-defined native_handle_type; // See 30.2.3
+    native_handle_type native_handle(); // See 30.2.3
+};
+
 class shared_timed_mutex
 {
 public:
@@ -118,7 +141,7 @@
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
-class _LIBCPP_TYPE_VIS shared_timed_mutex
+struct _LIBCPP_TYPE_VIS __shared_mutex_base
 {
     mutex               __mut_;
     condition_variable  __gate1_;
@@ -127,6 +150,58 @@
 
     static const unsigned __write_entered_ = 1U << (sizeof(unsigned)*__CHAR_BIT__ - 1);
     static const unsigned __n_readers_ = ~__write_entered_;
+
+    __shared_mutex_base();
+    _LIBCPP_INLINE_VISIBILITY ~__shared_mutex_base() = default;
+
+    __shared_mutex_base(const __shared_mutex_base&) = delete;
+    __shared_mutex_base& operator=(const __shared_mutex_base&) = delete;
+
+    // Exclusive ownership
+    void lock(); // blocking
+    bool try_lock();
+    void unlock();
+
+    // Shared ownership
+    void lock_shared(); // blocking
+    bool try_lock_shared();
+    void unlock_shared();
+
+//     typedef implementation-defined native_handle_type; // See 30.2.3
+//     native_handle_type native_handle(); // See 30.2.3
+};
+
+
+#if _LIBCPP_STD_VER > 14
+class _LIBCPP_TYPE_VIS shared_mutex
+{
+	__shared_mutex_base __base;
+public:
+    shared_mutex() : __base() {}
+    _LIBCPP_INLINE_VISIBILITY ~shared_mutex() = default;
+
+    shared_mutex(const shared_mutex&) = delete;
+    shared_mutex& operator=(const shared_mutex&) = delete;
+
+    // Exclusive ownership
+    _LIBCPP_INLINE_VISIBILITY void lock()     { return __base.lock(); }
+    _LIBCPP_INLINE_VISIBILITY bool try_lock() { return __base.try_lock(); }
+    _LIBCPP_INLINE_VISIBILITY void unlock()   { return __base.unlock(); }
+
+    // Shared ownership
+    _LIBCPP_INLINE_VISIBILITY void lock_shared()     { return __base.lock_shared(); }
+    _LIBCPP_INLINE_VISIBILITY bool try_lock_shared() { return __base.try_lock_shared(); }
+    _LIBCPP_INLINE_VISIBILITY void unlock_shared()   { return __base.unlock_shared(); }
+
+//     typedef __shared_mutex_base::native_handle_type native_handle_type;
+//     _LIBCPP_INLINE_VISIBILITY native_handle_type native_handle() { return __base::unlock_shared(); }
+};
+#endif
+
+
+class _LIBCPP_TYPE_VIS shared_timed_mutex
+{
+	__shared_mutex_base __base;
 public:
     shared_timed_mutex();
     _LIBCPP_INLINE_VISIBILITY ~shared_timed_mutex() = default;
@@ -170,29 +245,30 @@
 shared_timed_mutex::try_lock_until(
                         const chrono::time_point<_Clock, _Duration>& __abs_time)
 {
-    unique_lock<mutex> __lk(__mut_);
-    if (__state_ & __write_entered_)
+    unique_lock<mutex> __lk(__base.__mut_);
+    if (__base.__state_ & __base.__write_entered_)
     {
         while (true)
         {
-            cv_status __status = __gate1_.wait_until(__lk, __abs_time);
-            if ((__state_ & __write_entered_) == 0)
+            cv_status __status = __base.__gate1_.wait_until(__lk, __abs_time);
+            if ((__base.__state_ & __base.__write_entered_) == 0)
                 break;
             if (__status == cv_status::timeout)
                 return false;
         }
     }
-    __state_ |= __write_entered_;
-    if (__state_ & __n_readers_)
+    __base.__state_ |= __base.__write_entered_;
+    if (__base.__state_ & __base.__n_readers_)
     {
         while (true)
         {
-            cv_status __status = __gate2_.wait_until(__lk, __abs_time);
-            if ((__state_ & __n_readers_) == 0)
+            cv_status __status = __base.__gate2_.wait_until(__lk, __abs_time);
+            if ((__base.__state_ & __base.__n_readers_) == 0)
                 break;
             if (__status == cv_status::timeout)
             {
-                __state_ &= ~__write_entered_;
+                __base.__state_ &= ~__base.__write_entered_;
+                __base.__gate1_.notify_all();
                 return false;
             }
         }
@@ -205,22 +281,22 @@
 shared_timed_mutex::try_lock_shared_until(
                         const chrono::time_point<_Clock, _Duration>& __abs_time)
 {
-    unique_lock<mutex> __lk(__mut_);
-    if ((__state_ & __write_entered_) || (__state_ & __n_readers_) == __n_readers_)
+    unique_lock<mutex> __lk(__base.__mut_);
+    if ((__base.__state_ & __base.__write_entered_) || (__base.__state_ & __base.__n_readers_) == __base.__n_readers_)
     {
         while (true)
         {
-            cv_status status = __gate1_.wait_until(__lk, __abs_time);
-            if ((__state_ & __write_entered_) == 0 &&
-                                       (__state_ & __n_readers_) < __n_readers_)
+            cv_status status = __base.__gate1_.wait_until(__lk, __abs_time);
+            if ((__base.__state_ & __base.__write_entered_) == 0 &&
+                                       (__base.__state_ & __base.__n_readers_) < __base.__n_readers_)
                 break;
             if (status == cv_status::timeout)
                 return false;
         }
     }
-    unsigned __num_readers = (__state_ & __n_readers_) + 1;
-    __state_ &= ~__n_readers_;
-    __state_ |= __num_readers;
+    unsigned __num_readers = (__base.__state_ & __base.__n_readers_) + 1;
+    __base.__state_ &= ~__base.__n_readers_;
+    __base.__state_ |= __num_readers;
     return true;
 }
 
diff --git a/include/string b/include/string
index 840932a..2c677ce 100644
--- a/include/string
+++ b/include/string
@@ -220,8 +220,8 @@
     basic_string substr(size_type pos = 0, size_type n = npos) const;
 
     void swap(basic_string& str)
-        noexcept(!allocator_type::propagate_on_container_swap::value ||
-                 __is_nothrow_swappable<allocator_type>::value)
+        noexcept(allocator_traits<allocator_type>::propagate_on_container_swap::value ||
+                 allocator_traits<allocator_type>::is_always_equal::value);  // C++17
 
     const value_type* c_str() const noexcept;
     const value_type* data() const noexcept;
@@ -742,7 +742,7 @@
     static inline _LIBCPP_CONSTEXPR bool eq_int_type(int_type __c1, int_type __c2) _NOEXCEPT
         {return __c1 == __c2;}
     static inline _LIBCPP_CONSTEXPR int_type eof() _NOEXCEPT
-        {return int_type(0xDFFF);}
+        {return int_type(0xFFFF);}
 };
 
 inline _LIBCPP_INLINE_VISIBILITY
@@ -1322,13 +1322,26 @@
 
     _LIBCPP_INLINE_VISIBILITY basic_string()
         _NOEXCEPT_(is_nothrow_default_constructible<allocator_type>::value);
-    _LIBCPP_INLINE_VISIBILITY explicit basic_string(const allocator_type& __a);
+
+    _LIBCPP_INLINE_VISIBILITY explicit basic_string(const allocator_type& __a)
+#if _LIBCPP_STD_VER <= 14
+        _NOEXCEPT_(is_nothrow_copy_constructible<allocator_type>::value);
+#else
+        _NOEXCEPT;
+#endif
+
     basic_string(const basic_string& __str);
     basic_string(const basic_string& __str, const allocator_type& __a);
+
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     _LIBCPP_INLINE_VISIBILITY
     basic_string(basic_string&& __str)
+#if _LIBCPP_STD_VER <= 14
         _NOEXCEPT_(is_nothrow_move_constructible<allocator_type>::value);
+#else
+        _NOEXCEPT;
+#endif
+
     _LIBCPP_INLINE_VISIBILITY
     basic_string(basic_string&& __str, const allocator_type& __a);
 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
@@ -1591,8 +1604,12 @@
 
     _LIBCPP_INLINE_VISIBILITY
     void swap(basic_string& __str)
-        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<allocator_type>::value);
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT;
+#else
+        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 
+                    __is_nothrow_swappable<allocator_type>::value);
+#endif
 
     _LIBCPP_INLINE_VISIBILITY
     const value_type* c_str() const _NOEXCEPT {return data();}
@@ -1855,24 +1872,6 @@
         _NOEXCEPT
         {}
 
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(allocator_type& __x, allocator_type& __y)
-        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<allocator_type>::value)
-        {__swap_alloc(__x, __y, integral_constant<bool,
-                      __alloc_traits::propagate_on_container_swap::value>());}
-
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(allocator_type& __x, allocator_type& __y, true_type)
-        _NOEXCEPT_(__is_nothrow_swappable<allocator_type>::value)
-        {
-            using _VSTD::swap;
-            swap(__x, __y);
-        }
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(allocator_type&, allocator_type&, false_type) _NOEXCEPT
-        {}
-
     _LIBCPP_INLINE_VISIBILITY void __invalidate_all_iterators();
     _LIBCPP_INLINE_VISIBILITY void __invalidate_iterators_past(size_type);
 
@@ -1937,7 +1936,12 @@
 template <class _CharT, class _Traits, class _Allocator>
 inline _LIBCPP_INLINE_VISIBILITY
 basic_string<_CharT, _Traits, _Allocator>::basic_string(const allocator_type& __a)
-    : __r_(__a)
+#if _LIBCPP_STD_VER <= 14
+        _NOEXCEPT_(is_nothrow_copy_constructible<allocator_type>::value)
+#else
+        _NOEXCEPT
+#endif
+: __r_(__a)
 {
 #if _LIBCPP_DEBUG_LEVEL >= 2
     __get_db()->__insert_c(this);
@@ -2070,7 +2074,11 @@
 template <class _CharT, class _Traits, class _Allocator>
 inline _LIBCPP_INLINE_VISIBILITY
 basic_string<_CharT, _Traits, _Allocator>::basic_string(basic_string&& __str)
+#if _LIBCPP_STD_VER <= 14
         _NOEXCEPT_(is_nothrow_move_constructible<allocator_type>::value)
+#else
+        _NOEXCEPT
+#endif
     : __r_(_VSTD::move(__str.__r_))
 {
     __str.__zero();
@@ -3349,8 +3357,12 @@
 inline _LIBCPP_INLINE_VISIBILITY
 void
 basic_string<_CharT, _Traits, _Allocator>::swap(basic_string& __str)
-        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<allocator_type>::value)
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT
+#else
+        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 
+                    __is_nothrow_swappable<allocator_type>::value)
+#endif
 {
 #if _LIBCPP_DEBUG_LEVEL >= 2
     if (!__is_long())
@@ -3360,7 +3372,7 @@
     __get_db()->swap(this, &__str);
 #endif
     _VSTD::swap(__r_.first(), __str.__r_.first());
-    __swap_alloc(__alloc(), __str.__alloc());
+    __swap_allocator(__alloc(), __str.__alloc());
 }
 
 // find
diff --git a/include/tuple b/include/tuple
index 21fa900..3a22aa5 100644
--- a/include/tuple
+++ b/include/tuple
@@ -161,10 +161,8 @@
 
 // __tuple_leaf
 
-template <size_t _Ip, class _Hp, bool=is_empty<_Hp>::value
-#if __has_feature(is_final)
-                                 && !__is_final(_Hp)
-#endif
+template <size_t _Ip, class _Hp,
+          bool=is_empty<_Hp>::value && !__libcpp_is_final<_Hp>::value
          >
 class __tuple_leaf;
 
@@ -846,8 +844,6 @@
 
 namespace { const __ignore_t<unsigned char> ignore = __ignore_t<unsigned char>(); }
 
-template <class _Tp> class _LIBCPP_TYPE_VIS_ONLY reference_wrapper;
-
 template <class _Tp>
 struct __make_tuple_return_impl
 {
diff --git a/include/type_traits b/include/type_traits
index 1820bb2..f0defaf 100644
--- a/include/type_traits
+++ b/include/type_traits
@@ -19,8 +19,13 @@
 
     // helper class:
     template <class T, T v> struct integral_constant;
-    typedef integral_constant<bool, true>  true_type;
-    typedef integral_constant<bool, false> false_type;
+    typedef integral_constant<bool, true>  true_type;   // C++11
+    typedef integral_constant<bool, false> false_type;  // C++11
+    
+    template <bool B>                                   // C++14
+    using bool_constant = integral_constant<bool, B>;   // C++14
+    typedef bool_constant<true> true_type;              // C++14
+    typedef bool_constant<false> false_type;            // C++14
 
     // helper traits
     template <bool, class T = void> struct enable_if;
@@ -211,10 +216,11 @@
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
-#ifndef _LIBCPP_HAS_NO_VARIADICS
-template <class...> 
+template <class>
 struct __void_t { typedef void type; };
-#endif
+
+template <class _Tp>
+struct __identity { typedef _Tp type; };
 
 template <class _Tp, bool>
 struct _LIBCPP_TYPE_VIS_ONLY __dependent_type : public _Tp {};
@@ -260,8 +266,16 @@
 template <class _Tp, _Tp __v>
 _LIBCPP_CONSTEXPR const _Tp integral_constant<_Tp, __v>::value;
 
-typedef integral_constant<bool, true>  true_type;
-typedef integral_constant<bool, false> false_type;
+#if _LIBCPP_STD_VER > 14
+template <bool __b>
+using bool_constant = integral_constant<bool, __b>;
+#define	_LIBCPP_BOOL_CONSTANT(__b) bool_constant<(__b)>
+#else
+#define	_LIBCPP_BOOL_CONSTANT(__b) integral_constant<bool,(__b)>
+#endif
+
+typedef _LIBCPP_BOOL_CONSTANT(true)  true_type;
+typedef _LIBCPP_BOOL_CONSTANT(false) false_type;
 
 // is_const
 
@@ -460,25 +474,21 @@
 // template <class _Tp, class _Up> struct __libcpp_is_member_function_pointer<_Tp _Up::*> : public is_function<_Tp> {};
 // 
 
-template <class _MP, bool _IsMemberFuctionPtr, bool _IsMemberObjectPtr>
+template <class _MP, bool _IsMemberFunctionPtr, bool _IsMemberObjectPtr>
 struct __member_pointer_traits_imp
 {  // forward declaration; specializations later
 };
 
 
-namespace __libcpp_is_member_function_pointer_imp {
-    template <typename _Tp>
-    char __test(typename std::__member_pointer_traits_imp<_Tp, true, false>::_FnType *);
-
-    template <typename>
-    std::__two __test(...);
-};
-    
 template <class _Tp> struct __libcpp_is_member_function_pointer
-    : public integral_constant<bool, sizeof(__libcpp_is_member_function_pointer_imp::__test<_Tp>(nullptr)) == 1> {};
+    : public false_type {};
+
+template <class _Ret, class _Class>
+struct __libcpp_is_member_function_pointer<_Ret _Class::*>
+    : public is_function<_Ret> {};
 
 template <class _Tp> struct _LIBCPP_TYPE_VIS_ONLY is_member_function_pointer
-    : public __libcpp_is_member_function_pointer<typename remove_cv<_Tp>::type> {};
+    : public __libcpp_is_member_function_pointer<typename remove_cv<_Tp>::type>::type {};
 
 // is_member_pointer
 
@@ -679,7 +689,7 @@
 // is_signed
 
 template <class _Tp, bool = is_integral<_Tp>::value>
-struct __libcpp_is_signed_impl : public integral_constant<bool, _Tp(-1) < _Tp(0)> {};
+struct __libcpp_is_signed_impl : public _LIBCPP_BOOL_CONSTANT(_Tp(-1) < _Tp(0)) {};
 
 template <class _Tp>
 struct __libcpp_is_signed_impl<_Tp, false> : public true_type {};  // floating point
@@ -694,7 +704,7 @@
 // is_unsigned
 
 template <class _Tp, bool = is_integral<_Tp>::value>
-struct __libcpp_is_unsigned_impl : public integral_constant<bool, _Tp(0) < _Tp(-1)> {};
+struct __libcpp_is_unsigned_impl : public _LIBCPP_BOOL_CONSTANT(_Tp(0) < _Tp(-1)) {};
 
 template <class _Tp>
 struct __libcpp_is_unsigned_impl<_Tp, false> : public false_type {};  // floating point
@@ -796,8 +806,16 @@
 
 // is_final
 
-#if _LIBCPP_STD_VER > 11 && __has_feature(is_final)
-template <class _Tp> struct _LIBCPP_TYPE_VIS_ONLY 
+#if defined(_LIBCPP_HAS_IS_FINAL)
+template <class _Tp> struct _LIBCPP_TYPE_VIS_ONLY
+__libcpp_is_final : public integral_constant<bool, __is_final(_Tp)> {};
+#else
+template <class _Tp> struct _LIBCPP_TYPE_VIS_ONLY
+__libcpp_is_final : public false_type {};
+#endif
+
+#if defined(_LIBCPP_HAS_IS_FINAL) && _LIBCPP_STD_VER > 11
+template <class _Tp> struct _LIBCPP_TYPE_VIS_ONLY
 is_final : public integral_constant<bool, __is_final(_Tp)> {};
 #endif
 
@@ -838,7 +856,7 @@
 
 // is_convertible
 
-#if __has_feature(is_convertible_to)
+#if __has_feature(is_convertible_to) && !defined(_LIBCPP_USE_IS_CONVERTIBLE_FALLBACK)
 
 template <class _T1, class _T2> struct _LIBCPP_TYPE_VIS_ONLY is_convertible
     : public integral_constant<bool, __is_convertible_to(_T1, _T2) &&
@@ -848,7 +866,16 @@
 
 namespace __is_convertible_imp
 {
-template <class _Tp> char  __test(_Tp);
+template <class _Tp> void  __test_convert(_Tp);
+
+template <class _From, class _To, class = void>
+struct __is_convertible_test : public false_type {};
+
+template <class _From, class _To>
+struct __is_convertible_test<_From, _To,
+    decltype(__test_convert<_To>(_VSTD::declval<_From>()))> : public true_type
+{};
+
 template <class _Tp> __two __test(...);
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 template <class _Tp> _Tp&& __source();
@@ -883,10 +910,8 @@
     unsigned _T2_is_array_function_or_void = __is_convertible_imp::__is_array_function_or_void<_T2>::value>
 struct __is_convertible
     : public integral_constant<bool,
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-        sizeof(__is_convertible_imp::__test<_T2>(__is_convertible_imp::__source<_T1>())) == 1
-#else
-        sizeof(__is_convertible_imp::__test<_T2>(__is_convertible_imp::__source<_T1>())) == 1
+        __is_convertible_imp::__is_convertible_test<_T1, _T2>::value
+#if defined(_LIBCPP_HAS_NO_RVALUE_REFERENCES)
          && !(!is_function<_T1>::value && !is_reference<_T1>::value && is_reference<_T2>::value
               && (!is_const<typename remove_reference<_T2>::type>::value
                   || is_volatile<typename remove_reference<_T2>::type>::value)
@@ -900,6 +925,7 @@
 template <class _T1, class _T2> struct __is_convertible<_T1, _T2, 1, 0> : false_type {};
 
 template <class _T1> struct __is_convertible<_T1, const _T1&, 1, 0> : true_type {};
+template <class _T1> struct __is_convertible<const _T1, const _T1&, 1, 0> : true_type {};
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 template <class _T1> struct __is_convertible<_T1, _T1&&, 1, 0> : true_type {};
 template <class _T1> struct __is_convertible<_T1, const _T1&&, 1, 0> : true_type {};
@@ -1525,7 +1551,7 @@
 struct __is_assignable_imp
     : public common_type
         <
-            decltype(__is_assignable_test(declval<_Tp>(), declval<_Arg>()))
+            decltype(_VSTD::__is_assignable_test(declval<_Tp>(), declval<_Arg>()))
         >::type {};
 
 template <class _Tp, class _Arg>
@@ -1772,7 +1798,8 @@
     typedef _Rp (_FnType) (_Param..., ...);
 };
 
-#if __has_feature(cxx_reference_qualified_functions)
+#if __has_feature(cxx_reference_qualified_functions) || \
+    (defined(_GNUC_VER) && _GNUC_VER >= 409)
 
 template <class _Rp, class _Class, class ..._Param>
 struct __member_pointer_traits_imp<_Rp (_Class::*)(_Param...) &, true, false>
@@ -1902,7 +1929,7 @@
     typedef _Rp (_FnType) (_Param..., ...);
 };
 
-#endif  // __has_feature(cxx_reference_qualified_functions)
+#endif  // __has_feature(cxx_reference_qualified_functions) || _GNUC_VER >= 409
 
 #else  // _LIBCPP_HAS_NO_VARIADICS
 
@@ -2228,7 +2255,7 @@
 
 template <class _MP, class _Tp>
 struct __result_of_mp<_MP, _Tp, true>
-    : public common_type<typename __member_pointer_traits<_MP>::_ReturnType>
+    : public __identity<typename __member_pointer_traits<_MP>::_ReturnType>
 {
 };
 
@@ -2296,7 +2323,7 @@
 class _LIBCPP_TYPE_VIS_ONLY result_of<_Fn()>
     : public __result_of<_Fn(),
                          is_class<typename remove_reference<_Fn>::type>::value ||
-                         is_function<typename remove_reference<_Fn>::type>::value,
+                         is_function<typename remove_pointer<typename remove_reference<_Fn>::type>::type>::value,
                          is_member_pointer<typename remove_reference<_Fn>::type>::value
                         >
 {
@@ -2306,7 +2333,7 @@
 class _LIBCPP_TYPE_VIS_ONLY result_of<_Fn(_A0)>
     : public __result_of<_Fn(_A0),
                          is_class<typename remove_reference<_Fn>::type>::value ||
-                         is_function<typename remove_reference<_Fn>::type>::value,
+                         is_function<typename remove_pointer<typename remove_reference<_Fn>::type>::type>::value,
                          is_member_pointer<typename remove_reference<_Fn>::type>::value
                         >
 {
@@ -2316,7 +2343,7 @@
 class _LIBCPP_TYPE_VIS_ONLY result_of<_Fn(_A0, _A1)>
     : public __result_of<_Fn(_A0, _A1),
                          is_class<typename remove_reference<_Fn>::type>::value ||
-                         is_function<typename remove_reference<_Fn>::type>::value,
+                         is_function<typename remove_pointer<typename remove_reference<_Fn>::type>::type>::value,
                          is_member_pointer<typename remove_reference<_Fn>::type>::value
                         >
 {
@@ -2326,7 +2353,7 @@
 class _LIBCPP_TYPE_VIS_ONLY result_of<_Fn(_A0, _A1, _A2)>
     : public __result_of<_Fn(_A0, _A1, _A2),
                          is_class<typename remove_reference<_Fn>::type>::value ||
-                         is_function<typename remove_reference<_Fn>::type>::value,
+                         is_function<typename remove_pointer<typename remove_reference<_Fn>::type>::type>::value,
                          is_member_pointer<typename remove_reference<_Fn>::type>::value
                         >
 {
@@ -2674,7 +2701,7 @@
 
 #ifndef _LIBCPP_HAS_NO_VARIADICS
 
-#if __has_feature(is_trivially_constructible)
+#if __has_feature(is_trivially_constructible) || _GNUC_VER >= 501
 
 template <class _Tp, class... _Args>
 struct _LIBCPP_TYPE_VIS_ONLY is_trivially_constructible
@@ -2733,7 +2760,7 @@
 {
 };
 
-#if __has_feature(is_trivially_constructible)
+#if __has_feature(is_trivially_constructible) || _GNUC_VER >= 501
 
 template <class _Tp>
 struct _LIBCPP_TYPE_VIS_ONLY is_trivially_constructible<_Tp, __is_construct::__nat,
@@ -2821,7 +2848,7 @@
 
 // is_trivially_assignable
 
-#if __has_feature(is_trivially_assignable)
+#if __has_feature(is_trivially_assignable) || _GNUC_VER >= 501
 
 template <class _Tp, class _Arg>
 struct is_trivially_assignable
@@ -2890,6 +2917,9 @@
 template <class _Tp> struct _LIBCPP_TYPE_VIS_ONLY is_trivially_destructible
     : public __libcpp_trivial_destructor<typename remove_all_extents<_Tp>::type> {};
 
+template <class _Tp> struct _LIBCPP_TYPE_VIS_ONLY is_trivially_destructible<_Tp[]>
+    : public false_type {};
+
 #endif
 
 // is_nothrow_constructible
@@ -3214,6 +3244,10 @@
 template <class _Tp> struct _LIBCPP_TYPE_VIS_ONLY is_nothrow_destructible
     : public __libcpp_nothrow_destructor<typename remove_all_extents<_Tp>::type> {};
 
+template <class _Tp>
+struct _LIBCPP_TYPE_VIS_ONLY is_nothrow_destructible<_Tp[]>
+    : public false_type {};
+
 #endif
 
 // is_pod
@@ -3259,6 +3293,8 @@
 template <class _Tp> struct _LIBCPP_TYPE_VIS_ONLY is_trivially_copyable
 #if __has_feature(is_trivially_copyable)
     : public integral_constant<bool, __is_trivially_copyable(_Tp)>
+#elif _GNUC_VER >= 501
+    : public integral_constant<bool, !is_volatile<_Tp>::value && __is_trivially_copyable(_Tp)>
 #else
     : integral_constant<bool, is_scalar<typename remove_all_extents<_Tp>::type>::value>
 #endif
@@ -3267,7 +3303,7 @@
 // is_trivial;
 
 template <class _Tp> struct _LIBCPP_TYPE_VIS_ONLY is_trivial
-#if __has_feature(is_trivial) || (_GNUC_VER >= 407)
+#if __has_feature(is_trivial) || _GNUC_VER >= 407
     : public integral_constant<bool, __is_trivial(_Tp)>
 #else
     : integral_constant<bool, is_trivially_copyable<_Tp>::value &&
diff --git a/include/unordered_map b/include/unordered_map
index 0fa87d1..cf70ab6 100644
--- a/include/unordered_map
+++ b/include/unordered_map
@@ -122,7 +122,25 @@
         void insert(InputIterator first, InputIterator last);
     void insert(initializer_list<value_type>);
 
+    template <class... Args>
+        pair<iterator, bool> try_emplace(const key_type& k, Args&&... args);          // C++17
+    template <class... Args>
+        pair<iterator, bool> try_emplace(key_type&& k, Args&&... args);               // C++17
+    template <class... Args>
+        iterator try_emplace(const_iterator hint, const key_type& k, Args&&... args); // C++17
+    template <class... Args>
+        iterator try_emplace(const_iterator hint, key_type&& k, Args&&... args);      // C++17
+    template <class M>
+        pair<iterator, bool> insert_or_assign(const key_type& k, M&& obj);            // C++17
+    template <class M>
+        pair<iterator, bool> insert_or_assign(key_type&& k, M&& obj);                 // C++17
+    template <class M>
+        iterator insert_or_assign(const_iterator hint, const key_type& k, M&& obj);   // C++17
+    template <class M>
+        iterator insert_or_assign(const_iterator hint, key_type&& k, M&& obj);        // C++17
+
     iterator erase(const_iterator position);
+    iterator erase(iterator position);  // C++14
     size_type erase(const key_type& k);
     iterator erase(const_iterator first, const_iterator last);
     void clear() noexcept;
@@ -287,6 +305,7 @@
     void insert(initializer_list<value_type>);
 
     iterator erase(const_iterator position);
+    iterator erase(iterator position);  // C++14
     size_type erase(const key_type& k);
     iterator erase(const_iterator first, const_iterator last);
     void clear() noexcept;
@@ -359,10 +378,8 @@
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
-template <class _Key, class _Cp, class _Hash, bool = is_empty<_Hash>::value
-#if __has_feature(is_final)
-                                         && !__is_final(_Hash)
-#endif
+template <class _Key, class _Cp, class _Hash,
+          bool = is_empty<_Hash>::value && !__libcpp_is_final<_Hash>::value
          >
 class __unordered_map_hasher
     : private _Hash
@@ -384,6 +401,12 @@
     _LIBCPP_INLINE_VISIBILITY
     size_t operator()(const _Key& __x) const
         {return static_cast<const _Hash&>(*this)(__x);}
+    void swap(__unordered_map_hasher&__y)
+        _NOEXCEPT_(__is_nothrow_swappable<_Hash>::value)
+    {
+        using _VSTD::swap;
+        swap(static_cast<const _Hash&>(*this), static_cast<const _Hash&>(__y));
+    }
 };
 
 template <class _Key, class _Cp, class _Hash>
@@ -408,12 +431,26 @@
     _LIBCPP_INLINE_VISIBILITY
     size_t operator()(const _Key& __x) const
         {return __hash_(__x);}
+    void swap(__unordered_map_hasher&__y)
+        _NOEXCEPT_(__is_nothrow_swappable<_Hash>::value)
+    {
+        using _VSTD::swap;
+        swap(__hash_, __y.__hash_);
+    }
 };
 
-template <class _Key, class _Cp, class _Pred, bool = is_empty<_Pred>::value
-#if __has_feature(is_final)
-                                         && !__is_final(_Pred)
-#endif
+template <class _Key, class _Cp, class _Hash, bool __b>
+inline _LIBCPP_INLINE_VISIBILITY
+void
+swap(__unordered_map_hasher<_Key, _Cp, _Hash, __b>& __x,
+     __unordered_map_hasher<_Key, _Cp, _Hash, __b>& __y)
+    _NOEXCEPT_(_NOEXCEPT_(__x.swap(__y)))
+{
+    __x.swap(__y);
+}
+
+template <class _Key, class _Cp, class _Pred,
+          bool = is_empty<_Pred>::value && !__libcpp_is_final<_Pred>::value
          >
 class __unordered_map_equal
     : private _Pred
@@ -438,6 +475,12 @@
     _LIBCPP_INLINE_VISIBILITY
     bool operator()(const _Key& __x, const _Cp& __y) const
         {return static_cast<const _Pred&>(*this)(__x, __y.__cc.first);}
+    void swap(__unordered_map_equal&__y)
+        _NOEXCEPT_(__is_nothrow_swappable<_Pred>::value)
+    {
+        using _VSTD::swap;
+        swap(static_cast<const _Pred&>(*this), static_cast<const _Pred&>(__y));
+    }
 };
 
 template <class _Key, class _Cp, class _Pred>
@@ -465,8 +508,24 @@
     _LIBCPP_INLINE_VISIBILITY
     bool operator()(const _Key& __x, const _Cp& __y) const
         {return __pred_(__x, __y.__cc.first);}
+    void swap(__unordered_map_equal&__y)
+        _NOEXCEPT_(__is_nothrow_swappable<_Pred>::value)
+    {
+        using _VSTD::swap;
+        swap(__pred_, __y.__pred_);
+    }
 };
 
+template <class _Key, class _Cp, class _Pred, bool __b>
+inline _LIBCPP_INLINE_VISIBILITY
+void
+swap(__unordered_map_equal<_Key, _Cp, _Pred, __b>& __x,
+     __unordered_map_equal<_Key, _Cp, _Pred, __b>& __y)
+    _NOEXCEPT_(_NOEXCEPT_(__x.swap(__y)))
+{
+    __x.swap(__y);
+}
+
 template <class _Alloc>
 class __hash_map_node_destructor
 {
@@ -551,7 +610,7 @@
 
     _LIBCPP_INLINE_VISIBILITY
     __hash_value_type(__hash_value_type&& __v)
-        : __nc(std::move(__v.__nc)) {}
+        : __nc(_VSTD::move(__v.__nc)) {}
 
     _LIBCPP_INLINE_VISIBILITY
     __hash_value_type& operator=(const __hash_value_type& __v)
@@ -559,7 +618,7 @@
 
     _LIBCPP_INLINE_VISIBILITY
     __hash_value_type& operator=(__hash_value_type&& __v)
-        {__nc = std::move(__v.__nc); return *this;}
+        {__nc = _VSTD::move(__v.__nc); return *this;}
 
     _LIBCPP_INLINE_VISIBILITY
     ~__hash_value_type() {__cc.~value_type();}
@@ -730,13 +789,8 @@
     typedef __hash_value_type<key_type, mapped_type>                 __value_type;
     typedef __unordered_map_hasher<key_type, __value_type, hasher>   __hasher;
     typedef __unordered_map_equal<key_type, __value_type, key_equal> __key_equal;
-    typedef typename allocator_traits<allocator_type>::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-            rebind_alloc<__value_type>
-#else
-            rebind_alloc<__value_type>::other
-#endif
-                                                           __allocator_type;
+    typedef typename __rebind_alloc_helper<allocator_traits<allocator_type>,
+                                                 __value_type>::type __allocator_type;
 
     typedef __hash_table<__value_type, __hasher,
                          __key_equal,  __allocator_type>   __table;
@@ -946,9 +1000,125 @@
         {insert(__il.begin(), __il.end());}
 #endif  // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
 
+#if _LIBCPP_STD_VER > 14
+#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#ifndef _LIBCPP_HAS_NO_VARIADICS
+    template <class... _Args>
+        _LIBCPP_INLINE_VISIBILITY
+        pair<iterator, bool> try_emplace(const key_type& __k, _Args&&... __args)
+    {
+        iterator __p = __table_.find(__k);
+        if ( __p != end())
+            return _VSTD::make_pair(__p, false);
+        else
+            return _VSTD::make_pair(
+                      emplace_hint(__p, 
+                        _VSTD::piecewise_construct, _VSTD::forward_as_tuple(__k), 
+                        _VSTD::forward_as_tuple(_VSTD::forward<_Args>(__args)...)),
+                      true);
+    }
+
+    template <class... _Args>
+        _LIBCPP_INLINE_VISIBILITY
+        pair<iterator, bool> try_emplace(key_type&& __k, _Args&&... __args)
+    {
+        iterator __p = __table_.find(__k);
+        if ( __p != end())
+            return _VSTD::make_pair(__p, false);
+        else
+            return _VSTD::make_pair(
+                      emplace_hint(__p, 
+                        _VSTD::piecewise_construct, _VSTD::forward_as_tuple(_VSTD::move(__k)), 
+                        _VSTD::forward_as_tuple(_VSTD::forward<_Args>(__args)...)),
+                      true);
+    }
+
+    template <class... _Args>
+        _LIBCPP_INLINE_VISIBILITY
+        iterator try_emplace(const_iterator __h, const key_type& __k, _Args&&... __args)
+    {
+        iterator __p = __table_.find(__k);
+        if ( __p != end())
+            return __p;
+        else
+            return emplace_hint(__h, 
+                      _VSTD::piecewise_construct, _VSTD::forward_as_tuple(__k), 
+                      _VSTD::forward_as_tuple(_VSTD::forward<_Args>(__args)...));
+    }
+
+    template <class... _Args>
+        _LIBCPP_INLINE_VISIBILITY
+        iterator try_emplace(const_iterator __h, key_type&& __k, _Args&&... __args)
+    {
+        iterator __p = __table_.find(__k);
+        if ( __p != end())
+            return __p;
+        else
+            return emplace_hint(__h, 
+                      _VSTD::piecewise_construct, _VSTD::forward_as_tuple(_VSTD::move(__k)), 
+                      _VSTD::forward_as_tuple(_VSTD::forward<_Args>(__args)...));
+    }
+
+    template <class _Vp>
+        _LIBCPP_INLINE_VISIBILITY
+        pair<iterator, bool> insert_or_assign(const key_type& __k, _Vp&& __v)
+    {
+        iterator __p = __table_.find(__k);
+        if ( __p != end())
+        {
+            __p->second = _VSTD::move(__v);
+            return _VSTD::make_pair(__p, false);
+        }
+        return _VSTD::make_pair(emplace_hint(__p, __k, _VSTD::forward<_Vp>(__v)), true);
+    }
+        
+    template <class _Vp>
+        _LIBCPP_INLINE_VISIBILITY
+        pair<iterator, bool> insert_or_assign(key_type&& __k, _Vp&& __v)
+    {
+        iterator __p = __table_.find(__k);
+        if ( __p != end())
+        {
+            __p->second = _VSTD::move(__v);
+            return _VSTD::make_pair(__p, false);
+        }
+        return _VSTD::make_pair(emplace_hint(__p, _VSTD::forward<key_type>(__k), _VSTD::forward<_Vp>(__v)), true);
+    }
+
+    template <class _Vp>
+        _LIBCPP_INLINE_VISIBILITY
+        iterator insert_or_assign(const_iterator __h, const key_type& __k, _Vp&& __v)
+     {
+        iterator __p = __table_.find(__k);
+        if ( __p != end())
+        {
+            __p->second = _VSTD::move(__v);
+            return __p;
+        }
+        return emplace_hint(__h, __k, _VSTD::forward<_Vp>(__v));
+     }
+
+    template <class _Vp>
+        _LIBCPP_INLINE_VISIBILITY
+        iterator insert_or_assign(const_iterator __h, key_type&& __k, _Vp&& __v)
+     {
+        iterator __p = __table_.find(__k);
+        if ( __p != end())
+        {
+            __p->second = _VSTD::move(__v);
+            return __p;
+        }
+        return emplace_hint(__h, _VSTD::forward<key_type>(__k), _VSTD::forward<_Vp>(__v));
+     }
+#endif
+#endif
+#endif
+
     _LIBCPP_INLINE_VISIBILITY
     iterator erase(const_iterator __p) {return __table_.erase(__p.__i_);}
     _LIBCPP_INLINE_VISIBILITY
+    iterator erase(iterator __p)       {return __table_.erase(__p.__i_);}
+    _LIBCPP_INLINE_VISIBILITY
     size_type erase(const key_type& __k) {return __table_.__erase_unique(__k);}
     _LIBCPP_INLINE_VISIBILITY
     iterator erase(const_iterator __first, const_iterator __last)
@@ -1469,13 +1639,8 @@
     typedef __hash_value_type<key_type, mapped_type>                 __value_type;
     typedef __unordered_map_hasher<key_type, __value_type, hasher>   __hasher;
     typedef __unordered_map_equal<key_type, __value_type, key_equal> __key_equal;
-    typedef typename allocator_traits<allocator_type>::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-            rebind_alloc<__value_type>
-#else
-            rebind_alloc<__value_type>::other
-#endif
-                                                           __allocator_type;
+    typedef typename __rebind_alloc_helper<allocator_traits<allocator_type>,
+                                                 __value_type>::type __allocator_type;
 
     typedef __hash_table<__value_type, __hasher,
                          __key_equal,  __allocator_type>   __table;
@@ -1654,6 +1819,8 @@
     _LIBCPP_INLINE_VISIBILITY
     iterator erase(const_iterator __p) {return __table_.erase(__p.__i_);}
     _LIBCPP_INLINE_VISIBILITY
+    iterator erase(iterator __p)       {return __table_.erase(__p.__i_);}
+    _LIBCPP_INLINE_VISIBILITY
     size_type erase(const key_type& __k) {return __table_.__erase_multi(__k);}
     _LIBCPP_INLINE_VISIBILITY
     iterator erase(const_iterator __first, const_iterator __last)
diff --git a/include/unordered_set b/include/unordered_set
index d06629f..f6ccdc3 100644
--- a/include/unordered_set
+++ b/include/unordered_set
@@ -114,16 +114,15 @@
     void insert(initializer_list<value_type>);
 
     iterator erase(const_iterator position);
+    iterator erase(iterator position);  // C++14
     size_type erase(const key_type& k);
     iterator erase(const_iterator first, const_iterator last);
     void clear() noexcept;
 
     void swap(unordered_set&)
-        noexcept(
-            (!allocator_type::propagate_on_container_swap::value ||
-             __is_nothrow_swappable<allocator_type>::value) &&
-            __is_nothrow_swappable<hasher>::value &&
-            __is_nothrow_swappable<key_equal>::value);
+       noexcept(allocator_traits<Allocator>::is_always_equal::value &&
+                 noexcept(swap(declval<hasher&>(), declval<hasher&>())) &&
+                 noexcept(swap(declval<key_equal&>(), declval<key_equal&>()))); // C++17
 
     hasher hash_function() const;
     key_equal key_eq() const;
@@ -263,16 +262,15 @@
     void insert(initializer_list<value_type>);
 
     iterator erase(const_iterator position);
+    iterator erase(iterator position);  // C++14
     size_type erase(const key_type& k);
     iterator erase(const_iterator first, const_iterator last);
     void clear() noexcept;
 
     void swap(unordered_multiset&)
-        noexcept(
-            (!allocator_type::propagate_on_container_swap::value ||
-             __is_nothrow_swappable<allocator_type>::value) &&
-            __is_nothrow_swappable<hasher>::value &&
-            __is_nothrow_swappable<key_equal>::value);
+       noexcept(allocator_traits<Allocator>::is_always_equal::value &&
+                 noexcept(swap(declval<hasher&>(), declval<hasher&>())) &&
+                 noexcept(swap(declval<key_equal&>(), declval<key_equal&>()))); // C++17
 
     hasher hash_function() const;
     key_equal key_eq() const;
diff --git a/include/utility b/include/utility
index 96db60a..54cfc8b 100644
--- a/include/utility
+++ b/include/utility
@@ -513,10 +513,6 @@
     : public integral_constant<size_t, 2> {};
 
 template <class _T1, class _T2>
-  class _LIBCPP_TYPE_VIS_ONLY tuple_size<const pair<_T1, _T2> >
-    : public integral_constant<size_t, 2> {};
-
-template <class _T1, class _T2>
 class _LIBCPP_TYPE_VIS_ONLY tuple_element<0, pair<_T1, _T2> >
 {
 public:
@@ -530,20 +526,6 @@
     typedef _T2 type;
 };
 
-template <class _T1, class _T2>
-class _LIBCPP_TYPE_VIS_ONLY tuple_element<0, const pair<_T1, _T2> >
-{
-public:
-    typedef const _T1 type;
-};
-
-template <class _T1, class _T2>
-class _LIBCPP_TYPE_VIS_ONLY tuple_element<1, const pair<_T1, _T2> >
-{
-public:
-    typedef const _T2 type;
-};
-
 template <size_t _Ip> struct __get_pair;
 
 template <>
diff --git a/include/vector b/include/vector
index 22a6343..049d3c8 100644
--- a/include/vector
+++ b/include/vector
@@ -119,8 +119,8 @@
     void resize(size_type sz, const value_type& c);
 
     void swap(vector&)
-        noexcept(!allocator_type::propagate_on_container_swap::value ||
-                 __is_nothrow_swappable<allocator_type>::value);
+        noexcept(allocator_traits<allocator_type>::propagate_on_container_swap::value ||
+                 allocator_traits<allocator_type>::is_always_equal::value);  // C++17
 
     bool __invariants() const;
 };
@@ -237,8 +237,8 @@
     void resize(size_type sz, value_type x);
 
     void swap(vector&)
-        noexcept(!allocator_type::propagate_on_container_swap::value ||
-                 __is_nothrow_swappable<allocator_type>::value);
+        noexcept(allocator_traits<allocator_type>::propagate_on_container_swap::value ||
+                 allocator_traits<allocator_type>::is_always_equal::value);  // C++17
     void flip() noexcept;
 
     bool __invariants() const;
@@ -385,14 +385,6 @@
             is_nothrow_move_assignable<allocator_type>::value)
         {__move_assign_alloc(__c, integral_constant<bool,
                       __alloc_traits::propagate_on_container_move_assignment::value>());}
-
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(allocator_type& __x, allocator_type& __y)
-        _NOEXCEPT_(
-            !__alloc_traits::propagate_on_container_swap::value ||
-            __is_nothrow_swappable<allocator_type>::value)
-        {__swap_alloc(__x, __y, integral_constant<bool,
-                      __alloc_traits::propagate_on_container_swap::value>());}
 private:
     _LIBCPP_INLINE_VISIBILITY
     void __copy_assign_alloc(const __vector_base& __c, true_type)
@@ -421,18 +413,6 @@
     void __move_assign_alloc(__vector_base&, false_type)
         _NOEXCEPT
         {}
-
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(allocator_type& __x, allocator_type& __y, true_type)
-        _NOEXCEPT_(is_nothrow_move_assignable<allocator_type>::value)
-        {
-            using _VSTD::swap;
-            swap(__x, __y);
-        }
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(allocator_type&, allocator_type&, false_type)
-        _NOEXCEPT
-        {}
 };
 
 template <class _Tp, class _Allocator>
@@ -500,14 +480,18 @@
                   "Allocator::value_type must be same type as value_type");
 
     _LIBCPP_INLINE_VISIBILITY
-    vector()
-        _NOEXCEPT_(is_nothrow_default_constructible<allocator_type>::value)
+    vector() _NOEXCEPT_(is_nothrow_default_constructible<allocator_type>::value)
         {
 #if _LIBCPP_DEBUG_LEVEL >= 2
             __get_db()->__insert_c(this);
 #endif
         }
     _LIBCPP_INLINE_VISIBILITY explicit vector(const allocator_type& __a)
+#if _LIBCPP_STD_VER <= 14
+        _NOEXCEPT_(is_nothrow_copy_constructible<allocator_type>::value)
+#else
+        _NOEXCEPT
+#endif
         : __base(__a)
     {
 #if _LIBCPP_DEBUG_LEVEL >= 2
@@ -569,7 +553,11 @@
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     _LIBCPP_INLINE_VISIBILITY
     vector(vector&& __x)
+#if _LIBCPP_STD_VER > 14
+        _NOEXCEPT;
+#else
         _NOEXCEPT_(is_nothrow_move_constructible<allocator_type>::value);
+#endif
     _LIBCPP_INLINE_VISIBILITY
     vector(vector&& __x, const allocator_type& __a);
     _LIBCPP_INLINE_VISIBILITY
@@ -756,8 +744,12 @@
     void resize(size_type __sz, const_reference __x);
 
     void swap(vector&)
-        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<allocator_type>::value);
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT;
+#else
+        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 
+                    __is_nothrow_swappable<allocator_type>::value);
+#endif
 
     bool __invariants() const;
 
@@ -783,7 +775,7 @@
             __is_forward_iterator<_ForwardIterator>::value,
             void
         >::type
-        __construct_at_end(_ForwardIterator __first, _ForwardIterator __last);
+        __construct_at_end(_ForwardIterator __first, _ForwardIterator __last, size_type __n);
     void __append(size_type __n);
     void __append(size_type __n, const_reference __x);
     _LIBCPP_INLINE_VISIBILITY
@@ -868,17 +860,17 @@
     // but if an exception is thrown after that the annotation has to be undone.
     struct __RAII_IncreaseAnnotator {
       __RAII_IncreaseAnnotator(const vector &__v, size_type __n = 1)
-        : __commit(false), __v(__v), __n(__n) {
+        : __commit(false), __v(__v), __old_size(__v.size() + __n) {
         __v.__annotate_increase(__n);
       }
       void __done() { __commit = true; }
       ~__RAII_IncreaseAnnotator() {
         if (__commit) return;
-        __v.__annotate_shrink(__v.size() + __n);
+        __v.__annotate_shrink(__old_size);
       }
       bool __commit;
-      size_type __n;
       const vector &__v;
+      size_type __old_size;
     };
 #else
     struct __RAII_IncreaseAnnotator {
@@ -1021,16 +1013,12 @@
     __is_forward_iterator<_ForwardIterator>::value,
     void
 >::type
-vector<_Tp, _Allocator>::__construct_at_end(_ForwardIterator __first, _ForwardIterator __last)
+vector<_Tp, _Allocator>::__construct_at_end(_ForwardIterator __first, _ForwardIterator __last, size_type __n)
 {
     allocator_type& __a = this->__alloc();
-    for (; __first != __last; ++__first)
-    {
-        __RAII_IncreaseAnnotator __annotator(*this);
-        __alloc_traits::construct(__a, _VSTD::__to_raw_pointer(this->__end_), *__first);
-        __annotator.__done();
-        ++this->__end_;
-    }
+    __RAII_IncreaseAnnotator __annotator(*this, __n);
+    __alloc_traits::__construct_range_forward(__a, __first, __last, this->__end_);
+    __annotator.__done();
 }
 
 //  Default constructs __n objects starting at __end_
@@ -1177,7 +1165,7 @@
     if (__n > 0)
     {
         allocate(__n);
-        __construct_at_end(__first, __last);
+        __construct_at_end(__first, __last, __n);
     }
 }
 
@@ -1197,7 +1185,7 @@
     if (__n > 0)
     {
         allocate(__n);
-        __construct_at_end(__first, __last);
+        __construct_at_end(__first, __last, __n);
     }
 }
 
@@ -1212,7 +1200,7 @@
     if (__n > 0)
     {
         allocate(__n);
-        __construct_at_end(__x.__begin_, __x.__end_);
+        __construct_at_end(__x.__begin_, __x.__end_, __n);
     }
 }
 
@@ -1227,7 +1215,7 @@
     if (__n > 0)
     {
         allocate(__n);
-        __construct_at_end(__x.__begin_, __x.__end_);
+        __construct_at_end(__x.__begin_, __x.__end_, __n);
     }
 }
 
@@ -1236,7 +1224,11 @@
 template <class _Tp, class _Allocator>
 inline _LIBCPP_INLINE_VISIBILITY
 vector<_Tp, _Allocator>::vector(vector&& __x)
+#if _LIBCPP_STD_VER > 14
+        _NOEXCEPT
+#else
         _NOEXCEPT_(is_nothrow_move_constructible<allocator_type>::value)
+#endif
     : __base(_VSTD::move(__x.__alloc()))
 {
 #if _LIBCPP_DEBUG_LEVEL >= 2
@@ -1286,7 +1278,7 @@
     if (__il.size() > 0)
     {
         allocate(__il.size());
-        __construct_at_end(__il.begin(), __il.end());
+        __construct_at_end(__il.begin(), __il.end(), __il.size());
     }
 }
 
@@ -1301,7 +1293,7 @@
     if (__il.size() > 0)
     {
         allocate(__il.size());
-        __construct_at_end(__il.begin(), __il.end());
+        __construct_at_end(__il.begin(), __il.end(), __il.size());
     }
 }
 
@@ -1394,12 +1386,12 @@
 >::type
 vector<_Tp, _Allocator>::assign(_ForwardIterator __first, _ForwardIterator __last)
 {
-    typename iterator_traits<_ForwardIterator>::difference_type __new_size = _VSTD::distance(__first, __last);
-    if (static_cast<size_type>(__new_size) <= capacity())
+    size_type __new_size = static_cast<size_type>(_VSTD::distance(__first, __last));
+    if (__new_size <= capacity())
     {
         _ForwardIterator __mid = __last;
         bool __growing = false;
-        if (static_cast<size_type>(__new_size) > size())
+        if (__new_size > size())
         {
             __growing = true;
             __mid =  __first;
@@ -1407,15 +1399,15 @@
         }
         pointer __m = _VSTD::copy(__first, __mid, this->__begin_);
         if (__growing)
-            __construct_at_end(__mid, __last);
+            __construct_at_end(__mid, __last, __new_size - size());
         else
             this->__destruct_at_end(__m);
     }
     else
     {
         deallocate();
-        allocate(__recommend(static_cast<size_type>(__new_size)));
-        __construct_at_end(__first, __last);
+        allocate(__recommend(__new_size));
+        __construct_at_end(__first, __last, __new_size);
     }
 }
 
@@ -1905,9 +1897,11 @@
     pointer __old_last = this->__end_;
     for (; this->__end_ != this->__end_cap() && __first != __last; ++__first)
     {
+        __RAII_IncreaseAnnotator __annotator(*this);
         __alloc_traits::construct(__a, _VSTD::__to_raw_pointer(this->__end_),
                                   *__first);
         ++this->__end_;
+        __annotator.__done();
     }
     __split_buffer<value_type, allocator_type&> __v(__a);
     if (__first != __last)
@@ -1967,8 +1961,9 @@
             if (__n > __dx)
             {
                 __m = __first;
-                _VSTD::advance(__m, this->__end_ - __p);
-                __construct_at_end(__m, __last);
+                difference_type __diff = this->__end_ - __p;
+                _VSTD::advance(__m, __diff);
+                __construct_at_end(__m, __last, __n - __diff);
                 __n = __dx;
             }
             if (__n > 0)
@@ -2015,8 +2010,12 @@
 template <class _Tp, class _Allocator>
 void
 vector<_Tp, _Allocator>::swap(vector& __x)
-        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<allocator_type>::value)
+#if _LIBCPP_STD_VER >= 14
+    _NOEXCEPT
+#else
+    _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 
+                __is_nothrow_swappable<allocator_type>::value)
+#endif
 {
     _LIBCPP_ASSERT(__alloc_traits::propagate_on_container_swap::value ||
                    this->__alloc() == __x.__alloc(),
@@ -2025,7 +2024,8 @@
     _VSTD::swap(this->__begin_, __x.__begin_);
     _VSTD::swap(this->__end_, __x.__end_);
     _VSTD::swap(this->__end_cap(), __x.__end_cap());
-    __base::__swap_alloc(this->__alloc(), __x.__alloc());
+    __swap_allocator(this->__alloc(), __x.__alloc(), 
+        integral_constant<bool,__alloc_traits::propagate_on_container_swap::value>());
 #if _LIBCPP_DEBUG_LEVEL >= 2
     __get_db()->swap(this, &__x);
 #endif  // _LIBCPP_DEBUG_LEVEL >= 2
@@ -2128,13 +2128,7 @@
     typedef _VSTD::reverse_iterator<const_iterator>   const_reverse_iterator;
 
 private:
-    typedef typename __alloc_traits::template
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-                rebind_alloc<__storage_type>
-#else
-                rebind_alloc<__storage_type>::other
-#endif
-                                                     __storage_allocator;
+    typedef typename __rebind_alloc_helper<__alloc_traits, __storage_type>::type __storage_allocator;
     typedef allocator_traits<__storage_allocator>    __storage_traits;
     typedef typename __storage_traits::pointer       __storage_pointer;
     typedef typename __storage_traits::const_pointer __const_storage_pointer;
@@ -2170,9 +2164,14 @@
 
 public:
     _LIBCPP_INLINE_VISIBILITY
-    vector()
-        _NOEXCEPT_(is_nothrow_default_constructible<allocator_type>::value);
-    _LIBCPP_INLINE_VISIBILITY explicit vector(const allocator_type& __a);
+    vector() _NOEXCEPT_(is_nothrow_default_constructible<allocator_type>::value);
+
+    _LIBCPP_INLINE_VISIBILITY explicit vector(const allocator_type& __a)
+#if _LIBCPP_STD_VER <= 14
+        _NOEXCEPT_(is_nothrow_copy_constructible<allocator_type>::value);
+#else
+        _NOEXCEPT;
+#endif
     ~vector();
     explicit vector(size_type __n);
 #if _LIBCPP_STD_VER > 11
@@ -2206,7 +2205,11 @@
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     _LIBCPP_INLINE_VISIBILITY
     vector(vector&& __v)
+#if _LIBCPP_STD_VER > 14
+        _NOEXCEPT;
+#else
         _NOEXCEPT_(is_nothrow_move_constructible<allocator_type>::value);
+#endif
     vector(vector&& __v, const allocator_type& __a);
     _LIBCPP_INLINE_VISIBILITY
     vector& operator=(vector&& __v)
@@ -2354,8 +2357,12 @@
     void clear() _NOEXCEPT {__size_ = 0;}
 
     void swap(vector&)
-        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<allocator_type>::value);
+#if _LIBCPP_STD_VER >= 14
+        _NOEXCEPT;
+#else
+        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 
+                    __is_nothrow_swappable<allocator_type>::value);
+#endif
 
     void resize(size_type __sz, value_type __x = false);
     void flip() _NOEXCEPT;
@@ -2433,26 +2440,6 @@
         _NOEXCEPT
         {}
 
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__storage_allocator& __x, __storage_allocator& __y)
-        _NOEXCEPT_(
-            !__storage_traits::propagate_on_container_swap::value ||
-            __is_nothrow_swappable<allocator_type>::value)
-        {__swap_alloc(__x, __y, integral_constant<bool,
-                      __storage_traits::propagate_on_container_swap::value>());}
-
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__storage_allocator& __x, __storage_allocator& __y, true_type)
-        _NOEXCEPT_(__is_nothrow_swappable<allocator_type>::value)
-        {
-            using _VSTD::swap;
-            swap(__x, __y);
-        }
-    _LIBCPP_INLINE_VISIBILITY
-    static void __swap_alloc(__storage_allocator&, __storage_allocator&, false_type)
-        _NOEXCEPT
-        {}
-
     size_t __hash_code() const _NOEXCEPT;
 
     friend class __bit_reference<vector>;
@@ -2559,7 +2546,7 @@
 template <class _Allocator>
 inline _LIBCPP_INLINE_VISIBILITY
 vector<bool, _Allocator>::vector()
-        _NOEXCEPT_(is_nothrow_default_constructible<allocator_type>::value)
+    _NOEXCEPT_(is_nothrow_default_constructible<allocator_type>::value)
     : __begin_(nullptr),
       __size_(0),
       __cap_alloc_(0)
@@ -2569,6 +2556,11 @@
 template <class _Allocator>
 inline _LIBCPP_INLINE_VISIBILITY
 vector<bool, _Allocator>::vector(const allocator_type& __a)
+#if _LIBCPP_STD_VER <= 14
+        _NOEXCEPT_(is_nothrow_copy_constructible<allocator_type>::value)
+#else
+        _NOEXCEPT
+#endif
     : __begin_(nullptr),
       __size_(0),
       __cap_alloc_(0, static_cast<__storage_allocator>(__a))
@@ -2807,7 +2799,11 @@
 template <class _Allocator>
 inline _LIBCPP_INLINE_VISIBILITY
 vector<bool, _Allocator>::vector(vector&& __v)
+#if _LIBCPP_STD_VER > 14
+        _NOEXCEPT
+#else
         _NOEXCEPT_(is_nothrow_move_constructible<allocator_type>::value)
+#endif
     : __begin_(__v.__begin_),
       __size_(__v.__size_),
       __cap_alloc_(__v.__cap_alloc_)
@@ -3150,13 +3146,18 @@
 template <class _Allocator>
 void
 vector<bool, _Allocator>::swap(vector& __x)
-        _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
-                   __is_nothrow_swappable<allocator_type>::value)
+#if _LIBCPP_STD_VER >= 14
+    _NOEXCEPT
+#else
+    _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 
+                __is_nothrow_swappable<allocator_type>::value)
+#endif
 {
     _VSTD::swap(this->__begin_, __x.__begin_);
     _VSTD::swap(this->__size_, __x.__size_);
     _VSTD::swap(this->__cap(), __x.__cap());
-    __swap_alloc(this->__alloc(), __x.__alloc());
+    __swap_allocator(this->__alloc(), __x.__alloc(), 
+        integral_constant<bool, __alloc_traits::propagate_on_container_swap::value>());
 }
 
 template <class _Allocator>
diff --git a/lib/CMakeLists.txt b/lib/CMakeLists.txt
index d50b2cc..26dee67 100644
--- a/lib/CMakeLists.txt
+++ b/lib/CMakeLists.txt
@@ -1,3 +1,5 @@
+set(LIBCXX_LIB_CMAKEFILES_DIR "${CMAKE_CURRENT_BINARY_DIR}${CMAKE_FILES_DIRECTORY}"  PARENT_SCOPE)
+
 # Get sources
 file(GLOB LIBCXX_SOURCES ../src/*.cpp)
 if(WIN32)
@@ -23,58 +25,70 @@
 endif()
 
 if (LIBCXX_ENABLE_SHARED)
-  add_library(cxx SHARED
-    ${LIBCXX_SOURCES}
-    ${LIBCXX_HEADERS}
-    )
+  add_library(cxx SHARED ${LIBCXX_SOURCES} ${LIBCXX_HEADERS})
 else()
-  add_library(cxx STATIC
-    ${LIBCXX_SOURCES}
-    ${LIBCXX_HEADERS}
-    )
-endif()
-
-#if LIBCXX_CXX_ABI_LIBRARY_PATH is defined we want to add it to the search path.
-if (DEFINED LIBCXX_CXX_ABI_LIBRARY_PATH)
-  target_link_libraries(cxx "-L${LIBCXX_CXX_ABI_LIBRARY_PATH}")
+  add_library(cxx STATIC ${LIBCXX_SOURCES} ${LIBCXX_HEADERS})
 endif()
 
 if (DEFINED LIBCXX_CXX_ABI_DEPS)
   add_dependencies(cxx LIBCXX_CXX_ABI_DEPS)
 endif()
 
-set(libraries "")
-if (LIBCXX_ENABLE_STATIC_ABI_LIBRARY)
-    # TODO(ericwf): Remove these GNU specific linker flags and let CMake do the
-    # configuration. This will be more portable.
-    list(APPEND libraries "-Wl,--whole-archive" "-Wl,-Bstatic")
-    list(APPEND libraries "${LIBCXX_CXX_ABI_LIBRARY}")
-    list(APPEND libraries "-Wl,-Bdynamic" "-Wl,--no-whole-archive")
-else()
-    list(APPEND libraries "${LIBCXX_CXX_ABI_LIBRARY}")
+#if LIBCXX_CXX_ABI_LIBRARY_PATH is defined we want to add it to the search path.
+add_link_flags_if(LIBCXX_CXX_ABI_LIBRARY_PATH "-L${LIBCXX_CXX_ABI_LIBRARY_PATH}")
+
+add_library_flags_if(LIBCXX_COVERAGE_LIBRARY "${LIBCXX_COVERAGE_LIBRARY}")
+
+add_library_flags_if(LIBCXX_ENABLE_STATIC_ABI_LIBRARY "-Wl,--whole-archive" "-Wl,-Bstatic")
+add_library_flags("${LIBCXX_CXX_ABI_LIBRARY}")
+add_library_flags_if(LIBCXX_ENABLE_STATIC_ABI_LIBRARY "-Wl,-Bdynamic" "-Wl,--no-whole-archive")
+
+if (APPLE AND LLVM_USE_SANITIZER)
+  if ("${LLVM_USE_SANITIZER}" STREQUAL "Address")
+    set(LIBFILE "libclang_rt.asan_osx_dynamic.dylib")
+  elseif("${LLVM_USE_SANITIZER}" STREQUAL "Undefined")
+    set(LIBFILE "libclang_rt.ubsan_osx_dynamic.dylib")
+  else()
+    message(WARNING "LLVM_USE_SANITIZER=${LLVM_USE_SANITIZER} is not supported on OS X")
+  endif()
+  if (LIBFILE)
+    execute_process(COMMAND ${CMAKE_CXX_COMPILER} -print-file-name=lib OUTPUT_VARIABLE LIBDIR RESULT_VARIABLE Result)
+    if (NOT ${Result} EQUAL "0")
+      message(FATAL "Failed to find library resource directory")
+    endif()
+    string(STRIP "${LIBDIR}" LIBDIR)
+    set(LIBDIR "${LIBDIR}/darwin/")
+    if (NOT IS_DIRECTORY "${LIBDIR}")
+      message(FATAL_ERROR "Cannot find compiler-rt directory on OS X required for LLVM_USE_SANITIZER")
+    endif()
+    set(LIBCXX_SANITIZER_LIBRARY "${LIBDIR}/${LIBFILE}")
+    set(LIBCXX_SANITIZER_LIBRARY "${LIBCXX_SANITIZER_LIBRARY}" PARENT_SCOPE)
+    message(STATUS "Manually linking compiler-rt library: ${LIBCXX_SANITIZER_LIBRARY}")
+    add_library_flags("${LIBCXX_SANITIZER_LIBRARY}")
+    add_link_flags("-Wl,-rpath,${LIBDIR}")
+  endif()
 endif()
 
 # Generate library list.
-append_if(libraries LIBCXX_HAS_PTHREAD_LIB pthread)
-append_if(libraries LIBCXX_HAS_C_LIB c)
-append_if(libraries LIBCXX_HAS_M_LIB m)
-append_if(libraries LIBCXX_HAS_RT_LIB rt)
-append_if(libraries LIBCXX_HAS_GCC_S_LIB gcc_s)
-
-target_link_libraries(cxx ${libraries})
+add_library_flags_if(LIBCXX_HAS_PTHREAD_LIB pthread)
+add_library_flags_if(LIBCXX_HAS_C_LIB c)
+add_library_flags_if(LIBCXX_HAS_M_LIB m)
+add_library_flags_if(LIBCXX_HAS_RT_LIB rt)
+add_library_flags_if(LIBCXX_HAS_GCC_S_LIB gcc_s)
 
 # Setup flags.
-append_if(LIBCXX_COMPILE_FLAGS LIBCXX_HAS_FPIC_FLAG -fPIC)
-append_if(LIBCXX_LINK_FLAGS LIBCXX_HAS_NODEFAULTLIBS_FLAG -nodefaultlibs)
+add_flags_if_supported(-fPIC)
+add_link_flags_if_supported(-nodefaultlibs)
 
-if ( APPLE )
+if ( APPLE AND (LIBCXX_CXX_ABI_LIBNAME STREQUAL "libcxxabi" OR
+                LIBCXX_CXX_ABI_LIBNAME STREQUAL "none"))
   if (NOT DEFINED LIBCXX_LIBCPPABI_VERSION)
     set(LIBCXX_LIBCPPABI_VERSION "2")
   endif()
 
   if ( CMAKE_OSX_DEPLOYMENT_TARGET STREQUAL "10.6" )
-    list(APPEND LIBCXX_COMPILE_FLAGS "-U__STRICT_ANSI__")
-    list(APPEND LIBCXX_LINK_FLAGS
+    add_definitions(-D__STRICT_ANSI__)
+    add_link_flags(
       "-compatibility_version 1"
       "-current_version 1"
       "-install_name /usr/lib/libc++.1.dylib"
@@ -96,7 +110,7 @@
       set (OSX_RE_EXPORT_LINE "/usr/lib/libc++abi.dylib -Wl,-reexported_symbols_list,${CMAKE_CURRENT_SOURCE_DIR}/libc++abi${LIBCXX_LIBCPPABI_VERSION}.exp")
     endif()
 
-    list(APPEND LIBCXX_LINK_FLAGS
+    add_link_flags(
       "-compatibility_version 1"
       "-install_name /usr/lib/libc++.1.dylib"
       "-Wl,-unexported_symbols_list,${CMAKE_CURRENT_SOURCE_DIR}/libc++unexp.exp"
@@ -106,8 +120,9 @@
   endif()
 endif()
 
-string(REPLACE ";" " " LIBCXX_COMPILE_FLAGS "${LIBCXX_COMPILE_FLAGS}")
-string(REPLACE ";" " " LIBCXX_LINK_FLAGS "${LIBCXX_LINK_FLAGS}")
+target_link_libraries(cxx ${LIBCXX_LIBRARIES})
+split_list(LIBCXX_COMPILE_FLAGS)
+split_list(LIBCXX_LINK_FLAGS)
 
 set_target_properties(cxx
   PROPERTIES
diff --git a/src/algorithm.cpp b/src/algorithm.cpp
index c13d5f2..e548856 100644
--- a/src/algorithm.cpp
+++ b/src/algorithm.cpp
@@ -7,7 +7,6 @@
 //
 //===----------------------------------------------------------------------===//
 
-#define _LIBCPP_EXTERN_TEMPLATE(...) extern template __VA_ARGS__;
 #include "algorithm"
 #include "random"
 #include "mutex"
diff --git a/src/any.cpp b/src/any.cpp
new file mode 100644
index 0000000..8c3e977
--- /dev/null
+++ b/src/any.cpp
@@ -0,0 +1,22 @@
+//===---------------------------- any.cpp ---------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#include "experimental/any"
+
+_LIBCPP_BEGIN_NAMESPACE_LFTS
+
+// TODO(EricWF) Enable or delete these
+//bad_any_cast::bad_any_cast() _NOEXCEPT {}
+//bad_any_cast::~bad_any_cast() _NOEXCEPT {}
+
+const char* bad_any_cast::what() const _NOEXCEPT {
+    return "bad any cast";
+}
+
+_LIBCPP_END_NAMESPACE_LFTS
diff --git a/src/chrono.cpp b/src/chrono.cpp
index 4569411..62149fb 100644
--- a/src/chrono.cpp
+++ b/src/chrono.cpp
@@ -8,14 +8,21 @@
 //===----------------------------------------------------------------------===//
 
 #include "chrono"
-#include <sys/time.h>        //for gettimeofday and timeval
-#ifdef __APPLE__
+#include "cerrno"        // errno
+#include "system_error"  // __throw_system_error
+#include <time.h>        // clock_gettime, CLOCK_MONOTONIC and CLOCK_REALTIME
+
+#if !defined(CLOCK_REALTIME)
+#include <sys/time.h>        // for gettimeofday and timeval
+#endif
+
+#if !defined(_LIBCPP_HAS_NO_MONOTONIC_CLOCK) && !defined(CLOCK_MONOTONIC)
+#if __APPLE__
 #include <mach/mach_time.h>  // mach_absolute_time, mach_timebase_info_data_t
-#else  /* !__APPLE__ */
-#include <cerrno>  // errno
-#include <system_error>  // __throw_system_error
-#include <time.h>  // clock_gettime, CLOCK_MONOTONIC
-#endif  // __APPLE__
+#else
+#error "Monotonic clock not implemented"
+#endif
+#endif
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
@@ -29,9 +36,16 @@
 system_clock::time_point
 system_clock::now() _NOEXCEPT
 {
+#ifdef CLOCK_REALTIME
+    struct timespec tp;
+    if (0 != clock_gettime(CLOCK_REALTIME, &tp))
+        __throw_system_error(errno, "clock_gettime(CLOCK_REALTIME) failed");
+    return time_point(seconds(tp.tv_sec) + microseconds(tp.tv_nsec / 1000));
+#else  // !CLOCK_REALTIME
     timeval tv;
     gettimeofday(&tv, 0);
     return time_point(seconds(tv.tv_sec) + microseconds(tv.tv_usec));
+#endif  // CLOCK_REALTIME
 }
 
 time_t
@@ -48,10 +62,26 @@
 
 #ifndef _LIBCPP_HAS_NO_MONOTONIC_CLOCK
 // steady_clock
+//
+// Warning:  If this is not truly steady, then it is non-conforming.  It is
+//  better for it to not exist and have the rest of libc++ use system_clock
+//  instead.
 
 const bool steady_clock::is_steady;
 
-#ifdef __APPLE__
+#ifdef CLOCK_MONOTONIC
+
+steady_clock::time_point
+steady_clock::now() _NOEXCEPT
+{
+    struct timespec tp;
+    if (0 != clock_gettime(CLOCK_MONOTONIC, &tp))
+        __throw_system_error(errno, "clock_gettime(CLOCK_MONOTONIC) failed");
+    return time_point(seconds(tp.tv_sec) + nanoseconds(tp.tv_nsec));
+}
+
+#elif defined(__APPLE__)
+
 //   mach_absolute_time() * MachInfo.numer / MachInfo.denom is the number of
 //   nanoseconds since the computer booted up.  MachInfo.numer and MachInfo.denom
 //   are run time constants supplied by the OS.  This clock has no relationship
@@ -108,23 +138,9 @@
     return time_point(duration(fp()));
 }
 
-#else  // __APPLE__
-// FIXME: if _LIBCPP_HAS_NO_MONOTONIC_CLOCK, then clock_gettime isn't going to
-// work. It may be possible to fall back on something else, depending on the system.
-
-// Warning:  If this is not truly steady, then it is non-conforming.  It is
-//  better for it to not exist and have the rest of libc++ use system_clock
-//  instead.
-
-steady_clock::time_point
-steady_clock::now() _NOEXCEPT
-{
-    struct timespec tp;
-    if (0 != clock_gettime(CLOCK_MONOTONIC, &tp))
-        __throw_system_error(errno, "clock_gettime(CLOCK_MONOTONIC) failed");
-    return time_point(seconds(tp.tv_sec) + nanoseconds(tp.tv_nsec));
-}
-#endif  // __APPLE__
+#else
+#error "Monotonic clock not implemented"
+#endif
 
 #endif // !_LIBCPP_HAS_NO_MONOTONIC_CLOCK
 
diff --git a/src/debug.cpp b/src/debug.cpp
index 60694a3..b1a16e6 100644
--- a/src/debug.cpp
+++ b/src/debug.cpp
@@ -214,10 +214,10 @@
             else
                 q->__next_ = p->__next_;
             __c_node* c = p->__c_;
-            free(p);
             --__isz_;
             if (c != nullptr)
                 c->__remove(p);
+            free(p);
         }
     }
 }
diff --git a/src/exception.cpp b/src/exception.cpp
index b5c46c0..2c16060 100644
--- a/src/exception.cpp
+++ b/src/exception.cpp
@@ -29,7 +29,7 @@
     #define __terminate_handler  __cxxabiapple::__cxa_terminate_handler
     #define __unexpected_handler __cxxabiapple::__cxa_unexpected_handler
   #endif  // _LIBCPPABI_VERSION
-#elif defined(LIBCXXRT) || __has_include(<cxxabi.h>)
+#elif defined(LIBCXXRT) || defined(LIBCXX_BUILDING_LIBCXXABI) || __has_include(<cxxabi.h>)
   #include <cxxabi.h>
   using namespace __cxxabiv1;
   #if defined(LIBCXXRT) || defined(_LIBCPPABI_VERSION)
@@ -90,14 +90,14 @@
 #endif  // _LIBCPP_NO_EXCEPTIONS
         (*get_terminate())();
         // handler should not return
-        printf("terminate_handler unexpectedly returned\n");
+        fprintf(stderr, "terminate_handler unexpectedly returned\n");
         ::abort();
 #ifndef _LIBCPP_NO_EXCEPTIONS
     }
     catch (...)
     {
         // handler should not throw exception
-        printf("terminate_handler unexpectedly threw an exception\n");
+        fprintf(stderr, "terminate_handler unexpectedly threw an exception\n");
         ::abort();
     }
 #endif  // _LIBCPP_NO_EXCEPTIONS
@@ -106,18 +106,24 @@
 #endif // !defined(LIBCXXRT) && !defined(_LIBCPPABI_VERSION)
 
 #if !defined(LIBCXXRT) && !defined(__GLIBCXX__) && !defined(__EMSCRIPTEN__)
-bool uncaught_exception() _NOEXCEPT
+bool uncaught_exception() _NOEXCEPT { return uncaught_exceptions() > 0; }
+
+int uncaught_exceptions() _NOEXCEPT
 {
 #if defined(__APPLE__) || defined(_LIBCPPABI_VERSION)
-    // on Darwin, there is a helper function so __cxa_get_globals is private
-    return __cxa_uncaught_exception();
+   // on Darwin, there is a helper function so __cxa_get_globals is private
+# if _LIBCPPABI_VERSION > 1101
+    return __cxa_uncaught_exceptions();
+# else
+    return __cxa_uncaught_exception() ? 1 : 0;
+# endif
 #else  // __APPLE__
 #   if defined(_MSC_VER) && ! defined(__clang__)
-        _LIBCPP_WARNING("uncaught_exception not yet implemented")
+        _LIBCPP_WARNING("uncaught_exceptions not yet implemented")
 #   else
 #       warning uncaught_exception not yet implemented
 #   endif
-    printf("uncaught_exception not yet implemented\n");
+    fprintf(stderr, "uncaught_exceptions not yet implemented\n");
     ::abort();
 #endif  // __APPLE__
 }
@@ -190,7 +196,7 @@
 #   else
 #       warning exception_ptr not yet implemented
 #   endif
-    printf("exception_ptr not yet implemented\n");
+    fprintf(stderr, "exception_ptr not yet implemented\n");
     ::abort();
 #endif
 }
@@ -209,7 +215,7 @@
 #   else
 #       warning exception_ptr not yet implemented
 #   endif
-    printf("exception_ptr not yet implemented\n");
+    fprintf(stderr, "exception_ptr not yet implemented\n");
     ::abort();
 #endif
 }
@@ -234,7 +240,7 @@
 #   else
 #       warning exception_ptr not yet implemented
 #   endif
-    printf("exception_ptr not yet implemented\n");
+    fprintf(stderr, "exception_ptr not yet implemented\n");
     ::abort();
 #endif
 }
@@ -278,7 +284,7 @@
 #   else
 #       warning exception_ptr not yet implemented
 #   endif
-    printf("exception_ptr not yet implemented\n");
+    fprintf(stderr, "exception_ptr not yet implemented\n");
     ::abort();
 #endif
 }
@@ -300,7 +306,7 @@
 #   else
 #       warning exception_ptr not yet implemented
 #   endif
-    printf("exception_ptr not yet implemented\n");
+    fprintf(stderr, "exception_ptr not yet implemented\n");
     ::abort();
 #endif
 }
diff --git a/src/future.cpp b/src/future.cpp
index 0c5c2c4..3132b18 100644
--- a/src/future.cpp
+++ b/src/future.cpp
@@ -98,7 +98,6 @@
 #endif
     __state_ |= __constructed | ready;
     __cv_.notify_all();
-    __lk.unlock();
 }
 
 void
@@ -111,7 +110,6 @@
 #endif
     __state_ |= __constructed;
     __thread_local_data()->__make_ready_at_thread_exit(this);
-    __lk.unlock();
 }
 
 void
@@ -124,7 +122,6 @@
 #endif
     __exception_ = __p;
     __state_ |= ready;
-    __lk.unlock();
     __cv_.notify_all();
 }
 
@@ -138,7 +135,6 @@
 #endif
     __exception_ = __p;
     __thread_local_data()->__make_ready_at_thread_exit(this);
-    __lk.unlock();
 }
 
 void
@@ -146,7 +142,6 @@
 {
     unique_lock<mutex> __lk(__mut_);
     __state_ |= ready;
-    __lk.unlock();
     __cv_.notify_all();
 }
 
diff --git a/src/iostream.cpp b/src/iostream.cpp
index 7102e43..e073aec 100644
--- a/src/iostream.cpp
+++ b/src/iostream.cpp
@@ -13,55 +13,75 @@
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
-static mbstate_t state_types[6] = {};
-
-_ALIGNAS_TYPE (__stdinbuf<char> ) static char __cin [sizeof(__stdinbuf <char>)];
-_ALIGNAS_TYPE (__stdoutbuf<char>) static char __cout[sizeof(__stdoutbuf<char>)];
-_ALIGNAS_TYPE (__stdoutbuf<char>) static char __cerr[sizeof(__stdoutbuf<char>)];
-_ALIGNAS_TYPE (__stdinbuf<wchar_t> ) static char __wcin [sizeof(__stdinbuf <wchar_t>)];
-_ALIGNAS_TYPE (__stdoutbuf<wchar_t>) static char __wcout[sizeof(__stdoutbuf<wchar_t>)];
-_ALIGNAS_TYPE (__stdoutbuf<wchar_t>) static char __wcerr[sizeof(__stdoutbuf<wchar_t>)];
-
+#ifndef _LIBCPP_HAS_NO_STDIN
 _ALIGNAS_TYPE (istream)  _LIBCPP_FUNC_VIS char cin [sizeof(istream)];
-_ALIGNAS_TYPE (ostream)  _LIBCPP_FUNC_VIS char cout[sizeof(ostream)];
-_ALIGNAS_TYPE (ostream)  _LIBCPP_FUNC_VIS char cerr[sizeof(ostream)];
-_ALIGNAS_TYPE (ostream)  _LIBCPP_FUNC_VIS char clog[sizeof(ostream)];
+_ALIGNAS_TYPE (__stdinbuf<char> ) static char __cin [sizeof(__stdinbuf <char>)];
+static mbstate_t mb_cin;
 _ALIGNAS_TYPE (wistream) _LIBCPP_FUNC_VIS char wcin [sizeof(wistream)];
+_ALIGNAS_TYPE (__stdinbuf<wchar_t> ) static char __wcin [sizeof(__stdinbuf <wchar_t>)];
+static mbstate_t mb_wcin;
+#endif
+
+#ifndef _LIBCPP_HAS_NO_STDOUT
+_ALIGNAS_TYPE (ostream)  _LIBCPP_FUNC_VIS char cout[sizeof(ostream)];
+_ALIGNAS_TYPE (__stdoutbuf<char>) static char __cout[sizeof(__stdoutbuf<char>)];
+static mbstate_t mb_cout;
 _ALIGNAS_TYPE (wostream) _LIBCPP_FUNC_VIS char wcout[sizeof(wostream)];
+_ALIGNAS_TYPE (__stdoutbuf<wchar_t>) static char __wcout[sizeof(__stdoutbuf<wchar_t>)];
+static mbstate_t mb_wcout;
+#endif
+
+_ALIGNAS_TYPE (ostream)  _LIBCPP_FUNC_VIS char cerr[sizeof(ostream)];
+_ALIGNAS_TYPE (__stdoutbuf<char>) static char __cerr[sizeof(__stdoutbuf<char>)];
+static mbstate_t mb_cerr;
 _ALIGNAS_TYPE (wostream) _LIBCPP_FUNC_VIS char wcerr[sizeof(wostream)];
+_ALIGNAS_TYPE (__stdoutbuf<wchar_t>) static char __wcerr[sizeof(__stdoutbuf<wchar_t>)];
+static mbstate_t mb_wcerr;
+
+_ALIGNAS_TYPE (ostream)  _LIBCPP_FUNC_VIS char clog[sizeof(ostream)];
 _ALIGNAS_TYPE (wostream) _LIBCPP_FUNC_VIS char wclog[sizeof(wostream)];
 
 ios_base::Init __start_std_streams;
 
 ios_base::Init::Init()
 {
-    istream* cin_ptr  = ::new(cin)  istream(::new(__cin)  __stdinbuf <char>(stdin, state_types+0) );
-    ostream* cout_ptr = ::new(cout) ostream(::new(__cout) __stdoutbuf<char>(stdout, state_types+1));
-    ostream* cerr_ptr = ::new(cerr) ostream(::new(__cerr) __stdoutbuf<char>(stderr, state_types+2));
+#ifndef _LIBCPP_HAS_NO_STDIN
+    istream* cin_ptr  = ::new(cin)  istream(::new(__cin)  __stdinbuf <char>(stdin, &mb_cin));
+    wistream* wcin_ptr  = ::new(wcin)  wistream(::new(__wcin)  __stdinbuf <wchar_t>(stdin, &mb_wcin));
+#endif
+#ifndef _LIBCPP_HAS_NO_STDOUT
+    ostream* cout_ptr = ::new(cout) ostream(::new(__cout) __stdoutbuf<char>(stdout, &mb_cout));
+    wostream* wcout_ptr = ::new(wcout) wostream(::new(__wcout) __stdoutbuf<wchar_t>(stdout, &mb_wcout));
+#endif
+    ostream* cerr_ptr = ::new(cerr) ostream(::new(__cerr) __stdoutbuf<char>(stderr, &mb_cerr));
                         ::new(clog) ostream(cerr_ptr->rdbuf());
-    cin_ptr->tie(cout_ptr);
-    _VSTD::unitbuf(*cerr_ptr);
-    cerr_ptr->tie(cout_ptr);
-
-    wistream* wcin_ptr  = ::new(wcin)  wistream(::new(__wcin)  __stdinbuf <wchar_t>(stdin, state_types+3) );
-    wostream* wcout_ptr = ::new(wcout) wostream(::new(__wcout) __stdoutbuf<wchar_t>(stdout, state_types+4));
-    wostream* wcerr_ptr = ::new(wcerr) wostream(::new(__wcerr) __stdoutbuf<wchar_t>(stderr, state_types+5));
+    wostream* wcerr_ptr = ::new(wcerr) wostream(::new(__wcerr) __stdoutbuf<wchar_t>(stderr, &mb_wcerr));
                           ::new(wclog) wostream(wcerr_ptr->rdbuf());
+
+#if !defined(_LIBCPP_HAS_NO_STDIN) && !defined(_LIBCPP_HAS_NO_STDOUT)
+    cin_ptr->tie(cout_ptr);
     wcin_ptr->tie(wcout_ptr);
+#endif
+    _VSTD::unitbuf(*cerr_ptr);
     _VSTD::unitbuf(*wcerr_ptr);
+#ifndef _LIBCPP_HAS_NO_STDOUT
+    cerr_ptr->tie(cout_ptr);
     wcerr_ptr->tie(wcout_ptr);
+#endif
 }
 
 ios_base::Init::~Init()
 {
+#ifndef _LIBCPP_HAS_NO_STDOUT
     ostream* cout_ptr = reinterpret_cast<ostream*>(cout);
-    ostream* clog_ptr = reinterpret_cast<ostream*>(clog);
-    cout_ptr->flush();
-    clog_ptr->flush();
-
     wostream* wcout_ptr = reinterpret_cast<wostream*>(wcout);
-    wostream* wclog_ptr = reinterpret_cast<wostream*>(wclog);
+    cout_ptr->flush();
     wcout_ptr->flush();
+#endif
+
+    ostream* clog_ptr = reinterpret_cast<ostream*>(clog);
+    wostream* wclog_ptr = reinterpret_cast<wostream*>(wclog);
+    clog_ptr->flush();
     wclog_ptr->flush();
 }
 
diff --git a/src/locale.cpp b/src/locale.cpp
index 39ff351..bdc73e1 100644
--- a/src/locale.cpp
+++ b/src/locale.cpp
@@ -7,8 +7,6 @@
 //
 //===----------------------------------------------------------------------===//
 
-#define _LIBCPP_EXTERN_TEMPLATE(...) extern template __VA_ARGS__;
-
 // On Solaris, we need to define something to make the C99 parts of localeconv
 // visible.
 #ifdef __sun__
@@ -29,7 +27,7 @@
 #include "cwctype"
 #include "__sso_allocator"
 #if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
-#include <support/win32/locale_win32.h>
+#include "support/win32/locale_win32.h"
 #elif !defined(__ANDROID__)
 #include <langinfo.h>
 #endif
@@ -577,8 +575,10 @@
     locale& g = __global();
     locale r = g;
     g = loc;
+#ifndef __CloudABI__
     if (g.name() != "*")
         setlocale(LC_ALL, g.name().c_str());
+#endif
     return r;
 }
 
@@ -815,7 +815,7 @@
 #elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) || defined(__NetBSD__)
     return isascii(c) ? ctype<char>::__classic_upper_table()[c] : c;
 #else
-    return (isascii(c) && iswlower_l(c, __cloc())) ? c-L'a'+L'A' : c;
+    return (isascii(c) && iswlower_l(c, _LIBCPP_GET_C_LOCALE)) ? c-L'a'+L'A' : c;
 #endif
 }
 
@@ -829,7 +829,7 @@
         *low = isascii(*low) ? ctype<char>::__classic_upper_table()[*low]
                              : *low;
 #else
-        *low = (isascii(*low) && islower_l(*low, __cloc())) ? (*low-L'a'+L'A') : *low;
+        *low = (isascii(*low) && islower_l(*low, _LIBCPP_GET_C_LOCALE)) ? (*low-L'a'+L'A') : *low;
 #endif
     return low;
 }
@@ -842,7 +842,7 @@
 #elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) || defined(__NetBSD__)
     return isascii(c) ? ctype<char>::__classic_lower_table()[c] : c;
 #else
-    return (isascii(c) && isupper_l(c, __cloc())) ? c-L'A'+'a' : c;
+    return (isascii(c) && isupper_l(c, _LIBCPP_GET_C_LOCALE)) ? c-L'A'+'a' : c;
 #endif
 }
 
@@ -856,7 +856,7 @@
         *low = isascii(*low) ? ctype<char>::__classic_lower_table()[*low]
                              : *low;
 #else
-        *low = (isascii(*low) && isupper_l(*low, __cloc())) ? *low-L'A'+L'a' : *low;
+        *low = (isascii(*low) && isupper_l(*low, _LIBCPP_GET_C_LOCALE)) ? *low-L'A'+L'a' : *low;
 #endif
     return low;
 }
@@ -925,7 +925,7 @@
     return isascii(c) ? 
       static_cast<char>(__classic_upper_table()[static_cast<unsigned char>(c)]) : c;
 #else
-    return (isascii(c) && islower_l(c, __cloc())) ? c-'a'+'A' : c;
+    return (isascii(c) && islower_l(c, _LIBCPP_GET_C_LOCALE)) ? c-'a'+'A' : c;
 #endif
 }
 
@@ -942,7 +942,7 @@
         *low = isascii(*low) ?
           static_cast<char>(__classic_upper_table()[static_cast<size_t>(*low)]) : *low;
 #else
-        *low = (isascii(*low) && islower_l(*low, __cloc())) ? *low-'a'+'A' : *low;
+        *low = (isascii(*low) && islower_l(*low, _LIBCPP_GET_C_LOCALE)) ? *low-'a'+'A' : *low;
 #endif
     return low;
 }
@@ -959,7 +959,7 @@
     return isascii(c) ?
       static_cast<char>(__classic_lower_table()[static_cast<size_t>(c)]) : c;
 #else
-    return (isascii(c) && isupper_l(c, __cloc())) ? c-'A'+'a' : c;
+    return (isascii(c) && isupper_l(c, _LIBCPP_GET_C_LOCALE)) ? c-'A'+'a' : c;
 #endif
 }
 
@@ -974,7 +974,7 @@
 #elif defined(__GLIBC__) || defined(__EMSCRIPTEN__)
         *low = isascii(*low) ? static_cast<char>(__classic_lower_table()[static_cast<size_t>(*low)]) : *low;
 #else
-        *low = (isascii(*low) && isupper_l(*low, __cloc())) ? *low-'A'+'a' : *low;
+        *low = (isascii(*low) && isupper_l(*low, _LIBCPP_GET_C_LOCALE)) ? *low-'A'+'a' : *low;
 #endif
     return low;
 }
@@ -1107,7 +1107,7 @@
 #elif defined(__NetBSD__)
     return _C_ctype_tab_ + 1;
 #elif defined(__GLIBC__)
-    return __cloc()->__ctype_b;
+    return _LIBCPP_GET_C_LOCALE->__ctype_b;
 #elif __sun__
     return __ctype_mask;
 #elif defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
@@ -1136,13 +1136,13 @@
 const int*
 ctype<char>::__classic_lower_table() _NOEXCEPT
 {
-    return __cloc()->__ctype_tolower;
+    return _LIBCPP_GET_C_LOCALE->__ctype_tolower;
 }
 
 const int*
 ctype<char>::__classic_upper_table() _NOEXCEPT
 {
-    return __cloc()->__ctype_toupper;
+    return _LIBCPP_GET_C_LOCALE->__ctype_toupper;
 }
 #elif __NetBSD__
 const short*
@@ -1265,16 +1265,16 @@
 #else
     bool result = false;
     wint_t ch = static_cast<wint_t>(c);
-    if (m & space) result |= (iswspace_l(ch, __l) != 0);
-    if (m & print) result |= (iswprint_l(ch, __l) != 0);
-    if (m & cntrl) result |= (iswcntrl_l(ch, __l) != 0);
-    if (m & upper) result |= (iswupper_l(ch, __l) != 0);
-    if (m & lower) result |= (iswlower_l(ch, __l) != 0);
-    if (m & alpha) result |= (iswalpha_l(ch, __l) != 0);
-    if (m & digit) result |= (iswdigit_l(ch, __l) != 0);
-    if (m & punct) result |= (iswpunct_l(ch, __l) != 0);
-    if (m & xdigit) result |= (iswxdigit_l(ch, __l) != 0);
-    if (m & blank) result |= (iswblank_l(ch, __l) != 0);
+    if ((m & space) == space) result |= (iswspace_l(ch, __l) != 0);
+    if ((m & print) == print) result |= (iswprint_l(ch, __l) != 0);
+    if ((m & cntrl) == cntrl) result |= (iswcntrl_l(ch, __l) != 0);
+    if ((m & upper) == upper) result |= (iswupper_l(ch, __l) != 0);
+    if ((m & lower) == lower) result |= (iswlower_l(ch, __l) != 0);
+    if ((m & alpha) == alpha) result |= (iswalpha_l(ch, __l) != 0);
+    if ((m & digit) == digit) result |= (iswdigit_l(ch, __l) != 0);
+    if ((m & punct) == punct) result |= (iswpunct_l(ch, __l) != 0);
+    if ((m & xdigit) == xdigit) result |= (iswxdigit_l(ch, __l) != 0);
+    if ((m & blank) == blank) result |= (iswblank_l(ch, __l) != 0);
     return result;
 #endif
 }
@@ -1292,22 +1292,32 @@
             wint_t ch = static_cast<wint_t>(*low);
             if (iswspace_l(ch, __l))
                 *vec |= space;
+#ifndef _LIBCPP_CTYPE_MASK_IS_COMPOSITE_PRINT
             if (iswprint_l(ch, __l))
                 *vec |= print;
+#endif
             if (iswcntrl_l(ch, __l))
                 *vec |= cntrl;
             if (iswupper_l(ch, __l))
                 *vec |= upper;
             if (iswlower_l(ch, __l))
                 *vec |= lower;
+#ifndef _LIBCPP_CTYPE_MASK_IS_COMPOSITE_ALPHA
             if (iswalpha_l(ch, __l))
                 *vec |= alpha;
+#endif
             if (iswdigit_l(ch, __l))
                 *vec |= digit;
             if (iswpunct_l(ch, __l))
                 *vec |= punct;
+#ifndef _LIBCPP_CTYPE_MASK_IS_COMPOSITE_XDIGIT
             if (iswxdigit_l(ch, __l))
                 *vec |= xdigit;
+#endif
+#if !defined(__sun__)
+            if (iswblank_l(ch, __l))
+                *vec |= blank;
+#endif
         }
     }
     return low;
@@ -1323,16 +1333,16 @@
             break;
 #else
         wint_t ch = static_cast<wint_t>(*low);
-        if (m & space && iswspace_l(ch, __l)) break;
-        if (m & print && iswprint_l(ch, __l)) break;
-        if (m & cntrl && iswcntrl_l(ch, __l)) break;
-        if (m & upper && iswupper_l(ch, __l)) break;
-        if (m & lower && iswlower_l(ch, __l)) break;
-        if (m & alpha && iswalpha_l(ch, __l)) break;
-        if (m & digit && iswdigit_l(ch, __l)) break;
-        if (m & punct && iswpunct_l(ch, __l)) break;
-        if (m & xdigit && iswxdigit_l(ch, __l)) break;
-        if (m & blank && iswblank_l(ch, __l)) break;
+        if ((m & space) == space && iswspace_l(ch, __l)) break;
+        if ((m & print) == print && iswprint_l(ch, __l)) break;
+        if ((m & cntrl) == cntrl && iswcntrl_l(ch, __l)) break;
+        if ((m & upper) == upper && iswupper_l(ch, __l)) break;
+        if ((m & lower) == lower && iswlower_l(ch, __l)) break;
+        if ((m & alpha) == alpha && iswalpha_l(ch, __l)) break;
+        if ((m & digit) == digit && iswdigit_l(ch, __l)) break;
+        if ((m & punct) == punct && iswpunct_l(ch, __l)) break;
+        if ((m & xdigit) == xdigit && iswxdigit_l(ch, __l)) break;
+        if ((m & blank) == blank && iswblank_l(ch, __l)) break;
 #endif
     }
     return low;
@@ -1348,16 +1358,16 @@
             break;
 #else
         wint_t ch = static_cast<wint_t>(*low);
-        if (m & space && iswspace_l(ch, __l)) continue;
-        if (m & print && iswprint_l(ch, __l)) continue;
-        if (m & cntrl && iswcntrl_l(ch, __l)) continue;
-        if (m & upper && iswupper_l(ch, __l)) continue;
-        if (m & lower && iswlower_l(ch, __l)) continue;
-        if (m & alpha && iswalpha_l(ch, __l)) continue;
-        if (m & digit && iswdigit_l(ch, __l)) continue;
-        if (m & punct && iswpunct_l(ch, __l)) continue;
-        if (m & xdigit && iswxdigit_l(ch, __l)) continue;
-        if (m & blank && iswblank_l(ch, __l)) continue;
+        if ((m & space) == space && iswspace_l(ch, __l)) continue;
+        if ((m & print) == print && iswprint_l(ch, __l)) continue;
+        if ((m & cntrl) == cntrl && iswcntrl_l(ch, __l)) continue;
+        if ((m & upper) == upper && iswupper_l(ch, __l)) continue;
+        if ((m & lower) == lower && iswlower_l(ch, __l)) continue;
+        if ((m & alpha) == alpha && iswalpha_l(ch, __l)) continue;
+        if ((m & digit) == digit && iswdigit_l(ch, __l)) continue;
+        if ((m & punct) == punct && iswpunct_l(ch, __l)) continue;
+        if ((m & xdigit) == xdigit && iswxdigit_l(ch, __l)) continue;
+        if ((m & blank) == blank && iswblank_l(ch, __l)) continue;
         break;
 #endif
     }
@@ -1649,7 +1659,7 @@
             frm_nxt = frm;
             return frm_nxt == frm_end ? ok : partial;
         }
-        if (n == 0)
+        if (n == size_t(-1))
             return error;
         to_nxt += n;
         if (to_nxt == to_end)
@@ -1699,22 +1709,23 @@
 int
 codecvt<wchar_t, char, mbstate_t>::do_encoding() const  _NOEXCEPT
 {
+#ifndef __CloudABI__
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
-    if (mbtowc_l(nullptr, nullptr, MB_LEN_MAX, __l) == 0)
+    if (mbtowc_l(nullptr, nullptr, MB_LEN_MAX, __l) != 0)
 #else
-    if (__mbtowc_l(nullptr, nullptr, MB_LEN_MAX, __l) == 0)
+    if (__mbtowc_l(nullptr, nullptr, MB_LEN_MAX, __l) != 0)
 #endif
-    {
-        // stateless encoding
+        return -1;
+#endif
+
+    // stateless encoding
 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
-        if (__l == 0 || MB_CUR_MAX_L(__l) == 1)  // there are no known constant length encodings
+    if (__l == 0 || MB_CUR_MAX_L(__l) == 1)  // there are no known constant length encodings
 #else
-        if (__l == 0 || __mb_cur_max_l(__l) == 1)  // there are no known constant length encodings
+    if (__l == 0 || __mb_cur_max_l(__l) == 1)  // there are no known constant length encodings
 #endif
-            return 1;                // which take more than 1 char to form a wchar_t
-         return 0;
-    }
-    return -1;
+        return 1;                // which take more than 1 char to form a wchar_t
+    return 0;
 }
 
 bool
diff --git a/src/memory.cpp b/src/memory.cpp
index 8a4eb34..66fb143 100644
--- a/src/memory.cpp
+++ b/src/memory.cpp
@@ -13,24 +13,28 @@
 #include "mutex"
 #include "thread"
 #endif
+#include "support/atomic_support.h"
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
 namespace
 {
 
+// NOTE: Relaxed and acq/rel atomics (for increment and decrement respectively)
+// should be sufficient for thread safety.
+// See https://llvm.org/bugs/show_bug.cgi?id=22803
 template <class T>
 inline T
 increment(T& t) _NOEXCEPT
 {
-    return __sync_add_and_fetch(&t, 1);
+    return __libcpp_atomic_add(&t, 1, _AO_Relaxed);
 }
 
 template <class T>
 inline T
 decrement(T& t) _NOEXCEPT
 {
-    return __sync_add_and_fetch(&t, -1);
+    return __libcpp_atomic_add(&t, -1, _AO_Acq_Rel);
 }
 
 }  // namespace
@@ -99,14 +103,13 @@
 __shared_weak_count*
 __shared_weak_count::lock() _NOEXCEPT
 {
-    long object_owners = __shared_owners_;
+    long object_owners = __libcpp_atomic_load(&__shared_owners_);
     while (object_owners != -1)
     {
-        if (__sync_bool_compare_and_swap(&__shared_owners_,
-                                         object_owners,
-                                         object_owners+1))
+        if (__libcpp_atomic_compare_exchange(&__shared_owners_,
+                                             &object_owners,
+                                             object_owners+1))
             return this;
-        object_owners = __shared_owners_;
     }
     return 0;
 }
diff --git a/src/mutex.cpp b/src/mutex.cpp
index e56271d..5f8ba0a 100644
--- a/src/mutex.cpp
+++ b/src/mutex.cpp
@@ -12,6 +12,7 @@
 #include "limits"
 #include "system_error"
 #include "cassert"
+#include "support/atomic_support.h"
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 #ifndef _LIBCPP_HAS_NO_THREADS
@@ -220,6 +221,9 @@
 static pthread_cond_t  cv  = PTHREAD_COND_INITIALIZER;
 #endif
 
+/// NOTE: Changes to flag are done via relaxed atomic stores
+///       even though the accesses are protected by a mutex because threads
+///       just entering 'call_once` concurrently read from flag.
 void
 __call_once(volatile unsigned long& flag, void* arg, void(*func)(void*))
 {
@@ -252,11 +256,11 @@
         try
         {
 #endif  // _LIBCPP_NO_EXCEPTIONS
-            flag = 1;
+            __libcpp_relaxed_store(&flag, 1ul);
             pthread_mutex_unlock(&mut);
             func(arg);
             pthread_mutex_lock(&mut);
-            flag = ~0ul;
+            __libcpp_relaxed_store(&flag, ~0ul);
             pthread_mutex_unlock(&mut);
             pthread_cond_broadcast(&cv);
 #ifndef _LIBCPP_NO_EXCEPTIONS
@@ -264,7 +268,7 @@
         catch (...)
         {
             pthread_mutex_lock(&mut);
-            flag = 0ul;
+            __libcpp_relaxed_store(&flag, 0ul);
             pthread_mutex_unlock(&mut);
             pthread_cond_broadcast(&cv);
             throw;
diff --git a/src/new.cpp b/src/new.cpp
index c46d073..c28fcb5 100644
--- a/src/new.cpp
+++ b/src/new.cpp
@@ -140,13 +140,6 @@
 
 _LIBCPP_WEAK _LIBCPP_NEW_DELETE_VIS
 void
-operator delete(void* ptr, size_t, const std::nothrow_t& nt) _NOEXCEPT
-{
-    ::operator delete(ptr, nt);
-}
-
-_LIBCPP_WEAK _LIBCPP_NEW_DELETE_VIS
-void
 operator delete[] (void* ptr) _NOEXCEPT
 {
     ::operator delete(ptr);
@@ -166,13 +159,6 @@
     ::operator delete[](ptr);
 }
 
-_LIBCPP_WEAK _LIBCPP_NEW_DELETE_VIS
-void
-operator delete[] (void* ptr, size_t, const std::nothrow_t& nt) _NOEXCEPT
-{
-    ::operator delete[](ptr, nt);
-}
-
 #endif // !__GLIBCXX__
 
 namespace std
diff --git a/src/random.cpp b/src/random.cpp
index 0a1d2a5..4ab424e 100644
--- a/src/random.cpp
+++ b/src/random.cpp
@@ -7,11 +7,10 @@
 //
 //===----------------------------------------------------------------------===//
 
-#if defined(_WIN32)
+#if defined(_LIBCPP_USING_WIN32_RANDOM)
 // Must be defined before including stdlib.h to enable rand_s().
 #define _CRT_RAND_S
-#include <stdio.h>
-#endif // defined(_WIN32)
+#endif // defined(_LIBCPP_USING_WIN32_RANDOM)
 
 #include "random"
 #include "system_error"
@@ -19,46 +18,27 @@
 #if defined(__sun__)
 #define rename solaris_headers_are_broken
 #endif // defined(__sun__)
-#if !defined(_WIN32)
+
+#include <errno.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#if defined(_LIBCPP_USING_DEV_RANDOM)
 #include <fcntl.h>
 #include <unistd.h>
-#endif // !defined(_WIN32)
-#include <errno.h>
-#if defined(_LIBCPP_USING_NACL_RANDOM)
+#elif defined(_LIBCPP_USING_NACL_RANDOM)
 #include <nacl/nacl_random.h>
-#endif // defined(_LIBCPP_USING_NACL_RANDOM)
+#endif
+
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
-#if defined(_WIN32)
-
-random_device::random_device(const string&)
-{
-}
-
-random_device::~random_device()
-{
-}
-
-unsigned
-random_device::operator()()
-{
-    unsigned r;
-    errno_t err = rand_s(&r);
-    if (err)
-        __throw_system_error(err, "random_device rand_s failed.");
-    return r;
-}
-
-#elif defined(_LIBCPP_USING_NACL_RANDOM)
+#if defined(_LIBCPP_USING_ARC4_RANDOM)
 
 random_device::random_device(const string& __token)
 {
     if (__token != "/dev/urandom")
         __throw_system_error(ENOENT, ("random device not supported " + __token).c_str());
-    int error = nacl_secure_random_init();
-    if (error)
-        __throw_system_error(error, ("random device failed to open " + __token).c_str());
 }
 
 random_device::~random_device()
@@ -68,18 +48,10 @@
 unsigned
 random_device::operator()()
 {
-    unsigned r;
-    size_t n = sizeof(r);
-    size_t bytes_written;
-    int error = nacl_secure_random(&r, n, &bytes_written);
-    if (error != 0)
-        __throw_system_error(error, "random_device failed getting bytes");
-    else if (bytes_written != n)
-        __throw_runtime_error("random_device failed to obtain enough bytes");
-    return r;
+    return arc4random();
 }
 
-#else // !defined(_WIN32) && !defined(_LIBCPP_USING_NACL_RANDOM)
+#elif defined(_LIBCPP_USING_DEV_RANDOM)
 
 random_device::random_device(const string& __token)
     : __f_(open(__token.c_str(), O_RDONLY))
@@ -116,7 +88,60 @@
     return r;
 }
 
-#endif // defined(_WIN32) || defined(_LIBCPP_USING_NACL_RANDOM)
+#elif defined(_LIBCPP_USING_NACL_RANDOM)
+
+random_device::random_device(const string& __token)
+{
+    if (__token != "/dev/urandom")
+        __throw_system_error(ENOENT, ("random device not supported " + __token).c_str());
+    int error = nacl_secure_random_init();
+    if (error)
+        __throw_system_error(error, ("random device failed to open " + __token).c_str());
+}
+
+random_device::~random_device()
+{
+}
+
+unsigned
+random_device::operator()()
+{
+    unsigned r;
+    size_t n = sizeof(r);
+    size_t bytes_written;
+    int error = nacl_secure_random(&r, n, &bytes_written);
+    if (error != 0)
+        __throw_system_error(error, "random_device failed getting bytes");
+    else if (bytes_written != n)
+        __throw_runtime_error("random_device failed to obtain enough bytes");
+    return r;
+}
+
+#elif defined(_LIBCPP_USING_WIN32_RANDOM)
+
+random_device::random_device(const string& __token)
+{
+    if (__token != "/dev/urandom")
+        __throw_system_error(ENOENT, ("random device not supported " + __token).c_str());
+}
+
+random_device::~random_device()
+{
+}
+
+unsigned
+random_device::operator()()
+{
+    unsigned r;
+    errno_t err = rand_s(&r);
+    if (err)
+        __throw_system_error(err, "random_device rand_s failed.");
+    return r;
+}
+
+#else
+#error "Random device not implemented for this architecture"
+#endif
 
 double
 random_device::entropy() const _NOEXCEPT
diff --git a/src/shared_mutex.cpp b/src/shared_mutex.cpp
index 2b78c1f..874aceb 100644
--- a/src/shared_mutex.cpp
+++ b/src/shared_mutex.cpp
@@ -15,7 +15,8 @@
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
-shared_timed_mutex::shared_timed_mutex()
+// Shared Mutex Base
+__shared_mutex_base::__shared_mutex_base()
     : __state_(0)
 {
 }
@@ -23,7 +24,7 @@
 // Exclusive ownership
 
 void
-shared_timed_mutex::lock()
+__shared_mutex_base::lock()
 {
     unique_lock<mutex> lk(__mut_);
     while (__state_ & __write_entered_)
@@ -34,7 +35,7 @@
 }
 
 bool
-shared_timed_mutex::try_lock()
+__shared_mutex_base::try_lock()
 {
     unique_lock<mutex> lk(__mut_);
     if (__state_ == 0)
@@ -46,7 +47,7 @@
 }
 
 void
-shared_timed_mutex::unlock()
+__shared_mutex_base::unlock()
 {
     lock_guard<mutex> _(__mut_);
     __state_ = 0;
@@ -56,7 +57,7 @@
 // Shared ownership
 
 void
-shared_timed_mutex::lock_shared()
+__shared_mutex_base::lock_shared()
 {
     unique_lock<mutex> lk(__mut_);
     while ((__state_ & __write_entered_) || (__state_ & __n_readers_) == __n_readers_)
@@ -67,7 +68,7 @@
 }
 
 bool
-shared_timed_mutex::try_lock_shared()
+__shared_mutex_base::try_lock_shared()
 {
     unique_lock<mutex> lk(__mut_);
     unsigned num_readers = __state_ & __n_readers_;
@@ -82,7 +83,7 @@
 }
 
 void
-shared_timed_mutex::unlock_shared()
+__shared_mutex_base::unlock_shared()
 {
     lock_guard<mutex> _(__mut_);
     unsigned num_readers = (__state_ & __n_readers_) - 1;
@@ -101,6 +102,16 @@
 }
 
 
+// Shared Timed Mutex
+// These routines are here for ABI stability
+shared_timed_mutex::shared_timed_mutex() : __base() {}
+void shared_timed_mutex::lock()     { return __base.lock(); }
+bool shared_timed_mutex::try_lock() { return __base.try_lock(); }
+void shared_timed_mutex::unlock()   { return __base.unlock(); }
+void shared_timed_mutex::lock_shared() { return __base.lock_shared(); }
+bool shared_timed_mutex::try_lock_shared() { return __base.try_lock_shared(); }
+void shared_timed_mutex::unlock_shared() { return __base.unlock_shared(); }
+
 _LIBCPP_END_NAMESPACE_STD
 
 #endif // !_LIBCPP_HAS_NO_THREADS
diff --git a/src/string.cpp b/src/string.cpp
index 8aea0f7..d3f29df 100644
--- a/src/string.cpp
+++ b/src/string.cpp
@@ -7,8 +7,6 @@
 //
 //===----------------------------------------------------------------------===//
 
-#define _LIBCPP_EXTERN_TEMPLATE(...) extern template __VA_ARGS__;
-
 #include "string"
 #include "cstdlib"
 #include "cwchar"
@@ -41,7 +39,7 @@
 #ifndef _LIBCPP_NO_EXCEPTIONS
     throw T( msg );
 #else
-    printf("%s\n", msg.c_str());
+    fprintf(stderr, "%s\n", msg.c_str());
     abort();
 #endif
 }
diff --git a/src/support/atomic_support.h b/src/support/atomic_support.h
new file mode 100644
index 0000000..e738a51
--- /dev/null
+++ b/src/support/atomic_support.h
@@ -0,0 +1,142 @@
+#ifndef ATOMIC_SUPPORT_H
+#define ATOMIC_SUPPORT_H
+
+#include "__config"
+#include "memory" // for __libcpp_relaxed_load
+
+#if defined(__clang__) && __has_builtin(__atomic_load_n)             \
+                       && __has_builtin(__atomic_store_n)            \
+                       && __has_builtin(__atomic_add_fetch)          \
+                       && __has_builtin(__atomic_compare_exchange_n) \
+                       && defined(__ATOMIC_RELAXED)                  \
+                       && defined(__ATOMIC_CONSUME)                  \
+                       && defined(__ATOMIC_ACQUIRE)                  \
+                       && defined(__ATOMIC_RELEASE)                  \
+                       && defined(__ATOMIC_ACQ_REL)                  \
+                       && defined(__ATOMIC_SEQ_CST)
+#   define _LIBCPP_HAS_ATOMIC_BUILTINS
+#elif !defined(__clang__) && defined(_GNUC_VER) && _GNUC_VER >= 407
+#   define _LIBCPP_HAS_ATOMIC_BUILTINS
+#endif
+
+#if !defined(_LIBCPP_HAS_ATOMIC_BUILTINS) && !defined(_LIBCPP_HAS_NO_THREADS)
+# if defined(_MSC_VER) && !defined(__clang__)
+    _LIBCPP_WARNING("Building libc++ without __atomic builtins is unsupported")
+# else
+#   warning Building libc++ without __atomic builtins is unsupported
+# endif
+#endif
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+namespace {
+
+#if defined(_LIBCPP_HAS_ATOMIC_BUILTINS) && !defined(_LIBCPP_HAS_NO_THREADS)
+
+enum __libcpp_atomic_order {
+    _AO_Relaxed = __ATOMIC_RELAXED,
+    _AO_Consume = __ATOMIC_CONSUME,
+    _AO_Aquire  = __ATOMIC_ACQUIRE,
+    _AO_Release = __ATOMIC_RELEASE,
+    _AO_Acq_Rel = __ATOMIC_ACQ_REL,
+    _AO_Seq     = __ATOMIC_SEQ_CST
+};
+
+template <class _ValueType, class _FromType>
+inline _LIBCPP_INLINE_VISIBILITY
+void __libcpp_atomic_store(_ValueType* __dest, _FromType __val,
+                           int __order = _AO_Seq)
+{
+    __atomic_store_n(__dest, __val, __order);
+}
+
+template <class _ValueType, class _FromType>
+inline _LIBCPP_INLINE_VISIBILITY
+void __libcpp_relaxed_store(_ValueType* __dest, _FromType __val)
+{
+    __atomic_store_n(__dest, __val, _AO_Relaxed);
+}
+
+template <class _ValueType>
+inline _LIBCPP_INLINE_VISIBILITY
+_ValueType __libcpp_atomic_load(_ValueType const* __val,
+                                int __order = _AO_Seq)
+{
+    return __atomic_load_n(__val, __order);
+}
+
+template <class _ValueType, class _AddType>
+inline _LIBCPP_INLINE_VISIBILITY
+_ValueType __libcpp_atomic_add(_ValueType* __val, _AddType __a,
+                               int __order = _AO_Seq)
+{
+    return __atomic_add_fetch(__val, __a, __order);
+}
+
+template <class _ValueType>
+inline _LIBCPP_INLINE_VISIBILITY
+bool __libcpp_atomic_compare_exchange(_ValueType* __val,
+    _ValueType* __expected, _ValueType __after,
+    int __success_order = _AO_Seq,
+    int __fail_order = _AO_Seq)
+{
+    return __atomic_compare_exchange_n(__val, __expected, __after, true,
+                                       __success_order, __fail_order);
+}
+
+#else // _LIBCPP_HAS_NO_THREADS
+
+enum __libcpp_atomic_order {
+    _AO_Relaxed,
+    _AO_Consume,
+    _AO_Acquire,
+    _AO_Release,
+    _AO_Acq_Rel,
+    _AO_Seq
+};
+
+template <class _ValueType, class _FromType>
+inline _LIBCPP_INLINE_VISIBILITY
+void __libcpp_atomic_store(_ValueType* __dest, _FromType __val,
+                           int = 0)
+{
+    *__dest = __val;
+}
+
+template <class _ValueType>
+inline _LIBCPP_INLINE_VISIBILITY
+_ValueType __libcpp_atomic_load(_ValueType const* __val,
+                                int = 0)
+{
+    return *__val;
+}
+
+template <class _ValueType, class _AddType>
+inline _LIBCPP_INLINE_VISIBILITY
+_ValueType __libcpp_atomic_add(_ValueType* __val, _AddType __a,
+                               int = 0)
+{
+    return *__val += __a;
+}
+
+template <class _ValueType>
+inline _LIBCPP_INLINE_VISIBILITY
+bool __libcpp_atomic_compare_exchange(_ValueType* __val,
+    _ValueType* __expected, _ValueType __after,
+    int = 0, int = 0)
+{
+    if (*__val == *__expected) {
+        *__val = __after;
+        return true;
+    }
+    *__expected = *__val;
+    return false;
+}
+
+#endif // _LIBCPP_HAS_NO_THREADS
+
+} // end namespace
+
+_LIBCPP_END_NAMESPACE_STD
+
+#endif // ATOMIC_SUPPORT_H
diff --git a/src/system_error.cpp b/src/system_error.cpp
index c032fc0..18f668f 100644
--- a/src/system_error.cpp
+++ b/src/system_error.cpp
@@ -152,7 +152,7 @@
             what_arg += ": ";
         what_arg += ec.message();
     }
-    return _VSTD::move(what_arg);
+    return what_arg;
 }
 
 system_error::system_error(error_code ec, const string& what_arg)
diff --git a/src/thread.cpp b/src/thread.cpp
index 6aad558..bd27f28 100644
--- a/src/thread.cpp
+++ b/src/thread.cpp
@@ -17,9 +17,9 @@
 #include "limits"
 #include <sys/types.h>
 #if !defined(_WIN32)
-# if !defined(__sun__) && !defined(__linux__) && !defined(_AIX) && !defined(__native_client__)
+# if !defined(__sun__) && !defined(__linux__) && !defined(_AIX) && !defined(__native_client__) && !defined(__CloudABI__)
 #   include <sys/sysctl.h>
-# endif // !defined(__sun__) && !defined(__linux__) && !defined(_AIX) && !defined(__native_client__)
+# endif // !defined(__sun__) && !defined(__linux__) && !defined(_AIX) && !defined(__native_client__) && !defined(__CloudABI__)
 # include <unistd.h>
 #endif // !_WIN32
 
diff --git a/src/valarray.cpp b/src/valarray.cpp
index e4c9ed0..2d8db52 100644
--- a/src/valarray.cpp
+++ b/src/valarray.cpp
@@ -7,8 +7,6 @@
 //
 //===----------------------------------------------------------------------===//
 
-#define _LIBCPP_EXTERN_TEMPLATE(...) extern template __VA_ARGS__;
-
 #include "valarray"
 
 _LIBCPP_BEGIN_NAMESPACE_STD
diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt
index 6af4c98..60dd7c2 100644
--- a/test/CMakeLists.txt
+++ b/test/CMakeLists.txt
@@ -6,69 +6,48 @@
   endif()
 endmacro()
 
-set(LIT_EXECUTABLE "" CACHE FILEPATH "Path to LLVM's llvm-lit.")
+set(LIBCXX_LIT_VARIANT "libcxx" CACHE STRING
+    "Configuration variant to use for LIT.")
 
-if(LIBCXX_BUILT_STANDALONE)
-  # Make sure we can use the console pool for recent cmake and ninja > 1.5
-  if(CMAKE_VERSION VERSION_LESS 3.1.20141117)
-    set(cmake_3_2_USES_TERMINAL)
-  else()
-    set(cmake_3_2_USES_TERMINAL USES_TERMINAL)
-  endif()
-else()
-  include(FindPythonInterp)
-  if(PYTHONINTERP_FOUND)
-    set(LIT_EXECUTABLE
-        ${PYTHON_EXECUTABLE} ${CMAKE_SOURCE_DIR}/utils/lit/lit.py)
-  else()
-    message(WARNING "Could not find Python, cannot set LIT_EXECUTABLE.")
-  endif()
+pythonize_bool(LIBCXX_ENABLE_EXCEPTIONS)
+pythonize_bool(LIBCXX_ENABLE_RTTI)
+pythonize_bool(LIBCXX_ENABLE_SHARED)
+pythonize_bool(LIBCXX_BUILD_32_BITS)
+pythonize_bool(LIBCXX_ENABLE_GLOBAL_FILESYSTEM_NAMESPACE)
+pythonize_bool(LIBCXX_ENABLE_STDIN)
+pythonize_bool(LIBCXX_ENABLE_STDOUT)
+pythonize_bool(LIBCXX_ENABLE_THREADS)
+pythonize_bool(LIBCXX_ENABLE_THREAD_UNSAFE_C_FUNCTIONS)
+pythonize_bool(LIBCXX_ENABLE_MONOTONIC_CLOCK)
+pythonize_bool(LIBCXX_GENERATE_COVERAGE)
+pythonize_bool(LIBCXXABI_USE_LLVM_UNWINDER)
+
+# The tests shouldn't link to any ABI library when it has been linked into
+# libc++ statically.
+if (LIBCXX_ENABLE_STATIC_ABI_LIBRARY)
+  set(LIBCXX_CXX_ABI_LIBNAME "none")
 endif()
+set(LIBCXX_TARGET_INFO "libcxx.test.target_info.LocalTI" CACHE STRING
+    "TargetInfo to use when setting up test environment.")
+set(LIBCXX_EXECUTOR "None" CACHE STRING
+    "Executor to use when running tests.")
 
-if (LIT_EXECUTABLE)
-  set(LIT_ARGS_DEFAULT "-sv --show-unsupported --show-xfail")
-  if (MSVC OR XCODE)
-    set(LIT_ARGS_DEFAULT "${LIT_ARGS_DEFAULT} --no-progress-bar")
-  endif()
-  set(LLVM_LIT_ARGS "${LIT_ARGS_DEFAULT}"
-      CACHE STRING "Default options for lit")
-  set(LIT_ARGS "${LLVM_LIT_ARGS}")
-  separate_arguments(LIT_ARGS)
+set(AUTO_GEN_COMMENT "## Autogenerated by libcxx configuration.\n# Do not edit!")
 
-  set(LIBCXX_LIT_VARIANT "libcxx" CACHE STRING
-      "Configuration variant to use for LIT.")
+configure_file(
+  ${CMAKE_CURRENT_SOURCE_DIR}/lit.site.cfg.in
+  ${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg
+  @ONLY)
 
-  pythonize_bool(LIBCXX_ENABLE_EXCEPTIONS)
-  pythonize_bool(LIBCXX_ENABLE_RTTI)
-  pythonize_bool(LIBCXX_ENABLE_SHARED)
-  pythonize_bool(LIBCXX_BUILD_32_BITS)
-  pythonize_bool(LIBCXX_ENABLE_THREADS)
-  pythonize_bool(LIBCXX_ENABLE_MONOTONIC_CLOCK)
-  # The tests shouldn't link to any ABI library when it has been linked into
-  # libc++ statically.
-  if (LIBCXX_ENABLE_STATIC_ABI_LIBRARY)
-    set(LIBCXX_CXX_ABI_LIBNAME "none")
-  endif()
-  set(LIBCXX_TARGET_INFO "libcxx.test.target_info.LocalTI" CACHE STRING
-      "TargetInfo to use when setting up test environment.")
-  set(LIBCXX_EXECUTOR "None" CACHE STRING
-      "Executor to use when running tests.")
+add_lit_testsuite(check-libcxx
+  "Running libcxx tests"
+  ${CMAKE_CURRENT_BINARY_DIR}
+  DEPENDS cxx)
 
-  set(AUTO_GEN_COMMENT "## Autogenerated by libcxx configuration.\n# Do not edit!")
-
-  configure_file(
-    ${CMAKE_CURRENT_SOURCE_DIR}/lit.site.cfg.in
-    ${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg
-    @ONLY)
-
-  add_custom_target(check-libcxx
-    COMMAND ${LIT_EXECUTABLE}
-            ${LIT_ARGS}
-            ${CMAKE_CURRENT_BINARY_DIR}
-    DEPENDS cxx
-    COMMENT "Running libcxx tests"
-    ${cmake_3_2_USES_TERMINAL})
-else()
-  message(WARNING
-          "LIT_EXECUTABLE not set, no check-libcxx target will be available!")
+if (LIBCXX_GENERATE_COVERAGE)
+  include(CodeCoverage)
+  set(output_dir "${CMAKE_CURRENT_BINARY_DIR}/coverage")
+  set(capture_dirs "${LIBCXX_LIB_CMAKEFILES_DIR}/cxx.dir/;${CMAKE_CURRENT_BINARY_DIR}")
+  set(extract_dirs "${LIBCXX_SOURCE_DIR}/include;${LIBCXX_SOURCE_DIR}/src")
+  setup_lcov_test_target_coverage("cxx" "${output_dir}" "${capture_dirs}" "${extract_dirs}")
 endif()
diff --git a/test/libcxx/compiler.py b/test/libcxx/compiler.py
index 4828874..24ac431 100644
--- a/test/libcxx/compiler.py
+++ b/test/libcxx/compiler.py
@@ -107,12 +107,15 @@
             # Otherwise wrap the filename in a context manager function.
             with_fn = lambda: libcxx.util.nullContext(object_file)
         with with_fn() as object_file:
-            cmd, output, err, rc = self.compile(source_file, object_file,
-                                                flags=flags, env=env, cwd=cwd)
+            cc_cmd, cc_stdout, cc_stderr, rc = self.compile(
+                    source_file, object_file, flags=flags, env=env, cwd=cwd)
             if rc != 0:
-                return cmd, output, err, rc
-            return self.link(object_file, out=out, flags=flags, env=env,
-                             cwd=cwd)
+                return cc_cmd, cc_stdout, cc_stderr, rc
+
+            link_cmd, link_stdout, link_stderr, rc = self.link(
+                    object_file, out=out, flags=flags, env=env, cwd=cwd)
+            return (cc_cmd + ['&&'] + link_cmd, cc_stdout + link_stdout,
+                    cc_stderr + link_stderr, rc)
 
     def dumpMacros(self, source_files=None, flags=[], env=None, cwd=None):
         if source_files is None:
@@ -134,3 +137,27 @@
     def getTriple(self):
         cmd = [self.path] + self.flags + ['-dumpmachine']
         return lit.util.capture(cmd).strip()
+
+    def hasCompileFlag(self, flag):
+        if isinstance(flag, list):
+            flags = list(flag)
+        else:
+            flags = [flag]
+        # Add -Werror to ensure that an unrecognized flag causes a non-zero
+        # exit code. -Werror is supported on all known compiler types.
+        if self.type is not None:
+            flags += ['-Werror']
+        cmd, out, err, rc = self.compile(os.devnull, out=os.devnull,
+                                         flags=flags)
+        return rc == 0
+
+    def addCompileFlagIfSupported(self, flag):
+        if isinstance(flag, list):
+            flags = list(flag)
+        else:
+            flags = [flag]
+        if self.hasCompileFlag(flags):
+            self.compile_flags += flags
+            return True
+        else:
+            return False
diff --git a/test/std/containers/sequences/vector/asan.pass.cpp b/test/libcxx/containers/sequences/vector/asan.pass.cpp
similarity index 75%
rename from test/std/containers/sequences/vector/asan.pass.cpp
rename to test/libcxx/containers/sequences/vector/asan.pass.cpp
index 86c02b2..0a11147 100644
--- a/test/std/containers/sequences/vector/asan.pass.cpp
+++ b/test/libcxx/containers/sequences/vector/asan.pass.cpp
@@ -15,15 +15,18 @@
 #include <cassert>
 #include <cstdlib>
 
-#include "min_allocator.h"
 #include "asan_testing.h"
+#include "min_allocator.h"
+#include "test_iterators.h"
+#include "test_macros.h"
 
 #ifndef _LIBCPP_HAS_NO_ASAN
 extern "C" void __asan_set_error_exit_code(int);
 
+
 int main()
 {
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
         typedef int T;
         typedef std::vector<T, min_allocator<T>> C;
@@ -33,7 +36,18 @@
         T foo = c[c.size()];    // bad, but not caught by ASAN
     }
 #endif
-    
+
+    {
+        typedef input_iterator<int*> MyInputIter;
+        // Sould not trigger ASan.
+        std::vector<int> v;
+        v.reserve(1);
+        int i[] = {42};
+        v.insert(v.begin(), MyInputIter(i), MyInputIter(i + 1));
+        assert(v[0] == 42);
+        assert(is_contiguous_container_asan_correct(v));
+    }
+
     __asan_set_error_exit_code(0);
     {
         typedef int T;
@@ -41,7 +55,7 @@
         const T t[] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
         C c(std::begin(t), std::end(t));
         c.reserve(2*c.size());
-        assert(is_contiguous_container_asan_correct(c)); 
+        assert(is_contiguous_container_asan_correct(c));
         assert(!__sanitizer_verify_contiguous_container ( c.data(), c.data() + 1, c.data() + c.capacity()));
         T foo = c[c.size()];    // should trigger ASAN
         assert(false);          // if we got here, ASAN didn't trigger
diff --git a/test/std/containers/sequences/vector/asan_throw.pass.cc b/test/libcxx/containers/sequences/vector/asan_throw.pass.cpp
similarity index 84%
rename from test/std/containers/sequences/vector/asan_throw.pass.cc
rename to test/libcxx/containers/sequences/vector/asan_throw.pass.cpp
index a1dce4a..c100da1 100644
--- a/test/std/containers/sequences/vector/asan_throw.pass.cc
+++ b/test/libcxx/containers/sequences/vector/asan_throw.pass.cpp
@@ -37,6 +37,22 @@
   char a;
 };
 
+class ThrowOnCopy {
+public:
+    ThrowOnCopy() : should_throw(false) {}
+    explicit ThrowOnCopy(bool should_throw) : should_throw(should_throw) {}
+
+    ThrowOnCopy(ThrowOnCopy const & other)
+        : should_throw(other.should_throw)
+    {
+        if (should_throw) {
+            throw 0;
+        }
+    }
+
+    bool should_throw;
+};
+
 void test_push_back() {
   std::vector<X> v;
   v.reserve(2);
@@ -157,6 +173,23 @@
   assert(0);
 }
 
+
+void test_insert_n2() {
+  std::vector<ThrowOnCopy> v(10);
+  v.reserve(100);
+  assert(v.size() == 10);
+  v[6].should_throw = true;
+  try {
+    v.insert(v.cbegin(), 5, ThrowOnCopy());
+    assert(0);
+  } catch (int e) {
+    assert(v.size() == 11);
+    assert(is_contiguous_container_asan_correct(v));
+    return;
+  }
+  assert(0);
+}
+
 void test_resize() {
   std::vector<X> v;
   v.reserve(3);
@@ -193,6 +226,7 @@
   test_emplace();
   test_insert_range2();
   test_insert_n();
+  test_insert_n2();
   test_resize();
   test_resize_param();
 }
diff --git a/test/libcxx/containers/unord/unord.set/insert_dup_alloc.pass.cpp b/test/libcxx/containers/unord/unord.set/insert_dup_alloc.pass.cpp
new file mode 100644
index 0000000..76ceafe
--- /dev/null
+++ b/test/libcxx/containers/unord/unord.set/insert_dup_alloc.pass.cpp
@@ -0,0 +1,48 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// Check that we don't allocate when trying to insert a duplicate value into a
+// unordered_set. See PR12999 http://llvm.org/bugs/show_bug.cgi?id=12999
+
+#include <cassert>
+#include <unordered_set>
+#include "count_new.hpp"
+#include "MoveOnly.h"
+
+int main()
+{
+    {
+    std::unordered_set<int> s;
+    assert(globalMemCounter.checkNewCalledEq(0));
+
+    for(int i=0; i < 100; ++i)
+        s.insert(3);
+
+    assert(s.size() == 1);
+    assert(s.count(3) == 1);
+    assert(globalMemCounter.checkNewCalledEq(2));
+    }
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    globalMemCounter.reset();
+#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+    {
+    std::unordered_set<MoveOnly> s;
+    assert(globalMemCounter.checkNewCalledEq(0));
+
+    for(int i=0; i<100; i++)
+        s.insert(MoveOnly(3));
+
+    assert(s.size() == 1);
+    assert(s.count(MoveOnly(3)) == 1);
+    assert(globalMemCounter.checkNewCalledEq(2));
+    }
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    globalMemCounter.reset();
+#endif
+}
diff --git a/test/libcxx/double_include.sh.cpp b/test/libcxx/double_include.sh.cpp
index fd08128..5620e5b 100644
--- a/test/libcxx/double_include.sh.cpp
+++ b/test/libcxx/double_include.sh.cpp
@@ -49,6 +49,7 @@
 #include <cwctype>
 #include <deque>
 #include <exception>
+#include <experimental/algorithm>
 #include <experimental/chrono>
 #include <experimental/dynarray>
 #include <experimental/optional>
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/libcxx/experimental/algorithms/header.algorithm.synop/includes.pass.cpp
similarity index 69%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/libcxx/experimental/algorithms/header.algorithm.synop/includes.pass.cpp
index b58f5c5..accdd69 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/libcxx/experimental/algorithms/header.algorithm.synop/includes.pass.cpp
@@ -7,6 +7,14 @@
 //
 //===----------------------------------------------------------------------===//
 
+// <experimental/algorithm>
+
+#include <experimental/algorithm>
+
+#ifndef _LIBCPP_ALGORITHM
+#  error "<experimental/algorithm> must include <algorithm>"
+#endif
+
 int main()
 {
 }
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/libcxx/experimental/algorithms/version.pass.cpp
similarity index 73%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/libcxx/experimental/algorithms/version.pass.cpp
index b58f5c5..6d9d0c6 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/libcxx/experimental/algorithms/version.pass.cpp
@@ -7,6 +7,14 @@
 //
 //===----------------------------------------------------------------------===//
 
+// <experimental/algorithm>
+
+#include <experimental/algorithm>
+
+#ifndef _LIBCPP_VERSION
+#  error _LIBCPP_VERSION not defined
+#endif
+
 int main()
 {
 }
diff --git a/test/libcxx/experimental/any/size_and_alignment.pass.cpp b/test/libcxx/experimental/any/size_and_alignment.pass.cpp
new file mode 100644
index 0000000..b7db540
--- /dev/null
+++ b/test/libcxx/experimental/any/size_and_alignment.pass.cpp
@@ -0,0 +1,23 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// Check that the size and alignment of any are what we expect.
+
+#include <experimental/any>
+
+int main()
+{
+    using std::experimental::any;
+    static_assert(sizeof(any) == sizeof(void*)*4, "");
+    static_assert(alignof(any) == alignof(void*), "");
+}
diff --git a/test/libcxx/experimental/any/small_type.pass.cpp b/test/libcxx/experimental/any/small_type.pass.cpp
new file mode 100644
index 0000000..bcd15f1
--- /dev/null
+++ b/test/libcxx/experimental/any/small_type.pass.cpp
@@ -0,0 +1,40 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// Check that the size and alignment of any are what we expect.
+
+#include <experimental/any>
+#include "any_helpers.h"
+
+class SmallThrowsDtor
+{
+public:
+    SmallThrowsDtor() {}
+    SmallThrowsDtor(SmallThrowsDtor const &) noexcept {}
+    SmallThrowsDtor(SmallThrowsDtor &&) noexcept {}
+    ~SmallThrowsDtor() noexcept(false) {}
+};
+
+int main()
+{
+    using std::experimental::any;
+    using std::experimental::__any_imp::_IsSmallObject;
+    static_assert(_IsSmallObject<small>::value, "");
+    static_assert(_IsSmallObject<void*>::value, "");
+    static_assert(!_IsSmallObject<SmallThrowsDtor>::value, "");
+    static_assert(!_IsSmallObject<large>::value, "");
+    // long double is over aligned.
+    static_assert(sizeof(long double) <= sizeof(void*) * 3, "");
+    static_assert(alignof(long double) > alignof(void*), "");
+    static_assert(!_IsSmallObject<long double>::value, "");
+}
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/libcxx/experimental/any/version.pass.cpp
similarity index 75%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/libcxx/experimental/any/version.pass.cpp
index b58f5c5..611d650 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/libcxx/experimental/any/version.pass.cpp
@@ -7,6 +7,14 @@
 //
 //===----------------------------------------------------------------------===//
 
+// <experimental/any>
+
+#include <experimental/any>
+
+#ifndef _LIBCPP_VERSION
+#error _LIBCPP_VERSION not defined
+#endif
+
 int main()
 {
 }
diff --git a/test/std/containers/sequences/dynarray/dynarray.cons/alloc.pass.cpp b/test/libcxx/experimental/containers/sequences/dynarray/dynarray.cons/alloc.pass.cpp
similarity index 100%
rename from test/std/containers/sequences/dynarray/dynarray.cons/alloc.pass.cpp
rename to test/libcxx/experimental/containers/sequences/dynarray/dynarray.cons/alloc.pass.cpp
diff --git a/test/std/containers/sequences/dynarray/dynarray.cons/default.pass.cpp b/test/libcxx/experimental/containers/sequences/dynarray/dynarray.cons/default.pass.cpp
similarity index 100%
rename from test/std/containers/sequences/dynarray/dynarray.cons/default.pass.cpp
rename to test/libcxx/experimental/containers/sequences/dynarray/dynarray.cons/default.pass.cpp
diff --git a/test/std/containers/sequences/dynarray/dynarray.data/default.pass.cpp b/test/libcxx/experimental/containers/sequences/dynarray/dynarray.data/default.pass.cpp
similarity index 100%
rename from test/std/containers/sequences/dynarray/dynarray.data/default.pass.cpp
rename to test/libcxx/experimental/containers/sequences/dynarray/dynarray.data/default.pass.cpp
diff --git a/test/std/containers/sequences/dynarray/dynarray.mutate/default.pass.cpp b/test/libcxx/experimental/containers/sequences/dynarray/dynarray.mutate/default.pass.cpp
similarity index 100%
rename from test/std/containers/sequences/dynarray/dynarray.mutate/default.pass.cpp
rename to test/libcxx/experimental/containers/sequences/dynarray/dynarray.mutate/default.pass.cpp
diff --git a/test/std/containers/sequences/dynarray/dynarray.overview/at.pass.cpp b/test/libcxx/experimental/containers/sequences/dynarray/dynarray.overview/at.pass.cpp
similarity index 100%
rename from test/std/containers/sequences/dynarray/dynarray.overview/at.pass.cpp
rename to test/libcxx/experimental/containers/sequences/dynarray/dynarray.overview/at.pass.cpp
diff --git a/test/std/containers/sequences/dynarray/dynarray.overview/begin_end.pass.cpp b/test/libcxx/experimental/containers/sequences/dynarray/dynarray.overview/begin_end.pass.cpp
similarity index 100%
rename from test/std/containers/sequences/dynarray/dynarray.overview/begin_end.pass.cpp
rename to test/libcxx/experimental/containers/sequences/dynarray/dynarray.overview/begin_end.pass.cpp
diff --git a/test/std/containers/sequences/dynarray/dynarray.overview/capacity.pass.cpp b/test/libcxx/experimental/containers/sequences/dynarray/dynarray.overview/capacity.pass.cpp
similarity index 100%
rename from test/std/containers/sequences/dynarray/dynarray.overview/capacity.pass.cpp
rename to test/libcxx/experimental/containers/sequences/dynarray/dynarray.overview/capacity.pass.cpp
diff --git a/test/std/containers/sequences/dynarray/dynarray.overview/front_back.pass.cpp b/test/libcxx/experimental/containers/sequences/dynarray/dynarray.overview/front_back.pass.cpp
similarity index 100%
rename from test/std/containers/sequences/dynarray/dynarray.overview/front_back.pass.cpp
rename to test/libcxx/experimental/containers/sequences/dynarray/dynarray.overview/front_back.pass.cpp
diff --git a/test/std/containers/sequences/dynarray/dynarray.overview/indexing.pass.cpp b/test/libcxx/experimental/containers/sequences/dynarray/dynarray.overview/indexing.pass.cpp
similarity index 100%
rename from test/std/containers/sequences/dynarray/dynarray.overview/indexing.pass.cpp
rename to test/libcxx/experimental/containers/sequences/dynarray/dynarray.overview/indexing.pass.cpp
diff --git a/test/std/containers/sequences/dynarray/dynarray.traits/default.pass.cpp b/test/libcxx/experimental/containers/sequences/dynarray/dynarray.traits/default.pass.cpp
similarity index 100%
rename from test/std/containers/sequences/dynarray/dynarray.traits/default.pass.cpp
rename to test/libcxx/experimental/containers/sequences/dynarray/dynarray.traits/default.pass.cpp
diff --git a/test/std/containers/sequences/dynarray/dynarray.zero/default.pass.cpp b/test/libcxx/experimental/containers/sequences/dynarray/dynarray.zero/default.pass.cpp
similarity index 100%
rename from test/std/containers/sequences/dynarray/dynarray.zero/default.pass.cpp
rename to test/libcxx/experimental/containers/sequences/dynarray/dynarray.zero/default.pass.cpp
diff --git a/test/std/containers/sequences/dynarray/nothing_to_do.pass.cpp b/test/libcxx/experimental/containers/sequences/dynarray/nothing_to_do.pass.cpp
similarity index 100%
rename from test/std/containers/sequences/dynarray/nothing_to_do.pass.cpp
rename to test/libcxx/experimental/containers/sequences/dynarray/nothing_to_do.pass.cpp
diff --git a/test/libcxx/experimental/utilities/ratio/header.ratio.synop/includes.pass.cpp b/test/libcxx/experimental/utilities/ratio/header.ratio.synop/includes.pass.cpp
index 2ab3449..db9026a 100644
--- a/test/libcxx/experimental/utilities/ratio/header.ratio.synop/includes.pass.cpp
+++ b/test/libcxx/experimental/utilities/ratio/header.ratio.synop/includes.pass.cpp
@@ -13,7 +13,7 @@
 
 #include <experimental/ratio>
 
-#ifndef _LIBCPP_STD_VER > 11
+#if _LIBCPP_STD_VER > 11
 # ifndef _LIBCPP_RATIO
 #   error " <experimental/ratio> must include <ratio>"
 # endif
diff --git a/test/libcxx/experimental/utilities/syserror/header.system_error.synop/includes.pass.cpp b/test/libcxx/experimental/utilities/syserror/header.system_error.synop/includes.pass.cpp
index 57cbb73..88c7458 100644
--- a/test/libcxx/experimental/utilities/syserror/header.system_error.synop/includes.pass.cpp
+++ b/test/libcxx/experimental/utilities/syserror/header.system_error.synop/includes.pass.cpp
@@ -11,7 +11,7 @@
 
 #include <experimental/system_error>
 
-#ifndef _LIBCPP_STD_VER > 11
+#if _LIBCPP_STD_VER > 11
 # ifndef _LIBCPP_SYSTEM_ERROR
 #   error "<experimental/system_error> must include <system_error>"
 # endif
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/libcxx/experimental/utilities/tuple/header.tuple.synop/includes.pass.cpp
similarity index 64%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/libcxx/experimental/utilities/tuple/header.tuple.synop/includes.pass.cpp
index b58f5c5..544ddfb 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/libcxx/experimental/utilities/tuple/header.tuple.synop/includes.pass.cpp
@@ -7,6 +7,15 @@
 //
 //===----------------------------------------------------------------------===//
 
+// <experimental/tuple>
+
+#include <experimental/tuple>
+
 int main()
 {
+#if _LIBCPP_STD_VER > 11
+# ifndef _LIBCPP_TUPLE
+#   error "<experimental/tuple> must include <tuple>"
+# endif
+#endif /* _LIBCPP_STD_VER > 11 */
 }
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/libcxx/experimental/utilities/tuple/version.pass.cpp
similarity index 74%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/libcxx/experimental/utilities/tuple/version.pass.cpp
index b58f5c5..5a3fd2e 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/libcxx/experimental/utilities/tuple/version.pass.cpp
@@ -7,6 +7,14 @@
 //
 //===----------------------------------------------------------------------===//
 
+// <experimental/tuple>
+
+#include <experimental/tuple>
+
+#ifndef _LIBCPP_VERSION
+#error _LIBCPP_VERSION not defined
+#endif
+
 int main()
 {
 }
diff --git a/test/libcxx/selftest/test_macros.pass.cpp b/test/libcxx/selftest/test_macros.pass.cpp
new file mode 100644
index 0000000..2c8ed4f
--- /dev/null
+++ b/test/libcxx/selftest/test_macros.pass.cpp
@@ -0,0 +1,58 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// Test the "test_macros.h" header.
+#include "test_macros.h"
+
+#ifndef TEST_STD_VER
+#error TEST_STD_VER must be defined
+#endif
+
+#ifndef TEST_DECLTYPE
+#error TEST_DECLTYPE must be defined
+#endif
+
+#ifndef TEST_NOEXCEPT
+#error TEST_NOEXCEPT must be defined
+#endif
+
+#ifndef TEST_STATIC_ASSERT
+#error TEST_STATIC_ASSERT must be defined
+#endif
+
+template <class T, class U>
+struct is_same { enum { value = 0 }; };
+
+template <class T>
+struct is_same<T, T> { enum { value = 1 }; };
+
+int foo() { return 0; }
+
+void test_noexcept() TEST_NOEXCEPT
+{
+}
+
+void test_decltype()
+{
+  typedef TEST_DECLTYPE(foo()) MyType;
+  TEST_STATIC_ASSERT((is_same<MyType, int>::value), "is same");
+}
+
+void test_static_assert()
+{
+    TEST_STATIC_ASSERT((is_same<int, int>::value), "is same");
+    TEST_STATIC_ASSERT((!is_same<int, long>::value), "not same");
+}
+
+int main()
+{
+    test_noexcept();
+    test_decltype();
+    test_static_assert();
+}
diff --git a/test/libcxx/test/config.py b/test/libcxx/test/config.py
index 6bf1d60..502b688 100644
--- a/test/libcxx/test/config.py
+++ b/test/libcxx/test/config.py
@@ -52,6 +52,7 @@
         self.libcxx_src_root = None
         self.libcxx_obj_root = None
         self.cxx_library_root = None
+        self.abi_library_root = None
         self.env = {}
         self.use_target = False
         self.use_system_cxx_lib = False
@@ -90,13 +91,14 @@
         self.configure_use_clang_verify()
         self.configure_execute_external()
         self.configure_ccache()
-        self.configure_env()
         self.configure_compile_flags()
         self.configure_link_flags()
+        self.configure_env()
         self.configure_color_diagnostics()
         self.configure_debug_mode()
         self.configure_warnings()
         self.configure_sanitizer()
+        self.configure_coverage()
         self.configure_substitutions()
         self.configure_features()
 
@@ -199,8 +201,10 @@
         '''If set, run clang with -verify on failing tests.'''
         self.use_clang_verify = self.get_lit_bool('use_clang_verify')
         if self.use_clang_verify is None:
-            # TODO: Default this to True when using clang.
-            self.use_clang_verify = False
+            # NOTE: We do not test for the -verify flag directly because
+            #   -verify will always exit with non-zero on an empty file.
+            self.use_clang_verify = self.cxx.hasCompileFlag(
+                ['-Xclang', '-verify-ignore-unexpected'])
             self.lit_config.note(
                 "inferred use_clang_verify as: %r" % self.use_clang_verify)
 
@@ -221,7 +225,8 @@
         self.execute_external = not use_lit_shell
 
     def configure_ccache(self):
-        use_ccache = self.get_lit_bool('use_ccache', False)
+        use_ccache_default = os.environ.get('LIBCXX_USE_CCACHE') is not None
+        use_ccache = self.get_lit_bool('use_ccache', use_ccache_default)
         if use_ccache:
             self.cxx.use_ccache = True
             self.lit_config.note('enabling ccache')
@@ -322,6 +327,11 @@
         if self.long_tests:
             self.config.available_features.add('long_tests')
 
+        # Run a compile test for the -fsized-deallocation flag. This is needed
+        # in test/std/language.support/support.dynamic/new.delete
+        if self.cxx.hasCompileFlag('-fsized-deallocation'):
+            self.config.available_features.add('fsized-deallocation')
+
     def configure_compile_flags(self):
         no_default_flags = self.get_lit_bool('no_default_flags', False)
         if not no_default_flags:
@@ -347,6 +357,9 @@
         # Configure feature flags.
         self.configure_compile_flags_exceptions()
         self.configure_compile_flags_rtti()
+        self.configure_compile_flags_no_global_filesystem_namespace()
+        self.configure_compile_flags_no_stdin()
+        self.configure_compile_flags_no_stdout()
         enable_32bit = self.get_lit_bool('enable_32bit', False)
         if enable_32bit:
             self.cxx.flags += ['-m32']
@@ -361,6 +374,8 @@
         elif not enable_monotonic_clock:
             self.lit_config.fatal('enable_monotonic_clock cannot be false when'
                                   ' enable_threads is true.')
+        self.configure_compile_flags_no_thread_unsafe_c_functions()
+
         # Use verbose output for better errors
         self.cxx.flags += ['-v']
         sysroot = self.get_lit_conf('sysroot')
@@ -372,15 +387,6 @@
         if self.use_target:
             self.cxx.flags += ['-target', self.config.target_triple]
 
-        sysroot = self.get_lit_conf('sysroot')
-        if sysroot:
-            self.compile_flags += ['--sysroot', sysroot]
-        gcc_toolchain = self.get_lit_conf('gcc_toolchain')
-        if gcc_toolchain:
-            self.compile_flags += ['-gcc-toolchain', gcc_toolchain]
-
-        self.compile_flags += ['-target', self.config.target_triple]
-
     def configure_compile_flags_header_includes(self):
         support_path = os.path.join(self.libcxx_src_root, 'test/support')
         self.cxx.compile_flags += ['-I' + support_path]
@@ -404,10 +410,40 @@
             self.config.available_features.add('libcpp-no-rtti')
             self.cxx.compile_flags += ['-fno-rtti', '-D_LIBCPP_NO_RTTI']
 
+    def configure_compile_flags_no_global_filesystem_namespace(self):
+        enable_global_filesystem_namespace = self.get_lit_bool(
+            'enable_global_filesystem_namespace', True)
+        if not enable_global_filesystem_namespace:
+            self.config.available_features.add(
+                'libcpp-has-no-global-filesystem-namespace')
+            self.cxx.compile_flags += [
+                '-D_LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE']
+
+    def configure_compile_flags_no_stdin(self):
+        enable_stdin = self.get_lit_bool('enable_stdin', True)
+        if not enable_stdin:
+            self.config.available_features.add('libcpp-has-no-stdin')
+            self.cxx.compile_flags += ['-D_LIBCPP_HAS_NO_STDIN']
+
+    def configure_compile_flags_no_stdout(self):
+        enable_stdout = self.get_lit_bool('enable_stdout', True)
+        if not enable_stdout:
+            self.config.available_features.add('libcpp-has-no-stdout')
+            self.cxx.compile_flags += ['-D_LIBCPP_HAS_NO_STDOUT']
+
     def configure_compile_flags_no_threads(self):
         self.cxx.compile_flags += ['-D_LIBCPP_HAS_NO_THREADS']
         self.config.available_features.add('libcpp-has-no-threads')
 
+    def configure_compile_flags_no_thread_unsafe_c_functions(self):
+        enable_thread_unsafe_c_functions = self.get_lit_bool(
+            'enable_thread_unsafe_c_functions', True)
+        if not enable_thread_unsafe_c_functions:
+            self.cxx.compile_flags += [
+                '-D_LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS']
+            self.config.available_features.add(
+                'libcpp-has-no-thread-unsafe-c-functions')
+
     def configure_compile_flags_no_monotonic_clock(self):
         self.cxx.compile_flags += ['-D_LIBCPP_HAS_NO_MONOTONIC_CLOCK']
         self.config.available_features.add('libcpp-has-no-monotonic-clock')
@@ -450,10 +486,10 @@
 
     def configure_link_flags_abi_library_path(self):
         # Configure ABI library paths.
-        abi_library_path = self.get_lit_conf('abi_library_path', '')
-        if abi_library_path:
-            self.cxx.link_flags += ['-L' + abi_library_path,
-                                    '-Wl,-rpath,' + abi_library_path]
+        self.abi_library_root = self.get_lit_conf('abi_library_path')
+        if self.abi_library_root:
+            self.cxx.link_flags += ['-L' + self.abi_library_root,
+                                    '-Wl,-rpath,' + self.abi_library_root]
 
     def configure_link_flags_cxx_library(self):
         libcxx_library = self.get_lit_conf('libcxx_library')
@@ -499,7 +535,7 @@
             else:
                 self.cxx.link_flags += ['-lgcc_s']
         elif target_platform.startswith('freebsd'):
-            self.cxx.link_flags += ['-lc', '-lm', '-lpthread', '-lgcc_s']
+            self.cxx.link_flags += ['-lc', '-lm', '-lpthread', '-lgcc_s', '-lcxxrt']
         else:
             self.lit_config.fatal("unrecognized system: %r" % target_platform)
 
@@ -512,7 +548,15 @@
         if use_color != '':
             self.lit_config.fatal('Invalid value for color_diagnostics "%s".'
                                   % use_color)
-        self.cxx.flags += ['-fdiagnostics-color=always']
+        color_flag = '-fdiagnostics-color=always'
+        # Check if the compiler supports the color diagnostics flag. Issue a
+        # warning if it does not since color diagnostics have been requested.
+        if not self.cxx.hasCompileFlag(color_flag):
+            self.lit_config.warning(
+                'color diagnostics have been requested but are not supported '
+                'by the compiler')
+        else:
+            self.cxx.flags += [color_flag]
 
     def configure_debug_mode(self):
         debug_level = self.get_lit_conf('debug_level', None)
@@ -526,10 +570,20 @@
     def configure_warnings(self):
         enable_warnings = self.get_lit_bool('enable_warnings', False)
         if enable_warnings:
-            self.cxx.compile_flags += ['-Wsystem-headers', '-Wall', '-Werror']
-            if ('clang' in self.config.available_features or
-                'apple-clang' in self.config.available_features):
-                self.cxx.compile_flags += ['-Wno-user-defined-literals']
+            self.cxx.compile_flags += [
+                '-D_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER',
+                '-Wall', '-Werror'
+            ]
+            self.cxx.addCompileFlagIfSupported('-Wno-attributes')
+            if self.cxx.type == 'clang' or self.cxx.type == 'apple-clang':
+                self.cxx.addCompileFlagIfSupported('-Wno-pessimizing-move')
+                self.cxx.addCompileFlagIfSupported('-Wno-c++11-extensions')
+                self.cxx.addCompileFlagIfSupported('-Wno-user-defined-literals')
+            std = self.get_lit_conf('std', None)
+            if std in ['c++98', 'c++03']:
+                # The '#define static_assert' provided by libc++ in C++03 mode
+                # causes an unused local typedef whenever it is used.
+                self.cxx.addCompileFlagIfSupported('-Wno-unused-local-typedef')
 
     def configure_sanitizer(self):
         san = self.get_lit_conf('use_sanitizer', '').strip()
@@ -553,6 +607,7 @@
                 if llvm_symbolizer is not None:
                     self.env['ASAN_SYMBOLIZER_PATH'] = llvm_symbolizer
                 self.config.available_features.add('asan')
+                self.config.available_features.add('sanitizer-new-delete')
             elif san == 'Memory' or san == 'MemoryWithOrigins':
                 self.cxx.flags += ['-fsanitize=memory']
                 if san == 'MemoryWithOrigins':
@@ -561,18 +616,32 @@
                 if llvm_symbolizer is not None:
                     self.env['MSAN_SYMBOLIZER_PATH'] = llvm_symbolizer
                 self.config.available_features.add('msan')
+                self.config.available_features.add('sanitizer-new-delete')
             elif san == 'Undefined':
                 self.cxx.flags += ['-fsanitize=undefined',
                                    '-fno-sanitize=vptr,function',
                                    '-fno-sanitize-recover']
                 self.cxx.compile_flags += ['-O3']
                 self.config.available_features.add('ubsan')
+                if self.target_info.platform() == 'darwin':
+                    self.config.available_features.add('sanitizer-new-delete')
             elif san == 'Thread':
                 self.cxx.flags += ['-fsanitize=thread']
                 self.config.available_features.add('tsan')
+                self.config.available_features.add('sanitizer-new-delete')
             else:
                 self.lit_config.fatal('unsupported value for '
                                       'use_sanitizer: {0}'.format(san))
+            san_lib = self.get_lit_conf('sanitizer_library')
+            if san_lib:
+                self.cxx.link_flags += [
+                    san_lib, '-Wl,-rpath,%s' % os.path.dirname(san_lib)]
+
+    def configure_coverage(self):
+        self.generate_coverage = self.get_lit_bool('generate_coverage', False)
+        if self.generate_coverage:
+            self.cxx.flags += ['-g', '--coverage']
+            self.cxx.compile_flags += ['-O0']
 
     def configure_substitutions(self):
         sub = self.config.substitutions
@@ -639,12 +708,18 @@
                 "inferred target_triple as: %r" % self.config.target_triple)
 
     def configure_env(self):
-        if (self.target_info.platform() == 'darwin' and
-            not self.use_system_cxx_lib):
+        if self.target_info.platform() == 'darwin':
+            library_paths = []
+            # Configure the library path for libc++
             libcxx_library = self.get_lit_conf('libcxx_library')
-            if libcxx_library:
-                cxx_library_root = os.path.dirname(libcxx_library)
-            else:
-                cxx_library_root = self.cxx_library_root
-            if cxx_library_root:
-                self.env['DYLD_LIBRARY_PATH'] = cxx_library_root
+            if self.use_system_cxx_lib:
+                pass
+            elif libcxx_library:
+                library_paths += [os.path.dirname(libcxx_library)]
+            elif self.cxx_library_root:
+                library_paths += [self.cxx_library_root]
+            # Configure the abi library path
+            if self.abi_library_root:
+                library_paths += [self.abi_library_root]
+            if library_paths:
+                self.env['DYLD_LIBRARY_PATH'] = ':'.join(library_paths)
diff --git a/test/libcxx/test/executor.py b/test/libcxx/test/executor.py
index 492f934..f0356ce 100644
--- a/test/libcxx/test/executor.py
+++ b/test/libcxx/test/executor.py
@@ -17,7 +17,7 @@
             file_deps: [str]: Files required by the test
             env: {str: str}:  Environment variables to execute under
         Returns:
-            out, err, exitCode
+            cmd, out, err, exitCode
         """
         raise NotImplementedError
 
@@ -34,7 +34,8 @@
             env_cmd += ['%s=%s' % (k, v) for k, v in env.items()]
         if work_dir == '.':
             work_dir = os.getcwd()
-        return executeCommand(env_cmd + cmd, cwd=work_dir)
+        out, err, rc = executeCommand(env_cmd + cmd, cwd=work_dir)
+        return (env_cmd + cmd, out, err, rc)
 
 
 class PrefixExecutor(Executor):
@@ -129,6 +130,9 @@
                 srcs.extend(file_deps)
                 dsts.extend(dev_paths)
             self.copy_in(srcs, dsts)
+            # TODO(jroelofs): capture the copy_in and delete_remote commands,
+            # and conjugate them with '&&'s around the first tuple element
+            # returned here:
             return self._execute_command_remote(cmd, target_cwd, env)
         finally:
             if target_cwd:
diff --git a/test/libcxx/test/format.py b/test/libcxx/test/format.py
index 921f02b..238dcdb 100644
--- a/test/libcxx/test/format.py
+++ b/test/libcxx/test/format.py
@@ -6,6 +6,7 @@
 import lit.TestRunner  # pylint: disable=import-error
 import lit.util        # pylint: disable=import-error
 
+from libcxx.test.executor import LocalExecutor as LocalExecutor
 import libcxx.util
 
 
@@ -59,6 +60,10 @@
         is_pass_test = name.endswith('.pass.cpp')
         is_fail_test = name.endswith('.fail.cpp')
 
+        if test.config.unsupported:
+            return (lit.Test.UNSUPPORTED,
+                    "A lit.local.cfg marked this unsupported")
+
         res = lit.TestRunner.parseIntegratedTestScript(
             test, require_script=is_sh_test)
         # Check if a result for the test was returned. If so return that
@@ -75,7 +80,7 @@
 
         # Dispatch the test based on its suffix.
         if is_sh_test:
-            if self.executor:
+            if not isinstance(self.executor, LocalExecutor):
                 # We can't run ShTest tests with a executor yet.
                 # For now, bail on trying to run them
                 return lit.Test.UNSUPPORTED, 'ShTest format not yet supported'
@@ -120,8 +125,8 @@
             # should add a `// FILE-DEP: foo.dat` to each test to track this.
             data_files = [os.path.join(local_cwd, f)
                           for f in os.listdir(local_cwd) if f.endswith('.dat')]
-            out, err, rc = self.executor.run(exec_path, [exec_path],
-                                             local_cwd, data_files, env)
+            cmd, out, err, rc = self.executor.run(exec_path, [exec_path],
+                                                  local_cwd, data_files, env)
             if rc != 0:
                 report = libcxx.util.makeReport(cmd, out, err, rc)
                 report = "Compiled With: %s\n%s" % (compile_cmd, report)
@@ -136,13 +141,16 @@
 
     def _evaluate_fail_test(self, test):
         source_path = test.getSourcePath()
-        # TODO: Move the checking of USE_VERIFY into
-        # lit.TestRunner.parseIntegratedTestScript by adding support for custom
-        # tags.
         with open(source_path, 'r') as f:
             contents = f.read()
-        use_verify = 'USE_VERIFY' in contents and self.use_verify_for_fail
-        extra_flags = ['-Xclang', '-verify'] if use_verify else []
+        verify_tags = ['expected-note', 'expected-remark', 'expected-warning',
+                       'expected-error', 'expected-no-diagnostics']
+        use_verify = self.use_verify_for_fail and \
+                     any([tag in contents for tag in verify_tags])
+        extra_flags = []
+        if use_verify:
+            extra_flags += ['-Xclang', '-verify',
+                            '-Xclang', '-verify-ignore-unexpected=note']
         cmd, out, err, rc = self.cxx.compile(source_path, out=os.devnull,
                                              flags=extra_flags)
         expected_rc = 0 if use_verify else 1
@@ -150,5 +158,6 @@
             return lit.Test.PASS, ''
         else:
             report = libcxx.util.makeReport(cmd, out, err, rc)
-            return (lit.Test.FAIL,
-                    report + 'Expected compilation to fail!\n')
+            report_msg = ('Expected compilation to fail!' if not use_verify else
+                          'Expected compilation using verify to pass!')
+            return lit.Test.FAIL, report + report_msg + '\n'
diff --git a/test/libcxx/type_traits/convert_to_integral.pass.cpp b/test/libcxx/type_traits/convert_to_integral.pass.cpp
index 37060a0..b97832b 100644
--- a/test/libcxx/type_traits/convert_to_integral.pass.cpp
+++ b/test/libcxx/type_traits/convert_to_integral.pass.cpp
@@ -1,4 +1,7 @@
 
+// TODO: Make this test pass for all standards.
+// XFAIL: c++98, c++03
+
 #include <limits>
 #include <type_traits>
 #include <cstdint>
@@ -57,7 +60,7 @@
 }
 
 
-enum enum1 {};
+enum enum1 { zero = 0, one = 1 };
 enum enum2 {
   value = std::numeric_limits<unsigned long>::max()
 };
diff --git a/test/libcxx/utilities/memory/util.smartptr/race_condition.pass.cpp b/test/libcxx/utilities/memory/util.smartptr/race_condition.pass.cpp
new file mode 100644
index 0000000..25dd311
--- /dev/null
+++ b/test/libcxx/utilities/memory/util.smartptr/race_condition.pass.cpp
@@ -0,0 +1,94 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: libcpp-has-no-threads
+//
+// <memory>
+//
+// class shared_ptr
+//
+// This test attempts to create a race condition surrounding use_count()
+// with the hope that TSAN will diagnose it.
+
+#include <memory>
+#include <atomic>
+#include <thread>
+#include <cassert>
+
+typedef std::shared_ptr<int> Ptr;
+typedef std::weak_ptr<int> WeakPtr;
+
+std::atomic_bool Start;
+std::atomic_bool KeepRunning;
+
+struct TestRunner {
+    TestRunner(Ptr xx) : x(xx) {}
+    void operator()() {
+        while (Start == false) {}
+        while (KeepRunning) {
+            // loop to prevent always checking the atomic.
+            for (int i=0; i < 100000; ++i) {
+                Ptr x2 = x; // increment shared count
+                WeakPtr x3 = x; // increment weak count
+                Ptr x4 = x3.lock(); // increment shared count via lock
+                WeakPtr x5 = x3; // increment weak count
+            }
+        }
+    }
+    Ptr x;
+};
+
+void run_test(Ptr p) {
+    Start = false;
+    KeepRunning = true;
+    assert(p.use_count() == 2);
+    TestRunner r(p);
+    assert(p.use_count() == 3);
+    std::thread t1(r); // Start the test thread.
+    assert(p.use_count() == 4);
+    Start = true;
+    // Run until we witness 25 use count changes via both
+    // shared and weak pointer methods.
+    WeakPtr w = p;
+    int shared_changes_count = 0;
+    int weak_changes_count = 0;
+    while (shared_changes_count < 25 && weak_changes_count < 25) {
+        // check use_count on the shared_ptr
+       int last = p.use_count();
+       int new_val = p.use_count();
+       assert(last >= 4);
+       assert(new_val >= 4);
+       if (last != new_val) ++shared_changes_count;
+       // Check use_count on the weak_ptr
+       last = w.use_count();
+       new_val = w.use_count();
+       assert(last >= 4);
+       assert(new_val >= 4);
+       if (last != new_val) ++weak_changes_count;
+    }
+    // kill the test thread.
+    KeepRunning = false;
+    t1.join();
+    assert(p.use_count() == 3);
+}
+
+int main() {
+  {
+    // Test with out-of-place shared_count.
+    Ptr p(new int(42));
+    run_test(p);
+    assert(p.use_count() == 1);
+  }
+  {
+    // Test with in-place shared_count.
+    Ptr p = std::make_shared<int>(42);
+    run_test(p);
+    assert(p.use_count() == 1);
+  }
+}
diff --git a/test/lit.site.cfg.in b/test/lit.site.cfg.in
index 5a4445b..765ee7c 100644
--- a/test/lit.site.cfg.in
+++ b/test/lit.site.cfg.in
@@ -1,6 +1,5 @@
 @AUTO_GEN_COMMENT@
 config.cxx_under_test           = "@LIBCXX_COMPILER@"
-config.std                      = "@LIBCXX_STD_VERSION@"
 config.libcxx_src_root          = "@LIBCXX_SOURCE_DIR@"
 config.libcxx_obj_root          = "@LIBCXX_BINARY_DIR@"
 config.cxx_library_root         = "@LIBCXX_LIBRARY_DIR@"
@@ -8,17 +7,24 @@
 config.enable_rtti              = "@LIBCXX_ENABLE_RTTI@"
 config.enable_shared            = "@LIBCXX_ENABLE_SHARED@"
 config.enable_32bit             = "@LIBCXX_BUILD_32_BITS@"
+config.enable_global_filesystem_namespace = "@LIBCXX_ENABLE_GLOBAL_FILESYSTEM_NAMESPACE@"
+config.enable_stdin             = "@LIBCXX_ENABLE_STDIN@"
+config.enable_stdout            = "@LIBCXX_ENABLE_STDOUT@"
 config.enable_threads           = "@LIBCXX_ENABLE_THREADS@"
+config.enable_thread_unsafe_c_functions = "@LIBCXX_ENABLE_THREAD_UNSAFE_C_FUNCTIONS@"
 config.enable_monotonic_clock   = "@LIBCXX_ENABLE_MONOTONIC_CLOCK@"
 config.cxx_abi                  = "@LIBCXX_CXX_ABI_LIBNAME@"
 config.use_sanitizer            = "@LLVM_USE_SANITIZER@"
+config.sanitizer_library        = "@LIBCXX_SANITIZER_LIBRARY@"
 config.abi_library_path         = "@LIBCXX_CXX_ABI_LIBRARY_PATH@"
 config.configuration_variant    = "@LIBCXX_LIT_VARIANT@"
 config.target_triple            = "@LIBCXX_TARGET_TRIPLE@"
 config.sysroot                  = "@LIBCXX_SYSROOT@"
 config.gcc_toolchain            = "@LIBCXX_GCC_TOOLCHAIN@"
+config.generate_coverage        = "@LIBCXX_GENERATE_COVERAGE@"
 config.target_info              = "@LIBCXX_TARGET_INFO@"
 config.executor                 = "@LIBCXX_EXECUTOR@"
+config.llvm_unwinder            = "@LIBCXXABI_USE_LLVM_UNWINDER@"
 
 # Let the main config do the real work.
 lit_config.load_config(config, "@LIBCXX_SOURCE_DIR@/test/lit.cfg")
diff --git a/test/std/algorithms/alg.modifying.operations/alg.partitions/stable_partition.pass.cpp b/test/std/algorithms/alg.modifying.operations/alg.partitions/stable_partition.pass.cpp
index 7810dec..cf23c77 100644
--- a/test/std/algorithms/alg.modifying.operations/alg.partitions/stable_partition.pass.cpp
+++ b/test/std/algorithms/alg.modifying.operations/alg.partitions/stable_partition.pass.cpp
@@ -17,10 +17,9 @@
 
 #include <algorithm>
 #include <cassert>
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 #include <memory>
-#endif
 
+#include "test_macros.h"
 #include "test_iterators.h"
 
 struct is_odd
@@ -283,7 +282,7 @@
     }
 }
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#if TEST_STD_VER >= 11
 
 struct is_null
 {
@@ -298,9 +297,10 @@
     const unsigned size = 5;
     std::unique_ptr<int> array[size];
     Iter r = std::stable_partition(Iter(array), Iter(array+size), is_null());
+    assert(r == Iter(array+size));
 }
 
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#endif  // TEST_STD_VER >= 11
 
 int main()
 {
@@ -308,7 +308,7 @@
     test<random_access_iterator<std::pair<int,int>*> >();
     test<std::pair<int,int>*>();
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#if TEST_STD_VER >= 11
     test1<bidirectional_iterator<std::unique_ptr<int>*> >();
 #endif
 }
diff --git a/test/std/algorithms/alg.nonmodifying/mismatch/mismatch.pass.cpp b/test/std/algorithms/alg.nonmodifying/mismatch/mismatch.pass.cpp
index abc89dc..eb37cca 100644
--- a/test/std/algorithms/alg.nonmodifying/mismatch/mismatch.pass.cpp
+++ b/test/std/algorithms/alg.nonmodifying/mismatch/mismatch.pass.cpp
@@ -17,18 +17,16 @@
 #include <algorithm>
 #include <cassert>
 
+#include "test_macros.h"
 #include "test_iterators.h"
 
-#if _LIBCPP_STD_VER > 11
-#define HAS_FOUR_ITERATOR_VERSION
-#endif
 
 int main()
 {
     int ia[] = {0, 1, 2, 2, 0, 1, 2, 3};
     const unsigned sa = sizeof(ia)/sizeof(ia[0]);
     int ib[] = {0, 1, 2, 3, 0, 1, 2, 3};
-    const unsigned sb = sizeof(ib)/sizeof(ib[0]);
+    const unsigned sb = sizeof(ib)/sizeof(ib[0]); ((void)sb); // unused in c++11
 
     typedef input_iterator<const int*> II;
     typedef random_access_iterator<const int*>  RAI;
@@ -39,7 +37,7 @@
     assert(std::mismatch(RAI(ia), RAI(ia + sa), RAI(ib))
             == (std::pair<RAI, RAI>(RAI(ia+3), RAI(ib+3))));
 
-#ifdef HAS_FOUR_ITERATOR_VERSION
+#if TEST_STD_VER > 11 // We have the four iteration version
     assert(std::mismatch(II(ia), II(ia + sa), II(ib), II(ib+sb))
             == (std::pair<II, II>(II(ia+3), II(ib+3))));
 
diff --git a/test/std/algorithms/alg.nonmodifying/mismatch/mismatch_pred.pass.cpp b/test/std/algorithms/alg.nonmodifying/mismatch/mismatch_pred.pass.cpp
index 8d85d99..3e1dfd1 100644
--- a/test/std/algorithms/alg.nonmodifying/mismatch/mismatch_pred.pass.cpp
+++ b/test/std/algorithms/alg.nonmodifying/mismatch/mismatch_pred.pass.cpp
@@ -19,10 +19,11 @@
 #include <functional>
 #include <cassert>
 
+#include "test_macros.h"
 #include "test_iterators.h"
 #include "counting_predicates.hpp"
 
-#if _LIBCPP_STD_VER > 11
+#if TEST_STD_VER > 11
 #define HAS_FOUR_ITERATOR_VERSION
 #endif
 
@@ -31,7 +32,7 @@
     int ia[] = {0, 1, 2, 2, 0, 1, 2, 3};
     const unsigned sa = sizeof(ia)/sizeof(ia[0]);
     int ib[] = {0, 1, 2, 3, 0, 1, 2, 3};
-    const unsigned sb = sizeof(ib)/sizeof(ib[0]);
+    const unsigned sb = sizeof(ib)/sizeof(ib[0]); ((void)sb); // unused in c++11
     
     typedef input_iterator<const int*> II;
     typedef random_access_iterator<const int*>  RAI;
diff --git a/test/std/algorithms/alg.sorting/alg.merge/inplace_merge.pass.cpp b/test/std/algorithms/alg.sorting/alg.merge/inplace_merge.pass.cpp
index 01db088..8291573 100644
--- a/test/std/algorithms/alg.sorting/alg.merge/inplace_merge.pass.cpp
+++ b/test/std/algorithms/alg.sorting/alg.merge/inplace_merge.pass.cpp
@@ -20,12 +20,35 @@
 
 #include "test_iterators.h"
 
+#if TEST_STD_VER >= 11
+struct S {
+	S() : i_(0) {}
+	S(int i) : i_(i) {}
+	
+	S(const S&  rhs) : i_(rhs.i_) {}
+	S(      S&& rhs) : i_(rhs.i_) { rhs.i_ = -1; }
+	
+	S& operator =(const S&  rhs) { i_ = rhs.i_;              return *this; }
+	S& operator =(      S&& rhs) { i_ = rhs.i_; rhs.i_ = -2; assert(this != &rhs); return *this; }
+	S& operator =(int i)         { i_ = i;                   return *this; }
+	
+	bool operator  <(const S&  rhs) const { return i_ < rhs.i_; }
+	bool operator ==(const S&  rhs) const { return i_ == rhs.i_; }
+	bool operator ==(int i)         const { return i_ == i; }
+
+	void set(int i) { i_ = i; }
+	
+	int i_;
+	};
+#endif
+
 template <class Iter>
 void
 test_one(unsigned N, unsigned M)
 {
+    typedef typename std::iterator_traits<Iter>::value_type value_type;
     assert(M <= N);
-    int* ia = new int[N];
+    value_type* ia = new value_type[N];
     for (unsigned i = 0; i < N; ++i)
         ia[i] = i;
     std::random_shuffle(ia, ia+N);
@@ -76,4 +99,10 @@
     test<bidirectional_iterator<int*> >();
     test<random_access_iterator<int*> >();
     test<int*>();
+
+#if TEST_STD_VER >= 11
+    test<bidirectional_iterator<S*> >();
+    test<random_access_iterator<S*> >();
+    test<S*>();
+#endif  // TEST_STD_VER >= 11
 }
diff --git a/test/std/algorithms/alg.sorting/alg.merge/inplace_merge_comp.pass.cpp b/test/std/algorithms/alg.sorting/alg.merge/inplace_merge_comp.pass.cpp
index b54efb6..ca6f8e4 100644
--- a/test/std/algorithms/alg.sorting/alg.merge/inplace_merge_comp.pass.cpp
+++ b/test/std/algorithms/alg.sorting/alg.merge/inplace_merge_comp.pass.cpp
@@ -18,7 +18,10 @@
 #include <algorithm>
 #include <functional>
 #include <cassert>
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+
+#include "test_macros.h"
+
+#if TEST_STD_VER >= 11
 #include <memory>
 
 struct indirect_less
@@ -28,7 +31,29 @@
         {return *x < *y;}
 };
 
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
+struct S {
+	S() : i_(0) {}
+	S(int i) : i_(i) {}
+	
+	S(const S&  rhs) : i_(rhs.i_) {}
+	S(      S&& rhs) : i_(rhs.i_) { rhs.i_ = -1; }
+	
+	S& operator =(const S&  rhs) { i_ = rhs.i_;              return *this; }
+	S& operator =(      S&& rhs) { i_ = rhs.i_; rhs.i_ = -2; assert(this != &rhs); return *this; }
+	S& operator =(int i)         { i_ = i;                   return *this; }
+	
+	bool operator  <(const S&  rhs) const { return i_ < rhs.i_; }
+	bool operator  >(const S&  rhs) const { return i_ > rhs.i_; }
+	bool operator ==(const S&  rhs) const { return i_ == rhs.i_; }
+	bool operator ==(int i)         const { return i_ == i; }
+
+	void set(int i) { i_ = i; }
+	
+	int i_;
+	};
+
+
+#endif  // TEST_STD_VER >= 11
 
 #include "test_iterators.h"
 #include "counting_predicates.hpp"
@@ -38,19 +63,20 @@
 test_one(unsigned N, unsigned M)
 {
     assert(M <= N);
-    int* ia = new int[N];
+    typedef typename std::iterator_traits<Iter>::value_type value_type;
+    value_type* ia = new value_type[N];
     for (unsigned i = 0; i < N; ++i)
         ia[i] = i;
     std::random_shuffle(ia, ia+N);
-    std::sort(ia, ia+M, std::greater<int>());
-    std::sort(ia+M, ia+N, std::greater<int>());
-    binary_counting_predicate<std::greater<int>, int, int> pred((std::greater<int>()));
+    std::sort(ia, ia+M, std::greater<value_type>());
+    std::sort(ia+M, ia+N, std::greater<value_type>());
+    binary_counting_predicate<std::greater<value_type>, value_type, value_type> pred((std::greater<value_type>()));
     std::inplace_merge(Iter(ia), Iter(ia+M), Iter(ia+N), std::ref(pred));
     if(N > 0)
     {
         assert(ia[0] == N-1);
         assert(ia[N-1] == 0);
-        assert(std::is_sorted(ia, ia+N, std::greater<int>()));
+        assert(std::is_sorted(ia, ia+N, std::greater<value_type>()));
         assert(pred.count() <= (N-1));
     }
     delete [] ia;
@@ -93,7 +119,11 @@
     test<random_access_iterator<int*> >();
     test<int*>();
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#if TEST_STD_VER >= 11
+    test<bidirectional_iterator<S*> >();
+    test<random_access_iterator<S*> >();
+    test<S*>();
+
     {
     unsigned N = 100;
     unsigned M = 50;
@@ -112,5 +142,5 @@
     }
     delete [] ia;
     }
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#endif  // TEST_STD_VER >= 11
 }
diff --git a/test/std/algorithms/alg.sorting/alg.min.max/max_element.pass.cpp b/test/std/algorithms/alg.sorting/alg.min.max/max_element.pass.cpp
index 2788b19..2197b97 100644
--- a/test/std/algorithms/alg.sorting/alg.min.max/max_element.pass.cpp
+++ b/test/std/algorithms/alg.sorting/alg.min.max/max_element.pass.cpp
@@ -57,10 +57,24 @@
     test<Iter>(1000);
 }
 
+#if __cplusplus >= 201402L
+constexpr int il[] = { 2, 4, 6, 8, 7, 5, 3, 1 };
+#endif
+
+void constexpr_test()
+{
+#if __cplusplus >= 201402L
+    constexpr auto p = std::max_element(il,il+8);
+    static_assert ( *p == 8, "" );
+#endif
+}
+
 int main()
 {
     test<forward_iterator<const int*> >();
     test<bidirectional_iterator<const int*> >();
     test<random_access_iterator<const int*> >();
     test<const int*>();
+    
+    constexpr_test ();
 }
diff --git a/test/std/algorithms/alg.sorting/alg.min.max/max_element_comp.pass.cpp b/test/std/algorithms/alg.sorting/alg.min.max/max_element_comp.pass.cpp
index 74e9fe6..37c1813 100644
--- a/test/std/algorithms/alg.sorting/alg.min.max/max_element_comp.pass.cpp
+++ b/test/std/algorithms/alg.sorting/alg.min.max/max_element_comp.pass.cpp
@@ -75,6 +75,19 @@
     delete [] a;
 }
 
+#if __cplusplus >= 201402L
+constexpr int il[] = { 2, 4, 6, 8, 7, 5, 3, 1 };
+struct less { constexpr bool operator ()( const int &x, const int &y) const { return x < y; }};
+#endif
+
+void constexpr_test()
+{
+#if __cplusplus >= 201402L
+    constexpr auto p = std::max_element(il, il+8, less());
+    static_assert ( *p == 8, "" );
+#endif
+}
+
 int main()
 {
     test<forward_iterator<const int*> >();
@@ -82,4 +95,6 @@
     test<random_access_iterator<const int*> >();
     test<const int*>();
     test_eq();
+    
+    constexpr_test();
 }
diff --git a/test/std/algorithms/alg.sorting/alg.min.max/min_element.pass.cpp b/test/std/algorithms/alg.sorting/alg.min.max/min_element.pass.cpp
index fd41f7a..a9a9d61 100644
--- a/test/std/algorithms/alg.sorting/alg.min.max/min_element.pass.cpp
+++ b/test/std/algorithms/alg.sorting/alg.min.max/min_element.pass.cpp
@@ -57,10 +57,24 @@
     test<Iter>(1000);
 }
 
+#if __cplusplus >= 201402L
+constexpr int il[] = { 2, 4, 6, 8, 7, 5, 3, 1 };
+#endif
+
+void constexpr_test()
+{
+#if __cplusplus >= 201402L
+    constexpr auto p = std::min_element(il, il+8);
+    static_assert ( *p == 1, "" );
+#endif
+}
+
 int main()
 {
     test<forward_iterator<const int*> >();
     test<bidirectional_iterator<const int*> >();
     test<random_access_iterator<const int*> >();
     test<const int*>();
+
+    constexpr_test();
 }
diff --git a/test/std/algorithms/alg.sorting/alg.min.max/min_element_comp.pass.cpp b/test/std/algorithms/alg.sorting/alg.min.max/min_element_comp.pass.cpp
index 2b5fdb1..9517f7e 100644
--- a/test/std/algorithms/alg.sorting/alg.min.max/min_element_comp.pass.cpp
+++ b/test/std/algorithms/alg.sorting/alg.min.max/min_element_comp.pass.cpp
@@ -75,6 +75,19 @@
     delete [] a;
 }
 
+#if __cplusplus >= 201402L
+constexpr int il[] = { 2, 4, 6, 8, 7, 5, 3, 1 };
+struct less { constexpr bool operator ()( const int &x, const int &y) const { return x < y; }};
+#endif
+
+void constexpr_test()
+{
+#if __cplusplus >= 201402L
+	constexpr auto p = std::min_element(il, il+8, less());
+	static_assert(*p == 1, "");
+#endif
+}
+
 int main()
 {
     test<forward_iterator<const int*> >();
@@ -82,4 +95,6 @@
     test<random_access_iterator<const int*> >();
     test<const int*>();
     test_eq();
+    
+    constexpr_test();
 }
diff --git a/test/std/algorithms/alg.sorting/alg.min.max/minmax_element.pass.cpp b/test/std/algorithms/alg.sorting/alg.min.max/minmax_element.pass.cpp
index 6cdb87d..915b1d1 100644
--- a/test/std/algorithms/alg.sorting/alg.min.max/minmax_element.pass.cpp
+++ b/test/std/algorithms/alg.sorting/alg.min.max/minmax_element.pass.cpp
@@ -74,10 +74,25 @@
     }
 }
 
+#if __cplusplus >= 201402L
+constexpr int il[] = { 2, 4, 6, 8, 7, 5, 3, 1 };
+#endif
+
+void constexpr_test()
+{
+#if __cplusplus >= 201402L
+    constexpr auto p = std::minmax_element(il, il+8);
+    static_assert ( *(p.first)  == 1, "" );
+    static_assert ( *(p.second) == 8, "" );
+#endif
+}
+
 int main()
 {
     test<forward_iterator<const int*> >();
     test<bidirectional_iterator<const int*> >();
     test<random_access_iterator<const int*> >();
     test<const int*>();
+    
+   constexpr_test();
 }
diff --git a/test/std/algorithms/alg.sorting/alg.min.max/minmax_element_comp.pass.cpp b/test/std/algorithms/alg.sorting/alg.min.max/minmax_element_comp.pass.cpp
index cc0e66e..d3a067f 100644
--- a/test/std/algorithms/alg.sorting/alg.min.max/minmax_element_comp.pass.cpp
+++ b/test/std/algorithms/alg.sorting/alg.min.max/minmax_element_comp.pass.cpp
@@ -79,10 +79,26 @@
     }
 }
 
+#if __cplusplus >= 201402L
+constexpr int il[] = { 2, 4, 6, 8, 7, 5, 3, 1 };
+struct less { constexpr bool operator ()( const int &x, const int &y) const { return x < y; }};
+#endif
+
+void constexpr_test()
+{
+#if __cplusplus >= 201402L
+    constexpr auto p = std::minmax_element(il, il+8, less());
+    static_assert ( *(p.first)  == 1, "" );
+    static_assert ( *(p.second) == 8, "" );
+#endif
+}
+
 int main()
 {
     test<forward_iterator<const int*> >();
     test<bidirectional_iterator<const int*> >();
     test<random_access_iterator<const int*> >();
     test<const int*>();
+    
+    constexpr_test();
 }
diff --git a/test/std/algorithms/alg.sorting/alg.set.operations/includes/includes.pass.cpp b/test/std/algorithms/alg.sorting/alg.set.operations/includes/includes.pass.cpp
index 8db8177..70abd18 100644
--- a/test/std/algorithms/alg.sorting/alg.set.operations/includes/includes.pass.cpp
+++ b/test/std/algorithms/alg.sorting/alg.set.operations/includes/includes.pass.cpp
@@ -29,9 +29,9 @@
     int ib[] = {2, 4};
     const unsigned sb = sizeof(ib)/sizeof(ib[0]);
     int ic[] = {1, 2};
-    const unsigned sc = sizeof(ic)/sizeof(ic[0]);
+    const unsigned sc = sizeof(ic)/sizeof(ic[0]); ((void)sc);
     int id[] = {3, 3, 3, 3};
-    const unsigned sd = sizeof(id)/sizeof(id[0]);
+    const unsigned sd = sizeof(id)/sizeof(id[0]); ((void)sd);
 
     assert(std::includes(Iter1(ia), Iter1(ia), Iter2(ib), Iter2(ib)));
     assert(!std::includes(Iter1(ia), Iter1(ia), Iter2(ib), Iter2(ib+1)));
diff --git a/test/std/algorithms/alg.sorting/alg.set.operations/includes/includes_comp.pass.cpp b/test/std/algorithms/alg.sorting/alg.set.operations/includes/includes_comp.pass.cpp
index 7e1aef4..299dc89 100644
--- a/test/std/algorithms/alg.sorting/alg.set.operations/includes/includes_comp.pass.cpp
+++ b/test/std/algorithms/alg.sorting/alg.set.operations/includes/includes_comp.pass.cpp
@@ -30,9 +30,9 @@
     int ib[] = {2, 4};
     const unsigned sb = sizeof(ib)/sizeof(ib[0]);
     int ic[] = {1, 2};
-    const unsigned sc = sizeof(ic)/sizeof(ic[0]);
+    const unsigned sc = sizeof(ic)/sizeof(ic[0]); ((void)sc);
     int id[] = {3, 3, 3, 3};
-    const unsigned sd = sizeof(id)/sizeof(id[0]);
+    const unsigned sd = sizeof(id)/sizeof(id[0]); ((void)sd);
 
     assert(std::includes(Iter1(ia), Iter1(ia), Iter2(ib), Iter2(ib), std::less<int>()));
     assert(!std::includes(Iter1(ia), Iter1(ia), Iter2(ib), Iter2(ib+1), std::less<int>()));
diff --git a/test/std/atomics/atomics.flag/atomic_flag_clear.pass.cpp b/test/std/atomics/atomics.flag/atomic_flag_clear.pass.cpp
index 64093d6..8a60f81 100644
--- a/test/std/atomics/atomics.flag/atomic_flag_clear.pass.cpp
+++ b/test/std/atomics/atomics.flag/atomic_flag_clear.pass.cpp
@@ -22,13 +22,13 @@
 int main()
 {
     {
-        std::atomic_flag f;
+        std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         atomic_flag_clear(&f);
         assert(f.test_and_set() == 0);
     }
     {
-        volatile std::atomic_flag f;
+        volatile std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         atomic_flag_clear(&f);
         assert(f.test_and_set() == 0);
diff --git a/test/std/atomics/atomics.flag/atomic_flag_clear_explicit.pass.cpp b/test/std/atomics/atomics.flag/atomic_flag_clear_explicit.pass.cpp
index e1a9349..92e57ec 100644
--- a/test/std/atomics/atomics.flag/atomic_flag_clear_explicit.pass.cpp
+++ b/test/std/atomics/atomics.flag/atomic_flag_clear_explicit.pass.cpp
@@ -22,37 +22,37 @@
 int main()
 {
     {
-        std::atomic_flag f;
+        std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         atomic_flag_clear_explicit(&f, std::memory_order_relaxed);
         assert(f.test_and_set() == 0);
     }
     {
-        std::atomic_flag f;
+        std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         atomic_flag_clear_explicit(&f, std::memory_order_release);
         assert(f.test_and_set() == 0);
     }
     {
-        std::atomic_flag f;
+        std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         atomic_flag_clear_explicit(&f, std::memory_order_seq_cst);
         assert(f.test_and_set() == 0);
     }
     {
-        volatile std::atomic_flag f;
+        volatile std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         atomic_flag_clear_explicit(&f, std::memory_order_relaxed);
         assert(f.test_and_set() == 0);
     }
     {
-        volatile std::atomic_flag f;
+        volatile std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         atomic_flag_clear_explicit(&f, std::memory_order_release);
         assert(f.test_and_set() == 0);
     }
     {
-        volatile std::atomic_flag f;
+        volatile std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         atomic_flag_clear_explicit(&f, std::memory_order_seq_cst);
         assert(f.test_and_set() == 0);
diff --git a/test/std/atomics/atomics.flag/clear.pass.cpp b/test/std/atomics/atomics.flag/clear.pass.cpp
index 65051af..7c93626 100644
--- a/test/std/atomics/atomics.flag/clear.pass.cpp
+++ b/test/std/atomics/atomics.flag/clear.pass.cpp
@@ -22,49 +22,49 @@
 int main()
 {
     {
-        std::atomic_flag f;
+        std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         f.clear();
         assert(f.test_and_set() == 0);
     }
     {
-        std::atomic_flag f;
+        std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         f.clear(std::memory_order_relaxed);
         assert(f.test_and_set() == 0);
     }
     {
-        std::atomic_flag f;
+        std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         f.clear(std::memory_order_release);
         assert(f.test_and_set() == 0);
     }
     {
-        std::atomic_flag f;
+        std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         f.clear(std::memory_order_seq_cst);
         assert(f.test_and_set() == 0);
     }
     {
-        volatile std::atomic_flag f;
+        volatile std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         f.clear();
         assert(f.test_and_set() == 0);
     }
     {
-        volatile std::atomic_flag f;
+        volatile std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         f.clear(std::memory_order_relaxed);
         assert(f.test_and_set() == 0);
     }
     {
-        volatile std::atomic_flag f;
+        volatile std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         f.clear(std::memory_order_release);
         assert(f.test_and_set() == 0);
     }
     {
-        volatile std::atomic_flag f;
+        volatile std::atomic_flag f = ATOMIC_FLAG_INIT;
         f.test_and_set();
         f.clear(std::memory_order_seq_cst);
         assert(f.test_and_set() == 0);
diff --git a/test/std/atomics/atomics.flag/default.pass.cpp b/test/std/atomics/atomics.flag/default.pass.cpp
index 45f5e70..11c08f5 100644
--- a/test/std/atomics/atomics.flag/default.pass.cpp
+++ b/test/std/atomics/atomics.flag/default.pass.cpp
@@ -22,7 +22,8 @@
 int main()
 {
     std::atomic_flag f;
-
+    f.clear();
+    assert(f.test_and_set() == 0);
     {
         typedef std::atomic_flag A;
         _ALIGNAS_TYPE(A) char storage[sizeof(A)] = {1};
diff --git a/test/std/atomics/atomics.types.generic/address.pass.cpp b/test/std/atomics/atomics.types.generic/address.pass.cpp
index 3b9f3ce..eceac25 100644
--- a/test/std/atomics/atomics.types.generic/address.pass.cpp
+++ b/test/std/atomics/atomics.types.generic/address.pass.cpp
@@ -81,12 +81,13 @@
 {
     typedef typename std::remove_pointer<T>::type X;
     A obj(T(0));
+    bool b0 = obj.is_lock_free();
+    ((void)b0); // mark as unused
     assert(obj == T(0));
     std::atomic_init(&obj, T(1));
     assert(obj == T(1));
     std::atomic_init(&obj, T(2));
     assert(obj == T(2));
-    bool b0 = obj.is_lock_free();
     obj.store(T(0));
     assert(obj == T(0));
     obj.store(T(1), std::memory_order_release);
diff --git a/test/std/atomics/atomics.types.generic/bool.pass.cpp b/test/std/atomics/atomics.types.generic/bool.pass.cpp
index dd851e8..8eb04ee 100644
--- a/test/std/atomics/atomics.types.generic/bool.pass.cpp
+++ b/test/std/atomics/atomics.types.generic/bool.pass.cpp
@@ -60,7 +60,6 @@
 int main()
 {
     {
-        volatile std::atomic<bool> _;
         volatile std::atomic<bool> obj(true);
         assert(obj == true);
         std::atomic_init(&obj, false);
@@ -116,7 +115,6 @@
         assert(obj == true);
     }
     {
-        std::atomic<bool> _;
         std::atomic<bool> obj(true);
         assert(obj == true);
         std::atomic_init(&obj, false);
@@ -172,7 +170,6 @@
         assert(obj == true);
     }
     {
-        std::atomic_bool _;
         std::atomic_bool obj(true);
         assert(obj == true);
         std::atomic_init(&obj, false);
diff --git a/test/std/atomics/atomics.types.generic/integral.pass.cpp b/test/std/atomics/atomics.types.generic/integral.pass.cpp
index f9c7583..802a37c 100644
--- a/test/std/atomics/atomics.types.generic/integral.pass.cpp
+++ b/test/std/atomics/atomics.types.generic/integral.pass.cpp
@@ -103,6 +103,7 @@
     std::atomic_init(&obj, T(2));
     assert(obj == T(2));
     bool b0 = obj.is_lock_free();
+    ((void)b0); // mark as unused
     obj.store(T(0));
     assert(obj == T(0));
     obj.store(T(1), std::memory_order_release);
diff --git a/test/std/atomics/atomics.types.operations/atomics.types.operations.req/atomic_is_lock_free.pass.cpp b/test/std/atomics/atomics.types.operations/atomics.types.operations.req/atomic_is_lock_free.pass.cpp
index 18a1605..ee22912 100644
--- a/test/std/atomics/atomics.types.operations/atomics.types.operations.req/atomic_is_lock_free.pass.cpp
+++ b/test/std/atomics/atomics.types.operations/atomics.types.operations.req/atomic_is_lock_free.pass.cpp
@@ -20,6 +20,7 @@
 //     atomic_is_lock_free(const atomic<T>* obj);
 
 #include <atomic>
+#include <cassert>
 
 template <class T>
 void
@@ -30,6 +31,7 @@
     bool b1 = std::atomic_is_lock_free(static_cast<const A*>(&t));
     volatile A vt;
     bool b2 = std::atomic_is_lock_free(static_cast<const volatile A*>(&vt));
+    assert(b1 == b2);
 }
 
 struct A
diff --git a/test/std/atomics/atomics.types.operations/atomics.types.operations.req/ctor.pass.cpp b/test/std/atomics/atomics.types.operations/atomics.types.operations.req/ctor.pass.cpp
new file mode 100644
index 0000000..f85172a
--- /dev/null
+++ b/test/std/atomics/atomics.types.operations/atomics.types.operations.req/ctor.pass.cpp
@@ -0,0 +1,60 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++98, c++03
+
+// NOTE: atomic<> of a TriviallyCopyable class is wrongly rejected by older
+// clang versions. It was fixed right before the llvm 3.5 release. See PR18097.
+// XFAIL: apple-clang-6.0, clang-3.4, clang-3.3
+
+// <atomic>
+
+// constexpr atomic<T>::atomic(T value)
+
+#include <atomic>
+#include <type_traits>
+#include <cassert>
+
+struct UserType {
+    int i;
+
+    UserType() noexcept {}
+    constexpr explicit UserType(int d) noexcept : i(d) {}
+
+    friend bool operator==(const UserType& x, const UserType& y) {
+        return x.i == y.i;
+    }
+};
+
+template <class Tp>
+void test() {
+    typedef std::atomic<Tp> Atomic;
+    static_assert(std::is_literal_type<Atomic>::value, "");
+    constexpr Tp t(42);
+    {
+        constexpr Atomic a(t);
+        assert(a == t);
+    }
+    {
+        constexpr Atomic a{t};
+        assert(a == t);
+    }
+    {
+        constexpr Atomic a = ATOMIC_VAR_INIT(t);
+        assert(a == t);
+    }
+}
+
+
+int main()
+{
+    test<int>();
+    test<UserType>();
+}
diff --git a/test/std/containers/associative/map/compare.pass.cpp b/test/std/containers/associative/map/compare.pass.cpp
index aa4d599..26ac7af 100644
--- a/test/std/containers/associative/map/compare.pass.cpp
+++ b/test/std/containers/associative/map/compare.pass.cpp
@@ -17,16 +17,36 @@
 // http://llvm.org/bugs/show_bug.cgi?id=16549
 
 #include <map>
+#include <utility>
+#include <cassert>
 
 struct Key {
   template <typename T> Key(const T&) {}
   bool operator< (const Key&) const { return false; }
 };
 
-int
-main()
+int main()
 {
-    std::map<Key, int>::iterator it = std::map<Key, int>().find(Key(0));
-    std::pair<std::map<Key, int>::iterator, bool> result =
-                        std::map<Key, int>().insert(std::make_pair(Key(0), 0));
+    typedef std::map<Key, int> MapT;
+    typedef MapT::iterator Iter;
+    typedef std::pair<Iter, bool> IterBool;
+    {
+        MapT m_empty;
+        MapT m_contains;
+        m_contains[Key(0)] = 42;
+
+        Iter it = m_empty.find(Key(0));
+        assert(it == m_empty.end());
+        it = m_contains.find(Key(0));
+        assert(it != m_contains.end());
+    }
+    {
+        MapT map;
+        IterBool result = map.insert(std::make_pair(Key(0), 42));
+        assert(result.second);
+        assert(result.first->second = 42);
+        IterBool result2 = map.insert(std::make_pair(Key(0), 43));
+        assert(!result2.second);
+        assert(map[Key(0)] == 42);
+    }
 }
diff --git a/test/std/containers/associative/map/map.access/index_rv_key.pass.cpp b/test/std/containers/associative/map/map.access/index_rv_key.pass.cpp
index d14603e..7e0fd41 100644
--- a/test/std/containers/associative/map/map.access/index_rv_key.pass.cpp
+++ b/test/std/containers/associative/map/map.access/index_rv_key.pass.cpp
@@ -16,14 +16,14 @@
 #include <map>
 #include <cassert>
 
+#include "test_macros.h"
 #include "MoveOnly.h"
 #include "min_allocator.h"
 
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#if TEST_STD_VER >= 11
     {
-    typedef std::pair<MoveOnly, double> V;
     std::map<MoveOnly, double> m;
     assert(m.size() == 0);
     assert(m[1] == 0.0);
@@ -37,8 +37,6 @@
     assert(m[6] == 6.5);
     assert(m.size() == 2);
     }
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-#if __cplusplus >= 201103L
     {
     typedef std::pair<MoveOnly, double> V;
     std::map<MoveOnly, double, std::less<MoveOnly>, min_allocator<V>> m;
diff --git a/test/std/containers/associative/map/map.modifiers/erase_iter.pass.cpp b/test/std/containers/associative/map/map.modifiers/erase_iter.pass.cpp
index 05fb988..15c5ce0 100644
--- a/test/std/containers/associative/map/map.modifiers/erase_iter.pass.cpp
+++ b/test/std/containers/associative/map/map.modifiers/erase_iter.pass.cpp
@@ -18,6 +18,14 @@
 
 #include "min_allocator.h"
 
+struct TemplateConstructor
+{
+    template<typename T>
+    TemplateConstructor (const T&) {}
+};
+
+bool operator<(const TemplateConstructor&, const TemplateConstructor&) { return false; }
+
 int main()
 {
     {
@@ -234,4 +242,18 @@
         assert(i == m.end());
     }
 #endif
+#if __cplusplus >= 201402L
+    {
+    //  This is LWG #2059
+        typedef TemplateConstructor T;
+        typedef std::map<T, int> C;
+        typedef C::iterator I;
+
+        C c;
+        T a{0};
+        I it = c.find(a);
+        if (it != c.end())
+            c.erase(it);
+    }
+#endif
 }
diff --git a/test/std/containers/associative/map/map.modifiers/insert_or_assign.pass.cpp b/test/std/containers/associative/map/map.modifiers/insert_or_assign.pass.cpp
new file mode 100644
index 0000000..484ed06
--- /dev/null
+++ b/test/std/containers/associative/map/map.modifiers/insert_or_assign.pass.cpp
@@ -0,0 +1,192 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: c++03, c++11, c++14
+
+// <map>
+
+// class map
+
+// template <class M>
+//  pair<iterator, bool> insert_or_assign(const key_type& k, M&& obj);            // C++17
+// template <class M>
+//  pair<iterator, bool> insert_or_assign(key_type&& k, M&& obj);                 // C++17
+// template <class M>
+//  iterator insert_or_assign(const_iterator hint, const key_type& k, M&& obj);   // C++17
+// template <class M>
+//  iterator insert_or_assign(const_iterator hint, key_type&& k, M&& obj);        // C++17
+
+#include <__config>
+#include <map>
+#include <cassert>
+#include <tuple>
+
+#include <iostream>
+
+class Moveable
+{
+    Moveable(const Moveable&);
+    Moveable& operator=(const Moveable&);
+
+    int int_;
+    double double_;
+public:
+    Moveable() : int_(0), double_(0) {}
+    Moveable(int i, double d) : int_(i), double_(d) {}
+    Moveable(Moveable&& x)
+        : int_(x.int_), double_(x.double_)
+            {x.int_ = -1; x.double_ = -1;}
+    Moveable& operator=(Moveable&& x)
+        {int_ = x.int_; x.int_ = -1;
+         double_ = x.double_; x.double_ = -1;
+         return *this;
+        }
+
+    bool operator==(const Moveable& x) const
+        {return int_ == x.int_ && double_ == x.double_;}
+    bool operator<(const Moveable& x) const
+        {return int_ < x.int_ || (int_ == x.int_ && double_ < x.double_);}
+
+    int get() const {return int_;}
+    bool moved() const {return int_ == -1;}
+};
+
+
+int main()
+{
+#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#ifndef _LIBCPP_HAS_NO_VARIADICS
+
+    { // pair<iterator, bool> insert_or_assign(const key_type& k, M&& obj);
+        typedef std::map<int, Moveable> M;
+        typedef std::pair<M::iterator, bool> R;
+        M m;
+        R r;
+        for ( int i = 0; i < 20; i += 2 )
+            m.emplace ( i, Moveable(i, (double) i));
+        assert(m.size() == 10);
+
+        for (int i=0; i < 20; i += 2)
+        {
+            Moveable mv(i+1, i+1);
+            r = m.insert_or_assign(i, std::move(mv));
+            assert(m.size() == 10);
+            assert(!r.second);                    // was not inserted
+            assert(mv.moved());                   // was moved from
+            assert(r.first->first == i);          // key
+            assert(r.first->second.get() == i+1); // value
+        }
+
+        Moveable mv1(5, 5.0);
+        r = m.insert_or_assign(-1, std::move(mv1));
+        assert(m.size() == 11);
+        assert(r.second);                    // was inserted
+        assert(mv1.moved());                 // was moved from
+        assert(r.first->first        == -1); // key
+        assert(r.first->second.get() == 5);  // value
+
+        Moveable mv2(9, 9.0);
+        r = m.insert_or_assign(3, std::move(mv2));
+        assert(m.size() == 12);
+        assert(r.second);                   // was inserted
+        assert(mv2.moved());                // was moved from
+        assert(r.first->first        == 3); // key
+        assert(r.first->second.get() == 9); // value
+
+        Moveable mv3(-1, 5.0);
+        r = m.insert_or_assign(117, std::move(mv3));
+        assert(m.size() == 13);
+        assert(r.second);                     // was inserted
+        assert(mv3.moved());                  // was moved from
+        assert(r.first->first        == 117); // key
+        assert(r.first->second.get() == -1);  // value
+    }
+    { // pair<iterator, bool> insert_or_assign(key_type&& k, M&& obj);
+        typedef std::map<Moveable, Moveable> M;
+        typedef std::pair<M::iterator, bool> R;
+        M m;
+        R r;
+        for ( int i = 0; i < 20; i += 2 )
+            m.emplace ( Moveable(i, (double) i), Moveable(i+1, (double) i+1));
+        assert(m.size() == 10);
+
+        Moveable mvkey1(2, 2.0);
+        Moveable mv1(4, 4.0);
+        r = m.insert_or_assign(std::move(mvkey1), std::move(mv1));
+        assert(m.size() == 10);
+        assert(!r.second);                  // was not inserted
+        assert(!mvkey1.moved());            // was not moved from
+        assert(mv1.moved());                // was moved from
+        assert(r.first->first == mvkey1);   // key
+        assert(r.first->second.get() == 4); // value
+
+        Moveable mvkey2(3, 3.0);
+        Moveable mv2(5, 5.0);
+        r = m.try_emplace(std::move(mvkey2), std::move(mv2));
+        assert(m.size() == 11);
+        assert(r.second);                   // was inserted
+        assert(mv2.moved());                // was moved from
+        assert(mvkey2.moved());             // was moved from
+        assert(r.first->first.get()  == 3); // key
+        assert(r.first->second.get() == 5); // value
+    }
+    { // iterator insert_or_assign(const_iterator hint, const key_type& k, M&& obj);
+        typedef std::map<int, Moveable> M;
+        M m;
+        M::iterator r;
+        for ( int i = 0; i < 20; i += 2 )
+            m.emplace ( i, Moveable(i, (double) i));
+        assert(m.size() == 10);
+        M::const_iterator it = m.find(2);
+
+        Moveable mv1(3, 3.0);
+        r = m.insert_or_assign(it, 2, std::move(mv1));
+        assert(m.size() == 10);
+        assert(mv1.moved());           // was moved from
+        assert(r->first        == 2);  // key
+        assert(r->second.get() == 3);  // value
+
+        Moveable mv2(5, 5.0);
+        r = m.insert_or_assign(it, 3, std::move(mv2));
+        assert(m.size() == 11);
+        assert(mv2.moved());           // was moved from
+        assert(r->first        == 3);  // key
+        assert(r->second.get() == 5);  // value
+    }
+    { // iterator insert_or_assign(const_iterator hint, key_type&& k, M&& obj);
+        typedef std::map<Moveable, Moveable> M;
+        M m;
+        M::iterator r;
+        for ( int i = 0; i < 20; i += 2 )
+            m.emplace ( Moveable(i, (double) i), Moveable(i+1, (double) i+1));
+        assert(m.size() == 10);
+        M::const_iterator it = std::next(m.cbegin());
+
+        Moveable mvkey1(2, 2.0);
+        Moveable mv1(4, 4.0);
+        r = m.insert_or_assign(it, std::move(mvkey1), std::move(mv1));
+        assert(m.size() == 10);
+        assert(mv1.moved());          // was moved from
+        assert(!mvkey1.moved());      // was not moved from
+        assert(r->first == mvkey1);   // key
+        assert(r->second.get() == 4); // value
+
+        Moveable mvkey2(3, 3.0);
+        Moveable mv2(5, 5.0);
+        r = m.insert_or_assign(it, std::move(mvkey2), std::move(mv2));
+        assert(m.size() == 11);
+        assert(mv2.moved());           // was moved from
+        assert(mvkey2.moved());        // was moved from
+        assert(r->first.get()  == 3);  // key
+        assert(r->second.get() == 5);  // value
+    }
+
+#endif  // _LIBCPP_HAS_NO_VARIADICS
+#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
+}
\ No newline at end of file
diff --git a/test/std/containers/associative/map/map.modifiers/try.emplace.pass.cpp b/test/std/containers/associative/map/map.modifiers/try.emplace.pass.cpp
new file mode 100644
index 0000000..8e0dd75
--- /dev/null
+++ b/test/std/containers/associative/map/map.modifiers/try.emplace.pass.cpp
@@ -0,0 +1,189 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: c++03, c++11, c++14
+
+// <map>
+
+// class map
+
+// template <class... Args>
+//  pair<iterator, bool> try_emplace(const key_type& k, Args&&... args);          // C++17
+// template <class... Args>
+//  pair<iterator, bool> try_emplace(key_type&& k, Args&&... args);               // C++17
+// template <class... Args>
+//  iterator try_emplace(const_iterator hint, const key_type& k, Args&&... args); // C++17
+// template <class... Args>
+//  iterator try_emplace(const_iterator hint, key_type&& k, Args&&... args);      // C++17
+
+#include <__config>
+#include <map>
+#include <cassert>
+#include <tuple>
+
+class Moveable
+{
+    Moveable(const Moveable&);
+    Moveable& operator=(const Moveable&);
+
+    int int_;
+    double double_;
+public:
+    Moveable() : int_(0), double_(0) {}
+    Moveable(int i, double d) : int_(i), double_(d) {}
+    Moveable(Moveable&& x)
+        : int_(x.int_), double_(x.double_)
+            {x.int_ = -1; x.double_ = -1;}
+    Moveable& operator=(Moveable&& x)
+        {int_ = x.int_; x.int_ = -1;
+         double_ = x.double_; x.double_ = -1;
+         return *this;
+        }
+
+    bool operator==(const Moveable& x) const
+        {return int_ == x.int_ && double_ == x.double_;}
+    bool operator<(const Moveable& x) const
+        {return int_ < x.int_ || (int_ == x.int_ && double_ < x.double_);}
+
+    int get() const {return int_;}
+    bool moved() const {return int_ == -1;}
+};
+
+
+int main()
+{
+#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#ifndef _LIBCPP_HAS_NO_VARIADICS
+
+    { // pair<iterator, bool> try_emplace(const key_type& k, Args&&... args);
+        typedef std::map<int, Moveable> M;
+        typedef std::pair<M::iterator, bool> R;
+        M m;
+        R r;
+        for (int i = 0; i < 20; i += 2)
+            m.emplace (i, Moveable(i, (double) i));
+        assert(m.size() == 10);
+
+        Moveable mv1(3, 3.0);
+        for (int i=0; i < 20; i += 2)
+        {
+            r = m.try_emplace(i, std::move(mv1));
+            assert(m.size() == 10);
+            assert(!r.second);              // was not inserted
+            assert(!mv1.moved());           // was not moved from
+            assert(r.first->first == i);    // key
+        }
+
+        r = m.try_emplace(-1, std::move(mv1));
+        assert(m.size() == 11);
+        assert(r.second);                   // was inserted
+        assert(mv1.moved());                // was moved from
+        assert(r.first->first == -1);       // key
+        assert(r.first->second.get() == 3); // value
+
+        Moveable mv2(5, 3.0);
+        r = m.try_emplace(5, std::move(mv2));
+        assert(m.size() == 12);
+        assert(r.second);                   // was inserted
+        assert(mv2.moved());                // was moved from
+        assert(r.first->first == 5);        // key
+        assert(r.first->second.get() == 5); // value
+
+        Moveable mv3(-1, 3.0);
+        r = m.try_emplace(117, std::move(mv2));
+        assert(m.size() == 13);
+        assert(r.second);                    // was inserted
+        assert(mv2.moved());                 // was moved from
+        assert(r.first->first == 117);       // key
+        assert(r.first->second.get() == -1); // value
+    }
+
+    {  // pair<iterator, bool> try_emplace(key_type&& k, Args&&... args); 
+        typedef std::map<Moveable, Moveable> M;
+        typedef std::pair<M::iterator, bool> R;
+        M m;
+        R r;
+        for ( int i = 0; i < 20; i += 2 )
+            m.emplace ( Moveable(i, (double) i), Moveable(i+1, (double) i+1));
+        assert(m.size() == 10);
+
+        Moveable mvkey1(2, 2.0);
+        Moveable mv1(4, 4.0);
+        r = m.try_emplace(std::move(mvkey1), std::move(mv1));
+        assert(m.size() == 10);
+        assert(!r.second);                 // was not inserted
+        assert(!mv1.moved());              // was not moved from
+        assert(!mvkey1.moved());           // was not moved from
+        assert(r.first->first == mvkey1);  // key
+
+        Moveable mvkey2(3, 3.0);
+        r = m.try_emplace(std::move(mvkey2), std::move(mv1));
+        assert(m.size() == 11);
+        assert(r.second);                   // was inserted
+        assert(mv1.moved());                // was moved from
+        assert(mvkey2.moved());             // was moved from
+        assert(r.first->first.get()  == 3); // key
+        assert(r.first->second.get() == 4); // value
+    }
+
+    {  // iterator try_emplace(const_iterator hint, const key_type& k, Args&&... args);
+        typedef std::map<int, Moveable> M;
+        M m;
+        M::iterator r;
+        for ( int i = 0; i < 20; i += 2 )
+            m.try_emplace ( i, Moveable(i, (double) i));
+        assert(m.size() == 10);
+        M::const_iterator it = m.find(2);
+        
+        Moveable mv1(3, 3.0);
+        for (int i=0; i < 20; i += 2)
+        {
+            r = m.try_emplace(it, i, std::move(mv1));
+            assert(m.size() == 10);
+            assert(!mv1.moved());         // was not moved from
+            assert(r->first == i);        // key
+            assert(r->second.get() == i); // value
+        }
+
+        r = m.try_emplace(it, 3, std::move(mv1));
+        assert(m.size() == 11);
+        assert(mv1.moved());          // was moved from
+        assert(r->first == 3);        // key
+        assert(r->second.get() == 3); // value
+    }
+
+    {  // iterator try_emplace(const_iterator hint, key_type&& k, Args&&... args);
+        typedef std::map<Moveable, Moveable> M;
+        M m;
+        M::iterator r;
+        for ( int i = 0; i < 20; i += 2 )
+            m.emplace ( Moveable(i, (double) i), Moveable(i+1, (double) i+1));
+        assert(m.size() == 10);
+        M::const_iterator it = std::next(m.cbegin());
+
+        Moveable mvkey1(2, 2.0);
+        Moveable mv1(4, 4.0);
+        r = m.try_emplace(it, std::move(mvkey1), std::move(mv1));
+        assert(m.size() == 10);
+        assert(!mv1.moved());        // was not moved from
+        assert(!mvkey1.moved());     // was not moved from
+        assert(r->first == mvkey1);  // key
+
+        Moveable mvkey2(3, 3.0);
+        r = m.try_emplace(it, std::move(mvkey2), std::move(mv1));
+        assert(m.size() == 11);
+        assert(mv1.moved());          // was moved from
+        assert(mvkey2.moved());       // was moved from
+        assert(r->first.get()  == 3); // key
+        assert(r->second.get() == 4); // value
+    }
+
+#endif  // _LIBCPP_HAS_NO_VARIADICS
+#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
+}
diff --git a/test/std/containers/associative/map/map.ops/count.pass.cpp b/test/std/containers/associative/map/map.ops/count.pass.cpp
index 9668055..ae87ae8 100644
--- a/test/std/containers/associative/map/map.ops/count.pass.cpp
+++ b/test/std/containers/associative/map/map.ops/count.pass.cpp
@@ -18,6 +18,7 @@
 
 #include "min_allocator.h"
 #include "private_constructor.hpp"
+#include "is_transparent.h"
 
 int main()
 {
@@ -133,6 +134,25 @@
     assert(r == 1);
     r = m.count(4);
     assert(r == 0);
+
+    r = m.count(C2Int(5));
+    assert(r == 1);
+    r = m.count(C2Int(6));
+    assert(r == 1);
+    r = m.count(C2Int(7));
+    assert(r == 1);
+    r = m.count(C2Int(8));
+    assert(r == 1);
+    r = m.count(C2Int(9));
+    assert(r == 1);
+    r = m.count(C2Int(10));
+    assert(r == 1);
+    r = m.count(C2Int(11));
+    assert(r == 1);
+    r = m.count(C2Int(12));
+    assert(r == 1);
+    r = m.count(C2Int(4));
+    assert(r == 0);
     }
 
     {
diff --git a/test/std/containers/associative/map/map.ops/count0.pass.cpp b/test/std/containers/associative/map/map.ops/count0.pass.cpp
new file mode 100644
index 0000000..ce54936
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/count0.pass.cpp
@@ -0,0 +1,34 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// XFAIL: c++03, c++11
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+int main()
+{
+    typedef std::map<int, double, transparent_less> M;
+
+    M().count(C2Int{5});
+}
diff --git a/test/std/containers/associative/map/map.ops/count1.fail.cpp b/test/std/containers/associative/map/map.ops/count1.fail.cpp
new file mode 100644
index 0000000..9c15059
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/count1.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_no_type> M;
+
+    M().count(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/map/map.ops/count2.fail.cpp b/test/std/containers/associative/map/map.ops/count2.fail.cpp
new file mode 100644
index 0000000..7aa1553
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/count2.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_private> M;
+
+    M().count(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/map/map.ops/count3.fail.cpp b/test/std/containers/associative/map/map.ops/count3.fail.cpp
new file mode 100644
index 0000000..7e7bb8f
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/count3.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_not_a_type> M;
+
+    M().count(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/map/map.ops/equal_range.pass.cpp b/test/std/containers/associative/map/map.ops/equal_range.pass.cpp
index dff751c..a71149a 100644
--- a/test/std/containers/associative/map/map.ops/equal_range.pass.cpp
+++ b/test/std/containers/associative/map/map.ops/equal_range.pass.cpp
@@ -19,6 +19,7 @@
 
 #include "min_allocator.h"
 #include "private_constructor.hpp"
+#include "is_transparent.h"
 
 int main()
 {
@@ -365,6 +366,58 @@
     r = m.equal_range(20);
     assert(r.first == next(m.begin(), 8));
     assert(r.second == next(m.begin(), 8));
+
+    r = m.equal_range(C2Int(5));
+    assert(r.first == next(m.begin(), 0));
+    assert(r.second == next(m.begin(), 1));
+    r = m.equal_range(C2Int(7));
+    assert(r.first == next(m.begin(), 1));
+    assert(r.second == next(m.begin(), 2));
+    r = m.equal_range(C2Int(9));
+    assert(r.first == next(m.begin(), 2));
+    assert(r.second == next(m.begin(), 3));
+    r = m.equal_range(C2Int(11));
+    assert(r.first == next(m.begin(), 3));
+    assert(r.second == next(m.begin(), 4));
+    r = m.equal_range(C2Int(13));
+    assert(r.first == next(m.begin(), 4));
+    assert(r.second == next(m.begin(), 5));
+    r = m.equal_range(C2Int(15));
+    assert(r.first == next(m.begin(), 5));
+    assert(r.second == next(m.begin(), 6));
+    r = m.equal_range(C2Int(17));
+    assert(r.first == next(m.begin(), 6));
+    assert(r.second == next(m.begin(), 7));
+    r = m.equal_range(C2Int(19));
+    assert(r.first == next(m.begin(), 7));
+    assert(r.second == next(m.begin(), 8));
+    r = m.equal_range(C2Int(4));
+    assert(r.first == next(m.begin(), 0));
+    assert(r.second == next(m.begin(), 0));
+    r = m.equal_range(C2Int(6));
+    assert(r.first == next(m.begin(), 1));
+    assert(r.second == next(m.begin(), 1));
+    r = m.equal_range(C2Int(8));
+    assert(r.first == next(m.begin(), 2));
+    assert(r.second == next(m.begin(), 2));
+    r = m.equal_range(C2Int(10));
+    assert(r.first == next(m.begin(), 3));
+    assert(r.second == next(m.begin(), 3));
+    r = m.equal_range(C2Int(12));
+    assert(r.first == next(m.begin(), 4));
+    assert(r.second == next(m.begin(), 4));
+    r = m.equal_range(C2Int(14));
+    assert(r.first == next(m.begin(), 5));
+    assert(r.second == next(m.begin(), 5));
+    r = m.equal_range(C2Int(16));
+    assert(r.first == next(m.begin(), 6));
+    assert(r.second == next(m.begin(), 6));
+    r = m.equal_range(C2Int(18));
+    assert(r.first == next(m.begin(), 7));
+    assert(r.second == next(m.begin(), 7));
+    r = m.equal_range(C2Int(20));
+    assert(r.first == next(m.begin(), 8));
+    assert(r.second == next(m.begin(), 8));
     }
     {
     typedef PrivateConstructor PC;
diff --git a/test/std/containers/associative/map/map.ops/equal_range0.pass.cpp b/test/std/containers/associative/map/map.ops/equal_range0.pass.cpp
new file mode 100644
index 0000000..c95c3df
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/equal_range0.pass.cpp
@@ -0,0 +1,34 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// XFAIL: c++03, c++11
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+int main()
+{
+    typedef std::map<int, double, transparent_less> M;
+
+    M().equal_range(C2Int{5});
+}
diff --git a/test/std/containers/associative/map/map.ops/equal_range1.fail.cpp b/test/std/containers/associative/map/map.ops/equal_range1.fail.cpp
new file mode 100644
index 0000000..8f0da08
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/equal_range1.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_no_type> M;
+
+    M().equal_range(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/map/map.ops/equal_range2.fail.cpp b/test/std/containers/associative/map/map.ops/equal_range2.fail.cpp
new file mode 100644
index 0000000..e73122d
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/equal_range2.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_private> M;
+
+    M().equal_range(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/map/map.ops/equal_range3.fail.cpp b/test/std/containers/associative/map/map.ops/equal_range3.fail.cpp
new file mode 100644
index 0000000..bb72e9e
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/equal_range3.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_not_a_type> M;
+
+    M().equal_range(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/map/map.ops/find.pass.cpp b/test/std/containers/associative/map/map.ops/find.pass.cpp
index a757844..17463b6 100644
--- a/test/std/containers/associative/map/map.ops/find.pass.cpp
+++ b/test/std/containers/associative/map/map.ops/find.pass.cpp
@@ -19,6 +19,7 @@
 
 #include "min_allocator.h"
 #include "private_constructor.hpp"
+#include "is_transparent.h"
 
 int main()
 {
@@ -200,6 +201,25 @@
     assert(r == next(m.begin(), 7));
     r = m.find(4);
     assert(r == next(m.begin(), 8));
+
+    r = m.find(C2Int(5));
+    assert(r == m.begin());
+    r = m.find(C2Int(6));
+    assert(r == next(m.begin()));
+    r = m.find(C2Int(7));
+    assert(r == next(m.begin(), 2));
+    r = m.find(C2Int(8));
+    assert(r == next(m.begin(), 3));
+    r = m.find(C2Int(9));
+    assert(r == next(m.begin(), 4));
+    r = m.find(C2Int(10));
+    assert(r == next(m.begin(), 5));
+    r = m.find(C2Int(11));
+    assert(r == next(m.begin(), 6));
+    r = m.find(C2Int(12));
+    assert(r == next(m.begin(), 7));
+    r = m.find(C2Int(4));
+    assert(r == next(m.begin(), 8));
     }
 
     {
diff --git a/test/std/containers/associative/map/map.ops/find0.pass.cpp b/test/std/containers/associative/map/map.ops/find0.pass.cpp
new file mode 100644
index 0000000..5f310b0
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/find0.pass.cpp
@@ -0,0 +1,34 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// XFAIL: c++03, c++11
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+int main()
+{
+    typedef std::map<int, double, transparent_less> M;
+
+    M().find(C2Int{5});
+}
diff --git a/test/std/containers/associative/map/map.ops/find1.fail.cpp b/test/std/containers/associative/map/map.ops/find1.fail.cpp
new file mode 100644
index 0000000..c33b5a9
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/find1.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_no_type> M;
+
+    M().find(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/map/map.ops/find2.fail.cpp b/test/std/containers/associative/map/map.ops/find2.fail.cpp
new file mode 100644
index 0000000..40bf323
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/find2.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_private> M;
+
+    M().find(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/map/map.ops/find3.fail.cpp b/test/std/containers/associative/map/map.ops/find3.fail.cpp
new file mode 100644
index 0000000..9526c0e
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/find3.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_not_a_type> M;
+
+    M().find(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/map/map.ops/lower_bound.pass.cpp b/test/std/containers/associative/map/map.ops/lower_bound.pass.cpp
index 87b84ee..3cbfbf7 100644
--- a/test/std/containers/associative/map/map.ops/lower_bound.pass.cpp
+++ b/test/std/containers/associative/map/map.ops/lower_bound.pass.cpp
@@ -19,6 +19,7 @@
 
 #include "min_allocator.h"
 #include "private_constructor.hpp"
+#include "is_transparent.h"
 
 int main()
 {
@@ -280,6 +281,41 @@
     assert(r == next(m.begin(), 7));
     r = m.lower_bound(20);
     assert(r == next(m.begin(), 8));
+
+    r = m.lower_bound(C2Int(5));
+    assert(r == m.begin());
+    r = m.lower_bound(C2Int(7));
+    assert(r == next(m.begin()));
+    r = m.lower_bound(C2Int(9));
+    assert(r == next(m.begin(), 2));
+    r = m.lower_bound(C2Int(11));
+    assert(r == next(m.begin(), 3));
+    r = m.lower_bound(C2Int(13));
+    assert(r == next(m.begin(), 4));
+    r = m.lower_bound(C2Int(15));
+    assert(r == next(m.begin(), 5));
+    r = m.lower_bound(C2Int(17));
+    assert(r == next(m.begin(), 6));
+    r = m.lower_bound(C2Int(19));
+    assert(r == next(m.begin(), 7));
+    r = m.lower_bound(C2Int(4));
+    assert(r == next(m.begin(), 0));
+    r = m.lower_bound(C2Int(6));
+    assert(r == next(m.begin(), 1));
+    r = m.lower_bound(C2Int(8));
+    assert(r == next(m.begin(), 2));
+    r = m.lower_bound(C2Int(10));
+    assert(r == next(m.begin(), 3));
+    r = m.lower_bound(C2Int(12));
+    assert(r == next(m.begin(), 4));
+    r = m.lower_bound(C2Int(14));
+    assert(r == next(m.begin(), 5));
+    r = m.lower_bound(C2Int(16));
+    assert(r == next(m.begin(), 6));
+    r = m.lower_bound(C2Int(18));
+    assert(r == next(m.begin(), 7));
+    r = m.lower_bound(C2Int(20));
+    assert(r == next(m.begin(), 8));
     }
     
     {
diff --git a/test/std/containers/associative/map/map.ops/lower_bound0.pass.cpp b/test/std/containers/associative/map/map.ops/lower_bound0.pass.cpp
new file mode 100644
index 0000000..2fc095a
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/lower_bound0.pass.cpp
@@ -0,0 +1,34 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// XFAIL: c++03, c++11
+
+// <map>
+
+// class map
+
+//       iterator lower_bound(const key_type& k);
+// const_iterator lower_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+int main()
+{
+    typedef std::map<int, double, transparent_less> M;
+
+    M().lower_bound(C2Int{5});
+}
diff --git a/test/std/containers/associative/map/map.ops/lower_bound1.fail.cpp b/test/std/containers/associative/map/map.ops/lower_bound1.fail.cpp
new file mode 100644
index 0000000..a4a986c
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/lower_bound1.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator lower_bound(const key_type& k);
+// const_iterator lower_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_no_type> M;
+
+    M().lower_bound(C2Int{5});
+    }
+}
+#endif
diff --git a/test/std/containers/associative/map/map.ops/lower_bound2.fail.cpp b/test/std/containers/associative/map/map.ops/lower_bound2.fail.cpp
new file mode 100644
index 0000000..3f6380e
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/lower_bound2.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator lower_bound(const key_type& k);
+// const_iterator lower_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_private> M;
+
+    M().lower_bound(C2Int{5});
+    }
+}
+#endif
diff --git a/test/std/containers/associative/map/map.ops/lower_bound3.fail.cpp b/test/std/containers/associative/map/map.ops/lower_bound3.fail.cpp
new file mode 100644
index 0000000..18f2c7b
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/lower_bound3.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator lower_bound(const key_type& k);
+// const_iterator lower_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_not_a_type> M;
+
+    M().lower_bound(C2Int{5});
+    }
+}
+#endif
diff --git a/test/std/containers/associative/map/map.ops/upper_bound0.pass.cpp b/test/std/containers/associative/map/map.ops/upper_bound0.pass.cpp
new file mode 100644
index 0000000..c58e55f
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/upper_bound0.pass.cpp
@@ -0,0 +1,34 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// XFAIL: c++03, c++11
+
+// <map>
+
+// class map
+
+//       iterator upper_bound(const key_type& k);
+// const_iterator upper_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+int main()
+{
+    typedef std::map<int, double, transparent_less> M;
+
+    M().upper_bound(C2Int{5});
+}
diff --git a/test/std/containers/associative/map/map.ops/upper_bound1.fail.cpp b/test/std/containers/associative/map/map.ops/upper_bound1.fail.cpp
new file mode 100644
index 0000000..4647681
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/upper_bound1.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator upper_bound(const key_type& k);
+// const_iterator upper_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_no_type> M;
+
+    M().upper_bound(C2Int{5});
+    }
+}
+#endif
diff --git a/test/std/containers/associative/map/map.ops/upper_bound2.fail.cpp b/test/std/containers/associative/map/map.ops/upper_bound2.fail.cpp
new file mode 100644
index 0000000..11852fe
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/upper_bound2.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator upper_bound(const key_type& k);
+// const_iterator upper_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_private> M;
+
+    M().upper_bound(C2Int{5});
+    }
+}
+#endif
diff --git a/test/std/containers/associative/map/map.ops/upper_bound3.fail.cpp b/test/std/containers/associative/map/map.ops/upper_bound3.fail.cpp
new file mode 100644
index 0000000..9cddeb8
--- /dev/null
+++ b/test/std/containers/associative/map/map.ops/upper_bound3.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator upper_bound(const key_type& k);
+// const_iterator upper_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::map<int, double, transparent_less_not_a_type> M;
+
+    M().upper_bound(C2Int{5});
+    }
+}
+#endif
diff --git a/test/std/containers/associative/map/map.special/swap_noexcept.pass.cpp b/test/std/containers/associative/map/map.special/swap_noexcept.pass.cpp
index c238ed2..4598e99 100644
--- a/test/std/containers/associative/map/map.special/swap_noexcept.pass.cpp
+++ b/test/std/containers/associative/map/map.special/swap_noexcept.pass.cpp
@@ -12,6 +12,10 @@
 // void swap(map& c)
 //     noexcept(!allocator_type::propagate_on_container_swap::value ||
 //              __is_nothrow_swappable<allocator_type>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<Allocator>::is_always_equal::value &&
+//              noexcept(swap(declval<Compare&>(), declval<Compare&>())));                 
 
 // This tests a conforming extension
 
@@ -33,6 +37,60 @@
     typedef std::true_type propagate_on_container_swap;
 };
 
+template <class T>
+struct some_comp2
+{
+    typedef T value_type;
+    
+    some_comp2() {}
+    some_comp2(const some_comp2&) {}
+    void deallocate(void*, unsigned) {}
+    typedef std::true_type propagate_on_container_swap;
+};
+
+#if TEST_STD_VER >= 14
+template <typename T>
+void swap(some_comp2<T>&, some_comp2<T>&) noexcept {}
+#endif
+
+template <class T>
+struct some_alloc
+{
+    typedef T value_type;
+    
+    some_alloc() {}
+    some_alloc(const some_alloc&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::true_type propagate_on_container_swap;
+};
+
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
+template <class T>
+struct some_alloc3
+{
+    typedef T value_type;
+    
+    some_alloc3() {}
+    some_alloc3(const some_alloc3&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::false_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
@@ -56,5 +114,35 @@
         C c1, c2;
         static_assert(!noexcept(swap(c1, c2)), "");
     }
+
+#if TEST_STD_VER >= 14
+    { // POCS allocator, throwable swap for comp
+    typedef std::map<MoveOnly, MoveOnly, some_comp <MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, throwable swap for comp
+    typedef std::map<MoveOnly, MoveOnly, some_comp <MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, nothrow swap for comp
+    typedef std::map<MoveOnly, MoveOnly, some_comp2<MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, nothrow swap for comp
+    typedef std::map<MoveOnly, MoveOnly, some_comp2<MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+
+    { // NOT always equal allocator, nothrow swap for comp
+    typedef std::map<MoveOnly, MoveOnly, some_comp2<MoveOnly>, some_alloc3<MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/containers/associative/multimap/multimap.modifiers/erase_iter.pass.cpp b/test/std/containers/associative/multimap/multimap.modifiers/erase_iter.pass.cpp
index d91295b..ba55351 100644
--- a/test/std/containers/associative/multimap/multimap.modifiers/erase_iter.pass.cpp
+++ b/test/std/containers/associative/multimap/multimap.modifiers/erase_iter.pass.cpp
@@ -18,6 +18,14 @@
 
 #include "min_allocator.h"
 
+struct TemplateConstructor
+{
+    template<typename T>
+    TemplateConstructor (const T&) {}
+};
+
+bool operator<(const TemplateConstructor&, const TemplateConstructor&) { return false; }
+
 int main()
 {
     {
@@ -276,4 +284,18 @@
         assert(i == m.end());
     }
 #endif
+#if __cplusplus >= 201402L
+    {
+    //  This is LWG #2059
+        typedef TemplateConstructor T;
+        typedef std::multimap<T, int> C;
+        typedef C::iterator I;
+
+        C c;
+        T a{0};
+        I it = c.find(a);
+        if (it != c.end())
+            c.erase(it);
+    }
+#endif
 }
diff --git a/test/std/containers/associative/multimap/multimap.ops/count.pass.cpp b/test/std/containers/associative/multimap/multimap.ops/count.pass.cpp
index 2f172d1..c666c29 100644
--- a/test/std/containers/associative/multimap/multimap.ops/count.pass.cpp
+++ b/test/std/containers/associative/multimap/multimap.ops/count.pass.cpp
@@ -18,6 +18,7 @@
 
 #include "min_allocator.h"
 #include "private_constructor.hpp"
+#include "is_transparent.h"
 
 int main()
 {
@@ -122,6 +123,21 @@
     assert(r == 3);
     r = m.count(10);
     assert(r == 0);
+
+    r = m.count(C2Int(4));
+    assert(r == 0);
+    r = m.count(C2Int(5));
+    assert(r == 3);
+    r = m.count(C2Int(6));
+    assert(r == 0);
+    r = m.count(C2Int(7));
+    assert(r == 3);
+    r = m.count(C2Int(8));
+    assert(r == 0);
+    r = m.count(C2Int(9));
+    assert(r == 3);
+    r = m.count(C2Int(10));
+    assert(r == 0);
     }
 
     {
diff --git a/test/std/containers/associative/multimap/multimap.ops/count0.pass.cpp b/test/std/containers/associative/multimap/multimap.ops/count0.pass.cpp
new file mode 100644
index 0000000..7da13bb
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/count0.pass.cpp
@@ -0,0 +1,34 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// XFAIL: c++03, c++11
+
+// <map>
+
+// class multimap
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+int main()
+{
+    typedef std::multimap<int, double, transparent_less> M;
+
+    M().count(C2Int{5});
+}
diff --git a/test/std/containers/associative/multimap/multimap.ops/count1.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/count1.fail.cpp
new file mode 100644
index 0000000..f30d1bf
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/count1.fail.cpp
@@ -0,0 +1,37 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    typedef std::multimap<int, double, transparent_less_no_type> M;
+
+    M().count(C2Int{5});
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/multimap/multimap.ops/count2.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/count2.fail.cpp
new file mode 100644
index 0000000..ffb7eb6
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/count2.fail.cpp
@@ -0,0 +1,37 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    typedef std::multimap<int, double, transparent_less_private> M;
+
+    M().count(C2Int{5});
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/multimap/multimap.ops/count3.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/count3.fail.cpp
new file mode 100644
index 0000000..4bb9d14
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/count3.fail.cpp
@@ -0,0 +1,37 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    typedef std::multimap<int, double, transparent_less_not_a_type> M;
+
+    M().count(C2Int{5});
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/multimap/multimap.ops/equal_range.pass.cpp b/test/std/containers/associative/multimap/multimap.ops/equal_range.pass.cpp
index a408796..5a07104 100644
--- a/test/std/containers/associative/multimap/multimap.ops/equal_range.pass.cpp
+++ b/test/std/containers/associative/multimap/multimap.ops/equal_range.pass.cpp
@@ -7,7 +7,7 @@
 //
 //===----------------------------------------------------------------------===//
 
-// <map>
+// <multimap>
 
 // class multimap
 
@@ -19,6 +19,7 @@
 
 #include "min_allocator.h"
 #include "private_constructor.hpp"
+#include "is_transparent.h"
 
 int main()
 {
@@ -219,6 +220,28 @@
     r = m.equal_range(10);
     assert(r.first == m.end());
     assert(r.second == m.end());
+
+    r = m.equal_range(C2Int(4));
+    assert(r.first == m.begin());
+    assert(r.second == m.begin());
+    r = m.equal_range(C2Int(5));
+    assert(r.first == m.begin());
+    assert(r.second == next(m.begin(), 3));
+    r = m.equal_range(C2Int(6));
+    assert(r.first == next(m.begin(), 3));
+    assert(r.second == next(m.begin(), 3));
+    r = m.equal_range(C2Int(7));
+    assert(r.first == next(m.begin(), 3));
+    assert(r.second == next(m.begin(), 6));
+    r = m.equal_range(C2Int(8));
+    assert(r.first == next(m.begin(), 6));
+    assert(r.second == next(m.begin(), 6));
+    r = m.equal_range(C2Int(9));
+    assert(r.first == next(m.begin(), 6));
+    assert(r.second == next(m.begin(), 9));
+    r = m.equal_range(C2Int(10));
+    assert(r.first == m.end());
+    assert(r.second == m.end());
     }
 
     {
diff --git a/test/std/containers/associative/multimap/multimap.ops/equal_range0.pass.cpp b/test/std/containers/associative/multimap/multimap.ops/equal_range0.pass.cpp
new file mode 100644
index 0000000..c0f0746
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/equal_range0.pass.cpp
@@ -0,0 +1,34 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// XFAIL: c++03, c++11
+
+// <map>
+
+// class multimap
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+int main()
+{
+    typedef std::multimap<int, double, transparent_less> M;
+
+    M().equal_range(C2Int{5});
+}
diff --git a/test/std/containers/associative/multimap/multimap.ops/equal_range1.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/equal_range1.fail.cpp
new file mode 100644
index 0000000..f022e94
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/equal_range1.fail.cpp
@@ -0,0 +1,37 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    typedef std::multimap<int, double, transparent_less_no_type> M;
+
+    M().equal_range(C2Int{5});
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/multimap/multimap.ops/equal_range2.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/equal_range2.fail.cpp
new file mode 100644
index 0000000..695e717
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/equal_range2.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::multimap<int, double, transparent_less_private> M;
+
+    M().equal_range(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/multimap/multimap.ops/equal_range3.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/equal_range3.fail.cpp
new file mode 100644
index 0000000..59c2855
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/equal_range3.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::multimap<int, double, transparent_less_not_a_type> M;
+
+    M().equal_range(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/multimap/multimap.ops/find.pass.cpp b/test/std/containers/associative/multimap/multimap.ops/find.pass.cpp
index fb5afa2..a60e42c 100644
--- a/test/std/containers/associative/multimap/multimap.ops/find.pass.cpp
+++ b/test/std/containers/associative/multimap/multimap.ops/find.pass.cpp
@@ -19,6 +19,7 @@
 
 #include "min_allocator.h"
 #include "private_constructor.hpp"
+#include "is_transparent.h"
 
 int main()
 {
@@ -174,6 +175,19 @@
         assert(r == next(m.begin(), 6));
         r = m.find(10);
         assert(r == m.end());
+
+        r = m.find(C2Int(5));
+        assert(r == m.begin());
+        r = m.find(C2Int(6));
+        assert(r == m.end());
+        r = m.find(C2Int(7));
+        assert(r == next(m.begin(), 3));
+        r = m.find(C2Int(8));
+        assert(r == m.end());
+        r = m.find(C2Int(9));
+        assert(r == next(m.begin(), 6));
+        r = m.find(C2Int(10));
+        assert(r == m.end());
     }
 
     {
diff --git a/test/std/containers/associative/multimap/multimap.ops/find0.pass.cpp b/test/std/containers/associative/multimap/multimap.ops/find0.pass.cpp
new file mode 100644
index 0000000..4f33698
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/find0.pass.cpp
@@ -0,0 +1,34 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// XFAIL: c++03, c++11
+
+// <map>
+
+// class multimap
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+int main()
+{
+    typedef std::multimap<int, double, transparent_less> M;
+
+    M().find(C2Int{5});
+}
diff --git a/test/std/containers/associative/multimap/multimap.ops/find1.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/find1.fail.cpp
new file mode 100644
index 0000000..e1eef03
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/find1.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::multimap<int, double, transparent_less_no_type> M;
+
+    M().find(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/multimap/multimap.ops/find2.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/find2.fail.cpp
new file mode 100644
index 0000000..4c03f58
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/find2.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class map
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::multimap<int, double, transparent_less_private> M;
+
+    M().find(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/multimap/multimap.ops/find3.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/find3.fail.cpp
new file mode 100644
index 0000000..f10bc60
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/find3.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator find(const key_type& k);
+// const_iterator find(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::multimap<int, double, transparent_less_not_a_type> M;
+
+    M().find(C2Int{5});
+    }
+}
+#endif
\ No newline at end of file
diff --git a/test/std/containers/associative/multimap/multimap.ops/lower_bound.pass.cpp b/test/std/containers/associative/multimap/multimap.ops/lower_bound.pass.cpp
index 49cf6de..38b9318 100644
--- a/test/std/containers/associative/multimap/multimap.ops/lower_bound.pass.cpp
+++ b/test/std/containers/associative/multimap/multimap.ops/lower_bound.pass.cpp
@@ -19,6 +19,7 @@
 
 #include "min_allocator.h"
 #include "private_constructor.hpp"
+#include "is_transparent.h"
 
 int main()
 {
@@ -183,6 +184,21 @@
     assert(r == next(m.begin(), 6));
     r = m.lower_bound(10);
     assert(r == m.end());
+
+    r = m.lower_bound(C2Int(4));
+    assert(r == m.begin());
+    r = m.lower_bound(C2Int(5));
+    assert(r == m.begin());
+    r = m.lower_bound(C2Int(6));
+    assert(r == next(m.begin(), 3));
+    r = m.lower_bound(C2Int(7));
+    assert(r == next(m.begin(), 3));
+    r = m.lower_bound(C2Int(8));
+    assert(r == next(m.begin(), 6));
+    r = m.lower_bound(C2Int(9));
+    assert(r == next(m.begin(), 6));
+    r = m.lower_bound(C2Int(10));
+    assert(r == m.end());
     }
 
     {
diff --git a/test/std/containers/associative/multimap/multimap.ops/lower_bound0.pass.cpp b/test/std/containers/associative/multimap/multimap.ops/lower_bound0.pass.cpp
new file mode 100644
index 0000000..c5271f6
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/lower_bound0.pass.cpp
@@ -0,0 +1,34 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// XFAIL: c++03, c++11
+
+// <map>
+
+// class multimap
+
+//       iterator lower_bound(const key_type& k);
+// const_iterator lower_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+int main()
+{
+    typedef std::multimap<int, double, transparent_less> M;
+
+    M().lower_bound(C2Int{5});
+}
diff --git a/test/std/containers/associative/multimap/multimap.ops/lower_bound1.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/lower_bound1.fail.cpp
new file mode 100644
index 0000000..b452be8
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/lower_bound1.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator lower_bound(const key_type& k);
+// const_iterator lower_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::multimap<int, double, transparent_less_no_type> M;
+
+    M().lower_bound(C2Int{5});
+    }
+}
+#endif
diff --git a/test/std/containers/associative/multimap/multimap.ops/lower_bound2.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/lower_bound2.fail.cpp
new file mode 100644
index 0000000..a2ba302
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/lower_bound2.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator lower_bound(const key_type& k);
+// const_iterator lower_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::multimap<int, double, transparent_less_private> M;
+
+    M().lower_bound(C2Int{5});
+    }
+}
+#endif
diff --git a/test/std/containers/associative/multimap/multimap.ops/lower_bound3.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/lower_bound3.fail.cpp
new file mode 100644
index 0000000..50d9fca
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/lower_bound3.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator lower_bound(const key_type& k);
+// const_iterator lower_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::multimap<int, double, transparent_less_not_a_type> M;
+
+    M().lower_bound(C2Int{5});
+    }
+}
+#endif
diff --git a/test/std/containers/associative/multimap/multimap.ops/upper_bound.pass.cpp b/test/std/containers/associative/multimap/multimap.ops/upper_bound.pass.cpp
index 1920647..7c647a9 100644
--- a/test/std/containers/associative/multimap/multimap.ops/upper_bound.pass.cpp
+++ b/test/std/containers/associative/multimap/multimap.ops/upper_bound.pass.cpp
@@ -19,6 +19,7 @@
 
 #include "min_allocator.h"
 #include "private_constructor.hpp"
+#include "is_transparent.h"
 
 int main()
 {
@@ -183,6 +184,20 @@
     assert(r == next(m.begin(), 9));
     r = m.upper_bound(10);
     assert(r == m.end());
+
+    r = m.upper_bound(C2Int(4));
+    assert(r == m.begin());
+    r = m.upper_bound(C2Int(5));
+    assert(r == next(m.begin(), 3));
+    r = m.upper_bound(C2Int(6));
+    assert(r == next(m.begin(), 3));
+    r = m.upper_bound(C2Int(7));
+    assert(r == next(m.begin(), 6));
+    r = m.upper_bound(C2Int(8));
+    assert(r == next(m.begin(), 6));
+    r = m.upper_bound(C2Int(9));
+    assert(r == next(m.begin(), 9));
+    r = m.upper_bound(C2Int(10));
     }
 
     {
diff --git a/test/std/containers/associative/multimap/multimap.ops/upper_bound0.pass.cpp b/test/std/containers/associative/multimap/multimap.ops/upper_bound0.pass.cpp
new file mode 100644
index 0000000..322c6f5
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/upper_bound0.pass.cpp
@@ -0,0 +1,34 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// XFAIL: c++03, c++11
+
+// <map>
+
+// class multimap
+
+//       iterator upper_bound(const key_type& k);
+// const_iterator upper_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+int main()
+{
+    typedef std::multimap<int, double, transparent_less> M;
+
+    M().upper_bound(C2Int{5});
+}
diff --git a/test/std/containers/associative/multimap/multimap.ops/upper_bound1.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/upper_bound1.fail.cpp
new file mode 100644
index 0000000..bb78ad6
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/upper_bound1.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator upper_bound(const key_type& k);
+// const_iterator upper_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::multimap<int, double, transparent_less_no_type> M;
+
+    M().upper_bound(C2Int{5});
+    }
+}
+#endif
diff --git a/test/std/containers/associative/multimap/multimap.ops/upper_bound2.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/upper_bound2.fail.cpp
new file mode 100644
index 0000000..a79d593
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/upper_bound2.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator upper_bound(const key_type& k);
+// const_iterator upper_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::multimap<int, double, transparent_less_private> M;
+
+    M().upper_bound(C2Int{5});
+    }
+}
+#endif
diff --git a/test/std/containers/associative/multimap/multimap.ops/upper_bound3.fail.cpp b/test/std/containers/associative/multimap/multimap.ops/upper_bound3.fail.cpp
new file mode 100644
index 0000000..1c1dc74
--- /dev/null
+++ b/test/std/containers/associative/multimap/multimap.ops/upper_bound3.fail.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <map>
+
+// class multimap
+
+//       iterator upper_bound(const key_type& k);
+// const_iterator upper_bound(const key_type& k) const;
+// 
+//   The member function templates find, count, lower_bound, upper_bound, and 
+// equal_range shall not participate in overload resolution unless the 
+// qualified-id Compare::is_transparent is valid and denotes a type
+
+
+#include <map>
+#include <cassert>
+
+#include "is_transparent.h"
+
+#if _LIBCPP_STD_VER <= 11
+#error "This test requires is C++14 (or later)"
+#else
+
+int main()
+{
+    {
+    typedef std::multimap<int, double, transparent_less_not_a_type> M;
+
+    M().upper_bound(C2Int{5});
+    }
+}
+#endif
diff --git a/test/std/containers/associative/multimap/multimap.special/swap_noexcept.pass.cpp b/test/std/containers/associative/multimap/multimap.special/swap_noexcept.pass.cpp
index 07882a4..1013c62 100644
--- a/test/std/containers/associative/multimap/multimap.special/swap_noexcept.pass.cpp
+++ b/test/std/containers/associative/multimap/multimap.special/swap_noexcept.pass.cpp
@@ -12,6 +12,10 @@
 // void swap(multimap& c)
 //     noexcept(!allocator_type::propagate_on_container_swap::value ||
 //              __is_nothrow_swappable<allocator_type>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<Allocator>::is_always_equal::value &&
+//              noexcept(swap(declval<Compare&>(), declval<Compare&>())));                 
 
 // This tests a conforming extension
 
@@ -33,6 +37,60 @@
     typedef std::true_type propagate_on_container_swap;
 };
 
+template <class T>
+struct some_comp2
+{
+    typedef T value_type;
+    
+    some_comp2() {}
+    some_comp2(const some_comp2&) {}
+    void deallocate(void*, unsigned) {}
+    typedef std::true_type propagate_on_container_swap;
+};
+
+#if TEST_STD_VER >= 14
+template <typename T>
+void swap(some_comp2<T>&, some_comp2<T>&) noexcept {}
+#endif
+
+template <class T>
+struct some_alloc
+{
+    typedef T value_type;
+    
+    some_alloc() {}
+    some_alloc(const some_alloc&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::true_type propagate_on_container_swap;
+};
+
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
+template <class T>
+struct some_alloc3
+{
+    typedef T value_type;
+    
+    some_alloc3() {}
+    some_alloc3(const some_alloc3&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::false_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
@@ -56,5 +114,35 @@
         C c1, c2;
         static_assert(!noexcept(swap(c1, c2)), "");
     }
+
+#if TEST_STD_VER >= 14
+    { // POCS allocator, throwable swap for comp
+    typedef std::multimap<MoveOnly, MoveOnly, some_comp <MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, throwable swap for comp
+    typedef std::multimap<MoveOnly, MoveOnly, some_comp <MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, nothrow swap for comp
+    typedef std::multimap<MoveOnly, MoveOnly, some_comp2<MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, nothrow swap for comp
+    typedef std::multimap<MoveOnly, MoveOnly, some_comp2<MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+
+    { // NOT always equal allocator, nothrow swap for comp
+    typedef std::map<MoveOnly, MoveOnly, some_comp2<MoveOnly>, some_alloc3<MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/containers/associative/multimap/scary.pass.cpp b/test/std/containers/associative/multimap/scary.pass.cpp
index b99d9bc..e6dc5aa 100644
--- a/test/std/containers/associative/multimap/scary.pass.cpp
+++ b/test/std/containers/associative/multimap/scary.pass.cpp
@@ -21,4 +21,5 @@
     typedef std::multimap<int, int> M2;
     M2::iterator i;
     M1::iterator j = i;
+    ((void)j);
 }
diff --git a/test/std/containers/associative/multiset/erase_iter.pass.cpp b/test/std/containers/associative/multiset/erase_iter.pass.cpp
index b665666..1d41540 100644
--- a/test/std/containers/associative/multiset/erase_iter.pass.cpp
+++ b/test/std/containers/associative/multiset/erase_iter.pass.cpp
@@ -18,6 +18,14 @@
 
 #include "min_allocator.h"
 
+struct TemplateConstructor
+{
+    template<typename T>
+    TemplateConstructor (const T&) {}
+};
+
+bool operator<(const TemplateConstructor&, const TemplateConstructor&) { return false; }
+
 int main()
 {
     {
@@ -178,4 +186,18 @@
         assert(i == m.end());
     }
 #endif
+#if __cplusplus >= 201402L
+    {
+    //  This is LWG #2059
+        typedef TemplateConstructor T;
+        typedef std::multiset<T> C;
+        typedef C::iterator I;
+
+        C c;
+        T a{0};
+        I it = c.find(a);
+        if (it != c.end())
+            c.erase(it);
+    }
+#endif
 }
diff --git a/test/std/containers/associative/multiset/multiset.special/swap_noexcept.pass.cpp b/test/std/containers/associative/multiset/multiset.special/swap_noexcept.pass.cpp
index cd5be79..8e2c67c 100644
--- a/test/std/containers/associative/multiset/multiset.special/swap_noexcept.pass.cpp
+++ b/test/std/containers/associative/multiset/multiset.special/swap_noexcept.pass.cpp
@@ -12,6 +12,10 @@
 // void swap(multiset& c)
 //     noexcept(!allocator_type::propagate_on_container_swap::value ||
 //              __is_nothrow_swappable<allocator_type>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<Allocator>::is_always_equal::value &&
+//              noexcept(swap(declval<Compare&>(), declval<Compare&>())));                 
 
 // This tests a conforming extension
 
@@ -33,6 +37,60 @@
     typedef std::true_type propagate_on_container_swap;
 };
 
+template <class T>
+struct some_comp2
+{
+    typedef T value_type;
+    
+    some_comp2() {}
+    some_comp2(const some_comp2&) {}
+    void deallocate(void*, unsigned) {}
+    typedef std::true_type propagate_on_container_swap;
+};
+
+#if TEST_STD_VER >= 14
+template <typename T>
+void swap(some_comp2<T>&, some_comp2<T>&) noexcept {}
+#endif
+
+template <class T>
+struct some_alloc
+{
+    typedef T value_type;
+    
+    some_alloc() {}
+    some_alloc(const some_alloc&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::true_type propagate_on_container_swap;
+};
+
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
+template <class T>
+struct some_alloc3
+{
+    typedef T value_type;
+    
+    some_alloc3() {}
+    some_alloc3(const some_alloc3&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::false_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
@@ -56,5 +114,35 @@
         C c1, c2;
         static_assert(!noexcept(swap(c1, c2)), "");
     }
+
+#if TEST_STD_VER >= 14
+    { // POCS allocator, throwable swap for comp
+    typedef std::multiset<MoveOnly, some_comp <MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, throwable swap for comp
+    typedef std::multiset<MoveOnly, some_comp <MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, nothrow swap for comp
+    typedef std::multiset<MoveOnly, some_comp2<MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, nothrow swap for comp
+    typedef std::multiset<MoveOnly, some_comp2<MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+
+    { // NOT always equal allocator, nothrow swap for comp
+    typedef std::multiset<MoveOnly, some_comp2<MoveOnly>, some_alloc3<MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/containers/associative/multiset/scary.pass.cpp b/test/std/containers/associative/multiset/scary.pass.cpp
index f5ee327..bc4328b 100644
--- a/test/std/containers/associative/multiset/scary.pass.cpp
+++ b/test/std/containers/associative/multiset/scary.pass.cpp
@@ -21,4 +21,5 @@
     typedef std::multiset<int> M2;
     M2::iterator i;
     M1::iterator j = i;
+    ((void)j);
 }
diff --git a/test/std/containers/associative/set/erase_iter.pass.cpp b/test/std/containers/associative/set/erase_iter.pass.cpp
index 21666c3..36828be 100644
--- a/test/std/containers/associative/set/erase_iter.pass.cpp
+++ b/test/std/containers/associative/set/erase_iter.pass.cpp
@@ -18,6 +18,14 @@
 
 #include "min_allocator.h"
 
+struct TemplateConstructor
+{
+    template<typename T>
+    TemplateConstructor (const T&) {}
+};
+
+bool operator<(const TemplateConstructor&, const TemplateConstructor&) { return false; }
+
 int main()
 {
     {
@@ -178,4 +186,18 @@
         assert(i == m.end());
     }
 #endif
+#if __cplusplus >= 201402L
+    {
+    //  This is LWG #2059
+        typedef TemplateConstructor T;
+        typedef std::set<T> C;
+        typedef C::iterator I;
+
+        C c;
+        T a{0};
+        I it = c.find(a);
+        if (it != c.end())
+            c.erase(it);
+    }
+#endif
 }
diff --git a/test/std/containers/associative/set/set.special/swap_noexcept.pass.cpp b/test/std/containers/associative/set/set.special/swap_noexcept.pass.cpp
index a478b25..3ec6976 100644
--- a/test/std/containers/associative/set/set.special/swap_noexcept.pass.cpp
+++ b/test/std/containers/associative/set/set.special/swap_noexcept.pass.cpp
@@ -12,6 +12,10 @@
 // void swap(set& c)
 //     noexcept(!allocator_type::propagate_on_container_swap::value ||
 //              __is_nothrow_swappable<allocator_type>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<Allocator>::is_always_equal::value &&
+//              noexcept(swap(declval<Compare&>(), declval<Compare&>())));                 
 
 // This tests a conforming extension
 
@@ -33,6 +37,60 @@
     typedef std::true_type propagate_on_container_swap;
 };
 
+template <class T>
+struct some_comp2
+{
+    typedef T value_type;
+    
+    some_comp2() {}
+    some_comp2(const some_comp2&) {}
+    void deallocate(void*, unsigned) {}
+    typedef std::true_type propagate_on_container_swap;
+};
+
+#if TEST_STD_VER >= 14
+template <typename T>
+void swap(some_comp2<T>&, some_comp2<T>&) noexcept {}
+#endif
+
+template <class T>
+struct some_alloc
+{
+    typedef T value_type;
+    
+    some_alloc() {}
+    some_alloc(const some_alloc&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::true_type propagate_on_container_swap;
+};
+
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
+template <class T>
+struct some_alloc3
+{
+    typedef T value_type;
+    
+    some_alloc3() {}
+    some_alloc3(const some_alloc3&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::false_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
@@ -56,5 +114,35 @@
         C c1, c2;
         static_assert(!noexcept(swap(c1, c2)), "");
     }
+
+#if TEST_STD_VER >= 14
+    { // POCS allocator, throwable swap for comp
+    typedef std::set<MoveOnly, some_comp <MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, throwable swap for comp
+    typedef std::set<MoveOnly, some_comp <MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, nothrow swap for comp
+    typedef std::set<MoveOnly, some_comp2<MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, nothrow swap for comp
+    typedef std::set<MoveOnly, some_comp2<MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+
+    { // NOT always equal allocator, nothrow swap for comp
+    typedef std::set<MoveOnly, some_comp2<MoveOnly>, some_alloc3<MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/containers/sequences/array/array.cons/initializer_list.pass.cpp b/test/std/containers/sequences/array/array.cons/initializer_list.pass.cpp
index b9775ee..34db59d 100644
--- a/test/std/containers/sequences/array/array.cons/initializer_list.pass.cpp
+++ b/test/std/containers/sequences/array/array.cons/initializer_list.pass.cpp
@@ -14,6 +14,8 @@
 #include <array>
 #include <cassert>
 
+#include "../suppress_array_warnings.h"
+
 int main()
 {
     {
diff --git a/test/std/containers/sequences/array/array.data/data.pass.cpp b/test/std/containers/sequences/array/array.data/data.pass.cpp
index 08e4fd3..80b7d06 100644
--- a/test/std/containers/sequences/array/array.data/data.pass.cpp
+++ b/test/std/containers/sequences/array/array.data/data.pass.cpp
@@ -14,6 +14,8 @@
 #include <array>
 #include <cassert>
 
+#include "../suppress_array_warnings.h"
+
 int main()
 {
     {
diff --git a/test/std/containers/sequences/array/array.data/data_const.pass.cpp b/test/std/containers/sequences/array/array.data/data_const.pass.cpp
index 8eb9762..1c9abdd 100644
--- a/test/std/containers/sequences/array/array.data/data_const.pass.cpp
+++ b/test/std/containers/sequences/array/array.data/data_const.pass.cpp
@@ -14,6 +14,8 @@
 #include <array>
 #include <cassert>
 
+#include "../suppress_array_warnings.h"
+
 int main()
 {
     {
diff --git a/test/std/containers/sequences/array/array.fill/fill.pass.cpp b/test/std/containers/sequences/array/array.fill/fill.pass.cpp
index 675f495..f98dbbd 100644
--- a/test/std/containers/sequences/array/array.fill/fill.pass.cpp
+++ b/test/std/containers/sequences/array/array.fill/fill.pass.cpp
@@ -14,6 +14,8 @@
 #include <array>
 #include <cassert>
 
+#include "../suppress_array_warnings.h"
+
 int main()
 {
     {
diff --git a/test/std/containers/sequences/array/array.size/size.pass.cpp b/test/std/containers/sequences/array/array.size/size.pass.cpp
index fe5a0d5..89b893a 100644
--- a/test/std/containers/sequences/array/array.size/size.pass.cpp
+++ b/test/std/containers/sequences/array/array.size/size.pass.cpp
@@ -14,6 +14,8 @@
 #include <array>
 #include <cassert>
 
+#include "../suppress_array_warnings.h"
+
 int main()
 {
     {
diff --git a/test/std/containers/sequences/array/array.special/swap.pass.cpp b/test/std/containers/sequences/array/array.special/swap.pass.cpp
index 08e4377..82ce904 100644
--- a/test/std/containers/sequences/array/array.special/swap.pass.cpp
+++ b/test/std/containers/sequences/array/array.special/swap.pass.cpp
@@ -14,6 +14,8 @@
 #include <array>
 #include <cassert>
 
+#include "../suppress_array_warnings.h"
+
 int main()
 {
     {
diff --git a/test/std/containers/sequences/array/array.swap/swap.pass.cpp b/test/std/containers/sequences/array/array.swap/swap.pass.cpp
index c7a4cb8..22bf657 100644
--- a/test/std/containers/sequences/array/array.swap/swap.pass.cpp
+++ b/test/std/containers/sequences/array/array.swap/swap.pass.cpp
@@ -14,6 +14,8 @@
 #include <array>
 #include <cassert>
 
+#include "../suppress_array_warnings.h"
+
 int main()
 {
     {
diff --git a/test/std/containers/sequences/array/array.tuple/get.fail.cpp b/test/std/containers/sequences/array/array.tuple/get.fail.cpp
index 4f4fbcf..6b2385d 100644
--- a/test/std/containers/sequences/array/array.tuple/get.fail.cpp
+++ b/test/std/containers/sequences/array/array.tuple/get.fail.cpp
@@ -11,15 +11,28 @@
 
 // template <size_t I, class T, size_t N> T& get(array<T, N>& a);
 
+// Prevent -Warray-bounds from issuing a diagnostic when testing with clang verify.
+#if defined(__clang__)
+#pragma clang diagnostic ignored "-Warray-bounds"
+#endif
+
 #include <array>
 #include <cassert>
 
+#include "test_macros.h"
+#include "../suppress_array_warnings.h"
+
 int main()
 {
     {
         typedef double T;
         typedef std::array<T, 3> C;
         C c = {1, 2, 3.5};
-        std::get<3>(c) = 5.5;    // Can't get element 3!
+        std::get<3>(c) = 5.5; // expected-note {{requested here}}
+#if TEST_STD_VER >= 11
+        // expected-error@array:* {{static_assert failed "Index out of bounds in std::get<> (std::array)"}}
+#else
+        // expected-error@array:* {{implicit instantiation of undefined template '__static_assert_test<false>'}}
+#endif
     }
 }
diff --git a/test/std/containers/sequences/array/array.tuple/get.pass.cpp b/test/std/containers/sequences/array/array.tuple/get.pass.cpp
index d9e242c..c455707 100644
--- a/test/std/containers/sequences/array/array.tuple/get.pass.cpp
+++ b/test/std/containers/sequences/array/array.tuple/get.pass.cpp
@@ -14,12 +14,17 @@
 #include <array>
 #include <cassert>
 
-#if __cplusplus > 201103L
+#include "test_macros.h"
+
+#include "../suppress_array_warnings.h"
+
+
+#if TEST_STD_VER > 11
 struct S {
    std::array<int, 3> a;
    int k;
    constexpr S() : a{1,2,3}, k(std::get<2>(a)) {}
-   };
+};
 
 constexpr std::array<int, 2> getArr () { return { 3, 4 }; }
 #endif
@@ -35,7 +40,7 @@
         assert(c[1] == 5.5);
         assert(c[2] == 3.5);
     }
-#if _LIBCPP_STD_VER > 11
+#if TEST_STD_VER > 11
     {
         typedef double T;
         typedef std::array<T, 3> C;
diff --git a/test/std/containers/sequences/array/array.tuple/get_const.pass.cpp b/test/std/containers/sequences/array/array.tuple/get_const.pass.cpp
index 1cbdfa4..ddc2ab2 100644
--- a/test/std/containers/sequences/array/array.tuple/get_const.pass.cpp
+++ b/test/std/containers/sequences/array/array.tuple/get_const.pass.cpp
@@ -14,6 +14,10 @@
 #include <array>
 #include <cassert>
 
+#include "test_macros.h"
+
+#include "../suppress_array_warnings.h"
+
 int main()
 {
     {
@@ -24,7 +28,7 @@
         assert(std::get<1>(c) == 2);
         assert(std::get<2>(c) == 3.5);
     }
-#if _LIBCPP_STD_VER > 11
+#if TEST_STD_VER > 11
     {
         typedef double T;
         typedef std::array<T, 3> C;
diff --git a/test/std/containers/sequences/array/array.tuple/get_rv.pass.cpp b/test/std/containers/sequences/array/array.tuple/get_rv.pass.cpp
index 8eec3ce..412c7c7 100644
--- a/test/std/containers/sequences/array/array.tuple/get_rv.pass.cpp
+++ b/test/std/containers/sequences/array/array.tuple/get_rv.pass.cpp
@@ -11,14 +11,18 @@
 
 // template <size_t I, class T, size_t N> T&& get(array<T, N>&& a);
 
+// UNSUPPORTED: c++98, c++03
+
 #include <array>
 #include <memory>
 #include <utility>
 #include <cassert>
 
+#include "../suppress_array_warnings.h"
+
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+
     {
         typedef std::unique_ptr<double> T;
         typedef std::array<T, 1> C;
@@ -26,5 +30,4 @@
         T t = std::get<0>(std::move(c));
         assert(*t == 3.5);
     }
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/test/std/containers/sequences/array/array.tuple/tuple_element.pass.cpp b/test/std/containers/sequences/array/array.tuple/tuple_element.pass.cpp
index cd1dad6..91d6b4e 100644
--- a/test/std/containers/sequences/array/array.tuple/tuple_element.pass.cpp
+++ b/test/std/containers/sequences/array/array.tuple/tuple_element.pass.cpp
@@ -14,20 +14,41 @@
 #include <array>
 #include <type_traits>
 
-int main()
+template <class T>
+void test()
 {
     {
-        typedef double T;
-        typedef std::array<T, 3> C;
-        static_assert((std::is_same<std::tuple_element<0, C>::type, T>::value), "");
-        static_assert((std::is_same<std::tuple_element<1, C>::type, T>::value), "");
-        static_assert((std::is_same<std::tuple_element<2, C>::type, T>::value), "");
+    typedef T Exp;
+    typedef std::array<T, 3> C;
+    static_assert((std::is_same<typename std::tuple_element<0, C>::type, Exp>::value), "");
+    static_assert((std::is_same<typename std::tuple_element<1, C>::type, Exp>::value), "");
+    static_assert((std::is_same<typename std::tuple_element<2, C>::type, Exp>::value), "");
     }
     {
-        typedef int T;
-        typedef std::array<T, 3> C;
-        static_assert((std::is_same<std::tuple_element<0, C>::type, T>::value), "");
-        static_assert((std::is_same<std::tuple_element<1, C>::type, T>::value), "");
-        static_assert((std::is_same<std::tuple_element<2, C>::type, T>::value), "");
+    typedef T const Exp;
+    typedef std::array<T, 3> const C;
+    static_assert((std::is_same<typename std::tuple_element<0, C>::type, Exp>::value), "");
+    static_assert((std::is_same<typename std::tuple_element<1, C>::type, Exp>::value), "");
+    static_assert((std::is_same<typename std::tuple_element<2, C>::type, Exp>::value), "");
     }
+    {
+    typedef T volatile Exp;
+    typedef std::array<T, 3> volatile C;
+    static_assert((std::is_same<typename std::tuple_element<0, C>::type, Exp>::value), "");
+    static_assert((std::is_same<typename std::tuple_element<1, C>::type, Exp>::value), "");
+    static_assert((std::is_same<typename std::tuple_element<2, C>::type, Exp>::value), "");
+    }
+    {
+    typedef T const volatile Exp;
+    typedef std::array<T, 3> const volatile C;
+    static_assert((std::is_same<typename std::tuple_element<0, C>::type, Exp>::value), "");
+    static_assert((std::is_same<typename std::tuple_element<1, C>::type, Exp>::value), "");
+    static_assert((std::is_same<typename std::tuple_element<2, C>::type, Exp>::value), "");
+    }
+}
+
+int main()
+{
+    test<double>();
+    test<int>();
 }
diff --git a/test/std/containers/sequences/array/array.tuple/tuple_size.pass.cpp b/test/std/containers/sequences/array/array.tuple/tuple_size.pass.cpp
index 83394b1..1e565d1 100644
--- a/test/std/containers/sequences/array/array.tuple/tuple_size.pass.cpp
+++ b/test/std/containers/sequences/array/array.tuple/tuple_size.pass.cpp
@@ -13,16 +13,30 @@
 
 #include <array>
 
-int main()
+template <class T, std::size_t N>
+void test()
 {
     {
-        typedef double T;
-        typedef std::array<T, 3> C;
-        static_assert((std::tuple_size<C>::value == 3), "");
+    typedef std::array<T, N> C;
+    static_assert((std::tuple_size<C>::value == N), "");
     }
     {
-        typedef double T;
-        typedef std::array<T, 0> C;
-        static_assert((std::tuple_size<C>::value == 0), "");
+    typedef std::array<T const, N> C;
+    static_assert((std::tuple_size<C>::value == N), "");
     }
+    {
+    typedef std::array<T volatile, N> C;
+    static_assert((std::tuple_size<C>::value == N), "");
+    }
+    {
+    typedef std::array<T const volatile, N> C;
+    static_assert((std::tuple_size<C>::value == N), "");
+    }
+}
+
+int main()
+{
+    test<double, 0>();
+    test<double, 3>();
+    test<double, 5>();
 }
diff --git a/test/std/containers/sequences/array/at.pass.cpp b/test/std/containers/sequences/array/at.pass.cpp
index b5cf8a5..c4f7acb 100644
--- a/test/std/containers/sequences/array/at.pass.cpp
+++ b/test/std/containers/sequences/array/at.pass.cpp
@@ -17,6 +17,10 @@
 #include <array>
 #include <cassert>
 
+#include "test_macros.h"
+
+#include "suppress_array_warnings.h"
+
 int main()
 {
     {
@@ -27,7 +31,7 @@
         assert(r1 == 1);
         r1 = 5.5;
         assert(c.front() == 5.5);
-        
+
         C::reference r2 = c.at(2);
         assert(r2 == 3.5);
         r2 = 7.5;
@@ -50,7 +54,7 @@
         catch (const std::out_of_range &) {}
     }
     
-#if _LIBCPP_STD_VER > 11 
+#if TEST_STD_VER > 11
     {
         typedef double T;
         typedef std::array<T, 3> C;
diff --git a/test/std/containers/sequences/array/begin.pass.cpp b/test/std/containers/sequences/array/begin.pass.cpp
index 9cba0d6..a6218ae 100644
--- a/test/std/containers/sequences/array/begin.pass.cpp
+++ b/test/std/containers/sequences/array/begin.pass.cpp
@@ -14,6 +14,8 @@
 #include <array>
 #include <cassert>
 
+#include "suppress_array_warnings.h"
+
 int main()
 {
     {
@@ -27,6 +29,4 @@
         *i = 5.5;
         assert(c[0] == 5.5);
     }
-    {
-    }
 }
diff --git a/test/std/containers/sequences/array/contiguous.pass.cpp b/test/std/containers/sequences/array/contiguous.pass.cpp
new file mode 100644
index 0000000..27933b0
--- /dev/null
+++ b/test/std/containers/sequences/array/contiguous.pass.cpp
@@ -0,0 +1,31 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <array>
+
+// An array is a contiguous container
+
+#include <array>
+#include <cassert>
+
+template <class C>
+void test_contiguous ( const C &c )
+{
+    for ( size_t i = 0; i < c.size(); ++i )
+        assert ( *(c.begin() + i) == *(std::addressof(*c.begin()) + i));
+}
+
+int main()
+{
+    {
+        typedef double T;
+        typedef std::array<T, 3> C;
+        test_contiguous (C());
+    }
+}
diff --git a/test/std/containers/sequences/array/front_back.pass.cpp b/test/std/containers/sequences/array/front_back.pass.cpp
index 45a963b..ebe3a18 100644
--- a/test/std/containers/sequences/array/front_back.pass.cpp
+++ b/test/std/containers/sequences/array/front_back.pass.cpp
@@ -17,6 +17,10 @@
 #include <array>
 #include <cassert>
 
+#include "test_macros.h"
+
+#include "suppress_array_warnings.h"
+
 int main()
 {
     {
@@ -45,12 +49,12 @@
         assert(r2 == 3.5);
     }
 
-#if _LIBCPP_STD_VER > 11 
+#if TEST_STD_VER > 11
     {
         typedef double T;
         typedef std::array<T, 3> C;
         constexpr C c = {1, 2, 3.5};
-        
+
         constexpr T t1 = c.front();
         static_assert (t1 == 1, "");
 
diff --git a/test/std/containers/sequences/array/indexing.pass.cpp b/test/std/containers/sequences/array/indexing.pass.cpp
index e4dda0d..c550d14 100644
--- a/test/std/containers/sequences/array/indexing.pass.cpp
+++ b/test/std/containers/sequences/array/indexing.pass.cpp
@@ -17,6 +17,10 @@
 #include <array>
 #include <cassert>
 
+#include "test_macros.h"
+
+#include "suppress_array_warnings.h"
+
 int main()
 {
     {
@@ -42,13 +46,13 @@
         C::const_reference r2 = c[2];
         assert(r2 == 3.5);
     }
-    
-#if _LIBCPP_STD_VER > 11 
+
+#if TEST_STD_VER > 11
     {
         typedef double T;
         typedef std::array<T, 3> C;
         constexpr C c = {1, 2, 3.5};
-        
+
         constexpr T t1 = c[0];
         static_assert (t1 == 1, "");
 
diff --git a/test/std/containers/sequences/array/suppress_array_warnings.h b/test/std/containers/sequences/array/suppress_array_warnings.h
new file mode 100644
index 0000000..1dde3d3
--- /dev/null
+++ b/test/std/containers/sequences/array/suppress_array_warnings.h
@@ -0,0 +1,8 @@
+#ifndef SUPPRESS_ARRAY_WARNINGS_H
+#define SUPPRESS_ARRAY_WARNINGS_H
+
+// std::array is explicitly allowed to be initialized with A a = { init-list };.
+// Disable the missing braces warning for this reason.
+#pragma GCC diagnostic ignored "-Wmissing-braces"
+
+#endif // SUPPRESS_ARRAY_WARNINGS
diff --git a/test/std/containers/sequences/deque/deque.capacity/resize_size.pass.cpp b/test/std/containers/sequences/deque/deque.capacity/resize_size.pass.cpp
index 522f839..84f04f9 100644
--- a/test/std/containers/sequences/deque/deque.capacity/resize_size.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.capacity/resize_size.pass.cpp
@@ -14,6 +14,7 @@
 #include <deque>
 #include <cassert>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
 template <class C>
@@ -58,7 +59,6 @@
 void
 testN(int start, int N, int M)
 {
-    typedef typename C::const_iterator CI;
     C c1 = make<C>(N, start);
     test(c1, M);
 }
@@ -73,7 +73,7 @@
             for (int k = 0; k < N; ++k)
                 testN<std::deque<int> >(rng[i], rng[j], rng[k]);
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
diff --git a/test/std/containers/sequences/deque/deque.capacity/resize_size_value.pass.cpp b/test/std/containers/sequences/deque/deque.capacity/resize_size_value.pass.cpp
index 9eb514b..2bf2423 100644
--- a/test/std/containers/sequences/deque/deque.capacity/resize_size_value.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.capacity/resize_size_value.pass.cpp
@@ -14,6 +14,7 @@
 #include <deque>
 #include <cassert>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
 template <class C>
@@ -58,7 +59,6 @@
 void
 testN(int start, int N, int M)
 {
-    typedef typename C::const_iterator CI;
     C c1 = make<C>(N, start);
     test(c1, M, -10);
 }
@@ -73,7 +73,7 @@
             for (int k = 0; k < N; ++k)
                 testN<std::deque<int> >(rng[i], rng[j], rng[k]);
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
diff --git a/test/std/containers/sequences/deque/deque.capacity/shrink_to_fit.pass.cpp b/test/std/containers/sequences/deque/deque.capacity/shrink_to_fit.pass.cpp
index fb00069..0cf0387 100644
--- a/test/std/containers/sequences/deque/deque.capacity/shrink_to_fit.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.capacity/shrink_to_fit.pass.cpp
@@ -14,6 +14,7 @@
 #include <deque>
 #include <cassert>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
 template <class C>
@@ -51,7 +52,6 @@
 void
 testN(int start, int N)
 {
-    typedef typename C::const_iterator CI;
     C c1 = make<C>(N, start);
     test(c1);
 }
@@ -65,7 +65,7 @@
         for (int j = 0; j < N; ++j)
             testN<std::deque<int> >(rng[i], rng[j]);
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
diff --git a/test/std/containers/sequences/deque/deque.cons/assign_iter_iter.pass.cpp b/test/std/containers/sequences/deque/deque.cons/assign_iter_iter.pass.cpp
index 51a37cc..6507f58 100644
--- a/test/std/containers/sequences/deque/deque.cons/assign_iter_iter.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.cons/assign_iter_iter.pass.cpp
@@ -15,6 +15,7 @@
 #include <deque>
 #include <cassert>
 
+#include "test_macros.h"
 #include "test_iterators.h"
 #include "min_allocator.h"
 
@@ -44,7 +45,6 @@
 void
 test(C& c1, const C& c2)
 {
-    std::size_t c1_osize = c1.size();
     c1.assign(c2.begin(), c2.end());
     assert(distance(c1.begin(), c1.end()) == c1.size());
     assert(c1 == c2);
@@ -54,8 +54,6 @@
 void
 testN(int start, int N, int M)
 {
-    typedef typename C::iterator I;
-    typedef typename C::const_iterator CI;
     C c1 = make<C>(N, start);
     C c2 = make<C>(M);
     test(c1, c2);
@@ -67,7 +65,6 @@
 {
     typedef typename C::const_iterator CI;
     typedef input_iterator<CI> ICI;
-    std::size_t c1_osize = c1.size();
     c1.assign(ICI(c2.begin()), ICI(c2.end()));
     assert(distance(c1.begin(), c1.end()) == c1.size());
     assert(c1 == c2);
@@ -77,8 +74,6 @@
 void
 testNI(int start, int N, int M)
 {
-    typedef typename C::iterator I;
-    typedef typename C::const_iterator CI;
     C c1 = make<C>(N, start);
     C c2 = make<C>(M);
     testI(c1, c2);
@@ -95,7 +90,7 @@
                 testN<std::deque<int> >(rng[i], rng[j], rng[k]);
     testNI<std::deque<int> >(1500, 2000, 1000);
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
diff --git a/test/std/containers/sequences/deque/deque.cons/assign_size_value.pass.cpp b/test/std/containers/sequences/deque/deque.cons/assign_size_value.pass.cpp
index 3ab79a0..e00e044 100644
--- a/test/std/containers/sequences/deque/deque.cons/assign_size_value.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.cons/assign_size_value.pass.cpp
@@ -14,6 +14,7 @@
 #include <deque>
 #include <cassert>
 
+#include "test_macros.h"
 #include "test_iterators.h"
 #include "min_allocator.h"
 
@@ -44,7 +45,6 @@
 test(C& c1, int size, int v)
 {
     typedef typename C::const_iterator CI;
-    std::size_t c1_osize = c1.size();
     c1.assign(size, v);
     assert(c1.size() == size);
     assert(distance(c1.begin(), c1.end()) == c1.size());
@@ -56,8 +56,6 @@
 void
 testN(int start, int N, int M)
 {
-    typedef typename C::iterator I;
-    typedef typename C::const_iterator CI;
     C c1 = make<C>(N, start);
     test(c1, M, -10);
 }
@@ -72,7 +70,7 @@
             for (int k = 0; k < N; ++k)
                 testN<std::deque<int> >(rng[i], rng[j], rng[k]);
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
diff --git a/test/std/containers/sequences/deque/deque.modifiers/emplace.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/emplace.pass.cpp
index 7a0a251..713f215 100644
--- a/test/std/containers/sequences/deque/deque.modifiers/emplace.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.modifiers/emplace.pass.cpp
@@ -11,13 +11,14 @@
 
 // template <class... Args> iterator emplace(const_iterator p, Args&&... args);
 
+// UNSUPPORTED: c++98, c++03
+
 #include <deque>
 #include <cassert>
 
 #include "../../../Emplaceable.h"
 #include "min_allocator.h"
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
 template <class C>
 C
@@ -45,7 +46,6 @@
 void
 test(int P, C& c1)
 {
-    typedef typename C::iterator I;
     typedef typename C::const_iterator CI;
     std::size_t c1_osize = c1.size();
     CI i = c1.emplace(c1.begin() + P, Emplaceable(1, 2.5));
@@ -59,8 +59,6 @@
 void
 testN(int start, int N)
 {
-    typedef typename C::iterator I;
-    typedef typename C::const_iterator CI;
     for (int i = 0; i <= 3; ++i)
     {
         if (0 <= i && i <= N)
@@ -87,11 +85,9 @@
     }
 }
 
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
@@ -99,7 +95,6 @@
         for (int j = 0; j < N; ++j)
             testN<std::deque<Emplaceable> >(rng[i], rng[j]);
     }
-#if __cplusplus >= 201103L
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
@@ -107,6 +102,4 @@
         for (int j = 0; j < N; ++j)
             testN<std::deque<Emplaceable, min_allocator<Emplaceable>> >(rng[i], rng[j]);
     }
-#endif
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/test/std/containers/sequences/deque/deque.modifiers/erase_iter.invalidation.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/erase_iter.invalidation.pass.cpp
new file mode 100644
index 0000000..49465cd
--- /dev/null
+++ b/test/std/containers/sequences/deque/deque.modifiers/erase_iter.invalidation.pass.cpp
@@ -0,0 +1,70 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <deque>
+
+// iterator erase(const_iterator f)
+
+//  Erasing items from the beginning or the end of a deque shall not invalidate iterators
+//  to items that were not erased.
+
+#include <deque>
+#include <cassert>
+
+template <typename C>
+void del_at_start(C c)
+{
+    typename C::iterator first = c.begin();
+    typename C::iterator it1 = first + 1;
+    typename C::iterator it2 = c.end() - 1;
+    
+    c.erase (first);
+    
+    typename C::iterator it3 = c.begin();
+    typename C::iterator it4 = c.end() - 1;
+    assert(  it1 ==   it3);
+    assert( *it1 ==  *it3);
+    assert(&*it1 == &*it3);
+    assert(  it2 ==   it4);
+    assert( *it2 ==  *it4);
+    assert(&*it2 == &*it4);
+}
+
+template <typename C>
+void del_at_end(C c)
+{
+    typename C::iterator first = c.end() - 1;
+    typename C::iterator it1 = c.begin();
+    typename C::iterator it2 = first - 1;
+    
+    c.erase (first);
+
+    typename C::iterator it3 = c.begin();
+    typename C::iterator it4 = c.end() - 1;
+    assert(  it1 ==   it3);
+    assert( *it1 ==  *it3);
+    assert(&*it1 == &*it3);
+    assert(  it2 ==   it4);
+    assert( *it2 ==  *it4);
+    assert(&*it2 == &*it4);
+}
+
+int main()
+{
+    std::deque<int> queue;
+    for (int i = 0; i < 20; ++i)
+        queue.push_back(i);
+    
+    while (queue.size() > 1)
+    {
+        del_at_start(queue);
+        del_at_end(queue);
+        queue.pop_back();
+    }
+}
diff --git a/test/std/containers/sequences/deque/deque.modifiers/erase_iter_iter.invalidation.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/erase_iter_iter.invalidation.pass.cpp
new file mode 100644
index 0000000..c785e26
--- /dev/null
+++ b/test/std/containers/sequences/deque/deque.modifiers/erase_iter_iter.invalidation.pass.cpp
@@ -0,0 +1,78 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <deque>
+
+// iterator erase(const_iterator f, const_iterator l)
+
+//  Erasing items from the beginning or the end of a deque shall not invalidate iterators
+//  to items that were not erased.
+
+
+#include <deque>
+#include <cstdint>
+#include <cassert>
+
+template <typename C>
+void del_at_start(C c, size_t num)
+{
+    typename C::iterator first = c.begin();
+    typename C::iterator last  = first + num;
+    typename C::iterator it1 = last;
+    typename C::iterator it2 = c.end() - 1;
+    
+    c.erase (first, last);
+    
+    typename C::iterator it3 = c.begin();
+    typename C::iterator it4 = c.end() - 1;
+    assert(  it1 ==   it3);
+    assert( *it1 ==  *it3);
+    assert(&*it1 == &*it3);
+    assert(  it2 ==   it4);
+    assert( *it2 ==  *it4);
+    assert(&*it2 == &*it4);
+}
+    
+template <typename C>
+void del_at_end(C c, size_t num)
+{
+    typename C::iterator last  = c.end();
+    typename C::iterator first = last - num;
+    typename C::iterator it1 = c.begin();
+    typename C::iterator it2 = first - 1;
+    
+    c.erase (first, last);
+
+    typename C::iterator it3 = c.begin();
+    typename C::iterator it4 = c.end() - 1;
+    assert(  it1 ==   it3);
+    assert( *it1 ==  *it3);
+    assert(&*it1 == &*it3);
+    assert(  it2 ==   it4);
+    assert( *it2 ==  *it4);
+    assert(&*it2 == &*it4);
+}
+
+
+int main()
+{
+    std::deque<int> queue;
+    for (int i = 0; i < 20; ++i)
+        queue.push_back(i);
+
+    while (queue.size() > 1)
+    {
+        for (size_t i = 1; i < queue.size(); ++i)
+        {
+            del_at_start(queue, i);
+            del_at_end  (queue, i);
+        }
+        queue.pop_back();
+    }
+}
diff --git a/test/std/containers/sequences/deque/deque.modifiers/insert_iter_iter.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/insert_iter_iter.pass.cpp
index ecb95d7..fbe3cb6 100644
--- a/test/std/containers/sequences/deque/deque.modifiers/insert_iter_iter.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.modifiers/insert_iter_iter.pass.cpp
@@ -17,6 +17,7 @@
 #include <deque>
 #include <cassert>
 
+#include "test_macros.h"
 #include "test_iterators.h"
 #include "MoveOnly.h"
 #include "../../../stack_allocator.h"
@@ -49,7 +50,6 @@
 test(int P, const C& c0, const C& c2)
 {
     {
-    typedef typename C::iterator I;
     typedef typename C::const_iterator CI;
     typedef input_iterator<CI> BCI;
     C c1 = c0;
@@ -67,7 +67,6 @@
         assert(*i == j);
     }
     {
-    typedef typename C::iterator I;
     typedef typename C::const_iterator CI;
     typedef forward_iterator<CI> BCI;
     C c1 = c0;
@@ -85,7 +84,6 @@
         assert(*i == j);
     }
     {
-    typedef typename C::iterator I;
     typedef typename C::const_iterator CI;
     typedef bidirectional_iterator<CI> BCI;
     C c1 = c0;
@@ -108,8 +106,6 @@
 void
 testN(int start, int N, int M)
 {
-    typedef typename C::iterator I;
-    typedef typename C::const_iterator CI;
     for (int i = 0; i <= 3; ++i)
     {
         if (0 <= i && i <= N)
@@ -170,7 +166,6 @@
 void
 testI(int P, C& c1, const C& c2)
 {
-    typedef typename C::iterator I;
     typedef typename C::const_iterator CI;
     typedef input_iterator<CI> ICI;
     std::size_t c1_osize = c1.size();
@@ -191,8 +186,6 @@
 void
 testNI(int start, int N, int M)
 {
-    typedef typename C::iterator I;
-    typedef typename C::const_iterator CI;
     for (int i = 0; i <= 3; ++i)
     {
         if (0 <= i && i <= N)
@@ -244,7 +237,7 @@
 void
 test_move()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#if TEST_STD_VER >= 11
     C c;
     typedef typename C::const_iterator CI;
     {
@@ -263,7 +256,7 @@
     j = 0;
     for (CI i = c.begin(); i != c.end(); ++i, ++j)
         assert(*i == MoveOnly(j));
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#endif
 }
 
 int main()
@@ -276,11 +269,11 @@
             for (int k = 0; k < N; ++k)
                 testN<std::deque<int> >(rng[i], rng[j], rng[k]);
     testNI<std::deque<int> >(1500, 2000, 1000);
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#if TEST_STD_VER >= 11
     test_move<std::deque<MoveOnly, stack_allocator<MoveOnly, 2000> > >();
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#endif
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
diff --git a/test/std/containers/sequences/deque/deque.modifiers/insert_rvalue.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/insert_rvalue.pass.cpp
index b7e73f2..3c7b0fe 100644
--- a/test/std/containers/sequences/deque/deque.modifiers/insert_rvalue.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.modifiers/insert_rvalue.pass.cpp
@@ -11,13 +11,14 @@
 
 // iterator insert (const_iterator p, value_type&& v);
 
+// UNSUPPORTED: c++98, c++03
+
 #include <deque>
 #include <cassert>
 
 #include "MoveOnly.h"
 #include "min_allocator.h"
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
 template <class C>
 C
@@ -45,7 +46,6 @@
 void
 test(int P, C& c1, int x)
 {
-    typedef typename C::iterator I;
     typedef typename C::const_iterator CI;
     std::size_t c1_osize = c1.size();
     CI i = c1.insert(c1.begin() + P, MoveOnly(x));
@@ -65,8 +65,6 @@
 void
 testN(int start, int N)
 {
-    typedef typename C::iterator I;
-    typedef typename C::const_iterator CI;
     for (int i = 0; i <= 3; ++i)
     {
         if (0 <= i && i <= N)
@@ -93,11 +91,8 @@
     }
 }
 
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
@@ -105,7 +100,6 @@
         for (int j = 0; j < N; ++j)
             testN<std::deque<MoveOnly> >(rng[i], rng[j]);
     }
-#if __cplusplus >= 201103L
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
@@ -113,6 +107,4 @@
         for (int j = 0; j < N; ++j)
             testN<std::deque<MoveOnly, min_allocator<MoveOnly>> >(rng[i], rng[j]);
     }
-#endif
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/test/std/containers/sequences/deque/deque.modifiers/insert_size_value.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/insert_size_value.pass.cpp
index 2737dfb..0efe3b4 100644
--- a/test/std/containers/sequences/deque/deque.modifiers/insert_size_value.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.modifiers/insert_size_value.pass.cpp
@@ -16,6 +16,7 @@
 #include <deque>
 #include <cassert>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
 template <class C>
@@ -44,7 +45,6 @@
 void
 test(int P, C& c1, int size, int x)
 {
-    typedef typename C::iterator I;
     typedef typename C::const_iterator CI;
     std::size_t c1_osize = c1.size();
     CI i = c1.insert(c1.begin() + P, size, x);
@@ -64,8 +64,6 @@
 void
 testN(int start, int N, int M)
 {
-    typedef typename C::iterator I;
-    typedef typename C::const_iterator CI;
     for (int i = 0; i <= 3; ++i)
     {
         if (0 <= i && i <= N)
@@ -145,7 +143,7 @@
                 testN<std::deque<int> >(rng[i], rng[j], rng[k]);
     self_reference_test<std::deque<int> >();
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
diff --git a/test/std/containers/sequences/deque/deque.modifiers/insert_value.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/insert_value.pass.cpp
index fbbaad4..04c4ca4 100644
--- a/test/std/containers/sequences/deque/deque.modifiers/insert_value.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.modifiers/insert_value.pass.cpp
@@ -14,6 +14,7 @@
 #include <deque>
 #include <cassert>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
 template <class C>
@@ -42,7 +43,6 @@
 void
 test(int P, C& c1, int x)
 {
-    typedef typename C::iterator I;
     typedef typename C::const_iterator CI;
     std::size_t c1_osize = c1.size();
     CI i = c1.insert(c1.begin() + P, x);
@@ -62,8 +62,6 @@
 void
 testN(int start, int N)
 {
-    typedef typename C::iterator I;
-    typedef typename C::const_iterator CI;
     for (int i = 0; i <= 3; ++i)
     {
         if (0 <= i && i <= N)
@@ -126,7 +124,7 @@
             testN<std::deque<int> >(rng[i], rng[j]);
     self_reference_test<std::deque<int> >();
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
diff --git a/test/std/containers/sequences/deque/deque.modifiers/pop_back.invalidation.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/pop_back.invalidation.pass.cpp
new file mode 100644
index 0000000..1d84f73
--- /dev/null
+++ b/test/std/containers/sequences/deque/deque.modifiers/pop_back.invalidation.pass.cpp
@@ -0,0 +1,49 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <deque>
+
+// void pop_back()
+
+//  Erasing items from the beginning or the end of a deque shall not invalidate iterators
+//  to items that were not erased.
+
+#include <deque>
+#include <cassert>
+
+template <typename C>
+void test(C c)
+{
+    typename C::iterator it1 = c.begin();
+    typename C::iterator it2 = c.end() - 2;
+    
+    c.pop_back();
+    
+    typename C::iterator it3 = c.begin();
+    typename C::iterator it4 = c.end() - 1;
+    assert(  it1 ==   it3);
+    assert( *it1 ==  *it3);
+    assert(&*it1 == &*it3);
+    assert(  it2 ==   it4);
+    assert( *it2 ==  *it4);
+    assert(&*it2 == &*it4);
+}
+
+int main()
+{
+    std::deque<int> queue;
+    for (int i = 0; i < 20; ++i)
+        queue.push_back(i);
+    
+    while (queue.size() > 1)
+    {
+        test(queue);
+        queue.pop_back();
+    }
+}
diff --git a/test/std/containers/sequences/deque/deque.modifiers/pop_front.invalidation.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/pop_front.invalidation.pass.cpp
new file mode 100644
index 0000000..78317f3
--- /dev/null
+++ b/test/std/containers/sequences/deque/deque.modifiers/pop_front.invalidation.pass.cpp
@@ -0,0 +1,49 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <deque>
+
+// void pop_front()
+
+//  Erasing items from the beginning or the end of a deque shall not invalidate iterators
+//  to items that were not erased.
+
+#include <deque>
+#include <cassert>
+
+template <typename C>
+void test(C c)
+{
+    typename C::iterator it1 = c.begin() + 1;
+    typename C::iterator it2 = c.end() - 1;
+    
+    c.pop_front();
+    
+    typename C::iterator it3 = c.begin();
+    typename C::iterator it4 = c.end() - 1;
+    assert(  it1 ==   it3);
+    assert( *it1 ==  *it3);
+    assert(&*it1 == &*it3);
+    assert(  it2 ==   it4);
+    assert( *it2 ==  *it4);
+    assert(&*it2 == &*it4);
+}
+
+int main()
+{
+    std::deque<int> queue;
+    for (int i = 0; i < 20; ++i)
+        queue.push_back(i);
+    
+    while (queue.size() > 1)
+    {
+        test(queue);
+        queue.pop_back();
+    }
+}
diff --git a/test/std/containers/sequences/deque/deque.modifiers/push_back_exception_safety.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/push_back_exception_safety.pass.cpp
index 3e62879..8ad6b53 100644
--- a/test/std/containers/sequences/deque/deque.modifiers/push_back_exception_safety.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.modifiers/push_back_exception_safety.pass.cpp
@@ -12,12 +12,12 @@
 // void push_back(const value_type& x);
 
 #include <deque>
+#include "test_allocator.h"
 #include <cassert>
 
 // Flag that makes the copy constructor for CMyClass throw an exception
 static bool gCopyConstructorShouldThow = false;
 
-
 class CMyClass {
     public: CMyClass(int tag);
     public: CMyClass(const CMyClass& iOther);
@@ -25,6 +25,7 @@
 
     bool equal(const CMyClass &rhs) const
         { return fTag == rhs.fTag && fMagicValue == rhs.fMagicValue; }
+        
     private:
         int fMagicValue;
         int fTag;
@@ -66,6 +67,7 @@
 int main()
 {
     CMyClass instance(42);
+    {
     std::deque<CMyClass> vec;
 
     vec.push_back(instance);
@@ -74,8 +76,26 @@
     gCopyConstructorShouldThow = true;
     try {
         vec.push_back(instance);
+        assert(false);
+    }
+    catch (...) {
+	    gCopyConstructorShouldThow = false;
+        assert(vec==vec2);
+    }
+	}
+	
+	{
+	typedef std::deque<CMyClass, test_allocator<CMyClass> > C;
+    C vec;
+    C vec2(vec);
+
+	C::allocator_type::throw_after = 1;
+    try {
+        vec.push_back(instance);
+        assert(false);
     }
     catch (...) {
         assert(vec==vec2);
     }
+    }
 }
diff --git a/test/std/containers/sequences/deque/deque.modifiers/push_front_exception_safety.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/push_front_exception_safety.pass.cpp
index 6ae06db..e01b2a2 100644
--- a/test/std/containers/sequences/deque/deque.modifiers/push_front_exception_safety.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.modifiers/push_front_exception_safety.pass.cpp
@@ -13,6 +13,7 @@
 
 #include <deque>
 #include <cassert>
+#include "test_allocator.h"
 
 // Flag that makes the copy constructor for CMyClass throw an exception
 static bool gCopyConstructorShouldThow = false;
@@ -66,6 +67,7 @@
 int main()
 {
     CMyClass instance(42);
+    {
     std::deque<CMyClass> vec;
 
     vec.push_front(instance);
@@ -74,8 +76,26 @@
     gCopyConstructorShouldThow = true;
     try {
         vec.push_front(instance);
+        assert(false);
+    }
+    catch (...) {
+	    gCopyConstructorShouldThow = false;
+        assert(vec==vec2);
+    }
+	}
+	
+	{
+	typedef std::deque<CMyClass, test_allocator<CMyClass> > C;
+    C vec;
+    C vec2(vec);
+
+	C::allocator_type::throw_after = 1;
+    try {
+        vec.push_front(instance);
+        assert(false);
     }
     catch (...) {
         assert(vec==vec2);
     }
+    }
 }
diff --git a/test/std/containers/sequences/deque/deque.special/swap_noexcept.pass.cpp b/test/std/containers/sequences/deque/deque.special/swap_noexcept.pass.cpp
index 3c94eb0..83bcac8 100644
--- a/test/std/containers/sequences/deque/deque.special/swap_noexcept.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.special/swap_noexcept.pass.cpp
@@ -12,6 +12,9 @@
 // void swap(deque& c)
 //     noexcept(!allocator_type::propagate_on_container_swap::value ||
 //              __is_nothrow_swappable<allocator_type>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<Allocator>::is_always_equal::value);
 
 // This tests a conforming extension
 
@@ -33,6 +36,19 @@
     typedef std::true_type propagate_on_container_swap;
 };
 
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
@@ -54,7 +70,21 @@
     {
         typedef std::deque<MoveOnly, some_alloc<MoveOnly>> C;
         C c1, c2;
+#if TEST_STD_VER >= 14
+    //  In c++14, if POCS is set, swapping the allocator is required not to throw
+        static_assert( noexcept(swap(c1, c2)), "");
+#else
         static_assert(!noexcept(swap(c1, c2)), "");
+#endif
     }
+#if TEST_STD_VER >= 14
+    {
+        typedef std::deque<MoveOnly, some_alloc2<MoveOnly>> C;
+        C c1, c2;
+    //  if the allocators are always equal, then the swap can be noexcept
+        static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/containers/sequences/forwardlist/forwardlist.ops/splice_after_one.pass.cpp b/test/std/containers/sequences/forwardlist/forwardlist.ops/splice_after_one.pass.cpp
index 296ffcd..349a387 100644
--- a/test/std/containers/sequences/forwardlist/forwardlist.ops/splice_after_one.pass.cpp
+++ b/test/std/containers/sequences/forwardlist/forwardlist.ops/splice_after_one.pass.cpp
@@ -15,6 +15,7 @@
 #include <cassert>
 #include <iterator>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
 typedef int T;
@@ -44,7 +45,6 @@
 {
     typename C::const_iterator i = c.begin();
     int n = 0;
-    int d = 1;
     if (p == f || p == f+1)
     {
         for (n = 0; n < size_t1; ++n, ++i)
@@ -106,7 +106,7 @@
         }
     }
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
     // splicing different containers
     typedef std::forward_list<T, min_allocator<T>> C;
diff --git a/test/std/containers/sequences/forwardlist/forwardlist.spec/equal.pass.cpp b/test/std/containers/sequences/forwardlist/forwardlist.spec/equal.pass.cpp
index ca673b5..9f01fed 100644
--- a/test/std/containers/sequences/forwardlist/forwardlist.spec/equal.pass.cpp
+++ b/test/std/containers/sequences/forwardlist/forwardlist.spec/equal.pass.cpp
@@ -22,12 +22,12 @@
 #include <algorithm>
 #include <cassert>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
 template <class C>
 void test(int N, int M)
 {
-    typedef typename C::value_type T;
     C c1;
     for (int i = 0; i < N; ++i)
         c1.push_front(i);
@@ -52,7 +52,7 @@
     for (int i = 0; i < 10; ++i)
         for (int j = 0; j < 10; ++j)
             test<std::forward_list<int> >(i, j);
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     for (int i = 0; i < 10; ++i)
         for (int j = 0; j < 10; ++j)
             test<std::forward_list<int, min_allocator<int>> >(i, j);
diff --git a/test/std/containers/sequences/forwardlist/forwardlist.spec/relational.pass.cpp b/test/std/containers/sequences/forwardlist/forwardlist.spec/relational.pass.cpp
index 42e245d..e65e064 100644
--- a/test/std/containers/sequences/forwardlist/forwardlist.spec/relational.pass.cpp
+++ b/test/std/containers/sequences/forwardlist/forwardlist.spec/relational.pass.cpp
@@ -30,12 +30,12 @@
 #include <algorithm>
 #include <cassert>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
 template <class C>
 void test(int N, int M)
 {
-    typedef typename C::value_type T;
     C c1;
     for (int i = 0; i < N; ++i)
         c1.push_front(i);
@@ -57,7 +57,7 @@
     for (int i = 0; i < 10; ++i)
         for (int j = 0; j < 10; ++j)
             test<std::forward_list<int> >(i, j);
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     for (int i = 0; i < 10; ++i)
         for (int j = 0; j < 10; ++j)
             test<std::forward_list<int, min_allocator<int>> >(i, j);
diff --git a/test/std/containers/sequences/forwardlist/forwardlist.spec/swap_noexcept.pass.cpp b/test/std/containers/sequences/forwardlist/forwardlist.spec/swap_noexcept.pass.cpp
index e36ba5b..cbe8142 100644
--- a/test/std/containers/sequences/forwardlist/forwardlist.spec/swap_noexcept.pass.cpp
+++ b/test/std/containers/sequences/forwardlist/forwardlist.spec/swap_noexcept.pass.cpp
@@ -12,6 +12,9 @@
 // void swap(forward_list& c)
 //     noexcept(!allocator_type::propagate_on_container_swap::value ||
 //              __is_nothrow_swappable<allocator_type>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(is_always_equal<allocator_type>::value);
 
 // This tests a conforming extension
 
@@ -33,6 +36,19 @@
     typedef std::true_type propagate_on_container_swap;
 };
 
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
@@ -54,7 +70,21 @@
     {
         typedef std::forward_list<MoveOnly, some_alloc<MoveOnly>> C;
         C c1, c2;
+#if TEST_STD_VER >= 14
+    //  In c++14, if POCS is set, swapping the allocator is required not to throw
+        static_assert( noexcept(swap(c1, c2)), "");
+#else
         static_assert(!noexcept(swap(c1, c2)), "");
+#endif
     }
+#if TEST_STD_VER >= 14
+    {
+        typedef std::forward_list<MoveOnly, some_alloc2<MoveOnly>> C;
+        C c1, c2;
+    //  if the allocators are always equal, then the swap can be noexcept
+        static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/containers/sequences/list/list.modifiers/insert_iter_iter_iter.pass.cpp b/test/std/containers/sequences/list/list.modifiers/insert_iter_iter_iter.pass.cpp
index d69deac..a7f1917 100644
--- a/test/std/containers/sequences/list/list.modifiers/insert_iter_iter_iter.pass.cpp
+++ b/test/std/containers/sequences/list/list.modifiers/insert_iter_iter_iter.pass.cpp
@@ -12,7 +12,7 @@
 // template <InputIterator Iter>
 //   iterator insert(const_iterator position, Iter first, Iter last);
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #if _LIBCPP_DEBUG >= 1
 #define _LIBCPP_ASSERT(x, m) ((x) ? (void)0 : std::exit(0))
diff --git a/test/std/containers/sequences/list/list.modifiers/insert_iter_size_value.pass.cpp b/test/std/containers/sequences/list/list.modifiers/insert_iter_size_value.pass.cpp
index a552e1f..eeb74b8 100644
--- a/test/std/containers/sequences/list/list.modifiers/insert_iter_size_value.pass.cpp
+++ b/test/std/containers/sequences/list/list.modifiers/insert_iter_size_value.pass.cpp
@@ -11,7 +11,7 @@
 
 // iterator insert(const_iterator position, size_type n, const value_type& x);
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #if _LIBCPP_DEBUG >= 1
 #define _LIBCPP_ASSERT(x, m) ((x) ? (void)0 : std::exit(0))
diff --git a/test/std/containers/sequences/list/list.modifiers/insert_iter_value.pass.cpp b/test/std/containers/sequences/list/list.modifiers/insert_iter_value.pass.cpp
index 093ad42..406e93a 100644
--- a/test/std/containers/sequences/list/list.modifiers/insert_iter_value.pass.cpp
+++ b/test/std/containers/sequences/list/list.modifiers/insert_iter_value.pass.cpp
@@ -11,7 +11,7 @@
 
 // iterator insert(const_iterator position, const value_type& x);
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #if _LIBCPP_DEBUG >= 1
 #define _LIBCPP_ASSERT(x, m) ((x) ? (void)0 : std::exit(0))
diff --git a/test/std/containers/sequences/list/list.special/swap_noexcept.pass.cpp b/test/std/containers/sequences/list/list.special/swap_noexcept.pass.cpp
index 54ae359..9c83ad5 100644
--- a/test/std/containers/sequences/list/list.special/swap_noexcept.pass.cpp
+++ b/test/std/containers/sequences/list/list.special/swap_noexcept.pass.cpp
@@ -12,6 +12,9 @@
 // void swap(list& c)
 //     noexcept(!allocator_type::propagate_on_container_swap::value ||
 //              __is_nothrow_swappable<allocator_type>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<Allocator>::is_always_equal::value);
 
 // This tests a conforming extension
 
@@ -33,6 +36,19 @@
     typedef std::true_type propagate_on_container_swap;
 };
 
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
@@ -54,7 +70,21 @@
     {
         typedef std::list<MoveOnly, some_alloc<MoveOnly>> C;
         C c1, c2;
+#if TEST_STD_VER >= 14
+    //  In c++14, if POCS is set, swapping the allocator is required not to throw
+        static_assert( noexcept(swap(c1, c2)), "");
+#else
         static_assert(!noexcept(swap(c1, c2)), "");
+#endif
     }
+#if TEST_STD_VER >= 14
+    {
+        typedef std::list<MoveOnly, some_alloc2<MoveOnly>> C;
+        C c1, c2;
+    //  if the allocators are always equal, then the swap can be noexcept
+        static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/containers/sequences/vector.bool/construct_default.pass.cpp b/test/std/containers/sequences/vector.bool/construct_default.pass.cpp
index d3d6670..0782409 100644
--- a/test/std/containers/sequences/vector.bool/construct_default.pass.cpp
+++ b/test/std/containers/sequences/vector.bool/construct_default.pass.cpp
@@ -15,6 +15,7 @@
 #include <vector>
 #include <cassert>
 
+#include "test_macros.h"
 #include "test_allocator.h"
 #include "min_allocator.h"
 
@@ -22,11 +23,16 @@
 void
 test0()
 {
+#if TEST_STD_VER > 14
+	static_assert((noexcept(C{})), "" );
+#elif TEST_STD_VER >= 11
+	static_assert((noexcept(C()) == noexcept(typename C::allocator_type())), "" );
+#endif
     C c;
     assert(c.__invariants());
     assert(c.empty());
     assert(c.get_allocator() == typename C::allocator_type());
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     C c1 = {};
     assert(c1.__invariants());
     assert(c1.empty());
@@ -38,6 +44,11 @@
 void
 test1(const typename C::allocator_type& a)
 {
+#if TEST_STD_VER > 14
+	static_assert((noexcept(C{typename C::allocator_type{}})), "" );
+#elif TEST_STD_VER >= 11
+	static_assert((noexcept(C(typename C::allocator_type())) == std::is_nothrow_copy_constructible<typename C::allocator_type>::value), "" );
+#endif
     C c(a);
     assert(c.__invariants());
     assert(c.empty());
@@ -50,7 +61,7 @@
     test0<std::vector<bool> >();
     test1<std::vector<bool, test_allocator<bool> > >(test_allocator<bool>(3));
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
     test0<std::vector<bool, min_allocator<bool>> >();
     test1<std::vector<bool, min_allocator<bool> > >(min_allocator<bool>());
diff --git a/test/std/containers/sequences/vector.bool/move_noexcept.pass.cpp b/test/std/containers/sequences/vector.bool/move_noexcept.pass.cpp
index ab32bd0..132186b 100644
--- a/test/std/containers/sequences/vector.bool/move_noexcept.pass.cpp
+++ b/test/std/containers/sequences/vector.bool/move_noexcept.pass.cpp
@@ -43,7 +43,12 @@
     }
     {
         typedef std::vector<bool, some_alloc<bool>> C;
+    //  In C++17, move constructors for allocators are not allowed to throw
+#if TEST_STD_VER > 14
+        static_assert( std::is_nothrow_move_constructible<C>::value, "");
+#else
         static_assert(!std::is_nothrow_move_constructible<C>::value, "");
+#endif
     }
 #endif
 }
diff --git a/test/std/containers/sequences/vector.bool/swap_noexcept.pass.cpp b/test/std/containers/sequences/vector.bool/swap_noexcept.pass.cpp
index bcaf161..6f36473 100644
--- a/test/std/containers/sequences/vector.bool/swap_noexcept.pass.cpp
+++ b/test/std/containers/sequences/vector.bool/swap_noexcept.pass.cpp
@@ -12,6 +12,10 @@
 // void swap(vector& c)
 //     noexcept(!allocator_type::propagate_on_container_swap::value ||
 //              __is_nothrow_swappable<allocator_type>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<Allocator>::propagate_on_container_swap::value ||
+//              allocator_traits<Allocator>::is_always_equal::value);
 
 // This tests a conforming extension
 
@@ -32,6 +36,19 @@
     typedef std::true_type propagate_on_container_swap;
 };
 
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
@@ -53,7 +70,21 @@
     {
         typedef std::vector<bool, some_alloc<bool>> C;
         C c1, c2;
+#if TEST_STD_VER >= 14
+    //  In c++14, if POCS is set, swapping the allocator is required not to throw
+        static_assert( noexcept(swap(c1, c2)), "");
+#else
         static_assert(!noexcept(swap(c1, c2)), "");
+#endif
     }
+#if TEST_STD_VER >= 14
+    {
+        typedef std::vector<bool, some_alloc2<bool>> C;
+        C c1, c2;
+    //  if the allocators are always equal, then the swap can be noexcept
+        static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/containers/sequences/vector/contiguous.pass.cpp b/test/std/containers/sequences/vector/contiguous.pass.cpp
new file mode 100644
index 0000000..32f3807
--- /dev/null
+++ b/test/std/containers/sequences/vector/contiguous.pass.cpp
@@ -0,0 +1,52 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <vector>
+
+// An vector is a contiguous container
+
+#include <vector>
+#include <cassert>
+
+#include "test_allocator.h"
+#include "min_allocator.h"
+
+template <class C>
+void test_contiguous ( const C &c )
+{
+    for ( size_t i = 0; i < c.size(); ++i )
+        assert ( *(c.begin() + i) == *(std::addressof(*c.begin()) + i));
+}
+
+int main()
+{
+    {
+    typedef int T;
+    typedef std::vector<T> C;
+    test_contiguous(C());
+    test_contiguous(C(3, 5));
+    }
+
+    {
+    typedef double T;
+    typedef test_allocator<T> A;
+    typedef std::vector<T, A> C;
+    test_contiguous(C(A(3)));
+    test_contiguous(C(7, 9.0, A(5)));
+    }
+#if __cplusplus >= 201103L
+    {
+    typedef double T;
+    typedef min_allocator<T> A;
+    typedef std::vector<T, A> C;
+    test_contiguous(C(A{}));
+    test_contiguous(C(9, 11.0, A{}));
+    }
+#endif
+}
diff --git a/test/std/containers/sequences/vector/vector.cons/assign_initializer_list.pass.cpp b/test/std/containers/sequences/vector/vector.cons/assign_initializer_list.pass.cpp
index f5c06b1..3cb0b3b 100644
--- a/test/std/containers/sequences/vector/vector.cons/assign_initializer_list.pass.cpp
+++ b/test/std/containers/sequences/vector/vector.cons/assign_initializer_list.pass.cpp
@@ -17,30 +17,39 @@
 #include "min_allocator.h"
 #include "asan_testing.h"
 
-int main()
+template <typename Vec>
+void test ( Vec &v )
 {
 #ifndef _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
+    v.assign({3, 4, 5, 6});
+    assert(v.size() == 4);
+    assert(is_contiguous_container_asan_correct(v)); 
+    assert(v[0] == 3);
+    assert(v[1] == 4);
+    assert(v[2] == 5);
+    assert(v[3] == 6);
+#endif
+}
+
+int main()
+{
     {
-    std::vector<int> d;
-    d.assign({3, 4, 5, 6});
-    assert(d.size() == 4);
-    assert(is_contiguous_container_asan_correct(d)); 
-    assert(d[0] == 3);
-    assert(d[1] == 4);
-    assert(d[2] == 5);
-    assert(d[3] == 6);
+    typedef std::vector<int> V;
+    V d1;
+    V d2;
+    d2.reserve(10);  // no reallocation during assign.
+    test(d1);
+    test(d2);
     }
+
 #if __cplusplus >= 201103L
     {
-    std::vector<int, min_allocator<int>> d;
-    d.assign({3, 4, 5, 6});
-    assert(d.size() == 4);
-    assert(is_contiguous_container_asan_correct(d)); 
-    assert(d[0] == 3);
-    assert(d[1] == 4);
-    assert(d[2] == 5);
-    assert(d[3] == 6);
+    typedef std::vector<int, min_allocator<int>> V;
+    V d1;
+    V d2;
+    d2.reserve(10);  // no reallocation during assign.
+    test(d1);
+    test(d2);
     }
 #endif
-#endif  // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
 }
diff --git a/test/std/containers/sequences/vector/vector.cons/assign_size_value.pass.cpp b/test/std/containers/sequences/vector/vector.cons/assign_size_value.pass.cpp
new file mode 100644
index 0000000..e1b30bf
--- /dev/null
+++ b/test/std/containers/sequences/vector/vector.cons/assign_size_value.pass.cpp
@@ -0,0 +1,54 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <vector>
+
+// void assign(size_type n, const_reference v);
+
+#include <vector>
+#include <algorithm>
+#include <cassert>
+#include <iostream>
+
+#include "min_allocator.h"
+#include "asan_testing.h"
+
+bool is6(int x) { return x == 6; }
+
+template <typename Vec>
+void test ( Vec &v )
+{
+    v.assign(5, 6);
+    assert(v.size() == 5);
+    assert(is_contiguous_container_asan_correct(v)); 
+    assert(std::all_of(v.begin(), v.end(), is6));
+}
+
+int main()
+{
+    {
+    typedef std::vector<int> V;
+    V d1;
+    V d2;
+    d2.reserve(10);  // no reallocation during assign.
+    test(d1);
+    test(d2);
+    }
+
+#if __cplusplus >= 201103L
+    {
+    typedef std::vector<int, min_allocator<int>> V;
+    V d1;
+    V d2;
+    d2.reserve(10);  // no reallocation during assign.
+    test(d1);
+    test(d2);
+    }
+#endif
+}
diff --git a/test/std/containers/sequences/vector/vector.cons/construct_default.pass.cpp b/test/std/containers/sequences/vector/vector.cons/construct_default.pass.cpp
index 75772be..5e87c07 100644
--- a/test/std/containers/sequences/vector/vector.cons/construct_default.pass.cpp
+++ b/test/std/containers/sequences/vector/vector.cons/construct_default.pass.cpp
@@ -9,11 +9,13 @@
 
 // <vector>
 
-// vector(const Alloc& = Alloc());
+// vector();
+// vector(const Alloc&);
 
 #include <vector>
 #include <cassert>
 
+#include "test_macros.h"
 #include "test_allocator.h"
 #include "../../../NotConstructible.h"
 #include "../../../stack_allocator.h"
@@ -24,12 +26,17 @@
 void
 test0()
 {
+#if TEST_STD_VER > 14
+	static_assert((noexcept(C{})), "" );
+#elif TEST_STD_VER >= 11
+	static_assert((noexcept(C()) == noexcept(typename C::allocator_type())), "" );
+#endif
     C c;
     assert(c.__invariants());
     assert(c.empty());
     assert(c.get_allocator() == typename C::allocator_type());
     assert(is_contiguous_container_asan_correct(c)); 
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     C c1 = {};
     assert(c1.__invariants());
     assert(c1.empty());
@@ -42,6 +49,11 @@
 void
 test1(const typename C::allocator_type& a)
 {
+#if TEST_STD_VER > 14
+	static_assert((noexcept(C{typename C::allocator_type{}})), "" );
+#elif TEST_STD_VER >= 11
+	static_assert((noexcept(C(typename C::allocator_type())) == std::is_nothrow_copy_constructible<typename C::allocator_type>::value), "" );
+#endif
     C c(a);
     assert(c.__invariants());
     assert(c.empty());
@@ -62,7 +74,7 @@
         std::vector<int, stack_allocator<int, 10> > v;
         assert(v.empty());
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
     test0<std::vector<int, min_allocator<int>> >();
     test0<std::vector<NotConstructible, min_allocator<NotConstructible>> >();
diff --git a/test/std/containers/sequences/vector/vector.cons/default_noexcept.pass.cpp b/test/std/containers/sequences/vector/vector.cons/default_noexcept.pass.cpp
index 471c1d4..60f7b72 100644
--- a/test/std/containers/sequences/vector/vector.cons/default_noexcept.pass.cpp
+++ b/test/std/containers/sequences/vector/vector.cons/default_noexcept.pass.cpp
@@ -17,6 +17,7 @@
 #include <vector>
 #include <cassert>
 
+#include "test_macros.h"
 #include "MoveOnly.h"
 #include "test_allocator.h"
 
diff --git a/test/std/containers/sequences/vector/vector.cons/move_noexcept.pass.cpp b/test/std/containers/sequences/vector/vector.cons/move_noexcept.pass.cpp
index 46cad99..b7bbfaa 100644
--- a/test/std/containers/sequences/vector/vector.cons/move_noexcept.pass.cpp
+++ b/test/std/containers/sequences/vector/vector.cons/move_noexcept.pass.cpp
@@ -44,7 +44,12 @@
     }
     {
         typedef std::vector<MoveOnly, some_alloc<MoveOnly>> C;
+    //  In C++17, move constructors for allocators are not allowed to throw
+#if TEST_STD_VER > 14
+        static_assert( std::is_nothrow_move_constructible<C>::value, "");
+#else
         static_assert(!std::is_nothrow_move_constructible<C>::value, "");
+#endif
     }
 #endif
 }
diff --git a/test/std/containers/sequences/vector/vector.special/swap_noexcept.pass.cpp b/test/std/containers/sequences/vector/vector.special/swap_noexcept.pass.cpp
index 92d8756..1d00ff3 100644
--- a/test/std/containers/sequences/vector/vector.special/swap_noexcept.pass.cpp
+++ b/test/std/containers/sequences/vector/vector.special/swap_noexcept.pass.cpp
@@ -12,6 +12,10 @@
 // void swap(vector& c)
 //     noexcept(!allocator_type::propagate_on_container_swap::value ||
 //              __is_nothrow_swappable<allocator_type>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<Allocator>::propagate_on_container_swap::value ||
+//              allocator_traits<Allocator>::is_always_equal::value);
 
 // This tests a conforming extension
 
@@ -33,6 +37,19 @@
     typedef std::true_type propagate_on_container_swap;
 };
 
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
@@ -54,7 +71,21 @@
     {
         typedef std::vector<MoveOnly, some_alloc<MoveOnly>> C;
         C c1, c2;
+#if TEST_STD_VER >= 14
+    //  In c++14, if POCS is set, swapping the allocator is required not to throw
+        static_assert( noexcept(swap(c1, c2)), "");
+#else
         static_assert(!noexcept(swap(c1, c2)), "");
+#endif
     }
+#if TEST_STD_VER >= 14
+    {
+        typedef std::vector<MoveOnly, some_alloc2<MoveOnly>> C;
+        C c1, c2;
+    //  if the allocators are always equal, then the swap can be noexcept
+        static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/containers/unord/unord.map/bucket_count.pass.cpp b/test/std/containers/unord/unord.map/bucket_count.pass.cpp
index d3e80d8..bc37337 100644
--- a/test/std/containers/unord/unord.map/bucket_count.pass.cpp
+++ b/test/std/containers/unord/unord.map/bucket_count.pass.cpp
@@ -19,20 +19,18 @@
 #include <string>
 #include <cassert>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
 int main()
 {
     {
         typedef std::unordered_map<int, std::string> C;
-        typedef C::const_iterator I;
-        typedef std::pair<int, std::string> P;
         const C c;
         assert(c.bucket_count() == 0);
     }
     {
         typedef std::unordered_map<int, std::string> C;
-        typedef C::const_iterator I;
         typedef std::pair<int, std::string> P;
         P a[] =
         {
@@ -48,19 +46,16 @@
         const C c(std::begin(a), std::end(a));
         assert(c.bucket_count() >= 11);
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
         typedef std::unordered_map<int, std::string, std::hash<int>, std::equal_to<int>,
                             min_allocator<std::pair<const int, std::string>>> C;
-        typedef C::const_iterator I;
-        typedef std::pair<int, std::string> P;
         const C c;
         assert(c.bucket_count() == 0);
     }
     {
         typedef std::unordered_map<int, std::string, std::hash<int>, std::equal_to<int>,
                             min_allocator<std::pair<const int, std::string>>> C;
-        typedef C::const_iterator I;
         typedef std::pair<int, std::string> P;
         P a[] =
         {
diff --git a/test/std/containers/unord/unord.map/compare.pass.cpp b/test/std/containers/unord/unord.map/compare.pass.cpp
index 8979a3a..ea6d02f 100644
--- a/test/std/containers/unord/unord.map/compare.pass.cpp
+++ b/test/std/containers/unord/unord.map/compare.pass.cpp
@@ -17,6 +17,7 @@
 // http://llvm.org/bugs/show_bug.cgi?id=16549
 
 #include <unordered_map>
+#include <cassert>
 
 struct Key {
   template <typename T> Key(const T&) {}
@@ -35,8 +36,12 @@
 int
 main()
 {
-    std::unordered_map<Key, int>::iterator it =
-        std::unordered_map<Key, int>().find(Key(0));
-    std::pair<std::unordered_map<Key, int>::iterator, bool> result =
-        std::unordered_map<Key, int>().insert(std::make_pair(Key(0), 0));
+    typedef std::unordered_map<Key, int> MapT;
+    typedef MapT::iterator Iter;
+    MapT map;
+    Iter it = map.find(Key(0));
+    assert(it == map.end());
+    std::pair<Iter, bool> result = map.insert(std::make_pair(Key(0), 42));
+    assert(result.second);
+    assert(result.first->second == 42);
 }
diff --git a/test/std/containers/unord/unord.map/load_factor.pass.cpp b/test/std/containers/unord/unord.map/load_factor.pass.cpp
index 472e41a..b25c019 100644
--- a/test/std/containers/unord/unord.map/load_factor.pass.cpp
+++ b/test/std/containers/unord/unord.map/load_factor.pass.cpp
@@ -20,6 +20,7 @@
 #include <cassert>
 #include <cfloat>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
 int main()
@@ -43,11 +44,10 @@
     }
     {
         typedef std::unordered_map<int, std::string> C;
-        typedef std::pair<int, std::string> P;
         const C c;
         assert(c.load_factor() == 0);
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
         typedef std::unordered_map<int, std::string, std::hash<int>, std::equal_to<int>,
                             min_allocator<std::pair<const int, std::string>>> C;
@@ -69,7 +69,6 @@
     {
         typedef std::unordered_map<int, std::string, std::hash<int>, std::equal_to<int>,
                             min_allocator<std::pair<const int, std::string>>> C;
-        typedef std::pair<int, std::string> P;
         const C c;
         assert(c.load_factor() == 0);
     }
diff --git a/test/std/containers/unord/unord.map/max_bucket_count.pass.cpp b/test/std/containers/unord/unord.map/max_bucket_count.pass.cpp
index b4ca8eb..08f014d 100644
--- a/test/std/containers/unord/unord.map/max_bucket_count.pass.cpp
+++ b/test/std/containers/unord/unord.map/max_bucket_count.pass.cpp
@@ -19,23 +19,20 @@
 #include <string>
 #include <cassert>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
 int main()
 {
     {
         typedef std::unordered_map<int, std::string> C;
-        typedef C::const_iterator I;
-        typedef std::pair<int, std::string> P;
         const C c;
         assert(c.max_bucket_count() > 0);
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
         typedef std::unordered_map<int, std::string, std::hash<int>, std::equal_to<int>,
                             min_allocator<std::pair<const int, std::string>>> C;
-        typedef C::const_iterator I;
-        typedef std::pair<int, std::string> P;
         const C c;
         assert(c.max_bucket_count() > 0);
     }
diff --git a/test/std/containers/unord/unord.map/max_load_factor.pass.cpp b/test/std/containers/unord/unord.map/max_load_factor.pass.cpp
index 69fd70d..b19a6e6 100644
--- a/test/std/containers/unord/unord.map/max_load_factor.pass.cpp
+++ b/test/std/containers/unord/unord.map/max_load_factor.pass.cpp
@@ -16,44 +16,37 @@
 // float max_load_factor() const;
 // void max_load_factor(float mlf);
 
-#ifdef _LIBCPP_DEBUG
-#define _LIBCPP_ASSERT(x, m) ((x) ? (void)0 : std::exit(0))
-#endif
-
 #include <unordered_map>
 #include <string>
 #include <cassert>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
 int main()
 {
     {
         typedef std::unordered_map<int, std::string> C;
-        typedef std::pair<int, std::string> P;
         const C c;
         assert(c.max_load_factor() == 1);
     }
     {
         typedef std::unordered_map<int, std::string> C;
-        typedef std::pair<int, std::string> P;
         C c;
         assert(c.max_load_factor() == 1);
         c.max_load_factor(2.5);
         assert(c.max_load_factor() == 2.5);
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
         typedef std::unordered_map<int, std::string, std::hash<int>, std::equal_to<int>,
                             min_allocator<std::pair<const int, std::string>>> C;
-        typedef std::pair<int, std::string> P;
         const C c;
         assert(c.max_load_factor() == 1);
     }
     {
         typedef std::unordered_map<int, std::string, std::hash<int>, std::equal_to<int>,
                             min_allocator<std::pair<const int, std::string>>> C;
-        typedef std::pair<int, std::string> P;
         C c;
         assert(c.max_load_factor() == 1);
         c.max_load_factor(2.5);
diff --git a/test/std/containers/unord/unord.map/swap_member.pass.cpp b/test/std/containers/unord/unord.map/swap_member.pass.cpp
index 8ab1eb6..0f98b66 100644
--- a/test/std/containers/unord/unord.map/swap_member.pass.cpp
+++ b/test/std/containers/unord/unord.map/swap_member.pass.cpp
@@ -21,6 +21,7 @@
 
 #include "../../test_compare.h"
 #include "../../test_hash.h"
+#include "test_macros.h"
 #include "test_allocator.h"
 #include "min_allocator.h"
 
@@ -31,7 +32,6 @@
         typedef test_compare<std::equal_to<int> > Compare;
         typedef test_allocator<std::pair<const int, std::string> > Alloc;
         typedef std::unordered_map<int, std::string, Hash, Compare, Alloc> C;
-        typedef std::pair<int, std::string> P;
         C c1(0, Hash(1), Compare(1), Alloc(1));
         C c2(0, Hash(2), Compare(2), Alloc(2));
         c2.max_load_factor(2);
@@ -212,7 +212,6 @@
         typedef test_compare<std::equal_to<int> > Compare;
         typedef other_allocator<std::pair<const int, std::string> > Alloc;
         typedef std::unordered_map<int, std::string, Hash, Compare, Alloc> C;
-        typedef std::pair<int, std::string> P;
         C c1(0, Hash(1), Compare(1), Alloc(1));
         C c2(0, Hash(2), Compare(2), Alloc(2));
         c2.max_load_factor(2);
@@ -387,13 +386,12 @@
         assert(std::distance(c2.cbegin(), c2.cend()) == c2.size());
         assert(c2.max_load_factor() == 1);
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
         typedef test_hash<std::hash<int> > Hash;
         typedef test_compare<std::equal_to<int> > Compare;
         typedef min_allocator<std::pair<const int, std::string> > Alloc;
         typedef std::unordered_map<int, std::string, Hash, Compare, Alloc> C;
-        typedef std::pair<int, std::string> P;
         C c1(0, Hash(1), Compare(1), Alloc());
         C c2(0, Hash(2), Compare(2), Alloc());
         c2.max_load_factor(2);
diff --git a/test/std/containers/unord/unord.map/unord.map.cnstr/move.pass.cpp b/test/std/containers/unord/unord.map/unord.map.cnstr/move.pass.cpp
index 18e6683..1420204 100644
--- a/test/std/containers/unord/unord.map/unord.map.cnstr/move.pass.cpp
+++ b/test/std/containers/unord/unord.map/unord.map.cnstr/move.pass.cpp
@@ -15,6 +15,8 @@
 
 // unordered_map(unordered_map&& u);
 
+// UNSUPPORTED: c++98, c++03
+
 #include <unordered_map>
 #include <string>
 #include <cassert>
@@ -27,23 +29,12 @@
 
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     {
         typedef std::unordered_map<int, std::string,
                                    test_hash<std::hash<int> >,
                                    test_compare<std::equal_to<int> >,
                                    test_allocator<std::pair<const int, std::string> >
                                    > C;
-        typedef std::pair<int, std::string> P;
-        P a[] =
-        {
-            P(1, "one"),
-            P(2, "two"),
-            P(3, "three"),
-            P(4, "four"),
-            P(1, "four"),
-            P(2, "four"),
-        };
         C c0(7,
             test_hash<std::hash<int> >(8),
             test_compare<std::equal_to<int> >(9),
@@ -105,23 +96,12 @@
 
         assert(c0.empty());
     }
-#if __cplusplus >= 201103L
     {
         typedef std::unordered_map<int, std::string,
                                    test_hash<std::hash<int> >,
                                    test_compare<std::equal_to<int> >,
                                    min_allocator<std::pair<const int, std::string> >
                                    > C;
-        typedef std::pair<int, std::string> P;
-        P a[] =
-        {
-            P(1, "one"),
-            P(2, "two"),
-            P(3, "three"),
-            P(4, "four"),
-            P(1, "four"),
-            P(2, "four"),
-        };
         C c0(7,
             test_hash<std::hash<int> >(8),
             test_compare<std::equal_to<int> >(9),
@@ -183,7 +163,6 @@
 
         assert(c0.empty());
     }
-#endif
 #if _LIBCPP_DEBUG >= 1
     {
         std::unordered_map<int, int> s1 = {{1, 1}, {2, 2}, {3, 3}};
@@ -195,5 +174,4 @@
         assert(s2.size() == 2);
     }
 #endif
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/clear.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/clear.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/clear.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/clear.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/emplace.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/emplace.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/emplace.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/emplace.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/emplace_hint.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/emplace_hint.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/emplace_hint.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/emplace_hint.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/erase_const_iter.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/erase_const_iter.pass.cpp
similarity index 73%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/erase_const_iter.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/erase_const_iter.pass.cpp
index 422dbe4..803ecb5 100644
--- a/test/std/containers/unord/unord.map/unorder.map.modifiers/erase_const_iter.pass.cpp
+++ b/test/std/containers/unord/unord.map/unord.map.modifiers/erase_const_iter.pass.cpp
@@ -19,8 +19,18 @@
 #include <string>
 #include <cassert>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
+struct TemplateConstructor
+{
+    template<typename T>
+    TemplateConstructor (const T&) {}
+};
+
+bool operator==(const TemplateConstructor&, const TemplateConstructor&) { return false; }
+struct Hash { size_t operator() (const TemplateConstructor &) const { return 0; } };
+
 int main()
 {
     {
@@ -37,13 +47,13 @@
         };
         C c(a, a + sizeof(a)/sizeof(a[0]));
         C::const_iterator i = c.find(2);
-        C::iterator j = c.erase(i);
+        c.erase(i);
         assert(c.size() == 3);
         assert(c.at(1) == "one");
         assert(c.at(3) == "three");
         assert(c.at(4) == "four");
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
         typedef std::unordered_map<int, std::string, std::hash<int>, std::equal_to<int>,
                             min_allocator<std::pair<const int, std::string>>> C;
@@ -59,11 +69,25 @@
         };
         C c(a, a + sizeof(a)/sizeof(a[0]));
         C::const_iterator i = c.find(2);
-        C::iterator j = c.erase(i);
+        c.erase(i);
         assert(c.size() == 3);
         assert(c.at(1) == "one");
         assert(c.at(3) == "three");
         assert(c.at(4) == "four");
     }
 #endif
+#if TEST_STD_VER >= 14
+    {
+    //  This is LWG #2059
+        typedef TemplateConstructor T;
+        typedef std::unordered_map<T, int, Hash> C;
+        typedef C::iterator I;
+
+        C m;
+        T a{0};
+        I it = m.find(a);
+        if (it != m.end())
+            m.erase(it);
+    }
+#endif
 }
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/erase_iter_db1.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/erase_iter_db1.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/erase_iter_db1.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/erase_iter_db1.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/erase_iter_db2.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/erase_iter_db2.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/erase_iter_db2.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/erase_iter_db2.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/erase_iter_iter_db1.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/erase_iter_iter_db1.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/erase_iter_iter_db1.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/erase_iter_iter_db1.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/erase_iter_iter_db2.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/erase_iter_iter_db2.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/erase_iter_iter_db2.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/erase_iter_iter_db2.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/erase_iter_iter_db3.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/erase_iter_iter_db3.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/erase_iter_iter_db3.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/erase_iter_iter_db3.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/erase_iter_iter_db4.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/erase_iter_iter_db4.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/erase_iter_iter_db4.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/erase_iter_iter_db4.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/erase_key.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/erase_key.pass.cpp
similarity index 97%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/erase_key.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/erase_key.pass.cpp
index 0e8ef8b..cdd19eb 100644
--- a/test/std/containers/unord/unord.map/unorder.map.modifiers/erase_key.pass.cpp
+++ b/test/std/containers/unord/unord.map/unord.map.modifiers/erase_key.pass.cpp
@@ -19,15 +19,16 @@
 #include <string>
 #include <cassert>
 
+#include "test_macros.h"
 #include "min_allocator.h"
 
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
 template <typename Unordered>
 bool only_deletions ( const Unordered &whole, const Unordered &part ) {
     typename Unordered::const_iterator w = whole.begin();
     typename Unordered::const_iterator p = part.begin();
-    
-    while ( w != whole.end () && p != part.end()) {        
+
+    while ( w != whole.end () && p != part.end()) {
         if ( *w == *p )
             p++;
         w++;
@@ -96,7 +97,7 @@
         assert(c.erase(3) == 0);
         assert(c.size() == 0);
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
         typedef std::unordered_map<int, std::string, std::hash<int>, std::equal_to<int>,
                             min_allocator<std::pair<const int, std::string>>> C;
@@ -161,7 +162,7 @@
         m[i] = i;
         m2[i] = i;
         }
-    
+
     C::iterator i = m2.begin();
     int ctr = 0;
     while (i != m2.end()) {
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/erase_range.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/erase_range.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/erase_range.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/erase_range.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/insert_const_lvalue.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/insert_const_lvalue.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/insert_const_lvalue.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/insert_const_lvalue.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/insert_hint_const_lvalue.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/insert_hint_const_lvalue.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/insert_hint_const_lvalue.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/insert_hint_const_lvalue.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/insert_hint_rvalue.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/insert_hint_rvalue.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/insert_hint_rvalue.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/insert_hint_rvalue.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/insert_init.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/insert_init.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/insert_init.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/insert_init.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unord.map.modifiers/insert_or_assign.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/insert_or_assign.pass.cpp
new file mode 100644
index 0000000..a4d8abc
--- /dev/null
+++ b/test/std/containers/unord/unord.map/unord.map.modifiers/insert_or_assign.pass.cpp
@@ -0,0 +1,192 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: c++98, c++03, c++11, c++14
+
+// <unordered_map>
+
+// class unordered_map
+
+// template <class M>
+//  pair<iterator, bool> insert_or_assign(const key_type& k, M&& obj);            // C++17
+// template <class M>
+//  pair<iterator, bool> insert_or_assign(key_type&& k, M&& obj);                 // C++17
+// template <class M>
+//  iterator insert_or_assign(const_iterator hint, const key_type& k, M&& obj);   // C++17
+// template <class M>
+//  iterator insert_or_assign(const_iterator hint, key_type&& k, M&& obj);        // C++17
+
+#include <unordered_map>
+#include <cassert>
+#include <tuple>
+
+
+class Moveable
+{
+    Moveable(const Moveable&);
+    Moveable& operator=(const Moveable&);
+
+    int int_;
+    double double_;
+public:
+    Moveable() : int_(0), double_(0) {}
+    Moveable(int i, double d) : int_(i), double_(d) {}
+    Moveable(Moveable&& x)
+        : int_(x.int_), double_(x.double_)
+            {x.int_ = -1; x.double_ = -1;}
+    Moveable& operator=(Moveable&& x)
+        {int_ = x.int_; x.int_ = -1;
+         double_ = x.double_; x.double_ = -1;
+         return *this;
+        }
+
+    bool operator==(const Moveable& x) const
+        {return int_ == x.int_ && double_ == x.double_;}
+    bool operator<(const Moveable& x) const
+        {return int_ < x.int_ || (int_ == x.int_ && double_ < x.double_);}
+    size_t hash () const { return std::hash<int>()(int_) + std::hash<double>()(double_); }
+
+    int get() const {return int_;}
+    bool moved() const {return int_ == -1;}
+};
+
+namespace std {
+    template <> struct hash<Moveable> {
+        size_t operator () (const Moveable &m) const { return m.hash(); }
+    };
+}
+
+int main()
+{
+
+    { // pair<iterator, bool> insert_or_assign(const key_type& k, M&& obj);
+        typedef std::unordered_map<int, Moveable> M;
+        typedef std::pair<M::iterator, bool> R;
+        M m;
+        R r;
+        for (int i = 0; i < 20; i += 2)
+            m.emplace ( i, Moveable(i, (double) i));
+        assert(m.size() == 10);
+
+        for (int i=0; i < 20; i += 2)
+        {
+            Moveable mv(i+1, i+1);
+            r = m.insert_or_assign(i, std::move(mv));
+            assert(m.size() == 10);
+            assert(!r.second);                    // was not inserted
+            assert(mv.moved());                   // was moved from
+            assert(r.first->first == i);          // key
+            assert(r.first->second.get() == i+1); // value
+        }
+
+        Moveable mv1(5, 5.0);
+        r = m.insert_or_assign(-1, std::move(mv1));
+        assert(m.size() == 11);
+        assert(r.second);                    // was inserted
+        assert(mv1.moved());                 // was moved from
+        assert(r.first->first        == -1); // key
+        assert(r.first->second.get() == 5);  // value
+
+        Moveable mv2(9, 9.0);
+        r = m.insert_or_assign(3, std::move(mv2));
+        assert(m.size() == 12);
+        assert(r.second);                   // was inserted
+        assert(mv2.moved());                // was moved from
+        assert(r.first->first        == 3); // key
+        assert(r.first->second.get() == 9); // value
+
+        Moveable mv3(-1, 5.0);
+        r = m.insert_or_assign(117, std::move(mv3));
+        assert(m.size() == 13);
+        assert(r.second);                     // was inserted
+        assert(mv3.moved());                  // was moved from
+        assert(r.first->first        == 117); // key
+        assert(r.first->second.get() == -1);  // value
+    }
+    { // pair<iterator, bool> insert_or_assign(key_type&& k, M&& obj);
+        typedef std::unordered_map<Moveable, Moveable> M;
+        typedef std::pair<M::iterator, bool> R;
+        M m;
+        R r;
+        for (int i = 0; i < 20; i += 2)
+            m.emplace ( Moveable(i, (double) i), Moveable(i+1, (double) i+1));
+        assert(m.size() == 10);
+
+        Moveable mvkey1(2, 2.0);
+        Moveable mv1(4, 4.0);
+        r = m.insert_or_assign(std::move(mvkey1), std::move(mv1));
+        assert(m.size() == 10);
+        assert(!r.second);                  // was not inserted
+        assert(!mvkey1.moved());            // was not moved from
+        assert(mv1.moved());                // was moved from
+        assert(r.first->first == mvkey1);   // key
+        assert(r.first->second.get() == 4); // value
+
+        Moveable mvkey2(3, 3.0);
+        Moveable mv2(5, 5.0);
+        r = m.try_emplace(std::move(mvkey2), std::move(mv2));
+        assert(m.size() == 11);
+        assert(r.second);                   // was inserted
+        assert(mv2.moved());                // was moved from
+        assert(mvkey2.moved());             // was moved from
+        assert(r.first->first.get()  == 3); // key
+        assert(r.first->second.get() == 5); // value
+    }
+    { // iterator insert_or_assign(const_iterator hint, const key_type& k, M&& obj);
+        typedef std::unordered_map<int, Moveable> M;
+        M m;
+        M::iterator r;
+        for (int i = 0; i < 20; i += 2)
+            m.emplace ( i, Moveable(i, (double) i));
+        assert(m.size() == 10);
+        M::const_iterator it = m.find(2);
+
+        Moveable mv1(3, 3.0);
+        r = m.insert_or_assign(it, 2, std::move(mv1));
+        assert(m.size() == 10);
+        assert(mv1.moved());           // was moved from
+        assert(r->first        == 2);  // key
+        assert(r->second.get() == 3);  // value
+
+        Moveable mv2(5, 5.0);
+        r = m.insert_or_assign(it, 3, std::move(mv2));
+        assert(m.size() == 11);
+        assert(mv2.moved());           // was moved from
+        assert(r->first        == 3);  // key
+        assert(r->second.get() == 5);  // value
+    }
+    { // iterator insert_or_assign(const_iterator hint, key_type&& k, M&& obj);
+        typedef std::unordered_map<Moveable, Moveable> M;
+        M m;
+        M::iterator r;
+        for (int i = 0; i < 20; i += 2)
+            m.emplace ( Moveable(i, (double) i), Moveable(i+1, (double) i+1));
+        assert(m.size() == 10);
+        M::const_iterator it = std::next(m.cbegin());
+
+        Moveable mvkey1(2, 2.0);
+        Moveable mv1(4, 4.0);
+        r = m.insert_or_assign(it, std::move(mvkey1), std::move(mv1));
+        assert(m.size() == 10);
+        assert(mv1.moved());          // was moved from
+        assert(!mvkey1.moved());      // was not moved from
+        assert(r->first == mvkey1);   // key
+        assert(r->second.get() == 4); // value
+
+        Moveable mvkey2(3, 3.0);
+        Moveable mv2(5, 5.0);
+        r = m.insert_or_assign(it, std::move(mvkey2), std::move(mv2));
+        assert(m.size() == 11);
+        assert(mv2.moved());           // was moved from
+        assert(mvkey2.moved());        // was moved from
+        assert(r->first.get()  == 3);  // key
+        assert(r->second.get() == 5);  // value
+    }
+
+}
\ No newline at end of file
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/insert_range.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/insert_range.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/insert_range.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/insert_range.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unorder.map.modifiers/insert_rvalue.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/insert_rvalue.pass.cpp
similarity index 100%
rename from test/std/containers/unord/unord.map/unorder.map.modifiers/insert_rvalue.pass.cpp
rename to test/std/containers/unord/unord.map/unord.map.modifiers/insert_rvalue.pass.cpp
diff --git a/test/std/containers/unord/unord.map/unord.map.modifiers/try.emplace.pass.cpp b/test/std/containers/unord/unord.map/unord.map.modifiers/try.emplace.pass.cpp
new file mode 100644
index 0000000..eabcf2e
--- /dev/null
+++ b/test/std/containers/unord/unord.map/unord.map.modifiers/try.emplace.pass.cpp
@@ -0,0 +1,190 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: c++98, c++03, c++11, c++14
+
+// <unordered_map>
+
+// class unordered_map
+
+// template <class... Args>
+//  pair<iterator, bool> try_emplace(const key_type& k, Args&&... args);          // C++17
+// template <class... Args>
+//  pair<iterator, bool> try_emplace(key_type&& k, Args&&... args);               // C++17
+// template <class... Args>
+//  iterator try_emplace(const_iterator hint, const key_type& k, Args&&... args); // C++17
+// template <class... Args>
+//  iterator try_emplace(const_iterator hint, key_type&& k, Args&&... args);      // C++17
+
+#include <__config>
+#include <unordered_map>
+#include <cassert>
+#include <tuple>
+
+class Moveable
+{
+    Moveable(const Moveable&);
+    Moveable& operator=(const Moveable&);
+
+    int int_;
+    double double_;
+public:
+    Moveable() : int_(0), double_(0) {}
+    Moveable(int i, double d) : int_(i), double_(d) {}
+    Moveable(Moveable&& x)
+        : int_(x.int_), double_(x.double_)
+            {x.int_ = -1; x.double_ = -1;}
+    Moveable& operator=(Moveable&& x)
+        {int_ = x.int_; x.int_ = -1;
+         double_ = x.double_; x.double_ = -1;
+         return *this;
+        }
+
+    bool operator==(const Moveable& x) const
+        {return int_ == x.int_ && double_ == x.double_;}
+    bool operator<(const Moveable& x) const
+        {return int_ < x.int_ || (int_ == x.int_ && double_ < x.double_);}
+    size_t hash () const { return std::hash<int>()(int_) + std::hash<double>()(double_); }
+
+    int get() const {return int_;}
+    bool moved() const {return int_ == -1;}
+};
+
+namespace std {
+    template <> struct hash<Moveable> {
+        size_t operator () (const Moveable &m) const { return m.hash(); }
+    };
+}
+
+int main()
+{
+
+    { // pair<iterator, bool> try_emplace(const key_type& k, Args&&... args);
+        typedef std::unordered_map<int, Moveable> M;
+        typedef std::pair<M::iterator, bool> R;
+        M m;
+        R r;
+        for (int i = 0; i < 20; i += 2)
+            m.emplace (i, Moveable(i, (double) i));
+        assert(m.size() == 10);
+
+        Moveable mv1(3, 3.0);
+        for (int i=0; i < 20; i += 2)
+        {
+            r = m.try_emplace(i, std::move(mv1));
+            assert(m.size() == 10);
+            assert(!r.second);              // was not inserted
+            assert(!mv1.moved());           // was not moved from
+            assert(r.first->first == i);    // key
+        }
+
+        r = m.try_emplace(-1, std::move(mv1));
+        assert(m.size() == 11);
+        assert(r.second);                   // was inserted
+        assert(mv1.moved());                // was moved from
+        assert(r.first->first == -1);       // key
+        assert(r.first->second.get() == 3); // value
+
+        Moveable mv2(5, 3.0);
+        r = m.try_emplace(5, std::move(mv2));
+        assert(m.size() == 12);
+        assert(r.second);                   // was inserted
+        assert(mv2.moved());                // was moved from
+        assert(r.first->first == 5);        // key
+        assert(r.first->second.get() == 5); // value
+
+        Moveable mv3(-1, 3.0);
+        r = m.try_emplace(117, std::move(mv2));
+        assert(m.size() == 13);
+        assert(r.second);                    // was inserted
+        assert(mv2.moved());                 // was moved from
+        assert(r.first->first == 117);       // key
+        assert(r.first->second.get() == -1); // value
+    }
+
+    {  // pair<iterator, bool> try_emplace(key_type&& k, Args&&... args);
+        typedef std::unordered_map<Moveable, Moveable> M;
+        typedef std::pair<M::iterator, bool> R;
+        M m;
+        R r;
+        for (int i = 0; i < 20; i += 2)
+            m.emplace ( Moveable(i, (double) i), Moveable(i+1, (double) i+1));
+        assert(m.size() == 10);
+
+        Moveable mvkey1(2, 2.0);
+        Moveable mv1(4, 4.0);
+        r = m.try_emplace(std::move(mvkey1), std::move(mv1));
+        assert(m.size() == 10);
+        assert(!r.second);                 // was not inserted
+        assert(!mv1.moved());              // was not moved from
+        assert(!mvkey1.moved());           // was not moved from
+        assert(r.first->first == mvkey1);  // key
+
+        Moveable mvkey2(3, 3.0);
+        r = m.try_emplace(std::move(mvkey2), std::move(mv1));
+        assert(m.size() == 11);
+        assert(r.second);                   // was inserted
+        assert(mv1.moved());                // was moved from
+        assert(mvkey2.moved());             // was moved from
+        assert(r.first->first.get()  == 3); // key
+        assert(r.first->second.get() == 4); // value
+    }
+
+    {  // iterator try_emplace(const_iterator hint, const key_type& k, Args&&... args);
+        typedef std::unordered_map<int, Moveable> M;
+        M m;
+        M::iterator r;
+        for (int i = 0; i < 20; i += 2)
+            m.try_emplace ( i, Moveable(i, (double) i));
+        assert(m.size() == 10);
+        M::const_iterator it = m.find(2);
+
+        Moveable mv1(3, 3.0);
+        for (int i=0; i < 20; i += 2)
+        {
+            r = m.try_emplace(it, i, std::move(mv1));
+            assert(m.size() == 10);
+            assert(!mv1.moved());         // was not moved from
+            assert(r->first == i);        // key
+            assert(r->second.get() == i); // value
+        }
+
+        r = m.try_emplace(it, 3, std::move(mv1));
+        assert(m.size() == 11);
+        assert(mv1.moved());          // was moved from
+        assert(r->first == 3);        // key
+        assert(r->second.get() == 3); // value
+    }
+
+    {  // iterator try_emplace(const_iterator hint, key_type&& k, Args&&... args);
+        typedef std::unordered_map<Moveable, Moveable> M;
+        M m;
+        M::iterator r;
+        for ( int i = 0; i < 20; i += 2 )
+            m.emplace ( Moveable(i, (double) i), Moveable(i+1, (double) i+1));
+        assert(m.size() == 10);
+        M::const_iterator it = std::next(m.cbegin());
+
+        Moveable mvkey1(2, 2.0);
+        Moveable mv1(4, 4.0);
+        r = m.try_emplace(it, std::move(mvkey1), std::move(mv1));
+        assert(m.size() == 10);
+        assert(!mv1.moved());        // was not moved from
+        assert(!mvkey1.moved());     // was not moved from
+        assert(r->first == mvkey1);  // key
+
+        Moveable mvkey2(3, 3.0);
+        r = m.try_emplace(it, std::move(mvkey2), std::move(mv1));
+        assert(m.size() == 11);
+        assert(mv1.moved());          // was moved from
+        assert(mvkey2.moved());       // was moved from
+        assert(r->first.get()  == 3); // key
+        assert(r->second.get() == 4); // value
+    }
+}
diff --git a/test/std/containers/unord/unord.map/unord.map.swap/swap_noexcept.pass.cpp b/test/std/containers/unord/unord.map/unord.map.swap/swap_noexcept.pass.cpp
index a986882..1056c23 100644
--- a/test/std/containers/unord/unord.map/unord.map.swap/swap_noexcept.pass.cpp
+++ b/test/std/containers/unord/unord.map/unord.map.swap/swap_noexcept.pass.cpp
@@ -10,8 +10,16 @@
 // <unordered_map>
 
 // void swap(unordered_map& c)
-//     noexcept(!allocator_type::propagate_on_container_swap::value ||
-//              __is_nothrow_swappable<allocator_type>::value);
+//      noexcept(
+//          (!allocator_type::propagate_on_container_swap::value ||
+//           __is_nothrow_swappable<allocator_type>::value) &&
+//           __is_nothrow_swappable<hasher>::value &&
+//           __is_nothrow_swappable<key_equal>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<Allocator>::is_always_equal::value &&
+//               noexcept(swap(declval<Hash&>(), declval<Hash&>())) &&
+//               noexcept(swap(declval<Pred&>(), declval<Pred&>())));
 
 // This tests a conforming extension
 
@@ -31,6 +39,22 @@
 };
 
 template <class T>
+struct some_comp2
+{
+    typedef T value_type;
+    
+    some_comp2() {}
+    some_comp2(const some_comp2&) {}
+    void deallocate(void*, unsigned) {}
+    typedef std::true_type propagate_on_container_swap;
+};
+
+#if TEST_STD_VER >= 14
+template <typename T>
+void swap(some_comp2<T>&, some_comp2<T>&) noexcept {}
+#endif
+
+template <class T>
 struct some_hash
 {
     typedef T value_type;
@@ -38,9 +62,62 @@
     some_hash(const some_hash&);
 };
 
+template <class T>
+struct some_hash2
+{
+    typedef T value_type;
+    some_hash2() {}
+    some_hash2(const some_hash2&);
+};
+
+#if TEST_STD_VER >= 14
+template <typename T>
+void swap(some_hash2<T>&, some_hash2<T>&) noexcept {}
+#endif
+
+template <class T>
+struct some_alloc
+{
+    typedef T value_type;
+    
+    some_alloc() {}
+    some_alloc(const some_alloc&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::true_type propagate_on_container_swap;
+};
+
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
+template <class T>
+struct some_alloc3
+{
+    typedef T value_type;
+    
+    some_alloc3() {}
+    some_alloc3(const some_alloc3&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::false_type is_always_equal;
+};
+
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
+	typedef std::pair<const MoveOnly, MoveOnly> MapType;
     {
         typedef std::unordered_map<MoveOnly, MoveOnly> C;
         C c1, c2;
@@ -48,13 +125,13 @@
     }
     {
         typedef std::unordered_map<MoveOnly, MoveOnly, std::hash<MoveOnly>,
-                           std::equal_to<MoveOnly>, test_allocator<std::pair<const MoveOnly, MoveOnly>>> C;
+                           std::equal_to<MoveOnly>, test_allocator<MapType>> C;
         C c1, c2;
         static_assert(noexcept(swap(c1, c2)), "");
     }
     {
         typedef std::unordered_map<MoveOnly, MoveOnly, std::hash<MoveOnly>,
-                          std::equal_to<MoveOnly>, other_allocator<std::pair<const MoveOnly, MoveOnly>>> C;
+                          std::equal_to<MoveOnly>, other_allocator<MapType>> C;
         C c1, c2;
         static_assert(noexcept(swap(c1, c2)), "");
     }
@@ -69,5 +146,54 @@
         C c1, c2;
         static_assert(!noexcept(swap(c1, c2)), "");
     }
+
+#if TEST_STD_VER >= 14
+    { // POCS allocator, throwable swap for hash, throwable swap for comp
+    typedef std::unordered_map<MoveOnly, MoveOnly, some_hash<MoveOnly>, some_comp <MoveOnly>, some_alloc <MapType>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, throwable swap for hash, throwable swap for comp
+    typedef std::unordered_map<MoveOnly, MoveOnly, some_hash<MoveOnly>, some_comp <MoveOnly>, some_alloc2<MapType>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, throwable swap for hash, nothrow swap for comp
+    typedef std::unordered_map<MoveOnly, MoveOnly, some_hash<MoveOnly>, some_comp2<MoveOnly>, some_alloc <MapType>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, throwable swap for hash, nothrow swap for comp
+    typedef std::unordered_map<MoveOnly, MoveOnly, some_hash<MoveOnly>, some_comp2<MoveOnly>, some_alloc2<MapType>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, nothrow swap for hash, throwable swap for comp
+    typedef std::unordered_map<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp <MoveOnly>, some_alloc <MapType>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, nothrow swap for hash, throwable swap for comp
+    typedef std::unordered_map<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp <MoveOnly>, some_alloc2<MapType>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, nothrow swap for hash, nothrow swap for comp
+    typedef std::unordered_map<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc <MapType>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, nothrow swap for hash, nothrow swap for comp
+    typedef std::unordered_map<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc2<MapType>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+
+    { // NOT always equal allocator, nothrow swap for hash, nothrow swap for comp
+    typedef std::unordered_map<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc3<MapType>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
 #endif
 }
diff --git a/test/std/containers/unord/unord.map/unord.map.swap/swap_non_member.pass.cpp b/test/std/containers/unord/unord.map/unord.map.swap/swap_non_member.pass.cpp
index 7e04b8d..f3d51f6 100644
--- a/test/std/containers/unord/unord.map/unord.map.swap/swap_non_member.pass.cpp
+++ b/test/std/containers/unord/unord.map/unord.map.swap/swap_non_member.pass.cpp
@@ -21,6 +21,7 @@
 
 #include "../../../test_compare.h"
 #include "../../../test_hash.h"
+#include "test_macros.h"
 #include "test_allocator.h"
 #include "min_allocator.h"
 
@@ -31,7 +32,6 @@
         typedef test_compare<std::equal_to<int> > Compare;
         typedef test_allocator<std::pair<const int, std::string> > Alloc;
         typedef std::unordered_map<int, std::string, Hash, Compare, Alloc> C;
-        typedef std::pair<int, std::string> P;
         C c1(0, Hash(1), Compare(1), Alloc(1));
         C c2(0, Hash(2), Compare(2), Alloc(2));
         c2.max_load_factor(2);
@@ -212,7 +212,6 @@
         typedef test_compare<std::equal_to<int> > Compare;
         typedef other_allocator<std::pair<const int, std::string> > Alloc;
         typedef std::unordered_map<int, std::string, Hash, Compare, Alloc> C;
-        typedef std::pair<int, std::string> P;
         C c1(0, Hash(1), Compare(1), Alloc(1));
         C c2(0, Hash(2), Compare(2), Alloc(2));
         c2.max_load_factor(2);
@@ -387,13 +386,12 @@
         assert(std::distance(c2.cbegin(), c2.cend()) == c2.size());
         assert(c2.max_load_factor() == 1);
     }
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
         typedef test_hash<std::hash<int> > Hash;
         typedef test_compare<std::equal_to<int> > Compare;
         typedef min_allocator<std::pair<const int, std::string> > Alloc;
         typedef std::unordered_map<int, std::string, Hash, Compare, Alloc> C;
-        typedef std::pair<int, std::string> P;
         C c1(0, Hash(1), Compare(1), Alloc());
         C c2(0, Hash(2), Compare(2), Alloc());
         c2.max_load_factor(2);
diff --git a/test/std/containers/unord/unord.multimap/unord.multimap.modifiers/erase_const_iter.pass.cpp b/test/std/containers/unord/unord.multimap/unord.multimap.modifiers/erase_const_iter.pass.cpp
index 25d6a7a..b31a4e5 100644
--- a/test/std/containers/unord/unord.multimap/unord.multimap.modifiers/erase_const_iter.pass.cpp
+++ b/test/std/containers/unord/unord.multimap/unord.multimap.modifiers/erase_const_iter.pass.cpp
@@ -21,6 +21,15 @@
 
 #include "min_allocator.h"
 
+struct TemplateConstructor
+{
+    template<typename T>
+    TemplateConstructor (const T&) {}
+};
+
+bool operator==(const TemplateConstructor&, const TemplateConstructor&) { return false; }
+struct Hash { size_t operator() (const TemplateConstructor &) const { return 0; } };
+
 int main()
 {
     {
@@ -114,4 +123,18 @@
         assert(std::distance(c.cbegin(), c.cend()) == c.size());
     }
 #endif
+#if __cplusplus >= 201402L
+    {
+    //  This is LWG #2059
+        typedef TemplateConstructor T;
+        typedef std::unordered_multimap<T, int, Hash> C;
+        typedef C::iterator I;
+
+        C m;
+        T a{0};
+        I it = m.find(a);
+        if (it != m.end())
+            m.erase(it);
+    }
+#endif
 }
diff --git a/test/std/containers/unord/unord.multimap/unord.multimap.swap/swap_noexcept.pass.cpp b/test/std/containers/unord/unord.multimap/unord.multimap.swap/swap_noexcept.pass.cpp
index c690bb6..37c8119 100644
--- a/test/std/containers/unord/unord.multimap/unord.multimap.swap/swap_noexcept.pass.cpp
+++ b/test/std/containers/unord/unord.multimap/unord.multimap.swap/swap_noexcept.pass.cpp
@@ -10,8 +10,16 @@
 // <unordered_map>
 
 // void swap(unordered_multimap& c)
-//     noexcept(!allocator_type::propagate_on_container_swap::value ||
-//              __is_nothrow_swappable<allocator_type>::value);
+//      noexcept(
+//          (!allocator_type::propagate_on_container_swap::value ||
+//                __is_nothrow_swappable<allocator_type>::value) &&
+//           __is_nothrow_swappable<hasher>::value &&
+//           __is_nothrow_swappable<key_equal>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<allocator_type>::is_always_equal::value &&
+//               __is_nothrow_swappable<hasher>::value &&
+//               __is_nothrow_swappable<key_equal>::value);
 
 // This tests a conforming extension
 
@@ -31,6 +39,22 @@
 };
 
 template <class T>
+struct some_comp2
+{
+    typedef T value_type;
+    
+    some_comp2() {}
+    some_comp2(const some_comp2&) {}
+    void deallocate(void*, unsigned) {}
+    typedef std::true_type propagate_on_container_swap;
+};
+
+#if TEST_STD_VER >= 14
+template <typename T>
+void swap(some_comp2<T>&, some_comp2<T>&) noexcept {}
+#endif
+
+template <class T>
 struct some_hash
 {
     typedef T value_type;
@@ -38,9 +62,61 @@
     some_hash(const some_hash&);
 };
 
+template <class T>
+struct some_hash2
+{
+    typedef T value_type;
+    some_hash2() {}
+    some_hash2(const some_hash2&);
+};
+
+#if TEST_STD_VER >= 14
+template <typename T>
+void swap(some_hash2<T>&, some_hash2<T>&) noexcept {}
+#endif
+
+template <class T>
+struct some_alloc
+{
+    typedef T value_type;
+    
+    some_alloc() {}
+    some_alloc(const some_alloc&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::true_type propagate_on_container_swap;
+};
+
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
+template <class T>
+struct some_alloc3
+{
+    typedef T value_type;
+    
+    some_alloc3() {}
+    some_alloc3(const some_alloc3&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::false_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
+	typedef std::pair<const MoveOnly, MoveOnly> MapType;
     {
         typedef std::unordered_multimap<MoveOnly, MoveOnly> C;
         C c1, c2;
@@ -48,13 +124,13 @@
     }
     {
         typedef std::unordered_multimap<MoveOnly, MoveOnly, std::hash<MoveOnly>,
-                           std::equal_to<MoveOnly>, test_allocator<std::pair<const MoveOnly, MoveOnly>>> C;
+                           std::equal_to<MoveOnly>, test_allocator<MapType>> C;
         C c1, c2;
         static_assert(noexcept(swap(c1, c2)), "");
     }
     {
         typedef std::unordered_multimap<MoveOnly, MoveOnly, std::hash<MoveOnly>,
-                          std::equal_to<MoveOnly>, other_allocator<std::pair<const MoveOnly, MoveOnly>>> C;
+                          std::equal_to<MoveOnly>, other_allocator<MapType>> C;
         C c1, c2;
         static_assert(noexcept(swap(c1, c2)), "");
     }
@@ -69,5 +145,54 @@
         C c1, c2;
         static_assert(!noexcept(swap(c1, c2)), "");
     }
+
+#if TEST_STD_VER >= 14
+    { // POCS allocator, throwable swap for hash, throwable swap for comp
+    typedef std::unordered_multimap<MoveOnly, MoveOnly, some_hash<MoveOnly>, some_comp <MoveOnly>, some_alloc <MapType>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, throwable swap for hash, throwable swap for comp
+    typedef std::unordered_multimap<MoveOnly, MoveOnly, some_hash<MoveOnly>, some_comp <MoveOnly>, some_alloc2<MapType>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, throwable swap for hash, nothrow swap for comp
+    typedef std::unordered_multimap<MoveOnly, MoveOnly, some_hash<MoveOnly>, some_comp2<MoveOnly>, some_alloc <MapType>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, throwable swap for hash, nothrow swap for comp
+    typedef std::unordered_multimap<MoveOnly, MoveOnly, some_hash<MoveOnly>, some_comp2<MoveOnly>, some_alloc2<MapType>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, nothrow swap for hash, throwable swap for comp
+    typedef std::unordered_multimap<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp <MoveOnly>, some_alloc <MapType>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, nothrow swap for hash, throwable swap for comp
+    typedef std::unordered_multimap<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp <MoveOnly>, some_alloc2<MapType>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, nothrow swap for hash, nothrow swap for comp
+    typedef std::unordered_multimap<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc <MapType>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, nothrow swap for hash, nothrow swap for comp
+    typedef std::unordered_multimap<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc2<MapType>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+    { // NOT always equal allocator, nothrow swap for hash, nothrow swap for comp
+    typedef std::unordered_multimap<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc3<MapType>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/containers/unord/unord.multiset/erase_const_iter.pass.cpp b/test/std/containers/unord/unord.multiset/erase_const_iter.pass.cpp
index 6a005d3..d3be2b6 100644
--- a/test/std/containers/unord/unord.multiset/erase_const_iter.pass.cpp
+++ b/test/std/containers/unord/unord.multiset/erase_const_iter.pass.cpp
@@ -20,6 +20,15 @@
 
 #include "min_allocator.h"
 
+struct TemplateConstructor
+{
+    template<typename T>
+    TemplateConstructor (const T&) {}
+};
+
+bool operator==(const TemplateConstructor&, const TemplateConstructor&) { return false; }
+struct Hash { size_t operator() (const TemplateConstructor &) const { return 0; } };
+
 int main()
 {
     {
@@ -67,4 +76,18 @@
         assert(c.count(4) == 1);
     }
 #endif
+#if __cplusplus >= 201402L
+    {
+    //  This is LWG #2059
+        typedef TemplateConstructor T;
+        typedef std::unordered_set<T, Hash> C;
+        typedef C::iterator I;
+
+        C m;
+        T a{0};
+        I it = m.find(a);
+        if (it != m.end())
+            m.erase(it);
+    }
+#endif
 }
diff --git a/test/std/containers/unord/unord.multiset/unord.multiset.swap/swap_noexcept.pass.cpp b/test/std/containers/unord/unord.multiset/unord.multiset.swap/swap_noexcept.pass.cpp
index 7dc653b..63642fc 100644
--- a/test/std/containers/unord/unord.multiset/unord.multiset.swap/swap_noexcept.pass.cpp
+++ b/test/std/containers/unord/unord.multiset/unord.multiset.swap/swap_noexcept.pass.cpp
@@ -10,8 +10,16 @@
 // <unordered_set>
 
 // void swap(unordered_multiset& c)
-//     noexcept(!allocator_type::propagate_on_container_swap::value ||
-//              __is_nothrow_swappable<allocator_type>::value);
+//      noexcept(
+//          (!allocator_type::propagate_on_container_swap::value ||
+//           __is_nothrow_swappable<allocator_type>::value) &&
+//           __is_nothrow_swappable<hasher>::value &&
+//           __is_nothrow_swappable<key_equal>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<Allocator>::is_always_equal::value &&
+//               noexcept(swap(declval<Hash&>(), declval<Hash&>())) &&
+//               noexcept(swap(declval<Pred&>(), declval<Pred&>())));
 
 // This tests a conforming extension
 
@@ -31,6 +39,22 @@
 };
 
 template <class T>
+struct some_comp2
+{
+    typedef T value_type;
+    
+    some_comp2() {}
+    some_comp2(const some_comp2&) {}
+    void deallocate(void*, unsigned) {}
+    typedef std::true_type propagate_on_container_swap;
+};
+
+#if TEST_STD_VER >= 14
+template <typename T>
+void swap(some_comp2<T>&, some_comp2<T>&) noexcept {}
+#endif
+
+template <class T>
 struct some_hash
 {
     typedef T value_type;
@@ -38,6 +62,57 @@
     some_hash(const some_hash&);
 };
 
+template <class T>
+struct some_hash2
+{
+    typedef T value_type;
+    some_hash2() {}
+    some_hash2(const some_hash2&);
+};
+
+#if TEST_STD_VER >= 14
+template <typename T>
+void swap(some_hash2<T>&, some_hash2<T>&) noexcept {}
+#endif
+
+template <class T>
+struct some_alloc
+{
+    typedef T value_type;
+    
+    some_alloc() {}
+    some_alloc(const some_alloc&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::true_type propagate_on_container_swap;
+};
+
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
+template <class T>
+struct some_alloc3
+{
+    typedef T value_type;
+    
+    some_alloc3() {}
+    some_alloc3(const some_alloc3&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::false_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
@@ -69,5 +144,55 @@
         C c1, c2;
         static_assert(!noexcept(swap(c1, c2)), "");
     }
+
+#if TEST_STD_VER >= 14
+    { // POCS allocator, throwable swap for hash, throwable swap for comp
+    typedef std::unordered_multiset<MoveOnly, some_hash<MoveOnly>, some_comp <MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, throwable swap for hash, throwable swap for comp
+    typedef std::unordered_multiset<MoveOnly, some_hash<MoveOnly>, some_comp <MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, throwable swap for hash, nothrow swap for comp
+    typedef std::unordered_multiset<MoveOnly, some_hash<MoveOnly>, some_comp2<MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, throwable swap for hash, nothrow swap for comp
+    typedef std::unordered_multiset<MoveOnly, some_hash<MoveOnly>, some_comp2<MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, nothrow swap for hash, throwable swap for comp
+    typedef std::unordered_multiset<MoveOnly, some_hash2<MoveOnly>, some_comp <MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, nothrow swap for hash, throwable swap for comp
+    typedef std::unordered_multiset<MoveOnly, some_hash2<MoveOnly>, some_comp <MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, nothrow swap for hash, nothrow swap for comp
+    typedef std::unordered_multiset<MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, nothrow swap for hash, nothrow swap for comp
+    typedef std::unordered_multiset<MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+
+    { // NOT always equal allocator, nothrow swap for hash, nothrow swap for comp
+    typedef std::unordered_multiset<MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc3<MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/containers/unord/unord.set/erase_const_iter.pass.cpp b/test/std/containers/unord/unord.set/erase_const_iter.pass.cpp
index 3a9cb58..4110953 100644
--- a/test/std/containers/unord/unord.set/erase_const_iter.pass.cpp
+++ b/test/std/containers/unord/unord.set/erase_const_iter.pass.cpp
@@ -20,6 +20,15 @@
 
 #include "min_allocator.h"
 
+struct TemplateConstructor
+{
+    template<typename T>
+    TemplateConstructor (const T&) {}
+};
+
+bool operator==(const TemplateConstructor&, const TemplateConstructor&) { return false; }
+struct Hash { size_t operator() (const TemplateConstructor &) const { return 0; } };
+
 int main()
 {
     {
@@ -64,4 +73,18 @@
         assert(c.count(4) == 1);
     }
 #endif
+#if __cplusplus >= 201402L
+    {
+    //  This is LWG #2059
+        typedef TemplateConstructor T;
+        typedef std::unordered_set<T, Hash> C;
+        typedef C::iterator I;
+
+        C m;
+        T a{0};
+        I it = m.find(a);
+        if (it != m.end())
+            m.erase(it);
+    }
+#endif
 }
diff --git a/test/std/containers/unord/unord.set/unord.set.swap/swap_noexcept.pass.cpp b/test/std/containers/unord/unord.set/unord.set.swap/swap_noexcept.pass.cpp
index cba0923..5d74640 100644
--- a/test/std/containers/unord/unord.set/unord.set.swap/swap_noexcept.pass.cpp
+++ b/test/std/containers/unord/unord.set/unord.set.swap/swap_noexcept.pass.cpp
@@ -10,8 +10,16 @@
 // <unordered_set>
 
 // void swap(unordered_set& c)
-//     noexcept(!allocator_type::propagate_on_container_swap::value ||
-//              __is_nothrow_swappable<allocator_type>::value);
+//      noexcept(
+//          (!allocator_type::propagate_on_container_swap::value ||
+//           __is_nothrow_swappable<allocator_type>::value) &&
+//           __is_nothrow_swappable<hasher>::value &&
+//           __is_nothrow_swappable<key_equal>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<Allocator>::is_always_equal::value &&
+//               noexcept(swap(declval<Hash&>(), declval<Hash&>())) &&
+//               noexcept(swap(declval<Pred&>(), declval<Pred&>())));
 
 // This tests a conforming extension
 
@@ -31,6 +39,22 @@
 };
 
 template <class T>
+struct some_comp2
+{
+    typedef T value_type;
+    
+    some_comp2() {}
+    some_comp2(const some_comp2&) {}
+    void deallocate(void*, unsigned) {}
+    typedef std::true_type propagate_on_container_swap;
+};
+
+#if TEST_STD_VER >= 14
+template <typename T>
+void swap(some_comp2<T>&, some_comp2<T>&) noexcept {}
+#endif
+
+template <class T>
 struct some_hash
 {
     typedef T value_type;
@@ -38,6 +62,57 @@
     some_hash(const some_hash&);
 };
 
+template <class T>
+struct some_hash2
+{
+    typedef T value_type;
+    some_hash2() {}
+    some_hash2(const some_hash2&);
+};
+
+#if TEST_STD_VER >= 14
+template <typename T>
+void swap(some_hash2<T>&, some_hash2<T>&) noexcept {}
+#endif
+
+template <class T>
+struct some_alloc
+{
+    typedef T value_type;
+    
+    some_alloc() {}
+    some_alloc(const some_alloc&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::true_type propagate_on_container_swap;
+};
+
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
+template <class T>
+struct some_alloc3
+{
+    typedef T value_type;
+    
+    some_alloc3() {}
+    some_alloc3(const some_alloc3&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::false_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
@@ -69,5 +144,55 @@
         C c1, c2;
         static_assert(!noexcept(swap(c1, c2)), "");
     }
+
+#if TEST_STD_VER >= 14
+    { // POCS allocator, throwable swap for hash, throwable swap for comp
+    typedef std::unordered_set<MoveOnly, some_hash<MoveOnly>, some_comp <MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, throwable swap for hash, throwable swap for comp
+    typedef std::unordered_set<MoveOnly, some_hash<MoveOnly>, some_comp <MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, throwable swap for hash, nothrow swap for comp
+    typedef std::unordered_set<MoveOnly, some_hash<MoveOnly>, some_comp2<MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, throwable swap for hash, nothrow swap for comp
+    typedef std::unordered_set<MoveOnly, some_hash<MoveOnly>, some_comp2<MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, nothrow swap for hash, throwable swap for comp
+    typedef std::unordered_set<MoveOnly, some_hash2<MoveOnly>, some_comp <MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, nothrow swap for hash, throwable swap for comp
+    typedef std::unordered_set<MoveOnly, some_hash2<MoveOnly>, some_comp <MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert(!noexcept(swap(c1, c2)), "");
+    }
+    { // POCS allocator, nothrow swap for hash, nothrow swap for comp
+    typedef std::unordered_set<MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc <MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+    { // always equal allocator, nothrow swap for hash, nothrow swap for comp
+    typedef std::unordered_set<MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc2<MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+
+    { // NOT always equal allocator, nothrow swap for hash, nothrow swap for comp
+    typedef std::unordered_set<MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc3<MoveOnly>> C;
+    C c1, c2;
+    static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/depr/depr.auto.ptr/auto.ptr/auto.ptr.conv/convert_to_auto_ptr_ref.pass.cpp b/test/std/depr/depr.auto.ptr/auto.ptr/auto.ptr.conv/convert_to_auto_ptr_ref.pass.cpp
index f61a28e..a5db81e 100644
--- a/test/std/depr/depr.auto.ptr/auto.ptr/auto.ptr.conv/convert_to_auto_ptr_ref.pass.cpp
+++ b/test/std/depr/depr.auto.ptr/auto.ptr/auto.ptr.conv/convert_to_auto_ptr_ref.pass.cpp
@@ -24,6 +24,10 @@
     B* p1 = new B(1);
     std::auto_ptr<B> ap1(p1);
     std::auto_ptr_ref<A> apr = ap1;
+    std::auto_ptr<A> ap2(apr);
+    assert(ap1.get() == nullptr);
+    assert(ap2.get() == p1);
+    ap2.release();
     delete p1;
 }
 
diff --git a/test/std/depr/depr.auto.ptr/auto.ptr/element_type.pass.cpp b/test/std/depr/depr.auto.ptr/auto.ptr/element_type.pass.cpp
index 2d1c2af..2565634 100644
--- a/test/std/depr/depr.auto.ptr/auto.ptr/element_type.pass.cpp
+++ b/test/std/depr/depr.auto.ptr/auto.ptr/element_type.pass.cpp
@@ -25,6 +25,8 @@
 test()
 {
     static_assert((std::is_same<typename std::auto_ptr<T>::element_type, T>::value), "");
+    std::auto_ptr<T> p;
+    ((void)p);
 }
 
 int main()
@@ -32,5 +34,4 @@
     test<int>();
     test<double>();
     test<void>();
-    std::auto_ptr<void> p;
 }
diff --git a/test/std/depr/depr.c.headers/inttypes_h.pass.cpp b/test/std/depr/depr.c.headers/inttypes_h.pass.cpp
index 4adf82d..a799aea 100644
--- a/test/std/depr/depr.c.headers/inttypes_h.pass.cpp
+++ b/test/std/depr/depr.c.headers/inttypes_h.pass.cpp
@@ -631,7 +631,8 @@
 int main()
 {
     {
-    imaxdiv_t  i1 = {0};
+      imaxdiv_t  i1 = {0};
+      ((void)i1);
     }
     intmax_t i = 0;
     static_assert((std::is_same<decltype(imaxabs(i)), intmax_t>::value), "");
diff --git a/test/std/depr/depr.c.headers/locale_h.pass.cpp b/test/std/depr/depr.c.headers/locale_h.pass.cpp
index 6ecf5a8..f5735b6 100644
--- a/test/std/depr/depr.c.headers/locale_h.pass.cpp
+++ b/test/std/depr/depr.c.headers/locale_h.pass.cpp
@@ -42,7 +42,7 @@
 
 int main()
 {
-    lconv lc;
+    lconv lc; ((void)lc);
     static_assert((std::is_same<decltype(setlocale(0, "")), char*>::value), "");
     static_assert((std::is_same<decltype(localeconv()), lconv*>::value), "");
 }
diff --git a/test/std/depr/depr.c.headers/signal_h.pass.cpp b/test/std/depr/depr.c.headers/signal_h.pass.cpp
index a8ef5f9..83f45c9 100644
--- a/test/std/depr/depr.c.headers/signal_h.pass.cpp
+++ b/test/std/depr/depr.c.headers/signal_h.pass.cpp
@@ -50,7 +50,7 @@
 
 int main()
 {
-    sig_atomic_t sig;
+    sig_atomic_t sig; ((void)sig);
     typedef void (*func)(int);
     static_assert((std::is_same<decltype(signal(0, (func)0)), func>::value), "");
     static_assert((std::is_same<decltype(raise(0)), int>::value), "");
diff --git a/test/std/depr/depr.c.headers/stdarg_h.pass.cpp b/test/std/depr/depr.c.headers/stdarg_h.pass.cpp
index 7a60902..f7d12b1 100644
--- a/test/std/depr/depr.c.headers/stdarg_h.pass.cpp
+++ b/test/std/depr/depr.c.headers/stdarg_h.pass.cpp
@@ -32,4 +32,5 @@
 int main()
 {
     va_list va;
+    ((void)va);
 }
diff --git a/test/std/depr/depr.c.headers/stdio_h.pass.cpp b/test/std/depr/depr.c.headers/stdio_h.pass.cpp
index d4cfbc8..ba6714d 100644
--- a/test/std/depr/depr.c.headers/stdio_h.pass.cpp
+++ b/test/std/depr/depr.c.headers/stdio_h.pass.cpp
@@ -11,6 +11,7 @@
 
 #include <stdio.h>
 #include <type_traits>
+#include "test_macros.h"
 
 #ifndef BUFSIZ
 #error BUFSIZ not defined
@@ -78,14 +79,16 @@
 
 #include <cstdarg>
 
-#pragma clang diagnostic ignored "-Wformat-zero-length"
+#pragma GCC diagnostic ignored "-Wformat-zero-length"
+#pragma GCC diagnostic ignored "-Wdeprecated-declarations" // for tmpnam
 
 int main()
 {
     FILE* fp = 0;
     fpos_t fpos = {0};
-    size_t s = 0;
+    size_t s = 0; ((void)s);
     char* cp = 0;
+    char arr[] = {'a', 'b'};
     va_list va;
     static_assert((std::is_same<decltype(remove("")), int>::value), "");
     static_assert((std::is_same<decltype(rename("","")), int>::value), "");
@@ -117,7 +120,7 @@
     static_assert((std::is_same<decltype(fputs("",fp)), int>::value), "");
     static_assert((std::is_same<decltype(getc(fp)), int>::value), "");
     static_assert((std::is_same<decltype(getchar()), int>::value), "");
-#if _LIBCPP_STD_VER < 14
+#if TEST_STD_VER < 14
     static_assert((std::is_same<decltype(gets(cp)), char*>::value), "");
 #endif
     static_assert((std::is_same<decltype(putc(0,fp)), int>::value), "");
@@ -125,7 +128,7 @@
     static_assert((std::is_same<decltype(puts("")), int>::value), "");
     static_assert((std::is_same<decltype(ungetc(0,fp)), int>::value), "");
     static_assert((std::is_same<decltype(fread((void*)0,0,0,fp)), size_t>::value), "");
-    static_assert((std::is_same<decltype(fwrite((const void*)0,0,0,fp)), size_t>::value), "");
+    static_assert((std::is_same<decltype(fwrite((const void*)arr,1,0,fp)), size_t>::value), "");
     static_assert((std::is_same<decltype(fgetpos(fp, &fpos)), int>::value), "");
     static_assert((std::is_same<decltype(fseek(fp, 0,0)), int>::value), "");
     static_assert((std::is_same<decltype(fsetpos(fp, &fpos)), int>::value), "");
diff --git a/test/std/depr/depr.c.headers/stdlib_h.pass.cpp b/test/std/depr/depr.c.headers/stdlib_h.pass.cpp
index 98b19c6..d1cc443 100644
--- a/test/std/depr/depr.c.headers/stdlib_h.pass.cpp
+++ b/test/std/depr/depr.c.headers/stdlib_h.pass.cpp
@@ -34,10 +34,10 @@
 
 int main()
 {
-    size_t s = 0;
-    div_t d;
-    ldiv_t ld;
-    lldiv_t lld;
+    size_t s = 0; ((void)s);
+    div_t d; ((void)d);
+    ldiv_t ld; ((void)ld);
+    lldiv_t lld; ((void)lld);
     char** endptr = 0;
     static_assert((std::is_same<decltype(atof("")), double>::value), "");
     static_assert((std::is_same<decltype(atoi("")), int>::value), "");
@@ -71,12 +71,14 @@
     static_assert((std::is_same<decltype(div(0,0)), div_t>::value), "");
     static_assert((std::is_same<decltype(ldiv(0L,0L)), ldiv_t>::value), "");
     static_assert((std::is_same<decltype(lldiv(0LL,0LL)), lldiv_t>::value), "");
-    static_assert((std::is_same<decltype(mblen("",0)), int>::value), "");
     wchar_t* pw = 0;
     const wchar_t* pwc = 0;
     char* pc = 0;
+#ifndef _LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
+    static_assert((std::is_same<decltype(mblen("",0)), int>::value), "");
     static_assert((std::is_same<decltype(mbtowc(pw,"",0)), int>::value), "");
     static_assert((std::is_same<decltype(wctomb(pc,L' ')), int>::value), "");
+#endif
     static_assert((std::is_same<decltype(mbstowcs(pw,"",0)), size_t>::value), "");
     static_assert((std::is_same<decltype(wcstombs(pc,pwc,0)), size_t>::value), "");
 }
diff --git a/test/std/depr/depr.c.headers/string_h.pass.cpp b/test/std/depr/depr.c.headers/string_h.pass.cpp
index fc7f65d..afc784f 100644
--- a/test/std/depr/depr.c.headers/string_h.pass.cpp
+++ b/test/std/depr/depr.c.headers/string_h.pass.cpp
@@ -41,7 +41,9 @@
     static_assert((std::is_same<decltype(strrchr(cp, 0)), char*>::value), "");
     static_assert((std::is_same<decltype(strspn(cpc, cpc)), size_t>::value), "");
     static_assert((std::is_same<decltype(strstr(cp, cpc)), char*>::value), "");
+#ifndef _LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
     static_assert((std::is_same<decltype(strtok(cp, cpc)), char*>::value), "");
+#endif
     static_assert((std::is_same<decltype(memset(vp, 0, s)), void*>::value), "");
     static_assert((std::is_same<decltype(strerror(0)), char*>::value), "");
     static_assert((std::is_same<decltype(strlen(cpc)), size_t>::value), "");
diff --git a/test/std/depr/depr.c.headers/time_h.pass.cpp b/test/std/depr/depr.c.headers/time_h.pass.cpp
index c468693..0d229af 100644
--- a/test/std/depr/depr.c.headers/time_h.pass.cpp
+++ b/test/std/depr/depr.c.headers/time_h.pass.cpp
@@ -22,7 +22,7 @@
 
 int main()
 {
-    clock_t c = 0;
+    clock_t c = 0; ((void)c);
     size_t s = 0;
     time_t t = 0;
     tm tmv = {0};
diff --git a/test/std/depr/depr.c.headers/wchar_h.pass.cpp b/test/std/depr/depr.c.headers/wchar_h.pass.cpp
index 68bea49..8d1c3b7 100644
--- a/test/std/depr/depr.c.headers/wchar_h.pass.cpp
+++ b/test/std/depr/depr.c.headers/wchar_h.pass.cpp
@@ -28,6 +28,10 @@
 #error WEOF not defined
 #endif
 
+#if defined(__clang__)
+#pragma clang diagnostic ignored "-Wmissing-braces"
+#endif
+
 int main()
 {
     mbstate_t mb = {0};
diff --git a/test/std/depr/exception.unexpected/unexpected.handler/unexpected_handler.pass.cpp b/test/std/depr/exception.unexpected/unexpected.handler/unexpected_handler.pass.cpp
index 7fab500..5879529 100644
--- a/test/std/depr/exception.unexpected/unexpected.handler/unexpected_handler.pass.cpp
+++ b/test/std/depr/exception.unexpected/unexpected.handler/unexpected_handler.pass.cpp
@@ -16,4 +16,5 @@
 int main()
 {
     std::unexpected_handler p = f;
+    ((void)p);
 }
diff --git a/test/std/diagnostics/syserr/syserr.errcat/syserr.errcat.overview/error_category.pass.cpp b/test/std/diagnostics/syserr/syserr.errcat/syserr.errcat.overview/error_category.pass.cpp
index 2353058..79162dd 100644
--- a/test/std/diagnostics/syserr/syserr.errcat/syserr.errcat.overview/error_category.pass.cpp
+++ b/test/std/diagnostics/syserr/syserr.errcat/syserr.errcat.overview/error_category.pass.cpp
@@ -16,4 +16,5 @@
 int main()
 {
     std::error_category* p = 0;
+    ((void)p);
 }
diff --git a/test/std/experimental/algorithms/alg.random.sample/sample.fail.cpp b/test/std/experimental/algorithms/alg.random.sample/sample.fail.cpp
new file mode 100644
index 0000000..eeb4373
--- /dev/null
+++ b/test/std/experimental/algorithms/alg.random.sample/sample.fail.cpp
@@ -0,0 +1,36 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <algorithm>
+
+// template <class PopulationIterator, class SampleIterator, class Distance,
+//           class UniformRandomNumberGenerator>
+// SampleIterator sample(PopulationIterator first, PopulationIterator last,
+//                       SampleIterator out, Distance n,
+//                       UniformRandomNumberGenerator &&g);
+
+#include <experimental/algorithm>
+#include <random>
+#include <cassert>
+
+#include "test_iterators.h"
+
+template <class PopulationIterator, class SampleIterator> void test() {
+  int ia[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
+  const unsigned is = sizeof(ia) / sizeof(ia[0]);
+  const unsigned os = 4;
+  int oa[os];
+  std::minstd_rand g;
+  std::experimental::sample(PopulationIterator(ia), PopulationIterator(ia + is),
+                            SampleIterator(oa), os, g);
+}
+
+int main() {
+  test<input_iterator<int *>, output_iterator<int *> >();
+}
diff --git a/test/std/experimental/algorithms/alg.random.sample/sample.pass.cpp b/test/std/experimental/algorithms/alg.random.sample/sample.pass.cpp
new file mode 100644
index 0000000..0f0784d
--- /dev/null
+++ b/test/std/experimental/algorithms/alg.random.sample/sample.pass.cpp
@@ -0,0 +1,146 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <algorithm>
+
+// template <class PopulationIterator, class SampleIterator, class Distance,
+//           class UniformRandomNumberGenerator>
+// SampleIterator sample(PopulationIterator first, PopulationIterator last,
+//                       SampleIterator out, Distance n,
+//                       UniformRandomNumberGenerator &&g);
+
+#include <experimental/algorithm>
+#include <random>
+#include <cassert>
+
+#include "test_iterators.h"
+
+struct ReservoirSampleExpectations {
+  enum { os = 4 };
+  static int oa1[os];
+  static int oa2[os];
+};
+
+int ReservoirSampleExpectations::oa1[] = {10, 5, 9, 4};
+int ReservoirSampleExpectations::oa2[] = {5, 2, 10, 4};
+
+struct SelectionSampleExpectations {
+  enum { os = 4 };
+  static int oa1[os];
+  static int oa2[os];
+};
+
+int SelectionSampleExpectations::oa1[] = {1, 4, 6, 7};
+int SelectionSampleExpectations::oa2[] = {1, 2, 6, 8};
+
+template <class IteratorCategory> struct TestExpectations
+    : public SelectionSampleExpectations {};
+
+template <>
+struct TestExpectations<std::input_iterator_tag>
+    : public ReservoirSampleExpectations {};
+
+template <template<class> class PopulationIteratorType, class PopulationItem,
+          template<class> class SampleIteratorType, class SampleItem>
+void test() {
+  typedef PopulationIteratorType<PopulationItem *> PopulationIterator;
+  typedef SampleIteratorType<SampleItem *> SampleIterator;
+  PopulationItem ia[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
+  const unsigned is = sizeof(ia) / sizeof(ia[0]);
+  typedef TestExpectations<typename std::iterator_traits<
+      PopulationIterator>::iterator_category> Expectations;
+  const unsigned os = Expectations::os;
+  SampleItem oa[os];
+  const int *oa1 = Expectations::oa1;
+  const int *oa2 = Expectations::oa2;
+  std::minstd_rand g;
+  SampleIterator end;
+  end = std::experimental::sample(PopulationIterator(ia),
+                                  PopulationIterator(ia + is),
+                                  SampleIterator(oa), os, g);
+  assert(&*end - oa == std::min(os, is));
+  assert(std::equal(oa, oa + os, oa1));
+  end = std::experimental::sample(PopulationIterator(ia),
+                                  PopulationIterator(ia + is),
+                                  SampleIterator(oa), os, g);
+  assert(&*end - oa == std::min(os, is));
+  assert(std::equal(oa, oa + os, oa2));
+}
+
+template <template<class> class PopulationIteratorType, class PopulationItem,
+          template<class> class SampleIteratorType, class SampleItem>
+void test_empty_population() {
+  typedef PopulationIteratorType<PopulationItem *> PopulationIterator;
+  typedef SampleIteratorType<SampleItem *> SampleIterator;
+  PopulationItem ia[] = {42};
+  const unsigned os = 4;
+  SampleItem oa[os];
+  std::minstd_rand g;
+  SampleIterator end =
+      std::experimental::sample(PopulationIterator(ia), PopulationIterator(ia),
+                                SampleIterator(oa), os, g);
+  assert(&*end == oa);
+}
+
+template <template<class> class PopulationIteratorType, class PopulationItem,
+          template<class> class SampleIteratorType, class SampleItem>
+void test_empty_sample() {
+  typedef PopulationIteratorType<PopulationItem *> PopulationIterator;
+  typedef SampleIteratorType<SampleItem *> SampleIterator;
+  PopulationItem ia[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
+  const unsigned is = sizeof(ia) / sizeof(ia[0]);
+  SampleItem oa[1];
+  std::minstd_rand g;
+  SampleIterator end =
+      std::experimental::sample(PopulationIterator(ia), PopulationIterator(ia + is),
+                                SampleIterator(oa), 0, g);
+  assert(&*end == oa);
+}
+
+template <template<class> class PopulationIteratorType, class PopulationItem,
+          template<class> class SampleIteratorType, class SampleItem>
+void test_small_population() {
+  // The population size is less than the sample size.
+  typedef PopulationIteratorType<PopulationItem *> PopulationIterator;
+  typedef SampleIteratorType<SampleItem *> SampleIterator;
+  PopulationItem ia[] = {1, 2, 3, 4, 5};
+  const unsigned is = sizeof(ia) / sizeof(ia[0]);
+  const unsigned os = 8;
+  SampleItem oa[os];
+  const SampleItem oa1[] = {1, 2, 3, 4, 5};
+  std::minstd_rand g;
+  SampleIterator end;
+  end = std::experimental::sample(PopulationIterator(ia),
+                                  PopulationIterator(ia + is),
+                                  SampleIterator(oa), os, g);
+  assert(&*end - oa == std::min(os, is));
+  assert(std::equal(oa, &*end, oa1));
+}
+
+int main() {
+  test<input_iterator, int, random_access_iterator, int>();
+  test<forward_iterator, int, output_iterator, int>();
+  test<forward_iterator, int, random_access_iterator, int>();
+
+  test<input_iterator, int, random_access_iterator, double>();
+  test<forward_iterator, int, output_iterator, double>();
+  test<forward_iterator, int, random_access_iterator, double>();
+
+  test_empty_population<input_iterator, int, random_access_iterator, int>();
+  test_empty_population<forward_iterator, int, output_iterator, int>();
+  test_empty_population<forward_iterator, int, random_access_iterator, int>();
+
+  test_empty_sample<input_iterator, int, random_access_iterator, int>();
+  test_empty_sample<forward_iterator, int, output_iterator, int>();
+  test_empty_sample<forward_iterator, int, random_access_iterator, int>();
+
+  test_small_population<input_iterator, int, random_access_iterator, int>();
+  test_small_population<forward_iterator, int, output_iterator, int>();
+  test_small_population<forward_iterator, int, random_access_iterator, int>();
+}
diff --git a/test/std/experimental/algorithms/alg.random.sample/sample.stable.pass.cpp b/test/std/experimental/algorithms/alg.random.sample/sample.stable.pass.cpp
new file mode 100644
index 0000000..c805c66
--- /dev/null
+++ b/test/std/experimental/algorithms/alg.random.sample/sample.stable.pass.cpp
@@ -0,0 +1,53 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <algorithm>
+
+// template <class PopulationIterator, class SampleIterator, class Distance,
+//           class UniformRandomNumberGenerator>
+// SampleIterator sample(PopulationIterator first, PopulationIterator last,
+//                       SampleIterator out, Distance n,
+//                       UniformRandomNumberGenerator &&g);
+
+#include <experimental/algorithm>
+#include <random>
+#include <cassert>
+
+#include "test_iterators.h"
+
+// Stable if and only if PopulationIterator meets the requirements of a
+// ForwardIterator type.
+template <class PopulationIterator, class SampleIterator>
+void test_stability(bool expect_stable) {
+  const unsigned kPopulationSize = 100;
+  int ia[kPopulationSize];
+  for (unsigned i = 0; i < kPopulationSize; ++i)
+    ia[i] = i;
+  PopulationIterator first(ia);
+  PopulationIterator last(ia + kPopulationSize);
+
+  const unsigned kSampleSize = 20;
+  int oa[kPopulationSize];
+  SampleIterator out(oa);
+
+  std::minstd_rand g;
+
+  const int kIterations = 1000;
+  bool unstable = false;
+  for (int i = 0; i < kIterations; ++i) {
+    std::experimental::sample(first, last, out, kSampleSize, g);
+    unstable |= !std::is_sorted(oa, oa + kSampleSize);
+  }
+  assert(expect_stable == !unstable);
+}
+
+int main() {
+  test_stability<forward_iterator<int *>, output_iterator<int *> >(true);
+  test_stability<input_iterator<int *>, random_access_iterator<int *> >(false);
+}
diff --git a/test/std/experimental/algorithms/alg.search/search.pass.cpp b/test/std/experimental/algorithms/alg.search/search.pass.cpp
new file mode 100644
index 0000000..e27f0e4
--- /dev/null
+++ b/test/std/experimental/algorithms/alg.search/search.pass.cpp
@@ -0,0 +1,43 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <algorithm>
+
+//   template<class ForwardIterator, class Searcher>
+//   ForwardIterator search(ForwardIterator first, ForwardIterator last,
+//                          const Searcher& searcher);
+//
+//		returns searcher.operator(first, last)
+//
+
+#include <experimental/algorithm>
+#include <cassert>
+
+#include "test_iterators.h"
+
+int searcher_called = 0;
+
+struct MySearcher {
+    template <typename Iterator>
+    Iterator operator() ( Iterator b, Iterator /*e*/) const 
+    {
+        ++searcher_called;
+        return b;
+    }
+};
+
+
+int main() {
+    typedef int * RI;
+    static_assert(std::is_same<RI, decltype(std::experimental::search(RI(), RI(), MySearcher()))>::value, "" );
+
+    RI it{nullptr};
+    assert(it == std::experimental::search(it, it, MySearcher()));
+    assert(searcher_called == 1);
+}
diff --git a/test/std/experimental/any/any.class/any.assign/copy.pass.cpp b/test/std/experimental/any/any.class/any.assign/copy.pass.cpp
new file mode 100644
index 0000000..8ee575c
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.assign/copy.pass.cpp
@@ -0,0 +1,197 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// any& operator=(any const &);
+
+// Test copy assignment
+
+#include <experimental/any>
+#include <cassert>
+
+#include "any_helpers.h"
+#include "count_new.hpp"
+#include "test_macros.h"
+
+using std::experimental::any;
+using std::experimental::any_cast;
+
+template <class LHS, class RHS>
+void test_copy_assign() {
+    assert(LHS::count == 0);
+    assert(RHS::count == 0);
+    LHS::reset();
+    RHS::reset();
+    {
+        any lhs(LHS(1));
+        any const rhs(RHS(2));
+
+        assert(LHS::count == 1);
+        assert(RHS::count == 1);
+        assert(RHS::copied == 0);
+
+        lhs = rhs;
+
+        assert(RHS::copied == 1);
+        assert(LHS::count == 0);
+        assert(RHS::count == 2);
+
+        assertContains<RHS>(lhs, 2);
+        assertContains<RHS>(rhs, 2);
+    }
+    assert(LHS::count == 0);
+    assert(RHS::count == 0);
+}
+
+template <class LHS>
+void test_copy_assign_empty() {
+    assert(LHS::count == 0);
+    LHS::reset();
+    {
+        any lhs;
+        any const rhs(LHS(42));
+
+        assert(LHS::count == 1);
+        assert(LHS::copied == 0);
+
+        lhs = rhs;
+
+        assert(LHS::copied == 1);
+        assert(LHS::count == 2);
+
+        assertContains<LHS>(lhs, 42);
+        assertContains<LHS>(rhs, 42);
+    }
+    assert(LHS::count == 0);
+    LHS::reset();
+    {
+        any lhs(LHS(1));
+        any const rhs;
+
+        assert(LHS::count == 1);
+        assert(LHS::copied == 0);
+
+        lhs = rhs;
+
+        assert(LHS::copied == 0);
+        assert(LHS::count == 0);
+
+        assertEmpty<LHS>(lhs);
+        assertEmpty(rhs);
+    }
+    assert(LHS::count == 0);
+}
+
+void test_copy_assign_self() {
+    // empty
+    {
+        any a;
+        a = a;
+        assertEmpty(a);
+        assert(globalMemCounter.checkOutstandingNewEq(0));
+    }
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    // small
+    {
+        any a((small(1)));
+        assert(small::count == 1);
+
+        a = a;
+
+        assert(small::count == 1);
+        assertContains<small>(a, 1);
+        assert(globalMemCounter.checkOutstandingNewEq(0));
+    }
+    assert(small::count == 0);
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    // large
+    {
+        any a(large(1));
+        assert(large::count == 1);
+
+        a = a;
+
+        assert(large::count == 1);
+        assertContains<large>(a, 1);
+        assert(globalMemCounter.checkOutstandingNewEq(1));
+    }
+    assert(large::count == 0);
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+}
+
+template <class Tp>
+void test_copy_assign_throws()
+{
+#if !defined(TEST_HAS_NO_EXCEPTIONS)
+    auto try_throw =
+    [](any& lhs, any const& rhs) {
+        try {
+            lhs = rhs;
+            assert(false);
+        } catch (my_any_exception const &) {
+            // do nothing
+        } catch (...) {
+            assert(false);
+        }
+    };
+    // const lvalue to empty
+    {
+        any lhs;
+        any const rhs((Tp(1)));
+        assert(Tp::count == 1);
+
+        try_throw(lhs, rhs);
+
+        assert(Tp::count == 1);
+        assertEmpty<Tp>(lhs);
+        assertContains<Tp>(rhs);
+    }
+    {
+        any lhs((small(2)));
+        any const rhs((Tp(1)));
+        assert(small::count == 1);
+        assert(Tp::count == 1);
+
+        try_throw(lhs, rhs);
+
+        assert(small::count == 1);
+        assert(Tp::count == 1);
+        assertContains<small>(lhs, 2);
+        assertContains<Tp>(rhs);
+    }
+    {
+        any lhs((large(2)));
+        any const rhs((Tp(1)));
+        assert(large::count == 1);
+        assert(Tp::count == 1);
+
+        try_throw(lhs, rhs);
+
+        assert(large::count == 1);
+        assert(Tp::count == 1);
+        assertContains<large>(lhs, 2);
+        assertContains<Tp>(rhs);
+    }
+#endif
+}
+
+int main() {
+    test_copy_assign<small1, small2>();
+    test_copy_assign<large1, large2>();
+    test_copy_assign<small, large>();
+    test_copy_assign<large, small>();
+    test_copy_assign_empty<small>();
+    test_copy_assign_empty<large>();
+    test_copy_assign_self();
+    test_copy_assign_throws<small_throws_on_copy>();
+    test_copy_assign_throws<large_throws_on_copy>();
+}
diff --git a/test/std/experimental/any/any.class/any.assign/move.pass.cpp b/test/std/experimental/any/any.class/any.assign/move.pass.cpp
new file mode 100644
index 0000000..0a2d719
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.assign/move.pass.cpp
@@ -0,0 +1,102 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// any& operator=(any &&);
+
+// Test move assignment.
+
+#include <experimental/any>
+#include <cassert>
+
+#include "any_helpers.h"
+#include "test_macros.h"
+
+using std::experimental::any;
+using std::experimental::any_cast;
+
+template <class LHS, class RHS>
+void test_move_assign() {
+    assert(LHS::count == 0);
+    assert(RHS::count == 0);
+    {
+        LHS const s1(1);
+        any a(s1);
+        RHS const s2(2);
+        any a2(s2);
+
+        assert(LHS::count == 2);
+        assert(RHS::count == 2);
+
+        a = std::move(a2);
+
+        assert(LHS::count == 1);
+        assert(RHS::count == 2);
+
+        assertContains<RHS>(a, 2);
+        assertEmpty<RHS>(a2);
+    }
+    assert(LHS::count == 0);
+    assert(RHS::count == 0);
+}
+
+template <class LHS>
+void test_move_assign_empty() {
+    assert(LHS::count == 0);
+    {
+        any a;
+        any  a2((LHS(1)));
+
+        assert(LHS::count == 1);
+
+        a = std::move(a2);
+
+        assert(LHS::count == 1);
+
+        assertContains<LHS>(a, 1);
+        assertEmpty<LHS>(a2);
+    }
+    assert(LHS::count == 0);
+    {
+        any a((LHS(1)));
+        any a2;
+
+        assert(LHS::count == 1);
+
+        a = std::move(a2);
+
+        assert(LHS::count == 0);
+
+        assertEmpty<LHS>(a);
+        assertEmpty(a2);
+    }
+    assert(LHS::count == 0);
+}
+
+void test_move_assign_noexcept() {
+    any a1;
+    any a2;
+    static_assert(
+        noexcept(a1 = std::move(a2))
+      , "any & operator=(any &&) must be noexcept"
+      );
+}
+
+int main() {
+    test_move_assign_noexcept();
+    test_move_assign<small1, small2>();
+    test_move_assign<large1, large2>();
+    test_move_assign<small, large>();
+    test_move_assign<large, small>();
+    test_move_assign_empty<small>();
+    test_move_assign_empty<large>();
+}
diff --git a/test/std/experimental/any/any.class/any.assign/value.pass.cpp b/test/std/experimental/any/any.class/any.assign/value.pass.cpp
new file mode 100644
index 0000000..8262990
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.assign/value.pass.cpp
@@ -0,0 +1,177 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// any& operator=(any const &);
+
+// Test value copy and move assignment.
+
+#include <experimental/any>
+#include <cassert>
+
+#include "any_helpers.h"
+#include "count_new.hpp"
+#include "test_macros.h"
+
+using std::experimental::any;
+using std::experimental::any_cast;
+
+template <class LHS, class RHS>
+void test_assign_value() {
+    assert(LHS::count == 0);
+    assert(RHS::count == 0);
+    LHS::reset();
+    RHS::reset();
+    {
+        any lhs(LHS(1));
+        any const rhs(RHS(2));
+
+        assert(LHS::count == 1);
+        assert(RHS::count == 1);
+        assert(RHS::copied == 0);
+
+        lhs = rhs;
+
+        assert(RHS::copied == 1);
+        assert(LHS::count == 0);
+        assert(RHS::count == 2);
+
+        assertContains<RHS>(lhs, 2);
+        assertContains<RHS>(rhs, 2);
+    }
+    assert(LHS::count == 0);
+    assert(RHS::count == 0);
+    LHS::reset();
+    RHS::reset();
+    {
+        any lhs(LHS(1));
+        any rhs(RHS(2));
+
+        assert(LHS::count == 1);
+        assert(RHS::count == 1);
+        assert(RHS::moved == 1);
+
+        lhs = std::move(rhs);
+
+        assert(RHS::moved >= 1);
+        assert(RHS::copied == 0);
+        assert(LHS::count == 0);
+        assert(RHS::count == 1);
+
+        assertContains<RHS>(lhs, 2);
+        assertEmpty<RHS>(rhs);
+    }
+    assert(LHS::count == 0);
+    assert(RHS::count == 0);
+}
+
+template <class RHS>
+void test_assign_value_empty() {
+    assert(RHS::count == 0);
+    RHS::reset();
+    {
+        any lhs;
+        RHS rhs(42);
+        assert(RHS::count == 1);
+        assert(RHS::copied == 0);
+
+        lhs = rhs;
+
+        assert(RHS::count == 2);
+        assert(RHS::copied == 1);
+        assert(RHS::moved >= 0);
+        assertContains<RHS>(lhs, 42);
+    }
+    assert(RHS::count == 0);
+    RHS::reset();
+    {
+        any lhs;
+        RHS rhs(42);
+        assert(RHS::count == 1);
+        assert(RHS::moved == 0);
+
+        lhs = std::move(rhs);
+
+        assert(RHS::count == 2);
+        assert(RHS::copied == 0);
+        assert(RHS::moved >= 1);
+        assertContains<RHS>(lhs, 42);
+    }
+    assert(RHS::count == 0);
+    RHS::reset();
+}
+
+
+template <class Tp, bool Move = false>
+void test_assign_throws() {
+#if !defined(TEST_HAS_NO_EXCEPTIONS)
+    auto try_throw=
+    [](any& lhs, auto&& rhs) {
+        try {
+            Move ? lhs = std::move(rhs)
+                 : lhs = rhs;
+            assert(false);
+        } catch (my_any_exception const &) {
+            // do nothing
+        } catch (...) {
+            assert(false);
+        }
+    };
+    // const lvalue to empty
+    {
+        any lhs;
+        Tp rhs(1);
+        assert(Tp::count == 1);
+
+        try_throw(lhs, rhs);
+
+        assert(Tp::count == 1);
+        assertEmpty<Tp>(lhs);
+    }
+    {
+        any lhs((small(2)));
+        Tp  rhs(1);
+        assert(small::count == 1);
+        assert(Tp::count == 1);
+
+        try_throw(lhs, rhs);
+
+        assert(small::count == 1);
+        assert(Tp::count == 1);
+        assertContains<small>(lhs, 2);
+    }
+    {
+        any lhs((large(2)));
+        Tp rhs(1);
+        assert(large::count == 1);
+        assert(Tp::count == 1);
+
+        try_throw(lhs, rhs);
+
+        assert(large::count == 1);
+        assert(Tp::count == 1);
+        assertContains<large>(lhs, 2);
+    }
+#endif
+}
+
+int main() {
+    test_assign_value<small1, small2>();
+    test_assign_value<large1, large2>();
+    test_assign_value<small, large>();
+    test_assign_value<large, small>();
+    test_assign_value_empty<small>();
+    test_assign_value_empty<large>();
+    test_assign_throws<small_throws_on_copy>();
+    test_assign_throws<large_throws_on_copy>();
+    test_assign_throws<throws_on_move, /* Move = */ true>();
+}
\ No newline at end of file
diff --git a/test/std/experimental/any/any.class/any.assign/value_non_copyable_assign.fail.cpp b/test/std/experimental/any/any.class/any.assign/value_non_copyable_assign.fail.cpp
new file mode 100644
index 0000000..ce0d44f
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.assign/value_non_copyable_assign.fail.cpp
@@ -0,0 +1,38 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// template <class Value>
+// any& operator=(Value &&);
+
+// Instantiate the value assignment operator with a non-copyable type.
+
+#include <experimental/any>
+
+class non_copyable
+{
+    non_copyable(non_copyable const &);
+
+public:
+    non_copyable() {}
+    non_copyable(non_copyable &&) {}
+};
+
+int main()
+{
+    using namespace std::experimental;
+    non_copyable nc;
+    any a;
+    a = static_cast<non_copyable &&>(nc); // expected-error@experimental/any:* 2 {{static_assert failed "_ValueType must be CopyConstructible."}}
+        // expected-error@experimental/any:* {{calling a private constructor of class 'non_copyable'}}
+
+}
diff --git a/test/std/experimental/any/any.class/any.cons/copy.pass.cpp b/test/std/experimental/any/any.class/any.cons/copy.pass.cpp
new file mode 100644
index 0000000..3d0b34b
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.cons/copy.pass.cpp
@@ -0,0 +1,100 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// any(any const &);
+
+#include <experimental/any>
+#include <cassert>
+
+#include "any_helpers.h"
+#include "count_new.hpp"
+#include "test_macros.h"
+
+using std::experimental::any;
+using std::experimental::any_cast;
+
+template <class Type>
+void test_copy_throws() {
+#if !defined(TEST_HAS_NO_EXCEPTIONS)
+    assert(Type::count == 0);
+    {
+        any const a((Type(42)));
+        assert(Type::count == 1);
+        try {
+            any const a2(a);
+            assert(false);
+        } catch (my_any_exception const &) {
+            // do nothing
+        } catch (...) {
+            assert(false);
+        }
+        assert(Type::count == 1);
+        assertContains<Type>(a, 42);
+    }
+    assert(Type::count == 0);
+#endif
+}
+
+void test_copy_empty() {
+    DisableAllocationGuard g; ((void)g); // No allocations should occur.
+    any a1;
+    any a2(a1);
+
+    assertEmpty(a1);
+    assertEmpty(a2);
+}
+
+template <class Type>
+void test_copy()
+{
+    // Copying small types should not perform any allocations.
+    DisableAllocationGuard g(isSmallType<Type>()); ((void)g);
+    assert(Type::count == 0);
+    Type::reset();
+    {
+        any a((Type(42)));
+        assert(Type::count == 1);
+        assert(Type::copied == 0);
+
+        any a2(a);
+
+        assert(Type::copied == 1);
+        assert(Type::count == 2);
+        assertContains<Type>(a, 42);
+        assertContains<Type>(a, 42);
+
+        // Modify a and check that a2 is unchanged
+        modifyValue<Type>(a, -1);
+        assertContains<Type>(a, -1);
+        assertContains<Type>(a2, 42);
+
+        // modify a2 and check that a is unchanged
+        modifyValue<Type>(a2, 999);
+        assertContains<Type>(a, -1);
+        assertContains<Type>(a2, 999);
+
+        // clear a and check that a2 is unchanged
+        a.clear();
+        assertEmpty(a);
+        assertContains<Type>(a2, 999);
+    }
+    assert(Type::count == 0);
+}
+
+int main() {
+    test_copy<small>();
+    test_copy<large>();
+    test_copy_empty();
+    test_copy_throws<small_throws_on_copy>();
+    test_copy_throws<large_throws_on_copy>();
+}
diff --git a/test/std/experimental/any/any.class/any.cons/default.pass.cpp b/test/std/experimental/any/any.class/any.cons/default.pass.cpp
new file mode 100644
index 0000000..b52c83f
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.cons/default.pass.cpp
@@ -0,0 +1,38 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// any() noexcept;
+
+#include <experimental/any>
+#include <type_traits>
+#include <cassert>
+
+#include "any_helpers.h"
+#include "count_new.hpp"
+
+
+int main()
+{
+    using std::experimental::any;
+    {
+        static_assert(
+            std::is_nothrow_default_constructible<any>::value
+          , "Must be default constructible"
+          );
+    }
+    {
+        DisableAllocationGuard g; ((void)g);
+        any const a;
+        assertEmpty(a);
+    }
+}
diff --git a/test/std/experimental/any/any.class/any.cons/move.pass.cpp b/test/std/experimental/any/any.class/any.cons/move.pass.cpp
new file mode 100644
index 0000000..40534cb
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.cons/move.pass.cpp
@@ -0,0 +1,102 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// any(any &&) noexcept;
+
+#include <experimental/any>
+#include <utility>
+#include <type_traits>
+#include <cassert>
+
+#include "any_helpers.h"
+#include "count_new.hpp"
+#include "test_macros.h"
+
+using std::experimental::any;
+using std::experimental::any_cast;
+
+// Moves are always noexcept. The throws_on_move object
+// must be stored dynamically so the pointer is moved and
+// not the stored object.
+void test_move_does_not_throw()
+{
+#if !defined(TEST_HAS_NO_EXCEPTIONS)
+    assert(throws_on_move::count == 0);
+    {
+        throws_on_move v(42);
+        any a(v);
+        assert(throws_on_move::count == 2);
+        // No allocations should be performed after this point.
+        DisableAllocationGuard g; ((void)g);
+        try {
+            any const a2(std::move(a));
+            assertEmpty(a);
+            assertContains<throws_on_move>(a2, 42);
+        } catch (...) {
+            assert(false);
+        }
+        assert(throws_on_move::count == 1);
+        assertEmpty(a);
+    }
+    assert(throws_on_move::count == 0);
+#endif
+}
+
+void test_move_empty() {
+    DisableAllocationGuard g; ((void)g); // no allocations should be performed.
+
+    any a1;
+    any a2(std::move(a1));
+
+    assertEmpty(a1);
+    assertEmpty(a2);
+}
+
+template <class Type>
+void test_move() {
+    assert(Type::count == 0);
+    Type::reset();
+    {
+        any a((Type(42)));
+        assert(Type::count == 1);
+        assert(Type::copied == 0);
+        assert(Type::moved == 1);
+
+        // Moving should not perform allocations since it must be noexcept.
+        DisableAllocationGuard g; ((void)g);
+
+        any a2(std::move(a));
+
+        assert(Type::moved >= 1); // zero or more move operations can be performed.
+        assert(Type::copied == 0); // no copies can be performed.
+        assert(Type::count == 1);
+        assertEmpty(a); // Moves are always destructive.
+        assertContains<Type>(a2, 42);
+    }
+    assert(Type::count == 0);
+}
+
+int main()
+{
+    // noexcept test
+    {
+        static_assert(
+            std::is_nothrow_move_constructible<any>::value
+          , "any must be nothrow move constructible"
+          );
+    }
+    test_move<small>();
+    test_move<large>();
+    test_move_empty();
+    test_move_does_not_throw();
+}
diff --git a/test/std/experimental/any/any.class/any.cons/non_copyable_value.fail.cpp b/test/std/experimental/any/any.class/any.cons/non_copyable_value.fail.cpp
new file mode 100644
index 0000000..643b962
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.cons/non_copyable_value.fail.cpp
@@ -0,0 +1,36 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// any::any<Value>(Value &&)
+
+// Attempt to construct any with a non-copyable type.
+
+#include <experimental/any>
+
+class non_copyable
+{
+    non_copyable(non_copyable const &);
+
+public:
+    non_copyable() {}
+    non_copyable(non_copyable &&) {}
+};
+
+int main()
+{
+    using namespace std::experimental;
+    non_copyable nc;
+    any a(static_cast<non_copyable &&>(nc));
+    // expected-error@experimental/any:* 1 {{static_assert failed "_ValueType must be CopyConstructible."}}
+    // expected-error@experimental/any:* 1 {{calling a private constructor of class 'non_copyable'}}
+}
diff --git a/test/std/experimental/any/any.class/any.cons/value.pass.cpp b/test/std/experimental/any/any.class/any.cons/value.pass.cpp
new file mode 100644
index 0000000..7bb134e
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.cons/value.pass.cpp
@@ -0,0 +1,116 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// template <class Value> any(Value &&)
+
+// Test construction from a value.
+// Concerns:
+// ---------
+// 1. The value is properly move/copied depending on the value category.
+// 2. Both small and large values are properly handled.
+
+
+#include <experimental/any>
+#include <cassert>
+
+#include "any_helpers.h"
+#include "count_new.hpp"
+#include "test_macros.h"
+
+using std::experimental::any;
+using std::experimental::any_cast;
+
+template <class Type>
+void test_copy_value_throws()
+{
+#if !defined(TEST_HAS_NO_EXCEPTIONS)
+    assert(Type::count == 0);
+    {
+        Type const t(42);
+        assert(Type::count == 1);
+        try {
+            any const a2(t);
+            assert(false);
+        } catch (my_any_exception const &) {
+            // do nothing
+        } catch (...) {
+            assert(false);
+        }
+        assert(Type::count == 1);
+        assert(t.value == 42);
+    }
+    assert(Type::count == 0);
+#endif
+}
+
+void test_move_value_throws()
+{
+#if !defined(TEST_HAS_NO_EXCEPTIONS)
+    assert(throws_on_move::count == 0);
+    {
+        throws_on_move v;
+        assert(throws_on_move::count == 1);
+        try {
+            any const a(std::move(v));
+            assert(false);
+        } catch (my_any_exception const &) {
+            // do nothing
+        } catch (...) {
+            assert(false);
+        }
+        assert(throws_on_move::count == 1);
+    }
+    assert(throws_on_move::count == 0);
+#endif
+}
+
+template <class Type>
+void test_copy_move_value() {
+    // constructing from a small type should perform no allocations.
+    DisableAllocationGuard g(isSmallType<Type>()); ((void)g);
+    assert(Type::count == 0);
+    Type::reset();
+    {
+        Type t(42);
+        assert(Type::count == 1);
+
+        any a(t);
+
+        assert(Type::count == 2);
+        assert(Type::copied == 1);
+        assert(Type::moved == 0);
+        assertContains<Type>(a, 42);
+    }
+    assert(Type::count == 0);
+    Type::reset();
+    {
+        Type t(42);
+        assert(Type::count == 1);
+
+        any a(std::move(t));
+
+        assert(Type::count == 2);
+        assert(Type::copied == 0);
+        assert(Type::moved == 1);
+        assertContains<Type>(a, 42);
+    }
+}
+
+
+int main() {
+    test_copy_move_value<small>();
+    test_copy_move_value<large>();
+    test_copy_value_throws<small_throws_on_copy>();
+    test_copy_value_throws<large_throws_on_copy>();
+    test_move_value_throws();
+}
\ No newline at end of file
diff --git a/test/std/experimental/any/any.class/any.modifiers/clear.pass.cpp b/test/std/experimental/any/any.class/any.modifiers/clear.pass.cpp
new file mode 100644
index 0000000..603490c
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.modifiers/clear.pass.cpp
@@ -0,0 +1,63 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// any::clear() noexcept
+
+#include <experimental/any>
+#include <cassert>
+
+#include "any_helpers.h"
+
+int main()
+{
+    using std::experimental::any;
+    using std::experimental::any_cast;
+    // empty
+    {
+        any a;
+
+        // noexcept check
+        static_assert(
+            noexcept(a.clear())
+          , "any.clear() must be noexcept"
+          );
+
+        assertEmpty(a);
+
+        a.clear();
+
+        assertEmpty(a);
+    }
+    // small object
+    {
+        any a((small(1)));
+        assert(small::count == 1);
+        assertContains<small>(a, 1);
+
+        a.clear();
+
+        assertEmpty<small>(a);
+        assert(small::count == 0);
+    }
+    // large object
+    {
+        any a(large(1));
+        assert(large::count == 1);
+        assertContains<large>(a);
+
+        a.clear();
+
+        assertEmpty<large>(a);
+        assert(large::count == 0);
+    }
+}
diff --git a/test/std/experimental/any/any.class/any.modifiers/swap.pass.cpp b/test/std/experimental/any/any.class/any.modifiers/swap.pass.cpp
new file mode 100644
index 0000000..0649351
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.modifiers/swap.pass.cpp
@@ -0,0 +1,101 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// any::swap(any &) noexcept
+
+// Test swap(large, small) and swap(small, large)
+
+#include <experimental/any>
+#include <cassert>
+
+#include "any_helpers.h"
+
+using std::experimental::any;
+using std::experimental::any_cast;
+
+template <class LHS, class RHS>
+void test_swap() {
+    assert(LHS::count == 0);
+    assert(RHS::count == 0);
+    {
+        any a1((LHS(1)));
+        any a2(RHS{2});
+        assert(LHS::count == 1);
+        assert(RHS::count == 1);
+
+        a1.swap(a2);
+
+        assert(LHS::count == 1);
+        assert(RHS::count == 1);
+
+        assertContains<RHS>(a1, 2);
+        assertContains<LHS>(a2, 1);
+    }
+    assert(LHS::count == 0);
+    assert(RHS::count == 0);
+    assert(LHS::copied == 0);
+    assert(RHS::copied == 0);
+}
+
+template <class Tp>
+void test_swap_empty() {
+    assert(Tp::count == 0);
+    {
+        any a1((Tp(1)));
+        any a2;
+        assert(Tp::count == 1);
+
+        a1.swap(a2);
+
+        assert(Tp::count == 1);
+
+        assertContains<Tp>(a2, 1);
+        assertEmpty(a1);
+    }
+    assert(Tp::count == 0);
+    {
+        any a1((Tp(1)));
+        any a2;
+        assert(Tp::count == 1);
+
+        a2.swap(a1);
+
+        assert(Tp::count == 1);
+
+        assertContains<Tp>(a2, 1);
+        assertEmpty(a1);
+    }
+    assert(Tp::count == 0);
+    assert(Tp::copied == 0);
+}
+
+void test_noexcept()
+{
+    any a1;
+    any a2;
+    static_assert(
+        noexcept(a1.swap(a2))
+      , "any::swap(any&) must be noexcept"
+      );
+}
+
+int main()
+{
+    test_noexcept();
+    test_swap_empty<small>();
+    test_swap_empty<large>();
+    test_swap<small1, small2>();
+    test_swap<large1, large2>();
+    test_swap<small, large>();
+    test_swap<large, small>();
+}
diff --git a/test/std/experimental/any/any.class/any.observers/empty.pass.cpp b/test/std/experimental/any/any.class/any.observers/empty.pass.cpp
new file mode 100644
index 0000000..8c681f3
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.observers/empty.pass.cpp
@@ -0,0 +1,64 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// any::empty() noexcept
+
+#include <experimental/any>
+#include <cassert>
+
+#include "any_helpers.h"
+
+int main()
+{
+    using std::experimental::any;
+    // noexcept test
+    {
+        any a;
+        static_assert(noexcept(a.empty()), "any::empty() must be noexcept");
+    }
+    // empty
+    {
+        any a;
+        assert(a.empty());
+
+        a.clear();
+        assert(a.empty());
+
+        a = 42;
+        assert(!a.empty());
+    }
+    // small object
+    {
+        small const s(1);
+        any a(s);
+        assert(!a.empty());
+
+        a.clear();
+        assert(a.empty());
+
+        a = s;
+        assert(!a.empty());
+    }
+    // large object
+    {
+        large const l(1);
+        any a(l);
+        assert(!a.empty());
+
+        a.clear();
+        assert(a.empty());
+
+        a = l;
+        assert(!a.empty());
+    }
+}
diff --git a/test/std/experimental/any/any.class/any.observers/type.pass.cpp b/test/std/experimental/any/any.class/any.observers/type.pass.cpp
new file mode 100644
index 0000000..682b73b
--- /dev/null
+++ b/test/std/experimental/any/any.class/any.observers/type.pass.cpp
@@ -0,0 +1,41 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// XFAIL: libcpp-no-rtti
+
+// <experimental/any>
+
+// any::type() noexcept
+
+#include <experimental/any>
+#include <cassert>
+#include "any_helpers.h"
+
+int main()
+{
+    using std::experimental::any;
+    {
+        any const a;
+        assert(a.type() == typeid(void));
+        static_assert(noexcept(a.type()), "any::type() must be noexcept");
+    }
+    {
+        small const s(1);
+        any const a(s);
+        assert(a.type() == typeid(small));
+
+    }
+    {
+        large const l(1);
+        any const a(l);
+        assert(a.type() == typeid(large));
+    }
+}
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/experimental/any/any.class/nothing_to_do.pass.cpp
similarity index 86%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/std/experimental/any/any.class/nothing_to_do.pass.cpp
index b58f5c5..c21f8a7 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/experimental/any/any.class/nothing_to_do.pass.cpp
@@ -7,6 +7,6 @@
 //
 //===----------------------------------------------------------------------===//
 
-int main()
-{
-}
+#include <experimental/string_view>
+
+int main () {}
diff --git a/test/std/experimental/any/any.nonmembers/any.cast/any_cast_pointer.pass.cpp b/test/std/experimental/any/any.nonmembers/any.cast/any_cast_pointer.pass.cpp
new file mode 100644
index 0000000..9d9a5cd
--- /dev/null
+++ b/test/std/experimental/any/any.nonmembers/any.cast/any_cast_pointer.pass.cpp
@@ -0,0 +1,146 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// template <class ValueType>
+// ValueType const* any_cast(any const *) noexcept;
+//
+// template <class ValueType>
+// ValueType * any_cast(any *) noexcept;
+
+#include <experimental/any>
+#include <type_traits>
+#include <cassert>
+
+#include "any_helpers.h"
+
+using std::experimental::any;
+using std::experimental::any_cast;
+
+// Test that the operators are properly noexcept.
+void test_cast_is_noexcept() {
+    any a;
+    static_assert(noexcept(any_cast<int>(&a)), "");
+
+    any const& ca = a;
+    static_assert(noexcept(any_cast<int>(&ca)), "");
+}
+
+// Test that the return type of any_cast is correct.
+void test_cast_return_type() {
+    any a;
+    static_assert(std::is_same<decltype(any_cast<int>(&a)), int*>::value, "");
+    static_assert(std::is_same<decltype(any_cast<int const>(&a)), int const*>::value, "");
+
+    any const& ca = a;
+    static_assert(std::is_same<decltype(any_cast<int>(&ca)), int const*>::value, "");
+    static_assert(std::is_same<decltype(any_cast<int const>(&ca)), int const*>::value, "");
+}
+
+// Test that any_cast handles null pointers.
+void test_cast_nullptr() {
+    any* a = nullptr;
+    assert(nullptr == any_cast<int>(a));
+    assert(nullptr == any_cast<int const>(a));
+
+    any const* ca = nullptr;
+    assert(nullptr == any_cast<int>(ca));
+    assert(nullptr == any_cast<int const>(ca));
+}
+
+// Test casting an empty object.
+void test_cast_empty() {
+    {
+        any a;
+        assert(nullptr == any_cast<int>(&a));
+        assert(nullptr == any_cast<int const>(&a));
+
+        any const& ca = a;
+        assert(nullptr == any_cast<int>(&ca));
+        assert(nullptr == any_cast<int const>(&ca));
+    }
+    // Create as non-empty, then make empty and run test.
+    {
+        any a(42);
+        a.clear();
+        assert(nullptr == any_cast<int>(&a));
+        assert(nullptr == any_cast<int const>(&a));
+
+        any const& ca = a;
+        assert(nullptr == any_cast<int>(&ca));
+        assert(nullptr == any_cast<int const>(&ca));
+    }
+}
+
+template <class Type>
+void test_cast() {
+    assert(Type::count == 0);
+    Type::reset();
+    {
+        any a((Type(42)));
+        any const& ca = a;
+        assert(Type::count == 1);
+        assert(Type::copied == 0);
+        assert(Type::moved == 1);
+
+        // Try a cast to a bad type.
+        // NOTE: Type cannot be an int.
+        assert(any_cast<int>(&a) == nullptr);
+        assert(any_cast<int const>(&a) == nullptr);
+        assert(any_cast<int const volatile>(&a) == nullptr);
+
+        // Try a cast to the right type, but as a pointer.
+        assert(any_cast<Type*>(&a) == nullptr);
+        assert(any_cast<Type const*>(&a) == nullptr);
+
+        // Check getting a unqualified type from a non-const any.
+        Type* v = any_cast<Type>(&a);
+        assert(v != nullptr);
+        assert(v->value == 42);
+
+        // change the stored value and later check for the new value.
+        v->value = 999;
+
+        // Check getting a const qualified type from a non-const any.
+        Type const* cv = any_cast<Type const>(&a);
+        assert(cv != nullptr);
+        assert(cv == v);
+        assert(cv->value == 999);
+
+        // Check getting a unqualified type from a const any.
+        cv = any_cast<Type>(&ca);
+        assert(cv != nullptr);
+        assert(cv == v);
+        assert(cv->value == 999);
+
+        // Check getting a const-qualified type from a const any.
+        cv = any_cast<Type const>(&ca);
+        assert(cv != nullptr);
+        assert(cv == v);
+        assert(cv->value == 999);
+
+        // Check that no more objects were created, copied or moved.
+        assert(Type::count == 1);
+        assert(Type::copied == 0);
+        assert(Type::moved == 1);
+    }
+    assert(Type::count == 0);
+}
+
+int main() {
+    test_cast_is_noexcept();
+    test_cast_return_type();
+    test_cast_nullptr();
+    test_cast_empty();
+    test_cast<small>();
+    test_cast<large>();
+}
diff --git a/test/std/experimental/any/any.nonmembers/any.cast/any_cast_reference.pass.cpp b/test/std/experimental/any/any.nonmembers/any.cast/any_cast_reference.pass.cpp
new file mode 100644
index 0000000..e975609
--- /dev/null
+++ b/test/std/experimental/any/any.nonmembers/any.cast/any_cast_reference.pass.cpp
@@ -0,0 +1,309 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// template <class ValueType>
+// ValueType const any_cast(any const&);
+//
+// template <class ValueType>
+// ValueType any_cast(any &);
+//
+// template <class ValueType>
+// ValueType any_cast(any &&);
+
+#include <experimental/any>
+#include <type_traits>
+#include <cassert>
+
+#include "any_helpers.h"
+#include "count_new.hpp"
+#include "test_macros.h"
+
+using std::experimental::any;
+using std::experimental::any_cast;
+using std::experimental::bad_any_cast;
+
+
+// Test that the operators are NOT marked noexcept.
+void test_cast_is_not_noexcept() {
+    any a;
+    static_assert(!noexcept(any_cast<int>(static_cast<any&>(a))), "");
+    static_assert(!noexcept(any_cast<int>(static_cast<any const&>(a))), "");
+    static_assert(!noexcept(any_cast<int>(static_cast<any &&>(a))), "");
+}
+
+// Test that the return type of any_cast is correct.
+void test_cast_return_type() {
+    any a;
+    static_assert(std::is_same<decltype(any_cast<int>(a)), int>::value, "");
+    static_assert(std::is_same<decltype(any_cast<int const>(a)), int>::value, "");
+    static_assert(std::is_same<decltype(any_cast<int&>(a)), int&>::value, "");
+    static_assert(std::is_same<decltype(any_cast<int const&>(a)), int const&>::value, "");
+
+    //static_assert(std::is_same<decltype(any_cast<int&&>(a)), int&&>::value, "");
+    //static_assert(std::is_same<decltype(any_cast<int const&&>(a)), int const&&>::value, "");
+
+    static_assert(std::is_same<decltype(any_cast<int>(std::move(a))), int>::value, "");
+    static_assert(std::is_same<decltype(any_cast<int const>(std::move(a))), int>::value, "");
+    static_assert(std::is_same<decltype(any_cast<int&>(std::move(a))), int&>::value, "");
+    static_assert(std::is_same<decltype(any_cast<int const&>(std::move(a))), int const&>::value, "");
+
+    //static_assert(std::is_same<decltype(any_cast<int&&>(std::move(a))), int&&>::value, "");
+    //static_assert(std::is_same<decltype(any_cast<int const&&>(std::move(a))), int const&&>::value, "");
+
+    any const& ca = a;
+    static_assert(std::is_same<decltype(any_cast<int>(ca)), int>::value, "");
+    static_assert(std::is_same<decltype(any_cast<int const>(ca)), int>::value, "");
+    static_assert(std::is_same<decltype(any_cast<int const&>(ca)), int const&>::value, "");
+
+    //static_assert(std::is_same<decltype(any_cast<int const&&>(ca)), int const&&>::value, "");
+}
+
+template <class Type, class ConstT = Type>
+void checkThrows(any& a)
+{
+#if !defined(TEST_HAS_NO_EXCEPTIONS)
+    try {
+        any_cast<Type>(a);
+        assert(false);
+    } catch (bad_any_cast const &) {
+            // do nothing
+    } catch (...) {
+        assert(false);
+    }
+
+    try {
+        any_cast<ConstT>(static_cast<any const&>(a));
+        assert(false);
+    } catch (bad_any_cast const &) {
+            // do nothing
+    } catch (...) {
+        assert(false);
+    }
+
+    try {
+        any_cast<Type>(static_cast<any&&>(a));
+        assert(false);
+    } catch (bad_any_cast const &) {
+            // do nothing
+    } catch (...) {
+        assert(false);
+    }
+#endif
+}
+
+void test_cast_empty() {
+    // None of these operations should allocate.
+    DisableAllocationGuard g; ((void)g);
+    any a;
+    checkThrows<int>(a);
+}
+
+template <class Type>
+void test_cast_to_reference() {
+    assert(Type::count == 0);
+    Type::reset();
+    {
+        any a((Type(42)));
+        any const& ca = a;
+        assert(Type::count == 1);
+        assert(Type::copied == 0);
+        assert(Type::moved == 1);
+
+        // Try a cast to a bad type.
+        // NOTE: Type cannot be an int.
+        checkThrows<int>(a);
+        checkThrows<int&, int const&>(a);
+        checkThrows<Type*, Type const*>(a);
+        checkThrows<Type const*>(a);
+
+        // Check getting a type by reference from a non-const lvalue any.
+        {
+            Type& v = any_cast<Type&>(a);
+            assert(v.value == 42);
+
+            Type const &cv = any_cast<Type const&>(a);
+            assert(&cv == &v);
+        }
+        // Check getting a type by reference from a const lvalue any.
+        {
+            Type const& v = any_cast<Type const&>(ca);
+            assert(v.value == 42);
+
+            Type const &cv = any_cast<Type const&>(ca);
+            assert(&cv == &v);
+        }
+        // Check getting a type by reference from a non-const rvalue
+        {
+            Type& v = any_cast<Type&>(std::move(a));
+            assert(v.value == 42);
+
+            Type const &cv = any_cast<Type const&>(std::move(a));
+            assert(&cv == &v);
+        }
+        // Check getting a type by reference from a const rvalue any.
+        {
+            Type const& v = any_cast<Type const&>(std::move(ca));
+            assert(v.value == 42);
+
+            Type const &cv = any_cast<Type const&>(std::move(ca));
+            assert(&cv == &v);
+        }
+
+        // Check that the original object hasn't been changed.
+        assertContains<Type>(a, 42);
+
+        // Check that no objects have been created/copied/moved.
+        assert(Type::count == 1);
+        assert(Type::copied == 0);
+        assert(Type::moved == 1);
+    }
+    assert(Type::count == 0);
+}
+
+template <class Type>
+void test_cast_to_value() {
+    assert(Type::count == 0);
+    Type::reset();
+    {
+        any a((Type(42)));
+        any const& ca = a;
+        assert(Type::count == 1);
+        assert(Type::copied == 0);
+        assert(Type::moved == 1);
+
+        // Try a cast to a bad type.
+        // NOTE: Type cannot be an int.
+        checkThrows<int>(a);
+        checkThrows<int&, int const&>(a);
+        checkThrows<Type*, Type const*>(a);
+        checkThrows<Type const*>(a);
+
+        Type::reset(); // NOTE: reset does not modify Type::count
+        // Check getting Type by value from a non-const lvalue any.
+        // This should cause the non-const copy constructor to be called.
+        {
+            Type t = any_cast<Type>(a);
+
+            assert(Type::count == 2);
+            assert(Type::copied == 1);
+            assert(Type::const_copied == 0);
+            assert(Type::non_const_copied == 1);
+            assert(Type::moved == 0);
+            assert(t.value == 42);
+        }
+        assert(Type::count == 1);
+        Type::reset();
+        // Check getting const Type by value from a non-const lvalue any.
+        // This should cause the const copy constructor to be called.
+        {
+            Type t = any_cast<Type const>(a);
+
+            assert(Type::count == 2);
+            assert(Type::copied == 1);
+            assert(Type::const_copied == 1);
+            assert(Type::non_const_copied == 0);
+            assert(Type::moved == 0);
+            assert(t.value == 42);
+        }
+        assert(Type::count == 1);
+        Type::reset();
+        // Check getting Type by value from a non-const lvalue any.
+        // This should cause the const copy constructor to be called.
+        {
+            Type t = any_cast<Type>(static_cast<any const&>(a));
+
+            assert(Type::count == 2);
+            assert(Type::copied == 1);
+            assert(Type::const_copied == 1);
+            assert(Type::non_const_copied == 0);
+            assert(Type::moved == 0);
+            assert(t.value == 42);
+        }
+        assert(Type::count == 1);
+        Type::reset();
+        // Check getting Type by value from a non-const rvalue any.
+        // This should cause the non-const copy constructor to be called.
+        {
+            Type t = any_cast<Type>(static_cast<any &&>(a));
+
+            assert(Type::count == 2);
+            assert(Type::copied == 1);
+            assert(Type::const_copied == 0);
+            assert(Type::non_const_copied == 1);
+            assert(Type::moved == 0);
+            assert(t.value == 42);
+        }
+        assert(Type::count == 1);
+        Type::reset();
+        // Check getting const Type by value from a non-const rvalue any.
+        // This should cause the const copy constructor to be called.
+        {
+            Type t = any_cast<Type const>(static_cast<any &&>(a));
+
+            assert(Type::count == 2);
+            assert(Type::copied == 1);
+            assert(Type::const_copied == 1);
+            assert(Type::non_const_copied == 0);
+            assert(Type::moved == 0);
+            assert(t.value == 42);
+        }
+        assert(Type::count == 1);
+        Type::reset();
+        // Check getting Type by value from a const rvalue any.
+        // This should cause the const copy constructor to be called.
+        {
+            Type t = any_cast<Type>(static_cast<any const&&>(a));
+
+            assert(Type::count == 2);
+            assert(Type::copied == 1);
+            assert(Type::const_copied == 1);
+            assert(Type::non_const_copied == 0);
+            assert(Type::moved == 0);
+            assert(t.value == 42);
+        }
+        // Ensure we still only have 1 Type object alive.
+        assert(Type::count == 1);
+
+        // Check that the original object hasn't been changed.
+        assertContains<Type>(a, 42);
+    }
+    assert(Type::count == 0);
+}
+
+// Even though you can't get a non-copyable class into std::any
+// the standard requires that these overloads compile and function.
+void test_non_copyable_ref() {
+    struct no_copy
+    {
+        no_copy() {}
+        no_copy(no_copy &&) {}
+    private:
+        no_copy(no_copy const &);
+    };
+
+    any a;
+    checkThrows<no_copy &, no_copy const&>(a);
+    checkThrows<no_copy const&>(a);
+    assertEmpty(a);
+}
+
+int main() {
+    test_cast_is_not_noexcept();
+    test_cast_return_type();
+    test_cast_empty();
+    test_cast_to_reference<small>();
+    test_cast_to_reference<large>();
+    test_cast_to_value<small>();
+    test_cast_to_value<large>();
+    test_non_copyable_ref();
+}
diff --git a/test/std/experimental/any/any.nonmembers/any.cast/const_correctness.fail.cpp b/test/std/experimental/any/any.nonmembers/any.cast/const_correctness.fail.cpp
new file mode 100644
index 0000000..db51492
--- /dev/null
+++ b/test/std/experimental/any/any.nonmembers/any.cast/const_correctness.fail.cpp
@@ -0,0 +1,38 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// template <class ValueType>
+// ValueType any_cast(any const &);
+
+// Try and cast away const.
+
+#include <experimental/any>
+
+struct TestType {};
+struct TestType2 {};
+
+int main()
+{
+    using std::experimental::any;
+    using std::experimental::any_cast;
+
+    any a;
+
+    // expected-error@experimental/any:* 2 {{binding value of type '_Tp' (aka 'const TestType') to reference to type 'TestType' drops 'const' qualifier}}
+    any_cast<TestType &>(static_cast<any const&>(a)); // expected-note {{requested here}}
+    any_cast<TestType &&>(static_cast<any const&>(a)); // expected-note {{requested here}}
+
+    // expected-error@experimental/any:* 2 {{binding value of type '_Tp' (aka 'const TestType2') to reference to type 'TestType2' drops 'const' qualifier}}
+    any_cast<TestType2 &>(static_cast<any const&&>(a)); // expected-note {{requested here}}
+    any_cast<TestType2 &&>(static_cast<any const&&>(a)); // expected-note {{requested here}}
+}
diff --git a/test/std/experimental/any/any.nonmembers/any.cast/not_copy_constructible.fail.cpp b/test/std/experimental/any/any.nonmembers/any.cast/not_copy_constructible.fail.cpp
new file mode 100644
index 0000000..c6cc68d
--- /dev/null
+++ b/test/std/experimental/any/any.nonmembers/any.cast/not_copy_constructible.fail.cpp
@@ -0,0 +1,45 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// template <class ValueType>
+// ValueType const any_cast(any const&);
+//
+// template <class ValueType>
+// ValueType any_cast(any &);
+//
+// template <class ValueType>
+// ValueType any_cast(any &&);
+
+// Test instantiating the any_cast with a non-copyable type.
+
+#include <experimental/any>
+
+using std::experimental::any;
+using std::experimental::any_cast;
+
+struct no_copy
+{
+    no_copy() {}
+    no_copy(no_copy &&) {}
+private:
+    no_copy(no_copy const &);
+};
+
+int main() {
+    any a;
+    any_cast<no_copy>(static_cast<any&>(a));
+    any_cast<no_copy>(static_cast<any const&>(a));
+    any_cast<no_copy>(static_cast<any &&>(a));
+    // expected-error@experimental/any:* 3 {{static_assert failed "_ValueType is required to be a reference or a CopyConstructible type."}}
+    // expected-error@experimental/any:* 3 {{calling a private constructor of class 'no_copy'}}
+}
\ No newline at end of file
diff --git a/test/std/experimental/any/any.nonmembers/any.cast/reference_types.fail.cpp b/test/std/experimental/any/any.nonmembers/any.cast/reference_types.fail.cpp
new file mode 100644
index 0000000..6c6ccc6
--- /dev/null
+++ b/test/std/experimental/any/any.nonmembers/any.cast/reference_types.fail.cpp
@@ -0,0 +1,37 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// template <class ValueType>
+// ValueType const* any_cast(any const *) noexcept;
+//
+// template <class ValueType>
+// ValueType * any_cast(any *) noexcept;
+
+#include <experimental/any>
+
+using std::experimental::any;
+using std::experimental::any_cast;
+
+int main()
+{
+    any a(1);
+    any_cast<int &>(&a); // expected-error@experimental/any:* 1 {{static_assert failed "_ValueType may not be a reference."}}
+    any_cast<int &&>(&a); // expected-error@experimental/any:* 1 {{static_assert failed "_ValueType may not be a reference."}}
+    any_cast<int const &>(&a); // expected-error@experimental/any:* 1 {{static_assert failed "_ValueType may not be a reference."}}
+    any_cast<int const&&>(&a); // expected-error@experimental/any:* 1 {{static_assert failed "_ValueType may not be a reference."}}
+    any const& a2 = a;
+    any_cast<int &>(&a2); // expected-error@experimental/any:* 1 {{static_assert failed "_ValueType may not be a reference."}}
+    any_cast<int &&>(&a2); // expected-error@experimental/any:* 1 {{static_assert failed "_ValueType may not be a reference."}}
+    any_cast<int const &>(&a2); // expected-error@experimental/any:* 1 {{static_assert failed "_ValueType may not be a reference."}}
+    any_cast<int const &&>(&a2); // expected-error@experimental/any:* 1 {{static_assert failed "_ValueType may not be a reference."}}
+}
diff --git a/test/std/experimental/any/any.nonmembers/swap.pass.cpp b/test/std/experimental/any/any.nonmembers/swap.pass.cpp
new file mode 100644
index 0000000..a3fbd43
--- /dev/null
+++ b/test/std/experimental/any/any.nonmembers/swap.pass.cpp
@@ -0,0 +1,40 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/any>
+
+// void swap(any &, any &) noexcept
+
+// swap(...) just wraps any::swap(...). That function is tested elsewhere.
+
+#include <experimental/any>
+#include <cassert>
+
+using std::experimental::any;
+using std::experimental::any_cast;
+
+int main()
+{
+
+    { // test noexcept
+        any a;
+        static_assert(noexcept(swap(a, a)), "swap(any&, any&) must be noexcept");
+    }
+    {
+        any a1(1);
+        any a2(2);
+
+        swap(a1, a2);
+
+        assert(any_cast<int>(a1) == 2);
+        assert(any_cast<int>(a2) == 1);
+    }
+}
diff --git a/test/std/experimental/func/func.searchers/func.searchers.default/default.pass.cpp b/test/std/experimental/func/func.searchers/func.searchers.default/default.pass.cpp
new file mode 100644
index 0000000..446dcbd
--- /dev/null
+++ b/test/std/experimental/func/func.searchers/func.searchers.default/default.pass.cpp
@@ -0,0 +1,95 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <functional>
+
+// default searcher
+// template<class _ForwardIterator, class _BinaryPredicate = equal_to<>>
+// class default_searcher {
+// public:
+//     default_searcher(_ForwardIterator __f, _ForwardIterator __l, 
+//                             _BinaryPredicate __p = _BinaryPredicate())
+//         : __first_(__f), __last_(__l), __pred_(__p) {}
+// 
+//     template <typename _ForwardIterator2>
+//     _ForwardIterator2 operator () (_ForwardIterator2 __f, _ForwardIterator2 __l) const {
+//         return std::search(__f, __l, __first_, __last_, __pred_);
+//         }
+// 
+// private:
+//     _ForwardIterator __first_;
+//     _ForwardIterator __last_;
+//     _BinaryPredicate __pred_;
+//     };
+
+
+#include <experimental/algorithm>
+#include <experimental/functional>
+#include <cassert>
+
+#include "test_iterators.h"
+
+template <typename Iter1, typename Iter2>
+void do_search(Iter1 b1, Iter1 e1, Iter2 b2, Iter2 e2, Iter1 result) {
+    std::experimental::default_searcher<Iter2> s{b2, e2};
+    assert(result == std::experimental::search(b1, e1, s));
+}
+
+template <class Iter1, class Iter2>
+void
+test()
+{
+    int ia[] = {0, 1, 2, 3, 4, 5};
+    const unsigned sa = sizeof(ia)/sizeof(ia[0]);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia),      Iter2(ia),    Iter1(ia));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia),      Iter2(ia+1),  Iter1(ia));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+1),    Iter2(ia+2),  Iter1(ia+1));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+2),    Iter2(ia+2),  Iter1(ia));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+2),    Iter2(ia+3),  Iter1(ia+2));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+2),    Iter2(ia+3),  Iter1(ia+2));
+    do_search(Iter1(ia), Iter1(ia),      Iter2(ia+2),    Iter2(ia+3),  Iter1(ia));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+sa-1), Iter2(ia+sa), Iter1(ia+sa-1));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+sa-3), Iter2(ia+sa), Iter1(ia+sa-3));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia),      Iter2(ia+sa), Iter1(ia));
+    do_search(Iter1(ia), Iter1(ia+sa-1), Iter2(ia),      Iter2(ia+sa), Iter1(ia+sa-1));
+    do_search(Iter1(ia), Iter1(ia+1),    Iter2(ia),      Iter2(ia+sa), Iter1(ia+1));
+    int ib[] = {0, 1, 2, 0, 1, 2, 3, 0, 1, 2, 3, 4};
+    const unsigned sb = sizeof(ib)/sizeof(ib[0]);
+    int ic[] = {1};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(ic), Iter2(ic+1), Iter1(ib+1));
+    int id[] = {1, 2};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(id), Iter2(id+2), Iter1(ib+1));
+    int ie[] = {1, 2, 3};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(ie), Iter2(ie+3), Iter1(ib+4));
+    int ig[] = {1, 2, 3, 4};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(ig), Iter2(ig+4), Iter1(ib+8));
+    int ih[] = {0, 1, 1, 1, 1, 2, 3, 0, 1, 2, 3, 4};
+    const unsigned sh = sizeof(ih)/sizeof(ih[0]);
+    int ii[] = {1, 1, 2};
+    do_search(Iter1(ih), Iter1(ih+sh), Iter2(ii), Iter2(ii+3), Iter1(ih+3));
+    int ij[] = {0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0};
+    const unsigned sj = sizeof(ij)/sizeof(ij[0]);
+    int ik[] = {0, 0, 0, 0, 1, 1, 1, 1, 0, 0};
+    const unsigned sk = sizeof(ik)/sizeof(ik[0]);
+    do_search(Iter1(ij), Iter1(ij+sj), Iter2(ik), Iter2(ik+sk), Iter1(ij+6));
+}
+
+int main() {
+    test<forward_iterator<const int*>, forward_iterator<const int*> >();
+    test<forward_iterator<const int*>, bidirectional_iterator<const int*> >();
+    test<forward_iterator<const int*>, random_access_iterator<const int*> >();
+    test<bidirectional_iterator<const int*>, forward_iterator<const int*> >();
+    test<bidirectional_iterator<const int*>, bidirectional_iterator<const int*> >();
+    test<bidirectional_iterator<const int*>, random_access_iterator<const int*> >();
+    test<random_access_iterator<const int*>, forward_iterator<const int*> >();
+    test<random_access_iterator<const int*>, bidirectional_iterator<const int*> >();
+    test<random_access_iterator<const int*>, random_access_iterator<const int*> >();
+}
diff --git a/test/std/experimental/func/func.searchers/func.searchers.default/default.pred.pass.cpp b/test/std/experimental/func/func.searchers/func.searchers.default/default.pred.pass.cpp
new file mode 100644
index 0000000..b65c500
--- /dev/null
+++ b/test/std/experimental/func/func.searchers/func.searchers.default/default.pred.pass.cpp
@@ -0,0 +1,102 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <functional>
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// default searcher
+// template<class _ForwardIterator, class _BinaryPredicate = equal_to<>>
+// class default_searcher {
+// public:
+//     default_searcher(_ForwardIterator __f, _ForwardIterator __l, 
+//                             _BinaryPredicate __p = _BinaryPredicate())
+//         : __first_(__f), __last_(__l), __pred_(__p) {}
+// 
+//     template <typename _ForwardIterator2>
+//     _ForwardIterator2 operator () (_ForwardIterator2 __f, _ForwardIterator2 __l) const {
+//         return std::search(__f, __l, __first_, __last_, __pred_);
+//         }
+// 
+// private:
+//     _ForwardIterator __first_;
+//     _ForwardIterator __last_;
+//     _BinaryPredicate __pred_;
+//     };
+
+
+#include <experimental/algorithm>
+#include <experimental/functional>
+#include <cassert>
+
+#include "test_iterators.h"
+
+struct count_equal
+{
+    static unsigned count;
+    template <class T>
+    bool operator()(const T& x, const T& y) const
+        {++count; return x == y;}
+};
+
+unsigned count_equal::count = 0;
+
+template <typename Iter1, typename Iter2>
+void do_search(Iter1 b1, Iter1 e1, Iter2 b2, Iter2 e2, Iter1 result, unsigned max_count) {
+    std::experimental::default_searcher<Iter2, count_equal> s{b2, e2};
+    count_equal::count = 0;
+    assert(result == std::experimental::search(b1, e1, s));
+    assert(count_equal::count <= max_count);
+}
+
+template <class Iter1, class Iter2>
+void
+test()
+{
+    int ia[] = {0, 1, 2, 3, 4, 5};
+    const unsigned sa = sizeof(ia)/sizeof(ia[0]);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia),      Iter2(ia),    Iter1(ia),      0);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia),      Iter2(ia+1),  Iter1(ia),      sa);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+1),    Iter2(ia+2),  Iter1(ia+1),    sa);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+2),    Iter2(ia+2),  Iter1(ia),      0);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+2),    Iter2(ia+3),  Iter1(ia+2),    sa);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+2),    Iter2(ia+3),  Iter1(ia+2),    sa);
+    do_search(Iter1(ia), Iter1(ia),      Iter2(ia+2),    Iter2(ia+3),  Iter1(ia),      0);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+sa-1), Iter2(ia+sa), Iter1(ia+sa-1), sa);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+sa-3), Iter2(ia+sa), Iter1(ia+sa-3), 3*sa);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia),      Iter2(ia+sa), Iter1(ia),      sa*sa);
+    do_search(Iter1(ia), Iter1(ia+sa-1), Iter2(ia),      Iter2(ia+sa), Iter1(ia+sa-1), (sa-1)*sa);
+    do_search(Iter1(ia), Iter1(ia+1),    Iter2(ia),      Iter2(ia+sa), Iter1(ia+1),    sa);
+    int ib[] = {0, 1, 2, 0, 1, 2, 3, 0, 1, 2, 3, 4};
+    const unsigned sb = sizeof(ib)/sizeof(ib[0]);
+    int ic[] = {1};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(ic), Iter2(ic+1), Iter1(ib+1), sb);
+    int id[] = {1, 2};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(id), Iter2(id+2), Iter1(ib+1), sb*2);
+    int ie[] = {1, 2, 3};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(ie), Iter2(ie+3), Iter1(ib+4), sb*3);
+    int ig[] = {1, 2, 3, 4};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(ig), Iter2(ig+4), Iter1(ib+8), sb*4);
+    int ih[] = {0, 1, 1, 1, 1, 2, 3, 0, 1, 2, 3, 4};
+    const unsigned sh = sizeof(ih)/sizeof(ih[0]);
+    int ii[] = {1, 1, 2};
+    do_search(Iter1(ih), Iter1(ih+sh), Iter2(ii), Iter2(ii+3), Iter1(ih+3),  sh*3);
+}
+
+int main() {
+    test<forward_iterator<const int*>, forward_iterator<const int*> >();
+    test<forward_iterator<const int*>, bidirectional_iterator<const int*> >();
+    test<forward_iterator<const int*>, random_access_iterator<const int*> >();
+    test<bidirectional_iterator<const int*>, forward_iterator<const int*> >();
+    test<bidirectional_iterator<const int*>, bidirectional_iterator<const int*> >();
+    test<bidirectional_iterator<const int*>, random_access_iterator<const int*> >();
+    test<random_access_iterator<const int*>, forward_iterator<const int*> >();
+    test<random_access_iterator<const int*>, bidirectional_iterator<const int*> >();
+    test<random_access_iterator<const int*>, random_access_iterator<const int*> >();
+}
diff --git a/test/std/experimental/func/func.searchers/func.searchers.default/func.searchers.default.creation/make_default_searcher.pass.cpp b/test/std/experimental/func/func.searchers/func.searchers.default/func.searchers.default.creation/make_default_searcher.pass.cpp
new file mode 100644
index 0000000..9528002
--- /dev/null
+++ b/test/std/experimental/func/func.searchers/func.searchers.default/func.searchers.default.creation/make_default_searcher.pass.cpp
@@ -0,0 +1,81 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <functional>
+
+// template<class ForwardIterator, class BinaryPredicate = equal_to<>>
+// default_searcher<ForwardIterator, BinaryPredicate>
+// make_default_searcher(ForwardIterator pat_first, ForwardIterator pat_last,
+//                       BinaryPredicate pred = BinaryPredicate());
+
+
+#include <experimental/algorithm>
+#include <experimental/functional>
+#include <cassert>
+
+#include "test_iterators.h"
+
+template <typename Iter1, typename Iter2>
+void do_search(Iter1 b1, Iter1 e1, Iter2 b2, Iter2 e2, Iter1 result) {
+    assert(result == std::experimental::search(b1, e1, 
+        std::experimental::make_default_searcher(b2, e2)));
+}
+
+template <class Iter1, class Iter2>
+void
+test()
+{
+    int ia[] = {0, 1, 2, 3, 4, 5};
+    const unsigned sa = sizeof(ia)/sizeof(ia[0]);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia),      Iter2(ia),     Iter1(ia));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia),      Iter2(ia+1),  Iter1(ia));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+1),    Iter2(ia+2),  Iter1(ia+1));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+2),    Iter2(ia+2),  Iter1(ia));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+2),    Iter2(ia+3),  Iter1(ia+2));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+2),    Iter2(ia+3),  Iter1(ia+2));
+    do_search(Iter1(ia), Iter1(ia),      Iter2(ia+2),    Iter2(ia+3),  Iter1(ia));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+sa-1), Iter2(ia+sa), Iter1(ia+sa-1));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+sa-3), Iter2(ia+sa), Iter1(ia+sa-3));
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia),      Iter2(ia+sa), Iter1(ia));
+    do_search(Iter1(ia), Iter1(ia+sa-1), Iter2(ia),      Iter2(ia+sa), Iter1(ia+sa-1));
+    do_search(Iter1(ia), Iter1(ia+1),    Iter2(ia),      Iter2(ia+sa), Iter1(ia+1));
+    int ib[] = {0, 1, 2, 0, 1, 2, 3, 0, 1, 2, 3, 4};
+    const unsigned sb = sizeof(ib)/sizeof(ib[0]);
+    int ic[] = {1};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(ic), Iter2(ic+1), Iter1(ib+1));
+    int id[] = {1, 2};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(id), Iter2(id+2), Iter1(ib+1));
+    int ie[] = {1, 2, 3};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(ie), Iter2(ie+3), Iter1(ib+4));
+    int ig[] = {1, 2, 3, 4};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(ig), Iter2(ig+4), Iter1(ib+8));
+    int ih[] = {0, 1, 1, 1, 1, 2, 3, 0, 1, 2, 3, 4};
+    const unsigned sh = sizeof(ih)/sizeof(ih[0]);
+    int ii[] = {1, 1, 2};
+    do_search(Iter1(ih), Iter1(ih+sh), Iter2(ii), Iter2(ii+3), Iter1(ih+3));
+    int ij[] = {0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0};
+    const unsigned sj = sizeof(ij)/sizeof(ij[0]);
+    int ik[] = {0, 0, 0, 0, 1, 1, 1, 1, 0, 0};
+    const unsigned sk = sizeof(ik)/sizeof(ik[0]);
+    do_search(Iter1(ij), Iter1(ij+sj), Iter2(ik), Iter2(ik+sk), Iter1(ij+6));
+}
+
+int main() {
+    test<forward_iterator<const int*>, forward_iterator<const int*> >();
+    test<forward_iterator<const int*>, bidirectional_iterator<const int*> >();
+    test<forward_iterator<const int*>, random_access_iterator<const int*> >();
+    test<bidirectional_iterator<const int*>, forward_iterator<const int*> >();
+    test<bidirectional_iterator<const int*>, bidirectional_iterator<const int*> >();
+    test<bidirectional_iterator<const int*>, random_access_iterator<const int*> >();
+    test<random_access_iterator<const int*>, forward_iterator<const int*> >();
+    test<random_access_iterator<const int*>, bidirectional_iterator<const int*> >();
+    test<random_access_iterator<const int*>, random_access_iterator<const int*> >();
+}
diff --git a/test/std/experimental/func/func.searchers/func.searchers.default/func.searchers.default.creation/make_default_searcher.pred.pass.cpp b/test/std/experimental/func/func.searchers/func.searchers.default/func.searchers.default.creation/make_default_searcher.pred.pass.cpp
new file mode 100644
index 0000000..2770202
--- /dev/null
+++ b/test/std/experimental/func/func.searchers/func.searchers.default/func.searchers.default.creation/make_default_searcher.pred.pass.cpp
@@ -0,0 +1,88 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <functional>
+
+// template<class ForwardIterator, class BinaryPredicate = equal_to<>>
+// default_searcher<ForwardIterator, BinaryPredicate>
+// make_default_searcher(ForwardIterator pat_first, ForwardIterator pat_last,
+//                       BinaryPredicate pred = BinaryPredicate());
+
+
+#include <experimental/algorithm>
+#include <experimental/functional>
+#include <cassert>
+
+#include "test_iterators.h"
+
+struct count_equal
+{
+    static unsigned count;
+    template <class T>
+    bool operator()(const T& x, const T& y)
+        {++count; return x == y;}
+};
+
+unsigned count_equal::count = 0;
+
+template <typename Iter1, typename Iter2>
+void do_search(Iter1 b1, Iter1 e1, Iter2 b2, Iter2 e2, Iter1 result, unsigned max_count) {
+    count_equal::count = 0;
+    assert(result == std::experimental::search(b1, e1, 
+        std::experimental::make_default_searcher(b2, e2)));
+    assert(count_equal::count <= max_count);
+}
+
+template <class Iter1, class Iter2>
+void
+test()
+{
+    int ia[] = {0, 1, 2, 3, 4, 5};
+    const unsigned sa = sizeof(ia)/sizeof(ia[0]);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia),      Iter2(ia),    Iter1(ia),      0);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia),      Iter2(ia+1),  Iter1(ia),      sa);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+1),    Iter2(ia+2),  Iter1(ia+1),    sa);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+2),    Iter2(ia+2),  Iter1(ia),      0);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+2),    Iter2(ia+3),  Iter1(ia+2),    sa);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+2),    Iter2(ia+3),  Iter1(ia+2),    sa);
+    do_search(Iter1(ia), Iter1(ia),      Iter2(ia+2),    Iter2(ia+3),  Iter1(ia),      0);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+sa-1), Iter2(ia+sa), Iter1(ia+sa-1), sa);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia+sa-3), Iter2(ia+sa), Iter1(ia+sa-3), 3*sa);
+    do_search(Iter1(ia), Iter1(ia+sa),   Iter2(ia),      Iter2(ia+sa), Iter1(ia),      sa*sa);
+    do_search(Iter1(ia), Iter1(ia+sa-1), Iter2(ia),      Iter2(ia+sa), Iter1(ia+sa-1), (sa-1)*sa);
+    do_search(Iter1(ia), Iter1(ia+1),    Iter2(ia),      Iter2(ia+sa), Iter1(ia+1),    sa);
+    int ib[] = {0, 1, 2, 0, 1, 2, 3, 0, 1, 2, 3, 4};
+    const unsigned sb = sizeof(ib)/sizeof(ib[0]);
+    int ic[] = {1};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(ic), Iter2(ic+1), Iter1(ib+1), sb);
+    int id[] = {1, 2};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(id), Iter2(id+2), Iter1(ib+1), sb*2);
+    int ie[] = {1, 2, 3};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(ie), Iter2(ie+3), Iter1(ib+4), sb*3);
+    int ig[] = {1, 2, 3, 4};
+    do_search(Iter1(ib), Iter1(ib+sb), Iter2(ig), Iter2(ig+4), Iter1(ib+8), sb*4);
+    int ih[] = {0, 1, 1, 1, 1, 2, 3, 0, 1, 2, 3, 4};
+    const unsigned sh = sizeof(ih)/sizeof(ih[0]);
+    int ii[] = {1, 1, 2};
+    do_search(Iter1(ih), Iter1(ih+sh), Iter2(ii), Iter2(ii+3), Iter1(ih+3),  sh*3);
+}
+
+int main() {
+    test<forward_iterator<const int*>, forward_iterator<const int*> >();
+    test<forward_iterator<const int*>, bidirectional_iterator<const int*> >();
+    test<forward_iterator<const int*>, random_access_iterator<const int*> >();
+    test<bidirectional_iterator<const int*>, forward_iterator<const int*> >();
+    test<bidirectional_iterator<const int*>, bidirectional_iterator<const int*> >();
+    test<bidirectional_iterator<const int*>, random_access_iterator<const int*> >();
+    test<random_access_iterator<const int*>, forward_iterator<const int*> >();
+    test<random_access_iterator<const int*>, bidirectional_iterator<const int*> >();
+    test<random_access_iterator<const int*>, random_access_iterator<const int*> >();
+}
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/experimental/func/func.searchers/nothing_to_do.pass.cpp
similarity index 95%
rename from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
rename to test/std/experimental/func/func.searchers/nothing_to_do.pass.cpp
index b58f5c5..9a59227 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/experimental/func/func.searchers/nothing_to_do.pass.cpp
@@ -1,3 +1,4 @@
+// -*- C++ -*-
 //===----------------------------------------------------------------------===//
 //
 //                     The LLVM Compiler Infrastructure
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/experimental/func/header.functional.synop/includes.pass.cpp
similarity index 68%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/std/experimental/func/header.functional.synop/includes.pass.cpp
index b58f5c5..1b72d4a 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/experimental/func/header.functional.synop/includes.pass.cpp
@@ -7,6 +7,15 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/functional>
+//
+//  has to include <functional>
+
+#include <experimental/functional>
+
 int main()
 {
+  std::function<int(int)> x;
 }
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/experimental/func/nothing_to_do.pass.cpp
similarity index 95%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/std/experimental/func/nothing_to_do.pass.cpp
index b58f5c5..9a59227 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/experimental/func/nothing_to_do.pass.cpp
@@ -1,3 +1,4 @@
+// -*- C++ -*-
 //===----------------------------------------------------------------------===//
 //
 //                     The LLVM Compiler Infrastructure
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/experimental/utilities/tuple/header.tuple.synop/includes.pass.cpp
similarity index 75%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/std/experimental/utilities/tuple/header.tuple.synop/includes.pass.cpp
index b58f5c5..d37557a 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/experimental/utilities/tuple/header.tuple.synop/includes.pass.cpp
@@ -7,6 +7,13 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/tuple>
+
+#include <experimental/tuple>
+
 int main()
 {
+  std::tuple<int> x(1);
 }
diff --git a/test/std/experimental/utilities/tuple/tuple.apply/arg_type.pass.cpp b/test/std/experimental/utilities/tuple/tuple.apply/arg_type.pass.cpp
new file mode 100644
index 0000000..56dc3c6
--- /dev/null
+++ b/test/std/experimental/utilities/tuple/tuple.apply/arg_type.pass.cpp
@@ -0,0 +1,182 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/tuple>
+
+// template <class F, class T> constexpr decltype(auto) apply(F &&, T &&)
+
+// Test with different ref/ptr/cv qualified argument types.
+
+#include <experimental/tuple>
+#include <array>
+#include <utility>
+#include <cassert>
+
+namespace ex = std::experimental;
+
+int call_with_value(int x, int y) { return (x + y); }
+int call_with_ref(int & x, int & y) { return (x + y); }
+int call_with_const_ref(int const & x, int const & y) { return (x + y); }
+int call_with_rvalue_ref(int && x, int && y) { return (x + y); }
+int call_with_pointer(int * x, int * y) { return (*x + *y); }
+int call_with_const_pointer(int const* x, int const * y) { return (*x + *y); }
+
+
+template <class Tuple>
+void test_values()
+{
+    {
+        Tuple t{1, 2};
+        assert(3 == ex::apply(call_with_value, t));
+    }
+    {
+        Tuple t{2, 2};
+        assert(4 == ex::apply(call_with_ref, t));
+    }
+    {
+        Tuple t{2, 3};
+        assert(5 == ex::apply(call_with_const_ref, t));
+    }
+    {
+        Tuple t{3, 3};
+        assert(6 == ex::apply(call_with_rvalue_ref, static_cast<Tuple &&>(t)));
+    }
+    {
+        Tuple const t{4, 4};
+        assert(8 == ex::apply(call_with_value, t));
+    }
+    {
+        Tuple const t{4, 5};
+        assert(9 == ex::apply(call_with_const_ref, t));
+    }
+}
+
+template <class Tuple>
+void test_refs()
+{
+    int x = 0;
+    int y = 0;
+    {
+        x = 1; y = 2;
+        Tuple t{x, y};
+        assert(3 == ex::apply(call_with_value, t));
+    }
+    {
+        x = 2; y = 2;
+        Tuple t{x, y};
+        assert(4 == ex::apply(call_with_ref, t));
+    }
+    {
+        x = 2; y = 3;
+        Tuple t{x, y};
+        assert(5 == ex::apply(call_with_const_ref, t));
+    }
+    {
+        x = 3; y = 3;
+        Tuple const t{x, y};
+        assert(6 == ex::apply(call_with_value, t));
+    }
+    {
+        x = 3; y = 4;
+        Tuple const t{x, y};
+        assert(7 == ex::apply(call_with_const_ref, t));
+    }
+}
+
+template <class Tuple>
+void test_const_refs()
+{
+    int x = 0;
+    int y = 0;
+    {
+        x = 1; y = 2;
+        Tuple t{x, y};
+        assert(3 == ex::apply(call_with_value, t));
+    }
+    {
+        x = 2; y = 3;
+        Tuple t{x, y};
+        assert(5 == ex::apply(call_with_const_ref, t));
+    }
+    {
+        x = 3; y = 3;
+        Tuple const t{x, y};
+        assert(6 == ex::apply(call_with_value, t));
+    }
+    {
+        x = 3; y = 4;
+        Tuple const t{x, y};
+        assert(7 == ex::apply(call_with_const_ref, t));
+    }
+}
+
+
+template <class Tuple>
+void test_pointer()
+{
+    int x = 0;
+    int y = 0;
+    {
+        x = 2; y = 2;
+        Tuple t{&x, &y};
+        assert(4 == ex::apply(call_with_pointer, t));
+    }
+    {
+        x = 2; y = 3;
+        Tuple t{&x, &y};
+        assert(5 == ex::apply(call_with_const_pointer, t));
+    }
+    {
+        x = 3; y = 4;
+        Tuple const t{&x, &y};
+        assert(7 == ex::apply(call_with_const_pointer, t));
+    }
+}
+
+
+template <class Tuple>
+void test_const_pointer()
+{
+    int x = 0;
+    int y = 0;
+    {
+        x = 2; y = 3;
+        Tuple t{&x, &y};
+        assert(5 == ex::apply(call_with_const_pointer, t));
+    }
+    {
+        x = 3; y = 4;
+        Tuple const t{&x, &y};
+        assert(7 == ex::apply(call_with_const_pointer, t));
+    }
+}
+
+
+int main()
+{
+    test_values<std::tuple<int, int>>();
+    test_values<std::pair<int, int>>();
+    test_values<std::array<int, 2>>();
+
+    test_refs<std::tuple<int &, int &>>();
+    test_refs<std::pair<int &, int &>>();
+
+    test_const_refs<std::tuple<int const &, int const &>>();
+    test_const_refs<std::pair<int const &, int const &>>();
+
+    test_pointer<std::tuple<int *, int *>>();
+    test_pointer<std::pair<int *, int *>>();
+    test_pointer<std::array<int *, 2>>();
+
+    test_const_pointer<std::tuple<int const *, int const *>>();
+    test_const_pointer<std::pair<int const *, int const *>>();
+    test_const_pointer<std::array<int const *, 2>>();
+}
diff --git a/test/std/experimental/utilities/tuple/tuple.apply/constexpr_types.pass.cpp b/test/std/experimental/utilities/tuple/tuple.apply/constexpr_types.pass.cpp
new file mode 100644
index 0000000..2d70048
--- /dev/null
+++ b/test/std/experimental/utilities/tuple/tuple.apply/constexpr_types.pass.cpp
@@ -0,0 +1,123 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// TODO(ericwf)
+// constexpr support temporarily reverted due to bug:
+// https://llvm.org/bugs/show_bug.cgi?id=23141
+// XFAIL: *
+
+// <experimental/tuple>
+
+// template <class F, class T> constexpr decltype(auto) apply(F &&, T &&)
+
+// Testing constexpr evaluation
+
+#include <experimental/tuple>
+#include <utility>
+#include <cassert>
+
+constexpr int f_int_0() { return 1; }
+constexpr int f_int_1(int x) { return  x; }
+constexpr int f_int_2(int x, int y) { return (x + y); }
+
+struct A_int_0
+{
+    constexpr A_int_0() {}
+    constexpr int operator()() const { return 1; }
+};
+
+struct A_int_1
+{
+    constexpr A_int_1() {}
+    constexpr int operator()(int x) const { return x; }
+};
+
+struct A_int_2
+{
+    constexpr A_int_2() {}
+    constexpr int operator()(int x, int y) const { return (x + y); }
+};
+
+namespace ex = std::experimental;
+
+template <class Tuple>
+void test_0()
+{
+    // function
+    {
+        constexpr Tuple t{};
+        static_assert(1 == ex::apply(f_int_0, t), "");
+    }
+    // function pointer
+    {
+        constexpr Tuple t{};
+        constexpr auto fp = &f_int_0;
+        static_assert(1 == ex::apply(fp, t), "");
+    }
+    // functor
+    {
+        constexpr Tuple t{};
+        constexpr A_int_0 a;
+        static_assert(1 == ex::apply(a, t), "");
+    }
+}
+
+template <class Tuple>
+void test_1()
+{
+    // function
+    {
+        constexpr Tuple t{1};
+        static_assert(1 == ex::apply(f_int_1, t), "");
+    }
+    // function pointer
+    {
+        constexpr Tuple t{2};
+        constexpr int (*fp)(int) = f_int_1;
+        static_assert(2 == ex::apply(fp, t), "");
+    }
+    // functor
+    {
+        constexpr Tuple t{3};
+        constexpr A_int_1 fn;
+        static_assert(3 == ex::apply(fn, t), "");
+    }
+}
+
+template <class Tuple>
+void test_2()
+{
+    // function
+    {
+        constexpr Tuple t{1, 2};
+        static_assert(3 == ex::apply(f_int_2, t), "");
+    }
+        // function pointer
+    {
+        constexpr Tuple t{2, 3};
+        constexpr auto fp = &f_int_2;
+        static_assert(5 == ex::apply(fp, t), "");
+    }
+    // functor
+    {
+        constexpr Tuple t{3, 4};
+        constexpr A_int_2 a;
+        static_assert(7 == ex::apply(a, t), "");
+    }
+}
+
+int main()
+{
+    test_0<std::tuple<>>();
+    test_1<std::tuple<int>>();
+    test_2<std::tuple<int, int>>();
+    test_2<std::pair<int, int>>();
+}
diff --git a/test/std/experimental/utilities/tuple/tuple.apply/extended_types.pass.cpp b/test/std/experimental/utilities/tuple/tuple.apply/extended_types.pass.cpp
new file mode 100644
index 0000000..3225549
--- /dev/null
+++ b/test/std/experimental/utilities/tuple/tuple.apply/extended_types.pass.cpp
@@ -0,0 +1,423 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/tuple>
+
+// template <class F, class T> constexpr decltype(auto) apply(F &&, T &&)
+
+// Testing extended function types. The extented function types are those
+// named by INVOKE but that are not actual callable objects. These include
+// bullets 1-4 of invoke.
+
+#include <experimental/tuple>
+#include <array>
+#include <utility>
+#include <cassert>
+
+int count = 0;
+
+struct A_int_0
+{
+    A_int_0() : obj1(0){}
+    A_int_0(int x) : obj1(x) {}
+    int mem1() { return ++count; }
+    int mem2() const { return ++count; }
+    int const obj1;
+};
+
+struct A_int_1
+{
+    A_int_1() {}
+    A_int_1(int) {}
+    int mem1(int x) { return count += x; }
+    int mem2(int x) const { return count += x; }
+};
+
+struct A_int_2
+{
+    A_int_2() {}
+    A_int_2(int) {}
+    int mem1(int x, int y) { return count += (x + y); }
+    int mem2(int x, int y) const { return count += (x + y); }
+};
+
+template <class A>
+struct A_wrap
+{
+    A_wrap() {}
+    A_wrap(int x) : m_a(x) {}
+    A & operator*() { return m_a; }
+    A const & operator*() const { return m_a; }
+    A m_a;
+};
+
+typedef A_wrap<A_int_0> A_wrap_0;
+typedef A_wrap<A_int_1> A_wrap_1;
+typedef A_wrap<A_int_2> A_wrap_2;
+
+
+template <class A>
+struct A_base : public A
+{
+    A_base() : A() {}
+    A_base(int x) : A(x) {}
+};
+
+typedef A_base<A_int_0> A_base_0;
+typedef A_base<A_int_1> A_base_1;
+typedef A_base<A_int_2> A_base_2;
+
+namespace ex = std::experimental;
+
+template <
+    class Tuple, class ConstTuple
+  , class TuplePtr, class ConstTuplePtr
+  , class TupleWrap, class ConstTupleWrap
+  , class TupleBase, class ConstTupleBase
+  >
+void test_ext_int_0()
+{
+    count = 0;
+    typedef A_int_0 T;
+    typedef A_wrap_0 Wrap;
+    typedef A_base_0 Base;
+
+    typedef int(T::*mem1_t)();
+    mem1_t mem1 = &T::mem1;
+
+    typedef int(T::*mem2_t)() const;
+    mem2_t mem2 = &T::mem2;
+
+    typedef int const T::*obj1_t;
+    obj1_t obj1 = &T::obj1;
+
+    // member function w/ref
+    {
+        T a;
+        Tuple t{a};
+        assert(1 == ex::apply(mem1, t));
+        assert(count == 1);
+    }
+    count = 0;
+    // member function w/pointer
+    {
+        T a;
+        TuplePtr t{&a};
+        assert(1 == ex::apply(mem1, t));
+        assert(count == 1);
+    }
+    count = 0;
+    // member function w/base
+    {
+        Base a;
+        TupleBase t{a};
+        assert(1 == ex::apply(mem1, t));
+        assert(count == 1);
+    }
+    count = 0;
+    // member function w/wrap
+    {
+        Wrap a;
+        TupleWrap t{a};
+        assert(1 == ex::apply(mem1, t));
+        assert(count == 1);
+    }
+    count = 0;
+    // const member function w/ref
+    {
+        T const a;
+        ConstTuple t{a};
+        assert(1 == ex::apply(mem2, t));
+        assert(count == 1);
+    }
+    count = 0;
+    // const member function w/pointer
+    {
+        T const a;
+        ConstTuplePtr t{&a};
+        assert(1 == ex::apply(mem2, t));
+        assert(count == 1);
+    }
+    count = 0;
+    // const member function w/base
+    {
+        Base const a;
+        ConstTupleBase t{a};
+        assert(1 == ex::apply(mem2, t));
+        assert(count == 1);
+    }
+    count = 0;
+    // const member function w/wrapper
+    {
+        Wrap const a;
+        ConstTupleWrap t{a};
+        assert(1 == ex::apply(mem2, t));
+        assert(1 == count);
+    }
+    // member object w/ref
+    {
+        T a{42};
+        Tuple t{a};
+        assert(42 == ex::apply(obj1, t));
+    }
+    // member object w/pointer
+    {
+        T a{42};
+        TuplePtr t{&a};
+        assert(42 == ex::apply(obj1, t));
+    }
+    // member object w/base
+    {
+        Base a{42};
+        TupleBase t{a};
+        assert(42 == ex::apply(obj1, t));
+    }
+    // member object w/wrapper
+    {
+        Wrap a{42};
+        TupleWrap t{a};
+        assert(42 == ex::apply(obj1, t));
+    }
+}
+
+
+template <
+    class Tuple, class ConstTuple
+  , class TuplePtr, class ConstTuplePtr
+  , class TupleWrap, class ConstTupleWrap
+  , class TupleBase, class ConstTupleBase
+  >
+void test_ext_int_1()
+{
+    count = 0;
+    typedef A_int_1 T;
+    typedef A_wrap_1 Wrap;
+    typedef A_base_1 Base;
+
+    typedef int(T::*mem1_t)(int);
+    mem1_t mem1 = &T::mem1;
+
+    typedef int(T::*mem2_t)(int) const;
+    mem2_t mem2 = &T::mem2;
+
+    // member function w/ref
+    {
+        T a;
+        Tuple t{a, 2};
+        assert(2 == ex::apply(mem1, t));
+        assert(count == 2);
+    }
+    count = 0;
+    // member function w/pointer
+    {
+        T a;
+        TuplePtr t{&a, 3};
+        assert(3 == ex::apply(mem1, t));
+        assert(count == 3);
+    }
+    count = 0;
+    // member function w/base
+    {
+        Base a;
+        TupleBase t{a, 4};
+        assert(4 == ex::apply(mem1, t));
+        assert(count == 4);
+    }
+    count = 0;
+    // member function w/wrap
+    {
+        Wrap a;
+        TupleWrap t{a, 5};
+        assert(5 == ex::apply(mem1, t));
+        assert(count == 5);
+    }
+    count = 0;
+    // const member function w/ref
+    {
+        T const a;
+        ConstTuple t{a, 6};
+        assert(6 == ex::apply(mem2, t));
+        assert(count == 6);
+    }
+    count = 0;
+    // const member function w/pointer
+    {
+        T const a;
+        ConstTuplePtr t{&a, 7};
+        assert(7 == ex::apply(mem2, t));
+        assert(count == 7);
+    }
+    count = 0;
+    // const member function w/base
+    {
+        Base const a;
+        ConstTupleBase t{a, 8};
+        assert(8 == ex::apply(mem2, t));
+        assert(count == 8);
+    }
+    count = 0;
+    // const member function w/wrapper
+    {
+        Wrap const a;
+        ConstTupleWrap t{a, 9};
+        assert(9 == ex::apply(mem2, t));
+        assert(9 == count);
+    }
+}
+
+
+template <
+    class Tuple, class ConstTuple
+  , class TuplePtr, class ConstTuplePtr
+  , class TupleWrap, class ConstTupleWrap
+  , class TupleBase, class ConstTupleBase
+  >
+void test_ext_int_2()
+{
+    count = 0;
+    typedef A_int_2 T;
+    typedef A_wrap_2 Wrap;
+    typedef A_base_2 Base;
+
+    typedef int(T::*mem1_t)(int, int);
+    mem1_t mem1 = &T::mem1;
+
+    typedef int(T::*mem2_t)(int, int) const;
+    mem2_t mem2 = &T::mem2;
+
+    // member function w/ref
+    {
+        T a;
+        Tuple t{a, 1, 1};
+        assert(2 == ex::apply(mem1, t));
+        assert(count == 2);
+    }
+    count = 0;
+    // member function w/pointer
+    {
+        T a;
+        TuplePtr t{&a, 1, 2};
+        assert(3 == ex::apply(mem1, t));
+        assert(count == 3);
+    }
+    count = 0;
+    // member function w/base
+    {
+        Base a;
+        TupleBase t{a, 2, 2};
+        assert(4 == ex::apply(mem1, t));
+        assert(count == 4);
+    }
+    count = 0;
+    // member function w/wrap
+    {
+        Wrap a;
+        TupleWrap t{a, 2, 3};
+        assert(5 == ex::apply(mem1, t));
+        assert(count == 5);
+    }
+    count = 0;
+    // const member function w/ref
+    {
+        T const a;
+        ConstTuple t{a, 3, 3};
+        assert(6 == ex::apply(mem2, t));
+        assert(count == 6);
+    }
+    count = 0;
+    // const member function w/pointer
+    {
+        T const a;
+        ConstTuplePtr t{&a, 3, 4};
+        assert(7 == ex::apply(mem2, t));
+        assert(count == 7);
+    }
+    count = 0;
+    // const member function w/base
+    {
+        Base const a;
+        ConstTupleBase t{a, 4, 4};
+        assert(8 == ex::apply(mem2, t));
+        assert(count == 8);
+    }
+    count = 0;
+    // const member function w/wrapper
+    {
+        Wrap const a;
+        ConstTupleWrap t{a, 4, 5};
+        assert(9 == ex::apply(mem2, t));
+        assert(9 == count);
+    }
+}
+
+int main()
+{
+    {
+        test_ext_int_0<
+            std::tuple<A_int_0 &>, std::tuple<A_int_0 const &>
+          , std::tuple<A_int_0 *>, std::tuple<A_int_0 const *>
+          , std::tuple<A_wrap_0 &>, std::tuple<A_wrap_0 const &>
+          , std::tuple<A_base_0 &>, std::tuple<A_base_0 const &>
+          >();
+        test_ext_int_0<
+            std::tuple<A_int_0>, std::tuple<A_int_0 const>
+          , std::tuple<A_int_0 *>, std::tuple<A_int_0 const *>
+          , std::tuple<A_wrap_0>, std::tuple<A_wrap_0 const>
+          , std::tuple<A_base_0>, std::tuple<A_base_0 const>
+          >();
+        test_ext_int_0<
+            std::array<A_int_0, 1>, std::array<A_int_0 const, 1>
+          , std::array<A_int_0*, 1>, std::array<A_int_0 const*, 1>
+          , std::array<A_wrap_0, 1>, std::array<A_wrap_0 const, 1>
+          , std::array<A_base_0, 1>, std::array<A_base_0 const, 1>
+          >();
+    }
+    {
+        test_ext_int_1<
+            std::tuple<A_int_1 &, int>, std::tuple<A_int_1 const &, int>
+          , std::tuple<A_int_1 *, int>, std::tuple<A_int_1 const *, int>
+          , std::tuple<A_wrap_1 &, int>, std::tuple<A_wrap_1 const &, int>
+          , std::tuple<A_base_1 &, int>, std::tuple<A_base_1 const &, int>
+          >();
+        test_ext_int_1<
+            std::tuple<A_int_1, int>, std::tuple<A_int_1 const, int>
+          , std::tuple<A_int_1 *, int>, std::tuple<A_int_1 const *, int>
+          , std::tuple<A_wrap_1, int>, std::tuple<A_wrap_1 const, int>
+          , std::tuple<A_base_1, int>, std::tuple<A_base_1 const, int>
+          >();
+        test_ext_int_1<
+            std::pair<A_int_1 &, int>, std::pair<A_int_1 const &, int>
+          , std::pair<A_int_1 *, int>, std::pair<A_int_1 const *, int>
+          , std::pair<A_wrap_1 &, int>, std::pair<A_wrap_1 const &, int>
+          , std::pair<A_base_1 &, int>, std::pair<A_base_1 const &, int>
+          >();
+        test_ext_int_1<
+            std::pair<A_int_1, int>, std::pair<A_int_1 const, int>
+          , std::pair<A_int_1 *, int>, std::pair<A_int_1 const *, int>
+          , std::pair<A_wrap_1, int>, std::pair<A_wrap_1 const, int>
+          , std::pair<A_base_1, int>, std::pair<A_base_1 const, int>
+          >();
+    }
+    {
+        test_ext_int_2<
+            std::tuple<A_int_2 &, int, int>, std::tuple<A_int_2 const &, int, int>
+          , std::tuple<A_int_2 *, int, int>, std::tuple<A_int_2 const *, int, int>
+          , std::tuple<A_wrap_2 &, int, int>, std::tuple<A_wrap_2 const &, int, int>
+          , std::tuple<A_base_2 &, int, int>, std::tuple<A_base_2 const &, int, int>
+          >();
+        test_ext_int_2<
+            std::tuple<A_int_2, int, int>, std::tuple<A_int_2 const, int, int>
+          , std::tuple<A_int_2 *, int, int>, std::tuple<A_int_2 const *, int, int>
+          , std::tuple<A_wrap_2, int, int>, std::tuple<A_wrap_2 const, int, int>
+          , std::tuple<A_base_2, int, int>, std::tuple<A_base_2 const, int, int>
+          >();
+    }
+}
diff --git a/test/std/experimental/utilities/tuple/tuple.apply/large_arity.pass.cpp b/test/std/experimental/utilities/tuple/tuple.apply/large_arity.pass.cpp
new file mode 100644
index 0000000..027258a
--- /dev/null
+++ b/test/std/experimental/utilities/tuple/tuple.apply/large_arity.pass.cpp
@@ -0,0 +1,146 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/tuple>
+
+// template <class F, class T> constexpr decltype(auto) apply(F &&, T &&)
+
+// Stress testing large arities with tuple and array.
+
+#include <experimental/tuple>
+#include <array>
+#include <utility>
+#include <cassert>
+
+////////////////////////////////////////////////////////////////////////////////
+template <class T, std::size_t Dummy = 0>
+struct always_imp
+{
+    typedef T type;
+};
+
+template <class T, std::size_t Dummy = 0>
+using always_t = typename always_imp<T, Dummy>::type;
+
+////////////////////////////////////////////////////////////////////////////////
+template <class Tuple, class Idx>
+struct make_function;
+
+template <class Tp, std::size_t ...Idx>
+struct make_function<Tp, std::integer_sequence<std::size_t, Idx...>>
+{
+    using type = bool (*)(always_t<Tp, Idx>...);
+};
+
+template <class Tp, std::size_t Size>
+using make_function_t = typename make_function<Tp, std::make_index_sequence<Size>>::type;
+
+////////////////////////////////////////////////////////////////////////////////
+template <class Tp, class Idx>
+struct make_tuple_imp;
+
+////////////////////////////////////////////////////////////////////////////////
+template <class Tp, std::size_t ...Idx>
+struct make_tuple_imp<Tp, std::integer_sequence<std::size_t, Idx...>>
+{
+    using type = std::tuple<always_t<Tp, Idx>...>;
+};
+
+template <class Tp, std::size_t Size>
+using make_tuple_t = typename make_tuple_imp<Tp, std::make_index_sequence<Size>>::type;
+
+template <class ...Types>
+bool test_apply_fn(Types...) { return true; }
+
+namespace ex = std::experimental;
+
+template <std::size_t Size>
+void test_all()
+{
+
+    using A = std::array<int, Size>;
+    using ConstA = std::array<int const, Size>;
+
+    using Tuple = make_tuple_t<int, Size>;
+    using CTuple = make_tuple_t<const int, Size>;
+
+    using ValFn  = make_function_t<int, Size>;
+    ValFn val_fn = &test_apply_fn;
+
+    using RefFn  = make_function_t<int &, Size>;
+    RefFn ref_fn = &test_apply_fn;
+
+    using CRefFn = make_function_t<int const &, Size>;
+    CRefFn cref_fn = &test_apply_fn;
+
+    using RRefFn = make_function_t<int &&, Size>;
+    RRefFn rref_fn = &test_apply_fn;
+
+    {
+        A a{};
+        assert(ex::apply(val_fn, a));
+        assert(ex::apply(ref_fn, a));
+        assert(ex::apply(cref_fn, a));
+        assert(ex::apply(rref_fn, std::move(a)));
+    }
+    {
+        ConstA a{};
+        assert(ex::apply(val_fn, a));
+        assert(ex::apply(cref_fn, a));
+    }
+    {
+        Tuple a{};
+        assert(ex::apply(val_fn, a));
+        assert(ex::apply(ref_fn, a));
+        assert(ex::apply(cref_fn, a));
+        assert(ex::apply(rref_fn, std::move(a)));
+    }
+    {
+        CTuple a{};
+        assert(ex::apply(val_fn, a));
+        assert(ex::apply(cref_fn, a));
+    }
+
+}
+
+
+template <std::size_t Size>
+void test_one()
+{
+    using A = std::array<int, Size>;
+    using Tuple = make_tuple_t<int, Size>;
+
+    using ValFn  = make_function_t<int, Size>;
+    ValFn val_fn = &test_apply_fn;
+
+    {
+        A a{};
+        assert(ex::apply(val_fn, a));
+    }
+    {
+        Tuple a{};
+        assert(ex::apply(val_fn, a));
+    }
+}
+
+int main()
+{
+    // Instantiate with 1-5 arguments.
+    test_all<1>();
+    test_all<2>();
+    test_all<3>();
+    test_all<4>();
+    test_all<5>();
+
+    // Stress test with 128.
+    test_one<128>();
+    //test_one<256>();
+}
diff --git a/test/std/experimental/utilities/tuple/tuple.apply/ref_qualifiers.pass.cpp b/test/std/experimental/utilities/tuple/tuple.apply/ref_qualifiers.pass.cpp
new file mode 100644
index 0000000..3cf259f
--- /dev/null
+++ b/test/std/experimental/utilities/tuple/tuple.apply/ref_qualifiers.pass.cpp
@@ -0,0 +1,53 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/tuple>
+
+// template <class F, class T> constexpr decltype(auto) apply(F &&, T &&)
+
+// Testing ref qualified functions
+
+#include <experimental/tuple>
+#include <cassert>
+
+struct func_obj
+{
+    constexpr func_obj() {}
+
+    constexpr int operator()() const & { return 1; }
+    constexpr int operator()() const && { return 2; }
+    constexpr int operator()() & { return 3; }
+    constexpr int operator()() && { return 4; }
+};
+
+namespace ex = std::experimental;
+
+int main()
+{
+// TODO(ericwf): Re-enable constexpr support
+/*
+    {
+        constexpr func_obj f;
+        constexpr std::tuple<> tp;
+
+        static_assert(1 == ex::apply(static_cast<func_obj const &>(f), tp), "");
+        static_assert(2 == ex::apply(static_cast<func_obj const &&>(f), tp), "");
+    }
+*/
+    {
+        func_obj f;
+        std::tuple<> tp;
+        assert(1 == ex::apply(static_cast<func_obj const &>(f), tp));
+        assert(2 == ex::apply(static_cast<func_obj const &&>(f), tp));
+        assert(3 == ex::apply(static_cast<func_obj &>(f), tp));
+        assert(4 == ex::apply(static_cast<func_obj &&>(f), tp));
+    }
+}
diff --git a/test/std/experimental/utilities/tuple/tuple.apply/return_type.pass.cpp b/test/std/experimental/utilities/tuple/tuple.apply/return_type.pass.cpp
new file mode 100644
index 0000000..1ec38da
--- /dev/null
+++ b/test/std/experimental/utilities/tuple/tuple.apply/return_type.pass.cpp
@@ -0,0 +1,76 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/tuple>
+
+// template <class F, class T> constexpr decltype(auto) apply(F &&, T &&)
+
+// Test the return type deduction.
+
+#include <experimental/tuple>
+#include <cassert>
+
+static int my_int = 42;
+
+template <int N> struct index {};
+
+void f(index<0>) {}
+
+int f(index<1>) { return 0; }
+int const f(index<2>) { return 0; }
+int volatile f(index<3>) { return 0; }
+int const volatile f(index<4>) { return 0; }
+
+int & f(index<5>) { return static_cast<int &>(my_int); }
+int const & f(index<6>) { return static_cast<int const &>(my_int); }
+int volatile & f(index<7>) { return static_cast<int volatile &>(my_int); }
+int const volatile & f(index<8>) { return static_cast<int const volatile &>(my_int); }
+
+int && f(index<9>) { return static_cast<int &&>(my_int); }
+int const && f(index<10>) { return static_cast<int const &&>(my_int); }
+int volatile && f(index<11>) { return static_cast<int volatile &&>(my_int); }
+int const volatile && f(index<12>) { return static_cast<int const volatile &&>(my_int); }
+
+int * f(index<13>) { return static_cast<int *>(&my_int); }
+int const * f(index<14>) { return static_cast<int const *>(&my_int); }
+int volatile * f(index<15>) { return static_cast<int volatile *>(&my_int); }
+int const volatile * f(index<16>) { return static_cast<int const volatile *>(&my_int); }
+
+
+template <int Func, class Expect>
+void test()
+{
+    using F = decltype((f(index<Func>{})));
+    static_assert(std::is_same<F, Expect>::value, "");
+}
+
+namespace ex = std::experimental;
+
+int main()
+{
+    test<0, void>();
+    test<1, int>();
+    //test<2, int const>();
+    //test<3, int volatile>();
+    //test<4, int const volatile>();
+    test<5, int &>();
+    test<6, int const &>();
+    test<7, int volatile &>();
+    test<8, int const volatile &>();
+    test<9, int &&>();
+    test<10, int const &&>();
+    test<11, int volatile &&>();
+    test<12, int const volatile &&>();
+    test<13, int *>();
+    test<14, int const *>();
+    test<15, int volatile *>();
+    test<16, int const volatile *>();
+}
diff --git a/test/std/experimental/utilities/tuple/tuple.apply/types.pass.cpp b/test/std/experimental/utilities/tuple/tuple.apply/types.pass.cpp
new file mode 100644
index 0000000..5d3d564
--- /dev/null
+++ b/test/std/experimental/utilities/tuple/tuple.apply/types.pass.cpp
@@ -0,0 +1,427 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/tuple>
+
+// template <class F, class T> constexpr decltype(auto) apply(F &&, T &&)
+
+// Test function types.
+
+#include <experimental/tuple>
+#include <array>
+#include <utility>
+#include <cassert>
+
+namespace ex = std::experimental;
+
+int count = 0;
+
+void f_void_0() { ++count; }
+void f_void_1(int i) { count += i; }
+void f_void_2(int x, int y) { count += (x + y); }
+void f_void_3(int x, int y, int z) { count += (x + y + z); }
+
+int f_int_0() { return ++count; }
+int f_int_1(int x) { return count += x; }
+int f_int_2(int x, int y) { return count += (x + y); }
+int f_int_3(int x, int y, int z) { return count += (x + y + z); }
+
+struct A_void_0
+{
+    A_void_0() {}
+    void operator()() { ++count; }
+    void operator()() const { ++count; ++count; }
+};
+
+struct A_void_1
+{
+    A_void_1() {}
+    void operator()(int x) { count += x; }
+    void operator()(int x) const { count += x + 1; }
+};
+
+struct A_void_2
+{
+    A_void_2() {}
+    void operator()(int x, int y) { count += (x + y); }
+    void operator()(int x, int y) const { count += (x + y) + 1; }
+};
+
+struct A_void_3
+{
+    A_void_3() {}
+    void operator()(int x, int y, int z) { count += (x + y + z); }
+    void operator()(int x, int y, int z) const { count += (x + y + z) + 1; }
+};
+
+
+struct A_int_0
+{
+    A_int_0() {}
+    int operator()() { return ++count; }
+    int operator()() const { ++count; return ++count; }
+};
+
+struct A_int_1
+{
+    A_int_1() {}
+    int operator()(int x) { return count += x; }
+    int operator()(int x) const { return count += (x + 1); }
+
+};
+
+struct A_int_2
+{
+    A_int_2() {}
+    int operator()(int x, int y) { return count += (x + y); }
+    int operator()(int x, int y) const { return count += (x + y + 1); }
+};
+
+struct A_int_3
+{
+    A_int_3() {}
+    int operator()(int x, int y, int z) { return count += (x + y + z); }
+    int operator()(int x, int y, int z) const { return count += (x + y + z + 1); }
+};
+
+
+template <class Tuple>
+void test_void_0()
+{
+    count = 0;
+    // function
+    {
+        Tuple t{};
+        ex::apply(f_void_0, t);
+        assert(count == 1);
+    }
+    count = 0;
+    // function pointer
+    {
+        Tuple t{};
+        auto fp = &f_void_0;
+        ex::apply(fp, t);
+        assert(count == 1);
+    }
+    count = 0;
+    // functor
+    {
+        Tuple t{};
+        A_void_0 a;
+        ex::apply(a, t);
+        assert(count == 1);
+    }
+    count = 0;
+    // const functor
+    {
+        Tuple t{};
+        A_void_0 const a;
+        ex::apply(a, t);
+        assert(count == 2);
+    }
+}
+
+template <class Tuple>
+void test_void_1()
+{
+    count = 0;
+    // function
+    {
+        Tuple t{1};
+        ex::apply(f_void_1, t);
+        assert(count == 1);
+    }
+    count = 0;
+    // function pointer
+    {
+        Tuple t{2};
+        void (*fp)(int) = f_void_1;
+        ex::apply(fp, t);
+        assert(count == 2);
+    }
+    count = 0;
+    // functor
+    {
+        Tuple t{3};
+        A_void_1 fn;
+        ex::apply(fn, t);
+        assert(count == 3);
+    }
+    count = 0;
+    // const functor
+    {
+        Tuple t{4};
+        A_void_1 const a;
+        ex::apply(a, t);
+        assert(count == 5);
+    }
+}
+
+template <class Tuple>
+void test_void_2()
+{
+    count = 0;
+    // function
+    {
+        Tuple t{1, 2};
+        ex::apply(f_void_2, t);
+        assert(count == 3);
+    }
+    count = 0;
+    // function pointer
+    {
+        Tuple t{2, 3};
+        auto fp = &f_void_2;
+        ex::apply(fp, t);
+        assert(count == 5);
+    }
+    count = 0;
+    // functor
+    {
+        Tuple t{3, 4};
+        A_void_2 a;
+        ex::apply(a, t);
+        assert(count == 7);
+    }
+    count = 0;
+    // const functor
+    {
+        Tuple t{4, 5};
+        A_void_2 const a;
+        ex::apply(a, t);
+        assert(count == 10);
+    }
+}
+
+template <class Tuple>
+void test_void_3()
+{
+    count = 0;
+    // function
+    {
+        Tuple t{1, 2, 3};
+        ex::apply(f_void_3, t);
+        assert(count == 6);
+    }
+    count = 0;
+    // function pointer
+    {
+        Tuple t{2, 3, 4};
+        auto fp = &f_void_3;
+        ex::apply(fp, t);
+        assert(count == 9);
+    }
+    count = 0;
+    // functor
+    {
+        Tuple t{3, 4, 5};
+        A_void_3 a;
+        ex::apply(a, t);
+        assert(count == 12);
+    }
+    count = 0;
+    // const functor
+    {
+        Tuple t{4, 5, 6};
+        A_void_3 const a;
+        ex::apply(a, t);
+        assert(count == 16);
+    }
+}
+
+
+
+template <class Tuple>
+void test_int_0()
+{
+    count = 0;
+    // function
+    {
+        Tuple t{};
+        assert(1 == ex::apply(f_int_0, t));
+        assert(count == 1);
+    }
+    count = 0;
+    // function pointer
+    {
+        Tuple t{};
+        auto fp = &f_int_0;
+        assert(1 == ex::apply(fp, t));
+        assert(count == 1);
+    }
+    count = 0;
+    // functor
+    {
+        Tuple t{};
+        A_int_0 a;
+        assert(1 == ex::apply(a, t));
+        assert(count == 1);
+    }
+    count = 0;
+    // const functor
+    {
+        Tuple t{};
+        A_int_0 const a;
+        assert(2 == ex::apply(a, t));
+        assert(count == 2);
+    }
+}
+
+template <class Tuple>
+void test_int_1()
+{
+    count = 0;
+    // function
+    {
+        Tuple t{1};
+        assert(1 == ex::apply(f_int_1, t));
+        assert(count == 1);
+    }
+    count = 0;
+    // function pointer
+    {
+        Tuple t{2};
+        int (*fp)(int) = f_int_1;
+        assert(2 == ex::apply(fp, t));
+        assert(count == 2);
+    }
+    count = 0;
+    // functor
+    {
+        Tuple t{3};
+        A_int_1 fn;
+        assert(3 == ex::apply(fn, t));
+        assert(count == 3);
+    }
+    count = 0;
+    // const functor
+    {
+        Tuple t{4};
+        A_int_1 const a;
+        assert(5 == ex::apply(a, t));
+        assert(count == 5);
+    }
+}
+
+template <class Tuple>
+void test_int_2()
+{
+    count = 0;
+    // function
+    {
+        Tuple t{1, 2};
+        assert(3 == ex::apply(f_int_2, t));
+        assert(count == 3);
+    }
+    count = 0;
+    // function pointer
+    {
+        Tuple t{2, 3};
+        auto fp = &f_int_2;
+        assert(5 == ex::apply(fp, t));
+        assert(count == 5);
+    }
+    count = 0;
+    // functor
+    {
+        Tuple t{3, 4};
+        A_int_2 a;
+        assert(7 == ex::apply(a, t));
+        assert(count == 7);
+    }
+    count = 0;
+    // const functor
+    {
+        Tuple t{4, 5};
+        A_int_2 const a;
+        assert(10 == ex::apply(a, t));
+        assert(count == 10);
+    }
+}
+
+template <class Tuple>
+void test_int_3()
+{
+    count = 0;
+    // function
+    {
+        Tuple t{1, 2, 3};
+        assert(6 == ex::apply(f_int_3, t));
+        assert(count == 6);
+    }
+    count = 0;
+    // function pointer
+    {
+        Tuple t{2, 3, 4};
+        auto fp = &f_int_3;
+        assert(9 == ex::apply(fp, t));
+        assert(count == 9);
+    }
+    count = 0;
+    // functor
+    {
+        Tuple t{3, 4, 5};
+        A_int_3 a;
+        assert(12 == ex::apply(a, t));
+        assert(count == 12);
+    }
+    count = 0;
+    // const functor
+    {
+        Tuple t{4, 5, 6};
+        A_int_3 const a;
+        assert(16 == ex::apply(a, t));
+        assert(count == 16);
+    }
+}
+
+template <class Tuple>
+void test_0()
+{
+    test_void_0<Tuple>();
+    test_int_0<Tuple>();
+}
+
+template <class Tuple>
+void test_1()
+{
+    test_void_1<Tuple>();
+    test_int_1<Tuple>();
+}
+
+template <class Tuple>
+void test_2()
+{
+    test_void_2<Tuple>();
+    test_int_2<Tuple>();
+}
+
+template <class Tuple>
+void test_3()
+{
+    test_void_3<Tuple>();
+    test_int_3<Tuple>();
+}
+
+int main()
+{
+    test_0<std::tuple<>>();
+
+    test_1<std::tuple<int>>();
+    test_1<std::array<int, 1>>();
+
+    test_2<std::tuple<int, int>>();
+    test_2<std::pair<int, int>>();
+    test_2<std::array<int, 2>>();
+
+    test_3<std::tuple<int, int, int>>();
+    test_3<std::array<int, 3>>();
+}
diff --git a/test/std/experimental/utilities/tuple/tuple_size_v.fail.cpp b/test/std/experimental/utilities/tuple/tuple_size_v.fail.cpp
new file mode 100644
index 0000000..a25b18c
--- /dev/null
+++ b/test/std/experimental/utilities/tuple/tuple_size_v.fail.cpp
@@ -0,0 +1,25 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/tuple>
+
+// template <class T> constexpr size_t tuple_size_v = tuple_size<T>::value;
+
+// Test with reference
+
+#include <experimental/tuple>
+
+namespace ex = std::experimental;
+
+int main()
+{
+    auto x = ex::tuple_size_v<std::tuple<> &>;
+}
diff --git a/test/std/experimental/utilities/tuple/tuple_size_v.pass.cpp b/test/std/experimental/utilities/tuple/tuple_size_v.pass.cpp
new file mode 100644
index 0000000..d7a5aa6
--- /dev/null
+++ b/test/std/experimental/utilities/tuple/tuple_size_v.pass.cpp
@@ -0,0 +1,45 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/tuple>
+
+// template <class T> constexpr size_t tuple_size_v = tuple_size<T>::value;
+
+#include <experimental/tuple>
+#include <utility>
+#include <array>
+
+namespace ex = std::experimental;
+
+template <class Tuple, int Expect>
+void test()
+{
+    static_assert(ex::tuple_size_v<Tuple> == Expect, "");
+    static_assert(ex::tuple_size_v<Tuple> == std::tuple_size<Tuple>::value, "");
+    static_assert(ex::tuple_size_v<Tuple const> == std::tuple_size<Tuple>::value, "");
+    static_assert(ex::tuple_size_v<Tuple volatile> == std::tuple_size<Tuple>::value, "");
+    static_assert(ex::tuple_size_v<Tuple const volatile> == std::tuple_size<Tuple>::value, "");
+}
+
+int main()
+{
+    test<std::tuple<>, 0>();
+
+    test<std::tuple<int>, 1>();
+    test<std::array<int, 1>, 1>();
+
+    test<std::tuple<int, int>, 2>();
+    test<std::pair<int, int>, 2>();
+    test<std::array<int, 2>, 2>();
+
+    test<std::tuple<int, int, int>, 3>();
+    test<std::array<int, 3>, 3>();
+}
diff --git a/test/std/experimental/utilities/tuple/tuple_size_v_2.fail.cpp b/test/std/experimental/utilities/tuple/tuple_size_v_2.fail.cpp
new file mode 100644
index 0000000..a95ac49
--- /dev/null
+++ b/test/std/experimental/utilities/tuple/tuple_size_v_2.fail.cpp
@@ -0,0 +1,25 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/tuple>
+
+// template <class T> constexpr size_t tuple_size_v = tuple_size<T>::value;
+
+// Test with non tuple type
+
+#include <experimental/tuple>
+
+namespace ex = std::experimental;
+
+int main()
+{
+    auto x = ex::tuple_size_v<int>;
+}
diff --git a/test/std/experimental/utilities/tuple/tuple_size_v_3.fail.cpp b/test/std/experimental/utilities/tuple/tuple_size_v_3.fail.cpp
new file mode 100644
index 0000000..7c2f0cc
--- /dev/null
+++ b/test/std/experimental/utilities/tuple/tuple_size_v_3.fail.cpp
@@ -0,0 +1,25 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11
+
+// <experimental/tuple>
+
+// template <class T> constexpr size_t tuple_size_v = tuple_size<T>::value;
+
+// Test with pointer
+
+#include <experimental/tuple>
+
+namespace ex = std::experimental;
+
+int main()
+{
+    auto x = ex::tuple_size_v<std::tuple<>*>;
+}
diff --git a/test/std/input.output/file.streams/c.files/cstdio.pass.cpp b/test/std/input.output/file.streams/c.files/cstdio.pass.cpp
index 1a60dd6..ec4ad8a 100644
--- a/test/std/input.output/file.streams/c.files/cstdio.pass.cpp
+++ b/test/std/input.output/file.streams/c.files/cstdio.pass.cpp
@@ -88,27 +88,17 @@
     std::size_t s = 0;
     char* cp = 0;
     std::va_list va;
-    static_assert((std::is_same<decltype(std::remove("")), int>::value), "");
-    static_assert((std::is_same<decltype(std::rename("","")), int>::value), "");
-    static_assert((std::is_same<decltype(std::tmpfile()), std::FILE*>::value), "");
-    static_assert((std::is_same<decltype(std::tmpnam(cp)), char*>::value), "");
     static_assert((std::is_same<decltype(std::fclose(fp)), int>::value), "");
     static_assert((std::is_same<decltype(std::fflush(fp)), int>::value), "");
-    static_assert((std::is_same<decltype(std::fopen("", "")), std::FILE*>::value), "");
-    static_assert((std::is_same<decltype(std::freopen("", "", fp)), std::FILE*>::value), "");
     static_assert((std::is_same<decltype(std::setbuf(fp,cp)), void>::value), "");
     static_assert((std::is_same<decltype(std::vfprintf(fp,"",va)), int>::value), "");
     static_assert((std::is_same<decltype(std::fprintf(fp," ")), int>::value), "");
     static_assert((std::is_same<decltype(std::fscanf(fp,"")), int>::value), "");
-    static_assert((std::is_same<decltype(std::printf(" ")), int>::value), "");
-    static_assert((std::is_same<decltype(std::scanf(" ")), int>::value), "");
     static_assert((std::is_same<decltype(std::snprintf(cp,0," ")), int>::value), "");
     static_assert((std::is_same<decltype(std::sprintf(cp," ")), int>::value), "");
     static_assert((std::is_same<decltype(std::sscanf("","")), int>::value), "");
     static_assert((std::is_same<decltype(std::vfprintf(fp,"",va)), int>::value), "");
     static_assert((std::is_same<decltype(std::vfscanf(fp,"",va)), int>::value), "");
-    static_assert((std::is_same<decltype(std::vprintf(" ",va)), int>::value), "");
-    static_assert((std::is_same<decltype(std::vscanf("",va)), int>::value), "");
     static_assert((std::is_same<decltype(std::vsnprintf(cp,0," ",va)), int>::value), "");
     static_assert((std::is_same<decltype(std::vsprintf(cp," ",va)), int>::value), "");
     static_assert((std::is_same<decltype(std::vsscanf("","",va)), int>::value), "");
@@ -117,13 +107,7 @@
     static_assert((std::is_same<decltype(std::fputc(0,fp)), int>::value), "");
     static_assert((std::is_same<decltype(std::fputs("",fp)), int>::value), "");
     static_assert((std::is_same<decltype(std::getc(fp)), int>::value), "");
-    static_assert((std::is_same<decltype(std::getchar()), int>::value), "");
-#if _LIBCPP_STD_VER <= 11
-    static_assert((std::is_same<decltype(std::gets(cp)), char*>::value), "");
-#endif
     static_assert((std::is_same<decltype(std::putc(0,fp)), int>::value), "");
-    static_assert((std::is_same<decltype(std::putchar(0)), int>::value), "");
-    static_assert((std::is_same<decltype(std::puts("")), int>::value), "");
     static_assert((std::is_same<decltype(std::ungetc(0,fp)), int>::value), "");
     static_assert((std::is_same<decltype(std::fread((void*)0,0,0,fp)), std::size_t>::value), "");
     static_assert((std::is_same<decltype(std::fwrite((const void*)0,0,0,fp)), std::size_t>::value), "");
@@ -136,4 +120,29 @@
     static_assert((std::is_same<decltype(std::feof(fp)), int>::value), "");
     static_assert((std::is_same<decltype(std::ferror(fp)), int>::value), "");
     static_assert((std::is_same<decltype(std::perror("")), void>::value), "");
+
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
+    static_assert((std::is_same<decltype(std::fopen("", "")), std::FILE*>::value), "");
+    static_assert((std::is_same<decltype(std::freopen("", "", fp)), std::FILE*>::value), "");
+    static_assert((std::is_same<decltype(std::remove("")), int>::value), "");
+    static_assert((std::is_same<decltype(std::rename("","")), int>::value), "");
+    static_assert((std::is_same<decltype(std::tmpfile()), std::FILE*>::value), "");
+    static_assert((std::is_same<decltype(std::tmpnam(cp)), char*>::value), "");
+#endif
+
+#ifndef _LIBCPP_HAS_NO_STDIN
+    static_assert((std::is_same<decltype(std::getchar()), int>::value), "");
+#if _LIBCPP_STD_VER <= 11
+    static_assert((std::is_same<decltype(std::gets(cp)), char*>::value), "");
+#endif
+    static_assert((std::is_same<decltype(std::scanf(" ")), int>::value), "");
+    static_assert((std::is_same<decltype(std::vscanf("",va)), int>::value), "");
+#endif
+
+#ifndef _LIBCPP_HAS_NO_STDOUT
+    static_assert((std::is_same<decltype(std::printf(" ")), int>::value), "");
+    static_assert((std::is_same<decltype(std::putchar(0)), int>::value), "");
+    static_assert((std::is_same<decltype(std::puts("")), int>::value), "");
+    static_assert((std::is_same<decltype(std::vprintf(" ",va)), int>::value), "");
+#endif
 }
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/input.output/file.streams/c.files/no.global.filesystem.namespace/fopen.fail.cpp
similarity index 71%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/std/input.output/file.streams/c.files/no.global.filesystem.namespace/fopen.fail.cpp
index b58f5c5..4d83296 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/input.output/file.streams/c.files/no.global.filesystem.namespace/fopen.fail.cpp
@@ -7,6 +7,9 @@
 //
 //===----------------------------------------------------------------------===//
 
-int main()
-{
+#include <cstdio>
+
+int main() {
+    // fopen is not available on systems without a global filesystem namespace.
+    std::fopen("", "");
 }
diff --git a/test/std/input.output/file.streams/c.files/no.global.filesystem.namespace/lit.local.cfg b/test/std/input.output/file.streams/c.files/no.global.filesystem.namespace/lit.local.cfg
new file mode 100644
index 0000000..4ea6709
--- /dev/null
+++ b/test/std/input.output/file.streams/c.files/no.global.filesystem.namespace/lit.local.cfg
@@ -0,0 +1,2 @@
+if 'libcpp-has-no-global-filesystem-namespace' not in config.available_features:
+    config.unsupported = True
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/input.output/file.streams/c.files/no.global.filesystem.namespace/rename.fail.cpp
similarity index 71%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/std/input.output/file.streams/c.files/no.global.filesystem.namespace/rename.fail.cpp
index b58f5c5..deca9bf 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/input.output/file.streams/c.files/no.global.filesystem.namespace/rename.fail.cpp
@@ -7,6 +7,9 @@
 //
 //===----------------------------------------------------------------------===//
 
-int main()
-{
+#include <cstdio>
+
+int main() {
+    // rename is not available on systems without a global filesystem namespace.
+    std::rename("", "");
 }
diff --git a/test/std/input.output/file.streams/fstreams/lit.local.cfg b/test/std/input.output/file.streams/fstreams/lit.local.cfg
new file mode 100644
index 0000000..25ac02b
--- /dev/null
+++ b/test/std/input.output/file.streams/fstreams/lit.local.cfg
@@ -0,0 +1,2 @@
+if 'libcpp-has-no-global-filesystem-namespace' in config.available_features:
+    config.unsupported = True
diff --git a/test/std/input.output/iostream.format/output.streams/ostream.formatted/ostream.inserters.arithmetic/pointer.pass.cpp b/test/std/input.output/iostream.format/output.streams/ostream.formatted/ostream.inserters.arithmetic/pointer.pass.cpp
index 114bba9..b74d99a 100644
--- a/test/std/input.output/iostream.format/output.streams/ostream.formatted/ostream.inserters.arithmetic/pointer.pass.cpp
+++ b/test/std/input.output/iostream.format/output.streams/ostream.formatted/ostream.inserters.arithmetic/pointer.pass.cpp
@@ -59,18 +59,27 @@
         assert(os.fail());
     }
     {
-        testbuf<char> sb;
-        std::ostream os(&sb);
-        const void* n = 0;
-        os << n;
-        assert(os.good());
-        // %p is implementation defined.
-        // On some platforms (Windows), it's a hex number without
-        // any leading 0x like prefix.
-        // In that format, we assume a null pointer will yield 2 '0' hex digits
-        // for each 8 bits of address space.
-        assert(sb.str() == "0x0" || sb.str() == "(nil)" ||
-                                  sb.str() == std::string(sizeof(void*)*2,'0'));
+        testbuf<char> sb1;
+        std::ostream os1(&sb1);
+        int n1;
+        os1 << &n1;
+        assert(os1.good());
+        std::string s1(sb1.str());
+
+        testbuf<char> sb2;
+        std::ostream os2(&sb2);
+        int n2;
+        os2 << &n2;
+        assert(os2.good());
+        std::string s2(sb2.str());
+
+        // %p is implementation defined. Instead of validating the
+        // output, at least ensure that it does not generate an empty
+        // string. Also make sure that given two distinct addresses, the
+        // output of %p is different.
+        assert(!s1.empty());
+        assert(!s2.empty());
+        assert(s1 != s2);
     }
     {
         testbuf<char> sb;
diff --git a/test/std/input.output/iostream.format/output.streams/ostream.seeks/seekp.pass.cpp b/test/std/input.output/iostream.format/output.streams/ostream.seeks/seekp.pass.cpp
index e09627b..ec3fe48 100644
--- a/test/std/input.output/iostream.format/output.streams/ostream.seeks/seekp.pass.cpp
+++ b/test/std/input.output/iostream.format/output.streams/ostream.seeks/seekp.pass.cpp
@@ -40,11 +40,13 @@
 int main()
 {
     {
+        seekpos_called = 0;
         std::ostream os((std::streambuf*)0);
         assert(&os.seekp(5) == &os);
         assert(seekpos_called == 0);
     }
     {
+        seekpos_called = 0;
         testbuf<char> sb;
         std::ostream os(&sb);
         assert(&os.seekp(10) == &os);
@@ -54,4 +56,13 @@
         assert(seekpos_called == 2);
         assert(os.fail());
     }
+    { // See https://llvm.org/bugs/show_bug.cgi?id=21361
+        seekpos_called = 0;
+        testbuf<char> sb;
+        std::ostream os(&sb);
+        os.setstate(std::ios_base::eofbit);
+        assert(&os.seekp(10) == &os);
+        assert(seekpos_called == 1);
+        assert(os.rdstate() == std::ios_base::eofbit);
+    }
 }
diff --git a/test/std/input.output/iostream.format/output.streams/ostream.seeks/seekp2.pass.cpp b/test/std/input.output/iostream.format/output.streams/ostream.seeks/seekp2.pass.cpp
index 69b26f3..ebfd24a 100644
--- a/test/std/input.output/iostream.format/output.streams/ostream.seeks/seekp2.pass.cpp
+++ b/test/std/input.output/iostream.format/output.streams/ostream.seeks/seekp2.pass.cpp
@@ -42,11 +42,13 @@
 int main()
 {
     {
+        seekoff_called = 0;
         std::ostream os((std::streambuf*)0);
         assert(&os.seekp(5, std::ios_base::beg) == &os);
         assert(seekoff_called == 0);
     }
     {
+        seekoff_called = 0;
         testbuf<char> sb;
         std::ostream os(&sb);
         assert(&os.seekp(10, std::ios_base::beg) == &os);
@@ -56,4 +58,13 @@
         assert(seekoff_called == 2);
         assert(os.fail());
     }
+    { // See https://llvm.org/bugs/show_bug.cgi?id=21361
+        seekoff_called = 0;
+        testbuf<char> sb;
+        std::ostream os(&sb);
+        os.setstate(std::ios_base::eofbit);
+        assert(&os.seekp(10, std::ios_base::beg) == &os);
+        assert(seekoff_called == 1);
+        assert(os.rdstate() == std::ios_base::eofbit);
+    }
 }
diff --git a/test/std/input.output/iostream.objects/narrow.stream.objects/cerr.pass.cpp b/test/std/input.output/iostream.objects/narrow.stream.objects/cerr.pass.cpp
index 9206d17..cdf53f8 100644
--- a/test/std/input.output/iostream.objects/narrow.stream.objects/cerr.pass.cpp
+++ b/test/std/input.output/iostream.objects/narrow.stream.objects/cerr.pass.cpp
@@ -19,7 +19,11 @@
 #if 0
     std::cerr << "Hello World!\n";
 #else
+#ifdef _LIBCPP_HAS_NO_STDOUT
+    assert(std::cerr.tie() == NULL);
+#else
     assert(std::cerr.tie() == &std::cout);
+#endif
     assert(std::cerr.flags() & std::ios_base::unitbuf);
 #endif  // 0
 }
diff --git a/test/std/input.output/iostream.objects/narrow.stream.objects/cin.pass.cpp b/test/std/input.output/iostream.objects/narrow.stream.objects/cin.pass.cpp
index 3481598..1ce04ff 100644
--- a/test/std/input.output/iostream.objects/narrow.stream.objects/cin.pass.cpp
+++ b/test/std/input.output/iostream.objects/narrow.stream.objects/cin.pass.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// XFAIL: libcpp-has-no-stdin
+
 // <iostream>
 
 // istream cin;
@@ -23,6 +25,10 @@
     std::cin >> i;
     std::cout << "The number is : " << i << '\n';
 #else  // 0
+#ifdef _LIBCPP_HAS_NO_STDOUT
+    assert(std::cin.tie() == NULL);
+#else
     assert(std::cin.tie() == &std::cout);
 #endif
+#endif
 }
diff --git a/test/std/input.output/iostream.objects/narrow.stream.objects/cout.pass.cpp b/test/std/input.output/iostream.objects/narrow.stream.objects/cout.pass.cpp
index 6000ae2..e5887e1 100644
--- a/test/std/input.output/iostream.objects/narrow.stream.objects/cout.pass.cpp
+++ b/test/std/input.output/iostream.objects/narrow.stream.objects/cout.pass.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// XFAIL: libcpp-has-no-stdout
+
 // <iostream>
 
 // istream cout;
diff --git a/test/std/input.output/iostream.objects/wide.stream.objects/wcerr.pass.cpp b/test/std/input.output/iostream.objects/wide.stream.objects/wcerr.pass.cpp
index 19a1dcd..b050781 100644
--- a/test/std/input.output/iostream.objects/wide.stream.objects/wcerr.pass.cpp
+++ b/test/std/input.output/iostream.objects/wide.stream.objects/wcerr.pass.cpp
@@ -19,7 +19,11 @@
 #if 0
     std::wcerr << L"Hello World!\n";
 #else
+#ifdef _LIBCPP_HAS_NO_STDOUT
+    assert(std::wcerr.tie() == NULL);
+#else
     assert(std::wcerr.tie() == &std::wcout);
+#endif
     assert(std::wcerr.flags() & std::ios_base::unitbuf);
 #endif  // 0
 }
diff --git a/test/std/input.output/iostream.objects/wide.stream.objects/wcin.pass.cpp b/test/std/input.output/iostream.objects/wide.stream.objects/wcin.pass.cpp
index 90a5668..6abd6af 100644
--- a/test/std/input.output/iostream.objects/wide.stream.objects/wcin.pass.cpp
+++ b/test/std/input.output/iostream.objects/wide.stream.objects/wcin.pass.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// XFAIL: libcpp-has-no-stdin
+
 // <iostream>
 
 // istream wcin;
@@ -23,6 +25,10 @@
     std::wcin >> i;
     std::wcout << L"The number is : " << i << L'\n';
 #else  // 0
+#ifdef _LIBCPP_HAS_NO_STDOUT
+    assert(std::wcin.tie() == NULL);
+#else
     assert(std::wcin.tie() == &std::wcout);
 #endif
+#endif
 }
diff --git a/test/std/input.output/iostream.objects/wide.stream.objects/wcout.pass.cpp b/test/std/input.output/iostream.objects/wide.stream.objects/wcout.pass.cpp
index 7a546aa..6543e0a 100644
--- a/test/std/input.output/iostream.objects/wide.stream.objects/wcout.pass.cpp
+++ b/test/std/input.output/iostream.objects/wide.stream.objects/wcout.pass.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// XFAIL: libcpp-has-no-stdout
+
 // <iostream>
 
 // istream wcout;
diff --git a/test/std/input.output/stream.buffers/streambuf/streambuf.members/streambuf.locales/locales.pass.cpp b/test/std/input.output/stream.buffers/streambuf/streambuf.members/streambuf.locales/locales.pass.cpp
index deb2dc7..95dd2db 100644
--- a/test/std/input.output/stream.buffers/streambuf/streambuf.members/streambuf.locales/locales.pass.cpp
+++ b/test/std/input.output/stream.buffers/streambuf/streambuf.members/streambuf.locales/locales.pass.cpp
@@ -45,7 +45,8 @@
     {
         test<char> t;
         assert(t.getloc().name() == LOCALE_en_US_UTF_8);
-        assert(t.pubimbue(std::locale(LOCALE_fr_FR_UTF_8)).name() == "en_US.UTF-8");
+        assert(t.pubimbue(std::locale(LOCALE_fr_FR_UTF_8)).name() ==
+               LOCALE_en_US_UTF_8);
         assert(t.getloc().name() == LOCALE_fr_FR_UTF_8);
     }
 }
diff --git a/test/std/input.output/string.streams/stringbuf/stringbuf.virtuals/overflow.pass.cpp b/test/std/input.output/string.streams/stringbuf/stringbuf.virtuals/overflow.pass.cpp
index 3abf942..67363b5 100644
--- a/test/std/input.output/string.streams/stringbuf/stringbuf.virtuals/overflow.pass.cpp
+++ b/test/std/input.output/string.streams/stringbuf/stringbuf.virtuals/overflow.pass.cpp
@@ -29,7 +29,7 @@
         : base(str, which) {}
 
     typename base::int_type
-        overflow(typename base::int_type c = base::type_traits::eof())
+        overflow(typename base::int_type c = base::traits_type::eof())
         {++overflow_called; return base::overflow(c);}
 
     void pbump(int n) {base::pbump(n);}
@@ -37,6 +37,10 @@
 
 int main()
 {
+    {  // sanity check
+    testbuf<char> tb("");;
+    tb.overflow();
+    }
     {
         testbuf<char> sb("abc");
         assert(sb.sputc('1') == '1');
diff --git a/test/std/input.output/string.streams/stringbuf/stringbuf.virtuals/pbackfail.pass.cpp b/test/std/input.output/string.streams/stringbuf/stringbuf.virtuals/pbackfail.pass.cpp
index 4af0e63..a050900 100644
--- a/test/std/input.output/string.streams/stringbuf/stringbuf.virtuals/pbackfail.pass.cpp
+++ b/test/std/input.output/string.streams/stringbuf/stringbuf.virtuals/pbackfail.pass.cpp
@@ -27,7 +27,7 @@
         : base(str, which) {}
 
     typename base::int_type
-        pbackfail(typename base::int_type c = base::type_traits::eof())
+        pbackfail(typename base::int_type c = base::traits_type::eof())
         {return base::pbackfail(c);}
 
     void pbump(int n) {base::pbump(n);}
@@ -35,6 +35,10 @@
 
 int main()
 {
+    {  // sanity check
+    testbuf<char> tb("");;
+    tb.pbackfail();
+    }
     {
         testbuf<char> sb("123", std::ios_base::in);
         assert(sb.sgetc() == '1');
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/no-variadics.pass.cpp b/test/std/iterators/stream.iterators/istream.iterator/istream.iterator.cons/default.fail.cpp
similarity index 60%
rename from test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/no-variadics.pass.cpp
rename to test/std/iterators/stream.iterators/istream.iterator/istream.iterator.cons/default.fail.cpp
index 7099c45..5e6cc54 100644
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/no-variadics.pass.cpp
+++ b/test/std/iterators/stream.iterators/istream.iterator/istream.iterator.cons/default.fail.cpp
@@ -7,18 +7,24 @@
 //
 //===----------------------------------------------------------------------===//
 
-// <functional>
+// <iterator>
 
-// class function<R()>
+// class istream_iterator
 
-// template<class F> function(F);
+// constexpr istream_iterator();
 
-#define _LIBCPP_HAS_NO_VARIADICS
-#include <functional>
+#include <iterator>
 #include <cassert>
 
+struct S { S(); }; // not constexpr 
+
 int main()
 {
-    std::function<void()> f(static_cast<void(*)()>(0));
-    assert(!f);
+#if __cplusplus >= 201103L
+    {
+    constexpr std::istream_iterator<S> it;
+    }
+#else
+#error "C++11 only test"
+#endif
 }
diff --git a/test/std/iterators/stream.iterators/istream.iterator/istream.iterator.cons/default.pass.cpp b/test/std/iterators/stream.iterators/istream.iterator/istream.iterator.cons/default.pass.cpp
index f6c3dba..bea07ec 100644
--- a/test/std/iterators/stream.iterators/istream.iterator/istream.iterator.cons/default.pass.cpp
+++ b/test/std/iterators/stream.iterators/istream.iterator/istream.iterator.cons/default.pass.cpp
@@ -11,13 +11,20 @@
 
 // class istream_iterator
 
-// istream_iterator();
+// constexpr istream_iterator();
 
 #include <iterator>
 #include <cassert>
 
 int main()
 {
-    std::istream_iterator<int> i;
-    assert(i == std::istream_iterator<int>());
+    {
+    typedef std::istream_iterator<int> T;
+    T it;
+    assert(it == T());
+#if __cplusplus >= 201103L
+    constexpr T it2;
+#endif
+    }
+    
 }
diff --git a/test/std/iterators/stream.iterators/istream.iterator/types.pass.cpp b/test/std/iterators/stream.iterators/istream.iterator/types.pass.cpp
index be55c97..85a70a0 100644
--- a/test/std/iterators/stream.iterators/istream.iterator/types.pass.cpp
+++ b/test/std/iterators/stream.iterators/istream.iterator/types.pass.cpp
@@ -19,9 +19,14 @@
 //     typedef traits traits_type;
 //     typedef basic_istream<charT,traits> istream_type;
 //     ...
+//
+//   If T is a literal type, then the default constructor shall be a constexpr constructor.
+//   If T is a literal type, then this constructor shall be a trivial copy constructor.
+//   If T is a literal type, then this destructor shall be a trivial destructor.
 
 #include <iterator>
 #include <type_traits>
+#include <string>
 
 int main()
 {
@@ -32,6 +37,9 @@
     static_assert((std::is_same<I1::char_type, char>::value), "");
     static_assert((std::is_same<I1::traits_type, std::char_traits<char> >::value), "");
     static_assert((std::is_same<I1::istream_type, std::istream>::value), "");
+    static_assert( std::is_trivially_copy_constructible<I1>::value, "");
+    static_assert( std::is_trivially_destructible<I1>::value, "");
+
     typedef std::istream_iterator<unsigned, wchar_t> I2;
     static_assert((std::is_convertible<I2,
         std::iterator<std::input_iterator_tag, unsigned, std::ptrdiff_t,
@@ -39,4 +47,10 @@
     static_assert((std::is_same<I2::char_type, wchar_t>::value), "");
     static_assert((std::is_same<I2::traits_type, std::char_traits<wchar_t> >::value), "");
     static_assert((std::is_same<I2::istream_type, std::wistream>::value), "");
+    static_assert( std::is_trivially_copy_constructible<I2>::value, "");
+    static_assert( std::is_trivially_destructible<I2>::value, "");
+
+    typedef std::istream_iterator<std::string> I3;
+    static_assert(!std::is_trivially_copy_constructible<I3>::value, "");
+    static_assert(!std::is_trivially_destructible<I3>::value, "");
 }
diff --git a/test/std/iterators/stream.iterators/istreambuf.iterator/istreambuf.iterator.cons/default.pass.cpp b/test/std/iterators/stream.iterators/istreambuf.iterator/istreambuf.iterator.cons/default.pass.cpp
index d1eabba..46ac390 100644
--- a/test/std/iterators/stream.iterators/istreambuf.iterator/istreambuf.iterator.cons/default.pass.cpp
+++ b/test/std/iterators/stream.iterators/istreambuf.iterator/istreambuf.iterator.cons/default.pass.cpp
@@ -10,8 +10,11 @@
 // <iterator>
 
 // istreambuf_iterator
-
+//
 // istreambuf_iterator() throw();
+//
+// All specializations of istreambuf_iterator shall have a trivial copy constructor, 
+//    a constexpr default constructor and a trivial destructor.
 
 #include <iterator>
 #include <sstream>
@@ -20,11 +23,19 @@
 int main()
 {
     {
-        std::istreambuf_iterator<char> i;
-        assert(i == std::istreambuf_iterator<char>());
+        typedef std::istreambuf_iterator<char> T;
+        T it;
+        assert(it == T());
+#if __cplusplus >= 201103L
+        constexpr T it2;
+#endif
     }
     {
-        std::istreambuf_iterator<wchar_t> i;
-        assert(i == std::istreambuf_iterator<wchar_t>());
+        typedef std::istreambuf_iterator<wchar_t> T;
+        T it;
+        assert(it == T());
+#if __cplusplus >= 201103L
+        constexpr T it2;
+#endif
     }
 }
diff --git a/test/std/iterators/stream.iterators/istreambuf.iterator/types.pass.cpp b/test/std/iterators/stream.iterators/istreambuf.iterator/types.pass.cpp
index 75894a8..2ad927c 100644
--- a/test/std/iterators/stream.iterators/istreambuf.iterator/types.pass.cpp
+++ b/test/std/iterators/stream.iterators/istreambuf.iterator/types.pass.cpp
@@ -22,6 +22,9 @@
 //     typedef basic_streambuf<charT,traits> streambuf_type;
 //     typedef basic_istream<charT,traits>   istream_type;
 //     ...
+//
+// All specializations of istreambuf_iterator shall have a trivial copy constructor, 
+//    a constexpr default constructor and a trivial destructor.
 
 #include <iterator>
 #include <string>
@@ -38,6 +41,9 @@
     static_assert((std::is_same<I1::int_type, I1::traits_type::int_type>::value), "");
     static_assert((std::is_same<I1::streambuf_type, std::streambuf>::value), "");
     static_assert((std::is_same<I1::istream_type, std::istream>::value), "");
+    static_assert((std::is_nothrow_default_constructible<I1>::value), "" );
+    static_assert((std::is_trivially_copy_constructible<I1>::value), "" );
+    static_assert((std::is_trivially_destructible<I1>::value), "" );
 
     typedef std::istreambuf_iterator<wchar_t> I2;
     static_assert((std::is_convertible<I2,
@@ -48,4 +54,7 @@
     static_assert((std::is_same<I2::int_type, I2::traits_type::int_type>::value), "");
     static_assert((std::is_same<I2::streambuf_type, std::wstreambuf>::value), "");
     static_assert((std::is_same<I2::istream_type, std::wistream>::value), "");
+    static_assert((std::is_nothrow_default_constructible<I2>::value), "" );
+    static_assert((std::is_trivially_copy_constructible<I2>::value), "" );
+    static_assert((std::is_trivially_destructible<I2>::value), "" );
 }
diff --git a/test/std/language.support/support.dynamic/alloc.errors/new.handler/new_handler.pass.cpp b/test/std/language.support/support.dynamic/alloc.errors/new.handler/new_handler.pass.cpp
index 6b799a3..0d4524c 100644
--- a/test/std/language.support/support.dynamic/alloc.errors/new.handler/new_handler.pass.cpp
+++ b/test/std/language.support/support.dynamic/alloc.errors/new.handler/new_handler.pass.cpp
@@ -10,10 +10,14 @@
 // test new_handler
 
 #include <new>
+#include <type_traits>
+#include <cassert>
 
 void f() {}
 
 int main()
 {
+    static_assert((std::is_same<std::new_handler, void(*)()>::value), "");
     std::new_handler p = f;
+    assert(p == &f);
 }
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array.pass.cpp
index 052d88f..a1a3035 100644
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array.pass.cpp
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array.pass.cpp
@@ -9,7 +9,7 @@
 
 // test operator new[]
 // NOTE: asan and msan will not call the new handler.
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 
 #include <new>
@@ -38,7 +38,8 @@
     std::set_new_handler(new_handler);
     try
     {
-        void*volatile vp = operator new[] (std::numeric_limits<std::size_t>::max());
+        void* volatile vp = operator new[] (std::numeric_limits<std::size_t>::max());
+        ((void)vp);
         assert(false);
     }
     catch (std::bad_alloc&)
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array_nothrow.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array_nothrow.pass.cpp
index 259f5b0..b0db4a8 100644
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array_nothrow.pass.cpp
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array_nothrow.pass.cpp
@@ -9,7 +9,7 @@
 
 // test operator new [] (nothrow)
 // NOTE: asan and msan will not call the new handler.
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 
 #include <new>
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array_nothrow_replace.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array_nothrow_replace.pass.cpp
index 3e3a00c..105c7a9 100644
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array_nothrow_replace.pass.cpp
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array_nothrow_replace.pass.cpp
@@ -9,7 +9,7 @@
 
 // test operator new [] nothrow by replacing only operator new
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <new>
 #include <cstddef>
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array_replace.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array_replace.pass.cpp
index acf972b..92bd7b9 100644
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array_replace.pass.cpp
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.array/new_array_replace.pass.cpp
@@ -9,7 +9,7 @@
 
 // test operator new[] replacement by replacing only operator new
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <new>
 #include <cstddef>
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array.pass.cpp
deleted file mode 100644
index 57e6cd6..0000000
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array.pass.cpp
+++ /dev/null
@@ -1,77 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// test sized operator delete[] by replacing unsized operator delete[].
-
-// UNSUPPORTED: asan, msan
-
-#include <new>
-#include <cstddef>
-#include <cstdlib>
-#include <cassert>
-#include <limits>
-
-int delete_called = 0;
-int delete_nothrow_called = 0;
-
-void operator delete[](void* p) throw()
-{
-    ++delete_called;
-    delete_nothrow_called;
-    std::free(p);
-}
-
-void operator delete[](void* p, const std::nothrow_t&) throw()
-{
-    ++delete_nothrow_called;
-    std::free(p);
-}
-
-int new_handler_called = 0;
-
-void new_handler()
-{
-    ++new_handler_called;
-    std::set_new_handler(0);
-}
-
-int A_constructed = 0;
-
-struct A
-{
-    A() {++A_constructed;}
-    ~A() {--A_constructed;}
-};
-
-int main()
-{
-    std::set_new_handler(new_handler);
-    try
-    {
-        void* vp = operator new [] (std::numeric_limits<std::size_t>::max());
-        assert(false);
-    }
-    catch (std::bad_alloc&)
-    {
-        assert(new_handler_called == 1);
-    }
-    catch (...)
-    {
-        assert(false);
-    }
-    A* ap = new A[3];
-    assert(ap);
-    assert(A_constructed == 3);
-    assert(!delete_called);
-    assert(!delete_nothrow_called);
-    delete [] ap;
-    assert(A_constructed == 0);
-    assert(delete_called == 1);
-    assert(!delete_nothrow_called);
-}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array11.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array11.pass.cpp
new file mode 100644
index 0000000..0f7840c
--- /dev/null
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array11.pass.cpp
@@ -0,0 +1,68 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// test sized operator delete[] replacement.
+
+// Note that sized delete operator definitions below are simply ignored
+// when sized deallocation is not supported, e.g., prior to C++14.
+
+// UNSUPPORTED: c++14, c++1z
+// UNSUPPORTED: sanitizer-new-delete
+
+#include <new>
+#include <cstddef>
+#include <cstdlib>
+#include <cassert>
+
+int unsized_delete_called = 0;
+int unsized_delete_nothrow_called = 0;
+int sized_delete_called = 0;
+
+void operator delete[](void* p) throw()
+{
+    ++unsized_delete_called;
+    std::free(p);
+}
+
+void operator delete[](void* p, const std::nothrow_t&) throw()
+{
+    ++unsized_delete_nothrow_called;
+    std::free(p);
+}
+
+void operator delete[](void* p, std::size_t) throw()
+{
+    ++sized_delete_called;
+    std::free(p);
+}
+
+// NOTE: Use a class with a non-trivial destructor as the test type in order
+// to ensure the correct overload is called.
+// C++14 5.3.5 [expr.delete]p10
+// - If the type is complete and if, for the second alternative (delete array)
+//   only, the operand is a pointer to a class type with a non-trivial
+//   destructor or a (possibly multi-dimensional) array thereof, the function
+//   with two parameters is selected.
+// - Otherwise, it is unspecified which of the two deallocation functions is
+//   selected.
+struct A { ~A() {} };
+
+int main()
+{
+
+    A* x = new A[3];
+    assert(0 == unsized_delete_called);
+    assert(0 == unsized_delete_nothrow_called);
+    assert(0 == sized_delete_called);
+
+    delete [] x;
+    assert(1 == unsized_delete_called);
+    assert(0 == sized_delete_called);
+    assert(0 == unsized_delete_nothrow_called);
+}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array14.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array14.pass.cpp
new file mode 100644
index 0000000..0e2cc6d
--- /dev/null
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array14.pass.cpp
@@ -0,0 +1,72 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// test sized operator delete[] replacement.
+
+// UNSUPPORTED: sanitizer-new-delete, c++98, c++03, c++11
+
+// NOTE: Clang does not enable sized-deallocation in c++14 and beyond by
+// default. It is only enabled when -fsized-deallocation is given.
+// (except clang-3.6 which temporarily enabled sized-deallocation)
+// UNSUPPORTED: clang, apple-clang
+
+// NOTE: GCC 4.9.1 does not support sized-deallocation in c++14. However
+// GCC 5.1 does.
+// XFAIL: gcc-4.7, gcc-4.8, gcc-4.9
+
+#include <new>
+#include <cstddef>
+#include <cstdlib>
+#include <cassert>
+
+int unsized_delete_called = 0;
+int unsized_delete_nothrow_called = 0;
+int sized_delete_called = 0;
+
+void operator delete[](void* p) throw()
+{
+    ++unsized_delete_called;
+    std::free(p);
+}
+
+void operator delete[](void* p, const std::nothrow_t&) throw()
+{
+    ++unsized_delete_nothrow_called;
+    std::free(p);
+}
+
+void operator delete[](void* p, std::size_t) throw()
+{
+    ++sized_delete_called;
+    std::free(p);
+}
+
+// NOTE: Use a class with a non-trivial destructor as the test type in order
+// to ensure the correct overload is called.
+// C++14 5.3.5 [expr.delete]p10
+// - If the type is complete and if, for the second alternative (delete array)
+//   only, the operand is a pointer to a class type with a non-trivial
+//   destructor or a (possibly multi-dimensional) array thereof, the function
+//   with two parameters is selected.
+// - Otherwise, it is unspecified which of the two deallocation functions is
+//   selected.
+struct A { ~A() {} };
+
+int main()
+{
+    A* x = new A[3];
+    assert(0 == unsized_delete_called);
+    assert(0 == unsized_delete_nothrow_called);
+    assert(0 == sized_delete_called);
+
+    delete [] x;
+    assert(0 == unsized_delete_called);
+    assert(0 == unsized_delete_nothrow_called);
+    assert(1 == sized_delete_called);
+}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_calls_unsized_delete_array.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_calls_unsized_delete_array.pass.cpp
new file mode 100644
index 0000000..6d24aec
--- /dev/null
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_calls_unsized_delete_array.pass.cpp
@@ -0,0 +1,56 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// test sized operator [] delete calls the unsized operator [] delete.
+// When sized operator delete [] is not available (ex C++11) then the unsized
+// operator delete [] is called directly.
+
+// UNSUPPORTED: sanitizer-new-delete
+
+#include <new>
+#include <cstddef>
+#include <cstdlib>
+#include <cassert>
+
+int delete_called = 0;
+int delete_nothrow_called = 0;
+
+void operator delete[](void* p) throw()
+{
+    ++delete_called;
+    std::free(p);
+}
+
+void operator delete[](void* p, const std::nothrow_t&) throw()
+{
+    ++delete_nothrow_called;
+    std::free(p);
+}
+
+// NOTE: Use a class with a non-trivial destructor as the test type in order
+// to ensure the correct overload is called.
+// C++14 5.3.5 [expr.delete]p10
+// - If the type is complete and if, for the second alternative (delete array)
+//   only, the operand is a pointer to a class type with a non-trivial
+//   destructor or a (possibly multi-dimensional) array thereof, the function
+//   with two parameters is selected.
+// - Otherwise, it is unspecified which of the two deallocation functions is
+//   selected.
+struct A { ~A() {} };
+
+int main()
+{
+    A* x = new A[3];
+    assert(0 == delete_called);
+    assert(0 == delete_nothrow_called);
+
+    delete [] x;
+    assert(1 == delete_called);
+    assert(0 == delete_nothrow_called);
+}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_fsizeddeallocation.sh.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_fsizeddeallocation.sh.cpp
new file mode 100644
index 0000000..7dd510b
--- /dev/null
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_fsizeddeallocation.sh.cpp
@@ -0,0 +1,80 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// test sized operator delete[] replacement.
+
+// Note that sized delete operator definitions below are simply ignored
+// when sized deallocation is not supported, e.g., prior to C++14.
+
+// UNSUPPORTED: sanitizer-new-delete
+
+// NOTE: Only clang-3.7 and GCC 5.1 and greater support -fsized-deallocation.
+// REQUIRES: fsized-deallocation
+
+// RUN: %build -fsized-deallocation
+// RUN: %run
+
+#if !defined(__cpp_sized_deallocation)
+# error __cpp_sized_deallocation should be defined
+#endif
+
+#if !(__cpp_sized_deallocation >= 201309L)
+# error expected __cpp_sized_deallocation >= 201309L
+#endif
+
+#include <new>
+#include <cstddef>
+#include <cstdlib>
+#include <cassert>
+
+int unsized_delete_called = 0;
+int unsized_delete_nothrow_called = 0;
+int sized_delete_called = 0;
+
+void operator delete[](void* p) throw()
+{
+    ++unsized_delete_called;
+    std::free(p);
+}
+
+void operator delete[](void* p, const std::nothrow_t&) throw()
+{
+    ++unsized_delete_nothrow_called;
+    std::free(p);
+}
+
+void operator delete[](void* p, std::size_t) throw()
+{
+    ++sized_delete_called;
+    std::free(p);
+}
+
+// NOTE: Use a class with a non-trivial destructor as the test type in order
+// to ensure the correct overload is called.
+// C++14 5.3.5 [expr.delete]p10
+// - If the type is complete and if, for the second alternative (delete array)
+//   only, the operand is a pointer to a class type with a non-trivial
+//   destructor or a (possibly multi-dimensional) array thereof, the function
+//   with two parameters is selected.
+// - Otherwise, it is unspecified which of the two deallocation functions is
+//   selected.
+struct A { ~A() {} };
+
+int main()
+{
+    A* x = new A[3];
+    assert(0 == unsized_delete_called);
+    assert(0 == unsized_delete_nothrow_called);
+    assert(0 == sized_delete_called);
+
+    delete [] x;
+    assert(0 == unsized_delete_called);
+    assert(0 == unsized_delete_nothrow_called);
+    assert(1 == sized_delete_called);
+}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_nothrow.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_nothrow.pass.cpp
deleted file mode 100644
index 05dc013..0000000
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_nothrow.pass.cpp
+++ /dev/null
@@ -1,80 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// test nothrow sized operator delete[] by replacing
-// nothrow unsized operator delete[].
-
-// UNSUPPORTED: asan, msan
-
-#include <new>
-#include <cstddef>
-#include <cstdlib>
-#include <cassert>
-#include <limits>
-
-int delete_called = 0;
-int delete_nothrow_called = 0;
-
-void operator delete[](void* p) throw()
-{
-    ++delete_called;
-    std::free(p);
-}
-
-void operator delete[](void* p, const std::nothrow_t&) throw()
-{
-    ++delete_nothrow_called;
-    std::free(p);
-}
-
-int new_handler_called = 0;
-
-void new_handler()
-{
-    ++new_handler_called;
-    std::set_new_handler(0);
-}
-
-bool A_constructed = false;
-
-struct A
-{
-    A() {A_constructed = true;}
-    ~A() {A_constructed = false;}
-};
-
-struct BadA : public A {
-  BadA() { throw std::bad_alloc(); }
-};
-
-int main()
-{
-    std::set_new_handler(new_handler);
-    try
-    {
-        void*volatile vp = operator new [] (std::numeric_limits<std::size_t>::max(), std::nothrow);
-        assert(new_handler_called == 1);
-        assert(vp == 0);
-    }
-    catch (...)
-    {
-        assert(false);
-    }
-    try
-    {
-        A* ap = new(std::nothrow) BadA [3];
-        assert(false);
-    }
-    catch (...)
-    {
-        assert(!A_constructed);
-        assert(!delete_called);
-        assert(delete_nothrow_called == 1);
-    }
-}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_nothrow_replace.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_nothrow_replace.pass.cpp
deleted file mode 100644
index 6a5320b..0000000
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_nothrow_replace.pass.cpp
+++ /dev/null
@@ -1,109 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// test nothrow sized operator delete[] replacement.
-
-// Note that sized delete operator definitions below are simply ignored
-// when sized deallocation is not supported, e.g., prior to C++14.
-
-// UNSUPPORTED: asan, msan
-
-#include <new>
-#include <cstddef>
-#include <cstdlib>
-#include <cassert>
-#include <limits>
-
-int unsized_delete_called = 0;
-int unsized_delete_nothrow_called = 0;
-int sized_delete_called = 0;
-int sized_delete_nothrow_called = 0;
-
-void operator delete[](void* p) throw()
-{
-    ++unsized_delete_called;
-    std::free(p);
-}
-
-void operator delete[](void* p, const std::nothrow_t&) throw()
-{
-    ++unsized_delete_nothrow_called;
-    std::free(p);
-}
-
-void operator delete[](void* p, std::size_t) throw()
-{
-    ++sized_delete_called;
-    std::free(p);
-}
-
-void operator delete[](void* p, std::size_t, const std::nothrow_t&) throw()
-{
-    ++sized_delete_nothrow_called;
-    std::free(p);
-}
-
-int new_handler_called = 0;
-
-void new_handler()
-{
-    ++new_handler_called;
-    std::set_new_handler(0);
-}
-
-bool A_constructed = false;
-
-struct A
-{
-    A() {A_constructed = true;}
-    ~A() {A_constructed = false;}
-};
-
-struct BadA : public A {
-    BadA() { throw std::bad_alloc(); }
-};
-
-int main()
-{
-    std::set_new_handler(new_handler);
-    try
-    {
-        void*volatile vp = operator new [] (std::numeric_limits<std::size_t>::max(), std::nothrow);
-        assert(new_handler_called == 1);
-        assert(vp == 0);
-    }
-    catch (...)
-    {
-        assert(false);
-    }
-    try
-    {
-        A* ap = new(std::nothrow) BadA [3];
-        assert(false);
-    }
-    catch (...)
-    {
-        assert(!A_constructed);
-#if _LIBCPP_STD_VER >= 14
-        // FIXME: Do we need a version of [Expr.Delete]#10 for nothrow
-        // deallocation functions (selecting sized ones whenever available)?
-        // It is not required by the standard. If it were, the following would
-        // be the expected behaviour (instead of the current one):
-        //   assert(!unsized_delete_nothrow_called);
-        //   assert(sized_delete_nothrow_called == 1);
-        assert(unsized_delete_nothrow_called == 1);
-        assert(!sized_delete_nothrow_called);
-#else // if _LIBCPP_STD_VER < 14
-        assert(unsized_delete_nothrow_called == 1);
-        assert(!sized_delete_nothrow_called);
-#endif
-        assert(!unsized_delete_called);
-        assert(!sized_delete_called);
-    }
-}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_replace.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_replace.pass.cpp
deleted file mode 100644
index 752cd70..0000000
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array_replace.pass.cpp
+++ /dev/null
@@ -1,102 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// test sized operator delete[] replacement.
-
-// Note that sized delete operator definitions below are simply ignored
-// when sized deallocation is not supported, e.g., prior to C++14.
-
-// UNSUPPORTED: asan, msan
-
-#include <new>
-#include <cstddef>
-#include <cstdlib>
-#include <cassert>
-#include <limits>
-
-int unsized_delete_called = 0;
-int unsized_delete_nothrow_called = 0;
-int sized_delete_called = 0;
-int sized_delete_nothrow_called = 0;
-
-void operator delete[](void* p) throw()
-{
-    ++unsized_delete_called;
-    std::free(p);
-}
-
-void operator delete[](void* p, const std::nothrow_t&) throw()
-{
-    ++unsized_delete_nothrow_called;
-    std::free(p);
-}
-
-void operator delete[](void* p, std::size_t) throw()
-{
-    ++sized_delete_called;
-    std::free(p);
-}
-
-void operator delete[](void* p, std::size_t, const std::nothrow_t&) throw()
-{
-    ++sized_delete_nothrow_called;
-    std::free(p);
-}
-
-int new_handler_called = 0;
-
-void new_handler()
-{
-    ++new_handler_called;
-    std::set_new_handler(0);
-}
-
-int A_constructed = 0;
-
-struct A
-{
-    A() {++A_constructed;}
-    ~A() {--A_constructed;}
-};
-
-int main()
-{
-    std::set_new_handler(new_handler);
-    try
-    {
-        void* vp = operator new [] (std::numeric_limits<std::size_t>::max());
-        assert(false);
-    }
-    catch (std::bad_alloc&)
-    {
-        assert(new_handler_called == 1);
-    }
-    catch (...)
-    {
-        assert(false);
-    }
-    A* ap = new A[3];
-    assert(ap);
-    assert(A_constructed == 3);
-    assert(!unsized_delete_called);
-    assert(!unsized_delete_nothrow_called);
-    assert(!sized_delete_called);
-    assert(!sized_delete_nothrow_called);
-    delete [] ap;
-    assert(A_constructed == 0);
-#if _LIBCPP_STD_VER >= 14
-    assert(!unsized_delete_called);
-    assert(sized_delete_called == 1);
-#else // if _LIBCPP_STD_VER < 14
-    assert(unsized_delete_called == 1);
-    assert(!sized_delete_called);
-#endif
-    assert(!unsized_delete_nothrow_called);
-    assert(!sized_delete_nothrow_called);
-}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.single/new.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.single/new.pass.cpp
index 3ba71dd..5dc9f71 100644
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.single/new.pass.cpp
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.single/new.pass.cpp
@@ -10,7 +10,7 @@
 // test operator new
 
 // asan and msan will not call the new handler.
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <new>
 #include <cstddef>
@@ -39,6 +39,7 @@
     try
     {
         void* vp = operator new (std::numeric_limits<std::size_t>::max());
+        ((void)vp);
         assert(false);
     }
     catch (std::bad_alloc&)
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.single/new_nothrow.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.single/new_nothrow.pass.cpp
index c76bfa0..8c095ad 100644
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.single/new_nothrow.pass.cpp
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.single/new_nothrow.pass.cpp
@@ -10,7 +10,7 @@
 // test operator new (nothrow)
 
 // asan and msan will not call the new handler.
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <new>
 #include <cstddef>
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.single/new_nothrow_replace.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.single/new_nothrow_replace.pass.cpp
index f2dbb98..cd70f90 100644
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.single/new_nothrow_replace.pass.cpp
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.single/new_nothrow_replace.pass.cpp
@@ -9,7 +9,7 @@
 
 // test operator new nothrow by replacing only operator new
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <new>
 #include <cstddef>
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.single/new_replace.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.single/new_replace.pass.cpp
index 2d411b9..0df3a93 100644
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.single/new_replace.pass.cpp
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.single/new_replace.pass.cpp
@@ -9,7 +9,7 @@
 
 // test operator new replacement
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <new>
 #include <cstddef>
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete.pass.cpp
deleted file mode 100644
index 6e3a235..0000000
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete.pass.cpp
+++ /dev/null
@@ -1,77 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// test sized operator delete by replacing unsized operator delete.
-
-// UNSUPPORTED: asan, msan
-
-#include <new>
-#include <cstddef>
-#include <cstdlib>
-#include <cassert>
-#include <limits>
-
-int delete_called = 0;
-int delete_nothrow_called = 0;
-
-void operator delete(void* p) throw()
-{
-    ++delete_called;
-    delete_nothrow_called;
-    std::free(p);
-}
-
-void operator delete(void* p, const std::nothrow_t&) throw()
-{
-    ++delete_nothrow_called;
-    std::free(p);
-}
-
-int new_handler_called = 0;
-
-void new_handler()
-{
-    ++new_handler_called;
-    std::set_new_handler(0);
-}
-
-bool A_constructed = false;
-
-struct A
-{
-    A() {A_constructed = true;}
-    ~A() {A_constructed = false;}
-};
-
-int main()
-{
-    std::set_new_handler(new_handler);
-    try
-    {
-        void* vp = operator new (std::numeric_limits<std::size_t>::max());
-        assert(false);
-    }
-    catch (std::bad_alloc&)
-    {
-        assert(new_handler_called == 1);
-    }
-    catch (...)
-    {
-        assert(false);
-    }
-    A* ap = new A;
-    assert(ap);
-    assert(A_constructed);
-    assert(!delete_called);
-    assert(!delete_nothrow_called);
-    delete ap;
-    assert(!A_constructed);
-    assert(delete_called == 1);
-    assert(!delete_nothrow_called);
-}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete11.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete11.pass.cpp
new file mode 100644
index 0000000..e4064e2
--- /dev/null
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete11.pass.cpp
@@ -0,0 +1,56 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// test sized operator delete replacement.
+
+// Note that sized delete operator definitions below are simply ignored
+// when sized deallocation is not supported, e.g., prior to C++14.
+
+// UNSUPPORTED: c++14, c++1z
+// UNSUPPORTED: sanitizer-new-delete
+
+#include <new>
+#include <cstddef>
+#include <cstdlib>
+#include <cassert>
+
+int unsized_delete_called = 0;
+int unsized_delete_nothrow_called = 0;
+int sized_delete_called = 0;
+
+void operator delete(void* p) throw()
+{
+    ++unsized_delete_called;
+    std::free(p);
+}
+
+void operator delete(void* p, const std::nothrow_t&) throw()
+{
+    ++unsized_delete_nothrow_called;
+    std::free(p);
+}
+
+void operator delete(void* p, std::size_t) throw()
+{
+    ++sized_delete_called;
+    std::free(p);
+}
+
+int main()
+{
+    int *x = new int(42);
+    assert(0 == unsized_delete_called);
+    assert(0 == unsized_delete_nothrow_called);
+    assert(0 == sized_delete_called);
+
+    delete x;
+    assert(1 == unsized_delete_called);
+    assert(0 == sized_delete_called);
+    assert(0 == unsized_delete_nothrow_called);
+}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete14.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete14.pass.cpp
new file mode 100644
index 0000000..5d9ddd4
--- /dev/null
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete14.pass.cpp
@@ -0,0 +1,61 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// test sized operator delete replacement.
+
+// UNSUPPORTED: sanitizer-new-delete, c++98, c++03, c++11
+
+// NOTE: Clang does not enable sized-deallocation in c++14 and beyond by
+// default. It is only enabled when -fsized-deallocation is given.
+// (except clang-3.6 which temporarily enabled sized-deallocation)
+// UNSUPPORTED: clang, apple-clang
+
+// NOTE: GCC 4.9.1 does not support sized-deallocation in c++14. However
+// GCC 5.1 does.
+// XFAIL: gcc-4.7, gcc-4.8, gcc-4.9
+
+#include <new>
+#include <cstddef>
+#include <cstdlib>
+#include <cassert>
+
+int unsized_delete_called = 0;
+int unsized_delete_nothrow_called = 0;
+int sized_delete_called = 0;
+
+void operator delete(void* p) throw()
+{
+    ++unsized_delete_called;
+    std::free(p);
+}
+
+void operator delete(void* p, const std::nothrow_t&) throw()
+{
+    ++unsized_delete_nothrow_called;
+    std::free(p);
+}
+
+void operator delete(void* p, std::size_t) throw()
+{
+    ++sized_delete_called;
+    std::free(p);
+}
+
+int main()
+{
+    int *x = new int(42);
+    assert(0 == unsized_delete_called);
+    assert(0 == unsized_delete_nothrow_called);
+    assert(0 == sized_delete_called);
+
+    delete x;
+    assert(0 == unsized_delete_called);
+    assert(1 == sized_delete_called);
+    assert(0 == unsized_delete_nothrow_called);
+}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_calls_unsized_delete.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_calls_unsized_delete.pass.cpp
new file mode 100644
index 0000000..5c4eba5
--- /dev/null
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_calls_unsized_delete.pass.cpp
@@ -0,0 +1,45 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// test sized operator delete calls the unsized operator delete.
+// When sized operator delete is not available (ex C++11) then the unsized
+// operator delete is called directly.
+
+// UNSUPPORTED: sanitizer-new-delete
+
+#include <new>
+#include <cstddef>
+#include <cstdlib>
+#include <cassert>
+
+int delete_called = 0;
+int delete_nothrow_called = 0;
+
+void operator delete(void* p) throw()
+{
+    ++delete_called;
+    std::free(p);
+}
+
+void operator delete(void* p, const std::nothrow_t&) throw()
+{
+    ++delete_nothrow_called;
+    std::free(p);
+}
+
+int main()
+{
+    int *x = new int(42);
+    assert(0 == delete_called);
+    assert(0 == delete_nothrow_called);
+
+    delete x;
+    assert(1 == delete_called);
+    assert(0 == delete_nothrow_called);
+}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_fsizeddeallocation.sh.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_fsizeddeallocation.sh.cpp
new file mode 100644
index 0000000..da43d49
--- /dev/null
+++ b/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_fsizeddeallocation.sh.cpp
@@ -0,0 +1,69 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// test sized operator delete replacement.
+
+// Note that sized delete operator definitions below are simply ignored
+// when sized deallocation is not supported, e.g., prior to C++14.
+
+// UNSUPPORTED: sanitizer-new-delete
+
+// NOTE: Only clang-3.7 and GCC 5.1 and greater support -fsized-deallocation.
+// REQUIRES: fsized-deallocation
+
+// RUN: %build -fsized-deallocation
+// RUN: %run
+
+#if !defined(__cpp_sized_deallocation)
+# error __cpp_sized_deallocation should be defined
+#endif
+
+#if !(__cpp_sized_deallocation >= 201309L)
+# error expected __cpp_sized_deallocation >= 201309L
+#endif
+
+#include <new>
+#include <cstddef>
+#include <cstdlib>
+#include <cassert>
+
+int unsized_delete_called = 0;
+int unsized_delete_nothrow_called = 0;
+int sized_delete_called = 0;
+
+void operator delete(void* p) throw()
+{
+    ++unsized_delete_called;
+    std::free(p);
+}
+
+void operator delete(void* p, const std::nothrow_t&) throw()
+{
+    ++unsized_delete_nothrow_called;
+    std::free(p);
+}
+
+void operator delete(void* p, std::size_t) throw()
+{
+    ++sized_delete_called;
+    std::free(p);
+}
+
+int main()
+{
+    int *x = new int(42);
+    assert(0 == sized_delete_called);
+    assert(0 == unsized_delete_called);
+    assert(0 == unsized_delete_nothrow_called);
+
+    delete x;
+    assert(1 == sized_delete_called);
+    assert(0 == unsized_delete_called);
+    assert(0 == unsized_delete_nothrow_called);
+}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_nothrow.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_nothrow.pass.cpp
deleted file mode 100644
index 690e8af..0000000
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_nothrow.pass.cpp
+++ /dev/null
@@ -1,80 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// test nothrow sized operator delete by replacing
-// nothrow unsized operator delete.
-
-// UNSUPPORTED: asan, msan
-
-#include <new>
-#include <cstddef>
-#include <cstdlib>
-#include <cassert>
-#include <limits>
-
-int delete_called = 0;
-int delete_nothrow_called = 0;
-
-void operator delete(void* p) throw()
-{
-    ++delete_called;
-    std::free(p);
-}
-
-void operator delete(void* p, const std::nothrow_t&) throw()
-{
-    ++delete_nothrow_called;
-    std::free(p);
-}
-
-int new_handler_called = 0;
-
-void new_handler()
-{
-    ++new_handler_called;
-    std::set_new_handler(0);
-}
-
-bool A_constructed = false;
-
-struct A
-{
-    A() {A_constructed = true;}
-    ~A() {A_constructed = false;}
-};
-
-struct BadA : public A {
-    BadA() { throw std::bad_alloc(); }
-};
-
-int main()
-{
-    std::set_new_handler(new_handler);
-    try
-    {
-        void* volatile vp = operator new (std::numeric_limits<std::size_t>::max(), std::nothrow);
-        assert(new_handler_called == 1);
-        assert(vp == 0);
-    }
-    catch (...)
-    {
-        assert(false);
-    }
-    try
-    {
-        A* ap = new(std::nothrow) BadA;
-        assert(false);
-    }
-    catch (...)
-    {
-        assert(!A_constructed);
-        assert(!delete_called);
-        assert(delete_nothrow_called == 1);
-    }
-}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_nothrow_replace.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_nothrow_replace.pass.cpp
deleted file mode 100644
index b5eb9f2..0000000
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_nothrow_replace.pass.cpp
+++ /dev/null
@@ -1,109 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// test nothrow sized operator delete replacement.
-
-// Note that sized delete operator definitions below are simply ignored
-// when sized deallocation is not supported, e.g., prior to C++14.
-
-// UNSUPPORTED: asan, msan
-
-#include <new>
-#include <cstddef>
-#include <cstdlib>
-#include <cassert>
-#include <limits>
-
-int unsized_delete_called = 0;
-int unsized_delete_nothrow_called = 0;
-int sized_delete_called = 0;
-int sized_delete_nothrow_called = 0;
-
-void operator delete(void* p) throw()
-{
-    ++unsized_delete_called;
-    std::free(p);
-}
-
-void operator delete(void* p, const std::nothrow_t&) throw()
-{
-    ++unsized_delete_nothrow_called;
-    std::free(p);
-}
-
-void operator delete(void* p, std::size_t) throw()
-{
-    ++sized_delete_called;
-    std::free(p);
-}
-
-void operator delete(void* p, std::size_t, const std::nothrow_t&) throw()
-{
-    ++sized_delete_nothrow_called;
-    std::free(p);
-}
-
-int new_handler_called = 0;
-
-void new_handler()
-{
-    ++new_handler_called;
-    std::set_new_handler(0);
-}
-
-bool A_constructed = false;
-
-struct A
-{
-    A() {A_constructed = true;}
-    ~A() {A_constructed = false;}
-};
-
-struct BadA : public A {
-    BadA() { throw std::bad_alloc(); }
-};
-
-int main()
-{
-    std::set_new_handler(new_handler);
-    try
-    {
-        void*volatile vp = operator new (std::numeric_limits<std::size_t>::max(), std::nothrow);
-        assert(new_handler_called == 1);
-        assert(vp == 0);
-    }
-    catch (...)
-    {
-        assert(false);
-    }
-    try
-    {
-        A* ap = new(std::nothrow) BadA;
-        assert(false);
-    }
-    catch (...)
-    {
-        assert(!A_constructed);
-#if _LIBCPP_STD_VER >= 14
-        // FIXME: Do we need a version of [Expr.Delete]#10 for nothrow
-        // deallocation functions (selecting sized ones whenever available)?
-        // It is not required by the standard. If it were, the following would
-        // be the expected behaviour (instead of the current one):
-        //   assert(!unsized_delete_nothrow_called);
-        //   assert(sized_delete_nothrow_called == 1);
-        assert(unsized_delete_nothrow_called == 1);
-        assert(!sized_delete_nothrow_called);
-#else // if _LIBCPP_STD_VER < 14
-        assert(unsized_delete_nothrow_called == 1);
-        assert(!sized_delete_nothrow_called);
-#endif
-        assert(!unsized_delete_called);
-        assert(!sized_delete_called);
-    }
-}
diff --git a/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_replace.pass.cpp b/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_replace.pass.cpp
deleted file mode 100644
index 4e0d7c7..0000000
--- a/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete_replace.pass.cpp
+++ /dev/null
@@ -1,102 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// test sized operator delete replacement.
-
-// Note that sized delete operator definitions below are simply ignored
-// when sized deallocation is not supported, e.g., prior to C++14.
-
-// UNSUPPORTED: asan, msan
-
-#include <new>
-#include <cstddef>
-#include <cstdlib>
-#include <cassert>
-#include <limits>
-
-int unsized_delete_called = 0;
-int unsized_delete_nothrow_called = 0;
-int sized_delete_called = 0;
-int sized_delete_nothrow_called = 0;
-
-void operator delete(void* p) throw()
-{
-    ++unsized_delete_called;
-    std::free(p);
-}
-
-void operator delete(void* p, const std::nothrow_t&) throw()
-{
-    ++unsized_delete_nothrow_called;
-    std::free(p);
-}
-
-void operator delete(void* p, std::size_t) throw()
-{
-    ++sized_delete_called;
-    std::free(p);
-}
-
-void operator delete(void* p, std::size_t, const std::nothrow_t&) throw()
-{
-    ++sized_delete_nothrow_called;
-    std::free(p);
-}
-
-int new_handler_called = 0;
-
-void new_handler()
-{
-    ++new_handler_called;
-    std::set_new_handler(0);
-}
-
-bool A_constructed = false;
-
-struct A
-{
-    A() {A_constructed = true;}
-    ~A() {A_constructed = false;}
-};
-
-int main()
-{
-    std::set_new_handler(new_handler);
-    try
-    {
-        void* vp = operator new (std::numeric_limits<std::size_t>::max());
-        assert(false);
-    }
-    catch (std::bad_alloc&)
-    {
-        assert(new_handler_called == 1);
-    }
-    catch (...)
-    {
-        assert(false);
-    }
-    A* ap = new A;
-    assert(ap);
-    assert(A_constructed);
-    assert(!unsized_delete_called);
-    assert(!unsized_delete_nothrow_called);
-    assert(!sized_delete_called);
-    assert(!sized_delete_nothrow_called);
-    delete ap;
-    assert(!A_constructed);
-#if _LIBCPP_STD_VER >= 14
-    assert(!unsized_delete_called);
-    assert(sized_delete_called == 1);
-#else // if _LIBCPP_STD_VER < 14
-    assert(unsized_delete_called == 1);
-    assert(!sized_delete_called);
-#endif
-    assert(!unsized_delete_nothrow_called);
-    assert(!sized_delete_nothrow_called);
-}
diff --git a/test/std/language.support/support.exception/except.nested/throw_with_nested.pass.cpp b/test/std/language.support/support.exception/except.nested/throw_with_nested.pass.cpp
index 887264a..dad0df2 100644
--- a/test/std/language.support/support.exception/except.nested/throw_with_nested.pass.cpp
+++ b/test/std/language.support/support.exception/except.nested/throw_with_nested.pass.cpp
@@ -36,6 +36,10 @@
     friend bool operator==(const B& x, const B& y) {return x.data_ == y.data_;}
 };
 
+#if __cplusplus > 201103L
+struct Final final {};
+#endif
+
 int main()
 {
     {
@@ -100,4 +104,16 @@
             assert(i == 7);
         }
     }
+#if __cplusplus > 201103L
+    {
+        try
+        {
+            std::throw_with_nested(Final());
+            assert(false);
+        }
+        catch (const Final &f)
+        {
+        }
+    }
+#endif
 }
diff --git a/test/std/language.support/support.exception/exception.terminate/terminate.handler/terminate_handler.pass.cpp b/test/std/language.support/support.exception/exception.terminate/terminate.handler/terminate_handler.pass.cpp
index 232ce0a..e477f52 100644
--- a/test/std/language.support/support.exception/exception.terminate/terminate.handler/terminate_handler.pass.cpp
+++ b/test/std/language.support/support.exception/exception.terminate/terminate.handler/terminate_handler.pass.cpp
@@ -10,10 +10,14 @@
 // test terminate_handler
 
 #include <exception>
+#include <type_traits>
+#include <cassert>
 
 void f() {}
 
 int main()
 {
+    static_assert((std::is_same<std::terminate_handler, void(*)()>::value), "");
     std::terminate_handler p = f;
+    assert(p == &f);
 }
diff --git a/test/std/language.support/support.exception/uncaught/uncaught_exceptions.pass.cpp b/test/std/language.support/support.exception/uncaught/uncaught_exceptions.pass.cpp
new file mode 100644
index 0000000..1adc904
--- /dev/null
+++ b/test/std/language.support/support.exception/uncaught/uncaught_exceptions.pass.cpp
@@ -0,0 +1,45 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// test uncaught_exceptions
+
+#include <exception>
+#include <cassert>
+
+struct A
+{
+    ~A()
+    {
+        assert(std::uncaught_exceptions() > 0);
+    }
+};
+
+struct B
+{
+    B()
+    {
+        // http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#475
+        assert(std::uncaught_exceptions() == 0);
+    }
+};
+
+int main()
+{
+    try
+    {
+        A a;
+        assert(std::uncaught_exceptions() == 0);
+        throw B();
+    }
+    catch (...)
+    {
+        assert(std::uncaught_exception() == 0);
+    }
+    assert(std::uncaught_exceptions() == 0);
+}
diff --git a/test/std/language.support/support.runtime/csignal.pass.cpp b/test/std/language.support/support.runtime/csignal.pass.cpp
index 717347d..a42363f 100644
--- a/test/std/language.support/support.runtime/csignal.pass.cpp
+++ b/test/std/language.support/support.runtime/csignal.pass.cpp
@@ -50,7 +50,8 @@
 
 int main()
 {
-    std::sig_atomic_t sig;
+    std::sig_atomic_t sig = 0;
+    ((void)sig);
     typedef void (*func)(int);
     static_assert((std::is_same<decltype(std::signal(0, (func)0)), func>::value), "");
     static_assert((std::is_same<decltype(std::raise(0)), int>::value), "");
diff --git a/test/std/language.support/support.runtime/cstdarg.pass.cpp b/test/std/language.support/support.runtime/cstdarg.pass.cpp
index 059ad2f..9d6f610 100644
--- a/test/std/language.support/support.runtime/cstdarg.pass.cpp
+++ b/test/std/language.support/support.runtime/cstdarg.pass.cpp
@@ -32,4 +32,5 @@
 int main()
 {
     std::va_list va;
+    ((void)va);
 }
diff --git a/test/std/language.support/support.runtime/cstdlib.pass.cpp b/test/std/language.support/support.runtime/cstdlib.pass.cpp
index e14e70e..8191350 100644
--- a/test/std/language.support/support.runtime/cstdlib.pass.cpp
+++ b/test/std/language.support/support.runtime/cstdlib.pass.cpp
@@ -11,6 +11,7 @@
 
 #include <cstdlib>
 #include <type_traits>
+#include <cassert>
 
 #ifndef EXIT_FAILURE
 #error EXIT_FAILURE not defined
@@ -32,12 +33,23 @@
 #error RAND_MAX not defined
 #endif
 
+template <class TestType, class IntType>
+void test_div_struct() {
+    TestType obj;
+    static_assert(sizeof(obj) >= sizeof(IntType) * 2, ""); // >= to account for alignment.
+    static_assert((std::is_same<decltype(obj.quot), IntType>::value), "");
+    static_assert((std::is_same<decltype(obj.rem), IntType>::value), "");
+    ((void) obj);
+};
+
 int main()
 {
     std::size_t s = 0;
-    std::div_t d;
-    std::ldiv_t ld;
-    std::lldiv_t lld;
+    ((void)s);
+    static_assert((std::is_same<std::size_t, decltype(sizeof(int))>::value), "");
+    test_div_struct<std::div_t, int>();
+    test_div_struct<std::ldiv_t, long>();
+    test_div_struct<std::lldiv_t, long long>();
     char** endptr = 0;
     static_assert((std::is_same<decltype(std::atof("")), double>::value), "");
     static_assert((std::is_same<decltype(std::atoi("")), int>::value), "");
@@ -75,12 +87,14 @@
     static_assert((std::is_same<decltype(std::div(0LL,0LL)), std::lldiv_t>::value), "");
     static_assert((std::is_same<decltype(std::ldiv(0L,0L)), std::ldiv_t>::value), "");
     static_assert((std::is_same<decltype(std::lldiv(0LL,0LL)), std::lldiv_t>::value), "");
-    static_assert((std::is_same<decltype(std::mblen("",0)), int>::value), "");
     wchar_t* pw = 0;
     const wchar_t* pwc = 0;
     char* pc = 0;
+#ifndef _LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
+    static_assert((std::is_same<decltype(std::mblen("",0)), int>::value), "");
     static_assert((std::is_same<decltype(std::mbtowc(pw,"",0)), int>::value), "");
     static_assert((std::is_same<decltype(std::wctomb(pc,L' ')), int>::value), "");
+#endif
     static_assert((std::is_same<decltype(std::mbstowcs(pw,"",0)), std::size_t>::value), "");
     static_assert((std::is_same<decltype(std::wcstombs(pc,pwc,0)), std::size_t>::value), "");
 }
diff --git a/test/std/language.support/support.runtime/ctime.pass.cpp b/test/std/language.support/support.runtime/ctime.pass.cpp
index 495d6eb..03a0aa4 100644
--- a/test/std/language.support/support.runtime/ctime.pass.cpp
+++ b/test/std/language.support/support.runtime/ctime.pass.cpp
@@ -23,6 +23,7 @@
 int main()
 {
     std::clock_t c = 0;
+    ((void)c);
     std::size_t s = 0;
     std::time_t t = 0;
     std::tm tm = {0};
@@ -30,10 +31,12 @@
     static_assert((std::is_same<decltype(std::difftime(t,t)), double>::value), "");
     static_assert((std::is_same<decltype(std::mktime(&tm)), std::time_t>::value), "");
     static_assert((std::is_same<decltype(std::time(&t)), std::time_t>::value), "");
+#ifndef _LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
     static_assert((std::is_same<decltype(std::asctime(&tm)), char*>::value), "");
     static_assert((std::is_same<decltype(std::ctime(&t)), char*>::value), "");
     static_assert((std::is_same<decltype(std::gmtime(&t)), std::tm*>::value), "");
     static_assert((std::is_same<decltype(std::localtime(&t)), std::tm*>::value), "");
+#endif
     char* c1 = 0;
     const char* c2 = 0;
     static_assert((std::is_same<decltype(std::strftime(c1,s,c2,&tm)), std::size_t>::value), "");
diff --git a/test/std/localization/c.locales/clocale.pass.cpp b/test/std/localization/c.locales/clocale.pass.cpp
index 3b3e933..a90725b 100644
--- a/test/std/localization/c.locales/clocale.pass.cpp
+++ b/test/std/localization/c.locales/clocale.pass.cpp
@@ -12,6 +12,8 @@
 #include <clocale>
 #include <type_traits>
 
+#ifndef _LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
+
 #ifndef LC_ALL
 #error LC_ALL not defined
 #endif
@@ -36,6 +38,8 @@
 #error LC_TIME not defined
 #endif
 
+#endif // !_LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
+
 #ifndef NULL
 #error NULL not defined
 #endif
@@ -43,6 +47,8 @@
 int main()
 {
     std::lconv lc;
+#ifndef _LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
     static_assert((std::is_same<decltype(std::setlocale(0, "")), char*>::value), "");
+#endif
     static_assert((std::is_same<decltype(std::localeconv()), std::lconv*>::value), "");
 }
diff --git a/test/std/localization/locale.categories/category.ctype/locale.ctype.byname/mask.pass.cpp b/test/std/localization/locale.categories/category.ctype/locale.ctype.byname/mask.pass.cpp
new file mode 100644
index 0000000..a09072a
--- /dev/null
+++ b/test/std/localization/locale.categories/category.ctype/locale.ctype.byname/mask.pass.cpp
@@ -0,0 +1,53 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <locale>
+
+// template <class charT> class ctype_byname;
+
+// bool is(mask m, charT c) const;
+
+#include <locale>
+#include <type_traits>
+#include <cassert>
+
+int main()
+{
+    {
+        std::locale l("C");
+        {
+            typedef std::ctype<wchar_t> WF;
+            const WF& wf = std::use_facet<WF>(l);
+            typedef std::ctype<char> CF;
+            const CF& cf = std::use_facet<CF>(l);
+
+            // The ctype masks in Newlib don't form a proper bitmask because
+            // the mask is only 8 bits wide, and there are more than 8 mask
+            // kinds. This means that the mask for alpha is (_U | _L), which
+            // is tricky to match in the do_is implementation because in
+            // [22.4.1.1.2 2] the standard specifies that the match code behaves
+            // like (m & M) != 0, but following this exactly would give false
+            // positives for characters that are both 'upper' and 'alpha', but
+            // not 'lower', for example.
+            assert( wf.is(WF::upper, L'A'));
+            assert( cf.is(CF::upper,  'A'));
+            assert(!wf.is(WF::lower, L'A'));
+            assert(!cf.is(CF::lower,  'A'));
+            assert( wf.is(WF::alpha, L'A'));
+            assert( cf.is(CF::alpha,  'A'));
+
+            assert(!wf.is(WF::upper, L'a'));
+            assert(!cf.is(CF::upper,  'a'));
+            assert( wf.is(WF::lower, L'a'));
+            assert( cf.is(CF::lower,  'a'));
+            assert( wf.is(WF::alpha, L'a'));
+            assert( cf.is(CF::alpha,  'a'));
+        }
+    }
+}
diff --git a/test/std/localization/locale.categories/category.time/locale.time.put/locale.time.put.members/put2.pass.cpp b/test/std/localization/locale.categories/category.time/locale.time.put/locale.time.put.members/put2.pass.cpp
index 427d7c5..d9e7f3c 100644
--- a/test/std/localization/locale.categories/category.time/locale.time.put/locale.time.put.members/put2.pass.cpp
+++ b/test/std/localization/locale.categories/category.time/locale.time.put/locale.time.put.members/put2.pass.cpp
@@ -14,9 +14,6 @@
 // iter_type put(iter_type s, ios_base& str, char_type fill, const tm* t,
 //               char format, char modifier = 0) const;
 
-// TODO: investigation needed
-// XFAIL: linux-gnu
-
 #include <locale>
 #include <cassert>
 #include "test_iterators.h"
@@ -36,7 +33,7 @@
     const my_facet f(1);
     char str[200];
     output_iterator<char*> iter;
-    tm t = {0};
+    tm t = {};
     t.tm_sec = 6;
     t.tm_min = 3;
     t.tm_hour = 13;
@@ -44,7 +41,7 @@
     t.tm_mon = 4;
     t.tm_year = 109;
     t.tm_wday = 6;
-    t.tm_yday = -1;
+    t.tm_yday = 121;
     t.tm_isdst = 1;
     std::ios ios(0);
     {
@@ -160,12 +157,12 @@
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'U', 'O');
         std::string ex(str, iter.base());
-        assert(ex == "00");
+        assert(ex == "17");
     }
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'V', 'O');
         std::string ex(str, iter.base());
-        assert(ex == "52");
+        assert(ex == "18");
     }
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'w', 'O');
@@ -175,7 +172,7 @@
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'W', 'O');
         std::string ex(str, iter.base());
-        assert(ex == "00");
+        assert(ex == "17");
     }
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'y', 'O');
@@ -183,11 +180,6 @@
         assert(ex == "09");
     }
     {
-        iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'B', 'O');
-        std::string ex(str, iter.base());
-        assert(ex == "May");
-    }
-    {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'e');
         std::string ex(str, iter.base());
         assert(ex == " 2");
@@ -200,12 +192,12 @@
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'G');
         std::string ex(str, iter.base());
-        assert(ex == "2008");
+        assert(ex == "2009");
     }
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'g');
         std::string ex(str, iter.base());
-        assert(ex == "08");
+        assert(ex == "09");
     }
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'H');
@@ -225,17 +217,7 @@
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'j');
         std::string ex(str, iter.base());
-        assert(ex == "000");
-    }
-    {
-        iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'k');
-        std::string ex(str, iter.base());
-        assert(ex == "13");
-    }
-    {
-        iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'l');
-        std::string ex(str, iter.base());
-        assert(ex == " 1");
+        assert(ex == "122");
     }
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'M');
@@ -273,11 +255,6 @@
         assert(ex == "06");
     }
     {
-        iter = f.put(output_iterator<char*>(str), ios, '*', &t, 's');
-        std::string ex(str, iter.base());
-//        assert(ex == "1241283786");  depends on time zone
-    }
-    {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'T');
         std::string ex(str, iter.base());
         assert(ex == "13:03:06");
@@ -290,7 +267,7 @@
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'U');
         std::string ex(str, iter.base());
-        assert(ex == "00");
+        assert(ex == "17");
     }
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'u');
@@ -300,17 +277,12 @@
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'V');
         std::string ex(str, iter.base());
-        assert(ex == "52");
-    }
-    {
-        iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'v');
-        std::string ex(str, iter.base());
-        assert(ex == " 2-May-2009");
+        assert(ex == "18");
     }
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'W');
         std::string ex(str, iter.base());
-        assert(ex == "00");
+        assert(ex == "17");
     }
     {
         iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'w');
@@ -357,14 +329,4 @@
         std::string ex(str, iter.base());
         assert(ex == "%");
     }
-    {
-        iter = f.put(output_iterator<char*>(str), ios, '*', &t, '%', 'J');
-        std::string ex(str, iter.base());
-        assert(ex == "J%");
-    }
-    {
-        iter = f.put(output_iterator<char*>(str), ios, '*', &t, 'J');
-        std::string ex(str, iter.base());
-        assert(ex == "J");
-    }
 }
diff --git a/test/std/localization/locales/locale.convenience/conversions/conversions.buffer/lit.local.cfg b/test/std/localization/locales/locale.convenience/conversions/conversions.buffer/lit.local.cfg
new file mode 100644
index 0000000..25ac02b
--- /dev/null
+++ b/test/std/localization/locales/locale.convenience/conversions/conversions.buffer/lit.local.cfg
@@ -0,0 +1,2 @@
+if 'libcpp-has-no-global-filesystem-namespace' in config.available_features:
+    config.unsupported = True
diff --git a/test/std/localization/locales/locale/locale.cons/assign.pass.cpp b/test/std/localization/locales/locale/locale.cons/assign.pass.cpp
index 75ce9b5..80afe1e 100644
--- a/test/std/localization/locales/locale/locale.cons/assign.pass.cpp
+++ b/test/std/localization/locales/locale/locale.cons/assign.pass.cpp
@@ -8,7 +8,7 @@
 //===----------------------------------------------------------------------===//
 
 // REQUIRES: locale.ru_RU.UTF-8
-// UNSUPPORTED: msan, asan
+// UNSUPPORTED: sanitizer-new-delete
 
 // <locale>
 
diff --git a/test/std/localization/locales/locale/locale.cons/char_pointer.pass.cpp b/test/std/localization/locales/locale/locale.cons/char_pointer.pass.cpp
index 01857a4..3567bf5 100644
--- a/test/std/localization/locales/locale/locale.cons/char_pointer.pass.cpp
+++ b/test/std/localization/locales/locale/locale.cons/char_pointer.pass.cpp
@@ -9,7 +9,7 @@
 
 // REQUIRES: locale.ru_RU.UTF-8
 // REQUIRES: locale.zh_CN.UTF-8
-// UNSUPPORTED: msan, asan
+// UNSUPPORTED: sanitizer-new-delete
 
 // <locale>
 
diff --git a/test/std/localization/locales/locale/locale.cons/copy.pass.cpp b/test/std/localization/locales/locale/locale.cons/copy.pass.cpp
index 629c9e6..0760cc4 100644
--- a/test/std/localization/locales/locale/locale.cons/copy.pass.cpp
+++ b/test/std/localization/locales/locale/locale.cons/copy.pass.cpp
@@ -8,7 +8,7 @@
 //===----------------------------------------------------------------------===//
 
 // REQUIRES: locale.fr_FR.UTF-8
-// UNSUPPORTED: msan, asan
+// UNSUPPORTED: sanitizer-new-delete
 
 // <locale>
 
diff --git a/test/std/localization/locales/locale/locale.cons/locale_char_pointer_cat.pass.cpp b/test/std/localization/locales/locale/locale.cons/locale_char_pointer_cat.pass.cpp
index eaadbb9..2a9e20f 100644
--- a/test/std/localization/locales/locale/locale.cons/locale_char_pointer_cat.pass.cpp
+++ b/test/std/localization/locales/locale/locale.cons/locale_char_pointer_cat.pass.cpp
@@ -9,7 +9,7 @@
 
 // REQUIRES: locale.en_US.UTF-8
 // REQUIRES: locale.ru_RU.UTF-8
-// UNSUPPORTED: msan, asan
+// UNSUPPORTED: sanitizer-new-delete
 
 // <locale>
 
diff --git a/test/std/localization/locales/locale/locale.cons/locale_facetptr.pass.cpp b/test/std/localization/locales/locale/locale.cons/locale_facetptr.pass.cpp
index 8b83bc0..fb6e39e 100644
--- a/test/std/localization/locales/locale/locale.cons/locale_facetptr.pass.cpp
+++ b/test/std/localization/locales/locale/locale.cons/locale_facetptr.pass.cpp
@@ -8,7 +8,7 @@
 //===----------------------------------------------------------------------===//
 
 // REQUIRES: locale.ru_RU.UTF-8
-// UNSUPPORTED: msan, asan
+// UNSUPPORTED: sanitizer-new-delete
 
 // <locale>
 
diff --git a/test/std/localization/locales/locale/locale.cons/locale_locale_cat.pass.cpp b/test/std/localization/locales/locale/locale.cons/locale_locale_cat.pass.cpp
index 05f0619..fa87eb2 100644
--- a/test/std/localization/locales/locale/locale.cons/locale_locale_cat.pass.cpp
+++ b/test/std/localization/locales/locale/locale.cons/locale_locale_cat.pass.cpp
@@ -9,7 +9,7 @@
 
 // REQUIRES: locale.en_US.UTF-8
 // REQUIRES: locale.ru_RU.UTF-8
-// UNSUPPORTED: msan, asan
+// UNSUPPORTED: sanitizer-new-delete
 
 // <locale>
 
diff --git a/test/std/localization/locales/locale/locale.cons/locale_string_cat.pass.cpp b/test/std/localization/locales/locale/locale.cons/locale_string_cat.pass.cpp
index 66be76d..d48a572 100644
--- a/test/std/localization/locales/locale/locale.cons/locale_string_cat.pass.cpp
+++ b/test/std/localization/locales/locale/locale.cons/locale_string_cat.pass.cpp
@@ -8,7 +8,7 @@
 //===----------------------------------------------------------------------===//
 
 // REQUIRES: locale.ru_RU.UTF-8
-// UNSUPPORTED: msan, asan
+// UNSUPPORTED: sanitizer-new-delete
 
 // <locale>
 
diff --git a/test/std/localization/locales/locale/locale.cons/string.pass.cpp b/test/std/localization/locales/locale/locale.cons/string.pass.cpp
index 32c3507..c9f9441 100644
--- a/test/std/localization/locales/locale/locale.cons/string.pass.cpp
+++ b/test/std/localization/locales/locale/locale.cons/string.pass.cpp
@@ -9,7 +9,7 @@
 
 // REQUIRES: locale.ru_RU.UTF-8
 // REQUIRES: locale.zh_CN.UTF-8
-// UNSUPPORTED: msan, asan
+// UNSUPPORTED: sanitizer-new-delete
 
 // <locale>
 
diff --git a/test/std/numerics/cfenv/cfenv.syn/cfenv.pass.cpp b/test/std/numerics/cfenv/cfenv.syn/cfenv.pass.cpp
index d46d91f..fcf075a 100644
--- a/test/std/numerics/cfenv/cfenv.syn/cfenv.pass.cpp
+++ b/test/std/numerics/cfenv/cfenv.syn/cfenv.pass.cpp
@@ -60,8 +60,8 @@
 
 int main()
 {
-    std::fenv_t fenv = {0};
-    std::fexcept_t fex = 0;
+    std::fenv_t fenv;
+    std::fexcept_t fex;
     static_assert((std::is_same<decltype(std::feclearexcept(0)), int>::value), "");
     static_assert((std::is_same<decltype(std::fegetexceptflag(&fex, 0)), int>::value), "");
     static_assert((std::is_same<decltype(std::feraiseexcept(0)), int>::value), "");
diff --git a/test/std/numerics/rand/rand.device/ctor.pass.cpp b/test/std/numerics/rand/rand.device/ctor.pass.cpp
index 2d9bc2f..97f46b2 100644
--- a/test/std/numerics/rand/rand.device/ctor.pass.cpp
+++ b/test/std/numerics/rand/rand.device/ctor.pass.cpp
@@ -23,14 +23,12 @@
 #include <unistd.h>
 
 bool is_valid_random_device(const std::string &token) {
-#if defined(_WIN32)
-  return true;
-#elif defined(_LIBCPP_USING_NACL_RANDOM)
-  return token == "/dev/urandom";
-#else  // !defined(_WIN32) && !defined(_LIBCPP_USING_NACL_RANDOM)
+#if defined(_LIBCPP_USING_DEV_RANDOM)
   // Not an exhaustive list: they're the only tokens that are tested below.
   return token == "/dev/urandom" || token == "/dev/random";
-#endif // defined(_WIN32) || defined(_LIBCPP_USING_NACL_RANDOM)
+#else
+  return token == "/dev/urandom";
+#endif
 }
 
 void check_random_device_valid(const std::string &token) {
diff --git a/test/std/re/re.alg/re.alg.match/awk.pass.cpp b/test/std/re/re.alg/re.alg.match/awk.pass.cpp
index d2065a0..e4b2f3e 100644
--- a/test/std/re/re.alg/re.alg.match/awk.pass.cpp
+++ b/test/std/re/re.alg/re.alg.match/awk.pass.cpp
@@ -19,9 +19,10 @@
 
 #include <regex>
 #include <cassert>
-
 #include "test_iterators.h"
 
+#include "platform_support.h" // locale name macros
+
 int main()
 {
 /*    {
@@ -613,7 +614,7 @@
                                                  std::regex_constants::awk)));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
 */    {
         std::cmatch m;
         const char s[] = "m";
@@ -1294,7 +1295,7 @@
                                                  std::regex_constants::awk)));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::wcmatch m;
         const wchar_t s[] = L"m";
diff --git a/test/std/re/re.alg/re.alg.match/basic.pass.cpp b/test/std/re/re.alg/re.alg.match/basic.pass.cpp
index 4139cea..2ddc07a 100644
--- a/test/std/re/re.alg/re.alg.match/basic.pass.cpp
+++ b/test/std/re/re.alg/re.alg.match/basic.pass.cpp
@@ -23,9 +23,10 @@
 
 #include <regex>
 #include <cassert>
-
 #include "test_iterators.h"
 
+#include "platform_support.h" // locale name macros
+
 int main()
 {
     {
@@ -619,7 +620,7 @@
                                                  std::regex_constants::basic)));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::cmatch m;
         const char s[] = "m";
@@ -1287,7 +1288,7 @@
                                                  std::regex_constants::basic)));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::wcmatch m;
         const wchar_t s[] = L"m";
diff --git a/test/std/re/re.alg/re.alg.match/ecma.pass.cpp b/test/std/re/re.alg/re.alg.match/ecma.pass.cpp
index 3854056..785a61c 100644
--- a/test/std/re/re.alg/re.alg.match/ecma.pass.cpp
+++ b/test/std/re/re.alg/re.alg.match/ecma.pass.cpp
@@ -23,9 +23,10 @@
 
 #include <regex>
 #include <cassert>
-
 #include "test_iterators.h"
 
+#include "platform_support.h" // locale name macros
+
 int main()
 {
     {
@@ -581,7 +582,7 @@
         assert(!std::regex_match(s, m, std::regex("[a[.hyphen.]z]")));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::cmatch m;
         const char s[] = "m";
@@ -1246,7 +1247,7 @@
         assert(!std::regex_match(s, m, std::wregex(L"[a[.hyphen.]z]")));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::wcmatch m;
         const wchar_t s[] = L"m";
diff --git a/test/std/re/re.alg/re.alg.match/extended.pass.cpp b/test/std/re/re.alg/re.alg.match/extended.pass.cpp
index c54825d..9ca31d1 100644
--- a/test/std/re/re.alg/re.alg.match/extended.pass.cpp
+++ b/test/std/re/re.alg/re.alg.match/extended.pass.cpp
@@ -23,9 +23,10 @@
 
 #include <regex>
 #include <cassert>
-
 #include "test_iterators.h"
 
+#include "platform_support.h" // locale name macros
+
 int main()
 {
     {
@@ -617,7 +618,7 @@
                                                  std::regex_constants::extended)));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::cmatch m;
         const char s[] = "m";
@@ -1283,7 +1284,7 @@
                                                  std::regex_constants::extended)));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::wcmatch m;
         const wchar_t s[] = L"m";
diff --git a/test/std/re/re.alg/re.alg.search/awk.pass.cpp b/test/std/re/re.alg/re.alg.search/awk.pass.cpp
index 521e98b..7fc1b3f 100644
--- a/test/std/re/re.alg/re.alg.search/awk.pass.cpp
+++ b/test/std/re/re.alg/re.alg.search/awk.pass.cpp
@@ -23,9 +23,10 @@
 
 #include <regex>
 #include <cassert>
-
 #include "test_iterators.h"
 
+#include "platform_support.h" // locale name macros
+
 int main()
 {
     {
@@ -689,7 +690,7 @@
                                                  std::regex_constants::awk)));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::cmatch m;
         const char s[] = "m";
@@ -1460,7 +1461,7 @@
                                                  std::regex_constants::awk)));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::wcmatch m;
         const wchar_t s[] = L"m";
diff --git a/test/std/re/re.alg/re.alg.search/basic.pass.cpp b/test/std/re/re.alg/re.alg.search/basic.pass.cpp
index 838294e..bdfcd9c 100644
--- a/test/std/re/re.alg/re.alg.search/basic.pass.cpp
+++ b/test/std/re/re.alg/re.alg.search/basic.pass.cpp
@@ -23,9 +23,10 @@
 
 #include <regex>
 #include <cassert>
-
 #include "test_iterators.h"
 
+#include "platform_support.h" // locale name macros
+
 int main()
 {
     {
@@ -691,7 +692,7 @@
                                                  std::regex_constants::basic)));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::cmatch m;
         const char s[] = "m";
@@ -1449,7 +1450,7 @@
                                                  std::regex_constants::basic)));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::wcmatch m;
         const wchar_t s[] = L"m";
diff --git a/test/std/re/re.alg/re.alg.search/ecma.pass.cpp b/test/std/re/re.alg/re.alg.search/ecma.pass.cpp
index 2796850..fb9fc26 100644
--- a/test/std/re/re.alg/re.alg.search/ecma.pass.cpp
+++ b/test/std/re/re.alg/re.alg.search/ecma.pass.cpp
@@ -23,9 +23,10 @@
 
 #include <regex>
 #include <cassert>
-
 #include "test_iterators.h"
 
+#include "platform_support.h" // locale name macros
+
 int main()
 {
     {
@@ -671,7 +672,7 @@
         assert(!std::regex_search(s, m, std::regex("[a[.hyphen.]z]")));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::cmatch m;
         const char s[] = "m";
@@ -1450,7 +1451,7 @@
         assert(!std::regex_search(s, m, std::wregex(L"[a[.hyphen.]z]")));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::wcmatch m;
         const wchar_t s[] = L"m";
diff --git a/test/std/re/re.alg/re.alg.search/extended.pass.cpp b/test/std/re/re.alg/re.alg.search/extended.pass.cpp
index a8a121b..81eef2f 100644
--- a/test/std/re/re.alg/re.alg.search/extended.pass.cpp
+++ b/test/std/re/re.alg/re.alg.search/extended.pass.cpp
@@ -23,9 +23,10 @@
 
 #include <regex>
 #include <cassert>
-
 #include "test_iterators.h"
 
+#include "platform_support.h" // locale name macros
+
 int main()
 {
     {
@@ -689,7 +690,7 @@
                                                  std::regex_constants::extended)));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::cmatch m;
         const char s[] = "m";
@@ -1445,7 +1446,7 @@
                                                  std::regex_constants::extended)));
         assert(m.size() == 0);
     }
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     {
         std::wcmatch m;
         const wchar_t s[] = L"m";
diff --git a/test/std/re/re.const/re.matchflag/match_not_bol.pass.cpp b/test/std/re/re.const/re.matchflag/match_not_bol.pass.cpp
new file mode 100644
index 0000000..41ac0ce
--- /dev/null
+++ b/test/std/re/re.const/re.matchflag/match_not_bol.pass.cpp
@@ -0,0 +1,50 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <regex>
+
+// match_not_bol:
+//     The first character in the sequence [first,last) shall be treated as 
+//     though it is not at the beginning of a line, so the character ^ in the 
+//     regular expression shall not match [first,first).
+
+#include <regex>
+#include <cassert>
+
+int main()
+{
+    {
+    std::string target = "foo";
+    std::regex re("^foo");
+    assert( std::regex_match(target, re));
+    assert(!std::regex_match(target, re, std::regex_constants::match_not_bol));
+    }
+
+    {
+    std::string target = "foo";
+    std::regex re("foo");
+    assert( std::regex_match(target, re));
+    assert( std::regex_match(target, re, std::regex_constants::match_not_bol));
+    }
+
+    {
+    std::string target = "fooby";
+    std::regex re("^foo");
+    assert( std::regex_search(target, re));
+    assert(!std::regex_search(target, re, std::regex_constants::match_not_bol));
+    }
+
+    {
+    std::string target = "fooby";
+    std::regex re("foo");
+    assert( std::regex_search(target, re));
+    assert( std::regex_search(target, re, std::regex_constants::match_not_bol));
+    }
+}
diff --git a/test/std/re/re.const/re.matchflag/match_not_eol.pass.cpp b/test/std/re/re.const/re.matchflag/match_not_eol.pass.cpp
new file mode 100644
index 0000000..594c9fb
--- /dev/null
+++ b/test/std/re/re.const/re.matchflag/match_not_eol.pass.cpp
@@ -0,0 +1,50 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <regex>
+
+// match_not_eol:
+//     The last character in the sequence [first,last) shall be treated as 
+//     though it is not at the end of a line, so the character "$" in 
+//     the regular expression shall not match [last,last).
+
+#include <regex>
+#include <cassert>
+
+int main()
+{
+    {
+    std::string target = "foo";
+    std::regex re("foo$");
+    assert( std::regex_match(target, re));
+    assert(!std::regex_match(target, re, std::regex_constants::match_not_eol));
+    }
+
+    {
+    std::string target = "foo";
+    std::regex re("foo");
+    assert( std::regex_match(target, re));
+    assert( std::regex_match(target, re, std::regex_constants::match_not_eol));
+    }
+
+    {
+    std::string target = "refoo";
+    std::regex re("foo$");
+    assert( std::regex_search(target, re));
+    assert(!std::regex_search(target, re, std::regex_constants::match_not_eol));
+    }
+
+    {
+    std::string target = "refoo";
+    std::regex re("foo");
+    assert( std::regex_search(target, re));
+    assert( std::regex_search(target, re, std::regex_constants::match_not_eol));
+    }
+}
diff --git a/test/std/re/re.regex/re.regex.construct/bad_escape.pass.cpp b/test/std/re/re.regex/re.regex.construct/bad_escape.pass.cpp
index 9455527..ddf2607 100644
--- a/test/std/re/re.regex/re.regex.construct/bad_escape.pass.cpp
+++ b/test/std/re/re.regex/re.regex.construct/bad_escape.pass.cpp
@@ -22,7 +22,7 @@
     bool result = false;
     try {
         std::regex re(pat);
-    } catch (std::regex_error &ex) {
+    } catch (const std::regex_error &ex) {
         result = (ex.code() == std::regex_constants::error_escape);
     }
     return result;
diff --git a/test/std/re/re.regex/re.regex.construct/bad_repeat.pass.cpp b/test/std/re/re.regex/re.regex.construct/bad_repeat.pass.cpp
new file mode 100644
index 0000000..bc70ec1
--- /dev/null
+++ b/test/std/re/re.regex/re.regex.construct/bad_repeat.pass.cpp
@@ -0,0 +1,42 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <regex>
+
+// template <class charT, class traits = regex_traits<charT>> class basic_regex;
+
+// template <class ST, class SA>
+//    basic_regex(const basic_string<charT, ST, SA>& s);
+
+#include <regex>
+#include <cassert>
+
+static bool error_badrepeat_thrown(const char *pat) 
+{
+    bool result = false;
+    try {
+        std::regex re(pat);
+    } catch (const std::regex_error &ex) {
+        result = (ex.code() == std::regex_constants::error_badrepeat);
+    }
+    return result;
+}
+
+int main() 
+{
+    assert(error_badrepeat_thrown("?a"));
+    assert(error_badrepeat_thrown("*a"));
+    assert(error_badrepeat_thrown("+a"));
+    assert(error_badrepeat_thrown("{a"));
+
+    assert(error_badrepeat_thrown("?(a+)"));
+    assert(error_badrepeat_thrown("*(a+)"));
+    assert(error_badrepeat_thrown("+(a+)"));
+    assert(error_badrepeat_thrown("{(a+)"));
+}
diff --git a/test/std/re/re.traits/lookup_collatename.pass.cpp b/test/std/re/re.traits/lookup_collatename.pass.cpp
index d495f8a..a7cd5f0 100644
--- a/test/std/re/re.traits/lookup_collatename.pass.cpp
+++ b/test/std/re/re.traits/lookup_collatename.pass.cpp
@@ -25,6 +25,8 @@
 #include <cassert>
 #include "test_iterators.h"
 
+#include "platform_support.h" // locale name macros
+
 template <class char_type>
 void
 test(const char_type* A, const std::basic_string<char_type>& expected)
@@ -108,7 +110,7 @@
 
     test("tild", std::string(""));
     test("ch", std::string(""));
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     test("ch", std::string("ch"));
     std::locale::global(std::locale("C"));
 
@@ -184,7 +186,7 @@
 
     test(L"tild", std::wstring(L""));
     test(L"ch", std::wstring(L""));
-    std::locale::global(std::locale("cs_CZ.ISO8859-2"));
+    std::locale::global(std::locale(LOCALE_cs_CZ_ISO8859_2));
     test(L"ch", std::wstring(L"ch"));
     std::locale::global(std::locale("C"));
 }
diff --git a/test/std/re/re.traits/transform.pass.cpp b/test/std/re/re.traits/transform.pass.cpp
index c3bce79..85235e0 100644
--- a/test/std/re/re.traits/transform.pass.cpp
+++ b/test/std/re/re.traits/transform.pass.cpp
@@ -21,6 +21,8 @@
 #include <cassert>
 #include "test_iterators.h"
 
+#include "platform_support.h" // locale name macros
+
 int main()
 {
     {
@@ -29,7 +31,7 @@
         const char B[] = "B";
         typedef forward_iterator<const char*> F;
         assert(t.transform(F(a), F(a+1)) > t.transform(F(B), F(B+1)));
-        t.imbue(std::locale("cs_CZ.ISO8859-2"));
+        t.imbue(std::locale(LOCALE_cs_CZ_ISO8859_2));
         assert(t.transform(F(a), F(a+1)) < t.transform(F(B), F(B+1)));
     }
     {
@@ -38,7 +40,7 @@
         const wchar_t B[] = L"B";
         typedef forward_iterator<const wchar_t*> F;
         assert(t.transform(F(a), F(a+1)) > t.transform(F(B), F(B+1)));
-        t.imbue(std::locale("cs_CZ.ISO8859-2"));
+        t.imbue(std::locale(LOCALE_cs_CZ_ISO8859_2));
         assert(t.transform(F(a), F(a+1)) < t.transform(F(B), F(B+1)));
     }
 }
diff --git a/test/std/re/re.traits/transform_primary.pass.cpp b/test/std/re/re.traits/transform_primary.pass.cpp
index 28734d6..438cd75 100644
--- a/test/std/re/re.traits/transform_primary.pass.cpp
+++ b/test/std/re/re.traits/transform_primary.pass.cpp
@@ -22,6 +22,8 @@
 #include <cassert>
 #include "test_iterators.h"
 
+#include "platform_support.h" // locale name macros
+
 int main()
 {
     {
@@ -31,7 +33,7 @@
         typedef forward_iterator<const char*> F;
         assert(t.transform_primary(F(A), F(A+1)) !=
                t.transform_primary(F(Aacute), F(Aacute+1)));
-        t.imbue(std::locale("cs_CZ.ISO8859-2"));
+        t.imbue(std::locale(LOCALE_cs_CZ_ISO8859_2));
         assert(t.transform_primary(F(A), F(A+1)) ==
                t.transform_primary(F(Aacute), F(Aacute+1)));
     }
@@ -42,7 +44,7 @@
         typedef forward_iterator<const wchar_t*> F;
         assert(t.transform_primary(F(A), F(A+1)) !=
                t.transform_primary(F(Aacute), F(Aacute+1)));
-        t.imbue(std::locale("cs_CZ.ISO8859-2"));
+        t.imbue(std::locale(LOCALE_cs_CZ_ISO8859_2));
         assert(t.transform_primary(F(A), F(A+1)) ==
                t.transform_primary(F(Aacute), F(Aacute+1)));
     }
diff --git a/test/std/strings/basic.string/string.capacity/max_size.pass.cpp b/test/std/strings/basic.string/string.capacity/max_size.pass.cpp
index f426425..e4ff556 100644
--- a/test/std/strings/basic.string/string.capacity/max_size.pass.cpp
+++ b/test/std/strings/basic.string/string.capacity/max_size.pass.cpp
@@ -16,7 +16,7 @@
 //    returns null.
 // 2. If allocator_may_return_null=1 then they will fail because the allocation
 //    is too large to succeed.
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <string>
 #include <cassert>
diff --git a/test/std/strings/basic.string/string.cons/alloc.pass.cpp b/test/std/strings/basic.string/string.cons/alloc.pass.cpp
index 512d118..1c4f204 100644
--- a/test/std/strings/basic.string/string.cons/alloc.pass.cpp
+++ b/test/std/strings/basic.string/string.cons/alloc.pass.cpp
@@ -14,6 +14,7 @@
 #include <string>
 #include <cassert>
 
+#include "test_macros.h"
 #include "test_allocator.h"
 #include "min_allocator.h"
 
@@ -22,6 +23,11 @@
 test()
 {
     {
+#if TEST_STD_VER > 14
+	static_assert((noexcept(S{})), "" );
+#elif TEST_STD_VER >= 11
+	static_assert((noexcept(S()) == noexcept(typename S::allocator_type())), "" );
+#endif
     S s;
     assert(s.__invariants());
     assert(s.data());
@@ -30,6 +36,11 @@
     assert(s.get_allocator() == typename S::allocator_type());
     }
     {
+#if TEST_STD_VER > 14
+	static_assert((noexcept(S{typename S::allocator_type{}})), "" );
+#elif TEST_STD_VER >= 11
+	static_assert((noexcept(S(typename S::allocator_type())) == std::is_nothrow_copy_constructible<typename S::allocator_type>::value), "" );
+#endif
     S s(typename S::allocator_type(5));
     assert(s.__invariants());
     assert(s.data());
@@ -39,13 +50,18 @@
     }
 }
 
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
 
 template <class S>
 void
 test2()
 {
     {
+#if TEST_STD_VER > 14
+	static_assert((noexcept(S{})), "" );
+#elif TEST_STD_VER >= 11
+	static_assert((noexcept(S()) == noexcept(typename S::allocator_type())), "" );
+#endif
     S s;
     assert(s.__invariants());
     assert(s.data());
@@ -54,6 +70,11 @@
     assert(s.get_allocator() == typename S::allocator_type());
     }
     {
+#if TEST_STD_VER > 14
+	static_assert((noexcept(S{typename S::allocator_type{}})), "" );
+#elif TEST_STD_VER >= 11
+	static_assert((noexcept(S(typename S::allocator_type())) == std::is_nothrow_copy_constructible<typename S::allocator_type>::value), "" );
+#endif
     S s(typename S::allocator_type{});
     assert(s.__invariants());
     assert(s.data());
@@ -68,7 +89,7 @@
 int main()
 {
     test<std::basic_string<char, std::char_traits<char>, test_allocator<char> > >();
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     test2<std::basic_string<char, std::char_traits<char>, min_allocator<char> > >();
 #endif
 }
diff --git a/test/std/strings/basic.string/string.cons/default_noexcept.pass.cpp b/test/std/strings/basic.string/string.cons/default_noexcept.pass.cpp
index f935db8..af11710 100644
--- a/test/std/strings/basic.string/string.cons/default_noexcept.pass.cpp
+++ b/test/std/strings/basic.string/string.cons/default_noexcept.pass.cpp
@@ -17,6 +17,7 @@
 #include <string>
 #include <cassert>
 
+#include "test_macros.h"
 #include "test_allocator.h"
 
 template <class T>
diff --git a/test/std/strings/basic.string/string.cons/move_alloc.pass.cpp b/test/std/strings/basic.string/string.cons/move_alloc.pass.cpp
index 1f96314..a232a46 100644
--- a/test/std/strings/basic.string/string.cons/move_alloc.pass.cpp
+++ b/test/std/strings/basic.string/string.cons/move_alloc.pass.cpp
@@ -16,6 +16,7 @@
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
+#include "test_macros.h"
 #include "test_allocator.h"
 #include "min_allocator.h"
 
@@ -34,6 +35,11 @@
 }
 
 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
+// #if _LIBCPP_STD_VER <= 14
+//         _NOEXCEPT_(is_nothrow_move_constructible<allocator_type>::value);
+// #else
+//         _NOEXCEPT;
+// #endif
 
 int main()
 {
@@ -41,6 +47,11 @@
     {
     typedef test_allocator<char> A;
     typedef std::basic_string<char, std::char_traits<char>, A> S;
+#if TEST_STD_VER > 14
+	static_assert((noexcept(S{})), "" );
+#elif TEST_STD_VER >= 11
+	static_assert((noexcept(S()) == std::is_nothrow_move_constructible<A>::value), "" );
+#endif
     test(S(), A(3));
     test(S("1"), A(5));
     test(S("1234567890123456789012345678901234567890123456789012345678901234567890"), A(7));
@@ -50,15 +61,25 @@
     {
     typedef test_allocator<char> A;
     typedef std::basic_string<char, std::char_traits<char>, A> S;
+#if TEST_STD_VER > 14
+	static_assert((noexcept(S{})), "" );
+#elif TEST_STD_VER >= 11
+	static_assert((noexcept(S()) == std::is_nothrow_move_constructible<A>::value), "" );
+#endif
     S s1 ( "Twas brillig, and the slivy toves did gyre and gymbal in the wabe" );
     S s2 (std::move(s1), A(1));
     }
     assert ( test_alloc_base::alloc_count == alloc_count );
     
-#if __cplusplus >= 201103L
+#if TEST_STD_VER >= 11
     {
     typedef min_allocator<char> A;
     typedef std::basic_string<char, std::char_traits<char>, A> S;
+#if TEST_STD_VER > 14
+	static_assert((noexcept(S{})), "" );
+#elif TEST_STD_VER >= 11
+	static_assert((noexcept(S()) == std::is_nothrow_move_constructible<A>::value), "" );
+#endif
     test(S(), A());
     test(S("1"), A());
     test(S("1234567890123456789012345678901234567890123456789012345678901234567890"), A());
diff --git a/test/std/strings/basic.string/string.cons/move_noexcept.pass.cpp b/test/std/strings/basic.string/string.cons/move_noexcept.pass.cpp
index 556aabd..b287a94 100644
--- a/test/std/strings/basic.string/string.cons/move_noexcept.pass.cpp
+++ b/test/std/strings/basic.string/string.cons/move_noexcept.pass.cpp
@@ -17,6 +17,7 @@
 #include <string>
 #include <cassert>
 
+#include "test_macros.h"
 #include "test_allocator.h"
 
 template <class T>
@@ -39,7 +40,11 @@
     }
     {
         typedef std::basic_string<char, std::char_traits<char>, some_alloc<char>> C;
+#if TEST_STD_VER <= 14
         static_assert(!std::is_nothrow_move_constructible<C>::value, "");
+#else
+        static_assert( std::is_nothrow_move_constructible<C>::value, "");
+#endif
     }
 #endif
 }
diff --git a/test/std/strings/basic.string/string.nonmembers/string.special/swap_noexcept.pass.cpp b/test/std/strings/basic.string/string.nonmembers/string.special/swap_noexcept.pass.cpp
index 4d5d796..cfe0365 100644
--- a/test/std/strings/basic.string/string.nonmembers/string.special/swap_noexcept.pass.cpp
+++ b/test/std/strings/basic.string/string.nonmembers/string.special/swap_noexcept.pass.cpp
@@ -12,6 +12,10 @@
 // void swap(basic_string& c)
 //     noexcept(!allocator_type::propagate_on_container_swap::value ||
 //              __is_nothrow_swappable<allocator_type>::value);
+//
+//  In C++17, the standard says that swap shall have:
+//     noexcept(allocator_traits<Allocator>::propagate_on_container_swap::value ||
+//              allocator_traits<Allocator>::is_always_equal::value);
 
 // This tests a conforming extension
 
@@ -32,6 +36,19 @@
     typedef std::true_type propagate_on_container_swap;
 };
 
+template <class T>
+struct some_alloc2
+{
+    typedef T value_type;
+    
+    some_alloc2() {}
+    some_alloc2(const some_alloc2&);
+    void deallocate(void*, unsigned) {}
+
+    typedef std::false_type propagate_on_container_swap;
+    typedef std::true_type is_always_equal;
+};
+
 int main()
 {
 #if __has_feature(cxx_noexcept)
@@ -48,7 +65,21 @@
     {
         typedef std::basic_string<char, std::char_traits<char>, some_alloc<char>> C;
         C c1, c2;
+#if TEST_STD_VER >= 14
+    //  In c++14, if POCS is set, swapping the allocator is required not to throw
+        static_assert( noexcept(swap(c1, c2)), "");
+#else
         static_assert(!noexcept(swap(c1, c2)), "");
+#endif
     }
+#if TEST_STD_VER >= 14
+    {
+        typedef std::basic_string<char, std::char_traits<char>, some_alloc2<char>> C;
+        C c1, c2;
+    //  if the allocators are always equal, then the swap can be noexcept
+        static_assert( noexcept(swap(c1, c2)), "");
+    }
+#endif
+
 #endif
 }
diff --git a/test/std/strings/basic.string/string.require/contiguous.pass.cpp b/test/std/strings/basic.string/string.require/contiguous.pass.cpp
new file mode 100644
index 0000000..ca31ace
--- /dev/null
+++ b/test/std/strings/basic.string/string.require/contiguous.pass.cpp
@@ -0,0 +1,53 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <array>
+
+// An string is a contiguous container
+
+#include <string>
+#include <cassert>
+
+#include "test_allocator.h"
+#include "min_allocator.h"
+
+
+template <class C>
+void test_contiguous ( const C &c )
+{
+    for ( size_t i = 0; i < c.size(); ++i )
+        assert ( *(c.begin() + i) == *(std::addressof(*c.begin()) + i));
+}
+
+int main()
+{
+    {
+    typedef std::string S;
+    test_contiguous(S());
+    test_contiguous(S("1"));
+    test_contiguous(S("1234567890123456789012345678901234567890123456789012345678901234567890"));
+    }
+
+    {
+    typedef test_allocator<char> A;
+    typedef std::basic_string<char, std::char_traits<char>, A> S;
+    test_contiguous(S(A(3)));
+    test_contiguous(S("1", A(5)));
+    test_contiguous(S("1234567890123456789012345678901234567890123456789012345678901234567890", A(7)));
+    }
+#if __cplusplus >= 201103L
+    {
+    typedef min_allocator<char> A;
+    typedef std::basic_string<char, std::char_traits<char>, A> S;
+    test_contiguous(S(A{}));
+    test_contiguous(S("1", A()));
+    test_contiguous(S("1234567890123456789012345678901234567890123456789012345678901234567890", A()));
+    }
+#endif
+}
diff --git a/test/std/strings/c.strings/cstring.pass.cpp b/test/std/strings/c.strings/cstring.pass.cpp
index 5ed7e6c..20f4050 100644
--- a/test/std/strings/c.strings/cstring.pass.cpp
+++ b/test/std/strings/c.strings/cstring.pass.cpp
@@ -46,7 +46,9 @@
     static_assert((std::is_same<decltype(std::strspn(cpc, cpc)), std::size_t>::value), "");
 //    static_assert((std::is_same<decltype(std::strstr(cpc, cpc)), const char*>::value), "");
     static_assert((std::is_same<decltype(std::strstr(cp, cpc)), char*>::value), "");
+#ifndef _LIBCPP_HAS_NO_THREAD_UNSAFE_C_FUNCTIONS
     static_assert((std::is_same<decltype(std::strtok(cp, cpc)), char*>::value), "");
+#endif
     static_assert((std::is_same<decltype(std::memset(vp, 0, s)), void*>::value), "");
     static_assert((std::is_same<decltype(std::strerror(0)), char*>::value), "");
     static_assert((std::is_same<decltype(std::strlen(cpc)), std::size_t>::value), "");
diff --git a/test/std/strings/c.strings/cwchar.pass.cpp b/test/std/strings/c.strings/cwchar.pass.cpp
index d0481b7..c3d868f 100644
--- a/test/std/strings/c.strings/cwchar.pass.cpp
+++ b/test/std/strings/c.strings/cwchar.pass.cpp
@@ -50,19 +50,13 @@
     static_assert((std::is_same<decltype(std::vfwscanf(fp, L"", va)), int>::value), "");
     static_assert((std::is_same<decltype(std::vswprintf(ws, s, L"", va)), int>::value), "");
     static_assert((std::is_same<decltype(std::vswscanf(L"", L"", va)), int>::value), "");
-    static_assert((std::is_same<decltype(std::vwprintf(L"", va)), int>::value), "");
-    static_assert((std::is_same<decltype(std::vwscanf(L"", va)), int>::value), "");
-    static_assert((std::is_same<decltype(std::wprintf(L"")), int>::value), "");
-    static_assert((std::is_same<decltype(std::wscanf(L"")), int>::value), "");
     static_assert((std::is_same<decltype(std::fgetwc(fp)), std::wint_t>::value), "");
     static_assert((std::is_same<decltype(std::fgetws(ws, 0, fp)), wchar_t*>::value), "");
     static_assert((std::is_same<decltype(std::fputwc(L' ', fp)), std::wint_t>::value), "");
     static_assert((std::is_same<decltype(std::fputws(L"", fp)), int>::value), "");
     static_assert((std::is_same<decltype(std::fwide(fp, 0)), int>::value), "");
     static_assert((std::is_same<decltype(std::getwc(fp)), std::wint_t>::value), "");
-    static_assert((std::is_same<decltype(std::getwchar()), std::wint_t>::value), "");
     static_assert((std::is_same<decltype(std::putwc(L' ', fp)), std::wint_t>::value), "");
-    static_assert((std::is_same<decltype(std::putwchar(L' ')), std::wint_t>::value), "");
     static_assert((std::is_same<decltype(std::ungetwc(L' ', fp)), std::wint_t>::value), "");
     static_assert((std::is_same<decltype(std::wcstod(L"", (wchar_t**)0)), double>::value), "");
     static_assert((std::is_same<decltype(std::wcstof(L"", (wchar_t**)0)), float>::value), "");
@@ -106,4 +100,16 @@
     static_assert((std::is_same<decltype(std::wcrtomb(ns, L' ', &mb)), std::size_t>::value), "");
     static_assert((std::is_same<decltype(std::mbsrtowcs(ws, (const char**)0, s, &mb)), std::size_t>::value), "");
     static_assert((std::is_same<decltype(std::wcsrtombs(ns, (const wchar_t**)0, s, &mb)), std::size_t>::value), "");
+
+#ifndef _LIBCPP_HAS_NO_STDIN
+    static_assert((std::is_same<decltype(std::getwchar()), std::wint_t>::value), "");
+    static_assert((std::is_same<decltype(std::vwscanf(L"", va)), int>::value), "");
+    static_assert((std::is_same<decltype(std::wscanf(L"")), int>::value), "");
+#endif
+
+#ifndef _LIBCPP_HAS_NO_STDOUT
+    static_assert((std::is_same<decltype(std::putwchar(L' ')), std::wint_t>::value), "");
+    static_assert((std::is_same<decltype(std::vwprintf(L"", va)), int>::value), "");
+    static_assert((std::is_same<decltype(std::wprintf(L"")), int>::value), "");
+#endif
 }
diff --git a/test/std/thread/futures/futures.async/async.pass.cpp b/test/std/thread/futures/futures.async/async.pass.cpp
index c8a7425..6cfed59 100644
--- a/test/std/thread/futures/futures.async/async.pass.cpp
+++ b/test/std/thread/futures/futures.async/async.pass.cpp
@@ -8,6 +8,7 @@
 //===----------------------------------------------------------------------===//
 //
 // UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++98, c++03
 
 // <future>
 
diff --git a/test/std/thread/futures/futures.async/async_race.pass.cpp b/test/std/thread/futures/futures.async/async_race.pass.cpp
new file mode 100644
index 0000000..9acdd1a
--- /dev/null
+++ b/test/std/thread/futures/futures.async/async_race.pass.cpp
@@ -0,0 +1,68 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++98, c++03
+
+// <future>
+
+// template <class F, class... Args>
+//     future<typename result_of<F(Args...)>::type>
+//     async(F&& f, Args&&... args);
+
+// template <class F, class... Args>
+//     future<typename result_of<F(Args...)>::type>
+//     async(launch policy, F&& f, Args&&... args);
+
+// This test is designed to cause and allow TSAN to detect the race condition
+// reported in PR23293. (http://llvm.org/PR23293).
+
+#include <future>
+#include <chrono>
+#include <thread>
+#include <memory>
+#include <cassert>
+
+int f_async() {
+    typedef std::chrono::milliseconds ms;
+    std::this_thread::sleep_for(ms(200));
+    return 42;
+}
+
+bool ran = false;
+
+int f_deferred() {
+    ran = true;
+    return 42;
+}
+
+void test_each() {
+    {
+        std::future<int> f = std::async(f_async);
+        int const result = f.get();
+        assert(result == 42);
+    }
+    {
+        std::future<int> f = std::async(std::launch::async, f_async);
+        int const result = f.get();
+        assert(result == 42);
+    }
+    {
+        ran = false;
+        std::future<int> f = std::async(std::launch::deferred, f_deferred);
+        assert(ran == false);
+        int const result = f.get();
+        assert(ran == true);
+        assert(result == 42);
+    }
+}
+
+int main() {
+    for (int i=0; i < 25; ++i) test_each();
+}
diff --git a/test/std/thread/futures/futures.tas/futures.task.members/ctor2.fail.cpp b/test/std/thread/futures/futures.tas/futures.task.members/ctor2.fail.cpp
index e81adfa..e4df4ec 100644
--- a/test/std/thread/futures/futures.tas/futures.task.members/ctor2.fail.cpp
+++ b/test/std/thread/futures/futures.tas/futures.task.members/ctor2.fail.cpp
@@ -11,7 +11,7 @@
 
 // class packaged_task<R(ArgTypes...)>
 // template <class F, class Allocator>
-//   explicit packaged_task(allocator_arg_t, const Allocator& a, F&& f);
+//   packaged_task(allocator_arg_t, const Allocator& a, F&& f);
 // These constructors shall not participate in overload resolution if 
 //    decay<F>::type is the same type as std::packaged_task<R(ArgTypes...)>.
 
diff --git a/test/std/thread/thread.mutex/thread.lock/thread.lock.shared/thread.lock.shared.cons/mutex_adopt_lock.pass.cpp b/test/std/thread/thread.mutex/thread.lock/thread.lock.shared/thread.lock.shared.cons/mutex_adopt_lock.pass.cpp
index 9082e57..3b49b30 100644
--- a/test/std/thread/thread.mutex/thread.lock/thread.lock.shared/thread.lock.shared.cons/mutex_adopt_lock.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.lock/thread.lock.shared/thread.lock.shared.cons/mutex_adopt_lock.pass.cpp
@@ -22,7 +22,7 @@
 {
 #if _LIBCPP_STD_VER > 11
     std::shared_timed_mutex m;
-    m.lock();
+    m.lock_shared();
     std::shared_lock<std::shared_timed_mutex> lk(m, std::adopt_lock);
     assert(lk.mutex() == &m);
     assert(lk.owns_lock() == true);
diff --git a/test/std/containers/sequences/dynarray/nothing_to_do.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/nothing_to_do.pass.cpp
similarity index 100%
copy from test/std/containers/sequences/dynarray/nothing_to_do.pass.cpp
copy to test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/nothing_to_do.pass.cpp
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/assign.fail.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/assign.fail.cpp
new file mode 100644
index 0000000..7bcb2d6
--- /dev/null
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/assign.fail.cpp
@@ -0,0 +1,29 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <shared_mutex>
+
+// class shared_mutex;
+
+// shared_mutex& operator=(const shared_mutex&) = delete;
+
+#include <shared_mutex>
+
+#include "test_macros.h"
+
+int main()
+{
+#if TEST_STD_VER > 14
+    std::shared_mutex m0;
+    std::shared_mutex m1;
+    m1 = m0;
+#else
+#   error
+#endif
+}
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/no-variadics.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/copy.fail.cpp
similarity index 60%
copy from test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/no-variadics.pass.cpp
copy to test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/copy.fail.cpp
index 7099c45..af064ae 100644
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/no-variadics.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/copy.fail.cpp
@@ -7,18 +7,22 @@
 //
 //===----------------------------------------------------------------------===//
 
-// <functional>
+// <shared_mutex>
 
-// class function<R()>
+// class shared_mutex;
 
-// template<class F> function(F);
+// shared_mutex(const shared_mutex&) = delete;
 
-#define _LIBCPP_HAS_NO_VARIADICS
-#include <functional>
-#include <cassert>
+#include <shared_mutex>
+
+#include "test_macros.h"
 
 int main()
 {
-    std::function<void()> f(static_cast<void(*)()>(0));
-    assert(!f);
+#if TEST_STD_VER > 14
+    std::shared_mutex m0;
+    std::shared_mutex m1(m0);
+#else
+#   error
+#endif
 }
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/default.pass.cpp
similarity index 64%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/default.pass.cpp
index b58f5c5..c61a93a 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/default.pass.cpp
@@ -6,7 +6,19 @@
 // Source Licenses. See LICENSE.TXT for details.
 //
 //===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11, c++14
+
+// <shared_mutex>
+
+// class shared_mutex;
+
+// shared_mutex();
+
+#include <shared_mutex>
 
 int main()
 {
+    std::shared_mutex m;
 }
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/lock.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/lock.pass.cpp
new file mode 100644
index 0000000..9bf7a79
--- /dev/null
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/lock.pass.cpp
@@ -0,0 +1,50 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11, c++14
+
+// <shared_mutex>
+
+// class shared_mutex;
+
+// void lock();
+
+#include <shared_mutex>
+#include <thread>
+#include <cstdlib>
+#include <cassert>
+
+
+std::shared_mutex m;
+
+typedef std::chrono::system_clock Clock;
+typedef Clock::time_point time_point;
+typedef Clock::duration duration;
+typedef std::chrono::milliseconds ms;
+typedef std::chrono::nanoseconds ns;
+
+void f()
+{
+    time_point t0 = Clock::now();
+    m.lock();
+    time_point t1 = Clock::now();
+    m.unlock();
+    ns d = t1 - t0 - ms(250);
+    assert(d < ms(50));  // within 50ms
+}
+
+int main()
+{
+    m.lock();
+    std::thread t(f);
+    std::this_thread::sleep_for(ms(250));
+    m.unlock();
+    t.join();
+}
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/lock_shared.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/lock_shared.pass.cpp
new file mode 100644
index 0000000..3ffa9e2
--- /dev/null
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/lock_shared.pass.cpp
@@ -0,0 +1,73 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11, c++14
+
+// <shared_mutex>
+
+// class shared_mutex;
+
+// void lock_shared();
+
+#include <shared_mutex>
+#include <thread>
+#include <vector>
+#include <cstdlib>
+#include <cassert>
+
+std::shared_mutex m;
+
+typedef std::chrono::system_clock Clock;
+typedef Clock::time_point time_point;
+typedef Clock::duration duration;
+typedef std::chrono::milliseconds ms;
+typedef std::chrono::nanoseconds ns;
+
+void f()
+{
+    time_point t0 = Clock::now();
+    m.lock_shared();
+    time_point t1 = Clock::now();
+    m.unlock_shared();
+    ns d = t1 - t0 - ms(250);
+    assert(d < ms(50));  // within 50ms
+}
+
+void g()
+{
+    time_point t0 = Clock::now();
+    m.lock_shared();
+    time_point t1 = Clock::now();
+    m.unlock_shared();
+    ns d = t1 - t0;
+    assert(d < ms(50));  // within 50ms
+}
+
+
+int main()
+{
+    m.lock();
+    std::vector<std::thread> v;
+    for (int i = 0; i < 5; ++i)
+        v.push_back(std::thread(f));
+    std::this_thread::sleep_for(ms(250));
+    m.unlock();
+    for (auto& t : v)
+        t.join();
+    m.lock_shared();
+    for (auto& t : v)
+        t = std::thread(g);
+    std::thread q(f);
+    std::this_thread::sleep_for(ms(250));
+    m.unlock_shared();
+    for (auto& t : v)
+        t.join();
+    q.join();
+}
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/try_lock.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/try_lock.pass.cpp
new file mode 100644
index 0000000..6f3ca24
--- /dev/null
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/try_lock.pass.cpp
@@ -0,0 +1,53 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11, c++14
+
+// <shared_mutex>
+
+// class shared_mutex;
+
+// bool try_lock();
+
+#include <shared_mutex>
+#include <thread>
+#include <cstdlib>
+#include <cassert>
+
+std::shared_mutex m;
+
+typedef std::chrono::system_clock Clock;
+typedef Clock::time_point time_point;
+typedef Clock::duration duration;
+typedef std::chrono::milliseconds ms;
+typedef std::chrono::nanoseconds ns;
+
+void f()
+{
+    time_point t0 = Clock::now();
+    assert(!m.try_lock());
+    assert(!m.try_lock());
+    assert(!m.try_lock());
+    while(!m.try_lock())
+        ;
+    time_point t1 = Clock::now();
+    m.unlock();
+    ns d = t1 - t0 - ms(250);
+    assert(d < ms(200));  // within 200ms
+}
+
+int main()
+{
+    m.lock();
+    std::thread t(f);
+    std::this_thread::sleep_for(ms(250));
+    m.unlock();
+    t.join();
+}
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/try_lock_shared.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/try_lock_shared.pass.cpp
new file mode 100644
index 0000000..5200715
--- /dev/null
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.shared_mutex.requirements/thread.shared_mutex.class/try_lock_shared.pass.cpp
@@ -0,0 +1,58 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11, c++14
+
+// <shared_mutex>
+
+// class shared_mutex;
+
+// bool try_lock_shared();
+
+#include <shared_mutex>
+#include <thread>
+#include <vector>
+#include <cstdlib>
+#include <cassert>
+
+std::shared_mutex m;
+
+typedef std::chrono::system_clock Clock;
+typedef Clock::time_point time_point;
+typedef Clock::duration duration;
+typedef std::chrono::milliseconds ms;
+typedef std::chrono::nanoseconds ns;
+
+void f()
+{
+    time_point t0 = Clock::now();
+    assert(!m.try_lock_shared());
+    assert(!m.try_lock_shared());
+    assert(!m.try_lock_shared());
+    while(!m.try_lock_shared())
+        ;
+    time_point t1 = Clock::now();
+    m.unlock_shared();
+    ns d = t1 - t0 - ms(250);
+    assert(d < ms(200));  // within 200ms
+}
+
+
+int main()
+{
+    m.lock();
+    std::vector<std::thread> v;
+    for (int i = 0; i < 5; ++i)
+        v.push_back(std::thread(f));
+    std::this_thread::sleep_for(ms(250));
+    m.unlock();
+    for (auto& t : v)
+        t.join();
+}
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/default.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/default.pass.cpp
index a90b6c9..45cd563 100644
--- a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/default.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/default.pass.cpp
@@ -8,6 +8,7 @@
 //===----------------------------------------------------------------------===//
 //
 // UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11
 
 // <shared_mutex>
 
@@ -19,7 +20,5 @@
 
 int main()
 {
-#if _LIBCPP_STD_VER > 11
     std::shared_timed_mutex m;
-#endif
 }
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/lock.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/lock.pass.cpp
index b4f9ba3..62bb736 100644
--- a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/lock.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/lock.pass.cpp
@@ -8,6 +8,7 @@
 //===----------------------------------------------------------------------===//
 //
 // UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11
 
 // <shared_mutex>
 
@@ -20,8 +21,6 @@
 #include <cstdlib>
 #include <cassert>
 
-#if _LIBCPP_STD_VER > 11
-
 std::shared_timed_mutex m;
 
 typedef std::chrono::system_clock Clock;
@@ -40,15 +39,11 @@
     assert(d < ms(50));  // within 50ms
 }
 
-#endif  // _LIBCPP_STD_VER > 11
-
 int main()
 {
-#if _LIBCPP_STD_VER > 11
     m.lock();
     std::thread t(f);
     std::this_thread::sleep_for(ms(250));
     m.unlock();
     t.join();
-#endif  // _LIBCPP_STD_VER > 11
 }
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/lock_shared.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/lock_shared.pass.cpp
index ac5e206..8fc6299 100644
--- a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/lock_shared.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/lock_shared.pass.cpp
@@ -8,6 +8,7 @@
 //===----------------------------------------------------------------------===//
 //
 // UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11
 
 // <shared_mutex>
 
@@ -21,8 +22,6 @@
 #include <cstdlib>
 #include <cassert>
 
-#if _LIBCPP_STD_VER > 11
-
 std::shared_timed_mutex m;
 
 typedef std::chrono::system_clock Clock;
@@ -51,11 +50,9 @@
     assert(d < ms(50));  // within 50ms
 }
 
-#endif  // _LIBCPP_STD_VER > 11
 
 int main()
 {
-#if _LIBCPP_STD_VER > 11
     m.lock();
     std::vector<std::thread> v;
     for (int i = 0; i < 5; ++i)
@@ -73,5 +70,4 @@
     for (auto& t : v)
         t.join();
     q.join();
-#endif  // _LIBCPP_STD_VER > 11
 }
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock.pass.cpp
index 33b0696..61900ba 100644
--- a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock.pass.cpp
@@ -8,6 +8,7 @@
 //===----------------------------------------------------------------------===//
 //
 // UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11
 
 // <shared_mutex>
 
@@ -20,8 +21,6 @@
 #include <cstdlib>
 #include <cassert>
 
-#if _LIBCPP_STD_VER > 11
-
 std::shared_timed_mutex m;
 
 typedef std::chrono::system_clock Clock;
@@ -44,15 +43,11 @@
     assert(d < ms(200));  // within 200ms
 }
 
-#endif  // _LIBCPP_STD_VER > 11
-
 int main()
 {
-#if _LIBCPP_STD_VER > 11
     m.lock();
     std::thread t(f);
     std::this_thread::sleep_for(ms(250));
     m.unlock();
     t.join();
-#endif  // _LIBCPP_STD_VER > 11
 }
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_for.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_for.pass.cpp
index 98cd8f9..ab20241 100644
--- a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_for.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_for.pass.cpp
@@ -8,6 +8,7 @@
 //===----------------------------------------------------------------------===//
 //
 // UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11
 
 // <shared_mutex>
 
@@ -21,8 +22,6 @@
 #include <cstdlib>
 #include <cassert>
 
-#if _LIBCPP_STD_VER > 11
-
 std::shared_timed_mutex m;
 
 typedef std::chrono::steady_clock Clock;
@@ -50,11 +49,8 @@
     assert(d < ms(50));  // within 50ms
 }
 
-#endif  // _LIBCPP_STD_VER > 11
-
 int main()
 {
-#if _LIBCPP_STD_VER > 11
     {
         m.lock();
         std::thread t(f1);
@@ -69,5 +65,4 @@
         m.unlock();
         t.join();
     }
-#endif  // _LIBCPP_STD_VER > 11
 }
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_shared.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_shared.pass.cpp
index a006e17..9c2d8c9 100644
--- a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_shared.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_shared.pass.cpp
@@ -8,6 +8,7 @@
 //===----------------------------------------------------------------------===//
 //
 // UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11
 
 // <shared_mutex>
 
@@ -21,8 +22,6 @@
 #include <cstdlib>
 #include <cassert>
 
-#if _LIBCPP_STD_VER > 11
-
 std::shared_timed_mutex m;
 
 typedef std::chrono::system_clock Clock;
@@ -45,11 +44,8 @@
     assert(d < ms(200));  // within 200ms
 }
 
-#endif  // _LIBCPP_STD_VER > 11
-
 int main()
 {
-#if _LIBCPP_STD_VER > 11
     m.lock();
     std::vector<std::thread> v;
     for (int i = 0; i < 5; ++i)
@@ -58,5 +54,4 @@
     m.unlock();
     for (auto& t : v)
         t.join();
-#endif  // _LIBCPP_STD_VER > 11
 }
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_shared_for.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_shared_for.pass.cpp
index b2cc15e..3544411 100644
--- a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_shared_for.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_shared_for.pass.cpp
@@ -8,6 +8,7 @@
 //===----------------------------------------------------------------------===//
 //
 // UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11
 
 // <shared_mutex>
 
@@ -22,8 +23,6 @@
 #include <cstdlib>
 #include <cassert>
 
-#if _LIBCPP_STD_VER > 11
-
 std::shared_timed_mutex m;
 
 typedef std::chrono::steady_clock Clock;
@@ -51,11 +50,8 @@
     assert(d < ms(50));  // within 50ms
 }
 
-#endif  // _LIBCPP_STD_VER > 11
-
 int main()
 {
-#if _LIBCPP_STD_VER > 11
     {
         m.lock();
         std::vector<std::thread> v;
@@ -76,5 +72,4 @@
         for (auto& t : v)
             t.join();
     }
-#endif  // _LIBCPP_STD_VER > 11
 }
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_shared_until.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_shared_until.pass.cpp
index d1b1121..4e0f19d 100644
--- a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_shared_until.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_shared_until.pass.cpp
@@ -8,6 +8,7 @@
 //===----------------------------------------------------------------------===//
 //
 // UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11
 
 // <shared_mutex>
 
@@ -22,8 +23,6 @@
 #include <cstdlib>
 #include <cassert>
 
-#if _LIBCPP_STD_VER > 11
-
 std::shared_timed_mutex m;
 
 typedef std::chrono::steady_clock Clock;
@@ -51,11 +50,8 @@
     assert(d < ms(50));  // within 50ms
 }
 
-#endif  // _LIBCPP_STD_VER > 11
-
 int main()
 {
-#if _LIBCPP_STD_VER > 11
     {
         m.lock();
         std::vector<std::thread> v;
@@ -76,5 +72,4 @@
         for (auto& t : v)
             t.join();
     }
-#endif  // _LIBCPP_STD_VER > 11
 }
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_until.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_until.pass.cpp
index 5a8e624..aa90cf7 100644
--- a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_until.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_until.pass.cpp
@@ -8,6 +8,7 @@
 //===----------------------------------------------------------------------===//
 //
 // UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11
 
 // <shared_mutex>
 
@@ -21,7 +22,7 @@
 #include <cstdlib>
 #include <cassert>
 
-#if _LIBCPP_STD_VER > 11
+#include "test_macros.h"
 
 std::shared_timed_mutex m;
 
@@ -50,11 +51,8 @@
     assert(d < ms(50));  // within 50ms
 }
 
-#endif  // _LIBCPP_STD_VER > 11
-
 int main()
 {
-#if _LIBCPP_STD_VER > 11
     {
         m.lock();
         std::thread t(f1);
@@ -69,5 +67,4 @@
         m.unlock();
         t.join();
     }
-#endif  // _LIBCPP_STD_VER > 11
 }
diff --git a/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_until_deadlock_bug.pass.cpp b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_until_deadlock_bug.pass.cpp
new file mode 100644
index 0000000..ed28809
--- /dev/null
+++ b/test/std/thread/thread.mutex/thread.mutex.requirements/thread.sharedtimedmutex.requirements/thread.sharedtimedmutex.class/try_lock_until_deadlock_bug.pass.cpp
@@ -0,0 +1,70 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: libcpp-has-no-threads
+// UNSUPPORTED: c++03, c++98, c++11
+
+// <shared_mutex>
+
+// class shared_timed_mutex;
+
+#include <shared_mutex>
+
+#include <atomic>
+#include <chrono>
+#include <thread>
+#include <cstdlib>
+#include <cassert>
+
+std::shared_timed_mutex m;
+
+const int total_readers = 2;
+std::atomic<int> readers_started(0);
+std::atomic<int> readers_finished(0);
+
+// Wait for the readers to start then try and acquire the write lock.
+void writer_one() {
+  while (readers_started != total_readers) {}
+  bool b = m.try_lock_for(std::chrono::milliseconds(500));
+  assert(b == false);
+}
+
+void blocked_reader() {
+  ++readers_started;
+  // Wait until writer_one is waiting for the write lock.
+  while (m.try_lock_shared()) {
+    m.unlock_shared();
+  }
+  // Attempt to get the read lock. writer_one should be blocking us because
+  // writer_one is blocked by main.
+  m.lock_shared();
+  ++readers_finished;
+  m.unlock_shared();
+}
+
+int main()
+{
+  typedef std::chrono::steady_clock Clock;
+
+  m.lock_shared();
+  std::thread t1(writer_one);
+  // create some readers
+  std::thread t2(blocked_reader);
+  std::thread t3(blocked_reader);
+  // Kill the test after 10 seconds if it hasn't completed.
+  auto end_point = Clock::now() + std::chrono::seconds(10);
+  while (readers_finished != total_readers && Clock::now() < end_point) {
+    std::this_thread::sleep_for(std::chrono::seconds(1));
+  }
+  assert(readers_finished == total_readers);
+  m.unlock_shared();
+  t1.join();
+  t2.join();
+  t3.join();
+}
diff --git a/test/std/thread/thread.mutex/thread.once/thread.once.callonce/call_once.pass.cpp b/test/std/thread/thread.mutex/thread.once/thread.once.callonce/call_once.pass.cpp
index 5395c85..89b9934 100644
--- a/test/std/thread/thread.mutex/thread.once/thread.once.callonce/call_once.pass.cpp
+++ b/test/std/thread/thread.mutex/thread.once/thread.once.callonce/call_once.pass.cpp
@@ -14,7 +14,7 @@
 // struct once_flag;
 
 // template<class Callable, class ...Args>
-//   void call_once(once_flag& flag, Callable func, Args&&... args);
+//   void call_once(once_flag& flag, Callable&& func, Args&&... args);
 
 #include <mutex>
 #include <thread>
@@ -153,6 +153,35 @@
     }
 };
 
+class NonCopyable
+{
+#if !defined(__clang__)
+   // GCC 4.8 complains about the following being private
+public:
+    NonCopyable(const NonCopyable&)
+    {
+    }
+#else
+    NonCopyable(const NonCopyable&);
+#endif
+public:
+    NonCopyable() {}
+
+    void operator()(int&) {}
+};
+
+#if __cplusplus >= 201103L
+// reference qualifiers on functions are a C++11 extension
+struct RefQual
+{
+    int lv_called, rv_called;
+
+    RefQual() : lv_called(0), rv_called(0) {}
+
+    void operator()() & { ++lv_called; }
+    void operator()() && { ++rv_called; }
+};
+#endif
 #endif
 
 int main()
@@ -204,5 +233,22 @@
         std::once_flag f;
         std::call_once(f, MoveOnly(), MoveOnly());
     }
+    // check LWG2442: call_once() shouldn't DECAY_COPY()
+    {
+        std::once_flag f;
+        int i = 0;
+        std::call_once(f, NonCopyable(), i);
+    }
+#if __cplusplus >= 201103L
+// reference qualifiers on functions are a C++11 extension
+    {
+        std::once_flag f1, f2;
+        RefQual rq;
+        std::call_once(f1, rq);
+        assert(rq.lv_called == 1);
+        std::call_once(f2, std::move(rq));
+        assert(rq.rv_called == 1);
+    }
+#endif
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 }
diff --git a/test/std/thread/thread.threads/thread.thread.class/thread.thread.algorithm/swap.pass.cpp b/test/std/thread/thread.threads/thread.thread.class/thread.thread.algorithm/swap.pass.cpp
index 476ca0c..4d3a742 100644
--- a/test/std/thread/thread.threads/thread.thread.class/thread.thread.algorithm/swap.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.class/thread.thread.algorithm/swap.pass.cpp
@@ -45,7 +45,8 @@
 int main()
 {
     {
-        std::thread t0((G()));
+        G g;
+        std::thread t0(g);
         std::thread::id id0 = t0.get_id();
         std::thread t1;
         std::thread::id id1 = t1.get_id();
diff --git a/test/std/thread/thread.threads/thread.thread.class/thread.thread.assign/move.pass.cpp b/test/std/thread/thread.threads/thread.thread.class/thread.thread.assign/move.pass.cpp
index 94a30e7..2db9430 100644
--- a/test/std/thread/thread.threads/thread.thread.class/thread.thread.assign/move.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.class/thread.thread.assign/move.pass.cpp
@@ -48,13 +48,16 @@
     {
         assert(G::n_alive == 0);
         assert(!G::op_run);
-        std::thread t0(G(), 5, 5.5);
+        {
+        G g;
+        std::thread t0(g, 5, 5.5);
         std::thread::id id = t0.get_id();
         std::thread t1;
         t1 = std::move(t0);
         assert(t1.get_id() == id);
         assert(t0.get_id() == std::thread::id());
         t1.join();
+        }
         assert(G::n_alive == 0);
         assert(G::op_run);
     }
diff --git a/test/std/thread/thread.threads/thread.thread.class/thread.thread.assign/move2.pass.cpp b/test/std/thread/thread.threads/thread.thread.class/thread.thread.assign/move2.pass.cpp
index 8cb2cb1..6c31df5 100644
--- a/test/std/thread/thread.threads/thread.thread.class/thread.thread.assign/move2.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.class/thread.thread.assign/move2.pass.cpp
@@ -8,10 +8,7 @@
 //===----------------------------------------------------------------------===//
 //
 // UNSUPPORTED: libcpp-has-no-threads
-
-// NOTE: std::terminate is called so the destructors are not invoked and the
-// memory is not freed. This will cause ASAN to fail.
-// XFAIL: asan
+// UNSUPPORTED: c++98, c++03
 
 // <thread>
 
@@ -35,12 +32,7 @@
     G(const G& g) : alive_(g.alive_) {++n_alive;}
     ~G() {alive_ = 0; --n_alive;}
 
-    void operator()()
-    {
-        assert(alive_ == 1);
-        assert(n_alive >= 1);
-        op_run = true;
-    }
+
 
     void operator()(int i, double j)
     {
@@ -57,19 +49,18 @@
 
 void f1()
 {
-    std::exit(0);
+    std::_Exit(0);
 }
 
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     std::set_terminate(f1);
     {
-        std::thread t0(G(), 5, 5.5);
+        G g;
+        std::thread t0(g, 5, 5.5);
         std::thread::id id = t0.get_id();
         std::thread t1;
         t0 = std::move(t1);
         assert(false);
     }
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/test/std/thread/thread.threads/thread.thread.class/thread.thread.constr/F.pass.cpp b/test/std/thread/thread.threads/thread.thread.class/thread.thread.constr/F.pass.cpp
index 0f5d5aa..a8b4be1 100644
--- a/test/std/thread/thread.threads/thread.thread.class/thread.thread.constr/F.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.class/thread.thread.constr/F.pass.cpp
@@ -15,7 +15,7 @@
 
 // template <class F, class ...Args> thread(F&& f, Args&&... args);
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <thread>
 #include <new>
diff --git a/test/std/thread/thread.threads/thread.thread.class/thread.thread.constr/move.pass.cpp b/test/std/thread/thread.threads/thread.thread.class/thread.thread.constr/move.pass.cpp
index 36e0fbd..e88304e 100644
--- a/test/std/thread/thread.threads/thread.thread.class/thread.thread.constr/move.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.class/thread.thread.constr/move.pass.cpp
@@ -55,16 +55,18 @@
 {
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     {
-        assert(G::n_alive == 0);
+        G g;
+        assert(G::n_alive == 1);
         assert(!G::op_run);
-        std::thread t0(G(), 5, 5.5);
+        std::thread t0(g, 5, 5.5);
         std::thread::id id = t0.get_id();
         std::thread t1 = std::move(t0);
         assert(t1.get_id() == id);
         assert(t0.get_id() == std::thread::id());
         t1.join();
-        assert(G::n_alive == 0);
+        assert(G::n_alive == 1);
         assert(G::op_run);
     }
+    assert(G::n_alive == 0);
 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/test/std/thread/thread.threads/thread.thread.class/thread.thread.destr/dtor.pass.cpp b/test/std/thread/thread.threads/thread.thread.class/thread.thread.destr/dtor.pass.cpp
index 20c8da1..ddf96d0 100644
--- a/test/std/thread/thread.threads/thread.thread.class/thread.thread.destr/dtor.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.class/thread.thread.destr/dtor.pass.cpp
@@ -9,6 +9,9 @@
 //
 // UNSUPPORTED: libcpp-has-no-threads
 
+// NOTE: TSAN will report this test as leaking a thread.
+// XFAIL: tsan
+
 // <thread>
 
 // class thread
@@ -53,8 +56,11 @@
     {
         assert(G::n_alive == 0);
         assert(!G::op_run);
-        std::thread t((G()));
-        std::this_thread::sleep_for(std::chrono::milliseconds(250));
+        G g;
+        {
+          std::thread t(g);
+          std::this_thread::sleep_for(std::chrono::milliseconds(250));
+        }
     }
     assert(false);
 }
diff --git a/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/detach.pass.cpp b/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/detach.pass.cpp
index 5a31232..f4a4d1f 100644
--- a/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/detach.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/detach.pass.cpp
@@ -16,26 +16,41 @@
 // void detach();
 
 #include <thread>
-#include <new>
-#include <cstdlib>
+#include <atomic>
 #include <cassert>
 
+std::atomic_bool done = ATOMIC_VAR_INIT(false);
+
 class G
 {
     int alive_;
+    bool done_;
 public:
     static int n_alive;
     static bool op_run;
 
-    G() : alive_(1) {++n_alive;}
-    G(const G& g) : alive_(g.alive_) {++n_alive;}
-    ~G() {alive_ = 0; --n_alive;}
+    G() : alive_(1), done_(false)
+    {
+        ++n_alive;
+    }
+
+    G(const G& g) : alive_(g.alive_), done_(false)
+    {
+        ++n_alive;
+    }
+    ~G()
+    {
+        alive_ = 0;
+        --n_alive;
+        if (done_) done = true;
+    }
 
     void operator()()
     {
         assert(alive_ == 1);
         assert(n_alive >= 1);
         op_run = true;
+        done_ = true;
     }
 };
 
@@ -45,12 +60,14 @@
 int main()
 {
     {
-        std::thread t0((G()));
+        G g;
+        std::thread t0(g);
         assert(t0.joinable());
         t0.detach();
         assert(!t0.joinable());
-        std::this_thread::sleep_for(std::chrono::milliseconds(250));
+        while (!done) {}
         assert(G::op_run);
-        assert(G::n_alive == 0);
+        assert(G::n_alive == 1);
     }
+    assert(G::n_alive == 0);
 }
diff --git a/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/get_id.pass.cpp b/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/get_id.pass.cpp
index a5ea55a..5cca7b0 100644
--- a/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/get_id.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/get_id.pass.cpp
@@ -45,7 +45,8 @@
 int main()
 {
     {
-        std::thread t0((G()));
+        G g;
+        std::thread t0(g);
         std::thread::id id0 = t0.get_id();
         std::thread t1;
         std::thread::id id1 = t1.get_id();
diff --git a/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/join.pass.cpp b/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/join.pass.cpp
index 2559303..0512e49 100644
--- a/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/join.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/join.pass.cpp
@@ -45,7 +45,8 @@
 int main()
 {
     {
-        std::thread t0((G()));
+        G g;
+        std::thread t0(g);
         assert(t0.joinable());
         t0.join();
         assert(!t0.joinable());
diff --git a/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/joinable.pass.cpp b/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/joinable.pass.cpp
index 351c1cf..b97839c 100644
--- a/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/joinable.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/joinable.pass.cpp
@@ -45,7 +45,8 @@
 int main()
 {
     {
-        std::thread t0((G()));
+        G g;
+        std::thread t0(g);
         assert(t0.joinable());
         t0.join();
         assert(!t0.joinable());
diff --git a/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/native_handle.pass.cpp b/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/native_handle.pass.cpp
index 37c2d9c..c8807a9 100644
--- a/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/native_handle.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/native_handle.pass.cpp
@@ -45,7 +45,8 @@
 int main()
 {
     {
-        std::thread t0((G()));
+        G g;
+        std::thread t0(g);
         pthread_t pid = t0.native_handle();
         assert(pid != 0);
         t0.join();
diff --git a/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/swap.pass.cpp b/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/swap.pass.cpp
index e8dede1..49d4618 100644
--- a/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/swap.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.class/thread.thread.member/swap.pass.cpp
@@ -45,7 +45,8 @@
 int main()
 {
     {
-        std::thread t0((G()));
+        G g;
+        std::thread t0(g);
         std::thread::id id0 = t0.get_id();
         std::thread t1;
         std::thread::id id1 = t1.get_id();
diff --git a/test/std/thread/thread.threads/thread.thread.this/sleep_for.pass.cpp b/test/std/thread/thread.threads/thread.thread.this/sleep_for.pass.cpp
index bffb5f3..27e1d2a 100644
--- a/test/std/thread/thread.threads/thread.thread.this/sleep_for.pass.cpp
+++ b/test/std/thread/thread.threads/thread.thread.this/sleep_for.pass.cpp
@@ -17,14 +17,17 @@
 #include <thread>
 #include <cstdlib>
 #include <cassert>
+#include <cstring>
 #include <signal.h>
 #include <sys/time.h>
 
+void sig_action(int) {}
+
 int main()
 {
     int ec;
     struct sigaction action;
-    action.sa_handler = [](int) {};
+    action.sa_handler = &sig_action;
     sigemptyset(&action.sa_mask);
     action.sa_flags = 0;
 
@@ -32,7 +35,7 @@
     assert(!ec);
 
     struct itimerval it;
-    it.it_interval = { 0 };
+    std::memset(&it, 0, sizeof(itimerval));
     it.it_value.tv_sec = 0;
     it.it_value.tv_usec = 250000;
     // This will result in a SIGALRM getting fired resulting in the nanosleep
diff --git a/test/std/utilities/allocator.adaptor/allocator.adaptor.types/is_always_equal.pass.cpp b/test/std/utilities/allocator.adaptor/allocator.adaptor.types/is_always_equal.pass.cpp
new file mode 100644
index 0000000..e19e731
--- /dev/null
+++ b/test/std/utilities/allocator.adaptor/allocator.adaptor.types/is_always_equal.pass.cpp
@@ -0,0 +1,75 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <memory>
+
+// template <class OuterAlloc, class... InnerAllocs>
+//   class scoped_allocator_adaptor
+
+// typedef see below is_always_equal;
+
+#include <scoped_allocator>
+#include <type_traits>
+
+#include "allocators.h"
+#include "min_allocator.h"
+
+int main()
+{
+#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+
+    // sanity checks
+    static_assert( (std::is_same<
+    		std::allocator_traits<A1<int>>::is_always_equal, std::false_type>::value
+    		), "" );
+
+    static_assert( (std::is_same<
+    		std::allocator_traits<min_allocator<int>>::is_always_equal, std::true_type>::value
+    		), "" );
+    
+    // wrapping one allocator
+    static_assert(
+        (std::is_same<
+            std::scoped_allocator_adaptor<A1<int>>::is_always_equal,
+            std::allocator_traits<A1<int>>::is_always_equal
+        >::value), "");
+
+    // wrapping one allocator
+    static_assert(
+        (std::is_same<
+            std::scoped_allocator_adaptor<min_allocator<int>>::is_always_equal,
+            std::allocator_traits<min_allocator<int>>::is_always_equal
+        >::value), "");
+
+    // wrapping two allocators (check the values instead of the types)
+    static_assert((
+            std::scoped_allocator_adaptor<A1<int>, A2<int>>::is_always_equal::value ==
+            ( std::allocator_traits<A1<int>>::is_always_equal::value &&
+              std::allocator_traits<A2<int>>::is_always_equal::value)    
+        ), "");
+
+    // wrapping two allocators (check the values instead of the types)
+    static_assert((
+            std::scoped_allocator_adaptor<A1<int>, min_allocator<int>>::is_always_equal::value ==
+            ( std::allocator_traits<A1<int>>::is_always_equal::value &&
+              std::allocator_traits<min_allocator<int>>::is_always_equal::value)    
+        ), "");
+
+
+    // wrapping three allocators (check the values instead of the types)
+    static_assert((
+            std::scoped_allocator_adaptor<A1<int>, A2<int>, A3<int>>::is_always_equal::value ==
+            ( std::allocator_traits<A1<int>>::is_always_equal::value &&
+              std::allocator_traits<A2<int>>::is_always_equal::value &&    
+              std::allocator_traits<A3<int>>::is_always_equal::value)    
+        ), "");
+
+
+#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
+}
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/utilities/date.time/asctime.thread-unsafe.fail.cpp
similarity index 67%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/std/utilities/date.time/asctime.thread-unsafe.fail.cpp
index b58f5c5..3a9749e 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/utilities/date.time/asctime.thread-unsafe.fail.cpp
@@ -7,6 +7,12 @@
 //
 //===----------------------------------------------------------------------===//
 
-int main()
-{
+// REQUIRES: libcpp-has-no-thread-unsafe-c-functions
+
+#include <ctime>
+
+int main() {
+    // asctime is not thread-safe.
+    std::time_t t = 0;
+    std::asctime(&t);
 }
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/utilities/date.time/ctime.thread-unsafe.fail.cpp
similarity index 68%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/std/utilities/date.time/ctime.thread-unsafe.fail.cpp
index b58f5c5..cd246c6 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/utilities/date.time/ctime.thread-unsafe.fail.cpp
@@ -7,6 +7,12 @@
 //
 //===----------------------------------------------------------------------===//
 
-int main()
-{
+// REQUIRES: libcpp-has-no-thread-unsafe-c-functions
+
+#include <ctime>
+
+int main() {
+    // ctime is not thread-safe.
+    std::time_t t = 0;
+    std::ctime(&t);
 }
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/utilities/date.time/gmtime.thread-unsafe.fail.cpp
similarity index 68%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/std/utilities/date.time/gmtime.thread-unsafe.fail.cpp
index b58f5c5..a6debcb 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/utilities/date.time/gmtime.thread-unsafe.fail.cpp
@@ -7,6 +7,12 @@
 //
 //===----------------------------------------------------------------------===//
 
-int main()
-{
+// REQUIRES: libcpp-has-no-thread-unsafe-c-functions
+
+#include <ctime>
+
+int main() {
+    // gmtime is not thread-safe.
+    std::time_t t = 0;
+    std::gmtime(&t);
 }
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/utilities/date.time/localtime.thread-unsafe.fail.cpp
similarity index 67%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/std/utilities/date.time/localtime.thread-unsafe.fail.cpp
index b58f5c5..c9e55c8 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/utilities/date.time/localtime.thread-unsafe.fail.cpp
@@ -7,6 +7,12 @@
 //
 //===----------------------------------------------------------------------===//
 
-int main()
-{
+// REQUIRES: libcpp-has-no-thread-unsafe-c-functions
+
+#include <ctime>
+
+int main() {
+    // localtime is not thread-safe.
+    std::time_t t = 0;
+    std::localtime(&t);
 }
diff --git a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/copy.pass.cpp b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/copy.pass.cpp
index 6315598..ad03e8f 100644
--- a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/copy.pass.cpp
+++ b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/copy.pass.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <functional>
 
 // template<CopyConstructible Fn, CopyConstructible... Types>
diff --git a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_function_object.pass.cpp b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_function_object.pass.cpp
index 33bf018..4577d0b 100644
--- a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_function_object.pass.cpp
+++ b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_function_object.pass.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <functional>
 
 // template<CopyConstructible Fn, CopyConstructible... Types>
diff --git a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_int_0.pass.cpp b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_int_0.pass.cpp
index ab4dd59..815096f 100644
--- a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_int_0.pass.cpp
+++ b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_int_0.pass.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <functional>
 
 // template<CopyConstructible Fn, CopyConstructible... Types>
diff --git a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_lvalue.pass.cpp b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_lvalue.pass.cpp
index af5efe4..f69afbf 100644
--- a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_lvalue.pass.cpp
+++ b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_lvalue.pass.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <functional>
 
 // template<CopyConstructible Fn, CopyConstructible... Types>
diff --git a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_rvalue.pass.cpp b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_rvalue.pass.cpp
index 4913a51..a1137ee 100644
--- a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_rvalue.pass.cpp
+++ b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_rvalue.pass.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <functional>
 
 // template<CopyConstructible Fn, CopyConstructible... Types>
diff --git a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_void_0.pass.cpp b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_void_0.pass.cpp
index 03447db..73f26e4 100644
--- a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_void_0.pass.cpp
+++ b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/invoke_void_0.pass.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <functional>
 
 // template<CopyConstructible Fn, CopyConstructible... Types>
@@ -39,21 +41,34 @@
 
 void f() {++count;}
 
-struct A_int_0
+int g() {++count; return 0;}
+
+struct A_void_0
 {
     void operator()() {++count;}
     void operator()() const {count += 2;}
 };
 
+struct A_int_0
+{
+    int operator()() {++count; return 4;}
+    int operator()() const {count += 2; return 5;}
+};
+
 int main()
 {
     test(std::bind(f));
     test(std::bind(&f));
-    test(std::bind(A_int_0()));
-    test_const(std::bind(A_int_0()));
+    test(std::bind(A_void_0()));
+    test_const(std::bind(A_void_0()));
 
     test(std::bind<void>(f));
     test(std::bind<void>(&f));
+    test(std::bind<void>(A_void_0()));
+    test_const(std::bind<void>(A_void_0()));
+
+    test(std::bind<void>(g));
+    test(std::bind<void>(&g));
     test(std::bind<void>(A_int_0()));
     test_const(std::bind<void>(A_int_0()));
 }
diff --git a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/nested.pass.cpp b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/nested.pass.cpp
index 12720f7..f61d93a 100644
--- a/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/nested.pass.cpp
+++ b/test/std/utilities/function.objects/bind/func.bind/func.bind.bind/nested.pass.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <functional>
 
 // template<CopyConstructible Fn, CopyConstructible... Types>
diff --git a/test/std/utilities/function.objects/bind/func.bind/func.bind.isbind/is_bind_expression.pass.cpp b/test/std/utilities/function.objects/bind/func.bind/func.bind.isbind/is_bind_expression.pass.cpp
index 7f8dd4a..83fa452 100644
--- a/test/std/utilities/function.objects/bind/func.bind/func.bind.isbind/is_bind_expression.pass.cpp
+++ b/test/std/utilities/function.objects/bind/func.bind/func.bind.isbind/is_bind_expression.pass.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <functional>
 
 // template<class T> struct is_bind_expression
diff --git a/test/std/utilities/function.objects/bind/func.bind/func.bind.isbind/is_bind_expression_03.pass.cpp b/test/std/utilities/function.objects/bind/func.bind/func.bind.isbind/is_bind_expression_03.pass.cpp
new file mode 100644
index 0000000..12a78db
--- /dev/null
+++ b/test/std/utilities/function.objects/bind/func.bind/func.bind.isbind/is_bind_expression_03.pass.cpp
@@ -0,0 +1,39 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <functional>
+
+//-----------------------------------------------------------------------------
+// TESTING template<class T> struct is_bind_expression
+//
+// bind is not implemented in C++03 so nothing is a bind expression. However
+// for compatibility reasons the trait is_bind_expression should be available
+// in C++03 and it should always return false.
+
+#include <functional>
+
+template <class T>
+void test() {
+    static_assert(!std::is_bind_expression<T>::value, "");
+}
+
+struct C {};
+
+int main() {
+    test<int>();
+    test<void>();
+    test<C>();
+    test<C&>();
+    test<C const&>();
+    test<C*>();
+    test<void()>();
+    test<int(*)()>();
+    test<int (C::*)()>();
+    test<decltype(std::placeholders::_2)>();
+}
diff --git a/test/std/utilities/function.objects/func.invoke/invoke.pass.cpp b/test/std/utilities/function.objects/func.invoke/invoke.pass.cpp
new file mode 100644
index 0000000..4b9cc76
--- /dev/null
+++ b/test/std/utilities/function.objects/func.invoke/invoke.pass.cpp
@@ -0,0 +1,268 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++98, c++03, c++11, c++14
+
+// <functional>
+
+// template <class F, class ...Args>
+// result_of_t<F&&(Args&&...)> invoke(F&&, Args&&...);
+
+/// C++14 [func.def] 20.9.0
+/// (1) The following definitions apply to this Clause:
+/// (2) A call signature is the name of a return type followed by a parenthesized
+///     comma-separated list of zero or more argument types.
+/// (3) A callable type is a function object type (20.9) or a pointer to member.
+/// (4) A callable object is an object of a callable type.
+/// (5) A call wrapper type is a type that holds a callable object and supports
+///     a call operation that forwards to that object.
+/// (6) A call wrapper is an object of a call wrapper type.
+/// (7) A target object is the callable object held by a call wrapper.
+
+/// C++14 [func.require] 20.9.1
+///
+/// Define INVOKE (f, t1, t2, ..., tN) as follows:
+///   (1.1) - (t1.*f)(t2, ..., tN) when f is a pointer to a member function of a class T and t1 is an object of
+///   type T or a reference to an object of type T or a reference to an object of a type derived from T;
+///   (1.2) - ((*t1).*f)(t2, ..., tN) when f is a pointer to a member function of a class T and t1 is not one of
+///   the types described in the previous item;
+///   (1.3) - t1.*f when N == 1 and f is a pointer to member data of a class T and t1 is an object of type T or a
+///   reference to an object of type T or a reference to an object of a type derived from T;
+///   (1.4) - (*t1).*f when N == 1 and f is a pointer to member data of a class T and t1 is not one of the types
+///   described in the previous item;
+///   (1.5) - f(t1, t2, ..., tN) in all other cases.
+
+#include <functional>
+#include <type_traits>
+#include <cassert>
+
+struct NonCopyable {
+    NonCopyable() {}
+private:
+    NonCopyable(NonCopyable const&) = delete;
+    NonCopyable& operator=(NonCopyable const&) = delete;
+};
+
+struct TestClass {
+    explicit TestClass(int x) : data(x) {}
+
+    int& operator()(NonCopyable&&) & { return data; }
+    int const& operator()(NonCopyable&&) const & { return data; }
+    int volatile& operator()(NonCopyable&&) volatile & { return data; }
+    int const volatile& operator()(NonCopyable&&) const volatile & { return data; }
+
+    int&& operator()(NonCopyable&&) && { return std::move(data); }
+    int const&& operator()(NonCopyable&&) const && { return std::move(data); }
+    int volatile&& operator()(NonCopyable&&) volatile && { return std::move(data); }
+    int const volatile&& operator()(NonCopyable&&) const volatile && { return std::move(data); }
+
+    int data;
+private:
+    TestClass(TestClass const&) = delete;
+    TestClass& operator=(TestClass const&) = delete;
+};
+
+struct DerivedFromTestClass : public TestClass {
+    explicit DerivedFromTestClass(int x) : TestClass(x) {}
+};
+
+int& foo(NonCopyable&&) {
+    static int data = 42;
+    return data;
+}
+
+template <class Signature,  class Expect, class Functor>
+void test_b12(Functor&& f) {
+    // Create the callable object.
+    typedef Signature TestClass::*ClassFunc;
+    ClassFunc func_ptr = &TestClass::operator();
+
+    // Create the dummy arg.
+    NonCopyable arg;
+
+    // Check that the deduced return type of invoke is what is expected.
+    typedef decltype(
+        std::invoke(func_ptr, std::forward<Functor>(f), std::move(arg))
+    ) DeducedReturnType;
+    static_assert((std::is_same<DeducedReturnType, Expect>::value), "");
+
+    // Check that result_of_t matches Expect.
+    typedef typename std::result_of<ClassFunc&&(Functor&&, NonCopyable&&)>::type
+      ResultOfReturnType;
+    static_assert((std::is_same<ResultOfReturnType, Expect>::value), "");
+
+    // Run invoke and check the return value.
+    DeducedReturnType ret =
+            std::invoke(func_ptr, std::forward<Functor>(f), std::move(arg));
+    assert(ret == 42);
+}
+
+template <class Expect, class Functor>
+void test_b34(Functor&& f) {
+    // Create the callable object.
+    typedef int TestClass::*ClassFunc;
+    ClassFunc func_ptr = &TestClass::data;
+
+    // Check that the deduced return type of invoke is what is expected.
+    typedef decltype(
+        std::invoke(func_ptr, std::forward<Functor>(f))
+    ) DeducedReturnType;
+    static_assert((std::is_same<DeducedReturnType, Expect>::value), "");
+
+    // Check that result_of_t matches Expect.
+    typedef typename std::result_of<ClassFunc&&(Functor&&)>::type
+            ResultOfReturnType;
+    static_assert((std::is_same<ResultOfReturnType, Expect>::value), "");
+
+    // Run invoke and check the return value.
+    DeducedReturnType ret =
+            std::invoke(func_ptr, std::forward<Functor>(f));
+    assert(ret == 42);
+}
+
+template <class Expect, class Functor>
+void test_b5(Functor&& f) {
+    NonCopyable arg;
+
+    // Check that the deduced return type of invoke is what is expected.
+    typedef decltype(
+        std::invoke(std::forward<Functor>(f), std::move(arg))
+    ) DeducedReturnType;
+    static_assert((std::is_same<DeducedReturnType, Expect>::value), "");
+
+    // Check that result_of_t matches Expect.
+    typedef typename std::result_of<Functor&&(NonCopyable&&)>::type
+            ResultOfReturnType;
+    static_assert((std::is_same<ResultOfReturnType, Expect>::value), "");
+
+    // Run invoke and check the return value.
+    DeducedReturnType ret = std::invoke(std::forward<Functor>(f), std::move(arg));
+    assert(ret == 42);
+}
+
+void bullet_one_two_tests() {
+    {
+        TestClass cl(42);
+        test_b12<int&(NonCopyable&&) &, int&>(cl);
+        test_b12<int const&(NonCopyable&&) const &, int const&>(cl);
+        test_b12<int volatile&(NonCopyable&&) volatile &, int volatile&>(cl);
+        test_b12<int const volatile&(NonCopyable&&) const volatile &, int const volatile&>(cl);
+
+        test_b12<int&&(NonCopyable&&) &&, int&&>(std::move(cl));
+        test_b12<int const&&(NonCopyable&&) const &&, int const&&>(std::move(cl));
+        test_b12<int volatile&&(NonCopyable&&) volatile &&, int volatile&&>(std::move(cl));
+        test_b12<int const volatile&&(NonCopyable&&) const volatile &&, int const volatile&&>(std::move(cl));
+    }
+    {
+        DerivedFromTestClass cl(42);
+        test_b12<int&(NonCopyable&&) &, int&>(cl);
+        test_b12<int const&(NonCopyable&&) const &, int const&>(cl);
+        test_b12<int volatile&(NonCopyable&&) volatile &, int volatile&>(cl);
+        test_b12<int const volatile&(NonCopyable&&) const volatile &, int const volatile&>(cl);
+
+        test_b12<int&&(NonCopyable&&) &&, int&&>(std::move(cl));
+        test_b12<int const&&(NonCopyable&&) const &&, int const&&>(std::move(cl));
+        test_b12<int volatile&&(NonCopyable&&) volatile &&, int volatile&&>(std::move(cl));
+        test_b12<int const volatile&&(NonCopyable&&) const volatile &&, int const volatile&&>(std::move(cl));
+    }
+    {
+        TestClass cl_obj(42);
+        TestClass *cl = &cl_obj;
+        test_b12<int&(NonCopyable&&) &, int&>(cl);
+        test_b12<int const&(NonCopyable&&) const &, int const&>(cl);
+        test_b12<int volatile&(NonCopyable&&) volatile &, int volatile&>(cl);
+        test_b12<int const volatile&(NonCopyable&&) const volatile &, int const volatile&>(cl);
+    }
+    {
+        DerivedFromTestClass cl_obj(42);
+        DerivedFromTestClass *cl = &cl_obj;
+        test_b12<int&(NonCopyable&&) &, int&>(cl);
+        test_b12<int const&(NonCopyable&&) const &, int const&>(cl);
+        test_b12<int volatile&(NonCopyable&&) volatile &, int volatile&>(cl);
+        test_b12<int const volatile&(NonCopyable&&) const volatile &, int const volatile&>(cl);
+    }
+}
+
+void bullet_three_four_tests() {
+    {
+        typedef TestClass Fn;
+        Fn cl(42);
+        test_b34<int&>(cl);
+        test_b34<int const&>(static_cast<Fn const&>(cl));
+        test_b34<int volatile&>(static_cast<Fn volatile&>(cl));
+        test_b34<int const volatile&>(static_cast<Fn const volatile &>(cl));
+
+        test_b34<int&&>(static_cast<Fn &&>(cl));
+        test_b34<int const&&>(static_cast<Fn const&&>(cl));
+        test_b34<int volatile&&>(static_cast<Fn volatile&&>(cl));
+        test_b34<int const volatile&&>(static_cast<Fn const volatile&&>(cl));
+    }
+    {
+        typedef DerivedFromTestClass Fn;
+        Fn cl(42);
+        test_b34<int&>(cl);
+        test_b34<int const&>(static_cast<Fn const&>(cl));
+        test_b34<int volatile&>(static_cast<Fn volatile&>(cl));
+        test_b34<int const volatile&>(static_cast<Fn const volatile &>(cl));
+
+        test_b34<int&&>(static_cast<Fn &&>(cl));
+        test_b34<int const&&>(static_cast<Fn const&&>(cl));
+        test_b34<int volatile&&>(static_cast<Fn volatile&&>(cl));
+        test_b34<int const volatile&&>(static_cast<Fn const volatile&&>(cl));
+    }
+    {
+        typedef TestClass Fn;
+        Fn cl_obj(42);
+        Fn* cl = &cl_obj;
+        test_b34<int&>(cl);
+        test_b34<int const&>(static_cast<Fn const*>(cl));
+        test_b34<int volatile&>(static_cast<Fn volatile*>(cl));
+        test_b34<int const volatile&>(static_cast<Fn const volatile *>(cl));
+    }
+    {
+        typedef DerivedFromTestClass Fn;
+        Fn cl_obj(42);
+        Fn* cl = &cl_obj;
+        test_b34<int&>(cl);
+        test_b34<int const&>(static_cast<Fn const*>(cl));
+        test_b34<int volatile&>(static_cast<Fn volatile*>(cl));
+        test_b34<int const volatile&>(static_cast<Fn const volatile *>(cl));
+    }
+}
+
+void bullet_five_tests() {
+    using FooType = int&(NonCopyable&&);
+    {
+        FooType& fn = foo;
+        test_b5<int &>(fn);
+    }
+    {
+        FooType* fn = foo;
+        test_b5<int &>(fn);
+    }
+    {
+        typedef TestClass Fn;
+        Fn cl(42);
+        test_b5<int&>(cl);
+        test_b5<int const&>(static_cast<Fn const&>(cl));
+        test_b5<int volatile&>(static_cast<Fn volatile&>(cl));
+        test_b5<int const volatile&>(static_cast<Fn const volatile &>(cl));
+
+        test_b5<int&&>(static_cast<Fn &&>(cl));
+        test_b5<int const&&>(static_cast<Fn const&&>(cl));
+        test_b5<int volatile&&>(static_cast<Fn volatile&&>(cl));
+        test_b5<int const volatile&&>(static_cast<Fn const volatile&&>(cl));
+    }
+}
+
+int main() {
+    bullet_one_two_tests();
+    bullet_three_four_tests();
+    bullet_five_tests();
+}
diff --git a/test/std/utilities/function.objects/func.require/bullet_1_and_2.pass.cpp b/test/std/utilities/function.objects/func.require/bullet_1_and_2.pass.cpp
new file mode 100644
index 0000000..e579f20
--- /dev/null
+++ b/test/std/utilities/function.objects/func.require/bullet_1_and_2.pass.cpp
@@ -0,0 +1,318 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <functional>
+
+// INVOKE (f, t1, t2, ..., tN)
+
+//------------------------------------------------------------------------------
+// TESTING INVOKE(f, t1, t2, ..., tN)
+//   - Bullet 1 -- (t1.*f)(t2, ..., tN)
+//   - Bullet 2 -- ((*t1).*f)(t2, ..., tN)
+//
+// Overview:
+//    Bullets 1 and 2 handle the case where 'f' is a pointer to member function.
+//    Bullet 1 only handles the cases where t1 is an object of type T or a
+//    type derived from 'T'. Bullet 2 handles all other cases.
+//
+// Concerns:
+//   1) cv-qualified member function signatures are accepted.
+//   2) reference qualified member function signatures are accepted.
+//   3) member functions with varargs at the end are accepted.
+//   4) The arguments are perfect forwarded to the member function call.
+//   5) Classes that are publicly derived from 'T' are accepted as the call object
+//   6) All types that dereference to T or a type derived from T can be used
+//      as the call object.
+//   7) Pointers to T or a type derived from T can be used as the call object.
+//   8) Reference return types are properly deduced.
+//
+//
+// Plan:
+//   1) Create a class that contains a set, 'S', of non-static functions.
+//     'S' should include functions that cover every single combination
+//      of qualifiers and varargs for arities of 0, 1 and 2 (C-1,2,3).
+//      The argument types used in the functions should be non-copyable (C-4).
+//      The functions should return 'MethodID::setUncheckedCall()'.
+//
+//   2) Create a set of supported call object, 'Objs', of different types
+//      and behaviors. (C-5,6,7)
+//
+//   3) Attempt to call each function, 'f', in 'S' with each call object, 'c',
+//      in 'Objs'. After every attempted call to 'f' check that 'f' was
+//      actually called using 'MethodID::checkCalled(<return-value>)'
+//
+//       3b) If 'f' is reference qualified call 'f' with the properly qualified
+//       call object. Otherwise call 'f' with lvalue call objects.
+//
+//       3a) If 'f' is const, volatile, or cv qualified then call it with call
+//       objects that are equally or less cv-qualified.
+
+#include <functional>
+#include <type_traits>
+#include <cassert>
+
+#include "test_macros.h"
+#include "invoke_helpers.h"
+
+//==============================================================================
+// MemFun03 - C++03 compatible set of test member functions.
+struct MemFun03 {
+    typedef void*& R;
+#define F(...) \
+    R f(__VA_ARGS__) { return MethodID<R(MemFun03::*)(__VA_ARGS__)>::setUncheckedCall(); } \
+    R f(__VA_ARGS__) const { return MethodID<R(MemFun03::*)(__VA_ARGS__) const>::setUncheckedCall(); } \
+    R f(__VA_ARGS__) volatile { return MethodID<R(MemFun03::*)(__VA_ARGS__) volatile>::setUncheckedCall(); } \
+    R f(__VA_ARGS__) const volatile { return MethodID<R(MemFun03::*)(__VA_ARGS__) const volatile>::setUncheckedCall(); }
+#
+    F()
+    F(...)
+    F(ArgType&)
+    F(ArgType&, ...)
+    F(ArgType&, ArgType&)
+    F(ArgType&, ArgType&, ...)
+    F(ArgType&, ArgType&, ArgType&)
+    F(ArgType&, ArgType&, ArgType&, ...)
+#undef F
+public:
+    MemFun03() {}
+private:
+    MemFun03(MemFun03 const&);
+    MemFun03& operator=(MemFun03 const&);
+};
+
+
+#if TEST_STD_VER >= 11
+
+//==============================================================================
+// MemFun11 - C++11 reference qualified test member functions.
+struct MemFun11 {
+    typedef void*& R;
+    typedef MemFun11 C;
+#define F(...) \
+    R f(__VA_ARGS__) & { return MethodID<R(C::*)(__VA_ARGS__) &>::setUncheckedCall(); } \
+    R f(__VA_ARGS__) const & { return MethodID<R(C::*)(__VA_ARGS__) const &>::setUncheckedCall(); } \
+    R f(__VA_ARGS__) volatile & { return MethodID<R(C::*)(__VA_ARGS__) volatile &>::setUncheckedCall(); } \
+    R f(__VA_ARGS__) const volatile & { return MethodID<R(C::*)(__VA_ARGS__) const volatile &>::setUncheckedCall(); } \
+    R f(__VA_ARGS__) && { return MethodID<R(C::*)(__VA_ARGS__) &&>::setUncheckedCall(); } \
+    R f(__VA_ARGS__) const && { return MethodID<R(C::*)(__VA_ARGS__) const &&>::setUncheckedCall(); } \
+    R f(__VA_ARGS__) volatile && { return MethodID<R(C::*)(__VA_ARGS__) volatile &&>::setUncheckedCall(); } \
+    R f(__VA_ARGS__) const volatile && { return MethodID<R(C::*)(__VA_ARGS__) const volatile &&>::setUncheckedCall(); }
+#
+    F()
+    F(...)
+    F(ArgType&&)
+    F(ArgType&&, ...)
+    F(ArgType&&, ArgType&&)
+    F(ArgType&&, ArgType&&, ...)
+    F(ArgType&&, ArgType&&, ArgType&&)
+    F(ArgType&&, ArgType&&, ArgType&&, ...)
+#undef F
+public:
+    MemFun11() {}
+private:
+    MemFun11(MemFun11 const&);
+    MemFun11& operator=(MemFun11 const&);
+};
+
+#endif // TEST_STD_VER >= 11
+
+
+//==============================================================================
+// TestCase - A test case for a single member function.
+//   ClassType - The type of the class being tested.
+//   CallSig   - The function signature of the method being tested.
+//   Arity     - the arity of 'CallSig'
+//   CV        - the cv qualifiers of 'CallSig' represented as a type tag.
+//   RValue    - The method is RValue qualified.
+//   ArgRValue - Call the method with RValue arguments.
+template <class ClassType, class CallSig, int Arity, class CV,
+          bool RValue = false, bool ArgRValue = false>
+struct TestCaseImp {
+public:
+
+    static void run() { TestCaseImp().doTest(); }
+
+private:
+    //==========================================================================
+    // TEST DISPATCH
+    void doTest() {
+         // (Plan-2) Create test call objects.
+        typedef ClassType T;
+        typedef DerivedFromType<T> D;
+        T obj;
+        T* obj_ptr = &obj;
+        D der;
+        D* der_ptr = &der;
+        DerefToType<T>   dref;
+        DerefPropType<T> dref2;
+
+         // (Plan-3) Dispatch based on the CV tags.
+        CV tag;
+        Bool<!RValue> NotRValue;
+        runTestDispatch(tag,  obj);
+        runTestDispatch(tag,  der);
+        runTestDispatch(tag, dref2);
+        runTestDispatchIf(NotRValue, tag,  dref);
+        runTestDispatchIf(NotRValue, tag,  obj_ptr);
+        runTestDispatchIf(NotRValue, tag, der_ptr);
+    }
+
+    template <class QT, class Tp>
+    void runTestDispatchIf(Bool<true>, QT q, Tp& v) {
+        runTestDispatch(q, v);
+    }
+
+    template <class QT, class Tp>
+    void runTestDispatchIf(Bool<false>, QT, Tp&) {
+    }
+
+    template <class Tp>
+    void runTestDispatch(Q_None, Tp& v) {
+        runTest(v);
+    }
+
+    template <class Tp>
+    void runTestDispatch(Q_Const, Tp& v) {
+        Tp const& cv = v;
+        runTest(v);
+        runTest(cv);
+    }
+
+    template <class Tp>
+    void runTestDispatch(Q_Volatile, Tp& v) {
+        Tp volatile& vv = v;
+        runTest(v);
+        runTest(vv);
+    }
+
+    template <class Tp>
+    void runTestDispatch(Q_CV, Tp& v) {
+        Tp const& cv = v;
+        Tp volatile& vv = v;
+        Tp const volatile& cvv = v;
+        runTest(v);
+        runTest(cv);
+        runTest(vv);
+        runTest(cvv);
+    }
+
+    template <class Obj>
+    void runTest(Obj& obj) {
+        typedef Caster<Q_None, RValue> SCast;
+        typedef Caster<Q_None, ArgRValue> ACast;
+        typedef CallSig (ClassType::*MemPtr);
+        // Delegate test to logic in invoke_helpers.h
+        BasicTest<MethodID<MemPtr>, Arity, SCast, ACast> b;
+        b.runTest( (MemPtr)&ClassType::f, obj);
+    }
+};
+
+template <class Sig, int Arity, class CV>
+struct TestCase : public TestCaseImp<MemFun03, Sig, Arity, CV> {};
+
+#if TEST_STD_VER >= 11
+template <class Sig, int Arity, class CV, bool RValue = false>
+struct TestCase11 : public TestCaseImp<MemFun11, Sig, Arity, CV, RValue, true> {};
+#endif
+
+int main() {
+    typedef void*& R;
+    typedef ArgType A;
+    TestCase<R(),                                   0, Q_None>::run();
+    TestCase<R() const,                             0, Q_Const>::run();
+    TestCase<R() volatile,                          0, Q_Volatile>::run();
+    TestCase<R() const volatile,                    0, Q_CV>::run();
+    TestCase<R(...),                                0, Q_None>::run();
+    TestCase<R(...) const,                          0, Q_Const>::run();
+    TestCase<R(...) volatile,                       0, Q_Volatile>::run();
+    TestCase<R(...) const volatile,                 0, Q_CV>::run();
+    TestCase<R(A&),                                 1, Q_None>::run();
+    TestCase<R(A&) const,                           1, Q_Const>::run();
+    TestCase<R(A&) volatile,                        1, Q_Volatile>::run();
+    TestCase<R(A&) const volatile,                  1, Q_CV>::run();
+    TestCase<R(A&, ...),                            1, Q_None>::run();
+    TestCase<R(A&, ...) const,                      1, Q_Const>::run();
+    TestCase<R(A&, ...) volatile,                   1, Q_Volatile>::run();
+    TestCase<R(A&, ...) const volatile,             1, Q_CV>::run();
+    TestCase<R(A&, A&),                             2, Q_None>::run();
+    TestCase<R(A&, A&) const,                       2, Q_Const>::run();
+    TestCase<R(A&, A&) volatile,                    2, Q_Volatile>::run();
+    TestCase<R(A&, A&) const volatile,              2, Q_CV>::run();
+    TestCase<R(A&, A&, ...),                        2, Q_None>::run();
+    TestCase<R(A&, A&, ...) const,                  2, Q_Const>::run();
+    TestCase<R(A&, A&, ...) volatile,               2, Q_Volatile>::run();
+    TestCase<R(A&, A&, ...) const volatile,         2, Q_CV>::run();
+    TestCase<R(A&, A&, A&),                         3, Q_None>::run();
+    TestCase<R(A&, A&, A&) const,                   3, Q_Const>::run();
+    TestCase<R(A&, A&, A&) volatile,                3, Q_Volatile>::run();
+    TestCase<R(A&, A&, A&) const volatile,          3, Q_CV>::run();
+    TestCase<R(A&, A&, A&, ...),                    3, Q_None>::run();
+    TestCase<R(A&, A&, A&, ...) const,              3, Q_Const>::run();
+    TestCase<R(A&, A&, A&, ...) volatile,           3, Q_Volatile>::run();
+    TestCase<R(A&, A&, A&, ...) const volatile,     3, Q_CV>::run();
+
+#if TEST_STD_VER >= 11
+    TestCase11<R() &,                               0, Q_None>::run();
+    TestCase11<R() const &,                         0, Q_Const>::run();
+    TestCase11<R() volatile &,                      0, Q_Volatile>::run();
+    TestCase11<R() const volatile &,                0, Q_CV>::run();
+    TestCase11<R(...) &,                            0, Q_None>::run();
+    TestCase11<R(...) const &,                      0, Q_Const>::run();
+    TestCase11<R(...) volatile &,                   0, Q_Volatile>::run();
+    TestCase11<R(...) const volatile &,             0, Q_CV>::run();
+    TestCase11<R(A&&) &,                            1, Q_None>::run();
+    TestCase11<R(A&&) const &,                      1, Q_Const>::run();
+    TestCase11<R(A&&) volatile &,                   1, Q_Volatile>::run();
+    TestCase11<R(A&&) const volatile &,             1, Q_CV>::run();
+    TestCase11<R(A&&, ...) &,                       1, Q_None>::run();
+    TestCase11<R(A&&, ...) const &,                 1, Q_Const>::run();
+    TestCase11<R(A&&, ...) volatile &,              1, Q_Volatile>::run();
+    TestCase11<R(A&&, ...) const volatile &,        1, Q_CV>::run();
+    TestCase11<R(A&&, A&&) &,                       2, Q_None>::run();
+    TestCase11<R(A&&, A&&) const &,                 2, Q_Const>::run();
+    TestCase11<R(A&&, A&&) volatile &,              2, Q_Volatile>::run();
+    TestCase11<R(A&&, A&&) const volatile &,        2, Q_CV>::run();
+    TestCase11<R(A&&, A&&, ...) &,                  2, Q_None>::run();
+    TestCase11<R(A&&, A&&, ...) const &,            2, Q_Const>::run();
+    TestCase11<R(A&&, A&&, ...) volatile &,         2, Q_Volatile>::run();
+    TestCase11<R(A&&, A&&, ...) const volatile &,   2, Q_CV>::run();
+    TestCase11<R() &&,                              0, Q_None, /* RValue */ true>::run();
+    TestCase11<R() const &&,                        0, Q_Const, /* RValue */ true>::run();
+    TestCase11<R() volatile &&,                     0, Q_Volatile, /* RValue */ true>::run();
+    TestCase11<R() const volatile &&,               0, Q_CV, /* RValue */ true>::run();
+    TestCase11<R(...) &&,                           0, Q_None, /* RValue */ true>::run();
+    TestCase11<R(...) const &&,                     0, Q_Const, /* RValue */ true>::run();
+    TestCase11<R(...) volatile &&,                  0, Q_Volatile, /* RValue */ true>::run();
+    TestCase11<R(...) const volatile &&,            0, Q_CV, /* RValue */ true>::run();
+    TestCase11<R(A&&) &&,                           1, Q_None, /* RValue */ true>::run();
+    TestCase11<R(A&&) const &&,                     1, Q_Const, /* RValue */ true>::run();
+    TestCase11<R(A&&) volatile &&,                  1, Q_Volatile, /* RValue */ true>::run();
+    TestCase11<R(A&&) const volatile &&,            1, Q_CV, /* RValue */ true>::run();
+    TestCase11<R(A&&, ...) &&,                      1, Q_None, /* RValue */ true>::run();
+    TestCase11<R(A&&, ...) const &&,                1, Q_Const, /* RValue */ true>::run();
+    TestCase11<R(A&&, ...) volatile &&,             1, Q_Volatile, /* RValue */ true>::run();
+    TestCase11<R(A&&, ...) const volatile &&,       1, Q_CV, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&) &&,                      2, Q_None, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&) const &&,                2, Q_Const, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&) volatile &&,             2, Q_Volatile, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&) const volatile &&,       2, Q_CV, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&, ...) &&,                 2, Q_None, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&, ...) const &&,           2, Q_Const, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&, ...) volatile &&,        2, Q_Volatile, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&, ...) const volatile &&,  2, Q_CV, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&, A&&) &&,                 3, Q_None, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&, A&&) const &&,           3, Q_Const, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&, A&&) volatile &&,        3, Q_Volatile, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&, A&&) const volatile &&,  3, Q_CV, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&, A&&, ...)  &&,                 3, Q_None, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&, A&&, ...)  const &&,           3, Q_Const, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&, A&&, ...)  volatile &&,        3, Q_Volatile, /* RValue */ true>::run();
+    TestCase11<R(A&&, A&&, A&&, ...)  const volatile &&,  3, Q_CV, /* RValue */ true>::run();
+#endif
+}
\ No newline at end of file
diff --git a/test/std/utilities/function.objects/func.require/bullet_3_and_4.pass.cpp b/test/std/utilities/function.objects/func.require/bullet_3_and_4.pass.cpp
new file mode 100644
index 0000000..b6fe190
--- /dev/null
+++ b/test/std/utilities/function.objects/func.require/bullet_3_and_4.pass.cpp
@@ -0,0 +1,164 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <functional>
+
+// INVOKE (f, t1, t2, ..., tN)
+
+//------------------------------------------------------------------------------
+// TESTING INVOKE(f, t1, t2, ..., tN)
+//   - Bullet 3 -- t1.*f
+//   - Bullet 4 -- (*t1).*f
+//
+// Overview:
+//    Bullets 3 and 4 handle the case where 'f' is a pointer to member object.
+//    Bullet 3 only handles the cases where t1 is an object of type T or a
+//    type derived from 'T'. Bullet 4 handles all other cases.
+//
+// Concerns:
+//   1) The return type is always an lvalue reference.
+//   2) The return type is not less cv-qualified that the object that contains it.
+//   3) The return type is not less cv-qualified than object type.
+//   4) The call object is perfectly forwarded.
+//   5) Classes that are publicly derived from 'T' are accepted as the call object
+//   6) All types that dereference to T or a type derived from T can be used
+//      as the call object.
+//   7) Pointers to T or a type derived from T can be used as the call object.
+
+#include <functional>
+#include <type_traits>
+#include <cassert>
+
+#include "test_macros.h"
+#include "invoke_helpers.h"
+
+template <class Tp>
+struct TestMemberObject {
+    TestMemberObject() : object() {}
+    Tp object;
+private:
+    TestMemberObject(TestMemberObject const&);
+    TestMemberObject& operator=(TestMemberObject const&);
+};
+
+template <class ObjectType>
+struct TestCase {
+    public:
+
+    static void run() { TestCase().doTest(); }
+
+private:
+    typedef TestMemberObject<ObjectType> TestType;
+
+    //==========================================================================
+    // TEST DISPATCH
+    void doTest() {
+        typedef DerivedFromType<TestType> Derived;
+        TestType obj;
+        TestType* obj_ptr = &obj;
+        Derived der;
+        Derived* der_ptr = &der;
+        DerefToType<TestType>   dref;
+        DerefPropType<TestType> dref2;
+
+        {
+            typedef ObjectType (TestType::*MemPtr);
+            typedef ObjectType E;
+            MemPtr M = &TestType::object;
+            runTestDispatch<E>(M, obj, &obj.object);
+            runTestDispatch<E>(M, der, &der.object);
+            runTestDispatch<E>(M, dref2, &dref2.object.object);
+            runTestPointerDispatch<E>(M, obj_ptr, &obj_ptr->object);
+            runTestPointerDispatch<E>(M, der_ptr, &der_ptr->object);
+            runTestPointerDispatch<E>(M, dref, &dref.object.object);
+        }
+        {
+            typedef ObjectType const (TestType::*CMemPtr);
+            typedef ObjectType const E;
+            CMemPtr M = &TestType::object;
+            runTestDispatch<E>(M, obj, &obj.object);
+            runTestDispatch<E>(M, der, &der.object);
+            runTestDispatch<E>(M, dref2, &dref2.object.object);
+            runTestPointerDispatch<E>(M, obj_ptr, &obj_ptr->object);
+            runTestPointerDispatch<E>(M, der_ptr, &der_ptr->object);
+            runTestPointerDispatch<E>(M, dref, &dref.object.object);
+        }
+        {
+            typedef ObjectType volatile (TestType::*VMemPtr);
+            typedef ObjectType volatile E;
+            VMemPtr M = &TestType::object;
+            runTestDispatch<E>(M, obj,  &obj.object);
+            runTestDispatch<E>(M, der,  &der.object);
+            runTestDispatch<E>(M, dref2, &dref2.object.object);
+            runTestPointerDispatch<E>(M, obj_ptr, &obj_ptr->object);
+            runTestPointerDispatch<E>(M, der_ptr, &der_ptr->object);
+            runTestPointerDispatch<E>(M, dref,    &dref.object.object);
+        }
+        {
+            typedef ObjectType const volatile (TestType::*CVMemPtr);
+            typedef ObjectType const volatile E;
+            CVMemPtr M = &TestType::object;
+            runTestDispatch<E>(M, obj,   &obj.object);
+            runTestDispatch<E>(M, der,   &der.object);
+            runTestDispatch<E>(M, dref2, &dref2.object.object);
+            runTestPointerDispatch<E>(M, obj_ptr, &obj_ptr->object);
+            runTestPointerDispatch<E>(M, der_ptr, &der_ptr->object);
+            runTestPointerDispatch<E>(M, dref,    &dref.object.object);
+        }
+    }
+
+    template <class Expect, class Fn, class T>
+    void runTestDispatch(Fn M, T& obj, ObjectType* expect) {
+        runTest<Expect &>              (M, C_<T&>(obj),                expect);
+        runTest<Expect const&>         (M, C_<T const&>(obj),          expect);
+        runTest<Expect volatile&>      (M, C_<T volatile&>(obj),       expect);
+        runTest<Expect const volatile&>(M, C_<T const volatile&>(obj), expect);
+#if TEST_STD_VER >= 11
+        runTest<Expect&&>               (M, C_<T&&>(obj),                expect);
+        runTest<Expect const&&>         (M, C_<T const&&>(obj),          expect);
+        runTest<Expect volatile&&>      (M, C_<T volatile&&>(obj),       expect);
+        runTest<Expect const volatile&&>(M, C_<T const volatile&&>(obj), expect);
+#endif
+    }
+
+    template <class Expect, class Fn, class T>
+    void runTestPointerDispatch(Fn M, T& obj, ObjectType* expect) {
+        runTest<Expect&>(M, C_<T &>(obj),               expect);
+        runTest<Expect&>(M, C_<T const&>(obj),          expect);
+        runTest<Expect&>(M, C_<T volatile&>(obj),       expect);
+        runTest<Expect&>(M, C_<T const volatile&>(obj), expect);
+#if TEST_STD_VER >= 11
+        runTest<Expect&>(M, C_<T&&>(obj),                expect);
+        runTest<Expect&>(M, C_<T const&&>(obj),          expect);
+        runTest<Expect&>(M, C_<T volatile&&>(obj),       expect);
+        runTest<Expect&>(M, C_<T const volatile&&>(obj), expect);
+#endif
+    }
+
+    template <class Expect, class Fn, class T>
+#if TEST_STD_VER >= 11
+    void runTest(Fn M, T&& obj, ObjectType* expect) {
+#else
+    void runTest(Fn M, T& obj, ObjectType* expect ) {
+#endif
+        static_assert((std::is_same<
+            decltype(std::__invoke(M, std::forward<T>(obj))), Expect
+          >::value), "");
+        Expect e = std::__invoke(M, std::forward<T>(obj));
+        assert(&e == expect);
+    }
+};
+
+int main() {
+    TestCase<ArgType>::run();
+    TestCase<ArgType const>::run();
+    TestCase<ArgType volatile>::run();
+    TestCase<ArgType const volatile>::run();
+    TestCase<ArgType*>::run();
+}
\ No newline at end of file
diff --git a/test/std/utilities/function.objects/func.require/bullet_5.pass.cpp b/test/std/utilities/function.objects/func.require/bullet_5.pass.cpp
new file mode 100644
index 0000000..3f3c96a
--- /dev/null
+++ b/test/std/utilities/function.objects/func.require/bullet_5.pass.cpp
@@ -0,0 +1,327 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <functional>
+
+// INVOKE (f, t1, t2, ..., tN)
+
+//------------------------------------------------------------------------------
+// TESTING INVOKE(f, t1, t2, ..., tN)
+//   - Bullet 5 -- f(t2, ..., tN)
+//
+// Overview:
+//    Bullet 5 handles the cases where the first argument is not a member
+//   function.
+//
+// Concerns:
+//   1) Different types of callable objects are supported. Including
+//      1a) Free Function pointers and references.
+//      1b) Classes which provide a call operator
+//      1c) lambdas
+//   2) The callable objects are perfect forwarded.
+//   3) The arguments are perfect forwarded.
+//   4) Signatures which include varargs are supported.
+//   5) In C++03 3 extra arguments should be allowed.
+//
+// Plan:
+//  1) Define a set of free functions, 'SF', and class types with call
+//     operators, 'SC', that address concerns 4 and 5. The free functions should
+//     return 'FunctionID::setUncheckedCall()' and the call operators should
+//     return 'MethodID::setUncheckedCall()'.
+//
+//  2) For each function 'f' in 'SF' and 'SC' attempt to call 'f'
+//     using the correct number of arguments and cv-ref qualifiers. Check that
+//     'f' has been called using 'FunctionID::checkCall()' if 'f' is a free
+//     function and 'MethodID::checkCall()' otherwise.
+
+
+
+#include <functional>
+#include <type_traits>
+#include <cassert>
+
+#include "test_macros.h"
+#include "invoke_helpers.h"
+
+
+//==============================================================================
+// freeFunction03 - A C++03 free function.
+void*& freeFunction03() {
+    return FunctionPtrID<void*&(), freeFunction03>::setUncheckedCall();
+}
+
+void*& freeFunction03(...) {
+    return FunctionPtrID<void*&(...), freeFunction03>::setUncheckedCall();
+}
+
+template <class A0>
+void*& freeFunction03(A0&) {
+    return FunctionPtrID<void*&(A0&), freeFunction03>::setUncheckedCall();
+}
+
+
+template <class A0>
+void*& freeFunction03(A0&, ...) {
+    return FunctionPtrID<void*&(A0&, ...), freeFunction03>::setUncheckedCall();
+}
+
+template <class A0, class A1>
+void*& freeFunction03(A0&, A1&) {
+    return FunctionPtrID<void*&(A0&, A1&), freeFunction03>::setUncheckedCall();
+}
+
+
+template <class A0, class A1>
+void*& freeFunction03(A0&, A1&, ...) {
+    return FunctionPtrID<void*&(A0&, A1&, ...), freeFunction03>::setUncheckedCall();
+}
+
+template <class A0, class A1, class A2>
+void*& freeFunction03(A0&, A1&, A2&) {
+    return FunctionPtrID<void*&(A0&, A1&, A2&), freeFunction03>::setUncheckedCall();
+}
+
+template <class A0, class A1, class A2>
+void*& freeFunction03(A0&, A1&, A2&, ...) {
+    return FunctionPtrID<void*&(A0&, A1&, A2&, ...), freeFunction03>::setUncheckedCall();
+}
+
+//==============================================================================
+// Functor03 - C++03 compatible functor object
+struct Functor03 {
+    typedef void*& R;
+    typedef Functor03 C;
+#define F(Args, ...) \
+    __VA_ARGS__ R operator() Args { return MethodID<R(C::*) Args>::setUncheckedCall(); } \
+    __VA_ARGS__ R operator() Args const { return MethodID<R(C::*) Args const>::setUncheckedCall(); } \
+    __VA_ARGS__ R operator() Args volatile { return MethodID<R(C::*) Args volatile>::setUncheckedCall(); } \
+    __VA_ARGS__ R operator() Args const volatile { return MethodID<R(C::*) Args const volatile>::setUncheckedCall(); }
+#
+    F(())
+    F((A0&), template <class A0>)
+    F((A0&, A1&), template <class A0, class A1>)
+    F((A0&, A1&, A2&), template <class A0, class A1, class A2>)
+#undef F
+public:
+    Functor03() {}
+private:
+    Functor03(Functor03 const&);
+    Functor03& operator=(Functor03 const&);
+};
+
+
+#if TEST_STD_VER >= 11
+
+//==============================================================================
+// freeFunction11 - A C++11 free function.
+template <class ...Args>
+void*& freeFunction11(Args&&...) {
+    return FunctionPtrID<void*&(Args&&...), freeFunction11>::setUncheckedCall();
+}
+
+template <class ...Args>
+void*& freeFunction11(Args&&...,...) {
+    return FunctionPtrID<void*&(Args&&...,...), freeFunction11>::setUncheckedCall();
+}
+
+//==============================================================================
+// Functor11 - C++11 reference qualified test member functions.
+struct Functor11 {
+    typedef void*& R;
+    typedef Functor11 C;
+
+#define F(CV) \
+    template <class ...Args> \
+    R operator()(Args&&...) CV { return MethodID<R(C::*)(Args&&...) CV>::setUncheckedCall(); }
+#
+    F(&)
+    F(const &)
+    F(volatile &)
+    F(const volatile &)
+    F(&&)
+    F(const &&)
+    F(volatile &&)
+    F(const volatile &&)
+#undef F
+public:
+    Functor11() {}
+private:
+    Functor11(Functor11 const&);
+    Functor11& operator=(Functor11 const&);
+};
+
+#endif // TEST_STD_VER >= 11
+
+
+//==============================================================================
+// TestCaseFunctorImp - A test case for an operator() class method.
+//   ClassType - The type of the call object.
+//   CallSig   - The function signature of the call operator being tested.
+//   Arity     - the arity of 'CallSig'
+//   ObjCaster - Transformation function applied to call object.
+//   ArgCaster - Transformation function applied to the extra arguments.
+template <class ClassType, class CallSig, int Arity,
+          class ObjCaster, class ArgCaster = LValueCaster>
+struct TestCaseFunctorImp {
+public:
+    static void run() {
+        typedef MethodID<CallSig ClassType::*> MID;
+        BasicTest<MID, Arity, ObjCaster, ArgCaster> t;
+        typedef ClassType T;
+        typedef DerivedFromType<T> D;
+        T obj;
+        D der;
+        t.runTest(obj);
+        t.runTest(der);
+    }
+};
+
+//==============================================================================
+// TestCaseFreeFunction - A test case for a free function.
+//   CallSig   - The function signature of the free function being tested.
+//   FnPtr     - The function being tested.
+//   Arity     - the arity of 'CallSig'
+//   ArgCaster - Transformation function to be applied to the extra arguments.
+template <class CallSig, CallSig* FnPtr, int Arity, class ArgCaster>
+struct TestCaseFreeFunction {
+public:
+    static void run() {
+        typedef FunctionPtrID<CallSig, FnPtr> FID;
+        BasicTest<FID, Arity, LValueCaster, ArgCaster> t;
+
+        DerefToType<CallSig*> deref_to(FnPtr);
+        DerefToType<CallSig&> deref_to_ref(*FnPtr);
+
+        t.runTest(FnPtr);
+        t.runTest(*FnPtr);
+        t.runTest(deref_to);
+        t.runTest(deref_to_ref);
+    }
+};
+
+//==============================================================================
+//                          runTest Helpers
+//==============================================================================
+#if TEST_STD_VER >= 11
+template <class Sig, int Arity, class ArgCaster>
+void runFunctionTestCase11() {
+    TestCaseFreeFunction<Sig, freeFunction11, Arity, ArgCaster>();
+}
+#endif
+
+template <class Sig, int Arity, class ArgCaster>
+void runFunctionTestCase() {
+    TestCaseFreeFunction<Sig, freeFunction03, Arity, ArgCaster>();
+#if TEST_STD_VER >= 11
+    runFunctionTestCase11<Sig, Arity, ArgCaster>();
+#endif
+}
+
+template <class Sig, int Arity, class ObjCaster, class ArgCaster>
+void runFunctorTestCase() {
+    TestCaseFunctorImp<Functor03, Sig, Arity, ObjCaster, ArgCaster>::run();
+}
+
+template <class Sig, int Arity, class ObjCaster>
+void runFunctorTestCase() {
+    TestCaseFunctorImp<Functor03, Sig, Arity, ObjCaster>::run();
+}
+
+#if TEST_STD_VER >= 11
+// runTestCase - Run a test case for C++11 class functor types
+template <class Sig, int Arity, class ObjCaster, class ArgCaster = LValueCaster>
+void runFunctorTestCase11() {
+    TestCaseFunctorImp<Functor11, Sig, Arity, ObjCaster, ArgCaster>::run();
+}
+#endif
+
+// runTestCase - Run a test case for both function and functor types.
+template <class Sig, int Arity, class ArgCaster>
+void runTestCase() {
+    runFunctionTestCase<Sig, Arity, ArgCaster>();
+    runFunctorTestCase <Sig, Arity, LValueCaster, ArgCaster>();
+};
+
+int main() {
+    typedef void*& R;
+    typedef ArgType A;
+    typedef A const CA;
+
+    runTestCase< R(),                                   0, LValueCaster      >();
+    runTestCase< R(A&),                                 1, LValueCaster      >();
+    runTestCase< R(A&, A&),                             2, LValueCaster      >();
+    runTestCase< R(A&, A&, A&),                         3, LValueCaster      >();
+    runTestCase< R(CA&),                                1, ConstCaster       >();
+    runTestCase< R(CA&, CA&),                           2, ConstCaster       >();
+    runTestCase< R(CA&, CA&, CA&),                      3, ConstCaster       >();
+
+    runFunctionTestCase<R(...),                         0, LValueCaster      >();
+    runFunctionTestCase<R(A&, ...),                     1, LValueCaster      >();
+    runFunctionTestCase<R(A&, A&, ...),                 2, LValueCaster      >();
+    runFunctionTestCase<R(A&, A&, A&, ...),             3, LValueCaster      >();
+
+#if TEST_STD_VER >= 11
+    runFunctionTestCase11<R(A&&),                       1, MoveCaster        >();
+    runFunctionTestCase11<R(A&&, ...),                  1, MoveCaster        >();
+#endif
+
+    runFunctorTestCase<R(),                             0, LValueCaster      >();
+    runFunctorTestCase<R() const,                       0, ConstCaster       >();
+    runFunctorTestCase<R() volatile,                    0, VolatileCaster    >();
+    runFunctorTestCase<R() const volatile,              0, CVCaster          >();
+    runFunctorTestCase<R(A&),                           1, LValueCaster      >();
+    runFunctorTestCase<R(A&) const,                     1, ConstCaster       >();
+    runFunctorTestCase<R(A&) volatile,                  1, VolatileCaster    >();
+    runFunctorTestCase<R(A&) const volatile,            1, CVCaster          >();
+    runFunctorTestCase<R(A&, A&),                       2, LValueCaster      >();
+    runFunctorTestCase<R(A&, A&) const,                 2, ConstCaster       >();
+    runFunctorTestCase<R(A&, A&) volatile,              2, VolatileCaster    >();
+    runFunctorTestCase<R(A&, A&) const volatile,        2, CVCaster          >();
+    runFunctorTestCase<R(A&, A&, A&),                   3, LValueCaster      >();
+    runFunctorTestCase<R(A&, A&, A&) const,             3, ConstCaster       >();
+    runFunctorTestCase<R(A&, A&, A&) volatile,          3, VolatileCaster    >();
+    runFunctorTestCase<R(A&, A&, A&) const volatile,    3, CVCaster          >();
+    {
+    typedef ConstCaster CC;
+    runFunctorTestCase<R(CA&),                          1, LValueCaster,   CC>();
+    runFunctorTestCase<R(CA&) const,                    1, ConstCaster,    CC>();
+    runFunctorTestCase<R(CA&) volatile,                 1, VolatileCaster, CC>();
+    runFunctorTestCase<R(CA&) const volatile,           1, CVCaster,       CC>();
+    runFunctorTestCase<R(CA&, CA&),                     2, LValueCaster,   CC>();
+    runFunctorTestCase<R(CA&, CA&) const,               2, ConstCaster,    CC>();
+    runFunctorTestCase<R(CA&, CA&) volatile,            2, VolatileCaster, CC>();
+    runFunctorTestCase<R(CA&, CA&) const volatile,      2, CVCaster,       CC>();
+    runFunctorTestCase<R(CA&, CA&, CA&),                3, LValueCaster,   CC>();
+    runFunctorTestCase<R(CA&, CA&, CA&) const,          3, ConstCaster,    CC>();
+    runFunctorTestCase<R(CA&, CA&, CA&) volatile,       3, VolatileCaster, CC>();
+    runFunctorTestCase<R(CA&, CA&, CA&) const volatile, 3, CVCaster,       CC>();
+    }
+
+#if TEST_STD_VER >= 11
+    runFunctorTestCase11<R() &,                    0, LValueCaster          >();
+    runFunctorTestCase11<R() const &,              0, ConstCaster           >();
+    runFunctorTestCase11<R() volatile &,           0, VolatileCaster        >();
+    runFunctorTestCase11<R() const volatile &,     0, CVCaster              >();
+    runFunctorTestCase11<R() &&,                   0, MoveCaster            >();
+    runFunctorTestCase11<R() const &&,             0, MoveConstCaster       >();
+    runFunctorTestCase11<R() volatile &&,          0, MoveVolatileCaster    >();
+    runFunctorTestCase11<R() const volatile &&,    0, MoveCVCaster          >();
+    {
+    typedef MoveCaster MC;
+    runFunctorTestCase11<R(A&&) &,                 1, LValueCaster,       MC>();
+    runFunctorTestCase11<R(A&&) const &,           1, ConstCaster,        MC>();
+    runFunctorTestCase11<R(A&&) volatile &,        1, VolatileCaster,     MC>();
+    runFunctorTestCase11<R(A&&) const volatile &,  1, CVCaster,           MC>();
+    runFunctorTestCase11<R(A&&) &&,                1, MoveCaster,         MC>();
+    runFunctorTestCase11<R(A&&) const &&,          1, MoveConstCaster,    MC>();
+    runFunctorTestCase11<R(A&&) volatile &&,       1, MoveVolatileCaster, MC>();
+    runFunctorTestCase11<R(A&&) const volatile &&, 1, MoveCVCaster,       MC>();
+    }
+#endif
+}
diff --git a/test/std/utilities/function.objects/func.require/invoke_helpers.h b/test/std/utilities/function.objects/func.require/invoke_helpers.h
new file mode 100644
index 0000000..0583b62
--- /dev/null
+++ b/test/std/utilities/function.objects/func.require/invoke_helpers.h
@@ -0,0 +1,317 @@
+#ifndef INVOKE_HELPERS_H
+#define INVOKE_HELPERS_H
+
+#include <type_traits>
+#include <cassert>
+#include <functional>
+
+#include "test_macros.h"
+
+template <int I>
+struct Int : public std::integral_constant<int, I> {};
+
+template <bool P>
+struct Bool : public std::integral_constant<bool, P> {};
+
+struct Q_None {
+    template <class T>
+    struct apply { typedef T type; };
+};
+
+struct Q_Const {
+    template <class T>
+    struct apply { typedef T const type; };
+};
+
+struct Q_Volatile {
+    template <class T>
+    struct apply { typedef T volatile type; };
+};
+
+struct Q_CV {
+    template <class T>
+    struct apply { typedef T const volatile type; };
+};
+
+// Caster - A functor object that performs cv-qualifier and value category
+//   conversions.
+//   QualTag - A metafunction type that applies cv-qualifiers to its argument.
+//   RValue - True if the resulting object should be an RValue reference.
+//            False otherwise.
+template <class QualTag, bool RValue = false>
+struct Caster {
+    template <class T>
+    struct apply {
+        typedef typename std::remove_reference<T>::type RawType;
+        typedef typename QualTag::template apply<RawType>::type CVType;
+#if TEST_STD_VER >= 11
+        typedef typename std::conditional<RValue,
+            CVType&&, CVType&
+        >::type type;
+#else
+        typedef CVType& type;
+#endif
+    };
+
+    template <class T>
+    typename apply<T>::type
+    operator()(T& obj) const {
+        typedef typename apply<T>::type OutType;
+        return static_cast<OutType>(obj);
+    }
+};
+
+typedef Caster<Q_None>           LValueCaster;
+typedef Caster<Q_Const>          ConstCaster;
+typedef Caster<Q_Volatile>       VolatileCaster;
+typedef Caster<Q_CV>             CVCaster;
+typedef Caster<Q_None,     true> MoveCaster;
+typedef Caster<Q_Const,    true> MoveConstCaster;
+typedef Caster<Q_Volatile, true> MoveVolatileCaster;
+typedef Caster<Q_CV,       true> MoveCVCaster;
+
+// A shorter name for 'static_cast'
+template <class QualType, class Tp>
+QualType C_(Tp& v) { return static_cast<QualType>(v); };
+
+//==============================================================================
+// ArgType - A non-copyable type intended to be used as a dummy argument type
+//   to test functions.
+struct ArgType {
+    int value;
+    explicit ArgType(int val = 0) : value(val) {}
+private:
+    ArgType(ArgType const&);
+    ArgType& operator=(ArgType const&);
+};
+
+//==============================================================================
+// DerivedFromBase - A type that derives from it's template argument 'Base'
+template <class Base>
+struct DerivedFromType : public Base {
+    DerivedFromType() : Base() {}
+    template <class Tp>
+    explicit DerivedFromType(Tp const& t) : Base(t) {}
+};
+
+//==============================================================================
+// DerefToType - A type that dereferences to it's template argument 'To'.
+//   The cv-ref qualifiers of the 'DerefToType' object do not propagate
+//   to the resulting 'To' object.
+template <class To>
+struct DerefToType {
+    To object;
+
+    DerefToType() {}
+
+    template <class Up>
+    explicit DerefToType(Up const& val) : object(val) {}
+
+    To& operator*() const volatile { return const_cast<To&>(object); }
+};
+
+//==============================================================================
+// DerefPropToType - A type that dereferences to it's template argument 'To'.
+//   The cv-ref qualifiers of the 'DerefPropToType' object propagate
+//   to the resulting 'To' object.
+template <class To>
+struct DerefPropType {
+    To object;
+
+    DerefPropType() {}
+
+    template <class Up>
+    explicit DerefPropType(Up const& val) : object(val) {}
+
+#if TEST_STD_VER < 11
+    To& operator*() { return object; }
+    To const& operator*() const { return object; }
+    To volatile& operator*() volatile  { return object; }
+    To const volatile& operator*() const volatile { return object; }
+#else
+    To& operator*() & { return object; }
+    To const& operator*() const & { return object; }
+    To volatile& operator*() volatile  & { return object; }
+    To const volatile& operator*() const volatile & { return object; }
+    To&& operator*() && { return static_cast<To &&>(object); }
+    To const&& operator*() const && { return static_cast<To const&&>(object); }
+    To volatile&& operator*() volatile  && { return static_cast<To volatile&&>(object); }
+    To const volatile&& operator*() const volatile && { return static_cast<To const volatile&&>(object); }
+#endif
+};
+
+//==============================================================================
+// MethodID - A type that uniquely identifies a member function for a class.
+//   This type is used to communicate between the member functions being tested
+//   and the tests invoking them.
+// - Test methods should call 'setUncheckedCall()' whenever they are invoked.
+// - Tests consume the unchecked call using checkCall(<return-value>)` to assert
+//   that the method has been called and that the return value of `__invoke`
+//   matches what the method actually returned.
+template <class T>
+struct MethodID {
+    typedef void* IDType;
+
+    static int dummy; // A dummy memory location.
+    static void* id; // The "ID" is the value of this pointer.
+    static bool unchecked_call; // Has a call happened that has not been checked.
+
+    static void*& setUncheckedCall() {
+        assert(unchecked_call == false);
+        unchecked_call = true;
+        return id;
+    }
+
+    static bool checkCalled(void*& return_value) {
+        bool old = unchecked_call;
+        unchecked_call = false;
+        return old && id == return_value && &id == &return_value;
+    }
+};
+
+template <class T> int   MethodID<T>::dummy = 0;
+template <class T> void* MethodID<T>::id = (void*)&MethodID<T>::dummy;
+template <class T> bool  MethodID<T>::unchecked_call = false;
+
+
+//==============================================================================
+// FunctionPtrID - Like MethodID but for free function pointers.
+template <class T, T*>
+struct FunctionPtrID {
+    static int dummy; // A dummy memory location.
+    static void* id; // The "ID" is the value of this pointer.
+    static bool unchecked_call; // Has a call happened that has not been checked.
+
+    static void*& setUncheckedCall() {
+        assert(unchecked_call == false);
+        unchecked_call = true;
+        return id;
+    }
+
+    static bool checkCalled(void*& return_value) {
+        bool old = unchecked_call;
+        unchecked_call = false;
+        return old && id == return_value && &id == &return_value;
+    }
+};
+
+template <class T, T* Ptr> int   FunctionPtrID<T, Ptr>::dummy = 0;
+template <class T, T* Ptr> void* FunctionPtrID<T, Ptr>::id = (void*)&FunctionPtrID<T, Ptr>::dummy;
+template <class T, T* Ptr> bool  FunctionPtrID<T, Ptr>::unchecked_call = false;
+
+//==============================================================================
+// BasicTest - The basic test structure for everything except
+// member object pointers.
+// ID - The "Function Identifier" type used either MethodID or FunctionPtrID.
+// Arity - The Arity of the call signature.
+// ObjectCaster - The object transformation functor type.
+// ArgCaster - The extra argument transformation functor type.
+template <class ID, int Arity, class ObjectCaster = LValueCaster,
+                               class ArgCaster    = LValueCaster>
+struct BasicTest {
+    template <class ObjectT>
+    void runTest(ObjectT& object) {
+        Int<Arity> A;
+        runTestImp(A, object);
+    }
+
+    template <class MethodPtr, class ObjectT>
+    void runTest(MethodPtr ptr, ObjectT& object) {
+        Int<Arity> A;
+        runTestImp(A, ptr, object);
+    }
+
+private:
+    typedef void*& CallRet;
+    ObjectCaster object_cast;
+    ArgCaster arg_cast;
+    ArgType a0, a1, a2;
+
+    //==========================================================================
+    //                       BULLET 1 AND 2 TEST METHODS
+    //==========================================================================
+    template <class MethodPtr, class ObjectT>
+    void runTestImp(Int<0>, MethodPtr ptr, ObjectT& object) {
+        static_assert((std::is_same<
+            decltype(std::__invoke(ptr, object_cast(object)))
+          , CallRet>::value), "");
+        assert(ID::unchecked_call == false);
+        CallRet ret = std::__invoke(ptr, object_cast(object));
+        assert(ID::checkCalled(ret));
+    }
+
+    template <class MethodPtr, class ObjectT>
+    void runTestImp(Int<1>, MethodPtr ptr, ObjectT& object) {
+        static_assert((std::is_same<
+            decltype(std::__invoke(ptr, object_cast(object), arg_cast(a0)))
+          , CallRet>::value), "");
+        assert(ID::unchecked_call == false);
+        CallRet ret = std::__invoke(ptr, object_cast(object), arg_cast(a0));
+        assert(ID::checkCalled(ret));
+    }
+
+    template <class MethodPtr, class ObjectT>
+    void runTestImp(Int<2>, MethodPtr ptr, ObjectT& object) {
+        static_assert((std::is_same<
+            decltype(std::__invoke(ptr, object_cast(object), arg_cast(a0), arg_cast(a1)))
+          , CallRet>::value), "");
+        assert(ID::unchecked_call == false);
+        CallRet ret = std::__invoke(ptr, object_cast(object), arg_cast(a0), arg_cast(a1));
+        assert(ID::checkCalled(ret));
+    }
+
+    template <class MethodPtr, class ObjectT>
+    void runTestImp(Int<3>, MethodPtr ptr, ObjectT& object) {
+        static_assert((std::is_same<
+            decltype(std::__invoke(ptr, object_cast(object), arg_cast(a0), arg_cast(a1), arg_cast(a2)))
+          , CallRet>::value), "");
+        assert(ID::unchecked_call == false);
+        CallRet ret = std::__invoke(ptr, object_cast(object), arg_cast(a0), arg_cast(a1), arg_cast(a2));
+        assert(ID::checkCalled(ret));
+    }
+
+    //==========================================================================
+    //                       BULLET 5 TEST METHODS
+    //==========================================================================
+    template <class ObjectT>
+    void runTestImp(Int<0>, ObjectT& object) {
+        static_assert((std::is_same<
+            decltype(std::__invoke(object_cast(object)))
+          , CallRet>::value), "");
+        assert(ID::unchecked_call == false);
+        CallRet ret = std::__invoke(object_cast(object));
+        assert(ID::checkCalled(ret));
+    }
+
+    template <class ObjectT>
+    void runTestImp(Int<1>, ObjectT& object) {
+        static_assert((std::is_same<
+            decltype(std::__invoke(object_cast(object), arg_cast(a0)))
+          , CallRet>::value), "");
+        assert(ID::unchecked_call == false);
+        CallRet ret = std::__invoke(object_cast(object), arg_cast(a0));
+        assert(ID::checkCalled(ret));
+    }
+
+    template <class ObjectT>
+    void runTestImp(Int<2>, ObjectT& object) {
+        static_assert((std::is_same<
+            decltype(std::__invoke(object_cast(object), arg_cast(a0), arg_cast(a1)))
+          , CallRet>::value), "");
+        assert(ID::unchecked_call == false);
+        CallRet ret = std::__invoke(object_cast(object), arg_cast(a0), arg_cast(a1));
+        assert(ID::checkCalled(ret));
+    }
+
+    template <class ObjectT>
+    void runTestImp(Int<3>, ObjectT& object) {
+        static_assert((std::is_same<
+            decltype(std::__invoke(object_cast(object), arg_cast(a0), arg_cast(a1), arg_cast(a2)))
+          , CallRet>::value), "");
+        assert(ID::unchecked_call == false);
+        CallRet ret = std::__invoke(object_cast(object), arg_cast(a0), arg_cast(a1), arg_cast(a2));
+        assert(ID::checkCalled(ret));
+    }
+};
+
+#endif // INVOKE_HELPERS_H
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/F.pass.cpp b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/F.pass.cpp
index cd86e4c..82a6f6c 100644
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/F.pass.cpp
+++ b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/F.pass.cpp
@@ -11,7 +11,7 @@
 
 // class function<R(ArgTypes...)>
 
-// function(nullptr_t);
+// function(F);
 
 #include <functional>
 #include <cassert>
@@ -87,4 +87,8 @@
       assert(f.target<int(*)(int)>() != 0);
       f(1);
     }
+    {
+        std::function <void()> f(static_cast<void (*)()>(0));
+        assert(!f);
+    }
 }
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc.pass.cpp b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc.pass.cpp
index 4feac30..f97e34d 100644
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc.pass.cpp
+++ b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc.pass.cpp
@@ -16,10 +16,12 @@
 #include <functional>
 #include <cassert>
 
-#include "test_allocator.h"
+#include "min_allocator.h"
 
 int main()
 {
-    std::function<int(int)> f(std::allocator_arg, test_allocator<int>());
+    {
+    std::function<int(int)> f(std::allocator_arg, bare_allocator<int>());
     assert(!f);
+    }
 }
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_F.pass.cpp b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_F.pass.cpp
index 28e44a6..352ecfc 100644
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_F.pass.cpp
+++ b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_F.pass.cpp
@@ -16,85 +16,91 @@
 #include <functional>
 #include <cassert>
 
+#include "min_allocator.h"
 #include "test_allocator.h"
+#include "count_new.hpp"
+#include "../function_types.h"
 
-class A
+class DummyClass {};
+
+template <class FuncType, class AllocType>
+void test_FunctionObject(AllocType& alloc)
 {
-    int data_[10];
-public:
-    static int count;
-
-    A()
+    assert(globalMemCounter.checkOutstandingNewEq(0));
     {
-        ++count;
-        for (int i = 0; i < 10; ++i)
-            data_[i] = i;
+    FunctionObject target;
+    assert(FunctionObject::count == 1);
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    std::function<FuncType> f2(std::allocator_arg, alloc, target);
+    assert(FunctionObject::count == 2);
+    assert(globalMemCounter.checkOutstandingNewEq(1));
+    assert(f2.template target<FunctionObject>());
+    assert(f2.template target<FuncType>() == 0);
+    assert(f2.template target<FuncType*>() == 0);
     }
+    assert(FunctionObject::count == 0);
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+}
 
-    A(const A&) {++count;}
 
-    ~A() {--count;}
-
-    int operator()(int i) const
+template <class FuncType, class AllocType>
+void test_FreeFunction(AllocType& alloc)
+{
+    assert(globalMemCounter.checkOutstandingNewEq(0));
     {
-        for (int j = 0; j < 10; ++j)
-            i += data_[j];
-        return i;
+    FuncType* target = &FreeFunction;
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    std::function<FuncType> f2(std::allocator_arg, alloc, target);
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    assert(f2.template target<FuncType*>());
+    assert(*f2.template target<FuncType*>() == target);
+    assert(f2.template target<FuncType>() == 0);
+    assert(f2.template target<DummyClass>() == 0);
     }
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+}
 
-    int foo(int) const {return 1;}
-};
+template <class TargetType, class FuncType, class AllocType>
+void test_MemFunClass(AllocType& alloc)
+{
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    {
+    TargetType target = &MemFunClass::foo;
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    std::function<FuncType> f2(std::allocator_arg, alloc, target);
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    assert(f2.template target<TargetType>());
+    assert(*f2.template target<TargetType>() == target);
+    assert(f2.template target<FuncType*>() == 0);
+    }
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+}
 
-int A::count = 0;
+template <class Alloc>
+void test_for_alloc(Alloc& alloc) {
+    test_FunctionObject<int()>(alloc);
+    test_FunctionObject<int(int)>(alloc);
+    test_FunctionObject<int(int, int)>(alloc);
+    test_FunctionObject<int(int, int, int)>(alloc);
 
-int g(int) {return 0;}
+    test_FreeFunction<int()>(alloc);
+    test_FreeFunction<int(int)>(alloc);
+    test_FreeFunction<int(int, int)>(alloc);
+    test_FreeFunction<int(int, int, int)>(alloc);
 
-class Foo {
-public:
-  void bar(int k) { }
-};
+    test_MemFunClass<int(MemFunClass::*)() const, int(MemFunClass&)>(alloc);
+    test_MemFunClass<int(MemFunClass::*)(int) const, int(MemFunClass&, int)>(alloc);
+    test_MemFunClass<int(MemFunClass::*)(int, int) const, int(MemFunClass&, int, int)>(alloc);
+}
 
 int main()
 {
     {
-    std::function<int(int)> f(std::allocator_arg, test_allocator<A>(), A());
-    assert(A::count == 1);
-    assert(f.target<A>());
-    assert(f.target<int(*)(int)>() == 0);
-    }
-    assert(A::count == 0);
-    {
-    std::function<int(int)> f(std::allocator_arg, test_allocator<int(*)(int)>(), g);
-    assert(f.target<int(*)(int)>());
-    assert(f.target<A>() == 0);
+        bare_allocator<DummyClass> bare_alloc;
+        test_for_alloc(bare_alloc);
     }
     {
-    std::function<int(int)> f(std::allocator_arg, test_allocator<int(*)(int)>(),
-                              (int (*)(int))0);
-    assert(!f);
-    assert(f.target<int(*)(int)>() == 0);
-    assert(f.target<A>() == 0);
-    }
-    {
-    std::function<int(const A*, int)> f(std::allocator_arg,
-                                        test_allocator<int(A::*)(int)const>(),
-                                        &A::foo);
-    assert(f);
-    assert(f.target<int (A::*)(int) const>() != 0);
-    }
-#if __cplusplus >= 201103L
-    {
-    Foo f;
-    std::function<void(int)> fun = std::bind(&Foo::bar, &f, std::placeholders::_1);
-    fun(10);
-    }
-#endif
-    {
-    std::function<void(int)> fun(std::allocator_arg,
-                                 test_allocator<int(*)(int)>(),
-                                 &g);
-    assert(fun);
-    assert(fun.target<int(*)(int)>() != 0);
-    fun(10);
+        non_default_test_allocator<DummyClass> non_default_alloc(42);
+        test_for_alloc(non_default_alloc);
     }
 }
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_function.pass.cpp b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_function.pass.cpp
index bb8feff..371eb98 100644
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_function.pass.cpp
+++ b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_function.pass.cpp
@@ -17,83 +17,108 @@
 #include <functional>
 #include <cassert>
 
+#include "min_allocator.h"
 #include "test_allocator.h"
 #include "count_new.hpp"
+#include "../function_types.h"
 
-class A
+class DummyClass {};
+
+template <class FuncType, class AllocType>
+void test_FunctionObject(AllocType& alloc)
 {
-    int data_[10];
-public:
-    static int count;
-
-    A()
+    assert(globalMemCounter.checkOutstandingNewEq(0));
     {
-        ++count;
-        for (int i = 0; i < 10; ++i)
-            data_[i] = i;
+    // Construct function from FunctionObject.
+    std::function<FuncType> f = FunctionObject();
+    assert(FunctionObject::count == 1);
+    assert(globalMemCounter.checkOutstandingNewEq(1));
+    assert(f.template target<FunctionObject>());
+    assert(f.template target<FuncType>() == 0);
+    assert(f.template target<FuncType*>() == 0);
+    // Copy function with allocator
+    std::function<FuncType> f2(std::allocator_arg, alloc, f);
+    assert(FunctionObject::count == 2);
+    assert(globalMemCounter.checkOutstandingNewEq(2));
+    assert(f2.template target<FunctionObject>());
+    assert(f2.template target<FuncType>() == 0);
+    assert(f2.template target<FuncType*>() == 0);
     }
+    assert(FunctionObject::count == 0);
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+}
 
-    A(const A&) {++count;}
-
-    ~A() {--count;}
-
-    int operator()(int i) const
+template <class FuncType, class AllocType>
+void test_FreeFunction(AllocType& alloc)
+{
+    assert(globalMemCounter.checkOutstandingNewEq(0));
     {
-        for (int j = 0; j < 10; ++j)
-            i += data_[j];
-        return i;
+    // Construct function from function pointer.
+    FuncType* target = &FreeFunction;
+    std::function<FuncType> f = target;
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    assert(f.template target<FuncType*>());
+    assert(*f.template target<FuncType*>() == target);
+    assert(f.template target<FuncType>() == 0);
+    // Copy function with allocator
+    std::function<FuncType> f2(std::allocator_arg, alloc, f);
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    assert(f2.template target<FuncType*>());
+    assert(*f2.template target<FuncType*>() == target);
+    assert(f2.template target<FuncType>() == 0);
     }
-};
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+}
 
-int A::count = 0;
+template <class TargetType, class FuncType, class AllocType>
+void test_MemFunClass(AllocType& alloc)
+{
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    {
+    // Construct function from function pointer.
+    TargetType target = &MemFunClass::foo;
+    std::function<FuncType> f = target;
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    assert(f.template target<TargetType>());
+    assert(*f.template target<TargetType>() == target);
+    assert(f.template target<FuncType*>() == 0);
+    // Copy function with allocator
+    std::function<FuncType> f2(std::allocator_arg, alloc, f);
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+    assert(f2.template target<TargetType>());
+    assert(*f2.template target<TargetType>() == target);
+    assert(f2.template target<FuncType*>() == 0);
+    }
+    assert(globalMemCounter.checkOutstandingNewEq(0));
+}
 
-int g(int) {return 0;}
+template <class Alloc>
+void test_for_alloc(Alloc& alloc)
+{
+    // Large FunctionObject -- Allocation should occur
+    test_FunctionObject<int()>(alloc);
+    test_FunctionObject<int(int)>(alloc);
+    test_FunctionObject<int(int, int)>(alloc);
+    test_FunctionObject<int(int, int, int)>(alloc);
+    // Free function -- No allocation should occur
+    test_FreeFunction<int()>(alloc);
+    test_FreeFunction<int(int)>(alloc);
+    test_FreeFunction<int(int, int)>(alloc);
+    test_FreeFunction<int(int, int, int)>(alloc);
+    // Member function -- No allocation should occur.
+    test_MemFunClass<int(MemFunClass::*)() const, int(MemFunClass&)>(alloc);
+    test_MemFunClass<int(MemFunClass::*)(int) const, int(MemFunClass&, int)>(alloc);
+    test_MemFunClass<int(MemFunClass::*)(int, int) const, int(MemFunClass&, int, int)>(alloc);
+}
 
 int main()
 {
-    assert(globalMemCounter.checkOutstandingNewEq(0));
-    {
-    std::function<int(int)> f = A();
-    assert(A::count == 1);
-    assert(globalMemCounter.checkOutstandingNewEq(1));
-    assert(f.target<A>());
-    assert(f.target<int(*)(int)>() == 0);
-    std::function<int(int)> f2(std::allocator_arg, test_allocator<A>(), f);
-    assert(A::count == 2);
-    assert(globalMemCounter.checkOutstandingNewEq(2));
-    assert(f2.target<A>());
-    assert(f2.target<int(*)(int)>() == 0);
-    }
-    assert(A::count == 0);
-    assert(globalMemCounter.checkOutstandingNewEq(0));
-    {
-    std::function<int(int)> f = g;
-    assert(globalMemCounter.checkOutstandingNewEq(0));
-    assert(f.target<int(*)(int)>());
-    assert(f.target<A>() == 0);
-    std::function<int(int)> f2(std::allocator_arg, test_allocator<int(*)(int)>(), f);
-    assert(globalMemCounter.checkOutstandingNewEq(0));
-    assert(f2.target<int(*)(int)>());
-    assert(f2.target<A>() == 0);
-    }
-    assert(globalMemCounter.checkOutstandingNewEq(0));
-    {
-    assert(globalMemCounter.checkOutstandingNewEq(0));
-    non_default_test_allocator<std::function<int(int)> > al(1);
-    std::function<int(int)> f2(std::allocator_arg, al, g);
-    assert(globalMemCounter.checkOutstandingNewEq(0));
-    assert(f2.target<int(*)(int)>());
-    assert(f2.target<A>() == 0);
-    }
-    assert(globalMemCounter.checkOutstandingNewEq(0));
-    {
-    std::function<int(int)> f;
-    assert(globalMemCounter.checkOutstandingNewEq(0));
-    assert(f.target<int(*)(int)>() == 0);
-    assert(f.target<A>() == 0);
-    std::function<int(int)> f2(std::allocator_arg, test_allocator<int>(), f);
-    assert(globalMemCounter.checkOutstandingNewEq(0));
-    assert(f2.target<int(*)(int)>() == 0);
-    assert(f2.target<A>() == 0);
-    }
+  {
+    bare_allocator<DummyClass> alloc;
+    test_for_alloc(alloc);
+  }
+  {
+    non_default_test_allocator<DummyClass> alloc(42);
+    test_for_alloc(alloc);
+  }
 }
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_nullptr.pass.cpp b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_nullptr.pass.cpp
index 956136b..2350f92 100644
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_nullptr.pass.cpp
+++ b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_nullptr.pass.cpp
@@ -16,10 +16,10 @@
 #include <functional>
 #include <cassert>
 
-#include "test_allocator.h"
+#include "min_allocator.h"
 
 int main()
 {
-    std::function<int(int)> f(std::allocator_arg, test_allocator<int>(), nullptr);
+    std::function<int(int)> f(std::allocator_arg, bare_allocator<int>(), nullptr);
     assert(!f);
 }
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_rfunction.pass.cpp b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_rfunction.pass.cpp
index 15b7c8b..aa6b743 100644
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_rfunction.pass.cpp
+++ b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.con/alloc_rfunction.pass.cpp
@@ -16,7 +16,7 @@
 #include <functional>
 #include <cassert>
 
-#include "test_allocator.h"
+#include "min_allocator.h"
 #include "count_new.hpp"
 
 class A
@@ -56,7 +56,7 @@
     assert(globalMemCounter.checkOutstandingNewEq(1));
     assert(f.target<A>());
     assert(f.target<int(*)(int)>() == 0);
-    std::function<int(int)> f2(std::allocator_arg, test_allocator<A>(), std::move(f));
+    std::function<int(int)> f2(std::allocator_arg, bare_allocator<A>(), std::move(f));
     assert(A::count == 1);
     assert(globalMemCounter.checkOutstandingNewEq(1));
     assert(f2.target<A>());
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke.fail.cpp b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke.fail.cpp
index 6dcd285..61eda72 100644
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke.fail.cpp
+++ b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke.fail.cpp
@@ -30,13 +30,13 @@
 {
     // member data pointer
     {
-    int A_int_1::*fp = &A_int_1::data_;
-    A_int_1 a;
-    std::function<int& (const A_int_1*)> r2(fp);
-    const A_int_1* ap = &a;
-    assert(r2(ap) == 6);
-    r2(ap) = 7;
-    assert(r2(ap) == 7);
+        int A_int_1::*fp = &A_int_1::data_;
+        A_int_1 a;
+        std::function<int& (const A_int_1*)> r2(fp);
+        const A_int_1* ap = &a;
+        assert(r2(ap) == 6);
+        r2(ap) = 7;
+        assert(r2(ap) == 7);
     }
 }
 
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke.pass.cpp b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke.pass.cpp
index 31b80c3..cc4315c 100644
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke.pass.cpp
+++ b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke.pass.cpp
@@ -16,8 +16,85 @@
 #include <functional>
 #include <cassert>
 
+
 int count = 0;
 
+
+// 0 args, return int
+
+int f_int_0()
+{
+    return 3;
+}
+
+struct A_int_0
+{
+    int operator()() {return 4;}
+};
+
+void test_int_0()
+{
+    // function
+    {
+        std::function<int ()> r1(f_int_0);
+        assert(r1() == 3);
+    }
+    // function pointer
+    {
+        int (*fp)() = f_int_0;
+        std::function<int ()> r1(fp);
+        assert(r1() == 3);
+    }
+    // functor
+    {
+        A_int_0 a0;
+        std::function<int ()> r1(a0);
+        assert(r1() == 4);
+    }
+}
+
+
+// 0 args, return void
+
+void f_void_0()
+{
+    ++count;
+}
+
+struct A_void_0
+{
+    void operator()() {++count;}
+};
+
+void
+test_void_0()
+{
+    int save_count = count;
+    // function
+    {
+        std::function<void ()> r1(f_void_0);
+        r1();
+        assert(count == save_count+1);
+        save_count = count;
+    }
+    // function pointer
+    {
+        void (*fp)() = f_void_0;
+        std::function<void ()> r1(fp);
+        r1();
+        assert(count == save_count+1);
+        save_count = count;
+    }
+    // functor
+    {
+        A_void_0 a0;
+        std::function<void ()> r1(a0);
+        r1();
+        assert(count == save_count+1);
+        save_count = count;
+    }
+}
+
 // 1 arg, return void
 
 void f_void_1(int i)
@@ -42,57 +119,57 @@
     int save_count = count;
     // function
     {
-    std::function<void (int)> r1(f_void_1);
-    int i = 2;
-    r1(i);
-    assert(count == save_count+2);
-    save_count = count;
+        std::function<void (int)> r1(f_void_1);
+        int i = 2;
+        r1(i);
+        assert(count == save_count+2);
+        save_count = count;
     }
     // function pointer
     {
-    void (*fp)(int) = f_void_1;
-    std::function<void (int)> r1(fp);
-    int i = 3;
-    r1(i);
-    assert(count == save_count+3);
-    save_count = count;
+        void (*fp)(int) = f_void_1;
+        std::function<void (int)> r1(fp);
+        int i = 3;
+        r1(i);
+        assert(count == save_count+3);
+        save_count = count;
     }
     // functor
     {
-    A_void_1 a0;
-    std::function<void (int)> r1(a0);
-    int i = 4;
-    r1(i);
-    assert(count == save_count+4);
-    save_count = count;
+        A_void_1 a0;
+        std::function<void (int)> r1(a0);
+        int i = 4;
+        r1(i);
+        assert(count == save_count+4);
+        save_count = count;
     }
     // member function pointer
     {
-    void (A_void_1::*fp)() = &A_void_1::mem1;
-    std::function<void (A_void_1)> r1(fp);
-    A_void_1 a;
-    r1(a);
-    assert(count == save_count+1);
-    save_count = count;
-    A_void_1* ap = &a;
-    std::function<void (A_void_1*)> r2 = fp;
-    r2(ap);
-    assert(count == save_count+1);
-    save_count = count;
+        void (A_void_1::*fp)() = &A_void_1::mem1;
+        std::function<void (A_void_1)> r1(fp);
+        A_void_1 a;
+        r1(a);
+        assert(count == save_count+1);
+        save_count = count;
+        A_void_1* ap = &a;
+        std::function<void (A_void_1*)> r2 = fp;
+        r2(ap);
+        assert(count == save_count+1);
+        save_count = count;
     }
     // const member function pointer
     {
-    void (A_void_1::*fp)() const = &A_void_1::mem2;
-    std::function<void (A_void_1)> r1(fp);
-    A_void_1 a;
-    r1(a);
-    assert(count == save_count+1);
-    save_count = count;
-    std::function<void (A_void_1*)> r2(fp);
-    A_void_1* ap = &a;
-    r2(ap);
-    assert(count == save_count+1);
-    save_count = count;
+        void (A_void_1::*fp)() const = &A_void_1::mem2;
+        std::function<void (A_void_1)> r1(fp);
+        A_void_1 a;
+        r1(a);
+        assert(count == save_count+1);
+        save_count = count;
+        std::function<void (A_void_1*)> r2(fp);
+        A_void_1* ap = &a;
+        r2(ap);
+        assert(count == save_count+1);
+        save_count = count;
     }
 }
 
@@ -121,57 +198,57 @@
 {
     // function
     {
-    std::function<int (int)> r1(f_int_1);
-    int i = 2;
-    assert(r1(i) == 3);
+        std::function<int (int)> r1(f_int_1);
+        int i = 2;
+        assert(r1(i) == 3);
     }
     // function pointer
     {
-    int (*fp)(int) = f_int_1;
-    std::function<int (int)> r1(fp);
-    int i = 3;
-    assert(r1(i) == 4);
+        int (*fp)(int) = f_int_1;
+        std::function<int (int)> r1(fp);
+        int i = 3;
+        assert(r1(i) == 4);
     }
     // functor
     {
-    A_int_1 a0;
-    std::function<int (int)> r1(a0);
-    int i = 4;
-    assert(r1(i) == 3);
+        A_int_1 a0;
+        std::function<int (int)> r1(a0);
+        int i = 4;
+        assert(r1(i) == 3);
     }
     // member function pointer
     {
-    int (A_int_1::*fp)() = &A_int_1::mem1;
-    std::function<int (A_int_1)> r1(fp);
-    A_int_1 a;
-    assert(r1(a) == 3);
-    std::function<int (A_int_1*)> r2(fp);
-    A_int_1* ap = &a;
-    assert(r2(ap) == 3);
+        int (A_int_1::*fp)() = &A_int_1::mem1;
+        std::function<int (A_int_1)> r1(fp);
+        A_int_1 a;
+        assert(r1(a) == 3);
+        std::function<int (A_int_1*)> r2(fp);
+        A_int_1* ap = &a;
+        assert(r2(ap) == 3);
     }
     // const member function pointer
     {
-    int (A_int_1::*fp)() const = &A_int_1::mem2;
-    std::function<int (A_int_1)> r1(fp);
-    A_int_1 a;
-    assert(r1(a) == 4);
-    std::function<int (A_int_1*)> r2(fp);
-    A_int_1* ap = &a;
-    assert(r2(ap) == 4);
+        int (A_int_1::*fp)() const = &A_int_1::mem2;
+        std::function<int (A_int_1)> r1(fp);
+        A_int_1 a;
+        assert(r1(a) == 4);
+        std::function<int (A_int_1*)> r2(fp);
+        A_int_1* ap = &a;
+        assert(r2(ap) == 4);
     }
     // member data pointer
     {
-    int A_int_1::*fp = &A_int_1::data_;
-    std::function<int& (A_int_1&)> r1(fp);
-    A_int_1 a;
-    assert(r1(a) == 5);
-    r1(a) = 6;
-    assert(r1(a) == 6);
-    std::function<int& (A_int_1*)> r2(fp);
-    A_int_1* ap = &a;
-    assert(r2(ap) == 6);
-    r2(ap) = 7;
-    assert(r2(ap) == 7);
+        int A_int_1::*fp = &A_int_1::data_;
+        std::function<int& (A_int_1&)> r1(fp);
+        A_int_1 a;
+        assert(r1(a) == 5);
+        r1(a) = 6;
+        assert(r1(a) == 6);
+        std::function<int& (A_int_1*)> r2(fp);
+        A_int_1* ap = &a;
+        assert(r2(ap) == 6);
+        r2(ap) = 7;
+        assert(r2(ap) == 7);
     }
 }
 
@@ -199,62 +276,62 @@
     int save_count = count;
     // function
     {
-    std::function<void (int, int)> r1(f_void_2);
-    int i = 2;
-    int j = 3;
-    r1(i, j);
-    assert(count == save_count+5);
-    save_count = count;
+        std::function<void (int, int)> r1(f_void_2);
+        int i = 2;
+        int j = 3;
+        r1(i, j);
+        assert(count == save_count+5);
+        save_count = count;
     }
     // function pointer
     {
-    void (*fp)(int, int) = f_void_2;
-    std::function<void (int, int)> r1(fp);
-    int i = 3;
-    int j = 4;
-    r1(i, j);
-    assert(count == save_count+7);
-    save_count = count;
+        void (*fp)(int, int) = f_void_2;
+        std::function<void (int, int)> r1(fp);
+        int i = 3;
+        int j = 4;
+        r1(i, j);
+        assert(count == save_count+7);
+        save_count = count;
     }
     // functor
     {
-    A_void_2 a0;
-    std::function<void (int, int)> r1(a0);
-    int i = 4;
-    int j = 5;
-    r1(i, j);
-    assert(count == save_count+9);
-    save_count = count;
+        A_void_2 a0;
+        std::function<void (int, int)> r1(a0);
+        int i = 4;
+        int j = 5;
+        r1(i, j);
+        assert(count == save_count+9);
+        save_count = count;
     }
     // member function pointer
     {
-    void (A_void_2::*fp)(int) = &A_void_2::mem1;
-    std::function<void (A_void_2, int)> r1(fp);
-    A_void_2 a;
-    int i = 3;
-    r1(a, i);
-    assert(count == save_count+3);
-    save_count = count;
-    std::function<void (A_void_2*, int)> r2(fp);
-    A_void_2* ap = &a;
-    r2(ap, i);
-    assert(count == save_count+3);
-    save_count = count;
+        void (A_void_2::*fp)(int) = &A_void_2::mem1;
+        std::function<void (A_void_2, int)> r1(fp);
+        A_void_2 a;
+        int i = 3;
+        r1(a, i);
+        assert(count == save_count+3);
+        save_count = count;
+        std::function<void (A_void_2*, int)> r2(fp);
+        A_void_2* ap = &a;
+        r2(ap, i);
+        assert(count == save_count+3);
+        save_count = count;
     }
     // const member function pointer
     {
-    void (A_void_2::*fp)(int) const = &A_void_2::mem2;
-    std::function<void (A_void_2, int)> r1(fp);
-    A_void_2 a;
-    int i = 4;
-    r1(a, i);
-    assert(count == save_count+4);
-    save_count = count;
-    std::function<void (A_void_2*, int)> r2(fp);
-    A_void_2* ap = &a;
-    r2(ap, i);
-    assert(count == save_count+4);
-    save_count = count;
+        void (A_void_2::*fp)(int) const = &A_void_2::mem2;
+        std::function<void (A_void_2, int)> r1(fp);
+        A_void_2 a;
+        int i = 4;
+        r1(a, i);
+        assert(count == save_count+4);
+        save_count = count;
+        std::function<void (A_void_2*, int)> r2(fp);
+        A_void_2* ap = &a;
+        r2(ap, i);
+        assert(count == save_count+4);
+        save_count = count;
     }
 }
 
@@ -276,60 +353,61 @@
     int mem2(int i) const {return i+2;}
 };
 
-void
-testint_2()
+void test_int_2()
 {
     // function
     {
-    std::function<int (int, int)> r1(f_int_2);
-    int i = 2;
-    int j = 3;
-    assert(r1(i, j) == i+j);
+        std::function<int (int, int)> r1(f_int_2);
+        int i = 2;
+        int j = 3;
+        assert(r1(i, j) == i+j);
     }
     // function pointer
     {
-    int (*fp)(int, int) = f_int_2;
-    std::function<int (int, int)> r1(fp);
-    int i = 3;
-    int j = 4;
-    assert(r1(i, j) == i+j);
+        int (*fp)(int, int) = f_int_2;
+        std::function<int (int, int)> r1(fp);
+        int i = 3;
+        int j = 4;
+        assert(r1(i, j) == i+j);
     }
     // functor
     {
-    A_int_2 a0;
-    std::function<int (int, int)> r1(a0);
-    int i = 4;
-    int j = 5;
-    assert(r1(i, j) == i+j);
+        A_int_2 a0;
+        std::function<int (int, int)> r1(a0);
+        int i = 4;
+        int j = 5;
+        assert(r1(i, j) == i+j);
     }
     // member function pointer
     {
-    int(A_int_2::*fp)(int) = &A_int_2::mem1;
-    std::function<int (A_int_2, int)> r1(fp);
-    A_int_2 a;
-    int i = 3;
-    assert(r1(a, i) == i+1);
-    std::function<int (A_int_2*, int)> r2(fp);
-    A_int_2* ap = &a;
-    assert(r2(ap, i) == i+1);
+        int(A_int_2::*fp)(int) = &A_int_2::mem1;
+        std::function<int (A_int_2, int)> r1(fp);
+        A_int_2 a;
+        int i = 3;
+        assert(r1(a, i) == i+1);
+        std::function<int (A_int_2*, int)> r2(fp);
+        A_int_2* ap = &a;
+        assert(r2(ap, i) == i+1);
     }
     // const member function pointer
     {
-    int (A_int_2::*fp)(int) const = &A_int_2::mem2;
-    std::function<int (A_int_2, int)> r1(fp);
-    A_int_2 a;
-    int i = 4;
-    assert(r1(a, i) == i+2);
-    std::function<int (A_int_2*, int)> r2(fp);
-    A_int_2* ap = &a;
-    assert(r2(ap, i) == i+2);
+        int (A_int_2::*fp)(int) const = &A_int_2::mem2;
+        std::function<int (A_int_2, int)> r1(fp);
+        A_int_2 a;
+        int i = 4;
+        assert(r1(a, i) == i+2);
+        std::function<int (A_int_2*, int)> r2(fp);
+        A_int_2* ap = &a;
+        assert(r2(ap, i) == i+2);
     }
 }
 
 int main()
 {
+    test_void_0();
+    test_int_0();
     test_void_1();
     test_int_1();
     test_void_2();
-    testint_2();
+    test_int_2();
 }
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke_int_0.pass.cpp b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke_int_0.pass.cpp
deleted file mode 100644
index 67b4ec2..0000000
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke_int_0.pass.cpp
+++ /dev/null
@@ -1,58 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <functional>
-
-// class function<R(ArgTypes...)>
-
-// R operator()(ArgTypes... args) const
-
-#include <functional>
-#include <cassert>
-
-// 0 args, return int
-
-int count = 0;
-
-int f_int_0()
-{
-    return 3;
-}
-
-struct A_int_0
-{
-    int operator()() {return 4;}
-};
-
-void
-test_int_0()
-{
-    // function
-    {
-    std::function<int ()> r1(f_int_0);
-    assert(r1() == 3);
-    }
-    // function pointer
-    {
-    int (*fp)() = f_int_0;
-    std::function<int ()> r1(fp);
-    assert(r1() == 3);
-    }
-    // functor
-    {
-    A_int_0 a0;
-    std::function<int ()> r1(a0);
-    assert(r1() == 4);
-    }
-}
-
-int main()
-{
-    test_int_0();
-}
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke_no_variadics.pass.cpp b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke_no_variadics.pass.cpp
deleted file mode 100644
index c0a14fd..0000000
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke_no_variadics.pass.cpp
+++ /dev/null
@@ -1,60 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <functional>
-
-// class function<R()>
-
-// Test that we properly return both values and void for all non-variadic
-// overloads of function::operator()(...)
-
-#define _LIBCPP_HAS_NO_VARIADICS
-#include <functional>
-#include <cassert>
-
-int foo0() { return 42; }
-int foo1(int) { return 42; }
-int foo2(int, int) { return 42; }
-int foo3(int, int, int) { return 42; }
-
-int main()
-{
-    {
-        std::function<int()> f(&foo0);
-        assert(f() == 42);
-    }
-    {
-        std::function<int(int)> f(&foo1);
-        assert(f(1) == 42);
-    }
-    {
-        std::function<int(int, int)> f(&foo2);
-        assert(f(1, 1) == 42);
-    }
-    {
-        std::function<int(int, int, int)> f(&foo3);
-        assert(f(1, 1, 1) == 42);
-    }
-    {
-        std::function<void()> f(&foo0);
-        f();
-    }
-    {
-        std::function<void(int)> f(&foo1);
-        f(1);
-    }
-    {
-        std::function<void(int, int)> f(&foo2);
-        f(1, 1);
-    }
-    {
-        std::function<void(int, int, int)> f(&foo3);
-        f(1, 1, 1);
-    }
-}
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke_void_0.pass.cpp b/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke_void_0.pass.cpp
deleted file mode 100644
index a820cb1..0000000
--- a/test/std/utilities/function.objects/func.wrap/func.wrap.func/func.wrap.func.inv/invoke_void_0.pass.cpp
+++ /dev/null
@@ -1,67 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <functional>
-
-// class function<R(ArgTypes...)>
-
-// R operator()(ArgTypes... args) const
-
-#include <functional>
-#include <new>
-#include <cstdlib>
-#include <cassert>
-
-// 0 args, return void
-
-int count = 0;
-
-void f_void_0()
-{
-    ++count;
-}
-
-struct A_void_0
-{
-    void operator()() {++count;}
-};
-
-void
-test_void_0()
-{
-    int save_count = count;
-    // function
-    {
-    std::function<void ()> r1(f_void_0);
-    r1();
-    assert(count == save_count+1);
-    save_count = count;
-    }
-    // function pointer
-    {
-    void (*fp)() = f_void_0;
-    std::function<void ()> r1(fp);
-    r1();
-    assert(count == save_count+1);
-    save_count = count;
-    }
-    // functor
-    {
-    A_void_0 a0;
-    std::function<void ()> r1(a0);
-    r1();
-    assert(count == save_count+1);
-    save_count = count;
-    }
-}
-
-int main()
-{
-    test_void_0();
-}
diff --git a/test/std/utilities/function.objects/func.wrap/func.wrap.func/function_types.h b/test/std/utilities/function.objects/func.wrap/func.wrap.func/function_types.h
new file mode 100644
index 0000000..55eb80f
--- /dev/null
+++ b/test/std/utilities/function.objects/func.wrap/func.wrap.func/function_types.h
@@ -0,0 +1,57 @@
+#ifndef FUNCTION_TYPES_H
+#define FUNCTION_TYPES_H
+
+
+class FunctionObject
+{
+    int data_[10]; // dummy variable to prevent small object optimization in
+                   // std::function
+public:
+    static int count;
+
+    FunctionObject() {
+        ++count;
+        for (int i = 0; i < 10; ++i) data_[i] = i;
+    }
+
+    FunctionObject(const FunctionObject&) {++count;}
+    ~FunctionObject() {--count; ((void)data_); }
+
+    int operator()() const { return 42; }
+    int operator()(int i) const { return i; }
+    int operator()(int i, int) const { return i; }
+    int operator()(int i, int, int) const { return i; }
+};
+
+int FunctionObject::count = 0;
+
+class MemFunClass
+{
+    int data_[10]; // dummy variable to prevent small object optimization in
+                   // std::function
+public:
+    static int count;
+
+    MemFunClass() {
+        ++count;
+        for (int i = 0; i < 10; ++i) data_[i] = 0;
+    }
+
+    MemFunClass(const MemFunClass&) {++count; ((void)data_); }
+
+    ~MemFunClass() {--count;}
+
+    int foo() const { return 42; }
+    int foo(int i) const { return i; }
+    int foo(int i, int) const { return i; }
+    int foo(int i, int, int) const { return i; }
+};
+
+int MemFunClass::count = 0;
+
+int FreeFunction() { return 42; }
+int FreeFunction(int i) {return i;}
+int FreeFunction(int i, int) { return i; }
+int FreeFunction(int i, int, int) { return i; }
+
+#endif // FUNCTION_TYPES_H
diff --git a/test/std/utilities/memory/allocator.traits/allocator.traits.types/is_always_equal.pass.cpp b/test/std/utilities/memory/allocator.traits/allocator.traits.types/is_always_equal.pass.cpp
new file mode 100644
index 0000000..31a0f17
--- /dev/null
+++ b/test/std/utilities/memory/allocator.traits/allocator.traits.types/is_always_equal.pass.cpp
@@ -0,0 +1,52 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <memory>
+
+// template <class Alloc>
+// struct allocator_traits
+// {
+//   typedef Alloc::is_always_equal
+//         | is_empty                     is_always_equal;
+//     ...
+// };
+
+#include <memory>
+#include <type_traits>
+
+template <class T>
+struct A
+{
+    typedef T value_type;
+    typedef std::true_type is_always_equal;
+};
+
+template <class T>
+struct B
+{
+    typedef T value_type;
+};
+
+template <class T>
+struct C
+{
+    typedef T value_type;
+	int not_empty_;  // some random member variable
+};
+
+int main()
+{
+    static_assert((std::is_same<std::allocator_traits<A<char> >::is_always_equal, std::true_type>::value), "");
+    static_assert((std::is_same<std::allocator_traits<B<char> >::is_always_equal, std::true_type>::value), "");
+    static_assert((std::is_same<std::allocator_traits<C<char> >::is_always_equal, std::false_type>::value), "");
+
+    static_assert((std::is_same<std::allocator_traits<A<const char> >::is_always_equal, std::true_type>::value), "");
+    static_assert((std::is_same<std::allocator_traits<B<const char> >::is_always_equal, std::true_type>::value), "");
+    static_assert((std::is_same<std::allocator_traits<C<const char> >::is_always_equal, std::false_type>::value), "");
+}
diff --git a/test/std/utilities/memory/default.allocator/allocator.members/construct.pass.cpp b/test/std/utilities/memory/default.allocator/allocator.members/construct.pass.cpp
index d0a870e..40c44d9 100644
--- a/test/std/utilities/memory/default.allocator/allocator.members/construct.pass.cpp
+++ b/test/std/utilities/memory/default.allocator/allocator.members/construct.pass.cpp
@@ -15,6 +15,7 @@
 #include <memory>
 #include <cassert>
 
+#include "test_macros.h"
 #include "count_new.hpp"
 
 int A_constructed = 0;
@@ -34,30 +35,22 @@
 
 int move_only_constructed = 0;
 
+#if TEST_STD_VER >= 11
 class move_only
 {
     int data;
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    move_only(const move_only&);
-    move_only& operator=(const move_only&);
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    move_only(move_only&);
-    move_only& operator=(move_only&);
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
+
+    move_only(const move_only&) = delete;
+    move_only& operator=(const move_only&)= delete;
 
 public:
-
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     move_only(move_only&&) {++move_only_constructed;}
     move_only& operator=(move_only&&) {return *this;}
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    operator std::__rv<move_only> () {return std::__rv<move_only>(*this);}
-    move_only(std::__rv<move_only>) {++move_only_constructed;}
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
     move_only() {++move_only_constructed;}
     ~move_only() {--move_only_constructed;}
 };
+#endif // TEST_STD_VER >= 11
 
 int main()
 {
@@ -108,6 +101,7 @@
     assert(globalMemCounter.checkOutstandingNewEq(0));
     assert(A_constructed == 0);
     }
+#if TEST_STD_VER >= 11
     {
     std::allocator<move_only> a;
     assert(globalMemCounter.checkOutstandingNewEq(0));
@@ -139,4 +133,5 @@
     assert(globalMemCounter.checkOutstandingNewEq(0));
     assert(move_only_constructed == 0);
     }
+#endif
 }
diff --git a/test/std/utilities/memory/default.allocator/allocator_types.pass.cpp b/test/std/utilities/memory/default.allocator/allocator_types.pass.cpp
index db08123..cba3210 100644
--- a/test/std/utilities/memory/default.allocator/allocator_types.pass.cpp
+++ b/test/std/utilities/memory/default.allocator/allocator_types.pass.cpp
@@ -22,6 +22,7 @@
 //     typedef typename add_lvalue_reference<T>::type       reference;
 //     typedef typename add_lvalue_reference<const T>::type const_reference;
 //     typedef T                                     value_type;
+//     typedef true_type                             is_always_equal;
 //
 //     template <class U> struct rebind {typedef allocator<U> other;};
 // ...
@@ -42,6 +43,10 @@
     static_assert((std::is_same<std::allocator<char>::const_reference, const char&>::value), "");
     static_assert((std::is_same<std::allocator<char>::rebind<int>::other,
                                 std::allocator<int> >::value), "");
+
+    static_assert((std::is_same<std::allocator<      char>::is_always_equal, std::true_type>::value), "");
+    static_assert((std::is_same<std::allocator<const char>::is_always_equal, std::true_type>::value), "");
+
     std::allocator<char> a;
     std::allocator<char> a2 = a;
     a2 = a;
diff --git a/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/uninitialized_copy.pass.cpp b/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/uninitialized_copy.pass.cpp
index 7de7ecc..f431335 100644
--- a/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/uninitialized_copy.pass.cpp
+++ b/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/uninitialized_copy.pass.cpp
@@ -28,8 +28,19 @@
 
 int B::count_ = 0;
 
+struct Nasty
+{
+    Nasty() : i_ ( counter_++ ) {}
+    Nasty * operator &() const { return NULL; }
+    int i_;
+    static int counter_; 
+};
+
+int Nasty::counter_ = 0;
+
 int main()
 {
+    {
     const int N = 5;
     char pool[sizeof(B)*N] = {0};
     B* bp = (B*)pool;
@@ -48,4 +59,17 @@
     std::uninitialized_copy(b, b+2, bp);
     for (int i = 0; i < 2; ++i)
         assert(bp[i].data_ == 1);
+    }
+    {
+    const int N = 5;
+    char pool[sizeof(Nasty)*N] = {0};
+    Nasty * p = (Nasty *) pool;
+    Nasty arr[N];
+    std::uninitialized_copy(arr, arr+N, p);
+    for (int i = 0; i < N; ++i) {
+        assert(arr[i].i_ == i);
+        assert(  p[i].i_ == i);
+        }
+    }
+    
 }
diff --git a/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/uninitialized_copy_n.pass.cpp b/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/uninitialized_copy_n.pass.cpp
index 79afa4f..3b2007b 100644
--- a/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/uninitialized_copy_n.pass.cpp
+++ b/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/uninitialized_copy_n.pass.cpp
@@ -28,8 +28,19 @@
 
 int B::count_ = 0;
 
+struct Nasty
+{
+    Nasty() : i_ ( counter_++ ) {}
+    Nasty * operator &() const { return NULL; }
+    int i_;
+    static int counter_; 
+};
+
+int Nasty::counter_ = 0;
+
 int main()
 {
+    {
     const int N = 5;
     char pool[sizeof(B)*N] = {0};
     B* bp = (B*)pool;
@@ -48,4 +59,16 @@
     std::uninitialized_copy_n(b, 2, bp);
     for (int i = 0; i < 2; ++i)
         assert(bp[i].data_ == 1);
+    }
+    {
+    const int N = 5;
+    char pool[sizeof(Nasty)*N] = {0};
+    Nasty * p = (Nasty *) pool;
+    Nasty arr[N];
+    std::uninitialized_copy_n(arr, N, p);
+    for (int i = 0; i < N; ++i) {
+        assert(arr[i].i_ == i);
+        assert(  p[i].i_ == i);
+    }
+    }
 }
diff --git a/test/std/utilities/memory/specialized.algorithms/uninitialized.fill.n/uninitialized_fill_n.pass.cpp b/test/std/utilities/memory/specialized.algorithms/uninitialized.fill.n/uninitialized_fill_n.pass.cpp
index 8fc6b81..d2b1dfa 100644
--- a/test/std/utilities/memory/specialized.algorithms/uninitialized.fill.n/uninitialized_fill_n.pass.cpp
+++ b/test/std/utilities/memory/specialized.algorithms/uninitialized.fill.n/uninitialized_fill_n.pass.cpp
@@ -27,8 +27,19 @@
 
 int B::count_ = 0;
 
+struct Nasty
+{
+    Nasty() : i_ ( counter_++ ) {}
+    Nasty * operator &() const { return NULL; }
+    int i_;
+    static int counter_; 
+};
+
+int Nasty::counter_ = 0;
+
 int main()
 {
+    {
     const int N = 5;
     char pool[sizeof(B)*N] = {0};
     B* bp = (B*)pool;
@@ -47,4 +58,18 @@
     assert(r == bp + 2);
     for (int i = 0; i < 2; ++i)
         assert(bp[i].data_ == 1);
+    }
+    {
+    {
+    const int N = 5;
+    char pool[N*sizeof(Nasty)] = {0};
+    Nasty* bp = (Nasty*)pool;
+
+    Nasty::counter_ = 23;
+    std::uninitialized_fill_n(bp, N, Nasty());
+    for (int i = 0; i < N; ++i)
+        assert(bp[i].i_ == 23);
+    }
+
+    }
 }
diff --git a/test/std/utilities/memory/specialized.algorithms/uninitialized.fill/uninitialized_fill.pass.cpp b/test/std/utilities/memory/specialized.algorithms/uninitialized.fill/uninitialized_fill.pass.cpp
index c34fdc7..47cabdf 100644
--- a/test/std/utilities/memory/specialized.algorithms/uninitialized.fill/uninitialized_fill.pass.cpp
+++ b/test/std/utilities/memory/specialized.algorithms/uninitialized.fill/uninitialized_fill.pass.cpp
@@ -28,8 +28,19 @@
 
 int B::count_ = 0;
 
+struct Nasty
+{
+    Nasty() : i_ ( counter_++ ) {}
+    Nasty * operator &() const { return NULL; }
+    int i_;
+    static int counter_; 
+};
+
+int Nasty::counter_ = 0;
+
 int main()
 {
+    {
     const int N = 5;
     char pool[sizeof(B)*N] = {0};
     B* bp = (B*)pool;
@@ -47,4 +58,15 @@
     std::uninitialized_fill(bp, bp+2, B());
     for (int i = 0; i < 2; ++i)
         assert(bp[i].data_ == 1);
+    }
+    {
+    const int N = 5;
+    char pool[N*sizeof(Nasty)] = {0};
+    Nasty* bp = (Nasty*)pool;
+
+    Nasty::counter_ = 23;
+    std::uninitialized_fill(bp, bp+N, Nasty());
+    for (int i = 0; i < N; ++i)
+        assert(bp[i].i_ == 23);
+    }
 }
diff --git a/test/std/utilities/memory/storage.iterator/raw_storag_iterator.base.pass.cpp b/test/std/utilities/memory/storage.iterator/raw_storag_iterator.base.pass.cpp
new file mode 100644
index 0000000..27b6205
--- /dev/null
+++ b/test/std/utilities/memory/storage.iterator/raw_storag_iterator.base.pass.cpp
@@ -0,0 +1,48 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// raw_storage_iterator
+
+#include <memory>
+#include <type_traits>
+#include <cassert>
+
+int A_constructed = 0;
+
+struct A
+{
+    int data_;
+public:
+    explicit A(int i) : data_(i) {++A_constructed;}
+
+    A(const A& a) : data_(a.data_)  {++A_constructed;}
+    ~A() {--A_constructed; data_ = 0;}
+
+    bool operator==(int i) const {return data_ == i;}
+};
+
+int main()
+{
+#if __cplusplus >= 201402L
+    typedef std::aligned_storage<3*sizeof(A), std::alignment_of<A>::value>::type
+            Storage;
+    Storage buffer;
+    std::raw_storage_iterator<A*, A> it((A*)&buffer);
+    assert(A_constructed == 0);
+    assert(it.base() == (A*)&buffer);
+    for (int i = 0; i < 3; ++i)
+    {
+        *it++ = A(i+1);
+        A* ap = (A*)&buffer + i;
+        assert(*ap == i+1);
+        assert(A_constructed == i+1);
+        assert(it.base() == ap + 1);  // next place to write
+    }
+#endif
+}
diff --git a/test/std/utilities/memory/unique.ptr/deleter.h b/test/std/utilities/memory/unique.ptr/deleter.h
index fb26044..ab13c65 100644
--- a/test/std/utilities/memory/unique.ptr/deleter.h
+++ b/test/std/utilities/memory/unique.ptr/deleter.h
@@ -20,21 +20,19 @@
 #include <utility>
 #include <cassert>
 
+#include "test_macros.h"
+
+#if TEST_STD_VER >= 11
+
 template <class T>
 class Deleter
 {
     int state_;
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     Deleter(const Deleter&);
     Deleter& operator=(const Deleter&);
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    Deleter(Deleter&);
-    Deleter& operator=(Deleter&);
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
 public:
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     Deleter(Deleter&& r) : state_(r.state_) {r.state_ = 0;}
     Deleter& operator=(Deleter&& r)
     {
@@ -42,22 +40,12 @@
         r.state_ = 0;
         return *this;
     }
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    operator std::__rv<Deleter>() {return std::__rv<Deleter>(*this);}
-    Deleter(std::__rv<Deleter> r) : state_(r->state_) {r->state_ = 0;}
-    Deleter& operator=(std::__rv<Deleter> r)
-    {
-        state_ = r->state_;
-        r->state_ = 0;
-        return *this;
-    }
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
+
 
     Deleter() : state_(0) {}
     explicit Deleter(int s) : state_(s) {}
     ~Deleter() {assert(state_ >= 0); state_ = -1;}
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     template <class U>
         Deleter(Deleter<U>&& d,
             typename std::enable_if<!std::is_same<U, T>::value>::type* = 0)
@@ -67,12 +55,6 @@
     template <class U>
         Deleter(const Deleter<U>& d,
             typename std::enable_if<!std::is_same<U, T>::value>::type* = 0);
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    template <class U>
-        Deleter(Deleter<U> d,
-            typename std::enable_if<!std::is_same<U, T>::value>::type* = 0)
-            : state_(d.state()) {}
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 public:
     int state() const {return state_;}
     void set_state(int i) {state_ = i;}
@@ -85,16 +67,11 @@
 {
     int state_;
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     Deleter(const Deleter&);
     Deleter& operator=(const Deleter&);
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    Deleter(Deleter&);
-    Deleter& operator=(Deleter&);
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
 public:
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+
     Deleter(Deleter&& r) : state_(r.state_) {r.state_ = 0;}
     Deleter& operator=(Deleter&& r)
     {
@@ -102,16 +79,6 @@
         r.state_ = 0;
         return *this;
     }
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    operator std::__rv<Deleter>() {return std::__rv<Deleter>(*this);}
-    Deleter(std::__rv<Deleter> r) : state_(r->state_) {r->state_ = 0;}
-    Deleter& operator=(std::__rv<Deleter> r)
-    {
-        state_ = r->state_;
-        r->state_ = 0;
-        return *this;
-    }
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
     Deleter() : state_(0) {}
     explicit Deleter(int s) : state_(s) {}
@@ -123,6 +90,69 @@
     void operator()(T* p) {delete [] p;}
 };
 
+#else // TEST_STD_VER < 11
+
+template <class T>
+class Deleter
+{
+    mutable int state_;
+
+public:
+    Deleter() : state_(0) {}
+    explicit Deleter(int s) : state_(s) {}
+
+    Deleter(Deleter const & other) : state_(other.state_) {
+        other.state_ = 0;
+    }
+    Deleter& operator=(Deleter const& other) {
+        state_ = other.state_;
+        other.state_ = 0;
+        return *this;
+    }
+
+    ~Deleter() {assert(state_ >= 0); state_ = -1;}
+
+private:
+    template <class U>
+        Deleter(Deleter<U> d,
+            typename std::enable_if<!std::is_same<U, T>::value>::type* = 0)
+            : state_(d.state()) {}
+
+public:
+    int state() const {return state_;}
+    void set_state(int i) {state_ = i;}
+
+    void operator()(T* p) {delete p;}
+};
+
+template <class T>
+class Deleter<T[]>
+{
+    mutable int state_;
+
+public:
+
+    Deleter(Deleter const& other) : state_(other.state_) {
+        other.state_ = 0;
+    }
+    Deleter& operator=(Deleter const& other) {
+        state_ = other.state_;
+        other.state_ = 0;
+        return *this;
+    }
+
+    Deleter() : state_(0) {}
+    explicit Deleter(int s) : state_(s) {}
+    ~Deleter() {assert(state_ >= 0); state_ = -1;}
+
+    int state() const {return state_;}
+    void set_state(int i) {state_ = i;}
+
+    void operator()(T* p) {delete [] p;}
+};
+
+#endif
+
 template <class T>
 void
 swap(Deleter<T>& x, Deleter<T>& y)
@@ -132,6 +162,7 @@
     y = std::move(t);
 }
 
+
 template <class T>
 class CDeleter
 {
@@ -179,4 +210,130 @@
     y = std::move(t);
 }
 
+// Non-copyable deleter
+template <class T>
+class NCDeleter
+{
+    int state_;
+    NCDeleter(NCDeleter const&);
+    NCDeleter& operator=(NCDeleter const&);
+public:
+
+    NCDeleter() : state_(0) {}
+    explicit NCDeleter(int s) : state_(s) {}
+    ~NCDeleter() {assert(state_ >= 0); state_ = -1;}
+
+    int state() const {return state_;}
+    void set_state(int i) {state_ = i;}
+
+    void operator()(T* p) {delete p;}
+};
+
+
+template <class T>
+class NCDeleter<T[]>
+{
+    int state_;
+    NCDeleter(NCDeleter const&);
+    NCDeleter& operator=(NCDeleter const&);
+public:
+
+    NCDeleter() : state_(0) {}
+    explicit NCDeleter(int s) : state_(s) {}
+    ~NCDeleter() {assert(state_ >= 0); state_ = -1;}
+
+    int state() const {return state_;}
+    void set_state(int i) {state_ = i;}
+
+    void operator()(T* p) {delete [] p;}
+};
+
+
+// Non-copyable deleter
+template <class T>
+class NCConstDeleter
+{
+    int state_;
+    NCConstDeleter(NCConstDeleter const&);
+    NCConstDeleter& operator=(NCConstDeleter const&);
+public:
+
+    NCConstDeleter() : state_(0) {}
+    explicit NCConstDeleter(int s) : state_(s) {}
+    ~NCConstDeleter() {assert(state_ >= 0); state_ = -1;}
+
+    int state() const {return state_;}
+    void set_state(int i) {state_ = i;}
+
+    void operator()(T* p) const {delete p;}
+};
+
+
+template <class T>
+class NCConstDeleter<T[]>
+{
+    int state_;
+    NCConstDeleter(NCConstDeleter const&);
+    NCConstDeleter& operator=(NCConstDeleter const&);
+public:
+
+    NCConstDeleter() : state_(0) {}
+    explicit NCConstDeleter(int s) : state_(s) {}
+    ~NCConstDeleter() {assert(state_ >= 0); state_ = -1;}
+
+    int state() const {return state_;}
+    void set_state(int i) {state_ = i;}
+
+    void operator()(T* p) const {delete [] p;}
+};
+
+
+// Non-copyable deleter
+template <class T>
+class CopyDeleter
+{
+    int state_;
+public:
+
+    CopyDeleter() : state_(0) {}
+    explicit CopyDeleter(int s) : state_(s) {}
+    ~CopyDeleter() {assert(state_ >= 0); state_ = -1;}
+
+    CopyDeleter(CopyDeleter const& other) : state_(other.state_) {}
+    CopyDeleter& operator=(CopyDeleter const& other) {
+        state_ = other.state_;
+        return *this;
+    }
+
+    int state() const {return state_;}
+    void set_state(int i) {state_ = i;}
+
+    void operator()(T* p) {delete p;}
+};
+
+
+template <class T>
+class CopyDeleter<T[]>
+{
+    int state_;
+
+public:
+
+    CopyDeleter() : state_(0) {}
+    explicit CopyDeleter(int s) : state_(s) {}
+    ~CopyDeleter() {assert(state_ >= 0); state_ = -1;}
+
+    CopyDeleter(CopyDeleter const& other) : state_(other.state_) {}
+    CopyDeleter& operator=(CopyDeleter const& other) {
+        state_ = other.state_;
+        return *this;
+    }
+
+    int state() const {return state_;}
+    void set_state(int i) {state_ = i;}
+
+    void operator()(T* p) {delete [] p;}
+};
+
+
 #endif  // DELETER_H
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/move01.fail.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/move01.fail.cpp
index 17375ed..ed94c1a 100644
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/move01.fail.cpp
+++ b/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/move01.fail.cpp
@@ -14,26 +14,15 @@
 // Test unique_ptr move assignment
 
 #include <memory>
-#include <utility>
-#include <cassert>
 
-// Can't copy from lvalue
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    ~A() {--count;}
-};
-
-int A::count = 0;
+#include "test_macros.h"
 
 int main()
 {
-    {
-    std::unique_ptr<A> s(new A);
-    std::unique_ptr<A> s2;
-    s2 = s;
-    }
+    std::unique_ptr<int> s, s2;
+#if TEST_STD_VER >= 11
+    s2 = s; // expected-error {{cannot be assigned because its copy assignment operator is implicitly deleted}}
+#else
+    s2 = s; // expected-error {{'operator=' is a private member of 'std::__1::unique_ptr}}
+#endif
 }
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/default01.fail.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/default01.fail.cpp
index 95350a6..b6bcad9 100644
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/default01.fail.cpp
+++ b/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/default01.fail.cpp
@@ -15,7 +15,6 @@
 
 // default unique_ptr ctor should require default Deleter ctor
 
-// USE_VERIFY
 
 #include <memory>
 
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/move01.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/move01.pass.cpp
index 03747b4..5088a44 100644
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/move01.pass.cpp
+++ b/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/move01.pass.cpp
@@ -32,22 +32,6 @@
 
 int A::count = 0;
 
-class NCDeleter
-{
-    int state_;
-
-    NCDeleter(NCDeleter&);
-    NCDeleter& operator=(NCDeleter&);
-public:
-
-    NCDeleter() : state_(5) {}
-
-    int state() const {return state_;}
-    void set_state(int s) {state_ = s;}
-
-    void operator()(A* p) {delete [] p;}
-};
-
 int main()
 {
     {
@@ -71,10 +55,10 @@
     }
     assert(A::count == 0);
     {
-    NCDeleter d;
-    std::unique_ptr<A[], NCDeleter&> s(new A[3], d);
+    NCDeleter<A[]> d;
+    std::unique_ptr<A[], NCDeleter<A[]>&> s(new A[3], d);
     A* p = s.get();
-    std::unique_ptr<A[], NCDeleter&> s2 = std::move(s);
+    std::unique_ptr<A[], NCDeleter<A[]>&> s2 = std::move(s);
     assert(s2.get() == p);
     assert(s.get() == 0);
     assert(A::count == 3);
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/move02.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/move02.pass.cpp
index ef821a9..5720d3b 100644
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/move02.pass.cpp
+++ b/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/move02.pass.cpp
@@ -31,21 +31,6 @@
 
 int A::count = 0;
 
-class NCDeleter
-{
-    int state_;
-
-    NCDeleter(NCDeleter&);
-    NCDeleter& operator=(NCDeleter&);
-public:
-
-    NCDeleter() : state_(5) {}
-
-    int state() const {return state_;}
-    void set_state(int s) {state_ = s;}
-
-    void operator()(A* p) {delete [] p;}
-};
 
 std::unique_ptr<A[]>
 source1()
@@ -67,14 +52,14 @@
 {
 }
 
-std::unique_ptr<A[], NCDeleter&>
+std::unique_ptr<A[], NCDeleter<A[]>&>
 source3()
 {
-    static NCDeleter d;
-    return std::unique_ptr<A[], NCDeleter&>(new A[3], d);
+    static NCDeleter<A[]> d;
+    return std::unique_ptr<A[], NCDeleter<A[]>&>(new A[3], d);
 }
 
-void sink3(std::unique_ptr<A[], NCDeleter&> p)
+void sink3(std::unique_ptr<A[], NCDeleter<A[]>&> p)
 {
 }
 
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/pointer_deleter04.fail.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/pointer_deleter04.fail.cpp
index b635d50..9d3f940 100644
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/pointer_deleter04.fail.cpp
+++ b/test/std/utilities/memory/unique.ptr/unique.ptr.runtime/unique.ptr.runtime.ctor/pointer_deleter04.fail.cpp
@@ -7,6 +7,8 @@
 //
 //===----------------------------------------------------------------------===//
 
+// XFAIL: c++98, c++03
+
 // <memory>
 
 // unique_ptr
@@ -16,40 +18,16 @@
 // unique_ptr<T, const D&>(pointer, D()) should not compile
 
 #include <memory>
-#include <cassert>
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    ~A() {--count;}
-};
-
-int A::count = 0;
 
 class Deleter
 {
-    int state_;
-
 public:
-
-    Deleter() : state_(5) {}
-
-    int state() const {return state_;}
-    void set_state(int s) {state_ = s;}
-
-    void operator()(A* p) const {delete [] p;}
+    Deleter() {}
+    void operator()(int* p) const {delete [] p;}
 };
 
 int main()
 {
-    {
-    A* p = new A[3];
-    assert(A::count == 3);
-    std::unique_ptr<A[], const Deleter&> s(p, Deleter());
-    assert(s.get() == p);
-    assert(s.get_deleter().state() == 5);
-    }
-    assert(A::count == 0);
+    int* p = nullptr;
+    std::unique_ptr<int[], const Deleter&> s(p, Deleter()); // expected-error@memory:* {{static_assert failed "rvalue deleter bound to reference"}}
 }
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/default.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/default.pass.cpp
new file mode 100644
index 0000000..2694538
--- /dev/null
+++ b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/default.pass.cpp
@@ -0,0 +1,86 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <memory>
+
+// unique_ptr
+
+//=============================================================================
+// TESTING std::unique_ptr::unique_ptr()
+//
+// Concerns:
+//   1 The default constructor works for any default constructible deleter types.
+//   2 The stored type 'T' is allowed to be incomplete.
+//
+// Plan
+//  1 Default construct unique_ptr's with various deleter types (C-1)
+//  2 Default construct a unique_ptr with a incomplete element_type and
+//    various deleter types (C-1,2)
+
+#include <memory>
+#include <cassert>
+
+#include "../../deleter.h"
+
+struct IncompleteT;
+
+void checkNumIncompleteTypeAlive(int i);
+
+template <class Del = std::default_delete<IncompleteT> >
+struct StoresIncomplete {
+  std::unique_ptr<IncompleteT, Del> m_ptr;
+  StoresIncomplete() {}
+  ~StoresIncomplete();
+
+  IncompleteT* get() const { return m_ptr.get(); }
+  Del& get_deleter() { return m_ptr.get_deleter(); }
+};
+
+int main()
+{
+    {
+      std::unique_ptr<int> p;
+      assert(p.get() == 0);
+    }
+    {
+      std::unique_ptr<int, NCDeleter<int> > p;
+      assert(p.get() == 0);
+      assert(p.get_deleter().state() == 0);
+      p.get_deleter().set_state(5);
+      assert(p.get_deleter().state() == 5);
+    }
+    {
+        StoresIncomplete<> s;
+        assert(s.get() == 0);
+        checkNumIncompleteTypeAlive(0);
+    }
+    checkNumIncompleteTypeAlive(0);
+    {
+        StoresIncomplete< Deleter<IncompleteT> > s;
+        assert(s.get() == 0);
+        assert(s.get_deleter().state() == 0);
+        checkNumIncompleteTypeAlive(0);
+    }
+    checkNumIncompleteTypeAlive(0);
+}
+
+struct IncompleteT {
+    static int count;
+    IncompleteT() { ++count; }
+    ~IncompleteT() {--count; }
+};
+
+int IncompleteT::count = 0;
+
+void checkNumIncompleteTypeAlive(int i) {
+    assert(IncompleteT::count == i);
+}
+
+template <class Del>
+StoresIncomplete<Del>::~StoresIncomplete() { }
\ No newline at end of file
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/default01.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/default01.pass.cpp
deleted file mode 100644
index e63db5c..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/default01.pass.cpp
+++ /dev/null
@@ -1,46 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr default ctor
-
-#include <memory>
-#include <cassert>
-
-// default unique_ptr ctor should only require default Deleter ctor
-class Deleter
-{
-    int state_;
-
-    Deleter(Deleter&);
-    Deleter& operator=(Deleter&);
-
-public:
-    Deleter() : state_(5) {}
-
-    int state() const {return state_;}
-
-    void operator()(void*) {}
-};
-
-int main()
-{
-    {
-    std::unique_ptr<int> p;
-    assert(p.get() == 0);
-    }
-    {
-    std::unique_ptr<int, Deleter> p;
-    assert(p.get() == 0);
-    assert(p.get_deleter().state() == 5);
-    }
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/default02.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/default02.pass.cpp
deleted file mode 100644
index e9af7e2..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/default02.pass.cpp
+++ /dev/null
@@ -1,84 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test default unique_ptr ctor
-
-#include <memory>
-#include <cassert>
-
-// default unique_ptr ctor shouldn't require complete type
-
-struct A;
-
-class Deleter
-{
-    int state_;
-
-    Deleter(Deleter&);
-    Deleter& operator=(Deleter&);
-
-public:
-    Deleter() : state_(5) {}
-
-    int state() const {return state_;}
-
-    void operator()(A* p);
-};
-
-void check(int i);
-
-template <class D = std::default_delete<A> >
-struct B
-{
-    std::unique_ptr<A, D> a_;
-    B() {}
-    ~B();
-
-    A* get() const {return a_.get();}
-    D& get_deleter() {return a_.get_deleter();}
-};
-
-int main()
-{
-    {
-    B<> s;
-    assert(s.get() == 0);
-    }
-    check(0);
-    {
-    B<Deleter> s;
-    assert(s.get() == 0);
-    assert(s.get_deleter().state() == 5);
-    }
-    check(0);
-}
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    ~A() {--count;}
-};
-
-int A::count = 0;
-
-void Deleter::operator()(A* p) {delete p;}
-
-void check(int i)
-{
-    assert(A::count == i);
-}
-
-template <class D>
-B<D>::~B() {}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move.pass.cpp
new file mode 100644
index 0000000..4c5cc84
--- /dev/null
+++ b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move.pass.cpp
@@ -0,0 +1,140 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <memory>
+
+// unique_ptr
+
+// Test unique_ptr move ctor
+
+#include <memory>
+#include <utility>
+#include <cassert>
+
+#include "../../deleter.h"
+
+//=============================================================================
+// TESTING unique_ptr(unique_ptr&&)
+//
+// Concerns
+//   1 The moved from pointer is empty and the new pointer stores the old value.
+//   2 The only requirement on the deleter is that it is MoveConstructible
+//     or a reference.
+//   3 The constructor works for explicitly moved values (ie std::move(x))
+//   4 The constructor works for true temporaries (ie a return value)
+//
+// Plan
+//  1 Explicitly construct unique_ptr<T, D> for various deleter types 'D'.
+//    check that the value and deleter have been properly moved. (C-1,2,3)
+//
+//  2 Use the expression 'sink(source())' to move construct a unique_ptr<T, D>
+//    from a temporary. 'source' should return the unique_ptr by value and
+//    'sink' should accept the unique_ptr by value. (C-1,2,4)
+
+struct A
+{
+    static int count;
+    A() {++count;}
+    A(const A&) {++count;}
+    virtual ~A() {--count;}
+};
+
+int A::count = 0;
+
+template <class Expect>
+void sinkFunction(Expect)
+{
+}
+
+typedef std::unique_ptr<A> APtrSource1;
+typedef std::unique_ptr<A, Deleter<A> > APtrSource2;
+typedef std::unique_ptr<A, NCDeleter<A>& > APtrSource3;
+
+APtrSource1 source1() {
+    return APtrSource1 (new A);
+}
+
+void sink1(APtrSource1 p) {
+    assert(p.get() != nullptr);
+}
+
+APtrSource2 source2() {
+    return APtrSource2(new A, Deleter<A>(5));
+}
+
+void sink2(APtrSource2 p) {
+    assert(p.get() != nullptr);
+    assert(p.get_deleter().state() == 5);
+}
+
+APtrSource3 source3() {
+    static NCDeleter<A> d(5);
+    return APtrSource3(new A, d);
+}
+
+void sink3(APtrSource3 p) {
+    assert(p.get() != nullptr);
+    assert(p.get_deleter().state() == 5);
+    assert(&p.get_deleter() == &source3().get_deleter());
+}
+
+int main()
+{
+    {
+        typedef std::unique_ptr<A> APtr;
+        APtr s(new A);
+        A* p = s.get();
+        APtr s2 = std::move(s);
+        assert(s2.get() == p);
+        assert(s.get() == 0);
+        assert(A::count == 1);
+    }
+    assert(A::count == 0);
+    {
+        typedef Deleter<A> MoveDel;
+        typedef std::unique_ptr<A, MoveDel> APtr;
+        MoveDel d(5);
+        APtr s(new A, std::move(d));
+        assert(d.state() == 0);
+        assert(s.get_deleter().state() == 5);
+        A* p = s.get();
+        APtr s2 = std::move(s);
+        assert(s2.get() == p);
+        assert(s.get() == 0);
+        assert(A::count == 1);
+        assert(s2.get_deleter().state() == 5);
+        assert(s.get_deleter().state() == 0);
+    }
+    assert(A::count == 0);
+    {
+        typedef NCDeleter<A> NonCopyDel;
+        typedef std::unique_ptr<A, NonCopyDel&> APtr;
+
+        NonCopyDel d;
+        APtr s(new A, d);
+        A* p = s.get();
+        APtr s2 = std::move(s);
+        assert(s2.get() == p);
+        assert(s.get() == 0);
+        assert(A::count == 1);
+        d.set_state(6);
+        assert(s2.get_deleter().state() == d.state());
+        assert(s.get_deleter().state() ==  d.state());
+    }
+    assert(A::count == 0);
+    {
+       sink1(source1());
+       assert(A::count == 0);
+       sink2(source2());
+       assert(A::count == 0);
+       sink3(source3());
+       assert(A::count == 0);
+    }
+    assert(A::count == 0);
+}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move01.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move01.pass.cpp
deleted file mode 100644
index dc16c31..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move01.pass.cpp
+++ /dev/null
@@ -1,142 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr move ctor
-
-#include <memory>
-#include <utility>
-#include <cassert>
-
-// test move ctor.  Should only require a MoveConstructible deleter, or if
-//    deleter is a reference, not even that.
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    ~A() {--count;}
-};
-
-int A::count = 0;
-
-template <class T>
-class Deleter
-{
-    int state_;
-
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    Deleter(const Deleter&);
-    Deleter& operator=(const Deleter&);
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    Deleter(Deleter&);
-    Deleter& operator=(Deleter&);
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
-public:
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    Deleter(Deleter&& r) : state_(r.state_) {r.state_ = 0;}
-    Deleter& operator=(Deleter&& r)
-    {
-        state_ = r.state_;
-        r.state_ = 0;
-        return *this;
-    }
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    operator std::__rv<Deleter>() {return std::__rv<Deleter>(*this);}
-    Deleter(std::__rv<Deleter> r) : state_(r->state_) {r->state_ = 0;}
-    Deleter& operator=(std::__rv<Deleter> r)
-    {
-        state_ = r->state_;
-        r->state_ = 0;
-        return *this;
-    }
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
-    Deleter() : state_(5) {}
-
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    template <class U>
-        Deleter(Deleter<U>&& d,
-            typename std::enable_if<!std::is_same<U, T>::value>::type* = 0)
-            : state_(d.state()) {d.set_state(0);}
-
-private:
-    template <class U>
-        Deleter(const Deleter<U>& d,
-            typename std::enable_if<!std::is_same<U, T>::value>::type* = 0);
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    template <class U>
-        Deleter(Deleter<U> d,
-            typename std::enable_if<!std::is_same<U, T>::value>::type* = 0)
-            : state_(d.state()) {}
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-public:
-    int state() const {return state_;}
-    void set_state(int i) {state_ = i;}
-
-    void operator()(T* p) {delete p;}
-};
-
-class CDeleter
-{
-    int state_;
-
-    CDeleter(CDeleter&);
-    CDeleter& operator=(CDeleter&);
-public:
-
-    CDeleter() : state_(5) {}
-
-    int state() const {return state_;}
-    void set_state(int s) {state_ = s;}
-
-    void operator()(A* p) {delete p;}
-};
-
-int main()
-{
-    {
-    std::unique_ptr<A> s(new A);
-    A* p = s.get();
-    std::unique_ptr<A> s2 = std::move(s);
-    assert(s2.get() == p);
-    assert(s.get() == 0);
-    assert(A::count == 1);
-    }
-    assert(A::count == 0);
-    {
-    std::unique_ptr<A, Deleter<A> > s(new A);
-    A* p = s.get();
-    std::unique_ptr<A, Deleter<A> > s2 = std::move(s);
-    assert(s2.get() == p);
-    assert(s.get() == 0);
-    assert(A::count == 1);
-    assert(s2.get_deleter().state() == 5);
-    assert(s.get_deleter().state() == 0);
-    }
-    assert(A::count == 0);
-    {
-    CDeleter d;
-    std::unique_ptr<A, CDeleter&> s(new A, d);
-    A* p = s.get();
-    std::unique_ptr<A, CDeleter&> s2 = std::move(s);
-    assert(s2.get() == p);
-    assert(s.get() == 0);
-    assert(A::count == 1);
-    d.set_state(6);
-    assert(s2.get_deleter().state() == d.state());
-    assert(s.get_deleter().state() ==  d.state());
-    }
-    assert(A::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move02.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move02.pass.cpp
deleted file mode 100644
index 4b997df..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move02.pass.cpp
+++ /dev/null
@@ -1,143 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr move ctor
-
-#include <memory>
-#include <cassert>
-
-// test move ctor.  Should only require a MoveConstructible deleter, or if
-//    deleter is a reference, not even that.
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    ~A() {--count;}
-};
-
-int A::count = 0;
-
-template <class T>
-class Deleter
-{
-    int state_;
-
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    Deleter(const Deleter&);
-    Deleter& operator=(const Deleter&);
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    Deleter(Deleter&);
-    Deleter& operator=(Deleter&);
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
-public:
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    Deleter(Deleter&& r) : state_(r.state_) {r.state_ = 0;}
-    Deleter& operator=(Deleter&& r)
-    {
-        state_ = r.state_;
-        r.state_ = 0;
-        return *this;
-    }
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    operator std::__rv<Deleter>() {return std::__rv<Deleter>(*this);}
-    Deleter(std::__rv<Deleter> r) : state_(r->state_) {r->state_ = 0;}
-    Deleter& operator=(std::__rv<Deleter> r)
-    {
-        state_ = r->state_;
-        r->state_ = 0;
-        return *this;
-    }
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
-    Deleter() : state_(5) {}
-
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    template <class U>
-        Deleter(Deleter<U>&& d,
-            typename std::enable_if<!std::is_same<U, T>::value>::type* = 0)
-            : state_(d.state()) {d.set_state(0);}
-
-private:
-    template <class U>
-        Deleter(const Deleter<U>& d,
-            typename std::enable_if<!std::is_same<U, T>::value>::type* = 0);
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    template <class U>
-        Deleter(Deleter<U> d,
-            typename std::enable_if<!std::is_same<U, T>::value>::type* = 0)
-            : state_(d.state()) {}
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-public:
-    int state() const {return state_;}
-    void set_state(int i) {state_ = i;}
-
-    void operator()(T* p) {delete p;}
-};
-
-class CDeleter
-{
-    int state_;
-
-    CDeleter(CDeleter&);
-    CDeleter& operator=(CDeleter&);
-public:
-
-    CDeleter() : state_(5) {}
-
-    int state() const {return state_;}
-    void set_state(int s) {state_ = s;}
-
-    void operator()(A* p) {delete p;}
-};
-
-std::unique_ptr<A>
-source1()
-{
-    return std::unique_ptr<A>(new A);
-}
-
-void sink1(std::unique_ptr<A> p)
-{
-}
-
-std::unique_ptr<A, Deleter<A> >
-source2()
-{
-    return std::unique_ptr<A, Deleter<A> >(new A);
-}
-
-void sink2(std::unique_ptr<A, Deleter<A> > p)
-{
-}
-
-std::unique_ptr<A, CDeleter&>
-source3()
-{
-    static CDeleter d;
-    return std::unique_ptr<A, CDeleter&>(new A, d);
-}
-
-void sink3(std::unique_ptr<A, CDeleter&> p)
-{
-}
-
-int main()
-{
-    sink1(source1());
-    sink2(source2());
-    sink3(source3());
-    assert(A::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert.pass.cpp
new file mode 100644
index 0000000..7136253
--- /dev/null
+++ b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert.pass.cpp
@@ -0,0 +1,175 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+
+//===----------------------------------------------------------------------===//
+
+// <memory>
+
+// unique_ptr
+
+// Test unique_ptr converting move ctor
+
+// NOTE: unique_ptr does not provide converting constructors in c++03
+// XFAIL: c++98, c++03
+
+
+#include <memory>
+#include <type_traits>
+#include <utility>
+#include <cassert>
+
+#include "../../deleter.h"
+
+// test converting move ctor.  Should only require a MoveConstructible deleter, or if
+//    deleter is a reference, not even that.
+// Explicit version
+
+struct A
+{
+    static int count;
+    A() {++count;}
+    A(const A&) {++count;}
+    virtual ~A() {--count;}
+};
+
+int A::count = 0;
+
+struct B
+    : public A
+{
+    static int count;
+    B() {++count;}
+    B(const B&) {++count;}
+    virtual ~B() {--count;}
+};
+
+int B::count = 0;
+
+template <class OrigPtr, class NewPtr>
+void checkDeleter(OrigPtr& O, NewPtr& N, int OrigState, int NewState) {
+    typedef typename NewPtr::deleter_type NewDel;
+    if (std::is_reference<NewDel>::value) {
+      O.get_deleter().set_state(42);
+      assert(O.get_deleter().state() == 42);
+      assert(N.get_deleter().state() == 42);
+      O.get_deleter().set_state(99);
+      assert(O.get_deleter().state() == 99);
+      assert(N.get_deleter().state() == 99);
+    } else {
+      // TODO(EricWF) Enable this?
+      // assert(OrigState != NewState);
+      assert(O.get_deleter().state() == OrigState);
+      assert(N.get_deleter().state() == NewState);
+    }
+}
+
+template <class APtr, class BPtr>
+void testMoveConvertExplicit()
+{
+    { // Test explicit constructor
+        BPtr s(new B);
+        A* p = s.get();
+        APtr s2(std::move(s));
+        assert(s2.get() == p);
+        assert(s.get() == 0);
+        assert(A::count == 1);
+        assert(B::count == 1);
+    }
+    assert(A::count == 0);
+    assert(B::count == 0);
+}
+
+template <class APtr, class BPtr>
+void testMoveConvertImplicit() {
+
+    { // Test implicit constructor
+        BPtr s(new B);
+        A* p = s.get();
+        APtr s2 = std::move(s);
+        assert(s2.get() == p);
+        assert(s.get() == 0);
+        assert(A::count == 1);
+        assert(B::count == 1);
+    }
+    assert(A::count == 0);
+    assert(B::count == 0);
+}
+
+template <class APtr, class BPtr, class Deleter>
+#if TEST_STD_VER >= 11
+void testMoveConvertExplicit(Deleter&& del) {
+#else
+void testMoveConvert(Deleter& del) {
+#endif
+    int old_val = del.state();
+    { // Test Explicit constructor
+        BPtr s(new B, std::forward<Deleter>(del));
+        A* p = s.get();
+        APtr s2(std::move(s));
+        assert(s2.get() == p);
+        assert(s.get() == 0);
+        checkDeleter(s, s2, del.state(), old_val);
+        assert(A::count == 1);
+        assert(B::count == 1);
+    }
+    assert(A::count == 0);
+    assert(B::count == 0);
+}
+
+
+template <class APtr, class BPtr, class Deleter>
+#if TEST_STD_VER >= 11
+void testMoveConvertImplicit(Deleter&& del) {
+#else
+void testMoveConvertImplicit(Deleter& del) {
+#endif
+    int old_val = del.state();
+    { // Test Implicit constructor
+        BPtr s(new B, std::forward<Deleter>(del));
+        A* p = s.get();
+        APtr s2 = std::move(s);
+        assert(s2.get() == p);
+        assert(s.get() == 0);
+        checkDeleter(s, s2, del.state(), old_val);
+        assert(A::count == 1);
+        assert(B::count == 1);
+    }
+    assert(A::count == 0);
+    assert(B::count == 0);
+}
+int main()
+{
+    {
+        typedef std::unique_ptr<A> APtr;
+        typedef std::unique_ptr<B> BPtr;
+        testMoveConvertExplicit<APtr, BPtr>();
+        testMoveConvertImplicit<APtr, BPtr>();
+    }
+    {
+        typedef std::unique_ptr<A, Deleter<A> > APtr;
+        typedef std::unique_ptr<B, Deleter<B> > BPtr;
+        Deleter<B> del(5);
+        testMoveConvertExplicit<APtr, BPtr>(std::move(del));
+        del.set_state(5);
+        testMoveConvertImplicit<APtr, BPtr>(std::move(del));
+    }
+    {
+        typedef std::unique_ptr<A, NCDeleter<A>& > APtr;
+        typedef std::unique_ptr<B, NCDeleter<A>& > BPtr;
+        NCDeleter<A> del(5);
+        testMoveConvertExplicit<APtr, BPtr>(del);
+        testMoveConvertImplicit<APtr, BPtr>(del);
+    }
+    {
+        typedef std::unique_ptr<A, CDeleter<A> > APtr;
+        typedef std::unique_ptr<B, CDeleter<B>& > BPtr;
+        CDeleter<B> del(5);
+        testMoveConvertImplicit<APtr, BPtr>(del);
+        testMoveConvertExplicit<APtr, BPtr>(del);
+    }
+}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert01.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert01.pass.cpp
deleted file mode 100644
index b65cf56..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert01.pass.cpp
+++ /dev/null
@@ -1,58 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr converting move ctor
-
-#include <memory>
-#include <utility>
-#include <cassert>
-
-// test converting move ctor.  Should only require a MoveConstructible deleter, or if
-//    deleter is a reference, not even that.
-// Explicit version
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    virtual ~A() {--count;}
-};
-
-int A::count = 0;
-
-struct B
-    : public A
-{
-    static int count;
-    B() {++count;}
-    B(const B&) {++count;}
-    virtual ~B() {--count;}
-};
-
-int B::count = 0;
-
-int main()
-{
-    {
-    std::unique_ptr<B> s(new B);
-    A* p = s.get();
-    std::unique_ptr<A> s2(std::move(s));
-    assert(s2.get() == p);
-    assert(s.get() == 0);
-    assert(A::count == 1);
-    assert(B::count == 1);
-    }
-    assert(A::count == 0);
-    assert(B::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert02.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert02.pass.cpp
deleted file mode 100644
index 829e755..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert02.pass.cpp
+++ /dev/null
@@ -1,62 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr converting move ctor
-
-#include <memory>
-#include <utility>
-#include <cassert>
-
-#include "../../deleter.h"
-
-// test converting move ctor.  Should only require a MoveConstructible deleter, or if
-//    deleter is a reference, not even that.
-// Explicit version
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    virtual ~A() {--count;}
-};
-
-int A::count = 0;
-
-struct B
-    : public A
-{
-    static int count;
-    B() {++count;}
-    B(const B&) {++count;}
-    virtual ~B() {--count;}
-};
-
-int B::count = 0;
-
-int main()
-{
-    {
-    std::unique_ptr<B, Deleter<B> > s(new B, Deleter<B>(5));
-    A* p = s.get();
-    std::unique_ptr<A, Deleter<A> > s2(std::move(s));
-    assert(s2.get() == p);
-    assert(s.get() == 0);
-    assert(A::count == 1);
-    assert(B::count == 1);
-    assert(s2.get_deleter().state() == 5);
-    assert(s.get_deleter().state() == 0);
-    }
-    assert(A::count == 0);
-    assert(B::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert03.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert03.pass.cpp
deleted file mode 100644
index 792076a..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert03.pass.cpp
+++ /dev/null
@@ -1,79 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr converting move ctor
-
-#include <memory>
-#include <utility>
-#include <cassert>
-
-// test converting move ctor.  Should only require a MoveConstructible deleter, or if
-//    deleter is a reference, not even that.
-// Explicit version
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    virtual ~A() {--count;}
-};
-
-int A::count = 0;
-
-struct B
-    : public A
-{
-    static int count;
-    B() {++count;}
-    B(const B&) {++count;}
-    virtual ~B() {--count;}
-};
-
-int B::count = 0;
-
-template <class T>
-class CDeleter
-{
-    int state_;
-
-    CDeleter(CDeleter&);
-    CDeleter& operator=(CDeleter&);
-public:
-
-    CDeleter() : state_(5) {}
-
-    int state() const {return state_;}
-    void set_state(int s) {state_ = s;}
-
-    void operator()(T* p) {delete p;}
-};
-
-int main()
-{
-    {
-    CDeleter<A> d;
-    std::unique_ptr<B, CDeleter<A>&> s(new B, d);
-    A* p = s.get();
-    std::unique_ptr<A, CDeleter<A>&> s2(std::move(s));
-    assert(s2.get() == p);
-    assert(s.get() == 0);
-    assert(A::count == 1);
-    assert(B::count == 1);
-    d.set_state(6);
-    assert(s2.get_deleter().state() == d.state());
-    assert(s.get_deleter().state() ==  d.state());
-    }
-    assert(A::count == 0);
-    assert(B::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert04.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert04.pass.cpp
deleted file mode 100644
index 12ab17f..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert04.pass.cpp
+++ /dev/null
@@ -1,58 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr converting move ctor
-
-#include <memory>
-#include <utility>
-#include <cassert>
-
-// test converting move ctor.  Should only require a MoveConstructible deleter, or if
-//    deleter is a reference, not even that.
-// implicit version
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    virtual ~A() {--count;}
-};
-
-int A::count = 0;
-
-struct B
-    : public A
-{
-    static int count;
-    B() {++count;}
-    B(const B&) {++count;}
-    virtual ~B() {--count;}
-};
-
-int B::count = 0;
-
-int main()
-{
-    {
-    std::unique_ptr<B> s(new B);
-    A* p = s.get();
-    std::unique_ptr<A> s2 = std::move(s);
-    assert(s2.get() == p);
-    assert(s.get() == 0);
-    assert(A::count == 1);
-    assert(B::count == 1);
-    }
-    assert(A::count == 0);
-    assert(B::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert05.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert05.pass.cpp
deleted file mode 100644
index 8077b0d..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert05.pass.cpp
+++ /dev/null
@@ -1,62 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr converting move ctor
-
-#include <memory>
-#include <utility>
-#include <cassert>
-
-#include "../../deleter.h"
-
-// test converting move ctor.  Should only require a MoveConstructible deleter, or if
-//    deleter is a reference, not even that.
-// Implicit version
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    virtual ~A() {--count;}
-};
-
-int A::count = 0;
-
-struct B
-    : public A
-{
-    static int count;
-    B() {++count;}
-    B(const B&) {++count;}
-    virtual ~B() {--count;}
-};
-
-int B::count = 0;
-
-int main()
-{
-    {
-    std::unique_ptr<B, Deleter<B> > s(new B, Deleter<B>(5));
-    A* p = s.get();
-    std::unique_ptr<A, Deleter<A> > s2 = std::move(s);
-    assert(s2.get() == p);
-    assert(s.get() == 0);
-    assert(A::count == 1);
-    assert(B::count == 1);
-    assert(s2.get_deleter().state() == 5);
-    assert(s.get_deleter().state() == 0);
-    }
-    assert(A::count == 0);
-    assert(B::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert06.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert06.pass.cpp
deleted file mode 100644
index 4115107..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert06.pass.cpp
+++ /dev/null
@@ -1,79 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr converting move ctor
-
-#include <memory>
-#include <utility>
-#include <cassert>
-
-// test converting move ctor.  Should only require a MoveConstructible deleter, or if
-//    deleter is a reference, not even that.
-// Explicit version
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    virtual ~A() {--count;}
-};
-
-int A::count = 0;
-
-struct B
-    : public A
-{
-    static int count;
-    B() {++count;}
-    B(const B&) {++count;}
-    virtual ~B() {--count;}
-};
-
-int B::count = 0;
-
-template <class T>
-class CDeleter
-{
-    int state_;
-
-    CDeleter(CDeleter&);
-    CDeleter& operator=(CDeleter&);
-public:
-
-    CDeleter() : state_(5) {}
-
-    int state() const {return state_;}
-    void set_state(int s) {state_ = s;}
-
-    void operator()(T* p) {delete p;}
-};
-
-int main()
-{
-    {
-    CDeleter<A> d;
-    std::unique_ptr<B, CDeleter<A>&> s(new B, d);
-    A* p = s.get();
-    std::unique_ptr<A, CDeleter<A>&> s2 = std::move(s);
-    assert(s2.get() == p);
-    assert(s.get() == 0);
-    assert(A::count == 1);
-    assert(B::count == 1);
-    d.set_state(6);
-    assert(s2.get_deleter().state() == d.state());
-    assert(s.get_deleter().state() ==  d.state());
-    }
-    assert(A::count == 0);
-    assert(B::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert07.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert07.pass.cpp
deleted file mode 100644
index 978cb0e..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/move_convert07.pass.cpp
+++ /dev/null
@@ -1,63 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr converting move ctor
-
-#include <memory>
-#include <utility>
-#include <cassert>
-
-#include "../../deleter.h"
-
-// test converting move ctor.  Should only require a MoveConstructible deleter, or if
-//    deleter is a reference, not even that.
-// Implicit version
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    virtual ~A() {--count;}
-};
-
-int A::count = 0;
-
-struct B
-    : public A
-{
-    static int count;
-    B() {++count;}
-    B(const B&) {++count;}
-    virtual ~B() {--count;}
-};
-
-int B::count = 0;
-
-int main()
-{
-    {
-    CDeleter<B> b(5);
-    std::unique_ptr<B, CDeleter<B>&> s(new B, b);
-    A* p = s.get();
-    std::unique_ptr<A, CDeleter<A> > s2 = std::move(s);
-    assert(s2.get() == p);
-    assert(s.get() == 0);
-    assert(A::count == 1);
-    assert(B::count == 1);
-    assert(s2.get_deleter().state() == 5);
-    assert(s.get_deleter().state() == 5);
-    }
-    assert(A::count == 0);
-    assert(B::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer.pass.cpp
new file mode 100644
index 0000000..faa554d
--- /dev/null
+++ b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer.pass.cpp
@@ -0,0 +1,163 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <memory>
+
+// unique_ptr
+
+//=============================================================================
+// TESTING std::unique_ptr::unique_ptr()
+//
+// Concerns:
+//   1 The pointer constructor works for any default constructible deleter types.
+//   2 The pointer constructor accepts pointers to derived types.
+//   2 The stored type 'T' is allowed to be incomplete.
+//
+// Plan
+//  1 Construct unique_ptr<T, D>'s with a pointer to 'T' and various deleter
+//   types (C-1)
+//  2 Construct unique_ptr<T, D>'s with a pointer to 'D' and various deleter
+//    types where 'D' is derived from 'T'. (C-1,2)
+//  3 Construct a unique_ptr<T, D> with a pointer to 'T' and various deleter
+//    types where 'T' is an incomplete type (C-1,3)
+
+// Test unique_ptr(pointer) ctor
+
+#include <memory>
+#include <cassert>
+
+#include "../../deleter.h"
+
+// unique_ptr(pointer) ctor should only require default Deleter ctor
+
+struct A
+{
+    static int count;
+    A() {++count;}
+    A(const A&) {++count;}
+    virtual ~A() {--count;}
+};
+
+int A::count = 0;
+
+
+struct B
+    : public A
+{
+    static int count;
+    B() {++count;}
+    B(const B&) {++count;}
+    virtual ~B() {--count;}
+};
+
+int B::count = 0;
+
+
+struct IncompleteT;
+
+IncompleteT* getIncomplete();
+void checkNumIncompleteTypeAlive(int i);
+
+template <class Del = std::default_delete<IncompleteT> >
+struct StoresIncomplete {
+  std::unique_ptr<IncompleteT, Del> m_ptr;
+  StoresIncomplete() {}
+  explicit StoresIncomplete(IncompleteT* ptr) : m_ptr(ptr) {}
+  ~StoresIncomplete();
+
+  IncompleteT* get() const { return m_ptr.get(); }
+  Del& get_deleter() { return m_ptr.get_deleter(); }
+};
+
+void test_pointer()
+{
+    {
+        A* p = new A;
+        assert(A::count == 1);
+        std::unique_ptr<A> s(p);
+        assert(s.get() == p);
+    }
+    assert(A::count == 0);
+    {
+        A* p = new A;
+        assert(A::count == 1);
+        std::unique_ptr<A, NCDeleter<A> > s(p);
+        assert(s.get() == p);
+        assert(s.get_deleter().state() == 0);
+    }
+    assert(A::count == 0);
+}
+
+void test_derived()
+{
+    {
+        B* p = new B;
+        assert(A::count == 1);
+        assert(B::count == 1);
+        std::unique_ptr<A> s(p);
+        assert(s.get() == p);
+    }
+    assert(A::count == 0);
+    assert(B::count == 0);
+    {
+        B* p = new B;
+        assert(A::count == 1);
+        assert(B::count == 1);
+        std::unique_ptr<A, NCDeleter<A> > s(p);
+        assert(s.get() == p);
+        assert(s.get_deleter().state() == 0);
+    }
+    assert(A::count == 0);
+    assert(B::count == 0);
+}
+
+void test_incomplete()
+{
+    {
+        IncompleteT* p = getIncomplete();
+        checkNumIncompleteTypeAlive(1);
+        StoresIncomplete<> s(p);
+        assert(s.get() == p);
+    }
+    checkNumIncompleteTypeAlive(0);
+    {
+        IncompleteT* p = getIncomplete();
+        checkNumIncompleteTypeAlive(1);
+        StoresIncomplete< NCDeleter<IncompleteT> > s(p);
+        assert(s.get() == p);
+        assert(s.get_deleter().state() == 0);
+    }
+    checkNumIncompleteTypeAlive(0);
+}
+
+struct IncompleteT {
+    static int count;
+    IncompleteT() { ++count; }
+    ~IncompleteT() {--count; }
+};
+
+int IncompleteT::count = 0;
+
+IncompleteT* getIncomplete() {
+    return new IncompleteT;
+}
+
+void checkNumIncompleteTypeAlive(int i) {
+    assert(IncompleteT::count == i);
+}
+
+template <class Del>
+StoresIncomplete<Del>::~StoresIncomplete() { }
+
+int main()
+{
+    test_pointer();
+    test_derived();
+    test_incomplete();
+}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer01.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer01.pass.cpp
deleted file mode 100644
index e5fff77..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer01.pass.cpp
+++ /dev/null
@@ -1,63 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr(pointer) ctor
-
-#include <memory>
-#include <cassert>
-
-// unique_ptr(pointer) ctor should only require default Deleter ctor
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    ~A() {--count;}
-};
-
-int A::count = 0;
-
-class Deleter
-{
-    int state_;
-
-    Deleter(Deleter&);
-    Deleter& operator=(Deleter&);
-
-public:
-    Deleter() : state_(5) {}
-
-    int state() const {return state_;}
-
-    void operator()(A* p) {delete p;}
-};
-
-int main()
-{
-    {
-    A* p = new A;
-    assert(A::count == 1);
-    std::unique_ptr<A> s(p);
-    assert(s.get() == p);
-    }
-    assert(A::count == 0);
-    {
-    A* p = new A;
-    assert(A::count == 1);
-    std::unique_ptr<A, Deleter> s(p);
-    assert(s.get() == p);
-    assert(s.get_deleter().state() == 5);
-    }
-    assert(A::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer02.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer02.pass.cpp
deleted file mode 100644
index a226e87..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer02.pass.cpp
+++ /dev/null
@@ -1,95 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr(pointer) ctor
-
-#include <memory>
-#include <cassert>
-
-// unique_ptr(pointer) ctor shouldn't require complete type
-
-struct A;
-
-class Deleter
-{
-    int state_;
-
-    Deleter(Deleter&);
-    Deleter& operator=(Deleter&);
-
-public:
-    Deleter() : state_(5) {}
-
-    int state() const {return state_;}
-
-    void operator()(A* p);
-};
-
-void check(int i);
-
-template <class D = std::default_delete<A> >
-struct B
-{
-    std::unique_ptr<A, D> a_;
-    explicit B(A*);
-    ~B();
-
-    A* get() const {return a_.get();}
-    D& get_deleter() {return a_.get_deleter();}
-};
-
-A* get();
-
-int main()
-{
-    {
-    A* p = get();
-    check(1);
-    B<> s(p);
-    assert(s.get() == p);
-    }
-    check(0);
-    {
-    A* p = get();
-    check(1);
-    B<Deleter> s(p);
-    assert(s.get() == p);
-    assert(s.get_deleter().state() == 5);
-    }
-    check(0);
-}
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    ~A() {--count;}
-};
-
-int A::count = 0;
-
-A* get() {return new A;}
-
-void Deleter::operator()(A* p) {delete p;}
-
-void check(int i)
-{
-    assert(A::count == i);
-}
-
-template <class D>
-B<D>::B(A* a) : a_(a) {}
-
-template <class D>
-B<D>::~B() {}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer03.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer03.pass.cpp
deleted file mode 100644
index 42fc094..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer03.pass.cpp
+++ /dev/null
@@ -1,78 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr(pointer) ctor
-
-#include <memory>
-#include <cassert>
-
-// unique_ptr(pointer) ctor should work with derived pointers
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    virtual ~A() {--count;}
-};
-
-int A::count = 0;
-
-struct B
-    : public A
-{
-    static int count;
-    B() {++count;}
-    B(const B&) {++count;}
-    virtual ~B() {--count;}
-};
-
-int B::count = 0;
-
-class Deleter
-{
-    int state_;
-
-    Deleter(Deleter&);
-    Deleter& operator=(Deleter&);
-
-public:
-    Deleter() : state_(5) {}
-
-    int state() const {return state_;}
-
-    void operator()(A* p) {delete p;}
-};
-
-int main()
-{
-    {
-    B* p = new B;
-    assert(A::count == 1);
-    assert(B::count == 1);
-    std::unique_ptr<A> s(p);
-    assert(s.get() == p);
-    }
-    assert(A::count == 0);
-    assert(B::count == 0);
-    {
-    B* p = new B;
-    assert(A::count == 1);
-    assert(B::count == 1);
-    std::unique_ptr<A, Deleter> s(p);
-    assert(s.get() == p);
-    assert(s.get_deleter().state() == 5);
-    }
-    assert(A::count == 0);
-    assert(B::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter.pass.cpp
new file mode 100644
index 0000000..7ddd162
--- /dev/null
+++ b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter.pass.cpp
@@ -0,0 +1,123 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <memory>
+
+// unique_ptr
+
+//=============================================================================
+// TESTING unique_ptr(pointer, deleter)
+//
+// Concerns:
+//   1 unique_ptr(pointer, deleter&&) only requires a MoveConstructible deleter.
+//   2 unique_ptr(pointer, deleter&) requires a CopyConstructible deleter.
+//   3 unique_ptr<T, D&>(pointer, deleter) does not require a CopyConstructible deleter.
+//   4 unique_ptr<T, D const&>(pointer, deleter) does not require a CopyConstructible deleter.
+//   5 unique_ptr(pointer, deleter) should work for derived pointers.
+//   6 unique_ptr(pointer, deleter) should work with function pointers.
+//   7 unique_ptr<void> should work.
+
+
+#include <memory>
+#include <cassert>
+
+#include "../../deleter.h"
+
+struct A
+{
+    static int count;
+    A() {++count;}
+    A(const A&) {++count;}
+    virtual ~A() {--count;}
+};
+
+int A::count = 0;
+
+
+struct B
+    : public A
+{
+    static int count;
+    B() {++count;}
+    B(const B&) {++count;}
+    virtual ~B() {--count;}
+};
+
+int B::count = 0;
+
+bool my_free_called = false;
+
+void my_free(void*) {
+    my_free_called = true;
+}
+
+int main()
+{
+    { // MoveConstructible deleter (C-1)
+        A* p = new A;
+        assert(A::count == 1);
+        std::unique_ptr<A, Deleter<A> > s(p, Deleter<A>(5));
+        assert(s.get() == p);
+        assert(s.get_deleter().state() == 5);
+    }
+    assert(A::count == 0);
+    { // CopyConstructible deleter (C-2)
+        A* p = new A;
+        assert(A::count == 1);
+        CopyDeleter<A> d(5);
+        std::unique_ptr<A, CopyDeleter<A> > s(p, d);
+        assert(s.get() == p);
+        assert(s.get_deleter().state() == 5);
+        d.set_state(6);
+        assert(s.get_deleter().state() == 5);
+    }
+    assert(A::count == 0);
+    { // Reference deleter (C-3)
+        A* p = new A;
+        assert(A::count == 1);
+        NCDeleter<A> d(5);
+        std::unique_ptr<A, NCDeleter<A>&> s(p, d);
+        assert(s.get() == p);
+        assert(&s.get_deleter() == &d);
+        assert(s.get_deleter().state() == 5);
+        d.set_state(6);
+        assert(s.get_deleter().state() == 6);
+    }
+    assert(A::count == 0);
+    { // Const Reference deleter (C-4)
+        A* p = new A;
+        assert(A::count == 1);
+        NCConstDeleter<A> d(5);
+        std::unique_ptr<A, NCConstDeleter<A> const&> s(p, d);
+        assert(s.get() == p);
+        assert(s.get_deleter().state() == 5);
+        assert(&s.get_deleter() == &d);
+    }
+    assert(A::count == 0);
+    { // Derived pointers (C-5)
+        B* p = new B;
+        assert(A::count == 1);
+        assert(B::count == 1);
+        std::unique_ptr<A, Deleter<A> > s(p, Deleter<A>(5));
+        assert(s.get() == p);
+        assert(s.get_deleter().state() == 5);
+    }
+    assert(A::count == 0);
+    assert(B::count == 0);
+    { // Void and function pointers (C-6,7)
+        {
+        int i = 0;
+        std::unique_ptr<void, void(*)(void*)> s(&i, my_free);
+        assert(s.get() == &i);
+        assert(s.get_deleter() == my_free);
+        assert(!my_free_called);
+        }
+        assert(my_free_called);
+    }
+}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter01.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter01.pass.cpp
deleted file mode 100644
index 130f91d..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter01.pass.cpp
+++ /dev/null
@@ -1,99 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr(pointer) ctor
-
-#include <memory>
-#include <cassert>
-
-// unique_ptr(pointer, deleter()) only requires MoveConstructible deleter
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    ~A() {--count;}
-};
-
-int A::count = 0;
-
-template <class T>
-class Deleter
-{
-    int state_;
-
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    Deleter(const Deleter&);
-    Deleter& operator=(const Deleter&);
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    Deleter(Deleter&);
-    Deleter& operator=(Deleter&);
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
-public:
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    Deleter(Deleter&& r) : state_(r.state_) {r.state_ = 0;}
-    Deleter& operator=(Deleter&& r)
-    {
-        state_ = r.state_;
-        r.state_ = 0;
-        return *this;
-    }
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    operator std::__rv<Deleter>() {return std::__rv<Deleter>(*this);}
-    Deleter(std::__rv<Deleter> r) : state_(r->state_) {r->state_ = 0;}
-    Deleter& operator=(std::__rv<Deleter> r)
-    {
-        state_ = r->state_;
-        r->state_ = 0;
-        return *this;
-    }
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
-    Deleter() : state_(5) {}
-
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    template <class U>
-        Deleter(Deleter<U>&& d,
-            typename std::enable_if<!std::is_same<U, T>::value>::type* = 0)
-            : state_(d.state()) {d.set_state(0);}
-
-private:
-    template <class U>
-        Deleter(const Deleter<U>& d,
-            typename std::enable_if<!std::is_same<U, T>::value>::type* = 0);
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    template <class U>
-        Deleter(Deleter<U> d,
-            typename std::enable_if<!std::is_same<U, T>::value>::type* = 0)
-            : state_(d.state()) {}
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-public:
-    int state() const {return state_;}
-    void set_state(int i) {state_ = i;}
-
-    void operator()(T* p) {delete p;}
-};
-
-int main()
-{
-    {
-    A* p = new A;
-    assert(A::count == 1);
-    std::unique_ptr<A, Deleter<A> > s(p, Deleter<A>());
-    assert(s.get() == p);
-    assert(s.get_deleter().state() == 5);
-    }
-    assert(A::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter02.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter02.pass.cpp
deleted file mode 100644
index 421bec5..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter02.pass.cpp
+++ /dev/null
@@ -1,58 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr(pointer) ctor
-
-#include <memory>
-#include <cassert>
-
-// unique_ptr(pointer, d) requires CopyConstructible deleter
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    ~A() {--count;}
-};
-
-int A::count = 0;
-
-class Deleter
-{
-    int state_;
-
-public:
-
-    Deleter() : state_(5) {}
-
-    int state() const {return state_;}
-    void set_state(int s) {state_ = s;}
-
-    void operator()(A* p) {delete p;}
-};
-
-int main()
-{
-    {
-    A* p = new A;
-    assert(A::count == 1);
-    Deleter d;
-    std::unique_ptr<A, Deleter> s(p, d);
-    assert(s.get() == p);
-    assert(s.get_deleter().state() == 5);
-    d.set_state(6);
-    assert(s.get_deleter().state() == 5);
-    }
-    assert(A::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter03.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter03.pass.cpp
deleted file mode 100644
index bce79db..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter03.pass.cpp
+++ /dev/null
@@ -1,60 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr(pointer) ctor
-
-#include <memory>
-#include <cassert>
-
-// unique_ptr<T, D&>(pointer, d) does not requires CopyConstructible deleter
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    ~A() {--count;}
-};
-
-int A::count = 0;
-
-class Deleter
-{
-    int state_;
-
-    Deleter(const Deleter&);
-    Deleter& operator=(const Deleter&);
-public:
-
-    Deleter() : state_(5) {}
-
-    int state() const {return state_;}
-    void set_state(int s) {state_ = s;}
-
-    void operator()(A* p) {delete p;}
-};
-
-int main()
-{
-    {
-    A* p = new A;
-    assert(A::count == 1);
-    Deleter d;
-    std::unique_ptr<A, Deleter&> s(p, d);
-    assert(s.get() == p);
-    assert(s.get_deleter().state() == 5);
-    d.set_state(6);
-    assert(s.get_deleter().state() == 6);
-    }
-    assert(A::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter04.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter04.pass.cpp
deleted file mode 100644
index a7750fc..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter04.pass.cpp
+++ /dev/null
@@ -1,58 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr(pointer) ctor
-
-#include <memory>
-#include <cassert>
-
-// unique_ptr<T, const D&>(pointer, d) does not requires CopyConstructible deleter
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    ~A() {--count;}
-};
-
-int A::count = 0;
-
-class Deleter
-{
-    int state_;
-
-    Deleter(const Deleter&);
-    Deleter& operator=(const Deleter&);
-public:
-
-    Deleter() : state_(5) {}
-
-    int state() const {return state_;}
-    void set_state(int s) {state_ = s;}
-
-    void operator()(A* p) const {delete p;}
-};
-
-int main()
-{
-    {
-    A* p = new A;
-    assert(A::count == 1);
-    Deleter d;
-    std::unique_ptr<A, const Deleter&> s(p, d);
-    assert(s.get() == p);
-    assert(s.get_deleter().state() == 5);
-    }
-    assert(A::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter05.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter05.pass.cpp
deleted file mode 100644
index 1a83258..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter05.pass.cpp
+++ /dev/null
@@ -1,66 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr(pointer, deleter) ctor
-
-#include <memory>
-#include <cassert>
-
-// unique_ptr(pointer, deleter) should work with derived pointers
-
-struct A
-{
-    static int count;
-    A() {++count;}
-    A(const A&) {++count;}
-    virtual ~A() {--count;}
-};
-
-int A::count = 0;
-
-struct B
-    : public A
-{
-    static int count;
-    B() {++count;}
-    B(const B&) {++count;}
-    virtual ~B() {--count;}
-};
-
-int B::count = 0;
-
-class Deleter
-{
-    int state_;
-
-public:
-    Deleter() : state_(5) {}
-
-    int state() const {return state_;}
-
-    void operator()(A* p) {delete p;}
-};
-
-int main()
-{
-    {
-    B* p = new B;
-    assert(A::count == 1);
-    assert(B::count == 1);
-    std::unique_ptr<A, Deleter> s(p, Deleter());
-    assert(s.get() == p);
-    assert(s.get_deleter().state() == 5);
-    }
-    assert(A::count == 0);
-    assert(B::count == 0);
-}
diff --git a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter06.pass.cpp b/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter06.pass.cpp
deleted file mode 100644
index ed68052..0000000
--- a/test/std/utilities/memory/unique.ptr/unique.ptr.single/unique.ptr.single.ctor/pointer_deleter06.pass.cpp
+++ /dev/null
@@ -1,39 +0,0 @@
-//===----------------------------------------------------------------------===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-// <memory>
-
-// unique_ptr
-
-// Test unique_ptr(pointer, deleter) ctor
-
-#include <memory>
-#include <cassert>
-
-// unique_ptr(pointer, deleter) should work with function pointers
-// unique_ptr<void> should work
-
-bool my_free_called = false;
-
-void my_free(void*)
-{
-    my_free_called = true;
-}
-
-int main()
-{
-    {
-    int i = 0;
-    std::unique_ptr<void, void (*)(void*)> s(&i, my_free);
-    assert(s.get() == &i);
-    assert(s.get_deleter() == my_free);
-    assert(!my_free_called);
-    }
-    assert(my_free_called);
-}
diff --git a/test/std/utilities/memory/util.smartptr/util.smartptr.enab/enable_shared_from_this.pass.cpp b/test/std/utilities/memory/util.smartptr/util.smartptr.enab/enable_shared_from_this.pass.cpp
index 58686d6..77af13f 100644
--- a/test/std/utilities/memory/util.smartptr/util.smartptr.enab/enable_shared_from_this.pass.cpp
+++ b/test/std/utilities/memory/util.smartptr/util.smartptr.enab/enable_shared_from_this.pass.cpp
@@ -34,6 +34,10 @@
 
 int main()
 {
+    {  // https://llvm.org/bugs/show_bug.cgi?id=18843
+    std::shared_ptr<T const> t1(new T);
+    std::shared_ptr<T const> t2(std::make_shared<T>());
+    }
     {
     std::shared_ptr<Y> p(new Z);
     std::shared_ptr<T> q = p->shared_from_this();
diff --git a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.assign/unique_ptr_Y.pass.cpp b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.assign/unique_ptr_Y.pass.cpp
index 742d8c1..30e0fce 100644
--- a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.assign/unique_ptr_Y.pass.cpp
+++ b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.assign/unique_ptr_Y.pass.cpp
@@ -67,7 +67,7 @@
             pB = std::move(pA);
             assert(B::count == 0);
             assert(A::count == 0);
-            assert(pB.use_count() == 1);
+//          assert(pB.use_count() == 1); // no longer true due to LWG 2415
             assert(pA.get() == 0);
             assert(pB.get() == ptrA);
         }
@@ -101,7 +101,7 @@
             pB = std::move(pA);
             assert(B::count == 0);
             assert(A::count == 0);
-            assert(pB.use_count() == 1);
+//          assert(pB.use_count() == 1); // no longer true due to LWG 2415
             assert(pA.get() == 0);
             assert(pB.get() == ptrA);
         }
diff --git a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/auto_ptr.pass.cpp b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/auto_ptr.pass.cpp
index 28e49d6..b2e61fa 100644
--- a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/auto_ptr.pass.cpp
+++ b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/auto_ptr.pass.cpp
@@ -11,7 +11,7 @@
 
 // template<class Y> explicit shared_ptr(auto_ptr<Y>&& r);
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <memory>
 #include <new>
diff --git a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/nullptr_t_deleter_throw.pass.cpp b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/nullptr_t_deleter_throw.pass.cpp
index a8588cc..97d3f69 100644
--- a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/nullptr_t_deleter_throw.pass.cpp
+++ b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/nullptr_t_deleter_throw.pass.cpp
@@ -13,7 +13,7 @@
 
 // template<class D> shared_ptr(nullptr_t, D d);
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <memory>
 #include <cassert>
diff --git a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/pointer_deleter_throw.pass.cpp b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/pointer_deleter_throw.pass.cpp
index b024f7e..ead0816 100644
--- a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/pointer_deleter_throw.pass.cpp
+++ b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/pointer_deleter_throw.pass.cpp
@@ -13,7 +13,7 @@
 
 // template<class Y, class D> shared_ptr(Y* p, D d);
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <memory>
 #include <cassert>
diff --git a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/pointer_throw.pass.cpp b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/pointer_throw.pass.cpp
index 28fb8bf..041fe9a 100644
--- a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/pointer_throw.pass.cpp
+++ b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/pointer_throw.pass.cpp
@@ -11,7 +11,7 @@
 
 // template<class Y> explicit shared_ptr(Y* p);
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <memory>
 #include <new>
diff --git a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/unique_ptr.pass.cpp b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/unique_ptr.pass.cpp
index dc2a6af..5e09d9a 100644
--- a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/unique_ptr.pass.cpp
+++ b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.const/unique_ptr.pass.cpp
@@ -11,7 +11,7 @@
 
 // template <class Y, class D> explicit shared_ptr(unique_ptr<Y, D>&&r);
 
-// UNSUPPORTED: asan, msan
+// UNSUPPORTED: sanitizer-new-delete
 
 #include <memory>
 #include <new>
@@ -58,6 +58,9 @@
 void fn ( const std::shared_ptr<int> &) {}
 void fn ( const std::shared_ptr<B> &) { assert (false); }
 
+template <typename T>
+void assert_deleter ( T * ) { assert(false); }
+
 int main()
 {
     {
@@ -100,4 +103,13 @@
     throw_next = false;
     fn(std::unique_ptr<int>(new int));
     }
+
+#if __cplusplus >= 201402L
+    // LWG 2415
+    {
+    std::unique_ptr<int, void (*)(int*)> p(nullptr, assert_deleter<int>);
+    std::shared_ptr<int> p2(std::move(p)); // should not call deleter when going out of scope
+    }
+#endif
+    
 }
diff --git a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.create/make_shared.pass.cpp b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.create/make_shared.pass.cpp
index 5dfa4cd..8cb972b 100644
--- a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.create/make_shared.pass.cpp
+++ b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.create/make_shared.pass.cpp
@@ -37,6 +37,14 @@
 
 int A::count = 0;
 
+
+struct Foo
+{
+    Foo() = default;
+    virtual ~Foo() = default;
+};
+
+
 int main()
 {
     int nc = globalMemCounter.outstanding_new;
@@ -49,6 +57,14 @@
     assert(p->get_int() == 67);
     assert(p->get_char() == 'e');
     }
+
+    { // https://llvm.org/bugs/show_bug.cgi?id=24137
+    std::shared_ptr<Foo> p1       = std::make_shared<Foo>();
+    assert(p1.get());
+    std::shared_ptr<const Foo> p2 = std::make_shared<const Foo>();
+    assert(p2.get());
+    }
+
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     nc = globalMemCounter.outstanding_new;
     {
diff --git a/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.create/make_shared.volatile.pass.cpp b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.create/make_shared.volatile.pass.cpp
new file mode 100644
index 0000000..1045f93
--- /dev/null
+++ b/test/std/utilities/memory/util.smartptr/util.smartptr.shared/util.smartptr.shared.create/make_shared.volatile.pass.cpp
@@ -0,0 +1,61 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// <memory>
+
+// shared_ptr
+
+// template<class T, class... Args> shared_ptr<T> make_shared(Args&&... args);
+
+#include <memory>
+#include <cassert>
+
+template <typename T>
+void test(const T &t0)
+{
+    {
+    T t1 = t0;
+    std::shared_ptr<T> p0 = std::make_shared<T>(t0);
+    std::shared_ptr<T> p1 = std::make_shared<T>(t1);
+    assert(*p0 == t0);
+    assert(*p1 == t1);
+    }
+
+    {
+    const T t1 = t0;
+    std::shared_ptr<const T> p0 = std::make_shared<const T>(t0);
+    std::shared_ptr<const T> p1 = std::make_shared<const T>(t1);
+    assert(*p0 == t0);
+    assert(*p1 == t1);
+    }
+    
+    {
+    volatile T t1 = t0;
+    std::shared_ptr<volatile T> p0 = std::make_shared<volatile T>(t0);
+    std::shared_ptr<volatile T> p1 = std::make_shared<volatile T>(t1);
+    assert(*p0 == t0);
+    assert(*p1 == t1);
+    }
+
+    {
+    const volatile T t1 = t0;
+    std::shared_ptr<const volatile T> p0 = std::make_shared<const volatile T>(t0);
+    std::shared_ptr<const volatile T> p1 = std::make_shared<const volatile T>(t1);
+    assert(*p0 == t0);
+    assert(*p1 == t1);
+    }
+    
+}
+
+int main()
+{
+    test<bool>(true);
+    test<int>(3);
+    test<double>(5.0);
+}
diff --git a/test/std/utilities/meta/meta.hel/bool_constant.pass.cpp b/test/std/utilities/meta/meta.hel/bool_constant.pass.cpp
new file mode 100644
index 0000000..71110ea
--- /dev/null
+++ b/test/std/utilities/meta/meta.hel/bool_constant.pass.cpp
@@ -0,0 +1,32 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// type_traits
+
+// bool_constant
+
+#include <type_traits>
+#include <cassert>
+
+int main()
+{
+#if __cplusplus > 201402L
+    typedef std::bool_constant<true> _t;
+    static_assert(_t::value, "");
+    static_assert((std::is_same<_t::value_type, bool>::value), "");
+    static_assert((std::is_same<_t::type, _t>::value), "");
+    static_assert((_t() == true), "");
+
+    typedef std::bool_constant<false> _f;
+    static_assert(!_f::value, "");
+    static_assert((std::is_same<_f::value_type, bool>::value), "");
+    static_assert((std::is_same<_f::type, _f>::value), "");
+    static_assert((_f() == false), "");
+#endif
+}
diff --git a/test/std/utilities/meta/meta.rel/is_convertible.pass.cpp b/test/std/utilities/meta/meta.rel/is_convertible.pass.cpp
index 718e0ff..429fb33 100644
--- a/test/std/utilities/meta/meta.rel/is_convertible.pass.cpp
+++ b/test/std/utilities/meta/meta.rel/is_convertible.pass.cpp
@@ -186,4 +186,10 @@
     static_assert((std::is_convertible<volatile NonCopyable&, const volatile NonCopyable&>::value), "");
     static_assert((std::is_convertible<const volatile NonCopyable&, const volatile NonCopyable&>::value), "");
     static_assert((!std::is_convertible<const NonCopyable&, NonCopyable&>::value), "");
+// This test requires Access control SFINAE which we only have in C++11 or when
+// we are using the compiler builtin for is_convertible.
+#if __cplusplus >= 201103L || !defined(_LIBCPP_USE_IS_CONVERTIBLE_FALLBACK)
+    test_is_not_convertible<NonCopyable&, NonCopyable>();
+#endif
+
 }
diff --git a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp b/test/std/utilities/meta/meta.rel/is_convertible_fallback.pass.cpp
similarity index 69%
copy from test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
copy to test/std/utilities/meta/meta.rel/is_convertible_fallback.pass.cpp
index b58f5c5..bd35ef6 100644
--- a/test/std/strings/basic.string/string.require/nothing_to_do.pass.cpp
+++ b/test/std/utilities/meta/meta.rel/is_convertible_fallback.pass.cpp
@@ -7,6 +7,12 @@
 //
 //===----------------------------------------------------------------------===//
 
-int main()
-{
-}
+// type_traits
+
+// is_convertible
+
+// Test the fallback implementation.
+
+#define _LIBCPP_USE_IS_CONVERTIBLE_FALLBACK
+#include "is_convertible.pass.cpp"
+
diff --git a/test/std/utilities/meta/meta.trans/meta.trans.other/result_of.pass.cpp b/test/std/utilities/meta/meta.trans/meta.trans.other/result_of.pass.cpp
index 1064d59..5a925bb 100644
--- a/test/std/utilities/meta/meta.trans/meta.trans.other/result_of.pass.cpp
+++ b/test/std/utilities/meta/meta.trans/meta.trans.other/result_of.pass.cpp
@@ -13,83 +13,240 @@
 
 #include <type_traits>
 #include <memory>
-
-typedef bool (&PF1)();
-typedef short (*PF2)(long);
+#include "test_macros.h"
 
 struct S
 {
-    operator PF2() const;
+    typedef short (*FreeFunc)(long);
+    operator FreeFunc() const;
     double operator()(char, int&);
-    void calc(long) const;
-    char data_;
+    double const& operator()(char, int&) const;
+    double volatile& operator()(char, int&) volatile;
+    double const volatile& operator()(char, int&) const volatile;
 };
 
-typedef void (S::*PMS)(long) const;
-typedef char S::*PMD;
-
-struct wat
-{
-    wat& operator*() { return *this; }
-    void foo();
+template <class Tp>
+struct Voider {
+    typedef void type;
 };
 
-struct F {};
+template <class T, class = void>
+struct HasType : std::false_type {};
+
+template <class T>
+struct HasType<T, typename Voider<typename T::type>::type> : std::true_type {};
 
 template <class T, class U>
-void test_result_of_imp()
+void test_result_of()
 {
     static_assert((std::is_same<typename std::result_of<T>::type, U>::value), "");
-#if _LIBCPP_STD_VER > 11
-    static_assert((std::is_same<std::result_of_t<T>, U>::value), "");
+}
+
+template <class T>
+void test_no_result()
+{
+#if TEST_STD_VER >= 11
+    static_assert((!HasType<std::result_of<T> >::value), "");
 #endif
 }
 
 int main()
 {
-    test_result_of_imp<S(int), short> ();
-    test_result_of_imp<S&(unsigned char, int&), double> ();
-    test_result_of_imp<PF1(), bool> ();
-    test_result_of_imp<PMS(std::unique_ptr<S>, int), void> ();
-    test_result_of_imp<PMS(S, int), void> ();
-    test_result_of_imp<PMS(const S&, int), void> ();
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    test_result_of_imp<PMD(S), char&&> ();
-#endif
-    test_result_of_imp<PMD(const S*), const char&> ();
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    test_result_of_imp<int (F::* (F       &)) ()       &, int> ();
-    test_result_of_imp<int (F::* (F       &)) () const &, int> ();
-    test_result_of_imp<int (F::* (F const &)) () const &, int> ();
-    test_result_of_imp<int (F::* (F      &&)) ()      &&, int> ();
-    test_result_of_imp<int (F::* (F      &&)) () const&&, int> ();
-    test_result_of_imp<int (F::* (F const&&)) () const&&, int> ();
-#endif
-#ifndef _LIBCPP_HAS_NO_TEMPLATE_ALIASES
-    using type1 = std::result_of<decltype(&wat::foo)(wat)>::type;
-    static_assert(std::is_same<type1, void>::value, "");
-#endif
-#if _LIBCPP_STD_VER > 11
-    using type2 = std::result_of_t<decltype(&wat::foo)(wat)>;
-    static_assert(std::is_same<type2, void>::value, "");
-#endif
+    { // functor object
+    test_result_of<S(int), short> ();
+    test_result_of<S&(unsigned char, int&), double> ();
+    test_result_of<S const&(unsigned char, int&), double const &> ();
+    test_result_of<S volatile&(unsigned char, int&), double volatile&> ();
+    test_result_of<S const volatile&(unsigned char, int&), double const volatile&> ();
+    }
+    { // pointer to function
+    typedef bool         (&RF0)();
+    typedef bool*       (&RF1)(int);
+    typedef bool&       (&RF2)(int, int);
+    typedef bool const& (&RF3)(int, int, int);
+    typedef bool        (*PF0)();
+    typedef bool*       (*PF1)(int);
+    typedef bool&       (*PF2)(int, int);
+    typedef bool const& (*PF3)(int, int, int);
+    typedef bool        (*&PRF0)();
+    typedef bool*       (*&PRF1)(int);
+    typedef bool&       (*&PRF2)(int, int);
+    typedef bool const& (*&PRF3)(int, int, int);
+    test_result_of<RF0(), bool>();
+    test_result_of<RF1(int), bool*>();
+    test_result_of<RF2(int, long), bool&>();
+    test_result_of<RF3(int, long, int), bool const&>();
+    test_result_of<PF0(), bool>();
+    test_result_of<PF1(int), bool*>();
+    test_result_of<PF2(int, long), bool&>();
+    test_result_of<PF3(int, long, int), bool const&>();
+    test_result_of<PRF0(), bool>();
+    test_result_of<PRF1(int), bool*>();
+    test_result_of<PRF2(int, long), bool&>();
+    test_result_of<PRF3(int, long, int), bool const&>();
+    }
+    { // pointer to member function
 
-    static_assert((std::is_same<std::result_of<S(int)>::type, short>::value), "Error!");
-    static_assert((std::is_same<std::result_of<S&(unsigned char, int&)>::type, double>::value), "Error!");
-    static_assert((std::is_same<std::result_of<PF1()>::type, bool>::value), "Error!");
-    static_assert((std::is_same<std::result_of<PMS(std::unique_ptr<S>, int)>::type, void>::value), "Error!");
-    static_assert((std::is_same<std::result_of<PMS(S, int)>::type, void>::value), "Error!");
-    static_assert((std::is_same<std::result_of<PMS(const S&, int)>::type, void>::value), "Error!");
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    static_assert((std::is_same<std::result_of<PMD(S)>::type, char&&>::value), "Error!");
-#endif
-    static_assert((std::is_same<std::result_of<PMD(const S*)>::type, const char&>::value), "Error!");
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    static_assert((std::is_same<std::result_of<int (F::* (F       &)) ()       &>::type, int>::value), "Error!");
-    static_assert((std::is_same<std::result_of<int (F::* (F       &)) () const &>::type, int>::value), "Error!");
-    static_assert((std::is_same<std::result_of<int (F::* (F const &)) () const &>::type, int>::value), "Error!");
-    static_assert((std::is_same<std::result_of<int (F::* (F      &&)) ()      &&>::type, int>::value), "Error!");
-    static_assert((std::is_same<std::result_of<int (F::* (F      &&)) () const&&>::type, int>::value), "Error!");
-    static_assert((std::is_same<std::result_of<int (F::* (F const&&)) () const&&>::type, int>::value), "Error!");
-#endif
+    typedef int         (S::*PMS0)();
+    typedef int*        (S::*PMS1)(long);
+    typedef int&        (S::*PMS2)(long, int);
+    test_result_of<PMS0(               S),   int> ();
+    test_result_of<PMS0(               S&),  int> ();
+    test_result_of<PMS0(               S*),  int> ();
+    test_result_of<PMS0(               S*&), int> ();
+    test_result_of<PMS0(std::unique_ptr<S>), int> ();
+    test_no_result<PMS0(const          S&)>();
+    test_no_result<PMS0(volatile       S&)>();
+    test_no_result<PMS0(const volatile S&)>();
+
+    test_result_of<PMS1(               S,   int), int*> ();
+    test_result_of<PMS1(               S&,  int), int*> ();
+    test_result_of<PMS1(               S*,  int), int*> ();
+    test_result_of<PMS1(               S*&, int), int*> ();
+    test_result_of<PMS1(std::unique_ptr<S>, int), int*> ();
+    test_no_result<PMS1(const          S&, int)>();
+    test_no_result<PMS1(volatile       S&, int)>();
+    test_no_result<PMS1(const volatile S&, int)>();
+
+    test_result_of<PMS2(               S,   int, int), int&> ();
+    test_result_of<PMS2(               S&,  int, int), int&> ();
+    test_result_of<PMS2(               S*,  int, int), int&> ();
+    test_result_of<PMS2(               S*&, int, int), int&> ();
+    test_result_of<PMS2(std::unique_ptr<S>, int, int), int&> ();
+    test_no_result<PMS2(const          S&, int, int)>();
+    test_no_result<PMS2(volatile       S&, int, int)>();
+    test_no_result<PMS2(const volatile S&, int, int)>();
+
+    typedef int        (S::*PMS0C)() const;
+    typedef int*       (S::*PMS1C)(long) const;
+    typedef int&       (S::*PMS2C)(long, int) const;
+    test_result_of<PMS0C(               S),   int> ();
+    test_result_of<PMS0C(               S&),  int> ();
+    test_result_of<PMS0C(const          S&),  int> ();
+    test_result_of<PMS0C(               S*),  int> ();
+    test_result_of<PMS0C(const          S*),  int> ();
+    test_result_of<PMS0C(               S*&), int> ();
+    test_result_of<PMS0C(const          S*&), int> ();
+    test_result_of<PMS0C(std::unique_ptr<S>), int> ();
+    test_no_result<PMS0C(volatile       S&)>();
+    test_no_result<PMS0C(const volatile S&)>();
+
+    test_result_of<PMS1C(               S,   int), int*> ();
+    test_result_of<PMS1C(               S&,  int), int*> ();
+    test_result_of<PMS1C(const          S&,  int), int*> ();
+    test_result_of<PMS1C(               S*,  int), int*> ();
+    test_result_of<PMS1C(const          S*,  int), int*> ();
+    test_result_of<PMS1C(               S*&, int), int*> ();
+    test_result_of<PMS1C(const          S*&, int), int*> ();
+    test_result_of<PMS1C(std::unique_ptr<S>, int), int*> ();
+    test_no_result<PMS1C(volatile       S&, int)>();
+    test_no_result<PMS1C(const volatile S&, int)>();
+
+    test_result_of<PMS2C(               S,   int, int), int&> ();
+    test_result_of<PMS2C(               S&,  int, int), int&> ();
+    test_result_of<PMS2C(const          S&,  int, int), int&> ();
+    test_result_of<PMS2C(               S*,  int, int), int&> ();
+    test_result_of<PMS2C(const          S*,  int, int), int&> ();
+    test_result_of<PMS2C(               S*&, int, int), int&> ();
+    test_result_of<PMS2C(const          S*&, int, int), int&> ();
+    test_result_of<PMS2C(std::unique_ptr<S>, int, int), int&> ();
+    test_no_result<PMS2C(volatile       S&, int, int)>();
+    test_no_result<PMS2C(const volatile S&, int, int)>();
+
+    typedef int       (S::*PMS0V)() volatile;
+    typedef int*       (S::*PMS1V)(long) volatile;
+    typedef int&       (S::*PMS2V)(long, int) volatile;
+    test_result_of<PMS0V(               S),   int> ();
+    test_result_of<PMS0V(               S&),  int> ();
+    test_result_of<PMS0V(volatile       S&),  int> ();
+    test_result_of<PMS0V(               S*),  int> ();
+    test_result_of<PMS0V(volatile       S*),  int> ();
+    test_result_of<PMS0V(               S*&), int> ();
+    test_result_of<PMS0V(volatile       S*&), int> ();
+    test_result_of<PMS0V(std::unique_ptr<S>), int> ();
+    test_no_result<PMS0V(const          S&)>();
+    test_no_result<PMS0V(const volatile S&)>();
+
+    test_result_of<PMS1V(               S,   int), int*> ();
+    test_result_of<PMS1V(               S&,  int), int*> ();
+    test_result_of<PMS1V(volatile       S&,  int), int*> ();
+    test_result_of<PMS1V(               S*,  int), int*> ();
+    test_result_of<PMS1V(volatile       S*,  int), int*> ();
+    test_result_of<PMS1V(               S*&, int), int*> ();
+    test_result_of<PMS1V(volatile       S*&, int), int*> ();
+    test_result_of<PMS1V(std::unique_ptr<S>, int), int*> ();
+    test_no_result<PMS1V(const          S&, int)>();
+    test_no_result<PMS1V(const volatile S&, int)>();
+
+    test_result_of<PMS2V(               S,   int, int), int&> ();
+    test_result_of<PMS2V(               S&,  int, int), int&> ();
+    test_result_of<PMS2V(volatile       S&,  int, int), int&> ();
+    test_result_of<PMS2V(               S*,  int, int), int&> ();
+    test_result_of<PMS2V(volatile       S*,  int, int), int&> ();
+    test_result_of<PMS2V(               S*&, int, int), int&> ();
+    test_result_of<PMS2V(volatile       S*&, int, int), int&> ();
+    test_result_of<PMS2V(std::unique_ptr<S>, int, int), int&> ();
+    test_no_result<PMS2V(const          S&, int, int)>();
+    test_no_result<PMS2V(const volatile S&, int, int)>();
+
+    typedef int        (S::*PMS0CV)() const volatile;
+    typedef int*       (S::*PMS1CV)(long) const volatile;
+    typedef int&       (S::*PMS2CV)(long, int) const volatile;
+    test_result_of<PMS0CV(               S),   int> ();
+    test_result_of<PMS0CV(               S&),  int> ();
+    test_result_of<PMS0CV(const          S&),  int> ();
+    test_result_of<PMS0CV(volatile       S&),  int> ();
+    test_result_of<PMS0CV(const volatile S&),  int> ();
+    test_result_of<PMS0CV(               S*),  int> ();
+    test_result_of<PMS0CV(const          S*),  int> ();
+    test_result_of<PMS0CV(volatile       S*),  int> ();
+    test_result_of<PMS0CV(const volatile S*),  int> ();
+    test_result_of<PMS0CV(               S*&), int> ();
+    test_result_of<PMS0CV(const          S*&), int> ();
+    test_result_of<PMS0CV(volatile       S*&), int> ();
+    test_result_of<PMS0CV(const volatile S*&), int> ();
+    test_result_of<PMS0CV(std::unique_ptr<S>), int> ();
+
+    test_result_of<PMS1CV(               S,   int), int*> ();
+    test_result_of<PMS1CV(               S&,  int), int*> ();
+    test_result_of<PMS1CV(const          S&,  int), int*> ();
+    test_result_of<PMS1CV(volatile       S&,  int), int*> ();
+    test_result_of<PMS1CV(const volatile S&,  int), int*> ();
+    test_result_of<PMS1CV(               S*,  int), int*> ();
+    test_result_of<PMS1CV(const          S*,  int), int*> ();
+    test_result_of<PMS1CV(volatile       S*,  int), int*> ();
+    test_result_of<PMS1CV(const volatile S*,  int), int*> ();
+    test_result_of<PMS1CV(               S*&, int), int*> ();
+    test_result_of<PMS1CV(const          S*&, int), int*> ();
+    test_result_of<PMS1CV(volatile       S*&, int), int*> ();
+    test_result_of<PMS1CV(const volatile S*&, int), int*> ();
+    test_result_of<PMS1CV(std::unique_ptr<S>, int), int*> ();
+
+    test_result_of<PMS2CV(               S,   int, int), int&> ();
+    test_result_of<PMS2CV(               S&,  int, int), int&> ();
+    test_result_of<PMS2CV(const          S&,  int, int), int&> ();
+    test_result_of<PMS2CV(volatile       S&,  int, int), int&> ();
+    test_result_of<PMS2CV(const volatile S&,  int, int), int&> ();
+    test_result_of<PMS2CV(               S*,  int, int), int&> ();
+    test_result_of<PMS2CV(const          S*,  int, int), int&> ();
+    test_result_of<PMS2CV(volatile       S*,  int, int), int&> ();
+    test_result_of<PMS2CV(const volatile S*,  int, int), int&> ();
+    test_result_of<PMS2CV(               S*&, int, int), int&> ();
+    test_result_of<PMS2CV(const          S*&, int, int), int&> ();
+    test_result_of<PMS2CV(volatile       S*&, int, int), int&> ();
+    test_result_of<PMS2CV(const volatile S*&, int, int), int&> ();
+    test_result_of<PMS2CV(std::unique_ptr<S>, int, int), int&> ();
+    }
+    { // pointer to member data
+    typedef char S::*PMD;
+    test_result_of<PMD(S&), char &>();
+    test_result_of<PMD(S*), char &>();
+    test_result_of<PMD(S* const), char &>();
+    test_result_of<PMD(const S&), const char&> ();
+    test_result_of<PMD(const S*), const char&> ();
+    test_result_of<PMD(volatile S&), volatile char&> ();
+    test_result_of<PMD(volatile S*), volatile char&> ();
+    test_result_of<PMD(const volatile S&), const volatile char&> ();
+    test_result_of<PMD(const volatile S*), const volatile char&> ();
+    }
 }
diff --git a/test/std/utilities/meta/meta.trans/meta.trans.other/result_of11.pass.cpp b/test/std/utilities/meta/meta.trans/meta.trans.other/result_of11.pass.cpp
new file mode 100644
index 0000000..6996cdd
--- /dev/null
+++ b/test/std/utilities/meta/meta.trans/meta.trans.other/result_of11.pass.cpp
@@ -0,0 +1,88 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// UNSUPPORTED: c++98, c++03
+//
+// <functional>
+//
+// result_of<Fn(ArgTypes...)>
+
+#include <type_traits>
+#include "test_macros.h"
+
+struct wat
+{
+    wat& operator*() { return *this; }
+    void foo();
+};
+
+struct F {};
+
+template <class T, class U>
+void test_result_of_imp()
+{
+    static_assert((std::is_same<typename std::result_of<T>::type, U>::value), "");
+#if TEST_STD_VER > 11
+    static_assert((std::is_same<std::result_of_t<T>, U>::value), "");
+#endif
+}
+
+int main()
+{
+    {
+    typedef char F::*PMD;
+    test_result_of_imp<PMD(F                &), char                &>();
+    test_result_of_imp<PMD(F const          &), char const          &>();
+    test_result_of_imp<PMD(F volatile       &), char volatile       &>();
+    test_result_of_imp<PMD(F const volatile &), char const volatile &>();
+
+    test_result_of_imp<PMD(F                &&), char                &&>();
+    test_result_of_imp<PMD(F const          &&), char const          &&>();
+    test_result_of_imp<PMD(F volatile       &&), char volatile       &&>();
+    test_result_of_imp<PMD(F const volatile &&), char const volatile &&>();
+
+    test_result_of_imp<PMD(F                ), char &&>();
+    test_result_of_imp<PMD(F const          ), char &&>();
+    test_result_of_imp<PMD(F volatile       ), char &&>();
+    test_result_of_imp<PMD(F const volatile ), char &&>();
+    }
+    {
+    test_result_of_imp<int (F::* (F       &)) ()                &, int> ();
+    test_result_of_imp<int (F::* (F       &)) () const          &, int> ();
+    test_result_of_imp<int (F::* (F       &)) () volatile       &, int> ();
+    test_result_of_imp<int (F::* (F       &)) () const volatile &, int> ();
+    test_result_of_imp<int (F::* (F const &)) () const          &, int> ();
+    test_result_of_imp<int (F::* (F const &)) () const volatile &, int> ();
+    test_result_of_imp<int (F::* (F volatile &)) () volatile       &, int> ();
+    test_result_of_imp<int (F::* (F volatile &)) () const volatile &, int> ();
+    test_result_of_imp<int (F::* (F const volatile &)) () const volatile &, int> ();
+
+    test_result_of_imp<int (F::* (F       &&)) ()                &&, int> ();
+    test_result_of_imp<int (F::* (F       &&)) () const          &&, int> ();
+    test_result_of_imp<int (F::* (F       &&)) () volatile       &&, int> ();
+    test_result_of_imp<int (F::* (F       &&)) () const volatile &&, int> ();
+    test_result_of_imp<int (F::* (F const &&)) () const          &&, int> ();
+    test_result_of_imp<int (F::* (F const &&)) () const volatile &&, int> ();
+    test_result_of_imp<int (F::* (F volatile &&)) () volatile       &&, int> ();
+    test_result_of_imp<int (F::* (F volatile &&)) () const volatile &&, int> ();
+    test_result_of_imp<int (F::* (F const volatile &&)) () const volatile &&, int> ();
+
+    test_result_of_imp<int (F::* (F       )) ()                &&, int> ();
+    test_result_of_imp<int (F::* (F       )) () const          &&, int> ();
+    test_result_of_imp<int (F::* (F       )) () volatile       &&, int> ();
+    test_result_of_imp<int (F::* (F       )) () const volatile &&, int> ();
+    test_result_of_imp<int (F::* (F const )) () const          &&, int> ();
+    test_result_of_imp<int (F::* (F const )) () const volatile &&, int> ();
+    test_result_of_imp<int (F::* (F volatile )) () volatile       &&, int> ();
+    test_result_of_imp<int (F::* (F volatile )) () const volatile &&, int> ();
+    test_result_of_imp<int (F::* (F const volatile )) () const volatile &&, int> ();
+    }
+
+    test_result_of_imp<decltype(&wat::foo)(wat), void>();
+}
diff --git a/test/std/utilities/meta/meta.unary/meta.unary.cat/member_function_pointer.pass.cpp b/test/std/utilities/meta/meta.unary/meta.unary.cat/member_function_pointer.pass.cpp
index 67ef3db..6f546ef 100644
--- a/test/std/utilities/meta/meta.unary/meta.unary.cat/member_function_pointer.pass.cpp
+++ b/test/std/utilities/meta/meta.unary/meta.unary.cat/member_function_pointer.pass.cpp
@@ -12,12 +12,13 @@
 // member_function_pointer
 
 #include <type_traits>
+#include "test_macros.h"
 
 template <class T>
 void test_member_function_pointer_imp()
 {
     static_assert(!std::is_void<T>::value, "");
-#if _LIBCPP_STD_VER > 11
+#if TEST_STD_VER > 11
     static_assert(!std::is_null_pointer<T>::value, "");
 #endif
     static_assert(!std::is_integral<T>::value, "");
@@ -73,30 +74,63 @@
     test_member_function_pointer<void (Class::*)(int, ...) volatile>();
     test_member_function_pointer<void (Class::*)(int, char, ...) volatile>();
 
-#if __cplusplus >= 201103L
 // reference qualifiers on functions are a C++11 extension
-    test_member_function_pointer<void (Class::*)() &&>();
-    test_member_function_pointer<void (Class::*)(int) &&>();
-    test_member_function_pointer<void (Class::*)(int, char) &&>();
-
+#if TEST_STD_VER >= 11
     test_member_function_pointer<void (Class::*)() &>();
     test_member_function_pointer<void (Class::*)(int) &>();
     test_member_function_pointer<void (Class::*)(int, char) &>();
-
-    test_member_function_pointer<void (Class::*)() volatile &&>();
-    test_member_function_pointer<void (Class::*)(int) volatile &&>();
-    test_member_function_pointer<void (Class::*)(int, char) volatile &&>();
-
-    test_member_function_pointer<void (Class::*)(...) &&>();
-    test_member_function_pointer<void (Class::*)(int,...) &&>();
-    test_member_function_pointer<void (Class::*)(int, char,...) &&>();
-
     test_member_function_pointer<void (Class::*)(...) &>();
     test_member_function_pointer<void (Class::*)(int,...) &>();
     test_member_function_pointer<void (Class::*)(int, char,...) &>();
 
+    test_member_function_pointer<void (Class::*)() const &>();
+    test_member_function_pointer<void (Class::*)(int) const &>();
+    test_member_function_pointer<void (Class::*)(int, char) const &>();
+    test_member_function_pointer<void (Class::*)(...) const &>();
+    test_member_function_pointer<void (Class::*)(int,...) const &>();
+    test_member_function_pointer<void (Class::*)(int, char,...) const &>();
+
+    test_member_function_pointer<void (Class::*)() volatile &>();
+    test_member_function_pointer<void (Class::*)(int) volatile &>();
+    test_member_function_pointer<void (Class::*)(int, char) volatile &>();
+    test_member_function_pointer<void (Class::*)(...) volatile &>();
+    test_member_function_pointer<void (Class::*)(int,...) volatile &>();
+    test_member_function_pointer<void (Class::*)(int, char,...) volatile &>();
+
+    test_member_function_pointer<void (Class::*)() const volatile &>();
+    test_member_function_pointer<void (Class::*)(int) const volatile &>();
+    test_member_function_pointer<void (Class::*)(int, char) const volatile &>();
+    test_member_function_pointer<void (Class::*)(...) const volatile &>();
+    test_member_function_pointer<void (Class::*)(int,...) const volatile &>();
+    test_member_function_pointer<void (Class::*)(int, char,...) const volatile &>();
+
+    // RValue qualifiers
+    test_member_function_pointer<void (Class::*)() &&>();
+    test_member_function_pointer<void (Class::*)(int) &&>();
+    test_member_function_pointer<void (Class::*)(int, char) &&>();
+    test_member_function_pointer<void (Class::*)(...) &&>();
+    test_member_function_pointer<void (Class::*)(int,...) &&>();
+    test_member_function_pointer<void (Class::*)(int, char,...) &&>();
+
+    test_member_function_pointer<void (Class::*)() const &&>();
+    test_member_function_pointer<void (Class::*)(int) const &&>();
+    test_member_function_pointer<void (Class::*)(int, char) const &&>();
+    test_member_function_pointer<void (Class::*)(...) const &&>();
+    test_member_function_pointer<void (Class::*)(int,...) const &&>();
+    test_member_function_pointer<void (Class::*)(int, char,...) const &&>();
+
+    test_member_function_pointer<void (Class::*)() volatile &&>();
+    test_member_function_pointer<void (Class::*)(int) volatile &&>();
+    test_member_function_pointer<void (Class::*)(int, char) volatile &&>();
     test_member_function_pointer<void (Class::*)(...) volatile &&>();
     test_member_function_pointer<void (Class::*)(int,...) volatile &&>();
     test_member_function_pointer<void (Class::*)(int, char,...) volatile &&>();
+
+    test_member_function_pointer<void (Class::*)() const volatile &&>();
+    test_member_function_pointer<void (Class::*)(int) const volatile &&>();
+    test_member_function_pointer<void (Class::*)(int, char) const volatile &&>();
+    test_member_function_pointer<void (Class::*)(...) const volatile &&>();
+    test_member_function_pointer<void (Class::*)(int,...) const volatile &&>();
+    test_member_function_pointer<void (Class::*)(int, char,...) const volatile &&>();
 #endif
 }
diff --git a/test/std/utilities/meta/meta.unary/meta.unary.prop/is_assignable.pass.cpp b/test/std/utilities/meta/meta.unary/meta.unary.prop/is_assignable.pass.cpp
index b46a4d6..d33019b 100644
--- a/test/std/utilities/meta/meta.unary/meta.unary.prop/is_assignable.pass.cpp
+++ b/test/std/utilities/meta/meta.unary/meta.unary.prop/is_assignable.pass.cpp
@@ -49,6 +49,9 @@
 };
 #endif
 
+template <typename T>
+struct X { T t; };
+
 int main()
 {
     test_is_assignable<int&, int&> ();
@@ -67,4 +70,7 @@
     test_is_not_assignable<void, const void> ();
     test_is_not_assignable<const void, const void> ();
     test_is_not_assignable<int(), int> ();
+    
+//  pointer to incomplete template type
+	test_is_assignable<X<D>*&, X<D>*> ();
 }
diff --git a/test/std/utilities/meta/meta.unary/meta.unary.prop/is_destructible.pass.cpp b/test/std/utilities/meta/meta.unary/meta.unary.prop/is_destructible.pass.cpp
index 807745e..fae9557 100644
--- a/test/std/utilities/meta/meta.unary/meta.unary.prop/is_destructible.pass.cpp
+++ b/test/std/utilities/meta/meta.unary/meta.unary.prop/is_destructible.pass.cpp
@@ -13,6 +13,8 @@
 
 #include <type_traits>
 
+#include "test_macros.h"
+
 template <class T>
 void test_is_destructible()
 {
@@ -68,6 +70,7 @@
 struct PureProtectedDestructor           { protected: virtual ~PureProtectedDestructor() = 0; };
 struct PurePrivateDestructor             { private:   virtual ~PurePrivateDestructor() = 0; };
 
+#if TEST_STD_VER >= 11
 struct DeletedPublicDestructor           { public:    ~DeletedPublicDestructor() = delete; };
 struct DeletedProtectedDestructor        { protected: ~DeletedProtectedDestructor() = delete; };
 struct DeletedPrivateDestructor          { private:   ~DeletedPrivateDestructor() = delete; };
@@ -75,6 +78,7 @@
 struct DeletedVirtualPublicDestructor    { public:    virtual ~DeletedVirtualPublicDestructor() = delete; };
 struct DeletedVirtualProtectedDestructor { protected: virtual ~DeletedVirtualProtectedDestructor() = delete; };
 struct DeletedVirtualPrivateDestructor   { private:   virtual ~DeletedVirtualPrivateDestructor() = delete; };
+#endif
 
 
 int main()
@@ -99,23 +103,27 @@
 
     test_is_not_destructible<int[]>();
     test_is_not_destructible<void>();
+    test_is_not_destructible<Function>();
 
+#if TEST_STD_VER >= 11
+    // Test access controlled destructors
     test_is_not_destructible<ProtectedDestructor>();
     test_is_not_destructible<PrivateDestructor>();
     test_is_not_destructible<VirtualProtectedDestructor>();
     test_is_not_destructible<VirtualPrivateDestructor>();
     test_is_not_destructible<PureProtectedDestructor>();
     test_is_not_destructible<PurePrivateDestructor>();
+
+    // Test deleted constructors
     test_is_not_destructible<DeletedPublicDestructor>();
     test_is_not_destructible<DeletedProtectedDestructor>();
     test_is_not_destructible<DeletedPrivateDestructor>();
-
-//     test_is_not_destructible<DeletedVirtualPublicDestructor>(); // currently fails due to clang bug #20268
+    //test_is_not_destructible<DeletedVirtualPublicDestructor>(); // previously failed due to clang bug #20268
     test_is_not_destructible<DeletedVirtualProtectedDestructor>();
     test_is_not_destructible<DeletedVirtualPrivateDestructor>();
 
-#if __has_feature(cxx_access_control_sfinae) 
+    // Test private destructors
     test_is_not_destructible<NotEmpty>();
 #endif
-    test_is_not_destructible<Function>();
+
 }
diff --git a/test/std/utilities/meta/meta.unary/meta.unary.prop/is_nothrow_destructible.pass.cpp b/test/std/utilities/meta/meta.unary/meta.unary.prop/is_nothrow_destructible.pass.cpp
index 8fd5bab..5827c92 100644
--- a/test/std/utilities/meta/meta.unary/meta.unary.prop/is_nothrow_destructible.pass.cpp
+++ b/test/std/utilities/meta/meta.unary/meta.unary.prop/is_nothrow_destructible.pass.cpp
@@ -13,6 +13,8 @@
 
 #include <type_traits>
 
+#include "test_macros.h"
+
 template <class T>
 void test_is_nothrow_destructible()
 {
@@ -31,14 +33,23 @@
     static_assert(!std::is_nothrow_destructible<const volatile T>::value, "");
 }
 
+
+struct PublicDestructor           { public:     ~PublicDestructor() {}};
+struct ProtectedDestructor        { protected:  ~ProtectedDestructor() {}};
+struct PrivateDestructor          { private:    ~PrivateDestructor() {}};
+
+struct VirtualPublicDestructor           { public:    virtual ~VirtualPublicDestructor() {}};
+struct VirtualProtectedDestructor        { protected: virtual ~VirtualProtectedDestructor() {}};
+struct VirtualPrivateDestructor          { private:   virtual ~VirtualPrivateDestructor() {}};
+
+struct PurePublicDestructor              { public:    virtual ~PurePublicDestructor() = 0; };
+struct PureProtectedDestructor           { protected: virtual ~PureProtectedDestructor() = 0; };
+struct PurePrivateDestructor             { private:   virtual ~PurePrivateDestructor() = 0; };
+
 class Empty
 {
 };
 
-class NotEmpty
-{
-    virtual ~NotEmpty();
-};
 
 union Union {};
 
@@ -52,40 +63,36 @@
     virtual void foo() = 0;
 };
 
-class AbstractDestructor
-{
-    virtual ~AbstractDestructor() = 0;
-};
-
-struct A
-{
-    ~A();
-};
 
 int main()
 {
     test_is_not_nothrow_destructible<void>();
-    test_is_not_nothrow_destructible<AbstractDestructor>();
-    test_is_not_nothrow_destructible<NotEmpty>();
     test_is_not_nothrow_destructible<char[]>();
+    test_is_not_nothrow_destructible<char[][3]>();
 
-#if __has_feature(cxx_noexcept)
-    test_is_nothrow_destructible<A>();
-#endif
     test_is_nothrow_destructible<int&>();
-#if  __has_feature(cxx_unrestricted_unions) 
-    test_is_nothrow_destructible<Union>();
-#endif
-#if __has_feature(cxx_access_control_sfinae)
-    test_is_nothrow_destructible<Empty>();
-#endif
     test_is_nothrow_destructible<int>();
     test_is_nothrow_destructible<double>();
     test_is_nothrow_destructible<int*>();
     test_is_nothrow_destructible<const int*>();
     test_is_nothrow_destructible<char[3]>();
-    test_is_nothrow_destructible<Abstract>();
-#if __has_feature(cxx_noexcept)
+
+#if TEST_STD_VER >= 11
+    // requires noexcept. These are all destructible.
+    test_is_nothrow_destructible<PublicDestructor>();
+    test_is_nothrow_destructible<VirtualPublicDestructor>();
+    test_is_nothrow_destructible<PurePublicDestructor>();
     test_is_nothrow_destructible<bit_zero>();
+    test_is_nothrow_destructible<Abstract>();
+    test_is_nothrow_destructible<Empty>();
+    test_is_nothrow_destructible<Union>();
+
+    // requires access control
+    test_is_not_nothrow_destructible<ProtectedDestructor>();
+    test_is_not_nothrow_destructible<PrivateDestructor>();
+    test_is_not_nothrow_destructible<VirtualProtectedDestructor>();
+    test_is_not_nothrow_destructible<VirtualPrivateDestructor>();
+    test_is_not_nothrow_destructible<PureProtectedDestructor>();
+    test_is_not_nothrow_destructible<PurePrivateDestructor>();
 #endif
 }
diff --git a/test/std/utilities/meta/meta.unary/meta.unary.prop/is_trivially_destructible.pass.cpp b/test/std/utilities/meta/meta.unary/meta.unary.prop/is_trivially_destructible.pass.cpp
index b18ace4..0908f8b 100644
--- a/test/std/utilities/meta/meta.unary/meta.unary.prop/is_trivially_destructible.pass.cpp
+++ b/test/std/utilities/meta/meta.unary/meta.unary.prop/is_trivially_destructible.pass.cpp
@@ -13,6 +13,8 @@
 
 #include <type_traits>
 
+#include "test_macros.h"
+
 template <class T>
 void test_is_trivially_destructible()
 {
@@ -31,15 +33,23 @@
     static_assert(!std::is_trivially_destructible<const volatile T>::value, "");
 }
 
+struct PublicDestructor           { public:     ~PublicDestructor() {}};
+struct ProtectedDestructor        { protected:  ~ProtectedDestructor() {}};
+struct PrivateDestructor          { private:    ~PrivateDestructor() {}};
+
+struct VirtualPublicDestructor           { public:    virtual ~VirtualPublicDestructor() {}};
+struct VirtualProtectedDestructor        { protected: virtual ~VirtualProtectedDestructor() {}};
+struct VirtualPrivateDestructor          { private:   virtual ~VirtualPrivateDestructor() {}};
+
+struct PurePublicDestructor              { public:    virtual ~PurePublicDestructor() = 0; };
+struct PureProtectedDestructor           { protected: virtual ~PureProtectedDestructor() = 0; };
+struct PurePrivateDestructor             { private:   virtual ~PurePrivateDestructor() = 0; };
+
+
 class Empty
 {
 };
 
-class NotEmpty
-{
-    virtual ~NotEmpty();
-};
-
 union Union {};
 
 struct bit_zero
@@ -66,18 +76,28 @@
 {
     test_is_not_trivially_destructible<void>();
     test_is_not_trivially_destructible<A>();
-    test_is_not_trivially_destructible<AbstractDestructor>();
-    test_is_not_trivially_destructible<NotEmpty>();
     test_is_not_trivially_destructible<char[]>();
+    test_is_not_trivially_destructible<VirtualPublicDestructor>();
+    test_is_not_trivially_destructible<PurePublicDestructor>();
 
     test_is_trivially_destructible<Abstract>();
-    test_is_trivially_destructible<int&>();
     test_is_trivially_destructible<Union>();
     test_is_trivially_destructible<Empty>();
+    test_is_trivially_destructible<int&>();
     test_is_trivially_destructible<int>();
     test_is_trivially_destructible<double>();
     test_is_trivially_destructible<int*>();
     test_is_trivially_destructible<const int*>();
     test_is_trivially_destructible<char[3]>();
     test_is_trivially_destructible<bit_zero>();
+
+#if TEST_STD_VER >= 11
+    // requires access control sfinae
+    test_is_not_trivially_destructible<ProtectedDestructor>();
+    test_is_not_trivially_destructible<PrivateDestructor>();
+    test_is_not_trivially_destructible<VirtualProtectedDestructor>();
+    test_is_not_trivially_destructible<VirtualPrivateDestructor>();
+    test_is_not_trivially_destructible<PureProtectedDestructor>();
+    test_is_not_trivially_destructible<PurePrivateDestructor>();
+#endif
 }
diff --git a/test/std/utilities/ratio/ratio.ratio/ratio.pass.cpp b/test/std/utilities/ratio/ratio.ratio/ratio.pass.cpp
index f942c96..a732616 100644
--- a/test/std/utilities/ratio/ratio.ratio/ratio.pass.cpp
+++ b/test/std/utilities/ratio/ratio.ratio/ratio.pass.cpp
@@ -7,7 +7,7 @@
 //
 //===----------------------------------------------------------------------===//
 
-// test ratio:  The static data members num and den shall have thcommon
+// test ratio:  The static data members num and den shall have the common
 //    divisor of the absolute values of N and D:
 
 #include <ratio>
diff --git a/test/std/utilities/template.bitset/bitset.cons/char_ptr_ctor.pass.cpp b/test/std/utilities/template.bitset/bitset.cons/char_ptr_ctor.pass.cpp
index 7fe78ba..df5ec4a 100644
--- a/test/std/utilities/template.bitset/bitset.cons/char_ptr_ctor.pass.cpp
+++ b/test/std/utilities/template.bitset/bitset.cons/char_ptr_ctor.pass.cpp
@@ -14,6 +14,8 @@
 
 #include <bitset>
 #include <cassert>
+#include <algorithm> // for 'min' and 'max'
+#include <stdexcept> // for 'invalid_argument'
 
 #pragma clang diagnostic ignored "-Wtautological-compare"
 
diff --git a/test/std/utilities/template.bitset/bitset.cons/string_ctor.pass.cpp b/test/std/utilities/template.bitset/bitset.cons/string_ctor.pass.cpp
index bcee50c..98083f8 100644
--- a/test/std/utilities/template.bitset/bitset.cons/string_ctor.pass.cpp
+++ b/test/std/utilities/template.bitset/bitset.cons/string_ctor.pass.cpp
@@ -11,6 +11,8 @@
 
 #include <bitset>
 #include <cassert>
+#include <algorithm> // for 'min' and 'max'
+#include <stdexcept> // for 'invalid_argument'
 
 #pragma clang diagnostic ignored "-Wtautological-compare"
 
diff --git a/test/std/utilities/template.bitset/bitset.cons/ull_ctor.pass.cpp b/test/std/utilities/template.bitset/bitset.cons/ull_ctor.pass.cpp
index 023fedc..f232447 100644
--- a/test/std/utilities/template.bitset/bitset.cons/ull_ctor.pass.cpp
+++ b/test/std/utilities/template.bitset/bitset.cons/ull_ctor.pass.cpp
@@ -11,6 +11,7 @@
 
 #include <bitset>
 #include <cassert>
+#include <algorithm> // for 'min' and 'max'
 
 #pragma clang diagnostic ignored "-Wtautological-compare"
 
diff --git a/test/std/utilities/utility/declval/declval.pass.cpp b/test/std/utilities/utility/declval/declval.pass.cpp
index 81f4df8..aabd0e6 100644
--- a/test/std/utilities/utility/declval/declval.pass.cpp
+++ b/test/std/utilities/utility/declval/declval.pass.cpp
@@ -14,6 +14,8 @@
 #include <utility>
 #include <type_traits>
 
+#include "test_macros.h"
+
 class A
 {
     A(const A&);
@@ -22,9 +24,9 @@
 
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#if TEST_STD_VER >= 11
     static_assert((std::is_same<decltype(std::declval<A>()), A&&>::value), "");
 #else
-    static_assert((std::is_same<decltype(std::declval<A>()), A>::value), "");
+    static_assert((std::is_same<decltype(std::declval<A>()), A&>::value), "");
 #endif
 }
diff --git a/test/std/utilities/utility/forward/move_copy.pass.cpp b/test/std/utilities/utility/forward/move_copy.pass.cpp
index 461a876..fa15553 100644
--- a/test/std/utilities/utility/forward/move_copy.pass.cpp
+++ b/test/std/utilities/utility/forward/move_copy.pass.cpp
@@ -9,6 +9,8 @@
 
 // test move
 
+// UNSUPPORTED: c++98, c++03
+
 #include <utility>
 #include <cassert>
 
@@ -17,25 +19,13 @@
 
 class A
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-#else
-#endif
-
 public:
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     A(const A&) {++copy_ctor;}
     A& operator=(const A&);
 
     A(A&&) {++move_ctor;}
     A& operator=(A&&);
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    A(const A&) {++copy_ctor;}
-    A& operator=(A&);
-
-    operator std::__rv<A> () {return std::__rv<A>(*this);}
-    A(std::__rv<A>) {++move_ctor;}
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
     A() {}
 };
diff --git a/test/std/utilities/utility/forward/move_if_noexcept.pass.cpp b/test/std/utilities/utility/forward/move_if_noexcept.pass.cpp
index f94ff2a..bc60d3d 100644
--- a/test/std/utilities/utility/forward/move_if_noexcept.pass.cpp
+++ b/test/std/utilities/utility/forward/move_if_noexcept.pass.cpp
@@ -20,6 +20,8 @@
 
 #include <utility>
 
+#include "test_macros.h"
+
 class A
 {
     A(const A&);
@@ -27,7 +29,7 @@
 public:
 
     A() {}
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#if TEST_STD_VER >= 11
     A(A&&) {}
 #endif
 };
@@ -47,20 +49,24 @@
     A a;
     const A ca;
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+#if TEST_STD_VER >= 11
     static_assert((std::is_same<decltype(std::move_if_noexcept(i)), int&&>::value), "");
     static_assert((std::is_same<decltype(std::move_if_noexcept(ci)), const int&&>::value), "");
     static_assert((std::is_same<decltype(std::move_if_noexcept(a)), A&&>::value), "");
     static_assert((std::is_same<decltype(std::move_if_noexcept(ca)), const A&&>::value), "");
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    static_assert((std::is_same<decltype(std::move_if_noexcept(i)), const int>::value), "");
-    static_assert((std::is_same<decltype(std::move_if_noexcept(ci)), const int>::value), "");
-    static_assert((std::is_same<decltype(std::move_if_noexcept(a)), const A>::value), "");
-    static_assert((std::is_same<decltype(std::move_if_noexcept(ca)), const A>::value), "");
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
     static_assert((std::is_same<decltype(std::move_if_noexcept(l)), const legacy&>::value), "");
+#else  // C++ < 11
+    // In C++03 libc++ #define's decltype to be __decltype on clang and
+    // __typeof__ for other compilers. __typeof__ does not deduce the reference
+    // qualifiers and will cause this test to fail.
+    static_assert((std::is_same<decltype(std::move_if_noexcept(i)), const int&>::value), "");
+    static_assert((std::is_same<decltype(std::move_if_noexcept(ci)), const int&>::value), "");
+    static_assert((std::is_same<decltype(std::move_if_noexcept(a)), const A&>::value), "");
+    static_assert((std::is_same<decltype(std::move_if_noexcept(ca)), const A&>::value), "");
+    static_assert((std::is_same<decltype(std::move_if_noexcept(l)), const legacy&>::value), "");
+#endif
 
-#if _LIBCPP_STD_VER > 11
+#if TEST_STD_VER > 11
     constexpr int i1 = 23;
     constexpr int i2 = std::move_if_noexcept(i1);
     static_assert(i2 == 23, "" );
diff --git a/test/std/utilities/utility/forward/move_only.pass.cpp b/test/std/utilities/utility/forward/move_only.pass.cpp
index 0588c11..520bf5e 100644
--- a/test/std/utilities/utility/forward/move_only.pass.cpp
+++ b/test/std/utilities/utility/forward/move_only.pass.cpp
@@ -9,28 +9,18 @@
 
 // test move
 
+// UNSUPPORTED: c++98, c++03
+
 #include <utility>
 #include <cassert>
 
 class move_only
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     move_only(const move_only&);
     move_only& operator=(const move_only&);
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    move_only(move_only&);
-    move_only& operator=(move_only&);
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
 public:
-
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     move_only(move_only&&) {}
     move_only& operator=(move_only&&) {return *this;}
-#else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    operator std::__rv<move_only> () {return std::__rv<move_only>(*this);}
-    move_only(std::__rv<move_only>) {}
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
     move_only() {}
 };
diff --git a/test/std/utilities/utility/pairs/pair.astuple/tuple_element.pass.cpp b/test/std/utilities/utility/pairs/pair.astuple/tuple_element.pass.cpp
index 9a303ba..5ac838b 100644
--- a/test/std/utilities/utility/pairs/pair.astuple/tuple_element.pass.cpp
+++ b/test/std/utilities/utility/pairs/pair.astuple/tuple_element.pass.cpp
@@ -15,16 +15,41 @@
 
 #include <utility>
 
-int main()
+template <class T1, class T2>
+void test()
 {
     {
-        typedef std::pair<int, short> P1;
-        static_assert((std::is_same<std::tuple_element<0, P1>::type, int>::value), "");
-        static_assert((std::is_same<std::tuple_element<1, P1>::type, short>::value), "");
+    typedef T1 Exp1;
+    typedef T2 Exp2;
+    typedef std::pair<T1, T2> P;
+    static_assert((std::is_same<typename std::tuple_element<0, P>::type, Exp1>::value), "");
+    static_assert((std::is_same<typename std::tuple_element<1, P>::type, Exp2>::value), "");
     }
     {
-        typedef std::pair<int*, char> P1;
-        static_assert((std::is_same<std::tuple_element<0, P1>::type, int*>::value), "");
-        static_assert((std::is_same<std::tuple_element<1, P1>::type, char>::value), "");
+    typedef T1 const Exp1;
+    typedef T2 const Exp2;
+    typedef std::pair<T1, T2> const P;
+    static_assert((std::is_same<typename std::tuple_element<0, P>::type, Exp1>::value), "");
+    static_assert((std::is_same<typename std::tuple_element<1, P>::type, Exp2>::value), "");
     }
+    {
+    typedef T1 volatile Exp1;
+    typedef T2 volatile Exp2;
+    typedef std::pair<T1, T2> volatile P;
+    static_assert((std::is_same<typename std::tuple_element<0, P>::type, Exp1>::value), "");
+    static_assert((std::is_same<typename std::tuple_element<1, P>::type, Exp2>::value), "");
+    }
+    {
+    typedef T1 const volatile Exp1;
+    typedef T2 const volatile Exp2;
+    typedef std::pair<T1, T2> const volatile P;
+    static_assert((std::is_same<typename std::tuple_element<0, P>::type, Exp1>::value), "");
+    static_assert((std::is_same<typename std::tuple_element<1, P>::type, Exp2>::value), "");
+    }
+}
+
+int main()
+{
+    test<int, short>();
+    test<int*, char>();
 }
diff --git a/test/std/utilities/utility/pairs/pair.astuple/tuple_size.pass.cpp b/test/std/utilities/utility/pairs/pair.astuple/tuple_size.pass.cpp
index 2be694e..3756e96 100644
--- a/test/std/utilities/utility/pairs/pair.astuple/tuple_size.pass.cpp
+++ b/test/std/utilities/utility/pairs/pair.astuple/tuple_size.pass.cpp
@@ -21,4 +21,16 @@
         typedef std::pair<int, short> P1;
         static_assert((std::tuple_size<P1>::value == 2), "");
     }
+    {
+        typedef std::pair<int, short> const P1;
+        static_assert((std::tuple_size<P1>::value == 2), "");
+    }
+    {
+        typedef std::pair<int, short> volatile P1;
+        static_assert((std::tuple_size<P1>::value == 2), "");
+    }
+    {
+        typedef std::pair<int, short> const volatile P1;
+        static_assert((std::tuple_size<P1>::value == 2), "");
+    }
 }
diff --git a/test/support/allocators.h b/test/support/allocators.h
index 5372c07..b7aba12 100644
--- a/test/support/allocators.h
+++ b/test/support/allocators.h
@@ -13,6 +13,8 @@
 #include <type_traits>
 #include <utility>
 
+#include "test_macros.h"
+
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
 template <class T>
@@ -20,7 +22,7 @@
 {
     int id_;
 public:
-    explicit A1(int id = 0) : id_(id) {}
+    explicit A1(int id = 0) TEST_NOEXCEPT : id_(id) {}
 
     typedef T value_type;
 
@@ -31,13 +33,13 @@
     static bool allocate_called;
     static std::pair<T*, std::size_t> deallocate_called;
 
-    A1(const A1& a) : id_(a.id()) {copy_called = true;}
-    A1(A1&& a) : id_(a.id())      {move_called = true;}
+    A1(const A1& a) TEST_NOEXCEPT : id_(a.id()) {copy_called = true;}
+    A1(A1&& a)      TEST_NOEXCEPT : id_(a.id()) {move_called = true;}
 
     template <class U>
-        A1(const A1<U>& a) : id_(a.id()) {copy_called = true;}
+        A1(const A1<U>& a) TEST_NOEXCEPT : id_(a.id()) {copy_called = true;}
     template <class U>
-        A1(A1<U>&& a) : id_(a.id()) {move_called = true;}
+        A1(A1<U>&& a) TEST_NOEXCEPT : id_(a.id()) {move_called = true;}
 
     T* allocate(std::size_t n)
     {
@@ -77,7 +79,7 @@
 {
     int id_;
 public:
-    explicit A2(int id = 0) : id_(id) {}
+    explicit A2(int id = 0) TEST_NOEXCEPT : id_(id) {}
 
     typedef T value_type;
 
@@ -92,8 +94,8 @@
     static bool move_called;
     static bool allocate_called;
 
-    A2(const A2& a) : id_(a.id()) {copy_called = true;}
-    A2(A2&& a) : id_(a.id())      {move_called = true;}
+    A2(const A2& a) TEST_NOEXCEPT : id_(a.id()) {copy_called = true;}
+    A2(A2&& a)      TEST_NOEXCEPT : id_(a.id()) {move_called = true;}
 
     T* allocate(std::size_t n, const void* hint)
     {
@@ -125,7 +127,7 @@
 {
     int id_;
 public:
-    explicit A3(int id = 0) : id_(id) {}
+    explicit A3(int id = 0) TEST_NOEXCEPT : id_(id) {}
 
     typedef T value_type;
 
@@ -139,8 +141,8 @@
     static bool constructed;
     static bool destroy_called;
 
-    A3(const A3& a) : id_(a.id()) {copy_called = true;}
-    A3(A3&& a) : id_(a.id())      {move_called = true;}
+    A3(const A3& a) TEST_NOEXCEPT : id_(a.id()) {copy_called = true;}
+    A3(A3&& a)      TEST_NOEXCEPT: id_(a.id())  {move_called = true;}
 
     template <class U, class ...Args>
     void construct(U* p, Args&& ...args)
diff --git a/test/support/any_helpers.h b/test/support/any_helpers.h
new file mode 100644
index 0000000..76b1922
--- /dev/null
+++ b/test/support/any_helpers.h
@@ -0,0 +1,318 @@
+#ifndef ANY_HELPERS_H
+#define ANY_HELPERS_H
+
+#include <experimental/any>
+#include <typeinfo>
+#include <type_traits>
+#include <cassert>
+
+#include "test_macros.h"
+
+#if !defined(TEST_HAS_NO_RTTI)
+#define RTTI_ASSERT(X) assert(X)
+#else
+#define RTTI_ASSERT(X)
+#endif
+
+template <class _Tp>
+  struct IsSmallObject
+    : public std::integral_constant<bool
+        , sizeof(_Tp) <= (sizeof(void*)*3)
+          && std::alignment_of<void*>::value
+             % std::alignment_of<_Tp>::value == 0
+          && std::is_nothrow_move_constructible<_Tp>::value
+        >
+  {};
+
+
+// Return 'true' if 'Type' will be considered a small type by 'any'
+template <class Type>
+bool isSmallType() {
+#if defined(_LIBCPP_VERSION)
+    return std::experimental::__any_imp::_IsSmallObject<Type>::value;
+#else
+    return IsSmallObject<Type>::value;
+#endif
+
+}
+
+// Assert that an object is empty. If the object used to contain an object
+// of type 'LastType' check that it can no longer be accessed.
+template <class LastType = int>
+void assertEmpty(std::experimental::any const& a) {
+    assert(a.empty());
+    RTTI_ASSERT(a.type() == typeid(void));
+    assert(std::experimental::any_cast<LastType const>(&a) == nullptr);
+}
+
+// Assert that an 'any' object stores the specified 'Type' and 'value'.
+template <class Type>
+void assertContains(std::experimental::any const& a, int value = 1) {
+    assert(!a.empty());
+    RTTI_ASSERT(a.type() == typeid(Type));
+    assert(std::experimental::any_cast<Type const &>(a).value == value);
+}
+
+// Modify the value of a "test type" stored within an any to the specified
+// 'value'.
+template <class Type>
+void modifyValue(std::experimental::any& a, int value) {
+    assert(!a.empty());
+    RTTI_ASSERT(a.type() == typeid(Type));
+    std::experimental::any_cast<Type&>(a).value = value;
+}
+
+// A test type that will trigger the small object optimization within 'any'.
+template <int Dummy = 0>
+struct small_type
+{
+    static int count;
+    static int copied;
+    static int moved;
+    static int const_copied;
+    static int non_const_copied;
+
+    static void reset() {
+        small_type::copied = 0;
+        small_type::moved = 0;
+        small_type::const_copied = 0;
+        small_type::non_const_copied = 0;
+    }
+
+    int value;
+
+    explicit small_type(int val) : value(val) {
+        ++count;
+    }
+
+    small_type(small_type const & other) throw() {
+        value = other.value;
+        ++count;
+        ++copied;
+        ++const_copied;
+    }
+
+    small_type(small_type& other) throw() {
+        value = other.value;
+        ++count;
+        ++copied;
+        ++non_const_copied;
+    }
+
+    small_type(small_type && other) throw() {
+        value = other.value;
+        other.value = 0;
+        ++count;
+        ++moved;
+    }
+
+    ~small_type() {
+        value = -1;
+        --count;
+    }
+
+private:
+    small_type& operator=(small_type const&) = delete;
+    small_type& operator=(small_type&&) = delete;
+};
+
+template <int Dummy>
+int small_type<Dummy>::count = 0;
+
+template <int Dummy>
+int small_type<Dummy>::copied = 0;
+
+template <int Dummy>
+int small_type<Dummy>::moved = 0;
+
+template <int Dummy>
+int small_type<Dummy>::const_copied = 0;
+
+template <int Dummy>
+int small_type<Dummy>::non_const_copied = 0;
+
+typedef small_type<> small;
+typedef small_type<1> small1;
+typedef small_type<2> small2;
+
+
+// A test type that will NOT trigger the small object optimization in any.
+template <int Dummy = 0>
+struct large_type
+{
+    static int count;
+    static int copied;
+    static int moved;
+    static int const_copied;
+    static int non_const_copied;
+
+    static void reset() {
+        large_type::copied = 0;
+        large_type::moved  = 0;
+        large_type::const_copied = 0;
+        large_type::non_const_copied = 0;
+    }
+
+    int value;
+
+    large_type(int val) : value(val) {
+        ++count;
+        data[0] = 0;
+    }
+
+    large_type(large_type const & other) {
+        value = other.value;
+        ++count;
+        ++copied;
+        ++const_copied;
+    }
+
+    large_type(large_type & other) {
+        value = other.value;
+        ++count;
+        ++copied;
+        ++non_const_copied;
+    }
+
+    large_type(large_type && other) {
+        value = other.value;
+        other.value = 0;
+        ++count;
+        ++moved;
+    }
+
+    ~large_type()  {
+        value = 0;
+        --count;
+    }
+
+private:
+    large_type& operator=(large_type const&) = delete;
+    large_type& operator=(large_type &&) = delete;
+    int data[10];
+};
+
+template <int Dummy>
+int large_type<Dummy>::count = 0;
+
+template <int Dummy>
+int large_type<Dummy>::copied = 0;
+
+template <int Dummy>
+int large_type<Dummy>::moved = 0;
+
+template <int Dummy>
+int large_type<Dummy>::const_copied = 0;
+
+template <int Dummy>
+int large_type<Dummy>::non_const_copied = 0;
+
+typedef large_type<> large;
+typedef large_type<1> large1;
+typedef large_type<2> large2;
+
+// The exception type thrown by 'small_throws_on_copy', 'large_throws_on_copy'
+// and 'throws_on_move'.
+struct my_any_exception {};
+
+void throwMyAnyExpression() {
+#if !defined(TEST_HAS_NO_EXCEPTIONS)
+        throw my_any_exception();
+#else
+        assert(false && "Exceptions are disabled");
+#endif
+}
+
+// A test type that will trigger the small object optimization within 'any'.
+// this type throws if it is copied.
+struct small_throws_on_copy
+{
+    static int count;
+    int value;
+
+    explicit small_throws_on_copy(int val = 0) : value(val) {
+        ++count;
+    }
+
+    small_throws_on_copy(small_throws_on_copy const &) {
+        throwMyAnyExpression();
+    }
+
+    small_throws_on_copy(small_throws_on_copy && other) throw() {
+        value = other.value;
+        ++count;
+    }
+
+    ~small_throws_on_copy() {
+        --count;
+    }
+private:
+    small_throws_on_copy& operator=(small_throws_on_copy const&) = delete;
+    small_throws_on_copy& operator=(small_throws_on_copy &&) = delete;
+};
+
+int small_throws_on_copy::count = 0;
+
+// A test type that will NOT trigger the small object optimization within 'any'.
+// this type throws if it is copied.
+struct large_throws_on_copy
+{
+    static int count;
+    int value = 0;
+
+    explicit large_throws_on_copy(int val = 0) : value(val) {
+        data[0] = 0;
+        ++count;
+    }
+
+    large_throws_on_copy(large_throws_on_copy const &) {
+         throwMyAnyExpression();
+    }
+
+    large_throws_on_copy(large_throws_on_copy && other) throw() {
+        value = other.value;
+        ++count;
+    }
+
+    ~large_throws_on_copy() {
+        --count;
+    }
+
+private:
+    large_throws_on_copy& operator=(large_throws_on_copy const&) = delete;
+    large_throws_on_copy& operator=(large_throws_on_copy &&) = delete;
+    int data[10];
+};
+
+int large_throws_on_copy::count = 0;
+
+// A test type that throws when it is moved. This object will NOT trigger
+// the small object optimization in 'any'.
+struct throws_on_move
+{
+    static int count;
+    int value;
+
+    explicit throws_on_move(int val = 0) : value(val) { ++count; }
+
+    throws_on_move(throws_on_move const & other) {
+        value = other.value;
+        ++count;
+    }
+
+    throws_on_move(throws_on_move &&) {
+        throwMyAnyExpression();
+    }
+
+    ~throws_on_move() {
+        --count;
+    }
+private:
+    throws_on_move& operator=(throws_on_move const&) = delete;
+    throws_on_move& operator=(throws_on_move &&) = delete;
+};
+
+int throws_on_move::count = 0;
+
+
+#endif
diff --git a/test/support/count_new.hpp b/test/support/count_new.hpp
index 00df7a1..57aca7d 100644
--- a/test/support/count_new.hpp
+++ b/test/support/count_new.hpp
@@ -10,7 +10,8 @@
 #endif
 
 #if  __has_feature(address_sanitizer) \
-  || __has_feature(memory_sanitizer)
+  || __has_feature(memory_sanitizer) \
+  || __has_feature(thread_sanitizer)
 #define DISABLE_NEW_COUNT
 #endif
 
@@ -29,6 +30,10 @@
     // All checks return true when disable_checking is enabled.
     static const bool disable_checking;
 
+    // Disallow any allocations from occurring. Useful for testing that
+    // code doesn't perform any allocations.
+    bool disable_allocations;
+
     int outstanding_new;
     int new_called;
     int delete_called;
@@ -42,6 +47,7 @@
 public:
     void newCalled(std::size_t s)
     {
+        assert(disable_allocations == false);
         assert(s);
         ++new_called;
         ++outstanding_new;
@@ -57,6 +63,7 @@
 
     void newArrayCalled(std::size_t s)
     {
+        assert(disable_allocations == false);
         assert(s);
         ++outstanding_array_new;
         ++new_array_called;
@@ -70,8 +77,20 @@
         ++delete_array_called;
     }
 
+    void disableAllocations()
+    {
+        disable_allocations = true;
+    }
+
+    void enableAllocations()
+    {
+        disable_allocations = false;
+    }
+
     void reset()
     {
+        disable_allocations = false;
+
         outstanding_new = 0;
         new_called = 0;
         delete_called = 0;
@@ -202,4 +221,29 @@
 
 #endif // DISABLE_NEW_COUNT
 
+
+struct DisableAllocationGuard {
+    explicit DisableAllocationGuard(bool disable = true) : m_disabled(disable)
+    {
+        // Don't re-disable if already disabled.
+        if (globalMemCounter.disable_allocations == true) m_disabled = false;
+        if (m_disabled) globalMemCounter.disableAllocations();
+    }
+
+    void release() {
+        if (m_disabled) globalMemCounter.enableAllocations();
+        m_disabled = false;
+    }
+
+    ~DisableAllocationGuard() {
+        release();
+    }
+
+private:
+    bool m_disabled;
+
+    DisableAllocationGuard(DisableAllocationGuard const&);
+    DisableAllocationGuard& operator=(DisableAllocationGuard const&);
+};
+
 #endif /* COUNT_NEW_HPP */
diff --git a/test/support/is_transparent.h b/test/support/is_transparent.h
new file mode 100644
index 0000000..5825524
--- /dev/null
+++ b/test/support/is_transparent.h
@@ -0,0 +1,73 @@
+//===----------------------------------------------------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef TRANSPARENT_H
+#define TRANSPARENT_H
+
+// testing transparent 
+#if _LIBCPP_STD_VER > 11
+
+struct transparent_less
+{
+    template <class T, class U>
+    constexpr auto operator()(T&& t, U&& u) const
+    noexcept(noexcept(std::forward<T>(t) < std::forward<U>(u)))
+    -> decltype      (std::forward<T>(t) < std::forward<U>(u))
+        { return      std::forward<T>(t) < std::forward<U>(u); }
+    typedef void is_transparent;  // correct
+};
+
+struct transparent_less_no_type
+{
+    template <class T, class U>
+    constexpr auto operator()(T&& t, U&& u) const
+    noexcept(noexcept(std::forward<T>(t) < std::forward<U>(u)))
+    -> decltype      (std::forward<T>(t) < std::forward<U>(u))
+        { return      std::forward<T>(t) < std::forward<U>(u); }
+private:
+//    typedef void is_transparent;  // error - should exist
+};
+
+struct transparent_less_private
+{
+    template <class T, class U>
+    constexpr auto operator()(T&& t, U&& u) const
+    noexcept(noexcept(std::forward<T>(t) < std::forward<U>(u)))
+    -> decltype      (std::forward<T>(t) < std::forward<U>(u))
+        { return      std::forward<T>(t) < std::forward<U>(u); }
+private:
+    typedef void is_transparent;  // error - should be accessible
+};
+
+struct transparent_less_not_a_type
+{
+    template <class T, class U>
+    constexpr auto operator()(T&& t, U&& u) const
+    noexcept(noexcept(std::forward<T>(t) < std::forward<U>(u)))
+    -> decltype      (std::forward<T>(t) < std::forward<U>(u))
+        { return      std::forward<T>(t) < std::forward<U>(u); }
+
+    int is_transparent;  // error - should be a type
+};
+
+struct C2Int { // comparable to int
+    C2Int() : i_(0) {}
+    C2Int(int i): i_(i) {}
+    int get () const { return i_; }
+private:
+    int i_;
+    };
+    
+bool operator <(int          rhs,   const C2Int& lhs) { return rhs       < lhs.get(); }
+bool operator <(const C2Int& rhs,   const C2Int& lhs) { return rhs.get() < lhs.get(); }
+bool operator <(const C2Int& rhs,            int lhs) { return rhs.get() < lhs; }
+
+#endif
+
+#endif  // TRANSPARENT_H
diff --git a/test/support/min_allocator.h b/test/support/min_allocator.h
index b643636..5e3ae5d 100644
--- a/test/support/min_allocator.h
+++ b/test/support/min_allocator.h
@@ -12,16 +12,18 @@
 
 #include <cstddef>
 
+#include "test_macros.h"
+
 template <class T>
 class bare_allocator
 {
 public:
     typedef T value_type;
 
-    bare_allocator() {}
+    bare_allocator() TEST_NOEXCEPT {}
 
     template <class U>
-    bare_allocator(bare_allocator<U>) {}
+    bare_allocator(bare_allocator<U>) TEST_NOEXCEPT {}
 
     T* allocate(std::size_t n)
     {
@@ -53,10 +55,10 @@
 {
     const void* ptr_;
 public:
-    min_pointer() noexcept = default;
-    min_pointer(std::nullptr_t) : ptr_(nullptr) {}
+    min_pointer() TEST_NOEXCEPT = default;
+    min_pointer(std::nullptr_t) TEST_NOEXCEPT : ptr_(nullptr) {}
     template <class T>
-    min_pointer(min_pointer<T> p) : ptr_(p.ptr_) {}
+    min_pointer(min_pointer<T> p) TEST_NOEXCEPT : ptr_(p.ptr_) {}
 
     explicit operator bool() const {return ptr_ != nullptr;}
 
@@ -70,15 +72,15 @@
 {
     void* ptr_;
 public:
-    min_pointer() noexcept = default;
-    min_pointer(std::nullptr_t) : ptr_(nullptr) {}
+    min_pointer() TEST_NOEXCEPT = default;
+    min_pointer(std::nullptr_t) TEST_NOEXCEPT : ptr_(nullptr) {}
     template <class T,
               class = typename std::enable_if
                        <
                             !std::is_const<T>::value
                        >::type
              >
-    min_pointer(min_pointer<T> p) : ptr_(p.ptr_) {}
+    min_pointer(min_pointer<T> p) TEST_NOEXCEPT : ptr_(p.ptr_) {}
 
     explicit operator bool() const {return ptr_ != nullptr;}
 
@@ -92,11 +94,11 @@
 {
     T* ptr_;
 
-    explicit min_pointer(T* p) : ptr_(p) {}
+    explicit min_pointer(T* p) TEST_NOEXCEPT : ptr_(p) {}
 public:
-    min_pointer() noexcept = default;
-    min_pointer(std::nullptr_t) : ptr_(nullptr) {}
-    explicit min_pointer(min_pointer<void> p) : ptr_(static_cast<T*>(p.ptr_)) {}
+    min_pointer() TEST_NOEXCEPT = default;
+    min_pointer(std::nullptr_t) TEST_NOEXCEPT : ptr_(nullptr) {}
+    explicit min_pointer(min_pointer<void> p) TEST_NOEXCEPT : ptr_(static_cast<T*>(p.ptr_)) {}
 
     explicit operator bool() const {return ptr_ != nullptr;}
 
@@ -164,7 +166,7 @@
 
     explicit min_pointer(const T* p) : ptr_(p) {}
 public:
-    min_pointer() noexcept = default;
+    min_pointer() TEST_NOEXCEPT = default;
     min_pointer(std::nullptr_t) : ptr_(nullptr) {}
     min_pointer(min_pointer<T> p) : ptr_(p.ptr_) {}
     explicit min_pointer(min_pointer<const void> p) : ptr_(static_cast<const T*>(p.ptr_)) {}
diff --git a/test/support/platform_support.h b/test/support/platform_support.h
index 180765e..233e721 100644
--- a/test/support/platform_support.h
+++ b/test/support/platform_support.h
@@ -15,6 +15,8 @@
 #ifndef PLATFORM_SUPPORT_H
 #define PLATFORM_SUPPORT_H
 
+#include <__config>
+
 // locale names
 #ifdef _WIN32
 // WARNING: Windows does not support UTF-8 codepages.
@@ -25,6 +27,16 @@
 #define LOCALE_fr_CA_ISO8859_1 "French_Canada.1252"
 #define LOCALE_ru_RU_UTF_8     "Russian_Russia.1251"
 #define LOCALE_zh_CN_UTF_8     "Chinese_China.936"
+#elif defined(__CloudABI__)
+// Timezones are integrated into locales through LC_TIMEZONE_MASK on
+// CloudABI. LC_ALL_MASK can only be used if a timezone has also been
+// provided. UTC should be all right.
+#define LOCALE_en_US_UTF_8     "en_US.UTF-8@UTC"
+#define LOCALE_fr_FR_UTF_8     "fr_FR.UTF-8@UTC"
+#define LOCALE_fr_CA_ISO8859_1 "fr_CA.ISO-8859-1@UTC"
+#define LOCALE_cs_CZ_ISO8859_2 "cs_CZ.ISO-8859-2@UTC"
+#define LOCALE_ru_RU_UTF_8     "ru_RU.UTF-8@UTC"
+#define LOCALE_zh_CN_UTF_8     "zh_CN.UTF-8@UTC"
 #else
 #define LOCALE_en_US_UTF_8     "en_US.UTF-8"
 #define LOCALE_fr_FR_UTF_8     "fr_FR.UTF-8"
@@ -55,6 +67,7 @@
 }
 #endif
 
+#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
 inline
 std::string
 get_temp_file_name()
@@ -80,5 +93,6 @@
     return Name;
 #endif
 }
+#endif // _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
 
 #endif // PLATFORM_SUPPORT_H
diff --git a/test/support/test_allocator.h b/test/support/test_allocator.h
index 683fac2..47ef1d5 100644
--- a/test/support/test_allocator.h
+++ b/test/support/test_allocator.h
@@ -17,6 +17,8 @@
 #include <climits>
 #include <cassert>
 
+#include "test_macros.h"
+
 class test_alloc_base
 {
 protected:
@@ -72,10 +74,10 @@
             }
             ++time_to_throw;
             ++alloc_count;
-            return (pointer)std::malloc(n * sizeof(T));
+            return (pointer)::operator new(n * sizeof(T));
         }
     void deallocate(pointer p, size_type n)
-        {assert(data_ >= 0); --alloc_count; std::free(p);}
+        {assert(data_ >= 0); --alloc_count; ::operator delete((void*)p);}
     size_type max_size() const throw()
         {return UINT_MAX / sizeof(T);}
     void construct(pointer p, const T& val)
@@ -132,10 +134,10 @@
             }
             ++time_to_throw;
             ++alloc_count;
-            return (pointer)std::malloc(n * sizeof(T));
+            return (pointer)::operator new (n * sizeof(T));
         }
     void deallocate(pointer p, size_type n)
-        {assert(data_ >= 0); --alloc_count; std::free(p);}
+        {assert(data_ >= 0); --alloc_count; ::operator delete((void*)p); }
     size_type max_size() const throw()
         {return UINT_MAX / sizeof(T);}
     void construct(pointer p, const T& val)
@@ -198,9 +200,9 @@
     template <class U> other_allocator(const other_allocator<U>& a)
         : data_(a.data_) {}
     T* allocate(std::size_t n)
-        {return (T*)std::malloc(n * sizeof(T));}
+        {return (T*)::operator new(n * sizeof(T));}
     void deallocate(T* p, std::size_t n)
-        {std::free(p);}
+        {::operator delete((void*)p);}
 
     other_allocator select_on_container_copy_construction() const
         {return other_allocator(-2);}
diff --git a/test/support/test_macros.h b/test/support/test_macros.h
new file mode 100644
index 0000000..08ec28f
--- /dev/null
+++ b/test/support/test_macros.h
@@ -0,0 +1,97 @@
+// -*- C++ -*-
+//===---------------------------- test_macros.h ---------------------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is dual licensed under the MIT and the University of Illinois Open
+// Source Licenses. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef SUPPORT_TEST_MACROS_HPP
+#define SUPPORT_TEST_MACROS_HPP
+
+#define TEST_CONCAT1(X, Y) X##Y
+#define TEST_CONCAT(X, Y) TEST_CONCAT1(X, Y)
+
+#ifdef __has_feature
+#define TEST_HAS_FEATURE(X) __has_feature(X)
+#else
+#define TEST_HAS_FEATURE(X) 0
+#endif
+
+#ifdef __has_extension
+#define TEST_HAS_EXTENSION(X) __has_extension(X)
+#else
+#define TEST_HAS_EXTENSION(X) 0
+#endif
+
+/* Make a nice name for the standard version */
+#if  __cplusplus <= 199711L
+# define TEST_STD_VER 3
+#elif __cplusplus <= 201103L
+# define TEST_STD_VER 11
+#elif __cplusplus <= 201402L
+# define TEST_STD_VER 14
+#else
+# define TEST_STD_VER 99    // greater than current standard
+#endif
+
+/* Features that were introduced in C++11 */
+#if TEST_STD_VER >= 11
+#define TEST_HAS_RVALUE_REFERENCES
+#define TEST_HAS_VARIADIC_TEMPLATES
+#define TEST_HAS_INITIALIZER_LISTS
+#define TEST_HAS_BASIC_CONSTEXPR
+#endif
+
+/* Features that were introduced in C++14 */
+#if TEST_STD_VER >= 14
+#define TEST_HAS_EXTENDED_CONSTEXPR
+#define TEST_HAS_VARIABLE_TEMPLATES
+#endif
+
+/* Features that were introduced after C++14 */
+#if TEST_STD_VER > 14
+#endif
+
+#if TEST_HAS_EXTENSION(cxx_decltype) || TEST_STD_VER >= 11
+#define TEST_DECLTYPE(T) decltype(T)
+#else
+#define TEST_DECLTYPE(T) __typeof__(T)
+#endif
+
+#if TEST_STD_VER >= 11
+#define TEST_NOEXCEPT noexcept
+#else
+#define TEST_NOEXCEPT
+#endif
+
+#if TEST_HAS_EXTENSION(cxx_static_assert) || TEST_STD_VER >= 11
+#  define TEST_STATIC_ASSERT(Expr, Msg) static_assert(Expr, Msg)
+#else
+#  define TEST_STATIC_ASSERT(Expr, Msg)                          \
+      typedef ::test_detail::static_assert_check<sizeof(         \
+          ::test_detail::static_assert_incomplete_test<(Expr)>)> \
+    TEST_CONCAT(test_assert, __LINE__)
+#
+#endif
+
+namespace test_detail {
+
+template <bool> struct static_assert_incomplete_test;
+template <> struct static_assert_incomplete_test<true> {};
+template <unsigned> struct static_assert_check {};
+
+} // end namespace test_detail
+
+
+#if !TEST_HAS_FEATURE(cxx_rtti) && !defined(__cxx_rtti)
+#define TEST_HAS_NO_RTTI
+#endif
+
+#if !TEST_HAS_FEATURE(cxx_exceptions) && !defined(__cxx_exceptions)
+#define TEST_HAS_NO_EXCEPTIONS
+#endif
+
+#endif // SUPPORT_TEST_MACROS_HPP
diff --git a/test/support/tracked_value.h b/test/support/tracked_value.h
new file mode 100644
index 0000000..b0869b2
--- /dev/null
+++ b/test/support/tracked_value.h
@@ -0,0 +1,50 @@
+#ifndef SUPPORT_TRACKED_VALUE_H
+#define SUPPORT_TRACKED_VALUE_H
+
+#include <cassert>
+
+struct TrackedValue {
+    enum State { CONSTRUCTED, MOVED_FROM, DESTROYED };
+    State state;
+
+    TrackedValue() : state(State::CONSTRUCTED) {}
+
+    TrackedValue(TrackedValue const& t) : state(State::CONSTRUCTED) {
+        assert(t.state != State::MOVED_FROM && "copying a moved-from object");
+        assert(t.state != State::DESTROYED  && "copying a destroyed object");
+    }
+
+#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+    TrackedValue(TrackedValue&& t) : state(State::CONSTRUCTED) {
+        assert(t.state != State::MOVED_FROM && "double moving from an object");
+        assert(t.state != State::DESTROYED  && "moving from a destroyed object");
+        t.state = State::MOVED_FROM;
+    }
+#endif
+
+    TrackedValue& operator=(TrackedValue const& t) {
+        assert(state != State::DESTROYED && "copy assigning into destroyed object");
+        assert(t.state != State::MOVED_FROM && "copying a moved-from object");
+        assert(t.state != State::DESTROYED  && "copying a destroyed object");
+        state = t.state;
+        return *this;
+    }
+
+#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+    TrackedValue& operator=(TrackedValue&& t) {
+        assert(state != State::DESTROYED && "move assigning into destroyed object");
+        assert(t.state != State::MOVED_FROM && "double moving from an object");
+        assert(t.state != State::DESTROYED  && "moving from a destroyed object");
+        state = t.state;
+        t.state = State::MOVED_FROM;
+        return *this;
+    }
+#endif
+
+    ~TrackedValue() {
+        assert(state != State::DESTROYED && "double-destroying an object");
+        state = State::DESTROYED;
+    }
+};
+
+#endif // SUPPORT_TRACKED_VALUE_H
diff --git a/utils/sym_check/linux_blacklist.txt b/utils/sym_check/linux_blacklist.txt
new file mode 100644
index 0000000..4d9d1d4
--- /dev/null
+++ b/utils/sym_check/linux_blacklist.txt
@@ -0,0 +1,19 @@
+# all guard variables
+_ZGVNSt3__
+# all vtables
+_ZTV
+# all VTT
+_ZTT
+# all non-virtual thunks
+_ZTh
+# all virtual thunks
+_ZTv
+# typeinfo for std::__1::__types
+#    There are no std::__types
+_ZTINSt3__1[0-9][0-9]*__
+# typeinfo name for std::__1::__types
+_ZTSNSt3__1[0-9][0-9]*__
+# anything using __hidden_allocator
+.*__hidden_allocator
+# anything using __sso_allocator
+.*__sso_allocator
diff --git a/utils/sym_check/osx_blacklist.txt b/utils/sym_check/osx_blacklist.txt
new file mode 100644
index 0000000..cfa911e
--- /dev/null
+++ b/utils/sym_check/osx_blacklist.txt
@@ -0,0 +1,19 @@
+# all guard variables
+__ZGVNSt3__
+# all vtables
+__ZTV
+# all VTT
+__ZTT
+# all non-virtual thunks
+__ZTh
+# all virtual thunks
+__ZTv
+# typeinfo for std::__1::__types
+#    There are no std::__types
+__ZTINSt3__1[0-9][0-9]*__
+# typeinfo name for std::__1::__types
+__ZTSNSt3__1[0-9][0-9]*__
+# anything using __hidden_allocator
+.*__hidden_allocator
+# anything using __sso_allocator
+.*__sso_allocator
diff --git a/utils/sym_check/sym_check/__init__.py b/utils/sym_check/sym_check/__init__.py
new file mode 100644
index 0000000..3c66803
--- /dev/null
+++ b/utils/sym_check/sym_check/__init__.py
@@ -0,0 +1,8 @@
+"""libcxx abi symbol checker"""
+
+__author__ = 'Eric Fiselier'
+__email__ = 'eric@efcs.ca'
+__versioninfo__ = (0, 1, 0)
+__version__ = ' '.join(str(v) for v in __versioninfo__) + 'dev'
+
+__all__ = ['diff', 'extract', 'util']
diff --git a/utils/sym_check/sym_check/diff.py b/utils/sym_check/sym_check/diff.py
new file mode 100644
index 0000000..a16e54d
--- /dev/null
+++ b/utils/sym_check/sym_check/diff.py
@@ -0,0 +1,93 @@
+# -*- Python -*- vim: set syntax=python tabstop=4 expandtab cc=80:
+"""
+diff - A set of functions for diff-ing two symbol lists.
+"""
+
+from sym_check import util
+
+
+def _symbol_difference(lhs, rhs):
+    lhs_names = set((n['name'] for n in lhs))
+    rhs_names = set((n['name'] for n in rhs))
+    diff_names = lhs_names - rhs_names
+    return [n for n in lhs if n['name'] in diff_names]
+
+
+def _find_by_key(sym_list, k):
+    for sym in sym_list:
+        if sym['name'] == k:
+            return sym
+    return None
+
+
+def added_symbols(old, new):
+    return _symbol_difference(new, old)
+
+
+def removed_symbols(old, new):
+    return _symbol_difference(old, new)
+
+
+def changed_symbols(old, new):
+    changed = []
+    for old_sym in old:
+        if old_sym in new:
+            continue
+        new_sym = _find_by_key(new, old_sym['name'])
+        if (new_sym is not None and not new_sym in old
+                and cmp(old_sym, new_sym) != 0):
+            changed += [(old_sym, new_sym)]
+    return changed
+
+
+def diff(old, new):
+    added = added_symbols(old, new)
+    removed = removed_symbols(old, new)
+    changed = changed_symbols(old, new)
+    return added, removed, changed
+
+
+def report_diff(added_syms, removed_syms, changed_syms, names_only=False,
+                demangle=True):
+    def maybe_demangle(name):
+        return util.demangle_symbol(name) if demangle else name
+
+    report = ''
+    for sym in added_syms:
+        report += 'Symbol added: %s\n' % maybe_demangle(sym['name'])
+        if not names_only:
+            report += '    %s\n\n' % sym
+    if added_syms and names_only:
+        report += '\n'
+    for sym in removed_syms:
+        report += 'SYMBOL REMOVED: %s\n' % maybe_demangle(sym['name'])
+        if not names_only:
+            report += '    %s\n\n' % sym
+    if removed_syms and names_only:
+        report += '\n'
+    if not names_only:
+        for sym_pair in changed_syms:
+            old_sym, new_sym = sym_pair
+            old_str = '\n    OLD SYMBOL: %s' % old_sym
+            new_str = '\n    NEW SYMBOL: %s' % new_sym
+            report += ('SYMBOL CHANGED: %s%s%s\n\n' %
+                       (maybe_demangle(old_sym['name']),
+                        old_str, new_str))
+
+    added = bool(len(added_syms) != 0)
+    abi_break = bool(len(removed_syms))
+    if not names_only:
+        abi_break = abi_break or len(changed_syms)
+    if added or abi_break:
+        report += 'Summary\n'
+        report += '    Added:   %d\n' % len(added_syms)
+        report += '    Removed: %d\n' % len(removed_syms)
+        if not names_only:
+            report += '    Changed: %d\n' % len(changed_syms)
+        if not abi_break:
+            report += 'Symbols added.'
+        else:
+            report += 'ABI BREAKAGE: SYMBOLS ADDED OR REMOVED!'
+    else:
+        report += 'Symbols match.'
+    return report, int(abi_break)
diff --git a/utils/sym_check/sym_check/extract.py b/utils/sym_check/sym_check/extract.py
new file mode 100644
index 0000000..b4f4cee
--- /dev/null
+++ b/utils/sym_check/sym_check/extract.py
@@ -0,0 +1,177 @@
+# -*- Python -*- vim: set syntax=python tabstop=4 expandtab cc=80:
+"""
+extract - A set of function that extract symbol lists from shared libraries.
+"""
+import distutils.spawn
+import sys
+
+from sym_check import util
+
+
+class NMExtractor(object):
+    """
+    NMExtractor - Extract symbol lists from libraries using nm.
+    """
+
+    @staticmethod
+    def find_tool():
+        """
+        Search for the nm executable and return the path.
+        """
+        return distutils.spawn.find_executable('nm')
+
+    def __init__(self):
+        """
+        Initialize the nm executable and flags that will be used to extract
+        symbols from shared libraries.
+        """
+        self.nm_exe = self.find_tool()
+        if self.nm_exe is None:
+            # ERROR no NM found
+            print("ERROR: Could not find nm")
+            sys.exit(1)
+        self.flags = ['-P', '-g']
+
+    def extract(self, lib):
+        """
+        Extract symbols from a library and return the results as a dict of
+        parsed symbols.
+        """
+        cmd = [self.nm_exe] + self.flags + [lib]
+        out, _, exit_code = util.execute_command_verbose(cmd)
+        if exit_code != 0:
+            raise RuntimeError('Failed to run %s on %s' % (self.nm_exe, lib))
+        fmt_syms = (self._extract_sym(l)
+                    for l in out.splitlines() if l.strip())
+            # Cast symbol to string.
+        final_syms = (repr(s) for s in fmt_syms if self._want_sym(s))
+        # Make unique and sort strings.
+        tmp_list = list(sorted(set(final_syms)))
+        # Cast string back to symbol.
+        return util.read_syms_from_list(tmp_list)
+
+    def _extract_sym(self, sym_str):
+        bits = sym_str.split()
+        # Everything we want has at least two columns.
+        if len(bits) < 2:
+            return None
+        new_sym = {
+            'name': bits[0],
+            'type': bits[1]
+        }
+        new_sym['name'] = new_sym['name'].replace('@@', '@')
+        new_sym = self._transform_sym_type(new_sym)
+        # NM types which we want to save the size for.
+        if new_sym['type'] == 'OBJECT' and len(bits) > 3:
+            new_sym['size'] = int(bits[3], 16)
+        return new_sym
+
+    @staticmethod
+    def _want_sym(sym):
+        """
+        Check that s is a valid symbol that we want to keep.
+        """
+        if sym is None or len(sym) < 2:
+            return False
+        bad_types = ['t', 'b', 'r', 'd', 'w']
+        return (sym['type'] not in bad_types
+                and sym['name'] not in ['__bss_start', '_end', '_edata'])
+
+    @staticmethod
+    def _transform_sym_type(sym):
+        """
+        Map the nm single letter output for type to either FUNC or OBJECT.
+        If the type is not recognized it is left unchanged.
+        """
+        func_types = ['T', 'W']
+        obj_types = ['B', 'D', 'R', 'V', 'S']
+        if sym['type'] in func_types:
+            sym['type'] = 'FUNC'
+        elif sym['type'] in obj_types:
+            sym['type'] = 'OBJECT'
+        return sym
+
+class ReadElfExtractor(object):
+    """
+    ReadElfExtractor - Extract symbol lists from libraries using readelf.
+    """
+
+    @staticmethod
+    def find_tool():
+        """
+        Search for the readelf executable and return the path.
+        """
+        return distutils.spawn.find_executable('readelf')
+
+    def __init__(self):
+        """
+        Initialize the readelf executable and flags that will be used to
+        extract symbols from shared libraries.
+        """
+        self.tool = self.find_tool()
+        if self.tool is None:
+            # ERROR no NM found
+            print("ERROR: Could not find readelf")
+            sys.exit(1)
+        self.flags = ['--wide', '--symbols']
+
+    def extract(self, lib):
+        """
+        Extract symbols from a library and return the results as a dict of
+        parsed symbols.
+        """
+        cmd = [self.tool] + self.flags + [lib]
+        out, _, exit_code = util.execute_command_verbose(cmd)
+        if exit_code != 0:
+            raise RuntimeError('Failed to run %s on %s' % (self.nm_exe, lib))
+        dyn_syms = self.get_dynsym_table(out)
+        return self.process_syms(dyn_syms)
+
+    def process_syms(self, sym_list):
+        new_syms = []
+        for s in sym_list:
+            parts = s.split()
+            if not parts:
+                continue
+            assert len(parts) == 7 or len(parts) == 8 or len(parts) == 9
+            if len(parts) == 7:
+                continue
+            new_sym = {
+                'name': parts[7],
+                'size': int(parts[2]),
+                'type': parts[3],
+            }
+            assert new_sym['type'] in ['OBJECT', 'FUNC', 'NOTYPE']
+            if new_sym['type'] == 'NOTYPE':
+                continue
+            if new_sym['type'] == 'FUNC':
+                del new_sym['size']
+            new_syms += [new_sym]
+        return new_syms
+
+    def get_dynsym_table(self, out):
+        lines = out.splitlines()
+        start = -1
+        end = -1
+        for i in range(len(lines)):
+            if lines[i].startswith("Symbol table '.dynsym'"):
+                start = i + 2
+            if start != -1 and end == -1 and not lines[i].strip():
+                end = i + 1
+        assert start != -1
+        if end == -1:
+            end = len(lines)
+        return lines[start:end]
+
+
+def extract_symbols(lib_file):
+    """
+    Extract and return a list of symbols extracted from a dynamic library.
+    The symbols are extracted using NM. They are then filtered and formated.
+    Finally they symbols are made unique.
+    """
+    if ReadElfExtractor.find_tool():
+        extractor = ReadElfExtractor()
+    else:
+        extractor = NMExtractor()
+    return extractor.extract(lib_file)
diff --git a/utils/sym_check/sym_check/match.py b/utils/sym_check/sym_check/match.py
new file mode 100644
index 0000000..9f49642
--- /dev/null
+++ b/utils/sym_check/sym_check/match.py
@@ -0,0 +1,32 @@
+# -*- Python -*- vim: set syntax=python tabstop=4 expandtab cc=80:
+"""
+match - A set of functions for matching symbols in a list to a list of regexs
+"""
+
+import re
+
+
+def find_and_report_matching(symbol_list, regex_list):
+    report = ''
+    found_count = 0
+    for regex_str in regex_list:
+        report += 'Matching regex "%s":\n' % regex_str
+        matching_list = find_matching_symbols(symbol_list, regex_str)
+        if not matching_list:
+            report += '    No matches found\n\n'
+            continue
+        # else
+        found_count += len(matching_list)
+        for m in matching_list:
+            report += '    MATCHES: %s\n' % m['name']
+        report += '\n'
+    return found_count, report
+
+
+def find_matching_symbols(symbol_list, regex_str):
+    regex = re.compile(regex_str)
+    matching_list = []
+    for s in symbol_list:
+        if regex.match(s['name']):
+            matching_list += [s]
+    return matching_list
diff --git a/utils/sym_check/sym_check/util.py b/utils/sym_check/sym_check/util.py
new file mode 100644
index 0000000..1d3b424
--- /dev/null
+++ b/utils/sym_check/sym_check/util.py
@@ -0,0 +1,128 @@
+import ast
+import distutils.spawn
+import signal
+import subprocess
+import sys
+
+
+def execute_command(cmd, input_str=None):
+    """
+    Execute a command, capture and return its output.
+    """
+    kwargs = {
+        'stdin': subprocess.PIPE,
+        'stdout': subprocess.PIPE,
+        'stderr': subprocess.PIPE,
+    }
+    p = subprocess.Popen(cmd, **kwargs)
+    out, err = p.communicate(input=input_str)
+    exitCode = p.wait()
+    if exitCode == -signal.SIGINT:
+        raise KeyboardInterrupt
+    return out, err, exitCode
+
+
+def execute_command_verbose(cmd, input_str=None):
+    """
+    Execute a command and print its output on failure.
+    """
+    out, err, exitCode = execute_command(cmd, input_str=input_str)
+    if exitCode != 0:
+        report = "Command: %s\n" % ' '.join(["'%s'" % a for a in cmd])
+        report += "Exit Code: %d\n" % exitCode
+        if out:
+            report += "Standard Output:\n--\n%s--" % out
+        if err:
+            report += "Standard Error:\n--\n%s--" % err
+        report += "\n\nFailed!"
+        sys.stderr.write('%s\n' % report)
+    return out, err, exitCode
+
+
+def read_syms_from_list(slist):
+    """
+    Read a list of symbols from a list of strings.
+    Each string is one symbol.
+    """
+    return [ast.literal_eval(l) for l in slist]
+
+
+def read_syms_from_file(filename):
+    """
+    Read a list of symbols in from a file.
+    """
+    with open(filename, 'r') as f:
+        data = f.read()
+    return read_syms_from_list(data.splitlines())
+
+
+def read_blacklist(filename):
+    with open(filename, 'r') as f:
+        data = f.read()
+    lines = [l.strip() for l in data.splitlines() if l.strip()]
+    lines = [l for l in lines if not l.startswith('#')]
+    return lines
+
+
+def write_syms(sym_list, out=None, names_only=False):
+    """
+    Write a list of symbols to the file named by out.
+    """
+    out_str = ''
+    out_list = sym_list
+    if names_only:
+        out_list = [sym['name'] for sym in sym_list]
+        out_list.sort()
+    for sym in out_list:
+        out_str += '%s\n' % sym
+    if out is None:
+        sys.stdout.write(out_str)
+    else:
+        with open(out, 'w') as f:
+            f.write(out_str)
+
+
+_cppfilt_exe = distutils.spawn.find_executable('c++filt')
+
+
+def demangle_symbol(symbol):
+    if _cppfilt_exe is None:
+        return symbol
+    out, _, exit_code = execute_command_verbose(
+        [_cppfilt_exe], input_str=symbol)
+    if exit_code != 0:
+        return symbol
+    return out
+
+
+def is_elf(filename):
+    with open(filename, 'r') as f:
+        magic_bytes = f.read(4)
+    return magic_bytes == '\x7fELF'
+
+
+def is_mach_o(filename):
+    with open(filename, 'r') as f:
+        magic_bytes = f.read(4)
+    return magic_bytes in [
+        '\xfe\xed\xfa\xce',  # MH_MAGIC
+        '\xce\xfa\xed\xfe',  # MH_CIGAM
+        '\xfe\xed\xfa\xcf',  # MH_MAGIC_64
+        '\xcf\xfa\xed\xfe',  # MH_CIGAM_64
+        '\xca\xfe\xba\xbe',  # FAT_MAGIC
+        '\xbe\xba\xfe\xca'   # FAT_CIGAM
+    ]
+
+
+def is_library_file(filename):
+    if sys.platform == 'darwin':
+        return is_mach_o(filename)
+    else:
+        return is_elf(filename)
+
+
+def extract_or_load(filename):
+    import sym_check.extract
+    if is_library_file(filename):
+        return sym_check.extract.extract_symbols(filename)
+    return read_syms_from_file(filename)
diff --git a/utils/sym_check/sym_diff.py b/utils/sym_check/sym_diff.py
new file mode 100755
index 0000000..054c6c1
--- /dev/null
+++ b/utils/sym_check/sym_diff.py
@@ -0,0 +1,47 @@
+#!/usr/bin/env python
+"""
+sym_diff - Compare two symbol lists and output the differences.
+"""
+from argparse import ArgumentParser
+import sys
+from sym_check import diff, util
+
+
+def main():
+    parser = ArgumentParser(
+        description='Extract a list of symbols from a shared library.')
+    parser.add_argument(
+        '--names-only', dest='names_only',
+        help='Only print symbol names',
+        action='store_true', default=False)
+    parser.add_argument(
+        '-o', '--output', dest='output',
+        help='The output file. stdout is used if not given',
+        type=str, action='store', default=None)
+    parser.add_argument(
+        '--demangle', dest='demangle', action='store_true', default=False)
+    parser.add_argument(
+        'old_syms', metavar='old-syms', type=str,
+        help='The file containing the old symbol list or a library')
+    parser.add_argument(
+        'new_syms', metavar='new-syms', type=str,
+        help='The file containing the new symbol list or a library')
+    args = parser.parse_args()
+
+    old_syms_list = util.extract_or_load(args.old_syms)
+    new_syms_list = util.extract_or_load(args.new_syms)
+
+    added, removed, changed = diff.diff(old_syms_list, new_syms_list)
+    report, is_break = diff.report_diff(added, removed, changed,
+                                        names_only=args.names_only,
+                                        demangle=args.demangle)
+    if args.output is None:
+        print(report)
+    else:
+        with open(args.output, 'w') as f:
+            f.write(report + '\n')
+    sys.exit(is_break)
+
+
+if __name__ == '__main__':
+    main()
diff --git a/utils/sym_check/sym_extract.py b/utils/sym_check/sym_extract.py
new file mode 100755
index 0000000..5d89539
--- /dev/null
+++ b/utils/sym_check/sym_extract.py
@@ -0,0 +1,29 @@
+#!/usr/bin/env python
+"""
+sym_extract - Extract and output a list of symbols from a shared library.
+"""
+from argparse import ArgumentParser
+from sym_check import extract, util
+
+
+def main():
+    parser = ArgumentParser(
+        description='Extract a list of symbols from a shared library.')
+    parser.add_argument('library', metavar='shared-lib', type=str,
+                        help='The library to extract symbols from')
+    parser.add_argument('-o', '--output', dest='output',
+                        help='The output file. stdout is used if not given',
+                        type=str, action='store', default=None)
+    parser.add_argument('--names-only', dest='names_only',
+                        help='Output only the name of the symbol',
+                        action='store_true', default=False)
+    args = parser.parse_args()
+    if args.output is not None:
+        print('Extracting symbols from %s to %s.'
+              % (args.library, args.output))
+    syms = extract.extract_symbols(args.library)
+    util.write_syms(syms, out=args.output, names_only=args.names_only)
+
+
+if __name__ == '__main__':
+    main()
diff --git a/utils/sym_check/sym_match.py b/utils/sym_check/sym_match.py
new file mode 100755
index 0000000..c60b246
--- /dev/null
+++ b/utils/sym_check/sym_match.py
@@ -0,0 +1,42 @@
+#!/usr/bin/env python
+"""
+sym_match - Match all symbols in a list against a list of regexes.
+"""
+from argparse import ArgumentParser
+import sys
+from sym_check import util, match, extract
+
+
+def main():
+    parser = ArgumentParser(
+        description='Extract a list of symbols from a shared library.')
+    parser.add_argument(
+        '--blacklist', dest='blacklist',
+        type=str, action='store', default=None)
+    parser.add_argument(
+        'symbol_list', metavar='symbol_list', type=str,
+        help='The file containing the old symbol list')
+    parser.add_argument(
+        'regexes', metavar='regexes', default=[], nargs='*',
+        help='The file containing the new symbol list or a library')
+    args = parser.parse_args()
+
+    if not args.regexes and args.blacklist is None:
+        sys.stderr.write('Either a regex or a blacklist must be specified.\n')
+        sys.exit(1)
+    if args.blacklist:
+        search_list = util.read_blacklist(args.blacklist)
+    else:
+        search_list = args.regexes
+
+    symbol_list = util.extract_or_load(args.symbol_list)
+
+    matching_count, report = match.find_and_report_matching(
+        symbol_list, search_list)
+    sys.stdout.write(report)
+    if matching_count != 0:
+        print('%d matching symbols found...' % matching_count)
+
+
+if __name__ == '__main__':
+    main()
diff --git a/www/atomic_design.html b/www/atomic_design.html
index 2314841..67021b8 100644
--- a/www/atomic_design.html
+++ b/www/atomic_design.html
@@ -22,8 +22,8 @@
 
   <div class="submenu">
     <label>Quick Links</label>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev">cfe-dev</a>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits">cfe-commits</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-dev">cfe-dev</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-commits">cfe-commits</a>
     <a href="http://llvm.org/bugs/">Bug Reports</a>
     <a href="http://llvm.org/svn/llvm-project/libcxx/trunk/">Browse SVN</a>
     <a href="http://llvm.org/viewvc/llvm-project/libcxx/trunk/">Browse ViewVC</a>
diff --git a/www/atomic_design_a.html b/www/atomic_design_a.html
index b329fd1..8e9fef2 100644
--- a/www/atomic_design_a.html
+++ b/www/atomic_design_a.html
@@ -22,8 +22,8 @@
 
   <div class="submenu">
     <label>Quick Links</label>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev">cfe-dev</a>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits">cfe-commits</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-dev">cfe-dev</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-commits">cfe-commits</a>
     <a href="http://llvm.org/bugs/">Bug Reports</a>
     <a href="http://llvm.org/svn/llvm-project/libcxx/trunk/">Browse SVN</a>
     <a href="http://llvm.org/viewvc/llvm-project/libcxx/trunk/">Browse ViewVC</a>
diff --git a/www/atomic_design_b.html b/www/atomic_design_b.html
index b738445..17ba9b3 100644
--- a/www/atomic_design_b.html
+++ b/www/atomic_design_b.html
@@ -22,8 +22,8 @@
 
   <div class="submenu">
     <label>Quick Links</label>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev">cfe-dev</a>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits">cfe-commits</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-dev">cfe-dev</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-commits">cfe-commits</a>
     <a href="http://llvm.org/bugs/">Bug Reports</a>
     <a href="http://llvm.org/svn/llvm-project/libcxx/trunk/">Browse SVN</a>
     <a href="http://llvm.org/viewvc/llvm-project/libcxx/trunk/">Browse ViewVC</a>
diff --git a/www/atomic_design_c.html b/www/atomic_design_c.html
index f574d4d..9c92b88 100644
--- a/www/atomic_design_c.html
+++ b/www/atomic_design_c.html
@@ -22,8 +22,8 @@
 
   <div class="submenu">
     <label>Quick Links</label>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev">cfe-dev</a>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits">cfe-commits</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-dev">cfe-dev</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-commits">cfe-commits</a>
     <a href="http://llvm.org/bugs/">Bug Reports</a>
     <a href="http://llvm.org/svn/llvm-project/libcxx/trunk/">Browse SVN</a>
     <a href="http://llvm.org/viewvc/llvm-project/libcxx/trunk/">Browse ViewVC</a>
diff --git a/www/cxx1y_status.html b/www/cxx1y_status.html
index ce7f216..2b9c05a 100644
--- a/www/cxx1y_status.html
+++ b/www/cxx1y_status.html
@@ -22,8 +22,8 @@
 
   <div class="submenu">
     <label>Quick Links</label>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev">cfe-dev</a>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits">cfe-commits</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-dev">cfe-dev</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-commits">cfe-commits</a>
     <a href="http://llvm.org/bugs/">Bug Reports</a>
     <a href="http://llvm.org/svn/llvm-project/libcxx/trunk/">Browse SVN</a>
     <a href="http://llvm.org/viewvc/llvm-project/libcxx/trunk/">Browse ViewVC</a>
diff --git a/www/cxx1z_status.html b/www/cxx1z_status.html
index 16b16f7..4369810 100644
--- a/www/cxx1z_status.html
+++ b/www/cxx1z_status.html
@@ -22,8 +22,8 @@
 
   <div class="submenu">
     <label>Quick Links</label>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev">cfe-dev</a>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits">cfe-commits</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-dev">cfe-dev</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-commits">cfe-commits</a>
     <a href="http://llvm.org/bugs/">Bug Reports</a>
     <a href="http://llvm.org/svn/llvm-project/libcxx/trunk/">Browse SVN</a>
     <a href="http://llvm.org/viewvc/llvm-project/libcxx/trunk/">Browse ViewVC</a>
@@ -54,14 +54,21 @@
 -->
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n3911">N3911</a></td><td>LWG</td></td><td>TransformationTrait Alias <code>void_t</code>.</td><td>Urbana</td><td>Complete</td><td>3.6</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4089">N4089</a></td><td>LWG</td></td><td>Safe conversions in <code>unique_ptr&lt;T[]&gt;</code>.</td><td>Urbana</td><td></td><td></td></tr>
-	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4169">N4169</a></td><td>LWG</td></td><td>A proposal to add invoke function template</td><td>Urbana</td><td></td><td></td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4169">N4169</a></td><td>LWG</td></td><td>A proposal to add invoke function template</td><td>Urbana</td><td>Complete</td><td>3.7</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4190">N4190</a></td></td><td>LWG</td><td>Removing auto_ptr, random_shuffle(), And Old <functional> Stuff.</td><td>Urbana</td><td></td><td></td></tr>
-	<tr><td><a href="http://wiki.edg.com/twiki/pub/Wg21urbana-champaign/StrawPolls/n4258.pdf">N4258</a></td><td>LWG</td></td><td>Cleaning-up noexcept in the Library.</td><td>Urbana</td><td></td><td></td></tr>
-	<tr><td><a href="http://wiki.edg.com/twiki/pub/Wg21urbana-champaign/StrawPolls/N4277.html">N4277</a></td><td>LWG</td></td><td>TriviallyCopyable <code>reference_wrapper</code>.</td><td>Urbana</td><td>Complete</td><td>3.2</td></tr>
-	<tr><td><a href="http://wiki.edg.com/twiki/pub/Wg21urbana-champaign/StrawPolls/n4279.html">N4279</a></td><td>LWG</td></td><td>Improved insertion interface for unique-key maps.</td><td>Urbana</td><td></td><td></td></tr>
-	<tr><td><a href="http://wiki.edg.com/twiki/pub/Wg21urbana-champaign/StrawPolls/n4280.pdf">N4280</a></td><td>LWG</td></td><td>Non-member size() and more</td><td>Urbana</td><td>Complete</td><td>3.6</td></tr>
-	<tr><td><a href="http://wiki.edg.com/twiki/pub/Wg21urbana-champaign/StrawPolls/n4284.html">N4284</a></td><td>LWG</td></td><td>Contiguous Iterators.</td><td>Urbana</td><td></td><td></td></tr>
-
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4258">N4258</a></td><td>LWG</td></td><td>Cleaning-up noexcept in the Library.</td><td>Urbana</td><td>In progress</td><td>3.7</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4259">N4259</a></td><td>CWG</td></td><td>Wording for std::uncaught_exceptions</td><td>Urbana</td><td>Complete</td><td>3.7</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4277">N4277</a></td><td>LWG</td></td><td>TriviallyCopyable <code>reference_wrapper</code>.</td><td>Urbana</td><td>Complete</td><td>3.2</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4279">N4279</a></td><td>LWG</td></td><td>Improved insertion interface for unique-key maps.</td><td>Urbana</td><td>Complete</td><td>3.7</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4280">N4280</a></td><td>LWG</td></td><td>Non-member size() and more</td><td>Urbana</td><td>Complete</td><td>3.6</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4284">N4284</a></td><td>LWG</td></td><td>Contiguous Iterators.</td><td>Urbana</td><td>Complete</td><td>3.6</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4285">N4285</a></td><td>CWG</td></td><td>Cleanup for exception-specification and throw-expression.</td><td>Urbana</td><td></td><td></td></tr>
+  	<tr><td></td><td></td><td></td><td></td><td></td><td></td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2015/n4387">N4387</a></td><td>LWG</td></td><td>improving pair and tuple</td><td>Lenexa</td><td></td><td></td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2015/n4389">N4389</a></td><td>LWG</td></td><td>bool_constant</td><td>Lenexa</td><td>Complete</td><td>3.7</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2015/n4508">N4508</a></td><td>LWG</td></td><td>shared_mutex for C++17</td><td>Lenexa</td><td>Complete</td><td>3.7</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2015/n4366">N4366</a></td><td>LWG</td></td><td>LWG 2228 missing SFINAE rule</td><td>Lenexa</td><td>Complete</td><td>3.1</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2015/n4510">N4510</a></td><td>LWG</td></td><td>Minimal incomplete type support for standard containers, revision 4</td><td>Lenexa</td><td>Complete</td><td>3.6</td></tr>
 <!--  	<tr><td></td><td></td><td></td><td></td><td></td><td></td></tr> -->
   </table>
 
@@ -71,38 +78,74 @@
 	<tr><th>Issue #</th><th>Issue Name</th><th>Meeting</th><th>Status</th></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2016">2016</a></td><td>Allocators must be no-throw swappable</td><td>Urbana</td><td></td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2376">2118</td><td><code>unique_ptr</code> for array does not support cv qualification conversion of actual argument</td><td>Urbana</td><td>Will be resolved by N4089</td></tr>
-	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2170">2170</a></td><td>Aggregates cannot be <code>DefaultConstructible</code></td><td>Urbana</td><td></td></tr>
-	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2387">2308</td><td>Clarify container destructor requirements w.r.t. <code>std::array</code></td><td>Urbana</td><td>Will be resolved by N4258</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2170">2170</a></td><td>Aggregates cannot be <code>DefaultConstructible</code></td><td>Urbana</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2308">2308</td><td>Clarify container destructor requirements w.r.t. <code>std::array</code></td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2340">2340</a></td><td>Replacement allocation functions declared as inline</td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2354">2354</a></td><td>Unnecessary copying when inserting into maps with braced-init syntax</td><td>Urbana</td><td></td></tr>
-	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2377">2377</a></td><td><code>std::align</code> requirements overly strict</td><td>Urbana</td><td></td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2377">2377</a></td><td><code>std::align</code> requirements overly strict</td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2396">2396</a></td><td><code>underlying_type</code> doesn't say what to do for an incomplete enumeration type</td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2399">2399</a></td><td><code>shared_ptr</code>'s constructor from <code>unique_ptr</code> should be constrained</td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2400">2400</a></td><td><code>shared_ptr</code>'s <code>get_deleter()</code> should use <code>addressof()</code></td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2401">2401</a></td><td><code>std::function</code> needs more noexcept</td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2404">2404</a></td><td><code>mismatch()</code>'s complexity needs to be updated</td><td>Urbana</td><td>Complete</td></tr>
-	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2408">2408</a></td><td>SFINAE-friendly <code>common_type</code> / <code>iterator_traits</code> is missing in C++14</td><td>Urbana</td><td></td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2408">2408</a></td><td>SFINAE-friendly <code>common_type</code> / <code>iterator_traits</code> is missing in C++14</td><td>Urbana</td><td><code>common_type</code> is waiting on <a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2465">LWG#2465</a></td></tr>
  	<tr><td></td><td></td><td></td><td></td></tr>
-
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2106">2106</td><td><code>move_iterator</code> wrapping iterators returning prvalues</td><td>Urbana</td><td></td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2129">2129</td><td>User specializations of <code>std::initializer_list</code></td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2212">2212</td><td><code>tuple_size</code> for <code>const pair</code> request <tuple> header</td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2217">2217</td><td><code>operator==(sub_match, string)</code> slices on embedded '\0's</td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2230">2230</td><td>"see below" for <code>initializer_list</code> constructors of unordered containers</td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2233">2233</td><td><code>bad_function_call::what()</code> unhelpful</td><td>Urbana</td><td>Complete</td></tr>
-	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2266">2266</td><td><code>vector</code> and <code>deque</code> have incorrect insert requirements</td><td>Urbana</td><td></td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2266">2266</td><td><code>vector</code> and <code>deque</code> have incorrect insert requirements</td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2325">2325</td><td><code>minmax_element()</code>'s behavior differing from <code>max_element()</code>'s should be noted</td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2361">2361</td><td>Apply 2299 resolution throughout library</td><td>Urbana</td><td></td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2365">2365</td><td>Missing noexcept in <code>shared_ptr::shared_ptr(nullptr_t)</code></td><td>Urbana</td><td>Complete</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2376">2376</td><td><code>bad_weak_ptr::what()</code> overspecified</td><td>Urbana</td><td>Complete</td></tr>
-	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2387">2387</td><td>More nested types that must be accessible and unambiguous</td><td>Urbana</td><td></td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2387">2387</td><td>More nested types that must be accessible and unambiguous</td><td>Urbana</td><td>Complete</td></tr>
+ 	<tr><td></td><td></td><td></td><td></td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2059">2059</td><td>C++0x ambiguity problem with map::erase</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2063">2063</td><td>Contradictory requirements for string move assignment</td><td>Lenexa</td><td></td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2076">2076</td><td>Bad CopyConstructible requirement in set constructors</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2160">2160</td><td>Unintended destruction ordering-specification of resize</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2168">2168</td><td>Inconsistent specification of uniform_real_distribution constructor</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2239">2239</td><td>min/max/minmax requirements</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2364">2364</td><td>deque and vector pop_back don't specify iterator invalidation requirements</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2369">2369</td><td>constexpr max(initializer_list) vs max_element</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2378">2378</td><td>Behaviour of standard exception types</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2403">2403</td><td>stof() should call strtof() and wcstof()</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2406">2406</td><td>negative_binomial_distribution should reject p == 1</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2407">2407</td><td>packaged_task(allocator_arg_t, const Allocator&, F&&) should neither be constrained nor explicit</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2411">2411</td><td>shared_ptr is only contextually convertible to bool</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2415">2415</td><td>Inconsistency between unique_ptr and shared_ptr</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2420">2420</td><td>function<void(ArgTypes...)> does not discard the return value of the target object</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2425">2425</td><td>operator delete(void*, size_t) doesn't invalidate pointers sufficiently</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2427">2427</td><td>Container adaptors as sequence containers, redux</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2428">2428</td><td>"External declaration" used without being defined</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2433">2433</td><td>uninitialized_copy()/etc. should tolerate overloaded operator&</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2434">2434</td><td>shared_ptr::use_count() is efficient</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2437">2437</td><td>iterator_traits::reference can and can't be void</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2438">2438</td><td>std::iterator inheritance shouldn't be mandated</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2439">2439</td><td>unique_copy() sometimes can't fall back to reading its output</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2440">2440</td><td>seed_seq::size() should be noexcept</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2442">2442</td><td>call_once() shouldn't DECAY_COPY()</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2448">2448</td><td>Non-normative Container destructor specification</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2454">2454</td><td>Add raw_storage_iterator::base() member</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2455">2455</td><td>Allocator default construction should be allowed to throw</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2458">2458</td><td>N3778 and new library deallocation signatures</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2459">2459</td><td>std::polar should require a non-negative rho</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2464">2464</td><td>try_emplace and insert_or_assign misspecified</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2467">2467</td><td>is_always_equal has slightly inconsistent default</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2470">2470</td><td>Allocator's destroy function should be allowed to fail to instantiate</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2482">2482</td><td>[c.strings] Table 73 mentions nonexistent functions</td><td>Lenexa</td><td>Complete</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2488">2488</td><td>Placeholders should be allowed and encouraged to be constexpr</td><td>Lenexa</td><td></td></tr>
+
 <!--
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#1214">1214</a></td><td>Insufficient/inconsistent key immutability requirements for associative containers</td><td>Urbana</td><td></td></tr>
 -->
 <!-- 	<tr><td></td><td></td><td></td><td></td></tr> -->
   </table>
 
-  <p>Last Updated: 18-Nov-2014</p>
+  <p>Last Updated: 27-May-2015</p>
 </div>
 </body>
 </html>
diff --git a/www/index.html b/www/index.html
index c608183..798d0c8 100644
--- a/www/index.html
+++ b/www/index.html
@@ -22,8 +22,8 @@
 
   <div class="submenu">
     <label>Quick Links</label>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev">cfe-dev</a>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits">cfe-commits</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-dev">cfe-dev</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-commits">cfe-commits</a>
     <a href="http://llvm.org/bugs/">Bug Reports</a>
     <a href="http://llvm.org/svn/llvm-project/libcxx/trunk/">Browse SVN</a>
     <a href="http://llvm.org/viewvc/llvm-project/libcxx/trunk/">Browse ViewVC</a>
@@ -184,26 +184,30 @@
 
   <p>In-tree build:</p>
   <ul>
+    <li><code>cd where-you-want-to-live</code></li>
     <li>Check out libcxx and <a href="http://libcxxabi.llvm.org/">libcxxabi</a>
       into llvm/projects</li>
-    <li><code>cd llvm</code></li>
+    <li><code>cd where-you-want-to-build</code></li>
     <li><code>mkdir build &amp;&amp; cd build</code></li>
-    <li><code>cmake .. # Linux may require -DCMAKE_C_COMPILER=clang
+    <li><code>cmake path/to/llvm # Linux may require -DCMAKE_C_COMPILER=clang
         -DCMAKE_CXX_COMPILER=clang++</code></li>
     <li><code>make cxx</code></li>
   </ul>
 
-  <p>Out-of-tree build:</p>
+  <p>Out-of-tree buildc:</p>
   <ul>
-    <li>Check out libcxx</li>
+    <li><code>cd where-you-want-to-live</code></li>
+    <li>Check out libcxx and llvm</li>
     <li>If not on a Mac, also check out
       <a href="http://libcxxabi.llvm.org/">libcxxabi</a></li>
-    <li><code>cd libcxx</code></li>
+    <li><code>cd where-you-want-to-build</code></li>
     <li><code>mkdir build &amp;&amp; cd build</code></li>
-    <li><code>cmake -DLIBCXX_CXX_ABI=libcxxabi
-        -DLIBCXX_LIBCXXABI_INCLUDE_PATHS=path/to/libcxxabi/include
-        -DLIT_EXECUTABLE=path/to/llvm/utils/lit/lit.py .. # Linux may require
-        -DCMAKE_C_COMPILER=clang -DCMAKE_CXX_COMPILER=clang++</code></li>
+    <li><code>cmake -DLLVM_PATH=path/to/llvm
+        -DLIBCXX_CXX_ABI=libcxxabi
+        -DLIBCXX_CXX_ABI_INCLUDE_PATHS=path/to/libcxxabi/include
+        -DCMAKE_C_COMPILER=clang -DCMAKE_CXX_COMPILER=clang++
+        path/to/libcxx
+    </code></li>
     <li><code>make</code></li>
   </ul>
 
@@ -239,21 +243,30 @@
 
   <p>
     Mac users, remember to be careful when replacing the system's libc++.
-    <strong>Your system will not be able to boot without a funcioning
+    <strong>Your system will not be able to boot without a functioning
     libc++.</strong>
   </p>
 
   <!--=====================================================================-->
-  <h3>Notes</h3>
+  <h3>Notes and Known Issues</h3>
   <!--=====================================================================-->
 
   <p>
-    Building libc++ with <code>-fno-rtti</code> is not supported.  However
-    linking against it with <code>-fno-rtti</code> is supported.
+    <ul>
+      <li>
+        Building libc++ with <code>-fno-rtti</code> is not supported. However
+        linking against it with <code>-fno-rtti</code> is supported.
+      </li>
+      <li>
+        On OS X v10.8 and older the CMake option
+        <code>-DLIBCXX_LIBCPPABI_VERSION=""</code> must be used during
+        configuration.
+      </li>
+    </ul>
   </p>
 
   <p>Send discussions to the
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev">clang mailing list</a>.</p>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-dev">clang mailing list</a>.</p>
 
   <!--=====================================================================-->
   <h2>Using libc++ in your programs</h2>
@@ -321,7 +334,7 @@
   <p>
   If you think you've found a bug in libc++, please report it using
   the <a href="http://llvm.org/bugs">LLVM Bugzilla</a>. If you're not sure, you
-  can post a message to the <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev">cfe-dev</a> 
+  can post a message to the <a href="http://lists.llvm.org/mailman/listinfo/cfe-dev">cfe-dev</a> 
   mailing list or on IRC. Please include "libc++" in your subject.
   </p>
 
@@ -373,7 +386,7 @@
      <ul>
        <li><code>CC=clang CXX=clang++ cmake -G "Unix Makefiles"
                 -DLIBCXX_CXX_ABI=libstdc++
-                -DLIBCXX_LIBSUPCXX_INCLUDE_PATHS="/usr/include/c++/4.7/;/usr/include/c++/4.7/x86_64-linux-gnu/"
+                -DLIBCXX_CXX_ABI_INCLUDE_PATHS="/usr/include/c++/4.7/;/usr/include/c++/4.7/x86_64-linux-gnu/"
                 -DCMAKE_BUILD_TYPE=Release
                 -DCMAKE_INSTALL_PREFIX=/usr
                 &lt;libc++-source-dir&gt;</code></li>
@@ -408,7 +421,7 @@
      <ul>
        <li><code>CC=clang CXX=clang++ cmake -G "Unix Makefiles"
                 -DLIBCXX_CXX_ABI=libcxxrt
-                -DLIBCXX_LIBCXXRT_INCLUDE_PATHS="&lt;libcxxrt-source-dir&gt;/src"
+                -DLIBCXX_CXX_ABI_INCLUDE_PATHS="&lt;libcxxrt-source-dir&gt;/src"
                 -DCMAKE_BUILD_TYPE=Release
                 -DCMAKE_INSTALL_PREFIX=/usr
                 &lt;libc++-source-dir&gt;</code></li>
@@ -450,7 +463,7 @@
     <ul>
     <li><code>CC=clang CXX=clang++ cmake
               -DLIBCXX_CXX_ABI=libc++abi
-              -DLIBCXX_LIBCXXABI_INCLUDE_PATHS="/path/to/libcxxabi/include"
+              -DLIBCXX_CXX_ABI_INCLUDE_PATHS="/path/to/libcxxabi/include"
               -DLIBCXX_CXX_ABI_LIBRARY_PATH="/path/to/libcxxabi-build/lib"
               path/to/libcxx</code></li>
     <li><code>make</code></li>
diff --git a/www/lit_usage.html b/www/lit_usage.html
index c6bfbae..2fcb2d0 100644
--- a/www/lit_usage.html
+++ b/www/lit_usage.html
@@ -37,8 +37,8 @@
 
   <div class="submenu">
     <label>Quick Links</label>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev">cfe-dev</a>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits">cfe-commits</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-dev">cfe-dev</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-commits">cfe-commits</a>
     <a href="http://llvm.org/bugs/">Bug Reports</a>
     <a href="http://llvm.org/svn/llvm-project/libcxx/trunk/">Browse SVN</a>
     <a href="http://llvm.org/viewvc/llvm-project/libcxx/trunk/">Browse ViewVC</a>
diff --git a/www/ts1z_status.html b/www/ts1z_status.html
index d3d29c2..b92f053 100644
--- a/www/ts1z_status.html
+++ b/www/ts1z_status.html
@@ -22,8 +22,8 @@
 
   <div class="submenu">
     <label>Quick Links</label>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev">cfe-dev</a>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits">cfe-commits</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-dev">cfe-dev</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-commits">cfe-commits</a>
     <a href="http://llvm.org/bugs/">Bug Reports</a>
     <a href="http://llvm.org/svn/llvm-project/libcxx/trunk/">Browse SVN</a>
     <a href="http://llvm.org/viewvc/llvm-project/libcxx/trunk/">Browse ViewVC</a>
@@ -47,10 +47,10 @@
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n3940.html">3940</a></td><td>Technical Specification - File System</td><td>File System</td></tr>
 	<tr><td></td><td></td><td></td></tr>
 
-	<tr><td><a href="http://wiki.edg.com/twiki/pub/Wg21urbana-champaign/StrawPolls/n4273.txt">4273</a></td><td>Uniform Container Erasure.</td><td>Library Fundamentals 2</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4273">4273</a></td><td>Uniform Container Erasure.</td><td>Library Fundamentals 2</td></tr>
 	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4061">4061</a></td><td>Greatest Common Divisor and Least Common Multiple.</td><td>Library Fundamentals 2</td></tr>
-	<tr><td><a href="http://wiki.edg.com/twiki/pub/Wg21urbana-champaign/StrawPolls/N4257.htm">4257</a></td><td>Delimited iterators.</td><td>Library Fundamentals 2</td></tr>
-	<tr><td><a href="http://wiki.edg.com/twiki/pub/Wg21urbana-champaign/StrawPolls/N4282.pdf">4282</a></td><td>The World's Dumbest Smart Pointer.</td><td>Library Fundamentals 2</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4257">4257</a></td><td>Delimited iterators.</td><td>Library Fundamentals 2</td></tr>
+	<tr><td><a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4282">4282</a></td><td>The World's Dumbest Smart Pointer.</td><td>Library Fundamentals 2</td></tr>
 	<tr><td></td><td></td><td></td></tr>
 
   </table>
@@ -61,24 +61,23 @@
 	<tr><td>Uses-allocator construction</td><td>Not started</td></tr>
 	<tr><td>Changes to std::shared_ptr and weak_ptr</td><td>Not started</td></tr>
 	<tr><td>Additions to std::function</td><td>Not started</td></tr>
-	<tr><td>Changes to std::common_type</td><td>Not started</td></tr>
-	<tr><td>Changes to std::iterator_traits</td><td>Not started</td></tr>
 	<tr><td>Additions to std::promise</td><td>Not started</td></tr>
 	<tr><td>Additions to std::packaged_task</td><td>Not started</td></tr>
   <tr><td></td><td></td></tr>
 	<tr><td>Class erased_type</td><td>Complete</td></tr>
-	<tr><td>Calling a function with a tuple of arguments</td><td>Implementation in progress</td></tr>
+	<tr><td>Calling a function with a tuple of arguments</td><td>Complete</td></tr>
+	<tr><td>Type traits (_v)</td><td>Complete</td></tr>
 	<tr><td>Other type transformations</td><td>Not started</td></tr>
 	<tr><td>Compile-time Rational Arithmetic</td><td>Implementation in progress</td></tr>
 	<tr><td>Time Utilities</td><td>Complete</td></tr>
 	<tr><td>System Error Support</td><td>Complete</td></tr>
   <tr><td></td><td></td></tr>
-	<tr><td>Searchers</td><td>Not started</td></tr>
+	<tr><td>Searchers</td><td>Implementation in progress</td></tr>
 	<tr><td>Optional Objects</td><td>Initial implementation complete</td></tr>
-	<tr><td>class any</td><td>Implementation in progress</td></tr>
-	<tr><td>string_view</td><td>Implementation in progress</td></tr>
+	<tr><td>class any</td><td>Complete</td></tr>
+	<tr><td>string_view</td><td>Complete</td></tr>
 	<tr><td>memory</td><td>Implementation in progress</td></tr>
-	<tr><td>Algorithms library</td><td>Not started</td></tr>
+	<tr><td>Algorithms library</td><td>Complete</td></tr>
 
   </table>
 
@@ -96,7 +95,7 @@
 
   </table>
 
-  <p>Last Updated: 2-June-2014</p>
+  <p>Last Updated: 21-Jul-2015</p>
 </div>
 </body>
 </html>
diff --git a/www/type_traits_design.html b/www/type_traits_design.html
index ea173a8..422bba4 100644
--- a/www/type_traits_design.html
+++ b/www/type_traits_design.html
@@ -22,8 +22,8 @@
 
   <div class="submenu">
     <label>Quick Links</label>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev">cfe-dev</a>
-    <a href="http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits">cfe-commits</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-dev">cfe-dev</a>
+    <a href="http://lists.llvm.org/mailman/listinfo/cfe-commits">cfe-commits</a>
     <a href="http://llvm.org/bugs/">Bug Reports</a>
     <a href="http://llvm.org/svn/llvm-project/libcxx/trunk/">Browse SVN</a>
     <a href="http://llvm.org/viewvc/llvm-project/libcxx/trunk/">Browse ViewVC</a>