Autor Beitrag
jaenicke
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 19315
Erhaltene Danke: 1747

W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
BeitragVerfasst: Mo 04.07.11 19:47 
Hallo,

wir benutzen eine Fremdbibliothek, aus der wir eine Funktion aufrufen.

Das hatte auch schon funktioniert. Wir haben an den Funktionen an sich nichts geändert, nur natürlich an anderen Stellen der Anwendung.

Jetzt haben wir das Problem, dass nach der Rückkehr aus der DLL die Anwendung einfach hängt. Selbst ein simples ShowMessage bleibt hängen.

Und jetzt die Quizfrage:
Was kann die DLL da so dermaßen zerschießen, dass danach noch nicht einmal ein simples ShowMessage funktioniert?

Als Nebeninfo: In der DLL werden Formulare erzeugt, die auch in dem Moment sichtbar sind.

Vielen Dank,
Schönen Gruß,
Sebastian
uko
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 220
Erhaltene Danke: 1

Win XP, VISTA, WIndows 7
Delphi 2007/2010 Prof
BeitragVerfasst: Di 05.07.11 06:04 
Guten Morgen,

nur so ein paar Ideen:
- Aufrufkonvention (cdecl, stdcall)
- übergebener Speicher der durch Anwendung oder Dll überschrieben wird
jaenicke Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 19315
Erhaltene Danke: 1747

W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
BeitragVerfasst: Di 05.07.11 10:58 
user profile iconuko hat folgendes geschrieben Zum zitierten Posting springen:
- Aufrufkonvention (cdecl, stdcall)
Die sind korrekt, in diesem Fall stdcall.

user profile iconuko hat folgendes geschrieben Zum zitierten Posting springen:
- übergebener Speicher der durch Anwendung oder Dll überschrieben wird
Das können wir zumindest bei der DLL zwar nicht ausschließen, halte ich aber für unwahrscheinlich.

Die Frage ist eigentlich was dabei passieren könnte, dass eben ein direkt nach dem Aufruf angezeigtes ShowMessage nicht mehr geht. Dann könnte ich die entsprechenden Speicherstellen überprüfen. Aber im Moment fehlt mir da ein wenig der Ansatz wo ich suchen könnte...
Boldar
ontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic starofftopic star
Beiträge: 1555
Erhaltene Danke: 70

Win7 Enterprise 64bit, Win XP SP2
Turbo Delphi
BeitragVerfasst: Di 05.07.11 12:02 
SInd die Parameter vielleicht unzulässig? String / PChar nicht verwechselt?
Ansonsten schau mal mit z.B. IDA wo das hängt.
Wenn die Showmessage nicht aufgerufen wird, hängt es ja schon in der dll, d.h. die Methode kehrt erst garnicht zurück.
mfg Boldar
jaenicke Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 19315
Erhaltene Danke: 1747

W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
BeitragVerfasst: Di 05.07.11 12:04 
Doch, sie wird aufgerufen, das ist es ja. Aber die Messagebox hängt dann einfach und die Anwendung reagiert nicht mehr.
bummi
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 1248
Erhaltene Danke: 187

XP - Server 2008R2
D2 - Delphi XE
BeitragVerfasst: Di 05.07.11 13:35 
Schmutz die DLL gegf. mit DisableTaskWindows o.ä. herum?

_________________
Das Problem liegt üblicherweise zwischen den Ohren H₂♂
DRY DRY KISS
Oliver Maas
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 55



BeitragVerfasst: Di 05.07.11 14:10 
Ich weiß nun nicht, ob es da einen Zusammenhang gibt, aber ich hatte auch schon mal einen Fall,
bei dem in einer Eventroutine einer 3rd-party Komponente (passt somit nicht direkt zu dem dll-Thema)
ein ShowMessage (oder das Anzeigen eines anderen Formulars) zum Hängenbleiben oder zu anderen Problemen führte.
Ich konnte das auch nie ursächlich lösen, hatte dann aber das ShowMessage über eine Timer-Routine angezeigt,
d.h. in der Eventroutine einfach Timer.Enabled := true geschrieben, und die besagte Eventroutine somit von dem ShowMessage "entkoppelt".
Das hat dann funktioniert.

Vermutlich gibt es da beim Anzeigen der Box in diesem Thread ein Problem (und der Timer hat halt einen neuen Thread als Basis).
Da die beschriebene dll ihrerseits auch Formulare anzeigt, hab ich da einen Zusammenhang erahnt.
uall@ogc
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 1826
Erhaltene Danke: 11

Win 2000 & VMware
Delphi 3 Prof, Delphi 7 Prof
BeitragVerfasst: Di 05.07.11 19:51 
@Oliver:
Die Delphi Timer Komponente verwendet keinen eigenen Thread. Wenn dann die exportierte Funktion im selben Thread ausgefuehrt wird sollte es funktionieren. Wenn nicht waere es schon ein Fehler ShowMessage zu verwenden, dies ist keine WinAPI ist sondern VCL und somit nicht zwingendermaßen Threadsafe. Im Event-Callback haettes du mit Synchronize arbeiten muessen.

@jaenicke:
Funktioniert MessageBox? Gibt es Callbacks in denen du auf die VCL zugreifst? Hast du mal im Debugger im Assembler code nen Breakpoint gemacht und durchgesteppt? ggf. mal auf kernel32.CreateThread einen Breakpoint setzen und schaun ob ein Thread von der Komponente erstellt wird. Außerdem hilft es mal die Imports der DL anzuschauen ob da nicht was komisches bei sein koennte. Bist du dir mit der Aufrufkonvention wirklich sicher, die kannst du an dem RET im Assembler erkennen von der exportieren Funktion erkennen (sehr leicht wenn mehr als 3 Parameter):

RET xy
: xy / 4 = Anzahl Parameter -> stdcall
: xy / 4 + 3 = Anzahl Parameter -> register
: xy = 0 -> cdecl

_________________
wer andern eine grube gräbt hat ein grubengrabgerät
- oder einfach zu viel zeit
jaenicke Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 19315
Erhaltene Danke: 1747

W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
BeitragVerfasst: Di 05.07.11 20:20 
user profile iconuall@ogc hat folgendes geschrieben Zum zitierten Posting springen:
Funktioniert MessageBox?
Das muss ich mal ausprobieren. Vor dem Aufruf in der DLL funktioniert ShowMessage übrigens ohne Probleme. Und Threads sind zumindest beim Aufruf aus der Anwendung nicht im Spiel.

user profile iconuall@ogc hat folgendes geschrieben Zum zitierten Posting springen:
Gibt es Callbacks in denen du auf die VCL zugreifst?
Nein, bzw. ich nutze zumindest keine. Was die DLL in der Hinsicht macht, weiß ich nicht. Es kann aber sein, dass die auf die VCL zugreift (wenn auch wohl eher auf die des C++ Builders, das weiß ich nicht).

user profile iconuall@ogc hat folgendes geschrieben Zum zitierten Posting springen:
Hast du mal im Debugger im Assembler code nen Breakpoint gemacht und durchgesteppt?
Das würde ich gern, aber der Rechner steht leider nicht direkt zur Verfügung (die DLL greift auf spezielle Hardware zu) und der Remotedebugger ist leider in der derzeitigen Form über DSL plus Tunnel praktisch unbrauchbar... :autsch:

user profile iconuall@ogc hat folgendes geschrieben Zum zitierten Posting springen:
ggf. mal auf kernel32.CreateThread einen Breakpoint setzen und schaun ob ein Thread von der Komponente erstellt wird
Das müsste ich herausfinden können, aber ich bin mir auch so relativ sicher, dass in der DLL Threads verwendet werden.

user profile iconuall@ogc hat folgendes geschrieben Zum zitierten Posting springen:
Bist du dir mit der Aufrufkonvention wirklich sicher
Ja, denn es hat an sich schon geklappt, ein Non-VCL-Programm funktioniert soweit, auch wenn es nicht alle Funktionen nutzt. Zudem stammen die Deklarationen 1:1 aus einem funktionierenden Beispielprogramm. Dieses besteht aber nur aus einem Fenster (das zum zeitpunkt der Aufrufe auch schon komplett erstellt und sichtbar ist), wohingegen das Zielprojekt ein paar mehr hat (davon zu dem Zeitpunkt zwei aktiv bzw. in der Erstellung). Deshalb vermute ich ja auch, dass da irgendetwas beim Fenstermanagement durcheinandergeht, insbesondere weil eben auch das ShowMessage (das zu Debugzwecken benutzt werden sollte) dann ein Problem hat.

Nebenbei:
Natürlich werden wir das auch mit dem Hersteller der DLL klären, aber die Hoffnung ist natürlich, dass es einen schnelleren Workaround gibt.