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

Указатели и C++


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

Здравствуйте! Почитал всякие статейки, посмотрел пару видео, но у меня все же возникли вопросы.

1. Допустим я ищу указатель 3 "уровня"... Но дело в том, что с каждым уровнем их порой не становится меньше, а все так же куча указателей (15-20 шт.) как и при первом поиске... Может есть какой-то более оптимальный поиск? А то разбирать все 15 указателей на "нужный"-"не нужный" при каждом поиске не ахти.

ЗЫ и насколько я понял, оффсеты могут измениться, допустим, при обновлении игры (это я на будущее), но, насколько мне известно, есть и более надежные способы для поиска нужного адреса.

2. Может ли кто-нибудь привести пример на C++, как обращаться к памяти через указатели. Как бы найти то я их могу (если их не так много, как я описал выше), а вот как и с чем их есть в С++ не понимаю)

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


DWORD* memory = (DWORD*)malloc(5 * sizeof(DWORD));
*memory = 10; // эквивалентно memory[0] = 10;
*(memory + 4) = 10; // эквивалентно memory[1] = 10;

Вот тебе и обращение к памяти по указателям :)

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


DWORD* memory = (DWORD*)malloc(5 * sizeof(DWORD));
*memory = 10; // эквивалентно memory[0] = 10;
*(memory + 4) = 10; // эквивалентно memory[1] = 10;

Вот тебе и обращение к памяти по указателям :)

А можно пример с ReadProcessMemory?

Я допустим через поинтер скан нашел какую-то цепочку указателей (их просто дохрена, около 10к... ппц) Но как мне через эту цепочку воздействовать на память то?

ЗЫ В *(memory + 4) = 10; // эквивалентно memory[4] = 10;, не?

Вообщем

48adc3620a301f28b419b08bba71d61f2377ee26.png

К какому адресу мне надо прибавлять 0x264 + 0x0 + 0x20 ? Просто не совсем догоняю... а если честно, то вообще не догоняю))

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

я ж уже говорил, что искать цепочки оффсетов и использовать их в трейнерах для современных игр трудоемко... Теперь по поводу адреса, этот самый адрес который ты не знаешь как достать называется базовым, для начала попробуй его увидеть через ollydbg, а потом уже программно доставай) Как его в ольке увидеть скажешь ты? Открываешь ольку, подключаешься к игре, идешь в обозреватель всех подключенных модулей(в гугле найдешь как попасть туда), там ищешь свою dll из цепочки оффсетов и смотришь на столбик BaseAddr вот там то и адрес твоей dll. В итоге у тебя уже такая цепочка получается BaseAddr + 15AC34 + 264 + 0 + 20.

Теперь по поводу того как прочитать данные из адреса по цепочке:


ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x15AC34, (LPVOID)baseAddr, 4, NULL);
ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x264, (LPVOID)baseAddr, 4, NULL);
ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x0, (LPVOID)baseAddr, 4, NULL);
ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x20, (LPVOID)baseAddr, 4, NULL);

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

я ж уже говорил, что искать цепочки оффсетов и использовать их в трейнерах для современных игр трудоемко... Теперь по поводу адреса, этот самый адрес который ты не знаешь как достать называется базовым, для начала попробуй его увидеть через ollydbg, а потом уже программно доставай) Как его в ольке увидеть скажешь ты? Открываешь ольку, подключаешься к игре, идешь в обозреватель всех подключенных модулей(в гугле найдешь как попасть туда), там ищешь свою dll из цепочки оффсетов и смотришь на столбик BaseAddr вот там то и адрес твоей dll. В итоге у тебя уже такая цепочка получается BaseAddr + 15AC34 + 264 + 0 + 20.

Теперь по поводу того как прочитать данные из адреса по цепочке:


ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x15AC34, (LPVOID)baseAddr, 4, NULL);
ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x264, (LPVOID)baseAddr, 4, NULL);
ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x0, (LPVOID)baseAddr, 4, NULL);
ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x20, (LPVOID)baseAddr, 4, NULL);

Благодарю! Я раньше немного в олли копался, поэтому думаю проблем возникнуть не должно :) А еще вопрос один, можно ли всю эту цепочку поместить в одну функцию?

Типо


ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x15AC34 + 0x264 + 0x0 + 0x20, (LPVOID)baseAddr, 4, NULL);

Внизу что-то очень страшное и неработающее :D

7361be99b0301c12b38197fd55e56277b6770726.png

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

Мда... Щас опять приаттачил ольку к процессу, посмотрел базовый адрес - совсем другой... И как быть? Как найти хоть что то статическое? Как мне, блин, уже пройтись по указателям и получить НУЖНЫЙ АДРЕС?!

Такой код не пашет

#include <iostream>
#include <windows.h>
using namespace std;

int main(){
DWORD baseAddr = 0x038D0000; // Базовый адрес, который меняется ._.
HWND hwnd = FindWindow(0,L"S.T.A.L.K.E.R.: Shadow Of Chernobyl");
DWORD pid;
int Money=0;
GetWindowThreadProcessId(hwnd,&pid);
HANDLE phandle = OpenProcess(PROCESS_ALL_ACCESS,0,pid);
ReadProcessMemory(phandle, (LPVOID)(baseAddr + 0x0028F96C), &baseAddr, sizeof(DWORD), 0); // + 0x744 + 0x44 + 0x234
ReadProcessMemory(phandle, (LPVOID)(baseAddr + 0x744), &baseAddr, sizeof(DWORD), 0);
ReadProcessMemory(phandle, (LPVOID)(baseAddr + 0x44), &baseAddr, sizeof(DWORD), 0);
ReadProcessMemory(phandle, (LPVOID)(baseAddr + 0x234), &baseAddr, sizeof(DWORD), 0);
ReadProcessMemory(phandle, (LPVOID)baseAddr, &Money, sizeof(Money), 0);
cout<<"Value: "<<money<<"\nerrors: "<<getlasterror()<<"\nnew="" value:="" ";="" system("pause="">>void");
}

Такой тоже


ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x15AC34, (LPVOID)baseAddr, 4, NULL);
ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x264, (LPVOID)baseAddr, 4, NULL);
ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x0, (LPVOID)baseAddr, 4, NULL);
ReadProcessMemory(hProcess, (LPVOID)baseAddr + 0x20, (LPVOID)baseAddr, 4, NULL);

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

Ты похоже про указателей ничего не знаешь.

Посмотри это видео, и сам поймешь в чем ошибка у тебя

там C# но суть одно.

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


memory[4] - эквивалентно *(memory + 16);

Могу только посоветовать учить самые основы C++.

Ты реально думаешь, что я лезу в память, не зная основ? Хах.

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

И да:

d93609f1c8d4a1b7f9da40c9ad14b8db5cbe8500.png

И лишь из-за этого я сделал соответствущий вывод.

ЗЫ только недавно начал как-то с памятью разбираться, поэтому не надо сразу посылать куда подальше :)

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

Ты похоже про указателей ничего не знаешь.

Посмотри это видео, и сам поймешь в чем ошибка у тебя

там C# но суть одно.

Раза 2 смотрел данное видео, но не до конца (лишь про поиск указателей). Щас повнимательней послушаю его...

Да и опять же повторюсь, искать базовый адрес + оффсеты первым методом - это самоубийство, ибо их там просто дохрена. А как мне извлечь базовый адрес из какого-либо модуля (dll допустим), с которого начинается все это смещение - я не пойму.

Что ты нам на скрине показать хочешь?

char - 1 байт

DWORD - 4 байта

Я это вспомнил сразу же после отправки поста, поэтому и добавил

"И лишь из-за этого я сделал соответствущий вывод."

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

Поможет тебе в этом деле - http://msdn.microsof...p/ms682489.aspx и http://msdn.microsof...p/ms684218.aspx и http://msdn.microsof...p/ms684221.aspx

О MODULEENTRY32 - http://msdn.microsoft.com/en-us/library/windows/desktop/ms684225.aspx

После того как снимок тебе будет не нужен, освободи его через CloseHandle.

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

Спасибо, буду разбираться, читать.

Coder, единственная причина, почему я не смотрю твои уроки - это WinAPI :) Мне в ближайшее время не хочется переходить на оконные приложения, а у тебя в основном работа идет с ними и в некоторых уроках, которые интересны мне, я не могу просмотреть какие-то участки кода, которые писались в предыдущих уроках. Ибо смотреть все уроки и ждать, пока ты начнешь писать нужный мне участок кода нет :D Вот так вот все печально выходит))

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

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

Спасибо, буду разбираться, читать.

Coder, единственная причина, почему я не смотрю твои уроки - это WinAPI :) Мне в ближайшее время не хочется переходить на оконные приложения, а у тебя в основном работа идет с ними и в некоторых уроках, которые интересны мне, я не могу просмотреть какие-то участки кода, которые писались в предыдущих уроках. Ибо смотреть все уроки и ждать, пока ты начнешь писать нужный мне участок кода нет :D Вот так вот все печально выходит))

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

A Read/Write ProcessMemory это не WinAPI?

Тебе вот это очень даже пригодится -

(в описании к роликам есть ссылки на pastebin и файловый архив)

И это

(видео про GUI можешь пропустить)
Ссылка на комментарий
Поделиться на другие сайты

Эти уроки - бесценны. Супер! :) Сразу их почему-то у тебя на канале (еще эдак с неделю назад, когда даже про форум этот не знал) не увидел их... Щас посмотрел три урока внимательно, все переписывая с экрана ииии вуаля! :) Все получилось.

STALKER TRAINER plus 1 ($ MONEY $) Succesfully completed. :D

Ха. И только одна проблема, кстати, возникла! Я нашел значение денег, вообщем... и такая беда, что если число шестизначное - то выводит лишь пять рандомных цифр. Как поправить? :\

Хм, кажется решил проблему.

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

Ииии у меня остался один-единственный, последний вопрос. Далее в эту тему писать не буду...

Вообщем, как мне зафризить какое-либо значение? Ну... просто у меня в голову приходит один вариант:


while(1){
if(GetAsyncKeyState(VK_NUMPAD1)){
Money+=50000;
mem->Write(&Money, moneyAddr, sizeof(unsigned long int));
cout<<"Current Money: "<<Money<<endl;
Sleep(400);
}
if(GetAsyncKeyState(VK_NUMPAD2)){
FreezeStamina = mem->Read(staminaAddr, sizeof(unsigned long int)).toUINT32();
(FreezeSt == 1 ? FreezeSt = 0:FreezeSt = 1);
}
if(GetAsyncKeyState(VK_NUMPAD9)) exit(0);
if(FreezeSt){
Stamina = mem->Read(staminaAddr, sizeof(unsigned long int)).toUINT32();
if(FreezeStamina != Stamina)
mem->Write(&FreezeStamina, staminaAddr, sizeof(unsigned long int));
}
Sleep(100);
}

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

Мне почему-то кажется, что из за постоянного использования Write, идет какая-то лишняя нагрузка. Поэтому хотелось бы немного это дело оптимизировать, если возможно.

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

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

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

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