Перейти к содержанию

Рекомендуемые сообщения

Привет! Цитирую и перевожу с официальных форумов СЕ:

aobscan(name,89 4D FC 8A 5D 08 83 FF 01 76 09 89 F8 89 FA FF 52 34 89 C6 85 F6)

bytes_239.jpg

После срабатывания скрипта в переменной name будет находиться 0x0053F2B3, согласно картинке, т.е. адрес этой инструкции. Туда можно будет что-нибудь записать, например - jmp newmem. Если это строчка определённых байт, то такая сигнатура называется wildcard, если я не ошибаюсь - в ней все байты уникальны. Если есть маска вида xxxx???xxxxx, в которой вместо "?" могут быть любые байты - то это вроде как просто сигнатура. Само собой, в скрипте команд aobscan может быть сколько угодно - лишь бы имена переменных были разные.

Ссылка на комментарий
Поделиться на другие сайты

А если ищешь например значение -10000 переходишь в отладчик по адресу значения, копируешь массив байт вот этот 00 00 00 00 00 88 C3 C0 00 00 00 00 00 00 69 40 00 00 00 00 00 00 00 00 D0 F7 10 61 07 00 00 00 и вставляешь в код, а он не пашет. А вот сигнатура которая в скрипте работает в чем может быть причина?


function debugger_onBreakpoint()
if (debugState ~= 3) then
debugState = 2
ONdebugger()
end
return 1
end
--------------------------------
function ONdebugger(pmAddress)
if (debugState == 0) then
debugState = 1
debugProcess()
debug_setBreakpoint(pmAddress)
end
if (debugState == 2) then
debugState = 3
debug_removeBreakpoint(pmAddress)
pause()
unpause()
adresgrav= EDI+0x58
end
end
-----------------------------------
function s2()
writeDouble(adresgrav, 10000)
end
function s3()
writeDouble(adresgrav, -10000)
end
-----------------------------------
-----------------------------------
function Obzor_AOB()
pause()
results=AOBScan("F3 0F 7E 47 58 66 0F 2E C1 76 24 8B 53 5C 8B 43 7C 8B 79 60 8D 4D D8 89 5D D8 89 55 DC 89 45 E0","+X-W-C")
unpause()
if (results~=nil) then
count=stringlist_getCount(results)
if (count==1) then
pmAddress=getAddress(stringlist_getString(results,0))
else
object_destroy(results)
results=nil
end
end
object_destroy(results)
results=nil
debugState = 0
ONdebugger(pmAddress)
end
function myattach(timer)
if getProcessIDFromProcessName("my_tank.exe") ~= nil then
object_destroy(timer)
openProcess("my_tank.exe")
count2=0
debugState = 0
Obzor_AOB()
else
showMessage("Client not found")
closeCE()
end
end
f=createForm(false) --create an invisible window
t=createTimer(F);
timer_setInterval(t,100) --10 might have been too fast for xp...
timer_onTimer(t,myattach)
function checkEnd(timer)
if (isKeyPressed(VK_F1)) then
s2()
end
if (isKeyPressed(VK_F2)) then
s3()
end
end
tEnd=createTimer(nil) --Блок hotkey
timer_setInterval(tEnd, 100)
timer_onTimer(tEnd, checkEnd)
timer_setEnabled(tEnd, true)
end

Ссылка на комментарий
Поделиться на другие сайты

Сигнатуры призваны искать код в памяти, адреса же могут в ней быть раскиданы как угодно. Т.е. вот это:

0x1234567: mov al,ah

сканер тебе найдёт, а вот это:

0x2233445: 1000

скорее всего - нет. Для этого лучше использовать указатели.

Ссылка на комментарий
Поделиться на другие сайты

Но а почему если перевести вотетот массив байт 00 00 00 00 00 88 C3 C0 00 00 00 00 00 00 69 40 00 00 00 00 00 00 00 00 D0 F7 10 61 07 00 00 00 в Double получается -10000, посути должна робить эта сигнатура но она не работает, а если перевести вот этот массив байт F3 0F 7E 47 58 66 0F 2E C1 76 24 8B 53 5C 8B 43 7C 8B 79 60 8D 4D D8 89 5D D8 89 55 DC 89 45 E0 получится совершенно другое число, но она работает ?

Ссылка на комментарий
Поделиться на другие сайты

Окей, давай ещё раз покажу. Вот картинка:

post-6695-0-32474400-1339614991_thumb.pn

1 - окно кода, в нём видно дизассемблированные команды программы (игры).

2 - окно данных, в нём видно значения переменных, констант и всё то, что, по сути, кодом не является, т.е. не выполняется.

post-6695-0-05457900-1339615085_thumb.pn

Вот тут выделено и обведено красненьким три команды. Вот эти:


00460D26 /. 55 PUSH EBP
00460D27 |. 8BEC MOV EBP,ESP
00460D29 |. 6A FF PUSH -1

Первый столбик - адрес, по которому команда хранится в памяти. Второй - [опкод] этой операции в 16-ричной системе счисления, третий - [мнемоника] это команды, или её более человеческое представление. Процессор понимает и оперирует исключительно опкодами, если очень огрубить, мнемоники созданы исключительно для программистов - чтобы можно было понимать\читать\писать код.

Третья картинка:

post-6695-0-45854300-1339615310_thumb.pn

Выделено четыре байта и адрес памяти, по которому эти четыре байта хранятся. Вот эти байты:

0046F000:  00 00 00 00

Соответственно, первый столбик - адрес памяти, второй - сами байты, которые хранятся по этому адресу.

В чём же состоит магия? Магия в том, что код, как и данные, хранится в памяти. Оперативной, ага. В неё загружается вся программа целиком, управление передаётся на первую инструкцию кода, он начинает выполняться, для всяких же переменных и прочих данных тоже выделяется память.

Вторая часть магии в том, что [исполняемые файлы] начинаются всегда с одного и того же адреса, положим, что 0x400000. Почему он определённый - читай про формат этих самых исполняемых файлов, документацию найти не трудно. Вспомним команды, которые у нас были в окне кода:


00460D26 /. 55 PUSH EBP
00460D27 |. 8BEC MOV EBP,ESP
00460D29 |. 6A FF PUSH -1

Учитывая то, что код всегда начинается с одного адреса, вычитаем:

0x00460D26 - 0x00400000 = 0x00060D26

60D26 - это смещение относительно начала секции кода. Одна из особенностей формата - он делится на секции. Кода, данных, импорта, экспорта - всё есть в документации.

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

Самое интересное в том, что данные при этом [раскидываются как угодно] - просто выделяется кусок оперативки достаточного размера, даётся его первый адрес, например:

0x123456

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

Надеюсь, что это более-менее понятно. Теперь, чем же нам поможет сигнатура? У нас есть набор опкодов:

55, 8B, EC, 6A, FF

Эти опкоды обозначают команды со второй картинки (их там аж три штуки). Мы знаем, что начало кода - всегда на 0х400000. Мы знаем размер файла. Поэтому мы можем перебрать каждую последовательность байт и если она совпадает с той, что повыше написана - значит мы наткнулись на нужную нам последовательность команд. Возвращаем её адрес - вуаля, можно записать туда что-нибудь ещё, например команду nop или прыжок на код-кейв. Т.е. даже если расположение этих команд внутри секции кода поменяется - скажем, разработчики патч напишут - мы всё равно сможем найти новый адрес по сигнатуре.

В секции же данных такое не прокатит, потому что по факту это - большущая помойка, одной только винде известно, как упорядоченная. Меняется там всё каждый запуск, каждый клик мыши. Куски данных меняются относительно начала, относительно друг друга и так далее - создаются и уничтожаются переменные, память выделяется, освобождается, в общем - разнообразных действий много.

Именно это - та причина, по которой сигнатуры в этом случае не помогут. Помогут тут указатели или изменение тех инструкций кода, которые читают нужные нам адреса.

Доступно? Если не очень - спроси, что не понял.

Ссылка на комментарий
Поделиться на другие сайты

×
×
  • Создать...

Важная информация

Находясь на нашем сайте, Вы автоматически соглашаетесь соблюдать наши Условия использования.