1#include "libc.h" 2#include "locale_impl.h" 3#include <locale.h> 4#include <time.h> 5#include <wchar.h> 6 7const char* __strftime_fmt_1(char (*s)[100], size_t* l, int f, const struct tm* tm, locale_t loc); 8 9size_t __wcsftime_l(wchar_t* restrict s, size_t n, const wchar_t* restrict f, 10 const struct tm* restrict tm, locale_t loc) { 11 size_t l, k; 12 char buf[100]; 13 wchar_t wbuf[100]; 14 wchar_t* p; 15 const char* t_mb; 16 const wchar_t* t; 17 int plus; 18 unsigned long width; 19 for (l = 0; l < n; f++) { 20 if (!*f) { 21 s[l] = 0; 22 return l; 23 } 24 if (*f != '%') { 25 s[l++] = *f; 26 continue; 27 } 28 f++; 29 if ((plus = (*f == '+'))) 30 f++; 31 width = wcstoul(f, &p, 10); 32 if (*p == 'C' || *p == 'F' || *p == 'G' || *p == 'Y') { 33 if (!width && p != f) 34 width = 1; 35 } else { 36 width = 0; 37 } 38 f = p; 39 if (*f == 'E' || *f == 'O') 40 f++; 41 t_mb = __strftime_fmt_1(&buf, &k, *f, tm, loc); 42 if (!t_mb) 43 break; 44 k = mbstowcs(wbuf, t_mb, sizeof wbuf / sizeof *wbuf); 45 if (k == (size_t)-1) 46 return 0; 47 t = wbuf; 48 if (width) { 49 for (; *t == '+' || *t == '-' || (*t == '0' && t[1]); t++, k--) 50 ; 51 width--; 52 if (plus && tm->tm_year >= 10000 - 1900) 53 s[l++] = '+'; 54 else if (tm->tm_year < -1900) 55 s[l++] = '-'; 56 else 57 width++; 58 for (; width > k && l < n; width--) 59 s[l++] = '0'; 60 } 61 if (k >= n - l) 62 k = n - l; 63 wmemcpy(s + l, t, k); 64 l += k; 65 } 66 if (n) { 67 if (l == n) 68 l = n - 1; 69 s[l] = 0; 70 } 71 return 0; 72} 73 74size_t wcsftime(wchar_t* restrict wcs, size_t n, const wchar_t* restrict f, 75 const struct tm* restrict tm) { 76 return __wcsftime_l(wcs, n, f, tm, CURRENT_LOCALE); 77} 78 79weak_alias(__wcsftime_l, wcsftime_l); 80