![]() |
Probleme mit Datentypen bei einer DLL
Moin,
ich habe eine DLL die mir laut Buch eine Adresse auf einen Null-Termierten String zurückgibt ( returns the address of a null-terminated character string ). Habe da bereits alle möglichen Datentypen ausprobiert und komme auf keinen grünen Zweig. Vielleicht hat hier jemand einen Tip? Die dll ist aus dem Jahre 2004 und wird seitdem nicht mehr verändert - ich arbeite hier mit Delphi XE unter Windows 7. der Aufruf ist: function xyzErrMsg ( errorCode : Word ) : String; stdcall; external xyzdll name 'ErrMsg'; Der Datentyp String passt hier leider nicht Gruss McInternet |
AW: Probleme mit Datentypen bei einer DLL
Hast Du es mal mit
Delphi-Quellcode:
versucht ?
PAnsiChar
Gruß K-H |
AW: Probleme mit Datentypen bei einer DLL
Zitat:
var Meldung : PAnsichar; Meldung := yxzErrMsg(errornummer); Gruss McInternet |
AW: Probleme mit Datentypen bei einer DLL
ne - kommt nur Blödsinn :(
Gruss McInternet |
AW: Probleme mit Datentypen bei einer DLL
Nein, ich glaube du hast ihn falsch verstanden, du musst sozusagen, wie du die Funktion importierst ändern.
Delphi-Quellcode:
zu:
function xyzErrMsg ( errorCode : Word
) : String; stdcall; external xyzdll name 'ErrMsg';
Delphi-Quellcode:
Gruß NickelM
function xyzErrMsg ( errorCode : Word
) : PAnsiChar; stdcall; external xyzdll name 'ErrMsg'; //Man verwendet ungern Strings, also den DatenTyp String von Delphi. PAnsiChar ist nur eine Adresse auf den Anfang eines Textes im Speicher. Und um im Speicher zu wissen, wann er aufhört, setzt man ein 0 Byte (#0 in Char) am Ende. D.h. wenn du auf den Datentyp PAnsiChar zugreifst, wird alles gelesen bis zum 0 Byte. |
AW: Probleme mit Datentypen bei einer DLL
Zitat:
Ich rufe dann diese Funktion so auf: var Meldung : PAnsiChar; Fehlernummer : Word; Begin Meldung := xyzErrMsg(Fehlernummer); ... ... end; nur leider steht da nur Blödsinn drin ( wenn ich schon mit dem Debugger reinschaue) => $495ABA{"} .... und drin stehen muß z.B. => success etc. Achso: Das Gleiche compiliert unter Delphi 2007 - einwandfrei! Gruß McInternet |
AW: Probleme mit Datentypen bei einer DLL
Der Funktionskopf ist schon ungewöhnlich für eine Funktion in einer DLL. Normalerweise übergibt man einen Speicherbereich, den man selbst reserviert hat, welcher dann durch die Funktion befüllt wird. Ist die DLL in Delphi geschrieben? Falls in C/C++, hast Du da Header-Dateien dafür? Wie sähe dann da der Originalaufruf aus?
|
AW: Probleme mit Datentypen bei einer DLL
Zitat:
Headerdateien gibt es auch keine :evil: Gruß McInternet |
AW: Probleme mit Datentypen bei einer DLL
Zitat:
Wie heißt das Produkt? Kann man sich diese DLL/API-Beschreibung noch von Intel herunter laden? |
AW: Probleme mit Datentypen bei einer DLL
Zitat:
Es gibt ja offensichtlich mehrere Fehlermeldungen, die über einen errorCode ausgewählt werden. Die Strings liegen in dem Fall hartcodiert im Speicherbereich der DLL und der Aufrufer bekommt lediglich einen Zeiger zurück.
Delphi-Quellcode:
function xyzErrMsg(errorCode : Word): PAnsiChar; stdcall; external xyzdll name 'ErrMsg';
var Meldung : AnsiString; // nicht PAnsiChar ! Fehlernummer : Word; Begin Fehlernummer := 42; // nicht vergessen die Fehlernummer zu setzen!!! Meldung := xyzErrMsg(Fehlernummer); // Zeiger auf 0-terminierten String wird automatisch in einen Delphi-String umgewandelt. (Compiler Magic) ShowMessage(Meldung); |
AW: Probleme mit Datentypen bei einer DLL
Zitat:
Gruss McInternet |
AW: Probleme mit Datentypen bei einer DLL
Liegt dir nicht der Original export vor?
In dem Buch wird doch sicher irgendwie ein Beispiel oder sonstwas stehen, oder wenn sie von C++ kommt poste mal die Dekleration von dort. Das Ding ist nämlich, bei PAnsiChar's gibt es 2 Mögliche aufrufe. - Erstens du übergibst die Variable, wo der Pointer "gespeichert" bzw. hinterlegt wird. Die DLL legt ggf. den Speicher fest und übergibt dir den Pointer (Adresse); - Du musst einen Speicher festlegen. Dazu müsstest du die Größe wissen, also wie Lang der Text sein wird. Du legst den Speicher fest und übergibst die Variable an die Funktion. Diese schreibt in die Adresse die Daten. In deinem Fall würd ich auf das erste Tippen. Versuch mal folgendes:
Delphi-Quellcode:
So bei irgendeinem Wert muss er ja einen Text zurückgeben. Und alle Imports mal durchgehen mit diesem Code.
function xyzErrMsg(errorCode : Word): Pointer; stdcall; external xyzdll name 'ErrMsg';
//oder mal das function xyzErrMsg(errorCode : Word): Pointer; cdecl; external xyzdll name 'ErrMsg'; //oder mal einen von den Beiden function xyzErrMsg(const errorCode : Word): Pointer; stdcall; external xyzdll name 'ErrMsg'; function xyzErrMsg(const errorCode : Word): Pointer; cdecl; external xyzdll name 'ErrMsg'; //noch eine Möglich aber unwahrscheinlich function xyzErrMsg(var errorCode : Word): Pointer; stdcall; external xyzdll name 'ErrMsg'; function xyzErrMsg(var errorCode : Word): Pointer; cdecl; external xyzdll name 'ErrMsg'; //Bei allen Möglchkeiten lass das Pointer mal hintendran. var Meldung : PAnsiChar; P : Pointer; ErrorCode : Word; Begin for ErrorCode := 0 to High(Word) do begin P := xyzErrMsg(ErrorCode); If P <> nil then begin Meldung := P; //Setz mal hier ein Breakpoint ShowMessage(Meldung); end; end; EDIT: Sorry, überlesen, hast ja schon gesagt, dass es keine Doku oder sonstwas gibt. Das sie in C geschrieben ist, sollte einer der cdecl; oben vielleicht eher funken. Vielleicht Funkt dan irgendwas. Gruß NickelM |
AW: Probleme mit Datentypen bei einer DLL
CONST bringt bei Word nicht viel (ändert garnichts).
"ErrMsg" ... C++ baut gerne auch die Parametersignatur in den Exportnamen ein. Eventuell heißt es ja nicht "ErrMsg". ( ist das eigentlich CaseSensitiv? ) Statt Pointer kann man auch gleich PAnsiChar nehmen. PWideChar wird es mit großer Wahrscheinlichkeit nicht sein. Neben cdecl und stdcall gibt es noch ein paar Varianten mehr, aber Anderes hab ich hier auch noch nicht gesehn. (außer selten mal savecall und in Delphi natürlich pascal) |
AW: Probleme mit Datentypen bei einer DLL
@himitsu : Ich weis, wegen Pointer. Wollte nur mal gugen, ob sich der Pointer immer ändert, ob er ungleich nil ist und wenn der Pointer existiert, ich die Adresse dann erst übertrage.
Wenn es dan funkt mit irgendeinem Funktionsaufruf, kann man immernoch Pointer durch PAnsiChar ersetzten. Stimmt CONST bringt bei PWideChar,PAnsiChar oder sonstwo nur was, wenn sie als Paramter übergeben werden richtig? Was macht das dan eigentlich für einen Unterschied? Ich denke mal CONST bringt, das bei PAnsiChar,PWideChar z.b. der Text im Speicher der Funktion liegt und nicht die Adresse des Textes oder? @Thread : Was mir gerade einfällt, so beim schreiben grad, wegen dem Namen der Funktion. Ich kenn die Dll nicht vielleicht heist die Funktion ja "ErrMsgA". Zumindest ist es oft bei WinAPIs so. Neuere Dlls, so ab Win2000 haben dann eine "ErrMsgA" und eine "ErrMsgW". Das "A" steht für ANSI und das "W" für Wide also PWideChar. Das wären jetzt meine einizg letzen Ideen. Gruß NickelM |
AW: Probleme mit Datentypen bei einer DLL
Raten bringt hier nicht viel.
Entweder mit dem Debugger in die DLL-Funktion springen und sich den Code anschaun oder gleich die ganze DLL diassemblieren (Windasm o.ä.). |
AW: Probleme mit Datentypen bei einer DLL
Problem ist gelöst.
da ich in die dll definitiv nicht hereinschauen kann, habe ich eine eigene Fehlercodetable aufgebaut :oops: danke an alle für die Tipps. Gruss mc |
Alle Zeitangaben in WEZ +1. Es ist jetzt 14:03 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