diff --git a/libc/config/gpu/entrypoints.txt b/libc/config/gpu/entrypoints.txt index b2644d2ebf386..9a4e7f3443beb 100644 --- a/libc/config/gpu/entrypoints.txt +++ b/libc/config/gpu/entrypoints.txt @@ -4,21 +4,35 @@ set(TARGET_LIBC_ENTRYPOINTS # ctype.h entrypoints libc.src.ctype.isalnum + libc.src.ctype.isalnum_l libc.src.ctype.isalpha + libc.src.ctype.isalpha_l libc.src.ctype.isascii libc.src.ctype.isblank + libc.src.ctype.isblank_l libc.src.ctype.iscntrl + libc.src.ctype.iscntrl_l libc.src.ctype.isdigit + libc.src.ctype.isdigit_l libc.src.ctype.isgraph + libc.src.ctype.isgraph_l libc.src.ctype.islower + libc.src.ctype.islower_l libc.src.ctype.isprint + libc.src.ctype.isprint_l libc.src.ctype.ispunct + libc.src.ctype.ispunct_l libc.src.ctype.isspace + libc.src.ctype.isspace_l libc.src.ctype.isupper + libc.src.ctype.isupper_l libc.src.ctype.isxdigit + libc.src.ctype.isxdigit_l libc.src.ctype.toascii libc.src.ctype.tolower + libc.src.ctype.tolower_l libc.src.ctype.toupper + libc.src.ctype.toupper_l # string.h entrypoints libc.src.string.bcmp @@ -231,6 +245,15 @@ set(TARGET_LIBC_ENTRYPOINTS # wchar.h entrypoints libc.src.wchar.wctob + # locale.h entrypoints + libc.src.locale.localeconv + libc.src.locale.duplocale + libc.src.locale.freelocale + libc.src.locale.localeconv + libc.src.locale.newlocale + libc.src.locale.setlocale + libc.src.locale.uselocale + # gpu/rpc.h entrypoints libc.src.gpu.rpc_host_call ) diff --git a/libc/config/gpu/headers.txt b/libc/config/gpu/headers.txt index 99280b7563a80..fc952c40f4daa 100644 --- a/libc/config/gpu/headers.txt +++ b/libc/config/gpu/headers.txt @@ -16,6 +16,7 @@ set(TARGET_PUBLIC_HEADERS libc.include.wchar libc.include.uchar libc.include.features + libc.include.locale # Header for RPC extensions libc.include.gpu_rpc diff --git a/libc/config/linux/x86_64/entrypoints.txt b/libc/config/linux/x86_64/entrypoints.txt index 65c5757efe627..bac1e3cfa85da 100644 --- a/libc/config/linux/x86_64/entrypoints.txt +++ b/libc/config/linux/x86_64/entrypoints.txt @@ -782,6 +782,22 @@ endif() if(LLVM_LIBC_FULL_BUILD) list(APPEND TARGET_LIBC_ENTRYPOINTS + # ctype.h entrypoints + libc.src.ctype.isalnum_l + libc.src.ctype.isalpha_l + libc.src.ctype.isblank_l + libc.src.ctype.iscntrl_l + libc.src.ctype.isdigit_l + libc.src.ctype.isgraph_l + libc.src.ctype.islower_l + libc.src.ctype.isprint_l + libc.src.ctype.ispunct_l + libc.src.ctype.isspace_l + libc.src.ctype.isupper_l + libc.src.ctype.isxdigit_l + libc.src.ctype.tolower_l + libc.src.ctype.toupper_l + # assert.h entrypoints libc.src.assert.__assert_fail @@ -982,6 +998,15 @@ if(LLVM_LIBC_FULL_BUILD) libc.src.time.nanosleep libc.src.time.time + # locale.h entrypoints + libc.src.locale.localeconv + libc.src.locale.duplocale + libc.src.locale.freelocale + libc.src.locale.localeconv + libc.src.locale.newlocale + libc.src.locale.setlocale + libc.src.locale.uselocale + # unistd.h entrypoints libc.src.unistd.__llvm_libc_syscall libc.src.unistd._exit diff --git a/libc/config/linux/x86_64/headers.txt b/libc/config/linux/x86_64/headers.txt index 77e454e64395d..881e149d9c40d 100644 --- a/libc/config/linux/x86_64/headers.txt +++ b/libc/config/linux/x86_64/headers.txt @@ -33,6 +33,7 @@ set(TARGET_PUBLIC_HEADERS libc.include.unistd libc.include.wchar libc.include.uchar + libc.include.locale libc.include.arpa_inet diff --git a/libc/hdr/types/CMakeLists.txt b/libc/hdr/types/CMakeLists.txt index 4fc28fd82e68d..f41576c07d99b 100644 --- a/libc/hdr/types/CMakeLists.txt +++ b/libc/hdr/types/CMakeLists.txt @@ -162,3 +162,12 @@ add_proxy_header_library( libc.include.llvm-libc-types.cookie_io_functions_t libc.include.stdio ) + +add_proxy_header_library( + locale_t + HDRS + locale_t.h + FULL_BUILD_DEPENDS + libc.include.llvm-libc-types.locale_t + libc.include.locale +) diff --git a/libc/hdr/types/locale_t.h b/libc/hdr/types/locale_t.h new file mode 100644 index 0000000000000..485258b461696 --- /dev/null +++ b/libc/hdr/types/locale_t.h @@ -0,0 +1,22 @@ +//===-- Definition of macros from locale_t.h ------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_HDR_LOCALE_T_H +#define LLVM_LIBC_HDR_LOCALE_T_H + +#ifdef LIBC_FULL_BUILD + +#include "include/llvm-libc-types/locale_t.h" + +#else // overlay mode + +#error "type not available in overlay mode" + +#endif // LLVM_LIBC_FULL_BUILD + +#endif // LLVM_LIBC_HDR_LOCALE_T_H diff --git a/libc/include/CMakeLists.txt b/libc/include/CMakeLists.txt index 2b6eb61782a63..8c0b2a2b1c574 100644 --- a/libc/include/CMakeLists.txt +++ b/libc/include/CMakeLists.txt @@ -45,6 +45,7 @@ add_header_macro( ctype.h DEPENDS .llvm_libc_common_h + .llvm-libc-types.locale_t ) add_header_macro( @@ -717,6 +718,18 @@ add_header_macro( .llvm-libc-types.wchar_t ) +add_header_macro( + locale + ../libc/newhdrgen/yaml/locale.yaml + locale.h.def + locale.h + DEPENDS + .llvm_libc_common_h + .llvm-libc-macros.locale_macros + .llvm-libc-types.locale_t + .llvm-libc-types.struct_lconv +) + if(LIBC_TARGET_OS_IS_GPU) file(MAKE_DIRECTORY ${LIBC_INCLUDE_DIR}/gpu) diff --git a/libc/include/llvm-libc-macros/CMakeLists.txt b/libc/include/llvm-libc-macros/CMakeLists.txt index 60a8725f9ef63..7b980232ba042 100644 --- a/libc/include/llvm-libc-macros/CMakeLists.txt +++ b/libc/include/llvm-libc-macros/CMakeLists.txt @@ -295,3 +295,9 @@ add_macro_header( HDR elf-macros.h ) + +add_macro_header( + locale_macros + HDR + locale-macros.h +) diff --git a/libc/include/llvm-libc-macros/locale-macros.h b/libc/include/llvm-libc-macros/locale-macros.h new file mode 100644 index 0000000000000..892f8b69f3a77 --- /dev/null +++ b/libc/include/llvm-libc-macros/locale-macros.h @@ -0,0 +1,32 @@ +//===-- Definition of macros from locale.h --------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_MACROS_LOCALE_MACROS_H +#define LLVM_LIBC_MACROS_LOCALE_MACROS_H + +#include "../llvm-libc-types/locale_t.h" + +#define LC_CTYPE 0 +#define LC_NUMERIC 1 +#define LC_TIME 2 +#define LC_COLLATE 3 +#define LC_MONETARY 4 +#define LC_MESSAGES 5 +#define LC_ALL 6 + +#define LC_GLOBAL_LOCALE ((locale_t)(-1)) + +#define LC_CTYPE_MASK (1 << LC_CTYPE) +#define LC_NUMERIC_MASK (1 << LC_NUMERIC) +#define LC_TIME_MASK (1 << LC_TIME) +#define LC_COLLATE_MASK (1 << LC_COLLATE) +#define LC_MONETARY_MASK (1 << LC_MONETARY) +#define LC_MESSAGES_MASK (1 << LC_MESSAGES) +#define LC_ALL_MASK 0x7fffffff + +#endif // LLVM_LIBC_MACROS_LOCALE_MACROS_H diff --git a/libc/include/llvm-libc-types/CMakeLists.txt b/libc/include/llvm-libc-types/CMakeLists.txt index 0fa86e0152f9b..583b84ccaae67 100644 --- a/libc/include/llvm-libc-types/CMakeLists.txt +++ b/libc/include/llvm-libc-types/CMakeLists.txt @@ -142,3 +142,5 @@ DEPENDS .fsblkcnt_t .fsfilcnt_t ) +add_header(locale_t HDR locale_t.h) +add_header(struct_lconv HDR struct_lconv.h) diff --git a/libc/include/llvm-libc-types/locale_t.h b/libc/include/llvm-libc-types/locale_t.h new file mode 100644 index 0000000000000..6d783001acf9f --- /dev/null +++ b/libc/include/llvm-libc-types/locale_t.h @@ -0,0 +1,22 @@ +//===-- Definition of type locale_t ---------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_TYPES_LOCALE_T_H +#define LLVM_LIBC_TYPES_LOCALE_T_H + +#define NUM_LOCALE_CATEGORIES 6 + +struct __locale_data; + +struct __locale_t { + struct __locale_data *data[NUM_LOCALE_CATEGORIES]; +}; + +typedef struct __locale_t *locale_t; + +#endif // LLVM_LIBC_TYPES_LOCALE_T_H diff --git a/libc/include/llvm-libc-types/struct_lconv.h b/libc/include/llvm-libc-types/struct_lconv.h new file mode 100644 index 0000000000000..9d69f055484da --- /dev/null +++ b/libc/include/llvm-libc-types/struct_lconv.h @@ -0,0 +1,39 @@ +//===-- Definition of type lconv ------------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_TYPES_LCONV_H +#define LLVM_LIBC_TYPES_LCONV_H + +struct lconv { + char *decimal_point; + char *thousands_sep; + char *grouping; + char *mon_decimal_point; + char *mon_thousands_sep; + char *mon_grouping; + char *positive_sign; + char *negative_sign; + char *currency_symbol; + char frac_digits; + char p_cs_precedes; + char n_cs_precedes; + char p_sep_by_space; + char n_sep_by_space; + char p_sign_posn; + char n_sign_posn; + char *int_curr_symbol; + char int_frac_digits; + char int_p_cs_precedes; + char int_n_cs_precedes; + char int_p_sep_by_space; + char int_n_sep_by_space; + char int_p_sign_posn; + char int_n_sign_posn; +}; + +#endif // LLVM_LIBC_TYPES_LCONV_H diff --git a/libc/include/locale.h.def b/libc/include/locale.h.def new file mode 100644 index 0000000000000..516c6e6275e68 --- /dev/null +++ b/libc/include/locale.h.def @@ -0,0 +1,20 @@ +//===-- C standard library header locale.h --------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_LOCALE_H +#define LLVM_LIBC_LOCALE_H + +#include "__llvm-libc-common.h" + +#include "llvm-libc-macros/locale-macros.h" +#include "llvm-libc-types/locale_t.h" +#include "llvm-libc-types/struct_lconv.h" + +%%public_api() + +#endif // LLVM_LIBC_LOCALE_H diff --git a/libc/newhdrgen/yaml/ctype.yaml b/libc/newhdrgen/yaml/ctype.yaml index f3108a34d4337..b4823c3e53234 100644 --- a/libc/newhdrgen/yaml/ctype.yaml +++ b/libc/newhdrgen/yaml/ctype.yaml @@ -1,6 +1,7 @@ header: ctype.h macros: [] -types: [] +types: + - type_name: locale_t enums: [] objects: [] functions: @@ -100,4 +101,101 @@ functions: return_type: int arguments: - type: int - functions: null + - name: isalnum_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: isalpha_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: isblank_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: iscntrl_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: isdigit_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: isgraph_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: islower_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: isprint_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: ispunct_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: isspace_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: isupper_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: isxdigit_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: tolower_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t + - name: toupper_l + standards: + - stdc + return_type: int + arguments: + - type: int + - type: locale_t diff --git a/libc/newhdrgen/yaml/locale.yaml b/libc/newhdrgen/yaml/locale.yaml new file mode 100644 index 0000000000000..7da7966ea730f --- /dev/null +++ b/libc/newhdrgen/yaml/locale.yaml @@ -0,0 +1,41 @@ +header: locale.h +functions: + - name: localeconv + standards: + - stdc + return_type: struct lconv * + arguments: + - type: void + - name: duplocale + standards: + - stdc + return_type: locale_t + arguments: + - type: locale_t + - name: freelocale + standards: + - stdc + return_type: void + arguments: + - type: locale_t + - name: newlocale + standards: + - stdc + return_type: locale_t + arguments: + - type: int + - type: const char * + - type: locale_t + - name: setlocale + standards: + - stdc + return_type: char * + arguments: + - type: int + - type: const char * + - name: uselocale + standards: + - stdc + return_type: locale_t + arguments: + - type: locale_t diff --git a/libc/spec/stdc.td b/libc/spec/stdc.td index e06a4f9b268e6..6fd3e6d861848 100644 --- a/libc/spec/stdc.td +++ b/libc/spec/stdc.td @@ -4,6 +4,7 @@ def StdC : StandardSpec<"stdc"> { PtrType StructTmPtr = PtrType; PtrType TimeTTypePtr = PtrType; NamedType ClockT = NamedType<"clock_t">; + NamedType LocaleT = NamedType<"locale_t">; NamedType DivTType = NamedType<"div_t">; NamedType LDivTType = NamedType<"ldiv_t">; @@ -34,7 +35,9 @@ def StdC : StandardSpec<"stdc"> { HeaderSpec CType = HeaderSpec< "ctype.h", [], // Macros - [], // Types + [ + LocaleT + ], // Types [], // Enumerations [ FunctionSpec< @@ -107,6 +110,76 @@ def StdC : StandardSpec<"stdc"> { RetValSpec, [ArgSpec] >, + FunctionSpec< + "isalnum_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "isalpha_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "isblank_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "iscntrl_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "isdigit_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "isgraph_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "islower_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "isprint_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "ispunct_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "isspace_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "isupper_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "isxdigit_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "tolower_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, + FunctionSpec< + "toupper_l", + RetValSpec, + [ArgSpec, ArgSpec] + >, ] >; @@ -1588,6 +1661,61 @@ def StdC : StandardSpec<"stdc"> { ] >; + + NamedType StructLconv : NamedType<"struct lconv">; + PtrType StructLconvPtr : PtrType; + + HeaderSpec Locale = HeaderSpec< + "locale.h", + [], // Macros + [LocaleT, StructLconv], // Types + [], // Enumerations + [ + FunctionSpec< + "duplocale", + RetValSpec, + [ + ArgSpec + ] + >, + FunctionSpec< + "freelocale", + RetValSpec, + [ + ArgSpec + ] + >, + FunctionSpec< + "localeconv", + RetValSpec, + [] + >, + FunctionSpec< + "newlocale", + RetValSpec, + [ + ArgSpec, + ArgSpec, + ArgSpec + ] + >, + FunctionSpec< + "setlocale", + RetValSpec, + [ + ArgSpec, + ArgSpec + ] + >, + FunctionSpec< + "uselocale", + RetValSpec, + [ + ArgSpec + ] + > + ] // Functions + >; let Headers = [ Assert, @@ -1610,5 +1738,6 @@ def StdC : StandardSpec<"stdc"> { Time, UChar, WChar, + Locale, ]; } diff --git a/libc/src/CMakeLists.txt b/libc/src/CMakeLists.txt index 9597e2380172b..d554c12fb1ec8 100644 --- a/libc/src/CMakeLists.txt +++ b/libc/src/CMakeLists.txt @@ -40,3 +40,4 @@ add_subdirectory(signal) add_subdirectory(spawn) add_subdirectory(threads) add_subdirectory(time) +add_subdirectory(locale) diff --git a/libc/src/ctype/CMakeLists.txt b/libc/src/ctype/CMakeLists.txt index ae4eec9615dc1..8830c1bccf9ea 100644 --- a/libc/src/ctype/CMakeLists.txt +++ b/libc/src/ctype/CMakeLists.txt @@ -146,3 +146,159 @@ add_entrypoint_object( DEPENDS libc.src.__support.ctype_utils ) + +# Do not build the locale versions in overlay mode. +if(NOT LLVM_LIBC_FULL_BUILD) + return() +endif() + +add_entrypoint_object( + isalnum_l + SRCS + isalnum_l.cpp + HDRS + isalnum_l.h + DEPENDS + libc.include.ctype + libc.src.__support.ctype_utils + libc.hdr.types.locale_t +) + +add_entrypoint_object( + isalpha_l + SRCS + isalpha_l.cpp + HDRS + isalpha_l.h + DEPENDS + libc.src.__support.ctype_utils + libc.hdr.types.locale_t +) + +add_entrypoint_object( + isblank_l + SRCS + isblank_l.cpp + HDRS + isblank_l.h + DEPENDS + libc.hdr.types.locale_t +) + +add_entrypoint_object( + iscntrl_l + SRCS + iscntrl_l.cpp + HDRS + iscntrl_l.h + DEPENDS + libc.hdr.types.locale_t +) + +add_entrypoint_object( + isdigit_l + SRCS + isdigit_l.cpp + HDRS + isdigit_l.h + DEPENDS + libc.src.__support.ctype_utils + libc.hdr.types.locale_t +) + +add_entrypoint_object( + isgraph_l + SRCS + isgraph_l.cpp + HDRS + isgraph_l.h + DEPENDS + libc.src.__support.ctype_utils + libc.hdr.types.locale_t +) + +add_entrypoint_object( + islower_l + SRCS + islower_l.cpp + HDRS + islower_l.h + DEPENDS + libc.src.__support.ctype_utils + libc.hdr.types.locale_t +) + +add_entrypoint_object( + isprint_l + SRCS + isprint_l.cpp + HDRS + isprint_l.h + DEPENDS + libc.hdr.types.locale_t +) + +add_entrypoint_object( + ispunct_l + SRCS + ispunct_l.cpp + HDRS + ispunct_l.h + DEPENDS + libc.src.__support.ctype_utils + libc.hdr.types.locale_t +) + +add_entrypoint_object( + isspace_l + SRCS + isspace_l.cpp + HDRS + isspace_l.h + DEPENDS + libc.hdr.types.locale_t +) + +add_entrypoint_object( + isupper_l + SRCS + isupper_l.cpp + HDRS + isupper_l.h + DEPENDS + libc.src.__support.ctype_utils + libc.hdr.types.locale_t +) + +add_entrypoint_object( + isxdigit_l + SRCS + isxdigit_l.cpp + HDRS + isxdigit_l.h + DEPENDS + libc.src.__support.ctype_utils + libc.hdr.types.locale_t +) + +add_entrypoint_object( + tolower_l + SRCS + tolower_l.cpp + HDRS + tolower_l.h + DEPENDS + libc.src.__support.ctype_utils + libc.hdr.types.locale_t +) + +add_entrypoint_object( + toupper_l + SRCS + toupper_l.cpp + HDRS + toupper_l.h + DEPENDS + libc.src.__support.ctype_utils + libc.hdr.types.locale_t +) diff --git a/libc/src/ctype/isalnum.cpp b/libc/src/ctype/isalnum.cpp index 382553c23a6bf..54a3e35748879 100644 --- a/libc/src/ctype/isalnum.cpp +++ b/libc/src/ctype/isalnum.cpp @@ -14,8 +14,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, isalnum, (int c)) { return static_cast(internal::isalnum(static_cast(c))); } diff --git a/libc/src/ctype/isalnum_l.cpp b/libc/src/ctype/isalnum_l.cpp new file mode 100644 index 0000000000000..671d9b75c4c33 --- /dev/null +++ b/libc/src/ctype/isalnum_l.cpp @@ -0,0 +1,21 @@ +//===-- Implementation of isalnum -----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/isalnum_l.h" +#include "src/__support/ctype_utils.h" + +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, isalnum_l, (int c, locale_t)) { + return static_cast(internal::isalnum(static_cast(c))); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/isalnum_l.h b/libc/src/ctype/isalnum_l.h new file mode 100644 index 0000000000000..5bc892e6c8747 --- /dev/null +++ b/libc/src/ctype/isalnum_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for isalnum_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_ISALNUM_H +#define LLVM_LIBC_SRC_CTYPE_ISALNUM_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int isalnum_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_ISALNUM_H diff --git a/libc/src/ctype/isalpha.cpp b/libc/src/ctype/isalpha.cpp index 1a63406780b6e..78b26f6a486ea 100644 --- a/libc/src/ctype/isalpha.cpp +++ b/libc/src/ctype/isalpha.cpp @@ -14,8 +14,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, isalpha, (int c)) { return static_cast(internal::isalpha(static_cast(c))); } diff --git a/libc/src/ctype/isalpha_l.cpp b/libc/src/ctype/isalpha_l.cpp new file mode 100644 index 0000000000000..0619d979bedf2 --- /dev/null +++ b/libc/src/ctype/isalpha_l.cpp @@ -0,0 +1,21 @@ +//===-- Implementation of isalpha -----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/isalpha_l.h" + +#include "src/__support/common.h" +#include "src/__support/ctype_utils.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, isalpha_l, (int c, locale_t)) { + return static_cast(internal::isalpha(static_cast(c))); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/isalpha_l.h b/libc/src/ctype/isalpha_l.h new file mode 100644 index 0000000000000..3591f1175cb9a --- /dev/null +++ b/libc/src/ctype/isalpha_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for isalpha_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_ISALPHA_H +#define LLVM_LIBC_SRC_CTYPE_ISALPHA_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int isalpha_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_ISALPHA_H diff --git a/libc/src/ctype/isblank.cpp b/libc/src/ctype/isblank.cpp index a4f33d265bd2d..e0a20829f86ce 100644 --- a/libc/src/ctype/isblank.cpp +++ b/libc/src/ctype/isblank.cpp @@ -13,8 +13,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, isblank, (int c)) { return static_cast(c == ' ' || c == '\t'); } diff --git a/libc/src/ctype/isblank_l.cpp b/libc/src/ctype/isblank_l.cpp new file mode 100644 index 0000000000000..4f6b0bfac2972 --- /dev/null +++ b/libc/src/ctype/isblank_l.cpp @@ -0,0 +1,20 @@ +//===-- Implementation of isblank -----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/isblank_l.h" + +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, isblank_l, (int c, locale_t)) { + return static_cast(c == ' ' || c == '\t'); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/isblank_l.h b/libc/src/ctype/isblank_l.h new file mode 100644 index 0000000000000..61ede30ae7677 --- /dev/null +++ b/libc/src/ctype/isblank_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for isblank_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_ISBLANK_H +#define LLVM_LIBC_SRC_CTYPE_ISBLANK_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int isblank_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_ISBLANK_H diff --git a/libc/src/ctype/iscntrl.cpp b/libc/src/ctype/iscntrl.cpp index fb582fd6ef082..2218adfcc33f3 100644 --- a/libc/src/ctype/iscntrl.cpp +++ b/libc/src/ctype/iscntrl.cpp @@ -13,8 +13,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, iscntrl, (int c)) { const unsigned ch = static_cast(c); return static_cast(ch < 0x20 || ch == 0x7f); diff --git a/libc/src/ctype/iscntrl_l.cpp b/libc/src/ctype/iscntrl_l.cpp new file mode 100644 index 0000000000000..83aa480299fad --- /dev/null +++ b/libc/src/ctype/iscntrl_l.cpp @@ -0,0 +1,21 @@ +//===-- Implementation of iscntrl -----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/iscntrl_l.h" + +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, iscntrl_l, (int c, locale_t)) { + const unsigned ch = static_cast(c); + return static_cast(ch < 0x20 || ch == 0x7f); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/iscntrl_l.h b/libc/src/ctype/iscntrl_l.h new file mode 100644 index 0000000000000..7dee44fcd0beb --- /dev/null +++ b/libc/src/ctype/iscntrl_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for iscntrl_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_ISCNTRL_H +#define LLVM_LIBC_SRC_CTYPE_ISCNTRL_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int iscntrl_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_ISCNTRL_H diff --git a/libc/src/ctype/isdigit.cpp b/libc/src/ctype/isdigit.cpp index 43c5f1940c7f0..1f711943861f8 100644 --- a/libc/src/ctype/isdigit.cpp +++ b/libc/src/ctype/isdigit.cpp @@ -13,8 +13,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, isdigit, (int c)) { return static_cast(internal::isdigit(static_cast(c))); } diff --git a/libc/src/ctype/isdigit_l.cpp b/libc/src/ctype/isdigit_l.cpp new file mode 100644 index 0000000000000..ca981362bfe83 --- /dev/null +++ b/libc/src/ctype/isdigit_l.cpp @@ -0,0 +1,20 @@ +//===-- Implementation of isdigit -----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/isdigit_l.h" +#include "src/__support/common.h" +#include "src/__support/ctype_utils.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, isdigit_l, (int c, locale_t)) { + return static_cast(internal::isdigit(static_cast(c))); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/isdigit_l.h b/libc/src/ctype/isdigit_l.h new file mode 100644 index 0000000000000..abeec3464941a --- /dev/null +++ b/libc/src/ctype/isdigit_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for isdigit_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_ISDIGIT_H +#define LLVM_LIBC_SRC_CTYPE_ISDIGIT_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int isdigit_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_ISDIGIT_H diff --git a/libc/src/ctype/isgraph.cpp b/libc/src/ctype/isgraph.cpp index a5b6e501b5813..74bb2e75d138e 100644 --- a/libc/src/ctype/isgraph.cpp +++ b/libc/src/ctype/isgraph.cpp @@ -14,8 +14,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, isgraph, (int c)) { return static_cast(internal::isgraph(static_cast(c))); } diff --git a/libc/src/ctype/isgraph_l.cpp b/libc/src/ctype/isgraph_l.cpp new file mode 100644 index 0000000000000..cbef6df148aed --- /dev/null +++ b/libc/src/ctype/isgraph_l.cpp @@ -0,0 +1,21 @@ +//===-- Implementation of isgraph -----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/isgraph_l.h" + +#include "src/__support/common.h" +#include "src/__support/ctype_utils.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, isgraph_l, (int c, locale_t)) { + return static_cast(internal::isgraph(static_cast(c))); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/isgraph_l.h b/libc/src/ctype/isgraph_l.h new file mode 100644 index 0000000000000..d96a460865509 --- /dev/null +++ b/libc/src/ctype/isgraph_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for isgraph_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_ISGRAPH_H +#define LLVM_LIBC_SRC_CTYPE_ISGRAPH_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int isgraph_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_ISGRAPH_H diff --git a/libc/src/ctype/islower.cpp b/libc/src/ctype/islower.cpp index 61ccbcc1db413..831aad32d3a22 100644 --- a/libc/src/ctype/islower.cpp +++ b/libc/src/ctype/islower.cpp @@ -14,8 +14,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, islower, (int c)) { return static_cast(internal::islower(static_cast(c))); } diff --git a/libc/src/ctype/islower_l.cpp b/libc/src/ctype/islower_l.cpp new file mode 100644 index 0000000000000..b9be6acc81c99 --- /dev/null +++ b/libc/src/ctype/islower_l.cpp @@ -0,0 +1,21 @@ +//===-- Implementation of islower -----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/islower_l.h" +#include "src/__support/ctype_utils.h" + +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, islower_l, (int c, locale_t)) { + return static_cast(internal::islower(static_cast(c))); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/islower_l.h b/libc/src/ctype/islower_l.h new file mode 100644 index 0000000000000..7d3e2f139602b --- /dev/null +++ b/libc/src/ctype/islower_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for islower_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_ISLOWER_H +#define LLVM_LIBC_SRC_CTYPE_ISLOWER_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int islower_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_ISLOWER_H diff --git a/libc/src/ctype/isprint.cpp b/libc/src/ctype/isprint.cpp index 42ab9cc8d238a..349aefe1c17bb 100644 --- a/libc/src/ctype/isprint.cpp +++ b/libc/src/ctype/isprint.cpp @@ -13,8 +13,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, isprint, (int c)) { const unsigned ch = static_cast(c); return static_cast((ch - ' ') < 95); diff --git a/libc/src/ctype/isprint_l.cpp b/libc/src/ctype/isprint_l.cpp new file mode 100644 index 0000000000000..8f51f7f0e3e94 --- /dev/null +++ b/libc/src/ctype/isprint_l.cpp @@ -0,0 +1,21 @@ +//===-- Implementation of isprint -----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/isprint_l.h" + +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, isprint_l, (int c, locale_t)) { + const unsigned ch = static_cast(c); + return static_cast((ch - ' ') < 95); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/isprint_l.h b/libc/src/ctype/isprint_l.h new file mode 100644 index 0000000000000..bd2ea9354c36a --- /dev/null +++ b/libc/src/ctype/isprint_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for isprint_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_ISPRINT_H +#define LLVM_LIBC_SRC_CTYPE_ISPRINT_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int isprint_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_ISPRINT_H diff --git a/libc/src/ctype/ispunct.cpp b/libc/src/ctype/ispunct.cpp index c1906e3acdd80..0635294220b9c 100644 --- a/libc/src/ctype/ispunct.cpp +++ b/libc/src/ctype/ispunct.cpp @@ -14,8 +14,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, ispunct, (int c)) { const unsigned ch = static_cast(c); return static_cast(!internal::isalnum(ch) && internal::isgraph(ch)); diff --git a/libc/src/ctype/ispunct_l.cpp b/libc/src/ctype/ispunct_l.cpp new file mode 100644 index 0000000000000..e825fbe2001b0 --- /dev/null +++ b/libc/src/ctype/ispunct_l.cpp @@ -0,0 +1,22 @@ +//===-- Implementation of ispunct -----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/ispunct_l.h" + +#include "src/__support/common.h" +#include "src/__support/ctype_utils.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, ispunct_l, (int c, locale_t)) { + const unsigned ch = static_cast(c); + return static_cast(!internal::isalnum(ch) && internal::isgraph(ch)); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/ispunct_l.h b/libc/src/ctype/ispunct_l.h new file mode 100644 index 0000000000000..862daf4836f78 --- /dev/null +++ b/libc/src/ctype/ispunct_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for ispunct_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_ISPUNCT_H +#define LLVM_LIBC_SRC_CTYPE_ISPUNCT_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int ispunct_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_ISPUNCT_H diff --git a/libc/src/ctype/isspace.cpp b/libc/src/ctype/isspace.cpp index f890849378784..005bf460fc103 100644 --- a/libc/src/ctype/isspace.cpp +++ b/libc/src/ctype/isspace.cpp @@ -14,8 +14,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, isspace, (int c)) { return static_cast(internal::isspace(static_cast(c))); } diff --git a/libc/src/ctype/isspace_l.cpp b/libc/src/ctype/isspace_l.cpp new file mode 100644 index 0000000000000..5c46dd6805126 --- /dev/null +++ b/libc/src/ctype/isspace_l.cpp @@ -0,0 +1,21 @@ +//===-- Implementation of isspace -----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/isspace_l.h" +#include "src/__support/ctype_utils.h" + +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, isspace_l, (int c, locale_t)) { + return static_cast(internal::isspace(static_cast(c))); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/isspace_l.h b/libc/src/ctype/isspace_l.h new file mode 100644 index 0000000000000..61bbf127956da --- /dev/null +++ b/libc/src/ctype/isspace_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for isspace_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_ISSPACE_H +#define LLVM_LIBC_SRC_CTYPE_ISSPACE_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int isspace_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_ISSPACE_H diff --git a/libc/src/ctype/isupper.cpp b/libc/src/ctype/isupper.cpp index 8f929ea1a009e..965fa336b28b4 100644 --- a/libc/src/ctype/isupper.cpp +++ b/libc/src/ctype/isupper.cpp @@ -14,8 +14,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, isupper, (int c)) { return static_cast(internal::isupper(static_cast(c))); } diff --git a/libc/src/ctype/isupper_l.cpp b/libc/src/ctype/isupper_l.cpp new file mode 100644 index 0000000000000..358990261d603 --- /dev/null +++ b/libc/src/ctype/isupper_l.cpp @@ -0,0 +1,21 @@ +//===-- Implementation of isupper -----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/isupper_l.h" +#include "src/__support/ctype_utils.h" + +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, isupper_l, (int c, locale_t)) { + return static_cast(internal::isupper(static_cast(c))); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/isupper_l.h b/libc/src/ctype/isupper_l.h new file mode 100644 index 0000000000000..9bee7ef8c09f5 --- /dev/null +++ b/libc/src/ctype/isupper_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for isupper_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_ISUPPER_H +#define LLVM_LIBC_SRC_CTYPE_ISUPPER_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int isupper_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_ISUPPER_H diff --git a/libc/src/ctype/isxdigit.cpp b/libc/src/ctype/isxdigit.cpp index 391c5c53cee1e..6b730c354db08 100644 --- a/libc/src/ctype/isxdigit.cpp +++ b/libc/src/ctype/isxdigit.cpp @@ -14,8 +14,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, isxdigit, (int c)) { const unsigned ch = static_cast(c); return static_cast(internal::isdigit(ch) || (ch | 32) - 'a' < 6); diff --git a/libc/src/ctype/isxdigit_l.cpp b/libc/src/ctype/isxdigit_l.cpp new file mode 100644 index 0000000000000..8a5c7d4d28ab1 --- /dev/null +++ b/libc/src/ctype/isxdigit_l.cpp @@ -0,0 +1,22 @@ +//===-- Implementation of isxdigit ----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/isxdigit_l.h" +#include "src/__support/ctype_utils.h" + +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, isxdigit_l, (int c, locale_t)) { + const unsigned ch = static_cast(c); + return static_cast(internal::isdigit(ch) || (ch | 32) - 'a' < 6); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/isxdigit_l.h b/libc/src/ctype/isxdigit_l.h new file mode 100644 index 0000000000000..ee847eda4eae9 --- /dev/null +++ b/libc/src/ctype/isxdigit_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for isxdigit_l ----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_ISXDIGIT_H +#define LLVM_LIBC_SRC_CTYPE_ISXDIGIT_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int isxdigit_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_ISXDIGIT_H diff --git a/libc/src/ctype/tolower.cpp b/libc/src/ctype/tolower.cpp index e230428eef2b1..3ecad7bc5d5d5 100644 --- a/libc/src/ctype/tolower.cpp +++ b/libc/src/ctype/tolower.cpp @@ -14,8 +14,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, tolower, (int c)) { return internal::tolower(c); } } // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/tolower_l.cpp b/libc/src/ctype/tolower_l.cpp new file mode 100644 index 0000000000000..7ccf31617e592 --- /dev/null +++ b/libc/src/ctype/tolower_l.cpp @@ -0,0 +1,21 @@ +//===-- Implementation of tolower -----------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/tolower_l.h" +#include "src/__support/ctype_utils.h" + +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, tolower_l, (int c, locale_t)) { + return internal::tolower(c); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/tolower_l.h b/libc/src/ctype/tolower_l.h new file mode 100644 index 0000000000000..6099b8c813469 --- /dev/null +++ b/libc/src/ctype/tolower_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for tolower_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_TOLOWER_H +#define LLVM_LIBC_SRC_CTYPE_TOLOWER_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int tolower_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_TOLOWER_H diff --git a/libc/src/ctype/toupper.cpp b/libc/src/ctype/toupper.cpp index 97c1ac2c02b8c..b5a23fc7f588b 100644 --- a/libc/src/ctype/toupper.cpp +++ b/libc/src/ctype/toupper.cpp @@ -14,8 +14,6 @@ namespace LIBC_NAMESPACE_DECL { -// TODO: Currently restricted to default locale. -// These should be extended using locale information. LLVM_LIBC_FUNCTION(int, toupper, (int c)) { if (internal::islower(c)) return c - ('a' - 'A'); diff --git a/libc/src/ctype/toupper_l.cpp b/libc/src/ctype/toupper_l.cpp new file mode 100644 index 0000000000000..f536ff3623616 --- /dev/null +++ b/libc/src/ctype/toupper_l.cpp @@ -0,0 +1,23 @@ +//===-- Implementation of toupper_l ---------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/ctype/toupper_l.h" +#include "src/__support/ctype_utils.h" + +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, toupper_l, (int c, locale_t)) { + if (internal::islower(c)) + return c - ('a' - 'A'); + return c; +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/ctype/toupper_l.h b/libc/src/ctype/toupper_l.h new file mode 100644 index 0000000000000..8877c35d492bd --- /dev/null +++ b/libc/src/ctype/toupper_l.h @@ -0,0 +1,21 @@ +//===-- Implementation header for toupper_l -----------------------*-C++-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_CTYPE_TOUPPER_H +#define LLVM_LIBC_SRC_CTYPE_TOUPPER_H + +#include "hdr/types/locale_t.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +int toupper_l(int c, locale_t locale); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_CTYPE_TOUPPER_H diff --git a/libc/src/locale/CMakeLists.txt b/libc/src/locale/CMakeLists.txt new file mode 100644 index 0000000000000..6aaeb2ac31488 --- /dev/null +++ b/libc/src/locale/CMakeLists.txt @@ -0,0 +1,76 @@ +add_object_library( + locale + SRCS + locale.cpp + HDRS + locale.h + DEPENDS + libc.include.locale +) + +add_entrypoint_object( + localeconv + SRCS + localeconv.cpp + HDRS + localeconv.h + DEPENDS + libc.include.locale + CXX_STANDARD + 20 # For designated initializers +) + +add_entrypoint_object( + newlocale + SRCS + newlocale.cpp + HDRS + newlocale.h + DEPENDS + libc.include.locale + .locale +) + +add_entrypoint_object( + duplocale + SRCS + duplocale.cpp + HDRS + duplocale.h + DEPENDS + libc.include.locale + .locale +) + +add_entrypoint_object( + setlocale + SRCS + setlocale.cpp + HDRS + setlocale.h + DEPENDS + libc.include.locale + .locale +) + +add_entrypoint_object( + uselocale + SRCS + uselocale.cpp + HDRS + uselocale.h + DEPENDS + libc.include.locale + .locale +) + +add_entrypoint_object( + freelocale + SRCS + freelocale.cpp + HDRS + freelocale.h + DEPENDS + libc.include.locale + .locale +) diff --git a/libc/src/locale/duplocale.cpp b/libc/src/locale/duplocale.cpp new file mode 100644 index 0000000000000..d1bd0835121fc --- /dev/null +++ b/libc/src/locale/duplocale.cpp @@ -0,0 +1,21 @@ +//===-- Implementation of duplocale ---------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/locale/duplocale.h" +#include "include/llvm-libc-macros/locale-macros.h" +#include "src/locale/locale.h" + +#include "src/__support/CPP/string_view.h" +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(locale_t, duplocale, (locale_t loc)) { return loc; } + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/locale/duplocale.h b/libc/src/locale/duplocale.h new file mode 100644 index 0000000000000..a745383860d83 --- /dev/null +++ b/libc/src/locale/duplocale.h @@ -0,0 +1,22 @@ +//===-- Implementation header for duplocale ---------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_LOCALE_DUPLOCALE_H +#define LLVM_LIBC_SRC_LOCALE_DUPLOCALE_H + +#include "src/__support/macros/config.h" + +#include "hdr/types/locale_t.h" + +namespace LIBC_NAMESPACE_DECL { + +locale_t duplocale(locale_t loc); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_LOCALE_DUPLOCALE_H diff --git a/libc/src/locale/freelocale.cpp b/libc/src/locale/freelocale.cpp new file mode 100644 index 0000000000000..2008995f101bf --- /dev/null +++ b/libc/src/locale/freelocale.cpp @@ -0,0 +1,21 @@ +//===-- Implementation of freelocale --------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/locale/freelocale.h" +#include "include/llvm-libc-macros/locale-macros.h" +#include "src/locale/locale.h" + +#include "src/__support/CPP/string_view.h" +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(void, freelocale, (locale_t)) {} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/locale/freelocale.h b/libc/src/locale/freelocale.h new file mode 100644 index 0000000000000..77ece30430738 --- /dev/null +++ b/libc/src/locale/freelocale.h @@ -0,0 +1,22 @@ +//===-- Implementation header for freelocale --------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_LOCALE_FREELOCALE_H +#define LLVM_LIBC_SRC_LOCALE_FREELOCALE_H + +#include "src/__support/macros/config.h" + +#include "hdr/types/locale_t.h" + +namespace LIBC_NAMESPACE_DECL { + +void freelocale(locale_t loc); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_LOCALE_FREELOCALE_H diff --git a/libc/src/locale/locale.cpp b/libc/src/locale/locale.cpp new file mode 100644 index 0000000000000..18ebc33ad5823 --- /dev/null +++ b/libc/src/locale/locale.cpp @@ -0,0 +1,21 @@ +//===-- Implementation of locale ------------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/locale/locale.h" + +#include "include/llvm-libc-macros/locale-macros.h" +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +__locale_t c_locale = {nullptr}; + +LIBC_THREAD_LOCAL locale_t locale = nullptr; + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/locale/locale.h b/libc/src/locale/locale.h new file mode 100644 index 0000000000000..6d6db2bcacad3 --- /dev/null +++ b/libc/src/locale/locale.h @@ -0,0 +1,36 @@ +//===-- Implementation header for the locale --------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_LOCALE_LOCALECONV_H +#define LLVM_LIBC_SRC_LOCALE_LOCALECONV_H + +#include "src/__support/macros/attributes.h" +#include "src/__support/macros/config.h" + +#include "hdr/types/locale_t.h" + +#include + +namespace LIBC_NAMESPACE_DECL { + +// We only support the "C" locale right now. +static constexpr size_t MAX_LOCALE_NAME_SIZE = 2; + +struct __locale_data { + char name[MAX_LOCALE_NAME_SIZE]; +}; + +// The pointer to the default "C" locale. +extern __locale_t c_locale; + +// The global locale instance. +LIBC_THREAD_LOCAL extern locale_t locale; + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_LOCALE_LOCALECONV_H diff --git a/libc/src/locale/localeconv.cpp b/libc/src/locale/localeconv.cpp new file mode 100644 index 0000000000000..e4d7536bf1ffb --- /dev/null +++ b/libc/src/locale/localeconv.cpp @@ -0,0 +1,49 @@ +//===-- Implementation of localeconv --------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/locale/localeconv.h" + +#include "src/__support/CPP/limits.h" +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +static char DOT_STRING[] = "."; +static char EMPTY_STRING[] = ""; + +static struct lconv C_LCONV = { + .decimal_point = DOT_STRING, + .thousands_sep = EMPTY_STRING, + .grouping = EMPTY_STRING, + .mon_decimal_point = EMPTY_STRING, + .mon_thousands_sep = EMPTY_STRING, + .mon_grouping = EMPTY_STRING, + .positive_sign = EMPTY_STRING, + .negative_sign = EMPTY_STRING, + .currency_symbol = EMPTY_STRING, + .frac_digits = CHAR_MAX, + .p_cs_precedes = CHAR_MAX, + .n_cs_precedes = CHAR_MAX, + .p_sep_by_space = CHAR_MAX, + .n_sep_by_space = CHAR_MAX, + .p_sign_posn = CHAR_MAX, + .n_sign_posn = CHAR_MAX, + .int_curr_symbol = EMPTY_STRING, + .int_frac_digits = CHAR_MAX, + .int_p_cs_precedes = CHAR_MAX, + .int_n_cs_precedes = CHAR_MAX, + .int_p_sep_by_space = CHAR_MAX, + .int_n_sep_by_space = CHAR_MAX, + .int_p_sign_posn = CHAR_MAX, + .int_n_sign_posn = CHAR_MAX, +}; + +LLVM_LIBC_FUNCTION(struct lconv *, localeconv, ()) { return &C_LCONV; } + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/locale/localeconv.h b/libc/src/locale/localeconv.h new file mode 100644 index 0000000000000..a8f7599b572bf --- /dev/null +++ b/libc/src/locale/localeconv.h @@ -0,0 +1,22 @@ +//===-- Implementation header for localeconv --------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_LOCALE_LOCALECONV_H +#define LLVM_LIBC_SRC_LOCALE_LOCALECONV_H + +#include "src/__support/macros/config.h" + +#include "include/llvm-libc-types/struct_lconv.h" + +namespace LIBC_NAMESPACE_DECL { + +struct lconv *localeconv(); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_LOCALE_LOCALECONV_H diff --git a/libc/src/locale/newlocale.cpp b/libc/src/locale/newlocale.cpp new file mode 100644 index 0000000000000..379e7e6385d09 --- /dev/null +++ b/libc/src/locale/newlocale.cpp @@ -0,0 +1,28 @@ +//===-- Implementation of newlocale ---------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/locale/newlocale.h" +#include "include/llvm-libc-macros/locale-macros.h" +#include "src/locale/locale.h" + +#include "src/__support/CPP/string_view.h" +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(locale_t, newlocale, + (int category_mask, const char *locale_name, locale_t)) { + cpp::string_view name(locale_name); + if (category_mask > LC_ALL || (!name.empty() && name != "C")) + return nullptr; + + return &c_locale; +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/locale/newlocale.h b/libc/src/locale/newlocale.h new file mode 100644 index 0000000000000..08a0071cb7aea --- /dev/null +++ b/libc/src/locale/newlocale.h @@ -0,0 +1,22 @@ +//===-- Implementation header for setlocale ---------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_LOCALE_SETLOCALE_H +#define LLVM_LIBC_SRC_LOCALE_SETLOCALE_H + +#include "src/__support/macros/config.h" + +#include "hdr/types/locale_t.h" + +namespace LIBC_NAMESPACE_DECL { + +locale_t newlocale(int category_mask, const char *locale_name, locale_t base); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_LOCALE_SETLOCALE_H diff --git a/libc/src/locale/setlocale.cpp b/libc/src/locale/setlocale.cpp new file mode 100644 index 0000000000000..0950ad73cbe2c --- /dev/null +++ b/libc/src/locale/setlocale.cpp @@ -0,0 +1,28 @@ +//===-- Implementation of setlocale ---------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/locale/setlocale.h" +#include "include/llvm-libc-macros/locale-macros.h" +#include "src/locale/locale.h" + +#include "src/__support/CPP/string_view.h" +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(char *, setlocale, (int category, const char *locale_name)) { + cpp::string_view name(locale_name); + if (category > LC_ALL || (!name.empty() && name != "C")) + return nullptr; + + static char locale_str[] = "C"; + return locale_str; +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/locale/setlocale.h b/libc/src/locale/setlocale.h new file mode 100644 index 0000000000000..a9213cf409a7b --- /dev/null +++ b/libc/src/locale/setlocale.h @@ -0,0 +1,22 @@ +//===-- Implementation header for setlocale ---------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_LOCALE_SETLOCALE_H +#define LLVM_LIBC_SRC_LOCALE_SETLOCALE_H + +#include "src/__support/macros/config.h" + +#include "hdr/types/locale_t.h" + +namespace LIBC_NAMESPACE_DECL { + +char *setlocale(int category, const char *locale_name); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_LOCALE_SETLOCALE_H diff --git a/libc/src/locale/uselocale.cpp b/libc/src/locale/uselocale.cpp new file mode 100644 index 0000000000000..d6fdad248f12b --- /dev/null +++ b/libc/src/locale/uselocale.cpp @@ -0,0 +1,23 @@ +//===-- Implementation of uselocale ---------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/locale/uselocale.h" +#include "src/locale/locale.h" + +#include "src/__support/common.h" +#include "src/__support/macros/config.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(locale_t, uselocale, (locale_t newloc)) { + if (!newloc) + return locale; + return locale = newloc; +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/locale/uselocale.h b/libc/src/locale/uselocale.h new file mode 100644 index 0000000000000..15403490d2f8c --- /dev/null +++ b/libc/src/locale/uselocale.h @@ -0,0 +1,22 @@ +//===-- Implementation header for uselocale ---------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_SRC_LOCALE_USELOCALE_H +#define LLVM_LIBC_SRC_LOCALE_USELOCALE_H + +#include "src/__support/macros/config.h" + +#include "hdr/types/locale_t.h" + +namespace LIBC_NAMESPACE_DECL { + +locale_t uselocale(locale_t newloc); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_LOCALE_USELOCALE_H diff --git a/libc/test/src/CMakeLists.txt b/libc/test/src/CMakeLists.txt index 60ea7e6a90d71..ddc6a5c7f6965 100644 --- a/libc/test/src/CMakeLists.txt +++ b/libc/test/src/CMakeLists.txt @@ -82,6 +82,7 @@ add_subdirectory(setjmp) add_subdirectory(signal) add_subdirectory(spawn) add_subdirectory(time) +add_subdirectory(locale) if(${LIBC_TARGET_OS} STREQUAL "linux") add_subdirectory(pthread) diff --git a/libc/test/src/locale/CMakeLists.txt b/libc/test/src/locale/CMakeLists.txt new file mode 100644 index 0000000000000..3192004db26dd --- /dev/null +++ b/libc/test/src/locale/CMakeLists.txt @@ -0,0 +1,25 @@ +add_custom_target(libc-locale-tests) + +add_libc_test( + locale_test + SUITE + libc-locale-tests + SRCS + locale_test.cpp + DEPENDS + libc.include.locale + libc.src.locale.newlocale + libc.src.locale.uselocale + libc.src.locale.freelocale +) + +add_libc_test( + localeconv_test + SUITE + libc-locale-tests + SRCS + localeconv_test.cpp + DEPENDS + libc.include.locale + libc.src.locale.localeconv +) diff --git a/libc/test/src/locale/locale_test.cpp b/libc/test/src/locale/locale_test.cpp new file mode 100644 index 0000000000000..bc48bb851f4e4 --- /dev/null +++ b/libc/test/src/locale/locale_test.cpp @@ -0,0 +1,27 @@ +//===-- Unittests for locale ----------------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "src/locale/freelocale.h" +#include "src/locale/newlocale.h" +#include "src/locale/uselocale.h" + +#include "test/UnitTest/Test.h" + +#include "include/llvm-libc-macros/locale-macros.h" + +TEST(LlvmLibcLocale, DefaultLocale) { + locale_t new_locale = LIBC_NAMESPACE::newlocale(LC_ALL, "C", nullptr); + EXPECT_NE(new_locale, static_cast(nullptr)); + + locale_t old_locale = LIBC_NAMESPACE::uselocale(new_locale); + EXPECT_NE(old_locale, static_cast(nullptr)); + + LIBC_NAMESPACE::freelocale(new_locale); + + LIBC_NAMESPACE::uselocale(old_locale); +} diff --git a/libc/test/src/locale/localeconv_test.cpp b/libc/test/src/locale/localeconv_test.cpp new file mode 100644 index 0000000000000..79264276dec35 --- /dev/null +++ b/libc/test/src/locale/localeconv_test.cpp @@ -0,0 +1,17 @@ +//===-- Unittests for localeconv ------------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "include/llvm-libc-macros/locale-macros.h" +#include "src/locale/localeconv.h" + +#include "test/UnitTest/Test.h" + +TEST(LlvmLibcLocale, DefaultLocale) { + struct lconv *conv = LIBC_NAMESPACE::localeconv(); + EXPECT_STREQ(conv->decimal_point, "."); +}