Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Object-Pascal / Delphi-Language (https://www.delphipraxis.net/32-object-pascal-delphi-language/)
-   -   Exit-Funktion erweitern (https://www.delphipraxis.net/134335-exit-funktion-erweitern.html)

Desmulator 20. Mai 2009 08:31


Exit-Funktion erweitern
 
Guten Morgen zusammen,

zur Zeit arbeite ich intensiv mit DLLs und habe deshalb eine GetLastError-Funktion. Diese wird natürlich mit eine SetLastError-Funktion intern gefüttert. Jetzt bin ich aber an einem Punkt, andem soetwas wie eine Exit-SetLastError-Funktion nützlich wäre. Also die ErrorVariable gesetzt wird und die Funktion beendet. Prinzipiell müsste ich doch einfach nur den Stack soweit zurück springen bis ich wieder beim Caller bin.

Beispiel:
Delphi-Quellcode:
// In der DLL
function ReadAll(Stream : TMyStream) : PChar; stdcall;
begin
  // LastError wird zu INVALID_PARAM, Result = nil, Ausgang von ReadAll
  if Stream = nil then SetLastErrorExit(BASE_ERR_INVALID_PARAM, nil)
  else begin
    ..
  end;
end;

// Im Programm
function Test() : Boolean;
var
  Stream : TMyStream;
begin
  Stream := TMyStream.Create; // Beispiel
  // Ich rufe eine Funktion meiner DLL auf
  if ReadAll(Stream) = nil then ShowMessage(Format('Fehler: %d', [GetLastError]));
  Stream.Free;
end;
Ist sowas möglich? Naja warscheinlich schon, allerdings sehr unsauber oder?

Mfg Desmu

quendolineDD 20. Mai 2009 08:35

Re: Exit-Funktion erweitern
 
Zum einen ist mir nicht bekannt, das Strings nil sein können (das C NULL wäre hier ''). Außerdem finde ich wäre es wohl besser, wenn du kritische Blöcke mit try ... except umfasst und dort die Fehler abfängst mithilfe von Exceptions und nicht mit Error-Meldungen um dich schmeißt, weil du da mal ganz schnell auch Windows-Fehler die für dich von Bedeutung sein könnten untergraben wirst.

Desmulator 20. Mai 2009 08:40

Re: Exit-Funktion erweitern
 
Zitat:

Zitat von quendolineDD
Zum einen ist mir nicht bekannt, das Strings nil sein können (das C NULL wäre hier ''). Außerdem finde ich wäre es wohl besser, wenn du kritische Blöcke mit try ... except umfasst und dort die Fehler abfängst mithilfe von Exceptions und nicht mit Error-Meldungen um dich schmeißt, weil du da mal ganz schnell auch Windows-Fehler die für dich von Bedeutung sein könnten untergraben wirst.

Es ging mir hierbei auch eher um eine Beispiel der Verwendung einer solchen Funktion. Ich hab jetzt mal das String durch PChar ersetzt. try..except-Blöcke brauche ich afaik nicht, da ich einfach mal behaupte, dass TMyStream eine eigene Klasse ist und keine Exception wirft. Es geht auch mehr darum, dass in einer DLL-Funktion schlecht Exception geworfen werden können. Deshalb führe ich in der DLL eine SetLastError-Funktion ein und exportiere eine GetLastError-Funktion.

Meine Frage ist jetzt, ob es nicht möglich wäre, eine Funktion zum beenden des Aufrufs, wie oben zu erstellen, in der LastError gesetzt wird, ein Rückgabewert gesetzt werden kann und die Funktion, die Aufgerufen wurde beendet wird.

jbg 20. Mai 2009 11:26

Re: Exit-Funktion erweitern
 
Zitat:

Zitat von Desmulator
Ich hab jetzt mal das String durch PChar ersetzt.

Wer gibt den PChar frei? Zeigt der PChar vielleicht noch auf einen temporären String der auf dem Stack liegt und somit beim Rücksprung nicht mehr gültig ist? Lauter Fragen, die du dir beantworten solltest.

Zitat:

Meine Frage ist jetzt, ob es nicht möglich wäre, eine Funktion zum beenden des Aufrufs, wie oben zu erstellen, in der LastError gesetzt wird, ein Rückgabewert gesetzt werden kann und die Funktion, die Aufgerufen wurde beendet wird.
Wenn du deine Funktion mit der cdecl Aufrufkonvention deklarierst, keine managed Datentypen (String, dyn. Array, Variant, Interface) und keine try-Blöcke verwendest, dann könnte man da schon was mit Assembler-Code machen. Aber ich bezweifle dass das dem Code gut täte.

Desmulator 20. Mai 2009 12:53

Re: Exit-Funktion erweitern
 
Zitat:

Zitat von jbg
Wenn du deine Funktion mit der cdecl Aufrufkonvention deklarierst, keine managed Datentypen (String, dyn. Array, Variant, Interface) und keine try-Blöcke verwendest, dann könnte man da schon was mit Assembler-Code machen. Aber ich bezweifle dass das dem Code gut täte.

Okay, sauber wird es wohl nie sein, und einbauen werde ich es wohl auch kaum, aber mich würde einfach aus reiner interesse interessieren wie das geht. :-)


Alle Zeitangaben in WEZ +1. Es ist jetzt 05:26 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz