diff options
Diffstat (limited to 'lib/libcxx/src')
57 files changed, 0 insertions, 16839 deletions
diff --git a/lib/libcxx/src/algorithm.cpp b/lib/libcxx/src/algorithm.cpp deleted file mode 100644 index f036eb7abe1..00000000000 --- a/lib/libcxx/src/algorithm.cpp +++ /dev/null @@ -1,91 +0,0 @@ -//===----------------------- algorithm.cpp --------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "algorithm" -#include "random" -#include "mutex" - -_LIBCPP_BEGIN_NAMESPACE_STD - -template void __sort<__less<char>&, char*>(char*, char*, __less<char>&); -template void __sort<__less<wchar_t>&, wchar_t*>(wchar_t*, wchar_t*, __less<wchar_t>&); -template void __sort<__less<signed char>&, signed char*>(signed char*, signed char*, __less<signed char>&); -template void __sort<__less<unsigned char>&, unsigned char*>(unsigned char*, unsigned char*, __less<unsigned char>&); -template void __sort<__less<short>&, short*>(short*, short*, __less<short>&); -template void __sort<__less<unsigned short>&, unsigned short*>(unsigned short*, unsigned short*, __less<unsigned short>&); -template void __sort<__less<int>&, int*>(int*, int*, __less<int>&); -template void __sort<__less<unsigned>&, unsigned*>(unsigned*, unsigned*, __less<unsigned>&); -template void __sort<__less<long>&, long*>(long*, long*, __less<long>&); -template void __sort<__less<unsigned long>&, unsigned long*>(unsigned long*, unsigned long*, __less<unsigned long>&); -template void __sort<__less<long long>&, long long*>(long long*, long long*, __less<long long>&); -template void __sort<__less<unsigned long long>&, unsigned long long*>(unsigned long long*, unsigned long long*, __less<unsigned long long>&); -template void __sort<__less<float>&, float*>(float*, float*, __less<float>&); -template void __sort<__less<double>&, double*>(double*, double*, __less<double>&); -template void __sort<__less<long double>&, long double*>(long double*, long double*, __less<long double>&); - -template bool __insertion_sort_incomplete<__less<char>&, char*>(char*, char*, __less<char>&); -template bool __insertion_sort_incomplete<__less<wchar_t>&, wchar_t*>(wchar_t*, wchar_t*, __less<wchar_t>&); -template bool __insertion_sort_incomplete<__less<signed char>&, signed char*>(signed char*, signed char*, __less<signed char>&); -template bool __insertion_sort_incomplete<__less<unsigned char>&, unsigned char*>(unsigned char*, unsigned char*, __less<unsigned char>&); -template bool __insertion_sort_incomplete<__less<short>&, short*>(short*, short*, __less<short>&); -template bool __insertion_sort_incomplete<__less<unsigned short>&, unsigned short*>(unsigned short*, unsigned short*, __less<unsigned short>&); -template bool __insertion_sort_incomplete<__less<int>&, int*>(int*, int*, __less<int>&); -template bool __insertion_sort_incomplete<__less<unsigned>&, unsigned*>(unsigned*, unsigned*, __less<unsigned>&); -template bool __insertion_sort_incomplete<__less<long>&, long*>(long*, long*, __less<long>&); -template bool __insertion_sort_incomplete<__less<unsigned long>&, unsigned long*>(unsigned long*, unsigned long*, __less<unsigned long>&); -template bool __insertion_sort_incomplete<__less<long long>&, long long*>(long long*, long long*, __less<long long>&); -template bool __insertion_sort_incomplete<__less<unsigned long long>&, unsigned long long*>(unsigned long long*, unsigned long long*, __less<unsigned long long>&); -template bool __insertion_sort_incomplete<__less<float>&, float*>(float*, float*, __less<float>&); -template bool __insertion_sort_incomplete<__less<double>&, double*>(double*, double*, __less<double>&); -template bool __insertion_sort_incomplete<__less<long double>&, long double*>(long double*, long double*, __less<long double>&); - -template unsigned __sort5<__less<long double>&, long double*>(long double*, long double*, long double*, long double*, long double*, __less<long double>&); - -#ifndef _LIBCPP_HAS_NO_THREADS -_LIBCPP_SAFE_STATIC static __libcpp_mutex_t __rs_mut = _LIBCPP_MUTEX_INITIALIZER; -#endif -unsigned __rs_default::__c_ = 0; - -__rs_default::__rs_default() -{ -#ifndef _LIBCPP_HAS_NO_THREADS - __libcpp_mutex_lock(&__rs_mut); -#endif - __c_ = 1; -} - -__rs_default::__rs_default(const __rs_default&) -{ - ++__c_; -} - -__rs_default::~__rs_default() -{ -#ifndef _LIBCPP_HAS_NO_THREADS - if (--__c_ == 0) - __libcpp_mutex_unlock(&__rs_mut); -#else - --__c_; -#endif -} - -__rs_default::result_type -__rs_default::operator()() -{ - static mt19937 __rs_g; - return __rs_g(); -} - -__rs_default -__rs_get() -{ - return __rs_default(); -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/any.cpp b/lib/libcxx/src/any.cpp deleted file mode 100644 index 3795258bb06..00000000000 --- a/lib/libcxx/src/any.cpp +++ /dev/null @@ -1,35 +0,0 @@ -//===---------------------------- any.cpp ---------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "any" - -namespace std { -const char* bad_any_cast::what() const _NOEXCEPT { - return "bad any cast"; -} -} - - -#include <experimental/__config> - -// Preserve std::experimental::any_bad_cast for ABI compatibility -// Even though it no longer exists in a header file -_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; -}; - -const char* bad_any_cast::what() const _NOEXCEPT { - return "bad any cast"; -} - -_LIBCPP_END_NAMESPACE_LFTS diff --git a/lib/libcxx/src/bind.cpp b/lib/libcxx/src/bind.cpp deleted file mode 100644 index b4c76ffe6a4..00000000000 --- a/lib/libcxx/src/bind.cpp +++ /dev/null @@ -1,30 +0,0 @@ -//===-------------------------- bind.cpp ----------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "functional" - -_LIBCPP_BEGIN_NAMESPACE_STD - -namespace placeholders -{ - -const __ph<1> _1{}; -const __ph<2> _2{}; -const __ph<3> _3{}; -const __ph<4> _4{}; -const __ph<5> _5{}; -const __ph<6> _6{}; -const __ph<7> _7{}; -const __ph<8> _8{}; -const __ph<9> _9{}; -const __ph<10> _10{}; - -} // placeholders - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/charconv.cpp b/lib/libcxx/src/charconv.cpp deleted file mode 100644 index ec241db7447..00000000000 --- a/lib/libcxx/src/charconv.cpp +++ /dev/null @@ -1,233 +0,0 @@ -//===------------------------- charconv.cpp -------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "charconv" -#include <string.h> - -_LIBCPP_BEGIN_NAMESPACE_STD - -namespace __itoa -{ - -static constexpr char cDigitsLut[200] = { - '0', '0', '0', '1', '0', '2', '0', '3', '0', '4', '0', '5', '0', '6', '0', - '7', '0', '8', '0', '9', '1', '0', '1', '1', '1', '2', '1', '3', '1', '4', - '1', '5', '1', '6', '1', '7', '1', '8', '1', '9', '2', '0', '2', '1', '2', - '2', '2', '3', '2', '4', '2', '5', '2', '6', '2', '7', '2', '8', '2', '9', - '3', '0', '3', '1', '3', '2', '3', '3', '3', '4', '3', '5', '3', '6', '3', - '7', '3', '8', '3', '9', '4', '0', '4', '1', '4', '2', '4', '3', '4', '4', - '4', '5', '4', '6', '4', '7', '4', '8', '4', '9', '5', '0', '5', '1', '5', - '2', '5', '3', '5', '4', '5', '5', '5', '6', '5', '7', '5', '8', '5', '9', - '6', '0', '6', '1', '6', '2', '6', '3', '6', '4', '6', '5', '6', '6', '6', - '7', '6', '8', '6', '9', '7', '0', '7', '1', '7', '2', '7', '3', '7', '4', - '7', '5', '7', '6', '7', '7', '7', '8', '7', '9', '8', '0', '8', '1', '8', - '2', '8', '3', '8', '4', '8', '5', '8', '6', '8', '7', '8', '8', '8', '9', - '9', '0', '9', '1', '9', '2', '9', '3', '9', '4', '9', '5', '9', '6', '9', - '7', '9', '8', '9', '9'}; - -template <typename T> -inline _LIBCPP_INLINE_VISIBILITY char* -append1(char* buffer, T i) -{ - *buffer = '0' + static_cast<char>(i); - return buffer + 1; -} - -template <typename T> -inline _LIBCPP_INLINE_VISIBILITY char* -append2(char* buffer, T i) -{ - memcpy(buffer, &cDigitsLut[(i)*2], 2); - return buffer + 2; -} - -template <typename T> -inline _LIBCPP_INLINE_VISIBILITY char* -append3(char* buffer, T i) -{ - return append2(append1(buffer, (i) / 100), (i) % 100); -} - -template <typename T> -inline _LIBCPP_INLINE_VISIBILITY char* -append4(char* buffer, T i) -{ - return append2(append2(buffer, (i) / 100), (i) % 100); -} - -char* -__u32toa(uint32_t value, char* buffer) -{ - if (value < 10000) - { - if (value < 100) - { - if (value < 10) - buffer = append1(buffer, value); - else - buffer = append2(buffer, value); - } - else - { - if (value < 1000) - buffer = append3(buffer, value); - else - buffer = append4(buffer, value); - } - } - else if (value < 100000000) - { - // value = bbbbcccc - const uint32_t b = value / 10000; - const uint32_t c = value % 10000; - - if (value < 1000000) - { - if (value < 100000) - buffer = append1(buffer, b); - else - buffer = append2(buffer, b); - } - else - { - if (value < 10000000) - buffer = append3(buffer, b); - else - buffer = append4(buffer, b); - } - - buffer = append4(buffer, c); - } - else - { - // value = aabbbbcccc in decimal - const uint32_t a = value / 100000000; // 1 to 42 - value %= 100000000; - - if (a < 10) - buffer = append1(buffer, a); - else - buffer = append2(buffer, a); - - buffer = append4(buffer, value / 10000); - buffer = append4(buffer, value % 10000); - } - - return buffer; -} - -char* -__u64toa(uint64_t value, char* buffer) -{ - if (value < 100000000) - { - uint32_t v = static_cast<uint32_t>(value); - if (v < 10000) - { - if (v < 100) - { - if (v < 10) - buffer = append1(buffer, v); - else - buffer = append2(buffer, v); - } - else - { - if (v < 1000) - buffer = append3(buffer, v); - else - buffer = append4(buffer, v); - } - } - else - { - // value = bbbbcccc - const uint32_t b = v / 10000; - const uint32_t c = v % 10000; - - if (v < 1000000) - { - if (v < 100000) - buffer = append1(buffer, b); - else - buffer = append2(buffer, b); - } - else - { - if (v < 10000000) - buffer = append3(buffer, b); - else - buffer = append4(buffer, b); - } - - buffer = append4(buffer, c); - } - } - else if (value < 10000000000000000) - { - const uint32_t v0 = static_cast<uint32_t>(value / 100000000); - const uint32_t v1 = static_cast<uint32_t>(value % 100000000); - - const uint32_t b0 = v0 / 10000; - const uint32_t c0 = v0 % 10000; - - if (v0 < 1000000) - { - if (v0 < 100000) - buffer = append1(buffer, b0); - else - buffer = append2(buffer, b0); - } - else - { - if (v0 < 10000000) - buffer = append3(buffer, b0); - else - buffer = append4(buffer, b0); - } - - buffer = append4(buffer, c0); - buffer = append4(buffer, v1 / 10000); - buffer = append4(buffer, v1 % 10000); - } - else - { - const uint32_t a = - static_cast<uint32_t>(value / 10000000000000000); // 1 to 1844 - value %= 10000000000000000; - - if (a < 100) - { - if (a < 10) - buffer = append1(buffer, a); - else - buffer = append2(buffer, a); - } - else - { - if (a < 1000) - buffer = append3(buffer, a); - else - buffer = append4(buffer, a); - } - - const uint32_t v0 = static_cast<uint32_t>(value / 100000000); - const uint32_t v1 = static_cast<uint32_t>(value % 100000000); - buffer = append4(buffer, v0 / 10000); - buffer = append4(buffer, v0 % 10000); - buffer = append4(buffer, v1 / 10000); - buffer = append4(buffer, v1 % 10000); - } - - return buffer; -} - -} // namespace __itoa - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/chrono.cpp b/lib/libcxx/src/chrono.cpp deleted file mode 100644 index 882d50b9d73..00000000000 --- a/lib/libcxx/src/chrono.cpp +++ /dev/null @@ -1,220 +0,0 @@ -//===------------------------- chrono.cpp ---------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "chrono" -#include "cerrno" // errno -#include "system_error" // __throw_system_error -#include <time.h> // clock_gettime, CLOCK_MONOTONIC and CLOCK_REALTIME -#include "include/apple_availability.h" - -#if !defined(__APPLE__) -#define _LIBCPP_USE_CLOCK_GETTIME -#endif // __APPLE__ - -#if defined(_LIBCPP_WIN32API) -#define WIN32_LEAN_AND_MEAN -#define VC_EXTRA_LEAN -#include <windows.h> -#if _WIN32_WINNT >= _WIN32_WINNT_WIN8 -#include <winapifamily.h> -#endif -#else -#if !defined(CLOCK_REALTIME) || !defined(_LIBCPP_USE_CLOCK_GETTIME) -#include <sys/time.h> // for gettimeofday and timeval -#endif // !defined(CLOCK_REALTIME) -#endif // defined(_LIBCPP_WIN32API) - -#if !defined(_LIBCPP_HAS_NO_MONOTONIC_CLOCK) -#if __APPLE__ -#include <mach/mach_time.h> // mach_absolute_time, mach_timebase_info_data_t -#elif !defined(_LIBCPP_WIN32API) && !defined(CLOCK_MONOTONIC) -#error "Monotonic clock not implemented" -#endif -#endif - -_LIBCPP_BEGIN_NAMESPACE_STD - -namespace chrono -{ - -// system_clock - -const bool system_clock::is_steady; - -system_clock::time_point -system_clock::now() _NOEXCEPT -{ -#if defined(_LIBCPP_WIN32API) - // FILETIME is in 100ns units - using filetime_duration = - _VSTD::chrono::duration<__int64, - _VSTD::ratio_multiply<_VSTD::ratio<100, 1>, - nanoseconds::period>>; - - // The Windows epoch is Jan 1 1601, the Unix epoch Jan 1 1970. - static _LIBCPP_CONSTEXPR const seconds nt_to_unix_epoch{11644473600}; - - FILETIME ft; -#if _WIN32_WINNT >= _WIN32_WINNT_WIN8 -#if WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_DESKTOP) - GetSystemTimePreciseAsFileTime(&ft); -#else - GetSystemTimeAsFileTime(&ft); -#endif -#else - GetSystemTimeAsFileTime(&ft); -#endif - - filetime_duration d{(static_cast<__int64>(ft.dwHighDateTime) << 32) | - static_cast<__int64>(ft.dwLowDateTime)}; - return time_point(duration_cast<duration>(d - nt_to_unix_epoch)); -#else -#if defined(_LIBCPP_USE_CLOCK_GETTIME) && defined(CLOCK_REALTIME) - struct timespec tp; - if (0 != clock_gettime(CLOCK_REALTIME, &tp)) - __throw_system_error(errno, "clock_gettime(CLOCK_REALTIME) failed"); - return time_point(seconds(tp.tv_sec) + microseconds(tp.tv_nsec / 1000)); -#else - timeval tv; - gettimeofday(&tv, 0); - return time_point(seconds(tv.tv_sec) + microseconds(tv.tv_usec)); -#endif // _LIBCPP_USE_CLOCK_GETTIME && CLOCK_REALTIME -#endif -} - -time_t -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 -{ - return system_clock::time_point(seconds(t)); -} - -#ifndef _LIBCPP_HAS_NO_MONOTONIC_CLOCK -// steady_clock -// -// Warning: If this is not truly steady, then it is non-conforming. It is -// better for it to not exist and have the rest of libc++ use system_clock -// instead. - -const bool steady_clock::is_steady; - -#if defined(__APPLE__) - -// Darwin libc versions >= 1133 provide ns precision via CLOCK_UPTIME_RAW -#if defined(_LIBCPP_USE_CLOCK_GETTIME) && defined(CLOCK_UPTIME_RAW) -steady_clock::time_point -steady_clock::now() _NOEXCEPT -{ - struct timespec tp; - if (0 != clock_gettime(CLOCK_UPTIME_RAW, &tp)) - __throw_system_error(errno, "clock_gettime(CLOCK_UPTIME_RAW) failed"); - return time_point(seconds(tp.tv_sec) + nanoseconds(tp.tv_nsec)); -} - -#else -// mach_absolute_time() * MachInfo.numer / MachInfo.denom is the number of -// nanoseconds since the computer booted up. MachInfo.numer and MachInfo.denom -// are run time constants supplied by the OS. This clock has no relationship -// to the Gregorian calendar. It's main use is as a high resolution timer. - -// MachInfo.numer / MachInfo.denom is often 1 on the latest equipment. Specialize -// for that case as an optimization. - -static -steady_clock::rep -steady_simplified() -{ - return static_cast<steady_clock::rep>(mach_absolute_time()); -} - -static -double -compute_steady_factor() -{ - mach_timebase_info_data_t MachInfo; - mach_timebase_info(&MachInfo); - return static_cast<double>(MachInfo.numer) / MachInfo.denom; -} - -static -steady_clock::rep -steady_full() -{ - static const double factor = compute_steady_factor(); - return static_cast<steady_clock::rep>(mach_absolute_time() * factor); -} - -typedef steady_clock::rep (*FP)(); - -static -FP -init_steady_clock() -{ - mach_timebase_info_data_t MachInfo; - mach_timebase_info(&MachInfo); - if (MachInfo.numer == MachInfo.denom) - return &steady_simplified; - return &steady_full; -} - -steady_clock::time_point -steady_clock::now() _NOEXCEPT -{ - static FP fp = init_steady_clock(); - return time_point(duration(fp())); -} -#endif // defined(_LIBCPP_USE_CLOCK_GETTIME) && defined(CLOCK_UPTIME_RAW) - -#elif defined(_LIBCPP_WIN32API) - -steady_clock::time_point -steady_clock::now() _NOEXCEPT -{ - static LARGE_INTEGER freq; - static BOOL initialized = FALSE; - if (!initialized) - initialized = QueryPerformanceFrequency(&freq); // always succceeds - - LARGE_INTEGER counter; - QueryPerformanceCounter(&counter); - return time_point(duration(counter.QuadPart * nano::den / freq.QuadPart)); -} - -#elif defined(CLOCK_MONOTONIC) - -// On Apple platforms only CLOCK_UPTIME_RAW or mach_absolute_time are able to -// time functions in the nanosecond range. Thus, they are the only acceptable -// implementations of steady_clock. -#ifdef __APPLE__ -#error "Never use CLOCK_MONOTONIC for steady_clock::now on Apple platforms" -#endif - -steady_clock::time_point -steady_clock::now() _NOEXCEPT -{ - struct timespec tp; - if (0 != clock_gettime(CLOCK_MONOTONIC, &tp)) - __throw_system_error(errno, "clock_gettime(CLOCK_MONOTONIC) failed"); - return time_point(seconds(tp.tv_sec) + nanoseconds(tp.tv_nsec)); -} - -#else -#error "Monotonic clock not implemented" -#endif - -#endif // !_LIBCPP_HAS_NO_MONOTONIC_CLOCK - -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/condition_variable.cpp b/lib/libcxx/src/condition_variable.cpp deleted file mode 100644 index 2200aefb804..00000000000 --- a/lib/libcxx/src/condition_variable.cpp +++ /dev/null @@ -1,93 +0,0 @@ -//===-------------------- condition_variable.cpp --------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "__config" - -#ifndef _LIBCPP_HAS_NO_THREADS - -#include "condition_variable" -#include "thread" -#include "system_error" -#include "__undef_macros" - -_LIBCPP_BEGIN_NAMESPACE_STD - -condition_variable::~condition_variable() -{ - __libcpp_condvar_destroy(&__cv_); -} - -void -condition_variable::notify_one() _NOEXCEPT -{ - __libcpp_condvar_signal(&__cv_); -} - -void -condition_variable::notify_all() _NOEXCEPT -{ - __libcpp_condvar_broadcast(&__cv_); -} - -void -condition_variable::wait(unique_lock<mutex>& lk) _NOEXCEPT -{ - if (!lk.owns_lock()) - __throw_system_error(EPERM, - "condition_variable::wait: mutex not locked"); - int ec = __libcpp_condvar_wait(&__cv_, lk.mutex()->native_handle()); - if (ec) - __throw_system_error(ec, "condition_variable wait failed"); -} - -void -condition_variable::__do_timed_wait(unique_lock<mutex>& lk, - chrono::time_point<chrono::system_clock, chrono::nanoseconds> tp) _NOEXCEPT -{ - using namespace chrono; - if (!lk.owns_lock()) - __throw_system_error(EPERM, - "condition_variable::timed wait: mutex not locked"); - nanoseconds d = tp.time_since_epoch(); - if (d > nanoseconds(0x59682F000000E941)) - d = nanoseconds(0x59682F000000E941); - timespec ts; - seconds s = duration_cast<seconds>(d); - typedef decltype(ts.tv_sec) ts_sec; - _LIBCPP_CONSTEXPR ts_sec ts_sec_max = numeric_limits<ts_sec>::max(); - if (s.count() < ts_sec_max) - { - ts.tv_sec = static_cast<ts_sec>(s.count()); - ts.tv_nsec = static_cast<decltype(ts.tv_nsec)>((d - s).count()); - } - else - { - ts.tv_sec = ts_sec_max; - ts.tv_nsec = giga::num - 1; - } - int ec = __libcpp_condvar_timedwait(&__cv_, lk.mutex()->native_handle(), &ts); - if (ec != 0 && ec != ETIMEDOUT) - __throw_system_error(ec, "condition_variable timed_wait failed"); -} - -void -notify_all_at_thread_exit(condition_variable& cond, unique_lock<mutex> lk) -{ - auto& tl_ptr = __thread_local_data(); - // If this thread was not created using std::thread then it will not have - // previously allocated. - if (tl_ptr.get() == nullptr) { - tl_ptr.set_pointer(new __thread_struct); - } - __thread_local_data()->notify_all_at_thread_exit(&cond, lk.release()); -} - -_LIBCPP_END_NAMESPACE_STD - -#endif // !_LIBCPP_HAS_NO_THREADS diff --git a/lib/libcxx/src/debug.cpp b/lib/libcxx/src/debug.cpp deleted file mode 100644 index f2fc1ceb495..00000000000 --- a/lib/libcxx/src/debug.cpp +++ /dev/null @@ -1,618 +0,0 @@ -//===-------------------------- debug.cpp ---------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "__config" -#include "__debug" -#include "functional" -#include "algorithm" -#include "string" -#include "cstdio" -#include "__hash_table" -#include "mutex" - -_LIBCPP_BEGIN_NAMESPACE_STD - -static std::string make_what_str(__libcpp_debug_info const& info) { - string msg = info.__file_; - msg += ":" + to_string(info.__line_) + ": _LIBCPP_ASSERT '"; - msg += info.__pred_; - msg += "' failed. "; - msg += info.__msg_; - return msg; -} - -_LIBCPP_SAFE_STATIC __libcpp_debug_function_type - __libcpp_debug_function = __libcpp_abort_debug_function; - -bool __libcpp_set_debug_function(__libcpp_debug_function_type __func) { - __libcpp_debug_function = __func; - return true; -} - -_LIBCPP_NORETURN void __libcpp_abort_debug_function(__libcpp_debug_info const& info) { - std::fprintf(stderr, "%s\n", make_what_str(info).c_str()); - std::abort(); -} - -_LIBCPP_NORETURN void __libcpp_throw_debug_function(__libcpp_debug_info const& info) { -#ifndef _LIBCPP_NO_EXCEPTIONS - throw __libcpp_debug_exception(info); -#else - __libcpp_abort_debug_function(info); -#endif -} - -struct __libcpp_debug_exception::__libcpp_debug_exception_imp { - __libcpp_debug_info __info_; - std::string __what_str_; -}; - -__libcpp_debug_exception::__libcpp_debug_exception() _NOEXCEPT - : __imp_(nullptr) { -} - -__libcpp_debug_exception::__libcpp_debug_exception( - __libcpp_debug_info const& info) : __imp_(new __libcpp_debug_exception_imp) -{ - __imp_->__info_ = info; - __imp_->__what_str_ = make_what_str(info); -} -__libcpp_debug_exception::__libcpp_debug_exception( - __libcpp_debug_exception const& other) : __imp_(nullptr) { - if (other.__imp_) - __imp_ = new __libcpp_debug_exception_imp(*other.__imp_); -} - -__libcpp_debug_exception::~__libcpp_debug_exception() _NOEXCEPT { - if (__imp_) - delete __imp_; -} - -const char* __libcpp_debug_exception::what() const _NOEXCEPT { - if (__imp_) - return __imp_->__what_str_.c_str(); - return "__libcpp_debug_exception"; -} - -_LIBCPP_FUNC_VIS -__libcpp_db* -__get_db() -{ - static __libcpp_db db; - return &db; -} - -_LIBCPP_FUNC_VIS -const __libcpp_db* -__get_const_db() -{ - return __get_db(); -} - -namespace -{ - -#ifndef _LIBCPP_HAS_NO_THREADS -typedef mutex mutex_type; -typedef lock_guard<mutex_type> WLock; -typedef lock_guard<mutex_type> RLock; - -mutex_type& -mut() -{ - static mutex_type m; - return m; -} -#endif // !_LIBCPP_HAS_NO_THREADS - -} // unnamed namespace - -__i_node::~__i_node() -{ - if (__next_) - { - __next_->~__i_node(); - free(__next_); - } -} - -__c_node::~__c_node() -{ - free(beg_); - if (__next_) - { - __next_->~__c_node(); - free(__next_); - } -} - -__libcpp_db::__libcpp_db() - : __cbeg_(nullptr), - __cend_(nullptr), - __csz_(0), - __ibeg_(nullptr), - __iend_(nullptr), - __isz_(0) -{ -} - -__libcpp_db::~__libcpp_db() -{ - if (__cbeg_) - { - for (__c_node** p = __cbeg_; p != __cend_; ++p) - { - if (*p != nullptr) - { - (*p)->~__c_node(); - free(*p); - } - } - free(__cbeg_); - } - if (__ibeg_) - { - for (__i_node** p = __ibeg_; p != __iend_; ++p) - { - if (*p != nullptr) - { - (*p)->~__i_node(); - free(*p); - } - } - free(__ibeg_); - } -} - -void* -__libcpp_db::__find_c_from_i(void* __i) const -{ -#ifndef _LIBCPP_HAS_NO_THREADS - RLock _(mut()); -#endif - __i_node* i = __find_iterator(__i); - _LIBCPP_ASSERT(i != nullptr, "iterator not found in debug database."); - return i->__c_ != nullptr ? i->__c_->__c_ : nullptr; -} - -void -__libcpp_db::__insert_ic(void* __i, const void* __c) -{ -#ifndef _LIBCPP_HAS_NO_THREADS - WLock _(mut()); -#endif - if (__cbeg_ == __cend_) - return; - size_t hc = hash<const void*>()(__c) % static_cast<size_t>(__cend_ - __cbeg_); - __c_node* c = __cbeg_[hc]; - if (c == nullptr) - return; - while (c->__c_ != __c) - { - c = c->__next_; - if (c == nullptr) - return; - } - __i_node* i = __insert_iterator(__i); - c->__add(i); - i->__c_ = c; -} - -__c_node* -__libcpp_db::__insert_c(void* __c) -{ -#ifndef _LIBCPP_HAS_NO_THREADS - WLock _(mut()); -#endif - if (__csz_ + 1 > static_cast<size_t>(__cend_ - __cbeg_)) - { - size_t nc = __next_prime(2*static_cast<size_t>(__cend_ - __cbeg_) + 1); - __c_node** cbeg = static_cast<__c_node**>(calloc(nc, sizeof(void*))); - if (cbeg == nullptr) - __throw_bad_alloc(); - - for (__c_node** p = __cbeg_; p != __cend_; ++p) - { - __c_node* q = *p; - while (q != nullptr) - { - size_t h = hash<void*>()(q->__c_) % nc; - __c_node* r = q->__next_; - q->__next_ = cbeg[h]; - cbeg[h] = q; - q = r; - } - } - free(__cbeg_); - __cbeg_ = cbeg; - __cend_ = __cbeg_ + nc; - } - size_t hc = hash<void*>()(__c) % static_cast<size_t>(__cend_ - __cbeg_); - __c_node* p = __cbeg_[hc]; - __c_node* r = __cbeg_[hc] = - static_cast<__c_node*>(malloc(sizeof(__c_node))); - if (__cbeg_[hc] == nullptr) - __throw_bad_alloc(); - - r->__c_ = __c; - r->__next_ = p; - ++__csz_; - return r; -} - -void -__libcpp_db::__erase_i(void* __i) -{ -#ifndef _LIBCPP_HAS_NO_THREADS - WLock _(mut()); -#endif - if (__ibeg_ != __iend_) - { - size_t hi = hash<void*>()(__i) % static_cast<size_t>(__iend_ - __ibeg_); - __i_node* p = __ibeg_[hi]; - if (p != nullptr) - { - __i_node* q = nullptr; - while (p->__i_ != __i) - { - q = p; - p = p->__next_; - if (p == nullptr) - return; - } - if (q == nullptr) - __ibeg_[hi] = p->__next_; - else - q->__next_ = p->__next_; - __c_node* c = p->__c_; - --__isz_; - if (c != nullptr) - c->__remove(p); - free(p); - } - } -} - -void -__libcpp_db::__invalidate_all(void* __c) -{ -#ifndef _LIBCPP_HAS_NO_THREADS - WLock _(mut()); -#endif - if (__cend_ != __cbeg_) - { - size_t hc = hash<void*>()(__c) % static_cast<size_t>(__cend_ - __cbeg_); - __c_node* p = __cbeg_[hc]; - if (p == nullptr) - return; - while (p->__c_ != __c) - { - p = p->__next_; - if (p == nullptr) - return; - } - while (p->end_ != p->beg_) - { - --p->end_; - (*p->end_)->__c_ = nullptr; - } - } -} - -__c_node* -__libcpp_db::__find_c_and_lock(void* __c) const -{ -#ifndef _LIBCPP_HAS_NO_THREADS - mut().lock(); -#endif - if (__cend_ == __cbeg_) - { -#ifndef _LIBCPP_HAS_NO_THREADS - mut().unlock(); -#endif - return nullptr; - } - size_t hc = hash<void*>()(__c) % static_cast<size_t>(__cend_ - __cbeg_); - __c_node* p = __cbeg_[hc]; - if (p == nullptr) - { -#ifndef _LIBCPP_HAS_NO_THREADS - mut().unlock(); -#endif - return nullptr; - } - while (p->__c_ != __c) - { - p = p->__next_; - if (p == nullptr) - { -#ifndef _LIBCPP_HAS_NO_THREADS - mut().unlock(); -#endif - return nullptr; - } - } - return p; -} - -__c_node* -__libcpp_db::__find_c(void* __c) const -{ - size_t hc = hash<void*>()(__c) % static_cast<size_t>(__cend_ - __cbeg_); - __c_node* p = __cbeg_[hc]; - _LIBCPP_ASSERT(p != nullptr, "debug mode internal logic error __find_c A"); - while (p->__c_ != __c) - { - p = p->__next_; - _LIBCPP_ASSERT(p != nullptr, "debug mode internal logic error __find_c B"); - } - return p; -} - -void -__libcpp_db::unlock() const -{ -#ifndef _LIBCPP_HAS_NO_THREADS - mut().unlock(); -#endif -} - -void -__libcpp_db::__erase_c(void* __c) -{ -#ifndef _LIBCPP_HAS_NO_THREADS - WLock _(mut()); -#endif - if (__cend_ != __cbeg_) - { - size_t hc = hash<void*>()(__c) % static_cast<size_t>(__cend_ - __cbeg_); - __c_node* p = __cbeg_[hc]; - if (p == nullptr) - return; - __c_node* q = nullptr; - _LIBCPP_ASSERT(p != nullptr, "debug mode internal logic error __erase_c A"); - while (p->__c_ != __c) - { - q = p; - p = p->__next_; - if (p == nullptr) - return; - _LIBCPP_ASSERT(p != nullptr, "debug mode internal logic error __erase_c B"); - } - if (q == nullptr) - __cbeg_[hc] = p->__next_; - else - q->__next_ = p->__next_; - while (p->end_ != p->beg_) - { - --p->end_; - (*p->end_)->__c_ = nullptr; - } - free(p->beg_); - free(p); - --__csz_; - } -} - -void -__libcpp_db::__iterator_copy(void* __i, const void* __i0) -{ -#ifndef _LIBCPP_HAS_NO_THREADS - WLock _(mut()); -#endif - __i_node* i = __find_iterator(__i); - __i_node* i0 = __find_iterator(__i0); - __c_node* c0 = i0 != nullptr ? i0->__c_ : nullptr; - if (i == nullptr && i0 != nullptr) - i = __insert_iterator(__i); - __c_node* c = i != nullptr ? i->__c_ : nullptr; - if (c != c0) - { - if (c != nullptr) - c->__remove(i); - if (i != nullptr) - { - i->__c_ = nullptr; - if (c0 != nullptr) - { - i->__c_ = c0; - i->__c_->__add(i); - } - } - } -} - -bool -__libcpp_db::__dereferenceable(const void* __i) const -{ -#ifndef _LIBCPP_HAS_NO_THREADS - RLock _(mut()); -#endif - __i_node* i = __find_iterator(__i); - return i != nullptr && i->__c_ != nullptr && i->__c_->__dereferenceable(__i); -} - -bool -__libcpp_db::__decrementable(const void* __i) const -{ -#ifndef _LIBCPP_HAS_NO_THREADS - RLock _(mut()); -#endif - __i_node* i = __find_iterator(__i); - return i != nullptr && i->__c_ != nullptr && i->__c_->__decrementable(__i); -} - -bool -__libcpp_db::__addable(const void* __i, ptrdiff_t __n) const -{ -#ifndef _LIBCPP_HAS_NO_THREADS - RLock _(mut()); -#endif - __i_node* i = __find_iterator(__i); - return i != nullptr && i->__c_ != nullptr && i->__c_->__addable(__i, __n); -} - -bool -__libcpp_db::__subscriptable(const void* __i, ptrdiff_t __n) const -{ -#ifndef _LIBCPP_HAS_NO_THREADS - RLock _(mut()); -#endif - __i_node* i = __find_iterator(__i); - return i != nullptr && i->__c_ != nullptr && i->__c_->__subscriptable(__i, __n); -} - -bool -__libcpp_db::__less_than_comparable(const void* __i, const void* __j) const -{ -#ifndef _LIBCPP_HAS_NO_THREADS - RLock _(mut()); -#endif - __i_node* i = __find_iterator(__i); - __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; -} - -void -__libcpp_db::swap(void* c1, void* c2) -{ -#ifndef _LIBCPP_HAS_NO_THREADS - WLock _(mut()); -#endif - size_t hc = hash<void*>()(c1) % static_cast<size_t>(__cend_ - __cbeg_); - __c_node* p1 = __cbeg_[hc]; - _LIBCPP_ASSERT(p1 != nullptr, "debug mode internal logic error swap A"); - while (p1->__c_ != c1) - { - p1 = p1->__next_; - _LIBCPP_ASSERT(p1 != nullptr, "debug mode internal logic error swap B"); - } - hc = hash<void*>()(c2) % static_cast<size_t>(__cend_ - __cbeg_); - __c_node* p2 = __cbeg_[hc]; - _LIBCPP_ASSERT(p2 != nullptr, "debug mode internal logic error swap C"); - while (p2->__c_ != c2) - { - p2 = p2->__next_; - _LIBCPP_ASSERT(p2 != nullptr, "debug mode internal logic error swap D"); - } - std::swap(p1->beg_, p2->beg_); - std::swap(p1->end_, p2->end_); - std::swap(p1->cap_, p2->cap_); - for (__i_node** p = p1->beg_; p != p1->end_; ++p) - (*p)->__c_ = p1; - for (__i_node** p = p2->beg_; p != p2->end_; ++p) - (*p)->__c_ = p2; -} - -void -__libcpp_db::__insert_i(void* __i) -{ -#ifndef _LIBCPP_HAS_NO_THREADS - WLock _(mut()); -#endif - __insert_iterator(__i); -} - -void -__c_node::__add(__i_node* i) -{ - if (end_ == cap_) - { - size_t nc = 2*static_cast<size_t>(cap_ - beg_); - if (nc == 0) - nc = 1; - __i_node** beg = - static_cast<__i_node**>(malloc(nc * sizeof(__i_node*))); - if (beg == nullptr) - __throw_bad_alloc(); - - if (nc > 1) - memcpy(beg, beg_, nc/2*sizeof(__i_node*)); - free(beg_); - beg_ = beg; - end_ = beg_ + nc/2; - cap_ = beg_ + nc; - } - *end_++ = i; -} - -// private api - -_LIBCPP_HIDDEN -__i_node* -__libcpp_db::__insert_iterator(void* __i) -{ - if (__isz_ + 1 > static_cast<size_t>(__iend_ - __ibeg_)) - { - size_t nc = __next_prime(2*static_cast<size_t>(__iend_ - __ibeg_) + 1); - __i_node** ibeg = static_cast<__i_node**>(calloc(nc, sizeof(void*))); - if (ibeg == nullptr) - __throw_bad_alloc(); - - for (__i_node** p = __ibeg_; p != __iend_; ++p) - { - __i_node* q = *p; - while (q != nullptr) - { - size_t h = hash<void*>()(q->__i_) % nc; - __i_node* r = q->__next_; - q->__next_ = ibeg[h]; - ibeg[h] = q; - q = r; - } - } - free(__ibeg_); - __ibeg_ = ibeg; - __iend_ = __ibeg_ + nc; - } - size_t hi = hash<void*>()(__i) % static_cast<size_t>(__iend_ - __ibeg_); - __i_node* p = __ibeg_[hi]; - __i_node* r = __ibeg_[hi] = - static_cast<__i_node*>(malloc(sizeof(__i_node))); - if (r == nullptr) - __throw_bad_alloc(); - - ::new(r) __i_node(__i, p, nullptr); - ++__isz_; - return r; -} - -_LIBCPP_HIDDEN -__i_node* -__libcpp_db::__find_iterator(const void* __i) const -{ - __i_node* r = nullptr; - if (__ibeg_ != __iend_) - { - size_t h = hash<const void*>()(__i) % static_cast<size_t>(__iend_ - __ibeg_); - for (__i_node* nd = __ibeg_[h]; nd != nullptr; nd = nd->__next_) - { - if (nd->__i_ == __i) - { - r = nd; - break; - } - } - } - return r; -} - -_LIBCPP_HIDDEN -void -__c_node::__remove(__i_node* p) -{ - __i_node** r = find(beg_, end_, p); - _LIBCPP_ASSERT(r != end_, "debug mode internal logic error __c_node::__remove"); - if (--end_ != r) - memmove(r, r+1, static_cast<size_t>(end_ - r)*sizeof(__i_node*)); -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/exception.cpp b/lib/libcxx/src/exception.cpp deleted file mode 100644 index 3d2dcfd5b10..00000000000 --- a/lib/libcxx/src/exception.cpp +++ /dev/null @@ -1,37 +0,0 @@ -//===------------------------ exception.cpp -------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "exception" -#include "new" -#include "typeinfo" - -#if defined(LIBCXXRT) || defined(LIBCXX_BUILDING_LIBCXXABI) || \ - (defined(__APPLE__) && !defined(_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY)) - #include <cxxabi.h> - using namespace __cxxabiv1; - #define HAVE_DEPENDENT_EH_ABI 1 -#endif - -#if defined(_LIBCPP_ABI_MICROSOFT) -#include "support/runtime/exception_msvc.ipp" -#include "support/runtime/exception_pointer_msvc.ipp" -#elif defined(_LIBCPPABI_VERSION) -#include "support/runtime/exception_libcxxabi.ipp" -#include "support/runtime/exception_pointer_cxxabi.ipp" -#elif defined(LIBCXXRT) -#include "support/runtime/exception_libcxxrt.ipp" -#include "support/runtime/exception_pointer_cxxabi.ipp" -#elif defined(__GLIBCXX__) -#include "support/runtime/exception_glibcxx.ipp" -#include "support/runtime/exception_pointer_glibcxx.ipp" -#else -#include "include/atomic_support.h" -#include "support/runtime/exception_fallback.ipp" -#include "support/runtime/exception_pointer_unimplemented.ipp" -#endif diff --git a/lib/libcxx/src/experimental/memory_resource.cpp b/lib/libcxx/src/experimental/memory_resource.cpp deleted file mode 100644 index 7f0052f2b50..00000000000 --- a/lib/libcxx/src/experimental/memory_resource.cpp +++ /dev/null @@ -1,155 +0,0 @@ -//===------------------------ memory_resource.cpp -------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "experimental/memory_resource" - -#ifndef _LIBCPP_HAS_NO_ATOMIC_HEADER -#include "atomic" -#elif !defined(_LIBCPP_HAS_NO_THREADS) -#include "mutex" -#endif - -_LIBCPP_BEGIN_NAMESPACE_LFTS_PMR - -// memory_resource - -//memory_resource::~memory_resource() {} - -// new_delete_resource() - -class _LIBCPP_TYPE_VIS __new_delete_memory_resource_imp - : public memory_resource -{ -public: - ~__new_delete_memory_resource_imp() = default; - -protected: - virtual void* do_allocate(size_t __size, size_t __align) - { return _VSTD::__libcpp_allocate(__size, __align); /* FIXME */} - - virtual void do_deallocate(void* __p, size_t __n, size_t __align) { - _VSTD::__libcpp_deallocate(__p, __n, __align); /* FIXME */ - } - - virtual bool do_is_equal(memory_resource const & __other) const _NOEXCEPT - { return &__other == this; } -}; - -// null_memory_resource() - -class _LIBCPP_TYPE_VIS __null_memory_resource_imp - : public memory_resource -{ -public: - ~__null_memory_resource_imp() = default; - -protected: - virtual void* do_allocate(size_t, size_t) { - __throw_bad_alloc(); - } - virtual void do_deallocate(void *, size_t, size_t) {} - virtual bool do_is_equal(memory_resource const & __other) const _NOEXCEPT - { return &__other == this; } -}; - -namespace { - -union ResourceInitHelper { - struct { - __new_delete_memory_resource_imp new_delete_res; - __null_memory_resource_imp null_res; - } resources; - char dummy; - _LIBCPP_CONSTEXPR_AFTER_CXX11 ResourceInitHelper() : resources() {} - ~ResourceInitHelper() {} -}; - -// Detect if the init_priority attribute is supported. -#if (defined(_LIBCPP_COMPILER_GCC) && defined(__APPLE__)) \ - || defined(_LIBCPP_COMPILER_MSVC) -// GCC on Apple doesn't support the init priority attribute, -// and MSVC doesn't support any GCC attributes. -# define _LIBCPP_INIT_PRIORITY_MAX -#else -# define _LIBCPP_INIT_PRIORITY_MAX __attribute__((init_priority(101))) -#endif - -// 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; - -} // end namespace - - -memory_resource * new_delete_resource() _NOEXCEPT { - return &res_init.resources.new_delete_res; -} - -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 -{ -#ifndef _LIBCPP_HAS_NO_ATOMIC_HEADER - _LIBCPP_SAFE_STATIC static atomic<memory_resource*> __res = - ATOMIC_VAR_INIT(&res_init.resources.new_delete_res); - if (set) { - new_res = new_res ? new_res : new_delete_resource(); - // TODO: Can a weaker ordering be used? - return _VSTD::atomic_exchange_explicit( - &__res, new_res, memory_order::memory_order_acq_rel); - } - else { - return _VSTD::atomic_load_explicit( - &__res, memory_order::memory_order_acquire); - } -#elif !defined(_LIBCPP_HAS_NO_THREADS) - _LIBCPP_SAFE_STATIC static memory_resource * res = &res_init.resources.new_delete_res; - static mutex res_lock; - if (set) { - new_res = new_res ? new_res : new_delete_resource(); - lock_guard<mutex> guard(res_lock); - memory_resource * old_res = res; - res = new_res; - return old_res; - } else { - lock_guard<mutex> guard(res_lock); - return res; - } -#else - _LIBCPP_SAFE_STATIC static memory_resource* res = &res_init.resources.new_delete_res; - if (set) { - new_res = new_res ? new_res : new_delete_resource(); - memory_resource * old_res = res; - res = new_res; - return old_res; - } else { - return res; - } -#endif -} - -memory_resource * get_default_resource() _NOEXCEPT -{ - return __default_memory_resource(); -} - -memory_resource * set_default_resource(memory_resource * __new_res) _NOEXCEPT -{ - return __default_memory_resource(true, __new_res); -} - -_LIBCPP_END_NAMESPACE_LFTS_PMR diff --git a/lib/libcxx/src/filesystem/directory_iterator.cpp b/lib/libcxx/src/filesystem/directory_iterator.cpp deleted file mode 100644 index f0d807a03db..00000000000 --- a/lib/libcxx/src/filesystem/directory_iterator.cpp +++ /dev/null @@ -1,396 +0,0 @@ -//===------------------ directory_iterator.cpp ----------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "filesystem" -#include "__config" -#if defined(_LIBCPP_WIN32API) -#define WIN32_LEAN_AND_MEAN -#include <Windows.h> -#else -#include <dirent.h> -#endif -#include <errno.h> - -#include "filesystem_common.h" - -_LIBCPP_BEGIN_NAMESPACE_FILESYSTEM - -namespace detail { -namespace { - -#if !defined(_LIBCPP_WIN32API) -template <class DirEntT, class = decltype(DirEntT::d_type)> -static file_type get_file_type(DirEntT* ent, int) { - switch (ent->d_type) { - case DT_BLK: - return file_type::block; - case DT_CHR: - return file_type::character; - case DT_DIR: - return file_type::directory; - case DT_FIFO: - return file_type::fifo; - case DT_LNK: - return file_type::symlink; - case DT_REG: - return file_type::regular; - case DT_SOCK: - return file_type::socket; - // Unlike in lstat, hitting "unknown" here simply means that the underlying - // filesystem doesn't support d_type. Report is as 'none' so we correctly - // set the cache to empty. - case DT_UNKNOWN: - break; - } - return file_type::none; -} - -template <class DirEntT> -static file_type get_file_type(DirEntT* ent, long) { - return file_type::none; -} - -static pair<string_view, file_type> posix_readdir(DIR* dir_stream, - error_code& ec) { - struct dirent* dir_entry_ptr = nullptr; - errno = 0; // zero errno in order to detect errors - ec.clear(); - if ((dir_entry_ptr = ::readdir(dir_stream)) == nullptr) { - if (errno) - ec = capture_errno(); - return {}; - } else { - return {dir_entry_ptr->d_name, get_file_type(dir_entry_ptr, 0)}; - } -} -#else - -static file_type get_file_type(const WIN32_FIND_DATA& data) { - //auto attrs = data.dwFileAttributes; - // FIXME(EricWF) - return file_type::unknown; -} -static uintmax_t get_file_size(const WIN32_FIND_DATA& data) { - return (data.nFileSizeHight * (MAXDWORD + 1)) + data.nFileSizeLow; -} -static file_time_type get_write_time(const WIN32_FIND_DATA& data) { - ULARGE_INTEGER tmp; - FILETIME& time = data.ftLastWriteTime; - tmp.u.LowPart = time.dwLowDateTime; - tmp.u.HighPart = time.dwHighDateTime; - return file_time_type(file_time_type::duration(time.QuadPart)); -} - -#endif - -} // namespace -} // namespace detail - -using detail::ErrorHandler; - -#if defined(_LIBCPP_WIN32API) -class __dir_stream { -public: - __dir_stream() = delete; - __dir_stream& operator=(const __dir_stream&) = delete; - - __dir_stream(__dir_stream&& __ds) noexcept : __stream_(__ds.__stream_), - __root_(move(__ds.__root_)), - __entry_(move(__ds.__entry_)) { - __ds.__stream_ = INVALID_HANDLE_VALUE; - } - - __dir_stream(const path& root, directory_options opts, error_code& ec) - : __stream_(INVALID_HANDLE_VALUE), __root_(root) { - __stream_ = ::FindFirstFileEx(root.c_str(), &__data_); - if (__stream_ == INVALID_HANDLE_VALUE) { - ec = error_code(::GetLastError(), generic_category()); - const bool ignore_permission_denied = - bool(opts & directory_options::skip_permission_denied); - if (ignore_permission_denied && ec.value() == ERROR_ACCESS_DENIED) - ec.clear(); - return; - } - } - - ~__dir_stream() noexcept { - if (__stream_ == INVALID_HANDLE_VALUE) - return; - close(); - } - - bool good() const noexcept { return __stream_ != INVALID_HANDLE_VALUE; } - - bool advance(error_code& ec) { - while (::FindNextFile(__stream_, &__data_)) { - if (!strcmp(__data_.cFileName, ".") || strcmp(__data_.cFileName, "..")) - continue; - // FIXME: Cache more of this - //directory_entry::__cached_data cdata; - //cdata.__type_ = get_file_type(__data_); - //cdata.__size_ = get_file_size(__data_); - //cdata.__write_time_ = get_write_time(__data_); - __entry_.__assign_iter_entry( - __root_ / __data_.cFileName, - directory_entry::__create_iter_result(get_file_type(__data))); - return true; - } - ec = error_code(::GetLastError(), generic_category()); - close(); - return false; - } - -private: - error_code close() noexcept { - error_code ec; - if (!::FindClose(__stream_)) - ec = error_code(::GetLastError(), generic_category()); - __stream_ = INVALID_HANDLE_VALUE; - return ec; - } - - HANDLE __stream_{INVALID_HANDLE_VALUE}; - WIN32_FIND_DATA __data_; - -public: - path __root_; - directory_entry __entry_; -}; -#else -class __dir_stream { -public: - __dir_stream() = delete; - __dir_stream& operator=(const __dir_stream&) = delete; - - __dir_stream(__dir_stream&& other) noexcept : __stream_(other.__stream_), - __root_(move(other.__root_)), - __entry_(move(other.__entry_)) { - other.__stream_ = nullptr; - } - - __dir_stream(const path& root, directory_options opts, error_code& ec) - : __stream_(nullptr), __root_(root) { - if ((__stream_ = ::opendir(root.c_str())) == nullptr) { - ec = detail::capture_errno(); - const bool allow_eacess = - bool(opts & directory_options::skip_permission_denied); - if (allow_eacess && ec.value() == EACCES) - ec.clear(); - return; - } - advance(ec); - } - - ~__dir_stream() noexcept { - if (__stream_) - close(); - } - - bool good() const noexcept { return __stream_ != nullptr; } - - bool advance(error_code& ec) { - while (true) { - auto str_type_pair = detail::posix_readdir(__stream_, ec); - auto& str = str_type_pair.first; - if (str == "." || str == "..") { - continue; - } else if (ec || str.empty()) { - close(); - return false; - } else { - __entry_.__assign_iter_entry( - __root_ / str, - directory_entry::__create_iter_result(str_type_pair.second)); - return true; - } - } - } - -private: - error_code close() noexcept { - error_code m_ec; - if (::closedir(__stream_) == -1) - m_ec = detail::capture_errno(); - __stream_ = nullptr; - return m_ec; - } - - DIR* __stream_{nullptr}; - -public: - path __root_; - directory_entry __entry_; -}; -#endif - -// directory_iterator - -directory_iterator::directory_iterator(const path& p, error_code* ec, - directory_options opts) { - ErrorHandler<void> err("directory_iterator::directory_iterator(...)", ec, &p); - - error_code m_ec; - __imp_ = make_shared<__dir_stream>(p, opts, m_ec); - if (ec) - *ec = m_ec; - if (!__imp_->good()) { - __imp_.reset(); - if (m_ec) - err.report(m_ec); - } -} - -directory_iterator& directory_iterator::__increment(error_code* ec) { - _LIBCPP_ASSERT(__imp_, "Attempting to increment an invalid iterator"); - ErrorHandler<void> err("directory_iterator::operator++()", ec); - - error_code m_ec; - if (!__imp_->advance(m_ec)) { - path root = move(__imp_->__root_); - __imp_.reset(); - if (m_ec) - err.report(m_ec, "at root \"%s\"", root); - } - return *this; -} - -directory_entry const& directory_iterator::__dereference() const { - _LIBCPP_ASSERT(__imp_, "Attempting to dereference an invalid iterator"); - return __imp_->__entry_; -} - -// recursive_directory_iterator - -struct recursive_directory_iterator::__shared_imp { - stack<__dir_stream> __stack_; - directory_options __options_; -}; - -recursive_directory_iterator::recursive_directory_iterator( - const path& p, directory_options opt, error_code* ec) - : __imp_(nullptr), __rec_(true) { - ErrorHandler<void> err("recursive_directory_iterator", ec, &p); - - error_code m_ec; - __dir_stream new_s(p, opt, m_ec); - if (m_ec) - err.report(m_ec); - if (m_ec || !new_s.good()) - return; - - __imp_ = make_shared<__shared_imp>(); - __imp_->__options_ = opt; - __imp_->__stack_.push(move(new_s)); -} - -void recursive_directory_iterator::__pop(error_code* ec) { - _LIBCPP_ASSERT(__imp_, "Popping the end iterator"); - if (ec) - ec->clear(); - __imp_->__stack_.pop(); - if (__imp_->__stack_.size() == 0) - __imp_.reset(); - else - __advance(ec); -} - -directory_options recursive_directory_iterator::options() const { - return __imp_->__options_; -} - -int recursive_directory_iterator::depth() const { - return __imp_->__stack_.size() - 1; -} - -const directory_entry& recursive_directory_iterator::__dereference() const { - return __imp_->__stack_.top().__entry_; -} - -recursive_directory_iterator& -recursive_directory_iterator::__increment(error_code* ec) { - if (ec) - ec->clear(); - if (recursion_pending()) { - if (__try_recursion(ec) || (ec && *ec)) - return *this; - } - __rec_ = true; - __advance(ec); - return *this; -} - -void recursive_directory_iterator::__advance(error_code* ec) { - ErrorHandler<void> err("recursive_directory_iterator::operator++()", ec); - - const directory_iterator end_it; - auto& stack = __imp_->__stack_; - error_code m_ec; - while (stack.size() > 0) { - if (stack.top().advance(m_ec)) - return; - if (m_ec) - break; - stack.pop(); - } - - if (m_ec) { - path root = move(stack.top().__root_); - __imp_.reset(); - err.report(m_ec, "at root \"%s\"", root); - } else { - __imp_.reset(); - } -} - -bool recursive_directory_iterator::__try_recursion(error_code* ec) { - ErrorHandler<void> err("recursive_directory_iterator::operator++()", ec); - - bool rec_sym = bool(options() & directory_options::follow_directory_symlink); - - auto& curr_it = __imp_->__stack_.top(); - - bool skip_rec = false; - error_code m_ec; - if (!rec_sym) { - file_status st(curr_it.__entry_.__get_sym_ft(&m_ec)); - if (m_ec && status_known(st)) - m_ec.clear(); - if (m_ec || is_symlink(st) || !is_directory(st)) - skip_rec = true; - } else { - file_status st(curr_it.__entry_.__get_ft(&m_ec)); - if (m_ec && status_known(st)) - m_ec.clear(); - if (m_ec || !is_directory(st)) - skip_rec = true; - } - - if (!skip_rec) { - __dir_stream new_it(curr_it.__entry_.path(), __imp_->__options_, m_ec); - if (new_it.good()) { - __imp_->__stack_.push(move(new_it)); - return true; - } - } - if (m_ec) { - const bool allow_eacess = - bool(__imp_->__options_ & directory_options::skip_permission_denied); - if (m_ec.value() == EACCES && allow_eacess) { - if (ec) - ec->clear(); - } else { - path at_ent = move(curr_it.__entry_.__p_); - __imp_.reset(); - err.report(m_ec, "attempting recursion into \"%s\"", at_ent); - } - } - return false; -} - -_LIBCPP_END_NAMESPACE_FILESYSTEM diff --git a/lib/libcxx/src/filesystem/filesystem_common.h b/lib/libcxx/src/filesystem/filesystem_common.h deleted file mode 100644 index 40419ee35e6..00000000000 --- a/lib/libcxx/src/filesystem/filesystem_common.h +++ /dev/null @@ -1,436 +0,0 @@ -//===----------------------------------------------------------------------===//// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===//// - -#ifndef FILESYSTEM_COMMON_H -#define FILESYSTEM_COMMON_H - -#include "__config" -#include "filesystem" -#include "array" -#include "chrono" -#include "cstdlib" -#include "climits" - -#include <unistd.h> -#include <sys/stat.h> -#include <sys/statvfs.h> -#include <sys/time.h> // for ::utimes as used in __last_write_time -#include <fcntl.h> /* values for fchmodat */ - -#include "../include/apple_availability.h" - -#if !defined(__APPLE__) -// We can use the presence of UTIME_OMIT to detect platforms that provide -// utimensat. -#if defined(UTIME_OMIT) -#define _LIBCPP_USE_UTIMENSAT -#endif -#endif - -#if defined(__GNUC__) -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wunused-function" -#endif - -_LIBCPP_BEGIN_NAMESPACE_FILESYSTEM - -namespace detail { -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& target) : target(target), 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; - } - - // 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 char* unwrap(string const& s) { return s.c_str(); } -const char* 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)...); -} - -error_code capture_errno() { - _LIBCPP_ASSERT(errno, "Expected errno to be non-zero"); - return error_code(errno, generic_category()); -} - -template <class T> -T error_value(); -template <> -_LIBCPP_CONSTEXPR_AFTER_CXX11 void error_value<void>() {} -template <> -bool error_value<bool>() { - return false; -} -template <> -uintmax_t error_value<uintmax_t>() { - return uintmax_t(-1); -} -template <> -_LIBCPP_CONSTEXPR_AFTER_CXX11 file_time_type error_value<file_time_type>() { - return file_time_type::min(); -} -template <> -path error_value<path>() { - return {}; -} - -template <class T> -struct ErrorHandler { - const char* func_name; - error_code* ec = nullptr; - const path* p1 = nullptr; - const path* p2 = nullptr; - - ErrorHandler(const char* fname, error_code* ec, const path* p1 = nullptr, - const path* p2 = nullptr) - : func_name(fname), ec(ec), p1(p1), p2(p2) { - if (ec) - ec->clear(); - } - - T report(const error_code& m_ec) const { - if (ec) { - *ec = m_ec; - return error_value<T>(); - } - string what = string("in ") + func_name; - switch (bool(p1) + bool(p2)) { - case 0: - __throw_filesystem_error(what, m_ec); - case 1: - __throw_filesystem_error(what, *p1, m_ec); - case 2: - __throw_filesystem_error(what, *p1, *p2, m_ec); - } - _LIBCPP_UNREACHABLE(); - } - - template <class... Args> - T report(const error_code& m_ec, const char* msg, Args const&... args) const { - if (ec) { - *ec = m_ec; - return error_value<T>(); - } - string what = - string("in ") + func_name + ": " + format_string(msg, args...); - switch (bool(p1) + bool(p2)) { - case 0: - __throw_filesystem_error(what, m_ec); - case 1: - __throw_filesystem_error(what, *p1, m_ec); - case 2: - __throw_filesystem_error(what, *p1, *p2, m_ec); - } - _LIBCPP_UNREACHABLE(); - } - - 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...); - } - -private: - ErrorHandler(ErrorHandler const&) = delete; - ErrorHandler& operator=(ErrorHandler const&) = delete; -}; - -using chrono::duration; -using chrono::duration_cast; - -using TimeSpec = struct ::timespec; -using StatT = struct ::stat; - -template <class FileTimeT, class TimeT, - bool IsFloat = is_floating_point<typename FileTimeT::rep>::value> -struct time_util_base { - using rep = typename FileTimeT::rep; - using fs_duration = typename FileTimeT::duration; - using fs_seconds = duration<rep>; - using fs_nanoseconds = duration<rep, nano>; - using fs_microseconds = duration<rep, micro>; - - static constexpr rep max_seconds = - duration_cast<fs_seconds>(FileTimeT::duration::max()).count(); - - static constexpr rep max_nsec = - duration_cast<fs_nanoseconds>(FileTimeT::duration::max() - - fs_seconds(max_seconds)) - .count(); - - static constexpr rep min_seconds = - duration_cast<fs_seconds>(FileTimeT::duration::min()).count(); - - static constexpr rep min_nsec_timespec = - duration_cast<fs_nanoseconds>( - (FileTimeT::duration::min() - fs_seconds(min_seconds)) + - fs_seconds(1)) - .count(); - -private: -#if _LIBCPP_STD_VER > 11 && !defined(_LIBCPP_HAS_NO_CXX14_CONSTEXPR) - static constexpr fs_duration get_min_nsecs() { - return duration_cast<fs_duration>( - fs_nanoseconds(min_nsec_timespec) - - duration_cast<fs_nanoseconds>(fs_seconds(1))); - } - // Static assert that these values properly round trip. - static_assert(fs_seconds(min_seconds) + get_min_nsecs() == - FileTimeT::duration::min(), - "value doesn't roundtrip"); - - static constexpr 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; - return duration_cast<Years>(fs_seconds(max_seconds)) > Years(250) && - duration_cast<Years>(fs_seconds(min_seconds)) < Years(-250); - } - return max_seconds >= numeric_limits<TimeT>::max() && - min_seconds <= numeric_limits<TimeT>::min(); - } - static_assert(check_range(), "the representable range is unacceptable small"); -#endif -}; - -template <class FileTimeT, class TimeT> -struct time_util_base<FileTimeT, TimeT, true> { - using rep = typename FileTimeT::rep; - using fs_duration = typename FileTimeT::duration; - using fs_seconds = duration<rep>; - using fs_nanoseconds = duration<rep, nano>; - using fs_microseconds = duration<rep, micro>; - - static const rep max_seconds; - static const rep max_nsec; - static const rep min_seconds; - static const rep min_nsec_timespec; -}; - -template <class FileTimeT, class TimeT> -const typename FileTimeT::rep - time_util_base<FileTimeT, TimeT, true>::max_seconds = - duration_cast<fs_seconds>(FileTimeT::duration::max()).count(); - -template <class FileTimeT, class TimeT> -const typename FileTimeT::rep time_util_base<FileTimeT, TimeT, true>::max_nsec = - duration_cast<fs_nanoseconds>(FileTimeT::duration::max() - - fs_seconds(max_seconds)) - .count(); - -template <class FileTimeT, class TimeT> -const typename FileTimeT::rep - time_util_base<FileTimeT, TimeT, true>::min_seconds = - duration_cast<fs_seconds>(FileTimeT::duration::min()).count(); - -template <class FileTimeT, class TimeT> -const typename FileTimeT::rep - time_util_base<FileTimeT, TimeT, true>::min_nsec_timespec = - duration_cast<fs_nanoseconds>((FileTimeT::duration::min() - - fs_seconds(min_seconds)) + - fs_seconds(1)) - .count(); - -template <class FileTimeT, class TimeT, class TimeSpecT> -struct time_util : time_util_base<FileTimeT, TimeT> { - using Base = time_util_base<FileTimeT, TimeT>; - using Base::max_nsec; - using Base::max_seconds; - using Base::min_nsec_timespec; - using Base::min_seconds; - - using typename Base::fs_duration; - using typename Base::fs_microseconds; - using typename Base::fs_nanoseconds; - using typename Base::fs_seconds; - -public: - template <class CType, class ChronoType> - static _LIBCPP_CONSTEXPR_AFTER_CXX11 bool checked_set(CType* out, - ChronoType time) { - using Lim = numeric_limits<CType>; - if (time > Lim::max() || time < Lim::min()) - return false; - *out = static_cast<CType>(time); - return true; - } - - static _LIBCPP_CONSTEXPR_AFTER_CXX11 bool is_representable(TimeSpecT tm) { - if (tm.tv_sec >= 0) { - return tm.tv_sec < max_seconds || - (tm.tv_sec == max_seconds && tm.tv_nsec <= max_nsec); - } else if (tm.tv_sec == (min_seconds - 1)) { - return tm.tv_nsec >= min_nsec_timespec; - } else { - return tm.tv_sec >= min_seconds; - } - } - - static _LIBCPP_CONSTEXPR_AFTER_CXX11 bool is_representable(FileTimeT tm) { - auto secs = duration_cast<fs_seconds>(tm.time_since_epoch()); - auto nsecs = duration_cast<fs_nanoseconds>(tm.time_since_epoch() - secs); - if (nsecs.count() < 0) { - secs = secs + fs_seconds(1); - nsecs = nsecs + fs_seconds(1); - } - using TLim = numeric_limits<TimeT>; - if (secs.count() >= 0) - return secs.count() <= TLim::max(); - return secs.count() >= TLim::min(); - } - - static _LIBCPP_CONSTEXPR_AFTER_CXX11 FileTimeT - convert_from_timespec(TimeSpecT tm) { - if (tm.tv_sec >= 0 || tm.tv_nsec == 0) { - return FileTimeT(fs_seconds(tm.tv_sec) + - duration_cast<fs_duration>(fs_nanoseconds(tm.tv_nsec))); - } else { // tm.tv_sec < 0 - auto adj_subsec = duration_cast<fs_duration>(fs_seconds(1) - - fs_nanoseconds(tm.tv_nsec)); - auto Dur = fs_seconds(tm.tv_sec + 1) - adj_subsec; - return FileTimeT(Dur); - } - } - - template <class SubSecT> - static _LIBCPP_CONSTEXPR_AFTER_CXX11 bool - set_times_checked(TimeT* sec_out, SubSecT* subsec_out, FileTimeT tp) { - auto dur = tp.time_since_epoch(); - auto sec_dur = duration_cast<fs_seconds>(dur); - auto subsec_dur = duration_cast<fs_nanoseconds>(dur - sec_dur); - // The tv_nsec and tv_usec fields must not be negative so adjust accordingly - if (subsec_dur.count() < 0) { - if (sec_dur.count() > min_seconds) { - sec_dur = sec_dur - fs_seconds(1); - subsec_dur = subsec_dur + fs_seconds(1); - } else { - subsec_dur = fs_nanoseconds::zero(); - } - } - return checked_set(sec_out, sec_dur.count()) && - checked_set(subsec_out, subsec_dur.count()); - } - static _LIBCPP_CONSTEXPR_AFTER_CXX11 bool convert_to_timespec(TimeSpecT& dest, - FileTimeT tp) { - if (!is_representable(tp)) - return false; - return set_times_checked(&dest.tv_sec, &dest.tv_nsec, tp); - } -}; - -using fs_time = time_util<file_time_type, time_t, TimeSpec>; - -#if defined(__APPLE__) -TimeSpec extract_mtime(StatT const& st) { return st.st_mtimespec; } -TimeSpec extract_atime(StatT const& st) { return st.st_atimespec; } -#else -TimeSpec extract_mtime(StatT const& st) { return st.st_mtim; } -TimeSpec extract_atime(StatT const& st) { return st.st_atim; } -#endif - -// allow the utimes implementation to compile even it we're not going -// to use it. - -bool posix_utimes(const path& p, std::array<TimeSpec, 2> const& TS, - error_code& ec) { - using namespace chrono; - auto Convert = [](long nsec) { - using int_type = decltype(std::declval< ::timeval>().tv_usec); - auto dur = duration_cast<microseconds>(nanoseconds(nsec)).count(); - return static_cast<int_type>(dur); - }; - struct ::timeval ConvertedTS[2] = {{TS[0].tv_sec, Convert(TS[0].tv_nsec)}, - {TS[1].tv_sec, Convert(TS[1].tv_nsec)}}; - if (::utimes(p.c_str(), ConvertedTS) == -1) { - ec = capture_errno(); - return true; - } - return false; -} - -#if defined(_LIBCPP_USE_UTIMENSAT) -bool posix_utimensat(const path& p, std::array<TimeSpec, 2> const& TS, - error_code& ec) { - if (::utimensat(AT_FDCWD, p.c_str(), TS.data(), 0) == -1) { - ec = capture_errno(); - return true; - } - return false; -} -#endif - -bool set_file_times(const path& p, std::array<TimeSpec, 2> const& TS, - error_code& ec) { -#if !defined(_LIBCPP_USE_UTIMENSAT) - return posix_utimes(p, TS, ec); -#else - return posix_utimensat(p, TS, ec); -#endif -} - -} // namespace -} // end namespace detail - -_LIBCPP_END_NAMESPACE_FILESYSTEM - -#endif // FILESYSTEM_COMMON_H diff --git a/lib/libcxx/src/filesystem/int128_builtins.cpp b/lib/libcxx/src/filesystem/int128_builtins.cpp deleted file mode 100644 index 66adbdd2dc8..00000000000 --- a/lib/libcxx/src/filesystem/int128_builtins.cpp +++ /dev/null @@ -1,55 +0,0 @@ -/*===-- int128_builtins.cpp - Implement __muloti4 --------------------------=== - * - * The LLVM Compiler Infrastructure - * - * This file is dual licensed under the MIT and the University of Illinois Open - * Source Licenses. See LICENSE.TXT for details. - * - * ===----------------------------------------------------------------------=== - * - * This file implements __muloti4, and is stolen from the compiler_rt library. - * - * FIXME: we steal and re-compile it into filesystem, which uses __int128_t, - * and requires this builtin when sanitized. See llvm.org/PR30643 - * - * ===----------------------------------------------------------------------=== - */ -#include "__config" -#include "climits" - -#if !defined(_LIBCPP_HAS_NO_INT128) - -extern "C" __attribute__((no_sanitize("undefined"))) -__int128_t __muloti4(__int128_t a, __int128_t b, int* overflow) { - const int N = (int)(sizeof(__int128_t) * CHAR_BIT); - const __int128_t MIN = (__int128_t)1 << (N - 1); - const __int128_t MAX = ~MIN; - *overflow = 0; - __int128_t result = a * b; - if (a == MIN) { - if (b != 0 && b != 1) - *overflow = 1; - return result; - } - if (b == MIN) { - if (a != 0 && a != 1) - *overflow = 1; - return result; - } - __int128_t sa = a >> (N - 1); - __int128_t abs_a = (a ^ sa) - sa; - __int128_t sb = b >> (N - 1); - __int128_t abs_b = (b ^ sb) - sb; - if (abs_a < 2 || abs_b < 2) - return result; - if (sa == sb) { - if (abs_a > MAX / abs_b) - *overflow = 1; - } else { - if (abs_a > MIN / -abs_b) - *overflow = 1; - } - return result; -} - -#endif diff --git a/lib/libcxx/src/filesystem/operations.cpp b/lib/libcxx/src/filesystem/operations.cpp deleted file mode 100644 index b4106188872..00000000000 --- a/lib/libcxx/src/filesystem/operations.cpp +++ /dev/null @@ -1,1760 +0,0 @@ -//===--------------------- filesystem/ops.cpp -----------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "filesystem" -#include "array" -#include "iterator" -#include "fstream" -#include "random" /* for unique_path */ -#include "string_view" -#include "type_traits" -#include "vector" -#include "cstdlib" -#include "climits" - -#include "filesystem_common.h" - -#include <unistd.h> -#include <sys/stat.h> -#include <sys/statvfs.h> -#include <time.h> -#include <fcntl.h> /* values for fchmodat */ - -#if defined(__linux__) -#include <linux/version.h> -#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 33) -#include <sys/sendfile.h> -#define _LIBCPP_USE_SENDFILE -#endif -#elif defined(__APPLE__) || __has_include(<copyfile.h>) -#include <copyfile.h> -#define _LIBCPP_USE_COPYFILE -#endif - -#if !defined(__APPLE__) -#define _LIBCPP_USE_CLOCK_GETTIME -#endif - -#if !defined(CLOCK_REALTIME) || !defined(_LIBCPP_USE_CLOCK_GETTIME) -#include <sys/time.h> // for gettimeofday and timeval -#endif // !defined(CLOCK_REALTIME) - -#if defined(_LIBCPP_COMPILER_GCC) -#if _GNUC_VER < 500 -#pragma GCC diagnostic ignored "-Wmissing-field-initializers" -#endif -#endif - -_LIBCPP_BEGIN_NAMESPACE_FILESYSTEM - -namespace { -namespace parser { - -using string_view_t = path::__string_view; -using string_view_pair = pair<string_view_t, string_view_t>; -using PosPtr = path::value_type const*; - -struct PathParser { - enum ParserState : unsigned char { - // Zero is a special sentinel value used by default constructed iterators. - PS_BeforeBegin = path::iterator::_BeforeBegin, - PS_InRootName = path::iterator::_InRootName, - PS_InRootDir = path::iterator::_InRootDir, - PS_InFilenames = path::iterator::_InFilenames, - PS_InTrailingSep = path::iterator::_InTrailingSep, - PS_AtEnd = path::iterator::_AtEnd - }; - - const string_view_t Path; - string_view_t RawEntry; - ParserState State; - -private: - PathParser(string_view_t P, ParserState State) noexcept : Path(P), - State(State) {} - -public: - PathParser(string_view_t P, string_view_t E, unsigned char S) - : Path(P), RawEntry(E), State(static_cast<ParserState>(S)) { - // S cannot be '0' or PS_BeforeBegin. - } - - static PathParser CreateBegin(string_view_t P) noexcept { - PathParser PP(P, PS_BeforeBegin); - PP.increment(); - return PP; - } - - static PathParser CreateEnd(string_view_t P) noexcept { - PathParser PP(P, PS_AtEnd); - return PP; - } - - PosPtr peek() const noexcept { - auto TkEnd = getNextTokenStartPos(); - auto End = getAfterBack(); - return TkEnd == End ? nullptr : TkEnd; - } - - void increment() noexcept { - const PosPtr End = getAfterBack(); - const PosPtr Start = getNextTokenStartPos(); - if (Start == End) - return makeState(PS_AtEnd); - - switch (State) { - case PS_BeforeBegin: { - PosPtr TkEnd = consumeSeparator(Start, End); - if (TkEnd) - return makeState(PS_InRootDir, Start, TkEnd); - else - return makeState(PS_InFilenames, Start, consumeName(Start, End)); - } - case PS_InRootDir: - return makeState(PS_InFilenames, Start, consumeName(Start, End)); - - case PS_InFilenames: { - PosPtr SepEnd = consumeSeparator(Start, End); - if (SepEnd != End) { - PosPtr TkEnd = consumeName(SepEnd, End); - if (TkEnd) - return makeState(PS_InFilenames, SepEnd, TkEnd); - } - return makeState(PS_InTrailingSep, Start, SepEnd); - } - - case PS_InTrailingSep: - return makeState(PS_AtEnd); - - case PS_InRootName: - case PS_AtEnd: - _LIBCPP_UNREACHABLE(); - } - } - - void decrement() noexcept { - const PosPtr REnd = getBeforeFront(); - const PosPtr RStart = getCurrentTokenStartPos() - 1; - if (RStart == REnd) // we're decrementing the begin - return makeState(PS_BeforeBegin); - - switch (State) { - case PS_AtEnd: { - // Try to consume a trailing separator or root directory first. - if (PosPtr SepEnd = consumeSeparator(RStart, REnd)) { - if (SepEnd == REnd) - return makeState(PS_InRootDir, Path.data(), RStart + 1); - return makeState(PS_InTrailingSep, SepEnd + 1, RStart + 1); - } else { - PosPtr TkStart = consumeName(RStart, REnd); - return makeState(PS_InFilenames, TkStart + 1, RStart + 1); - } - } - case PS_InTrailingSep: - return makeState(PS_InFilenames, consumeName(RStart, REnd) + 1, - RStart + 1); - case PS_InFilenames: { - PosPtr SepEnd = consumeSeparator(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); - } - case PS_InRootDir: - // return makeState(PS_InRootName, Path.data(), RStart + 1); - case PS_InRootName: - case PS_BeforeBegin: - _LIBCPP_UNREACHABLE(); - } - } - - /// \brief Return a view with the "preferred representation" of the current - /// element. For example trailing separators are represented as a '.' - string_view_t operator*() const noexcept { - switch (State) { - case PS_BeforeBegin: - case PS_AtEnd: - return ""; - case PS_InRootDir: - return "/"; - case PS_InTrailingSep: - return ""; - case PS_InRootName: - case PS_InFilenames: - return RawEntry; - } - _LIBCPP_UNREACHABLE(); - } - - explicit operator bool() const noexcept { - return State != PS_BeforeBegin && State != PS_AtEnd; - } - - PathParser& operator++() noexcept { - increment(); - return *this; - } - - PathParser& operator--() noexcept { - decrement(); - return *this; - } - - bool atEnd() const noexcept { - return State == PS_AtEnd; - } - - bool inRootDir() const noexcept { - return State == PS_InRootDir; - } - - bool inRootName() const noexcept { - return State == PS_InRootName; - } - - bool inRootPath() const noexcept { - return inRootName() || inRootDir(); - } - -private: - void makeState(ParserState NewState, PosPtr Start, PosPtr End) noexcept { - State = NewState; - RawEntry = string_view_t(Start, End - Start); - } - void makeState(ParserState NewState) noexcept { - State = NewState; - RawEntry = {}; - } - - PosPtr getAfterBack() const noexcept { return Path.data() + Path.size(); } - - PosPtr getBeforeFront() const noexcept { return Path.data() - 1; } - - /// \brief Return a pointer to the first character after the currently - /// lexed element. - PosPtr getNextTokenStartPos() const noexcept { - switch (State) { - case PS_BeforeBegin: - return Path.data(); - case PS_InRootName: - case PS_InRootDir: - case PS_InFilenames: - return &RawEntry.back() + 1; - case PS_InTrailingSep: - case PS_AtEnd: - return getAfterBack(); - } - _LIBCPP_UNREACHABLE(); - } - - /// \brief Return a pointer to the first character in the currently lexed - /// element. - PosPtr getCurrentTokenStartPos() const noexcept { - switch (State) { - case PS_BeforeBegin: - case PS_InRootName: - return &Path.front(); - case PS_InRootDir: - case PS_InFilenames: - case PS_InTrailingSep: - return &RawEntry.front(); - case PS_AtEnd: - return &Path.back() + 1; - } - _LIBCPP_UNREACHABLE(); - } - - PosPtr consumeSeparator(PosPtr P, PosPtr End) const noexcept { - if (P == End || *P != '/') - return nullptr; - const int Inc = P < End ? 1 : -1; - P += Inc; - while (P != End && *P == '/') - P += Inc; - return P; - } - - PosPtr consumeName(PosPtr P, PosPtr End) const noexcept { - if (P == End || *P == '/') - return nullptr; - const int Inc = P < End ? 1 : -1; - P += Inc; - while (P != End && *P != '/') - P += Inc; - return P; - } -}; - -string_view_pair separate_filename(string_view_t const& s) { - if (s == "." || s == ".." || s.empty()) - return string_view_pair{s, ""}; - auto pos = s.find_last_of('.'); - if (pos == string_view_t::npos || pos == 0) - return string_view_pair{s, string_view_t{}}; - return string_view_pair{s.substr(0, pos), s.substr(pos)}; -} - -string_view_t createView(PosPtr S, PosPtr E) noexcept { - return {S, static_cast<size_t>(E - S) + 1}; -} - -} // namespace parser -} // namespace - -// POSIX HELPERS - -namespace detail { -namespace { - -using value_type = path::value_type; -using string_type = path::string_type; - -struct FileDescriptor { - const path& name; - int fd = -1; - StatT m_stat; - file_status m_status; - - template <class... Args> - static FileDescriptor create(const path* p, error_code& ec, Args... args) { - ec.clear(); - int fd; - if ((fd = ::open(p->c_str(), args...)) == -1) { - ec = capture_errno(); - return FileDescriptor{p}; - } - return FileDescriptor(p, fd); - } - - template <class... Args> - static FileDescriptor create_with_status(const path* p, error_code& ec, - Args... args) { - FileDescriptor fd = create(p, ec, args...); - if (!ec) - fd.refresh_status(ec); - - return fd; - } - - file_status get_status() const { return m_status; } - StatT const& get_stat() const { return m_stat; } - - bool status_known() const { return _VSTD_FS::status_known(m_status); } - - file_status refresh_status(error_code& ec); - - void close() noexcept { - if (fd != -1) - ::close(fd); - fd = -1; - } - - FileDescriptor(FileDescriptor&& other) - : name(other.name), fd(other.fd), m_stat(other.m_stat), - m_status(other.m_status) { - other.fd = -1; - other.m_status = file_status{}; - } - - ~FileDescriptor() { close(); } - - FileDescriptor(FileDescriptor const&) = delete; - FileDescriptor& operator=(FileDescriptor const&) = delete; - -private: - explicit FileDescriptor(const path* p, int fd = -1) : name(*p), fd(fd) {} -}; - -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) - *ec = m_ec; - if (m_ec && (m_ec.value() == ENOENT || m_ec.value() == ENOTDIR)) { - return file_status(file_type::not_found); - } else if (m_ec) { - ErrorHandler<void> err("posix_stat", ec, &p); - err.report(m_ec, "failed to determine attributes for the specified path"); - return file_status(file_type::none); - } - // else - - file_status fs_tmp; - auto const mode = path_stat.st_mode; - if (S_ISLNK(mode)) - fs_tmp.type(file_type::symlink); - else if (S_ISREG(mode)) - fs_tmp.type(file_type::regular); - else if (S_ISDIR(mode)) - fs_tmp.type(file_type::directory); - else if (S_ISBLK(mode)) - fs_tmp.type(file_type::block); - else if (S_ISCHR(mode)) - fs_tmp.type(file_type::character); - else if (S_ISFIFO(mode)) - fs_tmp.type(file_type::fifo); - else if (S_ISSOCK(mode)) - fs_tmp.type(file_type::socket); - else - fs_tmp.type(file_type::unknown); - - fs_tmp.permissions(detail::posix_get_perms(path_stat)); - return fs_tmp; -} - -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) - m_ec = detail::capture_errno(); - return create_file_status(m_ec, p, path_stat, ec); -} - -file_status posix_stat(path const& p, error_code* ec) { - StatT path_stat; - return posix_stat(p, path_stat, 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) - m_ec = detail::capture_errno(); - return create_file_status(m_ec, p, path_stat, ec); -} - -file_status posix_lstat(path const& p, error_code* ec) { - StatT path_stat; - return posix_lstat(p, path_stat, 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) { - ec = capture_errno(); - return true; - } - ec.clear(); - return false; -} - -bool posix_fchmod(const FileDescriptor& fd, const StatT& st, error_code& ec) { - if (::fchmod(fd.fd, st.st_mode) == -1) { - ec = capture_errno(); - return true; - } - ec.clear(); - return false; -} - -bool stat_equivalent(const StatT& st1, const StatT& st2) { - return (st1.st_dev == st2.st_dev && st1.st_ino == st2.st_ino); -} - -file_status FileDescriptor::refresh_status(error_code& ec) { - // FD must be open and good. - m_status = file_status{}; - m_stat = {}; - error_code m_ec; - if (::fstat(fd, &m_stat) == -1) - m_ec = capture_errno(); - m_status = create_file_status(m_ec, name, m_stat, &ec); - return m_status; -} -} // namespace -} // end namespace detail - -using detail::capture_errno; -using detail::ErrorHandler; -using detail::StatT; -using detail::TimeSpec; -using parser::createView; -using parser::PathParser; -using parser::string_view_t; - -const bool _FilesystemClock::is_steady; - -_FilesystemClock::time_point _FilesystemClock::now() noexcept { - typedef chrono::duration<rep> __secs; -#if defined(_LIBCPP_USE_CLOCK_GETTIME) && defined(CLOCK_REALTIME) - typedef chrono::duration<rep, nano> __nsecs; - struct timespec tp; - if (0 != clock_gettime(CLOCK_REALTIME, &tp)) - __throw_system_error(errno, "clock_gettime(CLOCK_REALTIME) failed"); - return time_point(__secs(tp.tv_sec) + - chrono::duration_cast<duration>(__nsecs(tp.tv_nsec))); -#else - typedef chrono::duration<rep, micro> __microsecs; - timeval tv; - gettimeofday(&tv, 0); - return time_point(__secs(tv.tv_sec) + __microsecs(tv.tv_usec)); -#endif // _LIBCPP_USE_CLOCK_GETTIME && CLOCK_REALTIME -} - -filesystem_error::~filesystem_error() {} - -void filesystem_error::__create_what(int __num_paths) { - const char* derived_what = system_error::what(); - __storage_->__what_ = [&]() -> string { - const char* p1 = path1().native().empty() ? "\"\"" : path1().c_str(); - const char* p2 = path2().native().empty() ? "\"\"" : path2().c_str(); - switch (__num_paths) { - default: - return detail::format_string("filesystem error: %s", derived_what); - case 1: - return detail::format_string("filesystem error: %s [%s]", derived_what, - p1); - case 2: - return detail::format_string("filesystem error: %s [%s] [%s]", - derived_what, p1, p2); - } - }(); -} - -static path __do_absolute(const path& p, path* cwd, error_code* ec) { - if (ec) - ec->clear(); - if (p.is_absolute()) - return p; - *cwd = __current_path(ec); - if (ec && *ec) - return {}; - return (*cwd) / p; -} - -path __absolute(const path& p, error_code* ec) { - path cwd; - return __do_absolute(p, &cwd, ec); -} - -path __canonical(path const& orig_p, error_code* ec) { - path cwd; - ErrorHandler<path> err("canonical", ec, &orig_p, &cwd); - - path p = __do_absolute(orig_p, &cwd, ec); - char buff[PATH_MAX + 1]; - char* ret; - if ((ret = ::realpath(p.c_str(), buff)) == nullptr) - return err.report(capture_errno()); - return {ret}; -} - -void __copy(const path& from, const path& to, copy_options options, - error_code* ec) { - ErrorHandler<void> err("copy", ec, &from, &to); - - const bool sym_status = bool( - options & (copy_options::create_symlinks | copy_options::skip_symlinks)); - - const bool sym_status2 = bool(options & copy_options::copy_symlinks); - - error_code m_ec1; - StatT f_st = {}; - const file_status f = sym_status || sym_status2 - ? detail::posix_lstat(from, f_st, &m_ec1) - : detail::posix_stat(from, f_st, &m_ec1); - if (m_ec1) - return err.report(m_ec1); - - StatT t_st = {}; - const file_status t = sym_status ? detail::posix_lstat(to, t_st, &m_ec1) - : detail::posix_stat(to, t_st, &m_ec1); - - if (not status_known(t)) - return err.report(m_ec1); - - if (!exists(f) || is_other(f) || is_other(t) || - (is_directory(f) && is_regular_file(t)) || - detail::stat_equivalent(f_st, t_st)) { - return err.report(errc::function_not_supported); - } - - if (ec) - ec->clear(); - - if (is_symlink(f)) { - if (bool(copy_options::skip_symlinks & options)) { - // do nothing - } else if (not exists(t)) { - __copy_symlink(from, to, ec); - } else { - return err.report(errc::file_exists); - } - return; - } else if (is_regular_file(f)) { - if (bool(copy_options::directories_only & options)) { - // do nothing - } else if (bool(copy_options::create_symlinks & options)) { - __create_symlink(from, to, ec); - } else if (bool(copy_options::create_hard_links & options)) { - __create_hard_link(from, to, ec); - } else if (is_directory(t)) { - __copy_file(from, to / from.filename(), options, ec); - } else { - __copy_file(from, to, options, ec); - } - return; - } else if (is_directory(f) && bool(copy_options::create_symlinks & options)) { - return err.report(errc::is_a_directory); - } else if (is_directory(f) && (bool(copy_options::recursive & options) || - copy_options::none == options)) { - - if (!exists(t)) { - // create directory to with attributes from 'from'. - __create_directory(to, from, ec); - if (ec && *ec) { - return; - } - } - directory_iterator it = - ec ? directory_iterator(from, *ec) : directory_iterator(from); - if (ec && *ec) { - return; - } - error_code m_ec2; - for (; it != directory_iterator(); it.increment(m_ec2)) { - if (m_ec2) { - return err.report(m_ec2); - } - __copy(it->path(), to / it->path().filename(), - options | copy_options::__in_recursive_copy, ec); - if (ec && *ec) { - return; - } - } - } -} - -namespace detail { -namespace { - -#ifdef _LIBCPP_USE_SENDFILE -bool copy_file_impl_sendfile(FileDescriptor& read_fd, FileDescriptor& write_fd, - error_code& ec) { - - size_t count = read_fd.get_stat().st_size; - do { - ssize_t res; - if ((res = ::sendfile(write_fd.fd, read_fd.fd, nullptr, count)) == -1) { - ec = capture_errno(); - return false; - } - count -= res; - } while (count > 0); - - ec.clear(); - - return true; -} -#elif defined(_LIBCPP_USE_COPYFILE) -bool copy_file_impl_copyfile(FileDescriptor& read_fd, FileDescriptor& write_fd, - error_code& ec) { - struct CopyFileState { - copyfile_state_t state; - CopyFileState() { state = copyfile_state_alloc(); } - ~CopyFileState() { copyfile_state_free(state); } - - private: - CopyFileState(CopyFileState const&) = delete; - CopyFileState& operator=(CopyFileState const&) = delete; - }; - - CopyFileState cfs; - if (fcopyfile(read_fd.fd, write_fd.fd, cfs.state, COPYFILE_DATA) < 0) { - ec = capture_errno(); - return false; - } - - ec.clear(); - return true; -} -#endif - -// Note: This function isn't guarded by ifdef's even though it may be unused -// in order to assure it still compiles. -__attribute__((unused)) bool copy_file_impl_default(FileDescriptor& read_fd, - FileDescriptor& write_fd, - error_code& ec) { - ifstream in; - in.__open(read_fd.fd, ios::binary); - if (!in.is_open()) { - // This assumes that __open didn't reset the error code. - ec = capture_errno(); - return false; - } - ofstream out; - out.__open(write_fd.fd, ios::binary); - if (!out.is_open()) { - ec = capture_errno(); - return false; - } - - if (in.good() && out.good()) { - using InIt = istreambuf_iterator<char>; - using OutIt = ostreambuf_iterator<char>; - InIt bin(in); - InIt ein; - OutIt bout(out); - copy(bin, ein, bout); - } - if (out.fail() || in.fail()) { - ec = make_error_code(errc::io_error); - return false; - } - - ec.clear(); - return true; -} - -bool copy_file_impl(FileDescriptor& from, FileDescriptor& to, error_code& ec) { -#if defined(_LIBCPP_USE_SENDFILE) - return copy_file_impl_sendfile(from, to, ec); -#elif defined(_LIBCPP_USE_COPYFILE) - return copy_file_impl_copyfile(from, to, ec); -#else - return copy_file_impl_default(from, to, ec); -#endif -} - -} // namespace -} // namespace detail - -bool __copy_file(const path& from, const path& to, copy_options options, - error_code* ec) { - using detail::FileDescriptor; - 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); - if (m_ec) - return err.report(m_ec); - - auto from_st = from_fd.get_status(); - StatT const& from_stat = from_fd.get_stat(); - if (!is_regular_file(from_st)) { - if (not m_ec) - m_ec = make_error_code(errc::not_supported); - return err.report(m_ec); - } - - const bool skip_existing = bool(copy_options::skip_existing & options); - const bool update_existing = bool(copy_options::update_existing & options); - const bool overwrite_existing = - bool(copy_options::overwrite_existing & options); - - StatT to_stat_path; - file_status to_st = detail::posix_stat(to, to_stat_path, &m_ec); - if (!status_known(to_st)) - return err.report(m_ec); - - const bool to_exists = exists(to_st); - if (to_exists && !is_regular_file(to_st)) - return err.report(errc::not_supported); - - if (to_exists && detail::stat_equivalent(from_stat, to_stat_path)) - return err.report(errc::file_exists); - - if (to_exists && skip_existing) - return false; - - bool ShouldCopy = [&]() { - if (to_exists && update_existing) { - auto from_time = detail::extract_mtime(from_stat); - auto to_time = detail::extract_mtime(to_stat_path); - if (from_time.tv_sec < to_time.tv_sec) - return false; - if (from_time.tv_sec == to_time.tv_sec && - from_time.tv_nsec <= to_time.tv_nsec) - return false; - return true; - } - if (!to_exists || overwrite_existing) - return true; - return err.report(errc::file_exists); - }(); - if (!ShouldCopy) - return false; - - // 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; - if (!to_exists) - to_open_flags |= O_CREAT; - FileDescriptor to_fd = FileDescriptor::create_with_status( - &to, m_ec, to_open_flags, from_stat.st_mode); - if (m_ec) - return err.report(m_ec); - - if (to_exists) { - // Check that the file we initially stat'ed is equivalent to the one - // we opened. - // FIXME: report this better. - if (!detail::stat_equivalent(to_stat_path, to_fd.get_stat())) - return err.report(errc::bad_file_descriptor); - - // Set the permissions and truncate the file we opened. - if (detail::posix_fchmod(to_fd, from_stat, m_ec)) - return err.report(m_ec); - if (detail::posix_ftruncate(to_fd, 0, m_ec)) - return err.report(m_ec); - } - - if (!copy_file_impl(from_fd, to_fd, m_ec)) { - // FIXME: Remove the dest file if we failed, and it didn't exist previously. - return err.report(m_ec); - } - - return true; -} - -void __copy_symlink(const path& existing_symlink, const path& new_symlink, - error_code* ec) { - const path real_path(__read_symlink(existing_symlink, ec)); - 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); -} - -bool __create_directories(const path& p, error_code* ec) { - ErrorHandler<bool> err("create_directories", ec, &p); - - error_code m_ec; - auto const st = detail::posix_stat(p, &m_ec); - if (!status_known(st)) - return err.report(m_ec); - else if (is_directory(st)) - return false; - else if (exists(st)) - return err.report(errc::file_exists); - - const path parent = p.parent_path(); - if (!parent.empty()) { - const file_status parent_st = status(parent, m_ec); - if (not status_known(parent_st)) - return err.report(m_ec); - if (not exists(parent_st)) { - __create_directories(parent, ec); - if (ec && *ec) { - return false; - } - } - } - return __create_directory(p, ec); -} - -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) - return true; - if (errno != EEXIST) - err.report(capture_errno()); - return false; -} - -bool __create_directory(path const& p, path const& attributes, error_code* ec) { - ErrorHandler<bool> err("create_directory", ec, &p, &attributes); - - StatT attr_stat; - error_code mec; - auto 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) - return true; - if (errno != EEXIST) - err.report(capture_errno()); - 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) - 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) - 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) - return err.report(capture_errno()); -} - -path __current_path(error_code* ec) { - ErrorHandler<path> err("current_path", ec); - - 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) - return err.report(capture_errno(), "call to getcwd failed"); - - return {buff.get()}; -} - -void __current_path(const path& p, error_code* ec) { - ErrorHandler<void> err("current_path", ec, &p); - if (::chdir(p.c_str()) == -1) - err.report(capture_errno()); -} - -bool __equivalent(const path& p1, const path& p2, error_code* ec) { - ErrorHandler<bool> err("equivalent", ec, &p1, &p2); - - error_code ec1, ec2; - StatT st1 = {}, st2 = {}; - auto s1 = detail::posix_stat(p1.native(), st1, &ec1); - if (!exists(s1)) - return err.report(errc::not_supported); - auto s2 = detail::posix_stat(p2.native(), st2, &ec2); - if (!exists(s2)) - return err.report(errc::not_supported); - - return detail::stat_equivalent(st1, st2); -} - -uintmax_t __file_size(const path& p, error_code* ec) { - ErrorHandler<uintmax_t> err("file_size", ec, &p); - - error_code m_ec; - StatT st; - file_status fst = detail::posix_stat(p, st, &m_ec); - if (!exists(fst) || !is_regular_file(fst)) { - errc error_kind = - is_directory(fst) ? errc::is_a_directory : errc::not_supported; - if (!m_ec) - m_ec = make_error_code(error_kind); - return err.report(m_ec); - } - // is_regular_file(p) == true - return static_cast<uintmax_t>(st.st_size); -} - -uintmax_t __hard_link_count(const path& p, error_code* ec) { - ErrorHandler<uintmax_t> err("hard_link_count", ec, &p); - - error_code m_ec; - StatT st; - detail::posix_stat(p, st, &m_ec); - if (m_ec) - return err.report(m_ec); - return static_cast<uintmax_t>(st.st_nlink); -} - -bool __fs_is_empty(const path& p, error_code* ec) { - ErrorHandler<bool> err("is_empty", ec, &p); - - error_code m_ec; - StatT pst; - auto st = detail::posix_stat(p, pst, &m_ec); - if (m_ec) - return err.report(m_ec); - else if (!is_directory(st) && !is_regular_file(st)) - return err.report(errc::not_supported); - else if (is_directory(st)) { - auto it = ec ? directory_iterator(p, *ec) : directory_iterator(p); - if (ec && *ec) - return false; - return it == directory_iterator{}; - } else if (is_regular_file(st)) - return static_cast<uintmax_t>(pst.st_size) == 0; - - _LIBCPP_UNREACHABLE(); -} - -static file_time_type __extract_last_write_time(const path& p, const StatT& st, - error_code* ec) { - using detail::fs_time; - ErrorHandler<file_time_type> err("last_write_time", ec, &p); - - auto ts = detail::extract_mtime(st); - if (!fs_time::is_representable(ts)) - return err.report(errc::value_too_large); - - return fs_time::convert_from_timespec(ts); -} - -file_time_type __last_write_time(const path& p, error_code* ec) { - using namespace chrono; - ErrorHandler<file_time_type> err("last_write_time", ec, &p); - - error_code m_ec; - StatT st; - detail::posix_stat(p, st, &m_ec); - if (m_ec) - return err.report(m_ec); - return __extract_last_write_time(p, st, ec); -} - -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); - - error_code m_ec; - array<TimeSpec, 2> tbuf; -#if !defined(_LIBCPP_USE_UTIMENSAT) - // This implementation has a race condition between determining the - // last access time and attempting to set it to the same value using - // ::utimes - StatT st; - file_status fst = detail::posix_stat(p, st, &m_ec); - if (m_ec) - return err.report(m_ec); - tbuf[0] = detail::extract_atime(st); -#else - tbuf[0].tv_sec = 0; - tbuf[0].tv_nsec = UTIME_OMIT; -#endif - if (!fs_time::convert_to_timespec(tbuf[1], new_time)) - return err.report(errc::value_too_large); - - detail::set_file_times(p, tbuf, m_ec); - if (m_ec) - return err.report(m_ec); -} - -void __permissions(const path& p, perms prms, perm_options opts, - error_code* ec) { - ErrorHandler<void> err("permissions", ec, &p); - - auto has_opt = [&](perm_options o) { return bool(o & opts); }; - const bool resolve_symlinks = !has_opt(perm_options::nofollow); - const bool add_perms = has_opt(perm_options::add); - const bool remove_perms = has_opt(perm_options::remove); - _LIBCPP_ASSERT( - (add_perms + remove_perms + has_opt(perm_options::replace)) == 1, - "One and only one of the perm_options constants replace, add, or remove " - "is present in opts"); - - bool set_sym_perms = false; - prms &= perms::mask; - if (!resolve_symlinks || (add_perms || remove_perms)) { - error_code m_ec; - file_status st = resolve_symlinks ? detail::posix_stat(p, &m_ec) - : detail::posix_lstat(p, &m_ec); - set_sym_perms = is_symlink(st); - if (m_ec) - return err.report(m_ec); - _LIBCPP_ASSERT(st.permissions() != perms::unknown, - "Permissions unexpectedly unknown"); - if (add_perms) - prms |= st.permissions(); - else if (remove_perms) - prms = st.permissions() & ~prms; - } - const auto real_perms = detail::posix_convert_perms(prms); - -#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) { - return err.report(capture_errno()); - } -#else - if (set_sym_perms) - return err.report(errc::operation_not_supported); - if (::chmod(p.c_str(), real_perms) == -1) { - return err.report(capture_errno()); - } -#endif -} - -path __read_symlink(const path& p, error_code* ec) { - ErrorHandler<path> err("read_symlink", ec, &p); - - char buff[PATH_MAX + 1]; - error_code m_ec; - ::ssize_t ret; - if ((ret = ::readlink(p.c_str(), buff, PATH_MAX)) == -1) { - return err.report(capture_errno()); - } - _LIBCPP_ASSERT(ret <= PATH_MAX, "TODO"); - _LIBCPP_ASSERT(ret > 0, "TODO"); - buff[ret] = 0; - return {buff}; -} - -bool __remove(const path& p, error_code* ec) { - ErrorHandler<bool> err("remove", ec, &p); - if (::remove(p.c_str()) == -1) { - if (errno != ENOENT) - err.report(capture_errno()); - return false; - } - return true; -} - -namespace { - -uintmax_t remove_all_impl(path const& p, error_code& ec) { - const auto npos = static_cast<uintmax_t>(-1); - const file_status st = __symlink_status(p, &ec); - if (ec) - return npos; - uintmax_t count = 1; - if (is_directory(st)) { - for (directory_iterator it(p, ec); !ec && it != directory_iterator(); - it.increment(ec)) { - auto other_count = remove_all_impl(it->path(), ec); - if (ec) - return npos; - count += other_count; - } - if (ec) - return npos; - } - if (!__remove(p, &ec)) - return npos; - return count; -} - -} // end namespace - -uintmax_t __remove_all(const path& p, error_code* ec) { - ErrorHandler<uintmax_t> err("remove_all", ec, &p); - - error_code mec; - auto count = remove_all_impl(p, mec); - if (mec) { - if (mec == errc::no_such_file_or_directory) - return 0; - return err.report(mec); - } - return count; -} - -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) - 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) - 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) { - err.report(capture_errno()); - si.capacity = si.free = si.available = static_cast<uintmax_t>(-1); - return si; - } - // Multiply with overflow checking. - auto do_mult = [&](uintmax_t& out, uintmax_t other) { - out = other * m_svfs.f_frsize; - if (other == 0 || out / other != m_svfs.f_frsize) - out = static_cast<uintmax_t>(-1); - }; - do_mult(si.capacity, m_svfs.f_blocks); - do_mult(si.free, m_svfs.f_bfree); - do_mult(si.available, m_svfs.f_bavail); - return si; -} - -file_status __status(const path& p, error_code* ec) { - return detail::posix_stat(p, ec); -} - -file_status __symlink_status(const path& p, error_code* ec) { - return detail::posix_lstat(p, ec); -} - -path __temp_directory_path(error_code* ec) { - ErrorHandler<path> err("temp_directory_path", ec); - - const char* env_paths[] = {"TMPDIR", "TMP", "TEMP", "TEMPDIR"}; - const char* ret = nullptr; - - for (auto& ep : env_paths) - if ((ret = getenv(ep))) - break; - if (ret == nullptr) - ret = "/tmp"; - - path p(ret); - 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 \"%s\"", p); - - if (!exists(st) || !is_directory(st)) - return err.report(errc::not_a_directory, "path \"%s\" is not a directory", - p); - - return p; -} - -path __weakly_canonical(const path& p, error_code* ec) { - ErrorHandler<path> err("weakly_canonical", ec, &p); - - if (p.empty()) - return __canonical("", ec); - - path result; - path tmp; - tmp.__reserve(p.native().size()); - auto PP = PathParser::CreateEnd(p.native()); - --PP; - vector<string_view_t> DNEParts; - - while (PP.State != PathParser::PS_BeforeBegin) { - tmp.assign(createView(p.native().data(), &PP.RawEntry.back())); - error_code m_ec; - file_status st = __status(tmp, &m_ec); - if (!status_known(st)) { - return err.report(m_ec); - } else if (exists(st)) { - result = __canonical(tmp, ec); - break; - } - DNEParts.push_back(*PP); - --PP; - } - if (PP.State == PathParser::PS_BeforeBegin) - result = __canonical("", ec); - if (ec) - ec->clear(); - if (DNEParts.empty()) - return result; - for (auto It = DNEParts.rbegin(); It != DNEParts.rend(); ++It) - result /= *It; - return result.lexically_normal(); -} - -/////////////////////////////////////////////////////////////////////////////// -// path definitions -/////////////////////////////////////////////////////////////////////////////// - -constexpr path::value_type path::preferred_separator; - -path& path::replace_extension(path const& replacement) { - path p = extension(); - if (not p.empty()) { - __pn_.erase(__pn_.size() - p.native().size()); - } - if (!replacement.empty()) { - if (replacement.native()[0] != '.') { - __pn_ += "."; - } - __pn_.append(replacement.__pn_); - } - return *this; -} - -/////////////////////////////////////////////////////////////////////////////// -// path.decompose - -string_view_t path::__root_name() const { - auto PP = PathParser::CreateBegin(__pn_); - if (PP.State == PathParser::PS_InRootName) - return *PP; - return {}; -} - -string_view_t path::__root_directory() const { - auto PP = PathParser::CreateBegin(__pn_); - if (PP.State == PathParser::PS_InRootName) - ++PP; - if (PP.State == PathParser::PS_InRootDir) - return *PP; - return {}; -} - -string_view_t path::__root_path_raw() const { - auto PP = PathParser::CreateBegin(__pn_); - if (PP.State == PathParser::PS_InRootName) { - auto NextCh = PP.peek(); - if (NextCh && *NextCh == '/') { - ++PP; - return createView(__pn_.data(), &PP.RawEntry.back()); - } - return PP.RawEntry; - } - if (PP.State == PathParser::PS_InRootDir) - return *PP; - return {}; -} - -static bool ConsumeRootName(PathParser *PP) { - static_assert(PathParser::PS_BeforeBegin == 1 && - PathParser::PS_InRootName == 2, - "Values for enums are incorrect"); - while (PP->State <= PathParser::PS_InRootName) - ++(*PP); - return PP->State == PathParser::PS_AtEnd; -} - -static bool ConsumeRootDir(PathParser* PP) { - static_assert(PathParser::PS_BeforeBegin == 1 && - PathParser::PS_InRootName == 2 && - PathParser::PS_InRootDir == 3, "Values for enums are incorrect"); - while (PP->State <= PathParser::PS_InRootDir) - ++(*PP); - return PP->State == PathParser::PS_AtEnd; -} - -string_view_t path::__relative_path() const { - auto PP = PathParser::CreateBegin(__pn_); - if (ConsumeRootDir(&PP)) - return {}; - return createView(PP.RawEntry.data(), &__pn_.back()); -} - -string_view_t path::__parent_path() const { - if (empty()) - return {}; - // Determine if we have a root path but not a relative path. In that case - // return *this. - { - auto PP = PathParser::CreateBegin(__pn_); - if (ConsumeRootDir(&PP)) - return __pn_; - } - // Otherwise remove a single element from the end of the path, and return - // a string representing that path - { - auto PP = PathParser::CreateEnd(__pn_); - --PP; - if (PP.RawEntry.data() == __pn_.data()) - return {}; - --PP; - return createView(__pn_.data(), &PP.RawEntry.back()); - } -} - -string_view_t path::__filename() const { - if (empty()) - return {}; - { - PathParser PP = PathParser::CreateBegin(__pn_); - if (ConsumeRootDir(&PP)) - return {}; - } - return *(--PathParser::CreateEnd(__pn_)); -} - -string_view_t path::__stem() const { - return parser::separate_filename(__filename()).first; -} - -string_view_t path::__extension() const { - return parser::separate_filename(__filename()).second; -} - -//////////////////////////////////////////////////////////////////////////// -// path.gen - -enum PathPartKind : unsigned char { - PK_None, - PK_RootSep, - PK_Filename, - PK_Dot, - PK_DotDot, - PK_TrailingSep -}; - -static PathPartKind ClassifyPathPart(string_view_t Part) { - if (Part.empty()) - return PK_TrailingSep; - if (Part == ".") - return PK_Dot; - if (Part == "..") - return PK_DotDot; - if (Part == "/") - return PK_RootSep; - return PK_Filename; -} - -path path::lexically_normal() const { - if (__pn_.empty()) - return *this; - - using PartKindPair = pair<string_view_t, PathPartKind>; - vector<PartKindPair> Parts; - // Guess as to how many elements the path has to avoid reallocating. - Parts.reserve(32); - - // Track the total size of the parts as we collect them. This allows the - // resulting path to reserve the correct amount of memory. - size_t NewPathSize = 0; - auto AddPart = [&](PathPartKind K, string_view_t P) { - NewPathSize += P.size(); - Parts.emplace_back(P, K); - }; - auto LastPartKind = [&]() { - if (Parts.empty()) - return PK_None; - return Parts.back().second; - }; - - bool MaybeNeedTrailingSep = false; - // Build a stack containing the remaining elements of the path, popping off - // elements which occur before a '..' entry. - for (auto PP = PathParser::CreateBegin(__pn_); PP; ++PP) { - auto Part = *PP; - PathPartKind Kind = ClassifyPathPart(Part); - switch (Kind) { - case PK_Filename: - case PK_RootSep: { - // Add all non-dot and non-dot-dot elements to the stack of elements. - AddPart(Kind, Part); - MaybeNeedTrailingSep = false; - break; - } - case PK_DotDot: { - // Only push a ".." element if there are no elements preceding the "..", - // or if the preceding element is itself "..". - auto LastKind = LastPartKind(); - if (LastKind == PK_Filename) { - NewPathSize -= Parts.back().first.size(); - Parts.pop_back(); - } else if (LastKind != PK_RootSep) - AddPart(PK_DotDot, ".."); - MaybeNeedTrailingSep = LastKind == PK_Filename; - break; - } - case PK_Dot: - case PK_TrailingSep: { - MaybeNeedTrailingSep = true; - break; - } - case PK_None: - _LIBCPP_UNREACHABLE(); - } - } - // [fs.path.generic]p6.8: If the path is empty, add a dot. - if (Parts.empty()) - return "."; - - // [fs.path.generic]p6.7: If the last filename is dot-dot, remove any - // trailing directory-separator. - bool NeedTrailingSep = MaybeNeedTrailingSep && LastPartKind() == PK_Filename; - - path Result; - Result.__pn_.reserve(Parts.size() + NewPathSize + NeedTrailingSep); - for (auto& PK : Parts) - Result /= PK.first; - - if (NeedTrailingSep) - Result /= ""; - - return Result; -} - -static int DetermineLexicalElementCount(PathParser PP) { - int Count = 0; - for (; PP; ++PP) { - auto Elem = *PP; - if (Elem == "..") - --Count; - else if (Elem != "." && Elem != "") - ++Count; - } - return Count; -} - -path path::lexically_relative(const path& base) const { - { // perform root-name/root-directory mismatch checks - auto PP = PathParser::CreateBegin(__pn_); - auto PPBase = PathParser::CreateBegin(base.__pn_); - auto CheckIterMismatchAtBase = [&]() { - return PP.State != PPBase.State && - (PP.inRootPath() || PPBase.inRootPath()); - }; - if (PP.inRootName() && PPBase.inRootName()) { - if (*PP != *PPBase) - return {}; - } else if (CheckIterMismatchAtBase()) - return {}; - - if (PP.inRootPath()) - ++PP; - if (PPBase.inRootPath()) - ++PPBase; - if (CheckIterMismatchAtBase()) - return {}; - } - - // Find the first mismatching element - auto PP = PathParser::CreateBegin(__pn_); - auto PPBase = PathParser::CreateBegin(base.__pn_); - while (PP && PPBase && PP.State == PPBase.State && *PP == *PPBase) { - ++PP; - ++PPBase; - } - - // If there is no mismatch, return ".". - if (!PP && !PPBase) - return "."; - - // Otherwise, determine the number of elements, 'n', which are not dot or - // dot-dot minus the number of dot-dot elements. - int ElemCount = DetermineLexicalElementCount(PPBase); - if (ElemCount < 0) - return {}; - - // if n == 0 and (a == end() || a->empty()), returns path("."); otherwise - if (ElemCount == 0 && (PP.atEnd() || *PP == "")) - return "."; - - // return a path constructed with 'n' dot-dot elements, followed by the the - // elements of '*this' after the mismatch. - path Result; - // FIXME: Reserve enough room in Result that it won't have to re-allocate. - while (ElemCount--) - Result /= ".."; - for (; PP; ++PP) - Result /= *PP; - return Result; -} - -//////////////////////////////////////////////////////////////////////////// -// path.comparisons -static int CompareRootName(PathParser *LHS, PathParser *RHS) { - if (!LHS->inRootName() && !RHS->inRootName()) - return 0; - - auto GetRootName = [](PathParser *Parser) -> string_view_t { - return Parser->inRootName() ? **Parser : ""; - }; - int res = GetRootName(LHS).compare(GetRootName(RHS)); - ConsumeRootName(LHS); - ConsumeRootName(RHS); - return res; -} - -static int CompareRootDir(PathParser *LHS, PathParser *RHS) { - if (!LHS->inRootDir() && RHS->inRootDir()) - return -1; - else if (LHS->inRootDir() && !RHS->inRootDir()) - return 1; - else { - ConsumeRootDir(LHS); - ConsumeRootDir(RHS); - return 0; - } -} - -static int CompareRelative(PathParser *LHSPtr, PathParser *RHSPtr) { - auto &LHS = *LHSPtr; - auto &RHS = *RHSPtr; - - int res; - while (LHS && RHS) { - if ((res = (*LHS).compare(*RHS)) != 0) - return res; - ++LHS; - ++RHS; - } - return 0; -} - -static int CompareEndState(PathParser *LHS, PathParser *RHS) { - if (LHS->atEnd() && !RHS->atEnd()) - return -1; - else if (!LHS->atEnd() && RHS->atEnd()) - return 1; - return 0; -} - -int path::__compare(string_view_t __s) const { - auto LHS = PathParser::CreateBegin(__pn_); - auto RHS = PathParser::CreateBegin(__s); - int res; - - if ((res = CompareRootName(&LHS, &RHS)) != 0) - return res; - - if ((res = CompareRootDir(&LHS, &RHS)) != 0) - return res; - - if ((res = CompareRelative(&LHS, &RHS)) != 0) - return res; - - return CompareEndState(&LHS, &RHS); -} - -//////////////////////////////////////////////////////////////////////////// -// path.nonmembers -size_t hash_value(const path& __p) noexcept { - auto PP = PathParser::CreateBegin(__p.native()); - size_t hash_value = 0; - hash<string_view_t> hasher; - while (PP) { - hash_value = __hash_combine(hash_value, hasher(*PP)); - ++PP; - } - return hash_value; -} - -//////////////////////////////////////////////////////////////////////////// -// path.itr -path::iterator path::begin() const { - auto PP = PathParser::CreateBegin(__pn_); - iterator it; - it.__path_ptr_ = this; - it.__state_ = static_cast<path::iterator::_ParserState>(PP.State); - it.__entry_ = PP.RawEntry; - it.__stashed_elem_.__assign_view(*PP); - return it; -} - -path::iterator path::end() const { - iterator it{}; - it.__state_ = path::iterator::_AtEnd; - it.__path_ptr_ = this; - return it; -} - -path::iterator& path::iterator::__increment() { - PathParser PP(__path_ptr_->native(), __entry_, __state_); - ++PP; - __state_ = static_cast<_ParserState>(PP.State); - __entry_ = PP.RawEntry; - __stashed_elem_.__assign_view(*PP); - return *this; -} - -path::iterator& path::iterator::__decrement() { - PathParser PP(__path_ptr_->native(), __entry_, __state_); - --PP; - __state_ = static_cast<_ParserState>(PP.State); - __entry_ = PP.RawEntry; - __stashed_elem_.__assign_view(*PP); - return *this; -} - -/////////////////////////////////////////////////////////////////////////////// -// directory entry definitions -/////////////////////////////////////////////////////////////////////////////// - -#ifndef _LIBCPP_WIN32API -error_code directory_entry::__do_refresh() noexcept { - __data_.__reset(); - error_code failure_ec; - - StatT full_st; - file_status st = detail::posix_lstat(__p_, full_st, &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 = detail::posix_stat(__p_, full_st, &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{}; - } - // Otherwise, we resolved the link, potentially as not existing. - // That's OK. - __data_.__cache_type_ = directory_entry::_RefreshSymlink; - } - - if (_VSTD_FS::is_regular_file(st)) - __data_.__size_ = static_cast<uintmax_t>(full_st.st_size); - - if (_VSTD_FS::exists(st)) { - __data_.__nlink_ = static_cast<uintmax_t>(full_st.st_nlink); - - // Attempt to extract the mtime, and fail if it's not representable using - // file_time_type. For now we ignore the error, as we'll report it when - // the value is actually used. - error_code ignored_ec; - __data_.__write_time_ = - __extract_last_write_time(__p_, full_st, &ignored_ec); - } - - 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/functional.cpp b/lib/libcxx/src/functional.cpp deleted file mode 100644 index 5c2646f01b2..00000000000 --- a/lib/libcxx/src/functional.cpp +++ /dev/null @@ -1,26 +0,0 @@ -//===----------------------- functional.cpp -------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "functional" - -_LIBCPP_BEGIN_NAMESPACE_STD - -#ifdef _LIBCPP_ABI_BAD_FUNCTION_CALL_KEY_FUNCTION -bad_function_call::~bad_function_call() _NOEXCEPT -{ -} - -const char* -bad_function_call::what() const _NOEXCEPT -{ - return "std::bad_function_call"; -} -#endif - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/future.cpp b/lib/libcxx/src/future.cpp deleted file mode 100644 index cbcd2e7b728..00000000000 --- a/lib/libcxx/src/future.cpp +++ /dev/null @@ -1,278 +0,0 @@ -//===------------------------- future.cpp ---------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "__config" - -#ifndef _LIBCPP_HAS_NO_THREADS - -#include "future" -#include "string" - -_LIBCPP_BEGIN_NAMESPACE_STD - -class _LIBCPP_HIDDEN __future_error_category - : public __do_message -{ -public: - virtual const char* name() const _NOEXCEPT; - virtual string message(int ev) const; -}; - -const char* -__future_error_category::name() const _NOEXCEPT -{ - return "future"; -} - -#if defined(__clang__) -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wswitch" -#elif defined(__GNUC__) || defined(__GNUG__) -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wswitch" -#endif - -string -__future_error_category::message(int ev) const -{ - switch (static_cast<future_errc>(ev)) - { - case future_errc(0): // For backwards compatibility with C++11 (LWG 2056) - case future_errc::broken_promise: - return string("The associated promise has been destructed prior " - "to the associated state becoming ready."); - case future_errc::future_already_retrieved: - return string("The future has already been retrieved from " - "the promise or packaged_task."); - case future_errc::promise_already_satisfied: - return string("The state of the promise has already been set."); - case future_errc::no_state: - return string("Operation not permitted on an object without " - "an associated state."); - } - return string("unspecified future_errc value\n"); -} - -#if defined(__clang__) -#pragma clang diagnostic pop -#elif defined(__GNUC__) || defined(__GNUG__) -#pragma GCC diagnostic pop -#endif - -const error_category& -future_category() _NOEXCEPT -{ - static __future_error_category __f; - return __f; -} - -future_error::future_error(error_code __ec) - : logic_error(__ec.message()), - __ec_(__ec) -{ -} - -future_error::~future_error() _NOEXCEPT -{ -} - -void -__assoc_sub_state::__on_zero_shared() _NOEXCEPT -{ - delete this; -} - -void -__assoc_sub_state::set_value() -{ - unique_lock<mutex> __lk(__mut_); - if (__has_value()) - __throw_future_error(future_errc::promise_already_satisfied); - __state_ |= __constructed | ready; - __cv_.notify_all(); -} - -void -__assoc_sub_state::set_value_at_thread_exit() -{ - unique_lock<mutex> __lk(__mut_); - if (__has_value()) - __throw_future_error(future_errc::promise_already_satisfied); - __state_ |= __constructed; - __thread_local_data()->__make_ready_at_thread_exit(this); -} - -void -__assoc_sub_state::set_exception(exception_ptr __p) -{ - unique_lock<mutex> __lk(__mut_); - if (__has_value()) - __throw_future_error(future_errc::promise_already_satisfied); - __exception_ = __p; - __state_ |= ready; - __cv_.notify_all(); -} - -void -__assoc_sub_state::set_exception_at_thread_exit(exception_ptr __p) -{ - unique_lock<mutex> __lk(__mut_); - if (__has_value()) - __throw_future_error(future_errc::promise_already_satisfied); - __exception_ = __p; - __thread_local_data()->__make_ready_at_thread_exit(this); -} - -void -__assoc_sub_state::__make_ready() -{ - unique_lock<mutex> __lk(__mut_); - __state_ |= ready; - __cv_.notify_all(); -} - -void -__assoc_sub_state::copy() -{ - unique_lock<mutex> __lk(__mut_); - __sub_wait(__lk); - if (__exception_ != nullptr) - rethrow_exception(__exception_); -} - -void -__assoc_sub_state::wait() -{ - unique_lock<mutex> __lk(__mut_); - __sub_wait(__lk); -} - -void -__assoc_sub_state::__sub_wait(unique_lock<mutex>& __lk) -{ - if (!__is_ready()) - { - if (__state_ & static_cast<unsigned>(deferred)) - { - __state_ &= ~static_cast<unsigned>(deferred); - __lk.unlock(); - __execute(); - } - else - while (!__is_ready()) - __cv_.wait(__lk); - } -} - -void -__assoc_sub_state::__execute() -{ - __throw_future_error(future_errc::no_state); -} - -future<void>::future(__assoc_sub_state* __state) - : __state_(__state) -{ - __state_->__attach_future(); -} - -future<void>::~future() -{ - if (__state_) - __state_->__release_shared(); -} - -void -future<void>::get() -{ - unique_ptr<__shared_count, __release_shared_count> __(__state_); - __assoc_sub_state* __s = __state_; - __state_ = nullptr; - __s->copy(); -} - -promise<void>::promise() - : __state_(new __assoc_sub_state) -{ -} - -promise<void>::~promise() -{ - if (__state_) - { -#ifndef _LIBCPP_NO_EXCEPTIONS - if (!__state_->__has_value() && __state_->use_count() > 1) - __state_->set_exception(make_exception_ptr( - future_error(make_error_code(future_errc::broken_promise)) - )); -#endif // _LIBCPP_NO_EXCEPTIONS - __state_->__release_shared(); - } -} - -future<void> -promise<void>::get_future() -{ - if (__state_ == nullptr) - __throw_future_error(future_errc::no_state); - return future<void>(__state_); -} - -void -promise<void>::set_value() -{ - if (__state_ == nullptr) - __throw_future_error(future_errc::no_state); - __state_->set_value(); -} - -void -promise<void>::set_exception(exception_ptr __p) -{ - if (__state_ == nullptr) - __throw_future_error(future_errc::no_state); - __state_->set_exception(__p); -} - -void -promise<void>::set_value_at_thread_exit() -{ - if (__state_ == nullptr) - __throw_future_error(future_errc::no_state); - __state_->set_value_at_thread_exit(); -} - -void -promise<void>::set_exception_at_thread_exit(exception_ptr __p) -{ - if (__state_ == nullptr) - __throw_future_error(future_errc::no_state); - __state_->set_exception_at_thread_exit(__p); -} - -shared_future<void>::~shared_future() -{ - if (__state_) - __state_->__release_shared(); -} - -shared_future<void>& -shared_future<void>::operator=(const shared_future& __rhs) -{ - if (__rhs.__state_) - __rhs.__state_->__add_shared(); - if (__state_) - __state_->__release_shared(); - __state_ = __rhs.__state_; - return *this; -} - -_LIBCPP_END_NAMESPACE_STD - -#endif // !_LIBCPP_HAS_NO_THREADS diff --git a/lib/libcxx/src/hash.cpp b/lib/libcxx/src/hash.cpp deleted file mode 100644 index dc90f789c6b..00000000000 --- a/lib/libcxx/src/hash.cpp +++ /dev/null @@ -1,570 +0,0 @@ -//===-------------------------- hash.cpp ----------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "__hash_table" -#include "algorithm" -#include "stdexcept" -#include "type_traits" - -#ifdef __clang__ -#pragma clang diagnostic ignored "-Wtautological-constant-out-of-range-compare" -#endif - -_LIBCPP_BEGIN_NAMESPACE_STD - -namespace { - -// handle all next_prime(i) for i in [1, 210), special case 0 -const unsigned small_primes[] = -{ - 0, - 2, - 3, - 5, - 7, - 11, - 13, - 17, - 19, - 23, - 29, - 31, - 37, - 41, - 43, - 47, - 53, - 59, - 61, - 67, - 71, - 73, - 79, - 83, - 89, - 97, - 101, - 103, - 107, - 109, - 113, - 127, - 131, - 137, - 139, - 149, - 151, - 157, - 163, - 167, - 173, - 179, - 181, - 191, - 193, - 197, - 199, - 211 -}; - -// potential primes = 210*k + indices[i], k >= 1 -// these numbers are not divisible by 2, 3, 5 or 7 -// (or any integer 2 <= j <= 10 for that matter). -const unsigned indices[] = -{ - 1, - 11, - 13, - 17, - 19, - 23, - 29, - 31, - 37, - 41, - 43, - 47, - 53, - 59, - 61, - 67, - 71, - 73, - 79, - 83, - 89, - 97, - 101, - 103, - 107, - 109, - 113, - 121, - 127, - 131, - 137, - 139, - 143, - 149, - 151, - 157, - 163, - 167, - 169, - 173, - 179, - 181, - 187, - 191, - 193, - 197, - 199, - 209 -}; - -} - -// Returns: If n == 0, returns 0. Else returns the lowest prime number that -// is greater than or equal to n. -// -// The algorithm creates a list of small primes, plus an open-ended list of -// potential primes. All prime numbers are potential prime numbers. However -// some potential prime numbers are not prime. In an ideal world, all potential -// prime numbers would be prime. Candidate prime numbers are chosen as the next -// highest potential prime. Then this number is tested for prime by dividing it -// by all potential prime numbers less than the sqrt of the candidate. -// -// This implementation defines potential primes as those numbers not divisible -// by 2, 3, 5, and 7. Other (common) implementations define potential primes -// as those not divisible by 2. A few other implementations define potential -// primes as those not divisible by 2 or 3. By raising the number of small -// primes which the potential prime is not divisible by, the set of potential -// primes more closely approximates the set of prime numbers. And thus there -// are fewer potential primes to search, and fewer potential primes to divide -// against. - -template <size_t _Sz = sizeof(size_t)> -inline _LIBCPP_INLINE_VISIBILITY -typename enable_if<_Sz == 4, void>::type -__check_for_overflow(size_t N) -{ -#ifndef _LIBCPP_NO_EXCEPTIONS - if (N > 0xFFFFFFFB) - throw overflow_error("__next_prime overflow"); -#else - (void)N; -#endif -} - -template <size_t _Sz = sizeof(size_t)> -inline _LIBCPP_INLINE_VISIBILITY -typename enable_if<_Sz == 8, void>::type -__check_for_overflow(size_t N) -{ -#ifndef _LIBCPP_NO_EXCEPTIONS - if (N > 0xFFFFFFFFFFFFFFC5ull) - throw overflow_error("__next_prime overflow"); -#else - (void)N; -#endif -} - -size_t -__next_prime(size_t n) -{ - const size_t L = 210; - const size_t N = sizeof(small_primes) / sizeof(small_primes[0]); - // If n is small enough, search in small_primes - if (n <= small_primes[N-1]) - return *std::lower_bound(small_primes, small_primes + N, n); - // Else n > largest small_primes - // Check for overflow - __check_for_overflow(n); - // Start searching list of potential primes: L * k0 + indices[in] - const size_t M = sizeof(indices) / sizeof(indices[0]); - // Select first potential prime >= n - // Known a-priori n >= L - size_t k0 = n / L; - size_t in = static_cast<size_t>(std::lower_bound(indices, indices + M, n - k0 * L) - - indices); - n = L * k0 + indices[in]; - while (true) - { - // Divide n by all primes or potential primes (i) until: - // 1. The division is even, so try next potential prime. - // 2. The i > sqrt(n), in which case n is prime. - // It is known a-priori that n is not divisible by 2, 3, 5 or 7, - // so don't test those (j == 5 -> divide by 11 first). And the - // potential primes start with 211, so don't test against the last - // small prime. - for (size_t j = 5; j < N - 1; ++j) - { - const std::size_t p = small_primes[j]; - const std::size_t q = n / p; - if (q < p) - return n; - if (n == q * p) - goto next; - } - // n wasn't divisible by small primes, try potential primes - { - size_t i = 211; - while (true) - { - std::size_t q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 10; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 8; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 8; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 6; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 4; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 2; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - i += 10; - q = n / i; - if (q < i) - return n; - if (n == q * i) - break; - - // This will loop i to the next "plane" of potential primes - i += 2; - } - } -next: - // n is not prime. Increment n to next potential prime. - if (++in == M) - { - ++k0; - in = 0; - } - n = L * k0 + indices[in]; - } -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/include/apple_availability.h b/lib/libcxx/src/include/apple_availability.h deleted file mode 100644 index c12f7325cb4..00000000000 --- a/lib/libcxx/src/include/apple_availability.h +++ /dev/null @@ -1,52 +0,0 @@ -//===------------------------ apple_availability.h ------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// -#ifndef _LIBCPP_SRC_INCLUDE_APPLE_AVAILABILITY_H -#define _LIBCPP_SRC_INCLUDE_APPLE_AVAILABILITY_H - -#if defined(__APPLE__) - -#if defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) -#if __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ >= 101300 -#define _LIBCPP_USE_UTIMENSAT -#endif -#elif defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) -#if __ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ >= 110000 -#define _LIBCPP_USE_UTIMENSAT -#endif -#elif defined(__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__) -#if __ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ >= 110000 -#define _LIBCPP_USE_UTIMENSAT -#endif -#elif defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) -#if __ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ >= 40000 -#define _LIBCPP_USE_UTIMENSAT -#endif -#endif // __ENVIRONMENT_.*_VERSION_MIN_REQUIRED__ - -#if defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) -#if __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ >= 101200 -#define _LIBCPP_USE_CLOCK_GETTIME -#endif -#elif defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) -#if __ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ >= 100000 -#define _LIBCPP_USE_CLOCK_GETTIME -#endif -#elif defined(__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__) -#if __ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ >= 100000 -#define _LIBCPP_USE_CLOCK_GETTIME -#endif -#elif defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) -#if __ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ >= 30000 -#define _LIBCPP_USE_CLOCK_GETTIME -#endif -#endif // __ENVIRONMENT_.*_VERSION_MIN_REQUIRED__ - -#endif // __APPLE__ - -#endif // _LIBCPP_SRC_INCLUDE_APPLE_AVAILABILITY_H diff --git a/lib/libcxx/src/include/atomic_support.h b/lib/libcxx/src/include/atomic_support.h deleted file mode 100644 index ccd8d78d3d7..00000000000 --- a/lib/libcxx/src/include/atomic_support.h +++ /dev/null @@ -1,177 +0,0 @@ -//===----------------------------------------------------------------------===//// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===//// - -#ifndef ATOMIC_SUPPORT_H -#define ATOMIC_SUPPORT_H - -#include "__config" -#include "memory" // for __libcpp_relaxed_load - -#if defined(__clang__) && __has_builtin(__atomic_load_n) \ - && __has_builtin(__atomic_store_n) \ - && __has_builtin(__atomic_add_fetch) \ - && __has_builtin(__atomic_exchange_n) \ - && __has_builtin(__atomic_compare_exchange_n) \ - && defined(__ATOMIC_RELAXED) \ - && defined(__ATOMIC_CONSUME) \ - && defined(__ATOMIC_ACQUIRE) \ - && defined(__ATOMIC_RELEASE) \ - && defined(__ATOMIC_ACQ_REL) \ - && defined(__ATOMIC_SEQ_CST) -# define _LIBCPP_HAS_ATOMIC_BUILTINS -#elif !defined(__clang__) && defined(_GNUC_VER) && _GNUC_VER >= 407 -# define _LIBCPP_HAS_ATOMIC_BUILTINS -#endif - -#if !defined(_LIBCPP_HAS_ATOMIC_BUILTINS) && !defined(_LIBCPP_HAS_NO_THREADS) -# if defined(_LIBCPP_WARNING) - _LIBCPP_WARNING("Building libc++ without __atomic builtins is unsupported") -# else -# warning Building libc++ without __atomic builtins is unsupported -# endif -#endif - -_LIBCPP_BEGIN_NAMESPACE_STD - -namespace { - -#if defined(_LIBCPP_HAS_ATOMIC_BUILTINS) && !defined(_LIBCPP_HAS_NO_THREADS) - -enum __libcpp_atomic_order { - _AO_Relaxed = __ATOMIC_RELAXED, - _AO_Consume = __ATOMIC_CONSUME, - _AO_Acquire = __ATOMIC_ACQUIRE, - _AO_Release = __ATOMIC_RELEASE, - _AO_Acq_Rel = __ATOMIC_ACQ_REL, - _AO_Seq = __ATOMIC_SEQ_CST -}; - -template <class _ValueType, class _FromType> -inline _LIBCPP_INLINE_VISIBILITY -void __libcpp_atomic_store(_ValueType* __dest, _FromType __val, - int __order = _AO_Seq) -{ - __atomic_store_n(__dest, __val, __order); -} - -template <class _ValueType, class _FromType> -inline _LIBCPP_INLINE_VISIBILITY -void __libcpp_relaxed_store(_ValueType* __dest, _FromType __val) -{ - __atomic_store_n(__dest, __val, _AO_Relaxed); -} - -template <class _ValueType> -inline _LIBCPP_INLINE_VISIBILITY -_ValueType __libcpp_atomic_load(_ValueType const* __val, - int __order = _AO_Seq) -{ - return __atomic_load_n(__val, __order); -} - -template <class _ValueType, class _AddType> -inline _LIBCPP_INLINE_VISIBILITY -_ValueType __libcpp_atomic_add(_ValueType* __val, _AddType __a, - int __order = _AO_Seq) -{ - return __atomic_add_fetch(__val, __a, __order); -} - -template <class _ValueType> -inline _LIBCPP_INLINE_VISIBILITY -_ValueType __libcpp_atomic_exchange(_ValueType* __target, - _ValueType __value, int __order = _AO_Seq) -{ - return __atomic_exchange_n(__target, __value, __order); -} - -template <class _ValueType> -inline _LIBCPP_INLINE_VISIBILITY -bool __libcpp_atomic_compare_exchange(_ValueType* __val, - _ValueType* __expected, _ValueType __after, - int __success_order = _AO_Seq, - int __fail_order = _AO_Seq) -{ - return __atomic_compare_exchange_n(__val, __expected, __after, true, - __success_order, __fail_order); -} - -#else // _LIBCPP_HAS_NO_THREADS - -enum __libcpp_atomic_order { - _AO_Relaxed, - _AO_Consume, - _AO_Acquire, - _AO_Release, - _AO_Acq_Rel, - _AO_Seq -}; - -template <class _ValueType, class _FromType> -inline _LIBCPP_INLINE_VISIBILITY -void __libcpp_atomic_store(_ValueType* __dest, _FromType __val, - int = 0) -{ - *__dest = __val; -} - -template <class _ValueType, class _FromType> -inline _LIBCPP_INLINE_VISIBILITY -void __libcpp_relaxed_store(_ValueType* __dest, _FromType __val) -{ - *__dest = __val; -} - -template <class _ValueType> -inline _LIBCPP_INLINE_VISIBILITY -_ValueType __libcpp_atomic_load(_ValueType const* __val, - int = 0) -{ - return *__val; -} - -template <class _ValueType, class _AddType> -inline _LIBCPP_INLINE_VISIBILITY -_ValueType __libcpp_atomic_add(_ValueType* __val, _AddType __a, - int = 0) -{ - return *__val += __a; -} - -template <class _ValueType> -inline _LIBCPP_INLINE_VISIBILITY -_ValueType __libcpp_atomic_exchange(_ValueType* __target, - _ValueType __value, int __order = _AO_Seq) -{ - _ValueType old = *__target; - *__target = __value; - return old; -} - -template <class _ValueType> -inline _LIBCPP_INLINE_VISIBILITY -bool __libcpp_atomic_compare_exchange(_ValueType* __val, - _ValueType* __expected, _ValueType __after, - int = 0, int = 0) -{ - if (*__val == *__expected) { - *__val = __after; - return true; - } - *__expected = *__val; - return false; -} - -#endif // _LIBCPP_HAS_NO_THREADS - -} // end namespace - -_LIBCPP_END_NAMESPACE_STD - -#endif // ATOMIC_SUPPORT_H diff --git a/lib/libcxx/src/include/config_elast.h b/lib/libcxx/src/include/config_elast.h deleted file mode 100644 index c3cc19c2234..00000000000 --- a/lib/libcxx/src/include/config_elast.h +++ /dev/null @@ -1,40 +0,0 @@ -//===----------------------- config_elast.h -------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifndef _LIBCPP_CONFIG_ELAST -#define _LIBCPP_CONFIG_ELAST - -#include <__config> - -#if defined(_LIBCPP_MSVCRT_LIKE) -#include <stdlib.h> -#else -#include <errno.h> -#endif - -#if defined(ELAST) -#define _LIBCPP_ELAST ELAST -#elif defined(_NEWLIB_VERSION) -#define _LIBCPP_ELAST __ELASTERROR -#elif defined(__Fuchsia__) -// No _LIBCPP_ELAST needed on Fuchsia -#elif defined(__linux__) || defined(_LIBCPP_HAS_MUSL_LIBC) -#define _LIBCPP_ELAST 4095 -#elif defined(__APPLE__) -// No _LIBCPP_ELAST needed on Apple -#elif defined(__sun__) -#define _LIBCPP_ELAST ESTALE -#elif defined(_LIBCPP_MSVCRT_LIKE) -#define _LIBCPP_ELAST (_sys_nerr - 1) -#else -// Warn here so that the person doing the libcxx port has an easier time: -#warning ELAST for this platform not yet implemented -#endif - -#endif // _LIBCPP_CONFIG_ELAST diff --git a/lib/libcxx/src/include/refstring.h b/lib/libcxx/src/include/refstring.h deleted file mode 100644 index 702f2b7388d..00000000000 --- a/lib/libcxx/src/include/refstring.h +++ /dev/null @@ -1,128 +0,0 @@ -//===------------------------ __refstring ---------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifndef _LIBCPP_REFSTRING_H -#define _LIBCPP_REFSTRING_H - -#include <__config> -#include <stdexcept> -#include <cstddef> -#include <cstring> -#ifdef __APPLE__ -#include <dlfcn.h> -#include <mach-o/dyld.h> -#endif -#include "atomic_support.h" - -_LIBCPP_BEGIN_NAMESPACE_STD - -namespace __refstring_imp { namespace { -typedef int count_t; - -struct _Rep_base { - std::size_t len; - std::size_t cap; - count_t count; -}; - -inline _Rep_base* rep_from_data(const char *data_) noexcept { - char *data = const_cast<char *>(data_); - return reinterpret_cast<_Rep_base *>(data - sizeof(_Rep_base)); -} - -inline char * data_from_rep(_Rep_base *rep) noexcept { - char *data = reinterpret_cast<char *>(rep); - return data + sizeof(*rep); -} - -#if defined(__APPLE__) -inline -const char* compute_gcc_empty_string_storage() _NOEXCEPT -{ - void* handle = dlopen("/usr/lib/libstdc++.6.dylib", RTLD_NOLOAD); - if (handle == nullptr) - return nullptr; - void* sym = dlsym(handle, "_ZNSs4_Rep20_S_empty_rep_storageE"); - if (sym == nullptr) - return nullptr; - return data_from_rep(reinterpret_cast<_Rep_base *>(sym)); -} - -inline -const char* -get_gcc_empty_string_storage() _NOEXCEPT -{ - static const char* p = compute_gcc_empty_string_storage(); - return p; -} -#endif - -}} // namespace __refstring_imp - -using namespace __refstring_imp; - -inline -__libcpp_refstring::__libcpp_refstring(const char* msg) { - std::size_t len = strlen(msg); - _Rep_base* rep = static_cast<_Rep_base *>(::operator new(sizeof(*rep) + len + 1)); - rep->len = len; - rep->cap = len; - rep->count = 0; - char *data = data_from_rep(rep); - std::memcpy(data, msg, len + 1); - __imp_ = data; -} - -inline -__libcpp_refstring::__libcpp_refstring(const __libcpp_refstring &s) _NOEXCEPT - : __imp_(s.__imp_) -{ - if (__uses_refcount()) - __libcpp_atomic_add(&rep_from_data(__imp_)->count, 1); -} - -inline -__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_; - if (__uses_refcount()) - __libcpp_atomic_add(&rep_from_data(__imp_)->count, 1); - if (adjust_old_count) - { - if (__libcpp_atomic_add(&old_rep->count, count_t(-1)) < 0) - { - ::operator delete(old_rep); - } - } - return *this; -} - -inline -__libcpp_refstring::~__libcpp_refstring() { - if (__uses_refcount()) { - _Rep_base* rep = rep_from_data(__imp_); - if (__libcpp_atomic_add(&rep->count, count_t(-1)) < 0) { - ::operator delete(rep); - } - } -} - -inline -bool __libcpp_refstring::__uses_refcount() const { -#ifdef __APPLE__ - return __imp_ != get_gcc_empty_string_storage(); -#else - return true; -#endif -} - -_LIBCPP_END_NAMESPACE_STD - -#endif //_LIBCPP_REFSTRING_H diff --git a/lib/libcxx/src/ios.cpp b/lib/libcxx/src/ios.cpp deleted file mode 100644 index 0f1d88e378f..00000000000 --- a/lib/libcxx/src/ios.cpp +++ /dev/null @@ -1,467 +0,0 @@ -//===-------------------------- ios.cpp -----------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "__config" - -#include "ios" - -#include <stdlib.h> - -#include "__locale" -#include "algorithm" -#include "include/config_elast.h" -#include "istream" -#include "limits" -#include "memory" -#include "new" -#include "streambuf" -#include "string" -#include "__undef_macros" - -_LIBCPP_BEGIN_NAMESPACE_STD - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS basic_ios<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS basic_ios<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS basic_streambuf<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS basic_streambuf<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS basic_istream<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS basic_istream<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS basic_ostream<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS basic_ostream<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS basic_iostream<char>; - -class _LIBCPP_HIDDEN __iostream_category - : public __do_message -{ -public: - virtual const char* name() const _NOEXCEPT; - virtual string message(int ev) const; -}; - -const char* -__iostream_category::name() const _NOEXCEPT -{ - return "iostream"; -} - -string -__iostream_category::message(int ev) const -{ - if (ev != static_cast<int>(io_errc::stream) -#ifdef _LIBCPP_ELAST - && ev <= _LIBCPP_ELAST -#endif // _LIBCPP_ELAST - ) - return __do_message::message(ev); - return string("unspecified iostream_category error"); -} - -const error_category& -iostream_category() _NOEXCEPT -{ - static __iostream_category s; - return s; -} - -// ios_base::failure - -ios_base::failure::failure(const string& msg, const error_code& ec) - : system_error(ec, msg) -{ -} - -ios_base::failure::failure(const char* msg, const error_code& ec) - : system_error(ec, msg) -{ -} - -ios_base::failure::~failure() throw() -{ -} - -// ios_base locale - -const ios_base::fmtflags ios_base::boolalpha; -const ios_base::fmtflags ios_base::dec; -const ios_base::fmtflags ios_base::fixed; -const ios_base::fmtflags ios_base::hex; -const ios_base::fmtflags ios_base::internal; -const ios_base::fmtflags ios_base::left; -const ios_base::fmtflags ios_base::oct; -const ios_base::fmtflags ios_base::right; -const ios_base::fmtflags ios_base::scientific; -const ios_base::fmtflags ios_base::showbase; -const ios_base::fmtflags ios_base::showpoint; -const ios_base::fmtflags ios_base::showpos; -const ios_base::fmtflags ios_base::skipws; -const ios_base::fmtflags ios_base::unitbuf; -const ios_base::fmtflags ios_base::uppercase; -const ios_base::fmtflags ios_base::adjustfield; -const ios_base::fmtflags ios_base::basefield; -const ios_base::fmtflags ios_base::floatfield; - -const ios_base::iostate ios_base::badbit; -const ios_base::iostate ios_base::eofbit; -const ios_base::iostate ios_base::failbit; -const ios_base::iostate ios_base::goodbit; - -const ios_base::openmode ios_base::app; -const ios_base::openmode ios_base::ate; -const ios_base::openmode ios_base::binary; -const ios_base::openmode ios_base::in; -const ios_base::openmode ios_base::out; -const ios_base::openmode ios_base::trunc; - -void -ios_base::__call_callbacks(event ev) -{ - for (size_t i = __event_size_; i;) - { - --i; - __fn_[i](ev, *this, __index_[i]); - } -} - -// locale - -locale -ios_base::imbue(const locale& newloc) -{ - static_assert(sizeof(locale) == sizeof(__loc_), ""); - locale& loc_storage = *reinterpret_cast<locale*>(&__loc_); - locale oldloc = loc_storage; - loc_storage = newloc; - __call_callbacks(imbue_event); - return oldloc; -} - -locale -ios_base::getloc() const -{ - const locale& loc_storage = *reinterpret_cast<const locale*>(&__loc_); - return loc_storage; -} - -// xalloc -#if defined(_LIBCPP_HAS_C_ATOMIC_IMP) && !defined(_LIBCPP_HAS_NO_THREADS) -atomic<int> ios_base::__xindex_ = ATOMIC_VAR_INIT(0); -#else -int ios_base::__xindex_ = 0; -#endif - -template <typename _Tp> -static size_t __ios_new_cap(size_t __req_size, size_t __current_cap) -{ // Precondition: __req_size > __current_cap - const size_t mx = std::numeric_limits<size_t>::max() / sizeof(_Tp); - if (__req_size < mx/2) - return _VSTD::max(2 * __current_cap, __req_size); - else - return mx; -} - -int -ios_base::xalloc() -{ - return __xindex_++; -} - -long& -ios_base::iword(int index) -{ - size_t req_size = static_cast<size_t>(index)+1; - if (req_size > __iarray_cap_) - { - size_t newcap = __ios_new_cap<long>(req_size, __iarray_cap_); - long* iarray = static_cast<long*>(realloc(__iarray_, newcap * sizeof(long))); - if (iarray == 0) - { - setstate(badbit); - static long error; - error = 0; - return error; - } - __iarray_ = iarray; - for (long* p = __iarray_ + __iarray_size_; p < __iarray_ + newcap; ++p) - *p = 0; - __iarray_cap_ = newcap; - } - __iarray_size_ = max<size_t>(__iarray_size_, req_size); - return __iarray_[index]; -} - -void*& -ios_base::pword(int index) -{ - size_t req_size = static_cast<size_t>(index)+1; - if (req_size > __parray_cap_) - { - size_t newcap = __ios_new_cap<void *>(req_size, __iarray_cap_); - void** parray = static_cast<void**>(realloc(__parray_, newcap * sizeof(void *))); - if (parray == 0) - { - setstate(badbit); - static void* error; - error = 0; - return error; - } - __parray_ = parray; - for (void** p = __parray_ + __parray_size_; p < __parray_ + newcap; ++p) - *p = 0; - __parray_cap_ = newcap; - } - __parray_size_ = max<size_t>(__parray_size_, req_size); - return __parray_[index]; -} - -// register_callback - -void -ios_base::register_callback(event_callback fn, int index) -{ - size_t req_size = __event_size_ + 1; - if (req_size > __event_cap_) - { - size_t newcap = __ios_new_cap<event_callback>(req_size, __event_cap_); - event_callback* fns = static_cast<event_callback*>(realloc(__fn_, newcap * sizeof(event_callback))); - if (fns == 0) - setstate(badbit); - __fn_ = fns; - int* indxs = static_cast<int *>(realloc(__index_, newcap * sizeof(int))); - if (indxs == 0) - setstate(badbit); - __index_ = indxs; - __event_cap_ = newcap; - } - __fn_[__event_size_] = fn; - __index_[__event_size_] = index; - ++__event_size_; -} - -ios_base::~ios_base() -{ - __call_callbacks(erase_event); - locale& loc_storage = *reinterpret_cast<locale*>(&__loc_); - loc_storage.~locale(); - free(__fn_); - free(__index_); - free(__iarray_); - free(__parray_); -} - -// iostate - -void -ios_base::clear(iostate state) -{ - if (__rdbuf_) - __rdstate_ = state; - else - __rdstate_ = state | badbit; -#ifndef _LIBCPP_NO_EXCEPTIONS - if (((state | (__rdbuf_ ? goodbit : badbit)) & __exceptions_) != 0) - throw failure("ios_base::clear"); -#endif // _LIBCPP_NO_EXCEPTIONS -} - -// init - -void -ios_base::init(void* sb) -{ - __rdbuf_ = sb; - __rdstate_ = __rdbuf_ ? goodbit : badbit; - __exceptions_ = goodbit; - __fmtflags_ = skipws | dec; - __width_ = 0; - __precision_ = 6; - __fn_ = 0; - __index_ = 0; - __event_size_ = 0; - __event_cap_ = 0; - __iarray_ = 0; - __iarray_size_ = 0; - __iarray_cap_ = 0; - __parray_ = 0; - __parray_size_ = 0; - __parray_cap_ = 0; - ::new(&__loc_) locale; -} - -void -ios_base::copyfmt(const ios_base& rhs) -{ - // If we can't acquire the needed resources, throw bad_alloc (can't set badbit) - // Don't alter *this until all needed resources are acquired - unique_ptr<event_callback, void (*)(void*)> new_callbacks(0, free); - unique_ptr<int, void (*)(void*)> new_ints(0, free); - unique_ptr<long, void (*)(void*)> new_longs(0, free); - unique_ptr<void*, void (*)(void*)> new_pointers(0, free); - if (__event_cap_ < rhs.__event_size_) - { - size_t newesize = sizeof(event_callback) * rhs.__event_size_; - new_callbacks.reset(static_cast<event_callback*>(malloc(newesize))); -#ifndef _LIBCPP_NO_EXCEPTIONS - if (!new_callbacks) - throw bad_alloc(); -#endif // _LIBCPP_NO_EXCEPTIONS - - size_t newisize = sizeof(int) * rhs.__event_size_; - new_ints.reset(static_cast<int *>(malloc(newisize))); -#ifndef _LIBCPP_NO_EXCEPTIONS - if (!new_ints) - throw bad_alloc(); -#endif // _LIBCPP_NO_EXCEPTIONS - } - if (__iarray_cap_ < rhs.__iarray_size_) - { - size_t newsize = sizeof(long) * rhs.__iarray_size_; - new_longs.reset(static_cast<long*>(malloc(newsize))); -#ifndef _LIBCPP_NO_EXCEPTIONS - if (!new_longs) - throw bad_alloc(); -#endif // _LIBCPP_NO_EXCEPTIONS - } - if (__parray_cap_ < rhs.__parray_size_) - { - size_t newsize = sizeof(void*) * rhs.__parray_size_; - new_pointers.reset(static_cast<void**>(malloc(newsize))); -#ifndef _LIBCPP_NO_EXCEPTIONS - if (!new_pointers) - throw bad_alloc(); -#endif // _LIBCPP_NO_EXCEPTIONS - } - // Got everything we need. Copy everything but __rdstate_, __rdbuf_ and __exceptions_ - __fmtflags_ = rhs.__fmtflags_; - __precision_ = rhs.__precision_; - __width_ = rhs.__width_; - locale& lhs_loc = *reinterpret_cast<locale*>(&__loc_); - const locale& rhs_loc = *reinterpret_cast<const locale*>(&rhs.__loc_); - lhs_loc = rhs_loc; - if (__event_cap_ < rhs.__event_size_) - { - free(__fn_); - __fn_ = new_callbacks.release(); - free(__index_); - __index_ = new_ints.release(); - __event_cap_ = rhs.__event_size_; - } - for (__event_size_ = 0; __event_size_ < rhs.__event_size_; ++__event_size_) - { - __fn_[__event_size_] = rhs.__fn_[__event_size_]; - __index_[__event_size_] = rhs.__index_[__event_size_]; - } - if (__iarray_cap_ < rhs.__iarray_size_) - { - free(__iarray_); - __iarray_ = new_longs.release(); - __iarray_cap_ = rhs.__iarray_size_; - } - for (__iarray_size_ = 0; __iarray_size_ < rhs.__iarray_size_; ++__iarray_size_) - __iarray_[__iarray_size_] = rhs.__iarray_[__iarray_size_]; - if (__parray_cap_ < rhs.__parray_size_) - { - free(__parray_); - __parray_ = new_pointers.release(); - __parray_cap_ = rhs.__parray_size_; - } - for (__parray_size_ = 0; __parray_size_ < rhs.__parray_size_; ++__parray_size_) - __parray_[__parray_size_] = rhs.__parray_[__parray_size_]; -} - -void -ios_base::move(ios_base& rhs) -{ - // *this is uninitialized - __fmtflags_ = rhs.__fmtflags_; - __precision_ = rhs.__precision_; - __width_ = rhs.__width_; - __rdstate_ = rhs.__rdstate_; - __exceptions_ = rhs.__exceptions_; - __rdbuf_ = 0; - locale& rhs_loc = *reinterpret_cast<locale*>(&rhs.__loc_); - ::new(&__loc_) locale(rhs_loc); - __fn_ = rhs.__fn_; - rhs.__fn_ = 0; - __index_ = rhs.__index_; - rhs.__index_ = 0; - __event_size_ = rhs.__event_size_; - rhs.__event_size_ = 0; - __event_cap_ = rhs.__event_cap_; - rhs.__event_cap_ = 0; - __iarray_ = rhs.__iarray_; - rhs.__iarray_ = 0; - __iarray_size_ = rhs.__iarray_size_; - rhs.__iarray_size_ = 0; - __iarray_cap_ = rhs.__iarray_cap_; - rhs.__iarray_cap_ = 0; - __parray_ = rhs.__parray_; - rhs.__parray_ = 0; - __parray_size_ = rhs.__parray_size_; - rhs.__parray_size_ = 0; - __parray_cap_ = rhs.__parray_cap_; - rhs.__parray_cap_ = 0; -} - -void -ios_base::swap(ios_base& rhs) _NOEXCEPT -{ - _VSTD::swap(__fmtflags_, rhs.__fmtflags_); - _VSTD::swap(__precision_, rhs.__precision_); - _VSTD::swap(__width_, rhs.__width_); - _VSTD::swap(__rdstate_, rhs.__rdstate_); - _VSTD::swap(__exceptions_, rhs.__exceptions_); - locale& lhs_loc = *reinterpret_cast<locale*>(&__loc_); - locale& rhs_loc = *reinterpret_cast<locale*>(&rhs.__loc_); - _VSTD::swap(lhs_loc, rhs_loc); - _VSTD::swap(__fn_, rhs.__fn_); - _VSTD::swap(__index_, rhs.__index_); - _VSTD::swap(__event_size_, rhs.__event_size_); - _VSTD::swap(__event_cap_, rhs.__event_cap_); - _VSTD::swap(__iarray_, rhs.__iarray_); - _VSTD::swap(__iarray_size_, rhs.__iarray_size_); - _VSTD::swap(__iarray_cap_, rhs.__iarray_cap_); - _VSTD::swap(__parray_, rhs.__parray_); - _VSTD::swap(__parray_size_, rhs.__parray_size_); - _VSTD::swap(__parray_cap_, rhs.__parray_cap_); -} - -void -ios_base::__set_badbit_and_consider_rethrow() -{ - __rdstate_ |= badbit; -#ifndef _LIBCPP_NO_EXCEPTIONS - if (__exceptions_ & badbit) - throw; -#endif // _LIBCPP_NO_EXCEPTIONS -} - -void -ios_base::__set_failbit_and_consider_rethrow() -{ - __rdstate_ |= failbit; -#ifndef _LIBCPP_NO_EXCEPTIONS - if (__exceptions_ & failbit) - throw; -#endif // _LIBCPP_NO_EXCEPTIONS -} - -bool -ios_base::sync_with_stdio(bool sync) -{ - static bool previous_state = true; - bool r = previous_state; - previous_state = sync; - return r; -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/iostream.cpp b/lib/libcxx/src/iostream.cpp deleted file mode 100644 index 11bfb486208..00000000000 --- a/lib/libcxx/src/iostream.cpp +++ /dev/null @@ -1,124 +0,0 @@ -//===------------------------ iostream.cpp --------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "__std_stream" -#include "string" -#include "new" - -#define _str(s) #s -#define str(s) _str(s) -#define _LIBCPP_ABI_NAMESPACE_STR str(_LIBCPP_ABI_NAMESPACE) - -_LIBCPP_BEGIN_NAMESPACE_STD - -#ifndef _LIBCPP_HAS_NO_STDIN -_ALIGNAS_TYPE (istream) _LIBCPP_FUNC_VIS char cin[sizeof(istream)] -#if defined(_LIBCPP_ABI_MICROSOFT) && defined(__clang__) -__asm__("?cin@" _LIBCPP_ABI_NAMESPACE_STR "@std@@3V?$basic_istream@DU?$char_traits@D@" _LIBCPP_ABI_NAMESPACE_STR "@std@@@12@A") -#endif -; -_ALIGNAS_TYPE (__stdinbuf<char> ) static char __cin[sizeof(__stdinbuf <char>)]; -static mbstate_t mb_cin; -_ALIGNAS_TYPE (wistream) _LIBCPP_FUNC_VIS char wcin[sizeof(wistream)] -#if defined(_LIBCPP_ABI_MICROSOFT) && defined(__clang__) -__asm__("?wcin@" _LIBCPP_ABI_NAMESPACE_STR "@std@@3V?$basic_istream@_WU?$char_traits@_W@" _LIBCPP_ABI_NAMESPACE_STR "@std@@@12@A") -#endif -; -_ALIGNAS_TYPE (__stdinbuf<wchar_t> ) static char __wcin[sizeof(__stdinbuf <wchar_t>)]; -static mbstate_t mb_wcin; -#endif - -#ifndef _LIBCPP_HAS_NO_STDOUT -_ALIGNAS_TYPE (ostream) _LIBCPP_FUNC_VIS char cout[sizeof(ostream)] -#if defined(_LIBCPP_ABI_MICROSOFT) && defined(__clang__) -__asm__("?cout@" _LIBCPP_ABI_NAMESPACE_STR "@std@@3V?$basic_ostream@DU?$char_traits@D@" _LIBCPP_ABI_NAMESPACE_STR "@std@@@12@A") -#endif -; -_ALIGNAS_TYPE (__stdoutbuf<char>) static char __cout[sizeof(__stdoutbuf<char>)]; -static mbstate_t mb_cout; -_ALIGNAS_TYPE (wostream) _LIBCPP_FUNC_VIS char wcout[sizeof(wostream)] -#if defined(_LIBCPP_ABI_MICROSOFT) && defined(__clang__) -__asm__("?wcout@" _LIBCPP_ABI_NAMESPACE_STR "@std@@3V?$basic_ostream@_WU?$char_traits@_W@" _LIBCPP_ABI_NAMESPACE_STR "@std@@@12@A") -#endif -; -_ALIGNAS_TYPE (__stdoutbuf<wchar_t>) static char __wcout[sizeof(__stdoutbuf<wchar_t>)]; -static mbstate_t mb_wcout; -#endif - -_ALIGNAS_TYPE (ostream) _LIBCPP_FUNC_VIS char cerr[sizeof(ostream)] -#if defined(_LIBCPP_ABI_MICROSOFT) && defined(__clang__) -__asm__("?cerr@" _LIBCPP_ABI_NAMESPACE_STR "@std@@3V?$basic_ostream@DU?$char_traits@D@" _LIBCPP_ABI_NAMESPACE_STR "@std@@@12@A") -#endif -; -_ALIGNAS_TYPE (__stdoutbuf<char>) static char __cerr[sizeof(__stdoutbuf<char>)]; -static mbstate_t mb_cerr; -_ALIGNAS_TYPE (wostream) _LIBCPP_FUNC_VIS char wcerr[sizeof(wostream)] -#if defined(_LIBCPP_ABI_MICROSOFT) && defined(__clang__) -__asm__("?wcerr@" _LIBCPP_ABI_NAMESPACE_STR "@std@@3V?$basic_ostream@_WU?$char_traits@_W@" _LIBCPP_ABI_NAMESPACE_STR "@std@@@12@A") -#endif -; -_ALIGNAS_TYPE (__stdoutbuf<wchar_t>) static char __wcerr[sizeof(__stdoutbuf<wchar_t>)]; -static mbstate_t mb_wcerr; - -_ALIGNAS_TYPE (ostream) _LIBCPP_FUNC_VIS char clog[sizeof(ostream)] -#if defined(_LIBCPP_ABI_MICROSOFT) && defined(__clang__) -__asm__("?clog@" _LIBCPP_ABI_NAMESPACE_STR "@std@@3V?$basic_ostream@DU?$char_traits@D@" _LIBCPP_ABI_NAMESPACE_STR "@std@@@12@A") -#endif -; -_ALIGNAS_TYPE (wostream) _LIBCPP_FUNC_VIS char wclog[sizeof(wostream)] -#if defined(_LIBCPP_ABI_MICROSOFT) && defined(__clang__) -__asm__("?wclog@" _LIBCPP_ABI_NAMESPACE_STR "@std@@3V?$basic_ostream@_WU?$char_traits@_W@" _LIBCPP_ABI_NAMESPACE_STR "@std@@@12@A") -#endif -; - -_LIBCPP_HIDDEN ios_base::Init __start_std_streams; - -ios_base::Init::Init() -{ -#ifndef _LIBCPP_HAS_NO_STDIN - istream* cin_ptr = ::new(cin) istream(::new(__cin) __stdinbuf <char>(stdin, &mb_cin)); - wistream* wcin_ptr = ::new(wcin) wistream(::new(__wcin) __stdinbuf <wchar_t>(stdin, &mb_wcin)); -#endif -#ifndef _LIBCPP_HAS_NO_STDOUT - ostream* cout_ptr = ::new(cout) ostream(::new(__cout) __stdoutbuf<char>(stdout, &mb_cout)); - wostream* wcout_ptr = ::new(wcout) wostream(::new(__wcout) __stdoutbuf<wchar_t>(stdout, &mb_wcout)); -#endif - ostream* cerr_ptr = ::new(cerr) ostream(::new(__cerr) __stdoutbuf<char>(stderr, &mb_cerr)); - ::new(clog) ostream(cerr_ptr->rdbuf()); - wostream* wcerr_ptr = ::new(wcerr) wostream(::new(__wcerr) __stdoutbuf<wchar_t>(stderr, &mb_wcerr)); - ::new(wclog) wostream(wcerr_ptr->rdbuf()); - -#if !defined(_LIBCPP_HAS_NO_STDIN) && !defined(_LIBCPP_HAS_NO_STDOUT) - cin_ptr->tie(cout_ptr); - wcin_ptr->tie(wcout_ptr); -#endif - _VSTD::unitbuf(*cerr_ptr); - _VSTD::unitbuf(*wcerr_ptr); -#ifndef _LIBCPP_HAS_NO_STDOUT - cerr_ptr->tie(cout_ptr); - wcerr_ptr->tie(wcout_ptr); -#endif -} - -ios_base::Init::~Init() -{ -#ifndef _LIBCPP_HAS_NO_STDOUT - ostream* cout_ptr = reinterpret_cast<ostream*>(cout); - wostream* wcout_ptr = reinterpret_cast<wostream*>(wcout); - cout_ptr->flush(); - wcout_ptr->flush(); -#endif - - ostream* clog_ptr = reinterpret_cast<ostream*>(clog); - wostream* wclog_ptr = reinterpret_cast<wostream*>(wclog); - clog_ptr->flush(); - wclog_ptr->flush(); -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/locale.cpp b/lib/libcxx/src/locale.cpp deleted file mode 100644 index b9c701137df..00000000000 --- a/lib/libcxx/src/locale.cpp +++ /dev/null @@ -1,6163 +0,0 @@ -//===------------------------- locale.cpp ---------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -// On Solaris, we need to define something to make the C99 parts of localeconv -// visible. -#ifdef __sun__ -#define _LCONV_C99 -#endif - -#include "string" -#include "locale" -#include "codecvt" -#include "vector" -#include "algorithm" -#include "typeinfo" -#ifndef _LIBCPP_NO_EXCEPTIONS -# include "type_traits" -#endif -#include "clocale" -#include "cstring" -#if defined(_LIBCPP_MSVCRT) -#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__) -#include <langinfo.h> -#endif -#include <stdlib.h> -#include <stdio.h> -#include "include/atomic_support.h" -#include "__undef_macros" - -// On Linux, wint_t and wchar_t have different signed-ness, and this causes -// lots of noise in the build log, but no bugs that I know of. -#if defined(__clang__) -#pragma clang diagnostic ignored "-Wsign-conversion" -#endif - -_LIBCPP_BEGIN_NAMESPACE_STD - -struct __libcpp_unique_locale { - __libcpp_unique_locale(const char* nm) : __loc_(newlocale(LC_ALL_MASK, nm, 0)) {} - - ~__libcpp_unique_locale() { - if (__loc_) - freelocale(__loc_); - } - - explicit operator bool() const { return __loc_; } - - locale_t& get() { return __loc_; } - - locale_t __loc_; -private: - __libcpp_unique_locale(__libcpp_unique_locale const&); - __libcpp_unique_locale& operator=(__libcpp_unique_locale const&); -}; - -#ifdef __cloc_defined -locale_t __cloc() { - // In theory this could create a race condition. In practice - // the race condition is non-fatal since it will just create - // a little resource leak. Better approach would be appreciated. - static locale_t result = newlocale(LC_ALL_MASK, "C", 0); - return result; -} -#endif // __cloc_defined - -namespace { - -struct release -{ - void operator()(locale::facet* p) {p->__release_shared();} -}; - -template <class T, class A0> -inline -T& -make(A0 a0) -{ - static typename aligned_storage<sizeof(T)>::type buf; - auto *obj = ::new (&buf) T(a0); - return *obj; -} - -template <class T, class A0, class A1> -inline -T& -make(A0 a0, A1 a1) -{ - static typename aligned_storage<sizeof(T)>::type buf; - ::new (&buf) T(a0, a1); - return *reinterpret_cast<T*>(&buf); -} - -template <class T, class A0, class A1, class A2> -inline -T& -make(A0 a0, A1 a1, A2 a2) -{ - static typename aligned_storage<sizeof(T)>::type buf; - auto *obj = ::new (&buf) T(a0, a1, a2); - return *obj; -} - -template <typename T, size_t N> -inline -_LIBCPP_CONSTEXPR -size_t -countof(const T (&)[N]) -{ - return N; -} - -template <typename T> -inline -_LIBCPP_CONSTEXPR -size_t -countof(const T * const begin, const T * const end) -{ - return static_cast<size_t>(end - begin); -} - -_LIBCPP_NORETURN static void __throw_runtime_error(const string &msg) -{ -#ifndef _LIBCPP_NO_EXCEPTIONS - throw runtime_error(msg); -#else - (void)msg; - _VSTD::abort(); -#endif -} - -} - -#if defined(_AIX) -// Set priority to INT_MIN + 256 + 150 -# pragma priority ( -2147483242 ) -#endif - -const locale::category locale::none; -const locale::category locale::collate; -const locale::category locale::ctype; -const locale::category locale::monetary; -const locale::category locale::numeric; -const locale::category locale::time; -const locale::category locale::messages; -const locale::category locale::all; - -class _LIBCPP_HIDDEN locale::__imp - : public facet -{ - enum {N = 28}; -#if defined(_LIBCPP_COMPILER_MSVC) -// FIXME: MSVC doesn't support aligned parameters by value. -// I can't get the __sso_allocator to work here -// for MSVC I think for this reason. - vector<facet*> facets_; -#else - vector<facet*, __sso_allocator<facet*, N> > facets_; -#endif - string name_; -public: - explicit __imp(size_t refs = 0); - explicit __imp(const string& name, size_t refs = 0); - __imp(const __imp&); - __imp(const __imp&, const string&, locale::category c); - __imp(const __imp& other, const __imp& one, locale::category c); - __imp(const __imp&, facet* f, long id); - ~__imp(); - - const string& name() const {return name_;} - bool has_facet(long id) const - {return static_cast<size_t>(id) < facets_.size() && facets_[static_cast<size_t>(id)];} - const locale::facet* use_facet(long id) const; - - static const locale& make_classic(); - static locale& make_global(); -private: - void install(facet* f, long id); - template <class F> void install(F* f) {install(f, f->id.__get());} - template <class F> void install_from(const __imp& other); -}; - -locale::__imp::__imp(size_t refs) - : facet(refs), - facets_(N), - name_("C") -{ - facets_.clear(); - install(&make<_VSTD::collate<char> >(1u)); - install(&make<_VSTD::collate<wchar_t> >(1u)); - install(&make<_VSTD::ctype<char> >(nullptr, false, 1u)); - install(&make<_VSTD::ctype<wchar_t> >(1u)); - install(&make<codecvt<char, char, mbstate_t> >(1u)); - install(&make<codecvt<wchar_t, char, mbstate_t> >(1u)); - install(&make<codecvt<char16_t, char, mbstate_t> >(1u)); - install(&make<codecvt<char32_t, char, mbstate_t> >(1u)); - install(&make<numpunct<char> >(1u)); - install(&make<numpunct<wchar_t> >(1u)); - install(&make<num_get<char> >(1u)); - install(&make<num_get<wchar_t> >(1u)); - install(&make<num_put<char> >(1u)); - install(&make<num_put<wchar_t> >(1u)); - install(&make<moneypunct<char, false> >(1u)); - install(&make<moneypunct<char, true> >(1u)); - install(&make<moneypunct<wchar_t, false> >(1u)); - install(&make<moneypunct<wchar_t, true> >(1u)); - install(&make<money_get<char> >(1u)); - install(&make<money_get<wchar_t> >(1u)); - install(&make<money_put<char> >(1u)); - install(&make<money_put<wchar_t> >(1u)); - install(&make<time_get<char> >(1u)); - install(&make<time_get<wchar_t> >(1u)); - install(&make<time_put<char> >(1u)); - install(&make<time_put<wchar_t> >(1u)); - install(&make<_VSTD::messages<char> >(1u)); - install(&make<_VSTD::messages<wchar_t> >(1u)); -} - -locale::__imp::__imp(const string& name, size_t refs) - : facet(refs), - facets_(N), - name_(name) -{ -#ifndef _LIBCPP_NO_EXCEPTIONS - try - { -#endif // _LIBCPP_NO_EXCEPTIONS - facets_ = locale::classic().__locale_->facets_; - for (unsigned i = 0; i < facets_.size(); ++i) - if (facets_[i]) - facets_[i]->__add_shared(); - install(new collate_byname<char>(name_)); - install(new collate_byname<wchar_t>(name_)); - install(new ctype_byname<char>(name_)); - install(new ctype_byname<wchar_t>(name_)); - install(new codecvt_byname<char, char, mbstate_t>(name_)); - install(new codecvt_byname<wchar_t, char, mbstate_t>(name_)); - install(new codecvt_byname<char16_t, char, mbstate_t>(name_)); - install(new codecvt_byname<char32_t, char, mbstate_t>(name_)); - install(new numpunct_byname<char>(name_)); - install(new numpunct_byname<wchar_t>(name_)); - install(new moneypunct_byname<char, false>(name_)); - install(new moneypunct_byname<char, true>(name_)); - install(new moneypunct_byname<wchar_t, false>(name_)); - install(new moneypunct_byname<wchar_t, true>(name_)); - install(new time_get_byname<char>(name_)); - install(new time_get_byname<wchar_t>(name_)); - install(new time_put_byname<char>(name_)); - install(new time_put_byname<wchar_t>(name_)); - install(new messages_byname<char>(name_)); - install(new messages_byname<wchar_t>(name_)); -#ifndef _LIBCPP_NO_EXCEPTIONS - } - catch (...) - { - for (unsigned i = 0; i < facets_.size(); ++i) - if (facets_[i]) - facets_[i]->__release_shared(); - throw; - } -#endif // _LIBCPP_NO_EXCEPTIONS -} - -// NOTE avoid the `base class should be explicitly initialized in the -// copy constructor` warning emitted by GCC -#if defined(__clang__) || _GNUC_VER >= 406 -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wextra" -#endif - -locale::__imp::__imp(const __imp& other) - : facets_(max<size_t>(N, other.facets_.size())), - name_(other.name_) -{ - facets_ = other.facets_; - for (unsigned i = 0; i < facets_.size(); ++i) - if (facets_[i]) - facets_[i]->__add_shared(); -} - -#if defined(__clang__) || _GNUC_VER >= 406 -#pragma GCC diagnostic pop -#endif - -locale::__imp::__imp(const __imp& other, const string& name, locale::category c) - : facets_(N), - name_("*") -{ - facets_ = other.facets_; - for (unsigned i = 0; i < facets_.size(); ++i) - if (facets_[i]) - facets_[i]->__add_shared(); -#ifndef _LIBCPP_NO_EXCEPTIONS - try - { -#endif // _LIBCPP_NO_EXCEPTIONS - if (c & locale::collate) - { - install(new collate_byname<char>(name)); - install(new collate_byname<wchar_t>(name)); - } - if (c & locale::ctype) - { - install(new ctype_byname<char>(name)); - install(new ctype_byname<wchar_t>(name)); - install(new codecvt_byname<char, char, mbstate_t>(name)); - install(new codecvt_byname<wchar_t, char, mbstate_t>(name)); - install(new codecvt_byname<char16_t, char, mbstate_t>(name)); - install(new codecvt_byname<char32_t, char, mbstate_t>(name)); - } - if (c & locale::monetary) - { - install(new moneypunct_byname<char, false>(name)); - install(new moneypunct_byname<char, true>(name)); - install(new moneypunct_byname<wchar_t, false>(name)); - install(new moneypunct_byname<wchar_t, true>(name)); - } - if (c & locale::numeric) - { - install(new numpunct_byname<char>(name)); - install(new numpunct_byname<wchar_t>(name)); - } - if (c & locale::time) - { - install(new time_get_byname<char>(name)); - install(new time_get_byname<wchar_t>(name)); - install(new time_put_byname<char>(name)); - install(new time_put_byname<wchar_t>(name)); - } - if (c & locale::messages) - { - install(new messages_byname<char>(name)); - install(new messages_byname<wchar_t>(name)); - } -#ifndef _LIBCPP_NO_EXCEPTIONS - } - catch (...) - { - for (unsigned i = 0; i < facets_.size(); ++i) - if (facets_[i]) - facets_[i]->__release_shared(); - throw; - } -#endif // _LIBCPP_NO_EXCEPTIONS -} - -template<class F> -inline -void -locale::__imp::install_from(const locale::__imp& one) -{ - long id = F::id.__get(); - install(const_cast<F*>(static_cast<const F*>(one.use_facet(id))), id); -} - -locale::__imp::__imp(const __imp& other, const __imp& one, locale::category c) - : facets_(N), - name_("*") -{ - facets_ = other.facets_; - for (unsigned i = 0; i < facets_.size(); ++i) - if (facets_[i]) - facets_[i]->__add_shared(); -#ifndef _LIBCPP_NO_EXCEPTIONS - try - { -#endif // _LIBCPP_NO_EXCEPTIONS - if (c & locale::collate) - { - install_from<_VSTD::collate<char> >(one); - install_from<_VSTD::collate<wchar_t> >(one); - } - if (c & locale::ctype) - { - install_from<_VSTD::ctype<char> >(one); - install_from<_VSTD::ctype<wchar_t> >(one); - install_from<_VSTD::codecvt<char, char, mbstate_t> >(one); - install_from<_VSTD::codecvt<char16_t, char, mbstate_t> >(one); - install_from<_VSTD::codecvt<char32_t, char, mbstate_t> >(one); - install_from<_VSTD::codecvt<wchar_t, char, mbstate_t> >(one); - } - if (c & locale::monetary) - { - install_from<moneypunct<char, false> >(one); - install_from<moneypunct<char, true> >(one); - install_from<moneypunct<wchar_t, false> >(one); - install_from<moneypunct<wchar_t, true> >(one); - install_from<money_get<char> >(one); - install_from<money_get<wchar_t> >(one); - install_from<money_put<char> >(one); - install_from<money_put<wchar_t> >(one); - } - if (c & locale::numeric) - { - install_from<numpunct<char> >(one); - install_from<numpunct<wchar_t> >(one); - install_from<num_get<char> >(one); - install_from<num_get<wchar_t> >(one); - install_from<num_put<char> >(one); - install_from<num_put<wchar_t> >(one); - } - if (c & locale::time) - { - install_from<time_get<char> >(one); - install_from<time_get<wchar_t> >(one); - install_from<time_put<char> >(one); - install_from<time_put<wchar_t> >(one); - } - if (c & locale::messages) - { - install_from<_VSTD::messages<char> >(one); - install_from<_VSTD::messages<wchar_t> >(one); - } -#ifndef _LIBCPP_NO_EXCEPTIONS - } - catch (...) - { - for (unsigned i = 0; i < facets_.size(); ++i) - if (facets_[i]) - facets_[i]->__release_shared(); - throw; - } -#endif // _LIBCPP_NO_EXCEPTIONS -} - -locale::__imp::__imp(const __imp& other, facet* f, long id) - : facets_(max<size_t>(N, other.facets_.size()+1)), - name_("*") -{ - f->__add_shared(); - unique_ptr<facet, release> hold(f); - facets_ = other.facets_; - for (unsigned i = 0; i < other.facets_.size(); ++i) - if (facets_[i]) - facets_[i]->__add_shared(); - install(hold.get(), id); -} - -locale::__imp::~__imp() -{ - for (unsigned i = 0; i < facets_.size(); ++i) - if (facets_[i]) - facets_[i]->__release_shared(); -} - -void -locale::__imp::install(facet* f, long id) -{ - f->__add_shared(); - unique_ptr<facet, release> hold(f); - if (static_cast<size_t>(id) >= facets_.size()) - facets_.resize(static_cast<size_t>(id+1)); - if (facets_[static_cast<size_t>(id)]) - facets_[static_cast<size_t>(id)]->__release_shared(); - facets_[static_cast<size_t>(id)] = hold.release(); -} - -const locale::facet* -locale::__imp::use_facet(long id) const -{ -#ifndef _LIBCPP_NO_EXCEPTIONS - if (!has_facet(id)) - throw bad_cast(); -#endif // _LIBCPP_NO_EXCEPTIONS - return facets_[static_cast<size_t>(id)]; -} - -// locale - -const locale& -locale::__imp::make_classic() -{ - // only one thread can get in here and it only gets in once - static aligned_storage<sizeof(locale)>::type buf; - locale* c = reinterpret_cast<locale*>(&buf); - c->__locale_ = &make<__imp>(1u); - return *c; -} - -const locale& -locale::classic() -{ - static const locale& c = __imp::make_classic(); - return c; -} - -locale& -locale::__imp::make_global() -{ - // only one thread can get in here and it only gets in once - static aligned_storage<sizeof(locale)>::type buf; - auto *obj = ::new (&buf) locale(locale::classic()); - return *obj; -} - -locale& -locale::__global() -{ - static locale& g = __imp::make_global(); - return g; -} - -locale::locale() _NOEXCEPT - : __locale_(__global().__locale_) -{ - __locale_->__add_shared(); -} - -locale::locale(const locale& l) _NOEXCEPT - : __locale_(l.__locale_) -{ - __locale_->__add_shared(); -} - -locale::~locale() -{ - __locale_->__release_shared(); -} - -const locale& -locale::operator=(const locale& other) _NOEXCEPT -{ - other.__locale_->__add_shared(); - __locale_->__release_shared(); - __locale_ = other.__locale_; - return *this; -} - -locale::locale(const char* name) -#ifndef _LIBCPP_NO_EXCEPTIONS - : __locale_(name ? new __imp(name) - : throw runtime_error("locale constructed with null")) -#else // _LIBCPP_NO_EXCEPTIONS - : __locale_(new __imp(name)) -#endif -{ - __locale_->__add_shared(); -} - -locale::locale(const string& name) - : __locale_(new __imp(name)) -{ - __locale_->__add_shared(); -} - -locale::locale(const locale& other, const char* name, category c) -#ifndef _LIBCPP_NO_EXCEPTIONS - : __locale_(name ? new __imp(*other.__locale_, name, c) - : throw runtime_error("locale constructed with null")) -#else // _LIBCPP_NO_EXCEPTIONS - : __locale_(new __imp(*other.__locale_, name, c)) -#endif -{ - __locale_->__add_shared(); -} - -locale::locale(const locale& other, const string& name, category c) - : __locale_(new __imp(*other.__locale_, name, c)) -{ - __locale_->__add_shared(); -} - -locale::locale(const locale& other, const locale& one, category c) - : __locale_(new __imp(*other.__locale_, *one.__locale_, c)) -{ - __locale_->__add_shared(); -} - -string -locale::name() const -{ - return __locale_->name(); -} - -void -locale::__install_ctor(const locale& other, facet* f, long id) -{ - if (f) - __locale_ = new __imp(*other.__locale_, f, id); - else - __locale_ = other.__locale_; - __locale_->__add_shared(); -} - -locale -locale::global(const locale& loc) -{ - locale& g = __global(); - locale r = g; - g = loc; - if (g.name() != "*") - setlocale(LC_ALL, g.name().c_str()); - return r; -} - -bool -locale::has_facet(id& x) const -{ - return __locale_->has_facet(x.__get()); -} - -const locale::facet* -locale::use_facet(id& x) const -{ - return __locale_->use_facet(x.__get()); -} - -bool -locale::operator==(const locale& y) const -{ - return (__locale_ == y.__locale_) - || (__locale_->name() != "*" && __locale_->name() == y.__locale_->name()); -} - -// locale::facet - -locale::facet::~facet() -{ -} - -void -locale::facet::__on_zero_shared() _NOEXCEPT -{ - delete this; -} - -// locale::id - -int32_t locale::id::__next_id = 0; - -namespace -{ - -class __fake_bind -{ - locale::id* id_; - void (locale::id::* pmf_)(); -public: - __fake_bind(void (locale::id::* pmf)(), locale::id* id) - : id_(id), pmf_(pmf) {} - - void operator()() const - { - (id_->*pmf_)(); - } -}; - -} - -long -locale::id::__get() -{ - call_once(__flag_, __fake_bind(&locale::id::__init, this)); - return __id_ - 1; -} - -void -locale::id::__init() -{ - __id_ = __libcpp_atomic_add(&__next_id, 1); -} - -// template <> class collate_byname<char> - -collate_byname<char>::collate_byname(const char* n, size_t refs) - : collate<char>(refs), - __l(newlocale(LC_ALL_MASK, n, 0)) -{ - if (__l == 0) - __throw_runtime_error("collate_byname<char>::collate_byname" - " failed to construct for " + string(n)); -} - -collate_byname<char>::collate_byname(const string& name, size_t refs) - : collate<char>(refs), - __l(newlocale(LC_ALL_MASK, name.c_str(), 0)) -{ - if (__l == 0) - __throw_runtime_error("collate_byname<char>::collate_byname" - " failed to construct for " + name); -} - -collate_byname<char>::~collate_byname() -{ - freelocale(__l); -} - -int -collate_byname<char>::do_compare(const char_type* __lo1, const char_type* __hi1, - const char_type* __lo2, const char_type* __hi2) const -{ - string_type lhs(__lo1, __hi1); - string_type rhs(__lo2, __hi2); - int r = strcoll_l(lhs.c_str(), rhs.c_str(), __l); - if (r < 0) - return -1; - if (r > 0) - return 1; - return r; -} - -collate_byname<char>::string_type -collate_byname<char>::do_transform(const char_type* lo, const char_type* hi) const -{ - const string_type in(lo, hi); - string_type out(strxfrm_l(0, in.c_str(), 0, __l), char()); - strxfrm_l(const_cast<char*>(out.c_str()), in.c_str(), out.size()+1, __l); - return out; -} - -// template <> class collate_byname<wchar_t> - -collate_byname<wchar_t>::collate_byname(const char* n, size_t refs) - : collate<wchar_t>(refs), - __l(newlocale(LC_ALL_MASK, n, 0)) -{ - if (__l == 0) - __throw_runtime_error("collate_byname<wchar_t>::collate_byname(size_t refs)" - " failed to construct for " + string(n)); -} - -collate_byname<wchar_t>::collate_byname(const string& name, size_t refs) - : collate<wchar_t>(refs), - __l(newlocale(LC_ALL_MASK, name.c_str(), 0)) -{ - if (__l == 0) - __throw_runtime_error("collate_byname<wchar_t>::collate_byname(size_t refs)" - " failed to construct for " + name); -} - -collate_byname<wchar_t>::~collate_byname() -{ - freelocale(__l); -} - -int -collate_byname<wchar_t>::do_compare(const char_type* __lo1, const char_type* __hi1, - const char_type* __lo2, const char_type* __hi2) const -{ - string_type lhs(__lo1, __hi1); - string_type rhs(__lo2, __hi2); - int r = wcscoll_l(lhs.c_str(), rhs.c_str(), __l); - if (r < 0) - return -1; - if (r > 0) - return 1; - return r; -} - -collate_byname<wchar_t>::string_type -collate_byname<wchar_t>::do_transform(const char_type* lo, const char_type* hi) const -{ - const string_type in(lo, hi); - string_type out(wcsxfrm_l(0, in.c_str(), 0, __l), wchar_t()); - wcsxfrm_l(const_cast<wchar_t*>(out.c_str()), in.c_str(), out.size()+1, __l); - return out; -} - -// template <> class ctype<wchar_t>; - -const ctype_base::mask ctype_base::space; -const ctype_base::mask ctype_base::print; -const ctype_base::mask ctype_base::cntrl; -const ctype_base::mask ctype_base::upper; -const ctype_base::mask ctype_base::lower; -const ctype_base::mask ctype_base::alpha; -const ctype_base::mask ctype_base::digit; -const ctype_base::mask ctype_base::punct; -const ctype_base::mask ctype_base::xdigit; -const ctype_base::mask ctype_base::blank; -const ctype_base::mask ctype_base::alnum; -const ctype_base::mask ctype_base::graph; - -locale::id ctype<wchar_t>::id; - -ctype<wchar_t>::~ctype() -{ -} - -bool -ctype<wchar_t>::do_is(mask m, char_type c) const -{ - return isascii(c) ? (ctype<char>::classic_table()[c] & m) != 0 : false; -} - -const wchar_t* -ctype<wchar_t>::do_is(const char_type* low, const char_type* high, mask* vec) const -{ - for (; low != high; ++low, ++vec) - *vec = static_cast<mask>(isascii(*low) ? - ctype<char>::classic_table()[*low] : 0); - return low; -} - -const wchar_t* -ctype<wchar_t>::do_scan_is(mask m, const char_type* low, const char_type* high) const -{ - for (; low != high; ++low) - if (isascii(*low) && (ctype<char>::classic_table()[*low] & m)) - break; - return low; -} - -const wchar_t* -ctype<wchar_t>::do_scan_not(mask m, const char_type* low, const char_type* high) const -{ - for (; low != high; ++low) - if (!(isascii(*low) && (ctype<char>::classic_table()[*low] & m))) - break; - return low; -} - -wchar_t -ctype<wchar_t>::do_toupper(char_type c) const -{ -#ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE - return isascii(c) ? _DefaultRuneLocale.__mapupper[c] : c; -#elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) || \ - defined(__NetBSD__) - return isascii(c) ? ctype<char>::__classic_upper_table()[c] : c; -#else - return (isascii(c) && iswlower_l(c, _LIBCPP_GET_C_LOCALE)) ? c-L'a'+L'A' : c; -#endif -} - -const wchar_t* -ctype<wchar_t>::do_toupper(char_type* low, const char_type* high) const -{ - for (; low != high; ++low) -#ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE - *low = isascii(*low) ? _DefaultRuneLocale.__mapupper[*low] : *low; -#elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) || \ - defined(__NetBSD__) - *low = isascii(*low) ? ctype<char>::__classic_upper_table()[*low] - : *low; -#else - *low = (isascii(*low) && islower_l(*low, _LIBCPP_GET_C_LOCALE)) ? (*low-L'a'+L'A') : *low; -#endif - return low; -} - -wchar_t -ctype<wchar_t>::do_tolower(char_type c) const -{ -#ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE - return isascii(c) ? _DefaultRuneLocale.__maplower[c] : c; -#elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) || \ - defined(__NetBSD__) - return isascii(c) ? ctype<char>::__classic_lower_table()[c] : c; -#else - return (isascii(c) && isupper_l(c, _LIBCPP_GET_C_LOCALE)) ? c-L'A'+'a' : c; -#endif -} - -const wchar_t* -ctype<wchar_t>::do_tolower(char_type* low, const char_type* high) const -{ - for (; low != high; ++low) -#ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE - *low = isascii(*low) ? _DefaultRuneLocale.__maplower[*low] : *low; -#elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) || \ - defined(__NetBSD__) - *low = isascii(*low) ? ctype<char>::__classic_lower_table()[*low] - : *low; -#else - *low = (isascii(*low) && isupper_l(*low, _LIBCPP_GET_C_LOCALE)) ? *low-L'A'+L'a' : *low; -#endif - return low; -} - -wchar_t -ctype<wchar_t>::do_widen(char c) const -{ - return c; -} - -const char* -ctype<wchar_t>::do_widen(const char* low, const char* high, char_type* dest) const -{ - for (; low != high; ++low, ++dest) - *dest = *low; - return low; -} - -char -ctype<wchar_t>::do_narrow(char_type c, char dfault) const -{ - if (isascii(c)) - return static_cast<char>(c); - return dfault; -} - -const wchar_t* -ctype<wchar_t>::do_narrow(const char_type* low, const char_type* high, char dfault, char* dest) const -{ - for (; low != high; ++low, ++dest) - if (isascii(*low)) - *dest = static_cast<char>(*low); - else - *dest = dfault; - return low; -} - -// template <> class ctype<char>; - -locale::id ctype<char>::id; - -ctype<char>::ctype(const mask* tab, bool del, size_t refs) - : locale::facet(refs), - __tab_(tab), - __del_(del) -{ - if (__tab_ == 0) - __tab_ = classic_table(); -} - -ctype<char>::~ctype() -{ - if (__tab_ && __del_) - delete [] __tab_; -} - -char -ctype<char>::do_toupper(char_type c) const -{ -#ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE - return isascii(c) ? - static_cast<char>(_DefaultRuneLocale.__mapupper[static_cast<ptrdiff_t>(c)]) : c; -#elif defined(__NetBSD__) - return static_cast<char>(__classic_upper_table()[static_cast<unsigned char>(c)]); -#elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) - return isascii(c) ? - static_cast<char>(__classic_upper_table()[static_cast<unsigned char>(c)]) : c; -#else - return (isascii(c) && islower_l(c, _LIBCPP_GET_C_LOCALE)) ? c-'a'+'A' : c; -#endif -} - -const char* -ctype<char>::do_toupper(char_type* low, const char_type* high) const -{ - for (; low != high; ++low) -#ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE - *low = isascii(*low) ? - static_cast<char>(_DefaultRuneLocale.__mapupper[static_cast<ptrdiff_t>(*low)]) : *low; -#elif defined(__NetBSD__) - *low = static_cast<char>(__classic_upper_table()[static_cast<unsigned char>(*low)]); -#elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) - *low = isascii(*low) ? - static_cast<char>(__classic_upper_table()[static_cast<size_t>(*low)]) : *low; -#else - *low = (isascii(*low) && islower_l(*low, _LIBCPP_GET_C_LOCALE)) ? *low-'a'+'A' : *low; -#endif - return low; -} - -char -ctype<char>::do_tolower(char_type c) const -{ -#ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE - return isascii(c) ? - static_cast<char>(_DefaultRuneLocale.__maplower[static_cast<ptrdiff_t>(c)]) : c; -#elif defined(__NetBSD__) - return static_cast<char>(__classic_lower_table()[static_cast<unsigned char>(c)]); -#elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) - return isascii(c) ? - static_cast<char>(__classic_lower_table()[static_cast<size_t>(c)]) : c; -#else - return (isascii(c) && isupper_l(c, _LIBCPP_GET_C_LOCALE)) ? c-'A'+'a' : c; -#endif -} - -const char* -ctype<char>::do_tolower(char_type* low, const char_type* high) const -{ - for (; low != high; ++low) -#ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE - *low = isascii(*low) ? static_cast<char>(_DefaultRuneLocale.__maplower[static_cast<ptrdiff_t>(*low)]) : *low; -#elif defined(__NetBSD__) - *low = static_cast<char>(__classic_lower_table()[static_cast<unsigned char>(*low)]); -#elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) - *low = isascii(*low) ? static_cast<char>(__classic_lower_table()[static_cast<size_t>(*low)]) : *low; -#else - *low = (isascii(*low) && isupper_l(*low, _LIBCPP_GET_C_LOCALE)) ? *low-'A'+'a' : *low; -#endif - return low; -} - -char -ctype<char>::do_widen(char c) const -{ - return c; -} - -const char* -ctype<char>::do_widen(const char* low, const char* high, char_type* dest) const -{ - for (; low != high; ++low, ++dest) - *dest = *low; - return low; -} - -char -ctype<char>::do_narrow(char_type c, char dfault) const -{ - if (isascii(c)) - return static_cast<char>(c); - return dfault; -} - -const char* -ctype<char>::do_narrow(const char_type* low, const char_type* high, char dfault, char* dest) const -{ - for (; low != high; ++low, ++dest) - if (isascii(*low)) - *dest = *low; - else - *dest = dfault; - return low; -} - -#if defined(__EMSCRIPTEN__) -extern "C" const unsigned short ** __ctype_b_loc(); -extern "C" const int ** __ctype_tolower_loc(); -extern "C" const int ** __ctype_toupper_loc(); -#endif - -#ifdef _LIBCPP_PROVIDES_DEFAULT_RUNE_TABLE -const ctype<char>::mask* -ctype<char>::classic_table() _NOEXCEPT -{ - static _LIBCPP_CONSTEXPR const ctype<char>::mask builtin_table[table_size] = { - cntrl, cntrl, - cntrl, cntrl, - cntrl, cntrl, - cntrl, cntrl, - cntrl, cntrl | space | blank, - cntrl | space, cntrl | space, - cntrl | space, cntrl | space, - cntrl, cntrl, - cntrl, cntrl, - cntrl, cntrl, - cntrl, cntrl, - cntrl, cntrl, - cntrl, cntrl, - cntrl, cntrl, - cntrl, cntrl, - cntrl, cntrl, - space | blank | print, punct | print, - punct | print, punct | print, - punct | print, punct | print, - punct | print, punct | print, - punct | print, punct | print, - punct | print, punct | print, - punct | print, punct | print, - punct | print, punct | print, - digit | print | xdigit, digit | print | xdigit, - digit | print | xdigit, digit | print | xdigit, - digit | print | xdigit, digit | print | xdigit, - digit | print | xdigit, digit | print | xdigit, - digit | print | xdigit, digit | print | xdigit, - punct | print, punct | print, - punct | print, punct | print, - punct | print, punct | print, - punct | print, upper | xdigit | print | alpha, - upper | xdigit | print | alpha, upper | xdigit | print | alpha, - upper | xdigit | print | alpha, upper | xdigit | print | alpha, - upper | xdigit | print | alpha, upper | print | alpha, - upper | print | alpha, upper | print | alpha, - upper | print | alpha, upper | print | alpha, - upper | print | alpha, upper | print | alpha, - upper | print | alpha, upper | print | alpha, - upper | print | alpha, upper | print | alpha, - upper | print | alpha, upper | print | alpha, - upper | print | alpha, upper | print | alpha, - upper | print | alpha, upper | print | alpha, - upper | print | alpha, upper | print | alpha, - upper | print | alpha, punct | print, - punct | print, punct | print, - punct | print, punct | print, - punct | print, lower | xdigit | print | alpha, - lower | xdigit | print | alpha, lower | xdigit | print | alpha, - lower | xdigit | print | alpha, lower | xdigit | print | alpha, - lower | xdigit | print | alpha, lower | print | alpha, - lower | print | alpha, lower | print | alpha, - lower | print | alpha, lower | print | alpha, - lower | print | alpha, lower | print | alpha, - lower | print | alpha, lower | print | alpha, - lower | print | alpha, lower | print | alpha, - lower | print | alpha, lower | print | alpha, - lower | print | alpha, lower | print | alpha, - lower | print | alpha, lower | print | alpha, - lower | print | alpha, lower | print | alpha, - lower | print | alpha, punct | print, - punct | print, punct | print, - punct | print, cntrl, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 - }; - return builtin_table; -} -#else -const ctype<char>::mask* -ctype<char>::classic_table() _NOEXCEPT -{ -#if defined(__APPLE__) || defined(__FreeBSD__) - return _DefaultRuneLocale.__runetype; -#elif defined(__NetBSD__) - return _C_ctype_tab_ + 1; -#elif defined(__GLIBC__) - return _LIBCPP_GET_C_LOCALE->__ctype_b; -#elif __sun__ - return __ctype_mask; -#elif defined(_LIBCPP_MSVCRT) || defined(__MINGW32__) - return __pctype_func(); -#elif defined(__EMSCRIPTEN__) - return *__ctype_b_loc(); -#elif defined(_NEWLIB_VERSION) - // Newlib has a 257-entry table in ctype_.c, where (char)0 starts at [1]. - return _ctype_ + 1; -#elif defined(_AIX) - return (const unsigned int *)__lc_ctype_ptr->obj->mask; -#else - // Platform not supported: abort so the person doing the port knows what to - // fix -# warning ctype<char>::classic_table() is not implemented - printf("ctype<char>::classic_table() is not implemented\n"); - abort(); - return NULL; -#endif -} -#endif - -#if defined(__GLIBC__) -const int* -ctype<char>::__classic_lower_table() _NOEXCEPT -{ - return _LIBCPP_GET_C_LOCALE->__ctype_tolower; -} - -const int* -ctype<char>::__classic_upper_table() _NOEXCEPT -{ - return _LIBCPP_GET_C_LOCALE->__ctype_toupper; -} -#elif __NetBSD__ -const short* -ctype<char>::__classic_lower_table() _NOEXCEPT -{ - return _C_tolower_tab_ + 1; -} - -const short* -ctype<char>::__classic_upper_table() _NOEXCEPT -{ - return _C_toupper_tab_ + 1; -} - -#elif defined(__EMSCRIPTEN__) -const int* -ctype<char>::__classic_lower_table() _NOEXCEPT -{ - return *__ctype_tolower_loc(); -} - -const int* -ctype<char>::__classic_upper_table() _NOEXCEPT -{ - return *__ctype_toupper_loc(); -} -#endif // __GLIBC__ || __NETBSD__ || __EMSCRIPTEN__ - -// template <> class ctype_byname<char> - -ctype_byname<char>::ctype_byname(const char* name, size_t refs) - : ctype<char>(0, false, refs), - __l(newlocale(LC_ALL_MASK, name, 0)) -{ - if (__l == 0) - __throw_runtime_error("ctype_byname<char>::ctype_byname" - " failed to construct for " + string(name)); -} - -ctype_byname<char>::ctype_byname(const string& name, size_t refs) - : ctype<char>(0, false, refs), - __l(newlocale(LC_ALL_MASK, name.c_str(), 0)) -{ - if (__l == 0) - __throw_runtime_error("ctype_byname<char>::ctype_byname" - " failed to construct for " + name); -} - -ctype_byname<char>::~ctype_byname() -{ - freelocale(__l); -} - -char -ctype_byname<char>::do_toupper(char_type c) const -{ - return static_cast<char>(toupper_l(static_cast<unsigned char>(c), __l)); -} - -const char* -ctype_byname<char>::do_toupper(char_type* low, const char_type* high) const -{ - for (; low != high; ++low) - *low = static_cast<char>(toupper_l(static_cast<unsigned char>(*low), __l)); - return low; -} - -char -ctype_byname<char>::do_tolower(char_type c) const -{ - return static_cast<char>(tolower_l(static_cast<unsigned char>(c), __l)); -} - -const char* -ctype_byname<char>::do_tolower(char_type* low, const char_type* high) const -{ - for (; low != high; ++low) - *low = static_cast<char>(tolower_l(static_cast<unsigned char>(*low), __l)); - return low; -} - -// template <> class ctype_byname<wchar_t> - -ctype_byname<wchar_t>::ctype_byname(const char* name, size_t refs) - : ctype<wchar_t>(refs), - __l(newlocale(LC_ALL_MASK, name, 0)) -{ - if (__l == 0) - __throw_runtime_error("ctype_byname<wchar_t>::ctype_byname" - " failed to construct for " + string(name)); -} - -ctype_byname<wchar_t>::ctype_byname(const string& name, size_t refs) - : ctype<wchar_t>(refs), - __l(newlocale(LC_ALL_MASK, name.c_str(), 0)) -{ - if (__l == 0) - __throw_runtime_error("ctype_byname<wchar_t>::ctype_byname" - " failed to construct for " + name); -} - -ctype_byname<wchar_t>::~ctype_byname() -{ - freelocale(__l); -} - -bool -ctype_byname<wchar_t>::do_is(mask m, char_type c) const -{ -#ifdef _LIBCPP_WCTYPE_IS_MASK - return static_cast<bool>(iswctype_l(c, m, __l)); -#else - bool result = false; - wint_t ch = static_cast<wint_t>(c); - if ((m & space) == space) result |= (iswspace_l(ch, __l) != 0); - if ((m & print) == print) result |= (iswprint_l(ch, __l) != 0); - if ((m & cntrl) == cntrl) result |= (iswcntrl_l(ch, __l) != 0); - if ((m & upper) == upper) result |= (iswupper_l(ch, __l) != 0); - if ((m & lower) == lower) result |= (iswlower_l(ch, __l) != 0); - if ((m & alpha) == alpha) result |= (iswalpha_l(ch, __l) != 0); - if ((m & digit) == digit) result |= (iswdigit_l(ch, __l) != 0); - if ((m & punct) == punct) result |= (iswpunct_l(ch, __l) != 0); - if ((m & xdigit) == xdigit) result |= (iswxdigit_l(ch, __l) != 0); - if ((m & blank) == blank) result |= (iswblank_l(ch, __l) != 0); - return result; -#endif -} - -const wchar_t* -ctype_byname<wchar_t>::do_is(const char_type* low, const char_type* high, mask* vec) const -{ - for (; low != high; ++low, ++vec) - { - if (isascii(*low)) - *vec = static_cast<mask>(ctype<char>::classic_table()[*low]); - else - { - *vec = 0; - wint_t ch = static_cast<wint_t>(*low); - if (iswspace_l(ch, __l)) - *vec |= space; -#ifndef _LIBCPP_CTYPE_MASK_IS_COMPOSITE_PRINT - if (iswprint_l(ch, __l)) - *vec |= print; -#endif - if (iswcntrl_l(ch, __l)) - *vec |= cntrl; - if (iswupper_l(ch, __l)) - *vec |= upper; - if (iswlower_l(ch, __l)) - *vec |= lower; -#ifndef _LIBCPP_CTYPE_MASK_IS_COMPOSITE_ALPHA - if (iswalpha_l(ch, __l)) - *vec |= alpha; -#endif - if (iswdigit_l(ch, __l)) - *vec |= digit; - if (iswpunct_l(ch, __l)) - *vec |= punct; -#ifndef _LIBCPP_CTYPE_MASK_IS_COMPOSITE_XDIGIT - if (iswxdigit_l(ch, __l)) - *vec |= xdigit; -#endif -#if !defined(__sun__) - if (iswblank_l(ch, __l)) - *vec |= blank; -#endif - } - } - return low; -} - -const wchar_t* -ctype_byname<wchar_t>::do_scan_is(mask m, const char_type* low, const char_type* high) const -{ - for (; low != high; ++low) - { -#ifdef _LIBCPP_WCTYPE_IS_MASK - if (iswctype_l(*low, m, __l)) - break; -#else - wint_t ch = static_cast<wint_t>(*low); - if ((m & space) == space && iswspace_l(ch, __l)) break; - if ((m & print) == print && iswprint_l(ch, __l)) break; - if ((m & cntrl) == cntrl && iswcntrl_l(ch, __l)) break; - if ((m & upper) == upper && iswupper_l(ch, __l)) break; - if ((m & lower) == lower && iswlower_l(ch, __l)) break; - if ((m & alpha) == alpha && iswalpha_l(ch, __l)) break; - if ((m & digit) == digit && iswdigit_l(ch, __l)) break; - if ((m & punct) == punct && iswpunct_l(ch, __l)) break; - if ((m & xdigit) == xdigit && iswxdigit_l(ch, __l)) break; - if ((m & blank) == blank && iswblank_l(ch, __l)) break; -#endif - } - return low; -} - -const wchar_t* -ctype_byname<wchar_t>::do_scan_not(mask m, const char_type* low, const char_type* high) const -{ - for (; low != high; ++low) - { -#ifdef _LIBCPP_WCTYPE_IS_MASK - if (!iswctype_l(*low, m, __l)) - break; -#else - wint_t ch = static_cast<wint_t>(*low); - if ((m & space) == space && iswspace_l(ch, __l)) continue; - if ((m & print) == print && iswprint_l(ch, __l)) continue; - if ((m & cntrl) == cntrl && iswcntrl_l(ch, __l)) continue; - if ((m & upper) == upper && iswupper_l(ch, __l)) continue; - if ((m & lower) == lower && iswlower_l(ch, __l)) continue; - if ((m & alpha) == alpha && iswalpha_l(ch, __l)) continue; - if ((m & digit) == digit && iswdigit_l(ch, __l)) continue; - if ((m & punct) == punct && iswpunct_l(ch, __l)) continue; - if ((m & xdigit) == xdigit && iswxdigit_l(ch, __l)) continue; - if ((m & blank) == blank && iswblank_l(ch, __l)) continue; - break; -#endif - } - return low; -} - -wchar_t -ctype_byname<wchar_t>::do_toupper(char_type c) const -{ - return towupper_l(c, __l); -} - -const wchar_t* -ctype_byname<wchar_t>::do_toupper(char_type* low, const char_type* high) const -{ - for (; low != high; ++low) - *low = towupper_l(*low, __l); - return low; -} - -wchar_t -ctype_byname<wchar_t>::do_tolower(char_type c) const -{ - return towlower_l(c, __l); -} - -const wchar_t* -ctype_byname<wchar_t>::do_tolower(char_type* low, const char_type* high) const -{ - for (; low != high; ++low) - *low = towlower_l(*low, __l); - return low; -} - -wchar_t -ctype_byname<wchar_t>::do_widen(char c) const -{ - return __libcpp_btowc_l(c, __l); -} - -const char* -ctype_byname<wchar_t>::do_widen(const char* low, const char* high, char_type* dest) const -{ - for (; low != high; ++low, ++dest) - *dest = __libcpp_btowc_l(*low, __l); - return low; -} - -char -ctype_byname<wchar_t>::do_narrow(char_type c, char dfault) const -{ - int r = __libcpp_wctob_l(c, __l); - return r != static_cast<int>(WEOF) ? static_cast<char>(r) : dfault; -} - -const wchar_t* -ctype_byname<wchar_t>::do_narrow(const char_type* low, const char_type* high, char dfault, char* dest) const -{ - for (; low != high; ++low, ++dest) - { - int r = __libcpp_wctob_l(*low, __l); - *dest = r != static_cast<int>(WEOF) ? static_cast<char>(r) : dfault; - } - return low; -} - -// template <> class codecvt<char, char, mbstate_t> - -locale::id codecvt<char, char, mbstate_t>::id; - -codecvt<char, char, mbstate_t>::~codecvt() -{ -} - -codecvt<char, char, mbstate_t>::result -codecvt<char, char, mbstate_t>::do_out(state_type&, - const intern_type* frm, const intern_type*, const intern_type*& frm_nxt, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - frm_nxt = frm; - to_nxt = to; - return noconv; -} - -codecvt<char, char, mbstate_t>::result -codecvt<char, char, mbstate_t>::do_in(state_type&, - const extern_type* frm, const extern_type*, const extern_type*& frm_nxt, - intern_type* to, intern_type*, intern_type*& to_nxt) const -{ - frm_nxt = frm; - to_nxt = to; - return noconv; -} - -codecvt<char, char, mbstate_t>::result -codecvt<char, char, mbstate_t>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -codecvt<char, char, mbstate_t>::do_encoding() const _NOEXCEPT -{ - return 1; -} - -bool -codecvt<char, char, mbstate_t>::do_always_noconv() const _NOEXCEPT -{ - return true; -} - -int -codecvt<char, char, mbstate_t>::do_length(state_type&, - const extern_type* frm, const extern_type* end, size_t mx) const -{ - return static_cast<int>(min<size_t>(mx, static_cast<size_t>(end-frm))); -} - -int -codecvt<char, char, mbstate_t>::do_max_length() const _NOEXCEPT -{ - return 1; -} - -// template <> class codecvt<wchar_t, char, mbstate_t> - -locale::id codecvt<wchar_t, char, mbstate_t>::id; - -codecvt<wchar_t, char, mbstate_t>::codecvt(size_t refs) - : locale::facet(refs), - __l(_LIBCPP_GET_C_LOCALE) -{ -} - -codecvt<wchar_t, char, mbstate_t>::codecvt(const char* nm, size_t refs) - : locale::facet(refs), - __l(newlocale(LC_ALL_MASK, nm, 0)) -{ - if (__l == 0) - __throw_runtime_error("codecvt_byname<wchar_t, char, mbstate_t>::codecvt_byname" - " failed to construct for " + string(nm)); -} - -codecvt<wchar_t, char, mbstate_t>::~codecvt() -{ - if (__l != _LIBCPP_GET_C_LOCALE) - freelocale(__l); -} - -codecvt<wchar_t, char, mbstate_t>::result -codecvt<wchar_t, char, mbstate_t>::do_out(state_type& st, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - // look for first internal null in frm - const intern_type* fend = frm; - for (; fend != frm_end; ++fend) - if (*fend == 0) - break; - // loop over all null-terminated sequences in frm - to_nxt = to; - for (frm_nxt = frm; frm != frm_end && to != to_end; frm = frm_nxt, to = to_nxt) - { - // save state in case it is needed to recover to_nxt on error - mbstate_t save_state = st; - size_t n = __libcpp_wcsnrtombs_l(to, &frm_nxt, static_cast<size_t>(fend-frm), - static_cast<size_t>(to_end-to), &st, __l); - if (n == size_t(-1)) - { - // need to recover to_nxt - for (to_nxt = to; frm != frm_nxt; ++frm) - { - n = __libcpp_wcrtomb_l(to_nxt, *frm, &save_state, __l); - if (n == size_t(-1)) - break; - to_nxt += n; - } - frm_nxt = frm; - return error; - } - if (n == 0) - return partial; - to_nxt += n; - if (to_nxt == to_end) - break; - if (fend != frm_end) // set up next null terminated sequence - { - // Try to write the terminating null - extern_type tmp[MB_LEN_MAX]; - n = __libcpp_wcrtomb_l(tmp, intern_type(), &st, __l); - if (n == size_t(-1)) // on error - return error; - if (n > static_cast<size_t>(to_end-to_nxt)) // is there room? - return partial; - for (extern_type* p = tmp; n; --n) // write it - *to_nxt++ = *p++; - ++frm_nxt; - // look for next null in frm - for (fend = frm_nxt; fend != frm_end; ++fend) - if (*fend == 0) - break; - } - } - return frm_nxt == frm_end ? ok : partial; -} - -codecvt<wchar_t, char, mbstate_t>::result -codecvt<wchar_t, char, mbstate_t>::do_in(state_type& st, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - // look for first internal null in frm - const extern_type* fend = frm; - for (; fend != frm_end; ++fend) - if (*fend == 0) - break; - // loop over all null-terminated sequences in frm - to_nxt = to; - for (frm_nxt = frm; frm != frm_end && to != to_end; frm = frm_nxt, to = to_nxt) - { - // save state in case it is needed to recover to_nxt on error - mbstate_t save_state = st; - size_t n = __libcpp_mbsnrtowcs_l(to, &frm_nxt, static_cast<size_t>(fend-frm), - static_cast<size_t>(to_end-to), &st, __l); - if (n == size_t(-1)) - { - // need to recover to_nxt - for (to_nxt = to; frm != frm_nxt; ++to_nxt) - { - n = __libcpp_mbrtowc_l(to_nxt, frm, static_cast<size_t>(fend-frm), - &save_state, __l); - switch (n) - { - case 0: - ++frm; - break; - case size_t(-1): - frm_nxt = frm; - return error; - case size_t(-2): - frm_nxt = frm; - return partial; - default: - frm += n; - break; - } - } - frm_nxt = frm; - return frm_nxt == frm_end ? ok : partial; - } - if (n == size_t(-1)) - return error; - to_nxt += n; - if (to_nxt == to_end) - break; - if (fend != frm_end) // set up next null terminated sequence - { - // Try to write the terminating null - n = __libcpp_mbrtowc_l(to_nxt, frm_nxt, 1, &st, __l); - if (n != 0) // on error - return error; - ++to_nxt; - ++frm_nxt; - // look for next null in frm - for (fend = frm_nxt; fend != frm_end; ++fend) - if (*fend == 0) - break; - } - } - return frm_nxt == frm_end ? ok : partial; -} - -codecvt<wchar_t, char, mbstate_t>::result -codecvt<wchar_t, char, mbstate_t>::do_unshift(state_type& st, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - to_nxt = to; - extern_type tmp[MB_LEN_MAX]; - size_t n = __libcpp_wcrtomb_l(tmp, intern_type(), &st, __l); - if (n == size_t(-1) || n == 0) // on error - return error; - --n; - if (n > static_cast<size_t>(to_end-to_nxt)) // is there room? - return partial; - for (extern_type* p = tmp; n; --n) // write it - *to_nxt++ = *p++; - return ok; -} - -int -codecvt<wchar_t, char, mbstate_t>::do_encoding() const _NOEXCEPT -{ - if (__libcpp_mbtowc_l(nullptr, nullptr, MB_LEN_MAX, __l) != 0) - return -1; - - // stateless encoding - if (__l == 0 || __libcpp_mb_cur_max_l(__l) == 1) // there are no known constant length encodings - return 1; // which take more than 1 char to form a wchar_t - return 0; -} - -bool -codecvt<wchar_t, char, mbstate_t>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -codecvt<wchar_t, char, mbstate_t>::do_length(state_type& st, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - int nbytes = 0; - for (size_t nwchar_t = 0; nwchar_t < mx && frm != frm_end; ++nwchar_t) - { - size_t n = __libcpp_mbrlen_l(frm, static_cast<size_t>(frm_end-frm), &st, __l); - switch (n) - { - case 0: - ++nbytes; - ++frm; - break; - case size_t(-1): - case size_t(-2): - return nbytes; - default: - nbytes += n; - frm += n; - break; - } - } - return nbytes; -} - -int -codecvt<wchar_t, char, mbstate_t>::do_max_length() const _NOEXCEPT -{ - return __l == 0 ? 1 : static_cast<int>(__libcpp_mb_cur_max_l(__l)); -} - -// Valid UTF ranges -// UTF-32 UTF-16 UTF-8 # of code points -// first second first second third fourth -// 000000 - 00007F 0000 - 007F 00 - 7F 127 -// 000080 - 0007FF 0080 - 07FF C2 - DF, 80 - BF 1920 -// 000800 - 000FFF 0800 - 0FFF E0 - E0, A0 - BF, 80 - BF 2048 -// 001000 - 00CFFF 1000 - CFFF E1 - EC, 80 - BF, 80 - BF 49152 -// 00D000 - 00D7FF D000 - D7FF ED - ED, 80 - 9F, 80 - BF 2048 -// 00D800 - 00DFFF invalid -// 00E000 - 00FFFF E000 - FFFF EE - EF, 80 - BF, 80 - BF 8192 -// 010000 - 03FFFF D800 - D8BF, DC00 - DFFF F0 - F0, 90 - BF, 80 - BF, 80 - BF 196608 -// 040000 - 0FFFFF D8C0 - DBBF, DC00 - DFFF F1 - F3, 80 - BF, 80 - BF, 80 - BF 786432 -// 100000 - 10FFFF DBC0 - DBFF, DC00 - DFFF F4 - F4, 80 - 8F, 80 - BF, 80 - BF 65536 - -static -codecvt_base::result -utf16_to_utf8(const uint16_t* frm, const uint16_t* frm_end, const uint16_t*& frm_nxt, - uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & generate_header) - { - if (to_end-to_nxt < 3) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xEF); - *to_nxt++ = static_cast<uint8_t>(0xBB); - *to_nxt++ = static_cast<uint8_t>(0xBF); - } - for (; frm_nxt < frm_end; ++frm_nxt) - { - uint16_t wc1 = *frm_nxt; - if (wc1 > Maxcode) - return codecvt_base::error; - if (wc1 < 0x0080) - { - if (to_end-to_nxt < 1) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(wc1); - } - else if (wc1 < 0x0800) - { - if (to_end-to_nxt < 2) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xC0 | (wc1 >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc1 & 0x03F)); - } - else if (wc1 < 0xD800) - { - if (to_end-to_nxt < 3) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xE0 | (wc1 >> 12)); - *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc1 & 0x0FC0) >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc1 & 0x003F)); - } - else if (wc1 < 0xDC00) - { - if (frm_end-frm_nxt < 2) - return codecvt_base::partial; - uint16_t wc2 = frm_nxt[1]; - if ((wc2 & 0xFC00) != 0xDC00) - return codecvt_base::error; - if (to_end-to_nxt < 4) - return codecvt_base::partial; - if (((((wc1 & 0x03C0UL) >> 6) + 1) << 16) + - ((wc1 & 0x003FUL) << 10) + (wc2 & 0x03FF) > Maxcode) - return codecvt_base::error; - ++frm_nxt; - uint8_t z = ((wc1 & 0x03C0) >> 6) + 1; - *to_nxt++ = static_cast<uint8_t>(0xF0 | (z >> 2)); - *to_nxt++ = static_cast<uint8_t>(0x80 | ((z & 0x03) << 4) | ((wc1 & 0x003C) >> 2)); - *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc1 & 0x0003) << 4) | ((wc2 & 0x03C0) >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc2 & 0x003F)); - } - else if (wc1 < 0xE000) - { - return codecvt_base::error; - } - else - { - if (to_end-to_nxt < 3) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xE0 | (wc1 >> 12)); - *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc1 & 0x0FC0) >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc1 & 0x003F)); - } - } - return codecvt_base::ok; -} - -static -codecvt_base::result -utf16_to_utf8(const uint32_t* frm, const uint32_t* frm_end, const uint32_t*& frm_nxt, - uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & generate_header) - { - if (to_end-to_nxt < 3) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xEF); - *to_nxt++ = static_cast<uint8_t>(0xBB); - *to_nxt++ = static_cast<uint8_t>(0xBF); - } - for (; frm_nxt < frm_end; ++frm_nxt) - { - uint16_t wc1 = static_cast<uint16_t>(*frm_nxt); - if (wc1 > Maxcode) - return codecvt_base::error; - if (wc1 < 0x0080) - { - if (to_end-to_nxt < 1) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(wc1); - } - else if (wc1 < 0x0800) - { - if (to_end-to_nxt < 2) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xC0 | (wc1 >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc1 & 0x03F)); - } - else if (wc1 < 0xD800) - { - if (to_end-to_nxt < 3) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xE0 | (wc1 >> 12)); - *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc1 & 0x0FC0) >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc1 & 0x003F)); - } - else if (wc1 < 0xDC00) - { - if (frm_end-frm_nxt < 2) - return codecvt_base::partial; - uint16_t wc2 = static_cast<uint16_t>(frm_nxt[1]); - if ((wc2 & 0xFC00) != 0xDC00) - return codecvt_base::error; - if (to_end-to_nxt < 4) - return codecvt_base::partial; - if (((((wc1 & 0x03C0UL) >> 6) + 1) << 16) + - ((wc1 & 0x003FUL) << 10) + (wc2 & 0x03FF) > Maxcode) - return codecvt_base::error; - ++frm_nxt; - uint8_t z = ((wc1 & 0x03C0) >> 6) + 1; - *to_nxt++ = static_cast<uint8_t>(0xF0 | (z >> 2)); - *to_nxt++ = static_cast<uint8_t>(0x80 | ((z & 0x03) << 4) | ((wc1 & 0x003C) >> 2)); - *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc1 & 0x0003) << 4) | ((wc2 & 0x03C0) >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc2 & 0x003F)); - } - else if (wc1 < 0xE000) - { - return codecvt_base::error; - } - else - { - if (to_end-to_nxt < 3) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xE0 | (wc1 >> 12)); - *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc1 & 0x0FC0) >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc1 & 0x003F)); - } - } - return codecvt_base::ok; -} - -static -codecvt_base::result -utf8_to_utf16(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt, - uint16_t* to, uint16_t* to_end, uint16_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB && - frm_nxt[2] == 0xBF) - frm_nxt += 3; - } - for (; frm_nxt < frm_end && to_nxt < to_end; ++to_nxt) - { - uint8_t c1 = *frm_nxt; - if (c1 > Maxcode) - return codecvt_base::error; - if (c1 < 0x80) - { - *to_nxt = static_cast<uint16_t>(c1); - ++frm_nxt; - } - else if (c1 < 0xC2) - { - return codecvt_base::error; - } - else if (c1 < 0xE0) - { - if (frm_end-frm_nxt < 2) - return codecvt_base::partial; - uint8_t c2 = frm_nxt[1]; - if ((c2 & 0xC0) != 0x80) - return codecvt_base::error; - uint16_t t = static_cast<uint16_t>(((c1 & 0x1F) << 6) | (c2 & 0x3F)); - if (t > Maxcode) - return codecvt_base::error; - *to_nxt = t; - frm_nxt += 2; - } - else if (c1 < 0xF0) - { - if (frm_end-frm_nxt < 3) - return codecvt_base::partial; - uint8_t c2 = frm_nxt[1]; - uint8_t c3 = frm_nxt[2]; - switch (c1) - { - case 0xE0: - if ((c2 & 0xE0) != 0xA0) - return codecvt_base::error; - break; - case 0xED: - if ((c2 & 0xE0) != 0x80) - return codecvt_base::error; - break; - default: - if ((c2 & 0xC0) != 0x80) - return codecvt_base::error; - break; - } - if ((c3 & 0xC0) != 0x80) - return codecvt_base::error; - uint16_t t = static_cast<uint16_t>(((c1 & 0x0F) << 12) - | ((c2 & 0x3F) << 6) - | (c3 & 0x3F)); - if (t > Maxcode) - return codecvt_base::error; - *to_nxt = t; - frm_nxt += 3; - } - else if (c1 < 0xF5) - { - if (frm_end-frm_nxt < 4) - return codecvt_base::partial; - uint8_t c2 = frm_nxt[1]; - uint8_t c3 = frm_nxt[2]; - uint8_t c4 = frm_nxt[3]; - switch (c1) - { - case 0xF0: - if (!(0x90 <= c2 && c2 <= 0xBF)) - return codecvt_base::error; - break; - case 0xF4: - if ((c2 & 0xF0) != 0x80) - return codecvt_base::error; - break; - default: - if ((c2 & 0xC0) != 0x80) - return codecvt_base::error; - break; - } - if ((c3 & 0xC0) != 0x80 || (c4 & 0xC0) != 0x80) - return codecvt_base::error; - if (to_end-to_nxt < 2) - return codecvt_base::partial; - if ((((c1 & 7UL) << 18) + - ((c2 & 0x3FUL) << 12) + - ((c3 & 0x3FUL) << 6) + (c4 & 0x3F)) > Maxcode) - return codecvt_base::error; - *to_nxt = static_cast<uint16_t>( - 0xD800 - | (((((c1 & 0x07) << 2) | ((c2 & 0x30) >> 4)) - 1) << 6) - | ((c2 & 0x0F) << 2) - | ((c3 & 0x30) >> 4)); - *++to_nxt = static_cast<uint16_t>( - 0xDC00 - | ((c3 & 0x0F) << 6) - | (c4 & 0x3F)); - frm_nxt += 4; - } - else - { - return codecvt_base::error; - } - } - return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok; -} - -static -codecvt_base::result -utf8_to_utf16(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt, - uint32_t* to, uint32_t* to_end, uint32_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB && - frm_nxt[2] == 0xBF) - frm_nxt += 3; - } - for (; frm_nxt < frm_end && to_nxt < to_end; ++to_nxt) - { - uint8_t c1 = *frm_nxt; - if (c1 > Maxcode) - return codecvt_base::error; - if (c1 < 0x80) - { - *to_nxt = static_cast<uint32_t>(c1); - ++frm_nxt; - } - else if (c1 < 0xC2) - { - return codecvt_base::error; - } - else if (c1 < 0xE0) - { - if (frm_end-frm_nxt < 2) - return codecvt_base::partial; - uint8_t c2 = frm_nxt[1]; - if ((c2 & 0xC0) != 0x80) - return codecvt_base::error; - uint16_t t = static_cast<uint16_t>(((c1 & 0x1F) << 6) | (c2 & 0x3F)); - if (t > Maxcode) - return codecvt_base::error; - *to_nxt = static_cast<uint32_t>(t); - frm_nxt += 2; - } - else if (c1 < 0xF0) - { - if (frm_end-frm_nxt < 3) - return codecvt_base::partial; - uint8_t c2 = frm_nxt[1]; - uint8_t c3 = frm_nxt[2]; - switch (c1) - { - case 0xE0: - if ((c2 & 0xE0) != 0xA0) - return codecvt_base::error; - break; - case 0xED: - if ((c2 & 0xE0) != 0x80) - return codecvt_base::error; - break; - default: - if ((c2 & 0xC0) != 0x80) - return codecvt_base::error; - break; - } - if ((c3 & 0xC0) != 0x80) - return codecvt_base::error; - uint16_t t = static_cast<uint16_t>(((c1 & 0x0F) << 12) - | ((c2 & 0x3F) << 6) - | (c3 & 0x3F)); - if (t > Maxcode) - return codecvt_base::error; - *to_nxt = static_cast<uint32_t>(t); - frm_nxt += 3; - } - else if (c1 < 0xF5) - { - if (frm_end-frm_nxt < 4) - return codecvt_base::partial; - uint8_t c2 = frm_nxt[1]; - uint8_t c3 = frm_nxt[2]; - uint8_t c4 = frm_nxt[3]; - switch (c1) - { - case 0xF0: - if (!(0x90 <= c2 && c2 <= 0xBF)) - return codecvt_base::error; - break; - case 0xF4: - if ((c2 & 0xF0) != 0x80) - return codecvt_base::error; - break; - default: - if ((c2 & 0xC0) != 0x80) - return codecvt_base::error; - break; - } - if ((c3 & 0xC0) != 0x80 || (c4 & 0xC0) != 0x80) - return codecvt_base::error; - if (to_end-to_nxt < 2) - return codecvt_base::partial; - if ((((c1 & 7UL) << 18) + - ((c2 & 0x3FUL) << 12) + - ((c3 & 0x3FUL) << 6) + (c4 & 0x3F)) > Maxcode) - return codecvt_base::error; - *to_nxt = static_cast<uint32_t>( - 0xD800 - | (((((c1 & 0x07) << 2) | ((c2 & 0x30) >> 4)) - 1) << 6) - | ((c2 & 0x0F) << 2) - | ((c3 & 0x30) >> 4)); - *++to_nxt = static_cast<uint32_t>( - 0xDC00 - | ((c3 & 0x0F) << 6) - | (c4 & 0x3F)); - frm_nxt += 4; - } - else - { - return codecvt_base::error; - } - } - return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok; -} - -static -int -utf8_to_utf16_length(const uint8_t* frm, const uint8_t* frm_end, - size_t mx, unsigned long Maxcode = 0x10FFFF, - codecvt_mode mode = codecvt_mode(0)) -{ - const uint8_t* frm_nxt = frm; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB && - frm_nxt[2] == 0xBF) - frm_nxt += 3; - } - for (size_t nchar16_t = 0; frm_nxt < frm_end && nchar16_t < mx; ++nchar16_t) - { - uint8_t c1 = *frm_nxt; - if (c1 > Maxcode) - break; - if (c1 < 0x80) - { - ++frm_nxt; - } - else if (c1 < 0xC2) - { - break; - } - else if (c1 < 0xE0) - { - if ((frm_end-frm_nxt < 2) || (frm_nxt[1] & 0xC0) != 0x80) - break; - uint16_t t = static_cast<uint16_t>(((c1 & 0x1F) << 6) | (frm_nxt[1] & 0x3F)); - if (t > Maxcode) - break; - frm_nxt += 2; - } - else if (c1 < 0xF0) - { - if (frm_end-frm_nxt < 3) - break; - uint8_t c2 = frm_nxt[1]; - uint8_t c3 = frm_nxt[2]; - switch (c1) - { - case 0xE0: - if ((c2 & 0xE0) != 0xA0) - return static_cast<int>(frm_nxt - frm); - break; - case 0xED: - if ((c2 & 0xE0) != 0x80) - return static_cast<int>(frm_nxt - frm); - break; - default: - if ((c2 & 0xC0) != 0x80) - return static_cast<int>(frm_nxt - frm); - break; - } - if ((c3 & 0xC0) != 0x80) - break; - if ((((c1 & 0x0Fu) << 12) | ((c2 & 0x3Fu) << 6) | (c3 & 0x3Fu)) > Maxcode) - break; - frm_nxt += 3; - } - else if (c1 < 0xF5) - { - if (frm_end-frm_nxt < 4 || mx-nchar16_t < 2) - break; - uint8_t c2 = frm_nxt[1]; - uint8_t c3 = frm_nxt[2]; - uint8_t c4 = frm_nxt[3]; - switch (c1) - { - case 0xF0: - if (!(0x90 <= c2 && c2 <= 0xBF)) - return static_cast<int>(frm_nxt - frm); - break; - case 0xF4: - if ((c2 & 0xF0) != 0x80) - return static_cast<int>(frm_nxt - frm); - break; - default: - if ((c2 & 0xC0) != 0x80) - return static_cast<int>(frm_nxt - frm); - break; - } - if ((c3 & 0xC0) != 0x80 || (c4 & 0xC0) != 0x80) - break; - if ((((c1 & 7UL) << 18) + - ((c2 & 0x3FUL) << 12) + - ((c3 & 0x3FUL) << 6) + (c4 & 0x3F)) > Maxcode) - break; - ++nchar16_t; - frm_nxt += 4; - } - else - { - break; - } - } - return static_cast<int>(frm_nxt - frm); -} - -static -codecvt_base::result -ucs4_to_utf8(const uint32_t* frm, const uint32_t* frm_end, const uint32_t*& frm_nxt, - uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & generate_header) - { - if (to_end-to_nxt < 3) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xEF); - *to_nxt++ = static_cast<uint8_t>(0xBB); - *to_nxt++ = static_cast<uint8_t>(0xBF); - } - for (; frm_nxt < frm_end; ++frm_nxt) - { - uint32_t wc = *frm_nxt; - if ((wc & 0xFFFFF800) == 0x00D800 || wc > Maxcode) - return codecvt_base::error; - if (wc < 0x000080) - { - if (to_end-to_nxt < 1) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(wc); - } - else if (wc < 0x000800) - { - if (to_end-to_nxt < 2) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xC0 | (wc >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc & 0x03F)); - } - else if (wc < 0x010000) - { - if (to_end-to_nxt < 3) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xE0 | (wc >> 12)); - *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc & 0x0FC0) >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc & 0x003F)); - } - else // if (wc < 0x110000) - { - if (to_end-to_nxt < 4) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xF0 | (wc >> 18)); - *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc & 0x03F000) >> 12)); - *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc & 0x000FC0) >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc & 0x00003F)); - } - } - return codecvt_base::ok; -} - -static -codecvt_base::result -utf8_to_ucs4(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt, - uint32_t* to, uint32_t* to_end, uint32_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB && - frm_nxt[2] == 0xBF) - frm_nxt += 3; - } - for (; frm_nxt < frm_end && to_nxt < to_end; ++to_nxt) - { - uint8_t c1 = static_cast<uint8_t>(*frm_nxt); - if (c1 < 0x80) - { - if (c1 > Maxcode) - return codecvt_base::error; - *to_nxt = static_cast<uint32_t>(c1); - ++frm_nxt; - } - else if (c1 < 0xC2) - { - return codecvt_base::error; - } - else if (c1 < 0xE0) - { - if (frm_end-frm_nxt < 2) - return codecvt_base::partial; - uint8_t c2 = frm_nxt[1]; - if ((c2 & 0xC0) != 0x80) - return codecvt_base::error; - uint32_t t = static_cast<uint32_t>(((c1 & 0x1F) << 6) - | (c2 & 0x3F)); - if (t > Maxcode) - return codecvt_base::error; - *to_nxt = t; - frm_nxt += 2; - } - else if (c1 < 0xF0) - { - if (frm_end-frm_nxt < 3) - return codecvt_base::partial; - uint8_t c2 = frm_nxt[1]; - uint8_t c3 = frm_nxt[2]; - switch (c1) - { - case 0xE0: - if ((c2 & 0xE0) != 0xA0) - return codecvt_base::error; - break; - case 0xED: - if ((c2 & 0xE0) != 0x80) - return codecvt_base::error; - break; - default: - if ((c2 & 0xC0) != 0x80) - return codecvt_base::error; - break; - } - if ((c3 & 0xC0) != 0x80) - return codecvt_base::error; - uint32_t t = static_cast<uint32_t>(((c1 & 0x0F) << 12) - | ((c2 & 0x3F) << 6) - | (c3 & 0x3F)); - if (t > Maxcode) - return codecvt_base::error; - *to_nxt = t; - frm_nxt += 3; - } - else if (c1 < 0xF5) - { - if (frm_end-frm_nxt < 4) - return codecvt_base::partial; - uint8_t c2 = frm_nxt[1]; - uint8_t c3 = frm_nxt[2]; - uint8_t c4 = frm_nxt[3]; - switch (c1) - { - case 0xF0: - if (!(0x90 <= c2 && c2 <= 0xBF)) - return codecvt_base::error; - break; - case 0xF4: - if ((c2 & 0xF0) != 0x80) - return codecvt_base::error; - break; - default: - if ((c2 & 0xC0) != 0x80) - return codecvt_base::error; - break; - } - if ((c3 & 0xC0) != 0x80 || (c4 & 0xC0) != 0x80) - return codecvt_base::error; - uint32_t t = static_cast<uint32_t>(((c1 & 0x07) << 18) - | ((c2 & 0x3F) << 12) - | ((c3 & 0x3F) << 6) - | (c4 & 0x3F)); - if (t > Maxcode) - return codecvt_base::error; - *to_nxt = t; - frm_nxt += 4; - } - else - { - return codecvt_base::error; - } - } - return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok; -} - -static -int -utf8_to_ucs4_length(const uint8_t* frm, const uint8_t* frm_end, - size_t mx, unsigned long Maxcode = 0x10FFFF, - codecvt_mode mode = codecvt_mode(0)) -{ - const uint8_t* frm_nxt = frm; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB && - frm_nxt[2] == 0xBF) - frm_nxt += 3; - } - for (size_t nchar32_t = 0; frm_nxt < frm_end && nchar32_t < mx; ++nchar32_t) - { - uint8_t c1 = static_cast<uint8_t>(*frm_nxt); - if (c1 < 0x80) - { - if (c1 > Maxcode) - break; - ++frm_nxt; - } - else if (c1 < 0xC2) - { - break; - } - else if (c1 < 0xE0) - { - if ((frm_end-frm_nxt < 2) || ((frm_nxt[1] & 0xC0) != 0x80)) - break; - if ((((c1 & 0x1Fu) << 6) | (frm_nxt[1] & 0x3Fu)) > Maxcode) - break; - frm_nxt += 2; - } - else if (c1 < 0xF0) - { - if (frm_end-frm_nxt < 3) - break; - uint8_t c2 = frm_nxt[1]; - uint8_t c3 = frm_nxt[2]; - switch (c1) - { - case 0xE0: - if ((c2 & 0xE0) != 0xA0) - return static_cast<int>(frm_nxt - frm); - break; - case 0xED: - if ((c2 & 0xE0) != 0x80) - return static_cast<int>(frm_nxt - frm); - break; - default: - if ((c2 & 0xC0) != 0x80) - return static_cast<int>(frm_nxt - frm); - break; - } - if ((c3 & 0xC0) != 0x80) - break; - if ((((c1 & 0x0Fu) << 12) | ((c2 & 0x3Fu) << 6) | (c3 & 0x3Fu)) > Maxcode) - break; - frm_nxt += 3; - } - else if (c1 < 0xF5) - { - if (frm_end-frm_nxt < 4) - break; - uint8_t c2 = frm_nxt[1]; - uint8_t c3 = frm_nxt[2]; - uint8_t c4 = frm_nxt[3]; - switch (c1) - { - case 0xF0: - if (!(0x90 <= c2 && c2 <= 0xBF)) - return static_cast<int>(frm_nxt - frm); - break; - case 0xF4: - if ((c2 & 0xF0) != 0x80) - return static_cast<int>(frm_nxt - frm); - break; - default: - if ((c2 & 0xC0) != 0x80) - return static_cast<int>(frm_nxt - frm); - break; - } - if ((c3 & 0xC0) != 0x80 || (c4 & 0xC0) != 0x80) - break; - if ((((c1 & 0x07u) << 18) | ((c2 & 0x3Fu) << 12) | - ((c3 & 0x3Fu) << 6) | (c4 & 0x3Fu)) > Maxcode) - break; - frm_nxt += 4; - } - else - { - break; - } - } - return static_cast<int>(frm_nxt - frm); -} - -static -codecvt_base::result -ucs2_to_utf8(const uint16_t* frm, const uint16_t* frm_end, const uint16_t*& frm_nxt, - uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & generate_header) - { - if (to_end-to_nxt < 3) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xEF); - *to_nxt++ = static_cast<uint8_t>(0xBB); - *to_nxt++ = static_cast<uint8_t>(0xBF); - } - for (; frm_nxt < frm_end; ++frm_nxt) - { - uint16_t wc = *frm_nxt; - if ((wc & 0xF800) == 0xD800 || wc > Maxcode) - return codecvt_base::error; - if (wc < 0x0080) - { - if (to_end-to_nxt < 1) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(wc); - } - else if (wc < 0x0800) - { - if (to_end-to_nxt < 2) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xC0 | (wc >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc & 0x03F)); - } - else // if (wc <= 0xFFFF) - { - if (to_end-to_nxt < 3) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xE0 | (wc >> 12)); - *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc & 0x0FC0) >> 6)); - *to_nxt++ = static_cast<uint8_t>(0x80 | (wc & 0x003F)); - } - } - return codecvt_base::ok; -} - -static -codecvt_base::result -utf8_to_ucs2(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt, - uint16_t* to, uint16_t* to_end, uint16_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB && - frm_nxt[2] == 0xBF) - frm_nxt += 3; - } - for (; frm_nxt < frm_end && to_nxt < to_end; ++to_nxt) - { - uint8_t c1 = static_cast<uint8_t>(*frm_nxt); - if (c1 < 0x80) - { - if (c1 > Maxcode) - return codecvt_base::error; - *to_nxt = static_cast<uint16_t>(c1); - ++frm_nxt; - } - else if (c1 < 0xC2) - { - return codecvt_base::error; - } - else if (c1 < 0xE0) - { - if (frm_end-frm_nxt < 2) - return codecvt_base::partial; - uint8_t c2 = frm_nxt[1]; - if ((c2 & 0xC0) != 0x80) - return codecvt_base::error; - uint16_t t = static_cast<uint16_t>(((c1 & 0x1F) << 6) - | (c2 & 0x3F)); - if (t > Maxcode) - return codecvt_base::error; - *to_nxt = t; - frm_nxt += 2; - } - else if (c1 < 0xF0) - { - if (frm_end-frm_nxt < 3) - return codecvt_base::partial; - uint8_t c2 = frm_nxt[1]; - uint8_t c3 = frm_nxt[2]; - switch (c1) - { - case 0xE0: - if ((c2 & 0xE0) != 0xA0) - return codecvt_base::error; - break; - case 0xED: - if ((c2 & 0xE0) != 0x80) - return codecvt_base::error; - break; - default: - if ((c2 & 0xC0) != 0x80) - return codecvt_base::error; - break; - } - if ((c3 & 0xC0) != 0x80) - return codecvt_base::error; - uint16_t t = static_cast<uint16_t>(((c1 & 0x0F) << 12) - | ((c2 & 0x3F) << 6) - | (c3 & 0x3F)); - if (t > Maxcode) - return codecvt_base::error; - *to_nxt = t; - frm_nxt += 3; - } - else - { - return codecvt_base::error; - } - } - return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok; -} - -static -int -utf8_to_ucs2_length(const uint8_t* frm, const uint8_t* frm_end, - size_t mx, unsigned long Maxcode = 0x10FFFF, - codecvt_mode mode = codecvt_mode(0)) -{ - const uint8_t* frm_nxt = frm; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB && - frm_nxt[2] == 0xBF) - frm_nxt += 3; - } - for (size_t nchar32_t = 0; frm_nxt < frm_end && nchar32_t < mx; ++nchar32_t) - { - uint8_t c1 = static_cast<uint8_t>(*frm_nxt); - if (c1 < 0x80) - { - if (c1 > Maxcode) - break; - ++frm_nxt; - } - else if (c1 < 0xC2) - { - break; - } - else if (c1 < 0xE0) - { - if ((frm_end-frm_nxt < 2) || ((frm_nxt[1] & 0xC0) != 0x80)) - break; - if ((((c1 & 0x1Fu) << 6) | (frm_nxt[1] & 0x3Fu)) > Maxcode) - break; - frm_nxt += 2; - } - else if (c1 < 0xF0) - { - if (frm_end-frm_nxt < 3) - break; - uint8_t c2 = frm_nxt[1]; - uint8_t c3 = frm_nxt[2]; - switch (c1) - { - case 0xE0: - if ((c2 & 0xE0) != 0xA0) - return static_cast<int>(frm_nxt - frm); - break; - case 0xED: - if ((c2 & 0xE0) != 0x80) - return static_cast<int>(frm_nxt - frm); - break; - default: - if ((c2 & 0xC0) != 0x80) - return static_cast<int>(frm_nxt - frm); - break; - } - if ((c3 & 0xC0) != 0x80) - break; - if ((((c1 & 0x0Fu) << 12) | ((c2 & 0x3Fu) << 6) | (c3 & 0x3Fu)) > Maxcode) - break; - frm_nxt += 3; - } - else - { - break; - } - } - return static_cast<int>(frm_nxt - frm); -} - -static -codecvt_base::result -ucs4_to_utf16be(const uint32_t* frm, const uint32_t* frm_end, const uint32_t*& frm_nxt, - uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & generate_header) - { - if (to_end-to_nxt < 2) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xFE); - *to_nxt++ = static_cast<uint8_t>(0xFF); - } - for (; frm_nxt < frm_end; ++frm_nxt) - { - uint32_t wc = *frm_nxt; - if ((wc & 0xFFFFF800) == 0x00D800 || wc > Maxcode) - return codecvt_base::error; - if (wc < 0x010000) - { - if (to_end-to_nxt < 2) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(wc >> 8); - *to_nxt++ = static_cast<uint8_t>(wc); - } - else - { - if (to_end-to_nxt < 4) - return codecvt_base::partial; - uint16_t t = static_cast<uint16_t>( - 0xD800 - | ((((wc & 0x1F0000) >> 16) - 1) << 6) - | ((wc & 0x00FC00) >> 10)); - *to_nxt++ = static_cast<uint8_t>(t >> 8); - *to_nxt++ = static_cast<uint8_t>(t); - t = static_cast<uint16_t>(0xDC00 | (wc & 0x03FF)); - *to_nxt++ = static_cast<uint8_t>(t >> 8); - *to_nxt++ = static_cast<uint8_t>(t); - } - } - return codecvt_base::ok; -} - -static -codecvt_base::result -utf16be_to_ucs4(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt, - uint32_t* to, uint32_t* to_end, uint32_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFE && frm_nxt[1] == 0xFF) - frm_nxt += 2; - } - for (; frm_nxt < frm_end - 1 && to_nxt < to_end; ++to_nxt) - { - uint16_t c1 = static_cast<uint16_t>(frm_nxt[0] << 8 | frm_nxt[1]); - if ((c1 & 0xFC00) == 0xDC00) - return codecvt_base::error; - if ((c1 & 0xFC00) != 0xD800) - { - if (c1 > Maxcode) - return codecvt_base::error; - *to_nxt = static_cast<uint32_t>(c1); - frm_nxt += 2; - } - else - { - if (frm_end-frm_nxt < 4) - return codecvt_base::partial; - uint16_t c2 = static_cast<uint16_t>(frm_nxt[2] << 8 | frm_nxt[3]); - if ((c2 & 0xFC00) != 0xDC00) - return codecvt_base::error; - uint32_t t = static_cast<uint32_t>( - ((((c1 & 0x03C0) >> 6) + 1) << 16) - | ((c1 & 0x003F) << 10) - | (c2 & 0x03FF)); - if (t > Maxcode) - return codecvt_base::error; - *to_nxt = t; - frm_nxt += 4; - } - } - return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok; -} - -static -int -utf16be_to_ucs4_length(const uint8_t* frm, const uint8_t* frm_end, - size_t mx, unsigned long Maxcode = 0x10FFFF, - codecvt_mode mode = codecvt_mode(0)) -{ - const uint8_t* frm_nxt = frm; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFE && frm_nxt[1] == 0xFF) - frm_nxt += 2; - } - for (size_t nchar32_t = 0; frm_nxt < frm_end - 1 && nchar32_t < mx; ++nchar32_t) - { - uint16_t c1 = static_cast<uint16_t>(frm_nxt[0] << 8 | frm_nxt[1]); - if ((c1 & 0xFC00) == 0xDC00) - break; - if ((c1 & 0xFC00) != 0xD800) - { - if (c1 > Maxcode) - break; - frm_nxt += 2; - } - else - { - if (frm_end-frm_nxt < 4) - break; - uint16_t c2 = static_cast<uint16_t>(frm_nxt[2] << 8 | frm_nxt[3]); - if ((c2 & 0xFC00) != 0xDC00) - break; - uint32_t t = static_cast<uint32_t>( - ((((c1 & 0x03C0) >> 6) + 1) << 16) - | ((c1 & 0x003F) << 10) - | (c2 & 0x03FF)); - if (t > Maxcode) - break; - frm_nxt += 4; - } - } - return static_cast<int>(frm_nxt - frm); -} - -static -codecvt_base::result -ucs4_to_utf16le(const uint32_t* frm, const uint32_t* frm_end, const uint32_t*& frm_nxt, - uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & generate_header) - { - if (to_end - to_nxt < 2) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xFF); - *to_nxt++ = static_cast<uint8_t>(0xFE); - } - for (; frm_nxt < frm_end; ++frm_nxt) - { - uint32_t wc = *frm_nxt; - if ((wc & 0xFFFFF800) == 0x00D800 || wc > Maxcode) - return codecvt_base::error; - if (wc < 0x010000) - { - if (to_end-to_nxt < 2) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(wc); - *to_nxt++ = static_cast<uint8_t>(wc >> 8); - } - else - { - if (to_end-to_nxt < 4) - return codecvt_base::partial; - uint16_t t = static_cast<uint16_t>( - 0xD800 - | ((((wc & 0x1F0000) >> 16) - 1) << 6) - | ((wc & 0x00FC00) >> 10)); - *to_nxt++ = static_cast<uint8_t>(t); - *to_nxt++ = static_cast<uint8_t>(t >> 8); - t = static_cast<uint16_t>(0xDC00 | (wc & 0x03FF)); - *to_nxt++ = static_cast<uint8_t>(t); - *to_nxt++ = static_cast<uint8_t>(t >> 8); - } - } - return codecvt_base::ok; -} - -static -codecvt_base::result -utf16le_to_ucs4(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt, - uint32_t* to, uint32_t* to_end, uint32_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFF && frm_nxt[1] == 0xFE) - frm_nxt += 2; - } - for (; frm_nxt < frm_end - 1 && to_nxt < to_end; ++to_nxt) - { - uint16_t c1 = static_cast<uint16_t>(frm_nxt[1] << 8 | frm_nxt[0]); - if ((c1 & 0xFC00) == 0xDC00) - return codecvt_base::error; - if ((c1 & 0xFC00) != 0xD800) - { - if (c1 > Maxcode) - return codecvt_base::error; - *to_nxt = static_cast<uint32_t>(c1); - frm_nxt += 2; - } - else - { - if (frm_end-frm_nxt < 4) - return codecvt_base::partial; - uint16_t c2 = static_cast<uint16_t>(frm_nxt[3] << 8 | frm_nxt[2]); - if ((c2 & 0xFC00) != 0xDC00) - return codecvt_base::error; - uint32_t t = static_cast<uint32_t>( - ((((c1 & 0x03C0) >> 6) + 1) << 16) - | ((c1 & 0x003F) << 10) - | (c2 & 0x03FF)); - if (t > Maxcode) - return codecvt_base::error; - *to_nxt = t; - frm_nxt += 4; - } - } - return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok; -} - -static -int -utf16le_to_ucs4_length(const uint8_t* frm, const uint8_t* frm_end, - size_t mx, unsigned long Maxcode = 0x10FFFF, - codecvt_mode mode = codecvt_mode(0)) -{ - const uint8_t* frm_nxt = frm; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFF && frm_nxt[1] == 0xFE) - frm_nxt += 2; - } - for (size_t nchar32_t = 0; frm_nxt < frm_end - 1 && nchar32_t < mx; ++nchar32_t) - { - uint16_t c1 = static_cast<uint16_t>(frm_nxt[1] << 8 | frm_nxt[0]); - if ((c1 & 0xFC00) == 0xDC00) - break; - if ((c1 & 0xFC00) != 0xD800) - { - if (c1 > Maxcode) - break; - frm_nxt += 2; - } - else - { - if (frm_end-frm_nxt < 4) - break; - uint16_t c2 = static_cast<uint16_t>(frm_nxt[3] << 8 | frm_nxt[2]); - if ((c2 & 0xFC00) != 0xDC00) - break; - uint32_t t = static_cast<uint32_t>( - ((((c1 & 0x03C0) >> 6) + 1) << 16) - | ((c1 & 0x003F) << 10) - | (c2 & 0x03FF)); - if (t > Maxcode) - break; - frm_nxt += 4; - } - } - return static_cast<int>(frm_nxt - frm); -} - -static -codecvt_base::result -ucs2_to_utf16be(const uint16_t* frm, const uint16_t* frm_end, const uint16_t*& frm_nxt, - uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & generate_header) - { - if (to_end-to_nxt < 2) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xFE); - *to_nxt++ = static_cast<uint8_t>(0xFF); - } - for (; frm_nxt < frm_end; ++frm_nxt) - { - uint16_t wc = *frm_nxt; - if ((wc & 0xF800) == 0xD800 || wc > Maxcode) - return codecvt_base::error; - if (to_end-to_nxt < 2) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(wc >> 8); - *to_nxt++ = static_cast<uint8_t>(wc); - } - return codecvt_base::ok; -} - -static -codecvt_base::result -utf16be_to_ucs2(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt, - uint16_t* to, uint16_t* to_end, uint16_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFE && frm_nxt[1] == 0xFF) - frm_nxt += 2; - } - for (; frm_nxt < frm_end - 1 && to_nxt < to_end; ++to_nxt) - { - uint16_t c1 = static_cast<uint16_t>(frm_nxt[0] << 8 | frm_nxt[1]); - if ((c1 & 0xF800) == 0xD800 || c1 > Maxcode) - return codecvt_base::error; - *to_nxt = c1; - frm_nxt += 2; - } - return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok; -} - -static -int -utf16be_to_ucs2_length(const uint8_t* frm, const uint8_t* frm_end, - size_t mx, unsigned long Maxcode = 0x10FFFF, - codecvt_mode mode = codecvt_mode(0)) -{ - const uint8_t* frm_nxt = frm; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFE && frm_nxt[1] == 0xFF) - frm_nxt += 2; - } - for (size_t nchar16_t = 0; frm_nxt < frm_end - 1 && nchar16_t < mx; ++nchar16_t) - { - uint16_t c1 = static_cast<uint16_t>(frm_nxt[0] << 8 | frm_nxt[1]); - if ((c1 & 0xF800) == 0xD800 || c1 > Maxcode) - break; - frm_nxt += 2; - } - return static_cast<int>(frm_nxt - frm); -} - -static -codecvt_base::result -ucs2_to_utf16le(const uint16_t* frm, const uint16_t* frm_end, const uint16_t*& frm_nxt, - uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & generate_header) - { - if (to_end-to_nxt < 2) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(0xFF); - *to_nxt++ = static_cast<uint8_t>(0xFE); - } - for (; frm_nxt < frm_end; ++frm_nxt) - { - uint16_t wc = *frm_nxt; - if ((wc & 0xF800) == 0xD800 || wc > Maxcode) - return codecvt_base::error; - if (to_end-to_nxt < 2) - return codecvt_base::partial; - *to_nxt++ = static_cast<uint8_t>(wc); - *to_nxt++ = static_cast<uint8_t>(wc >> 8); - } - return codecvt_base::ok; -} - -static -codecvt_base::result -utf16le_to_ucs2(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt, - uint16_t* to, uint16_t* to_end, uint16_t*& to_nxt, - unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0)) -{ - frm_nxt = frm; - to_nxt = to; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFF && frm_nxt[1] == 0xFE) - frm_nxt += 2; - } - for (; frm_nxt < frm_end - 1 && to_nxt < to_end; ++to_nxt) - { - uint16_t c1 = static_cast<uint16_t>(frm_nxt[1] << 8 | frm_nxt[0]); - if ((c1 & 0xF800) == 0xD800 || c1 > Maxcode) - return codecvt_base::error; - *to_nxt = c1; - frm_nxt += 2; - } - return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok; -} - -static -int -utf16le_to_ucs2_length(const uint8_t* frm, const uint8_t* frm_end, - size_t mx, unsigned long Maxcode = 0x10FFFF, - codecvt_mode mode = codecvt_mode(0)) -{ - const uint8_t* frm_nxt = frm; - frm_nxt = frm; - if (mode & consume_header) - { - if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFF && frm_nxt[1] == 0xFE) - frm_nxt += 2; - } - for (size_t nchar16_t = 0; frm_nxt < frm_end - 1 && nchar16_t < mx; ++nchar16_t) - { - uint16_t c1 = static_cast<uint16_t>(frm_nxt[1] << 8 | frm_nxt[0]); - if ((c1 & 0xF800) == 0xD800 || c1 > Maxcode) - break; - frm_nxt += 2; - } - return static_cast<int>(frm_nxt - frm); -} - -// template <> class codecvt<char16_t, char, mbstate_t> - -locale::id codecvt<char16_t, char, mbstate_t>::id; - -codecvt<char16_t, char, mbstate_t>::~codecvt() -{ -} - -codecvt<char16_t, char, mbstate_t>::result -codecvt<char16_t, char, mbstate_t>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint16_t* _frm = reinterpret_cast<const uint16_t*>(frm); - const uint16_t* _frm_end = reinterpret_cast<const uint16_t*>(frm_end); - const uint16_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = utf16_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -codecvt<char16_t, char, mbstate_t>::result -codecvt<char16_t, char, mbstate_t>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint16_t* _to = reinterpret_cast<uint16_t*>(to); - uint16_t* _to_end = reinterpret_cast<uint16_t*>(to_end); - uint16_t* _to_nxt = _to; - result r = utf8_to_utf16(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -codecvt<char16_t, char, mbstate_t>::result -codecvt<char16_t, char, mbstate_t>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -codecvt<char16_t, char, mbstate_t>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -codecvt<char16_t, char, mbstate_t>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -codecvt<char16_t, char, mbstate_t>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf8_to_utf16_length(_frm, _frm_end, mx); -} - -int -codecvt<char16_t, char, mbstate_t>::do_max_length() const _NOEXCEPT -{ - return 4; -} - -// template <> class codecvt<char32_t, char, mbstate_t> - -locale::id codecvt<char32_t, char, mbstate_t>::id; - -codecvt<char32_t, char, mbstate_t>::~codecvt() -{ -} - -codecvt<char32_t, char, mbstate_t>::result -codecvt<char32_t, char, mbstate_t>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm); - const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end); - const uint32_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = ucs4_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -codecvt<char32_t, char, mbstate_t>::result -codecvt<char32_t, char, mbstate_t>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint32_t* _to = reinterpret_cast<uint32_t*>(to); - uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end); - uint32_t* _to_nxt = _to; - result r = utf8_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -codecvt<char32_t, char, mbstate_t>::result -codecvt<char32_t, char, mbstate_t>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -codecvt<char32_t, char, mbstate_t>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -codecvt<char32_t, char, mbstate_t>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -codecvt<char32_t, char, mbstate_t>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf8_to_ucs4_length(_frm, _frm_end, mx); -} - -int -codecvt<char32_t, char, mbstate_t>::do_max_length() const _NOEXCEPT -{ - return 4; -} - -// __codecvt_utf8<wchar_t> - -__codecvt_utf8<wchar_t>::result -__codecvt_utf8<wchar_t>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ -#if defined(_LIBCPP_SHORT_WCHAR) - const uint16_t* _frm = reinterpret_cast<const uint16_t*>(frm); - const uint16_t* _frm_end = reinterpret_cast<const uint16_t*>(frm_end); - const uint16_t* _frm_nxt = _frm; -#else - const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm); - const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end); - const uint32_t* _frm_nxt = _frm; -#endif - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; -#if defined(_LIBCPP_SHORT_WCHAR) - result r = ucs2_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); -#else - result r = ucs4_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); -#endif - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf8<wchar_t>::result -__codecvt_utf8<wchar_t>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; -#if defined(_LIBCPP_SHORT_WCHAR) - uint16_t* _to = reinterpret_cast<uint16_t*>(to); - uint16_t* _to_end = reinterpret_cast<uint16_t*>(to_end); - uint16_t* _to_nxt = _to; - result r = utf8_to_ucs2(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); -#else - uint32_t* _to = reinterpret_cast<uint32_t*>(to); - uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end); - uint32_t* _to_nxt = _to; - result r = utf8_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); -#endif - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf8<wchar_t>::result -__codecvt_utf8<wchar_t>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -__codecvt_utf8<wchar_t>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -__codecvt_utf8<wchar_t>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -__codecvt_utf8<wchar_t>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf8_to_ucs4_length(_frm, _frm_end, mx, _Maxcode_, _Mode_); -} - -int -__codecvt_utf8<wchar_t>::do_max_length() const _NOEXCEPT -{ - if (_Mode_ & consume_header) - return 7; - return 4; -} - -// __codecvt_utf8<char16_t> - -__codecvt_utf8<char16_t>::result -__codecvt_utf8<char16_t>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint16_t* _frm = reinterpret_cast<const uint16_t*>(frm); - const uint16_t* _frm_end = reinterpret_cast<const uint16_t*>(frm_end); - const uint16_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = ucs2_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf8<char16_t>::result -__codecvt_utf8<char16_t>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint16_t* _to = reinterpret_cast<uint16_t*>(to); - uint16_t* _to_end = reinterpret_cast<uint16_t*>(to_end); - uint16_t* _to_nxt = _to; - result r = utf8_to_ucs2(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf8<char16_t>::result -__codecvt_utf8<char16_t>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -__codecvt_utf8<char16_t>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -__codecvt_utf8<char16_t>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -__codecvt_utf8<char16_t>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf8_to_ucs2_length(_frm, _frm_end, mx, _Maxcode_, _Mode_); -} - -int -__codecvt_utf8<char16_t>::do_max_length() const _NOEXCEPT -{ - if (_Mode_ & consume_header) - return 6; - return 3; -} - -// __codecvt_utf8<char32_t> - -__codecvt_utf8<char32_t>::result -__codecvt_utf8<char32_t>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm); - const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end); - const uint32_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = ucs4_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf8<char32_t>::result -__codecvt_utf8<char32_t>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint32_t* _to = reinterpret_cast<uint32_t*>(to); - uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end); - uint32_t* _to_nxt = _to; - result r = utf8_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf8<char32_t>::result -__codecvt_utf8<char32_t>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -__codecvt_utf8<char32_t>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -__codecvt_utf8<char32_t>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -__codecvt_utf8<char32_t>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf8_to_ucs4_length(_frm, _frm_end, mx, _Maxcode_, _Mode_); -} - -int -__codecvt_utf8<char32_t>::do_max_length() const _NOEXCEPT -{ - if (_Mode_ & consume_header) - return 7; - return 4; -} - -// __codecvt_utf16<wchar_t, false> - -__codecvt_utf16<wchar_t, false>::result -__codecvt_utf16<wchar_t, false>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm); - const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end); - const uint32_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = ucs4_to_utf16be(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf16<wchar_t, false>::result -__codecvt_utf16<wchar_t, false>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint32_t* _to = reinterpret_cast<uint32_t*>(to); - uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end); - uint32_t* _to_nxt = _to; - result r = utf16be_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf16<wchar_t, false>::result -__codecvt_utf16<wchar_t, false>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -__codecvt_utf16<wchar_t, false>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -__codecvt_utf16<wchar_t, false>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -__codecvt_utf16<wchar_t, false>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf16be_to_ucs4_length(_frm, _frm_end, mx, _Maxcode_, _Mode_); -} - -int -__codecvt_utf16<wchar_t, false>::do_max_length() const _NOEXCEPT -{ - if (_Mode_ & consume_header) - return 6; - return 4; -} - -// __codecvt_utf16<wchar_t, true> - -__codecvt_utf16<wchar_t, true>::result -__codecvt_utf16<wchar_t, true>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm); - const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end); - const uint32_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = ucs4_to_utf16le(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf16<wchar_t, true>::result -__codecvt_utf16<wchar_t, true>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint32_t* _to = reinterpret_cast<uint32_t*>(to); - uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end); - uint32_t* _to_nxt = _to; - result r = utf16le_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf16<wchar_t, true>::result -__codecvt_utf16<wchar_t, true>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -__codecvt_utf16<wchar_t, true>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -__codecvt_utf16<wchar_t, true>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -__codecvt_utf16<wchar_t, true>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf16le_to_ucs4_length(_frm, _frm_end, mx, _Maxcode_, _Mode_); -} - -int -__codecvt_utf16<wchar_t, true>::do_max_length() const _NOEXCEPT -{ - if (_Mode_ & consume_header) - return 6; - return 4; -} - -// __codecvt_utf16<char16_t, false> - -__codecvt_utf16<char16_t, false>::result -__codecvt_utf16<char16_t, false>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint16_t* _frm = reinterpret_cast<const uint16_t*>(frm); - const uint16_t* _frm_end = reinterpret_cast<const uint16_t*>(frm_end); - const uint16_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = ucs2_to_utf16be(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf16<char16_t, false>::result -__codecvt_utf16<char16_t, false>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint16_t* _to = reinterpret_cast<uint16_t*>(to); - uint16_t* _to_end = reinterpret_cast<uint16_t*>(to_end); - uint16_t* _to_nxt = _to; - result r = utf16be_to_ucs2(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf16<char16_t, false>::result -__codecvt_utf16<char16_t, false>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -__codecvt_utf16<char16_t, false>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -__codecvt_utf16<char16_t, false>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -__codecvt_utf16<char16_t, false>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf16be_to_ucs2_length(_frm, _frm_end, mx, _Maxcode_, _Mode_); -} - -int -__codecvt_utf16<char16_t, false>::do_max_length() const _NOEXCEPT -{ - if (_Mode_ & consume_header) - return 4; - return 2; -} - -// __codecvt_utf16<char16_t, true> - -__codecvt_utf16<char16_t, true>::result -__codecvt_utf16<char16_t, true>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint16_t* _frm = reinterpret_cast<const uint16_t*>(frm); - const uint16_t* _frm_end = reinterpret_cast<const uint16_t*>(frm_end); - const uint16_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = ucs2_to_utf16le(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf16<char16_t, true>::result -__codecvt_utf16<char16_t, true>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint16_t* _to = reinterpret_cast<uint16_t*>(to); - uint16_t* _to_end = reinterpret_cast<uint16_t*>(to_end); - uint16_t* _to_nxt = _to; - result r = utf16le_to_ucs2(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf16<char16_t, true>::result -__codecvt_utf16<char16_t, true>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -__codecvt_utf16<char16_t, true>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -__codecvt_utf16<char16_t, true>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -__codecvt_utf16<char16_t, true>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf16le_to_ucs2_length(_frm, _frm_end, mx, _Maxcode_, _Mode_); -} - -int -__codecvt_utf16<char16_t, true>::do_max_length() const _NOEXCEPT -{ - if (_Mode_ & consume_header) - return 4; - return 2; -} - -// __codecvt_utf16<char32_t, false> - -__codecvt_utf16<char32_t, false>::result -__codecvt_utf16<char32_t, false>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm); - const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end); - const uint32_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = ucs4_to_utf16be(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf16<char32_t, false>::result -__codecvt_utf16<char32_t, false>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint32_t* _to = reinterpret_cast<uint32_t*>(to); - uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end); - uint32_t* _to_nxt = _to; - result r = utf16be_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf16<char32_t, false>::result -__codecvt_utf16<char32_t, false>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -__codecvt_utf16<char32_t, false>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -__codecvt_utf16<char32_t, false>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -__codecvt_utf16<char32_t, false>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf16be_to_ucs4_length(_frm, _frm_end, mx, _Maxcode_, _Mode_); -} - -int -__codecvt_utf16<char32_t, false>::do_max_length() const _NOEXCEPT -{ - if (_Mode_ & consume_header) - return 6; - return 4; -} - -// __codecvt_utf16<char32_t, true> - -__codecvt_utf16<char32_t, true>::result -__codecvt_utf16<char32_t, true>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm); - const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end); - const uint32_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = ucs4_to_utf16le(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf16<char32_t, true>::result -__codecvt_utf16<char32_t, true>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint32_t* _to = reinterpret_cast<uint32_t*>(to); - uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end); - uint32_t* _to_nxt = _to; - result r = utf16le_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf16<char32_t, true>::result -__codecvt_utf16<char32_t, true>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -__codecvt_utf16<char32_t, true>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -__codecvt_utf16<char32_t, true>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -__codecvt_utf16<char32_t, true>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf16le_to_ucs4_length(_frm, _frm_end, mx, _Maxcode_, _Mode_); -} - -int -__codecvt_utf16<char32_t, true>::do_max_length() const _NOEXCEPT -{ - if (_Mode_ & consume_header) - return 6; - return 4; -} - -// __codecvt_utf8_utf16<wchar_t> - -__codecvt_utf8_utf16<wchar_t>::result -__codecvt_utf8_utf16<wchar_t>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm); - const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end); - const uint32_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = utf16_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf8_utf16<wchar_t>::result -__codecvt_utf8_utf16<wchar_t>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint32_t* _to = reinterpret_cast<uint32_t*>(to); - uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end); - uint32_t* _to_nxt = _to; - result r = utf8_to_utf16(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf8_utf16<wchar_t>::result -__codecvt_utf8_utf16<wchar_t>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -__codecvt_utf8_utf16<wchar_t>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -__codecvt_utf8_utf16<wchar_t>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -__codecvt_utf8_utf16<wchar_t>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf8_to_utf16_length(_frm, _frm_end, mx, _Maxcode_, _Mode_); -} - -int -__codecvt_utf8_utf16<wchar_t>::do_max_length() const _NOEXCEPT -{ - if (_Mode_ & consume_header) - return 7; - return 4; -} - -// __codecvt_utf8_utf16<char16_t> - -__codecvt_utf8_utf16<char16_t>::result -__codecvt_utf8_utf16<char16_t>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint16_t* _frm = reinterpret_cast<const uint16_t*>(frm); - const uint16_t* _frm_end = reinterpret_cast<const uint16_t*>(frm_end); - const uint16_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = utf16_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf8_utf16<char16_t>::result -__codecvt_utf8_utf16<char16_t>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint16_t* _to = reinterpret_cast<uint16_t*>(to); - uint16_t* _to_end = reinterpret_cast<uint16_t*>(to_end); - uint16_t* _to_nxt = _to; - result r = utf8_to_utf16(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf8_utf16<char16_t>::result -__codecvt_utf8_utf16<char16_t>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -__codecvt_utf8_utf16<char16_t>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -__codecvt_utf8_utf16<char16_t>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -__codecvt_utf8_utf16<char16_t>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf8_to_utf16_length(_frm, _frm_end, mx, _Maxcode_, _Mode_); -} - -int -__codecvt_utf8_utf16<char16_t>::do_max_length() const _NOEXCEPT -{ - if (_Mode_ & consume_header) - return 7; - return 4; -} - -// __codecvt_utf8_utf16<char32_t> - -__codecvt_utf8_utf16<char32_t>::result -__codecvt_utf8_utf16<char32_t>::do_out(state_type&, - const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt, - extern_type* to, extern_type* to_end, extern_type*& to_nxt) const -{ - const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm); - const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end); - const uint32_t* _frm_nxt = _frm; - uint8_t* _to = reinterpret_cast<uint8_t*>(to); - uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end); - uint8_t* _to_nxt = _to; - result r = utf16_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf8_utf16<char32_t>::result -__codecvt_utf8_utf16<char32_t>::do_in(state_type&, - const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt, - intern_type* to, intern_type* to_end, intern_type*& to_nxt) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - const uint8_t* _frm_nxt = _frm; - uint32_t* _to = reinterpret_cast<uint32_t*>(to); - uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end); - uint32_t* _to_nxt = _to; - result r = utf8_to_utf16(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt, - _Maxcode_, _Mode_); - frm_nxt = frm + (_frm_nxt - _frm); - to_nxt = to + (_to_nxt - _to); - return r; -} - -__codecvt_utf8_utf16<char32_t>::result -__codecvt_utf8_utf16<char32_t>::do_unshift(state_type&, - extern_type* to, extern_type*, extern_type*& to_nxt) const -{ - to_nxt = to; - return noconv; -} - -int -__codecvt_utf8_utf16<char32_t>::do_encoding() const _NOEXCEPT -{ - return 0; -} - -bool -__codecvt_utf8_utf16<char32_t>::do_always_noconv() const _NOEXCEPT -{ - return false; -} - -int -__codecvt_utf8_utf16<char32_t>::do_length(state_type&, - const extern_type* frm, const extern_type* frm_end, size_t mx) const -{ - const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm); - const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end); - return utf8_to_utf16_length(_frm, _frm_end, mx, _Maxcode_, _Mode_); -} - -int -__codecvt_utf8_utf16<char32_t>::do_max_length() const _NOEXCEPT -{ - if (_Mode_ & consume_header) - return 7; - return 4; -} - -// __narrow_to_utf8<16> - -__narrow_to_utf8<16>::~__narrow_to_utf8() -{ -} - -// __narrow_to_utf8<32> - -__narrow_to_utf8<32>::~__narrow_to_utf8() -{ -} - -// __widen_from_utf8<16> - -__widen_from_utf8<16>::~__widen_from_utf8() -{ -} - -// __widen_from_utf8<32> - -__widen_from_utf8<32>::~__widen_from_utf8() -{ -} - - -static bool checked_string_to_wchar_convert(wchar_t& dest, - const char* ptr, - locale_t loc) { - if (*ptr == '\0') - return false; - mbstate_t mb = {}; - wchar_t out; - size_t ret = __libcpp_mbrtowc_l(&out, ptr, strlen(ptr), &mb, loc); - if (ret == static_cast<size_t>(-1) || ret == static_cast<size_t>(-2)) { - return false; - } - dest = out; - return true; -} - -static bool checked_string_to_char_convert(char& dest, - const char* ptr, - locale_t __loc) { - if (*ptr == '\0') - return false; - if (!ptr[1]) { - dest = *ptr; - return true; - } - // First convert the MBS into a wide char then attempt to narrow it using - // wctob_l. - wchar_t wout; - if (!checked_string_to_wchar_convert(wout, ptr, __loc)) - return false; - int res; - if ((res = __libcpp_wctob_l(wout, __loc)) != char_traits<char>::eof()) { - dest = res; - return true; - } - // FIXME: Work around specific multibyte sequences that we can reasonable - // translate into a different single byte. - switch (wout) { - case L'\u202F': // narrow non-breaking space - case L'\u00A0': // non-breaking space - dest = ' '; - return true; - default: - return false; - } - _LIBCPP_UNREACHABLE(); -} - - -// numpunct<char> && numpunct<wchar_t> - -locale::id numpunct< char >::id; -locale::id numpunct<wchar_t>::id; - -numpunct<char>::numpunct(size_t refs) - : locale::facet(refs), - __decimal_point_('.'), - __thousands_sep_(',') -{ -} - -numpunct<wchar_t>::numpunct(size_t refs) - : locale::facet(refs), - __decimal_point_(L'.'), - __thousands_sep_(L',') -{ -} - -numpunct<char>::~numpunct() -{ -} - -numpunct<wchar_t>::~numpunct() -{ -} - - char numpunct< char >::do_decimal_point() const {return __decimal_point_;} -wchar_t numpunct<wchar_t>::do_decimal_point() const {return __decimal_point_;} - - char numpunct< char >::do_thousands_sep() const {return __thousands_sep_;} -wchar_t numpunct<wchar_t>::do_thousands_sep() const {return __thousands_sep_;} - -string numpunct< char >::do_grouping() const {return __grouping_;} -string numpunct<wchar_t>::do_grouping() const {return __grouping_;} - - string numpunct< char >::do_truename() const {return "true";} -wstring numpunct<wchar_t>::do_truename() const {return L"true";} - - string numpunct< char >::do_falsename() const {return "false";} -wstring numpunct<wchar_t>::do_falsename() const {return L"false";} - -// numpunct_byname<char> - -numpunct_byname<char>::numpunct_byname(const char* nm, size_t refs) - : numpunct<char>(refs) -{ - __init(nm); -} - -numpunct_byname<char>::numpunct_byname(const string& nm, size_t refs) - : numpunct<char>(refs) -{ - __init(nm.c_str()); -} - -numpunct_byname<char>::~numpunct_byname() -{ -} - -void -numpunct_byname<char>::__init(const char* nm) -{ - if (strcmp(nm, "C") != 0) - { - __libcpp_unique_locale loc(nm); - if (!loc) - __throw_runtime_error("numpunct_byname<char>::numpunct_byname" - " failed to construct for " + string(nm)); - - lconv* lc = __libcpp_localeconv_l(loc.get()); - checked_string_to_char_convert(__decimal_point_, lc->decimal_point, - loc.get()); - checked_string_to_char_convert(__thousands_sep_, lc->thousands_sep, - loc.get()); - __grouping_ = lc->grouping; - // localization for truename and falsename is not available - } -} - -// numpunct_byname<wchar_t> - -numpunct_byname<wchar_t>::numpunct_byname(const char* nm, size_t refs) - : numpunct<wchar_t>(refs) -{ - __init(nm); -} - -numpunct_byname<wchar_t>::numpunct_byname(const string& nm, size_t refs) - : numpunct<wchar_t>(refs) -{ - __init(nm.c_str()); -} - -numpunct_byname<wchar_t>::~numpunct_byname() -{ -} - -void -numpunct_byname<wchar_t>::__init(const char* nm) -{ - if (strcmp(nm, "C") != 0) - { - __libcpp_unique_locale loc(nm); - if (!loc) - __throw_runtime_error("numpunct_byname<wchar_t>::numpunct_byname" - " failed to construct for " + string(nm)); - - lconv* lc = __libcpp_localeconv_l(loc.get()); - checked_string_to_wchar_convert(__decimal_point_, lc->decimal_point, - loc.get()); - checked_string_to_wchar_convert(__thousands_sep_, lc->thousands_sep, - loc.get()); - __grouping_ = lc->grouping; - // localization for truename and falsename is not available - } -} - -// num_get helpers - -int -__num_get_base::__get_base(ios_base& iob) -{ - ios_base::fmtflags __basefield = iob.flags() & ios_base::basefield; - if (__basefield == ios_base::oct) - return 8; - else if (__basefield == ios_base::hex) - return 16; - else if (__basefield == 0) - return 0; - return 10; -} - -const char __num_get_base::__src[33] = "0123456789abcdefABCDEFxX+-pPiInN"; - -void -__check_grouping(const string& __grouping, unsigned* __g, unsigned* __g_end, - ios_base::iostate& __err) -{ - if (__grouping.size() != 0) - { - reverse(__g, __g_end); - const char* __ig = __grouping.data(); - const char* __eg = __ig + __grouping.size(); - for (unsigned* __r = __g; __r < __g_end-1; ++__r) - { - if (0 < *__ig && *__ig < numeric_limits<char>::max()) - { - if (static_cast<unsigned>(*__ig) != *__r) - { - __err = ios_base::failbit; - return; - } - } - if (__eg - __ig > 1) - ++__ig; - } - if (0 < *__ig && *__ig < numeric_limits<char>::max()) - { - if (static_cast<unsigned>(*__ig) < __g_end[-1] || __g_end[-1] == 0) - __err = ios_base::failbit; - } - } -} - -void -__num_put_base::__format_int(char* __fmtp, const char* __len, bool __signd, - ios_base::fmtflags __flags) -{ - if (__flags & ios_base::showpos) - *__fmtp++ = '+'; - if (__flags & ios_base::showbase) - *__fmtp++ = '#'; - while(*__len) - *__fmtp++ = *__len++; - if ((__flags & ios_base::basefield) == ios_base::oct) - *__fmtp = 'o'; - else if ((__flags & ios_base::basefield) == ios_base::hex) - { - if (__flags & ios_base::uppercase) - *__fmtp = 'X'; - else - *__fmtp = 'x'; - } - else if (__signd) - *__fmtp = 'd'; - else - *__fmtp = 'u'; -} - -bool -__num_put_base::__format_float(char* __fmtp, const char* __len, - ios_base::fmtflags __flags) -{ - bool specify_precision = true; - if (__flags & ios_base::showpos) - *__fmtp++ = '+'; - if (__flags & ios_base::showpoint) - *__fmtp++ = '#'; - ios_base::fmtflags floatfield = __flags & ios_base::floatfield; - bool uppercase = (__flags & ios_base::uppercase) != 0; - if (floatfield == (ios_base::fixed | ios_base::scientific)) - specify_precision = false; - else - { - *__fmtp++ = '.'; - *__fmtp++ = '*'; - } - while(*__len) - *__fmtp++ = *__len++; - if (floatfield == ios_base::fixed) - { - if (uppercase) - *__fmtp = 'F'; - else - *__fmtp = 'f'; - } - else if (floatfield == ios_base::scientific) - { - if (uppercase) - *__fmtp = 'E'; - else - *__fmtp = 'e'; - } - else if (floatfield == (ios_base::fixed | ios_base::scientific)) - { - if (uppercase) - *__fmtp = 'A'; - else - *__fmtp = 'a'; - } - else - { - if (uppercase) - *__fmtp = 'G'; - else - *__fmtp = 'g'; - } - return specify_precision; -} - -char* -__num_put_base::__identify_padding(char* __nb, char* __ne, - const ios_base& __iob) -{ - switch (__iob.flags() & ios_base::adjustfield) - { - case ios_base::internal: - if (__nb[0] == '-' || __nb[0] == '+') - return __nb+1; - if (__ne - __nb >= 2 && __nb[0] == '0' - && (__nb[1] == 'x' || __nb[1] == 'X')) - return __nb+2; - break; - case ios_base::left: - return __ne; - case ios_base::right: - default: - break; - } - return __nb; -} - -// time_get - -static -string* -init_weeks() -{ - static string weeks[14]; - weeks[0] = "Sunday"; - weeks[1] = "Monday"; - weeks[2] = "Tuesday"; - weeks[3] = "Wednesday"; - weeks[4] = "Thursday"; - weeks[5] = "Friday"; - weeks[6] = "Saturday"; - weeks[7] = "Sun"; - weeks[8] = "Mon"; - weeks[9] = "Tue"; - weeks[10] = "Wed"; - weeks[11] = "Thu"; - weeks[12] = "Fri"; - weeks[13] = "Sat"; - return weeks; -} - -static -wstring* -init_wweeks() -{ - static wstring weeks[14]; - weeks[0] = L"Sunday"; - weeks[1] = L"Monday"; - weeks[2] = L"Tuesday"; - weeks[3] = L"Wednesday"; - weeks[4] = L"Thursday"; - weeks[5] = L"Friday"; - weeks[6] = L"Saturday"; - weeks[7] = L"Sun"; - weeks[8] = L"Mon"; - weeks[9] = L"Tue"; - weeks[10] = L"Wed"; - weeks[11] = L"Thu"; - weeks[12] = L"Fri"; - weeks[13] = L"Sat"; - return weeks; -} - -template <> -const string* -__time_get_c_storage<char>::__weeks() const -{ - static const string* weeks = init_weeks(); - return weeks; -} - -template <> -const wstring* -__time_get_c_storage<wchar_t>::__weeks() const -{ - static const wstring* weeks = init_wweeks(); - return weeks; -} - -static -string* -init_months() -{ - static string months[24]; - months[0] = "January"; - months[1] = "February"; - months[2] = "March"; - months[3] = "April"; - months[4] = "May"; - months[5] = "June"; - months[6] = "July"; - months[7] = "August"; - months[8] = "September"; - months[9] = "October"; - months[10] = "November"; - months[11] = "December"; - months[12] = "Jan"; - months[13] = "Feb"; - months[14] = "Mar"; - months[15] = "Apr"; - months[16] = "May"; - months[17] = "Jun"; - months[18] = "Jul"; - months[19] = "Aug"; - months[20] = "Sep"; - months[21] = "Oct"; - months[22] = "Nov"; - months[23] = "Dec"; - return months; -} - -static -wstring* -init_wmonths() -{ - static wstring months[24]; - months[0] = L"January"; - months[1] = L"February"; - months[2] = L"March"; - months[3] = L"April"; - months[4] = L"May"; - months[5] = L"June"; - months[6] = L"July"; - months[7] = L"August"; - months[8] = L"September"; - months[9] = L"October"; - months[10] = L"November"; - months[11] = L"December"; - months[12] = L"Jan"; - months[13] = L"Feb"; - months[14] = L"Mar"; - months[15] = L"Apr"; - months[16] = L"May"; - months[17] = L"Jun"; - months[18] = L"Jul"; - months[19] = L"Aug"; - months[20] = L"Sep"; - months[21] = L"Oct"; - months[22] = L"Nov"; - months[23] = L"Dec"; - return months; -} - -template <> -const string* -__time_get_c_storage<char>::__months() const -{ - static const string* months = init_months(); - return months; -} - -template <> -const wstring* -__time_get_c_storage<wchar_t>::__months() const -{ - static const wstring* months = init_wmonths(); - return months; -} - -static -string* -init_am_pm() -{ - static string am_pm[2]; - am_pm[0] = "AM"; - am_pm[1] = "PM"; - return am_pm; -} - -static -wstring* -init_wam_pm() -{ - static wstring am_pm[2]; - am_pm[0] = L"AM"; - am_pm[1] = L"PM"; - return am_pm; -} - -template <> -const string* -__time_get_c_storage<char>::__am_pm() const -{ - static const string* am_pm = init_am_pm(); - return am_pm; -} - -template <> -const wstring* -__time_get_c_storage<wchar_t>::__am_pm() const -{ - static const wstring* am_pm = init_wam_pm(); - return am_pm; -} - -template <> -const string& -__time_get_c_storage<char>::__x() const -{ - static string s("%m/%d/%y"); - return s; -} - -template <> -const wstring& -__time_get_c_storage<wchar_t>::__x() const -{ - static wstring s(L"%m/%d/%y"); - return s; -} - -template <> -const string& -__time_get_c_storage<char>::__X() const -{ - static string s("%H:%M:%S"); - return s; -} - -template <> -const wstring& -__time_get_c_storage<wchar_t>::__X() const -{ - static wstring s(L"%H:%M:%S"); - return s; -} - -template <> -const string& -__time_get_c_storage<char>::__c() const -{ - static string s("%a %b %d %H:%M:%S %Y"); - return s; -} - -template <> -const wstring& -__time_get_c_storage<wchar_t>::__c() const -{ - static wstring s(L"%a %b %d %H:%M:%S %Y"); - return s; -} - -template <> -const string& -__time_get_c_storage<char>::__r() const -{ - static string s("%I:%M:%S %p"); - return s; -} - -template <> -const wstring& -__time_get_c_storage<wchar_t>::__r() const -{ - static wstring s(L"%I:%M:%S %p"); - return s; -} - -// time_get_byname - -__time_get::__time_get(const char* nm) - : __loc_(newlocale(LC_ALL_MASK, nm, 0)) -{ - if (__loc_ == 0) - __throw_runtime_error("time_get_byname" - " failed to construct for " + string(nm)); -} - -__time_get::__time_get(const string& nm) - : __loc_(newlocale(LC_ALL_MASK, nm.c_str(), 0)) -{ - if (__loc_ == 0) - __throw_runtime_error("time_get_byname" - " failed to construct for " + nm); -} - -__time_get::~__time_get() -{ - freelocale(__loc_); -} -#if defined(__clang__) -#pragma clang diagnostic ignored "-Wmissing-field-initializers" -#endif -#if defined(__GNUG__) -#pragma GCC diagnostic ignored "-Wmissing-field-initializers" -#endif - -template <> -string -__time_get_storage<char>::__analyze(char fmt, const ctype<char>& ct) -{ - tm t = {0}; - t.tm_sec = 59; - t.tm_min = 55; - t.tm_hour = 23; - t.tm_mday = 31; - t.tm_mon = 11; - t.tm_year = 161; - t.tm_wday = 6; - t.tm_yday = 364; - t.tm_isdst = -1; - char buf[100]; - char f[3] = {0}; - f[0] = '%'; - f[1] = fmt; - size_t n = strftime_l(buf, countof(buf), f, &t, __loc_); - char* bb = buf; - char* be = buf + n; - string result; - while (bb != be) - { - if (ct.is(ctype_base::space, *bb)) - { - result.push_back(' '); - for (++bb; bb != be && ct.is(ctype_base::space, *bb); ++bb) - ; - continue; - } - char* w = bb; - ios_base::iostate err = ios_base::goodbit; - ptrdiff_t i = __scan_keyword(w, be, this->__weeks_, this->__weeks_+14, - ct, err, false) - - this->__weeks_; - if (i < 14) - { - result.push_back('%'); - if (i < 7) - result.push_back('A'); - else - result.push_back('a'); - bb = w; - continue; - } - w = bb; - i = __scan_keyword(w, be, this->__months_, this->__months_+24, - ct, err, false) - - this->__months_; - if (i < 24) - { - result.push_back('%'); - if (i < 12) - result.push_back('B'); - else - result.push_back('b'); - if (fmt == 'x' && ct.is(ctype_base::digit, this->__months_[i][0])) - result.back() = 'm'; - bb = w; - continue; - } - if (this->__am_pm_[0].size() + this->__am_pm_[1].size() > 0) - { - w = bb; - i = __scan_keyword(w, be, this->__am_pm_, this->__am_pm_+2, - ct, err, false) - this->__am_pm_; - if (i < 2) - { - result.push_back('%'); - result.push_back('p'); - bb = w; - continue; - } - } - w = bb; - if (ct.is(ctype_base::digit, *bb)) - { - switch(__get_up_to_n_digits(bb, be, err, ct, 4)) - { - case 6: - result.push_back('%'); - result.push_back('w'); - break; - case 7: - result.push_back('%'); - result.push_back('u'); - break; - case 11: - result.push_back('%'); - result.push_back('I'); - break; - case 12: - result.push_back('%'); - result.push_back('m'); - break; - case 23: - result.push_back('%'); - result.push_back('H'); - break; - case 31: - result.push_back('%'); - result.push_back('d'); - break; - case 55: - result.push_back('%'); - result.push_back('M'); - break; - case 59: - result.push_back('%'); - result.push_back('S'); - break; - case 61: - result.push_back('%'); - result.push_back('y'); - break; - case 364: - result.push_back('%'); - result.push_back('j'); - break; - case 2061: - result.push_back('%'); - result.push_back('Y'); - break; - default: - for (; w != bb; ++w) - result.push_back(*w); - break; - } - continue; - } - if (*bb == '%') - { - result.push_back('%'); - result.push_back('%'); - ++bb; - continue; - } - result.push_back(*bb); - ++bb; - } - return result; -} - -#if defined(__clang__) -#pragma clang diagnostic ignored "-Wmissing-braces" -#endif - -template <> -wstring -__time_get_storage<wchar_t>::__analyze(char fmt, const ctype<wchar_t>& ct) -{ - tm t = {0}; - t.tm_sec = 59; - t.tm_min = 55; - t.tm_hour = 23; - t.tm_mday = 31; - t.tm_mon = 11; - t.tm_year = 161; - t.tm_wday = 6; - t.tm_yday = 364; - t.tm_isdst = -1; - char buf[100]; - char f[3] = {0}; - f[0] = '%'; - f[1] = fmt; - strftime_l(buf, countof(buf), f, &t, __loc_); - wchar_t wbuf[100]; - wchar_t* wbb = wbuf; - mbstate_t mb = {0}; - const char* bb = buf; - size_t j = __libcpp_mbsrtowcs_l( wbb, &bb, countof(wbuf), &mb, __loc_); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wchar_t* wbe = wbb + j; - wstring result; - while (wbb != wbe) - { - if (ct.is(ctype_base::space, *wbb)) - { - result.push_back(L' '); - for (++wbb; wbb != wbe && ct.is(ctype_base::space, *wbb); ++wbb) - ; - continue; - } - wchar_t* w = wbb; - ios_base::iostate err = ios_base::goodbit; - ptrdiff_t i = __scan_keyword(w, wbe, this->__weeks_, this->__weeks_+14, - ct, err, false) - - this->__weeks_; - if (i < 14) - { - result.push_back(L'%'); - if (i < 7) - result.push_back(L'A'); - else - result.push_back(L'a'); - wbb = w; - continue; - } - w = wbb; - i = __scan_keyword(w, wbe, this->__months_, this->__months_+24, - ct, err, false) - - this->__months_; - if (i < 24) - { - result.push_back(L'%'); - if (i < 12) - result.push_back(L'B'); - else - result.push_back(L'b'); - if (fmt == 'x' && ct.is(ctype_base::digit, this->__months_[i][0])) - result.back() = L'm'; - wbb = w; - continue; - } - if (this->__am_pm_[0].size() + this->__am_pm_[1].size() > 0) - { - w = wbb; - i = __scan_keyword(w, wbe, this->__am_pm_, this->__am_pm_+2, - ct, err, false) - this->__am_pm_; - if (i < 2) - { - result.push_back(L'%'); - result.push_back(L'p'); - wbb = w; - continue; - } - } - w = wbb; - if (ct.is(ctype_base::digit, *wbb)) - { - switch(__get_up_to_n_digits(wbb, wbe, err, ct, 4)) - { - case 6: - result.push_back(L'%'); - result.push_back(L'w'); - break; - case 7: - result.push_back(L'%'); - result.push_back(L'u'); - break; - case 11: - result.push_back(L'%'); - result.push_back(L'I'); - break; - case 12: - result.push_back(L'%'); - result.push_back(L'm'); - break; - case 23: - result.push_back(L'%'); - result.push_back(L'H'); - break; - case 31: - result.push_back(L'%'); - result.push_back(L'd'); - break; - case 55: - result.push_back(L'%'); - result.push_back(L'M'); - break; - case 59: - result.push_back(L'%'); - result.push_back(L'S'); - break; - case 61: - result.push_back(L'%'); - result.push_back(L'y'); - break; - case 364: - result.push_back(L'%'); - result.push_back(L'j'); - break; - case 2061: - result.push_back(L'%'); - result.push_back(L'Y'); - break; - default: - for (; w != wbb; ++w) - result.push_back(*w); - break; - } - continue; - } - if (ct.narrow(*wbb, 0) == '%') - { - result.push_back(L'%'); - result.push_back(L'%'); - ++wbb; - continue; - } - result.push_back(*wbb); - ++wbb; - } - return result; -} - -template <> -void -__time_get_storage<char>::init(const ctype<char>& ct) -{ - tm t = {0}; - char buf[100]; - // __weeks_ - for (int i = 0; i < 7; ++i) - { - t.tm_wday = i; - strftime_l(buf, countof(buf), "%A", &t, __loc_); - __weeks_[i] = buf; - strftime_l(buf, countof(buf), "%a", &t, __loc_); - __weeks_[i+7] = buf; - } - // __months_ - for (int i = 0; i < 12; ++i) - { - t.tm_mon = i; - strftime_l(buf, countof(buf), "%B", &t, __loc_); - __months_[i] = buf; - strftime_l(buf, countof(buf), "%b", &t, __loc_); - __months_[i+12] = buf; - } - // __am_pm_ - t.tm_hour = 1; - strftime_l(buf, countof(buf), "%p", &t, __loc_); - __am_pm_[0] = buf; - t.tm_hour = 13; - strftime_l(buf, countof(buf), "%p", &t, __loc_); - __am_pm_[1] = buf; - __c_ = __analyze('c', ct); - __r_ = __analyze('r', ct); - __x_ = __analyze('x', ct); - __X_ = __analyze('X', ct); -} - -template <> -void -__time_get_storage<wchar_t>::init(const ctype<wchar_t>& ct) -{ - tm t = {0}; - char buf[100]; - wchar_t wbuf[100]; - wchar_t* wbe; - mbstate_t mb = {0}; - // __weeks_ - for (int i = 0; i < 7; ++i) - { - t.tm_wday = i; - strftime_l(buf, countof(buf), "%A", &t, __loc_); - mb = mbstate_t(); - const char* bb = buf; - size_t j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, __loc_); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wbe = wbuf + j; - __weeks_[i].assign(wbuf, wbe); - strftime_l(buf, countof(buf), "%a", &t, __loc_); - mb = mbstate_t(); - bb = buf; - j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, __loc_); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wbe = wbuf + j; - __weeks_[i+7].assign(wbuf, wbe); - } - // __months_ - for (int i = 0; i < 12; ++i) - { - t.tm_mon = i; - strftime_l(buf, countof(buf), "%B", &t, __loc_); - mb = mbstate_t(); - const char* bb = buf; - size_t j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, __loc_); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wbe = wbuf + j; - __months_[i].assign(wbuf, wbe); - strftime_l(buf, countof(buf), "%b", &t, __loc_); - mb = mbstate_t(); - bb = buf; - j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, __loc_); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wbe = wbuf + j; - __months_[i+12].assign(wbuf, wbe); - } - // __am_pm_ - t.tm_hour = 1; - strftime_l(buf, countof(buf), "%p", &t, __loc_); - mb = mbstate_t(); - const char* bb = buf; - size_t j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, __loc_); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wbe = wbuf + j; - __am_pm_[0].assign(wbuf, wbe); - t.tm_hour = 13; - strftime_l(buf, countof(buf), "%p", &t, __loc_); - mb = mbstate_t(); - bb = buf; - j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, __loc_); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wbe = wbuf + j; - __am_pm_[1].assign(wbuf, wbe); - __c_ = __analyze('c', ct); - __r_ = __analyze('r', ct); - __x_ = __analyze('x', ct); - __X_ = __analyze('X', ct); -} - -template <class CharT> -struct _LIBCPP_HIDDEN __time_get_temp - : public ctype_byname<CharT> -{ - explicit __time_get_temp(const char* nm) - : ctype_byname<CharT>(nm, 1) {} - explicit __time_get_temp(const string& nm) - : ctype_byname<CharT>(nm, 1) {} -}; - -template <> -__time_get_storage<char>::__time_get_storage(const char* __nm) - : __time_get(__nm) -{ - const __time_get_temp<char> ct(__nm); - init(ct); -} - -template <> -__time_get_storage<char>::__time_get_storage(const string& __nm) - : __time_get(__nm) -{ - const __time_get_temp<char> ct(__nm); - init(ct); -} - -template <> -__time_get_storage<wchar_t>::__time_get_storage(const char* __nm) - : __time_get(__nm) -{ - const __time_get_temp<wchar_t> ct(__nm); - init(ct); -} - -template <> -__time_get_storage<wchar_t>::__time_get_storage(const string& __nm) - : __time_get(__nm) -{ - const __time_get_temp<wchar_t> ct(__nm); - init(ct); -} - -template <> -time_base::dateorder -__time_get_storage<char>::__do_date_order() const -{ - unsigned i; - for (i = 0; i < __x_.size(); ++i) - if (__x_[i] == '%') - break; - ++i; - switch (__x_[i]) - { - case 'y': - case 'Y': - for (++i; i < __x_.size(); ++i) - if (__x_[i] == '%') - break; - if (i == __x_.size()) - break; - ++i; - switch (__x_[i]) - { - case 'm': - for (++i; i < __x_.size(); ++i) - if (__x_[i] == '%') - break; - if (i == __x_.size()) - break; - ++i; - if (__x_[i] == 'd') - return time_base::ymd; - break; - case 'd': - for (++i; i < __x_.size(); ++i) - if (__x_[i] == '%') - break; - if (i == __x_.size()) - break; - ++i; - if (__x_[i] == 'm') - return time_base::ydm; - break; - } - break; - case 'm': - for (++i; i < __x_.size(); ++i) - if (__x_[i] == '%') - break; - if (i == __x_.size()) - break; - ++i; - if (__x_[i] == 'd') - { - for (++i; i < __x_.size(); ++i) - if (__x_[i] == '%') - break; - if (i == __x_.size()) - break; - ++i; - if (__x_[i] == 'y' || __x_[i] == 'Y') - return time_base::mdy; - break; - } - break; - case 'd': - for (++i; i < __x_.size(); ++i) - if (__x_[i] == '%') - break; - if (i == __x_.size()) - break; - ++i; - if (__x_[i] == 'm') - { - for (++i; i < __x_.size(); ++i) - if (__x_[i] == '%') - break; - if (i == __x_.size()) - break; - ++i; - if (__x_[i] == 'y' || __x_[i] == 'Y') - return time_base::dmy; - break; - } - break; - } - return time_base::no_order; -} - -template <> -time_base::dateorder -__time_get_storage<wchar_t>::__do_date_order() const -{ - unsigned i; - for (i = 0; i < __x_.size(); ++i) - if (__x_[i] == L'%') - break; - ++i; - switch (__x_[i]) - { - case L'y': - case L'Y': - for (++i; i < __x_.size(); ++i) - if (__x_[i] == L'%') - break; - if (i == __x_.size()) - break; - ++i; - switch (__x_[i]) - { - case L'm': - for (++i; i < __x_.size(); ++i) - if (__x_[i] == L'%') - break; - if (i == __x_.size()) - break; - ++i; - if (__x_[i] == L'd') - return time_base::ymd; - break; - case L'd': - for (++i; i < __x_.size(); ++i) - if (__x_[i] == L'%') - break; - if (i == __x_.size()) - break; - ++i; - if (__x_[i] == L'm') - return time_base::ydm; - break; - } - break; - case L'm': - for (++i; i < __x_.size(); ++i) - if (__x_[i] == L'%') - break; - if (i == __x_.size()) - break; - ++i; - if (__x_[i] == L'd') - { - for (++i; i < __x_.size(); ++i) - if (__x_[i] == L'%') - break; - if (i == __x_.size()) - break; - ++i; - if (__x_[i] == L'y' || __x_[i] == L'Y') - return time_base::mdy; - break; - } - break; - case L'd': - for (++i; i < __x_.size(); ++i) - if (__x_[i] == L'%') - break; - if (i == __x_.size()) - break; - ++i; - if (__x_[i] == L'm') - { - for (++i; i < __x_.size(); ++i) - if (__x_[i] == L'%') - break; - if (i == __x_.size()) - break; - ++i; - if (__x_[i] == L'y' || __x_[i] == L'Y') - return time_base::dmy; - break; - } - break; - } - return time_base::no_order; -} - -// time_put - -__time_put::__time_put(const char* nm) - : __loc_(newlocale(LC_ALL_MASK, nm, 0)) -{ - if (__loc_ == 0) - __throw_runtime_error("time_put_byname" - " failed to construct for " + string(nm)); -} - -__time_put::__time_put(const string& nm) - : __loc_(newlocale(LC_ALL_MASK, nm.c_str(), 0)) -{ - if (__loc_ == 0) - __throw_runtime_error("time_put_byname" - " failed to construct for " + nm); -} - -__time_put::~__time_put() -{ - if (__loc_ != _LIBCPP_GET_C_LOCALE) - freelocale(__loc_); -} - -void -__time_put::__do_put(char* __nb, char*& __ne, const tm* __tm, - char __fmt, char __mod) const -{ - char fmt[] = {'%', __fmt, __mod, 0}; - if (__mod != 0) - swap(fmt[1], fmt[2]); - size_t n = strftime_l(__nb, countof(__nb, __ne), fmt, __tm, __loc_); - __ne = __nb + n; -} - -void -__time_put::__do_put(wchar_t* __wb, wchar_t*& __we, const tm* __tm, - char __fmt, char __mod) const -{ - char __nar[100]; - char* __ne = __nar + 100; - __do_put(__nar, __ne, __tm, __fmt, __mod); - mbstate_t mb = {0}; - const char* __nb = __nar; - size_t j = __libcpp_mbsrtowcs_l(__wb, &__nb, countof(__wb, __we), &mb, __loc_); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - __we = __wb + j; -} - -// moneypunct_byname - -template <class charT> -static -void -__init_pat(money_base::pattern& pat, basic_string<charT>& __curr_symbol_, - bool intl, char cs_precedes, char sep_by_space, char sign_posn, - charT space_char) -{ - const char sign = static_cast<char>(money_base::sign); - const char space = static_cast<char>(money_base::space); - const char none = static_cast<char>(money_base::none); - const char symbol = static_cast<char>(money_base::symbol); - const char value = static_cast<char>(money_base::value); - const bool symbol_contains_sep = intl && __curr_symbol_.size() == 4; - - // Comments on case branches reflect 'C11 7.11.2.1 The localeconv - // function'. "Space between sign and symbol or value" means that - // if the sign is adjacent to the symbol, there's a space between - // them, and otherwise there's a space between the sign and value. - // - // C11's localeconv specifies that the fourth character of an - // international curr_symbol is used to separate the sign and - // value when sep_by_space says to do so. C++ can't represent - // that, so we just use a space. When sep_by_space says to - // separate the symbol and value-or-sign with a space, we rearrange the - // curr_symbol to put its spacing character on the correct side of - // the symbol. - // - // We also need to avoid adding an extra space between the sign - // and value when the currency symbol is suppressed (by not - // setting showbase). We match glibc's strfmon by interpreting - // sep_by_space==1 as "omit the space when the currency symbol is - // absent". - // - // Users who want to get this right should use ICU instead. - - switch (cs_precedes) - { - case 0: // value before curr_symbol - if (symbol_contains_sep) { - // Move the separator to before the symbol, to place it - // between the value and symbol. - rotate(__curr_symbol_.begin(), __curr_symbol_.begin() + 3, - __curr_symbol_.end()); - } - switch (sign_posn) - { - case 0: // Parentheses surround the quantity and currency symbol. - pat.field[0] = sign; - pat.field[1] = value; - pat.field[2] = none; // Any space appears in the symbol. - pat.field[3] = symbol; - switch (sep_by_space) - { - case 0: // No space separates the currency symbol and value. - // This case may have changed between C99 and C11; - // assume the currency symbol matches the intention. - case 2: // Space between sign and currency or value. - // The "sign" is two parentheses, so no space here either. - return; - case 1: // Space between currency-and-sign or currency and value. - if (!symbol_contains_sep) { - // We insert the space into the symbol instead of - // setting pat.field[2]=space so that when - // showbase is not set, the space goes away too. - __curr_symbol_.insert(0, 1, space_char); - } - return; - default: - break; - } - break; - case 1: // The sign string precedes the quantity and currency symbol. - pat.field[0] = sign; - pat.field[3] = symbol; - switch (sep_by_space) - { - case 0: // No space separates the currency symbol and value. - pat.field[1] = value; - pat.field[2] = none; - return; - case 1: // Space between currency-and-sign or currency and value. - pat.field[1] = value; - pat.field[2] = none; - if (!symbol_contains_sep) { - // We insert the space into the symbol instead of - // setting pat.field[2]=space so that when - // showbase is not set, the space goes away too. - __curr_symbol_.insert(0, 1, space_char); - } - return; - case 2: // Space between sign and currency or value. - pat.field[1] = space; - pat.field[2] = value; - if (symbol_contains_sep) { - // Remove the separator from the symbol, since it - // has already appeared after the sign. - __curr_symbol_.erase(__curr_symbol_.begin()); - } - return; - default: - break; - } - break; - case 2: // The sign string succeeds the quantity and currency symbol. - pat.field[0] = value; - pat.field[3] = sign; - switch (sep_by_space) - { - case 0: // No space separates the currency symbol and value. - pat.field[1] = none; - pat.field[2] = symbol; - return; - case 1: // Space between currency-and-sign or currency and value. - if (!symbol_contains_sep) { - // We insert the space into the symbol instead of - // setting pat.field[1]=space so that when - // showbase is not set, the space goes away too. - __curr_symbol_.insert(0, 1, space_char); - } - pat.field[1] = none; - pat.field[2] = symbol; - return; - case 2: // Space between sign and currency or value. - pat.field[1] = symbol; - pat.field[2] = space; - if (symbol_contains_sep) { - // Remove the separator from the symbol, since it - // should not be removed if showbase is absent. - __curr_symbol_.erase(__curr_symbol_.begin()); - } - return; - default: - break; - } - break; - case 3: // The sign string immediately precedes the currency symbol. - pat.field[0] = value; - pat.field[3] = symbol; - switch (sep_by_space) - { - case 0: // No space separates the currency symbol and value. - pat.field[1] = none; - pat.field[2] = sign; - return; - case 1: // Space between currency-and-sign or currency and value. - pat.field[1] = space; - pat.field[2] = sign; - if (symbol_contains_sep) { - // Remove the separator from the symbol, since it - // has already appeared before the sign. - __curr_symbol_.erase(__curr_symbol_.begin()); - } - return; - case 2: // Space between sign and currency or value. - pat.field[1] = sign; - pat.field[2] = none; - if (!symbol_contains_sep) { - // We insert the space into the symbol instead of - // setting pat.field[2]=space so that when - // showbase is not set, the space goes away too. - __curr_symbol_.insert(0, 1, space_char); - } - return; - default: - break; - } - break; - case 4: // The sign string immediately succeeds the currency symbol. - pat.field[0] = value; - pat.field[3] = sign; - switch (sep_by_space) - { - case 0: // No space separates the currency symbol and value. - pat.field[1] = none; - pat.field[2] = symbol; - return; - case 1: // Space between currency-and-sign or currency and value. - pat.field[1] = none; - pat.field[2] = symbol; - if (!symbol_contains_sep) { - // We insert the space into the symbol instead of - // setting pat.field[1]=space so that when - // showbase is not set, the space goes away too. - __curr_symbol_.insert(0, 1, space_char); - } - return; - case 2: // Space between sign and currency or value. - pat.field[1] = symbol; - pat.field[2] = space; - if (symbol_contains_sep) { - // Remove the separator from the symbol, since it - // should not disappear when showbase is absent. - __curr_symbol_.erase(__curr_symbol_.begin()); - } - return; - default: - break; - } - break; - default: - break; - } - break; - case 1: // curr_symbol before value - switch (sign_posn) - { - case 0: // Parentheses surround the quantity and currency symbol. - pat.field[0] = sign; - pat.field[1] = symbol; - pat.field[2] = none; // Any space appears in the symbol. - pat.field[3] = value; - switch (sep_by_space) - { - case 0: // No space separates the currency symbol and value. - // This case may have changed between C99 and C11; - // assume the currency symbol matches the intention. - case 2: // Space between sign and currency or value. - // The "sign" is two parentheses, so no space here either. - return; - case 1: // Space between currency-and-sign or currency and value. - if (!symbol_contains_sep) { - // We insert the space into the symbol instead of - // setting pat.field[2]=space so that when - // showbase is not set, the space goes away too. - __curr_symbol_.insert(0, 1, space_char); - } - return; - default: - break; - } - break; - case 1: // The sign string precedes the quantity and currency symbol. - pat.field[0] = sign; - pat.field[3] = value; - switch (sep_by_space) - { - case 0: // No space separates the currency symbol and value. - pat.field[1] = symbol; - pat.field[2] = none; - return; - case 1: // Space between currency-and-sign or currency and value. - pat.field[1] = symbol; - pat.field[2] = none; - if (!symbol_contains_sep) { - // We insert the space into the symbol instead of - // setting pat.field[2]=space so that when - // showbase is not set, the space goes away too. - __curr_symbol_.push_back(space_char); - } - return; - case 2: // Space between sign and currency or value. - pat.field[1] = space; - pat.field[2] = symbol; - if (symbol_contains_sep) { - // Remove the separator from the symbol, since it - // has already appeared after the sign. - __curr_symbol_.pop_back(); - } - return; - default: - break; - } - break; - case 2: // The sign string succeeds the quantity and currency symbol. - pat.field[0] = symbol; - pat.field[3] = sign; - switch (sep_by_space) - { - case 0: // No space separates the currency symbol and value. - pat.field[1] = none; - pat.field[2] = value; - return; - case 1: // Space between currency-and-sign or currency and value. - pat.field[1] = none; - pat.field[2] = value; - if (!symbol_contains_sep) { - // We insert the space into the symbol instead of - // setting pat.field[1]=space so that when - // showbase is not set, the space goes away too. - __curr_symbol_.push_back(space_char); - } - return; - case 2: // Space between sign and currency or value. - pat.field[1] = value; - pat.field[2] = space; - if (symbol_contains_sep) { - // Remove the separator from the symbol, since it - // will appear before the sign. - __curr_symbol_.pop_back(); - } - return; - default: - break; - } - break; - case 3: // The sign string immediately precedes the currency symbol. - pat.field[0] = sign; - pat.field[3] = value; - switch (sep_by_space) - { - case 0: // No space separates the currency symbol and value. - pat.field[1] = symbol; - pat.field[2] = none; - return; - case 1: // Space between currency-and-sign or currency and value. - pat.field[1] = symbol; - pat.field[2] = none; - if (!symbol_contains_sep) { - // We insert the space into the symbol instead of - // setting pat.field[2]=space so that when - // showbase is not set, the space goes away too. - __curr_symbol_.push_back(space_char); - } - return; - case 2: // Space between sign and currency or value. - pat.field[1] = space; - pat.field[2] = symbol; - if (symbol_contains_sep) { - // Remove the separator from the symbol, since it - // has already appeared after the sign. - __curr_symbol_.pop_back(); - } - return; - default: - break; - } - break; - case 4: // The sign string immediately succeeds the currency symbol. - pat.field[0] = symbol; - pat.field[3] = value; - switch (sep_by_space) - { - case 0: // No space separates the currency symbol and value. - pat.field[1] = sign; - pat.field[2] = none; - return; - case 1: // Space between currency-and-sign or currency and value. - pat.field[1] = sign; - pat.field[2] = space; - if (symbol_contains_sep) { - // Remove the separator from the symbol, since it - // should not disappear when showbase is absent. - __curr_symbol_.pop_back(); - } - return; - case 2: // Space between sign and currency or value. - pat.field[1] = none; - pat.field[2] = sign; - if (!symbol_contains_sep) { - // We insert the space into the symbol instead of - // setting pat.field[1]=space so that when - // showbase is not set, the space goes away too. - __curr_symbol_.push_back(space_char); - } - return; - default: - break; - } - break; - default: - break; - } - break; - default: - break; - } - pat.field[0] = symbol; - pat.field[1] = sign; - pat.field[2] = none; - pat.field[3] = value; -} - -template<> -void -moneypunct_byname<char, false>::init(const char* nm) -{ - typedef moneypunct<char, false> base; - __libcpp_unique_locale loc(nm); - if (!loc) - __throw_runtime_error("moneypunct_byname" - " failed to construct for " + string(nm)); - - lconv* lc = __libcpp_localeconv_l(loc.get()); - if (!checked_string_to_char_convert(__decimal_point_, - lc->mon_decimal_point, - loc.get())) - __decimal_point_ = base::do_decimal_point(); - if (!checked_string_to_char_convert(__thousands_sep_, - lc->mon_thousands_sep, - loc.get())) - __thousands_sep_ = base::do_thousands_sep(); - - __grouping_ = lc->mon_grouping; - __curr_symbol_ = lc->currency_symbol; - if (lc->frac_digits != CHAR_MAX) - __frac_digits_ = lc->frac_digits; - else - __frac_digits_ = base::do_frac_digits(); - if (lc->p_sign_posn == 0) - __positive_sign_ = "()"; - else - __positive_sign_ = lc->positive_sign; - if (lc->n_sign_posn == 0) - __negative_sign_ = "()"; - else - __negative_sign_ = lc->negative_sign; - // Assume the positive and negative formats will want spaces in - // the same places in curr_symbol since there's no way to - // represent anything else. - string_type __dummy_curr_symbol = __curr_symbol_; - __init_pat(__pos_format_, __dummy_curr_symbol, false, - lc->p_cs_precedes, lc->p_sep_by_space, lc->p_sign_posn, ' '); - __init_pat(__neg_format_, __curr_symbol_, false, - lc->n_cs_precedes, lc->n_sep_by_space, lc->n_sign_posn, ' '); -} - -template<> -void -moneypunct_byname<char, true>::init(const char* nm) -{ - typedef moneypunct<char, true> base; - __libcpp_unique_locale loc(nm); - if (!loc) - __throw_runtime_error("moneypunct_byname" - " failed to construct for " + string(nm)); - - lconv* lc = __libcpp_localeconv_l(loc.get()); - if (!checked_string_to_char_convert(__decimal_point_, - lc->mon_decimal_point, - loc.get())) - __decimal_point_ = base::do_decimal_point(); - if (!checked_string_to_char_convert(__thousands_sep_, - lc->mon_thousands_sep, - loc.get())) - __thousands_sep_ = base::do_thousands_sep(); - __grouping_ = lc->mon_grouping; - __curr_symbol_ = lc->int_curr_symbol; - if (lc->int_frac_digits != CHAR_MAX) - __frac_digits_ = lc->int_frac_digits; - else - __frac_digits_ = base::do_frac_digits(); -#if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__) - if (lc->p_sign_posn == 0) -#else // _LIBCPP_MSVCRT - if (lc->int_p_sign_posn == 0) -#endif // !_LIBCPP_MSVCRT - __positive_sign_ = "()"; - else - __positive_sign_ = lc->positive_sign; -#if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__) - if(lc->n_sign_posn == 0) -#else // _LIBCPP_MSVCRT - if (lc->int_n_sign_posn == 0) -#endif // !_LIBCPP_MSVCRT - __negative_sign_ = "()"; - else - __negative_sign_ = lc->negative_sign; - // Assume the positive and negative formats will want spaces in - // the same places in curr_symbol since there's no way to - // represent anything else. - string_type __dummy_curr_symbol = __curr_symbol_; -#if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__) - __init_pat(__pos_format_, __dummy_curr_symbol, true, - lc->p_cs_precedes, lc->p_sep_by_space, lc->p_sign_posn, ' '); - __init_pat(__neg_format_, __curr_symbol_, true, - lc->n_cs_precedes, lc->n_sep_by_space, lc->n_sign_posn, ' '); -#else // _LIBCPP_MSVCRT - __init_pat(__pos_format_, __dummy_curr_symbol, true, - lc->int_p_cs_precedes, lc->int_p_sep_by_space, - lc->int_p_sign_posn, ' '); - __init_pat(__neg_format_, __curr_symbol_, true, - lc->int_n_cs_precedes, lc->int_n_sep_by_space, - lc->int_n_sign_posn, ' '); -#endif // !_LIBCPP_MSVCRT -} - -template<> -void -moneypunct_byname<wchar_t, false>::init(const char* nm) -{ - typedef moneypunct<wchar_t, false> base; - __libcpp_unique_locale loc(nm); - if (!loc) - __throw_runtime_error("moneypunct_byname" - " failed to construct for " + string(nm)); - lconv* lc = __libcpp_localeconv_l(loc.get()); - if (!checked_string_to_wchar_convert(__decimal_point_, - lc->mon_decimal_point, - loc.get())) - __decimal_point_ = base::do_decimal_point(); - if (!checked_string_to_wchar_convert(__thousands_sep_, - lc->mon_thousands_sep, - loc.get())) - __thousands_sep_ = base::do_thousands_sep(); - __grouping_ = lc->mon_grouping; - wchar_t wbuf[100]; - mbstate_t mb = {0}; - const char* bb = lc->currency_symbol; - size_t j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, loc.get()); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wchar_t* wbe = wbuf + j; - __curr_symbol_.assign(wbuf, wbe); - if (lc->frac_digits != CHAR_MAX) - __frac_digits_ = lc->frac_digits; - else - __frac_digits_ = base::do_frac_digits(); - if (lc->p_sign_posn == 0) - __positive_sign_ = L"()"; - else - { - mb = mbstate_t(); - bb = lc->positive_sign; - j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, loc.get()); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wbe = wbuf + j; - __positive_sign_.assign(wbuf, wbe); - } - if (lc->n_sign_posn == 0) - __negative_sign_ = L"()"; - else - { - mb = mbstate_t(); - bb = lc->negative_sign; - j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, loc.get()); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wbe = wbuf + j; - __negative_sign_.assign(wbuf, wbe); - } - // Assume the positive and negative formats will want spaces in - // the same places in curr_symbol since there's no way to - // represent anything else. - string_type __dummy_curr_symbol = __curr_symbol_; - __init_pat(__pos_format_, __dummy_curr_symbol, false, - lc->p_cs_precedes, lc->p_sep_by_space, lc->p_sign_posn, L' '); - __init_pat(__neg_format_, __curr_symbol_, false, - lc->n_cs_precedes, lc->n_sep_by_space, lc->n_sign_posn, L' '); -} - -template<> -void -moneypunct_byname<wchar_t, true>::init(const char* nm) -{ - typedef moneypunct<wchar_t, true> base; - __libcpp_unique_locale loc(nm); - if (!loc) - __throw_runtime_error("moneypunct_byname" - " failed to construct for " + string(nm)); - - lconv* lc = __libcpp_localeconv_l(loc.get()); - if (!checked_string_to_wchar_convert(__decimal_point_, - lc->mon_decimal_point, - loc.get())) - __decimal_point_ = base::do_decimal_point(); - if (!checked_string_to_wchar_convert(__thousands_sep_, - lc->mon_thousands_sep, - loc.get())) - __thousands_sep_ = base::do_thousands_sep(); - __grouping_ = lc->mon_grouping; - wchar_t wbuf[100]; - mbstate_t mb = {0}; - const char* bb = lc->int_curr_symbol; - size_t j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, loc.get()); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wchar_t* wbe = wbuf + j; - __curr_symbol_.assign(wbuf, wbe); - if (lc->int_frac_digits != CHAR_MAX) - __frac_digits_ = lc->int_frac_digits; - else - __frac_digits_ = base::do_frac_digits(); -#if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__) - if (lc->p_sign_posn == 0) -#else // _LIBCPP_MSVCRT - if (lc->int_p_sign_posn == 0) -#endif // !_LIBCPP_MSVCRT - __positive_sign_ = L"()"; - else - { - mb = mbstate_t(); - bb = lc->positive_sign; - j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, loc.get()); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wbe = wbuf + j; - __positive_sign_.assign(wbuf, wbe); - } -#if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__) - if (lc->n_sign_posn == 0) -#else // _LIBCPP_MSVCRT - if (lc->int_n_sign_posn == 0) -#endif // !_LIBCPP_MSVCRT - __negative_sign_ = L"()"; - else - { - mb = mbstate_t(); - bb = lc->negative_sign; - j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, loc.get()); - if (j == size_t(-1)) - __throw_runtime_error("locale not supported"); - wbe = wbuf + j; - __negative_sign_.assign(wbuf, wbe); - } - // Assume the positive and negative formats will want spaces in - // the same places in curr_symbol since there's no way to - // represent anything else. - string_type __dummy_curr_symbol = __curr_symbol_; -#if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__) - __init_pat(__pos_format_, __dummy_curr_symbol, true, - lc->p_cs_precedes, lc->p_sep_by_space, lc->p_sign_posn, L' '); - __init_pat(__neg_format_, __curr_symbol_, true, - lc->n_cs_precedes, lc->n_sep_by_space, lc->n_sign_posn, L' '); -#else // _LIBCPP_MSVCRT - __init_pat(__pos_format_, __dummy_curr_symbol, true, - lc->int_p_cs_precedes, lc->int_p_sep_by_space, - lc->int_p_sign_posn, L' '); - __init_pat(__neg_format_, __curr_symbol_, true, - lc->int_n_cs_precedes, lc->int_n_sep_by_space, - lc->int_n_sign_posn, L' '); -#endif // !_LIBCPP_MSVCRT -} - -void __do_nothing(void*) {} - -void __throw_runtime_error(const char* msg) -{ -#ifndef _LIBCPP_NO_EXCEPTIONS - throw runtime_error(msg); -#else - (void)msg; - _VSTD::abort(); -#endif -} - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS collate<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS collate<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS num_get<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS num_get<wchar_t>; - -template struct _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __num_get<char>; -template struct _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __num_get<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS num_put<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS num_put<wchar_t>; - -template struct _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __num_put<char>; -template struct _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __num_put<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_get<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_get<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_get_byname<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_get_byname<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_put<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_put<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_put_byname<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_put_byname<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct<char, false>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct<char, true>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct<wchar_t, false>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct<wchar_t, true>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct_byname<char, false>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct_byname<char, true>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct_byname<wchar_t, false>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct_byname<wchar_t, true>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS money_get<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS money_get<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __money_get<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __money_get<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS money_put<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS money_put<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __money_put<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __money_put<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS messages<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS messages<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS messages_byname<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS messages_byname<wchar_t>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<char, char, mbstate_t>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<wchar_t, char, mbstate_t>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<char16_t, char, mbstate_t>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<char32_t, char, mbstate_t>; - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/memory.cpp b/lib/libcxx/src/memory.cpp deleted file mode 100644 index 77ebe837c73..00000000000 --- a/lib/libcxx/src/memory.cpp +++ /dev/null @@ -1,235 +0,0 @@ -//===------------------------ memory.cpp ----------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "memory" -#ifndef _LIBCPP_HAS_NO_THREADS -#include "mutex" -#include "thread" -#endif -#include "include/atomic_support.h" - -_LIBCPP_BEGIN_NAMESPACE_STD - -const allocator_arg_t allocator_arg = allocator_arg_t(); - -bad_weak_ptr::~bad_weak_ptr() _NOEXCEPT {} - -const char* -bad_weak_ptr::what() const _NOEXCEPT -{ - return "bad_weak_ptr"; -} - -__shared_count::~__shared_count() -{ -} - -__shared_weak_count::~__shared_weak_count() -{ -} - -#if defined(_LIBCPP_DEPRECATED_ABI_LEGACY_LIBRARY_DEFINITIONS_FOR_INLINE_FUNCTIONS) -void -__shared_count::__add_shared() _NOEXCEPT -{ - __libcpp_atomic_refcount_increment(__shared_owners_); -} - -bool -__shared_count::__release_shared() _NOEXCEPT -{ - if (__libcpp_atomic_refcount_decrement(__shared_owners_) == -1) - { - __on_zero_shared(); - return true; - } - return false; -} - -void -__shared_weak_count::__add_shared() _NOEXCEPT -{ - __shared_count::__add_shared(); -} - -void -__shared_weak_count::__add_weak() _NOEXCEPT -{ - __libcpp_atomic_refcount_increment(__shared_weak_owners_); -} - -void -__shared_weak_count::__release_shared() _NOEXCEPT -{ - if (__shared_count::__release_shared()) - __release_weak(); -} - -#endif // _LIBCPP_DEPRECATED_ABI_LEGACY_LIBRARY_DEFINITIONS_FOR_INLINE_FUNCTIONS - -void -__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 - // having no other contended references. - // - // BENEFIT: We avoid expensive atomic stores like XADD and STREX - // in a common case. Those instructions are slow and do nasty - // things to caches. - // - // IS THIS SAFE? Yes. During weak destruction, if we see that we - // are the last reference, we know that no-one else is accessing - // us. If someone were accessing us, then they would be doing so - // while the last shared / weak_ptr was being destructed, and - // that's undefined anyway. - // - // If we see anything other than a 0, then we have possible - // contention, and need to use an atomicrmw primitive. - // The same arguments don't apply for increment, where it is legal - // (though inadvisable) to share shared_ptr references between - // threads, and have them all get copied at once. The argument - // also doesn't apply for __release_shared, because an outstanding - // weak_ptr::lock() could read / modify the shared count. - if (__libcpp_atomic_load(&__shared_weak_owners_, _AO_Acquire) == 0) - { - // no need to do this store, because we are about - // to destroy everything. - //__libcpp_atomic_store(&__shared_weak_owners_, -1, _AO_Release); - __on_zero_shared_weak(); - } - else if (__libcpp_atomic_refcount_decrement(__shared_weak_owners_) == -1) - __on_zero_shared_weak(); -} - -__shared_weak_count* -__shared_weak_count::lock() _NOEXCEPT -{ - long object_owners = __libcpp_atomic_load(&__shared_owners_); - while (object_owners != -1) - { - if (__libcpp_atomic_compare_exchange(&__shared_owners_, - &object_owners, - object_owners+1)) - return this; - } - return nullptr; -} - -#if !defined(_LIBCPP_NO_RTTI) || !defined(_LIBCPP_BUILD_STATIC) - -const void* -__shared_weak_count::__get_deleter(const type_info&) const _NOEXCEPT -{ - return nullptr; -} - -#endif // _LIBCPP_NO_RTTI - -#if !defined(_LIBCPP_HAS_NO_ATOMIC_HEADER) - -_LIBCPP_SAFE_STATIC static const std::size_t __sp_mut_count = 16; -_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_MUTEX_INITIALIZER, _LIBCPP_MUTEX_INITIALIZER, _LIBCPP_MUTEX_INITIALIZER, _LIBCPP_MUTEX_INITIALIZER, - _LIBCPP_MUTEX_INITIALIZER, _LIBCPP_MUTEX_INITIALIZER, _LIBCPP_MUTEX_INITIALIZER, _LIBCPP_MUTEX_INITIALIZER, - _LIBCPP_MUTEX_INITIALIZER, _LIBCPP_MUTEX_INITIALIZER, _LIBCPP_MUTEX_INITIALIZER, _LIBCPP_MUTEX_INITIALIZER -}; - -_LIBCPP_CONSTEXPR __sp_mut::__sp_mut(void* p) _NOEXCEPT - : __lx(p) -{ -} - -void -__sp_mut::lock() _NOEXCEPT -{ - auto m = static_cast<__libcpp_mutex_t*>(__lx); - unsigned count = 0; - while (!__libcpp_mutex_trylock(m)) - { - if (++count > 16) - { - __libcpp_mutex_lock(m); - break; - } - this_thread::yield(); - } -} - -void -__sp_mut::unlock() _NOEXCEPT -{ - __libcpp_mutex_unlock(static_cast<__libcpp_mutex_t*>(__lx)); -} - -__sp_mut& -__get_sp_mut(const void* p) -{ - static __sp_mut muts[__sp_mut_count] - { - &mut_back[ 0], &mut_back[ 1], &mut_back[ 2], &mut_back[ 3], - &mut_back[ 4], &mut_back[ 5], &mut_back[ 6], &mut_back[ 7], - &mut_back[ 8], &mut_back[ 9], &mut_back[10], &mut_back[11], - &mut_back[12], &mut_back[13], &mut_back[14], &mut_back[15] - }; - return muts[hash<const void*>()(p) & (__sp_mut_count-1)]; -} - -#endif // !defined(_LIBCPP_HAS_NO_ATOMIC_HEADER) - -void -declare_reachable(void*) -{ -} - -void -declare_no_pointers(char*, size_t) -{ -} - -void -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) -{ - return p; -} - -void* -align(size_t alignment, size_t size, void*& ptr, size_t& space) -{ - void* r = nullptr; - if (size <= space) - { - char* p1 = static_cast<char*>(ptr); - char* p2 = reinterpret_cast<char*>(reinterpret_cast<size_t>(p1 + (alignment - 1)) & -alignment); - size_t d = static_cast<size_t>(p2 - p1); - if (d <= space - size) - { - r = p2; - ptr = r; - space -= d; - } - } - return r; -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/mutex.cpp b/lib/libcxx/src/mutex.cpp deleted file mode 100644 index c61d34bb885..00000000000 --- a/lib/libcxx/src/mutex.cpp +++ /dev/null @@ -1,258 +0,0 @@ -//===------------------------- mutex.cpp ----------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "mutex" -#include "limits" -#include "system_error" -#include "include/atomic_support.h" -#include "__undef_macros" - -_LIBCPP_BEGIN_NAMESPACE_STD -#ifndef _LIBCPP_HAS_NO_THREADS - -const defer_lock_t defer_lock = {}; -const try_to_lock_t try_to_lock = {}; -const adopt_lock_t adopt_lock = {}; - -mutex::~mutex() -{ - __libcpp_mutex_destroy(&__m_); -} - -void -mutex::lock() -{ - int ec = __libcpp_mutex_lock(&__m_); - if (ec) - __throw_system_error(ec, "mutex lock failed"); -} - -bool -mutex::try_lock() _NOEXCEPT -{ - return __libcpp_mutex_trylock(&__m_); -} - -void -mutex::unlock() _NOEXCEPT -{ - int ec = __libcpp_mutex_unlock(&__m_); - (void)ec; - _LIBCPP_ASSERT(ec == 0, "call to mutex::unlock failed"); -} - -// recursive_mutex - -recursive_mutex::recursive_mutex() -{ - int ec = __libcpp_recursive_mutex_init(&__m_); - if (ec) - __throw_system_error(ec, "recursive_mutex constructor failed"); -} - -recursive_mutex::~recursive_mutex() -{ - int e = __libcpp_recursive_mutex_destroy(&__m_); - (void)e; - _LIBCPP_ASSERT(e == 0, "call to ~recursive_mutex() failed"); -} - -void -recursive_mutex::lock() -{ - int ec = __libcpp_recursive_mutex_lock(&__m_); - if (ec) - __throw_system_error(ec, "recursive_mutex lock failed"); -} - -void -recursive_mutex::unlock() _NOEXCEPT -{ - int e = __libcpp_recursive_mutex_unlock(&__m_); - (void)e; - _LIBCPP_ASSERT(e == 0, "call to recursive_mutex::unlock() failed"); -} - -bool -recursive_mutex::try_lock() _NOEXCEPT -{ - return __libcpp_recursive_mutex_trylock(&__m_); -} - -// timed_mutex - -timed_mutex::timed_mutex() - : __locked_(false) -{ -} - -timed_mutex::~timed_mutex() -{ - lock_guard<mutex> _(__m_); -} - -void -timed_mutex::lock() -{ - unique_lock<mutex> lk(__m_); - while (__locked_) - __cv_.wait(lk); - __locked_ = true; -} - -bool -timed_mutex::try_lock() _NOEXCEPT -{ - unique_lock<mutex> lk(__m_, try_to_lock); - if (lk.owns_lock() && !__locked_) - { - __locked_ = true; - return true; - } - return false; -} - -void -timed_mutex::unlock() _NOEXCEPT -{ - lock_guard<mutex> _(__m_); - __locked_ = false; - __cv_.notify_one(); -} - -// recursive_timed_mutex - -recursive_timed_mutex::recursive_timed_mutex() - : __count_(0), - __id_(0) -{ -} - -recursive_timed_mutex::~recursive_timed_mutex() -{ - lock_guard<mutex> _(__m_); -} - -void -recursive_timed_mutex::lock() -{ - __libcpp_thread_id id = __libcpp_thread_get_current_id(); - unique_lock<mutex> lk(__m_); - if (__libcpp_thread_id_equal(id, __id_)) - { - if (__count_ == numeric_limits<size_t>::max()) - __throw_system_error(EAGAIN, "recursive_timed_mutex lock limit reached"); - ++__count_; - return; - } - while (__count_ != 0) - __cv_.wait(lk); - __count_ = 1; - __id_ = id; -} - -bool -recursive_timed_mutex::try_lock() _NOEXCEPT -{ - __libcpp_thread_id id = __libcpp_thread_get_current_id(); - unique_lock<mutex> lk(__m_, try_to_lock); - if (lk.owns_lock() && (__count_ == 0 || __libcpp_thread_id_equal(id, __id_))) - { - if (__count_ == numeric_limits<size_t>::max()) - return false; - ++__count_; - __id_ = id; - return true; - } - return false; -} - -void -recursive_timed_mutex::unlock() _NOEXCEPT -{ - unique_lock<mutex> lk(__m_); - if (--__count_ == 0) - { - __id_ = 0; - lk.unlock(); - __cv_.notify_one(); - } -} - -#endif // !_LIBCPP_HAS_NO_THREADS - -// If dispatch_once_f ever handles C++ exceptions, and if one can get to it -// without illegal macros (unexpected macros not beginning with _UpperCase or -// __lowercase), and if it stops spinning waiting threads, then call_once should -// call into dispatch_once_f instead of here. Relevant radar this code needs to -// keep in sync with: 7741191. - -#ifndef _LIBCPP_HAS_NO_THREADS -_LIBCPP_SAFE_STATIC static __libcpp_mutex_t mut = _LIBCPP_MUTEX_INITIALIZER; -_LIBCPP_SAFE_STATIC static __libcpp_condvar_t cv = _LIBCPP_CONDVAR_INITIALIZER; -#endif - -void -__call_once(volatile unsigned long& flag, void* arg, void(*func)(void*)) -{ -#if defined(_LIBCPP_HAS_NO_THREADS) - if (flag == 0) - { -#ifndef _LIBCPP_NO_EXCEPTIONS - try - { -#endif // _LIBCPP_NO_EXCEPTIONS - flag = 1; - func(arg); - flag = ~0ul; -#ifndef _LIBCPP_NO_EXCEPTIONS - } - catch (...) - { - flag = 0ul; - throw; - } -#endif // _LIBCPP_NO_EXCEPTIONS - } -#else // !_LIBCPP_HAS_NO_THREADS - __libcpp_mutex_lock(&mut); - while (flag == 1) - __libcpp_condvar_wait(&cv, &mut); - if (flag == 0) - { -#ifndef _LIBCPP_NO_EXCEPTIONS - try - { -#endif // _LIBCPP_NO_EXCEPTIONS - __libcpp_relaxed_store(&flag, 1ul); - __libcpp_mutex_unlock(&mut); - func(arg); - __libcpp_mutex_lock(&mut); - __libcpp_atomic_store(&flag, ~0ul, _AO_Release); - __libcpp_mutex_unlock(&mut); - __libcpp_condvar_broadcast(&cv); -#ifndef _LIBCPP_NO_EXCEPTIONS - } - catch (...) - { - __libcpp_mutex_lock(&mut); - __libcpp_relaxed_store(&flag, 0ul); - __libcpp_mutex_unlock(&mut); - __libcpp_condvar_broadcast(&cv); - throw; - } -#endif // _LIBCPP_NO_EXCEPTIONS - } - else - __libcpp_mutex_unlock(&mut); -#endif // !_LIBCPP_HAS_NO_THREADS - -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/new.cpp b/lib/libcxx/src/new.cpp deleted file mode 100644 index cc8383d4f14..00000000000 --- a/lib/libcxx/src/new.cpp +++ /dev/null @@ -1,302 +0,0 @@ -//===--------------------------- new.cpp ----------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include <stdlib.h> - -#include "new" -#include "include/atomic_support.h" - -#if defined(_LIBCPP_ABI_MICROSOFT) -#if defined(_LIBCPP_NO_VCRUNTIME) -#include "support/runtime/new_handler_fallback.ipp" -#endif -#elif defined(LIBCXX_BUILDING_LIBCXXABI) -#include <cxxabi.h> -#elif defined(LIBCXXRT) -#include <cxxabi.h> -#include "support/runtime/new_handler_fallback.ipp" -#elif defined(__GLIBCXX__) -// nothing todo -#else -# if defined(__APPLE__) && !defined(_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY) -# include <cxxabi.h> // FIXME: remove this once buildit is gone. -# else -# include "support/runtime/new_handler_fallback.ipp" -# endif -#endif - -namespace std -{ - -#ifndef __GLIBCXX__ -const nothrow_t nothrow = {}; -#endif - -#ifndef LIBSTDCXX - -void -__throw_bad_alloc() -{ -#ifndef _LIBCPP_NO_EXCEPTIONS - throw bad_alloc(); -#else - _VSTD::abort(); -#endif -} - -#endif // !LIBSTDCXX - -} // std - -#if !defined(__GLIBCXX__) && \ - !defined(_LIBCPP_DEFER_NEW_TO_VCRUNTIME) && \ - !defined(_LIBCPP_DISABLE_NEW_DELETE_DEFINITIONS) - -// Implement all new and delete operators as weak definitions -// in this shared library, so that they can be overridden by programs -// that define non-weak copies of the functions. - -_LIBCPP_WEAK -void * -operator new(std::size_t size) _THROW_BAD_ALLOC -{ - if (size == 0) - size = 1; - void* p; - while ((p = ::malloc(size)) == 0) - { - // If malloc fails and there is a new_handler, - // call it to try free up memory. - std::new_handler nh = std::get_new_handler(); - if (nh) - nh(); - else -#ifndef _LIBCPP_NO_EXCEPTIONS - throw std::bad_alloc(); -#else - break; -#endif - } - return p; -} - -_LIBCPP_WEAK -void* -operator new(size_t size, const std::nothrow_t&) _NOEXCEPT -{ - void* p = 0; -#ifndef _LIBCPP_NO_EXCEPTIONS - try - { -#endif // _LIBCPP_NO_EXCEPTIONS - p = ::operator new(size); -#ifndef _LIBCPP_NO_EXCEPTIONS - } - catch (...) - { - } -#endif // _LIBCPP_NO_EXCEPTIONS - return p; -} - -_LIBCPP_WEAK -void* -operator new[](size_t size) _THROW_BAD_ALLOC -{ - return ::operator new(size); -} - -_LIBCPP_WEAK -void* -operator new[](size_t size, const std::nothrow_t&) _NOEXCEPT -{ - void* p = 0; -#ifndef _LIBCPP_NO_EXCEPTIONS - try - { -#endif // _LIBCPP_NO_EXCEPTIONS - p = ::operator new[](size); -#ifndef _LIBCPP_NO_EXCEPTIONS - } - catch (...) - { - } -#endif // _LIBCPP_NO_EXCEPTIONS - return p; -} - -_LIBCPP_WEAK -void -operator delete(void* ptr) _NOEXCEPT -{ - ::free(ptr); -} - -_LIBCPP_WEAK -void -operator delete(void* ptr, const std::nothrow_t&) _NOEXCEPT -{ - ::operator delete(ptr); -} - -_LIBCPP_WEAK -void -operator delete(void* ptr, size_t) _NOEXCEPT -{ - ::operator delete(ptr); -} - -_LIBCPP_WEAK -void -operator delete[] (void* ptr) _NOEXCEPT -{ - ::operator delete(ptr); -} - -_LIBCPP_WEAK -void -operator delete[] (void* ptr, const std::nothrow_t&) _NOEXCEPT -{ - ::operator delete[](ptr); -} - -_LIBCPP_WEAK -void -operator delete[] (void* ptr, size_t) _NOEXCEPT -{ - ::operator delete[](ptr); -} - -#if !defined(_LIBCPP_HAS_NO_LIBRARY_ALIGNED_ALLOCATION) - -_LIBCPP_WEAK -void * -operator new(std::size_t size, std::align_val_t alignment) _THROW_BAD_ALLOC -{ - if (size == 0) - size = 1; - if (static_cast<size_t>(alignment) < sizeof(void*)) - alignment = std::align_val_t(sizeof(void*)); - void* p; -#if defined(_LIBCPP_MSVCRT_LIKE) - while ((p = _aligned_malloc(size, static_cast<size_t>(alignment))) == nullptr) -#else - while (::posix_memalign(&p, static_cast<size_t>(alignment), size) != 0) -#endif - { - // If posix_memalign fails and there is a new_handler, - // call it to try free up memory. - std::new_handler nh = std::get_new_handler(); - if (nh) - nh(); - else { -#ifndef _LIBCPP_NO_EXCEPTIONS - throw std::bad_alloc(); -#else - p = nullptr; // posix_memalign doesn't initialize 'p' on failure - break; -#endif - } - } - return p; -} - -_LIBCPP_WEAK -void* -operator new(size_t size, std::align_val_t alignment, const std::nothrow_t&) _NOEXCEPT -{ - void* p = 0; -#ifndef _LIBCPP_NO_EXCEPTIONS - try - { -#endif // _LIBCPP_NO_EXCEPTIONS - p = ::operator new(size, alignment); -#ifndef _LIBCPP_NO_EXCEPTIONS - } - catch (...) - { - } -#endif // _LIBCPP_NO_EXCEPTIONS - return p; -} - -_LIBCPP_WEAK -void* -operator new[](size_t size, std::align_val_t alignment) _THROW_BAD_ALLOC -{ - return ::operator new(size, alignment); -} - -_LIBCPP_WEAK -void* -operator new[](size_t size, std::align_val_t alignment, const std::nothrow_t&) _NOEXCEPT -{ - void* p = 0; -#ifndef _LIBCPP_NO_EXCEPTIONS - try - { -#endif // _LIBCPP_NO_EXCEPTIONS - p = ::operator new[](size, alignment); -#ifndef _LIBCPP_NO_EXCEPTIONS - } - catch (...) - { - } -#endif // _LIBCPP_NO_EXCEPTIONS - return p; -} - -_LIBCPP_WEAK -void -operator delete(void* ptr, std::align_val_t) _NOEXCEPT -{ -#if defined(_LIBCPP_MSVCRT_LIKE) - ::_aligned_free(ptr); -#else - ::free(ptr); -#endif -} - -_LIBCPP_WEAK -void -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(ptr, alignment); -} - -_LIBCPP_WEAK -void -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[](ptr, alignment); -} - -_LIBCPP_WEAK -void -operator delete[] (void* ptr, size_t, std::align_val_t alignment) _NOEXCEPT -{ - ::operator delete[](ptr, alignment); -} - -#endif // !_LIBCPP_HAS_NO_LIBRARY_ALIGNED_ALLOCATION -#endif // !__GLIBCXX__ && (!_LIBCPP_ABI_MICROSOFT || _LIBCPP_NO_VCRUNTIME) && !_LIBCPP_DISABLE_NEW_DELETE_DEFINITIONS diff --git a/lib/libcxx/src/optional.cpp b/lib/libcxx/src/optional.cpp deleted file mode 100644 index 6099b6b41e8..00000000000 --- a/lib/libcxx/src/optional.cpp +++ /dev/null @@ -1,42 +0,0 @@ -//===------------------------ optional.cpp --------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "optional" - -namespace std -{ - -bad_optional_access::~bad_optional_access() _NOEXCEPT = default; - -const char* bad_optional_access::what() const _NOEXCEPT { - return "bad_optional_access"; - } - -} // std - - -#include <experimental/__config> - -// Preserve std::experimental::bad_optional_access for ABI compatibility -// Even though it no longer exists in a header file -_LIBCPP_BEGIN_NAMESPACE_EXPERIMENTAL - -class _LIBCPP_EXCEPTION_ABI _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS bad_optional_access - : public std::logic_error -{ -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; -}; - -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 deleted file mode 100644 index 9efac7a66a7..00000000000 --- a/lib/libcxx/src/random.cpp +++ /dev/null @@ -1,184 +0,0 @@ -//===-------------------------- random.cpp --------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include <__config> - -#if defined(_LIBCPP_USING_WIN32_RANDOM) -// Must be defined before including stdlib.h to enable rand_s(). -#define _CRT_RAND_S -#endif // defined(_LIBCPP_USING_WIN32_RANDOM) - -#include "random" -#include "system_error" - -#if defined(__sun__) -#define rename solaris_headers_are_broken -#endif // defined(__sun__) - -#include <errno.h> -#include <stdio.h> -#include <stdlib.h> - -#if defined(_LIBCPP_USING_GETENTROPY) -#include <sys/random.h> -#elif defined(_LIBCPP_USING_DEV_RANDOM) -#include <fcntl.h> -#include <unistd.h> -#elif defined(_LIBCPP_USING_NACL_RANDOM) -#include <nacl/nacl_random.h> -#endif - -#include <limits> - -_LIBCPP_BEGIN_NAMESPACE_STD - -#if defined(_LIBCPP_USING_GETENTROPY) - -random_device::random_device(const string& __token) -{ - if (__token != "/dev/urandom") - __throw_system_error(ENOENT, ("random device not supported " + __token).c_str()); -} - -random_device::~random_device() -{ -} - -unsigned -random_device::operator()() -{ - unsigned r; - size_t n = sizeof(r); - int err = getentropy(&r, n); - if (err) - __throw_system_error(errno, "random_device getentropy failed"); - return r; -} - -#elif defined(_LIBCPP_USING_ARC4_RANDOM) - -random_device::random_device(const string& __token) -{ - if (__token != "/dev/urandom") - __throw_system_error(ENOENT, ("random device not supported " + __token).c_str()); -} - -random_device::~random_device() -{ -} - -unsigned -random_device::operator()() -{ - return arc4random(); -} - -#elif defined(_LIBCPP_USING_DEV_RANDOM) - -random_device::random_device(const string& __token) - : __f_(open(__token.c_str(), O_RDONLY)) -{ - if (__f_ < 0) - __throw_system_error(errno, ("random_device failed to open " + __token).c_str()); -} - -random_device::~random_device() -{ - close(__f_); -} - -unsigned -random_device::operator()() -{ - unsigned r; - size_t n = sizeof(r); - char* p = reinterpret_cast<char*>(&r); - while (n > 0) - { - ssize_t s = read(__f_, p, n); - if (s == 0) - __throw_system_error(ENODATA, "random_device got EOF"); - if (s == -1) - { - if (errno != EINTR) - __throw_system_error(errno, "random_device got an unexpected error"); - continue; - } - n -= static_cast<size_t>(s); - p += static_cast<size_t>(s); - } - return r; -} - -#elif defined(_LIBCPP_USING_NACL_RANDOM) - -random_device::random_device(const string& __token) -{ - if (__token != "/dev/urandom") - __throw_system_error(ENOENT, ("random device not supported " + __token).c_str()); - int error = nacl_secure_random_init(); - if (error) - __throw_system_error(error, ("random device failed to open " + __token).c_str()); -} - -random_device::~random_device() -{ -} - -unsigned -random_device::operator()() -{ - unsigned r; - size_t n = sizeof(r); - size_t bytes_written; - int error = nacl_secure_random(&r, n, &bytes_written); - if (error != 0) - __throw_system_error(error, "random_device failed getting bytes"); - else if (bytes_written != n) - __throw_runtime_error("random_device failed to obtain enough bytes"); - return r; -} - -#elif defined(_LIBCPP_USING_WIN32_RANDOM) - -random_device::random_device(const string& __token) -{ - if (__token != "/dev/urandom") - __throw_system_error(ENOENT, ("random device not supported " + __token).c_str()); -} - -random_device::~random_device() -{ -} - -unsigned -random_device::operator()() -{ - unsigned r; - errno_t err = rand_s(&r); - if (err) - __throw_system_error(err, "random_device rand_s failed."); - return r; -} - -#else -#error "Random device not implemented for this architecture" -#endif - -double -random_device::entropy() const _NOEXCEPT -{ -#ifdef __OpenBSD__ - return std::numeric_limits<unsigned int>::digits; -#else - return 0; -#endif -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/regex.cpp b/lib/libcxx/src/regex.cpp deleted file mode 100644 index a7363599d5a..00000000000 --- a/lib/libcxx/src/regex.cpp +++ /dev/null @@ -1,315 +0,0 @@ -//===-------------------------- regex.cpp ---------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "regex" -#include "algorithm" -#include "iterator" - -_LIBCPP_BEGIN_NAMESPACE_STD - -static -const char* -make_error_type_string(regex_constants::error_type ecode) -{ - switch (ecode) - { - case regex_constants::error_collate: - return "The expression contained an invalid collating element name."; - case regex_constants::error_ctype: - return "The expression contained an invalid character class name."; - case regex_constants::error_escape: - return "The expression contained an invalid escaped character, or a " - "trailing escape."; - case regex_constants::error_backref: - return "The expression contained an invalid back reference."; - case regex_constants::error_brack: - return "The expression contained mismatched [ and ]."; - case regex_constants::error_paren: - return "The expression contained mismatched ( and )."; - case regex_constants::error_brace: - return "The expression contained mismatched { and }."; - case regex_constants::error_badbrace: - return "The expression contained an invalid range in a {} expression."; - case regex_constants::error_range: - return "The expression contained an invalid character range, " - "such as [b-a] in most encodings."; - case regex_constants::error_space: - return "There was insufficient memory to convert the expression into " - "a finite state machine."; - case regex_constants::error_badrepeat: - return "One of *?+{ was not preceded by a valid regular expression."; - case regex_constants::error_complexity: - return "The complexity of an attempted match against a regular " - "expression exceeded a pre-set level."; - case regex_constants::error_stack: - return "There was insufficient memory to determine whether the regular " - "expression could match the specified character sequence."; - case regex_constants::__re_err_grammar: - return "An invalid regex grammar has been requested."; - case regex_constants::__re_err_empty: - return "An empty regex is not allowed in the POSIX grammar."; - default: - break; - } - return "Unknown error type"; -} - -regex_error::regex_error(regex_constants::error_type ecode) - : runtime_error(make_error_type_string(ecode)), - __code_(ecode) -{} - -regex_error::~regex_error() throw() {} - -namespace { - -struct collationnames -{ - const char* elem_; - char char_; -}; - -const collationnames collatenames[] = -{ - {"A", 0x41}, - {"B", 0x42}, - {"C", 0x43}, - {"D", 0x44}, - {"E", 0x45}, - {"F", 0x46}, - {"G", 0x47}, - {"H", 0x48}, - {"I", 0x49}, - {"J", 0x4a}, - {"K", 0x4b}, - {"L", 0x4c}, - {"M", 0x4d}, - {"N", 0x4e}, - {"NUL", 0x00}, - {"O", 0x4f}, - {"P", 0x50}, - {"Q", 0x51}, - {"R", 0x52}, - {"S", 0x53}, - {"T", 0x54}, - {"U", 0x55}, - {"V", 0x56}, - {"W", 0x57}, - {"X", 0x58}, - {"Y", 0x59}, - {"Z", 0x5a}, - {"a", 0x61}, - {"alert", 0x07}, - {"ampersand", 0x26}, - {"apostrophe", 0x27}, - {"asterisk", 0x2a}, - {"b", 0x62}, - {"backslash", 0x5c}, - {"backspace", 0x08}, - {"c", 0x63}, - {"carriage-return", 0x0d}, - {"circumflex", 0x5e}, - {"circumflex-accent", 0x5e}, - {"colon", 0x3a}, - {"comma", 0x2c}, - {"commercial-at", 0x40}, - {"d", 0x64}, - {"dollar-sign", 0x24}, - {"e", 0x65}, - {"eight", 0x38}, - {"equals-sign", 0x3d}, - {"exclamation-mark", 0x21}, - {"f", 0x66}, - {"five", 0x35}, - {"form-feed", 0x0c}, - {"four", 0x34}, - {"full-stop", 0x2e}, - {"g", 0x67}, - {"grave-accent", 0x60}, - {"greater-than-sign", 0x3e}, - {"h", 0x68}, - {"hyphen", 0x2d}, - {"hyphen-minus", 0x2d}, - {"i", 0x69}, - {"j", 0x6a}, - {"k", 0x6b}, - {"l", 0x6c}, - {"left-brace", 0x7b}, - {"left-curly-bracket", 0x7b}, - {"left-parenthesis", 0x28}, - {"left-square-bracket", 0x5b}, - {"less-than-sign", 0x3c}, - {"low-line", 0x5f}, - {"m", 0x6d}, - {"n", 0x6e}, - {"newline", 0x0a}, - {"nine", 0x39}, - {"number-sign", 0x23}, - {"o", 0x6f}, - {"one", 0x31}, - {"p", 0x70}, - {"percent-sign", 0x25}, - {"period", 0x2e}, - {"plus-sign", 0x2b}, - {"q", 0x71}, - {"question-mark", 0x3f}, - {"quotation-mark", 0x22}, - {"r", 0x72}, - {"reverse-solidus", 0x5c}, - {"right-brace", 0x7d}, - {"right-curly-bracket", 0x7d}, - {"right-parenthesis", 0x29}, - {"right-square-bracket", 0x5d}, - {"s", 0x73}, - {"semicolon", 0x3b}, - {"seven", 0x37}, - {"six", 0x36}, - {"slash", 0x2f}, - {"solidus", 0x2f}, - {"space", 0x20}, - {"t", 0x74}, - {"tab", 0x09}, - {"three", 0x33}, - {"tilde", 0x7e}, - {"two", 0x32}, - {"u", 0x75}, - {"underscore", 0x5f}, - {"v", 0x76}, - {"vertical-line", 0x7c}, - {"vertical-tab", 0x0b}, - {"w", 0x77}, - {"x", 0x78}, - {"y", 0x79}, - {"z", 0x7a}, - {"zero", 0x30} -}; - -struct classnames -{ - const char* elem_; - regex_traits<char>::char_class_type mask_; -}; - -const classnames ClassNames[] = -{ - {"alnum", ctype_base::alnum}, - {"alpha", ctype_base::alpha}, - {"blank", ctype_base::blank}, - {"cntrl", ctype_base::cntrl}, - {"d", ctype_base::digit}, - {"digit", ctype_base::digit}, - {"graph", ctype_base::graph}, - {"lower", ctype_base::lower}, - {"print", ctype_base::print}, - {"punct", ctype_base::punct}, - {"s", ctype_base::space}, - {"space", ctype_base::space}, - {"upper", ctype_base::upper}, - {"w", regex_traits<char>::__regex_word}, - {"xdigit", ctype_base::xdigit} -}; - -struct use_strcmp -{ - bool operator()(const collationnames& x, const char* y) - {return strcmp(x.elem_, y) < 0;} - bool operator()(const classnames& x, const char* y) - {return strcmp(x.elem_, y) < 0;} -}; - -} - -string -__get_collation_name(const char* s) -{ - const collationnames* i = - _VSTD::lower_bound(begin(collatenames), end(collatenames), s, use_strcmp()); - string r; - if (i != end(collatenames) && strcmp(s, i->elem_) == 0) - r = char(i->char_); - return r; -} - -regex_traits<char>::char_class_type -__get_classname(const char* s, bool __icase) -{ - const classnames* i = - _VSTD::lower_bound(begin(ClassNames), end(ClassNames), s, use_strcmp()); - regex_traits<char>::char_class_type r = 0; - if (i != end(ClassNames) && strcmp(s, i->elem_) == 0) - { - r = i->mask_; - if (r == regex_traits<char>::__regex_word) - r |= ctype_base::alnum | ctype_base::upper | ctype_base::lower; - else if (__icase) - { - if (r & (ctype_base::lower | ctype_base::upper)) - r |= ctype_base::alpha; - } - } - return r; -} - -template <> -void -__match_any_but_newline<char>::__exec(__state& __s) const -{ - if (__s.__current_ != __s.__last_) - { - switch (*__s.__current_) - { - case '\r': - case '\n': - __s.__do_ = __state::__reject; - __s.__node_ = nullptr; - break; - default: - __s.__do_ = __state::__accept_and_consume; - ++__s.__current_; - __s.__node_ = this->first(); - break; - } - } - else - { - __s.__do_ = __state::__reject; - __s.__node_ = nullptr; - } -} - -template <> -void -__match_any_but_newline<wchar_t>::__exec(__state& __s) const -{ - if (__s.__current_ != __s.__last_) - { - switch (*__s.__current_) - { - case '\r': - case '\n': - case 0x2028: - case 0x2029: - __s.__do_ = __state::__reject; - __s.__node_ = nullptr; - break; - default: - __s.__do_ = __state::__accept_and_consume; - ++__s.__current_; - __s.__node_ = this->first(); - break; - } - } - else - { - __s.__do_ = __state::__reject; - __s.__node_ = nullptr; - } -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/shared_mutex.cpp b/lib/libcxx/src/shared_mutex.cpp deleted file mode 100644 index 6185f15deab..00000000000 --- a/lib/libcxx/src/shared_mutex.cpp +++ /dev/null @@ -1,116 +0,0 @@ -//===---------------------- shared_mutex.cpp ------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "__config" -#ifndef _LIBCPP_HAS_NO_THREADS - -#include "shared_mutex" - -_LIBCPP_BEGIN_NAMESPACE_STD - -// Shared Mutex Base -__shared_mutex_base::__shared_mutex_base() - : __state_(0) -{ -} - -// Exclusive ownership - -void -__shared_mutex_base::lock() -{ - unique_lock<mutex> lk(__mut_); - while (__state_ & __write_entered_) - __gate1_.wait(lk); - __state_ |= __write_entered_; - while (__state_ & __n_readers_) - __gate2_.wait(lk); -} - -bool -__shared_mutex_base::try_lock() -{ - unique_lock<mutex> lk(__mut_); - if (__state_ == 0) - { - __state_ = __write_entered_; - return true; - } - return false; -} - -void -__shared_mutex_base::unlock() -{ - lock_guard<mutex> _(__mut_); - __state_ = 0; - __gate1_.notify_all(); -} - -// Shared ownership - -void -__shared_mutex_base::lock_shared() -{ - unique_lock<mutex> lk(__mut_); - while ((__state_ & __write_entered_) || (__state_ & __n_readers_) == __n_readers_) - __gate1_.wait(lk); - unsigned num_readers = (__state_ & __n_readers_) + 1; - __state_ &= ~__n_readers_; - __state_ |= num_readers; -} - -bool -__shared_mutex_base::try_lock_shared() -{ - unique_lock<mutex> lk(__mut_); - unsigned num_readers = __state_ & __n_readers_; - if (!(__state_ & __write_entered_) && num_readers != __n_readers_) - { - ++num_readers; - __state_ &= ~__n_readers_; - __state_ |= num_readers; - return true; - } - return false; -} - -void -__shared_mutex_base::unlock_shared() -{ - lock_guard<mutex> _(__mut_); - unsigned num_readers = (__state_ & __n_readers_) - 1; - __state_ &= ~__n_readers_; - __state_ |= num_readers; - if (__state_ & __write_entered_) - { - if (num_readers == 0) - __gate2_.notify_one(); - } - else - { - if (num_readers == __n_readers_ - 1) - __gate1_.notify_one(); - } -} - - -// Shared Timed Mutex -// These routines are here for ABI stability -shared_timed_mutex::shared_timed_mutex() : __base() {} -void shared_timed_mutex::lock() { return __base.lock(); } -bool shared_timed_mutex::try_lock() { return __base.try_lock(); } -void shared_timed_mutex::unlock() { return __base.unlock(); } -void shared_timed_mutex::lock_shared() { return __base.lock_shared(); } -bool shared_timed_mutex::try_lock_shared() { return __base.try_lock_shared(); } -void shared_timed_mutex::unlock_shared() { return __base.unlock_shared(); } - -_LIBCPP_END_NAMESPACE_STD - -#endif // !_LIBCPP_HAS_NO_THREADS diff --git a/lib/libcxx/src/stdexcept.cpp b/lib/libcxx/src/stdexcept.cpp deleted file mode 100644 index 5e06e521e40..00000000000 --- a/lib/libcxx/src/stdexcept.cpp +++ /dev/null @@ -1,104 +0,0 @@ -//===------------------------ stdexcept.cpp -------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "stdexcept" -#include "new" -#include "string" -#include "system_error" -#include "include/refstring.h" - -/* For _LIBCPPABI_VERSION */ -#if !defined(_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY) && \ - (defined(LIBCXX_BUILDING_LIBCXXABI) || defined(__APPLE__) || defined(LIBCXXRT)) -#include <cxxabi.h> -#endif - -static_assert(sizeof(std::__libcpp_refstring) == sizeof(const char *), ""); - - -namespace std // purposefully not using versioning namespace -{ - -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::operator=(const logic_error& le) _NOEXCEPT -{ - __imp_ = le.__imp_; - return *this; -} - -#if !defined(_LIBCPPABI_VERSION) && !defined(LIBSTDCXX) - -logic_error::~logic_error() _NOEXCEPT -{ -} - -const char* -logic_error::what() const _NOEXCEPT -{ - return __imp_.c_str(); -} - -#endif - -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& le) _NOEXCEPT - : __imp_(le.__imp_) -{ -} - -runtime_error& -runtime_error::operator=(const runtime_error& le) _NOEXCEPT -{ - __imp_ = le.__imp_; - return *this; -} - -#if !defined(_LIBCPPABI_VERSION) && !defined(LIBSTDCXX) - -runtime_error::~runtime_error() _NOEXCEPT -{ -} - -const char* -runtime_error::what() const _NOEXCEPT -{ - return __imp_.c_str(); -} - -domain_error::~domain_error() _NOEXCEPT {} -invalid_argument::~invalid_argument() _NOEXCEPT {} -length_error::~length_error() _NOEXCEPT {} -out_of_range::~out_of_range() _NOEXCEPT {} - -range_error::~range_error() _NOEXCEPT {} -overflow_error::~overflow_error() _NOEXCEPT {} -underflow_error::~underflow_error() _NOEXCEPT {} - -#endif - -} // std diff --git a/lib/libcxx/src/string.cpp b/lib/libcxx/src/string.cpp deleted file mode 100644 index d7ebdd3e5c9..00000000000 --- a/lib/libcxx/src/string.cpp +++ /dev/null @@ -1,525 +0,0 @@ -//===------------------------- string.cpp ---------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "string" -#include "cstdlib" -#include "cwchar" -#include "cerrno" -#include "limits" -#include "stdexcept" -#include <stdio.h> - -_LIBCPP_BEGIN_NAMESPACE_STD - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __basic_string_common<true>; - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS basic_string<char>; -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS basic_string<wchar_t>; - -template - string - operator+<char, char_traits<char>, allocator<char> >(char const*, string const&); - -namespace -{ - -template<typename T> -inline -void throw_helper( const string& msg ) -{ -#ifndef _LIBCPP_NO_EXCEPTIONS - throw T( msg ); -#else - fprintf(stderr, "%s\n", msg.c_str()); - _VSTD::abort(); -#endif -} - -inline -void throw_from_string_out_of_range( const string& func ) -{ - throw_helper<out_of_range>(func + ": out of range"); -} - -inline -void throw_from_string_invalid_arg( const string& func ) -{ - throw_helper<invalid_argument>(func + ": no conversion"); -} - -// as_integer - -template<typename V, typename S, typename F> -inline -V -as_integer_helper(const string& func, const S& str, size_t* idx, int base, F f) -{ - typename S::value_type* ptr = nullptr; - const typename S::value_type* const p = str.c_str(); - typename remove_reference<decltype(errno)>::type errno_save = errno; - errno = 0; - V r = f(p, &ptr, base); - swap(errno, errno_save); - if (errno_save == ERANGE) - throw_from_string_out_of_range(func); - if (ptr == p) - throw_from_string_invalid_arg(func); - if (idx) - *idx = static_cast<size_t>(ptr - p); - return r; -} - -template<typename V, typename S> -inline -V -as_integer(const string& func, const S& s, size_t* idx, int base); - -// string -template<> -inline -int -as_integer(const string& func, const string& s, size_t* idx, int base ) -{ - // Use long as no Standard string to integer exists. - long r = as_integer_helper<long>( func, s, idx, base, strtol ); - if (r < numeric_limits<int>::min() || numeric_limits<int>::max() < r) - throw_from_string_out_of_range(func); - return static_cast<int>(r); -} - -template<> -inline -long -as_integer(const string& func, const string& s, size_t* idx, int base ) -{ - return as_integer_helper<long>( func, s, idx, base, strtol ); -} - -template<> -inline -unsigned long -as_integer( const string& func, const string& s, size_t* idx, int base ) -{ - return as_integer_helper<unsigned long>( func, s, idx, base, strtoul ); -} - -template<> -inline -long long -as_integer( const string& func, const string& s, size_t* idx, int base ) -{ - return as_integer_helper<long long>( func, s, idx, base, strtoll ); -} - -template<> -inline -unsigned long long -as_integer( const string& func, const string& s, size_t* idx, int base ) -{ - return as_integer_helper<unsigned long long>( func, s, idx, base, strtoull ); -} - -// wstring -template<> -inline -int -as_integer( const string& func, const wstring& s, size_t* idx, int base ) -{ - // Use long as no Stantard string to integer exists. - long r = as_integer_helper<long>( func, s, idx, base, wcstol ); - if (r < numeric_limits<int>::min() || numeric_limits<int>::max() < r) - throw_from_string_out_of_range(func); - return static_cast<int>(r); -} - -template<> -inline -long -as_integer( const string& func, const wstring& s, size_t* idx, int base ) -{ - return as_integer_helper<long>( func, s, idx, base, wcstol ); -} - -template<> -inline -unsigned long -as_integer( const string& func, const wstring& s, size_t* idx, int base ) -{ - return as_integer_helper<unsigned long>( func, s, idx, base, wcstoul ); -} - -template<> -inline -long long -as_integer( const string& func, const wstring& s, size_t* idx, int base ) -{ - return as_integer_helper<long long>( func, s, idx, base, wcstoll ); -} - -template<> -inline -unsigned long long -as_integer( const string& func, const wstring& s, size_t* idx, int base ) -{ - return as_integer_helper<unsigned long long>( func, s, idx, base, wcstoull ); -} - -// as_float - -template<typename V, typename S, typename F> -inline -V -as_float_helper(const string& func, const S& str, size_t* idx, F f ) -{ - typename S::value_type* ptr = nullptr; - const typename S::value_type* const p = str.c_str(); - typename remove_reference<decltype(errno)>::type errno_save = errno; - errno = 0; - V r = f(p, &ptr); - swap(errno, errno_save); - if (errno_save == ERANGE) - throw_from_string_out_of_range(func); - if (ptr == p) - throw_from_string_invalid_arg(func); - if (idx) - *idx = static_cast<size_t>(ptr - p); - return r; -} - -template<typename V, typename S> -inline -V as_float( const string& func, const S& s, size_t* idx = nullptr ); - -template<> -inline -float -as_float( const string& func, const string& s, size_t* idx ) -{ - return as_float_helper<float>( func, s, idx, strtof ); -} - -template<> -inline -double -as_float(const string& func, const string& s, size_t* idx ) -{ - return as_float_helper<double>( func, s, idx, strtod ); -} - -template<> -inline -long double -as_float( const string& func, const string& s, size_t* idx ) -{ - return as_float_helper<long double>( func, s, idx, strtold ); -} - -template<> -inline -float -as_float( const string& func, const wstring& s, size_t* idx ) -{ - return as_float_helper<float>( func, s, idx, wcstof ); -} - -template<> -inline -double -as_float( const string& func, const wstring& s, size_t* idx ) -{ - return as_float_helper<double>( func, s, idx, wcstod ); -} - -template<> -inline -long double -as_float( const string& func, const wstring& s, size_t* idx ) -{ - return as_float_helper<long double>( func, s, idx, wcstold ); -} - -} // unnamed namespace - -int -stoi(const string& str, size_t* idx, int base) -{ - return as_integer<int>( "stoi", str, idx, base ); -} - -int -stoi(const wstring& str, size_t* idx, int base) -{ - return as_integer<int>( "stoi", str, idx, base ); -} - -long -stol(const string& str, size_t* idx, int base) -{ - return as_integer<long>( "stol", str, idx, base ); -} - -long -stol(const wstring& str, size_t* idx, int base) -{ - return as_integer<long>( "stol", str, idx, base ); -} - -unsigned long -stoul(const string& str, size_t* idx, int base) -{ - return as_integer<unsigned long>( "stoul", str, idx, base ); -} - -unsigned long -stoul(const wstring& str, size_t* idx, int base) -{ - return as_integer<unsigned long>( "stoul", str, idx, base ); -} - -long long -stoll(const string& str, size_t* idx, int base) -{ - return as_integer<long long>( "stoll", str, idx, base ); -} - -long long -stoll(const wstring& str, size_t* idx, int base) -{ - return as_integer<long long>( "stoll", str, idx, base ); -} - -unsigned long long -stoull(const string& str, size_t* idx, int base) -{ - return as_integer<unsigned long long>( "stoull", str, idx, base ); -} - -unsigned long long -stoull(const wstring& str, size_t* idx, int base) -{ - return as_integer<unsigned long long>( "stoull", str, idx, base ); -} - -float -stof(const string& str, size_t* idx) -{ - return as_float<float>( "stof", str, idx ); -} - -float -stof(const wstring& str, size_t* idx) -{ - return as_float<float>( "stof", str, idx ); -} - -double -stod(const string& str, size_t* idx) -{ - return as_float<double>( "stod", str, idx ); -} - -double -stod(const wstring& str, size_t* idx) -{ - return as_float<double>( "stod", str, idx ); -} - -long double -stold(const string& str, size_t* idx) -{ - return as_float<long double>( "stold", str, idx ); -} - -long double -stold(const wstring& str, size_t* idx) -{ - return as_float<long double>( "stold", str, idx ); -} - -// to_string - -namespace -{ - -// as_string - -template<typename S, typename P, typename V > -inline -S -as_string(P sprintf_like, S s, const typename S::value_type* fmt, V a) -{ - typedef typename S::size_type size_type; - size_type available = s.size(); - while (true) - { - int status = sprintf_like(&s[0], available + 1, fmt, a); - if ( status >= 0 ) - { - size_type used = static_cast<size_type>(status); - if ( used <= available ) - { - s.resize( used ); - break; - } - available = used; // Assume this is advice of how much space we need. - } - else - available = available * 2 + 1; - s.resize(available); - } - return s; -} - -template <class S, class V, bool = is_floating_point<V>::value> -struct initial_string; - -template <class V, bool b> -struct initial_string<string, V, b> -{ - string - operator()() const - { - string s; - s.resize(s.capacity()); - return s; - } -}; - -template <class V> -struct initial_string<wstring, V, false> -{ - wstring - operator()() const - { - const size_t n = (numeric_limits<unsigned long long>::digits / 3) - + ((numeric_limits<unsigned long long>::digits % 3) != 0) - + 1; - wstring s(n, wchar_t()); - s.resize(s.capacity()); - return s; - } -}; - -template <class V> -struct initial_string<wstring, V, true> -{ - wstring - operator()() const - { - wstring s(20, wchar_t()); - s.resize(s.capacity()); - return s; - } -}; - -typedef int (*wide_printf)(wchar_t* __restrict, size_t, const wchar_t*__restrict, ...); - -inline -wide_printf -get_swprintf() -{ -#ifndef _LIBCPP_MSVCRT - return swprintf; -#else - return static_cast<int (__cdecl*)(wchar_t* __restrict, size_t, const wchar_t*__restrict, ...)>(_snwprintf); -#endif -} - -} // unnamed namespace - -string to_string(int val) -{ - return as_string(snprintf, initial_string<string, int>()(), "%d", val); -} - -string to_string(unsigned val) -{ - return as_string(snprintf, initial_string<string, unsigned>()(), "%u", val); -} - -string to_string(long val) -{ - return as_string(snprintf, initial_string<string, long>()(), "%ld", val); -} - -string to_string(unsigned long val) -{ - return as_string(snprintf, initial_string<string, unsigned long>()(), "%lu", val); -} - -string to_string(long long val) -{ - return as_string(snprintf, initial_string<string, long long>()(), "%lld", val); -} - -string to_string(unsigned long long val) -{ - return as_string(snprintf, initial_string<string, unsigned long long>()(), "%llu", val); -} - -string to_string(float val) -{ - return as_string(snprintf, initial_string<string, float>()(), "%f", val); -} - -string to_string(double val) -{ - return as_string(snprintf, initial_string<string, double>()(), "%f", val); -} - -string to_string(long double val) -{ - return as_string(snprintf, initial_string<string, long double>()(), "%Lf", val); -} - -wstring to_wstring(int val) -{ - return as_string(get_swprintf(), initial_string<wstring, int>()(), L"%d", val); -} - -wstring to_wstring(unsigned val) -{ - return as_string(get_swprintf(), initial_string<wstring, unsigned>()(), L"%u", val); -} - -wstring to_wstring(long val) -{ - return as_string(get_swprintf(), initial_string<wstring, long>()(), L"%ld", val); -} - -wstring to_wstring(unsigned long val) -{ - return as_string(get_swprintf(), initial_string<wstring, unsigned long>()(), L"%lu", val); -} - -wstring to_wstring(long long val) -{ - return as_string(get_swprintf(), initial_string<wstring, long long>()(), L"%lld", val); -} - -wstring to_wstring(unsigned long long val) -{ - return as_string(get_swprintf(), initial_string<wstring, unsigned long long>()(), L"%llu", val); -} - -wstring to_wstring(float val) -{ - return as_string(get_swprintf(), initial_string<wstring, float>()(), L"%f", val); -} - -wstring to_wstring(double val) -{ - return as_string(get_swprintf(), initial_string<wstring, double>()(), L"%f", val); -} - -wstring to_wstring(long double val) -{ - return as_string(get_swprintf(), initial_string<wstring, long double>()(), L"%Lf", val); -} -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/strstream.cpp b/lib/libcxx/src/strstream.cpp deleted file mode 100644 index 8b8521f76af..00000000000 --- a/lib/libcxx/src/strstream.cpp +++ /dev/null @@ -1,336 +0,0 @@ -//===------------------------ strstream.cpp -------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "strstream" -#include "algorithm" -#include "climits" -#include "cstring" -#include "cstdlib" -#include "__debug" -#include "__undef_macros" - -_LIBCPP_BEGIN_NAMESPACE_STD - -strstreambuf::strstreambuf(streamsize __alsize) - : __strmode_(__dynamic), - __alsize_(__alsize), - __palloc_(nullptr), - __pfree_(nullptr) -{ -} - -strstreambuf::strstreambuf(void* (*__palloc)(size_t), void (*__pfree)(void*)) - : __strmode_(__dynamic), - __alsize_(__default_alsize), - __palloc_(__palloc), - __pfree_(__pfree) -{ -} - -void -strstreambuf::__init(char* __gnext, streamsize __n, char* __pbeg) -{ - if (__n == 0) - __n = static_cast<streamsize>(strlen(__gnext)); - else if (__n < 0) - __n = INT_MAX; - if (__pbeg == nullptr) - setg(__gnext, __gnext, __gnext + __n); - else - { - setg(__gnext, __gnext, __pbeg); - setp(__pbeg, __pbeg + __n); - } -} - -strstreambuf::strstreambuf(char* __gnext, streamsize __n, char* __pbeg) - : __strmode_(), - __alsize_(__default_alsize), - __palloc_(nullptr), - __pfree_(nullptr) -{ - __init(__gnext, __n, __pbeg); -} - -strstreambuf::strstreambuf(const char* __gnext, streamsize __n) - : __strmode_(__constant), - __alsize_(__default_alsize), - __palloc_(nullptr), - __pfree_(nullptr) -{ - __init(const_cast<char *>(__gnext), __n, nullptr); -} - -strstreambuf::strstreambuf(signed char* __gnext, streamsize __n, signed char* __pbeg) - : __strmode_(), - __alsize_(__default_alsize), - __palloc_(nullptr), - __pfree_(nullptr) -{ - __init(const_cast<char *>(reinterpret_cast<const char*>(__gnext)), __n, reinterpret_cast<char*>(__pbeg)); -} - -strstreambuf::strstreambuf(const signed char* __gnext, streamsize __n) - : __strmode_(__constant), - __alsize_(__default_alsize), - __palloc_(nullptr), - __pfree_(nullptr) -{ - __init(const_cast<char *>(reinterpret_cast<const char*>(__gnext)), __n, nullptr); -} - -strstreambuf::strstreambuf(unsigned char* __gnext, streamsize __n, unsigned char* __pbeg) - : __strmode_(), - __alsize_(__default_alsize), - __palloc_(nullptr), - __pfree_(nullptr) -{ - __init(const_cast<char *>(reinterpret_cast<const char*>(__gnext)), __n, reinterpret_cast<char*>(__pbeg)); -} - -strstreambuf::strstreambuf(const unsigned char* __gnext, streamsize __n) - : __strmode_(__constant), - __alsize_(__default_alsize), - __palloc_(nullptr), - __pfree_(nullptr) -{ - __init(const_cast<char *>(reinterpret_cast<const char*>(__gnext)), __n, nullptr); -} - -strstreambuf::~strstreambuf() -{ - if (eback() && (__strmode_ & __allocated) != 0 && (__strmode_ & __frozen) == 0) - { - if (__pfree_) - __pfree_(eback()); - else - delete [] eback(); - } -} - -void -strstreambuf::swap(strstreambuf& __rhs) -{ - streambuf::swap(__rhs); - _VSTD::swap(__strmode_, __rhs.__strmode_); - _VSTD::swap(__alsize_, __rhs.__alsize_); - _VSTD::swap(__palloc_, __rhs.__palloc_); - _VSTD::swap(__pfree_, __rhs.__pfree_); -} - -void -strstreambuf::freeze(bool __freezefl) -{ - if (__strmode_ & __dynamic) - { - if (__freezefl) - __strmode_ |= __frozen; - else - __strmode_ &= ~__frozen; - } -} - -char* -strstreambuf::str() -{ - if (__strmode_ & __dynamic) - __strmode_ |= __frozen; - return eback(); -} - -int -strstreambuf::pcount() const -{ - return static_cast<int>(pptr() - pbase()); -} - -strstreambuf::int_type -strstreambuf::overflow(int_type __c) -{ - if (__c == EOF) - return int_type(0); - if (pptr() == epptr()) - { - if ((__strmode_ & __dynamic) == 0 || (__strmode_ & __frozen) != 0) - return int_type(EOF); - size_t old_size = static_cast<size_t> ((epptr() ? epptr() : egptr()) - eback()); - size_t new_size = max<size_t>(static_cast<size_t>(__alsize_), 2*old_size); - if (new_size == 0) - new_size = __default_alsize; - char* buf = nullptr; - if (__palloc_) - buf = static_cast<char*>(__palloc_(new_size)); - else - buf = new char[new_size]; - if (buf == nullptr) - return int_type(EOF); - if (old_size != 0) { - _LIBCPP_ASSERT(eback(), "overflow copying from NULL"); - memcpy(buf, eback(), static_cast<size_t>(old_size)); - } - ptrdiff_t ninp = gptr() - eback(); - ptrdiff_t einp = egptr() - eback(); - ptrdiff_t nout = pptr() - pbase(); - if (__strmode_ & __allocated) - { - if (__pfree_) - __pfree_(eback()); - else - delete [] eback(); - } - setg(buf, buf + ninp, buf + einp); - setp(buf + einp, buf + new_size); - __pbump(nout); - __strmode_ |= __allocated; - } - *pptr() = static_cast<char>(__c); - pbump(1); - return int_type(static_cast<unsigned char>(__c)); -} - -strstreambuf::int_type -strstreambuf::pbackfail(int_type __c) -{ - if (eback() == gptr()) - return EOF; - if (__c == EOF) - { - gbump(-1); - return int_type(0); - } - if (__strmode_ & __constant) - { - if (gptr()[-1] == static_cast<char>(__c)) - { - gbump(-1); - return __c; - } - return EOF; - } - gbump(-1); - *gptr() = static_cast<char>(__c); - return __c; -} - -strstreambuf::int_type -strstreambuf::underflow() -{ - if (gptr() == egptr()) - { - if (egptr() >= pptr()) - return EOF; - setg(eback(), gptr(), pptr()); - } - return int_type(static_cast<unsigned char>(*gptr())); -} - -strstreambuf::pos_type -strstreambuf::seekoff(off_type __off, ios_base::seekdir __way, ios_base::openmode __which) -{ - off_type __p(-1); - bool pos_in = (__which & ios::in) != 0; - bool pos_out = (__which & ios::out) != 0; - bool legal = false; - switch (__way) - { - case ios::beg: - case ios::end: - if (pos_in || pos_out) - legal = true; - break; - case ios::cur: - if (pos_in != pos_out) - legal = true; - break; - } - if (pos_in && gptr() == nullptr) - legal = false; - if (pos_out && pptr() == nullptr) - legal = false; - if (legal) - { - off_type newoff; - char* seekhigh = epptr() ? epptr() : egptr(); - switch (__way) - { - case ios::beg: - newoff = 0; - break; - case ios::cur: - newoff = (pos_in ? gptr() : pptr()) - eback(); - break; - case ios::end: - newoff = seekhigh - eback(); - break; - default: - _LIBCPP_UNREACHABLE(); - } - newoff += __off; - if (0 <= newoff && newoff <= seekhigh - eback()) - { - char* newpos = eback() + newoff; - if (pos_in) - setg(eback(), newpos, _VSTD::max(newpos, egptr())); - if (pos_out) - { - // min(pbase, newpos), newpos, epptr() - __off = epptr() - newpos; - setp(min(pbase(), newpos), epptr()); - __pbump((epptr() - pbase()) - __off); - } - __p = newoff; - } - } - return pos_type(__p); -} - -strstreambuf::pos_type -strstreambuf::seekpos(pos_type __sp, ios_base::openmode __which) -{ - off_type __p(-1); - bool pos_in = (__which & ios::in) != 0; - bool pos_out = (__which & ios::out) != 0; - if (pos_in || pos_out) - { - if (!((pos_in && gptr() == nullptr) || (pos_out && pptr() == nullptr))) - { - off_type newoff = __sp; - char* seekhigh = epptr() ? epptr() : egptr(); - if (0 <= newoff && newoff <= seekhigh - eback()) - { - char* newpos = eback() + newoff; - if (pos_in) - setg(eback(), newpos, _VSTD::max(newpos, egptr())); - if (pos_out) - { - // min(pbase, newpos), newpos, epptr() - off_type temp = epptr() - newpos; - setp(min(pbase(), newpos), epptr()); - __pbump((epptr() - pbase()) - temp); - } - __p = newoff; - } - } - } - return pos_type(__p); -} - -istrstream::~istrstream() -{ -} - -ostrstream::~ostrstream() -{ -} - -strstream::~strstream() -{ -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/support/runtime/exception_fallback.ipp b/lib/libcxx/src/support/runtime/exception_fallback.ipp deleted file mode 100644 index 16d387b99e8..00000000000 --- a/lib/libcxx/src/support/runtime/exception_fallback.ipp +++ /dev/null @@ -1,165 +0,0 @@ -// -*- C++ -*- -//===----------------------------------------------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include <cstdio> - -namespace std { - -_LIBCPP_SAFE_STATIC static std::terminate_handler __terminate_handler; -_LIBCPP_SAFE_STATIC static std::unexpected_handler __unexpected_handler; - - -// libcxxrt provides implementations of these functions itself. -unexpected_handler -set_unexpected(unexpected_handler func) _NOEXCEPT -{ - return __libcpp_atomic_exchange(&__unexpected_handler, func); -} - -unexpected_handler -get_unexpected() _NOEXCEPT -{ - return __libcpp_atomic_load(&__unexpected_handler); - -} - -_LIBCPP_NORETURN -void unexpected() -{ - (*get_unexpected())(); - // unexpected handler should not return - terminate(); -} - -terminate_handler -set_terminate(terminate_handler func) _NOEXCEPT -{ - return __libcpp_atomic_exchange(&__terminate_handler, func); -} - -terminate_handler -get_terminate() _NOEXCEPT -{ - return __libcpp_atomic_load(&__terminate_handler); -} - -#ifndef __EMSCRIPTEN__ // We provide this in JS -_LIBCPP_NORETURN -void -terminate() _NOEXCEPT -{ -#ifndef _LIBCPP_NO_EXCEPTIONS - try - { -#endif // _LIBCPP_NO_EXCEPTIONS - (*get_terminate())(); - // handler should not return - fprintf(stderr, "terminate_handler unexpectedly returned\n"); - ::abort(); -#ifndef _LIBCPP_NO_EXCEPTIONS - } - catch (...) - { - // handler should not throw exception - fprintf(stderr, "terminate_handler unexpectedly threw an exception\n"); - ::abort(); - } -#endif // _LIBCPP_NO_EXCEPTIONS -} -#endif // !__EMSCRIPTEN__ - -#if !defined(__EMSCRIPTEN__) -bool uncaught_exception() _NOEXCEPT { return uncaught_exceptions() > 0; } - -int uncaught_exceptions() _NOEXCEPT -{ -#warning uncaught_exception not yet implemented - fprintf(stderr, "uncaught_exceptions not yet implemented\n"); - ::abort(); -} -#endif // !__EMSCRIPTEN__ - - -exception::~exception() _NOEXCEPT -{ -} - -const char* exception::what() const _NOEXCEPT -{ - return "std::exception"; -} - -bad_exception::~bad_exception() _NOEXCEPT -{ -} - -const char* bad_exception::what() const _NOEXCEPT -{ - return "std::bad_exception"; -} - - -bad_alloc::bad_alloc() _NOEXCEPT -{ -} - -bad_alloc::~bad_alloc() _NOEXCEPT -{ -} - -const char* -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 -{ -} - -const char* -bad_array_new_length::what() const _NOEXCEPT -{ - return "bad_array_new_length"; -} - -bad_cast::bad_cast() _NOEXCEPT -{ -} - -bad_typeid::bad_typeid() _NOEXCEPT -{ -} - -bad_cast::~bad_cast() _NOEXCEPT -{ -} - -const char* -bad_cast::what() const _NOEXCEPT -{ - return "std::bad_cast"; -} - -bad_typeid::~bad_typeid() _NOEXCEPT -{ -} - -const char* -bad_typeid::what() const _NOEXCEPT -{ - return "std::bad_typeid"; -} - -} // namespace std diff --git a/lib/libcxx/src/support/runtime/exception_glibcxx.ipp b/lib/libcxx/src/support/runtime/exception_glibcxx.ipp deleted file mode 100644 index dda4432b508..00000000000 --- a/lib/libcxx/src/support/runtime/exception_glibcxx.ipp +++ /dev/null @@ -1,33 +0,0 @@ -// -*- C++ -*- -//===----------------------------------------------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifndef __GLIBCXX__ -#error header can only be used when targeting libstdc++ or libsupc++ -#endif - -namespace std { - -bad_alloc::bad_alloc() _NOEXCEPT -{ -} - -bad_array_new_length::bad_array_new_length() _NOEXCEPT -{ -} - -bad_cast::bad_cast() _NOEXCEPT -{ -} - -bad_typeid::bad_typeid() _NOEXCEPT -{ -} - -} // namespace std diff --git a/lib/libcxx/src/support/runtime/exception_libcxxabi.ipp b/lib/libcxx/src/support/runtime/exception_libcxxabi.ipp deleted file mode 100644 index feefc515289..00000000000 --- a/lib/libcxx/src/support/runtime/exception_libcxxabi.ipp +++ /dev/null @@ -1,28 +0,0 @@ -// -*- C++ -*- -//===----------------------------------------------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifndef _LIBCPPABI_VERSION -#error this header can only be used with libc++abi -#endif - -namespace std { - -bool uncaught_exception() _NOEXCEPT { return uncaught_exceptions() > 0; } - -int uncaught_exceptions() _NOEXCEPT -{ -# if _LIBCPPABI_VERSION > 1001 - return __cxa_uncaught_exceptions(); -# else - return __cxa_uncaught_exception() ? 1 : 0; -# endif -} - -} // namespace std diff --git a/lib/libcxx/src/support/runtime/exception_libcxxrt.ipp b/lib/libcxx/src/support/runtime/exception_libcxxrt.ipp deleted file mode 100644 index 52fe8635db7..00000000000 --- a/lib/libcxx/src/support/runtime/exception_libcxxrt.ipp +++ /dev/null @@ -1,26 +0,0 @@ -// -*- C++ -*- -//===----------------------------------------------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifndef LIBCXXRT -#error this header may only be used when targeting libcxxrt -#endif - -namespace std { - -bad_exception::~bad_exception() _NOEXCEPT -{ -} - -const char* bad_exception::what() const _NOEXCEPT -{ - return "std::bad_exception"; -} - -} // namespace std diff --git a/lib/libcxx/src/support/runtime/exception_msvc.ipp b/lib/libcxx/src/support/runtime/exception_msvc.ipp deleted file mode 100644 index 042d3add6c7..00000000000 --- a/lib/libcxx/src/support/runtime/exception_msvc.ipp +++ /dev/null @@ -1,164 +0,0 @@ -// -*- C++ -*- -//===----------------------------------------------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifndef _LIBCPP_ABI_MICROSOFT -#error this header can only be used when targeting the MSVC ABI -#endif - -#include <stdio.h> -#include <stdlib.h> - -extern "C" { -typedef void (__cdecl* terminate_handler)(); -_LIBCPP_CRT_FUNC terminate_handler __cdecl set_terminate( - terminate_handler _NewTerminateHandler) throw(); -_LIBCPP_CRT_FUNC terminate_handler __cdecl _get_terminate(); - -typedef void (__cdecl* unexpected_handler)(); -unexpected_handler __cdecl set_unexpected( - unexpected_handler _NewUnexpectedHandler) throw(); -unexpected_handler __cdecl _get_unexpected(); - -int __cdecl __uncaught_exceptions(); -} - -namespace std { - -unexpected_handler -set_unexpected(unexpected_handler func) _NOEXCEPT { - return ::set_unexpected(func); -} - -unexpected_handler get_unexpected() _NOEXCEPT { - return ::_get_unexpected(); -} - -_LIBCPP_NORETURN -void unexpected() { - (*get_unexpected())(); - // unexpected handler should not return - terminate(); -} - -terminate_handler set_terminate(terminate_handler func) _NOEXCEPT { - return ::set_terminate(func); -} - -terminate_handler get_terminate() _NOEXCEPT { - return ::_get_terminate(); -} - -_LIBCPP_NORETURN -void terminate() _NOEXCEPT -{ -#ifndef _LIBCPP_NO_EXCEPTIONS - try - { -#endif // _LIBCPP_NO_EXCEPTIONS - (*get_terminate())(); - // handler should not return - fprintf(stderr, "terminate_handler unexpectedly returned\n"); - ::abort(); -#ifndef _LIBCPP_NO_EXCEPTIONS - } - catch (...) - { - // handler should not throw exception - fprintf(stderr, "terminate_handler unexpectedly threw an exception\n"); - ::abort(); - } -#endif // _LIBCPP_NO_EXCEPTIONS -} - -bool uncaught_exception() _NOEXCEPT { return uncaught_exceptions() > 0; } - -int uncaught_exceptions() _NOEXCEPT { - return __uncaught_exceptions(); -} - -#if defined(_LIBCPP_NO_VCRUNTIME) -bad_cast::bad_cast() _NOEXCEPT -{ -} - -bad_cast::~bad_cast() _NOEXCEPT -{ -} - -const char * -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 -{ - return "std::bad_typeid"; -} - -exception::~exception() _NOEXCEPT -{ -} - -const char* exception::what() const _NOEXCEPT -{ - return "std::exception"; -} - - -bad_exception::~bad_exception() _NOEXCEPT -{ -} - -const char* bad_exception::what() const _NOEXCEPT -{ - return "std::bad_exception"; -} - - -bad_alloc::bad_alloc() _NOEXCEPT -{ -} - -bad_alloc::~bad_alloc() _NOEXCEPT -{ -} - -const char* -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 -{ -} - -const char* -bad_array_new_length::what() const _NOEXCEPT -{ - return "bad_array_new_length"; -} -#endif // _LIBCPP_NO_VCRUNTIME - -} // namespace std diff --git a/lib/libcxx/src/support/runtime/exception_pointer_cxxabi.ipp b/lib/libcxx/src/support/runtime/exception_pointer_cxxabi.ipp deleted file mode 100644 index dfac8648c49..00000000000 --- a/lib/libcxx/src/support/runtime/exception_pointer_cxxabi.ipp +++ /dev/null @@ -1,74 +0,0 @@ -// -*- C++ -*- -//===----------------------------------------------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifndef HAVE_DEPENDENT_EH_ABI -#error this header may only be used with libc++abi or libcxxrt -#endif - -namespace std { - -exception_ptr::~exception_ptr() _NOEXCEPT { - __cxa_decrement_exception_refcount(__ptr_); -} - -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 -{ - if (__ptr_ != other.__ptr_) - { - __cxa_increment_exception_refcount(other.__ptr_); - __cxa_decrement_exception_refcount(__ptr_); - __ptr_ = other.__ptr_; - } - return *this; -} - -nested_exception::nested_exception() _NOEXCEPT - : __ptr_(current_exception()) -{ -} - -nested_exception::~nested_exception() _NOEXCEPT -{ -} - -_LIBCPP_NORETURN -void -nested_exception::rethrow_nested() const -{ - if (__ptr_ == nullptr) - terminate(); - rethrow_exception(__ptr_); -} - -exception_ptr current_exception() _NOEXCEPT -{ - // be nicer if there was a constructor that took a ptr, then - // this whole function would be just: - // return exception_ptr(__cxa_current_primary_exception()); - exception_ptr ptr; - ptr.__ptr_ = __cxa_current_primary_exception(); - return ptr; -} - -_LIBCPP_NORETURN -void rethrow_exception(exception_ptr p) -{ - __cxa_rethrow_primary_exception(p.__ptr_); - // if p.__ptr_ is NULL, above returns so we terminate - terminate(); -} - -} // namespace std diff --git a/lib/libcxx/src/support/runtime/exception_pointer_glibcxx.ipp b/lib/libcxx/src/support/runtime/exception_pointer_glibcxx.ipp deleted file mode 100644 index 9d20dfe4862..00000000000 --- a/lib/libcxx/src/support/runtime/exception_pointer_glibcxx.ipp +++ /dev/null @@ -1,78 +0,0 @@ -// -*- C++ -*- -//===----------------------------------------------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -// libsupc++ does not implement the dependent EH ABI and the functionality -// it uses to implement std::exception_ptr (which it declares as an alias of -// std::__exception_ptr::exception_ptr) is not directly exported to clients. So -// we have little choice but to hijack std::__exception_ptr::exception_ptr's -// (which fortunately has the same layout as our std::exception_ptr) copy -// constructor, assignment operator and destructor (which are part of its -// stable ABI), and its rethrow_exception(std::__exception_ptr::exception_ptr) -// function. - -namespace std { - -namespace __exception_ptr -{ - -struct exception_ptr -{ - void* __ptr_; - - 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 -{ - reinterpret_cast<__exception_ptr::exception_ptr*>(this)->~exception_ptr(); -} - -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 -{ - *reinterpret_cast<__exception_ptr::exception_ptr*>(this) = - reinterpret_cast<const __exception_ptr::exception_ptr&>(other); - return *this; -} - -nested_exception::nested_exception() _NOEXCEPT - : __ptr_(current_exception()) -{ -} - - -_LIBCPP_NORETURN -void -nested_exception::rethrow_nested() const -{ - if (__ptr_ == nullptr) - terminate(); - rethrow_exception(__ptr_); -} - -_LIBCPP_NORETURN -void rethrow_exception(exception_ptr p) -{ - rethrow_exception(reinterpret_cast<__exception_ptr::exception_ptr&>(p)); -} - -} // namespace std diff --git a/lib/libcxx/src/support/runtime/exception_pointer_msvc.ipp b/lib/libcxx/src/support/runtime/exception_pointer_msvc.ipp deleted file mode 100644 index 9b0d2361e40..00000000000 --- a/lib/libcxx/src/support/runtime/exception_pointer_msvc.ipp +++ /dev/null @@ -1,87 +0,0 @@ -// -*- C++ -*- -//===----------------------------------------------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include <stdio.h> -#include <stdlib.h> - -_LIBCPP_CRT_FUNC void __cdecl __ExceptionPtrCreate(void*); -_LIBCPP_CRT_FUNC void __cdecl __ExceptionPtrDestroy(void*); -_LIBCPP_CRT_FUNC void __cdecl __ExceptionPtrCopy(void*, const void*); -_LIBCPP_CRT_FUNC void __cdecl __ExceptionPtrAssign(void*, const void*); -_LIBCPP_CRT_FUNC bool __cdecl __ExceptionPtrCompare(const void*, const void*); -_LIBCPP_CRT_FUNC bool __cdecl __ExceptionPtrToBool(const void*); -_LIBCPP_CRT_FUNC void __cdecl __ExceptionPtrSwap(void*, void*); -_LIBCPP_CRT_FUNC void __cdecl __ExceptionPtrCurrentException(void*); -[[noreturn]] _LIBCPP_CRT_FUNC void __cdecl __ExceptionPtrRethrow(const void*); -_LIBCPP_CRT_FUNC void __cdecl -__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(const exception_ptr& __other) _NOEXCEPT { - __ExceptionPtrCopy(this, &__other); -} -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 dummy; - __ExceptionPtrAssign(this, &dummy); - return *this; -} - -exception_ptr::~exception_ptr() _NOEXCEPT { __ExceptionPtrDestroy(this); } - -exception_ptr::operator bool() const _NOEXCEPT { - return __ExceptionPtrToBool(this); -} - -bool operator==(const exception_ptr& __x, const exception_ptr& __y) _NOEXCEPT { - return __ExceptionPtrCompare(&__x, &__y); -} - - -void swap(exception_ptr& lhs, exception_ptr& rhs) _NOEXCEPT { - __ExceptionPtrSwap(&rhs, &lhs); -} - -exception_ptr __copy_exception_ptr(void* __except, const void* __ptr) { - exception_ptr __ret = nullptr; - if (__ptr) - __ExceptionPtrCopyException(&__ret, __except, __ptr); - return __ret; -} - -exception_ptr current_exception() _NOEXCEPT { - exception_ptr __ret; - __ExceptionPtrCurrentException(&__ret); - return __ret; -} - -_LIBCPP_NORETURN -void rethrow_exception(exception_ptr p) { __ExceptionPtrRethrow(&p); } - -nested_exception::nested_exception() _NOEXCEPT : __ptr_(current_exception()) {} - -nested_exception::~nested_exception() _NOEXCEPT {} - -_LIBCPP_NORETURN -void nested_exception::rethrow_nested() const { - if (__ptr_ == nullptr) - terminate(); - rethrow_exception(__ptr_); -} - -} // namespace std diff --git a/lib/libcxx/src/support/runtime/exception_pointer_unimplemented.ipp b/lib/libcxx/src/support/runtime/exception_pointer_unimplemented.ipp deleted file mode 100644 index 21c182c8597..00000000000 --- a/lib/libcxx/src/support/runtime/exception_pointer_unimplemented.ipp +++ /dev/null @@ -1,80 +0,0 @@ -// -*- C++ -*- -//===----------------------------------------------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include <stdio.h> -#include <stdlib.h> - -namespace std { - -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 - : __ptr_(other.__ptr_) -{ -# warning exception_ptr not yet implemented - fprintf(stderr, "exception_ptr not yet implemented\n"); - ::abort(); -} - -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 - : __ptr_(current_exception()) -{ -} - -#if !defined(__GLIBCXX__) - -nested_exception::~nested_exception() _NOEXCEPT -{ -} - -#endif - -_LIBCPP_NORETURN -void -nested_exception::rethrow_nested() const -{ -# warning exception_ptr not yet implemented - fprintf(stderr, "exception_ptr not yet implemented\n"); - ::abort(); -#if 0 - if (__ptr_ == nullptr) - terminate(); - rethrow_exception(__ptr_); -#endif // FIXME -} - -exception_ptr current_exception() _NOEXCEPT -{ -# warning exception_ptr not yet implemented - fprintf(stderr, "exception_ptr not yet implemented\n"); - ::abort(); -} - -_LIBCPP_NORETURN -void rethrow_exception(exception_ptr p) -{ -# warning exception_ptr not yet implemented - fprintf(stderr, "exception_ptr not yet implemented\n"); - ::abort(); -} - -} // namespace std diff --git a/lib/libcxx/src/support/runtime/new_handler_fallback.ipp b/lib/libcxx/src/support/runtime/new_handler_fallback.ipp deleted file mode 100644 index ec3f52354ca..00000000000 --- a/lib/libcxx/src/support/runtime/new_handler_fallback.ipp +++ /dev/null @@ -1,27 +0,0 @@ -// -*- C++ -*- -//===----------------------------------------------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -namespace std { - -_LIBCPP_SAFE_STATIC static std::new_handler __new_handler; - -new_handler -set_new_handler(new_handler handler) _NOEXCEPT -{ - return __libcpp_atomic_exchange(&__new_handler, handler); -} - -new_handler -get_new_handler() _NOEXCEPT -{ - return __libcpp_atomic_load(&__new_handler); -} - -} // namespace std diff --git a/lib/libcxx/src/support/solaris/README b/lib/libcxx/src/support/solaris/README deleted file mode 100644 index 89c887a3b4a..00000000000 --- a/lib/libcxx/src/support/solaris/README +++ /dev/null @@ -1,4 +0,0 @@ -This directory contains a partial implementation of the xlocale APIs for -Solaris. Some portions are lifted from FreeBSD libc, and so are covered by a -2-clause BSD license instead of the MIT/UUIC license that the rest of libc++ is -distributed under. diff --git a/lib/libcxx/src/support/solaris/mbsnrtowcs.inc b/lib/libcxx/src/support/solaris/mbsnrtowcs.inc deleted file mode 100644 index 074045277ca..00000000000 --- a/lib/libcxx/src/support/solaris/mbsnrtowcs.inc +++ /dev/null @@ -1,76 +0,0 @@ - - -/*- - * As noted in the source, some portions of this implementation are copied from - * FreeBSD libc. These are covered by the following copyright: - * - * Copyright (c) 2002-2004 Tim J. Robbins. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - */ - -size_t -mbsnrtowcs_l(wchar_t * __restrict dst, const char ** __restrict src, - size_t nms, size_t len, mbstate_t * __restrict ps, locale_t loc) -{ - const char *s; - size_t nchr; - wchar_t wc; - size_t nb; - FIX_LOCALE(loc); - - s = *src; - nchr = 0; - - if (dst == NULL) { - for (;;) { - if ((nb = mbrtowc_l(&wc, s, nms, ps, loc)) == (size_t)-1) - /* Invalid sequence - mbrtowc() sets errno. */ - return ((size_t)-1); - else if (nb == 0 || nb == (size_t)-2) - return (nchr); - s += nb; - nms -= nb; - nchr++; - } - /*NOTREACHED*/ - } - - while (len-- > 0) { - if ((nb = mbrtowc_l(dst, s, nms, ps, loc)) == (size_t)-1) { - *src = s; - return ((size_t)-1); - } else if (nb == (size_t)-2) { - *src = s + nms; - return (nchr); - } else if (nb == 0) { - *src = NULL; - return (nchr); - } - s += nb; - nms -= nb; - nchr++; - dst++; - } - *src = s; - return (nchr); -} diff --git a/lib/libcxx/src/support/solaris/wcsnrtombs.inc b/lib/libcxx/src/support/solaris/wcsnrtombs.inc deleted file mode 100644 index 67e7078f2d5..00000000000 --- a/lib/libcxx/src/support/solaris/wcsnrtombs.inc +++ /dev/null @@ -1,93 +0,0 @@ -/*- - * Copyright (c) 2002-2004 Tim J. Robbins. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - */ - - -size_t -wcsnrtombs_l(char * __restrict dst, const wchar_t ** __restrict src, - size_t nwc, size_t len, mbstate_t * __restrict ps, locale_t loc) -{ - FIX_LOCALE(loc); - mbstate_t mbsbak; - char buf[MB_CUR_MAX_L(loc)]; - const wchar_t *s; - size_t nbytes; - size_t nb; - - s = *src; - nbytes = 0; - - if (dst == NULL) { - while (nwc-- > 0) { - if ((nb = wcrtomb_l(buf, *s, ps, loc)) == (size_t)-1) - /* Invalid character - wcrtomb() sets errno. */ - return ((size_t)-1); - else if (*s == L'\0') - return (nbytes + nb - 1); - s++; - nbytes += nb; - } - return (nbytes); - } - - while (len > 0 && nwc-- > 0) { - if (len > (size_t)MB_CUR_MAX_L(loc)) { - /* Enough space to translate in-place. */ - if ((nb = wcrtomb_l(dst, *s, ps, loc)) == (size_t)-1) { - *src = s; - return ((size_t)-1); - } - } else { - /* - * May not be enough space; use temp. buffer. - * - * We need to save a copy of the conversion state - * here so we can restore it if the multibyte - * character is too long for the buffer. - */ - mbsbak = *ps; - if ((nb = wcrtomb_l(buf, *s, ps, loc)) == (size_t)-1) { - *src = s; - return ((size_t)-1); - } - if (nb > (int)len) { - /* MB sequence for character won't fit. */ - *ps = mbsbak; - break; - } - memcpy(dst, buf, nb); - } - if (*s == L'\0') { - *src = NULL; - return (nbytes + nb - 1); - } - s++; - dst += nb; - len -= nb; - nbytes += nb; - } - *src = s; - return (nbytes); -} - diff --git a/lib/libcxx/src/support/solaris/xlocale.cpp b/lib/libcxx/src/support/solaris/xlocale.cpp deleted file mode 100644 index 6eaf317c768..00000000000 --- a/lib/libcxx/src/support/solaris/xlocale.cpp +++ /dev/null @@ -1,69 +0,0 @@ -//===----------------------------------------------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifdef __sun__ - -#include "support/solaris/xlocale.h" -#include <stdarg.h> -#include <stdio.h> -#include <sys/localedef.h> - -extern "C" { - -int isxdigit_l(int __c, locale_t __l) { - return isxdigit(__c); -} - -int iswxdigit_l(wint_t __c, locale_t __l) { - return isxdigit(__c); -} - -// FIXME: This disregards the locale, which is Very Wrong -#define vsnprintf_l(__s, __n, __l, __format, __va) \ - vsnprintf(__s, __n, __format, __va) - -int snprintf_l(char *__s, size_t __n, locale_t __l, const char *__format, ...) -{ - va_list __va; - va_start(__va, __format); - int __res = vsnprintf_l(__s, __n , __l, __format, __va); - va_end(__va); - return __res; -} - -int asprintf_l(char **__s, locale_t __l, const char *__format, ...) { - va_list __va; - va_start(__va, __format); - // FIXME: - int __res = vasprintf(__s, __format, __va); - va_end(__va); - return __res; -} - -int sscanf_l(const char *__s, locale_t __l, const char *__format, ...) { - va_list __va; - va_start(__va, __format); - // FIXME: - int __res = vsscanf(__s, __format, __va); - va_end(__va); - return __res; -} - -size_t mbrtowc_l(wchar_t *__pwc, const char *__pmb, - size_t __max, mbstate_t *__ps, locale_t __loc) { - return mbrtowc(__pwc, __pmb, __max, __ps); -} - -struct lconv *localeconv_l(locale_t __l) { - return localeconv(); -} - -}; - -#endif // __sun__ diff --git a/lib/libcxx/src/support/win32/locale_win32.cpp b/lib/libcxx/src/support/win32/locale_win32.cpp deleted file mode 100644 index cad9d4e8146..00000000000 --- a/lib/libcxx/src/support/win32/locale_win32.cpp +++ /dev/null @@ -1,123 +0,0 @@ -// -*- C++ -*- -//===-------------------- support/win32/locale_win32.cpp ------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include <locale> -#include <cstdarg> // va_start, va_end -#include <memory> -#include <type_traits> - -int __libcpp_vasprintf(char **sptr, const char *__restrict fmt, va_list ap); - -using std::__libcpp_locale_guard; - -// FIXME: base currently unused. Needs manual work to construct the new locale -locale_t newlocale( int mask, const char * locale, locale_t /*base*/ ) -{ - return {_create_locale( LC_ALL, locale ), locale}; -} - -decltype(MB_CUR_MAX) MB_CUR_MAX_L( locale_t __l ) -{ -#if defined(_LIBCPP_MSVCRT) - return ___mb_cur_max_l_func(__l); -#else - __libcpp_locale_guard __current(__l); - return MB_CUR_MAX; -#endif -} - - -lconv *localeconv_l( locale_t loc ) -{ - __libcpp_locale_guard __current(loc); - return localeconv(); -} -size_t mbrlen_l( const char *__restrict s, size_t n, - mbstate_t *__restrict ps, locale_t loc ) -{ - __libcpp_locale_guard __current(loc); - return mbrlen( s, n, ps ); -} -size_t mbsrtowcs_l( wchar_t *__restrict dst, const char **__restrict src, - size_t len, mbstate_t *__restrict ps, locale_t loc ) -{ - __libcpp_locale_guard __current(loc); - return mbsrtowcs( dst, src, len, ps ); -} -size_t wcrtomb_l( char *__restrict s, wchar_t wc, mbstate_t *__restrict ps, - locale_t loc ) -{ - __libcpp_locale_guard __current(loc); - return wcrtomb( s, wc, ps ); -} -size_t mbrtowc_l( wchar_t *__restrict pwc, const char *__restrict s, - size_t n, mbstate_t *__restrict ps, locale_t loc ) -{ - __libcpp_locale_guard __current(loc); - return mbrtowc( pwc, s, n, ps ); -} -size_t mbsnrtowcs_l( wchar_t *__restrict dst, const char **__restrict src, - size_t nms, size_t len, mbstate_t *__restrict ps, locale_t loc ) -{ - __libcpp_locale_guard __current(loc); - return mbsnrtowcs( dst, src, nms, len, ps ); -} -size_t wcsnrtombs_l( char *__restrict dst, const wchar_t **__restrict src, - size_t nwc, size_t len, mbstate_t *__restrict ps, locale_t loc ) -{ - __libcpp_locale_guard __current(loc); - return wcsnrtombs( dst, src, nwc, len, ps ); -} -wint_t btowc_l( int c, locale_t loc ) -{ - __libcpp_locale_guard __current(loc); - return btowc( c ); -} -int wctob_l( wint_t c, locale_t loc ) -{ - __libcpp_locale_guard __current(loc); - return wctob( c ); -} - -int snprintf_l(char *ret, size_t n, locale_t loc, const char *format, ...) -{ - __libcpp_locale_guard __current(loc); - va_list ap; - va_start( ap, format ); - int result = vsnprintf( ret, n, format, ap ); - va_end(ap); - return result; -} - -int asprintf_l( char **ret, locale_t loc, const char *format, ... ) -{ - va_list ap; - va_start( ap, format ); - int result = vasprintf_l( ret, loc, format, ap ); - va_end(ap); - return result; -} -int vasprintf_l( char **ret, locale_t loc, const char *format, va_list ap ) -{ - __libcpp_locale_guard __current(loc); - return __libcpp_vasprintf( ret, format, ap ); -} - -#if !defined(_LIBCPP_MSVCRT) -float strtof_l(const char* nptr, char** endptr, locale_t loc) { - __libcpp_locale_guard __current(loc); - return strtof(nptr, endptr); -} - -long double strtold_l(const char* nptr, char** endptr, locale_t loc) { - __libcpp_locale_guard __current(loc); - return strtold(nptr, endptr); -} -#endif diff --git a/lib/libcxx/src/support/win32/support.cpp b/lib/libcxx/src/support/win32/support.cpp deleted file mode 100644 index aa636fba50b..00000000000 --- a/lib/libcxx/src/support/win32/support.cpp +++ /dev/null @@ -1,155 +0,0 @@ -// -*- C++ -*- -//===----------------------- support/win32/support.h ----------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include <cstdarg> // va_start, va_end -#include <cstddef> // size_t -#include <cstdlib> // malloc -#include <cstdio> // vsprintf, vsnprintf -#include <cstring> // strcpy, wcsncpy -#include <cwchar> // mbstate_t - - -// Like sprintf, but when return value >= 0 it returns -// a pointer to a malloc'd string in *sptr. -// If return >= 0, use free to delete *sptr. -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 ); - if (count < 0) - return count; - size_t buffer_size = static_cast<size_t>(count) + 1; - char* p = static_cast<char*>(malloc(buffer_size)); - if ( ! p ) - return -1; - // If we haven't used exactly what was required, something is wrong. - // Maybe bug in vsnprintf. Report the error and return. - if (_vsnprintf(p, buffer_size, format, ap) != count) { - free(p); - return -1; - } - // All good. This is returning memory to the caller not freeing it. - *sptr = p; - return count; -} - -// Returns >= 0: the number of wide characters found in the -// multi byte sequence src (of src_size_bytes), that fit in the buffer dst -// (of max_dest_chars elements size). The count returned excludes the -// null terminator. When dst is NULL, no characters are copied -// and no "out" parameters are updated. -// Returns (size_t) -1: an incomplete sequence encountered. -// Leaves *src pointing the next character to convert or NULL -// if a null character was converted from *src. -size_t mbsnrtowcs( wchar_t *__restrict dst, const char **__restrict src, - size_t src_size_bytes, size_t max_dest_chars, mbstate_t *__restrict ps ) -{ - const size_t terminated_sequence = static_cast<size_t>(0); - //const size_t invalid_sequence = static_cast<size_t>(-1); - const size_t incomplete_sequence = static_cast< size_t>(-2); - - size_t dest_converted = 0; - size_t source_converted = 0; - size_t source_remaining = src_size_bytes; - size_t result = 0; - bool have_result = false; - - while ( source_remaining ) { - if ( dst && dest_converted >= max_dest_chars ) - break; - // Converts one multi byte character. - // if result > 0, it's the size in bytes of that character. - // othewise if result is zero it indicates the null character has been found. - // otherwise it's an error and errno may be set. - size_t char_size = mbrtowc( dst ? dst + dest_converted : NULL, *src + source_converted, source_remaining, ps ); - // Don't do anything to change errno from here on. - if ( char_size > 0 ) { - source_remaining -= char_size; - source_converted += char_size; - ++dest_converted; - continue; - } - result = char_size; - have_result = true; - break; - } - if ( dst ) { - if ( have_result && result == terminated_sequence ) - *src = NULL; - else - *src += source_converted; - } - if ( have_result && result != terminated_sequence && result != incomplete_sequence ) - return static_cast<size_t>(-1); - - return dest_converted; -} - -// Converts max_source_chars from the wide character buffer pointer to by *src, -// into the multi byte character sequence buffer stored at dst which must be -// dst_size_bytes bytes in size. -// Returns >= 0: the number of bytes in the sequence -// converted from *src, excluding the null terminator. -// Returns size_t(-1) if an error occurs, also sets errno. -// If dst is NULL dst_size_bytes is ignored and no bytes are copied to dst -// and no "out" parameters are updated. -size_t wcsnrtombs( char *__restrict dst, const wchar_t **__restrict src, - size_t max_source_chars, size_t dst_size_bytes, mbstate_t *__restrict ps ) -{ - //const size_t invalid_sequence = static_cast<size_t>(-1); - - size_t source_converted = 0; - size_t dest_converted = 0; - size_t dest_remaining = dst_size_bytes; - size_t char_size = 0; - const errno_t no_error = ( errno_t) 0; - errno_t result = ( errno_t ) 0; - bool have_result = false; - bool terminator_found = false; - - while ( source_converted != max_source_chars ) { - if ( ! dest_remaining ) - break; - wchar_t c = (*src)[source_converted]; - if ( dst ) - result = wcrtomb_s( &char_size, dst + dest_converted, dest_remaining, c, ps); - else - result = wcrtomb_s( &char_size, NULL, 0, c, ps); - // If result is zero there is no error and char_size contains the - // size of the multi-byte-sequence converted. - // Otherwise result indicates an errno type error. - if ( result == no_error ) { - if ( c == L'\0' ) { - terminator_found = true; - break; - } - ++source_converted; - if ( dst ) - dest_remaining -= char_size; - dest_converted += char_size; - continue; - } - have_result = true; - break; - } - if ( dst ) { - if ( terminator_found ) - *src = NULL; - else - *src = *src + source_converted; - } - if ( have_result && result != no_error ) { - errno = result; - return static_cast<size_t>(-1); - } - - return dest_converted; -} diff --git a/lib/libcxx/src/support/win32/thread_win32.cpp b/lib/libcxx/src/support/win32/thread_win32.cpp deleted file mode 100644 index 1567042d8e2..00000000000 --- a/lib/libcxx/src/support/win32/thread_win32.cpp +++ /dev/null @@ -1,276 +0,0 @@ -// -*- C++ -*- -//===-------------------- support/win32/thread_win32.cpp ------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include <__threading_support> -#include <windows.h> -#include <process.h> -#include <fibersapi.h> - -_LIBCPP_BEGIN_NAMESPACE_STD - -static_assert(sizeof(__libcpp_mutex_t) == sizeof(SRWLOCK), ""); -static_assert(alignof(__libcpp_mutex_t) == alignof(SRWLOCK), ""); - -static_assert(sizeof(__libcpp_recursive_mutex_t) == sizeof(CRITICAL_SECTION), - ""); -static_assert(alignof(__libcpp_recursive_mutex_t) == alignof(CRITICAL_SECTION), - ""); - -static_assert(sizeof(__libcpp_condvar_t) == sizeof(CONDITION_VARIABLE), ""); -static_assert(alignof(__libcpp_condvar_t) == alignof(CONDITION_VARIABLE), ""); - -static_assert(sizeof(__libcpp_exec_once_flag) == sizeof(INIT_ONCE), ""); -static_assert(alignof(__libcpp_exec_once_flag) == alignof(INIT_ONCE), ""); - -static_assert(sizeof(__libcpp_thread_id) == sizeof(DWORD), ""); -static_assert(alignof(__libcpp_thread_id) == alignof(DWORD), ""); - -static_assert(sizeof(__libcpp_thread_t) == sizeof(HANDLE), ""); -static_assert(alignof(__libcpp_thread_t) == alignof(HANDLE), ""); - -static_assert(sizeof(__libcpp_tls_key) == sizeof(DWORD), ""); -static_assert(alignof(__libcpp_tls_key) == alignof(DWORD), ""); - -// Mutex -int __libcpp_recursive_mutex_init(__libcpp_recursive_mutex_t *__m) -{ - InitializeCriticalSection((LPCRITICAL_SECTION)__m); - return 0; -} - -int __libcpp_recursive_mutex_lock(__libcpp_recursive_mutex_t *__m) -{ - EnterCriticalSection((LPCRITICAL_SECTION)__m); - return 0; -} - -bool __libcpp_recursive_mutex_trylock(__libcpp_recursive_mutex_t *__m) -{ - return TryEnterCriticalSection((LPCRITICAL_SECTION)__m) != 0; -} - -int __libcpp_recursive_mutex_unlock(__libcpp_recursive_mutex_t *__m) -{ - LeaveCriticalSection((LPCRITICAL_SECTION)__m); - return 0; -} - -int __libcpp_recursive_mutex_destroy(__libcpp_recursive_mutex_t *__m) -{ - DeleteCriticalSection((LPCRITICAL_SECTION)__m); - return 0; -} - -int __libcpp_mutex_lock(__libcpp_mutex_t *__m) -{ - AcquireSRWLockExclusive((PSRWLOCK)__m); - return 0; -} - -bool __libcpp_mutex_trylock(__libcpp_mutex_t *__m) -{ - return TryAcquireSRWLockExclusive((PSRWLOCK)__m) != 0; -} - -int __libcpp_mutex_unlock(__libcpp_mutex_t *__m) -{ - ReleaseSRWLockExclusive((PSRWLOCK)__m); - return 0; -} - -int __libcpp_mutex_destroy(__libcpp_mutex_t *__m) -{ - static_cast<void>(__m); - return 0; -} - -// Condition Variable -int __libcpp_condvar_signal(__libcpp_condvar_t *__cv) -{ - WakeConditionVariable((PCONDITION_VARIABLE)__cv); - return 0; -} - -int __libcpp_condvar_broadcast(__libcpp_condvar_t *__cv) -{ - WakeAllConditionVariable((PCONDITION_VARIABLE)__cv); - return 0; -} - -int __libcpp_condvar_wait(__libcpp_condvar_t *__cv, __libcpp_mutex_t *__m) -{ - SleepConditionVariableSRW((PCONDITION_VARIABLE)__cv, (PSRWLOCK)__m, INFINITE, 0); - return 0; -} - -int __libcpp_condvar_timedwait(__libcpp_condvar_t *__cv, __libcpp_mutex_t *__m, - timespec *__ts) -{ - using namespace _VSTD::chrono; - - auto duration = seconds(__ts->tv_sec) + nanoseconds(__ts->tv_nsec); - auto abstime = - system_clock::time_point(duration_cast<system_clock::duration>(duration)); - auto timeout_ms = duration_cast<milliseconds>(abstime - system_clock::now()); - - if (!SleepConditionVariableSRW((PCONDITION_VARIABLE)__cv, (PSRWLOCK)__m, - timeout_ms.count() > 0 ? timeout_ms.count() - : 0, - 0)) - { - auto __ec = GetLastError(); - return __ec == ERROR_TIMEOUT ? ETIMEDOUT : __ec; - } - return 0; -} - -int __libcpp_condvar_destroy(__libcpp_condvar_t *__cv) -{ - static_cast<void>(__cv); - return 0; -} - -// Execute Once -static inline _LIBCPP_INLINE_VISIBILITY BOOL CALLBACK -__libcpp_init_once_execute_once_thunk(PINIT_ONCE __init_once, PVOID __parameter, - PVOID *__context) -{ - static_cast<void>(__init_once); - static_cast<void>(__context); - - void (*init_routine)(void) = reinterpret_cast<void (*)(void)>(__parameter); - init_routine(); - return TRUE; -} - -int __libcpp_execute_once(__libcpp_exec_once_flag *__flag, - void (*__init_routine)(void)) -{ - if (!InitOnceExecuteOnce((PINIT_ONCE)__flag, __libcpp_init_once_execute_once_thunk, - reinterpret_cast<void *>(__init_routine), NULL)) - return GetLastError(); - return 0; -} - -// Thread ID -bool __libcpp_thread_id_equal(__libcpp_thread_id __lhs, - __libcpp_thread_id __rhs) -{ - return __lhs == __rhs; -} - -bool __libcpp_thread_id_less(__libcpp_thread_id __lhs, __libcpp_thread_id __rhs) -{ - return __lhs < __rhs; -} - -// Thread -struct __libcpp_beginthreadex_thunk_data -{ - void *(*__func)(void *); - void *__arg; -}; - -static inline _LIBCPP_INLINE_VISIBILITY unsigned WINAPI -__libcpp_beginthreadex_thunk(void *__raw_data) -{ - auto *__data = - static_cast<__libcpp_beginthreadex_thunk_data *>(__raw_data); - auto *__func = __data->__func; - void *__arg = __data->__arg; - delete __data; - return static_cast<unsigned>(reinterpret_cast<uintptr_t>(__func(__arg))); -} - -bool __libcpp_thread_isnull(const __libcpp_thread_t *__t) { - return *__t == 0; -} - -int __libcpp_thread_create(__libcpp_thread_t *__t, void *(*__func)(void *), - void *__arg) -{ - auto *__data = new __libcpp_beginthreadex_thunk_data; - __data->__func = __func; - __data->__arg = __arg; - - *__t = reinterpret_cast<HANDLE>(_beginthreadex(nullptr, 0, - __libcpp_beginthreadex_thunk, - __data, 0, nullptr)); - - if (*__t) - return 0; - return GetLastError(); -} - -__libcpp_thread_id __libcpp_thread_get_current_id() -{ - return GetCurrentThreadId(); -} - -__libcpp_thread_id __libcpp_thread_get_id(const __libcpp_thread_t *__t) -{ - return GetThreadId(*__t); -} - -int __libcpp_thread_join(__libcpp_thread_t *__t) -{ - if (WaitForSingleObjectEx(*__t, INFINITE, FALSE) == WAIT_FAILED) - return GetLastError(); - if (!CloseHandle(*__t)) - return GetLastError(); - return 0; -} - -int __libcpp_thread_detach(__libcpp_thread_t *__t) -{ - if (!CloseHandle(*__t)) - return GetLastError(); - return 0; -} - -void __libcpp_thread_yield() -{ - SwitchToThread(); -} - -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)); - // FIXME(compnerd) this should be an alertable sleep (WFSO or SleepEx) - Sleep(__ms.count()); -} - -// Thread Local Storage -int __libcpp_tls_create(__libcpp_tls_key* __key, - void(_LIBCPP_TLS_DESTRUCTOR_CC* __at_exit)(void*)) -{ - DWORD index = FlsAlloc(__at_exit); - if (index == FLS_OUT_OF_INDEXES) - return GetLastError(); - *__key = index; - return 0; -} - -void *__libcpp_tls_get(__libcpp_tls_key __key) -{ - return FlsGetValue(__key); -} - -int __libcpp_tls_set(__libcpp_tls_key __key, void *__p) -{ - if (!FlsSetValue(__key, __p)) - return GetLastError(); - return 0; -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/system_error.cpp b/lib/libcxx/src/system_error.cpp deleted file mode 100644 index 06caa6fecd9..00000000000 --- a/lib/libcxx/src/system_error.cpp +++ /dev/null @@ -1,296 +0,0 @@ -//===---------------------- system_error.cpp ------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "__config" - -#include "system_error" - -#include "include/config_elast.h" -#include "cerrno" -#include "cstring" -#include "cstdio" -#include "cstdlib" -#include "string" -#include "string.h" -#include "__debug" - -#if defined(__ANDROID__) -#include <android/api-level.h> -#endif - -_LIBCPP_BEGIN_NAMESPACE_STD - -// class error_category - -#if defined(_LIBCPP_DEPRECATED_ABI_LEGACY_LIBRARY_DEFINITIONS_FOR_INLINE_FUNCTIONS) -error_category::error_category() _NOEXCEPT -{ -} -#endif - -error_category::~error_category() _NOEXCEPT -{ -} - -error_condition -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 -{ - return default_error_condition(code) == condition; -} - -bool -error_category::equivalent(const error_code& code, int condition) const _NOEXCEPT -{ - return *this == code.category() && code.value() == condition; -} - -#if !defined(_LIBCPP_HAS_NO_THREADS) -namespace { - -// GLIBC also uses 1024 as the maximum buffer size internally. -constexpr size_t strerror_buff_size = 1024; - -string do_strerror_r(int ev); - -#if defined(_LIBCPP_MSVCRT_LIKE) -string do_strerror_r(int ev) { - char buffer[strerror_buff_size]; - if (::strerror_s(buffer, strerror_buff_size, ev) == 0) - return string(buffer); - std::snprintf(buffer, strerror_buff_size, "unknown error %d", ev); - return string(buffer); -} -#else - -// Only one of the two following functions will be used, depending on -// the return type of strerror_r: - -// For the GNU variant, a char* return value: -__attribute__((unused)) const char * -handle_strerror_r_return(char *strerror_return, char *buffer) { - // GNU always returns a string pointer in its return value. The - // string might point to either the input buffer, or a static - // buffer, but we don't care which. - return strerror_return; -} - -// For the POSIX variant: an int return value. -__attribute__((unused)) const char * -handle_strerror_r_return(int strerror_return, char *buffer) { - // The POSIX variant either: - // - fills in the provided buffer and returns 0 - // - returns a positive error value, or - // - returns -1 and fills in errno with an error value. - if (strerror_return == 0) - return buffer; - - // Only handle EINVAL. Other errors abort. - int new_errno = strerror_return == -1 ? errno : strerror_return; - if (new_errno == EINVAL) - return ""; - - _LIBCPP_ASSERT(new_errno == ERANGE, "unexpected error from ::strerror_r"); - // FIXME maybe? 'strerror_buff_size' is likely to exceed the - // maximum error size so ERANGE shouldn't be returned. - std::abort(); -} - -// This function handles both GNU and POSIX variants, dispatching to -// one of the two above functions. -string do_strerror_r(int ev) { - char buffer[strerror_buff_size]; - // Preserve errno around the call. (The C++ standard requires that - // system_error functions not modify errno). - const int old_errno = errno; - const char *error_message = handle_strerror_r_return( - ::strerror_r(ev, buffer, strerror_buff_size), buffer); - // If we didn't get any message, print one now. - if (!error_message[0]) { - std::snprintf(buffer, strerror_buff_size, "Unknown error %d", ev); - error_message = buffer; - } - errno = old_errno; - return string(error_message); -} -#endif -} // end namespace -#endif - -string -__do_message::message(int ev) const -{ -#if defined(_LIBCPP_HAS_NO_THREADS) - return string(::strerror(ev)); -#else - return do_strerror_r(ev); -#endif -} - -class _LIBCPP_HIDDEN __generic_error_category - : public __do_message -{ -public: - virtual const char* name() const _NOEXCEPT; - virtual string message(int ev) const; -}; - -const char* -__generic_error_category::name() const _NOEXCEPT -{ - return "generic"; -} - -string -__generic_error_category::message(int ev) const -{ -#ifdef _LIBCPP_ELAST - if (ev > _LIBCPP_ELAST) - return string("unspecified generic_category error"); -#endif // _LIBCPP_ELAST - return __do_message::message(ev); -} - -const error_category& -generic_category() _NOEXCEPT -{ - static __generic_error_category s; - return s; -} - -class _LIBCPP_HIDDEN __system_error_category - : public __do_message -{ -public: - virtual const char* name() const _NOEXCEPT; - virtual string message(int ev) const; - virtual error_condition default_error_condition(int ev) const _NOEXCEPT; -}; - -const char* -__system_error_category::name() const _NOEXCEPT -{ - return "system"; -} - -string -__system_error_category::message(int ev) const -{ -#ifdef _LIBCPP_ELAST - if (ev > _LIBCPP_ELAST) - return string("unspecified system_category error"); -#endif // _LIBCPP_ELAST - return __do_message::message(ev); -} - -error_condition -__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 - return error_condition(ev, generic_category()); -} - -const error_category& -system_category() _NOEXCEPT -{ - static __system_error_category s; - return s; -} - -// error_condition - -string -error_condition::message() const -{ - return __cat_->message(__val_); -} - -// error_code - -string -error_code::message() const -{ - return __cat_->message(__val_); -} - -// system_error - -string -system_error::__init(const error_code& ec, string what_arg) -{ - if (ec) - { - if (!what_arg.empty()) - what_arg += ": "; - what_arg += ec.message(); - } - return what_arg; -} - -system_error::system_error(error_code ec, const string& what_arg) - : runtime_error(__init(ec, what_arg)), - __ec_(ec) -{ -} - -system_error::system_error(error_code ec, const char* what_arg) - : runtime_error(__init(ec, what_arg)), - __ec_(ec) -{ -} - -system_error::system_error(error_code ec) - : runtime_error(__init(ec, "")), - __ec_(ec) -{ -} - -system_error::system_error(int ev, const error_category& ecat, const string& what_arg) - : runtime_error(__init(error_code(ev, ecat), what_arg)), - __ec_(error_code(ev, ecat)) -{ -} - -system_error::system_error(int ev, const error_category& ecat, const char* what_arg) - : runtime_error(__init(error_code(ev, ecat), what_arg)), - __ec_(error_code(ev, ecat)) -{ -} - -system_error::system_error(int ev, const error_category& ecat) - : runtime_error(__init(error_code(ev, ecat), "")), - __ec_(error_code(ev, ecat)) -{ -} - -system_error::~system_error() _NOEXCEPT -{ -} - -void -__throw_system_error(int ev, const char* what_arg) -{ -#ifndef _LIBCPP_NO_EXCEPTIONS - throw system_error(error_code(ev, system_category()), what_arg); -#else - (void)ev; - (void)what_arg; - _VSTD::abort(); -#endif -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/thread.cpp b/lib/libcxx/src/thread.cpp deleted file mode 100644 index 57ae90c686a..00000000000 --- a/lib/libcxx/src/thread.cpp +++ /dev/null @@ -1,222 +0,0 @@ -//===------------------------- thread.cpp----------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "__config" -#ifndef _LIBCPP_HAS_NO_THREADS - -#include "thread" -#include "exception" -#include "vector" -#include "future" -#include "limits" -#include <sys/types.h> - -#if defined(__unix__) || (defined(__APPLE__) && defined(__MACH__)) -# include <sys/param.h> -# if defined(__FreeBSD__) || defined(__NetBSD__) || defined(__OpenBSD__) || defined(__DragonFly__) || defined(__APPLE__) -# include <sys/sysctl.h> -# endif -#endif // defined(__unix__) || (defined(__APPLE__) && defined(__MACH__)) - -#if defined(__unix__) || (defined(__APPLE__) && defined(__MACH__)) || defined(__CloudABI__) || defined(__Fuchsia__) -# include <unistd.h> -#endif // defined(__unix__) || (defined(__APPLE__) && defined(__MACH__)) || defined(__CloudABI__) || defined(__Fuchsia__) - -#if defined(__NetBSD__) -#pragma weak pthread_create // Do not create libpthread dependency -#endif - -#if defined(_LIBCPP_WIN32API) -#include <windows.h> -#endif - -_LIBCPP_BEGIN_NAMESPACE_STD - -thread::~thread() -{ - if (!__libcpp_thread_isnull(&__t_)) - terminate(); -} - -void -thread::join() -{ - int ec = EINVAL; - if (!__libcpp_thread_isnull(&__t_)) - { - ec = __libcpp_thread_join(&__t_); - if (ec == 0) - __t_ = _LIBCPP_NULL_THREAD; - } - - if (ec) - __throw_system_error(ec, "thread::join failed"); -} - -void -thread::detach() -{ - int ec = EINVAL; - if (!__libcpp_thread_isnull(&__t_)) - { - ec = __libcpp_thread_detach(&__t_); - if (ec == 0) - __t_ = _LIBCPP_NULL_THREAD; - } - - if (ec) - __throw_system_error(ec, "thread::detach failed"); -} - -unsigned -thread::hardware_concurrency() _NOEXCEPT -{ -#if defined(CTL_HW) && defined(HW_NCPUONLINE) - unsigned n; - int mib[2] = {CTL_HW, HW_NCPUONLINE}; - std::size_t s = sizeof(n); - sysctl(mib, 2, &n, &s, 0, 0); - return n; -#elif defined(_SC_NPROCESSORS_ONLN) - long result = sysconf(_SC_NPROCESSORS_ONLN); - // sysconf returns -1 if the name is invalid, the option does not exist or - // does not have a definite limit. - // if sysconf returns some other negative number, we have no idea - // what is going on. Default to something safe. - if (result < 0) - return 0; - return static_cast<unsigned>(result); -#elif defined(_LIBCPP_WIN32API) - SYSTEM_INFO info; - GetSystemInfo(&info); - return info.dwNumberOfProcessors; -#else // defined(CTL_HW) && defined(HW_NCPU) - // TODO: grovel through /proc or check cpuid on x86 and similar - // instructions on other architectures. -# if defined(_LIBCPP_WARNING) - _LIBCPP_WARNING("hardware_concurrency not yet implemented") -# else -# warning hardware_concurrency not yet implemented -# endif - return 0; // Means not computable [thread.thread.static] -#endif // defined(CTL_HW) && defined(HW_NCPU) -} - -namespace this_thread -{ - -void -sleep_for(const chrono::nanoseconds& ns) -{ - if (ns > chrono::nanoseconds::zero()) - { - __libcpp_thread_sleep_for(ns); - } -} - -} // this_thread - -__thread_specific_ptr<__thread_struct>& -__thread_local_data() -{ - static __thread_specific_ptr<__thread_struct> __p; - return __p; -} - -// __thread_struct_imp - -template <class T> -class _LIBCPP_HIDDEN __hidden_allocator -{ -public: - typedef T value_type; - - T* allocate(size_t __n) - {return static_cast<T*>(::operator new(__n * sizeof(T)));} - void deallocate(T* __p, size_t) {::operator delete(static_cast<void*>(__p));} - - size_t max_size() const {return size_t(~0) / sizeof(T);} -}; - -class _LIBCPP_HIDDEN __thread_struct_imp -{ - typedef vector<__assoc_sub_state*, - __hidden_allocator<__assoc_sub_state*> > _AsyncStates; - typedef vector<pair<condition_variable*, mutex*>, - __hidden_allocator<pair<condition_variable*, mutex*> > > _Notify; - - _AsyncStates async_states_; - _Notify notify_; - - __thread_struct_imp(const __thread_struct_imp&); - __thread_struct_imp& operator=(const __thread_struct_imp&); -public: - __thread_struct_imp() {} - ~__thread_struct_imp(); - - void notify_all_at_thread_exit(condition_variable* cv, mutex* m); - void __make_ready_at_thread_exit(__assoc_sub_state* __s); -}; - -__thread_struct_imp::~__thread_struct_imp() -{ - for (_Notify::iterator i = notify_.begin(), e = notify_.end(); - i != e; ++i) - { - i->second->unlock(); - i->first->notify_all(); - } - for (_AsyncStates::iterator i = async_states_.begin(), e = async_states_.end(); - i != e; ++i) - { - (*i)->__make_ready(); - (*i)->__release_shared(); - } -} - -void -__thread_struct_imp::notify_all_at_thread_exit(condition_variable* cv, mutex* m) -{ - notify_.push_back(pair<condition_variable*, mutex*>(cv, m)); -} - -void -__thread_struct_imp::__make_ready_at_thread_exit(__assoc_sub_state* __s) -{ - async_states_.push_back(__s); - __s->__add_shared(); -} - -// __thread_struct - -__thread_struct::__thread_struct() - : __p_(new __thread_struct_imp) -{ -} - -__thread_struct::~__thread_struct() -{ - delete __p_; -} - -void -__thread_struct::notify_all_at_thread_exit(condition_variable* cv, mutex* m) -{ - __p_->notify_all_at_thread_exit(cv, m); -} - -void -__thread_struct::__make_ready_at_thread_exit(__assoc_sub_state* __s) -{ - __p_->__make_ready_at_thread_exit(__s); -} - -_LIBCPP_END_NAMESPACE_STD - -#endif // !_LIBCPP_HAS_NO_THREADS diff --git a/lib/libcxx/src/typeinfo.cpp b/lib/libcxx/src/typeinfo.cpp deleted file mode 100644 index 42ff9351ed2..00000000000 --- a/lib/libcxx/src/typeinfo.cpp +++ /dev/null @@ -1,58 +0,0 @@ -//===------------------------- typeinfo.cpp -------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "typeinfo" - -#if defined(_LIBCPP_ABI_MICROSOFT) && defined(_LIBCPP_NO_VCRUNTIME) -#include <string.h> - -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 { - // TODO(compnerd) cache demangled &__data.__decorated_name[1] - return &__data.__decorated_name[1]; -} - -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; -#else - constexpr size_t fnv_offset_basis = 2166136261ull; - constexpr size_t fnv_prime = 16777619ull; -#endif - - size_t value = fnv_offset_basis; - for (const char* c = &__data.__decorated_name[1]; *c; ++c) { - value ^= static_cast<size_t>(static_cast<unsigned char>(*c)); - value *= fnv_prime; - } - -#if defined(_WIN64) - value ^= value >> 32; -#endif - - return value; -} -#endif // _LIBCPP_ABI_MICROSOFT - -// FIXME: Remove __APPLE__ default here once buildit is gone. -// FIXME: Remove the _LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY configuration. -#if (!defined(LIBCXX_BUILDING_LIBCXXABI) && !defined(LIBCXXRT) && \ - !defined(__GLIBCXX__) && !defined(__APPLE__) && \ - !(defined(_LIBCPP_ABI_MICROSOFT) && !defined(_LIBCPP_NO_VCRUNTIME))) || \ - defined(_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY) -std::type_info::~type_info() -{ -} -#endif diff --git a/lib/libcxx/src/utility.cpp b/lib/libcxx/src/utility.cpp deleted file mode 100644 index 7dccffb73e5..00000000000 --- a/lib/libcxx/src/utility.cpp +++ /dev/null @@ -1,16 +0,0 @@ -//===------------------------ utility.cpp ---------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "utility" - -_LIBCPP_BEGIN_NAMESPACE_STD - -const piecewise_construct_t piecewise_construct = {}; - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/valarray.cpp b/lib/libcxx/src/valarray.cpp deleted file mode 100644 index 2d8db52ac36..00000000000 --- a/lib/libcxx/src/valarray.cpp +++ /dev/null @@ -1,54 +0,0 @@ -//===------------------------ valarray.cpp --------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "valarray" - -_LIBCPP_BEGIN_NAMESPACE_STD - -template valarray<size_t>::valarray(size_t); -template valarray<size_t>::~valarray(); -template void valarray<size_t>::resize(size_t, size_t); - -void -gslice::__init(size_t __start) -{ - valarray<size_t> __indices(__size_.size()); - size_t __k = __size_.size() != 0; - for (size_t __i = 0; __i < __size_.size(); ++__i) - __k *= __size_[__i]; - __1d_.resize(__k); - if (__1d_.size()) - { - __k = 0; - __1d_[__k] = __start; - while (true) - { - size_t __i = __indices.size() - 1; - while (true) - { - if (++__indices[__i] < __size_[__i]) - { - ++__k; - __1d_[__k] = __1d_[__k-1] + __stride_[__i]; - for (size_t __j = __i + 1; __j != __indices.size(); ++__j) - __1d_[__k] -= __stride_[__j] * (__size_[__j] - 1); - break; - } - else - { - if (__i == 0) - return; - __indices[__i--] = 0; - } - } - } - } -} - -_LIBCPP_END_NAMESPACE_STD diff --git a/lib/libcxx/src/variant.cpp b/lib/libcxx/src/variant.cpp deleted file mode 100644 index 5bb508c3f46..00000000000 --- a/lib/libcxx/src/variant.cpp +++ /dev/null @@ -1,18 +0,0 @@ -//===------------------------ variant.cpp ---------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "variant" - -namespace std { - -const char* bad_variant_access::what() const noexcept { - return "bad_variant_access"; -} - -} // namespace std diff --git a/lib/libcxx/src/vector.cpp b/lib/libcxx/src/vector.cpp deleted file mode 100644 index 300adaed5f4..00000000000 --- a/lib/libcxx/src/vector.cpp +++ /dev/null @@ -1,16 +0,0 @@ -//===------------------------- vector.cpp ---------------------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file is dual licensed under the MIT and the University of Illinois Open -// Source Licenses. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "vector" - -_LIBCPP_BEGIN_NAMESPACE_STD - -template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __vector_base_common<true>; - -_LIBCPP_END_NAMESPACE_STD |