Requirements:
- Delphi 7 or above
- A brain that can follow instructions
- Basic knowledge of any programming language(Not needed but helps alot)
Ok now to start off, to make .DLL trainers your going to have to understand a few pieces of code. Remember .DLL trainers revolve around the fact that when you inject a .DLL into a process the .DLL can read and write to the process as if it was its own memory.
Ok here is the first code I will teach you:
[i]PBYTE( $00000000 )^ ]
This code is used to write to a static address.
- PBYTE is used to make a reference to a Byte in the memory.
- The Char "$" is used to define the number as hex number, this also where your address goes.
- ^:= Basically means Change the value of the reference and not the reference itself and the 1 is the new value.
Now to write to a 4 byte address then instead of PBYTE you would use PDWORD. For a whole list of possible reference types go here.
Ok so I know now your asking, thats how you would write to the memory then how would you read from it. Well then basically you do it the same way. Heres an example:
Edit1.Text := IntToStr( PBYTE($00000000)^ );
This will set the text of edit box 1 to the value of that byte. IntToStr is used to convert the value from an integer to a string.
Now you have learned how to read and write to static addresses. But wait, how would I write to a pointer? Good question. The following code is used to writing to a pointer.
PBYTE( PBYTE( $00000000 )^ + $0000 )^ := 1;
From what you have learned from the previous lines of code I have showed you, you should be able to understand most of it. Your first Hex Number is the address and the one being added is of course the offset. The new value is the number you put after the "=" Character.
And again to read it into an edit you would do the following:
Edit1.Text := IntToStr( PBYTE( PBYTE( $00000000 )^ + $0000 )^ );
At this point all of this should be self explanatory. Now another thing that you should know when making .DLL trainers or any trainer for that matter is the "Try...Except...Do..." Statement. Why is it so important? Let's say your making a trainer and the user decides to start the hack while the address still doesn't exists, the hack involves writing a value every 250 ms(In other words freezing a value). Since you didn't write a Try statement to handle the "Access Violation" error that your getting then it will resort to its default way of handling it which is popping up an error window every time the error occurs, since its set to write every 250 ms then every 250 ms an error window will pop. If we had a Try statement to handle that certain Exception(error) then this wouldn't happen. Ok now on to code. This is an example of changing the text of an editbox every time the error occurs.
Try
Edit1.Text := IntToStr(PBYTE(PBYTE($00000000)^ + $0000)^);
Except
On E: EAccessViolation Do Edit1.Text := 'Address not found';
end;
Ok short and simple. The first thing is start off the try statement by writing Try. After the try you write you write the code you want to be executed. In this case we are reading the value of a pointer to an edit box. If the address doesn't exist then we normally get the AccessViolation error so after your code write the word Except, Then after that you state on what error, in this case its access violation so we write "On E: EAccessViolation Do" and after the do what you want to happen if this error occurs. In this case set the text of an edit to "Address not found". Then end it with and end statement. It’s simpler doing it than reading it.
Ok now that you know the basics its time to get to the actual trainer making. First off to start off a .DLL trainer you need to go to "File->New->Other-> .DLL Wizard" This should bring a project window. Now replace everything with this:
library Project1;
uses
SysUtils,
Windows,
Classes;
{$R *.res}
var dwTemp: DWORD;
procedure funcStart;
begin
end;
begin
CreateThread(nil,dwTemp,@funcStart,nil,dwTemp,dwTe mp);
end.
This will be your Trainer Template. Now make a new form "File->New->Form".
Now at this point go to the new unit that was creating in the editor. Now go to the part where var's are being declared. It should look like this:
var
Form1: TForm1;
Take note of the form name, in my case its "Form1". Now go back to the project in the editor and go to the first begin end statement. In between put the following code with your form name if its different. Your project should now look like this]library Project1;
uses
SysUtils,
Windows,
Classes,
Unit1 in 'Unit1.pas' {Form1};
{$R *.res}
var dwTemp: DWORD;
procedure funcStart;
begin
Form1 := tForm1.Create(nil);
Form1.ShowModal;
end;
begin
CreateThread(nil,dwTemp,@funcStart,nil,dwTemp,dwTe mp);
end. [/delphi]
Ok now go back to your form and add the following controls:
- 2 Edit Boxes
- 1 Button
- 1 Check Box
- 1 Timer
Ok now to add functionality to all those controls. First were going to take care of the reading. At the time of writing the point to the carat display is:
[i]Address: 0060A6A8
Offset]
So lets add that to our code. Go to your unit and under var we will put:
Const
Carat_Pointer = $0060A6A8;
Offset = $3BB0;
It should now look like this]unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, ExtCtrls, StdCtrls;
type
TForm1 = class(TForm)
GroupBox1: TGroupBox;
Edit1: TEdit;
GroupBox2: TGroupBox;
Edit2: TEdit;
Button1: TButton;
CheckBox1: TCheckBox;
Timer1: TTimer;
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
Const
Carat_Pointer = $0060A6A8;
Offset = $3BB0;
implementation
{$R *.dfm}
end. [/delphi]
Ok go to your form and double click on the timer. This should add this piece of code to your unit]procedure TForm1.Timer1Timer(Sender: TObject);
begin
end; [/delphi]
In between begin and end put the following code:
Try
Edit1.Text := IntToStr(PDWORD(PDWORD(Carat_Pointer)^ + Offset)^);
Except
On E: EAccessViolation Do Edit1.Text := 'Address not found';
end;
This code should be familiar, if you don't understand it go all the way to the top. Now that we are editing the timer we might as well add functionality to the check box. So below that code put]If CheckBox1.Checked = true then Try;
PDWORD(PDWORD(Carat_Pointer)^ + Offset)^ := StrToInt(Edit2.Text)
Except
On E: EAccessViolation Do Edit1.Text := 'Address not found';
end; [/delphi]
Basically this means if checkbox1 is checked then write whatever is in edit2 too the carat pointer. Ok now your code should look like this]unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, ExtCtrls, StdCtrls;
type
TForm1 = class(TForm)
GroupBox1: TGroupBox;
Edit1: TEdit;
GroupBox2: TGroupBox;
Edit2: TEdit;
Button1: TButton;
CheckBox1: TCheckBox;
Timer1: TTimer;
procedure Timer1Timer(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
Const
Carat_Pointer = $0060A6A8;
Offset = $3BB0;
implementation
{$R *.dfm}
procedure TForm1.Timer1Timer(Sender: TObject);
begin
Try
Edit1.Text := IntToStr(PDWORD(PDWORD(Carat_Pointer)^ + Offset)^);
Except
On E: EAccessViolation Do Edit1.Text := 'Address not found';
end;
If CheckBox1.Checked = true then Try;
PDWORD(PDWORD(Carat_Pointer)^ + Offset)^ := StrToInt(Edit2.Text)
Except
On E: EAccessViolation Do Edit1.Text := 'Address not found';
end;
end;
end. [/delphi]
Now there's just 1 thing to add functionality which is the button. Lets double click on the button. Now it should add the following code to the unit:
procedure TForm1.Button1Click(Sender: TObject);
begin
end;
In between that begin and end put the following code]Try
PDWORD(PDWORD(Carat_Pointer)^ + Offset)^ := StrToInt(Edit2.Text)
Except
On E: EAccessViolation Do
Windows.MessageBox(
handle,
'The address was not found',
'Error',
MB_SYSTEMMODAL or MB_SETFOREGROUND or MB_TOPMOST) ;
end; [/delphi]
Ok this is basically the same as the check box but since it doesn't freeze its safe to put an error box. So the code after Do is to make the Message Box. Where it says "Error" is the title and where it says "The address was not found" is the text. Now we are finally done. Your final Project should look something like this]library Project1;
uses
SysUtils,
Windows,
Classes,
Unit1 in 'Unit1.pas' {Form1};
{$R *.res}
var dwTemp: DWORD;
procedure funcStart;
begin
Form1 := tForm1.Create(nil);
Form1.ShowModal;
end;
begin
CreateThread(nil,dwTemp,@funcStart,nil,dwTemp,dwTe mp);
end. [/delphi]
And your final unit should look something like this]unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, ExtCtrls, StdCtrls;
type
TForm1 = class(TForm)
GroupBox1: TGroupBox;
Edit1: TEdit;
GroupBox2: TGroupBox;
Edit2: TEdit;
Button1: TButton;
CheckBox1: TCheckBox;
Timer1: TTimer;
procedure Timer1Timer(Sender: TObject);
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
Const
Carat_Pointer = $0060A6A8;
Offset = $3BB0;
implementation
{$R *.dfm}
procedure TForm1.Timer1Timer(Sender: TObject);
begin
Try
Edit1.Text := IntToStr(PDWORD(PDWORD(Carat_Pointer)^ + Offset)^);
Except
On E: EAccessViolation Do Edit1.Text := 'Address not found';
end;
If CheckBox1.Checked = true then Try;
PDWORD(PDWORD(Carat_Pointer)^ + Offset)^ := StrToInt(Edit2.Text)
Except
On E: EAccessViolation Do Edit1.Text := 'Address not found';
end;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
Try
PDWORD(PDWORD(Carat_Pointer)^ + Offset)^ := StrToInt(Edit2.Text)
Except
On E: EAccessViolation Do
Windows.MessageBox(
handle,
'The address was not found',
'Error',
MB_SYSTEMMODAL or MB_SETFOREGROUND or MB_TOPMOST) ;
end;
end;
end. [/delphi]
If it does, save all your files and compile it (Ctrl + F9). You should find your .DLL where you saved your files in. Congratulations you have now created your first .DLL Trainer.
Note: Pointers and addresses are outdated
© Luig