В работе использется клиент системы RS-Balance, работающий как консольное приложение Win32. Как оказалось, при запуске таких приложений под wineconsole (--backend=user), не работает ввод русских букв. Локаль - UTF8. При попытке ввести русские буквы вообще ничего не вводится. Сегодня пробовал запустить FAR под wineconsole на домашней FreeBSD с локалью koi8-r, wine-0.9.16. В ответ выводились различные символы, но никак не желаемые. Бегло посмотрел на код wineconsole. Похоже, что ввод формируется в функции WCUSER_GenerateKeyInputRecord(), файл user.c. У меня вызвал подозрение следующий код: if (down) { switch (ToUnicode(wParam, HIWORD(lParam), keyState, buf, 2, 0)) { case 2: /* FIXME... should generate two events... */ /* fall thru */ case 1: last = buf[0]; break; default: last = 0; break; } } ir.Event.KeyEvent.uChar.UnicodeChar = last; /* FIXME HACKY... and buggy 'coz it should be a stack, not a single value */ Похоже, что здесь получается ASCII из Unicode. А хотелось бы cp866.
рассмотрел источник возникновения баги. он находится в programs/wineconsole/curses.c Со стандартного ввода символ считывается в функции WCCURSES_GetEvents c помощью wgetch(stdstr), далее заполняется структура ir[numEvent].Event.KeyEvent в функции WCCURSES_FillSimpleChar. При этом в качестве Unicode-строки записывается однобайтовое значение: ir[numEvent].Event.KeyEvent.uChar.UnicodeChar = (unsigned char)inchar; С английскими символами проблем нет, поскольку они одинаково кодируются как в ASCII, так и в Unicode. Сделал патч, добавил перекодировку в Unicode перед обработкой. Теперь вводимый символ читается правильно, но на экран выводятся пустые поля. Пока не смог найти , кто и каки образом осуществляет вывод.
шзначально выводом на консоль текста занимается функция WriteConsoleOutputW в dlls/kernel/console.c
Created attachment 65 [details] неполный патч этот патч преобразует считываемый символ в Unicode-формат. Таким образом, символ правильно обрабатывается в дальнейшем. Т.е. в структуре ir правильно заполняется поле UnicodeChar. Но пока что не решена проблема правильной обработки VirtualKeyCode, поскольку сейчас определение VirtualKeyCode, насколько я понимаю, происходит с учетом, что считанный символ находится в кодировке ASCII. Также все остальные переменные структуры ir, кроме UnicodeChar, определются неверно (думаю требуется перекодировка в Ascii перед записбю в переменные). ш самое главное криво работает вывод символа на экран консоли. После патча латиница выводится, а кириллица выводится пробелами (раньше выводилась 1 латинским символом).
Created attachment 74 [details] Пример проблемы Теперь при попадании в функции FillSimpleChar в curses.c считываются дополнительно 3 символа и конвертируются в переменную типа wchar с кодировкой текущей локали. ш ir[numEvent].Event.KeyEvent.uChar.UnicodeChar заполняется данной переменной типа WCHAR.
Created attachment 75 [details] Окно с проблемой !Работает только после установки патча wineconsole_curses_out! Вывод на экран осуществляется теперь функцией mvwaddnwstr в функции Refresh. Работает как в 8-битной консоли,так и в Юникодной.
Created attachment 76 [details] Лог ошибки !Работает только после установки патча wineconsole_curses_out! Вывод на экран осуществляется теперь функцией mvwaddnwstr в функции Refresh. Работает как в 8-битной консоли,так и в Юникодной.
Насколько я понял, действительно правильный способ поддержки юникода - это использование libncursesw. Вот некоторые замечания по недавно вышедшей версии ncurses 5.6 http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=341661 http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=316663
Created attachment 120 [details] Программа, проявляющая проблему
Так как программы из состава RS-Bank так и не воспринимают русский ввод, снова открываю багу.
Всё воспринимает, что и было доказано Константину,как у меня так и на сервере. Ждём ответа от клиента!
Закрываю, т.к. несостоятельна. Открываю новую багу и ставлю depend on