| Autor |
Beitrag |
_eddy
Hält's aus hier
Beiträge: 6
|
Verfasst: So 24.06.07 01:58
Hallo Jungs und Mädels
Ich habe hier ein Problem, und zwar wollte ich per WriteProcessMemory einen Wert (halt in die Memory) schreiben. Hat auch soweit geklappt. Aber nur, wenn die Werte hardcodet waren (also im Programmcode schon implementiert).
Ich wollte dann später den Benutzer die Eingabe wählen lassen.
Zur Vorgeschichte:
Ich mache einen Trainer für MineSweeper
Naja, ich kann bis jetzt die Zeit auslesen, schreiben, einfrieren usw. Was halt nicht funktionieren will ist, den User die Zeit auswählen zu lassen, welches bei Minesweeper gesetzt werden soll.
Ich habe mir hier eine Funktion geschrieben:
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16:
| function InjectMemory(title: string; wheretowrite: Pointer; whattowrite: PChar; size: integer): integer; var c: cardinal; write: cardinal; begin c := FindWindow(nil,PChar(title)); if (c = 0) then begin result := 1; exit; end; GetWindowThreadProcessId(c, @c); c := OpenProcess(PROCESS_ALL_ACCESS, False, c); WriteProcessMemory(c,wheretowrite, whattowrite, size, write); CloseHandle(c); result := 0; end; |
Es macht halt nichts weiteres, als den Wert in die Memory zu schreiben. Ich rufe es wie folgt auf:
| Zitat: |
InjectMemory('MineSweeper',Ptr($1002FF5),chr($90)+chr($90)+chr($90)+chr($90)+chr($90)+chr($90),6);
|
Ich wähle halt den Titel der Anwendung, den Pointer zur Adresse, den Wert der geschrieben werden soll (in diesem Beispiel wird geNOPed) und die Länge. Das funktioniert halt alles auch, nur was nicht funktionieren will, ist sowas hier:
| Zitat: |
InjectMemory('MineSweeper',Ptr($100579C),Edit1.text[1]+Chr(0)+Chr(0)+Chr(0),4);
|
Dann erscheint die Fehlermeldung:
| Zitat: |
[Error] Unit1.pas(297): Incompatible types: 'ShortString' and 'PAnsiChar'
|
Ich weiß nicht wieso der bei so etwas streikt, oder wie der überhaupt auf ShortString kommt ?! Edit1.text[1] wäre ja hier ein String (oder halt Char), und was meine Funktion will ist ein PChar. Ich weiß nur, das Delphi selbst entscheidet ob er nun für String AnsiString oder ShortString nehmen soll.
Ich habe schon viele viele Varianten Probiert (Edit1.text in int umwandeln, es in ein byte speichern, in PChar umwandeln, einen AnsiString verwenden usw.)
Naja, wie auch immer, ich habs dann später so gelöst, dass ich aus ShortString einen String gemacht habe, und diesen dann zu PChar umgewandelt habe :S War schlecht gelöst, hat aber geklappt. Der Nachteil ist nun, ich kann nur eine Zahl die bis 255 reicht auswählen (kein Wunder, ShortString geht ja auch nur bis 255).
Weiß irgendeiner Rat?! Ich habe echt keine Ahnung mehr was ich noch machen kann... Moderiert von Gausi: Topic aus Dateizugriff verschoben am So 24.06.2007 um 10:22
|
|
Gausi
      
Beiträge: 8554
Erhaltene Danke: 480
Windows 7, Windows 10
D7 PE, Delphi XE3 Prof, Delphi 10.3 CE
|
Verfasst: So 24.06.07 10:18
Hallo und  in der Entwickler-Ecke!
Reicht da nicht ein einfacher Typecast?
InjectMemory('MineSweeper',Ptr($100579C),PChar(Edit1.text[1]+Chr(0)+Chr(0)+Chr(0)),4); 
_________________ We are, we were and will not be.
|
|
_eddy 
Hält's aus hier
Beiträge: 6
|
Verfasst: So 24.06.07 14:12
Hallo Gausi,
Nein das hatte ich auch schon öfters versucht. Dann erscheint auch ein anderer Error, nämlich:
| Zitat: |
[Error] Unit1.pas(297): Invalid typecast |
Und wenn ich nur den Edit1.text[1] zu PChar mache, erscheint folgendes:
| Zitat: |
[Error] Unit1.pas(297): Incompatible types: 'String' and 'PAnsiChar' |
*verzweifelt*
|
|
jakobwenzel
      
Beiträge: 1889
Erhaltene Danke: 1
XP home, ubuntu
BDS 2006 Prof
|
Verfasst: So 24.06.07 15:01
Probier mal, das ganze in nem String zwischenzuspeicehrn:
Delphi-Quelltext 1: 2: 3: 4:
| var s:String; begin s:=Edit1.text[1]+Chr(0)+Chr(0)+Chr(0); InjectMemory('MineSweeper',Ptr($100579C),PChar(s),4); |
_________________ I thought what I'd do was, I'd pretend I was one of those deaf-mutes.
|
|
_eddy 
Hält's aus hier
Beiträge: 6
|
Verfasst: So 24.06.07 16:20
Hallo Jakob,
Ja, das funktioniert zwar, aber leider wieder nur bis 255. Also, wenn ich genauso mache wie in deinem Beispiel nimmt der natürlich, bei der Eingabe "123" die "1" und das ist in der ASCII Tabelle die Zahl 49  Habs dann so versucht:
Delphi-Quelltext 1:
| s:=chr(strtoint(Edit1.text))+Chr(0)+Chr(0)+Chr(0); |
Jetzt funktionierts zwar, aber halt nur bis 255 *kopfkratz* Langsam glaube ich, das liegt an Chr? Kann ich das auch irgendwie anders lösen?!
Oder vielleicht liegt das daran, dass ich versuche mehr als 255 in ein Byte zu speichern? o_O Aber in den nächsten "Chr(0)" kann ich leider keine weitere Zahl hinspeichern
Weiß einer Rat?
//edit:
Ich merke gerade, dass es an Chr liegen MUSS (oder halt an dem Typ Byte) da man es auch nicht im Programm selber höher als 255 setzen kann:
Delphi-Quelltext 1:
| s:=Chr(700)+Chr(0)+Chr(0)+Chr(0); |
Funktioniert z.B. auch nicht.
|
|
GTA-Place
      

Beiträge: 5248
Erhaltene Danke: 2
WIN XP, IE 7, FF 2.0
Delphi 7, Lazarus
|
Verfasst: So 24.06.07 16:37
Es gibt ja auch nur 256 ASCII-Zeichen (0 - 255).
_________________ "Wer Ego-Shooter Killerspiele nennt, muss konsequenterweise jeden Horrorstreifen als Killerfilm bezeichnen." (Zeit.de)
|
|
uall@ogc
      
Beiträge: 1826
Erhaltene Danke: 11
Win 2000 & VMware
Delphi 3 Prof, Delphi 7 Prof
|
Verfasst: So 24.06.07 16:39
1) solltest du keinen PChar nehmen, da der kein #0 entahlten darf. Sollte zwar so wie du es hast kein Problem machen aber WhatToWrite soltle bm typ Pointer sein (ist Pchar eigentlich auch)
was du schreiben willst muss halt in einen String (der kann #0 enthalten)
und dann übergibst du das mit @s[1]
2) ein Byte kann nur Werte von 0 bis 255 annehmen, chhr oder char wandelt einen charachter (ASCII Wert) in ein Byte um, was eben nur 255 groß sein kann. willst du also einen wert wie 1000 in den speicher schreiben, so wird es sich um ein word oder dword handeln. den bekommst du mit
setlength(s,length(s)+4) // dword
PDWord(@s[length(s)-4])^ := StrToInt(edit1.text);
in einen string. Weiß jetzt auch keinen einfachereren Weg, aber hab auch was getrunken und keine Lust mir dadrüber nu den Kopf zu zerbrechen ^^
_________________ wer andern eine grube gräbt hat ein grubengrabgerät
- oder einfach zu viel zeit
|
|
_eddy 
Hält's aus hier
Beiträge: 6
|
Verfasst: So 24.06.07 17:37
Hallo,
Danke Leute, jetzt klappt alles wunderbar
Delphi-Quelltext 1: 2: 3:
| setlength(s,length(s)+4); PDWord(@s[1])^ := StrToInt(edit1.text); InjectMemoryS('MineSweeper',Ptr($100579C),@s[1],4); |
Muss jetzt nur noch herausfinden was ich dort GENAU gemacht habe
Wieso muss ich erst einen DWord-Pointer zu s[1] zeigen lassen, und dann erst den Wert verändern o_O Der String bleibt doch ein String, oder wie jetzt? *total verwirrt ist*
|
|
uall@ogc
      
Beiträge: 1826
Erhaltene Danke: 11
Win 2000 & VMware
Delphi 3 Prof, Delphi 7 Prof
|
Verfasst: So 24.06.07 19:31
Es soll ja genau die Werte annehmen. Mit PDword kannst du also 4 Chars in dem String ändern. Die sollen also genau den Integerwert annehmen. Wenn du dem String direkt nen Integer zuweist dann steht darin die Hexwerte der Zeichen, nicht aber der Integer wert selbst.
Bisl kompliziert, gib einfach den String aus dann siehst du es ;P
_________________ wer andern eine grube gräbt hat ein grubengrabgerät
- oder einfach zu viel zeit
|
|
_eddy 
Hält's aus hier
Beiträge: 6
|
Verfasst: So 24.06.07 20:38
Hm, habs immernoch nicht wirklich verstanden.
Aber, wo ist denn die Grenze von Dword ?! Dword = 4 Byte , also 1024 ?!
Also, versteh ich das Richtig, das PDWord als Parameter einen Pointer möchte, und wiederum einen Pointer zurück liefert, wessen inhalt aber nun ein DWord geworden ist?! Dann würde ich die Codezeile in etwa verstehen ^^
|
|
uall@ogc
      
Beiträge: 1826
Erhaltene Danke: 11
Win 2000 & VMware
Delphi 3 Prof, Delphi 7 Prof
|
Verfasst: So 24.06.07 21:51
Ne DWORD = 4byte = 2^32 = xx millonen oder mehr ;P
PDWORD ist ein Pointer auf ein DWord. Ich caste den String (@s) als DWord (@=Pointer) und setze den Wert mit ^
Sozusagen ist es ein Pointer als Parameter auch wenns einfach nen Typecast ist ;P
_________________ wer andern eine grube gräbt hat ein grubengrabgerät
- oder einfach zu viel zeit
|
|
_eddy 
Hält's aus hier
Beiträge: 6
|
Verfasst: Mo 25.06.07 01:20
OK, danke. Habs jetzt einigermaßen verstanden 
|
|
|