mirror of
https://github.com/cheat-engine/cheat-engine
synced 2026-08-15 02:26:08 -04:00
675 lines
20 KiB
ObjectPascal
675 lines
20 KiB
ObjectPascal
unit AddAddress;
|
|
|
|
interface
|
|
|
|
uses
|
|
Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
|
|
StdCtrls, ExtCtrls, Menus,cefuncproc,newkernelhandler,symbolhandler;
|
|
|
|
type TPointerInfo=record
|
|
addresstext:tlabel;
|
|
address:Tedit;
|
|
offsettext: tlabel;
|
|
offset: tedit;
|
|
ValueAtAddressText:Tlabel;
|
|
FinalDestination: Tlabel;
|
|
end;
|
|
|
|
type
|
|
TAddForm = class(TForm)
|
|
VarType: TComboBox;
|
|
Button1: TButton;
|
|
Button2: TButton;
|
|
Label1: TLabel;
|
|
Label2: TLabel;
|
|
Description: TEdit;
|
|
Label3: TLabel;
|
|
BitPanel: TPanel;
|
|
RadioButton1: TRadioButton;
|
|
RadioButton2: TRadioButton;
|
|
RadioButton3: TRadioButton;
|
|
RadioButton4: TRadioButton;
|
|
RadioButton5: TRadioButton;
|
|
RadioButton6: TRadioButton;
|
|
RadioButton7: TRadioButton;
|
|
RadioButton8: TRadioButton;
|
|
Label4: TLabel;
|
|
Label5: TLabel;
|
|
Label6: TLabel;
|
|
Label7: TLabel;
|
|
Label8: TLabel;
|
|
Label9: TLabel;
|
|
Label10: TLabel;
|
|
Label11: TLabel;
|
|
Label13: TLabel;
|
|
Label14: TLabel;
|
|
ValuePanel: TPanel;
|
|
Label12: TLabel;
|
|
Edit1: TEdit;
|
|
NewAddress: TEdit;
|
|
Edit2: TEdit;
|
|
cbPointer: TCheckBox;
|
|
Button3: TButton;
|
|
Button4: TButton;
|
|
Timer1: TTimer;
|
|
cbUnicode: TCheckBox;
|
|
procedure FormCreate(Sender: TObject);
|
|
procedure Button2Click(Sender: TObject);
|
|
procedure Button1Click(Sender: TObject);
|
|
procedure VarTypeChange(Sender: TObject);
|
|
procedure FormShow(Sender: TObject);
|
|
procedure NewAddressKeyPress(Sender: TObject; var Key: Char);
|
|
procedure Edit2KeyPress(Sender: TObject; var Key: Char);
|
|
procedure cbPointerClick(Sender: TObject);
|
|
procedure Edit3KeyPress(Sender: TObject; var Key: Char);
|
|
procedure Button4Click(Sender: TObject);
|
|
procedure Button3Click(Sender: TObject);
|
|
procedure Timer1Timer(Sender: TObject);
|
|
private
|
|
{ Private declarations }
|
|
PointerInfo: Array of TPointerInfo;
|
|
procedure offsetKeyPress(Sender: TObject; var Key: Char);
|
|
procedure processaddress;
|
|
public
|
|
{ Public declarations }
|
|
end;
|
|
|
|
var
|
|
AddForm: TAddForm;
|
|
|
|
implementation
|
|
|
|
uses MainUnit, formsettingsunit;
|
|
|
|
{$R *.DFM}
|
|
|
|
procedure taddform.processaddress;
|
|
var i,j,err,err2: integer;
|
|
currentaddress,currentaddress2,currentoffset: dword;
|
|
read:dword;
|
|
check: boolean;
|
|
begin
|
|
if length(pointerinfo)=0 then exit;
|
|
|
|
|
|
for i:=length(pointerinfo)-1 downto 0 do
|
|
begin
|
|
try
|
|
currentaddress:=symhandler.getaddressfromname(pointerinfo[i].address.Text);
|
|
err:=0;
|
|
except
|
|
err:=1;
|
|
end;
|
|
|
|
|
|
if err>0 then
|
|
begin
|
|
//everything after this address is wrong
|
|
pointerinfo[i].ValueAtAddressText.Caption:='This pointer points to address ????????';
|
|
pointerinfo[i].FinalDestination.Caption:='The offset you chose brings it to ????????';
|
|
newaddress.text:='????????';
|
|
|
|
for j:=i-1 downto 0 do
|
|
begin
|
|
pointerinfo[j].address.text:='Result of next pointer';
|
|
pointerinfo[j].ValueAtAddressText.Caption:='This pointer points to address ????????';
|
|
pointerinfo[j].FinalDestination.Caption:='The offset you chose brings it to ????????';
|
|
end;
|
|
exit;
|
|
end;
|
|
|
|
//still here so that address was right
|
|
|
|
check:=readprocessmemory(processhandle,pointer(currentaddress),@currentaddress2,4,read);
|
|
|
|
if length(pointerinfo[i].offset.text)>0 then
|
|
begin
|
|
if pointerinfo[i].offset.text[1]='-' then
|
|
val('-$'+copy(pointerinfo[i].offset.text,2,length(pointerinfo[i].offset.text)),currentoffset,err2)
|
|
else
|
|
val('$'+pointerinfo[i].offset.text,currentoffset,err2);
|
|
end else err2:=1;
|
|
|
|
if (not check) or (read<4) or (err2>0) then
|
|
begin
|
|
//everything after this address is wrong
|
|
if (check) or (read=4) then
|
|
pointerinfo[i].ValueAtAddressText.Caption:='This pointer points to address '+IntToHex(currentaddress2,8)
|
|
else
|
|
pointerinfo[i].ValueAtAddressText.Caption:='This pointer points to address ????????';
|
|
|
|
pointerinfo[i].FinalDestination.Caption:='The offset you chose brings it to ????????';
|
|
newaddress.text:='????????';
|
|
|
|
for j:=i-1 downto 0 do
|
|
begin
|
|
pointerinfo[j].address.text:='Result of next pointer';
|
|
pointerinfo[j].ValueAtAddressText.Caption:='This pointer points to address ????????';
|
|
pointerinfo[j].FinalDestination.Caption:='The offset you chose brings it to ????????';
|
|
end;
|
|
exit;
|
|
end;
|
|
|
|
|
|
//address+offset are correct AND the address is readable
|
|
pointerinfo[i].ValueAtAddressText.Caption:='This pointer points to address '+IntToHex(currentAddress2,8);
|
|
pointerinfo[i].FinalDestination.Caption:='The offset you chose brings it to '+IntToHex(currentAddress2+currentoffset,8);
|
|
|
|
if i=0 then
|
|
newaddress.text:=IntToHex(currentaddress2+currentoffset,8)
|
|
else
|
|
pointerinfo[i-1].address.text:=IntToHex(currentaddress2+currentoffset,8);
|
|
|
|
end;
|
|
|
|
end;
|
|
|
|
|
|
procedure TaddForm.offsetKeyPress(sender: TObject; var key:char);
|
|
begin
|
|
if key<>'-' then hexadecimal(key);
|
|
if cbpointer.Checked then timer1.Interval:=1;
|
|
end;
|
|
|
|
procedure TAddForm.FormCreate(Sender: TObject);
|
|
begin
|
|
vartype.ItemIndex:=3;
|
|
edit2.Text:='1';
|
|
NewAddress.text:='00400000';
|
|
cbunicode.Checked:=false;
|
|
end;
|
|
|
|
procedure TAddForm.Button2Click(Sender: TObject);
|
|
begin
|
|
AddForm.close;
|
|
end;
|
|
|
|
procedure TAddForm.Button1Click(Sender: TObject);
|
|
var i,j,error: Integer;
|
|
address: Dword;
|
|
bit: Byte;
|
|
vartype2: byte;
|
|
nrofbits: integer;
|
|
|
|
pt: dword;
|
|
offsets: array of integer;
|
|
|
|
interpretedpointer: string;
|
|
list: tstringlist;
|
|
baseaddress: string;
|
|
|
|
off: string;
|
|
tempoff: dword;
|
|
|
|
begin
|
|
{
|
|
5.4: Parse the string and see if it complies to the [[[[xxxx+xx]+xx]+xx]+xx] form, and if so, change it to a pointer of this type before progressing
|
|
}
|
|
list:=tstringlist.Create;
|
|
try
|
|
if symhandler.ParseAsPointer(newaddress.text,list) then
|
|
begin
|
|
cbpointer.Checked:=true;
|
|
|
|
baseaddress:=list[0];
|
|
setlength(offsets,list.count-1);
|
|
for i:=1 to list.Count-1 do //start from the first offset
|
|
begin
|
|
off:=copy(list[i],2,length(list[i]));
|
|
try
|
|
offsets[i-1]:=strtoint('$'+off);
|
|
except
|
|
exit;
|
|
end;
|
|
if list[i][1]='-' then
|
|
offsets[i-1]:=-offsets[i-1];
|
|
end;
|
|
|
|
for i:=1 to length(offsets)-1 do
|
|
button3.Click;
|
|
|
|
for i:=0 to length(offsets)-1 do
|
|
pointerinfo[length(pointerinfo)-1-i].offset.Text:=inttohex(offsets[i],1);
|
|
|
|
|
|
pointerinfo[length(pointerinfo)-1].address.text:=baseaddress;
|
|
exit;
|
|
end;
|
|
finally
|
|
list.free;
|
|
end;
|
|
|
|
setlength(offsets,0);
|
|
pt:=0;
|
|
|
|
if cbpointer.checked then
|
|
begin
|
|
if pointerinfo[length(pointerinfo)-1].address.text='' then raise exception.Create('Please fill in a pointer address');
|
|
|
|
try
|
|
pt:=symhandler.getaddressfromname(pointerinfo[length(pointerinfo)-1].address.text);
|
|
except
|
|
raise exception.Create('The pointer address you filled in isn''t a valid address');
|
|
end;
|
|
|
|
//make sure the offsets are valid
|
|
setlength(offsets,length(pointerinfo));
|
|
for i:=0 to length(pointerinfo)-1 do
|
|
begin
|
|
if (pointerinfo[i].offset.Text<>'') then
|
|
begin
|
|
if pointerinfo[i].offset.Text[1]='-' then
|
|
val('-$'+copy(pointerinfo[i].offset.Text,2,length(pointerinfo[i].offset.Text)-1),offsets[i],error)
|
|
else
|
|
val('$'+pointerinfo[i].offset.Text,offsets[i],error);
|
|
|
|
if error<>0 then raise exception.Create(pointerinfo[i].offset.Text+' is not a valid value');
|
|
end else raise exception.Create('You havn''t filled in all offsets');
|
|
end;
|
|
|
|
try
|
|
address:=symhandler.getaddressfromname(NewAddress.text);
|
|
except
|
|
//don't complain
|
|
end;
|
|
end else address:=symhandler.getaddressfromname(NewAddress.text); //complain when not valid
|
|
|
|
|
|
|
|
if RadioButton1.checked then bit:=0 else
|
|
if RadioButton2.checked then bit:=1 else
|
|
if RadioButton3.checked then Bit:=2 else
|
|
if RadioButton4.checked then Bit:=3 else
|
|
if RadioButton5.checked then Bit:=4 else
|
|
if RadioButton6.checked then Bit:=5 else
|
|
if RadioButton7.checked then Bit:=6 else
|
|
Bit:=7;
|
|
|
|
try
|
|
nrofbits:=StrToInt(edit2.Text);
|
|
except
|
|
raise exception.Create(edit2.Text+' is not a valid number');
|
|
end;
|
|
|
|
if valuepanel.visible then
|
|
begin
|
|
try
|
|
bit:=strtoint(edit1.Text);
|
|
except
|
|
raise exception.Create(edit1.text+' is not a valid value');
|
|
end;
|
|
end;
|
|
|
|
case vartype.Itemindex of
|
|
0 : VarType2:=5;
|
|
1 : VarType2:=0;
|
|
2 : VarType2:=1;
|
|
3 : VarType2:=2;
|
|
4 : VarType2:=6;
|
|
5 : VarType2:=3;
|
|
6 : VarType2:=4;
|
|
7 : Vartype2:=7;
|
|
8 : VarType2:=8;
|
|
else vartype2:=0;
|
|
end;
|
|
|
|
i:=mainform.NumberOfRecords;
|
|
|
|
|
|
|
|
if i=MainForm.NumberOfRecords then
|
|
begin
|
|
inc(MainForm.NumberOfRecords);
|
|
|
|
mainform.reserveMem;
|
|
|
|
if description.text='' then
|
|
mainform.memrec[MainForm.NumberOfRecords-1].Description:='No description'
|
|
else
|
|
mainform.memrec[MainForm.NumberOfRecords-1].Description:=description.text;
|
|
|
|
|
|
mainform.memrec[MainForm.NumberOfRecords-1].Address:=address;
|
|
mainform.memrec[MainForm.NumberOfRecords-1].interpretableaddress:=newaddress.text;
|
|
|
|
|
|
// mainform.memrec[MainForm.NumberOfRecords-1].VarType:=Vartype.itemindex;
|
|
//
|
|
mainform.memrec[MainForm.NumberOfRecords-1].VarType:=vartype2;
|
|
|
|
mainform.memrec[MainForm.NumberOfRecords-1].Bit:=bit;
|
|
mainform.memrec[MainForm.NumberOfRecords-1].bitlength:=nrofbits;
|
|
mainform.memrec[MainForm.NumberOfRecords-1].unicode:=cbunicode.Checked;
|
|
|
|
|
|
|
|
{add pointer stuff}
|
|
mainform.memrec[MainForm.NumberOfRecords-1].IsPointer:=cbpointer.Checked;
|
|
setlength(mainform.memrec[mainform.NumberOfRecords-1].pointers,length(pointerinfo));
|
|
|
|
for i:=0 to length(pointerinfo)-1 do
|
|
begin
|
|
if i=length(pointerinfo)-1 then
|
|
begin
|
|
mainform.memrec[mainform.NumberOfRecords-1].pointers[i].Interpretableaddress:=pointerinfo[length(pointerinfo)-1].address.text;
|
|
mainform.memrec[mainform.NumberOfRecords-1].pointers[i].Address:=pt;
|
|
end;
|
|
|
|
mainform.memrec[mainform.NumberOfRecords-1].pointers[i].offset:=offsets[i];
|
|
end;
|
|
|
|
|
|
|
|
mainform.memrec[MainForm.NumberOfRecords-1].Frozen:=false;
|
|
mainform.memrec[MainForm.NumberOfRecords-1].FrozenValue:=0;
|
|
MainForm.FrozenFvalue[MainForm.NumberOfRecords-1]:=0;
|
|
mainform.FrozenStrings[MainForm.NumberOfRecords-1]:='';
|
|
mainform.Hotkeystrings[Mainform.NumberOfRecords-1]:='';
|
|
mainform.Hotkeys[MainForm.NumberOfRecords-1]:=-1;
|
|
|
|
MainForm.UpdateScreen;
|
|
MainForm.updatelist;
|
|
|
|
addform.close;
|
|
end else showmessage('This address is already in the list');
|
|
end;
|
|
|
|
procedure TAddForm.VarTypeChange(Sender: TObject);
|
|
begin
|
|
bitpanel.Visible:=Vartype.itemindex=0;
|
|
if vartype.ItemIndex=7 then
|
|
begin
|
|
valuepanel.visible:=true;
|
|
valuepanel.BringToFront;
|
|
label12.Caption:='Nr. of Characters';
|
|
end
|
|
else if vartype.itemindex=8 then
|
|
begin
|
|
valuepanel.visible:=true;
|
|
label12.Caption:='Nr. of Bytes';
|
|
end
|
|
else valuepanel.visible:=false;
|
|
end;
|
|
|
|
procedure TAddForm.FormShow(Sender: TObject);
|
|
begin
|
|
addform.cbPointer.checked:=false;
|
|
NewAddress.SetFocus;
|
|
NewAddress.SelectAll;
|
|
description.Text:='No description';
|
|
end;
|
|
|
|
procedure TAddForm.NewAddressKeyPress(Sender: TObject; var Key: Char);
|
|
begin
|
|
if cbpointer.checked then timer1.Interval:=1;
|
|
end;
|
|
|
|
procedure TAddForm.Edit2KeyPress(Sender: TObject; var Key: Char);
|
|
begin
|
|
decimal(key);
|
|
end;
|
|
|
|
procedure TAddForm.cbPointerClick(Sender: TObject);
|
|
var i: integer;
|
|
startoffset,inputoffset,rowheight: integer;
|
|
begin
|
|
if cbpointer.checked then
|
|
begin
|
|
|
|
newaddress.Enabled:=false;
|
|
|
|
button3.visible:=true;
|
|
button4.visible:=true;
|
|
|
|
//create a address+offset combination and disable the normal address
|
|
startoffset:=button3.Top+button3.Height+2;
|
|
|
|
setlength(pointerinfo,1);
|
|
pointerinfo[length(pointerinfo)-1].ValueAtAddressText:=TLabel.Create(self);
|
|
with pointerinfo[length(pointerinfo)-1].ValueAtAddressText do
|
|
begin
|
|
top:=startoffset;
|
|
left:=4;
|
|
caption:='This pointer points to address ????????.';// The offset you chose brings it to ????????';
|
|
showhint:=true;
|
|
onkeypress:=offsetKeyPress;
|
|
parent:=self;
|
|
end;
|
|
|
|
pointerinfo[length(pointerinfo)-1].FinalDestination:=TLabel.Create(self);
|
|
with pointerinfo[length(pointerinfo)-1].FinalDestination do
|
|
begin
|
|
top:=startoffset;
|
|
left:=pointerinfo[length(pointerinfo)-1].ValueAtAddressText.left+pointerinfo[length(pointerinfo)-1].ValueAtAddressText.width+20;
|
|
caption:='The offset you chose brings it to ????????';
|
|
showhint:=true;
|
|
onkeypress:=offsetKeyPress;
|
|
parent:=self;
|
|
end;
|
|
|
|
inputoffset:=startoffset+pointerinfo[length(pointerinfo)-1].ValueAtAddressText.height;
|
|
|
|
pointerinfo[length(pointerinfo)-1].addresstext:=Tlabel.Create(self);
|
|
with pointerinfo[length(pointerinfo)-1].addresstext do
|
|
begin
|
|
top:=inputoffset+2;
|
|
left:=4;
|
|
caption:='Address of pointer';
|
|
parent:=self;
|
|
end;
|
|
|
|
pointerinfo[length(pointerinfo)-1].address:=TEdit.create(self);
|
|
with pointerinfo[length(pointerinfo)-1].address do
|
|
begin
|
|
top:=inputoffset;
|
|
left:=pointerinfo[length(pointerinfo)-1].addresstext.left+pointerinfo[length(pointerinfo)-1].addresstext.width+3;
|
|
width:=105;
|
|
onkeypress:=newaddress.onkeypress;
|
|
parent:=self;
|
|
end;
|
|
|
|
pointerinfo[length(pointerinfo)-1].offsettext:=Tlabel.create(self);
|
|
with pointerinfo[length(pointerinfo)-1].offsettext do
|
|
begin
|
|
top:=inputoffset+2;
|
|
left:=pointerinfo[length(pointerinfo)-1].FinalDestination.left;
|
|
caption:='Offset (Hex)';
|
|
parent:=self;
|
|
end;
|
|
|
|
pointerinfo[length(pointerinfo)-1].offset:=TEdit.create(self);
|
|
with pointerinfo[length(pointerinfo)-1].offset do
|
|
begin
|
|
top:=inputoffset;
|
|
left:=pointerinfo[length(pointerinfo)-1].offsettext.left+pointerinfo[length(pointerinfo)-1].offsettext.width+5;
|
|
width:=70;
|
|
text:='0';
|
|
hint:='Fill in the nr. of bytes after the location the pointer points to';
|
|
showhint:=true;
|
|
onkeypress:=offsetKeyPress;
|
|
parent:=self;
|
|
end;
|
|
|
|
|
|
|
|
|
|
rowheight:=pointerinfo[length(pointerinfo)-1].ValueAtAddressText.height;
|
|
rowheight:=rowheight+pointerinfo[length(pointerinfo)-1].address.height;
|
|
inc(rowheight,2);
|
|
|
|
height:=height+rowheight+button3.Height+5;
|
|
end
|
|
else
|
|
begin
|
|
clientheight:=cbPointer.Top+cbPointer.Height+8+button1.Height+8;
|
|
newaddress.enabled:=true;
|
|
button3.visible:=false;
|
|
button4.visible:=false;
|
|
|
|
for i:=0 to length(PointerInfo)-1 do
|
|
begin
|
|
pointerinfo[i].addresstext.free;
|
|
pointerinfo[i].address.Free;
|
|
pointerinfo[i].offsettext.Free;
|
|
pointerinfo[i].offset.Free;
|
|
pointerinfo[i].ValueAtAddressText.Free;
|
|
pointerinfo[i].FinalDestination.Free;
|
|
end;
|
|
|
|
setlength(pointerinfo,0);
|
|
|
|
end;
|
|
|
|
end;
|
|
|
|
procedure TAddForm.Edit3KeyPress(Sender: TObject; var Key: Char);
|
|
begin
|
|
if key<>'-' then hexadecimal(key);
|
|
end;
|
|
|
|
procedure TAddForm.Button4Click(Sender: TObject);
|
|
var
|
|
rowheight: integer;
|
|
i: integer;
|
|
oldmethod: boolean;
|
|
begin
|
|
if length(pointerinfo)=1 then cbPointer.checked:=false
|
|
else
|
|
begin
|
|
rowheight:=pointerinfo[length(pointerinfo)-1].ValueAtAddressText.height;
|
|
rowheight:=rowheight+pointerinfo[length(pointerinfo)-1].address.height;
|
|
inc(rowheight,2);
|
|
|
|
pointerinfo[length(pointerinfo)-2].address.enabled:=true;
|
|
|
|
oldmethod:=formsettings.cbOldPointerAddMethod.checked;
|
|
if (((GetKeyState(VK_CONTROL) shr 15) and 1)=1) then oldmethod:=not oldmethod;
|
|
if not oldmethod then
|
|
begin
|
|
pointerinfo[length(pointerinfo)-2].address.text:=pointerinfo[length(pointerinfo)-1].address.text;
|
|
for i:=0 to length(pointerinfo)-2 do
|
|
pointerinfo[i].offset.text:=pointerinfo[i+1].offset.text;
|
|
end
|
|
else
|
|
pointerinfo[length(pointerinfo)-2].address.text:='';
|
|
|
|
pointerinfo[length(pointerinfo)-1].addresstext.free;
|
|
pointerinfo[length(pointerinfo)-1].address.free;
|
|
pointerinfo[length(pointerinfo)-1].offsettext.free;
|
|
pointerinfo[length(pointerinfo)-1].offset.free;
|
|
pointerinfo[length(pointerinfo)-1].valueataddresstext.free;
|
|
pointerinfo[length(pointerinfo)-1].FinalDestination.free;
|
|
|
|
|
|
setlength(pointerinfo,length(pointerinfo)-1);
|
|
height:=height-rowheight;
|
|
|
|
end;
|
|
end;
|
|
|
|
procedure TAddForm.Button3Click(Sender: TObject);
|
|
var
|
|
rowheight: integer;
|
|
i: integer;
|
|
oldaddress: string;
|
|
oldmethod: boolean;
|
|
begin
|
|
rowheight:=pointerinfo[length(pointerinfo)-1].ValueAtAddressText.height;
|
|
rowheight:=rowheight+pointerinfo[length(pointerinfo)-1].address.height;
|
|
inc(rowheight,2);
|
|
|
|
oldaddress:=pointerinfo[length(pointerinfo)-1].address.text;
|
|
pointerinfo[length(pointerinfo)-1].address.text:='result of next pointer';
|
|
pointerinfo[length(pointerinfo)-1].address.enabled:=false;
|
|
|
|
setlength(pointerinfo,length(pointerinfo)+1);
|
|
|
|
pointerinfo[length(pointerinfo)-1].addresstext:=Tlabel.Create(self);
|
|
with pointerinfo[length(pointerinfo)-1].addresstext do
|
|
begin
|
|
top:=pointerinfo[length(pointerinfo)-2].addresstext.top+rowheight;
|
|
left:=4;
|
|
caption:='Address of pointer';
|
|
parent:=self;
|
|
end;
|
|
|
|
pointerinfo[length(pointerinfo)-1].address:=TEdit.create(self);
|
|
with pointerinfo[length(pointerinfo)-1].address do
|
|
begin
|
|
top:=pointerinfo[length(pointerinfo)-2].address.top+rowheight;
|
|
left:=pointerinfo[length(pointerinfo)-2].address.left;
|
|
width:=105;
|
|
onkeypress:=newaddress.onkeypress;
|
|
parent:=self;
|
|
end;
|
|
|
|
pointerinfo[length(pointerinfo)-1].offsettext:=Tlabel.create(self);
|
|
with pointerinfo[length(pointerinfo)-1].offsettext do
|
|
begin
|
|
top:=pointerinfo[length(pointerinfo)-2].offsettext.top+rowheight;
|
|
left:=pointerinfo[length(pointerinfo)-2].offsettext.left;
|
|
caption:='Offset (Hex)';
|
|
parent:=self;
|
|
end;
|
|
|
|
pointerinfo[length(pointerinfo)-1].offset:=TEdit.create(self);
|
|
with pointerinfo[length(pointerinfo)-1].offset do
|
|
begin
|
|
top:=pointerinfo[length(pointerinfo)-2].offset.top+rowheight;
|
|
left:=pointerinfo[length(pointerinfo)-2].offset.left;
|
|
width:=70;
|
|
text:='0';
|
|
hint:='Fill in the nr. of bytes after the location the pointer points to';
|
|
showhint:=true;
|
|
onkeypress:=offsetKeyPress;
|
|
parent:=self;
|
|
end;
|
|
|
|
pointerinfo[length(pointerinfo)-1].ValueAtAddressText:=TLabel.Create(self);
|
|
with pointerinfo[length(pointerinfo)-1].ValueAtAddressText do
|
|
begin
|
|
top:=pointerinfo[length(pointerinfo)-2].ValueAtAddressText.top+rowheight;
|
|
left:=pointerinfo[length(pointerinfo)-2].ValueAtAddressText.left;
|
|
caption:='This pointer points to address ????????.';// The offset you chose brings it to ????????';
|
|
showhint:=true;
|
|
onkeypress:=offsetKeyPress;
|
|
parent:=self;
|
|
end;
|
|
|
|
pointerinfo[length(pointerinfo)-1].FinalDestination:=TLabel.Create(self);
|
|
with pointerinfo[length(pointerinfo)-1].FinalDestination do
|
|
begin
|
|
top:=pointerinfo[length(pointerinfo)-2].FinalDestination.top+rowheight;
|
|
left:=pointerinfo[length(pointerinfo)-2].FinalDestination.left;
|
|
caption:='The offset you chose brings it to ????????';
|
|
showhint:=true;
|
|
onkeypress:=offsetKeyPress;
|
|
parent:=self;
|
|
end;
|
|
|
|
oldmethod:=formsettings.cbOldPointerAddMethod.checked;
|
|
if (((GetKeyState(VK_CONTROL) shr 15) and 1)=1) then oldmethod:=not oldmethod;
|
|
if not oldmethod then
|
|
begin
|
|
for i:=length(pointerinfo)-1 downto 1 do
|
|
pointerinfo[i].offset.Text:=pointerinfo[i-1].offset.text;
|
|
|
|
pointerinfo[0].offset.Text:='0';
|
|
pointerinfo[length(pointerinfo)-1].address.Text:=oldaddress;
|
|
end;
|
|
|
|
height:=height+rowheight;
|
|
end;
|
|
|
|
procedure TAddForm.Timer1Timer(Sender: TObject);
|
|
begin
|
|
timer1.Interval:=1000;
|
|
if visible and cbpointer.checked then
|
|
processaddress;
|
|
end;
|
|
|
|
end.
|
|
|
|
|
|
|
|
|