1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-27 19:27:35 +00:00

LibC: Implement wcsrtombs

This commit is contained in:
Tim Schumacher 2021-10-08 01:22:27 +02:00 committed by Brian Gianforcaro
parent fccb06b2cd
commit b0babd062e
3 changed files with 91 additions and 0 deletions

View file

@ -8,6 +8,7 @@
#include <AK/Format.h>
#include <AK/UnicodeUtils.h>
#include <errno.h>
#include <string.h>
#include <wchar.h>
static unsigned int mbstate_expected_bytes(mbstate_t* state)
@ -462,4 +463,46 @@ int wcwidth(wchar_t wc)
// TODO: Implement wcwidth for non-ASCII characters.
return 1;
}
size_t wcsrtombs(char* dest, const wchar_t** src, size_t len, mbstate_t* ps)
{
static mbstate_t _anonymous_state = {};
if (ps == nullptr)
ps = &_anonymous_state;
size_t written = 0;
while (true) {
size_t ret = 0;
char buf[MB_LEN_MAX];
// Convert next wchar to multibyte.
ret = wcrtomb(buf, **src, ps);
// wchar can't be represented as multibyte.
if (ret == (size_t)-1) {
errno = EILSEQ;
return (size_t)-1;
}
// New bytes don't fit the buffer.
if (dest && len < written + ret) {
return written;
}
if (dest) {
memcpy(dest, buf, ret);
dest += ret;
}
// Null character has been reached
if (**src == L'\0') {
*src = nullptr;
return written;
}
*src += 1;
written += ret;
}
}
}

View file

@ -56,5 +56,6 @@ double wcstod(const wchar_t*, wchar_t**);
long double wcstold(const wchar_t*, wchar_t**);
int swprintf(wchar_t*, size_t, const wchar_t*, ...);
int wcwidth(wchar_t);
size_t wcsrtombs(char*, const wchar_t**, size_t, mbstate_t*);
__END_DECLS