Другое С/С++ Вопрос - Ответ

ARMOR

kjor32 is legend
Модератор
4,852
6,084
Как найти функцию через IDA? К примеру, добавления сообщения в чат.
Пытаюсь, но, увы, не получается.
Прошу объяснить пошагово.

Открыл в IDA samp.dll, пытался по строкам найти функцию.
Посмотреть вложение 186391
Вот тут можешь увидеть вот эту строчку:
1674049023946.png


Это вызов функции 64520. В неё передается два параметра: Указатель на структуру чата, и сообщение ( Эта функция в САМП'е отвечает за отправление в чат сообщений по типу "Connecting to 185.189.15.89:7228...", "The server is full. Retrying"). Цвет ты тут указать не можешь, ибо функция берет цвет из структуры CChat.

Цвет у тебя будет такой:
1674049218632.png

Ну, или если у тебя замененный samp.dll то цвет может отличаться.

Если ты хочешь указывать цвет сам - тебе нужна функция CChat_AddMessage. В R1 её смещение 645A0. Принимает агрументы в таком порядке:
C++:
(CChat* this_, int color, const char* text)
 
  • Нравится
  • Вау
Реакции: lemeXe и Yuriy Code

Yuriy Code

Известный
754
928
Пытаюсь вызвать функцию из samp.dll, но крашит. Что не так?
1674068253923.png

1674068634662.png


C++:
SF->getSAMP()->registerChatCommand("func", [](std::string params) {
            using func_type = int (__stdcall*)(const char* a1, int a2, int a3);

            func_type func = reinterpret_cast<func_type>((DWORD)(GetModuleHandle("samp.dll") + 0x9C2C0));

            func("Func called", 0x3E8, 5);
});
 

kin4stat

mq-team
Всефорумный модератор
2,730
4,712
Пытаюсь вызвать функцию из samp.dll, но крашит. Что не так?
Посмотреть вложение 186452
Посмотреть вложение 186453

C++:
SF->getSAMP()->registerChatCommand("func", [](std::string params) {
            using func_type = int (__stdcall*)(const char* a1, int a2, int a3);

            func_type func = reinterpret_cast<func_type>((DWORD)(GetModuleHandle("samp.dll") + 0x9C2C0));

            func("Func called", 0x3E8, 5);
});
В оригинале там thiscall, и сигнатура выглядит вот так:
void __thiscall sub_A05D0(CGame *this, char *text, int duration, int style)

Но CGame можно опустить, потому что он не используется. Короче тебе просто повезло.
А ошибка в том, что ты прибавляешь к результату GetModuleHandle число напрямую. А под ним лежит указатель, поэтому прибавляется неверное количество байт. Правильно будет вот так:
C++:
SF->getSAMP()->registerChatCommand("func", [](std::string params) {
    using func_type = void(__stdcall*)(const char*, int, int);
    auto sampbase = reinterpret_cast<std::uintptr_t>(GetModuleHandle("samp.dll"));

    func_type func = reinterpret_cast<func_type>(sampbase + 0x9C2C0);
    func("Func called", 1000, 5);
});

А еще правильнее вот так:
C++:
SF->getSAMP()->registerChatCommand("func", [](std::string params) {
    using func_type = void(__thiscall*)(void*, const char*, int, int);
    auto sampbase = reinterpret_cast<std::uintptr_t>(GetModuleHandle("samp.dll"));

    
    func_type func = reinterpret_cast<func_type>(sampbase + 0x9C2C0);
    func(*reinterpet_cast<void**>(sampbase + /* R3 Addr: 0x26E8F4 */), "Func called", 1000, 5);
});
 

writeline

Новичок
15
8

Решил немного залезть в реверс.
Открыл иду и в неё кинул samp.dll.

Решил пропатчить строку от сампа, нашёл её адрес в IDA (наверное), пытаюсь пропатчить, но, она не патчится. То есть, текст там изменить хочу, но, он не изменяется.

Посмотреть вложение 186387

C++:
        SF->getSAMP()->registerChatCommand("patch", [](std::string params) {

            strcpy((char*)0x100D3A78, "SWWWWW CCCCCC the connection.");
            AddChat(-1, "Наверное, пропатчилось...");

        });

Посмотреть вложение 186388

C++ R3:
std::string str_kicked{ "Сервер закрыл соединение." };//0x8A77

class patchstr_kicked {
private:
    uintptr_t module_samp{ 0 };

public:
    patchstr_kicked() {
        module_samp = reinterpret_cast<uintptr_t>(GetModuleHandleA("samp.dll"));

        DWORD lpflOldProtect;
        VirtualProtect(reinterpret_cast<LPVOID>(module_samp + 0x8A77), 0x4, PAGE_EXECUTE_READWRITE, &lpflOldProtect);
        *reinterpret_cast<LPVOID*>(module_samp + 0x8A77) = &str_kicked[0];
        VirtualProtect(reinterpret_cast<LPVOID>(module_samp + 0x8A77), 0x4, lpflOldProtect, &lpflOldProtect);
    }
} pstr_kicked;

Цвет можешь указывать вот так:
С++:
std::string str_kicked{ " {ff0000} Сервер закрыл соединение." };
Либо
С++:
std::string str_kicked{ " {red} Сервер закрыл соединение." };
 

Вложения

  • srvclose.asi
    14 KB · Просмотры: 5
Последнее редактирование:

ARMOR

kjor32 is legend
Модератор
4,852
6,084
Как можно получить ID процесса по его названию? Нашел такую функцию в интернете:
1674498357123.png

C++:
DWORD GetProcessID(const char* processName)
{
    if (!processName)
        return 0;

    DWORD id = 0;
    HANDLE hSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);

    if (hSnap)
    {
        PROCESSENTRY32 pe32 = { sizeof(PROCESSENTRY32) };
        if (Process32First(hSnap, &pe32))
        {
            while (Process32Next(hSnap, &pe32))
            {
                if (strcmp(processName, pe32.szExeFile) == 0)
                {
                    id = pe32.th32ProcessID;
                    break;
                }
            }
        }
    }CloseHandle(hSnap);
    return id;
}
Но она выдает ошибку:

1674498319091.png
 
  • Грустно
Реакции: F0RQU1N and

EclipsedFlow

Известный
Проверенный
1,040
464
Как можно получить ID процесса по его названию? Нашел такую функцию в интернете:
Посмотреть вложение 187047
C++:
DWORD GetProcessID(const char* processName)
{
    if (!processName)
        return 0;

    DWORD id = 0;
    HANDLE hSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);

    if (hSnap)
    {
        PROCESSENTRY32 pe32 = { sizeof(PROCESSENTRY32) };
        if (Process32First(hSnap, &pe32))
        {
            while (Process32Next(hSnap, &pe32))
            {
                if (strcmp(processName, pe32.szExeFile) == 0)
                {
                    id = pe32.th32ProcessID;
                    break;
                }
            }
        }
    }CloseHandle(hSnap);
    return id;
}
Но она выдает ошибку:

Посмотреть вложение 187046
В настройках проекта выбери - многобайтовую кодировку.
1674498520384.png
 
  • Нравится
Реакции: Young123 и ARMOR

Young123

Новичок
10
0
Как можно вызвать функции из libsamp.so или libgtasa.so на samp mobile? Я в этом мало знаю, как это можно сделать? (К примеру вывод текста в чат)
 

Young123

Новичок
10
0
Помогите, компилю, но текст не выводится (делаю на самп мобайл)
Код:
#include "main.h"
#include "armhook.h"

void AddMessageJumpQ(const char* text, unsigned int time, unsigned short flag, bool bPreviousBrief)
{
    ((void(__cdecl*)(const char*, unsigned int, unsigned short, bool))(g_libGTASA+0x4D1EA4))(text, time, flag, bPreviousBrief);
}

void InitializeAndLoad() {
    while (*reinterpret_cast<unsigned char*>(g_libGTASA+0x9E75B8) != 9) {
        std::this_thread::sleep_for(std::chrono::milliseconds(100u));
    }
    AddMessageJumpQ("~r~Hello from blast.hk", 5000, 0, false);
}
 

writeline

Новичок
15
8

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

По типу такого:
73690



Может кто то, что нибудь подсказать?
 

AdCKuY_DpO4uLa

Известный
287
477

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

По типу такого:
73690



Может кто то, что нибудь подсказать?
SetWindowText(handle, "Заголовок");
 
  • Нравится
  • Клоун
Реакции: Fott и writeline

AdCKuY_DpO4uLa

Известный
287
477
Подскажи если сможешь, почему не хочет работать? 🧐

C++:
void windtext()
{
    HWND hwnd = FindWindow(NULL, "GTA:SA:MP");
    if (hwnd == NULL)
    {
        MessageBox(NULL, "Window not found!", "Error", MB_OK);
    }

    std::string newText = "GTA:BLAST.HK";
    SetWindowText(hwnd, newText.c_str());
}
У меня работает. Возможно ты используешь это в DLL и код вызывается до того, как самп инициализировался, а до того, как самп инициализировался, работать не будет, ибо там другое название окна
 
  • Клоун
Реакции: Fott