Home > itblogs > Поверхностное сравнение архитектуры консоли в Windows и Unix.

Поверхностное сравнение архитектуры консоли в Windows и Unix.

January 10th, 2010

Довольно интересно сравнить, как устроена консоль в Windows и Unix. Вот упрощенная схема как это работает в Unix:

Консоль в Unix

Консоль в Unix

Посимвольный ввод и вывод через stdin/stdout – единственный канал общения с консолью (терминалом), доступный приложению. Терминалом, при этом, может быть все что угодно – файл на диске, виртуальный терминал в X Window, труба (pipe) из другого приложения и т.д. Между терминалом и приложением передается текст. Нажатия нетекстовых клавиш (клавиш управления курсором, функциональных клавиш и т.п.) транслируются терминалом в управляющие последовательности/ESC коды (см. Ecma-35). С помощью аналогичных управляющих последовательностей приложение может посылать терминалу команды вроде «перейти на следующую строку».

Собственно говоря, полностью корректная отработка ESC кодов, – это весьма сложная задача ввиду сильнейшего разнообразия различных видов терминалов. Библиотека ncurses, к примеру, содержит описания более чем полутора тысяч разных терминальных конфигураций. Неразберихи добавляет и необходимость согласования кодировок текста, которым обмениваются терминал и приложение. К счастью, и разнообразие терминалов, и разнообразие кодировок постепенно сходит на нет – «железные» терминалы почти вымерли; Unicode шагает по планете.

Архитектура консольной подсистемы в Windows во многом отличается от Unix:

Консоль в Windows

Консоль в Windows

Вместо символьного ввода-вывода, приложение общается с консолью через вызовы удаленных функций (RPC). Клавиатурный ввод передается в виде последовательности нажатий клавиш, а не в виде последовательности символов, полученной в результате нажатия этих клавиш. В результате в Windows приложение может, например, отличить Ctrl+Shift+Left от Shift+Left. С другой стороны, в Windows приложение обязано знать тип и раскладку клавиатуры, выбранные в терминале, что в случае удаленного терминала превращается в проблему.

Для приложений, которым не интересны подробности нажатий клавиш, нажатия клавиш транслируется в традиционный символьный ввод-вывод. К примеру, ReadConsole глубоко внутри вызывает ReadConsoleInput. На Unix приходится решать обратную задачу – из потока символов выделять нажатия клавиш.

Стандартный ввод-вывод отделен от собственно консоли. В результате, перенаправление стандартного ввода-вывода не перехватывает весь консольный ввод-вывод. Попробуйте на досуге перенаправить вывод Far Manager в файл. А затем посмотрите, что получится если сделать то же самое с Midnight Commander.

Продолжение, надеюсь, следует…

  1. January 11th, 2010 at 02:16 | #1

    Познавательно, спасибо!

    Небольшая опечатка только в третьем абзаце: “необходимость согласования согласование кодировок текста”.

  2. January 11th, 2010 at 04:57 | #2

    Хочется продолжения весьма.

  3. January 11th, 2010 at 05:26 | #3

    А можно я вопрос задам по теме windows консоли?

    Почему python.exe при интерпретации команды subprocess.call(['cmd', '/c', 'cls']) чистит консоль, а php.exe при всех попытках выполнить аналогичную команду (command /c cls, cmd /c cls, с помощью exec, shell_exec, system, passthru, `backticks`) просто выводит на экран ASCII команды ←[2J, ♀?

    Правильно ли я понимаю, что разработчики питона — более тщательные разработчики и они специально вызывают системную FillConsoleOutputCharacter (или что-то подобное) когда перехватывают ASCII последовательность ←[2J?

  4. January 11th, 2010 at 07:45 | #4

    Илья Весенний :
    Небольшая опечатка только в третьем абзаце: “необходимость согласования согласование кодировок текста”.

    Спасибо, поправил.

    Val :
    Правильно ли я понимаю, что разработчики питона — более тщательные разработчики и они специально вызывают системную FillConsoleOutputCharacter (или что-то подобное) когда перехватывают ASCII последовательность ←[2J?

    Скорее разработчики php перемудрили, если уж они могу отранслировать вызов cmd.exe с командой очистки экрана в соотв. ESC последовательность. Еще как вариант php может неправильно определять тип терминала, ошибочно полагая, что тот поддерживает ESC команды.

  5. January 11th, 2010 at 10:22 | #5

    Очень интересно будет увидеть продолжение и может быть наконец узнать, почему в Windows нельзя изменить размер консоли мышкой, а в Linux запросто. Не ради холивара, а просто любопытно с чем связано такое ограничение.

  6. January 11th, 2010 at 10:47 | #6

    Алексей, а как тогда понимать вот эту фразу:
    “Windows NT does not support ANSI.SYS escape sequences in Win32 Console applications.” с http://academic.evergreen.edu/projects/biophysics/technotes/program/ansi_esc.htm ?

  7. vkni
    January 11th, 2010 at 11:11 | #7

    @Val
    ANSI.SYS – это драйвер MS DOS, предназначенный для вывода разноцветного текста средствами MS DOS. В частности, он позволял выводить цветной текст из .bat файлов. В программах же, обычно люди писали на экран напрямую. Т.е. тот же Dos Navigator никакого ANSI.SYS не требует.

    Так что никакого противоречия нет: консоль Win32 действительно не поддерживает escape sequences, т.к. в ней нет ANSI.SYS или эквивалентного драйвера.

  8. January 11th, 2010 at 11:48 | #8

    Максим Тремпольцев :
    почему в Windows нельзя изменить размер консоли мышкой

    В Windows 7 можно, не помню как в Vista. Иными словами банально недоделали.

  9. ddenis
    January 11th, 2010 at 15:59 | #9

    > В Windows 7 можно, не помню как в Vista. Иными словами банально недоделали.

    нет, в Win7 все еще нельзя к сожалению.

    RPC это конечно замечательно, но вот если бы вывод на консоль не был таким тормозным в Windows…

  10. January 11th, 2010 at 17:02 | #10

    нет, в Win7 все еще нельзя к сожалению.

    А, пардон. Действительно нельзя. У меня ширина консоли была больше, чем ширина окна.

    ddenis :
    RPC это конечно замечательно, но вот если бы вывод на консоль не был таким тормозным в Windows…

    Дык это RPC отчасти виноват.

  11. vkni
    January 11th, 2010 at 21:59 | #11

    Пока задавал свой вопрос, решил ещё раз поискать ответ. Может быть будет интересно – есть эмулятор консоли Windows с закладками, как в Konsole или Gnome Terminal. Называется этот эмулятор – Console, находится на http://console.sf.net

    Вроде и ничего, но максимизироваться не умеет, хотя растянуть во весь экран можно. И Far с этой штукой перестаёт максимизироваться по понятным причинам.

    Нет в жизни счастья. :-(

  12. January 11th, 2010 at 22:12 | #12

    vkni :
    есть эмулятор консоли Windows с закладками, как в Konsole или Gnome Terminal. Называется этот эмулятор – Console, находится на http://console.sf.net

    Да, есть такой. Это даже не эмулятор, а просто альтернативный интерфейс консольного окна. Настоящее консольное окно там есть, просто оно прячется.

    vkni :
    Вроде и ничего, но максимизироваться не умеет, хотя растянуть во весь экран можно. И Far с этой штукой перестаёт максимизироваться по понятным причинам.
    Нет в жизни счастья.

    Кстати вот чего никогда не понимал, так зачем людям нужен полноэкранный текстовый режим при наличии графики то? Привычка?

  13. Slavik Gnatenko
    January 12th, 2010 at 05:05 | #13

    “«железные» терминалы почти вымерли; Unicode шагает по планете” Тут не всё так просто. Совсем железные терминалы может и вымерли, но даже на писюках консоль – это не только эмулятор терминала в xterm, но и классические железно текстовые CGA compatible 80×25. У них есть очень большое преимущество: работают всегда. А вот что-то более продвинутое: тут как у видеодрайвера с конкретной карточкой звёзды встанут.

    “Кстати вот чего никогда не понимал, так зачем людям нужен полноэкранный текстовый режим при наличии графики то? Привычка?” Я как раз не сторонник FS, но аргументов наслышан:
    1) Вывод в железный текст быстрее, чем в графически эмулируемый;
    2) А если ещё и производитель видеокарточки не поленился напихать в её биос текстовых режимов типа 134×50, то информации на экране помещается предостаточно и графика не нужна.
    В общем приходи на #os2russian, там есть любителей. Расскажут :)

    Рассказать что ли, как в полуоси реализовано? Если кому-то кошмаров на сон грядущий не хватает.

  14. Michael
    January 12th, 2010 at 09:17 | #14

    Всё просто – полноэкранный текстовый режим нужен для FAR. И никакая графика не заменит – по скорости отклика интерфейса. А скорость отклика очень важна – для меня она вообще самая важная характеристика – иначе мысль сбивается.

  15. vkni
    January 12th, 2010 at 14:19 | #15

    @Алексей Пахунов

    А есть ещё эмуляторы консоли? Ну, или другие интерфейсы?

    ————
    Мне полноэкранный вывод Фара нужен потому, что у меня 15-ти и 12-ти дюймовые экраны. Да и на 21-о дюймовом я бы тоже пользовался полной максимизацией, т.к. оконный менеджер Виндов не умеет максимизировать по одной оси (правая/средняя кнопка на иконке максимизации КДЕ).

    А текстовый Фар (консоль в окне или полноэкранка) мне нужен для скорости по трём причинам:

    1) уже 15-ть лет как выученные горячие клавиши.

    2) простота интерфейса, в котором ровно один простой легкочитаемый консольный шрифт. Больше 2-х шрифтов на странице книги – плохо, а в интерфейсе утилиты – вообще мрак.

    3) текстовый режим Фара вообще мгновенно откликается на любой машине + ничего не отвлекает.

    Этим, кстати, хороши и текстовые терминалы Линукса, которыми я часто пользуюсь – мгновенность переключения почти вне зависимости от нагрузки машины, ровно один шрифт, хороший крупный шрифт и минимум посторонней информации. Очень книги хорошо читать и набирать в Vim’е.

    Причём в Линуксе это не настоящий текстовый режим, а framebuffer. ;-)

  16. January 12th, 2010 at 22:26 | #16

    vkni :
    А есть ещё эмуляторы консоли? Ну, или другие интерфейсы?

    Есть, скорее всего. Но на ум ничего не приходит.

    vkni :
    полноэкранный вывод Фара нужен потому

    Короче говоря, основные причины это скорость и привычка.

  17. January 12th, 2010 at 23:32 | #17

    Slavik Gnatenko :
    Рассказать что ли, как в полуоси реализовано? Если кому-то кошмаров на сон грядущий не хватает.

    А что там не так? Работает и работает неплохо. Под TextShell-ом вполе себе приятно. :)

  18. vkni
    January 13th, 2010 at 08:14 | #18

    Алексей Пахунов :
    Короче говоря, основные причины это скорость и привычка.

    Если включать сюда полное управление с клавиатуры, без участия мыши (не нужно руку переставлять, большинство операций с текстами с клавиатуры делается в несколько раз быстрее), то – да.

    Ещё очень важный плюс – то, что полноэкранный текстовый режим превращает монитор в “книгу”, отсекая практически все посторонние вещи – панель задач, курсор мыши, заголовки окон и т.д. Это очень помогает концентрации.

  19. January 13th, 2010 at 08:30 | #19

    vkni :
    Если включать сюда полное управление с клавиатуры, без участия мыши (не нужно руку переставлять, большинство операций с текстами с клавиатуры делается в несколько раз быстрее), то – да.

    Ну, строго говоря, к полноэкранности это отношения не имеет.

    vkni :
    Ещё очень важный плюс – то, что полноэкранный текстовый режим превращает монитор в “книгу”, отсекая практически все посторонние вещи – панель задач, курсор мыши, заголовки окон и т.д. Это очень помогает концентрации.

    Ага, а вот это интересное наблюдение.

  20. Slavik Gnatenko
    January 13th, 2010 at 08:36 | #20

    @Neandertalets
    Я могу много порассказать, как оно унутре сделано и работает. Но не уверен, что здесь это кому-то интересно.

    @vkni
    А что, управление с клавиатуры – это прерогатива FS text? :O Я писал вполне себе гуйные многооконные приложения, где мышь много всего дублировала, но при быстрой работе была нафиг не нужна. Собсно, в NC и его потомках она тоже поддерживается. Может даже кто-то и пользуется.

  21. January 13th, 2010 at 08:53 | #21

    Slavik Gnatenko :
    @Neandertalets
    Я могу много порассказать, как оно унутре сделано и работает. Но не уверен, что здесь это кому-то интересно.

    Интересно, интересно. ;-) К тому же, Neandertalets тут у нас самый главный сторонник OS/2.

    PS. Если вдруг получится целая статья, то я её согу разместить блоге. Или закросспостить (извините за мой французский).

  22. vkni
    January 13th, 2010 at 09:49 | #22

    Связь между горячими клавишами и текстовым режимом не прямая. Это не “причина-следствие”.

    Во-первых, программы текстового режима разрабатываются уже много лет. Было время вылизать.

    А во-вторых, мышью в текстовом режиме, за редким исключением, пользоваться крайне неудобно. И вменяемые разработчики ПО это понимают => компенсируют развитыми гор. клавишами.

    ————-
    Кстати, немаловажно, что из-за отсутствия виртуальных терминалов и framebuffer’а, под Windows текстовый режим теряет изрядную часть привлекательности, которую он имеет под Linux’ом:

    1) Стандартные текстовые режимы реализуются на обычных текстовых режимах видеокарты – часто видно зерно. На framebuffer’е – нет. Там и шрифты по-лучше, а скорость всё-равно запредельная.

    2) Переключение с одной текстовой задачи на другую приводит к 3-х кратной смене разрешения. С соответствующим миганием. В Линуксе переключения разрешения нет.

    Это тоже нужно учитывать при обсуждении текста vs графики.

  23. January 13th, 2010 at 09:55 | #23

    vkni :
    Это тоже нужно учитывать при обсуждении текста vs графики.

    Кстати, мне вот именно это и не понятно было. Я воспринял вопрос так как будто нужен именно аппаратный текстовый режим. А на самом деле нужно окно в весь экран (без рамки и проч.) в графике.

  24. Grohm
    January 13th, 2010 at 11:21 | #24

    Очередной раз убеждаюсь что консоль в винде полнейшее УГ

  25. January 13th, 2010 at 12:01 | #25

    Grohm :
    Очередной раз убеждаюсь что консоль в винде полнейшее УГ

    Молодец! Возьми с полки пирожок. :-)

  26. January 13th, 2010 at 23:14 | #26

    vkni :
    Причём в Линуксе это не настоящий текстовый режим, а framebuffer.

    Кстати, этот самый Linux framebuffer (не путать с просто framebuffer, который есть отображаемая область видеопамяти) – это очень забавный виток эволюции. Linux начинал с юниксного предположения, что терминал (в том числе графический) в большинстве случаев находится не на той машине, где крутятся приложения. Отсюда X protocol для графики и спецконтролы для /dev/tty (девайс, логически означающий консоль, а не RS-232 порт), выставляющие на нём скорость порта, да ещё и не числом, а жёстким набором абстрактных констант. Теперь в угоду, замученым тормозами, пользователям Linux отошёл от принципа юниксной минимальности и пришёл к архитектуре видеосистемы, которую в OS/2 сделали в году примерно 1993м. А потом наоборот, сводили видеодрайвер в единый, потому что производители замахались писать отдельные видеодрайвера для каждой подсистемы приложений (полного экрана, нативной графики и Win16).

    Да, и всё это происходит на фоне периодических попыток корпораций (то Sun, теперь вот Google) вернуть мир на тонкие клиенты, т.е. по сути на те самые отмершие аппаратные терминалы :)

  27. January 13th, 2010 at 23:36 | #27

    Алексей Пахунов :

    vkni :
    А есть ещё эмуляторы консоли? Ну, или другие интерфейсы?

    Есть, скорее всего. Но на ум ничего не приходит.

    Вспомнил. Есть еще ConEmu.

  28. vkni
    January 14th, 2010 at 09:45 | #28

    Алексей Пахунов :
    Вспомнил. Есть еще ConEmu.

    Спасибо. Можно несколько постронних вопросов?:

    А случайно не знаете, могут ли использоваться добавленные в x86-64 регистры в расчётах с плавающей точкой?

    Есть ли планы у вашей конторы прекратить создание x86-32 ОС?

    —————
    Ну, скажу вам, и дурной же этот blogspot: очень неприятно выдирать цитату на которую хочешь ответить из его дурной XML простыни. Видимо разработчики сами не пользуются этой дрянью.

  29. vkni
    January 14th, 2010 at 09:58 | #29

    Slavik Gnatenko :
    Теперь в угоду, замученым тормозами, пользователям Linux отошёл от принципа юниксной минимальности и пришёл к архитектуре видеосистемы, которую в OS/2 сделали в году примерно 1993м.
    А потом наоборот, сводили видеодрайвер в единый, потому что производители замахались писать отдельные видеодрайвера для каждой подсистемы приложений (полного экрана, нативной графики и Win16).

    Разнородность терминала и X-ов от того, что Х-ы появились через 10 или 15-ть лет после терминалов. Это одни из тех самых многочисленных “ушей” PDP-11, которые торчат из Linux.

    Сейчас идут какие-то подвижки в переносе драйверов из X в ядро. Это, скорее всего, правильно. Но вот только ядро – кубик-рубик-монолит :-( .

  30. vkni
    January 14th, 2010 at 10:10 | #30

    @Алексей Пахунов

    Кстати, ещё вопрос:

    У меня в какой-то момент Виста стала выдавать синий экран при засыпании. Я выяснил, что непосредственный виновник – установленная libusb. Но ведь в Vista стоит гибридное ядро. И я думал, что единственные драйвера, работающие в режиме “монолита” – видеодрайвера. Неужели – нет?

    Вас не затруднит либо дать ссылку на описание текущих дел в этой области или тут кратко рассказать?

    И ещё вопрос: зачем в NT 3.5 внесли видеодрайвер в режим ядра я понимаю – для скорости. Но сейчас ведь большую часть работы делает не ЦПУ, а видяха. Нельзя ли “заковырять всё обратно”? :-)

  31. January 14th, 2010 at 10:20 | #31

    vkni :
    А случайно не знаете, могут ли использоваться добавленные в x86-64 регистры в расчётах с плавающей точкой?

    x64 код использует SSE по умолчанию. x86 код может использовать первые восемь SSE регистров. Функция IsProcessorFeaturePresent (или соответствующий C runtime wrapper) позволяют выяснить наличие SSE, SSE2 и т.д.

    vkni :
    Есть ли планы у вашей конторы прекратить создание x86-32 ОС?

    Я ничего про такие планы не знаю. Это скорее к маркетологам, которые определяют какие версии и с каким набором фич выпускать.

    vkni :
    Ну, скажу вам, и дурной же этот blogspot: очень неприятно выдирать цитату на которую хочешь ответить из его дурной XML простыни. Видимо разработчики сами не пользуются этой дрянью.

    Это WordPress. :-) Редактирование комментариев могло быть и по-удобнее.

  32. vkni
    January 14th, 2010 at 11:05 | #32

    @Алексей Пахунов

    Ещё раз спасибо.

  33. January 14th, 2010 at 12:02 | #33

    vkni :
    Но ведь в Vista стоит гибридное ядро. И я думал, что единственные драйвера, работающие в режиме “монолита” – видеодрайвера. Неужели – нет?

    Любой драйвер ядра может положить систему. “Гибридное” ядро, если я правильно понимаю классификацию, – это ядро с подгружаемыми модулями AKA драйверами. Монолитное ядро этого, в теории, делать не умеет. На практике это умеют делать почти все в результате классификация идет по принципу “насколько широко используются подгружаемые драйвера”.

    vkni :
    Вас не затруднит либо дать ссылку на описание текущих дел в этой области или тут кратко рассказать?

    Затруднит, к сожалению. Хорошей ссылки под руками нет, а сам я не великий спец в этих классификациях.

    vkni :
    И ещё вопрос: зачем в NT 3.5 внесли видеодрайвер в режим ядра я понимаю – для скорости. Но сейчас ведь большую часть работы делает не ЦПУ, а видяха. Нельзя ли “заковырять всё обратно”?

    Теоретически – наверное можно. Практически – это великий гемморой с непонятными преимуществами. Из отрицательных последствий такого шага могу навскидку предложить порушенную совместимость и более глючные драйвера из-за грандиозного рефакторинга. BSODов, конечно, не будет, но и работать оно не будет.

  34. vkni
    January 14th, 2010 at 12:53 | #34

    Алексей Пахунов :

    vkni :
    Затруднит, к сожалению. Хорошей ссылки под руками нет, а сам я не великий спец в этих классификациях.

    Очень жаль. Ещё раз спасибо.

  35. January 21st, 2010 at 10:06 | #35

    Алексей Пахунов :
    Интересно, интересно. К тому же, Neandertalets тут у нас самый главный сторонник OS/2.

    Ну здесь может и “самый”, но ею как таковой уже некоторое время не пользуюсь. Хотя сохранил самые приятные впечатления от неё и ностальгии ради ковыряюсь в виртуалке (специально даже обновил до версии Parallels Desktop 4.0 :) ).
    Сейчас уполз на OpenBSD.
    Но OS/2 – мечта деЦЦтва. :)

  36. January 21st, 2010 at 10:22 | #36

    Neandertalets :
    Сейчас уполз на OpenBSD.

    А как дысал, как дысал! (c) :-)

  37. vkni
    January 25th, 2010 at 11:05 | #37

    Кстати, характерная иллюстрация к тому, что я говорил про лаконичность текстового интерфейса – см Фригат3:

    http://www.frigate3.com/screenshots.php

    В сравнении с Far, NC, DN он страшно перегружен. Над панелями пять (5) строк, под панелями 3, разных начертаний шрифтов я насчитал 7! Информация о том, что объект является каталогом, дублируется шрифтом и пиктограммой. Командная строка отсутствует, видимо скрыта.

    А в текстовом режиме максимально излишен Dos Navigator, который, тем не менее, не рябит в глазах. И это приемущество в эргономике исключительно из-за жёстких ограничений консоли!

Comments are closed.