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

как исключить не действительные адреса из фильтра ?


Alex2411

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

делаю фильтр  приерно такой

push eax
mov eax,ebx
mov eax,[eax+10]
mov eax,[eax+20]
cmp eax, ...
pop eax

игра  часто крашиться . долго  не мог найти  причину крашей  потом нашел . оказываеться  регистр  ebx иногда  принимат значения  которые не  могут быть адресами памяти .  если  это значение вставлять  вместо адреса в хекс вювере то там  только знаки ??????. когда  чит енжин проверяет  такое значение  вместо адреса  и считает смешение  от крашит игру . это  случаеться в разных играх .
как  сделать что бы чит енжин  не проверял  значения  регистра  если он  не может быть адресом  памяти ? я пробовал  отсеять слишком малые и большие . крашит реже , но все равно  плохо .

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

2 минуты назад, Alex2411 сказал:

если он  не может быть адресом  памяти ?

Я добивался чтобы не крашило, только суммой нескольких фильтров, проверяя адреса что остаются в Анализе структур.
Либо находить фильтр на этом же уровне указателя.

Либо делать совсем по другому - вариантов по написанию фильтра много, У меня много видео посвященное этому.

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

26 минут назад, Garik66 сказал:

Я добивался чтобы не крашило, только суммой нескольких фильтров

 

а  возможно сравнение  что бы чит енжин  с начала проверял  что значение указывает  на память , а не на знаки ???? , а  потом  считал смещение ? типа такого

mov eax,ebx
cmp [eax], ... // проверка  есть ли память по адресу
jn .... // если памяти  нет то уходим
mov eax,[eax+10]
cmp [eax], ... // проверка  есть ли память по адресу
jn .... // если памяти  нет то уходим
mov eax,[eax+20]

можеть быть  команда  не cmp , а какая то другая есть в ассемлере для  проверки ?

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

 

13 часов назад, Alex2411 сказал:

cmp [eax], ... // проверка есть ли память по адресу

Вариантов решений несколько

 

1. Могут быть адреса, которые явно читать не стоит. такие как

cmp eax, 0
cmp eax, 0xffffffff

Тогда просто сравнить их и все

 

2. Использовать API Windows для определения прав доступа к адресу на чтение и запись перед обращением

 

3. Использовать обработку исключений типа этого

Спойлер

label(Handler) 
label(NoException) 
label(ExceptionHandled) 
label(lpCaption) 
label(lpText) 

00270000:  // you need create thread on 00270000 
   pushad 
   mov esi, Handler 
   push esi 
   push fs:[0] 
   mov fs:[0], esp 

   mov ecx, [0]   // EXEPTION!

   Jmp NoException 
Handler: 
   mov esp,[esp+0x08] 
   pop fs:[0] 
   add esp, 4 
   popad 

   // This point if we have exception runnig 
   Jmp ExceptionHandled 
   Jmp NoException 

NoException: 
   pop fs:[0]         // restore the old EXEPTION 
   add esp, 0x24 //32+4 
   ret 

ExceptionHandled: 
   // the exception was eaten 
   push 0             //uType  (0=mb_ok) 
   push lpCaption 
   push lpText 
   push 0           //hWnd 
   call MessageBoxA 
   ret 

lpCaption: 
   db 'Exception!' 0 

lpText: 
   db 'You have exception' 0

 

 

4. Использовать CE Lua для определения доступа к адресу

function CheckAddress(address)
  return readInteger(address) ~= nil
end

Это функцию можно использовать двумя способами. 

Либо через вызов Lua функции из CE AA (в прочем там же можно и сразу писать значение)

image.png

Либо кешировать адреса в метки и по Lua таймеру записывать значение по адресам.

 

5. Вариант искать другое место кода для инъекции

6. Вариант искать условия, когда адрес всегда валидный (например, когда в той же структуре адреса имеют определенные значения)

 

В большинстве случаев подходит вариант5. Нужно найти другое место кода, откуда например читается значения во время игры только для игрока. Например, когда код читает значение и передает его на экран.

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

2 часа назад, MasterGH сказал:

Могут быть адреса, которые явно читать не стоит. такие как

 

это  первое что я сделал ))) стало не много  лучше , но все равно  вылетает . еще проблема  втом что не  правильные  адреса бывают  на следущем уровне  указателя . адрес в eax нормальный , а адрес  после [eax+10]  уже плохой . 

 

2 часа назад, MasterGH сказал:

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

 

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

игра Omerta - City of Gangsters .  то же самое  в игре Battle Brothers  в играх Aldorlea Games и  еще много других

 

ладно попробую  отсеивть  кучей фильтров .  я думал может есть простой  способ  проверки , а я  его просто не  знаю ))

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

Я бы пробовал

Спойлер

label(Handler) 
label(NoException) 
label(ExceptionHandled) 

00270000:  // you need create thread on 00270000 
   pushad 
   mov esi, Handler 
   push esi 
   push fs:[0] 
   mov fs:[0], esp 

   push eax
   mov eax,ebx
   mov eax,[eax+10]
   mov eax,[eax+20]
   cmp eax, ...
   pop eax

   Jmp NoException 
Handler: 
   mov esp,[esp+0x08] 
   pop fs:[0] 
   add esp, 4 
   popad 

   // This point if we have exception runnig 
   Jmp ExceptionHandled 
   Jmp NoException 

NoException: 
   pop fs:[0]         // restore the old EXEPTION 
   add esp, 0x24 //32+4 
   ret 

ExceptionHandled: 
   ret 

 

 

или пункт 6, который я написал.

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

30 минут назад, MasterGH сказал:

Я бы пробовал

 

попробую , но мне  такое пока сложно . я не знаю даже что  такое

fs:[0]

(((

 

31 минуту назад, MasterGH сказал:

или пункт 6, который я написал.

 

да . спасибо . пока  для меня  это самое понятное .  я хоть предстсавляю куда искать ))

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

4 минуты назад, Alex2411 сказал:

пока  для меня  это самое понятное .

Ну собственно именно про этот вариант я и писал - исключаем доп. фильтрами работы инструкции с не валидными адресами.

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

Только что, Garik66 сказал:

Ну собственно именно про этот вариант я и писал - исключаем доп. фильтрами работы инструкции с не валидными адресами.

 

да, но  это долгий  не надежный способ с  кучей не приятных  сюпрпизов .  надо потом очень  долго тестить  фильтр. помню  ломал игру на  деньги  вроде все  отфильтровал , но через час  игры  когда пришел в первы магазин  через фильтр денег  пролезли куча адресов  потому что в магазине  оказываеться то же  есть деньги )))))  фильтр  денег был привязан  к адресу героя  типа  когда мои  деньги да , а чужие нет . а в  магазине деньги  не чьи  поэтому на месте  уазателя  персонажа  стоял  игровой номер  магазина . игра крашнулась .

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

Только что, Garik66 сказал:

смотря как писать.:-D

 

как умею )))  на игры  которые мне  приходиться  ломать  вообще  не где нет  тренеров и таблиц . подсмотреть  правильные способы не  у кого и обучений  как их ломать  не где нет . по этому приходиться  придумывать самомму , а опыта у меня  мало ((

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

7. Вариант использовать для проверки на ноль команду ""test" вместо "cmp".

test - логическая "И"

test reg,reg- проверка на ноль.

 

Пример 1 (reg = 12345)

test reg ,reg  = test 12345,12345 = 12345 "И" 12345 = 12345

 

Пример 2 (reg = 0)

test reg ,reg  = test 0,0= 0"И" 0= 0

 

Спойлер

newmem:
push ecx
mov ecx,["Tutorial-i386.exe"+000A5010] // Помещаем в ecx содержимое адреса "Tutorial-i386.exe"+000A5010
test ecx,ecx//У нас ecx ~= 0 так как в "Tutorial-i386.exe"+000A5010 оказалось значение не 0 и не nil (??????)
jz exit // jz = JUMP_if_ZERO. У нас ecx не ноль, значит прыжок не делаем, но идем дальше по коду
mov ecx,[ecx+48] //Помещаем в ecx содержимое адреса ecx+48. Содержимое адреса ecx+48 равно ??????, то есть в ecx поместится 0
test ecx,ecx //ecx == 0
jz exit //Выходим на метку exit, так как на этой стадии проверки указатель стал неверным
mov ecx,[ecx+480]
test ecx,ecx
jz exit

mov [val],ecx {Помещаем в переменную val значение регистра ecx, либо выполнем другие желаемые действия с уже точно валидным указателем}

exit:
pop ecx
mov [ebx+00000480],eax
jmp returnhere

 

 

 

 

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

8. не заниматься ерундой с фильтрами, а найти инструкцию, которая работает с теми адресами, которые нужны.

9. вычислить адрес самостоятельно.

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

7 часов назад, Antonshka сказал:

7. Вариант использовать для проверки на ноль

 

проверка ноль не решит  проблемы других не правильных  значений .
 я думал если  можно  как то  найти  адреса памяти игры  первый и последний записать их  в метки  и сравнивать потом  регистры с этим меткми . если меньше первой и  больше после последней  то  прыжок на выход . только яне знаю как  это можно сделать  что бы найти крайние адерса.
 еще  хотел спросить . может  так быть что  в памяти игры в середине есть  пустые места с знаками ?????? ?  ну типа с 01000000 до 02000000 адреса рабочие  с 03000000 до 04000000 адреса то же рабочие , а по середине с 02000000 до 03000000 там стоят ?????? ?

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

5 часов назад, Alex2411 сказал:

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

Конечно, может. Посмотри карту памяти

Спойлер

image.png

 

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

В CE 6.8.3 можно сравнить ветви трассировки. Берешь правильную ветвь, берешь любую не правильную. Сравниваешь до верхнрего call-а и с него начинаешь многоуровневый указатель выстраивать или же на это м call-е смотришь параметры и стек, и там правишь код.

Спойлер

 

 

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

19 часов назад, MasterGH сказал:

пробуй сравнивать структуры

 

там как  я понял нет струткуры . инструкции  которые работают с  нужными адресами они  все с маленькими смещениями . типа  mov eax,[ebx] или mov ecx,[edx+04] или что то похоже . адреса нужных значений  находяться не далеко  друг от друга , но  если  скопировать в метку какой то  один , а остальные  взять  как метка + смещение  то после перезапуска  игры  все смещения   таблице слетают .  приходиться   каждое значение  сохранять в свою  метку

 

19 часов назад, MasterGH сказал:

пробуй трассервку

 

с трасером  там получаеться  такая проблема .  посоветуй пожалуйста  как решить.  инструкция обращаеться с  сотнями адресов  и  происходит  много тысяч срабатываний ,а на  нужном мне адресе срабатывает не часто .  когда я запускаю трасер  и ставлю срабатывать  бряк  трасера по условию на нужный  мне адрес то чит енжин  начинает проверять каждое срабатывание инструкции , а зеленая строка  на инструкции  все время мигает . игра  сразу замирает  и через сколько то секунд  крашиться или  на глухо виснет .  трасеровка  даже не успевает сработать. такое  у меня случаеться только  на играх где инсрукция срабатывает  очень часто . посоветуй что сделать  что бы так не было ? может  в настройках чит енжин дебагер другой выбрать или чт то другое поменять ?  у меня выбран  veh дебагер
спасибо  за помощь

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

3 часа назад, Alex2411 сказал:

ставлю срабатывать  бряк  трасера по условию на нужный  мне адрес то чит енжин  начинает проверять каждое срабатывание инструкции

 

Вот так ставим

Спойлер

image.png

 

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

50 минут назад, MasterGH сказал:

Вот так ставим

 

с начала у меня  так не работало и  я забросил такой  способ. сейчас снова  стал пробовать м разобрался  в чем дело . оказываеться не работает когда  в опциях дебагера стоит int3 instructions , а если поставиь  hardware breakpoints  то все получилось . не знал  этого . этим способом  трасеры  работают как надо . ура )))) спасибо за  помощь

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

34 минуты назад, Alex2411 сказал:

оказываеться не работает когда  в опциях дебагера стоит int3 instructions

 

int3 работает только на инструкциях, а аппаратные как на инструкциях так и на данных.

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

14 часов назад, Garik66 сказал:

Вариант

 

спасибо , но пока  плохо понимаю  как это работает .  буду  разбмраться

 

елси не  трудно  ты не мог бы  показать  как должен получиться скрипт ? как правильно  добавить твою проверку ?
вот  пример скрипт  из игры  Omerta - City of Gangsters

Спойлер

[ENABLE]

alloc(newMem, 2048)
label(return)
label(_testP)
registersymbol(_testP)

newMem:
 mov ecx,[ebx+08]
 cmp [ecx+10],74726964
 jne @f
 mov [_testP],ebx

@@:
 mov ecx,[ebx]
 mov eax,[ebp+14]
 jmp return

_testP:
 dd 0

Omerta.exe+12F749:
 jmp newMem

return:

[DISABLE]
	
Omerta.exe+12F749:
 db 8B 0B 8B 45 14

unregistersymbol(_testP)
dealloc(newMem)

{
// ORIGINAL CODE - INJECTION POINT: Omerta.exe+12F749

Omerta.exe+12F726: 8B B1 A0000000  - mov esi,[ecx+000000A0]
Omerta.exe+12F72C: E8 8F230000 - call 00531AC0
Omerta.exe+12F731: 83 78 04 00 - cmp dword ptr [eax+04],00
Omerta.exe+12F735: 75 08 - jne 0052F73F
Omerta.exe+12F737: 80 4A 06 01 - or byte ptr [edx+06],01
Omerta.exe+12F73B: 33 FF  - xor edi,edi
Omerta.exe+12F73D: EB 02 - jmp 0052F741
Omerta.exe+12F73F: 8B F8  - mov edi,eax
Omerta.exe+12F741: 85 FF  - test edi,edi
Omerta.exe+12F743: 0F85 91000000 - jne 0052F7DA
// ---------- INJECTING HERE ----------
Omerta.exe+12F749: 8B 0B  - mov ecx,[ebx]
Omerta.exe+12F74B: 8B 45 14  - mov eax,[ebp+14]
// ---------- DONE INJECTING  ----------
Omerta.exe+12F74E: 5F - pop edi
Omerta.exe+12F74F: 89 08  - mov [eax],ecx
Omerta.exe+12F751: 8B 53 04  - mov edx,[ebx+04]
Omerta.exe+12F754: 5E - pop esi
Omerta.exe+12F755: 89 50 04  - mov [eax+04],edx
Omerta.exe+12F758: 5B - pop ebx
Omerta.exe+12F759: 8B E5  - mov esp,ebp
Omerta.exe+12F75B: 5D - pop ebp
Omerta.exe+12F75C: C3 - ret 
Omerta.exe+12F75D: 8B C8  - mov ecx,eax
}

 

 

если  его включить  игра крашиться  почти сразу . я  пробовал отловить  мометн  вылета.  вылетало  когда  в  [ebx+08]  значение  00000004  или FF5A72A4 или еще друие адреса  по которым знаки ?????.

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

1 час назад, Alex2411 сказал:

как правильно  добавить твою проверку ?

не мою. @MasterGH

Попробуй так:

Спойлер

[ENABLE]
{$LUA}
  function CheckAddress(_testP)
    return readInteger('_testP') ~= nil
  end
{$ASM}
alloc(newMem, 2048)
label(return)
label(code)
label(_testP)
registersymbol(_testP)

newMem:
  mov ecx,[ebx+08]
  mov [_testP],ecx
// может придется добавить флаг, нужно проверять в игре, у меня потестить не начем
  mov ecx,[_testP]
  cmp [ecx+10],74726964
  jne code
  ....................// здесь то, что хотим
code:
  mov ecx,[ebx]
  mov eax,[ebp+14]
  jmp return

_testP:
  dd 0

Omerta.exe+12F749:
  jmp newMem
return:

[DISABLE]
Omerta.exe+12F749:
  db 8B 0B 8B 45 14

unregistersymbol(_testP)
dealloc(newMem)

{
// ORIGINAL CODE - INJECTION POINT: Omerta.exe+12F749

Omerta.exe+12F726: 8B B1 A0000000  - mov esi,[ecx+000000A0]
Omerta.exe+12F72C: E8 8F230000 - call 00531AC0
Omerta.exe+12F731: 83 78 04 00 - cmp dword ptr [eax+04],00
Omerta.exe+12F735: 75 08 - jne 0052F73F
Omerta.exe+12F737: 80 4A 06 01 - or byte ptr [edx+06],01
Omerta.exe+12F73B: 33 FF  - xor edi,edi
Omerta.exe+12F73D: EB 02 - jmp 0052F741
Omerta.exe+12F73F: 8B F8  - mov edi,eax
Omerta.exe+12F741: 85 FF  - test edi,edi
Omerta.exe+12F743: 0F85 91000000 - jne 0052F7DA
// ---------- INJECTING HERE ----------
Omerta.exe+12F749: 8B 0B  - mov ecx,[ebx]
Omerta.exe+12F74B: 8B 45 14  - mov eax,[ebp+14]
// ---------- DONE INJECTING  ----------
Omerta.exe+12F74E: 5F - pop edi
Omerta.exe+12F74F: 89 08  - mov [eax],ecx
Omerta.exe+12F751: 8B 53 04  - mov edx,[ebx+04]
Omerta.exe+12F754: 5E - pop esi
Omerta.exe+12F755: 89 50 04  - mov [eax+04],edx
Omerta.exe+12F758: 5B - pop ebx
Omerta.exe+12F759: 8B E5  - mov esp,ebp
Omerta.exe+12F75B: 5D - pop ebp
Omerta.exe+12F75C: C3 - ret
Omerta.exe+12F75D: 8B C8  - mov ecx,eax
}

Отпишись о результате.

 

 

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

14 минут назад, Garik66 сказал:

Отпишись.

 

 

сразу краш . вылетает  когда ecx  00000010 и  другие маленькие  значения .
 что бы их  отсеять  после записи метки  _testP в  есх  я поставил  фильтр

cmp ecx,00100000
jb code

и  дальше поставил  бряк на

cmp [ecx+10],74726964

что бы  посмотреть  на какие еще адреса  обрашаеться  эта инструкция  кроме  маленьких  когда вылетает . если  поможет вот  сделал скрин . последний  адрес с  ???

Спойлер

cBYumJcr71.png

 

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

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

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

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