From b38f8f07c55e384b16678f56a80ce02d6e3adf0e Mon Sep 17 00:00:00 2001 From: Marshall Clow Date: Thu, 10 Jul 2014 15:20:28 +0000 Subject: [PATCH] Add support for BIONIC C library (Android). Patch from Dan Albert llvm-svn: 212724 --- libcxx/include/__config | 2 + libcxx/include/__locale | 15 +- libcxx/include/locale | 14 +- libcxx/include/support/android/locale_bionic.h | 192 +++++++++++++++++++++++++ libcxx/src/locale.cpp | 6 +- 5 files changed, 217 insertions(+), 12 deletions(-) create mode 100644 libcxx/include/support/android/locale_bionic.h diff --git a/libcxx/include/__config b/libcxx/include/__config index 981cc9f..687f5c1 100644 --- a/libcxx/include/__config +++ b/libcxx/include/__config @@ -317,6 +317,8 @@ typedef __char32_t char32_t; #if defined(__FreeBSD__) #define _LIBCPP_HAS_QUICK_EXIT #define _LIBCPP_HAS_C11_FEATURES +#elif defined(__ANDROID__) +#define _LIBCPP_HAS_QUICK_EXIT #elif defined(__linux__) #include #if __GLIBC_PREREQ(2, 15) diff --git a/libcxx/include/__locale b/libcxx/include/__locale index fb5b196..3daa1f1 100644 --- a/libcxx/include/__locale +++ b/libcxx/include/__locale @@ -23,9 +23,16 @@ # include #elif defined(_AIX) # include -#elif (defined(__GLIBC__) || defined(__APPLE__) || defined(__FreeBSD__) || defined(__sun__)) || defined(__EMSCRIPTEN__) || defined(__IBMCPP__) +#elif defined(__ANDROID__) +// Android gained the locale aware functions in L (API level 21) +# include +# if __ANDROID_API__ <= 20 +# include +# endif +#elif (defined(__GLIBC__) || defined(__APPLE__) || defined(__FreeBSD__) \ + || defined(__sun__) || defined(__EMSCRIPTEN__) || defined(__IBMCPP__)) # include -#endif // _WIN32 || __GLIBC__ || __APPLE__ || __FreeBSD__ || __sun__ || __EMSCRIPTEN__ || __IBMCPP__ +#endif // __GLIBC__ || __APPLE__ || __FreeBSD__ || __sun__ || __EMSCRIPTEN__ || __IBMCPP__ #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) #pragma GCC system_header @@ -341,13 +348,15 @@ public: static const mask punct = _PUNCT; static const mask xdigit = _HEX; static const mask blank = _BLANK; -#elif defined(__APPLE__) || defined(__FreeBSD__) || defined(__EMSCRIPTEN__) || defined(__NetBSD__) +#elif defined(__APPLE__) || defined(__FreeBSD__) || defined(__EMSCRIPTEN__) || defined(__NetBSD__) || defined(__ANDROID__) #ifdef __APPLE__ typedef __uint32_t mask; #elif defined(__FreeBSD__) typedef unsigned long mask; #elif defined(__EMSCRIPTEN__) || defined(__NetBSD__) typedef unsigned short mask; +#elif defined(__ANDROID__) + typedef char mask; #endif static const mask space = _CTYPE_S; static const mask print = _CTYPE_R; diff --git a/libcxx/include/locale b/libcxx/include/locale index 7191290..8e01630 100644 --- a/libcxx/include/locale +++ b/libcxx/include/locale @@ -193,9 +193,9 @@ template class messages_byname; #include #if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__) #include -#else // _LIBCPP_MSVCRT +#elif !defined(__ANDROID__) #include -#endif // !_LIBCPP_MSVCRT +#endif #ifdef __APPLE__ #include @@ -3673,14 +3673,14 @@ template typename messages<_CharT>::catalog messages<_CharT>::do_open(const basic_string& __nm, const locale&) const { -#ifdef _WIN32 +#if defined(_WIN32) || defined(__ANDROID__) return -1; -#else // _WIN32 +#else // _WIN32 || __ANDROID__ catalog __cat = (catalog)catopen(__nm.c_str(), NL_CAT_LOCALE); if (__cat != -1) __cat = static_cast((static_cast(__cat) >> 1)); return __cat; -#endif // _WIN32 +#endif // _WIN32 || __ANDROID__ } template @@ -3688,7 +3688,7 @@ typename messages<_CharT>::string_type messages<_CharT>::do_get(catalog __c, int __set, int __msgid, const string_type& __dflt) const { -#ifdef _WIN32 +#if defined(_WIN32) || defined(__ANDROID__) return __dflt; #else // _WIN32 string __ndflt; @@ -3710,7 +3710,7 @@ template void messages<_CharT>::do_close(catalog __c) const { -#if !defined(_WIN32) +#if !defined(_WIN32) && !defined(__ANDROID__) if (__c != -1) __c <<= 1; nl_catd __cat = (nl_catd)__c; diff --git a/libcxx/include/support/android/locale_bionic.h b/libcxx/include/support/android/locale_bionic.h new file mode 100644 index 0000000..354fcfe --- /dev/null +++ b/libcxx/include/support/android/locale_bionic.h @@ -0,0 +1,192 @@ +// -*- C++ -*- +//===------------------- support/android/locale_bionic.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_SUPPORT_ANDROID_LOCALE_BIONIC_H +#define _LIBCPP_SUPPORT_ANDROID_LOCALE_BIONIC_H + +#if defined(__ANDROID__) + +#ifdef __cplusplus +extern "C" { +#endif + +#include +#include + +static inline int isalnum_l(int c, locale_t) { + return isalnum(c); +} + +static inline int isalpha_l(int c, locale_t) { + return isalpha(c); +} + +static inline int isblank_l(int c, locale_t) { + return isblank(c); +} + +static inline int iscntrl_l(int c, locale_t) { + return iscntrl(c); +} + +static inline int isdigit_l(int c, locale_t) { + return isdigit(c); +} + +static inline int isgraph_l(int c, locale_t) { + return isgraph(c); +} + +static inline int islower_l(int c, locale_t) { + return islower(c); +} + +static inline int isprint_l(int c, locale_t) { + return isprint(c); +} + +static inline int ispunct_l(int c, locale_t) { + return ispunct(c); +} + +static inline int isspace_l(int c, locale_t) { + return isspace(c); +} + +static inline int isupper_l(int c, locale_t) { + return isupper(c); +} + +static inline int isxdigit_l(int c, locale_t) { + return isxdigit(c); +} + +static inline int iswalnum_l(wint_t c, locale_t) { + return iswalnum(c); +} + +static inline int iswalpha_l(wint_t c, locale_t) { + return iswalpha(c); +} + +static inline int iswblank_l(wint_t c, locale_t) { + return iswblank(c); +} + +static inline int iswcntrl_l(wint_t c, locale_t) { + return iswcntrl(c); +} + +static inline int iswdigit_l(wint_t c, locale_t) { + return iswdigit(c); +} + +static inline int iswgraph_l(wint_t c, locale_t) { + return iswgraph(c); +} + +static inline int iswlower_l(wint_t c, locale_t) { + return iswlower(c); +} + +static inline int iswprint_l(wint_t c, locale_t) { + return iswprint(c); +} + +static inline int iswpunct_l(wint_t c, locale_t) { + return iswpunct(c); +} + +static inline int iswspace_l(wint_t c, locale_t) { + return iswspace(c); +} + +static inline int iswupper_l(wint_t c, locale_t) { + return iswupper(c); +} + +static inline int iswxdigit_l(wint_t c, locale_t) { + return iswxdigit(c); +} + +static inline int toupper_l(int c, locale_t) { + return toupper(c); +} + +static inline int tolower_l(int c, locale_t) { + return tolower(c); +} + +static inline int towupper_l(int c, locale_t) { + return towupper(c); +} + +static inline int towlower_l(int c, locale_t) { + return towlower(c); +} + +static inline int strcoll_l(const char *s1, const char *s2, locale_t) { + return strcoll(s1, s2); +} + +static inline size_t strxfrm_l(char *dest, const char *src, size_t n, + locale_t) { + return strxfrm(dest, src, n); +} + +static inline size_t strftime_l(char *s, size_t max, const char *format, + const struct tm *tm, locale_t) { + return strftime(s, max, format, tm); +} + +static inline int wcscoll_l(const wchar_t *ws1, const wchar_t *ws2, locale_t) { + return wcscoll(ws1, ws2); +} + +static inline size_t wcsxfrm_l(wchar_t *dest, const wchar_t *src, size_t n, + locale_t) { + return wcsxfrm(dest, src, n); +} + +static inline long double strtold_l(const char *nptr, char **endptr, locale_t) { + return strtold(nptr, endptr); +} + +static inline long long strtoll_l(const char *nptr, char **endptr, size_t base, + locale_t) { + return strtoll(nptr, endptr, base); +} + +static inline unsigned long long strtoull_l(const char *nptr, char **endptr, + size_t base, locale_t) { + return strtoull(nptr, endptr, base); +} + +static inline long long wcstoll_l(const wchar_t *nptr, wchar_t **endptr, + size_t base, locale_t) { + return wcstoll(nptr, endptr, base); +} + +static inline unsigned long long wcstoull_l(const wchar_t *nptr, + wchar_t **endptr, size_t base, + locale_t) { + return wcstoull(nptr, endptr, base); +} + +static inline long double wcstold_l(const wchar_t *nptr, wchar_t **endptr, + locale_t) { + return wcstold(nptr, endptr); +} + +#ifdef __cplusplus +} +#endif +#endif // defined(__ANDROID__) +#endif // _LIBCPP_SUPPORT_ANDROID_LOCALE_BIONIC_H diff --git a/libcxx/src/locale.cpp b/libcxx/src/locale.cpp index 4877f2b..fc314ca 100644 --- a/libcxx/src/locale.cpp +++ b/libcxx/src/locale.cpp @@ -30,9 +30,9 @@ #include "__sso_allocator" #if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__) #include -#else // _LIBCPP_MSVCRT +#elif !defined(__ANDROID__) #include -#endif // !_LIBCPP_MSVCRT +#endif #include #include @@ -1037,6 +1037,8 @@ ctype::classic_table() _NOEXCEPT return *__ctype_b_loc(); #elif defined(_AIX) return (const unsigned int *)__lc_ctype_ptr->obj->mask; +#elif defined(__ANDROID__) + return _ctype_; #else // Platform not supported: abort so the person doing the port knows what to // fix -- 2.7.4