Delphi-PRAXiS
Seite 2 von 3     12 3      

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Object-Pascal / Delphi-Language (https://www.delphipraxis.net/32-object-pascal-delphi-language/)
-   -   Delphi DLL wird nicht geladen - Warum nicht??? (https://www.delphipraxis.net/51821-dll-wird-nicht-geladen-warum-nicht.html)

Sprint 19. Aug 2005 17:20

Re: DLL wird nicht geladen - Warum nicht???
 
Hab das mal mit Delphi 3 unter Windows 95 getestet. Die Fehlermeldung kommt bei mir auch. Aber nur dann, wenn es sich nicht um eine DLL handelt.
Also hat delphifan2004 wohl keine DLL im TOpenDialog ausgewählt.

delphifan2004 19. Aug 2005 17:39

Re: DLL wird nicht geladen - Warum nicht???
 
Hallo tommie-lie!

Hab jetzt die folgende Dll erstellt, deren Aufruf funktioniert, aber mit paar kleinen Schönheitsfehlern. Zuerst der Code der DLL:

Delphi-Quellcode:
library MsgBoxDll;

uses
  SysUtils, Dialogs,
  Classes;

procedure MsgBox; stdcall;
begin
   ShowMessage('Diese Box ist in einer DLL codiert!');
end;

exports
 MsgBox;

begin
end.

//Habe mal ne andere Dll erzeugt, die ich jetzt lade.
//Habe den Code der Unit IntfApp jetzt wie folt geändert:

  //Hier, wie gehabt, der OpenDialog
  SetLastError(0);
  hDll := LoadLibrary(@fName[1]);
   if hDll = 0 then
    //kommt jetzt nicht mehr, Dll wird also geladen
    ShowMessage(SysErrorMessage(GetLastError));
  fProc := GetProcAddress(hDLL,'MsgBox');
  //Prozedur MsgBox aus meiner DLL zuweisen
  //da ich jetzt die obige Dll mit dieser Prozedur lade
  if fProc <> nil then begin
    @aProc := fProc;
  end else begin ShowMessage('DLL konnte nicht geladen werden!'); Exit; end;
  iPlg := aProc; //Hier erscheint dann die MessageBox (Procedure wird also aufgerufen)
  showMessage(iPlg.GetName); //Hier EAccessViolation ===WARUM???===
  iPlg := nil;
  FreeLibrary(hDLL);
 end;
Mit dieser Dll klappt das Laden und die Prozedur MsgBox läßt sich aufrufen. Bloß, mit der Zeile iPlg := aProc will ich doch erst mal einen Prozedurzeiger zuweisen. Erfolgt da ein Aufruf immer explizit, oder habe ich wieder mal ein Verständnisproblem?

Wenn ich die MessageBox aus der Dll mit [Ok] quittiere, erhalte ich anschließend eine EAccessViolation. Warum das nun wieder?

Zitat:

Zitat von tommie-lie
Gerät" heißt nicht ein Ding, das du anfassen kannst und irgendwo einstöpselst, es kann auch eine Datei sein.

Ist mir klar. Es kann auch eine Software Schnittstelle sein, für ein Physikalisches Gerät.
Du sagst, Gerät kann auch eine Datei sein. Im konkreten Fall vermutlich unsere Dll.

Zitat:

Zitat von tommie-lie
Und was machst du überhaupt mit der ShareMem? Willst du Pascal-Strings oder -Objekte an Funktionen der DLL übergeben? Ich dachte um das zu vermeiden willst du Interfaces verwenden?

Im Editoradapter kommt ein AnsiString als Ergebnistyp vor und wie ich die Sache mit ShareMem verstanden habe, muß, sobald ich lange Strings (nicht PCHar oder ShortString) zum Datenaustausch (über Parameter oder Funktionsergebnisse) verwende, die Unit ShareMem eingebunden werden, ob mir das gefällt oder nicht.

Zitat:

Zitat von Luckie
Aha. Und wer sagt dir, dass das aktuelle Verzeichnis auch das ist, wo du deine DLL hinkopiert hast?

Niemand. Aber darüber habe ich mir noch keine Gedanken gemacht, weil ich ja mit meinem OpenDialog in ein Verzeichnis gehen kann, wo ich dann die richtige Dll finde. Deshalb auch das Spielchen mit GetCurrentDir. Dorthin habe ich nun die DLL kopiert, damit sie vom System gefunden wird, wenn ich OpenDialog weglasse.

Delphifan2004

Sprint 19. Aug 2005 17:56

Re: DLL wird nicht geladen - Warum nicht???
 
Zitat:

Zitat von delphifan2004
Im Editoradapter kommt ein AnsiString als Ergebnistyp vor und wie ich die Sache mit ShareMem verstanden habe, muß, sobald ich lange Strings (nicht PCHar oder ShortString) zum Datenaustausch (über Parameter oder Funktionsergebnisse) verwende, die Unit ShareMem eingebunden werden, ob mir das gefällt oder nicht.

Benutze lieber einen ShareMem Ersatz deiner Wahl. Wie z.B. CMemMan oder FastShareMem. Dann brauchst du die Borland DLL nicht mit dir herum tragen.

glaubnix 19. Aug 2005 18:06

Re: DLL wird nicht geladen - Warum nicht???
 
Hallo Delphifan!

Haste auch den Prozedurtyp der neuen Situation angepasst? Wenn nicht, wundert mich die EAccessviolation nicht. Guck mal nach! Kannste glauben.

tommie-lie 19. Aug 2005 18:41

Re: DLL wird nicht geladen - Warum nicht???
 
Zitat:

Zitat von delphifan2004
Mit dieser Dll klappt das Laden und die Prozedur MsgBox läßt sich aufrufen. Bloß, mit der Zeile iPlg := aProc will ich doch erst mal einen Prozedurzeiger zuweisen.

Dann musst du das anders machen :mrgreen:
aProc ist die Funktion selbst, denn sie sit vom Typ TProcInitPlg. Wenn du in einem Delphi-Programm den Namen einer Funktion schreibst, die keinen Parameter benötigt, wird die Methode aufgerufen. Zum Beispiel GetLastError, schreibst du ja auch nicht, wie es eigentlich sinnvoll wäre, GetLastError(). Wenn du also iPlg := aProc hast, wird aProc aufgerufen und der Rückgabewert der Funktion der Variable iPlg zugewiesen. So, wie du deine Variablen deklariert hast, macht das für mich auch Sinn, daß iPlg := aProc die Funktion aProc auch aufruft, erscheint mir also richtig so (nicht nur syntaktisch, sondern auch semantisch).

Zitat:

Zitat von delphifan2004
Wenn ich die MessageBox aus der Dll mit [Ok] quittiere, erhalte ich anschließend eine EAccessViolation. Warum das nun wieder?

Vermutlich weil die Funktion eine Prozedur ist, die keinen Rückgabewert hat, er aber dennoch ausgelesen und zugewiesen wird (nuja, zumindest wird es versucht ;-)).

Zitat:

Zitat von delphifan2004
Du sagst, Gerät kann auch eine Datei sein. Im konkreten Fall vermutlich unsere Dll.

Vermute ich auch. Sprint sagte schon, daß er den Fehler bekommt, wenn er Dateien mit LoadLibrary lädt, die keine DLLs sind. Das ist das Verhalten, was ich aus der Fehlermeldung vermuten würde, auch wenn es für mich nicht viel Sinn macht, es sei denn du hast dich beim Klick so verhauen, daß du bei allen Versuchen mit dem Dialog nicht die DLL ausgewählt hast, sondern irgendwas anderes ;-)
Hast du denn mal vor dem Laden fName überprüft, zum Beispiel indem du es in einer MessageBox anzeigst?

Zitat:

Zitat von Sprint
Benutze lieber einen ShareMem Ersatz deiner Wahl. Wie z.B. CMemMan oder FastShareMem. Dann brauchst du die Borland DLL nicht mit dir herum tragen.

Um noch inkompatibler zum Rest der Welt zu werden?

delphifan2004 19. Aug 2005 21:15

Re: DLL wird nicht geladen - Warum nicht???
 
Hallo tommie-lie!

Danke erst mal für Deine Antwort.

Zitat:

Zitat von tommie-lie
Dann musst du das anders machen
aProc ist die Funktion selbst,...

Danke für die Hinweise! Hab grad noch mal den Quelltext der Plugin.dll angeguckt. Hast Recht. InitPlugin ist eine Funktion.
Damit weise ich an iPlg das Interface zu, das mit InitPlugin initialisiert wird. Damit ist erklärt, warum an dieser Stelle die Routine aufgerufen wird und die Zugriffsverletzung tritt auf, weil ich in meiner eigenen Test-Dll die exportierte Routine MsgBox als Prozedur definiert habe. Soweit Klar. Rest wird am Wochenende auseinander genommen.

Zitat:

Zitat von Sprint
Benutze lieber einen ShareMem Ersatz deiner Wahl. Wie z.B. CMemMan oder FastShareMem. Dann brauchst du die Borland DLL nicht mit dir herum tragen.

Hab mir die FastShareMem runtergeladen. Werd ich mal austesten, das Ganze.

@tommie-lie: Ob das "noch inkompatibler" wird, weiß ich nicht. Wenn die Unit OpenSource ist, muss ich sie halt bei Verwendung mit weitergeben. Hier geht es aber ohnehin erst mal darum, das Beispiel zu verstehen und da ist halt ein AnsiString als Funktionsrückgabe dabei. In der praktischen Anwendung kann ich dann bei Stringübergaben immer noch PChars nehmen.


Es grüßt

Delphifan2004

tommie-lie 19. Aug 2005 21:36

Re: DLL wird nicht geladen - Warum nicht???
 
Zitat:

Zitat von delphifan2004
InitPlugin ist eine Funktion.
Damit weise ich an iPlg das Interface zu, das mit InitPlugin initialisiert wird.

Genau.

Zitat:

Zitat von delphifan2004
Ob das "noch inkompatibler" wird, weiß ich nicht.

Auf jeden Fall werden sich alle Leute freuen, die deine DLL benutzen wollen und keinen Compiler von Borland benutzen ;-)

Zitat:

Zitat von delphifan2004
Wenn die Unit OpenSource ist, muss ich sie halt bei Verwendung mit weitergeben.

Ich weiß nicht, ob der MM sich über die Zeit verändert hat, aber unter Umständen erzwingst du damit gleichzeitig die Verwendung einer bestimmten Version, oder das Neukompilieren *aller* DLLs und der EXE mit dem jeweiligen Compiler des Systems.

Zitat:

Zitat von delphifan2004
In der praktischen Anwendung kann ich dann bei Stringübergaben immer noch PChars nehmen.

Ich lege es dir zumindest ans Herz. Nullterminierte Strings mögen ein wenig gewöhnungsbedürftig sein, wenn man mit ihnen arbeiten will, aber wenigstens zum reinen Datenaustausch sind sie das kompatibelste, in das man Zeichenketten nur packen kann.

Sprint 20. Aug 2005 11:23

Re: DLL wird nicht geladen - Warum nicht???
 
Zitat:

Zitat von tommie-lie
Zitat:

Zitat von Sprint
Benutze lieber einen ShareMem Ersatz deiner Wahl. Wie z.B. CMemMan oder FastShareMem. Dann brauchst du die Borland DLL nicht mit dir herum tragen.

Um noch inkompatibler zum Rest der Welt zu werden?

Wenn ich eine Anwendung mit Plugin Schnittstelle entwickle, dann benutze ich (D)COM oder eine sauber strukturierte API. So kann auch ein VB, VC und ein MASM Programmierer Plugins für meine Anwendungen schreiben.

Was nun delphifan2004 macht, ist mir eigentlich völlig egal. Und auch nichts mit dem Thema zu tun.

delphifan2004 20. Aug 2005 20:22

Re: DLL wird nicht geladen - Warum nicht???
 
Hallo!

Jetzt das Ganze noch mal im richtigen Thread:

Ich beziehe mich immer noch aud diesen Link:

http://www.delphipraxis.net/internal...t.php?p=405336

und diesen Link hier:

http://www.delphipraxis.net/internal...?p=29930#29930

Der folgende Codeausschnitt soll mein Plugin ausführen:

Delphi-Quellcode:
mApp := TApp.Create;
  if Assigned(iPlg) then
  begin
    iPlg.Execute(mApp);
  end else ShowMessage('Plugin konnte nicht initialisiert werden!');
Die MessageBox für den Fehlerfall erscheint nicht, und trotzdem erscheint der erwartete Text nach Drücken von Strg+V nicht in meinem Editor?

Was ist jetzt noch falsch?

Die Dll wird jetzt geladen und ich bekomme auch den Text "Mein Testplugin" angezeigt. Aber der Text: "Dieser Text erscheint im Editor" erscheint nicht. Warum nicht?

Zur Erinnerung noch mal die Execute Methode:


Delphi-Quellcode:
function TPlugin.Execute(App: IApp): Integer;
begin
  Result := 1; // True

  App.GetEditor.Content := 'Dieser Text erscheint im Editor.';
  App.GetEditor.CopyToClipboard;
end;
Sorry, Ich brauche doch noch mal Hilfe!

Es grüßt

Delphifan2004

tommie-lie 20. Aug 2005 20:52

Re: DLL wird nicht geladen - Warum nicht???
 
Zitat:

Zitat von delphifan2004
Die MessageBox für den Fehlerfall erscheint nicht

Det heeßt, daß zumindest irgendwas in der Variable drinsteckt. Ich weiß nicht, ob lokale Variablen in Delphi initialisiert werden, oder nicht, unter Umständen könnte das auch ein zufälliger Wert sein. Versuch also vorher mal iPlg explizit auf nil zu setzen und dann über die Funktion zuzuweisen, wenn dann Assigned() true ergibt, wurde etwas zurückgegeben.

Zitat:

Zitat von delphifan2004
und trotzdem erscheint der erwartete Text nach Drücken von Strg+V nicht in meinem Editor?

Das könnte auch am restlichen Aufruf liegen. Stehen dem Plugin alle Informationen (Editor) zur Verfügung? Hast du schon versucht die DLL zu debuggen? Hast du versucht, in der Execute-Methode einfach nur eine Nachricht auszugeben? Ich würde bei sowas am Anfang, wenn ich noch nicht weiß, wie das alles zusammenspielt, erstmal klein anfangen und nur Textnachrichten ausgeben, damit ich weiß, daß mein Interface soweit funktioniert. Wenn ich mich davon vergewissert habe, kann ich immer noch Variablen einführen und mit denen arbeiten. Im Augenblick, wo ich nichtmal deinen gesamten Quellcode kenne, gibt es immer noch zu viele Dinge, die noch reinspielen könnten.


Alle Zeitangaben in WEZ +1. Es ist jetzt 14:42 Uhr.
Seite 2 von 3     12 3      

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