Пятница, 01.11.2024, 6:41 AM
 
Главная Регистрация Вход
Приветствую Вас, Гость · RSS
Меню сайта
Категории каталога
Общие вопросы [25]
Прошивки и прочее [10]
Настройки и функции Операторов [2]
Неисправности и глюки [2]
FAQ по софту [1]
Статьи и руководства по пользованью разнообразных ПК-программ для работы с мобильными телефонами.
Мини-чат
Наш опрос
Чего не хватает на сайте?
Всего ответов: 49
 FAQ, Характеристики
Главная » Статьи » FAQ » Общие вопросы

Как самому стать патчером? (Siemens x65-x75)
1. Предыстория.

В Мае понял, что мой S55 морально устарел и решил брать новый телефон. Сразу понял, что это будет Сименс. Вот только какой? Не A, не CX, не M65 – т.к. там нет Bluetooth. Долго колебался между S65 и SK65. И выбрал последний (мне камера в телефоне не нужна, да и кнопки на S65 не очень). Надо сказать, выбери я все-таки S65, наверно и не знал бы сейчас ничего про программирование под телефоны.

Остался сильно доволен своей покупкой, огорчился было сначала, что прошивка 34, но потом понял, что патчи ставить можно. И вот тут настало сильное разочарование. Патчей под мой телефон оказалось совсем мало – а те, что были, в основном, сгенерированы Смелтером. А я привык к их обилию на S55. Вот тут-то и родилось желание сделать что-то самому.

2. Мои первые шаги.

В начале Июля начал искать в Интернете информацию, как стать патчером. В итоге наткнулся на 2 форума: siemens-club и allsiemens. Выбрал я сименс-клаб, потому что здесь есть раздел «Патчи для SK65» :). Но как копаться в фф на самом-самом начальном уровне я научился после прочтения темы на allsiemens.com.

Итак, я вооружился Win-Hex’ом, IDA и открыл свой фф. Открыл – и ничего почти не понял. Точнее понял, что надо учить ассемблер. В итоге числа 15 случайно наткнулся на справочник по ассемблеру для компа. Почитал вступление и немного понял принципы работы процессора.

И тут, еще до прочтения справочника, я портанул первый патч! Это был патч на отключение сообщений о вкл/выкл GPRS и Bluetooth (Смелтер генерирует их неправильно для моего телефона). Посмотрел, что меняются данные 32F1 на 80BD. Пошел в фф по адресу патча на откл. сообщений о вкл/выкл IrDA. Посмотрел чуть дальше и нашел те самые 32F1. Заменил на 80BD. Все заработало!

Но посмотрев на другие патчи, понял, что простым поиском исходной строки и ее замены не обойтись. Пытался посмотреть, что делают некоторые патчи, но в IDA получал какие-то непонятные команды (типа, BL 0x90000000 – таких адресов-то нет, кстати адреса в прошивке начинаются с A0xxxxxx или A1xxxxxx). Спросил у avkiev’а и узнал, что есть две кодировки команд – ARM и Thumb. Чтобы переключиться между ними, надо в IDA нажать Alt+G и написать «0», если переходим в ARM, а «1», если – в Thumb. В патчах чаще всего используется Thumb. И вот когда я это понял, понеслась!

3. Мои первые порты.

Первым более серьезным патчем был «Расширенный список вызовов». Но его я портанул с исходника – это не интересно. Рассмотрим патч «Черный/Белый список».

Сначала настроим IDA. Идем в Options->General и ставим в поле Number of opcode bytes цифру «4». Далее, открываем папку, куда установлен IDA. Идем в папку cfg. Открываем idagui.cfg. Ищем строчку DISPLAY_PATCH_SUBMENU и ставим после знака равно «YES». Ищем строку "PatchByte", раскомментируем ее и ставим справа любую кнопку, я сделал у себя так:

"PatchByte" = "i"

Все, вроде настроили. Как открыть фф, думаю, вы уже знаете, если что, можно посмотреть на allsiemens.com.
Вот этот патч для M65:
...
...
...
©SiNgle

0B137BC: 06D1 0028
0B137C0: 04D1 0028
0B13C0E: B0420ED1 CAF178ED
#pragma enable old_equal_ff
0CDE700: 00402DE9060050E10500001AFF3F2DE9
0CDE710: 0FE0A0E10CF09FE5FF3FBDE80040BDE8
0CDE720: 04F09FE50080BDE8993BB4A0313CB1A0
#pragma disable old_equal_ff
1289627: D5 E0
;0CDE70B: 1A 0A ;белый список (white list)
...
...
...
Брал я фф от M65. Сначала ищем энтрипоинт (точку входа).
0B13C0E: B0420ED1 CAF178ED
...
...
...
Идем в фф от M65 по этому адресу. Вот, что мы видим:

ROM:A0B13C0E B0 42 CMP R0, R6
ROM:A0B13C10 0E D1 BNE loc_A0B13C30
ROM:A0B13C12 20 78 LDRB R0, [R4]
ROM:A0B13C14 04 28 CMP R0, #4
ROM:A0B13C16 02 D1 BNE loc_A0B13C1E
ROM:A0B13C18 09 20 MOV R0, #9
ROM:A0B13C1A 10 AB ADD R3, SP, #0x40
ROM:A0B13C1C 18 72 STRB R0, [R3,#8]
ROM:A0B13C1E
ROM:A0B13C1E loc_A0B13C1E ; CODE XREF:
ROM:A0B13C1E 10 AB ADD R3, SP, #0x40
ROM:A0B13C20 18 7A LDRB R0, [R3,#8]
...
...
...
Так как программная основа у всей серии x65 практически одинаковая, то на моем SK65 тоже есть такой кусок программного кода. Надо его найти. Единственное, команды Bxx (B, BL, BLX), а также команда LDR чаще всего «непостоянны» (т.е. в других телефонах они выглядят не совсем так). Открываем фф SK65 в WinHex’е и врубаем поиск шестнадцатеричных значений. Ставим маску 3F (это те байты, которые мы не знаем, т.е. вместо этого значения может быть любой байт), и пишем в строке поиска B0423F3F207804283F3F092010AB1872, здесь я вместо 0ED1 и 02D1 я написал 3F3F, т.к. в SK65 вполне могут быть другие значения (т.к. это функции бранча, т.е. Bxx). Находим нужный адрес в конечном фф (от SK65). Если найдено несколько адресов, то надо попробовать увеличить строку поиска (т.е. дописать туда еще 10AB187A). Если так не получается, то тут уж надо анализировать каждый адрес (открывать его в IDA). Для SK65 это адрес 07093F6. А теперь проверим на всякий случай. Идем в фф SK65 по этому адресу, жмем ‘C’ и видим:
...
...
...
ROM:A07093F6 B0 42 CMP R0, R6
ROM:A07093F8 0E D1 BNE loc_A0709418
ROM:A07093FA
ROM:A07093FA loc_A07093FA ; CODE XREF: ROM:A07093E8j
ROM:A07093FA 20 78 LDRB R0, [R4]
ROM:A07093FC 04 28 CMP R0, #4
ROM:A07093FE 02 D1 BNE loc_A0709406
ROM:A0709400 09 20 MOV R0, #9
ROM:A0709402 10 AB ADD R3, SP, #0x40
ROM:A0709404 18 72 STRB R0, [R3,#8]
ROM:A0709406
ROM:A0709406 loc_A0709406 ; CODE XREF: ROM:A07093FEj
ROM:A0709406 10 AB ADD R3, SP, #0x40
ROM:A0709408 18 7A LDRB R0, [R3,#8]
...
...
...
Ура! Мы попали в цель. В данном случае на командах Bxx значения байт такие же, но помните, они могут иногда меняться, поэтому вместо них ставьте всегда ‘3F’.

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

Теперь беремся собственно за тело патча (те строки, которые пишутся вместо FF). Идем в исходном фф (от M65) по адресу патча, нажимаем «I» (или какую-либо другую кнопку, которую мы выставили в настройках в строке «Patch Byte»). В появившемся окошке вводим строки патча, только ставим пробел через каждые 2 символа (т.е. каждый байт пишем отдельно). И так для каждой строки патча (всего в данном патче их 3). Есть альтернативный способ: с помощью скриптов от AlexSid. Нажмите File->IDC file…, выберите файл Apply Patch.idc, затем в открывшемся окошке выберите патч (он должен быть НЕ в rtf формате) и нажмите “Open”, а затем при запросе скрипта нажмите “Yes”. Теперь идем в начало патча (адрес 0xA0CDE700), нажимаем Alt+G, ставим «0» (этот патч написан в кодировке ARM). Нажимаем «C» и видим следующее:
...
...
...
ROM:A0CDE700 ; ---------------------------------------------------------------------------
ROM:A0CDE700 00 40 2D E9 STMFD SP!, {LR}
ROM:A0CDE704 06 00 50 E1 CMP R0, R6
ROM:A0CDE708 05 00 00 1A BNE locret_A0CDE724
ROM:A0CDE70C FF 3F 2D E9 STMFD SP!, {R0-SP}
ROM:A0CDE710 0F E0 A0 E1 MOV LR, PC
ROM:A0CDE714 0C F0 9F E5 LDR PC, =unk_A0B43B99
ROM:A0CDE718 FF 3F BD E8 LDMFD SP!, {R0-SP}
ROM:A0CDE71C 00 40 BD E8 LDMFD SP!, {LR}
ROM:A0CDE720 04 F0 9F E5 LDR PC, =(loc_A0B13C30+1)
ROM:A0CDE724 ; ---------------------------------------------------------------------------
ROM:A0CDE724
ROM:A0CDE724 locret_A0CDE724 ; CODE XREF: ROM:A0CDE708j
ROM:A0CDE724 00 80 BD E8 LDMFD SP!, {PC}
ROM:A0CDE724 ; ---------------------------------------------------------------------------
ROM:A0CDE728 99 3B B4 A0 off_A0CDE728 DCD unk_A0B43B99 ; DATA XREF: ROM:A0CDE714r
ROM:A0CDE72C 31 3C B1 A0 off_A0CDE72C DCD loc_A0B13C30+1 ; DATA XREF: ROM:A0CDE720r
...
...
...
Смотрим, что тут собственно происходит и понимаем, что есть 2 ссылки на ВНЕШНИЕ функции, а эти ссылки надо бы изменить (т.к. в SK65 эти функции находятся по другим адресам).
Итак первый адрес 0xA0B43B99. Здесь в конце стоит 9, а не 8, т.к. эта функция написана в Thumb’е. Нажимаем «C» по адресу 0xA0B43B98 (предварительно «Alt+G» и пишем «1»), смотрим:
...
...
...
ROM:A0B43B98 08 B5 PUSH {R3,LR} ; CODE XREF: ROM:A0CDE714j
ROM:A0B43B98 ; DATA XREF: ROM:off_A0CDE728o
ROM:A0B43B9A 00 22 MOV R2, #0
ROM:A0B43B9C 13 1C ADD R3, R2, #0
ROM:A0B43B9E 82 21 MOV R1, #0x82
ROM:A0B43BA0 00 92 STR R2, [SP]
ROM:A0B43BA2 20 48 LDR R0, =0x4211
ROM:A0B43BA4 E3 F4 AE EF BLX sub_A0827B04
ROM:A0B43BA8 08 BD POP {R3,PC}
...
...
...
Ищем следующую строку 08 B50022131C8221009220483F3F3F3F08BD.
Я нашел ее по адресу 0xA075D8A8. Смотрим туда:

ROM:A075D828 08 B5 PUSH {R3,LR}
ROM:A075D82A 00 22 MOV R2, #0
ROM:A075D82C 13 1C ADD R3, R2, #0
ROM:A075D82E 82 21 MOV R1, #0x82
ROM:A075D830 00 92 STR R2, [SP,#8+var_8]
ROM:A075D832 20 48 LDR R0, =0x4211
ROM:A075D834 98 F1 BC EC BLX sub_A08F61B0
ROM:A075D838 08 BD POP {R3,PC}

Тут как раз видно то, о чем я говорил – внимательно посмотрите на адреса ROM:A0B43BA4 в M65 и ROM:A075D834 в SK65 – там стоят разные байты.

Переворачиваем байты нашего адреса и не забываем прибавить в конце единичку (т.к. Thumb). Получаем 29D875A0. Далее ищем вторую функцию по аналогии (попробуйте сами в качестве тренировки). Соответственно, заменяем адреса в конце тела патча полученными. Теперь надо найти место, куда воткнуть патч. Надо искать пустые блоки (где стоят сплошняком FF’ы), причем важно помнить, что ссылки по «бранчам» (функциям Bxx) действительны только в пределах +-4Mb или 0x400000. Нам надо дотянуться до патча с адреса 07093F6, поэтому мы его можем воткнуть в пределах 0x03093F6-0x0B093F6. Обычно патчи втыкают туда, где много свободного места, т.е. где в WinHex’е несколько страиц одни FF’ы. В указанных мной пределах я столько места не нашел, поэтому пришлось вставлять патч туда, где мало места, но ничего – хватило. Воткнул я сюда: 0473D00.

Ну и последнее: нам надо вызвать тело патча. То есть надо выполнить по адресу 0x07093F6 процедуру BLX 0x0473D00 (тут именно BLX потому, что в исходном сегменте команды написаны в Thumb’е, а нам надо перейти в ARM). Чтобы знать, что вписать, можно воспользоваться прогой ABraGen (но она у меня глючит), можно – дебаггером, но лучше всего - написать свою микропрограмму в Keil ARM. Так я вышел именно на строку 6AF584EC.

Вот конечный вариант порта:

0708FA4: 06D1 0028
0708FA8: 04D1 0028
07093F6: B0420ED1 6AF584EC
#pragma enable old_equal_ff
0473D00: 00402DE9060050E10500001AFF3F2DE9
0473D10: 0FE0A0E10CF09FE5FF3FBDE80040BDE8
0473D20: 04F09FE50080BDE829D875A0199470A0
#pragma disable old_equal_ff
09F96CF: D5 E0
;0473D0B: 1A 0A ;белый список (white list)

Сравни с оригиналом:

0B137BC: 06D1 0028
0B137C0: 04D1 0028
0B13C0E: B0420ED1 CAF178ED
#pragma enable old_equal_ff
0CDE700: 00402DE9060050E10500001AFF3F2DE9
0CDE710: 0FE0A0E10CF09FE5FF3FBDE80040BDE8
0CDE720: 04F09FE50080BDE8993BB4A0313CB1A0
#pragma disable old_equal_ff
1289627: D5 E0
;0CDE70B: 1A 0A ;белый список (white list)

Как видите – отличия только в адресах, в вызове патча и в последних 8 байтах тела патча.

4. Мой первый патч.

Теперь немного про мой патч. Его я делал на основе патча “Read SMS while keyboard locked”. Вот его оригинал:

;source for keil

$arm9e

HasNewSMS EQU 0xA0990660+1
HasFlashSMS EQU 0xA0935DB8+1
ReadNewSMS EQU 0xA0A2DBF8
ReadFlashSMS EQU 0xA098F63E+1
TempLigntOn EQU 0xA0B2C364+1
SetScreenSaver EQU 0xA0936A32+1

AREA STARTUPCODE, CODE
CODE16

Main:
PUSH {R6, LR}
MOV R6, #0
CMP R0, #05
BNE ExitOrg
BL HasFlashSMS
CMP R0, #1
BEQ ReadFlash
BL HasNewSMS
CMP R0, #1
BNE ExitOrg
ReadSMS:
MOV R0, #3
BL TempLigntOn
LDR R0, =ReadNewSMS
BLX R0
MOV R6, #2
B ExitOrg
ReadFlash:
MOV R0, #3
BL TempLigntOn
BL ReadFlashSMS
MOV R6, #1
ExitOrg:
ADD R0, R6, #0
POP {R6, PC}

Hook1:
MOV R3, #2
LDRSH R0, [R5,R3]
PUSH {LR}
BL Main
CMP R0, #0
BNE Hook1NewExit
BL 0xA08D9D5C ;Org Ins
POP {PC}
Hook1NewExit:
ADD SP, #4
LDR R1, =0xA08DAE28+1 ;return after processed
BX R1

Hook2:
MOV R3, #2
LDRSH R0, [R4,R3]
PUSH {R0, LR}
BL Main
CMP R0, #0
BNE Hook2NewExit
POP {R0, PC}
Hook2NewExit:
ADD SP, #8
CMP R0, #2
BNE Hook2Exit
MOV R0, #0
BL SetScreenSaver ;0 Leave screensaver
Hook2Exit:
LDR R1, =0xA09909FA+1 ;return after processed
BX R1

; Hook keyhandle of IDLE
AREA HOOK1, CODE, AT 0xA08DAEC6
CODE16
BL Hook1

; Hook KeyHandle of ScreenSaver
AREA HOOK2, CODE, AT 0xA099090E
CODE16
BL Hook2

END

Как видите, здесь идет ссылка на процедуру Hook1 (если залоченная клава) или Hook2 (если скринсейвер). Далее вызывается функция Main. Ее я чутка поменял. Видите, в регистре R0 содержится код нажатой кнопки. Далее идет его сравнение с числом 5 (это зеленая кнопка – полный список см. в теме «Обсуждение патча Говорящий Телефон»). Если в регистре НЕ число 5 (BNE – Branch if Non Equal), то идет ссылка на функцию выхода (ExitOrg), если же оно – то идем далее, идет проверка на наличие входящих непрочитанных СМС и флеш-СМС, если их нет, опять идем на ExitOrg. Если есть – вызывается встроенная в прошивку функция просмотра входящих СМС, а далее идем на все тот же ExitOrg. Что у нас в функции выхода? А там мы заносим в регистр R0 содержимое регистра R6 (если в R0 будет НОЛЬ, то будет показываться экранчик «Блокировка клавиатуры вкл, нажми #, чтобы вырубить», а если ЕДИНИЦА – то не будет). Далее идет команда pop {PC}. Этой командой мы возвращаемся к команде, вызвавшей функцию Main (т.е. дальше по функциям Hook1 и Hook2). Там уже вызываем замененную вызовом патча функцию и еще что-то (честно говоря, так еще и не понял что). Команды push и pop связаны с понятием СТЕК. Чтобы понять что это приведу пример П. Нортона. Представьте себе машину для мойки тарелок. Мы кладем тарелку наверх, на другие тарелки, потом сверху кладем еще несколько тарелок. Далее они помылись и мы забираем тарелки, причем ПЕРВАЯ тарелка, которую мы возьмем, будет ПОСЛЕДНЕЙ, положенной в машину. Т.е. действует правил «Последним вошел – первым вышел». Команда push «кладет» содержимое регистра в стек, а команда pop «вынимает» его оттуда.

Итак, что сделал я? Сначала (в версии 2 – версию 1 можно не вспоминать smile ) я просто заменил выход из патча при отсутствии входящих СМС на вызов проговаривания времени, примерно вот так:

Main:
PUSH {R6, LR}
MOV R6, #0
CMP R0, #05
BNE ExitOrg
BL HasFlashSMS
CMP R0, #1
BEQ ReadFlash
BL HasNewSMS
CMP R0, #1
BNE ReadTime



ReadTime:
BL 0x019D520 ;это у меня адрес функции проговаривания времени
B ExitOrg ;выход

Потом я пошел дальше и решил, что буду делать патч на основе буфера настройки (как у avkiev’а в патчах «Ежечасные события» и «Динамический провайдер»). Стал по его исходникам разбираться, как с ним (с буфером) работать. Делается это так:

PUSH {R4} ;заносим в стек регистр R4, т.к. он где-то еще используется
CMP R0, #1
BEQ Krasnaja_Knopka
CMP R0, #5
BEQ Zelenaja_Knopka
… ;делаем проверку нажатой кнопки и заносим в регистр R4 СМЕЩЕНИЕ в буфере (т.е. например, если нажата красная кнопка – то это 0, если зеленая – то 1 (это можно самому сделать как хочешь – т.е. можно и наоборот))
Krasnaja_Knopka:
MOV R4, #0 ;в регистр R4 пишем смещение в буфере, здесь оно равно 0
B Continue ;идем дальше
Zelenaja_Knopka:
MOV R4, #1 ;здесь смещение 1
B Continue ;идем дальше



AdrReg 3, aBuffer ;адресуем регистр R3 в наш буфер (здесь выбран он, т.к. он не используется в патче и в процедурах телефона рядом с той, из которой мы вызывали патч)
LDRB R0, [R3, R4] ;теперь регистр R0 нам не нужен (кнопку мы вычислили), заносим в него байт в буфере (команда LDRB; а можно в принципе и в R3 – тогда будет LDRB R3, [R3, R4]), находящемся по адресу, прописанному в R3, и по смещению, количественно равному значению R4. Надеюсь, понятно объяснил… Все, теперь в R0 у нас нужный байт, так что теперь делаем проверку, что же это за байт и вызываем нужную функцию.
;В конце патча надо дописать сам буфер:
aBuffer: dd 0x01, 0x0AB, 0x00…

Конечно, написал я тут про патч версии 7.5, хотя уже есть более поздние версии, но для получения начальных представлений, я думаю, и его сойдет.

5. Заключение.

Ну вот, собственно, все, что я хотел написать. Конечно, этот материал рассчитан на человека, понимающего немного в программировании, однако даже если вы не обладаете такими знаниями, помните – главное – это желание научиться.

Если будут какие-то вопросы – не стесняйтесь – задавайте (на форуме, в личке или еще где меня найдете smile ), я постараюсь на них ответить. Скорее всего, я буду дополнять эту статью в будущем, если она вызовет интерес.

Источник: http://www.siemens-club.org/faq/index.php?Action=showarticle&faqID=162

Категория: Общие вопросы | Добавил: X-Volp (14.11.2007) | Автор: 1nvisible
Просмотров: 856 | Комментарии: 1 | Рейтинг: 4.5/2 |
Всего комментариев: 1
1 Dimbunnilkiny  
0
Соберем для Вас по сети интернет базу данных
потенциальных клиентов для Вашего Бизнеса
название, телефон, факс, e-mail,
имена, адреса, товары, услуги итд
Более подробно узнайте по
Телефону: +79133913837
ICQ: 6288862
Skype: s.3837
Email: prodawez@mixmail.com

Добавлять комментарии могут только зарегистрированные пользователи.
[ Регистрация | Вход ]
Форма входа
Поиск
Друзья сайта
Статистика

Онлайн всего: 1
Гостей: 1
Участников: 0