Главная страница Межпроцессное взаимодействие (состязание) Ctty.task j;> (ndle evente Простые / символы / Escape-последовательности (OLrt phar v pause esca Специальные символы Конец строки (roll screen flush Рис. 3.26. Основные подпрограммы, используемые при выводе на консоль. Штриховой линией обозначено прямое копирование символов в буфер ramqueue подпрограммой cons write Эта подпрограмма при каждом вызове выполняет для указанного устройства как запись, так и чтение. В случае с консолью это означает, что сначала будут обработаны еще не принятые клавиатурные данные. Если необработанного ввода нет, переданные символы добавляются к другим символам, ожидающим вывода. Затем вызывается процедура cons write, выполняющая вывод для отображаемых в память экранов. Последняя использует подпрофамму phys copy, чтобы скопировать блок символов от пользовательского процесса в локальный буфер, причем, возможно, это действие будет повторено несколько раз, так как локальный буфер вмещает только 64 байта. Когда буфер укомплектовывается, каждый 8-битный байт переносится в другой буфер, ramqueue, представляющий собой массив 16-битных слов. Дополнительный байт заполняется текущим значением байта атрибутов, который определяет цвет символов, цвет фона и некоторые другие параметры текста. Когда это возможно, символы копируются напрямую в ramqueue, но некоторые символы, например управляющие символы, образующие ESC-последовательности, необходимо обрабатывать особо. Кроме того, специальная обработка требуется тогда, когда позиция символа превышает ширину экрана или когда ramqueue заполняется. В этом случае, чтобы передать символы и выполнить необходимые дополнительные действия, вызывается функция out char. Так, каждый раз когда на последней строке экрана принимается символ перевода строки, делается вызов подпрограммы scroll screen, а parse escape принимает символы, образующие ESC-последовательность. Обычно out char вызывает подпрограмму flush, которая копирует ramqueue в видеопамять при помощи ассемблерной подпрограммы mem vid copy. Функция flush также вызывается после того, как в ramqueue передается последний символ, чтобы гарантировать, что отображены все символы. Конечный результат работы flush - команда, предаваемая чипу видеоконтроллера 6845 с целью отобразить в нужном месте курсор. Байты, поступающие от пользовательского процесса, было бы логично выводить по одному, в цикле. Тем не менее, для систем класса Pentium с защитой памяти более эффективно предварительно накапливать их в ramqueue, а затем копировать весь блок при помощи вызова mem vid copy. Интересно, что в MINIX эта техника появилась в то время, когда система работала на более старых процессорах, не имевших защищенного режима. Предшественник mem vid copy решал другую проблему, проблему синхронизации. Дело в том, что у старых экранов запись в видеопамять необходимо было производить при очистке экрана, во время вертикального обратного хода луча, чтобы избежать появления мусора на экране. Сейчас такое устаревшее оборудование не поддерживается, так как это приводит к слишком большим накладным расходам. Тем не менее сама техника копирования целого блока из ramqueue применяется и поныне, хотя и для другой цели. Доступная консоли область видеопамяти задается полями c start и c limit структуры console. Текущее положение курсора хранится в полях c column и c row. Координатам (0,0) соответствует верхний левый угол экрана, с этого места аппаратное обеспечение начинает заполнять экран. Изображение начинается с адреса, задаваемого значением c org, и занимает 80 х 25 символов (4000 байт). Другими словами, чип 6845 извлекает из видеопамяти два байта по адресу c org и отображает в левом верхнем углу символ, используя второй байт для задания цветов, мигания и прочих атрибутов. Затем чип извлекает из памяти следующее двухбайтовое слово и отображает символ в позиции (1, 0). Этот процесс продолжается до тех пор, пока не будет достигнута позиция (79, 0), после чего начинается рисование второй строки экрана, начиная с координат (О, 1). При включении компьютера экран очищается, и данные записываются в видеопамять, начиная с положения c start, а c orig присваивается то же значение, что и c start. Таким образом, первая строка текста выводится в верхней строке экрана. Когда вывод переходит на следующую строку, под управлением ли символа перевода строки, либо в результате заполнения верхней строки экрана, новые символы помещаются по адресу, равному c start плюс 80. Со временем все 25 строк экрана окажутся заполнены и потребуется прокрутка экрана. Некоторым программам, например текстовым редакторам, требуется возможность прокручивать экран и в обратном направлении, когда курсор находится в верхней строке экрана и требуется перейти выше по тексту. Существует два подхода к решению задачи прокрутки экрана. Когда применяется программная прокрутка, символу с координатами (О, 0) всегда соответствует один и тот же адрес видеопамяти, с нулевым смещением относительно c start. Видеоконтроллер всегда выводит этот символ на одном месте, благодаря тому. что в c org хранится один и тот же адрес. Когда необходимо выполнить прокрутку, область видеопамяти, начинающаяся со второй строки экрана (смещение 80 относительно c start), копируется в начало занимаемой консолью области (смещение 0). Положение самой занимаемой экраном области памяти не меняется. В результате содержимое экрана перемещается на одну строку вверх. Эта операция занимает время, необходимое для сдвига 80 х 2000 слов памяти. При аппаратной прокрутке данные никуда не перемещаются. Вместо этого контроллер получает инструкцию начинать выводить данные с другого адреса, например с 80-го слова. Для этого новое значение записывается в c org, чтобы его можно было использовать в дальнейщем, а также копируется в нужный регистр видеоконтроллера. Такая схема будет работать, если контроллер достаточно умен и при достижении конца видеопамяти (адрес в c limit) переходит на ее начало (адрес в c start), или же при такой емкости видеопамяти, когда в ней помещается более одного экрана, то есть 80 х 2000 слов. У старых терминальных устройств обычно была небольшая память, зато они умели переходить на начало памяти, достигнув конца, и благодаря этому поддерживали аппаратную прокрутку. У современных контроллеров памяти обычно намного больше, чем это необходимо для хранения одного экрана, но перескакивать на начало они не научены. Так, контроллер с видеопамятью 32 768 байт может хранить в памяти 204 полные строки по 160 байт каждая и может 179 раз выполнить аппаратную прокрутку, прежде чем невозможность прыжка станет проблемой. Затем потребуется копирование области памяти с целью переместить данные с последних 24 строк в начало видеобуфера. Когда это делается, нижняя строка экрана заполняется пробелами для гарантии, что она пуста. При конфигурировании виртуальных консолей доступная видеопамять поровну делится между всеми консолями, для чего соответствующим образом инициализируются поля c start и c limit каждой консоли. Это оказывает влияние на прокрутку. Любому видеоконтроллеру, обладающему достаточно большой для поддержки нескольких виртуальных консолей памятью, время от времени необходима программная прокрутка, хотя номинально поддерживается аппаратная реализация сдвига экрана. Чем меньший объем памяти доступен каждому виртуальному дисплею, тем чаще требуется программная прокрутка. Предел достигается, когда создается максимально возможное количество виртуальных консолей. При этом каждая прокрутка будет программной. Положение курсора относительно начала видеопамяти можно вычислить, исходя из c column и c row, но быстрее хранить его в явном виде (c cur). Когда на экран выводится символ, он записывается в память по адресу c cur, который после вывода обновляется, как и значение в c column. Все поля структуры console, оказывающие влияние на текущее положение вывода и начало экрана в памяти, перечислены в табл. 3.12. При обработке символов, изменяющих текущую позицию (то есть символов перевода строки, забоя и т. д.), соответственным образом изменяются значения полей c column, c row и c cur. Это делается в конце кода процедуры flush, где находится вызов функции set 6845, которая устанавливает регистры видеоконтроллера.
|
© 2000 - 2024 ULTRASONEX-AMFODENT.RU.
Копирование материалов разрешено исключительно при условии цититирования. |