![]() |
Generic <T>, injected DLL, was aus Speicher auslesen?
Hallo,
kurze Frage, ist es möglich mittels <T> etwas aus dem Speicher auszulesen, ohne ReadProcessMemory? Da ich mich im gleichen Prozess befinde möchte ich natürlich darauf verzichten. Normalerweise würde es ja bei Integern z.B. so aussehen:
Delphi-Quellcode:
Wie würde ich bei einer Funktion mit T vorgehen? Ist mein Vorhaben überhaupt so einfach realisierbar?
i := PInteger($123456)^
Beispiel:
Delphi-Quellcode:
Gruß
function GetMem<T>(Offset: NativeUInt): T;
begin end; edit: Habe es schon gelöst bekommen, einfacher als gedacht :)
Delphi-Quellcode:
function GetMem<T>(Offset: NativeUInt): T;
type PT = ^T; begin result := PT(Offset)^ end; |
AW: Generic <T>, injected DLL, was aus Speicher auslesen?
Jain, das ist fast möglich, oder kann Delphi inzwischen doch schon generischen Prozeduren?
Und wenn nicht, dann solltest du im Profil, oder nächstes Mal im Post, mit angeben, für welchen Compiler du etwas suchst. Aber wenn du deine Funktion in eine Klasse verlagerst, wo es auch eine Klassenmethode sein kann, welche als Static im Kompilat praktisch genauso auferufen wird, wie eine entsprechende "normale" Funktion, dann ginge es. Wieso eigentlich Offset? OK, zum nil wäre es ein Offset, aber im Prinzip gibst du doch direkt deine Adresse an.
Delphi-Quellcode:
Nur wozu soll das Ganze gut sein?
class function TMyClass.GetMem<T>(Addr: Pointer): T; // Nja, oder zumindestens auch nochmal mit NativeUInt überladen.
type PT = ^T; // oder als public/private type direkt oben in der Klassendefinition begin Result := PT(Offset)^; end; // geht eventuell auch "direkt" class function TMyClass.GetMem<T>(Addr: Pointer): T; begin Result := T(Offset^); end; Ohne z.B. auch noch eine Typ-Konvertierung (ala Byte zu Integer oder String), ist das doch etwas "umständlich"? Also im Gegensatz zum direkten Cast? Vorallem ohne "inline" sind hier nun unnötige Codesprünge und bei Typen womöglich auch noch unnötige Speicheroperationen. (Referenzzählung von String und Interface, oder gar komplette Kopien, wie z.B. beim WideString)
Delphi-Quellcode:
i := PInteger($123456)^;
i := {TMyClass.}GetMem<Integer>($123456); |
AW: Generic <T>, injected DLL, was aus Speicher auslesen?
Hi himitsu,
Zitat:
Ich lese praktisch ein Array eines anderen Programms aus. In diesem Array sind Pointer die dann eben auf den eigentlichen Wert zeigen, und der kann unterschiedlich groß sein. Momentan kann ich damit ganz komfortabel darauf zugreifen. Steckt man das obige Beispiel so in eine Klasse sollte es ja keine Probleme geben. edit: oh ein edit
Delphi-Quellcode:
Funktioniert so leider nicht. NativeUInt habe ich so nur im Beispiel verwendet, ich gebe in Wirklichkeit den Index des Array an.
class function TMyClass.GetMem<T>(Addr: Pointer): T;
begin Result := T(Offset^); end; Gruß |
AW: Generic <T>, injected DLL, was aus Speicher auslesen?
Zitat:
Ach ja, ich hatte meinen letzten Beitrag in der Zwischenzeit nochmal bearbeitet ... war wohl nur etwas langsam dabei. :stupid: Und zum Array:
Delphi-Quellcode:
Das entspricht quasi einem
type
// diese Array-Typen gibt es manchmal auch vordefiniert (z.B. PByte für Array[] of Byte) // manche Pointer-Typen besitzen auch schon eine integrierte Pointer-Arithmetik, wo man sich das Array sparen kann (z.B. PAnsiChar) TIntegerArray: array[0..0] of Integer; PIntegerArray: ^TIntegerArray; var MyArr: PIntegerArray; MyArr := Pointer($12345678); for i := 0 to 10 of ShowMessage(IntToStr( MyArr[i] ));
Delphi-Quellcode:
var
MyPnt: NativeUInt; MyPnt := $12345678; for i := 0 to 10 of ShowMessage(IntToStr( PInteger(MyPnt + i * SizeOf(Integer))^ )); // wobei den Offset Delphi auch automatisch berechnen kann => siehe oben |
AW: Generic <T>, injected DLL, was aus Speicher auslesen?
Da sehe ich nun das Problem das auch int64 Werte vorhanden sind, daher gefiel mir der Generic eigentlich am Besten.
Wären alles 4 Byte Werte, wäre es ja halb so wild und man könnte schnell 'umcasten'. Vorher habe ich mir den Pointer zum Wert zurückgeben lassen und konnte dann einfach mit PInteger(Pointer)^ den Wert auslesen, optisch finde ich den Generic aber besser. Nur fraglich ob es von der Leistung her auch so toll ist, aber soll mir in einem nur-für-mich Projekt eigentlich egal sein ;) |
AW: Generic <T>, injected DLL, was aus Speicher auslesen?
Wieso sollte Int64 ein Problem sein?
In deinem Generic machst du doch genau das Selbe, nur halt etwas umständlicher weggekapselt. :zwinker: Du castest ja nicht den "Inhalt" des Pointers, welcher in Win32 zufällig 4 Byte ist, sondern das, worauf der Pointer zeigt und da ist die Größe egal. Ein untypisierter Pointer hat quasi eine Größe von 0 Byte und beim Cast auf andere Typen wird dort keine Größenprüfung vom Compier vorgenommen. |
AW: Generic <T>, injected DLL, was aus Speicher auslesen?
Ah verstehe ;)
Finde dennoch es sieht mit Generics ein wenig hübscher und übersichtlicher aus, da ich von sehr vielen Stellen aus darauf zugreife. Denke einen allzu großen Performance-Verlust sollte es da nicht geben, oder? Zumindest sieht der generierte asm Code dazu ganz sauber aus. Wobei es mir eh nicht um jede Nanosekunde geht. ^^ |
AW: Generic <T>, injected DLL, was aus Speicher auslesen?
Wenn du die Funktion als inline deklarierst und der Kompiler in der Lage ist, den Code auch direkt einzubinden, dann könnte es sein, daß der Compiler Vieles von der Funktion wegopimiert.
Delphi-Quellcode:
type
TMyClass<T> = class public type PT = ^T; // muß natürlich public sein, damit es an der aufrufenden Stelle verfügbar ist public class function GetMem<T>(Offset: NativeUInt): T; static; inline; end; |
Alle Zeitangaben in WEZ +1. Es ist jetzt 08:25 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz