Re: mutt_FormatString() not multibyte-aware
* Sat Jul 8 2006 Rocco Rutte <pdmef@xxxxxxx>
> * Ludolf Holzheid [06-07-07 21:18:52 +0200] wrote:
>
> >(I wonder why Tamo didn't jump into that earlier -- Maybe he's just
> >tired of explaining to the Europeans there are other scripts than
> >Latin.)
>
> I understand and know that perfectly well. Maybe it's just that I didn't
> make myself clear enough.
I believe that Rocco knows multibyte issues well (yes,
quite better than I). I said nothing against his opinion
just because I didn't find anything bad.
I can write bogus wc-funcs to complete my previous hack,
but I have no idea which is better (mine or Rocco's).
At this moment, mine is a _little_ better because he hasn't
posted a patch. I hope he will find a best way.
--
tamo
--- mbyte.c
+++ mbyte.c
@@ -463,6 +463,94 @@ size_t utf8rtowc (wchar_t *pwc, const ch
return (size_t)-2;
}
+/* wcswidth by Markus Kuhn -- 2000-02-08 -- public domain */
+int wcswidth(const wchar_t *pwcs, size_t n)
+{
+ int w, width = 0;
+
+ for (;*pwcs && n-- > 0; pwcs++)
+ if ((w = wcwidth(*pwcs)) < 0)
+ return -1;
+ else
+ width += w;
+
+ return width;
+}
+
+/* mbstowcs hack - may violate POSIX */
+size_t mbstowcs (wchar_t *pwcs, const char *s, size_t n)
+{
+ mbstate_t st;
+ size_t k;
+ wchar_t wc;
+ wchar_t *p = pwcs;
+
+ memset (&st, 0, sizeof (st));
+ for (; (k = mbrtowc (&wc, s, MB_LEN_MAX, &st)); s += k)
+ {
+ if (k == (size_t)(-1) || k == (size_t)(-2))
+ {
+ errno = EILSEQ;
+ return (size_t)(-1);
+ }
+ if (pwcs)
+ {
+ if (!n)
+ break;
+ *p++ = wc;
+ n--;
+ }
+ }
+ if (n && pwcs)
+ *p = 0;
+ return (p - pwcs);
+}
+
+/* wcstombs hack - may violate POSIX */
+size_t wcstombs (char *s, const wchar_t *pwcs, size_t n)
+{
+ size_t l, r = 0;
+ char buf[MB_LEN_MAX];
+
+ for (;*pwcs; pwcs++)
+ {
+ l = wcrtomb (buf, *pwcs, NULL);
+ if (l == (size_t)(-1))
+ {
+ errno = EILSEQ;
+ return l;
+ }
+ if (s)
+ {
+ if (n <= l)
+ break;
+ memcpy (s, buf, l);
+ s += l;
+ n -= l;
+ }
+ r += l;
+ }
+ if (s && n)
+ *s = '\0';
+ return r;
+}
+
+size_t wcslen (const wchar_t *s)
+{
+ size_t l = 0;
+ while (*s++)
+ l++;
+ return l;
+}
+
+wchar_t * wmemcpy (wchar_t *s1, const wchar_t *s2, size_t n)
+{
+ wchar_t *o = s1;
+ while (n--)
+ *s1++ = *s2++;
+ return o;
+}
+
#endif /* !HAVE_WC_FUNCS */
wchar_t replacement_char (void)
--- mbyte.h
+++ mbyte.h
@@ -19,6 +19,11 @@ wint_t towupper (wint_t wc);
wint_t towupper (wint_t wc);
wint_t towlower (wint_t wc);
int wcwidth (wchar_t wc);
+int wcswidth(const wchar_t *pwcs, size_t n);
+size_t mbstowcs (wchar_t *pwcs, const char *s, size_t n);
+size_t wcstombs (char *s, const wchar_t *pwcs, size_t n);
+size_t wcslen (const wchar_t *s);
+wchar_t * wmemcpy (wchar_t *s1, const wchar_t *s2, size_t n);
# endif /* !HAVE_WC_FUNCS */