aboutsummaryrefslogtreecommitdiff
path: root/lib/libcxx/src
diff options
context:
space:
mode:
authorAndrew Kelley <andrew@ziglang.org>2021-10-02 10:45:56 -0700
committerAndrew Kelley <andrew@ziglang.org>2021-10-02 10:45:56 -0700
commitdde0adcb363f3a3f306c0fc9eaec511cc3b74965 (patch)
tree9388d039a0b77211936c7264f5a3179f63ad51e6 /lib/libcxx/src
parentc4cd592f0e1eeff5a4056796610d97010ae4e38c (diff)
parent7a2624c3e40e2386a4a8a775b839e1d67608ec42 (diff)
downloadzig-dde0adcb363f3a3f306c0fc9eaec511cc3b74965.tar.gz
zig-dde0adcb363f3a3f306c0fc9eaec511cc3b74965.zip
Merge branch 'llvm13'
Diffstat (limited to 'lib/libcxx/src')
-rw-r--r--lib/libcxx/src/any.cpp6
-rw-r--r--lib/libcxx/src/charconv.cpp4
-rw-r--r--lib/libcxx/src/chrono.cpp31
-rw-r--r--lib/libcxx/src/condition_variable.cpp8
-rw-r--r--lib/libcxx/src/debug.cpp2
-rw-r--r--lib/libcxx/src/experimental/memory_resource.cpp21
-rw-r--r--lib/libcxx/src/filesystem/directory_iterator.cpp10
-rw-r--r--lib/libcxx/src/filesystem/filesystem_common.h201
-rw-r--r--lib/libcxx/src/filesystem/operations.cpp377
-rw-r--r--lib/libcxx/src/filesystem/posix_compat.h521
-rw-r--r--lib/libcxx/src/format.cpp19
-rw-r--r--lib/libcxx/src/functional.cpp4
-rw-r--r--lib/libcxx/src/future.cpp10
-rw-r--r--lib/libcxx/src/include/config_elast.h4
-rw-r--r--lib/libcxx/src/include/refstring.h8
-rw-r--r--lib/libcxx/src/include/sso_allocator.h77
-rw-r--r--lib/libcxx/src/ios.cpp14
-rw-r--r--lib/libcxx/src/locale.cpp167
-rw-r--r--lib/libcxx/src/memory.cpp33
-rw-r--r--lib/libcxx/src/mutex.cpp24
-rw-r--r--lib/libcxx/src/mutex_destructor.cpp2
-rw-r--r--lib/libcxx/src/new.cpp48
-rw-r--r--lib/libcxx/src/optional.cpp8
-rw-r--r--lib/libcxx/src/random.cpp2
-rw-r--r--lib/libcxx/src/string.cpp8
-rw-r--r--lib/libcxx/src/support/ibm/xlocale_zos.cpp137
-rw-r--r--lib/libcxx/src/support/runtime/exception_fallback.ipp50
-rw-r--r--lib/libcxx/src/support/runtime/exception_glibcxx.ipp8
-rw-r--r--lib/libcxx/src/support/runtime/exception_libcxxabi.ipp4
-rw-r--r--lib/libcxx/src/support/runtime/exception_libcxxrt.ipp4
-rw-r--r--lib/libcxx/src/support/runtime/exception_msvc.ipp50
-rw-r--r--lib/libcxx/src/support/runtime/exception_pointer_cxxabi.ipp12
-rw-r--r--lib/libcxx/src/support/runtime/exception_pointer_glibcxx.ipp14
-rw-r--r--lib/libcxx/src/support/runtime/exception_pointer_msvc.ipp24
-rw-r--r--lib/libcxx/src/support/runtime/exception_pointer_unimplemented.ipp12
-rw-r--r--lib/libcxx/src/support/runtime/new_handler_fallback.ipp4
-rw-r--r--lib/libcxx/src/support/runtime/stdexcept_default.ipp30
-rw-r--r--lib/libcxx/src/support/win32/support.cpp5
-rw-r--r--lib/libcxx/src/support/win32/thread_win32.cpp44
-rw-r--r--lib/libcxx/src/system_error.cpp34
-rw-r--r--lib/libcxx/src/thread.cpp4
-rw-r--r--lib/libcxx/src/typeinfo.cpp6
42 files changed, 1504 insertions, 547 deletions
diff --git a/lib/libcxx/src/any.cpp b/lib/libcxx/src/any.cpp
index 0cf0906883..415d23b0c9 100644
--- a/lib/libcxx/src/any.cpp
+++ b/lib/libcxx/src/any.cpp
@@ -9,7 +9,7 @@
#include "any"
namespace std {
-const char* bad_any_cast::what() const _NOEXCEPT {
+const char* bad_any_cast::what() const noexcept {
return "bad any cast";
}
}
@@ -24,10 +24,10 @@ _LIBCPP_BEGIN_NAMESPACE_LFTS
class _LIBCPP_EXCEPTION_ABI _LIBCPP_AVAILABILITY_BAD_ANY_CAST bad_any_cast : public bad_cast
{
public:
- virtual const char* what() const _NOEXCEPT;
+ virtual const char* what() const noexcept;
};
-const char* bad_any_cast::what() const _NOEXCEPT {
+const char* bad_any_cast::what() const noexcept {
return "bad any cast";
}
diff --git a/lib/libcxx/src/charconv.cpp b/lib/libcxx/src/charconv.cpp
index 8cfe40d156..78439f9683 100644
--- a/lib/libcxx/src/charconv.cpp
+++ b/lib/libcxx/src/charconv.cpp
@@ -99,7 +99,7 @@ append8_no_zeros(char* buffer, T v) noexcept
}
char*
-__u32toa(uint32_t value, char* buffer) _NOEXCEPT
+__u32toa(uint32_t value, char* buffer) noexcept
{
if (value < 100000000)
{
@@ -120,7 +120,7 @@ __u32toa(uint32_t value, char* buffer) _NOEXCEPT
}
char*
-__u64toa(uint64_t value, char* buffer) _NOEXCEPT
+__u64toa(uint64_t value, char* buffer) noexcept
{
if (value < 100000000)
{
diff --git a/lib/libcxx/src/chrono.cpp b/lib/libcxx/src/chrono.cpp
index 085fbfde26..13b375947b 100644
--- a/lib/libcxx/src/chrono.cpp
+++ b/lib/libcxx/src/chrono.cpp
@@ -6,9 +6,20 @@
//
//===----------------------------------------------------------------------===//
+#if defined(__MVS__)
+// As part of monotonic clock support on z/OS we need macro _LARGE_TIME_API
+// to be defined before any system header to include definition of struct timespec64.
+#define _LARGE_TIME_API
+#endif
+
#include "chrono"
#include "cerrno" // errno
#include "system_error" // __throw_system_error
+
+#if defined(__MVS__)
+#include <__support/ibm/gettod_zos.h> // gettimeofdayMonotonic
+#endif
+
#include <time.h> // clock_gettime and CLOCK_{MONOTONIC,REALTIME,MONOTONIC_RAW}
#include "include/apple_availability.h"
@@ -20,7 +31,7 @@
# include <sys/time.h> // for gettimeofday and timeval
#endif
-#if !defined(__APPLE__) && _POSIX_TIMERS > 0
+#if !defined(__APPLE__) && defined(_POSIX_TIMERS) && _POSIX_TIMERS > 0
# define _LIBCPP_USE_CLOCK_GETTIME
#endif
@@ -96,19 +107,19 @@ static system_clock::time_point __libcpp_system_clock_now() {
const bool system_clock::is_steady;
system_clock::time_point
-system_clock::now() _NOEXCEPT
+system_clock::now() noexcept
{
return __libcpp_system_clock_now();
}
time_t
-system_clock::to_time_t(const time_point& t) _NOEXCEPT
+system_clock::to_time_t(const time_point& t) noexcept
{
return time_t(duration_cast<seconds>(t.time_since_epoch()).count());
}
system_clock::time_point
-system_clock::from_time_t(time_t t) _NOEXCEPT
+system_clock::from_time_t(time_t t) noexcept
{
return system_clock::time_point(seconds(t));
}
@@ -218,6 +229,16 @@ static steady_clock::time_point __libcpp_steady_clock_now() {
return steady_clock::time_point(steady_clock::duration(dur));
}
+#elif defined(__MVS__)
+
+static steady_clock::time_point __libcpp_steady_clock_now() {
+ struct timespec64 ts;
+ if (0 != gettimeofdayMonotonic(&ts))
+ __throw_system_error(errno, "failed to obtain time of day");
+
+ return steady_clock::time_point(seconds(ts.tv_sec) + nanoseconds(ts.tv_nsec));
+}
+
#elif defined(CLOCK_MONOTONIC)
static steady_clock::time_point __libcpp_steady_clock_now() {
@@ -234,7 +255,7 @@ static steady_clock::time_point __libcpp_steady_clock_now() {
const bool steady_clock::is_steady;
steady_clock::time_point
-steady_clock::now() _NOEXCEPT
+steady_clock::now() noexcept
{
return __libcpp_steady_clock_now();
}
diff --git a/lib/libcxx/src/condition_variable.cpp b/lib/libcxx/src/condition_variable.cpp
index d133b010d7..1e29083e6e 100644
--- a/lib/libcxx/src/condition_variable.cpp
+++ b/lib/libcxx/src/condition_variable.cpp
@@ -24,19 +24,19 @@ _LIBCPP_BEGIN_NAMESPACE_STD
// ~condition_variable is defined elsewhere.
void
-condition_variable::notify_one() _NOEXCEPT
+condition_variable::notify_one() noexcept
{
__libcpp_condvar_signal(&__cv_);
}
void
-condition_variable::notify_all() _NOEXCEPT
+condition_variable::notify_all() noexcept
{
__libcpp_condvar_broadcast(&__cv_);
}
void
-condition_variable::wait(unique_lock<mutex>& lk) _NOEXCEPT
+condition_variable::wait(unique_lock<mutex>& lk) noexcept
{
if (!lk.owns_lock())
__throw_system_error(EPERM,
@@ -48,7 +48,7 @@ condition_variable::wait(unique_lock<mutex>& lk) _NOEXCEPT
void
condition_variable::__do_timed_wait(unique_lock<mutex>& lk,
- chrono::time_point<chrono::system_clock, chrono::nanoseconds> tp) _NOEXCEPT
+ chrono::time_point<chrono::system_clock, chrono::nanoseconds> tp) noexcept
{
using namespace chrono;
if (!lk.owns_lock())
diff --git a/lib/libcxx/src/debug.cpp b/lib/libcxx/src/debug.cpp
index 20055fcf75..dd5963fcce 100644
--- a/lib/libcxx/src/debug.cpp
+++ b/lib/libcxx/src/debug.cpp
@@ -438,7 +438,7 @@ __libcpp_db::__less_than_comparable(const void* __i, const void* __j) const
__i_node* j = __find_iterator(__j);
__c_node* ci = i != nullptr ? i->__c_ : nullptr;
__c_node* cj = j != nullptr ? j->__c_ : nullptr;
- return ci != nullptr && ci == cj;
+ return ci == cj;
}
void
diff --git a/lib/libcxx/src/experimental/memory_resource.cpp b/lib/libcxx/src/experimental/memory_resource.cpp
index 1304ef3df7..ffe8021514 100644
--- a/lib/libcxx/src/experimental/memory_resource.cpp
+++ b/lib/libcxx/src/experimental/memory_resource.cpp
@@ -40,7 +40,7 @@ class _LIBCPP_TYPE_VIS __new_delete_memory_resource_imp
_VSTD::__libcpp_deallocate(p, n, align);
}
- bool do_is_equal(memory_resource const & other) const _NOEXCEPT override
+ bool do_is_equal(memory_resource const & other) const noexcept override
{ return &other == this; }
public:
@@ -60,7 +60,7 @@ protected:
__throw_bad_alloc();
}
virtual void do_deallocate(void *, size_t, size_t) {}
- virtual bool do_is_equal(memory_resource const & __other) const _NOEXCEPT
+ virtual bool do_is_equal(memory_resource const & __other) const noexcept
{ return &__other == this; }
};
@@ -76,28 +76,23 @@ union ResourceInitHelper {
~ResourceInitHelper() {}
};
-// When compiled in C++14 this initialization should be a constant expression.
-// Only in C++11 is "init_priority" needed to ensure initialization order.
-#if _LIBCPP_STD_VER > 11
-_LIBCPP_SAFE_STATIC
-#endif
-ResourceInitHelper res_init _LIBCPP_INIT_PRIORITY_MAX;
+_LIBCPP_SAFE_STATIC ResourceInitHelper res_init _LIBCPP_INIT_PRIORITY_MAX;
} // end namespace
-memory_resource * new_delete_resource() _NOEXCEPT {
+memory_resource * new_delete_resource() noexcept {
return &res_init.resources.new_delete_res;
}
-memory_resource * null_memory_resource() _NOEXCEPT {
+memory_resource * null_memory_resource() noexcept {
return &res_init.resources.null_res;
}
// default_memory_resource()
static memory_resource *
-__default_memory_resource(bool set = false, memory_resource * new_res = nullptr) _NOEXCEPT
+__default_memory_resource(bool set = false, memory_resource * new_res = nullptr) noexcept
{
#ifndef _LIBCPP_HAS_NO_ATOMIC_HEADER
_LIBCPP_SAFE_STATIC static atomic<memory_resource*> __res =
@@ -138,12 +133,12 @@ __default_memory_resource(bool set = false, memory_resource * new_res = nullptr)
#endif
}
-memory_resource * get_default_resource() _NOEXCEPT
+memory_resource * get_default_resource() noexcept
{
return __default_memory_resource();
}
-memory_resource * set_default_resource(memory_resource * __new_res) _NOEXCEPT
+memory_resource * set_default_resource(memory_resource * __new_res) noexcept
{
return __default_memory_resource(true, __new_res);
}
diff --git a/lib/libcxx/src/filesystem/directory_iterator.cpp b/lib/libcxx/src/filesystem/directory_iterator.cpp
index 2721dea5c9..7b83ba9ff1 100644
--- a/lib/libcxx/src/filesystem/directory_iterator.cpp
+++ b/lib/libcxx/src/filesystem/directory_iterator.cpp
@@ -124,7 +124,8 @@ public:
ec = detail::make_windows_error(GetLastError());
const bool ignore_permission_denied =
bool(opts & directory_options::skip_permission_denied);
- if (ignore_permission_denied && ec.value() == ERROR_ACCESS_DENIED)
+ if (ignore_permission_denied &&
+ ec.value() == static_cast<int>(errc::permission_denied))
ec.clear();
return;
}
@@ -272,7 +273,7 @@ directory_iterator& directory_iterator::__increment(error_code* ec) {
path root = move(__imp_->__root_);
__imp_.reset();
if (m_ec)
- err.report(m_ec, "at root \"%s\"", root);
+ err.report(m_ec, "at root " PATH_CSTR_FMT, root.c_str());
}
return *this;
}
@@ -359,7 +360,7 @@ void recursive_directory_iterator::__advance(error_code* ec) {
if (m_ec) {
path root = move(stack.top().__root_);
__imp_.reset();
- err.report(m_ec, "at root \"%s\"", root);
+ err.report(m_ec, "at root " PATH_CSTR_FMT, root.c_str());
} else {
__imp_.reset();
}
@@ -404,7 +405,8 @@ bool recursive_directory_iterator::__try_recursion(error_code* ec) {
} else {
path at_ent = move(curr_it.__entry_.__p_);
__imp_.reset();
- err.report(m_ec, "attempting recursion into \"%s\"", at_ent);
+ err.report(m_ec, "attempting recursion into " PATH_CSTR_FMT,
+ at_ent.c_str());
}
}
return false;
diff --git a/lib/libcxx/src/filesystem/filesystem_common.h b/lib/libcxx/src/filesystem/filesystem_common.h
index e0fdbccf96..60d07059e3 100644
--- a/lib/libcxx/src/filesystem/filesystem_common.h
+++ b/lib/libcxx/src/filesystem/filesystem_common.h
@@ -35,15 +35,17 @@
#endif
#endif
-#if defined(__GNUC__)
+#if defined(__GNUC__) || defined(__clang__)
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wunused-function"
#endif
#if defined(_LIBCPP_WIN32API)
#define PS(x) (L##x)
+#define PATH_CSTR_FMT "\"%ls\""
#else
#define PS(x) (x)
+#define PATH_CSTR_FMT "\"%s\""
#endif
_LIBCPP_BEGIN_NAMESPACE_FILESYSTEM
@@ -57,68 +59,47 @@ errc __win_err_to_errc(int err);
namespace {
-static string format_string_imp(const char* msg, ...) {
- // we might need a second shot at this, so pre-emptivly make a copy
- struct GuardVAList {
- va_list& target;
- bool active = true;
- GuardVAList(va_list& tgt) : target(tgt), active(true) {}
- void clear() {
- if (active)
- va_end(target);
- active = false;
- }
- ~GuardVAList() {
- if (active)
- va_end(target);
- }
- };
- va_list args;
- va_start(args, msg);
- GuardVAList args_guard(args);
-
- va_list args_cp;
- va_copy(args_cp, args);
- GuardVAList args_copy_guard(args_cp);
-
- std::string result;
-
- array<char, 256> local_buff;
- size_t size_with_null = local_buff.size();
- auto ret = ::vsnprintf(local_buff.data(), size_with_null, msg, args_cp);
-
- args_copy_guard.clear();
-
- // handle empty expansion
- if (ret == 0)
- return result;
- if (static_cast<size_t>(ret) < size_with_null) {
- result.assign(local_buff.data(), static_cast<size_t>(ret));
- return result;
+static _LIBCPP_FORMAT_PRINTF(1, 0) string
+format_string_impl(const char* msg, va_list ap) {
+ array<char, 256> buf;
+
+ va_list apcopy;
+ va_copy(apcopy, ap);
+ int ret = ::vsnprintf(buf.data(), buf.size(), msg, apcopy);
+ va_end(apcopy);
+
+ string result;
+ if (static_cast<size_t>(ret) < buf.size()) {
+ result.assign(buf.data(), static_cast<size_t>(ret));
+ } else {
+ // we did not provide a long enough buffer on our first attempt. The
+ // return value is the number of bytes (excluding the null byte) that are
+ // needed for formatting.
+ size_t size_with_null = static_cast<size_t>(ret) + 1;
+ result.__resize_default_init(size_with_null - 1);
+ ret = ::vsnprintf(&result[0], size_with_null, msg, ap);
+ _LIBCPP_ASSERT(static_cast<size_t>(ret) == (size_with_null - 1), "TODO");
}
-
- // we did not provide a long enough buffer on our first attempt. The
- // return value is the number of bytes (excluding the null byte) that are
- // needed for formatting.
- size_with_null = static_cast<size_t>(ret) + 1;
- result.__resize_default_init(size_with_null - 1);
- ret = ::vsnprintf(&result[0], size_with_null, msg, args);
- _LIBCPP_ASSERT(static_cast<size_t>(ret) == (size_with_null - 1), "TODO");
-
return result;
}
-const path::value_type* unwrap(path::string_type const& s) { return s.c_str(); }
-const path::value_type* unwrap(path const& p) { return p.native().c_str(); }
-template <class Arg>
-Arg const& unwrap(Arg const& a) {
- static_assert(!is_class<Arg>::value, "cannot pass class here");
- return a;
-}
-
-template <class... Args>
-string format_string(const char* fmt, Args const&... args) {
- return format_string_imp(fmt, unwrap(args)...);
+static _LIBCPP_FORMAT_PRINTF(1, 2) string
+format_string(const char* msg, ...) {
+ string ret;
+ va_list ap;
+ va_start(ap, msg);
+#ifndef _LIBCPP_NO_EXCEPTIONS
+ try {
+#endif // _LIBCPP_NO_EXCEPTIONS
+ ret = format_string_impl(msg, ap);
+#ifndef _LIBCPP_NO_EXCEPTIONS
+ } catch (...) {
+ va_end(ap);
+ throw;
+ }
+#endif // _LIBCPP_NO_EXCEPTIONS
+ va_end(ap);
+ return ret;
}
error_code capture_errno() {
@@ -190,14 +171,14 @@ struct ErrorHandler {
_LIBCPP_UNREACHABLE();
}
- template <class... Args>
- T report(const error_code& ec, const char* msg, Args const&... args) const {
+ _LIBCPP_FORMAT_PRINTF(3, 0)
+ void report_impl(const error_code& ec, const char* msg, va_list ap) const {
if (ec_) {
*ec_ = ec;
- return error_value<T>();
+ return;
}
string what =
- string("in ") + func_name_ + ": " + format_string(msg, args...);
+ string("in ") + func_name_ + ": " + format_string_impl(msg, ap);
switch (bool(p1_) + bool(p2_)) {
case 0:
__throw_filesystem_error(what, ec);
@@ -209,11 +190,44 @@ struct ErrorHandler {
_LIBCPP_UNREACHABLE();
}
- T report(errc const& err) const { return report(make_error_code(err)); }
+ _LIBCPP_FORMAT_PRINTF(3, 4)
+ T report(const error_code& ec, const char* msg, ...) const {
+ va_list ap;
+ va_start(ap, msg);
+#ifndef _LIBCPP_NO_EXCEPTIONS
+ try {
+#endif // _LIBCPP_NO_EXCEPTIONS
+ report_impl(ec, msg, ap);
+#ifndef _LIBCPP_NO_EXCEPTIONS
+ } catch (...) {
+ va_end(ap);
+ throw;
+ }
+#endif // _LIBCPP_NO_EXCEPTIONS
+ va_end(ap);
+ return error_value<T>();
+ }
+
+ T report(errc const& err) const {
+ return report(make_error_code(err));
+ }
- template <class... Args>
- T report(errc const& err, const char* msg, Args const&... args) const {
- return report(make_error_code(err), msg, args...);
+ _LIBCPP_FORMAT_PRINTF(3, 4)
+ T report(errc const& err, const char* msg, ...) const {
+ va_list ap;
+ va_start(ap, msg);
+#ifndef _LIBCPP_NO_EXCEPTIONS
+ try {
+#endif // _LIBCPP_NO_EXCEPTIONS
+ report_impl(make_error_code(err), msg, ap);
+#ifndef _LIBCPP_NO_EXCEPTIONS
+ } catch (...) {
+ va_end(ap);
+ throw;
+ }
+#endif // _LIBCPP_NO_EXCEPTIONS
+ va_end(ap);
+ return error_value<T>();
}
private:
@@ -224,9 +238,41 @@ private:
using chrono::duration;
using chrono::duration_cast;
+#if defined(_LIBCPP_WIN32API)
+// Various C runtime versions (UCRT, or the legacy msvcrt.dll used by
+// some mingw toolchains) provide different stat function implementations,
+// with a number of limitations with respect to what we want from the
+// stat function. Instead provide our own (in the anonymous detail namespace
+// in posix_compat.h) which does exactly what we want, along with our own
+// stat structure and flag macros.
+
+struct TimeSpec {
+ int64_t tv_sec;
+ int64_t tv_nsec;
+};
+struct StatT {
+ unsigned st_mode;
+ TimeSpec st_atim;
+ TimeSpec st_mtim;
+ uint64_t st_dev; // FILE_ID_INFO::VolumeSerialNumber
+ struct FileIdStruct {
+ unsigned char id[16]; // FILE_ID_INFO::FileId
+ bool operator==(const FileIdStruct &other) const {
+ for (int i = 0; i < 16; i++)
+ if (id[i] != other.id[i])
+ return false;
+ return true;
+ }
+ } st_ino;
+ uint32_t st_nlink;
+ uintmax_t st_size;
+};
+
+#else
using TimeSpec = struct timespec;
using TimeVal = struct timeval;
using StatT = struct stat;
+#endif
template <class FileTimeT, class TimeT,
bool IsFloat = is_floating_point<typename FileTimeT::rep>::value>
@@ -255,8 +301,7 @@ struct time_util_base {
.count();
private:
-#if _LIBCPP_STD_VER > 11 && !defined(_LIBCPP_HAS_NO_CXX14_CONSTEXPR)
- static constexpr fs_duration get_min_nsecs() {
+ static _LIBCPP_CONSTEXPR_AFTER_CXX11 fs_duration get_min_nsecs() {
return duration_cast<fs_duration>(
fs_nanoseconds(min_nsec_timespec) -
duration_cast<fs_nanoseconds>(fs_seconds(1)));
@@ -266,7 +311,7 @@ private:
FileTimeT::duration::min(),
"value doesn't roundtrip");
- static constexpr bool check_range() {
+ static _LIBCPP_CONSTEXPR_AFTER_CXX11 bool check_range() {
// This kinda sucks, but it's what happens when we don't have __int128_t.
if (sizeof(TimeT) == sizeof(rep)) {
typedef duration<long long, ratio<3600 * 24 * 365> > Years;
@@ -277,7 +322,6 @@ private:
min_seconds <= numeric_limits<TimeT>::min();
}
static_assert(check_range(), "the representable range is unacceptable small");
-#endif
};
template <class FileTimeT, class TimeT>
@@ -405,7 +449,11 @@ public:
}
};
+#if defined(_LIBCPP_WIN32API)
+using fs_time = time_util<file_time_type, int64_t, TimeSpec>;
+#else
using fs_time = time_util<file_time_type, time_t, TimeSpec>;
+#endif
#if defined(__APPLE__)
inline TimeSpec extract_mtime(StatT const& st) { return st.st_mtimespec; }
@@ -419,11 +467,21 @@ inline TimeSpec extract_atime(StatT const& st) {
TimeSpec TS = {st.st_atime, 0};
return TS;
}
+#elif defined(_AIX)
+inline TimeSpec extract_mtime(StatT const& st) {
+ TimeSpec TS = {st.st_mtime, st.st_mtime_n};
+ return TS;
+}
+inline TimeSpec extract_atime(StatT const& st) {
+ TimeSpec TS = {st.st_atime, st.st_atime_n};
+ return TS;
+}
#else
inline TimeSpec extract_mtime(StatT const& st) { return st.st_mtim; }
inline TimeSpec extract_atime(StatT const& st) { return st.st_atim; }
#endif
+#if !defined(_LIBCPP_WIN32API)
inline TimeVal make_timeval(TimeSpec const& ts) {
using namespace chrono;
auto Convert = [](long nsec) {
@@ -466,6 +524,7 @@ bool set_file_times(const path& p, std::array<TimeSpec, 2> const& TS,
return posix_utimensat(p, TS, ec);
#endif
}
+#endif /* !_LIBCPP_WIN32API */
} // namespace
} // end namespace detail
diff --git a/lib/libcxx/src/filesystem/operations.cpp b/lib/libcxx/src/filesystem/operations.cpp
index 50a895dc2f..5179eeae42 100644
--- a/lib/libcxx/src/filesystem/operations.cpp
+++ b/lib/libcxx/src/filesystem/operations.cpp
@@ -17,6 +17,8 @@
#include "filesystem_common.h"
+#include "posix_compat.h"
+
#if defined(_LIBCPP_WIN32API)
# define WIN32_LEAN_AND_MEAN
# define NOMINMAX
@@ -40,7 +42,7 @@
# define _LIBCPP_FILESYSTEM_USE_FSTREAM
#endif
-#if !defined(CLOCK_REALTIME)
+#if !defined(CLOCK_REALTIME) && !defined(_LIBCPP_WIN32API)
# include <sys/time.h> // for gettimeofday and timeval
#endif
@@ -62,6 +64,10 @@ bool isSeparator(path::value_type C) {
return false;
}
+bool isDriveLetter(path::value_type C) {
+ return (C >= 'a' && C <= 'z') || (C >= 'A' && C <= 'Z');
+}
+
namespace parser {
using string_view_t = path::__string_view;
@@ -118,7 +124,13 @@ public:
switch (State) {
case PS_BeforeBegin: {
- PosPtr TkEnd = consumeSeparator(Start, End);
+ PosPtr TkEnd = consumeRootName(Start, End);
+ if (TkEnd)
+ return makeState(PS_InRootName, Start, TkEnd);
+ }
+ _LIBCPP_FALLTHROUGH();
+ case PS_InRootName: {
+ PosPtr TkEnd = consumeAllSeparators(Start, End);
if (TkEnd)
return makeState(PS_InRootDir, Start, TkEnd);
else
@@ -128,7 +140,7 @@ public:
return makeState(PS_InFilenames, Start, consumeName(Start, End));
case PS_InFilenames: {
- PosPtr SepEnd = consumeSeparator(Start, End);
+ PosPtr SepEnd = consumeAllSeparators(Start, End);
if (SepEnd != End) {
PosPtr TkEnd = consumeName(SepEnd, End);
if (TkEnd)
@@ -140,7 +152,6 @@ public:
case PS_InTrailingSep:
return makeState(PS_AtEnd);
- case PS_InRootName:
case PS_AtEnd:
_LIBCPP_UNREACHABLE();
}
@@ -155,12 +166,18 @@ public:
switch (State) {
case PS_AtEnd: {
// Try to consume a trailing separator or root directory first.
- if (PosPtr SepEnd = consumeSeparator(RStart, REnd)) {
+ if (PosPtr SepEnd = consumeAllSeparators(RStart, REnd)) {
if (SepEnd == REnd)
return makeState(PS_InRootDir, Path.data(), RStart + 1);
+ PosPtr TkStart = consumeRootName(SepEnd, REnd);
+ if (TkStart == REnd)
+ return makeState(PS_InRootDir, RStart, RStart + 1);
return makeState(PS_InTrailingSep, SepEnd + 1, RStart + 1);
} else {
- PosPtr TkStart = consumeName(RStart, REnd);
+ PosPtr TkStart = consumeRootName(RStart, REnd);
+ if (TkStart == REnd)
+ return makeState(PS_InRootName, TkStart + 1, RStart + 1);
+ TkStart = consumeName(RStart, REnd);
return makeState(PS_InFilenames, TkStart + 1, RStart + 1);
}
}
@@ -168,14 +185,20 @@ public:
return makeState(PS_InFilenames, consumeName(RStart, REnd) + 1,
RStart + 1);
case PS_InFilenames: {
- PosPtr SepEnd = consumeSeparator(RStart, REnd);
+ PosPtr SepEnd = consumeAllSeparators(RStart, REnd);
if (SepEnd == REnd)
return makeState(PS_InRootDir, Path.data(), RStart + 1);
- PosPtr TkEnd = consumeName(SepEnd, REnd);
- return makeState(PS_InFilenames, TkEnd + 1, SepEnd + 1);
+ PosPtr TkStart = consumeRootName(SepEnd ? SepEnd : RStart, REnd);
+ if (TkStart == REnd) {
+ if (SepEnd)
+ return makeState(PS_InRootDir, SepEnd + 1, RStart + 1);
+ return makeState(PS_InRootName, TkStart + 1, RStart + 1);
+ }
+ TkStart = consumeName(SepEnd, REnd);
+ return makeState(PS_InFilenames, TkStart + 1, SepEnd + 1);
}
case PS_InRootDir:
- // return makeState(PS_InRootName, Path.data(), RStart + 1);
+ return makeState(PS_InRootName, Path.data(), RStart + 1);
case PS_InRootName:
case PS_BeforeBegin:
_LIBCPP_UNREACHABLE();
@@ -281,8 +304,9 @@ private:
_LIBCPP_UNREACHABLE();
}
- PosPtr consumeSeparator(PosPtr P, PosPtr End) const noexcept {
- if (P == End || !isSeparator(*P))
+ // Consume all consecutive separators.
+ PosPtr consumeAllSeparators(PosPtr P, PosPtr End) const noexcept {
+ if (P == nullptr || P == End || !isSeparator(*P))
return nullptr;
const int Inc = P < End ? 1 : -1;
P += Inc;
@@ -291,15 +315,72 @@ private:
return P;
}
+ // Consume exactly N separators, or return nullptr.
+ PosPtr consumeNSeparators(PosPtr P, PosPtr End, int N) const noexcept {
+ PosPtr Ret = consumeAllSeparators(P, End);
+ if (Ret == nullptr)
+ return nullptr;
+ if (P < End) {
+ if (Ret == P + N)
+ return Ret;
+ } else {
+ if (Ret == P - N)
+ return Ret;
+ }
+ return nullptr;
+ }
+
PosPtr consumeName(PosPtr P, PosPtr End) const noexcept {
- if (P == End || isSeparator(*P))
+ PosPtr Start = P;
+ if (P == nullptr || P == End || isSeparator(*P))
return nullptr;
const int Inc = P < End ? 1 : -1;
P += Inc;
while (P != End && !isSeparator(*P))
P += Inc;
+ if (P == End && Inc < 0) {
+ // Iterating backwards and consumed all the rest of the input.
+ // Check if the start of the string would have been considered
+ // a root name.
+ PosPtr RootEnd = consumeRootName(End + 1, Start);
+ if (RootEnd)
+ return RootEnd - 1;
+ }
return P;
}
+
+ PosPtr consumeDriveLetter(PosPtr P, PosPtr End) const noexcept {
+ if (P == End)
+ return nullptr;
+ if (P < End) {
+ if (P + 1 == End || !isDriveLetter(P[0]) || P[1] != ':')
+ return nullptr;
+ return P + 2;
+ } else {
+ if (P - 1 == End || !isDriveLetter(P[-1]) || P[0] != ':')
+ return nullptr;
+ return P - 2;
+ }
+ }
+
+ PosPtr consumeNetworkRoot(PosPtr P, PosPtr End) const noexcept {
+ if (P == End)
+ return nullptr;
+ if (P < End)
+ return consumeName(consumeNSeparators(P, End, 2), End);
+ else
+ return consumeNSeparators(consumeName(P, End), End, 2);
+ }
+
+ PosPtr consumeRootName(PosPtr P, PosPtr End) const noexcept {
+#if defined(_LIBCPP_WIN32API)
+ if (PosPtr Ret = consumeDriveLetter(P, End))
+ return Ret;
+ if (PosPtr Ret = consumeNetworkRoot(P, End))
+ return Ret;
+#endif
+ return nullptr;
+ }
};
string_view_pair separate_filename(string_view_t const& s) {
@@ -331,6 +412,7 @@ errc __win_err_to_errc(int err) {
{ERROR_ACCESS_DENIED, errc::permission_denied},
{ERROR_ALREADY_EXISTS, errc::file_exists},
{ERROR_BAD_NETPATH, errc::no_such_file_or_directory},
+ {ERROR_BAD_PATHNAME, errc::no_such_file_or_directory},
{ERROR_BAD_UNIT, errc::no_such_device},
{ERROR_BROKEN_PIPE, errc::broken_pipe},
{ERROR_BUFFER_OVERFLOW, errc::filename_too_long},
@@ -403,7 +485,7 @@ struct FileDescriptor {
static FileDescriptor create(const path* p, error_code& ec, Args... args) {
ec.clear();
int fd;
- if ((fd = ::open(p->c_str(), args...)) == -1) {
+ if ((fd = detail::open(p->c_str(), args...)) == -1) {
ec = capture_errno();
return FileDescriptor{p};
}
@@ -429,7 +511,7 @@ struct FileDescriptor {
void close() noexcept {
if (fd != -1)
- ::close(fd);
+ detail::close(fd);
fd = -1;
}
@@ -453,10 +535,6 @@ perms posix_get_perms(const StatT& st) noexcept {
return static_cast<perms>(st.st_mode) & perms::mask;
}
-::mode_t posix_convert_perms(perms prms) {
- return static_cast< ::mode_t>(prms & perms::mask);
-}
-
file_status create_file_status(error_code& m_ec, path const& p,
const StatT& path_stat, error_code* ec) {
if (ec)
@@ -495,7 +573,7 @@ file_status create_file_status(error_code& m_ec, path const& p,
file_status posix_stat(path const& p, StatT& path_stat, error_code* ec) {
error_code m_ec;
- if (::stat(p.c_str(), &path_stat) == -1)
+ if (detail::stat(p.c_str(), &path_stat) == -1)
m_ec = detail::capture_errno();
return create_file_status(m_ec, p, path_stat, ec);
}
@@ -507,7 +585,7 @@ file_status posix_stat(path const& p, error_code* ec) {
file_status posix_lstat(path const& p, StatT& path_stat, error_code* ec) {
error_code m_ec;
- if (::lstat(p.c_str(), &path_stat) == -1)
+ if (detail::lstat(p.c_str(), &path_stat) == -1)
m_ec = detail::capture_errno();
return create_file_status(m_ec, p, path_stat, ec);
}
@@ -519,7 +597,7 @@ file_status posix_lstat(path const& p, error_code* ec) {
// http://pubs.opengroup.org/onlinepubs/9699919799/functions/ftruncate.html
bool posix_ftruncate(const FileDescriptor& fd, off_t to_size, error_code& ec) {
- if (::ftruncate(fd.fd, to_size) == -1) {
+ if (detail::ftruncate(fd.fd, to_size) == -1) {
ec = capture_errno();
return true;
}
@@ -528,7 +606,7 @@ bool posix_ftruncate(const FileDescriptor& fd, off_t to_size, error_code& ec) {
}
bool posix_fchmod(const FileDescriptor& fd, const StatT& st, error_code& ec) {
- if (::fchmod(fd.fd, st.st_mode) == -1) {
+ if (detail::fchmod(fd.fd, st.st_mode) == -1) {
ec = capture_errno();
return true;
}
@@ -545,7 +623,7 @@ file_status FileDescriptor::refresh_status(error_code& ec) {
m_status = file_status{};
m_stat = {};
error_code m_ec;
- if (::fstat(fd, &m_stat) == -1)
+ if (detail::fstat(fd, &m_stat) == -1)
m_ec = capture_errno();
m_status = create_file_status(m_ec, name, m_stat, &ec);
return m_status;
@@ -565,7 +643,14 @@ const bool _FilesystemClock::is_steady;
_FilesystemClock::time_point _FilesystemClock::now() noexcept {
typedef chrono::duration<rep> __secs;
-#if defined(CLOCK_REALTIME)
+#if defined(_LIBCPP_WIN32API)
+ typedef chrono::duration<rep, nano> __nsecs;
+ FILETIME time;
+ GetSystemTimeAsFileTime(&time);
+ TimeSpec tp = detail::filetime_to_timespec(time);
+ return time_point(__secs(tp.tv_sec) +
+ chrono::duration_cast<duration>(__nsecs(tp.tv_nsec)));
+#elif defined(CLOCK_REALTIME)
typedef chrono::duration<rep, nano> __nsecs;
struct timespec tp;
if (0 != clock_gettime(CLOCK_REALTIME, &tp))
@@ -582,27 +667,20 @@ _FilesystemClock::time_point _FilesystemClock::now() noexcept {
filesystem_error::~filesystem_error() {}
-#if defined(_LIBCPP_WIN32API)
-#define PS_FMT "%ls"
-#else
-#define PS_FMT "%s"
-#endif
-
void filesystem_error::__create_what(int __num_paths) {
const char* derived_what = system_error::what();
__storage_->__what_ = [&]() -> string {
- const path::value_type* p1 = path1().native().empty() ? PS("\"\"") : path1().c_str();
- const path::value_type* p2 = path2().native().empty() ? PS("\"\"") : path2().c_str();
switch (__num_paths) {
- default:
+ case 0:
return detail::format_string("filesystem error: %s", derived_what);
case 1:
- return detail::format_string("filesystem error: %s [" PS_FMT "]", derived_what,
- p1);
+ return detail::format_string("filesystem error: %s [" PATH_CSTR_FMT "]",
+ derived_what, path1().c_str());
case 2:
- return detail::format_string("filesystem error: %s [" PS_FMT "] [" PS_FMT "]",
- derived_what, p1, p2);
+ return detail::format_string("filesystem error: %s [" PATH_CSTR_FMT "] [" PATH_CSTR_FMT "]",
+ derived_what, path1().c_str(), path2().c_str());
}
+ _LIBCPP_UNREACHABLE();
}();
}
@@ -627,20 +705,20 @@ path __canonical(path const& orig_p, error_code* ec) {
ErrorHandler<path> err("canonical", ec, &orig_p, &cwd);
path p = __do_absolute(orig_p, &cwd, ec);
-#if defined(_POSIX_VERSION) && _POSIX_VERSION >= 200112
- std::unique_ptr<char, decltype(&::free)>
- hold(::realpath(p.c_str(), nullptr), &::free);
+#if (defined(_POSIX_VERSION) && _POSIX_VERSION >= 200112) || defined(_LIBCPP_WIN32API)
+ std::unique_ptr<path::value_type, decltype(&::free)>
+ hold(detail::realpath(p.c_str(), nullptr), &::free);
if (hold.get() == nullptr)
return err.report(capture_errno());
return {hold.get()};
#else
#if defined(__MVS__) && !defined(PATH_MAX)
- char buff[ _XOPEN_PATH_MAX + 1 ];
+ path::value_type buff[ _XOPEN_PATH_MAX + 1 ];
#else
- char buff[PATH_MAX + 1];
+ path::value_type buff[PATH_MAX + 1];
#endif
- char* ret;
- if ((ret = ::realpath(p.c_str(), buff)) == nullptr)
+ path::value_type* ret;
+ if ((ret = detail::realpath(p.c_str(), buff)) == nullptr)
return err.report(capture_errno());
return {ret};
#endif
@@ -819,8 +897,8 @@ bool __copy_file(const path& from, const path& to, copy_options options,
ErrorHandler<bool> err("copy_file", ec, &to, &from);
error_code m_ec;
- FileDescriptor from_fd =
- FileDescriptor::create_with_status(&from, m_ec, O_RDONLY | O_NONBLOCK);
+ FileDescriptor from_fd = FileDescriptor::create_with_status(
+ &from, m_ec, O_RDONLY | O_NONBLOCK | O_BINARY);
if (m_ec)
return err.report(m_ec);
@@ -872,7 +950,7 @@ bool __copy_file(const path& from, const path& to, copy_options options,
// Don't truncate right away. We may not be opening the file we originally
// looked at; we'll check this later.
- int to_open_flags = O_WRONLY;
+ int to_open_flags = O_WRONLY | O_BINARY;
if (!to_exists)
to_open_flags |= O_CREAT;
FileDescriptor to_fd = FileDescriptor::create_with_status(
@@ -908,10 +986,13 @@ void __copy_symlink(const path& existing_symlink, const path& new_symlink,
if (ec && *ec) {
return;
}
- // NOTE: proposal says you should detect if you should call
- // create_symlink or create_directory_symlink. I don't think this
- // is needed with POSIX
- __create_symlink(real_path, new_symlink, ec);
+#if defined(_LIBCPP_WIN32API)
+ error_code local_ec;
+ if (is_directory(real_path, local_ec))
+ __create_directory_symlink(real_path, new_symlink, ec);
+ else
+#endif
+ __create_symlink(real_path, new_symlink, ec);
}
bool __create_directories(const path& p, error_code* ec) {
@@ -932,31 +1013,34 @@ bool __create_directories(const path& p, error_code* ec) {
if (not status_known(parent_st))
return err.report(m_ec);
if (not exists(parent_st)) {
+ if (parent == p)
+ return err.report(errc::invalid_argument);
__create_directories(parent, ec);
if (ec && *ec) {
return false;
}
- }
+ } else if (not is_directory(parent_st))
+ return err.report(errc::not_a_directory);
}
- return __create_directory(p, ec);
+ bool ret = __create_directory(p, &m_ec);
+ if (m_ec)
+ return err.report(m_ec);
+ return ret;
}
bool __create_directory(const path& p, error_code* ec) {
ErrorHandler<bool> err("create_directory", ec, &p);
- if (::mkdir(p.c_str(), static_cast<int>(perms::all)) == 0)
+ if (detail::mkdir(p.c_str(), static_cast<int>(perms::all)) == 0)
return true;
- if (errno == EEXIST) {
- error_code mec = capture_errno();
- error_code ignored_ec;
- const file_status st = status(p, ignored_ec);
- if (!is_directory(st)) {
- err.report(mec);
- }
- } else {
- err.report(capture_errno());
- }
+ if (errno != EEXIST)
+ return err.report(capture_errno());
+ error_code mec = capture_errno();
+ error_code ignored_ec;
+ const file_status st = status(p, ignored_ec);
+ if (!is_directory(st))
+ return err.report(mec);
return false;
}
@@ -965,65 +1049,80 @@ bool __create_directory(path const& p, path const& attributes, error_code* ec) {
StatT attr_stat;
error_code mec;
- auto st = detail::posix_stat(attributes, attr_stat, &mec);
+ file_status st = detail::posix_stat(attributes, attr_stat, &mec);
if (!status_known(st))
return err.report(mec);
if (!is_directory(st))
return err.report(errc::not_a_directory,
"the specified attribute path is invalid");
- if (::mkdir(p.c_str(), attr_stat.st_mode) == 0)
+ if (detail::mkdir(p.c_str(), attr_stat.st_mode) == 0)
return true;
- if (errno == EEXIST) {
- error_code mec = capture_errno();
- error_code ignored_ec;
- const file_status st = status(p, ignored_ec);
- if (!is_directory(st)) {
- err.report(mec);
- }
- } else {
- err.report(capture_errno());
- }
+ if (errno != EEXIST)
+ return err.report(capture_errno());
+
+ mec = capture_errno();
+ error_code ignored_ec;
+ st = status(p, ignored_ec);
+ if (!is_directory(st))
+ return err.report(mec);
return false;
}
void __create_directory_symlink(path const& from, path const& to,
error_code* ec) {
ErrorHandler<void> err("create_directory_symlink", ec, &from, &to);
- if (::symlink(from.c_str(), to.c_str()) != 0)
+ if (detail::symlink_dir(from.c_str(), to.c_str()) == -1)
return err.report(capture_errno());
}
void __create_hard_link(const path& from, const path& to, error_code* ec) {
ErrorHandler<void> err("create_hard_link", ec, &from, &to);
- if (::link(from.c_str(), to.c_str()) == -1)
+ if (detail::link(from.c_str(), to.c_str()) == -1)
return err.report(capture_errno());
}
void __create_symlink(path const& from, path const& to, error_code* ec) {
ErrorHandler<void> err("create_symlink", ec, &from, &to);
- if (::symlink(from.c_str(), to.c_str()) == -1)
+ if (detail::symlink_file(from.c_str(), to.c_str()) == -1)
return err.report(capture_errno());
}
path __current_path(error_code* ec) {
ErrorHandler<path> err("current_path", ec);
+#if defined(_LIBCPP_WIN32API) || defined(__GLIBC__) || defined(__APPLE__)
+ // Common extension outside of POSIX getcwd() spec, without needing to
+ // preallocate a buffer. Also supported by a number of other POSIX libcs.
+ int size = 0;
+ path::value_type* ptr = nullptr;
+ typedef decltype(&::free) Deleter;
+ Deleter deleter = &::free;
+#else
auto size = ::pathconf(".", _PC_PATH_MAX);
_LIBCPP_ASSERT(size >= 0, "pathconf returned a 0 as max size");
- auto buff = unique_ptr<char[]>(new char[size + 1]);
- char* ret;
- if ((ret = ::getcwd(buff.get(), static_cast<size_t>(size))) == nullptr)
+ auto buff = unique_ptr<path::value_type[]>(new path::value_type[size + 1]);
+ path::value_type* ptr = buff.get();
+
+ // Preallocated buffer, don't free the buffer in the second unique_ptr
+ // below.
+ struct Deleter { void operator()(void*) const {} };
+ Deleter deleter;
+#endif
+
+ unique_ptr<path::value_type, Deleter> hold(detail::getcwd(ptr, size),
+ deleter);
+ if (hold.get() == nullptr)
return err.report(capture_errno(), "call to getcwd failed");
- return {buff.get()};
+ return {hold.get()};
}
void __current_path(const path& p, error_code* ec) {
ErrorHandler<void> err("current_path", ec, &p);
- if (::chdir(p.c_str()) == -1)
+ if (detail::chdir(p.c_str()) == -1)
err.report(capture_errno());
}
@@ -1119,6 +1218,17 @@ void __last_write_time(const path& p, file_time_type new_time, error_code* ec) {
using detail::fs_time;
ErrorHandler<void> err("last_write_time", ec, &p);
+#if defined(_LIBCPP_WIN32API)
+ TimeSpec ts;
+ if (!fs_time::convert_to_timespec(ts, new_time))
+ return err.report(errc::value_too_large);
+ detail::WinHandle h(p.c_str(), FILE_WRITE_ATTRIBUTES, 0);
+ if (!h)
+ return err.report(detail::make_windows_error(GetLastError()));
+ FILETIME last_write = timespec_to_filetime(ts);
+ if (!SetFileTime(h, nullptr, nullptr, &last_write))
+ return err.report(detail::make_windows_error(GetLastError()));
+#else
error_code m_ec;
array<TimeSpec, 2> tbuf;
#if !defined(_LIBCPP_USE_UTIMENSAT)
@@ -1140,6 +1250,7 @@ void __last_write_time(const path& p, file_time_type new_time, error_code* ec) {
detail::set_file_times(p, tbuf, m_ec);
if (m_ec)
return err.report(m_ec);
+#endif
}
void __permissions(const path& p, perms prms, perm_options opts,
@@ -1171,11 +1282,11 @@ void __permissions(const path& p, perms prms, perm_options opts,
else if (remove_perms)
prms = st.permissions() & ~prms;
}
- const auto real_perms = detail::posix_convert_perms(prms);
+ const auto real_perms = static_cast<detail::ModeT>(prms & perms::mask);
#if defined(AT_SYMLINK_NOFOLLOW) && defined(AT_FDCWD)
const int flags = set_sym_perms ? AT_SYMLINK_NOFOLLOW : 0;
- if (::fchmodat(AT_FDCWD, p.c_str(), real_perms, flags) == -1) {
+ if (detail::fchmodat(AT_FDCWD, p.c_str(), real_perms, flags) == -1) {
return err.report(capture_errno());
}
#else
@@ -1190,21 +1301,25 @@ void __permissions(const path& p, perms prms, perm_options opts,
path __read_symlink(const path& p, error_code* ec) {
ErrorHandler<path> err("read_symlink", ec, &p);
-#ifdef PATH_MAX
+#if defined(PATH_MAX) || defined(MAX_SYMLINK_SIZE)
struct NullDeleter { void operator()(void*) const {} };
+#ifdef MAX_SYMLINK_SIZE
+ const size_t size = MAX_SYMLINK_SIZE + 1;
+#else
const size_t size = PATH_MAX + 1;
- char stack_buff[size];
- auto buff = std::unique_ptr<char[], NullDeleter>(stack_buff);
+#endif
+ path::value_type stack_buff[size];
+ auto buff = std::unique_ptr<path::value_type[], NullDeleter>(stack_buff);
#else
StatT sb;
- if (::lstat(p.c_str(), &sb) == -1) {
+ if (detail::lstat(p.c_str(), &sb) == -1) {
return err.report(capture_errno());
}
const size_t size = sb.st_size + 1;
- auto buff = unique_ptr<char[]>(new char[size]);
+ auto buff = unique_ptr<path::value_type[]>(new path::value_type[size]);
#endif
- ::ssize_t ret;
- if ((ret = ::readlink(p.c_str(), buff.get(), size)) == -1)
+ detail::SSizeT ret;
+ if ((ret = detail::readlink(p.c_str(), buff.get(), size)) == -1)
return err.report(capture_errno());
_LIBCPP_ASSERT(ret > 0, "TODO");
if (static_cast<size_t>(ret) >= size)
@@ -1215,7 +1330,7 @@ path __read_symlink(const path& p, error_code* ec) {
bool __remove(const path& p, error_code* ec) {
ErrorHandler<bool> err("remove", ec, &p);
- if (::remove(p.c_str()) == -1) {
+ if (detail::remove(p.c_str()) == -1) {
if (errno != ENOENT)
err.report(capture_errno());
return false;
@@ -1264,21 +1379,21 @@ uintmax_t __remove_all(const path& p, error_code* ec) {
void __rename(const path& from, const path& to, error_code* ec) {
ErrorHandler<void> err("rename", ec, &from, &to);
- if (::rename(from.c_str(), to.c_str()) == -1)
+ if (detail::rename(from.c_str(), to.c_str()) == -1)
err.report(capture_errno());
}
void __resize_file(const path& p, uintmax_t size, error_code* ec) {
ErrorHandler<void> err("resize_file", ec, &p);
- if (::truncate(p.c_str(), static_cast< ::off_t>(size)) == -1)
+ if (detail::truncate(p.c_str(), static_cast< ::off_t>(size)) == -1)
return err.report(capture_errno());
}
space_info __space(const path& p, error_code* ec) {
ErrorHandler<void> err("space", ec, &p);
space_info si;
- struct statvfs m_svfs = {};
- if (::statvfs(p.c_str(), &m_svfs) == -1) {
+ detail::StatVFS m_svfs = {};
+ if (detail::statvfs(p.c_str(), &m_svfs) == -1) {
err.report(capture_errno());
si.capacity = si.free = si.available = static_cast<uintmax_t>(-1);
return si;
@@ -1306,6 +1421,19 @@ file_status __symlink_status(const path& p, error_code* ec) {
path __temp_directory_path(error_code* ec) {
ErrorHandler<path> err("temp_directory_path", ec);
+#if defined(_LIBCPP_WIN32API)
+ wchar_t buf[MAX_PATH];
+ DWORD retval = GetTempPathW(MAX_PATH, buf);
+ if (!retval)
+ return err.report(detail::make_windows_error(GetLastError()));
+ if (retval > MAX_PATH)
+ return err.report(errc::filename_too_long);
+ // GetTempPathW returns a path with a trailing slash, which we
+ // shouldn't include for consistency.
+ if (buf[retval-1] == L'\\')
+ buf[retval-1] = L'\0';
+ path p(buf);
+#else
const char* env_paths[] = {"TMPDIR", "TMP", "TEMP", "TEMPDIR"};
const char* ret = nullptr;
@@ -1316,14 +1444,15 @@ path __temp_directory_path(error_code* ec) {
ret = "/tmp";
path p(ret);
+#endif
error_code m_ec;
file_status st = detail::posix_stat(p, &m_ec);
if (!status_known(st))
- return err.report(m_ec, "cannot access path \"" PS_FMT "\"", p);
+ return err.report(m_ec, "cannot access path " PATH_CSTR_FMT, p.c_str());
if (!exists(st) || !is_directory(st))
- return err.report(errc::not_a_directory, "path \"" PS_FMT "\" is not a directory",
- p);
+ return err.report(errc::not_a_directory,
+ "path " PATH_CSTR_FMT " is not a directory", p.c_str());
return p;
}
@@ -1586,6 +1715,7 @@ path path::lexically_normal() const {
if (NeedTrailingSep)
Result /= PS("");
+ Result.make_preferred();
return Result;
}
@@ -1806,7 +1936,6 @@ size_t __char_to_wide(const string &str, wchar_t *out, size_t outlen) {
// directory entry definitions
///////////////////////////////////////////////////////////////////////////////
-#ifndef _LIBCPP_WIN32API
error_code directory_entry::__do_refresh() noexcept {
__data_.__reset();
error_code failure_ec;
@@ -1860,47 +1989,5 @@ error_code directory_entry::__do_refresh() noexcept {
return failure_ec;
}
-#else
-error_code directory_entry::__do_refresh() noexcept {
- __data_.__reset();
- error_code failure_ec;
-
- file_status st = _VSTD_FS::symlink_status(__p_, failure_ec);
- if (!status_known(st)) {
- __data_.__reset();
- return failure_ec;
- }
-
- if (!_VSTD_FS::exists(st) || !_VSTD_FS::is_symlink(st)) {
- __data_.__cache_type_ = directory_entry::_RefreshNonSymlink;
- __data_.__type_ = st.type();
- __data_.__non_sym_perms_ = st.permissions();
- } else { // we have a symlink
- __data_.__sym_perms_ = st.permissions();
- // Get the information about the linked entity.
- // Ignore errors from stat, since we don't want errors regarding symlink
- // resolution to be reported to the user.
- error_code ignored_ec;
- st = _VSTD_FS::status(__p_, ignored_ec);
-
- __data_.__type_ = st.type();
- __data_.__non_sym_perms_ = st.permissions();
-
- // If we failed to resolve the link, then only partially populate the
- // cache.
- if (!status_known(st)) {
- __data_.__cache_type_ = directory_entry::_RefreshSymlinkUnresolved;
- return error_code{};
- }
- __data_.__cache_type_ = directory_entry::_RefreshSymlink;
- }
-
- // FIXME: This is currently broken, and the implementation only a placeholder.
- // We need to cache last_write_time, file_size, and hard_link_count here before
- // the implementation actually works.
-
- return failure_ec;
-}
-#endif
_LIBCPP_END_NAMESPACE_FILESYSTEM
diff --git a/lib/libcxx/src/filesystem/posix_compat.h b/lib/libcxx/src/filesystem/posix_compat.h
new file mode 100644
index 0000000000..f5c8ec39df
--- /dev/null
+++ b/lib/libcxx/src/filesystem/posix_compat.h
@@ -0,0 +1,521 @@
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+//
+// POSIX-like portability helper functions.
+//
+// These generally behave like the proper posix functions, with these
+// exceptions:
+// On Windows, they take paths in wchar_t* form, instead of char* form.
+// The symlink() function is split into two frontends, symlink_file()
+// and symlink_dir().
+//
+// These are provided within an anonymous namespace within the detail
+// namespace - callers need to include this header and call them as
+// detail::function(), regardless of platform.
+//
+
+#ifndef POSIX_COMPAT_H
+#define POSIX_COMPAT_H
+
+#include "filesystem"
+
+#include "filesystem_common.h"
+
+#if defined(_LIBCPP_WIN32API)
+# define WIN32_LEAN_AND_MEAN
+# define NOMINMAX
+# include <windows.h>
+# include <io.h>
+# include <winioctl.h>
+#else
+# include <unistd.h>
+# include <sys/stat.h>
+# include <sys/statvfs.h>
+#endif
+#include <time.h>
+
+#if defined(_LIBCPP_WIN32API)
+// This struct isn't defined in the normal Windows SDK, but only in the
+// Windows Driver Kit.
+struct LIBCPP_REPARSE_DATA_BUFFER {
+ unsigned long ReparseTag;
+ unsigned short ReparseDataLength;
+ unsigned short Reserved;
+ union {
+ struct {
+ unsigned short SubstituteNameOffset;
+ unsigned short SubstituteNameLength;
+ unsigned short PrintNameOffset;
+ unsigned short PrintNameLength;
+ unsigned long Flags;
+ wchar_t PathBuffer[1];
+ } SymbolicLinkReparseBuffer;
+ struct {
+ unsigned short SubstituteNameOffset;
+ unsigned short SubstituteNameLength;
+ unsigned short PrintNameOffset;
+ unsigned short PrintNameLength;
+ wchar_t PathBuffer[1];
+ } MountPointReparseBuffer;
+ struct {
+ unsigned char DataBuffer[1];
+ } GenericReparseBuffer;
+ };
+};
+#endif
+
+_LIBCPP_BEGIN_NAMESPACE_FILESYSTEM
+
+namespace detail {
+namespace {
+
+#if defined(_LIBCPP_WIN32API)
+
+// Various C runtime header sets provide more or less of these. As we
+// provide our own implementation, undef all potential defines from the
+// C runtime headers and provide a complete set of macros of our own.
+
+#undef _S_IFMT
+#undef _S_IFDIR
+#undef _S_IFCHR
+#undef _S_IFIFO
+#undef _S_IFREG
+#undef _S_IFBLK
+#undef _S_IFLNK
+#undef _S_IFSOCK
+
+#define _S_IFMT 0xF000
+#define _S_IFDIR 0x4000
+#define _S_IFCHR 0x2000
+#define _S_IFIFO 0x1000
+#define _S_IFREG 0x8000
+#define _S_IFBLK 0x6000
+#define _S_IFLNK 0xA000
+#define _S_IFSOCK 0xC000
+
+#undef S_ISDIR
+#undef S_ISFIFO
+#undef S_ISCHR
+#undef S_ISREG
+#undef S_ISLNK
+#undef S_ISBLK
+#undef S_ISSOCK
+
+#define S_ISDIR(m) (((m) & _S_IFMT) == _S_IFDIR)
+#define S_ISCHR(m) (((m) & _S_IFMT) == _S_IFCHR)
+#define S_ISFIFO(m) (((m) & _S_IFMT) == _S_IFIFO)
+#define S_ISREG(m) (((m) & _S_IFMT) == _S_IFREG)
+#define S_ISBLK(m) (((m) & _S_IFMT) == _S_IFBLK)
+#define S_ISLNK(m) (((m) & _S_IFMT) == _S_IFLNK)
+#define S_ISSOCK(m) (((m) & _S_IFMT) == _S_IFSOCK)
+
+#define O_NONBLOCK 0
+
+
+// There were 369 years and 89 leap days from the Windows epoch
+// (1601) to the Unix epoch (1970).
+#define FILE_TIME_OFFSET_SECS (uint64_t(369 * 365 + 89) * (24 * 60 * 60))
+
+TimeSpec filetime_to_timespec(LARGE_INTEGER li) {
+ TimeSpec ret;
+ ret.tv_sec = li.QuadPart / 10000000 - FILE_TIME_OFFSET_SECS;
+ ret.tv_nsec = (li.QuadPart % 10000000) * 100;
+ return ret;
+}
+
+TimeSpec filetime_to_timespec(FILETIME ft) {
+ LARGE_INTEGER li;
+ li.LowPart = ft.dwLowDateTime;
+ li.HighPart = ft.dwHighDateTime;
+ return filetime_to_timespec(li);
+}
+
+FILETIME timespec_to_filetime(TimeSpec ts) {
+ LARGE_INTEGER li;
+ li.QuadPart =
+ ts.tv_nsec / 100 + (ts.tv_sec + FILE_TIME_OFFSET_SECS) * 10000000;
+ FILETIME ft;
+ ft.dwLowDateTime = li.LowPart;
+ ft.dwHighDateTime = li.HighPart;
+ return ft;
+}
+
+int set_errno(int e = GetLastError()) {
+ errno = static_cast<int>(__win_err_to_errc(e));
+ return -1;
+}
+
+class WinHandle {
+public:
+ WinHandle(const wchar_t *p, DWORD access, DWORD flags) {
+ h = CreateFileW(
+ p, access, FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE,
+ nullptr, OPEN_EXISTING, FILE_FLAG_BACKUP_SEMANTICS | flags, nullptr);
+ }
+ ~WinHandle() {
+ if (h != INVALID_HANDLE_VALUE)
+ CloseHandle(h);
+ }
+ operator HANDLE() const { return h; }
+ operator bool() const { return h != INVALID_HANDLE_VALUE; }
+
+private:
+ HANDLE h;
+};
+
+int stat_handle(HANDLE h, StatT *buf) {
+ FILE_BASIC_INFO basic;
+ if (!GetFileInformationByHandleEx(h, FileBasicInfo, &basic, sizeof(basic)))
+ return set_errno();
+ memset(buf, 0, sizeof(*buf));
+ buf->st_mtim = filetime_to_timespec(basic.LastWriteTime);
+ buf->st_atim = filetime_to_timespec(basic.LastAccessTime);
+ buf->st_mode = 0555; // Read-only
+ if (!(basic.FileAttributes & FILE_ATTRIBUTE_READONLY))
+ buf->st_mode |= 0222; // Write
+ if (basic.FileAttributes & FILE_ATTRIBUTE_DIRECTORY) {
+ buf->st_mode |= _S_IFDIR;
+ } else {
+ buf->st_mode |= _S_IFREG;
+ }
+ if (basic.FileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
+ FILE_ATTRIBUTE_TAG_INFO tag;
+ if (!GetFileInformationByHandleEx(h, FileAttributeTagInfo, &tag,
+ sizeof(tag)))
+ return set_errno();
+ if (tag.ReparseTag == IO_REPARSE_TAG_SYMLINK)
+ buf->st_mode = (buf->st_mode & ~_S_IFMT) | _S_IFLNK;
+ }
+ FILE_STANDARD_INFO standard;
+ if (!GetFileInformationByHandleEx(h, FileStandardInfo, &standard,
+ sizeof(standard)))
+ return set_errno();
+ buf->st_nlink = standard.NumberOfLinks;
+ buf->st_size = standard.EndOfFile.QuadPart;
+ BY_HANDLE_FILE_INFORMATION info;
+ if (!GetFileInformationByHandle(h, &info))
+ return set_errno();
+ buf->st_dev = info.dwVolumeSerialNumber;
+ memcpy(&buf->st_ino.id[0], &info.nFileIndexHigh, 4);
+ memcpy(&buf->st_ino.id[4], &info.nFileIndexLow, 4);
+ return 0;
+}
+
+int stat_file(const wchar_t *path, StatT *buf, DWORD flags) {
+ WinHandle h(path, FILE_READ_ATTRIBUTES, flags);
+ if (!h)
+ return set_errno();
+ int ret = stat_handle(h, buf);
+ return ret;
+}
+
+int stat(const wchar_t *path, StatT *buf) { return stat_file(path, buf, 0); }
+
+int lstat(const wchar_t *path, StatT *buf) {
+ return stat_file(path, buf, FILE_FLAG_OPEN_REPARSE_POINT);
+}
+
+int fstat(int fd, StatT *buf) {
+ HANDLE h = reinterpret_cast<HANDLE>(_get_osfhandle(fd));
+ return stat_handle(h, buf);
+}
+
+int mkdir(const wchar_t *path, int permissions) {
+ (void)permissions;
+ return _wmkdir(path);
+}
+
+int symlink_file_dir(const wchar_t *oldname, const wchar_t *newname,
+ bool is_dir) {
+ path dest(oldname);
+ dest.make_preferred();
+ oldname = dest.c_str();
+ DWORD flags = is_dir ? SYMBOLIC_LINK_FLAG_DIRECTORY : 0;
+ if (CreateSymbolicLinkW(newname, oldname,
+ flags | SYMBOLIC_LINK_FLAG_ALLOW_UNPRIVILEGED_CREATE))
+ return 0;
+ int e = GetLastError();
+ if (e != ERROR_INVALID_PARAMETER)
+ return set_errno(e);
+ if (CreateSymbolicLinkW(newname, oldname, flags))
+ return 0;
+ return set_errno();
+}
+
+int symlink_file(const wchar_t *oldname, const wchar_t *newname) {
+ return symlink_file_dir(oldname, newname, false);
+}
+
+int symlink_dir(const wchar_t *oldname, const wchar_t *newname) {
+ return symlink_file_dir(oldname, newname, true);
+}
+
+int link(const wchar_t *oldname, const wchar_t *newname) {
+ if (CreateHardLinkW(newname, oldname, nullptr))
+ return 0;
+ return set_errno();
+}
+
+int remove(const wchar_t *path) {
+ detail::WinHandle h(path, DELETE, FILE_FLAG_OPEN_REPARSE_POINT);
+ if (!h)
+ return set_errno();
+ FILE_DISPOSITION_INFO info;
+ info.DeleteFile = TRUE;
+ if (!SetFileInformationByHandle(h, FileDispositionInfo, &info, sizeof(info)))
+ return set_errno();
+ return 0;
+}
+
+int truncate_handle(HANDLE h, off_t length) {
+ LARGE_INTEGER size_param;
+ size_param.QuadPart = length;
+ if (!SetFilePointerEx(h, size_param, 0, FILE_BEGIN))
+ return set_errno();
+ if (!SetEndOfFile(h))
+ return set_errno();
+ return 0;
+}
+
+int ftruncate(int fd, off_t length) {
+ HANDLE h = reinterpret_cast<HANDLE>(_get_osfhandle(fd));
+ return truncate_handle(h, length);
+}
+
+int truncate(const wchar_t *path, off_t length) {
+ detail::WinHandle h(path, GENERIC_WRITE, 0);
+ if (!h)
+ return set_errno();
+ return truncate_handle(h, length);
+}
+
+int rename(const wchar_t *from, const wchar_t *to) {
+ if (!(MoveFileExW(from, to,
+ MOVEFILE_COPY_ALLOWED | MOVEFILE_REPLACE_EXISTING |
+ MOVEFILE_WRITE_THROUGH)))
+ return set_errno();
+ return 0;
+}
+
+template <class... Args> int open(const wchar_t *filename, Args... args) {
+ return _wopen(filename, args...);
+}
+int close(int fd) { return _close(fd); }
+int chdir(const wchar_t *path) { return _wchdir(path); }
+
+struct StatVFS {
+ uint64_t f_frsize;
+ uint64_t f_blocks;
+ uint64_t f_bfree;
+ uint64_t f_bavail;
+};
+
+int statvfs(const wchar_t *p, StatVFS *buf) {
+ path dir = p;
+ while (true) {
+ error_code local_ec;
+ const file_status st = status(dir, local_ec);
+ if (!exists(st) || is_directory(st))
+ break;
+ path parent = dir.parent_path();
+ if (parent == dir) {
+ errno = ENOENT;
+ return -1;
+ }
+ dir = parent;
+ }
+ ULARGE_INTEGER free_bytes_available_to_caller, total_number_of_bytes,
+ total_number_of_free_bytes;
+ if (!GetDiskFreeSpaceExW(dir.c_str(), &free_bytes_available_to_caller,
+ &total_number_of_bytes, &total_number_of_free_bytes))
+ return set_errno();
+ buf->f_frsize = 1;
+ buf->f_blocks = total_number_of_bytes.QuadPart;
+ buf->f_bfree = total_number_of_free_bytes.QuadPart;
+ buf->f_bavail = free_bytes_available_to_caller.QuadPart;
+ return 0;
+}
+
+wchar_t *getcwd(wchar_t *buff, size_t size) { return _wgetcwd(buff, size); }
+
+wchar_t *realpath(const wchar_t *path, wchar_t *resolved_name) {
+ // Only expected to be used with us allocating the buffer.
+ _LIBCPP_ASSERT(resolved_name == nullptr,
+ "Windows realpath() assumes a null resolved_name");
+
+ WinHandle h(path, FILE_READ_ATTRIBUTES, 0);
+ if (!h) {
+ set_errno();
+ return nullptr;
+ }
+ size_t buff_size = MAX_PATH + 10;
+ std::unique_ptr<wchar_t, decltype(&::free)> buff(
+ static_cast<wchar_t *>(malloc(buff_size * sizeof(wchar_t))), &::free);
+ DWORD retval = GetFinalPathNameByHandleW(
+ h, buff.get(), buff_size, FILE_NAME_NORMALIZED | VOLUME_NAME_DOS);
+ if (retval > buff_size) {
+ buff_size = retval;
+ buff.reset(static_cast<wchar_t *>(malloc(buff_size * sizeof(wchar_t))));
+ retval = GetFinalPathNameByHandleW(h, buff.get(), buff_size,
+ FILE_NAME_NORMALIZED | VOLUME_NAME_DOS);
+ }
+ if (!retval) {
+ set_errno();
+ return nullptr;
+ }
+ wchar_t *ptr = buff.get();
+ if (!wcsncmp(ptr, L"\\\\?\\", 4)) {
+ if (ptr[5] == ':') { // \\?\X: -> X:
+ memmove(&ptr[0], &ptr[4], (wcslen(&ptr[4]) + 1) * sizeof(wchar_t));
+ } else if (!wcsncmp(&ptr[4], L"UNC\\", 4)) { // \\?\UNC\server -> \\server
+ wcscpy(&ptr[0], L"\\\\");
+ memmove(&ptr[2], &ptr[8], (wcslen(&ptr[8]) + 1) * sizeof(wchar_t));
+ }
+ }
+ return buff.release();
+}
+
+#define AT_FDCWD -1
+#define AT_SYMLINK_NOFOLLOW 1
+using ModeT = int;
+
+int fchmod_handle(HANDLE h, int perms) {
+ FILE_BASIC_INFO basic;
+ if (!GetFileInformationByHandleEx(h, FileBasicInfo, &basic, sizeof(basic)))
+ return set_errno();
+ DWORD orig_attributes = basic.FileAttributes;
+ basic.FileAttributes &= ~FILE_ATTRIBUTE_READONLY;
+ if ((perms & 0222) == 0)
+ basic.FileAttributes |= FILE_ATTRIBUTE_READONLY;
+ if (basic.FileAttributes != orig_attributes &&
+ !SetFileInformationByHandle(h, FileBasicInfo, &basic, sizeof(basic)))
+ return set_errno();
+ return 0;
+}
+
+int fchmodat(int fd, const wchar_t *path, int perms, int flag) {
+ DWORD attributes = GetFileAttributesW(path);
+ if (attributes == INVALID_FILE_ATTRIBUTES)
+ return set_errno();
+ if (attributes & FILE_ATTRIBUTE_REPARSE_POINT &&
+ !(flag & AT_SYMLINK_NOFOLLOW)) {
+ // If the file is a symlink, and we are supposed to operate on the target
+ // of the symlink, we need to open a handle to it, without the
+ // FILE_FLAG_OPEN_REPARSE_POINT flag, to open the destination of the
+ // symlink, and operate on it via the handle.
+ detail::WinHandle h(path, FILE_READ_ATTRIBUTES | FILE_WRITE_ATTRIBUTES, 0);
+ if (!h)
+ return set_errno();
+ return fchmod_handle(h, perms);
+ } else {
+ // For a non-symlink, or if operating on the symlink itself instead of
+ // its target, we can use SetFileAttributesW, saving a few calls.
+ DWORD orig_attributes = attributes;
+ attributes &= ~FILE_ATTRIBUTE_READONLY;
+ if ((perms & 0222) == 0)
+ attributes |= FILE_ATTRIBUTE_READONLY;
+ if (attributes != orig_attributes && !SetFileAttributesW(path, attributes))
+ return set_errno();
+ }
+ return 0;
+}
+
+int fchmod(int fd, int perms) {
+ HANDLE h = reinterpret_cast<HANDLE>(_get_osfhandle(fd));
+ return fchmod_handle(h, perms);
+}
+
+#define MAX_SYMLINK_SIZE MAXIMUM_REPARSE_DATA_BUFFER_SIZE
+using SSizeT = ::int64_t;
+
+SSizeT readlink(const wchar_t *path, wchar_t *ret_buf, size_t bufsize) {
+ uint8_t buf[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
+ detail::WinHandle h(path, FILE_READ_ATTRIBUTES, FILE_FLAG_OPEN_REPARSE_POINT);
+ if (!h)
+ return set_errno();
+ DWORD out;
+ if (!DeviceIoControl(h, FSCTL_GET_REPARSE_POINT, nullptr, 0, buf, sizeof(buf),
+ &out, 0))
+ return set_errno();
+ const auto *reparse = reinterpret_cast<LIBCPP_REPARSE_DATA_BUFFER *>(buf);
+ size_t path_buf_offset = offsetof(LIBCPP_REPARSE_DATA_BUFFER,
+ SymbolicLinkReparseBuffer.PathBuffer[0]);
+ if (out < path_buf_offset) {
+ errno = EINVAL;
+ return -1;
+ }
+ if (reparse->ReparseTag != IO_REPARSE_TAG_SYMLINK) {
+ errno = EINVAL;
+ return -1;
+ }
+ const auto &symlink = reparse->SymbolicLinkReparseBuffer;
+ unsigned short name_offset, name_length;
+ if (symlink.PrintNameLength == 0) {
+ name_offset = symlink.SubstituteNameOffset;
+ name_length = symlink.SubstituteNameLength;
+ } else {
+ name_offset = symlink.PrintNameOffset;
+ name_length = symlink.PrintNameLength;
+ }
+ // name_offset/length are expressed in bytes, not in wchar_t
+ if (path_buf_offset + name_offset + name_length > out) {
+ errno = EINVAL;
+ return -1;
+ }
+ if (name_length / sizeof(wchar_t) > bufsize) {
+ errno = ENOMEM;
+ return -1;
+ }
+ memcpy(ret_buf, &symlink.PathBuffer[name_offset / sizeof(wchar_t)],
+ name_length);
+ return name_length / sizeof(wchar_t);
+}
+
+#else
+int symlink_file(const char *oldname, const char *newname) {
+ return ::symlink(oldname, newname);
+}
+int symlink_dir(const char *oldname, const char *newname) {
+ return ::symlink(oldname, newname);
+}
+using ::chdir;
+using ::close;
+using ::fchmod;
+#if defined(AT_SYMLINK_NOFOLLOW) && defined(AT_FDCWD)
+using ::fchmodat;
+#endif
+using ::fstat;
+using ::ftruncate;
+using ::getcwd;
+using ::link;
+using ::lstat;
+using ::mkdir;
+using ::open;
+using ::readlink;
+using ::realpath;
+using ::remove;
+using ::rename;
+using ::stat;
+using ::statvfs;
+using ::truncate;
+
+#define O_BINARY 0
+
+using StatVFS = struct statvfs;
+using ModeT = ::mode_t;
+using SSizeT = ::ssize_t;
+
+#endif
+
+} // namespace
+} // end namespace detail
+
+_LIBCPP_END_NAMESPACE_FILESYSTEM
+
+#endif // POSIX_COMPAT_H
diff --git a/lib/libcxx/src/format.cpp b/lib/libcxx/src/format.cpp
new file mode 100644
index 0000000000..c36c20e60a
--- /dev/null
+++ b/lib/libcxx/src/format.cpp
@@ -0,0 +1,19 @@
+//===------------------------- format.cpp ---------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "format"
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+#if _LIBCPP_STD_VER > 17
+
+format_error::~format_error() noexcept = default;
+
+#endif //_LIBCPP_STD_VER > 17
+
+_LIBCPP_END_NAMESPACE_STD
diff --git a/lib/libcxx/src/functional.cpp b/lib/libcxx/src/functional.cpp
index 555d2c53f2..cc5f43a9f2 100644
--- a/lib/libcxx/src/functional.cpp
+++ b/lib/libcxx/src/functional.cpp
@@ -11,12 +11,12 @@
_LIBCPP_BEGIN_NAMESPACE_STD
#ifdef _LIBCPP_ABI_BAD_FUNCTION_CALL_KEY_FUNCTION
-bad_function_call::~bad_function_call() _NOEXCEPT
+bad_function_call::~bad_function_call() noexcept
{
}
const char*
-bad_function_call::what() const _NOEXCEPT
+bad_function_call::what() const noexcept
{
return "std::bad_function_call";
}
diff --git a/lib/libcxx/src/future.cpp b/lib/libcxx/src/future.cpp
index 58d0b4c247..4c59f89e56 100644
--- a/lib/libcxx/src/future.cpp
+++ b/lib/libcxx/src/future.cpp
@@ -19,12 +19,12 @@ class _LIBCPP_HIDDEN __future_error_category
: public __do_message
{
public:
- virtual const char* name() const _NOEXCEPT;
+ virtual const char* name() const noexcept;
virtual string message(int ev) const;
};
const char*
-__future_error_category::name() const _NOEXCEPT
+__future_error_category::name() const noexcept
{
return "future";
}
@@ -65,7 +65,7 @@ __future_error_category::message(int ev) const
#endif
const error_category&
-future_category() _NOEXCEPT
+future_category() noexcept
{
static __future_error_category __f;
return __f;
@@ -77,12 +77,12 @@ future_error::future_error(error_code __ec)
{
}
-future_error::~future_error() _NOEXCEPT
+future_error::~future_error() noexcept
{
}
void
-__assoc_sub_state::__on_zero_shared() _NOEXCEPT
+__assoc_sub_state::__on_zero_shared() noexcept
{
delete this;
}
diff --git a/lib/libcxx/src/include/config_elast.h b/lib/libcxx/src/include/config_elast.h
index 3113f9fb5c..7880c733fb 100644
--- a/lib/libcxx/src/include/config_elast.h
+++ b/lib/libcxx/src/include/config_elast.h
@@ -35,8 +35,12 @@
// No _LIBCPP_ELAST needed on Apple
#elif defined(__sun__)
#define _LIBCPP_ELAST ESTALE
+#elif defined(__MVS__)
+#define _LIBCPP_ELAST 1160
#elif defined(_LIBCPP_MSVCRT_LIKE)
#define _LIBCPP_ELAST (_sys_nerr - 1)
+#elif defined(_AIX)
+#define _LIBCPP_ELAST 127
#else
// Warn here so that the person doing the libcxx port has an easier time:
#warning ELAST for this platform not yet implemented
diff --git a/lib/libcxx/src/include/refstring.h b/lib/libcxx/src/include/refstring.h
index cefd7caf0f..ad6cd162fb 100644
--- a/lib/libcxx/src/include/refstring.h
+++ b/lib/libcxx/src/include/refstring.h
@@ -55,7 +55,7 @@ inline char * data_from_rep(_Rep_base *rep) noexcept {
#if defined(_LIBCPP_CHECK_FOR_GCC_EMPTY_STRING_STORAGE)
inline
-const char* compute_gcc_empty_string_storage() _NOEXCEPT
+const char* compute_gcc_empty_string_storage() noexcept
{
void* handle = dlopen("/usr/lib/libstdc++.6.dylib", RTLD_NOLOAD);
if (handle == nullptr)
@@ -68,7 +68,7 @@ const char* compute_gcc_empty_string_storage() _NOEXCEPT
inline
const char*
-get_gcc_empty_string_storage() _NOEXCEPT
+get_gcc_empty_string_storage() noexcept
{
static const char* p = compute_gcc_empty_string_storage();
return p;
@@ -92,7 +92,7 @@ __libcpp_refstring::__libcpp_refstring(const char* msg) {
}
inline
-__libcpp_refstring::__libcpp_refstring(const __libcpp_refstring &s) _NOEXCEPT
+__libcpp_refstring::__libcpp_refstring(const __libcpp_refstring &s) noexcept
: __imp_(s.__imp_)
{
if (__uses_refcount())
@@ -100,7 +100,7 @@ __libcpp_refstring::__libcpp_refstring(const __libcpp_refstring &s) _NOEXCEPT
}
inline
-__libcpp_refstring& __libcpp_refstring::operator=(__libcpp_refstring const& s) _NOEXCEPT {
+__libcpp_refstring& __libcpp_refstring::operator=(__libcpp_refstring const& s) noexcept {
bool adjust_old_count = __uses_refcount();
struct _Rep_base *old_rep = rep_from_data(__imp_);
__imp_ = s.__imp_;
diff --git a/lib/libcxx/src/include/sso_allocator.h b/lib/libcxx/src/include/sso_allocator.h
new file mode 100644
index 0000000000..2baf599c5c
--- /dev/null
+++ b/lib/libcxx/src/include/sso_allocator.h
@@ -0,0 +1,77 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP_SSO_ALLOCATOR_H
+#define _LIBCPP_SSO_ALLOCATOR_H
+
+#include <__config>
+#include <memory>
+#include <new>
+#include <type_traits>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+template <class _Tp, size_t _Np> class _LIBCPP_HIDDEN __sso_allocator;
+
+template <size_t _Np>
+class _LIBCPP_HIDDEN __sso_allocator<void, _Np>
+{
+public:
+ typedef const void* const_pointer;
+ typedef void value_type;
+};
+
+template <class _Tp, size_t _Np>
+class _LIBCPP_HIDDEN __sso_allocator
+{
+ typename aligned_storage<sizeof(_Tp) * _Np>::type buf_;
+ bool __allocated_;
+public:
+ typedef size_t size_type;
+ typedef _Tp* pointer;
+ typedef _Tp value_type;
+
+ _LIBCPP_INLINE_VISIBILITY __sso_allocator() throw() : __allocated_(false) {}
+ _LIBCPP_INLINE_VISIBILITY __sso_allocator(const __sso_allocator&) throw() : __allocated_(false) {}
+ template <class _Up> _LIBCPP_INLINE_VISIBILITY __sso_allocator(const __sso_allocator<_Up, _Np>&) throw()
+ : __allocated_(false) {}
+private:
+ __sso_allocator& operator=(const __sso_allocator&);
+public:
+ _LIBCPP_INLINE_VISIBILITY pointer allocate(size_type __n, typename __sso_allocator<void, _Np>::const_pointer = nullptr)
+ {
+ if (!__allocated_ && __n <= _Np)
+ {
+ __allocated_ = true;
+ return (pointer)&buf_;
+ }
+ return allocator<_Tp>().allocate(__n);
+ }
+ _LIBCPP_INLINE_VISIBILITY void deallocate(pointer __p, size_type __n)
+ {
+ if (__p == (pointer)&buf_)
+ __allocated_ = false;
+ else
+ allocator<_Tp>().deallocate(__p, __n);
+ }
+ _LIBCPP_INLINE_VISIBILITY size_type max_size() const throw() {return size_type(~0) / sizeof(_Tp);}
+
+ _LIBCPP_INLINE_VISIBILITY
+ bool operator==(const __sso_allocator& __a) const {return &buf_ == &__a.buf_;}
+ _LIBCPP_INLINE_VISIBILITY
+ bool operator!=(const __sso_allocator& __a) const {return &buf_ != &__a.buf_;}
+};
+
+_LIBCPP_END_NAMESPACE_STD
+
+#endif // _LIBCPP_SSO_ALLOCATOR_H
diff --git a/lib/libcxx/src/ios.cpp b/lib/libcxx/src/ios.cpp
index 3a92964657..a8a99015a9 100644
--- a/lib/libcxx/src/ios.cpp
+++ b/lib/libcxx/src/ios.cpp
@@ -27,12 +27,12 @@ class _LIBCPP_HIDDEN __iostream_category
: public __do_message
{
public:
- virtual const char* name() const _NOEXCEPT;
+ virtual const char* name() const noexcept;
virtual string message(int ev) const;
};
const char*
-__iostream_category::name() const _NOEXCEPT
+__iostream_category::name() const noexcept
{
return "iostream";
}
@@ -43,14 +43,14 @@ __iostream_category::message(int ev) const
if (ev != static_cast<int>(io_errc::stream)
#ifdef _LIBCPP_ELAST
&& ev <= _LIBCPP_ELAST
-#endif // _LIBCPP_ELAST
+#endif // _LIBCPP_ELAST
)
return __do_message::message(ev);
return string("unspecified iostream_category error");
}
const error_category&
-iostream_category() _NOEXCEPT
+iostream_category() noexcept
{
static __iostream_category s;
return s;
@@ -387,7 +387,7 @@ ios_base::move(ios_base& rhs)
}
void
-ios_base::swap(ios_base& rhs) _NOEXCEPT
+ios_base::swap(ios_base& rhs) noexcept
{
_VSTD::swap(__fmtflags_, rhs.__fmtflags_);
_VSTD::swap(__precision_, rhs.__precision_);
@@ -416,7 +416,7 @@ ios_base::__set_badbit_and_consider_rethrow()
#ifndef _LIBCPP_NO_EXCEPTIONS
if (__exceptions_ & badbit)
throw;
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
}
void
@@ -426,7 +426,7 @@ ios_base::__set_failbit_and_consider_rethrow()
#ifndef _LIBCPP_NO_EXCEPTIONS
if (__exceptions_ & failbit)
throw;
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
}
bool
diff --git a/lib/libcxx/src/locale.cpp b/lib/libcxx/src/locale.cpp
index 989e522980..72982aa7d7 100644
--- a/lib/libcxx/src/locale.cpp
+++ b/lib/libcxx/src/locale.cpp
@@ -27,7 +27,6 @@
#define _CTYPE_DISABLE_MACROS
#endif
#include "cwctype"
-#include "__sso_allocator"
#if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
#include "__support/win32/locale_win32.h"
#elif !defined(__BIONIC__) && !defined(__NuttX__)
@@ -36,6 +35,7 @@
#include <stdlib.h>
#include <stdio.h>
#include "include/atomic_support.h"
+#include "include/sso_allocator.h"
#include "__undef_macros"
// On Linux, wint_t and wchar_t have different signed-ness, and this causes
@@ -206,7 +206,7 @@ _LIBCPP_SUPPRESS_DEPRECATED_PUSH
install(&make<codecvt<char16_t, char, mbstate_t> >(1u));
install(&make<codecvt<char32_t, char, mbstate_t> >(1u));
_LIBCPP_SUPPRESS_DEPRECATED_POP
-#ifndef _LIBCPP_NO_HAS_CHAR8_T
+#ifndef _LIBCPP_HAS_NO_CHAR8_T
install(&make<codecvt<char16_t, char8_t, mbstate_t> >(1u));
install(&make<codecvt<char32_t, char8_t, mbstate_t> >(1u));
#endif
@@ -240,7 +240,7 @@ locale::__imp::__imp(const string& name, size_t refs)
#ifndef _LIBCPP_NO_EXCEPTIONS
try
{
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
facets_ = locale::classic().__locale_->facets_;
for (unsigned i = 0; i < facets_.size(); ++i)
if (facets_[i])
@@ -255,7 +255,7 @@ _LIBCPP_SUPPRESS_DEPRECATED_PUSH
install(new codecvt_byname<char16_t, char, mbstate_t>(name_));
install(new codecvt_byname<char32_t, char, mbstate_t>(name_));
_LIBCPP_SUPPRESS_DEPRECATED_POP
-#ifndef _LIBCPP_NO_HAS_CHAR8_T
+#ifndef _LIBCPP_HAS_NO_CHAR8_T
install(new codecvt_byname<char16_t, char8_t, mbstate_t>(name_));
install(new codecvt_byname<char32_t, char8_t, mbstate_t>(name_));
#endif
@@ -280,7 +280,7 @@ _LIBCPP_SUPPRESS_DEPRECATED_POP
facets_[i]->__release_shared();
throw;
}
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
}
// NOTE avoid the `base class should be explicitly initialized in the
@@ -315,7 +315,7 @@ locale::__imp::__imp(const __imp& other, const string& name, locale::category c)
#ifndef _LIBCPP_NO_EXCEPTIONS
try
{
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
if (c & locale::collate)
{
install(new collate_byname<char>(name));
@@ -331,7 +331,7 @@ _LIBCPP_SUPPRESS_DEPRECATED_PUSH
install(new codecvt_byname<char16_t, char, mbstate_t>(name));
install(new codecvt_byname<char32_t, char, mbstate_t>(name));
_LIBCPP_SUPPRESS_DEPRECATED_POP
-#ifndef _LIBCPP_NO_HAS_CHAR8_T
+#ifndef _LIBCPP_HAS_NO_CHAR8_T
install(new codecvt_byname<char16_t, char8_t, mbstate_t>(name));
install(new codecvt_byname<char32_t, char8_t, mbstate_t>(name));
#endif
@@ -369,7 +369,7 @@ _LIBCPP_SUPPRESS_DEPRECATED_POP
facets_[i]->__release_shared();
throw;
}
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
}
template<class F>
@@ -392,7 +392,7 @@ locale::__imp::__imp(const __imp& other, const __imp& one, locale::category c)
#ifndef _LIBCPP_NO_EXCEPTIONS
try
{
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
if (c & locale::collate)
{
install_from<_VSTD::collate<char> >(one);
@@ -407,7 +407,7 @@ _LIBCPP_SUPPRESS_DEPRECATED_PUSH
install_from<_VSTD::codecvt<char16_t, char, mbstate_t> >(one);
install_from<_VSTD::codecvt<char32_t, char, mbstate_t> >(one);
_LIBCPP_SUPPRESS_DEPRECATED_POP
-#ifndef _LIBCPP_NO_HAS_CHAR8_T
+#ifndef _LIBCPP_HAS_NO_CHAR8_T
install_from<_VSTD::codecvt<char16_t, char8_t, mbstate_t> >(one);
install_from<_VSTD::codecvt<char32_t, char8_t, mbstate_t> >(one);
#endif
@@ -454,7 +454,7 @@ _LIBCPP_SUPPRESS_DEPRECATED_POP
facets_[i]->__release_shared();
throw;
}
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
}
locale::__imp::__imp(const __imp& other, facet* f, long id)
@@ -532,13 +532,13 @@ locale::__global()
return g;
}
-locale::locale() _NOEXCEPT
+locale::locale() noexcept
: __locale_(__global().__locale_)
{
__locale_->__add_shared();
}
-locale::locale(const locale& l) _NOEXCEPT
+locale::locale(const locale& l) noexcept
: __locale_(l.__locale_)
{
__locale_->__add_shared();
@@ -550,7 +550,7 @@ locale::~locale()
}
const locale&
-locale::operator=(const locale& other) _NOEXCEPT
+locale::operator=(const locale& other) noexcept
{
other.__locale_->__add_shared();
__locale_->__release_shared();
@@ -643,7 +643,7 @@ locale::facet::~facet()
}
void
-locale::facet::__on_zero_shared() _NOEXCEPT
+locale::facet::__on_zero_shared() noexcept
{
delete this;
}
@@ -1051,7 +1051,7 @@ extern "C" const int ** __ctype_toupper_loc();
#ifdef _LIBCPP_PROVIDES_DEFAULT_RUNE_TABLE
const ctype<char>::mask*
-ctype<char>::classic_table() _NOEXCEPT
+ctype<char>::classic_table() noexcept
{
static _LIBCPP_CONSTEXPR const ctype<char>::mask builtin_table[table_size] = {
cntrl, cntrl,
@@ -1131,7 +1131,7 @@ ctype<char>::classic_table() _NOEXCEPT
}
#else
const ctype<char>::mask*
-ctype<char>::classic_table() _NOEXCEPT
+ctype<char>::classic_table() noexcept
{
#if defined(__APPLE__) || defined(__FreeBSD__) || defined(__DragonFly__)
return _DefaultRuneLocale.__runetype;
@@ -1139,7 +1139,7 @@ ctype<char>::classic_table() _NOEXCEPT
return _C_ctype_tab_ + 1;
#elif defined(__GLIBC__)
return _LIBCPP_GET_C_LOCALE->__ctype_b;
-#elif __sun__
+#elif defined(__sun__)
return __ctype_mask;
#elif defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
return __pctype_func();
@@ -1163,38 +1163,38 @@ ctype<char>::classic_table() _NOEXCEPT
#if defined(__GLIBC__)
const int*
-ctype<char>::__classic_lower_table() _NOEXCEPT
+ctype<char>::__classic_lower_table() noexcept
{
return _LIBCPP_GET_C_LOCALE->__ctype_tolower;
}
const int*
-ctype<char>::__classic_upper_table() _NOEXCEPT
+ctype<char>::__classic_upper_table() noexcept
{
return _LIBCPP_GET_C_LOCALE->__ctype_toupper;
}
#elif defined(__NetBSD__)
const short*
-ctype<char>::__classic_lower_table() _NOEXCEPT
+ctype<char>::__classic_lower_table() noexcept
{
return _C_tolower_tab_ + 1;
}
const short*
-ctype<char>::__classic_upper_table() _NOEXCEPT
+ctype<char>::__classic_upper_table() noexcept
{
return _C_toupper_tab_ + 1;
}
#elif defined(__EMSCRIPTEN__)
const int*
-ctype<char>::__classic_lower_table() _NOEXCEPT
+ctype<char>::__classic_lower_table() noexcept
{
return *__ctype_tolower_loc();
}
const int*
-ctype<char>::__classic_upper_table() _NOEXCEPT
+ctype<char>::__classic_upper_table() noexcept
{
return *__ctype_toupper_loc();
}
@@ -1492,13 +1492,13 @@ codecvt<char, char, mbstate_t>::do_unshift(state_type&,
}
int
-codecvt<char, char, mbstate_t>::do_encoding() const _NOEXCEPT
+codecvt<char, char, mbstate_t>::do_encoding() const noexcept
{
return 1;
}
bool
-codecvt<char, char, mbstate_t>::do_always_noconv() const _NOEXCEPT
+codecvt<char, char, mbstate_t>::do_always_noconv() const noexcept
{
return true;
}
@@ -1511,7 +1511,7 @@ codecvt<char, char, mbstate_t>::do_length(state_type&,
}
int
-codecvt<char, char, mbstate_t>::do_max_length() const _NOEXCEPT
+codecvt<char, char, mbstate_t>::do_max_length() const noexcept
{
return 1;
}
@@ -1682,7 +1682,7 @@ codecvt<wchar_t, char, mbstate_t>::do_unshift(state_type& st,
}
int
-codecvt<wchar_t, char, mbstate_t>::do_encoding() const _NOEXCEPT
+codecvt<wchar_t, char, mbstate_t>::do_encoding() const noexcept
{
if (__libcpp_mbtowc_l(nullptr, nullptr, MB_LEN_MAX, __l) != 0)
return -1;
@@ -1694,7 +1694,7 @@ codecvt<wchar_t, char, mbstate_t>::do_encoding() const _NOEXCEPT
}
bool
-codecvt<wchar_t, char, mbstate_t>::do_always_noconv() const _NOEXCEPT
+codecvt<wchar_t, char, mbstate_t>::do_always_noconv() const noexcept
{
return false;
}
@@ -1726,7 +1726,7 @@ codecvt<wchar_t, char, mbstate_t>::do_length(state_type& st,
}
int
-codecvt<wchar_t, char, mbstate_t>::do_max_length() const _NOEXCEPT
+codecvt<wchar_t, char, mbstate_t>::do_max_length() const noexcept
{
return __l == 0 ? 1 : static_cast<int>(__libcpp_mb_cur_max_l(__l));
}
@@ -3169,13 +3169,13 @@ codecvt<char16_t, char, mbstate_t>::do_unshift(state_type&,
}
int
-codecvt<char16_t, char, mbstate_t>::do_encoding() const _NOEXCEPT
+codecvt<char16_t, char, mbstate_t>::do_encoding() const noexcept
{
return 0;
}
bool
-codecvt<char16_t, char, mbstate_t>::do_always_noconv() const _NOEXCEPT
+codecvt<char16_t, char, mbstate_t>::do_always_noconv() const noexcept
{
return false;
}
@@ -3190,12 +3190,12 @@ codecvt<char16_t, char, mbstate_t>::do_length(state_type&,
}
int
-codecvt<char16_t, char, mbstate_t>::do_max_length() const _NOEXCEPT
+codecvt<char16_t, char, mbstate_t>::do_max_length() const noexcept
{
return 4;
}
-#ifndef _LIBCPP_NO_HAS_CHAR8_T
+#ifndef _LIBCPP_HAS_NO_CHAR8_T
// template <> class codecvt<char16_t, char8_t, mbstate_t>
@@ -3248,13 +3248,13 @@ codecvt<char16_t, char8_t, mbstate_t>::do_unshift(state_type&,
}
int
-codecvt<char16_t, char8_t, mbstate_t>::do_encoding() const _NOEXCEPT
+codecvt<char16_t, char8_t, mbstate_t>::do_encoding() const noexcept
{
return 0;
}
bool
-codecvt<char16_t, char8_t, mbstate_t>::do_always_noconv() const _NOEXCEPT
+codecvt<char16_t, char8_t, mbstate_t>::do_always_noconv() const noexcept
{
return false;
}
@@ -3269,7 +3269,7 @@ codecvt<char16_t, char8_t, mbstate_t>::do_length(state_type&,
}
int
-codecvt<char16_t, char8_t, mbstate_t>::do_max_length() const _NOEXCEPT
+codecvt<char16_t, char8_t, mbstate_t>::do_max_length() const noexcept
{
return 4;
}
@@ -3327,13 +3327,13 @@ codecvt<char32_t, char, mbstate_t>::do_unshift(state_type&,
}
int
-codecvt<char32_t, char, mbstate_t>::do_encoding() const _NOEXCEPT
+codecvt<char32_t, char, mbstate_t>::do_encoding() const noexcept
{
return 0;
}
bool
-codecvt<char32_t, char, mbstate_t>::do_always_noconv() const _NOEXCEPT
+codecvt<char32_t, char, mbstate_t>::do_always_noconv() const noexcept
{
return false;
}
@@ -3348,12 +3348,12 @@ codecvt<char32_t, char, mbstate_t>::do_length(state_type&,
}
int
-codecvt<char32_t, char, mbstate_t>::do_max_length() const _NOEXCEPT
+codecvt<char32_t, char, mbstate_t>::do_max_length() const noexcept
{
return 4;
}
-#ifndef _LIBCPP_NO_HAS_CHAR8_T
+#ifndef _LIBCPP_HAS_NO_CHAR8_T
// template <> class codecvt<char32_t, char8_t, mbstate_t>
@@ -3406,13 +3406,13 @@ codecvt<char32_t, char8_t, mbstate_t>::do_unshift(state_type&,
}
int
-codecvt<char32_t, char8_t, mbstate_t>::do_encoding() const _NOEXCEPT
+codecvt<char32_t, char8_t, mbstate_t>::do_encoding() const noexcept
{
return 0;
}
bool
-codecvt<char32_t, char8_t, mbstate_t>::do_always_noconv() const _NOEXCEPT
+codecvt<char32_t, char8_t, mbstate_t>::do_always_noconv() const noexcept
{
return false;
}
@@ -3427,7 +3427,7 @@ codecvt<char32_t, char8_t, mbstate_t>::do_length(state_type&,
}
int
-codecvt<char32_t, char8_t, mbstate_t>::do_max_length() const _NOEXCEPT
+codecvt<char32_t, char8_t, mbstate_t>::do_max_length() const noexcept
{
return 4;
}
@@ -3500,13 +3500,13 @@ __codecvt_utf8<wchar_t>::do_unshift(state_type&,
}
int
-__codecvt_utf8<wchar_t>::do_encoding() const _NOEXCEPT
+__codecvt_utf8<wchar_t>::do_encoding() const noexcept
{
return 0;
}
bool
-__codecvt_utf8<wchar_t>::do_always_noconv() const _NOEXCEPT
+__codecvt_utf8<wchar_t>::do_always_noconv() const noexcept
{
return false;
}
@@ -3521,7 +3521,7 @@ __codecvt_utf8<wchar_t>::do_length(state_type&,
}
int
-__codecvt_utf8<wchar_t>::do_max_length() const _NOEXCEPT
+__codecvt_utf8<wchar_t>::do_max_length() const noexcept
{
if (_Mode_ & consume_header)
return 7;
@@ -3575,13 +3575,13 @@ __codecvt_utf8<char16_t>::do_unshift(state_type&,
}
int
-__codecvt_utf8<char16_t>::do_encoding() const _NOEXCEPT
+__codecvt_utf8<char16_t>::do_encoding() const noexcept
{
return 0;
}
bool
-__codecvt_utf8<char16_t>::do_always_noconv() const _NOEXCEPT
+__codecvt_utf8<char16_t>::do_always_noconv() const noexcept
{
return false;
}
@@ -3596,7 +3596,7 @@ __codecvt_utf8<char16_t>::do_length(state_type&,
}
int
-__codecvt_utf8<char16_t>::do_max_length() const _NOEXCEPT
+__codecvt_utf8<char16_t>::do_max_length() const noexcept
{
if (_Mode_ & consume_header)
return 6;
@@ -3650,13 +3650,13 @@ __codecvt_utf8<char32_t>::do_unshift(state_type&,
}
int
-__codecvt_utf8<char32_t>::do_encoding() const _NOEXCEPT
+__codecvt_utf8<char32_t>::do_encoding() const noexcept
{
return 0;
}
bool
-__codecvt_utf8<char32_t>::do_always_noconv() const _NOEXCEPT
+__codecvt_utf8<char32_t>::do_always_noconv() const noexcept
{
return false;
}
@@ -3671,7 +3671,7 @@ __codecvt_utf8<char32_t>::do_length(state_type&,
}
int
-__codecvt_utf8<char32_t>::do_max_length() const _NOEXCEPT
+__codecvt_utf8<char32_t>::do_max_length() const noexcept
{
if (_Mode_ & consume_header)
return 7;
@@ -3725,13 +3725,13 @@ __codecvt_utf16<wchar_t, false>::do_unshift(state_type&,
}
int
-__codecvt_utf16<wchar_t, false>::do_encoding() const _NOEXCEPT
+__codecvt_utf16<wchar_t, false>::do_encoding() const noexcept
{
return 0;
}
bool
-__codecvt_utf16<wchar_t, false>::do_always_noconv() const _NOEXCEPT
+__codecvt_utf16<wchar_t, false>::do_always_noconv() const noexcept
{
return false;
}
@@ -3746,7 +3746,7 @@ __codecvt_utf16<wchar_t, false>::do_length(state_type&,
}
int
-__codecvt_utf16<wchar_t, false>::do_max_length() const _NOEXCEPT
+__codecvt_utf16<wchar_t, false>::do_max_length() const noexcept
{
if (_Mode_ & consume_header)
return 6;
@@ -3800,13 +3800,13 @@ __codecvt_utf16<wchar_t, true>::do_unshift(state_type&,
}
int
-__codecvt_utf16<wchar_t, true>::do_encoding() const _NOEXCEPT
+__codecvt_utf16<wchar_t, true>::do_encoding() const noexcept
{
return 0;
}
bool
-__codecvt_utf16<wchar_t, true>::do_always_noconv() const _NOEXCEPT
+__codecvt_utf16<wchar_t, true>::do_always_noconv() const noexcept
{
return false;
}
@@ -3821,7 +3821,7 @@ __codecvt_utf16<wchar_t, true>::do_length(state_type&,
}
int
-__codecvt_utf16<wchar_t, true>::do_max_length() const _NOEXCEPT
+__codecvt_utf16<wchar_t, true>::do_max_length() const noexcept
{
if (_Mode_ & consume_header)
return 6;
@@ -3875,13 +3875,13 @@ __codecvt_utf16<char16_t, false>::do_unshift(state_type&,
}
int
-__codecvt_utf16<char16_t, false>::do_encoding() const _NOEXCEPT
+__codecvt_utf16<char16_t, false>::do_encoding() const noexcept
{
return 0;
}
bool
-__codecvt_utf16<char16_t, false>::do_always_noconv() const _NOEXCEPT
+__codecvt_utf16<char16_t, false>::do_always_noconv() const noexcept
{
return false;
}
@@ -3896,7 +3896,7 @@ __codecvt_utf16<char16_t, false>::do_length(state_type&,
}
int
-__codecvt_utf16<char16_t, false>::do_max_length() const _NOEXCEPT
+__codecvt_utf16<char16_t, false>::do_max_length() const noexcept
{
if (_Mode_ & consume_header)
return 4;
@@ -3950,13 +3950,13 @@ __codecvt_utf16<char16_t, true>::do_unshift(state_type&,
}
int
-__codecvt_utf16<char16_t, true>::do_encoding() const _NOEXCEPT
+__codecvt_utf16<char16_t, true>::do_encoding() const noexcept
{
return 0;
}
bool
-__codecvt_utf16<char16_t, true>::do_always_noconv() const _NOEXCEPT
+__codecvt_utf16<char16_t, true>::do_always_noconv() const noexcept
{
return false;
}
@@ -3971,7 +3971,7 @@ __codecvt_utf16<char16_t, true>::do_length(state_type&,
}
int
-__codecvt_utf16<char16_t, true>::do_max_length() const _NOEXCEPT
+__codecvt_utf16<char16_t, true>::do_max_length() const noexcept
{
if (_Mode_ & consume_header)
return 4;
@@ -4025,13 +4025,13 @@ __codecvt_utf16<char32_t, false>::do_unshift(state_type&,
}
int
-__codecvt_utf16<char32_t, false>::do_encoding() const _NOEXCEPT
+__codecvt_utf16<char32_t, false>::do_encoding() const noexcept
{
return 0;
}
bool
-__codecvt_utf16<char32_t, false>::do_always_noconv() const _NOEXCEPT
+__codecvt_utf16<char32_t, false>::do_always_noconv() const noexcept
{
return false;
}
@@ -4046,7 +4046,7 @@ __codecvt_utf16<char32_t, false>::do_length(state_type&,
}
int
-__codecvt_utf16<char32_t, false>::do_max_length() const _NOEXCEPT
+__codecvt_utf16<char32_t, false>::do_max_length() const noexcept
{
if (_Mode_ & consume_header)
return 6;
@@ -4100,13 +4100,13 @@ __codecvt_utf16<char32_t, true>::do_unshift(state_type&,
}
int
-__codecvt_utf16<char32_t, true>::do_encoding() const _NOEXCEPT
+__codecvt_utf16<char32_t, true>::do_encoding() const noexcept
{
return 0;
}
bool
-__codecvt_utf16<char32_t, true>::do_always_noconv() const _NOEXCEPT
+__codecvt_utf16<char32_t, true>::do_always_noconv() const noexcept
{
return false;
}
@@ -4121,7 +4121,7 @@ __codecvt_utf16<char32_t, true>::do_length(state_type&,
}
int
-__codecvt_utf16<char32_t, true>::do_max_length() const _NOEXCEPT
+__codecvt_utf16<char32_t, true>::do_max_length() const noexcept
{
if (_Mode_ & consume_header)
return 6;
@@ -4175,13 +4175,13 @@ __codecvt_utf8_utf16<wchar_t>::do_unshift(state_type&,
}
int
-__codecvt_utf8_utf16<wchar_t>::do_encoding() const _NOEXCEPT
+__codecvt_utf8_utf16<wchar_t>::do_encoding() const noexcept
{
return 0;
}
bool
-__codecvt_utf8_utf16<wchar_t>::do_always_noconv() const _NOEXCEPT
+__codecvt_utf8_utf16<wchar_t>::do_always_noconv() const noexcept
{
return false;
}
@@ -4196,7 +4196,7 @@ __codecvt_utf8_utf16<wchar_t>::do_length(state_type&,
}
int
-__codecvt_utf8_utf16<wchar_t>::do_max_length() const _NOEXCEPT
+__codecvt_utf8_utf16<wchar_t>::do_max_length() const noexcept
{
if (_Mode_ & consume_header)
return 7;
@@ -4250,13 +4250,13 @@ __codecvt_utf8_utf16<char16_t>::do_unshift(state_type&,
}
int
-__codecvt_utf8_utf16<char16_t>::do_encoding() const _NOEXCEPT
+__codecvt_utf8_utf16<char16_t>::do_encoding() const noexcept
{
return 0;
}
bool
-__codecvt_utf8_utf16<char16_t>::do_always_noconv() const _NOEXCEPT
+__codecvt_utf8_utf16<char16_t>::do_always_noconv() const noexcept
{
return false;
}
@@ -4271,7 +4271,7 @@ __codecvt_utf8_utf16<char16_t>::do_length(state_type&,
}
int
-__codecvt_utf8_utf16<char16_t>::do_max_length() const _NOEXCEPT
+__codecvt_utf8_utf16<char16_t>::do_max_length() const noexcept
{
if (_Mode_ & consume_header)
return 7;
@@ -4325,13 +4325,13 @@ __codecvt_utf8_utf16<char32_t>::do_unshift(state_type&,
}
int
-__codecvt_utf8_utf16<char32_t>::do_encoding() const _NOEXCEPT
+__codecvt_utf8_utf16<char32_t>::do_encoding() const noexcept
{
return 0;
}
bool
-__codecvt_utf8_utf16<char32_t>::do_always_noconv() const _NOEXCEPT
+__codecvt_utf8_utf16<char32_t>::do_always_noconv() const noexcept
{
return false;
}
@@ -4346,7 +4346,7 @@ __codecvt_utf8_utf16<char32_t>::do_length(state_type&,
}
int
-__codecvt_utf8_utf16<char32_t>::do_max_length() const _NOEXCEPT
+__codecvt_utf8_utf16<char32_t>::do_max_length() const noexcept
{
if (_Mode_ & consume_header)
return 7;
@@ -4597,7 +4597,10 @@ void
__num_put_base::__format_int(char* __fmtp, const char* __len, bool __signd,
ios_base::fmtflags __flags)
{
- if (__flags & ios_base::showpos)
+ if ((__flags & ios_base::showpos) &&
+ (__flags & ios_base::basefield) != ios_base::oct &&
+ (__flags & ios_base::basefield) != ios_base::hex &&
+ __signd)
*__fmtp++ = '+';
if (__flags & ios_base::showbase)
*__fmtp++ = '#';
@@ -6336,7 +6339,7 @@ template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<char, cha
template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<wchar_t, char, mbstate_t>;
template class _LIBCPP_DEPRECATED_IN_CXX20 _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<char16_t, char, mbstate_t>;
template class _LIBCPP_DEPRECATED_IN_CXX20 _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<char32_t, char, mbstate_t>;
-#ifndef _LIBCPP_NO_HAS_CHAR8_T
+#ifndef _LIBCPP_HAS_NO_CHAR8_T
template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<char16_t, char8_t, mbstate_t>;
template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<char32_t, char8_t, mbstate_t>;
#endif
diff --git a/lib/libcxx/src/memory.cpp b/lib/libcxx/src/memory.cpp
index 5a5894fd94..9bd27df268 100644
--- a/lib/libcxx/src/memory.cpp
+++ b/lib/libcxx/src/memory.cpp
@@ -20,10 +20,10 @@ _LIBCPP_BEGIN_NAMESPACE_STD
const allocator_arg_t allocator_arg = allocator_arg_t();
-bad_weak_ptr::~bad_weak_ptr() _NOEXCEPT {}
+bad_weak_ptr::~bad_weak_ptr() noexcept {}
const char*
-bad_weak_ptr::what() const _NOEXCEPT
+bad_weak_ptr::what() const noexcept
{
return "bad_weak_ptr";
}
@@ -38,13 +38,13 @@ __shared_weak_count::~__shared_weak_count()
#if defined(_LIBCPP_DEPRECATED_ABI_LEGACY_LIBRARY_DEFINITIONS_FOR_INLINE_FUNCTIONS)
void
-__shared_count::__add_shared() _NOEXCEPT
+__shared_count::__add_shared() noexcept
{
__libcpp_atomic_refcount_increment(__shared_owners_);
}
bool
-__shared_count::__release_shared() _NOEXCEPT
+__shared_count::__release_shared() noexcept
{
if (__libcpp_atomic_refcount_decrement(__shared_owners_) == -1)
{
@@ -55,19 +55,19 @@ __shared_count::__release_shared() _NOEXCEPT
}
void
-__shared_weak_count::__add_shared() _NOEXCEPT
+__shared_weak_count::__add_shared() noexcept
{
__shared_count::__add_shared();
}
void
-__shared_weak_count::__add_weak() _NOEXCEPT
+__shared_weak_count::__add_weak() noexcept
{
__libcpp_atomic_refcount_increment(__shared_weak_owners_);
}
void
-__shared_weak_count::__release_shared() _NOEXCEPT
+__shared_weak_count::__release_shared() noexcept
{
if (__shared_count::__release_shared())
__release_weak();
@@ -76,7 +76,7 @@ __shared_weak_count::__release_shared() _NOEXCEPT
#endif // _LIBCPP_DEPRECATED_ABI_LEGACY_LIBRARY_DEFINITIONS_FOR_INLINE_FUNCTIONS
void
-__shared_weak_count::__release_weak() _NOEXCEPT
+__shared_weak_count::__release_weak() noexcept
{
// NOTE: The acquire load here is an optimization of the very
// common case where a shared pointer is being destructed while
@@ -111,7 +111,7 @@ __shared_weak_count::__release_weak() _NOEXCEPT
}
__shared_weak_count*
-__shared_weak_count::lock() _NOEXCEPT
+__shared_weak_count::lock() noexcept
{
long object_owners = __libcpp_atomic_load(&__shared_owners_);
while (object_owners != -1)
@@ -125,7 +125,7 @@ __shared_weak_count::lock() _NOEXCEPT
}
const void*
-__shared_weak_count::__get_deleter(const type_info&) const _NOEXCEPT
+__shared_weak_count::__get_deleter(const type_info&) const noexcept
{
return nullptr;
}
@@ -141,13 +141,13 @@ _LIBCPP_SAFE_STATIC static __libcpp_mutex_t mut_back[__sp_mut_count] =
_LIBCPP_MUTEX_INITIALIZER, _LIBCPP_MUTEX_INITIALIZER, _LIBCPP_MUTEX_INITIALIZER, _LIBCPP_MUTEX_INITIALIZER
};
-_LIBCPP_CONSTEXPR __sp_mut::__sp_mut(void* p) _NOEXCEPT
+_LIBCPP_CONSTEXPR __sp_mut::__sp_mut(void* p) noexcept
: __lx(p)
{
}
void
-__sp_mut::lock() _NOEXCEPT
+__sp_mut::lock() noexcept
{
auto m = static_cast<__libcpp_mutex_t*>(__lx);
unsigned count = 0;
@@ -163,7 +163,7 @@ __sp_mut::lock() _NOEXCEPT
}
void
-__sp_mut::unlock() _NOEXCEPT
+__sp_mut::unlock() noexcept
{
__libcpp_mutex_unlock(static_cast<__libcpp_mutex_t*>(__lx));
}
@@ -198,13 +198,6 @@ undeclare_no_pointers(char*, size_t)
{
}
-#if !defined(_LIBCPP_ABI_POINTER_SAFETY_ENUM_TYPE)
-pointer_safety get_pointer_safety() _NOEXCEPT
-{
- return pointer_safety::relaxed;
-}
-#endif
-
void*
__undeclare_reachable(void* p)
{
diff --git a/lib/libcxx/src/mutex.cpp b/lib/libcxx/src/mutex.cpp
index 27a4fd8927..36362e34f3 100644
--- a/lib/libcxx/src/mutex.cpp
+++ b/lib/libcxx/src/mutex.cpp
@@ -36,13 +36,13 @@ mutex::lock()
}
bool
-mutex::try_lock() _NOEXCEPT
+mutex::try_lock() noexcept
{
return __libcpp_mutex_trylock(&__m_);
}
void
-mutex::unlock() _NOEXCEPT
+mutex::unlock() noexcept
{
int ec = __libcpp_mutex_unlock(&__m_);
(void)ec;
@@ -74,7 +74,7 @@ recursive_mutex::lock()
}
void
-recursive_mutex::unlock() _NOEXCEPT
+recursive_mutex::unlock() noexcept
{
int e = __libcpp_recursive_mutex_unlock(&__m_);
(void)e;
@@ -82,7 +82,7 @@ recursive_mutex::unlock() _NOEXCEPT
}
bool
-recursive_mutex::try_lock() _NOEXCEPT
+recursive_mutex::try_lock() noexcept
{
return __libcpp_recursive_mutex_trylock(&__m_);
}
@@ -109,7 +109,7 @@ timed_mutex::lock()
}
bool
-timed_mutex::try_lock() _NOEXCEPT
+timed_mutex::try_lock() noexcept
{
unique_lock<mutex> lk(__m_, try_to_lock);
if (lk.owns_lock() && !__locked_)
@@ -121,7 +121,7 @@ timed_mutex::try_lock() _NOEXCEPT
}
void
-timed_mutex::unlock() _NOEXCEPT
+timed_mutex::unlock() noexcept
{
lock_guard<mutex> _(__m_);
__locked_ = false;
@@ -160,7 +160,7 @@ recursive_timed_mutex::lock()
}
bool
-recursive_timed_mutex::try_lock() _NOEXCEPT
+recursive_timed_mutex::try_lock() noexcept
{
__thread_id id = this_thread::get_id();
unique_lock<mutex> lk(__m_, try_to_lock);
@@ -176,7 +176,7 @@ recursive_timed_mutex::try_lock() _NOEXCEPT
}
void
-recursive_timed_mutex::unlock() _NOEXCEPT
+recursive_timed_mutex::unlock() noexcept
{
unique_lock<mutex> lk(__m_);
if (--__count_ == 0)
@@ -209,7 +209,7 @@ void __call_once(volatile once_flag::_State_type& flag, void* arg,
#ifndef _LIBCPP_NO_EXCEPTIONS
try
{
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
flag = 1;
func(arg);
flag = ~once_flag::_State_type(0);
@@ -220,7 +220,7 @@ void __call_once(volatile once_flag::_State_type& flag, void* arg,
flag = 0;
throw;
}
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
}
#else // !_LIBCPP_HAS_NO_THREADS
__libcpp_mutex_lock(&mut);
@@ -231,7 +231,7 @@ void __call_once(volatile once_flag::_State_type& flag, void* arg,
#ifndef _LIBCPP_NO_EXCEPTIONS
try
{
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
__libcpp_relaxed_store(&flag, once_flag::_State_type(1));
__libcpp_mutex_unlock(&mut);
func(arg);
@@ -250,7 +250,7 @@ void __call_once(volatile once_flag::_State_type& flag, void* arg,
__libcpp_condvar_broadcast(&cv);
throw;
}
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
}
else
__libcpp_mutex_unlock(&mut);
diff --git a/lib/libcxx/src/mutex_destructor.cpp b/lib/libcxx/src/mutex_destructor.cpp
index 2038d2bbe2..07197c3fb4 100644
--- a/lib/libcxx/src/mutex_destructor.cpp
+++ b/lib/libcxx/src/mutex_destructor.cpp
@@ -41,7 +41,7 @@ public:
};
-mutex::~mutex() _NOEXCEPT
+mutex::~mutex() noexcept
{
__libcpp_mutex_destroy(&__m_);
}
diff --git a/lib/libcxx/src/new.cpp b/lib/libcxx/src/new.cpp
index 9d01330ba7..5486815abb 100644
--- a/lib/libcxx/src/new.cpp
+++ b/lib/libcxx/src/new.cpp
@@ -83,20 +83,20 @@ operator new(std::size_t size) _THROW_BAD_ALLOC
_LIBCPP_WEAK
void*
-operator new(size_t size, const std::nothrow_t&) _NOEXCEPT
+operator new(size_t size, const std::nothrow_t&) noexcept
{
void* p = nullptr;
#ifndef _LIBCPP_NO_EXCEPTIONS
try
{
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
p = ::operator new(size);
#ifndef _LIBCPP_NO_EXCEPTIONS
}
catch (...)
{
}
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
return p;
}
@@ -109,61 +109,61 @@ operator new[](size_t size) _THROW_BAD_ALLOC
_LIBCPP_WEAK
void*
-operator new[](size_t size, const std::nothrow_t&) _NOEXCEPT
+operator new[](size_t size, const std::nothrow_t&) noexcept
{
void* p = nullptr;
#ifndef _LIBCPP_NO_EXCEPTIONS
try
{
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
p = ::operator new[](size);
#ifndef _LIBCPP_NO_EXCEPTIONS
}
catch (...)
{
}
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
return p;
}
_LIBCPP_WEAK
void
-operator delete(void* ptr) _NOEXCEPT
+operator delete(void* ptr) noexcept
{
::free(ptr);
}
_LIBCPP_WEAK
void
-operator delete(void* ptr, const std::nothrow_t&) _NOEXCEPT
+operator delete(void* ptr, const std::nothrow_t&) noexcept
{
::operator delete(ptr);
}
_LIBCPP_WEAK
void
-operator delete(void* ptr, size_t) _NOEXCEPT
+operator delete(void* ptr, size_t) noexcept
{
::operator delete(ptr);
}
_LIBCPP_WEAK
void
-operator delete[] (void* ptr) _NOEXCEPT
+operator delete[] (void* ptr) noexcept
{
::operator delete(ptr);
}
_LIBCPP_WEAK
void
-operator delete[] (void* ptr, const std::nothrow_t&) _NOEXCEPT
+operator delete[] (void* ptr, const std::nothrow_t&) noexcept
{
::operator delete[](ptr);
}
_LIBCPP_WEAK
void
-operator delete[] (void* ptr, size_t) _NOEXCEPT
+operator delete[] (void* ptr, size_t) noexcept
{
::operator delete[](ptr);
}
@@ -204,20 +204,20 @@ operator new(std::size_t size, std::align_val_t alignment) _THROW_BAD_ALLOC
_LIBCPP_WEAK
void*
-operator new(size_t size, std::align_val_t alignment, const std::nothrow_t&) _NOEXCEPT
+operator new(size_t size, std::align_val_t alignment, const std::nothrow_t&) noexcept
{
void* p = nullptr;
#ifndef _LIBCPP_NO_EXCEPTIONS
try
{
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
p = ::operator new(size, alignment);
#ifndef _LIBCPP_NO_EXCEPTIONS
}
catch (...)
{
}
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
return p;
}
@@ -230,61 +230,61 @@ operator new[](size_t size, std::align_val_t alignment) _THROW_BAD_ALLOC
_LIBCPP_WEAK
void*
-operator new[](size_t size, std::align_val_t alignment, const std::nothrow_t&) _NOEXCEPT
+operator new[](size_t size, std::align_val_t alignment, const std::nothrow_t&) noexcept
{
void* p = nullptr;
#ifndef _LIBCPP_NO_EXCEPTIONS
try
{
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
p = ::operator new[](size, alignment);
#ifndef _LIBCPP_NO_EXCEPTIONS
}
catch (...)
{
}
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
return p;
}
_LIBCPP_WEAK
void
-operator delete(void* ptr, std::align_val_t) _NOEXCEPT
+operator delete(void* ptr, std::align_val_t) noexcept
{
std::__libcpp_aligned_free(ptr);
}
_LIBCPP_WEAK
void
-operator delete(void* ptr, std::align_val_t alignment, const std::nothrow_t&) _NOEXCEPT
+operator delete(void* ptr, std::align_val_t alignment, const std::nothrow_t&) noexcept
{
::operator delete(ptr, alignment);
}
_LIBCPP_WEAK
void
-operator delete(void* ptr, size_t, std::align_val_t alignment) _NOEXCEPT
+operator delete(void* ptr, size_t, std::align_val_t alignment) noexcept
{
::operator delete(ptr, alignment);
}
_LIBCPP_WEAK
void
-operator delete[] (void* ptr, std::align_val_t alignment) _NOEXCEPT
+operator delete[] (void* ptr, std::align_val_t alignment) noexcept
{
::operator delete(ptr, alignment);
}
_LIBCPP_WEAK
void
-operator delete[] (void* ptr, std::align_val_t alignment, const std::nothrow_t&) _NOEXCEPT
+operator delete[] (void* ptr, std::align_val_t alignment, const std::nothrow_t&) noexcept
{
::operator delete[](ptr, alignment);
}
_LIBCPP_WEAK
void
-operator delete[] (void* ptr, size_t, std::align_val_t alignment) _NOEXCEPT
+operator delete[] (void* ptr, size_t, std::align_val_t alignment) noexcept
{
::operator delete[](ptr, alignment);
}
diff --git a/lib/libcxx/src/optional.cpp b/lib/libcxx/src/optional.cpp
index 86d013b350..39405bec12 100644
--- a/lib/libcxx/src/optional.cpp
+++ b/lib/libcxx/src/optional.cpp
@@ -12,9 +12,9 @@
namespace std
{
-bad_optional_access::~bad_optional_access() _NOEXCEPT = default;
+bad_optional_access::~bad_optional_access() noexcept = default;
-const char* bad_optional_access::what() const _NOEXCEPT {
+const char* bad_optional_access::what() const noexcept {
return "bad_optional_access";
}
@@ -34,9 +34,9 @@ public:
bad_optional_access() : std::logic_error("Bad optional Access") {}
// Get the key function ~bad_optional_access() into the dylib
- virtual ~bad_optional_access() _NOEXCEPT;
+ virtual ~bad_optional_access() noexcept;
};
-bad_optional_access::~bad_optional_access() _NOEXCEPT = default;
+bad_optional_access::~bad_optional_access() noexcept = default;
_LIBCPP_END_NAMESPACE_EXPERIMENTAL
diff --git a/lib/libcxx/src/random.cpp b/lib/libcxx/src/random.cpp
index 29aa43b1e1..8ea080842e 100644
--- a/lib/libcxx/src/random.cpp
+++ b/lib/libcxx/src/random.cpp
@@ -175,7 +175,7 @@ random_device::operator()()
#endif
double
-random_device::entropy() const _NOEXCEPT
+random_device::entropy() const noexcept
{
#if defined(_LIBCPP_USING_DEV_RANDOM) && defined(RNDGETENTCNT)
int ent;
diff --git a/lib/libcxx/src/string.cpp b/lib/libcxx/src/string.cpp
index 5105594cf3..97a773f79a 100644
--- a/lib/libcxx/src/string.cpp
+++ b/lib/libcxx/src/string.cpp
@@ -20,6 +20,7 @@ _LIBCPP_BEGIN_NAMESPACE_STD
template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __basic_string_common<true>;
+#define _LIBCPP_EXTERN_TEMPLATE_DEFINE(...) template __VA_ARGS__;
#ifdef _LIBCPP_ABI_STRING_OPTIMIZED_EXTERNAL_INSTANTIATION
_LIBCPP_STRING_UNSTABLE_EXTERN_TEMPLATE_LIST(_LIBCPP_EXTERN_TEMPLATE_DEFINE, char)
_LIBCPP_STRING_UNSTABLE_EXTERN_TEMPLATE_LIST(_LIBCPP_EXTERN_TEMPLATE_DEFINE, wchar_t)
@@ -27,10 +28,9 @@ _LIBCPP_STRING_UNSTABLE_EXTERN_TEMPLATE_LIST(_LIBCPP_EXTERN_TEMPLATE_DEFINE, wch
_LIBCPP_STRING_V1_EXTERN_TEMPLATE_LIST(_LIBCPP_EXTERN_TEMPLATE_DEFINE, char)
_LIBCPP_STRING_V1_EXTERN_TEMPLATE_LIST(_LIBCPP_EXTERN_TEMPLATE_DEFINE, wchar_t)
#endif
+#undef _LIBCPP_EXTERN_TEMPLATE_DEFINE
-template
- string
- operator+<char, char_traits<char>, allocator<char> >(char const*, string const&);
+template string operator+<char, char_traits<char>, allocator<char> >(char const*, string const&);
namespace
{
@@ -423,7 +423,7 @@ get_swprintf()
}
template <typename S, typename V>
-S i_to_string(const V v)
+S i_to_string(V v)
{
// numeric_limits::digits10 returns value less on 1 than desired for unsigned numbers.
// For example, for 1-byte unsigned value digits10 is 2 (999 can not be represented),
diff --git a/lib/libcxx/src/support/ibm/xlocale_zos.cpp b/lib/libcxx/src/support/ibm/xlocale_zos.cpp
new file mode 100644
index 0000000000..cb3a9507eb
--- /dev/null
+++ b/lib/libcxx/src/support/ibm/xlocale_zos.cpp
@@ -0,0 +1,137 @@
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include <__support/ibm/xlocale.h>
+#include <sstream>
+#include <vector>
+
+#ifdef __cplusplus
+extern "C" {
+#endif // __cplusplus
+
+locale_t newlocale(int category_mask, const char* locale, locale_t base) {
+ // Maintain current locale name(s) to restore later.
+ std::string current_loc_name(setlocale(LC_ALL, 0));
+
+ // Check for errors.
+ if (category_mask == LC_ALL_MASK && setlocale(LC_ALL, locale) == NULL) {
+ errno = EINVAL;
+ return (locale_t)0;
+ } else {
+ for (int _Cat = 0; _Cat <= _LC_MAX; ++_Cat) {
+ if ((_CATMASK(_Cat) & category_mask) != 0 && setlocale(_Cat, locale) == NULL) {
+ setlocale(LC_ALL, current_loc_name.c_str());
+ errno = EINVAL;
+ return (locale_t)0;
+ }
+ }
+ }
+
+ // Create new locale.
+ locale_t newloc = new locale_struct();
+
+ if (base) {
+ if (category_mask != LC_ALL_MASK) {
+ // Copy base when it will not be overwritten.
+ memcpy(newloc, base, sizeof (locale_struct));
+ newloc->category_mask = category_mask | base->category_mask;
+ }
+ delete base;
+ } else {
+ newloc->category_mask = category_mask;
+ }
+
+ if (category_mask & LC_COLLATE_MASK)
+ newloc->lc_collate = locale;
+ if (category_mask & LC_CTYPE_MASK)
+ newloc->lc_ctype = locale;
+ if (category_mask & LC_MONETARY_MASK)
+ newloc->lc_monetary = locale;
+ if (category_mask & LC_NUMERIC_MASK)
+ newloc->lc_numeric = locale;
+ if (category_mask & LC_TIME_MASK)
+ newloc->lc_time = locale;
+ if (category_mask & LC_MESSAGES_MASK)
+ newloc->lc_messages = locale;
+
+ // Restore current locale.
+ setlocale(LC_ALL, current_loc_name.c_str());
+ return (locale_t)newloc;
+}
+
+void freelocale(locale_t locobj) {
+ delete locobj;
+}
+
+locale_t uselocale(locale_t newloc) {
+ // Maintain current locale name(s).
+ std::string current_loc_name(setlocale(LC_ALL, 0));
+
+ if (newloc) {
+ // Set locales and check for errors.
+ bool is_error =
+ (newloc->category_mask & LC_COLLATE_MASK &&
+ setlocale(LC_COLLATE, newloc->lc_collate.c_str()) == NULL) ||
+ (newloc->category_mask & LC_CTYPE_MASK &&
+ setlocale(LC_CTYPE, newloc->lc_ctype.c_str()) == NULL) ||
+ (newloc->category_mask & LC_MONETARY_MASK &&
+ setlocale(LC_MONETARY, newloc->lc_monetary.c_str()) == NULL) ||
+ (newloc->category_mask & LC_NUMERIC_MASK &&
+ setlocale(LC_NUMERIC, newloc->lc_numeric.c_str()) == NULL) ||
+ (newloc->category_mask & LC_TIME_MASK &&
+ setlocale(LC_TIME, newloc->lc_time.c_str()) == NULL) ||
+ (newloc->category_mask & LC_MESSAGES_MASK &&
+ setlocale(LC_MESSAGES, newloc->lc_messages.c_str()) == NULL);
+
+ if (is_error) {
+ setlocale(LC_ALL, current_loc_name.c_str());
+ errno = EINVAL;
+ return (locale_t)0;
+ }
+ }
+
+ // Construct and return previous locale.
+ locale_t previous_loc = new locale_struct();
+
+ // current_loc_name might be a comma-separated locale name list.
+ if (current_loc_name.find(',') != std::string::npos) {
+ // Tokenize locale name list.
+ const char delimiter = ',';
+ std::vector<std::string> tokenized;
+ std::stringstream ss(current_loc_name);
+ std::string s;
+
+ while (std::getline(ss, s, delimiter)) {
+ tokenized.push_back(s);
+ }
+
+ _LIBCPP_ASSERT(tokenized.size() >= _NCAT, "locale-name list is too short");
+
+ previous_loc->lc_collate = tokenized[LC_COLLATE];
+ previous_loc->lc_ctype = tokenized[LC_CTYPE];
+ previous_loc->lc_monetary = tokenized[LC_MONETARY];
+ previous_loc->lc_numeric = tokenized[LC_NUMERIC];
+ previous_loc->lc_time = tokenized[LC_TIME];
+ // Skip LC_TOD.
+ previous_loc->lc_messages = tokenized[LC_MESSAGES];
+ } else {
+ previous_loc->lc_collate = current_loc_name;
+ previous_loc->lc_ctype = current_loc_name;
+ previous_loc->lc_monetary = current_loc_name;
+ previous_loc->lc_numeric = current_loc_name;
+ previous_loc->lc_time = current_loc_name;
+ previous_loc->lc_messages = current_loc_name;
+ }
+
+ previous_loc->category_mask = LC_ALL_MASK;
+ return previous_loc;
+}
+
+#ifdef __cplusplus
+}
+#endif // __cplusplus
diff --git a/lib/libcxx/src/support/runtime/exception_fallback.ipp b/lib/libcxx/src/support/runtime/exception_fallback.ipp
index faa112f7f3..67ebde3061 100644
--- a/lib/libcxx/src/support/runtime/exception_fallback.ipp
+++ b/lib/libcxx/src/support/runtime/exception_fallback.ipp
@@ -17,13 +17,13 @@ _LIBCPP_SAFE_STATIC static std::unexpected_handler __unexpected_handler;
// libcxxrt provides implementations of these functions itself.
unexpected_handler
-set_unexpected(unexpected_handler func) _NOEXCEPT
+set_unexpected(unexpected_handler func) noexcept
{
return __libcpp_atomic_exchange(&__unexpected_handler, func);
}
unexpected_handler
-get_unexpected() _NOEXCEPT
+get_unexpected() noexcept
{
return __libcpp_atomic_load(&__unexpected_handler);
@@ -38,25 +38,25 @@ void unexpected()
}
terminate_handler
-set_terminate(terminate_handler func) _NOEXCEPT
+set_terminate(terminate_handler func) noexcept
{
return __libcpp_atomic_exchange(&__terminate_handler, func);
}
terminate_handler
-get_terminate() _NOEXCEPT
+get_terminate() noexcept
{
return __libcpp_atomic_load(&__terminate_handler);
}
_LIBCPP_NORETURN
void
-terminate() _NOEXCEPT
+terminate() noexcept
{
#ifndef _LIBCPP_NO_EXCEPTIONS
try
{
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
(*get_terminate())();
// handler should not return
fprintf(stderr, "terminate_handler unexpectedly returned\n");
@@ -69,12 +69,12 @@ terminate() _NOEXCEPT
fprintf(stderr, "terminate_handler unexpectedly threw an exception\n");
::abort();
}
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
}
-bool uncaught_exception() _NOEXCEPT { return uncaught_exceptions() > 0; }
+bool uncaught_exception() noexcept { return uncaught_exceptions() > 0; }
-int uncaught_exceptions() _NOEXCEPT
+int uncaught_exceptions() noexcept
{
#warning uncaught_exception not yet implemented
fprintf(stderr, "uncaught_exceptions not yet implemented\n");
@@ -82,77 +82,77 @@ int uncaught_exceptions() _NOEXCEPT
}
-exception::~exception() _NOEXCEPT
+exception::~exception() noexcept
{
}
-const char* exception::what() const _NOEXCEPT
+const char* exception::what() const noexcept
{
return "std::exception";
}
-bad_exception::~bad_exception() _NOEXCEPT
+bad_exception::~bad_exception() noexcept
{
}
-const char* bad_exception::what() const _NOEXCEPT
+const char* bad_exception::what() const noexcept
{
return "std::bad_exception";
}
-bad_alloc::bad_alloc() _NOEXCEPT
+bad_alloc::bad_alloc() noexcept
{
}
-bad_alloc::~bad_alloc() _NOEXCEPT
+bad_alloc::~bad_alloc() noexcept
{
}
const char*
-bad_alloc::what() const _NOEXCEPT
+bad_alloc::what() const noexcept
{
return "std::bad_alloc";
}
-bad_array_new_length::bad_array_new_length() _NOEXCEPT
+bad_array_new_length::bad_array_new_length() noexcept
{
}
-bad_array_new_length::~bad_array_new_length() _NOEXCEPT
+bad_array_new_length::~bad_array_new_length() noexcept
{
}
const char*
-bad_array_new_length::what() const _NOEXCEPT
+bad_array_new_length::what() const noexcept
{
return "bad_array_new_length";
}
-bad_cast::bad_cast() _NOEXCEPT
+bad_cast::bad_cast() noexcept
{
}
-bad_typeid::bad_typeid() _NOEXCEPT
+bad_typeid::bad_typeid() noexcept
{
}
-bad_cast::~bad_cast() _NOEXCEPT
+bad_cast::~bad_cast() noexcept
{
}
const char*
-bad_cast::what() const _NOEXCEPT
+bad_cast::what() const noexcept
{
return "std::bad_cast";
}
-bad_typeid::~bad_typeid() _NOEXCEPT
+bad_typeid::~bad_typeid() noexcept
{
}
const char*
-bad_typeid::what() const _NOEXCEPT
+bad_typeid::what() const noexcept
{
return "std::bad_typeid";
}
diff --git a/lib/libcxx/src/support/runtime/exception_glibcxx.ipp b/lib/libcxx/src/support/runtime/exception_glibcxx.ipp
index 4bf3c4d877..e478ccbb6e 100644
--- a/lib/libcxx/src/support/runtime/exception_glibcxx.ipp
+++ b/lib/libcxx/src/support/runtime/exception_glibcxx.ipp
@@ -13,19 +13,19 @@
namespace std {
-bad_alloc::bad_alloc() _NOEXCEPT
+bad_alloc::bad_alloc() noexcept
{
}
-bad_array_new_length::bad_array_new_length() _NOEXCEPT
+bad_array_new_length::bad_array_new_length() noexcept
{
}
-bad_cast::bad_cast() _NOEXCEPT
+bad_cast::bad_cast() noexcept
{
}
-bad_typeid::bad_typeid() _NOEXCEPT
+bad_typeid::bad_typeid() noexcept
{
}
diff --git a/lib/libcxx/src/support/runtime/exception_libcxxabi.ipp b/lib/libcxx/src/support/runtime/exception_libcxxabi.ipp
index 6bc049bf38..ee15e437e6 100644
--- a/lib/libcxx/src/support/runtime/exception_libcxxabi.ipp
+++ b/lib/libcxx/src/support/runtime/exception_libcxxabi.ipp
@@ -13,9 +13,9 @@
namespace std {
-bool uncaught_exception() _NOEXCEPT { return uncaught_exceptions() > 0; }
+bool uncaught_exception() noexcept { return uncaught_exceptions() > 0; }
-int uncaught_exceptions() _NOEXCEPT
+int uncaught_exceptions() noexcept
{
# if _LIBCPPABI_VERSION > 1001
return __cxa_uncaught_exceptions();
diff --git a/lib/libcxx/src/support/runtime/exception_libcxxrt.ipp b/lib/libcxx/src/support/runtime/exception_libcxxrt.ipp
index 0ebffdedba..62aa3229ed 100644
--- a/lib/libcxx/src/support/runtime/exception_libcxxrt.ipp
+++ b/lib/libcxx/src/support/runtime/exception_libcxxrt.ipp
@@ -13,11 +13,11 @@
namespace std {
-bad_exception::~bad_exception() _NOEXCEPT
+bad_exception::~bad_exception() noexcept
{
}
-const char* bad_exception::what() const _NOEXCEPT
+const char* bad_exception::what() const noexcept
{
return "std::bad_exception";
}
diff --git a/lib/libcxx/src/support/runtime/exception_msvc.ipp b/lib/libcxx/src/support/runtime/exception_msvc.ipp
index 7315b8261b..7e36c7068a 100644
--- a/lib/libcxx/src/support/runtime/exception_msvc.ipp
+++ b/lib/libcxx/src/support/runtime/exception_msvc.ipp
@@ -31,11 +31,11 @@ int __cdecl __uncaught_exceptions();
namespace std {
unexpected_handler
-set_unexpected(unexpected_handler func) _NOEXCEPT {
+set_unexpected(unexpected_handler func) noexcept {
return ::set_unexpected(func);
}
-unexpected_handler get_unexpected() _NOEXCEPT {
+unexpected_handler get_unexpected() noexcept {
return ::_get_unexpected();
}
@@ -46,21 +46,21 @@ void unexpected() {
terminate();
}
-terminate_handler set_terminate(terminate_handler func) _NOEXCEPT {
+terminate_handler set_terminate(terminate_handler func) noexcept {
return ::set_terminate(func);
}
-terminate_handler get_terminate() _NOEXCEPT {
+terminate_handler get_terminate() noexcept {
return ::_get_terminate();
}
_LIBCPP_NORETURN
-void terminate() _NOEXCEPT
+void terminate() noexcept
{
#ifndef _LIBCPP_NO_EXCEPTIONS
try
{
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
(*get_terminate())();
// handler should not return
fprintf(stderr, "terminate_handler unexpectedly returned\n");
@@ -73,88 +73,88 @@ void terminate() _NOEXCEPT
fprintf(stderr, "terminate_handler unexpectedly threw an exception\n");
::abort();
}
-#endif // _LIBCPP_NO_EXCEPTIONS
+#endif // _LIBCPP_NO_EXCEPTIONS
}
-bool uncaught_exception() _NOEXCEPT { return uncaught_exceptions() > 0; }
+bool uncaught_exception() noexcept { return uncaught_exceptions() > 0; }
-int uncaught_exceptions() _NOEXCEPT {
+int uncaught_exceptions() noexcept {
return __uncaught_exceptions();
}
#if !defined(_LIBCPP_ABI_VCRUNTIME)
-bad_cast::bad_cast() _NOEXCEPT
+bad_cast::bad_cast() noexcept
{
}
-bad_cast::~bad_cast() _NOEXCEPT
+bad_cast::~bad_cast() noexcept
{
}
const char *
-bad_cast::what() const _NOEXCEPT
+bad_cast::what() const noexcept
{
return "std::bad_cast";
}
-bad_typeid::bad_typeid() _NOEXCEPT
+bad_typeid::bad_typeid() noexcept
{
}
-bad_typeid::~bad_typeid() _NOEXCEPT
+bad_typeid::~bad_typeid() noexcept
{
}
const char *
-bad_typeid::what() const _NOEXCEPT
+bad_typeid::what() const noexcept
{
return "std::bad_typeid";
}
-exception::~exception() _NOEXCEPT
+exception::~exception() noexcept
{
}
-const char* exception::what() const _NOEXCEPT
+const char* exception::what() const noexcept
{
return "std::exception";
}
-bad_exception::~bad_exception() _NOEXCEPT
+bad_exception::~bad_exception() noexcept
{
}
-const char* bad_exception::what() const _NOEXCEPT
+const char* bad_exception::what() const noexcept
{
return "std::bad_exception";
}
-bad_alloc::bad_alloc() _NOEXCEPT
+bad_alloc::bad_alloc() noexcept
{
}
-bad_alloc::~bad_alloc() _NOEXCEPT
+bad_alloc::~bad_alloc() noexcept
{
}
const char*
-bad_alloc::what() const _NOEXCEPT
+bad_alloc::what() const noexcept
{
return "std::bad_alloc";
}
-bad_array_new_length::bad_array_new_length() _NOEXCEPT
+bad_array_new_length::bad_array_new_length() noexcept
{
}
-bad_array_new_length::~bad_array_new_length() _NOEXCEPT
+bad_array_new_length::~bad_array_new_length() noexcept
{
}
const char*
-bad_array_new_length::what() const _NOEXCEPT
+bad_array_new_length::what() const noexcept
{
return "bad_array_new_length";
}
diff --git a/lib/libcxx/src/support/runtime/exception_pointer_cxxabi.ipp b/lib/libcxx/src/support/runtime/exception_pointer_cxxabi.ipp
index 82a8e6972f..33aa94502b 100644
--- a/lib/libcxx/src/support/runtime/exception_pointer_cxxabi.ipp
+++ b/lib/libcxx/src/support/runtime/exception_pointer_cxxabi.ipp
@@ -13,17 +13,17 @@
namespace std {
-exception_ptr::~exception_ptr() _NOEXCEPT {
+exception_ptr::~exception_ptr() noexcept {
__cxa_decrement_exception_refcount(__ptr_);
}
-exception_ptr::exception_ptr(const exception_ptr& other) _NOEXCEPT
+exception_ptr::exception_ptr(const exception_ptr& other) noexcept
: __ptr_(other.__ptr_)
{
__cxa_increment_exception_refcount(__ptr_);
}
-exception_ptr& exception_ptr::operator=(const exception_ptr& other) _NOEXCEPT
+exception_ptr& exception_ptr::operator=(const exception_ptr& other) noexcept
{
if (__ptr_ != other.__ptr_)
{
@@ -34,12 +34,12 @@ exception_ptr& exception_ptr::operator=(const exception_ptr& other) _NOEXCEPT
return *this;
}
-nested_exception::nested_exception() _NOEXCEPT
+nested_exception::nested_exception() noexcept
: __ptr_(current_exception())
{
}
-nested_exception::~nested_exception() _NOEXCEPT
+nested_exception::~nested_exception() noexcept
{
}
@@ -52,7 +52,7 @@ nested_exception::rethrow_nested() const
rethrow_exception(__ptr_);
}
-exception_ptr current_exception() _NOEXCEPT
+exception_ptr current_exception() noexcept
{
// be nicer if there was a constructor that took a ptr, then
// this whole function would be just:
diff --git a/lib/libcxx/src/support/runtime/exception_pointer_glibcxx.ipp b/lib/libcxx/src/support/runtime/exception_pointer_glibcxx.ipp
index 3abc137c67..983a08808d 100644
--- a/lib/libcxx/src/support/runtime/exception_pointer_glibcxx.ipp
+++ b/lib/libcxx/src/support/runtime/exception_pointer_glibcxx.ipp
@@ -25,35 +25,35 @@ struct exception_ptr
{
void* __ptr_;
- exception_ptr(const exception_ptr&) _NOEXCEPT;
- exception_ptr& operator=(const exception_ptr&) _NOEXCEPT;
- ~exception_ptr() _NOEXCEPT;
+ exception_ptr(const exception_ptr&) noexcept;
+ exception_ptr& operator=(const exception_ptr&) noexcept;
+ ~exception_ptr() noexcept;
};
}
_LIBCPP_NORETURN void rethrow_exception(__exception_ptr::exception_ptr);
-exception_ptr::~exception_ptr() _NOEXCEPT
+exception_ptr::~exception_ptr() noexcept
{
reinterpret_cast<__exception_ptr::exception_ptr*>(this)->~exception_ptr();
}
-exception_ptr::exception_ptr(const exception_ptr& other) _NOEXCEPT
+exception_ptr::exception_ptr(const exception_ptr& other) noexcept
: __ptr_(other.__ptr_)
{
new (reinterpret_cast<void*>(this)) __exception_ptr::exception_ptr(
reinterpret_cast<const __exception_ptr::exception_ptr&>(other));
}
-exception_ptr& exception_ptr::operator=(const exception_ptr& other) _NOEXCEPT
+exception_ptr& exception_ptr::operator=(const exception_ptr& other) noexcept
{
*reinterpret_cast<__exception_ptr::exception_ptr*>(this) =
reinterpret_cast<const __exception_ptr::exception_ptr&>(other);
return *this;
}
-nested_exception::nested_exception() _NOEXCEPT
+nested_exception::nested_exception() noexcept
: __ptr_(current_exception())
{
}
diff --git a/lib/libcxx/src/support/runtime/exception_pointer_msvc.ipp b/lib/libcxx/src/support/runtime/exception_pointer_msvc.ipp
index b1a3695223..9e7f392e76 100644
--- a/lib/libcxx/src/support/runtime/exception_pointer_msvc.ipp
+++ b/lib/libcxx/src/support/runtime/exception_pointer_msvc.ipp
@@ -24,35 +24,35 @@ __ExceptionPtrCopyException(void*, const void*, const void*);
namespace std {
-exception_ptr::exception_ptr() _NOEXCEPT { __ExceptionPtrCreate(this); }
-exception_ptr::exception_ptr(nullptr_t) _NOEXCEPT { __ExceptionPtrCreate(this); }
+exception_ptr::exception_ptr() noexcept { __ExceptionPtrCreate(this); }
+exception_ptr::exception_ptr(nullptr_t) noexcept { __ExceptionPtrCreate(this); }
-exception_ptr::exception_ptr(const exception_ptr& __other) _NOEXCEPT {
+exception_ptr::exception_ptr(const exception_ptr& __other) noexcept {
__ExceptionPtrCopy(this, &__other);
}
-exception_ptr& exception_ptr::operator=(const exception_ptr& __other) _NOEXCEPT {
+exception_ptr& exception_ptr::operator=(const exception_ptr& __other) noexcept {
__ExceptionPtrAssign(this, &__other);
return *this;
}
-exception_ptr& exception_ptr::operator=(nullptr_t) _NOEXCEPT {
+exception_ptr& exception_ptr::operator=(nullptr_t) noexcept {
exception_ptr dummy;
__ExceptionPtrAssign(this, &dummy);
return *this;
}
-exception_ptr::~exception_ptr() _NOEXCEPT { __ExceptionPtrDestroy(this); }
+exception_ptr::~exception_ptr() noexcept { __ExceptionPtrDestroy(this); }
-exception_ptr::operator bool() const _NOEXCEPT {
+exception_ptr::operator bool() const noexcept {
return __ExceptionPtrToBool(this);
}
-bool operator==(const exception_ptr& __x, const exception_ptr& __y) _NOEXCEPT {
+bool operator==(const exception_ptr& __x, const exception_ptr& __y) noexcept {
return __ExceptionPtrCompare(&__x, &__y);
}
-void swap(exception_ptr& lhs, exception_ptr& rhs) _NOEXCEPT {
+void swap(exception_ptr& lhs, exception_ptr& rhs) noexcept {
__ExceptionPtrSwap(&rhs, &lhs);
}
@@ -63,7 +63,7 @@ exception_ptr __copy_exception_ptr(void* __except, const void* __ptr) {
return __ret;
}
-exception_ptr current_exception() _NOEXCEPT {
+exception_ptr current_exception() noexcept {
exception_ptr __ret;
__ExceptionPtrCurrentException(&__ret);
return __ret;
@@ -72,9 +72,9 @@ exception_ptr current_exception() _NOEXCEPT {
_LIBCPP_NORETURN
void rethrow_exception(exception_ptr p) { __ExceptionPtrRethrow(&p); }
-nested_exception::nested_exception() _NOEXCEPT : __ptr_(current_exception()) {}
+nested_exception::nested_exception() noexcept : __ptr_(current_exception()) {}
-nested_exception::~nested_exception() _NOEXCEPT {}
+nested_exception::~nested_exception() noexcept {}
_LIBCPP_NORETURN
void nested_exception::rethrow_nested() const {
diff --git a/lib/libcxx/src/support/runtime/exception_pointer_unimplemented.ipp b/lib/libcxx/src/support/runtime/exception_pointer_unimplemented.ipp
index 991bca9ecf..9e8ec04e11 100644
--- a/lib/libcxx/src/support/runtime/exception_pointer_unimplemented.ipp
+++ b/lib/libcxx/src/support/runtime/exception_pointer_unimplemented.ipp
@@ -12,14 +12,14 @@
namespace std {
-exception_ptr::~exception_ptr() _NOEXCEPT
+exception_ptr::~exception_ptr() noexcept
{
# warning exception_ptr not yet implemented
fprintf(stderr, "exception_ptr not yet implemented\n");
::abort();
}
-exception_ptr::exception_ptr(const exception_ptr& other) _NOEXCEPT
+exception_ptr::exception_ptr(const exception_ptr& other) noexcept
: __ptr_(other.__ptr_)
{
# warning exception_ptr not yet implemented
@@ -27,21 +27,21 @@ exception_ptr::exception_ptr(const exception_ptr& other) _NOEXCEPT
::abort();
}
-exception_ptr& exception_ptr::operator=(const exception_ptr& other) _NOEXCEPT
+exception_ptr& exception_ptr::operator=(const exception_ptr& other) noexcept
{
# warning exception_ptr not yet implemented
fprintf(stderr, "exception_ptr not yet implemented\n");
::abort();
}
-nested_exception::nested_exception() _NOEXCEPT
+nested_exception::nested_exception() noexcept
: __ptr_(current_exception())
{
}
#if !defined(__GLIBCXX__)
-nested_exception::~nested_exception() _NOEXCEPT
+nested_exception::~nested_exception() noexcept
{
}
@@ -61,7 +61,7 @@ nested_exception::rethrow_nested() const
#endif // FIXME
}
-exception_ptr current_exception() _NOEXCEPT
+exception_ptr current_exception() noexcept
{
# warning exception_ptr not yet implemented
fprintf(stderr, "exception_ptr not yet implemented\n");
diff --git a/lib/libcxx/src/support/runtime/new_handler_fallback.ipp b/lib/libcxx/src/support/runtime/new_handler_fallback.ipp
index 7205093942..a969b2a45d 100644
--- a/lib/libcxx/src/support/runtime/new_handler_fallback.ipp
+++ b/lib/libcxx/src/support/runtime/new_handler_fallback.ipp
@@ -12,13 +12,13 @@ namespace std {
_LIBCPP_SAFE_STATIC static std::new_handler __new_handler;
new_handler
-set_new_handler(new_handler handler) _NOEXCEPT
+set_new_handler(new_handler handler) noexcept
{
return __libcpp_atomic_exchange(&__new_handler, handler);
}
new_handler
-get_new_handler() _NOEXCEPT
+get_new_handler() noexcept
{
return __libcpp_atomic_load(&__new_handler);
}
diff --git a/lib/libcxx/src/support/runtime/stdexcept_default.ipp b/lib/libcxx/src/support/runtime/stdexcept_default.ipp
index c827ca4c51..ad7bd40b61 100644
--- a/lib/libcxx/src/support/runtime/stdexcept_default.ipp
+++ b/lib/libcxx/src/support/runtime/stdexcept_default.ipp
@@ -23,9 +23,9 @@ logic_error::logic_error(const string& msg) : __imp_(msg.c_str()) {}
logic_error::logic_error(const char* msg) : __imp_(msg) {}
-logic_error::logic_error(const logic_error& le) _NOEXCEPT : __imp_(le.__imp_) {}
+logic_error::logic_error(const logic_error& le) noexcept : __imp_(le.__imp_) {}
-logic_error& logic_error::operator=(const logic_error& le) _NOEXCEPT {
+logic_error& logic_error::operator=(const logic_error& le) noexcept {
__imp_ = le.__imp_;
return *this;
}
@@ -34,30 +34,30 @@ runtime_error::runtime_error(const string& msg) : __imp_(msg.c_str()) {}
runtime_error::runtime_error(const char* msg) : __imp_(msg) {}
-runtime_error::runtime_error(const runtime_error& re) _NOEXCEPT
+runtime_error::runtime_error(const runtime_error& re) noexcept
: __imp_(re.__imp_) {}
-runtime_error& runtime_error::operator=(const runtime_error& re) _NOEXCEPT {
+runtime_error& runtime_error::operator=(const runtime_error& re) noexcept {
__imp_ = re.__imp_;
return *this;
}
#if !defined(_LIBCPPABI_VERSION) && !defined(LIBSTDCXX)
-const char* logic_error::what() const _NOEXCEPT { return __imp_.c_str(); }
+const char* logic_error::what() const noexcept { return __imp_.c_str(); }
-const char* runtime_error::what() const _NOEXCEPT { return __imp_.c_str(); }
+const char* runtime_error::what() const noexcept { return __imp_.c_str(); }
-logic_error::~logic_error() _NOEXCEPT {}
-domain_error::~domain_error() _NOEXCEPT {}
-invalid_argument::~invalid_argument() _NOEXCEPT {}
-length_error::~length_error() _NOEXCEPT {}
-out_of_range::~out_of_range() _NOEXCEPT {}
+logic_error::~logic_error() noexcept {}
+domain_error::~domain_error() noexcept {}
+invalid_argument::~invalid_argument() noexcept {}
+length_error::~length_error() noexcept {}
+out_of_range::~out_of_range() noexcept {}
-runtime_error::~runtime_error() _NOEXCEPT {}
-range_error::~range_error() _NOEXCEPT {}
-overflow_error::~overflow_error() _NOEXCEPT {}
-underflow_error::~underflow_error() _NOEXCEPT {}
+runtime_error::~runtime_error() noexcept {}
+range_error::~range_error() noexcept {}
+overflow_error::~overflow_error() noexcept {}
+underflow_error::~underflow_error() noexcept {}
#endif
diff --git a/lib/libcxx/src/support/win32/support.cpp b/lib/libcxx/src/support/win32/support.cpp
index 52453f5479..5890e669a3 100644
--- a/lib/libcxx/src/support/win32/support.cpp
+++ b/lib/libcxx/src/support/win32/support.cpp
@@ -22,7 +22,10 @@ int __libcpp_vasprintf( char **sptr, const char *__restrict format, va_list ap )
{
*sptr = NULL;
// Query the count required.
- int count = _vsnprintf( NULL, 0, format, ap );
+ va_list ap_copy;
+ va_copy(ap_copy, ap);
+ int count = _vsnprintf( NULL, 0, format, ap_copy );
+ va_end(ap_copy);
if (count < 0)
return count;
size_t buffer_size = static_cast<size_t>(count) + 1;
diff --git a/lib/libcxx/src/support/win32/thread_win32.cpp b/lib/libcxx/src/support/win32/thread_win32.cpp
index 35c4c87145..63c5aa6537 100644
--- a/lib/libcxx/src/support/win32/thread_win32.cpp
+++ b/lib/libcxx/src/support/win32/thread_win32.cpp
@@ -8,6 +8,8 @@
//===----------------------------------------------------------------------===//
#include <__threading_support>
+#define NOMINMAX
+#define WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <process.h>
#include <fibersapi.h>
@@ -37,6 +39,9 @@ static_assert(alignof(__libcpp_thread_t) == alignof(HANDLE), "");
static_assert(sizeof(__libcpp_tls_key) == sizeof(DWORD), "");
static_assert(alignof(__libcpp_tls_key) == alignof(DWORD), "");
+static_assert(sizeof(__libcpp_semaphore_t) == sizeof(HANDLE), "");
+static_assert(alignof(__libcpp_semaphore_t) == alignof(HANDLE), "");
+
// Mutex
int __libcpp_recursive_mutex_init(__libcpp_recursive_mutex_t *__m)
{
@@ -241,10 +246,8 @@ void __libcpp_thread_yield()
void __libcpp_thread_sleep_for(const chrono::nanoseconds& __ns)
{
- using namespace chrono;
- // round-up to the nearest milisecond
- milliseconds __ms =
- duration_cast<milliseconds>(__ns + chrono::nanoseconds(999999));
+ // round-up to the nearest millisecond
+ chrono::milliseconds __ms = chrono::ceil<chrono::milliseconds>(__ns);
// FIXME(compnerd) this should be an alertable sleep (WFSO or SleepEx)
Sleep(__ms.count());
}
@@ -272,4 +275,37 @@ int __libcpp_tls_set(__libcpp_tls_key __key, void *__p)
return 0;
}
+// Semaphores
+bool __libcpp_semaphore_init(__libcpp_semaphore_t* __sem, int __init)
+{
+ *(PHANDLE)__sem = CreateSemaphoreEx(nullptr, __init, _LIBCPP_SEMAPHORE_MAX,
+ nullptr, 0, SEMAPHORE_ALL_ACCESS);
+ return *__sem != nullptr;
+}
+
+bool __libcpp_semaphore_destroy(__libcpp_semaphore_t* __sem)
+{
+ CloseHandle(*(PHANDLE)__sem);
+ return true;
+}
+
+bool __libcpp_semaphore_post(__libcpp_semaphore_t* __sem)
+{
+ return ReleaseSemaphore(*(PHANDLE)__sem, 1, nullptr);
+}
+
+bool __libcpp_semaphore_wait(__libcpp_semaphore_t* __sem)
+{
+ return WaitForSingleObjectEx(*(PHANDLE)__sem, INFINITE, false) ==
+ WAIT_OBJECT_0;
+}
+
+bool __libcpp_semaphore_wait_timed(__libcpp_semaphore_t* __sem,
+ chrono::nanoseconds const& __ns)
+{
+ chrono::milliseconds __ms = chrono::ceil<chrono::milliseconds>(__ns);
+ return WaitForSingleObjectEx(*(PHANDLE)__sem, __ms.count(), false) ==
+ WAIT_OBJECT_0;
+}
+
_LIBCPP_END_NAMESPACE_STD
diff --git a/lib/libcxx/src/system_error.cpp b/lib/libcxx/src/system_error.cpp
index 9ddf7bcbe0..a1ea6c4754 100644
--- a/lib/libcxx/src/system_error.cpp
+++ b/lib/libcxx/src/system_error.cpp
@@ -28,29 +28,29 @@ _LIBCPP_BEGIN_NAMESPACE_STD
// class error_category
#if defined(_LIBCPP_DEPRECATED_ABI_LEGACY_LIBRARY_DEFINITIONS_FOR_INLINE_FUNCTIONS)
-error_category::error_category() _NOEXCEPT
+error_category::error_category() noexcept
{
}
#endif
-error_category::~error_category() _NOEXCEPT
+error_category::~error_category() noexcept
{
}
error_condition
-error_category::default_error_condition(int ev) const _NOEXCEPT
+error_category::default_error_condition(int ev) const noexcept
{
return error_condition(ev, *this);
}
bool
-error_category::equivalent(int code, const error_condition& condition) const _NOEXCEPT
+error_category::equivalent(int code, const error_condition& condition) const noexcept
{
return default_error_condition(code) == condition;
}
bool
-error_category::equivalent(const error_code& code, int condition) const _NOEXCEPT
+error_category::equivalent(const error_code& code, int condition) const noexcept
{
return *this == code.category() && code.value() == condition;
}
@@ -141,12 +141,12 @@ class _LIBCPP_HIDDEN __generic_error_category
: public __do_message
{
public:
- virtual const char* name() const _NOEXCEPT;
+ virtual const char* name() const noexcept;
virtual string message(int ev) const;
};
const char*
-__generic_error_category::name() const _NOEXCEPT
+__generic_error_category::name() const noexcept
{
return "generic";
}
@@ -157,12 +157,12 @@ __generic_error_category::message(int ev) const
#ifdef _LIBCPP_ELAST
if (ev > _LIBCPP_ELAST)
return string("unspecified generic_category error");
-#endif // _LIBCPP_ELAST
+#endif // _LIBCPP_ELAST
return __do_message::message(ev);
}
const error_category&
-generic_category() _NOEXCEPT
+generic_category() noexcept
{
static __generic_error_category s;
return s;
@@ -172,13 +172,13 @@ class _LIBCPP_HIDDEN __system_error_category
: public __do_message
{
public:
- virtual const char* name() const _NOEXCEPT;
+ virtual const char* name() const noexcept;
virtual string message(int ev) const;
- virtual error_condition default_error_condition(int ev) const _NOEXCEPT;
+ virtual error_condition default_error_condition(int ev) const noexcept;
};
const char*
-__system_error_category::name() const _NOEXCEPT
+__system_error_category::name() const noexcept
{
return "system";
}
@@ -189,22 +189,22 @@ __system_error_category::message(int ev) const
#ifdef _LIBCPP_ELAST
if (ev > _LIBCPP_ELAST)
return string("unspecified system_category error");
-#endif // _LIBCPP_ELAST
+#endif // _LIBCPP_ELAST
return __do_message::message(ev);
}
error_condition
-__system_error_category::default_error_condition(int ev) const _NOEXCEPT
+__system_error_category::default_error_condition(int ev) const noexcept
{
#ifdef _LIBCPP_ELAST
if (ev > _LIBCPP_ELAST)
return error_condition(ev, system_category());
-#endif // _LIBCPP_ELAST
+#endif // _LIBCPP_ELAST
return error_condition(ev, generic_category());
}
const error_category&
-system_category() _NOEXCEPT
+system_category() noexcept
{
static __system_error_category s;
return s;
@@ -276,7 +276,7 @@ system_error::system_error(int ev, const error_category& ecat)
{
}
-system_error::~system_error() _NOEXCEPT
+system_error::~system_error() noexcept
{
}
diff --git a/lib/libcxx/src/thread.cpp b/lib/libcxx/src/thread.cpp
index 5959d8b711..8dddb240b5 100644
--- a/lib/libcxx/src/thread.cpp
+++ b/lib/libcxx/src/thread.cpp
@@ -70,7 +70,7 @@ thread::detach()
}
unsigned
-thread::hardware_concurrency() _NOEXCEPT
+thread::hardware_concurrency() noexcept
{
#if defined(_SC_NPROCESSORS_ONLN)
long result = sysconf(_SC_NPROCESSORS_ONLN);
@@ -94,7 +94,7 @@ thread::hardware_concurrency() _NOEXCEPT
# warning hardware_concurrency not yet implemented
# endif
return 0; // Means not computable [thread.thread.static]
-#endif // defined(CTL_HW) && defined(HW_NCPU)
+#endif // defined(CTL_HW) && defined(HW_NCPU)
}
namespace this_thread
diff --git a/lib/libcxx/src/typeinfo.cpp b/lib/libcxx/src/typeinfo.cpp
index 49a07ef7da..ce3867ea93 100644
--- a/lib/libcxx/src/typeinfo.cpp
+++ b/lib/libcxx/src/typeinfo.cpp
@@ -11,18 +11,18 @@
#if defined(_LIBCPP_ABI_MICROSOFT) && !defined(_LIBCPP_ABI_VCRUNTIME)
#include <string.h>
-int std::type_info::__compare(const type_info &__rhs) const _NOEXCEPT {
+int std::type_info::__compare(const type_info &__rhs) const noexcept {
if (&__data == &__rhs.__data)
return 0;
return strcmp(&__data.__decorated_name[1], &__rhs.__data.__decorated_name[1]);
}
-const char *std::type_info::name() const _NOEXCEPT {
+const char *std::type_info::name() const noexcept {
// TODO(compnerd) cache demangled &__data.__decorated_name[1]
return &__data.__decorated_name[1];
}
-size_t std::type_info::hash_code() const _NOEXCEPT {
+size_t std::type_info::hash_code() const noexcept {
#if defined(_WIN64)
constexpr size_t fnv_offset_basis = 14695981039346656037ull;
constexpr size_t fnv_prime = 10995116282110ull;