On Sun, Nov 21, 2010 at 10:26 AM, NARUSE, Yui <naruse / airemix.jp> wrote:
> usa is having a fever now, so I reply though I don't remember the detail..
>
> We discussed this problem before to extend writing UTF-8 string to console.
> It uses WriteConsoleW and allows to write strings to console even if its
> encoding is different from locale or the console's codepage.
> (it is the thread of [ruby-dev:35200])
>
> The result is rb_w32_write_console and it is in win32-unicode-test...
> why is it not merged to trunk...?
>
> r17825 and another fixes.
> http://svn.ruby-lang.org/cgi-bin/viewvc.cgi/branches/win32-unicode-test/win32/win32.c?view=log
>

Backporting the following code from win32-unicode-test seems to solve the issue:

diff --git a/io.c b/io.c
index afd4f31..e7bef18 100644
--- a/io.c
+++ b/io.c
@@ -961,6 +961,10 @@ do_writeconv(VALUE str, rb_io_t *fptr)
 static long
 io_fwrite(VALUE str, rb_io_t *fptr, int nosync)
 {
+#ifdef _WIN32
+    long len = rb_w32_write_console(str, fptr->fd);
+    if (len >= 0) return len;
+#endif
     str = do_writeconv(str, fptr);
     return io_binwrite(str, RSTRING_PTR(str), RSTRING_LEN(str),
 		       fptr, nosync);
diff --git a/win32/win32.c b/win32/win32.c
index e14ab49..6b3913d 100644
--- a/win32/win32.c
+++ b/win32/win32.c
@@ -5304,6 +5304,29 @@ rb_w32_write(int fd, const void *buf, size_t size)
     return ret;
 }

+long
+rb_w32_write_console(VALUE str, int fd)
+{
+    static int disable;
+    HANDLE handle;
+    DWORD dwMode, reslen;
+
+    if (disable) return -1L;
+    handle = (HANDLE)_osfhnd(fd);
+    if (!GetConsoleMode(handle, &dwMode) ||
+    !rb_econv_has_convpath_p(rb_enc_name(rb_enc_get(str)), "UTF-16LE"))
+    return -1L;
+
+    str = rb_str_encode(str, rb_enc_from_encoding(rb_enc_find("UTF-16LE")), 0,
+            Qnil);
+    if (!WriteConsoleW(handle, (LPWSTR)RSTRING_PTR(str),
RSTRING_LEN(str)/2, &reslen, NULL)) {
+    if (GetLastError() == ERROR_CALL_NOT_IMPLEMENTED)
+        disable = TRUE;
+    return -1L;
+    }
+    return (long)reslen;
+}
+
 static int
 unixtime_to_filetime(time_t time, FILETIME *ft)
 {


Should I commit it?

-- 
Luis Lavena
AREA 17
-
Perfection in design is achieved not when there is nothing more to add,
but rather when there is nothing more to take away.
Antoine de Saint-Exupy