Ну, во-первых, кому и для чего нужна русификация видеокарты? Ответ: для
марсиан! Конкретно, для тех, кто вольно или невольно в текстовом режиме
видит русский текст нерусскими буквами. Сразу оговорюсь: все
нижеследующее относится именно к текстовому режиму, и не относится к
графическому режиму современных операционных систем. Под текстовым
режимом подразумевается видеорежим с использованием аппаратного
знакогенератора видеокарты, а не текст в Word. Проще говоря, если вы
знаете, что такое DOS и командная строка, то это для вас, если нет — не
для вас.
Русификация
видеокарты решает следующие проблемы (в том числе в графических
режимах, если текст выводится стандартными шрифтами BIOS
— CGA/EGA/VGA и возможно SVGA графика, например, BGI драйвер Турбо Паскаля):
1. избавляет от необходимости пользоваться русификаторами экрана в
среде DOS (русификация клавиатуры по-прежнему нужна) — это экономит
10-15 кб памяти в пределах первого мегабайта;
2. BSOD Windows 3.x–ME — программисты из Microsoft написали русский
текст там, где часто отказывает любой русификатор, включая стандартный:
Device=display.sys con=(ega,866,,)
Mode con cp prep=((866),ega3.cpi)
Mode con cp select=866
3. загрузчик и полноэкранный режим DOS-окна Windows 3.x–ME — многие
русификаторы (в т.ч. KEYRUS) там глючат;
4. полноэкранный режим NTVDM — там шрифтами заведует операционная
система, но после смены видеорежима она иногда забывает подгрузить их;
5. текстовые режимы малоизвестных и устаревших операционных систем —
сомнительно, что кто-то писал для них русификаторы, или их сложно будет
найти в настоящее время;
6. написание собственных операционных систем, загрузчиков и пр.
специфических программ — они могут писать на русском языке, но это
пригодно лишь для первичной отладки и либо должно быть отключено в
конечных версиях, либо вы должны написать полноценный русификатор, не
надеясь на то, что пользователь имеет такую же русифицированную
видеокарту;
7. если найдете еще причину, добавим…
Что она не решает:
1. WinIce (отладчик) содержит собственный шрифт, и конечно же, не в
курсе, что существуют русские буквы. Впрочем, иногда он не в состоянии
загрузить даже свой собственный шрифт;
2. BSOD на NT системах — там текст почти всегда выводится в графическом
режиме, просто не всегда теми символами;
3. некоторые системные BIOS на японском языке, но на русском его не
было;
4. и многое другое…
Гарантии и копирайты
Сразу
оговорюсь: русификация есть перешивка BIOS видеокарты, причем даже не
на фирменный, а на модифицированный, со всеми вытекающими
последствиями! Т.е. аннулируется гарантия, возможны проблемы с работой
видеокарты, в том числе и в нетекстовых режимах. Кроме того,
русификация видео BIOS есть также и обратное конструирование кода, что
может быть запрещено в некоторых странах законами об авторском праве! В
общем, думайте сами, решайте сами, мое дело — предупредить.
Основы процесса
По
умолчанию BIOS видеокарты содержит шрифты с кодовой страницей 437
(CP437, стандартная латиница). Этого достаточно для английского,
турецкого, греческого и др. языков. Но символов кириллицы в них нет. В
разное время для кириллицы были разработаны кодовые страницы CP866
(DOS), CP1251 (Windows), KOI-8 (Unix) и ряд других, редко используемых.
Русификация
BIOS есть подмена шрифтов в BIOS видеокарты, чаще всего на содержащие
CP866, но можно взять и любой другой нужный вам набор символов. Уже на
этом этапе могут быть варианты:
* замена только кириллицы —
минимально необходимый набор в 64 знака;
* предыдущий вариант плюс немного эстетики — позволяет скорректировать
некоторый набор символов, например убрать «столбы» в псевдографике;
* замена всех шрифтов — дает наивысшую свободу фантазии.
Чем
выше степень свободы, тем жестче требования к имеющемуся BIOS
видеокарты — прошивка, терпящая издевательство первого уровня, может не
вытерпеть последующие…
Русифицировать можно те карты, в прошивке
которых можно выделить хоть немного места под новый блок шрифтов, или
которые позволяют без нареканий заменить уже имеющийся. Старые карты с
малым объемом программного кода содержали шрифты в чистом виде,
неупакованными, и их русификация при любой глубине была элементарной.
На сайте МИР NVIDIA доступна программа RVBEdit (автор Ray Adams),
позволяющая заменить шрифты в BIOS видеокарт на базе GeForce 256 — 4 Ti
несколькими движениями мыши.
Новые BIOS разрослись настолько,
что их размер превысил 64 килобайта. Хотя организация IBM PC позволяет
выделить для видеоBIOS до 128 Кб (см. ниже), производители, видимо,
сочли невыгодным ставить 128 Кб чипы EEPROM, и решили упаковать шрифты
с 10 Кб (по другим данным, с 6) до 3 Кб, плюс распаковщик. Современные
карты все равно имеют 128 Кб чипы, но шрифты так и остались
упакованными. Естественно, если бы был известен код фирменного
упаковщика (возможно, что он и не один), было бы проще. Но как раз его
мы и не знаем…
Как результат, чтобы заменить шрифты, нужно:
1. отыскать адрес, куда они распаковываются;
2. отыскать код распаковщика;
3. проанализировать этот код, что он делает, чем и как оперирует;
4. найти, где этот код заканчивается (как правило, он вместе с шрифтами
расположен в самом конце прошивки, но после него еще могут оставаться
разные данные);
5. определить, сколько места остается до конца памяти чипа, т.е. до
ближайшей границы 64 либо 128 Кб;
6. исходя из результатов пунктов 4 и 5, разработать стратегию
русификации;
7. подготовить свои шрифты в соответствии с выбранной стратегией;
8. попытаться реализовать стратегию (не исключено, что ее придется
поменять).
Инструментарий
Вот
список утилит, которые нам точно понадобятся: hiew, nvflash и nvflash
для Windows, набор моих вспомогательных программ: grb, bsum, fpaq,
funp.bin (это бинар, а не программа!). Можно еще воспользоваться IDA,
но я обошелся без него. Все программы можно скачать по ссылкам в конце
статьи.
Начало начал
Нет, начинаем мы не с hiew! Первое, что нам нужно сделать — сохранить имеющуюся прошивку. Это делается утилитой nvflash:
nvflash –save mybios.rom
или короче:
nvflash –b mybios.rom
где
mybios — имя файла, в который сохраняется прошивка, расширение должно
быть .rom, в противном случае вы не сможете использовать сохраненную
прошивку.
Сохранили? Теперь вам нужно научиться прошивать ее
обратно. При этом вы должны исходить из наихудшего предположения о
полной неработоспособности вашей видеокарты. Поэтому я настоятельно
советую вам не рисковать без наличия либо второй видеокарты с шиной PCI
(старой шины, для старых видеокарт, в новых материнских платах туда
обычно устанавливаются модемы и звуковые карты) или шины PCI Express,
если на вашей материнской плате два и более таких слота, либо иметь
встроенную видеокарту, которая без проблем работает вместе с
прошиваемой, и это лучше проверить заранее.
На этом этапе у меня
была проблема: в моей системе DOS-версия утилиты nvflash отказывалась
прошивать неработоспособную видеокарту, если была установлена вторая
карточка (S3 Trio64 PCI), как основная (в соответствии с FAQ), и
единственный монитор был подключен к ней — невозможно было восстановить
исходную прошивку. nvflash выдавала следующее:
NOTE: Unconfigured display adapter found, device not accessible:
GeForce 7600 GS (10DE,02E1,1043,8237) H:--:NRM B:01,AGP,D:00,F:00
ERROR: No NVIDIA display adapters found
Exit Code: 2
Однако, Windows-версия nvflash срабатывала всегда, но она работает только в Windows семейства NT! Отсюда вывод:
* Если мы прошиваем заведомо рабочую карту предположительно рабочей
прошивкой, лучше использовать DOS-версию nvflash;
* Если мы прошиваем заведомо НЕрабочую карту с запоротым нами (или не
нами) BIOS, лучше сразу использовать NT-версию nvflash, но для этого
требуется, чтобы загружалась операционная система (с использованием
интегрированного в чипсет материнской платы видеоядра или
дополнительнойвидеокарты).
nvflash mybios.rom
Поскольку мы прошили тот же BIOS, который только что сохранили, в работе карточки не должно было измениться ровным счетом ничего. Если же что-то испортилось, то лучше отказаться от дальнейших опытов. Модифицированные прошивки, которые вы будете делать сами, прошиваются точно также.
Русификация ASUS N7600GS Silent 256
Так как BIOS видеокарт разных поколений и производителей может сильно различаться, для русификации каждого требуется свой подход. Далее идет подробное описание процесса русификации BIOS нескольких карточек, и вам нужно внимательно читать написанное и следовать принципу «делай, как я».
ASUS N7600GS Silent 256 (моя видеокарта, с которой все и начиналось) — относительно простой случай. Делаем первую копию, с оригинальной прошивки — new1.rom. Так нужно делать после каждого удачного шажка. Т.е. получилось что-то — копируем удачный new1.rom в new2.rom и дальнейшие опыты проводим уже с ним. Опять получилось — делаем new3.rom, и т.д. пока не дойдем до совершенства. Не получилось — безжалостно стираем неудачный файл и начинаем с предыдущего. Только так!!!
Итак, у нас есть new1.rom. Запускаем hiew и смотрим его дамп:
00000000: 55 AA 78 EB-4B 37 34 30-30 E9 4C 19-77 CC 56 49 UêxûK7400ùL w¦VI 00000010: 44 45 4F 20-0D 00 00 00-B8 00 19 11-00 00 49 42 DEO ¬ IB 00000020: 4D 20 56 47-41 20 43 6F-6D 70 61 74-69 62 6C 65 M VGA Compatible 00000030: 01 00 00 00-80 10 94 8D-30 32 2F 30-37 2F 30 37 À ÔÍ02/07/07 ============ 0000EFD0: FF FF FF FF-FF FF FF FF-FF FF FF FF-FF FF FF FF 0000EFE0: FF FF FF FF-FF FF FF FF-FF FF FF FF-FF FF FF FF 0000EFF0: FF FF FF FF-FF FF FF FF-FF FF FF FF-FF FF FF 9C Ü
Здесь нужно пояснить формат блока BIOS (любого «культурного», не только видеокарты, этот формат описан еще в первой документации на IBM PC):
* 0000: 55 AA — это сигнатура, если ее не будет, системный BIOS
проигнорирует этот блок: «БИ-БИ, это что ты мне подсунул?», и результатом будет черный экран; * 0002: ХХ — очень важный байт, счетчик размера блока BIOS; сам размер есть 512 х ХХ = от 512 байт до 128 Кб; * bububu: xx — последний байт блока, такой, чтоб контрольная сумма по модулю 256 всех байтов в блоке, заданном байтом 0002, равнялась нулю. Если контрольная сумма не нулевая, результат будет такой же, как и при неверной сигнатуре; * 0003: jmp туда-то — точка входа в BIOS, сюда передается управление системным BIOS по команде callf. Возврат из BIOS соответствующий — retf.
С анализа готового распакованного BIOS начинается самое интересное. Считывается он с адресов C0000h—XXXXXh утилитой grb. Она создает файл grb.bin там же, где лежит сама. Этот файл и есть образ рабочего (т.е. уже загруженного и настроенного) BIOS видеокарты. Естественно, что шрифты в нем уже распакованные. Поэтому нужно отыскать, где оные начинаются. В этом нам поможет тот факт, что обычно шрифты начинаются с размера 8х8, и первые два символа с кодами 00h & 01h стандартные, и их можно рассматривать как сигнатуру:
0000C442: 00 00 00 00-00 00 00 00-7E 81 A5 81-BD 99 81 7E ~ÁåÁ-ÙÁ~
Найдя ее и посмотрев окрестности, убеждаемся, мы действительно нашли нужную точку. Итак, шрифты распаковываются по адресу C442h. Открываем new1.rom и ищем ссылки на этот адрес (разумеется, она может быть не одна, и выбор нужной зависит исключительно от опыта и таланта хакера):
0000EDF8: 6660 pushad 0000EDFA: 0E push cs 0000EDFB: 1F pop ds 0000EDFC: 8D3642C4 lea si,[0C442] 0000EE00: C7069DED0703 mov w,[0ED9D],00307 ;" " 0000EE06: 8D3EE4DF lea di,[0DFE4] 0000EE0A: 8D2EBEE5 lea bp,[0E5BE] 0000EE0E: E8AEFF call 00000EDBF --- (1) 0000EE11: C7069DED0F04 mov w,[0ED9D],0040F ;" " 0000EE17: 8D3E11E6 lea di,[0E611] 0000EE1B: 8D2E4BED lea bp,[0ED4B] 0000EE1F: E89DFF call 00000EDBF --- (2) 0000EE22: 6661 popad 0000EE24: E95349 jmp 00000377A --- (3)
Вот оно! Очевидно, EDBFh — распаковщик, читающий упакованные шрифты с адресов DFE4h, E5BEh, E611h, ED4Bh и записывающий их на адрес C442h, а сам распаковщик лежит прямо за шрифтами. Хотя код вызывается с адреса CB7Fh, после распаковки управление передается безусловным jmp 377Ah, потому что вызвавший код будет затерт распакованными шрифтами.
Имеем: для русификации достаточно после штатной распаковки записать по адресу C442h наш шрифт. Шрифт можно позаимствовать из файла ega3.cpi или iso.cpi из комплекта операционных систем Microsoft (DOS/Windows 3.x/Windows 9x) или из других источников (например, из русификатора keyrus, чтобы получить его шрифты, выполните исполняемый файл как keyrus.com /files). Но вот как его записать в BIOS? Полный комплект шрифтов 8х8 + 8х16 занимает 6 Кб = 1800h, а у нас остаток пространства BIOS только 10000h – EE20h = 11E0h. Решений может быть несколько:
* записать половину шрифтов, символы с 80h по FFh (требуется C00h свободного места); * записать целиком новые шрифты поверх стандартных, сжав их и заменив распаковщик.
Для начала пробуем первый способ. Раздуваем BIOS до 64 Кб ровно (байт 0003 = 80h), записываем по адресам F000h половинки наших шрифтов (8х8, затем 8х16) и дополняем штатный распаковщик нашим:
0000EE22: cld 0000EE23: mov di,0c842 0000EE25: mov si,0f000 0000EE28: mov cx,00400 0000EE2a: repe movsb 0000EE2c: mov di,0d442 0000EE2e: mov si,0f400 0000EE30: mov cx,00800 0000EE32: repe movsb 0000EE34: popad 0000EE36: jmp 00000377A
Теперь нужно пересчитать контрольную сумму. Выделяем в блок весь файл, кроме последнего байта! Выбираем команду CryBlk, вводим:
1: add bl,al 2: loop 1
Запускаем, смотрим содержимое BL, вычисляем 100h-BL, записываем его вместо последнего байта (разумеется, потом мне это надоело, и я создал утилиту bsum, которая делает все это сама).
Прошиваем, перезагружаемся (не забудьте отключить имеющийся русификатор). Работает! Но вот беда — не все русифицировалось. Остались символы С, Ы, Э, Ю, л, м… Это не проблема! Копируем new1.rom в new2.rom, и дальше работаем уже с новым файлом. Ищем данные (откуда дровишки? Из лесу, вестимо…):
00002678: 1D 00 00 00-00 00 24 66-FF 66 24 00-00 00 00 00 $f f$
ссылку на них:
00003809: 0E push cs 0000380A: 07 pop es 0000380B: BF7826 mov di,02678 ;"&x" 0000380E: B710 mov bh,010 ;" " 00003810: C3 retn
и ссылку на этот код:
000040CF: E837F7 call 000003809 --- (1) 000040D2: 2ADB sub bl,bl 000040D4: E87FF7 call 000003856 --- (2) 000040D7: E80AF7 call 0000037E4 --- (3) 000040DA: EB0B jmps 0000040E7 --- (4) 000040DC: E8D1F6 call 0000037B0 --- (5) 000040DF: 893E0C01 mov [010C],di 000040E3: 8C060E01 mov [010E],es 000040E7: C3 retn
Жмем 2, и оказываемся в патчере:
00003856: 53 push bx 00003857: 55 push bp 00003858: 1E push ds 00003859: 06 push es 0000385A: 8BF7 mov si,di
Забиваем 53h на C3h, снова чиним контрольную сумму, прошиваем и наслаждаемся победой!
Как убрать эффект «столбов»
Для сведения, что это такое. Текстовыми наши режимы называются лишь по организации видеопамяти, т.к. области B800h & B000h (монохромный режим) хранят именно символы, а не их точечные изображения, как в графике. На экране изображение всегда состоит из точек. До VGA существовали еще видеоадаптеры MDA (качественный ч/б текст), CGA & EGA. Они поддерживали эффективные экранные разрешения соответственно 720х350, 640х200 и 640х350, а матрицы символов для них имели размер 9х14, 8х8 и 8х14 точек соответственно. Для совместимости (великое дело!) с EGA, впервые позволявшим программно загружать шрифты, в VGA использовали шрифт шириной 8 точек, но при этом разрешили видеорежимы 720х400 точек. В результате получили качественный текст, в котором использовались символы полной ширины, отпала необходимость оставлять 7-й бит для раздела букв, а дополнительный пробел между буквами получался автоматически.
Проблема «столбов» заключается в том, что т.н. символы заполнения B0h, B1h, B2h, используемые в псевдографике для немонолитной заливки фона, разрабатывались для CGA и пригодны лишь в случае, когда символы вплотную примыкают друг к другу. На VGA же автоматические пробелы между символами, так удобные в других местах, с успехом разделяют по горизонтали и символы заполнения, что и известно визуально как «эффект столбов». Прочие символы псевдографики VGA дорисовывает сам, а эти — нет, т.к. при этом все равно получатся столбы.
Проблема решается заменой стандартных матриц этих символов на специально подогнанные под режим VGA. При этом заливка становится монолитной во всех режимах шириной 720 точек, но эти столбы проявляются уже в CGA/EGA режимах или в любом графическом — там ведь нет автоматических разделителей! Впрочем, я сомневаюсь, что в графическом режиме заполнители вообще нужны.
Итак, подменяем матрицы символов B0h, B1h, B2h на следующие (8х16, матрица 8х8 есть половина матрицы 8х16):
B0 — 49 00 49 00 49 00 49 00 49 00 49 00 49 00 49 00 B1 — 92 49 92 49 92 49 92 49 92 49 92 49 92 49 92 49 B2 — DB 92 DB 92 DB 92 DB 92 DB 92 DB 92 DB 92 DB 92
После этого столбы исчезли. О шрифте 8х14
Как его увидеть? Переключиться в режим EGA:
MODE CON LINES=43 MODE CON LINES=25
Откуда он берется? Он автоматически генерируется из шрифта 8х16, обрезанием самой верхней и самой нижней строк. Поэтому, подбирая шрифт 8х16, заранее подумайте, как будет выглядеть получившийся из него шрифт 8х14. Он имеет обыкновение появляться в самый неподходящий момент, например, при переключении видеорежима в консоли Windows.