IPB

Добро пожаловать, гость ( Вход | Регистрация )

 
Reply to this topicStart new topic
> Локализация EXE, Изменение длины строковых констант в EXE
Siberian GRemlin
Jun 29 2007, 16:52
Сообщение #1


Advanced Member
***

Группа: CTPAX-X
Сообщений: 533
Регистрация: 4-February 08
Пользователь №: 2
Спасибо сказали: 221 раз(а)



Уважаемые.
Добрался я до той ситуации, когда необходимо изменить длину строк в EXE, в частности под DOS. Как я понимаю, в бинарнике есть таблица с адресами и если мне нужно изменить длину первой строки (считаем от начала бинарника) на один символ (байт), то необходимо в таблице увеличить все значения адресов на единицу, кроме самого первого адреса (в смысле, адреса первой строки). Единственное, что мне пока неизвестно, где находится эта таблица в бинарнике и как там идёт индексация, а также адресация и есть ли где-то значение размера этой таблицы?
Ещё в интернете ища информацию, натыкался на информацию о том, что существует прога для автоматического изменения текста с его длинной, ремаппингом и т.п., а также что люди сами писали подобные программы. Гипотетически это возможно, но как бы это выяснить...
Может кто-от посоветует какие-нибудь статьи по данному вопросу (локализации текстовых констант в ЕХЕ)

P.S.: Опытного человека, моё сообщение может показаться ламерским бредом... но хочется расти в творческом плане и в одиночку без глупых вопросов не обойтись.

P.P.S.: Я доделываю русскую локализацию одной игры.
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
-=CHE@TER=-
Jun 29 2007, 18:54
Сообщение #2


Walter Sullivan
***

Группа: Root Admin
Сообщений: 1,353
Регистрация: 4-February 08
Пользователь №: 3
Спасибо сказали: 311 раз(а)



QUOTE(Siberian GRemlin @ Jun 29 2007, 04:52 PM) *
P.P.S.: Я доделываю русскую локализацию одной игры.
Хех, я так понимаю Кирандию первую добиваешь? (*улыбается*)

Тут, ИМХО, проблема такая, что без полной декомпиляции игры ты её не решишь. Понимаешь, строка, скажем так, вшита в .EXE файл. Ты можешь только:
1) уменьшить её (забить неиспользуемые символы в конце нулями, а лучше, пробелами) и
2) изменить её не меняя её длинны
Всё. Увеличить длинну нельзя по одной простой причине: если ты увеличить строку на 1 байт - это значит, что ВСЕ конструкции-переходы (CALL, JMP, J*) в программе, которые ссылаются на адреса выше/ниже того места, где ты вставил байт, будут ссылаться на один байт раньше/позже того места, куда должны бы.

Проблема в том, что все инструкции перехода записываются как
инструкция и на_сколько_ ОТНОСИТЕЛЬНО_ТЕКУЩЕГО_АДРЕСА_перейти

Например:
jmp +5 // перейти на адрес на 5 байт после текущей инструкции
call -60 // перейти на адрес на 60 байт выше данной инструкции

Т.е. если ты всунул 1 байт между этими двумя командами, то:
1) jmp будет уже на +6
2) call будет уже -61

Я думаю, что писать дизассмеблер это муторно, да и отловить все такие ситуации очень и очень сложно. Это не просто изменить длинну строки - это, можно считать, переколбасить всю программу.
Более того, я тут разобрал самый простой случий, без всяких структур (представь, что твоя строчка входила в структуру, или после неё стояла структура, адрес которой загружался при помощи команды lea).

Моё скромное ИМХО: задача по удлинению строки, в общем случае, очень тяжёлая (если не сказать невыполнимая) и не факт, что после этого .EXE файл будет корректно работать.

Если уж очень хочется, то можно сделать такой, малооправданный, трюк ушами (геммор, правда, чуть меньший, чем с правкой всех адресов в предыдущем способе):
1) Написать свой загрущик для оригинального .EXE-файла (типа виндового "запустить процесс спящим")
2) Выделить в загруженной программе дополнительную память, куда пихать свои, русские, строки
3) Перебить в памяти адреса, откуда берутся оригинальные строки, на те, где находятся загруженные соответствующие им русские
4) Дать оригинальной программе дальше работать (типа "ResumeThread")
Хотя опять-таки, если строчка входила в структуру, то нужно менять и её размер...
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
Siberian GRemlin
Jun 30 2007, 04:15
Сообщение #3


Advanced Member
***

Группа: CTPAX-X
Сообщений: 533
Регистрация: 4-February 08
Пользователь №: 2
Спасибо сказали: 221 раз(а)



Да. Её родимую. =)
Сокращать строки не приемлимо - я лучше заплачу человеку, который в этом разбирается больше меня, чтобы он сделал. Если есть такие люди - пишите мне личное сообщение или на эл. почту, о цене договоримся.
Есть её, кажется, более спортивный способ, который пришёл мне в голову:
Сесть самому, но лучше с кем-нибудь и, открыв EXE в IDA, выписать все смещения до байт, которые нужно изменять при удлинении строк (смещения отностительно начала оригинального не исправленного ни кем ЕХЕ), потом написать программу, которая изменяет корректно строки в ЕХЕ по файлу инструкции, который мы создадим специально для неё (т.е. все адреса для изменения о которых я писал выше) и на выходе получаем новый ЕХЕ. Думаю будет проще сделать импорт строк из TXT, чем полноценный редактор, которому придётся ещё сохранять в какой-то отдельный файл на сколько в прошлый раз увеличили его размер и по каким адресам всякие условные и безусловные переходы и пр., иначе он корректно не откроет/изменит уже исправленный нами когда-то ЕХЕ.
Ещё как вариант у меня есть исправленная версия ЕХЕ под итальянскую локализацию, сделанную моим знакомым - строки на итальянском длиннее чем на английском, но не факт что все и + он там добавил какую-то фигню, что запускать приходится с параметром: MAIN.EXE -L, но тогда я обломаюсь с другими частями этой игры.
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
-=CHE@TER=-
Jun 30 2007, 12:20
Сообщение #4


Walter Sullivan
***

Группа: Root Admin
Сообщений: 1,353
Регистрация: 4-February 08
Пользователь №: 3
Спасибо сказали: 311 раз(а)



Siberian GRemlin!
А чем тебе не нравится SCUMM (там есть поддержка первой Кирандии)? Вряд ли, ИМХО, кто-то будет играть в Кирандию под чистый DOS...
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
Siberian GRemlin
Jul 2 2007, 05:04
Сообщение #5


Advanced Member
***

Группа: CTPAX-X
Сообщений: 533
Регистрация: 4-February 08
Пользователь №: 2
Спасибо сказали: 221 раз(а)



'Если хочешь, чтобы что-то было сделано хорошо - сделай это сам.' - древняя мудрость.

Не хочу зависеть от разработчиков какой-то непонятной проги, в которой поддержка 2 и 3 частей неизвестно в какой пятилетке будет...

Не успел несколько дней назад отписаться - инет кончился:
Отбой. Я придумал пару хитростей (просто повезло с тем что разработчики дублировали некоторые строки, а я указатели дубляжей перенаправил на первый встречающийся экземпляр, а оставшееся место использовал в свою усмотрение) + разобрался с IDA и даже умудрился научиться изменять размеры кнопок =)


Пока есть только 1 проблемка, когда адрес на начало строки пихается в стэк - push именно это и делает если я понимаю, только непонятно где там адрес сам, чтобы его сменить. Можно мне подсказать, если я покажу кусок кода на асме с этим моментом?
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
-=CHE@TER=-
Jul 2 2007, 07:11
Сообщение #6


Walter Sullivan
***

Группа: Root Admin
Сообщений: 1,353
Регистрация: 4-February 08
Пользователь №: 3
Спасибо сказали: 311 раз(а)



QUOTE(Siberian GRemlin @ Jul 2 2007, 05:04 AM) *
Пока есть только 1 проблемка, когда адрес на начало строки пихается в стэк - push именно это и делает если я понимаю, только непонятно где там адрес сам, чтобы его сменить. Можно мне подсказать, если я покажу кусок кода на асме с этим моментом?
Пустил MAIN.EXE под IDA, что-то там куча строк, которые она даже не распознала - т.е. на них нет прямого указателя. Такое ощущение, что они там через базу+смещение до нужной строки, работают. На ту же строчку "Yes" я нигде явной ссылки не нашёл. Что-то я не там ищу что-ли?
Можешь, конечно, выложить код, но там не должно быть ничего сложного:
- если твоя новая строчка находится раньше старой, то просто считаешь между ними разницу и отнимаешь от того числа, которое суётся в стэк
- если строчка находится позже оригинальной - проделываешь всё тоже самое, только прибавляешь к число разницу
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
Siberian GRemlin
Jul 2 2007, 09:43
Сообщение #7


Advanced Member
***

Группа: CTPAX-X
Сообщений: 533
Регистрация: 4-February 08
Пользователь №: 2
Спасибо сказали: 221 раз(а)





Вот смотри, возьмём строчку "The poison..." её легко найти. Справа есть стрелочка, как я понял, ведущая туда где ?первый? раз обращаемся к ней. Как видно в подсказке, там как раз изврат, но думаю ты сам туда перейдёшь и посмотришь. Вот как там менять адрес, указывающий на начало строки?

В большинстве же случаев всё гораздо проще, как чуть ниже на снимке, например строчки как "The flask is now filled.....", там смотрим и видим просто указатель на эту строку, который и меняем на новый, после изменения длин строк.

P.S.: Ещё меня очень сильно угнетает, что в Hex View-A (16ричный режим просмотра) слева вместо стандартного смещения, какая-то хрень, типа dseg:####, ovr###:#### и т.п.
Можно сделать отображение смещений привычное глазу моему? =)

P.P.S.: Я завершил изменение размеров менюшек - всё вообще красиво теперь смотрится! 8 ) Никогда не думал, что я до такого дойду, но очень мечтал! Ура! =)

P.P.P.S: Есть ещё одна задачка - выставить показ текста в CD версии по умолчанию как в Floppy версии, а то получается, что вступление без вывода текста... Придётся пинать одного хакера знакомого, который всегда занятой.
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
-=CHE@TER=-
Jul 2 2007, 15:18
Сообщение #8


Walter Sullivan
***

Группа: Root Admin
Сообщений: 1,353
Регистрация: 4-February 08
Пользователь №: 3
Спасибо сказали: 311 раз(а)



Так, у тебя какая версия IDA? У меня IDA Pro Adv 4.8.0.847 и у меня эти строчки вообще как данные - т.е. там даже ссылок на их начало нет. Юзал на .EXE файле, который ты мне когда-то присылал, от оригинальной, английской версии. Сейчас ещё попробую IDA новую достать...
А "DATA HREF" - это тебе IDA подсказывает с какого места на эту константу ссылаются.
Наведи курсор или щёлкни мышкой по "aThePoison___" и нажми X - появится список мест кода, где идёт ссылка на эту строку. Щёлкаешь два раза по любому - и тут же туда переходишь. Вот там тебе адрес и нужно менять.

Насчёт смещений - не знаю. Никогда не требовалось, а если и требовалось, то по коду искал. (*улыбается*)
BTW, dseg:#### - это данные (сегмент данных), ovr### - это оверлей (если заметил - странный кусок в хвосте .EXE).
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
Siberian GRemlin
Jul 2 2007, 23:03
Сообщение #9


Advanced Member
***

Группа: CTPAX-X
Сообщений: 533
Регистрация: 4-February 08
Пользователь №: 2
Спасибо сказали: 221 раз(а)



У меня такая же IDA, хотя вчера нашёл в локальной сети дистрибутив 5.0
Вот файл от той версии, что надо =)

_http://upload.siberianet.ru/download.php?file=816KyraCDEng.rar
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
-=CHE@TER=-
Jul 3 2007, 08:21
Сообщение #10


Walter Sullivan
***

Группа: Root Admin
Сообщений: 1,353
Регистрация: 4-February 08
Пользователь №: 3
Спасибо сказали: 311 раз(а)



QUOTE(Siberian GRemlin @ Jul 2 2007, 11:03 PM) *
У меня такая же IDA, хотя вчера нашёл в локальной сети дистрибутив 5.0
Вот файл от той версии, что надо =)

_http://upload.siberianet.ru/download.php?file=816KyraCDEng.rar
Хе, а это другой .EXE. Он даже на 10 Кб толще. Видимо, тот что ты мне раньше высылал какой-нибудь заломанный был.
В ближайшее время ещё раз гляну.
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
Siberian GRemlin
Jul 3 2007, 12:06
Сообщение #11


Advanced Member
***

Группа: CTPAX-X
Сообщений: 533
Регистрация: 4-February 08
Пользователь №: 2
Спасибо сказали: 221 раз(а)



Прошлый был от Floppy версии, я перевожу полную CD которая была улучшена и издана на год позже, вместе с озвучкой, которой в Floppy не было по определению. =)
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
-=CHE@TER=-
Jul 3 2007, 16:40
Сообщение #12


Walter Sullivan
***

Группа: Root Admin
Сообщений: 1,353
Регистрация: 4-February 08
Пользователь №: 3
Спасибо сказали: 311 раз(а)



Понятно. Хотя этот .EXE файл тоже не лучше - на строчку "Yes" я тоже ссылки не нашёл...
Ну, ладно.
Так вот, насчёт строчки "aThePoison___" - щёлкаешь на ней мышкой, чтобы она подсветилась. Затем на клавиатуре жмёшь X (английская "икс"). В появившемся окне два раза кликаешь на смещение.
Попадаешь примерно на такой вот код:
CODE
ovr136:002C                 add     sp, 4
ovr136:002F                 push    0FFFEh         ; int
ovr136:0031                 push    0              ; char
ovr136:0033                 push    ds
ovr136:0034                 push    offset aThePoison___; "The poison..."
ovr136:0037                 push    1B58h          ; int
ovr136:003A                 call    sub_B6DA

Теперь кликаешь по "offset aThePoison___" и, затем, сверху на вкладку "HEX-View A" - там выделится вся эта команда их трёх байт: 68 5A 0F. Так вот - 52 0F, вернее $0F5A - это как раз смещение до строки (68 - это, похоже, код команды PUSH WORD). Его и меняешь, на какое тебе нужно (заметь, что это смещение относительно начала ТЕКУЩЕГО оверлея - т.е. на строчку в другом оверлее ты просто не сможешь указатель сделать).
Твоя строчка и находится там:
CODE
dseg:0F5A; char aThePoison___[]

Видишь - 0F5A - вот этот адрес там и записан. Менять можно через любой HEX редактор. Я обычно ищу последовательность байт (например 00 1E 68 5A 0F), смотрю чтобы она находилась одна (чтобы не перепутать с другим кодом) и потом меняю что нужно.
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
Siberian GRemlin
Jul 4 2007, 04:50
Сообщение #13


Advanced Member
***

Группа: CTPAX-X
Сообщений: 533
Регистрация: 4-February 08
Пользователь №: 2
Спасибо сказали: 221 раз(а)



QUOTE(-=CHE@TER=- @ Jul 4 2007, 12:40 AM) *
Понятно. Хотя этот .EXE файл тоже не лучше - на строчку "Yes" я тоже ссылки не нашёл...

А мне почему-то думается, что IDA игнорирует короткие строчки и не вносит их в список. Я, например, эти строчки искал так: посмотрел в TotalCmd какие рядом есть подлиннее - кажись "Main menu", в списке перешёл к нему и в коде уже нормально копался с ней и с короткими возле неё.

А можно определение Overlay'я? rolleyes.gif

P.S.: Спасибо большое. Моя жизнь стала ещё прекраснее и я теперь смогу сделать перевод ещё лучше!
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
Siberian GRemlin
Jul 4 2007, 08:11
Сообщение #14


Advanced Member
***

Группа: CTPAX-X
Сообщений: 533
Регистрация: 4-February 08
Пользователь №: 2
Спасибо сказали: 221 раз(а)



Я тут колупался. В итоге удалось изменить длины строк, по указанному тобой способу, но не все. например, я изменил длины строк:
"Amazing!"
"The effects of the poison are gone!"
"It's a jewel, but why is it black?"
и других из того куска кода.

Но во втором куске кода, где лежат 4 строчки, которые мне надо изменить:
"The poison..."
"I can't breathe..."
"I don't feel so good..."
"That snake must be poisonous!"

Делаю как в предыдущем блоке, т.е. как ты писал, но игре вообще пофиг на это. Я ещё случайно столкнулся с проблемой (точнее не с проблемой а так) - ну случайно по глупостью, когда ошибся смещением на 1 и вместо адреса сменил байт $68, т.е. команду push и после этого игра при попытки загрузить игру выдавала ошибку, что мол сохранёнка от другой игры, я свою оплошность ясень пень исправил... суть в том, что даже если поменять все байты в окрестности адреса до начала строчки "I don't feel so good...", то и даже так игре всё пофигу, она нормально загружает сохранёнки и отображает строки начиная с того адреса, как и было в оригинале. Где собака зарыта? Может есть подводные камни?

P.S.: Я решил методом тыка перебрать где это может быть и нашёл все места где встречается $680F т.е. адрес до строчки "I can't breathe...", его я взял из того места где push, т.е. байты $68680F, изменение которых ни к чему не приводит. Но перебирать 30 мест в файле очень геморойно =(
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
-=CHE@TER=-
Jul 4 2007, 09:26
Сообщение #15


Walter Sullivan
***

Группа: Root Admin
Сообщений: 1,353
Регистрация: 4-February 08
Пользователь №: 3
Спасибо сказали: 311 раз(а)



QUOTE(Siberian GRemlin @ Jul 4 2007, 04:50 AM) *
А можно определение Overlay'я? rolleyes.gif
Если с английским хорошо - вот тут есть описание/определение оверлея. Ещё могу такую цитату привести:
QUOTE
Блоки модуля Overlay понадобятся при разработке громоздких программ с перекрытиями (позволяет хранить в памяти только нужные части программы, а не требующиеся на данный момент удалять из памяти, сохраняя на диск, либо возвращать в память при необходимости).
Короче, это, по сути, кусок программы, который загружается в память, ему передаётся управление, он отрабатывает свою часть и, затем, завершает работу и выгружается из памяти (я так понимаю, это предтеча .DLL). В DOS это позволяет сильно съэкономить память, т.к. у тебя не вся программа в оперативке одновременно находится, а только её части. Насколько мне известно, в Windows оверлеи не применяются вообще (там даже такого механизма нет). Обычно оверлеи валяются в каталоге программы с расширением .OVR, но могу быть приделаны в хвост главного .EXE файла.


QUOTE(Siberian GRemlin @ Jul 4 2007, 08:11 AM) *
Где собака зарыта? Может есть подводные камни?
Не забывай, что ты изменяешь адрес начала строки. Строка, в свою очередь, кончается символом $00 на конце (ASCIIZ-строки). Т.е. длина строки считается как количество байт с адреса начала, до первого символа $00. Длина строки нигде не должа задаваться явно (если только где-нибудь временный буфер для пересылки жёстко не ограничен каким-нибудь значением).
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
Siberian GRemlin
Jul 4 2007, 15:10
Сообщение #16


Advanced Member
***

Группа: CTPAX-X
Сообщений: 533
Регистрация: 4-February 08
Пользователь №: 2
Спасибо сказали: 221 раз(а)



QUOTE(-=CHE@TER=- @ Jul 4 2007, 05:26 PM) *

Не забывай, что ты изменяешь адрес начала строки. Строка, в свою очередь, кончается символом $00 на конце (ASCIIZ-строки). Т.е. длина строки считается как количество байт с адреса начала, до первого символа $00. Длина строки нигде не должа задаваться явно (если только где-нибудь временный буфер для пересылки жёстко не ограничен каким-нибудь значением).

Это как бы не ответ на мой вопрос.
В моём patch'е в зависимости от новой длинны строки к адресу следующей прибавляется положительное либо отрицательное число.
Суть проблемы в том, что именно в том месте какие-либо изменения почему-то игнорируются. Что выглядит неправдоподобно.
P.S.: Либо я дурак, либо одно из двух.
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
-=CHE@TER=-
Jul 4 2007, 16:15
Сообщение #17


Walter Sullivan
***

Группа: Root Admin
Сообщений: 1,353
Регистрация: 4-February 08
Пользователь №: 3
Спасибо сказали: 311 раз(а)



QUOTE(Siberian GRemlin @ Jul 4 2007, 03:10 PM) *
Это как бы не ответ на мой вопрос.
Тогда ставь вопрос более корректно - чтобы тебя сразу поняли. (*улыбается*)

QUOTE(Siberian GRemlin @ Jul 4 2007, 03:10 PM) *
В моём patch'е в зависимости от новой длинны строки к адресу следующей прибавляется положительное либо отрицательное число.
Суть проблемы в том, что именно в том месте какие-либо изменения почему-то игнорируются. Что выглядит неправдоподобно.
P.S.: Либо я дурак, либо одно из двух.
Хорошо, а если поменять только это место и больше ничего не трогать - всё работает?
User is offlineProfile CardPM
Go to the top of the page
+Quote Post
Bourn
Sep 2 2008, 18:22
Сообщение #18


Незарегистрирован









Все просто - находим пустой адрес(можно и конец ехе), хотя если место особождается от уменьшение одной текстовой константы - его можно использовать для другой, ну и конечно если ехе не юзает секции - тогда проще(если сплошной код, а в конце кода константы, асм компилеры так генерят...)
Go to the top of the page
+Quote Post

Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0 -

 



Упрощённая версия Сейчас: 28th March 2024 - 19:26