Welcome to RaGEZONE - MMORPG Development Forums (sponsored by tfn.gr) Mark forums read | View Forum Leaders
RaGEZONE - MMORPG Development Forums (sponsored by tfn.gr)

Kal Development Discuss, [Guide] C++ DLL injection for Main Server at Kal Online forum; A small guide on how to inject C++ code/assembler into the Main Server. Thanks to Bakabug for some samples :-) ...




Reply
Thread Tools
[Guide] C++ DLL injection for Main Server
 
 
KalOnline Grand Old Man

Rank: Alpha Member


Reply With Quote
 
Join Date: Mar 2007
Location: Aarhus, Denmark
Posts: 2,597
03-24-2008, 02:38 PM
 
A small guide on how to inject C++ code/assembler into the Main Server.
Thanks to Bakabug for some samples :-)

Requirements
- Visual C++
- A hex editor
- Basic coding skills

Step 1 - Hex Injection
First thing to do , is unpack the MainServer.exe , or find a unpacked version.
When this is done, open the mainserver in your favorite hex editor, and search for "ADVAPI32.dll"

Now replace "ADVAPI32.dll" with "KalHooks.dll" , our new DLL.
Notice the mainserver will not function untill you provide the nessary dll in the same folder as the MainServer.exe

Step 2 - Some Basic Code
In visual studio, create a standard windows library project, and set it to create a DLL.
Now find dllmain.cpp , and replace it's content with the following code:

PHP Code:
#include "stdafx.h"

HMODULE libraryHandle;

_declspec(dllexportBOOL WINAPI GetUserNameA(LPSTR inputLPDWORD buffer)
{
    
typedef BOOL (WINAPICFunction) (LPSTR inputLPDWORD buffer);
    
CFunction getUserName = (CFunction)GetProcAddress(libraryHandle"GetUserNameA");
    return 
getUserName(inputbuffer);
}

BOOL WINAPI DllMain(HMODULE module,DWORD action,LPVOID reserved)
{
    
libraryHandle LoadLibraryA("ADVAPI32.dll");
    
    switch(
action)
    {
        case 
DLL_PROCESS_ATTACH:
            
// Startup Functions
        
break;
        case 
DLL_THREAD_ATTACH:
            
// Shutdown Functions 
        
break;
    }
    return 
true;

Step 3 - Injector Class
Now we wish to create a class handling our actions.

And here is the class, plus a example of a injected function. KalHooks::MemoryCopy and KalHooks::Intercept bluntly stolen from Bakabug.

KalHooks.cpp
PHP Code:
#include "stdafx.h"
#include "KalHook.h"

namespace Sword
{
    
///
    ///    DLL Loading.
    ///
    
void KalHook::Attach()
    {
       
this->DisableExperienceLoss();
    }

    
///
    ///    DLL Unloading.
    ///
    
void KalHook::Detach()
    {
    }

    
///
    ///    Disable experience loss when dying. 
    ///
    
void KalHook::DisableExperienceLoss()      
    {
        
unsigned char myCode[4] = {0xC20x040x000x90};
        
this->MemoryCopy((DWORD)0x004643A0,(DWORD)&myCode,4);
    }

    
///
    ///    Thread safe memory copying (address changing).
    ///
    
LPVOID KalHook::MemoryCopy(DWORD destinationDWORD sourceint length)
    {
        
DWORD oldSource      0;
        
DWORD oldDestination 0;
        
        
VirtualProtect((LPVOID)source,length,PAGE_EXECUTE_READWRITE,&oldSource);
         
VirtualProtect((LPVOID)destination,length,PAGE_EXECUTE_READWRITE,&oldDestination);
        
        
memcpy((void*)destination,(void*)source,length);
        
        
VirtualProtect((LPVOID)destination,length,oldDestination,&oldDestination);
        
VirtualProtect((LPVOID)source,length,oldSource,&oldSource);
        
        return (
LPVOID)destination;
    };

    
///
    ///    Intercept a instruction into the memory.
    ///
    
DWORD KalHook::Intercept(int instructionDWORD sourceDWORD destinationint length)
    {
        
DWORD realTarget;
        
LPBYTE buffer = new BYTE[length];
        
        
memset(buffer,0x90,length); 

        if(
instruction != INST_NOP && length >= 5)
        {
            
buffer[(length-5)] = instruction;
            
DWORD dwJMP = (DWORD)destination - (source + (length-5));
            
memcpy(&realTarget,(void*)(source+1),4);
            
realTarget realTarget source 5;
            
memcpy(buffer + (length 5),&dwJMP,4);
        }
        
        if(
instruction == SHORT_JZ)
        {
            
buffer[0] = instruction;
            
buffer[1] = (BYTE)destination;
        }
        
        if(
instruction == INST_BYTE)
        {
            
buffer[0] = (BYTE)destination;
        }
        
        
this->MemoryCopy(source,(DWORD)buffer,length);
        
delete[] buffer;
        
        return 
realTarget;
    }

KalHooks.h
PHP Code:
///
/// KalOnline DLL hook handler.
///
/// By Windcape and KingIzu.
/// 
#define INST_NOP  0x90
#define INST_CALL 0xE8
#define INST_JMP  0xE9
#define INST_BYTE 0x00
#define SHORT_JZ  0x74

namespace Sword
{    
    class 
KalHook
    
{
        public:
            
void Attach();
            
void Detach();
            
void DisableExperienceLoss();

        private:
            
LPVOID MemoryCopy(DWORD destinationDWORD sourceint length);
            
DWORD Intercept(int instructionDWORD sourceDWORD destinationint length);
    };
}; 
And now change dllmain.cpp to the following

PHP Code:
#include "stdafx.h"
#include "KalHook.h"

HMODULE libraryHandle;

/// 
/// Implementation of the WINBASE.H method GetUserNameA().
/// Required for proxying the ADVAPI32.dll library.
/// 
_declspec(dllexportBOOL WINAPI GetUserNameA(LPSTR inputLPDWORD buffer)
{
    
typedef BOOL (WINAPICFunction)(LPSTR input,LPDWORD buffer);
    
CFunction getUserName = (CFunction)GetProcAddress(libraryHandle"GetUserNameA");
    return 
getUserName(inputbuffer);
}

/// 
/// Initialize and attach the KalHooks class to the DLL loading
/// allowing us to do inline assembler and memory editing.
/// 
BOOL WINAPI DllMain(HMODULE module,DWORD action,LPVOID reserved)
{
    
libraryHandle LoadLibraryA("ADVAPI32.dll");
    
    
Sword::KalHook *hook = new Sword::KalHook();
    switch(
action)
    {
        case 
DLL_PROCESS_ATTACH:
            
hook->Attach();
        break;
        case 
DLL_THREAD_ATTACH:
            
hook->Detach();
        break;
    }
    return 
true;

Step 4 - Finalizing
Before we compile, one more important addition is required.

Due to a error made in the 70's by the Windows C developers, DLLs are compiled by default to have a _ (underscore) before a function name.
But since the MainServer cannot handle this, we need to create a new file, to ensure the underscores are not added.

Simply, add a file named Exports.def to your project, with following content

PHP Code:
LIBRARY    "KalHooks"
EXPORTS
    GetUserNameA
    DllMain 
Step 5 - Compiling
Compile (Make sure to compile to Release!), and copy your new KalHooks.dll into your MainServer folder.
Once this is done, run the MainServer and cross your fingers you did not do any ASM hacks that didden't work.

Last edited by DeathArt; 03-24-2008 at 04:15 PM.
 
 
permalink
 

RaGEZONE is proudly sponsored by
 
KalOnline Grand Old Man

Rank: Alpha Member


Reply With Quote
 
Join Date: Mar 2007
Location: Aarhus, Denmark
Posts: 2,597
03-24-2008, 02:41 PM
 
Part 2 - ASM Injects
The tricky part about doing injections is you need to use the Assembly language , ASM, to change call buildin methods of the Main Server.
I'm not going to teach you ASM, but just provide a few examples which you can call from the KalHooks::Attach()

The trick is to use a ASM address from [Only Registered and Activated Users Can See Links. Click Here To Register...] , which links to a method, and
then call the method with the correct params. The params you can get from disassemble the mainserver using [Only Registered and Activated Users Can See Links. Click Here To Register...]
In REC browse to the address() (as a function) and you'll get a list of arguments + type.

Feel free to add your own examples , but PLEASE use the proper CODE or PHP tags to encapsule the code.

PHP Code:
    ///
    /// Broadcast a message to all players ingame.    
    ///
    
void KalHook::ShowServerMessage(LPCSTR text)
    {
        
DWORD addr 0x00450910
        
__asm {
            
push text
            push 0x004B4484
            push 0x0F
            call addr
            add esp
0x0C 
        
}
    } 
PHP Code:
    ///
    /// Kicks a user from the server using the players UserId.    
    ///
    
void KalHook::KickUser(DWORD userId)
    {
        
__asm {
            
push eax
            push ecx
            push edx
            push ebx
        
}
        
        
DWORD kick 0x00452E60;
        
DWORD s 0x004B4DE8;
        
DWORD x = (DWORD)0x2D;
        
        
__asm {
            
push 1
            push s
            push x
            push userId
            call kick
            add ESP
0x10
        
}
        
        
__asm {
            
pop ebx
            pop edx
            pop ecx
            pop eax
        
}
    } 
 
 
permalink
 

 
SwordOnline

Rank: Member


Reply With Quote
 
Join Date: Sep 2006
Location: Belgium
Posts: 1,393
03-24-2008, 03:03 PM
 
Nice. but where is the MainSvr packed with?
 
 
permalink
 


 
KalOnline Grand Old Man

Rank: Alpha Member


Reply With Quote
 
Join Date: Mar 2007
Location: Aarhus, Denmark
Posts: 2,597
03-24-2008, 03:07 PM
 
Actually I don't think it's packed, atleast not the most common versions.If it is, the same packaging as the client.

Oh, and it have to be a CLEAN client. Anything allready using KOSP or similiar will not work with this.
I also updated the Part 2, as I just tested REC for finding function arguments , it works very well.
 
 
permalink
 

 
SwordOnline

Rank: Member


Reply With Quote
 
Join Date: Sep 2006
Location: Belgium
Posts: 1,393
03-24-2008, 03:25 PM
 
It's KalHook.h and not KalHooks.h :D for the rest it worked by me
 
 
permalink
 

 
SwordOnline

Rank: Member


Reply With Quote
 
Join Date: Sep 2006
Location: Belgium
Posts: 1,393
03-24-2008, 03:38 PM
 
---------------------------
MainSvrT.exe - Entrypoint not found
---------------------------
Can't find entrypoint from GetUserNameA in DLL-file KalHooks.dll.
---------------------------
OK
---------------------------
 
 
permalink
 

 
KalOnline Grand Old Man

Rank: Alpha Member


Reply With Quote
 
Join Date: Mar 2007
Location: Aarhus, Denmark
Posts: 2,597
03-24-2008, 03:44 PM
 
You forgot the Exports.def

Edit: Updated the dllmain.cpp source with a performance improvement for the HMODULE libraryHandle.
 
 
permalink
 

 
SwordOnline

Rank: Member


Reply With Quote
 
Join Date: Sep 2006
Location: Belgium
Posts: 1,393
03-24-2008, 06:19 PM
 
I added a file Exports.def in the same folder as my other files and then compiled it... is it wrong?
 
 
permalink
 

 
KalOnline Grand Old Man

Rank: Alpha Member


Reply With Quote
 
Join Date: Mar 2007
Location: Aarhus, Denmark
Posts: 2,597
03-24-2008, 06:40 PM
 
Did you add a "Definitions" file using the GUI, or manually added a text file you renamed to .def ?
The former is the correct way to do it.
 
 
permalink
 

 
SwordOnline

Rank: Member


Reply With Quote
 
Join Date: Sep 2006
Location: Belgium
Posts: 1,393
03-24-2008, 07:31 PM
 
Add New Item... dialougue doesnt contain Definition filetype
 
 
permalink
 

 
KalOnline Grand Old Man

Rank: Alpha Member


Reply With Quote
 
Join Date: Mar 2007
Location: Aarhus, Denmark
Posts: 2,597
03-24-2008, 08:57 PM
 
Sure there is:

 
 
permalink
 

 
SwordOnline

Rank: Member


Reply With Quote
 
Join Date: Sep 2006
Location: Belgium
Posts: 1,393
03-24-2008, 09:05 PM
 
[Only Registered and Activated Users Can See Links. Click Here To Register...]

oO Visual C++ Express 2008
 
 
permalink
 

 
void;

Rank: Member


Reply With Quote
 
Join Date: Dec 2006
Posts: 823
03-24-2008, 10:51 PM
 
Visual C++ Express is targeted toward C++/CLI.
 
 
permalink
 

 
SwordOnline

Rank: Member


Reply With Quote
 
Join Date: Sep 2006
Location: Belgium
Posts: 1,393
03-24-2008, 11:01 PM
 
aren't there template packs or smth?
 
 
permalink
 

 
If Im Here I'll Help SURE

Rank: Member


Reply With Quote
 
Join Date: Oct 2006
Location: Travvling to oCountry
Posts: 364
03-25-2008, 12:25 PM
 
hello :)
wow cool it is so nice tut DeathArt
hmm i realy still dont able to understand the things of c# ^^ as you are unsing namespaces even with c++ (yes im beginner xD )

so here whati did with my little knowledge :)
this example will let you edit as you like you just need to know what codes to use :
As i renamed my hacking project [SyRoN]of pservers to [SyRoN X]Int server
so i named this little thing [PME X]

First make new project :
File >> New >> Project >> Win32 Console application
name is :WSOCK32
Next >> [DLL][Empty Project]

then start to add items

dllmain.cpp
I used proxy of WSOCK32.dll as it has just 75 exports and only used with MainSvrt.exe just use this proxy source and yes you can use other dll as you like
PHP Code:
#include "PME_X.h"

void Begin()
{
    
Hook KalHook;//to make KalHook as Hook Class
    
KalHook.LvlupPoints(6);
}

HINSTANCE hLThis 0;
HINSTANCE hL 0;
FARPROC p[75] = {0};

BOOL WINAPI DllMain(HINSTANCE hInst,DWORD reason,LPVOID)
    {
    if (
reason == DLL_PROCESS_ATTACH)
        {
        
hLThis hInst;
        
char system[MAX_PATH];
        
GetSystemDirectoryA(system,sizeof(system));
        
strcat_s(system,"\\WSOCK32.dll");
        
hL LoadLibraryA(system);
        if (!
hL) return false;
        
        
//start our things
        
Begin();

        
p[0] = GetProcAddress(hL,"AcceptEx");
        
p[1] = GetProcAddress(hL,"EnumProtocolsA");
        
p[2] = GetProcAddress(hL,"EnumProtocolsW");
        
p[3] = GetProcAddress(hL,"GetAcceptExSockaddrs");
        
p[4] = GetProcAddress(hL,"GetAddressByNameA");
        
p[5] = GetProcAddress(hL,"GetAddressByNameW");
        
p[6] = GetProcAddress(hL,"GetNameByTypeA");
        
p[7] = GetProcAddress(hL,"GetNameByTypeW");
        
p[8] = GetProcAddress(hL,"GetServiceA");
        
p[9] = GetProcAddress(hL,"GetServiceW");
        
p[10] = GetProcAddress(hL,"GetTypeByNameA");
        
p[11] = GetProcAddress(hL,"GetTypeByNameW");
        
p[12] = GetProcAddress(hL,"MigrateWinsockConfiguration");
        
p[13] = GetProcAddress(hL,"NPLoadNameSpaces");
        
p[14] = GetProcAddress(hL,"SetServiceA");
        
p[15] = GetProcAddress(hL,"SetServiceW");
        
p[16] = GetProcAddress(hL,"TransmitFile");
        
p[17] = GetProcAddress(hL,"WEP");
        
p[18] = GetProcAddress(hL,"WSAAsyncGetHostByAddr");
        
p[19] = GetProcAddress(hL,"WSAAsyncGetHostByName");
        
p[20] = GetProcAddress(hL,"WSAAsyncGetProtoByName");
        
p[21] = GetProcAddress(hL,"WSAAsyncGetProtoByNumber");
        
p[22] = GetProcAddress(hL,"WSAAsyncGetServByName");
        
p[23] = GetProcAddress(hL,"WSAAsyncGetServByPort");
        
p[24] = GetProcAddress(hL,"WSAAsyncSelect");
        
p[25] = GetProcAddress(hL,"WSACancelAsyncRequest");
        
p[26] = GetProcAddress(hL,"WSACancelBlockingCall");
        
p[27] = GetProcAddress(hL,"WSACleanup");
        
p[28] = GetProcAddress(hL,"WSAGetLastError");
        
p[29] = GetProcAddress(hL,"WSAIsBlocking");
        
p[30] = GetProcAddress(hL,"WSARecvEx");
        
p[31] = GetProcAddress(hL,"WSASetBlockingHook");
        
p[32] = GetProcAddress(hL,"WSASetLastError");
        
p[33] = GetProcAddress(hL,"WSAStartup"