diff options
-rw-r--r-- | ChangeLog | 6 | ||||
-rw-r--r-- | common.mk | 2 | ||||
-rw-r--r-- | win32/win32.c | 36 |
3 files changed, 32 insertions, 12 deletions
@@ -1,4 +1,8 @@ -Mon Aug 5 17:33:18 2013 Nobuyoshi Nakada <nobu@ruby-lang.org> +Mon Aug 5 17:38:15 2013 Nobuyoshi Nakada <nobu@ruby-lang.org> + + * win32/win32.c (rb_w32_write_console): use MultiByteToWideChar() for + the last step of conversion to WCHAR, to get rid of warnings from + rb_enc_find() in miniruby. [ruby-dev:47584] [Bug #8733] * win32/win32.c (wstr_to_mbstr, mbstr_to_wstr): fix wrong trimming. WideCharToMultiByte() and MultiByteToWideChar() do not count @@ -836,7 +836,7 @@ utf_8.$(OBJEXT): {$(VPATH)}utf_8.c {$(VPATH)}regenc.h {$(VPATH)}config.h \ {$(VPATH)}oniguruma.h {$(VPATH)}missing.h $(RUBY_H_INCLUDES) win32/win32.$(OBJEXT): {$(VPATH)}win32/win32.c {$(VPATH)}dln.h {$(VPATH)}dln_find.c \ - $(RUBY_H_INCLUDES) $(PLATFORM_D) + {$(VPATH)}internal.h $(RUBY_H_INCLUDES) $(PLATFORM_D) win32/file.$(OBJEXT): {$(VPATH)}win32/file.c $(RUBY_H_INCLUDES) $(PLATFORM_D) $(NEWLINE_C): $(srcdir)/enc/trans/newline.trans $(srcdir)/tool/transcode-tblgen.rb diff --git a/win32/win32.c b/win32/win32.c index ab2b64a5e4..587f4cbb1f 100644 --- a/win32/win32.c +++ b/win32/win32.c @@ -48,6 +48,7 @@ #endif #include "ruby/win32.h" #include "win32/dir.h" +#include "internal.h" #define isdirsep(x) ((x) == '/' || (x) == '\\') #if defined _MSC_VER && _MSC_VER <= 1200 @@ -466,8 +467,6 @@ get_system_directory(WCHAR *path, UINT len) return GetWindowsDirectoryW(path, len); } -#define numberof(array) (sizeof(array) / sizeof(*array)) - /* License: Ruby's */ VALUE rb_w32_special_folder(int type) @@ -6397,34 +6396,51 @@ rb_w32_write_console(uintptr_t strarg, int fd) HANDLE handle; DWORD dwMode, reslen; VALUE str = strarg; - rb_encoding *utf16 = rb_enc_find("UTF-16LE"); + int encindex; + WCHAR *wbuffer = 0; const WCHAR *ptr, *next; struct constat *s; long len; 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")) + if (!GetConsoleMode(handle, &dwMode)) return -1L; - str = rb_str_encode(str, rb_enc_from_encoding(utf16), - ECONV_INVALID_REPLACE|ECONV_UNDEF_REPLACE, Qnil); - ptr = (const WCHAR *)RSTRING_PTR(str); - len = RSTRING_LEN(str) / sizeof(WCHAR); s = constat_handle(handle); + encindex = ENCODING_GET(str); + switch (encindex) { + default: + if (!rb_econv_has_convpath_p(rb_enc_name(rb_enc_from_index(encindex)), "UTF-8")) + return -1L; + str = rb_str_conv_enc_opts(str, NULL, rb_enc_from_index(ENCINDEX_UTF_8), + ECONV_INVALID_REPLACE|ECONV_UNDEF_REPLACE, Qnil); + /* fall through */ + case ENCINDEX_US_ASCII: + case ENCINDEX_ASCII: + /* assume UTF-8 */ + case ENCINDEX_UTF_8: + ptr = wbuffer = mbstr_to_wstr(CP_UTF8, RSTRING_PTR(str), RSTRING_LEN(str), &len); + break; + case ENCINDEX_UTF_16LE: + ptr = (const WCHAR *)RSTRING_PTR(str); + len = RSTRING_LEN(str) / sizeof(WCHAR); + break; + } while (len > 0) { long curlen = constat_parse(handle, s, (next = ptr, &next), &len); if (curlen > 0) { if (!WriteConsoleW(handle, ptr, curlen, &reslen, NULL)) { if (GetLastError() == ERROR_CALL_NOT_IMPLEMENTED) disable = TRUE; - return -1L; + reslen = (DWORD)-1L; + break; } } ptr = next; } RB_GC_GUARD(str); + if (wbuffer) free(wbuffer); return (long)reslen; } |