![]() |
Fehler in RunProcess Funktion?!
Hi@all!
Ich versuche gerade für einen Kunden ein Programm zu schreiben, was neben anderen hauptaufgaben versuchen soll, einen anderen Prozess zu überwachen, ob dieser ausgeführt wird. Dabei überprüfe ich 1 innerhalb eines vorgegebenen Zeitraums, ob das Prozesshandle =0 ist, und falls dem so ist, benutze ich die "RunProcess" Funktion aus dem Forum hier, um den Prozess neuzustarten:
Delphi-Quellcode:
Dabei habe ich folgendes Verhalten festgestellt: Wenn CreateProcess nicht erfolgreich war und "False" zurückgibt (bei mir simuliert durch einen falschen Dateinamen), bekomme ich eine Exception in der Zeile "CloseHandle(ProcessInfo.hProcess)".
function RunProcess(FileName: string; ShowCmd: DWORD; wait: Boolean; ProcID: PCardinal): Longword;
var StartupInfo: TStartupInfo; ProcessInfo: TProcessInformation; begin FillChar(StartupInfo, SizeOf(StartupInfo), #0); StartupInfo.cb := SizeOf(StartupInfo); StartupInfo.dwFlags := STARTF_USESHOWWINDOW or STARTF_FORCEONFEEDBACK; StartupInfo.wShowWindow := ShowCmd; if not CreateProcess(nil, @Filename[1], nil, nil, False, CREATE_NEW_CONSOLE or NORMAL_PRIORITY_CLASS, nil, nil, StartupInfo, ProcessInfo) then Result := WAIT_FAILED else begin if wait = FALSE then begin if ProcID <> nil then ProcID^ := ProcessInfo.dwProcessId; exit; end; WaitForSingleObject(ProcessInfo.hProcess, INFINITE); GetExitCodeProcess(ProcessInfo.hProcess, Result); end; if ProcessInfo.hProcess <> 0 then CloseHandle(ProcessInfo.hProcess); if ProcessInfo.hThread <> 0 then CloseHandle(ProcessInfo.hThread); end; Wäre es nicht richtiger, die beiden "CloseHandles" nur dann aufzurufen, wenn das CreateProcess zuvor ein "True" zurückgegeben hat? Viele Grüße und besten Dank, Euer Michael |
Re: Fehler in RunProcess Funktion?!
Eigentlich hatte ich es noch nie erlebt, daß CloseHandle eine Exception wirft :shock:
Aber bevor man hier erstmal weiter rumspielt: Bist du sicher, daß diese Funktion überhaupt für dich von nutzen ist? Es wird hier ja gewartet, bis sich der andere Prozess beendet hat, was für eine Überwachung doch nicht so vorteilhaft sein sollte. ganz übersehn, daß man dieses abschalten kann bin gleich zurück [edit] so, - das fehlende Result wird gesetzt - die Handles werden korrekt und vorallem IMMER geschlossen (im Original wurde das oftmals vergessen)
Delphi-Quellcode:
function RunProcess(const FileName: string; ShowCmd: LongWord; Wait: Boolean; ProcessID: PLongWord = nil): LongWord;
var StartupInfo: TStartupInfo; ProcessInfo: TProcessInformation; begin ZeroMemory(@StartupInfo, SizeOf(StartupInfo)); StartupInfo.cb := SizeOf(StartupInfo); StartupInfo.dwFlags := STARTF_USESHOWWINDOW or STARTF_FORCEONFEEDBACK; StartupInfo.wShowWindow := ShowCmd; if CreateProcess(nil, PChar(Filename), nil, nil, False, CREATE_NEW_CONSOLE or NORMAL_PRIORITY_CLASS, nil, nil, StartupInfo, ProcessInfo) then begin try CloseHandle(ProcessInfo.hThread); if Wait then begin WaitForSingleObject(ProcessInfo.hProcess, INFINITE); GetExitCodeProcess(ProcessInfo.hProcess, Result); end else begin if Assigned(ProcessID) then ProcessID^ := ProcessInfo.dwProcessId; Result := S_OK; end; finally CloseHandle(ProcessInfo.hProcess); end; end else Result := WAIT_FAILED; end; |
Re: Fehler in RunProcess Funktion?!
Okay, schaut gut aus...keine korrektur:
Delphi-Quellcode:
Aber warum müssen die Handles geschlossen werden, wenn das Programm gar nicht gestartet werden konnte?
ZeroMemory(@StartupInfo, SizeOf(StartupInfo));
|
Re: Fehler in RunProcess Funktion?!
da müssen sie garnicht :nerd:
Luckie hätte für diesen Fall auch den ProcessInfo initialisieren sollen, da CreateProcess nur bei Erfolg die Handle/IDs dort einträgt und sonst nix macht. |
Re: Fehler in RunProcess Funktion?!
Okay, dann sollten wir das vielleicht mal in der Code-Library ändern...entweder meine Änderung, oder Himitsu's
Mein Vorschlag wäre ja:
Delphi-Quellcode:
function RunProcess(FileName: string; ShowCmd: DWORD; wait: Boolean; ProcID: PCardinal): Longword;
var StartupInfo: TStartupInfo; ProcessInfo: TProcessInformation; begin FillChar(StartupInfo, SizeOf(StartupInfo), #0); StartupInfo.cb := SizeOf(StartupInfo); StartupInfo.dwFlags := STARTF_USESHOWWINDOW or STARTF_FORCEONFEEDBACK; StartupInfo.wShowWindow := ShowCmd; if not CreateProcess(nil, @Filename[1], nil, nil, False, CREATE_NEW_CONSOLE or NORMAL_PRIORITY_CLASS, nil, nil, StartupInfo, ProcessInfo) then Result := WAIT_FAILED else begin if wait = FALSE then begin if ProcID <> nil then ProcID^ := ProcessInfo.dwProcessId; exit; end; WaitForSingleObject(ProcessInfo.hProcess, INFINITE); GetExitCodeProcess(ProcessInfo.hProcess, Result); if ProcessInfo.hProcess <> 0 then CloseHandle(ProcessInfo.hProcess); if ProcessInfo.hThread <> 0 then CloseHandle(ProcessInfo.hThread); end; end; |
Re: Fehler in RunProcess Funktion?!
bei dir dürftest du die if ProcessInfo.xxx <> 0 then weglassen können, da an dieser Stelle die Handles ja vorhanden sein sollten.
PS: bei if wait = FALSE then ... exit; wären die Handles nicht freigegeben worden und auch das Result wäre da undefiniert geblieben (meckert diesbezüglich eigentlich Delphi nicht? )
Delphi-Quellcode:
function RunProcess(FileName: string; ShowCmd: DWORD; wait: Boolean; ProcID: PCardinal): Longword;
var StartupInfo: TStartupInfo; ProcessInfo: TProcessInformation; begin FillChar(StartupInfo, SizeOf(StartupInfo), #0); StartupInfo.cb := SizeOf(StartupInfo); StartupInfo.dwFlags := STARTF_USESHOWWINDOW or STARTF_FORCEONFEEDBACK; StartupInfo.wShowWindow := ShowCmd; if not CreateProcess(nil, @Filename[1], nil, nil, False, CREATE_NEW_CONSOLE or NORMAL_PRIORITY_CLASS, nil, nil, StartupInfo, ProcessInfo) then Result := WAIT_FAILED else begin try if not wait then begin if ProcID <> nil then ProcID^ := ProcessInfo.dwProcessId; Result := S_OK; exit; end; WaitForSingleObject(ProcessInfo.hProcess, INFINITE); GetExitCodeProcess(ProcessInfo.hProcess, Result); finally CloseHandle(ProcessInfo.hProcess); CloseHandle(ProcessInfo.hThread); end; end; end; Zitat:
[edit] noch schnell das Result:=S_OK; eingefügt :oops: |
Re: Fehler in RunProcess Funktion?!
So könnte der Rückgabewert aber undefiniert sein. Anderer Vorschlag:
Delphi-Quellcode:
function RunProcess(FileName: string; ShowCmd: DWORD; wait: Boolean; ProcID: PCardinal): Longword;
var StartupInfo: TStartupInfo; ProcessInfo: TProcessInformation; begin FillChar(StartupInfo, SizeOf(StartupInfo), #0); StartupInfo.cb := SizeOf(StartupInfo); StartupInfo.dwFlags := STARTF_USESHOWWINDOW or STARTF_FORCEONFEEDBACK; StartupInfo.wShowWindow := ShowCmd; if not CreateProcess(nil, @Filename[1], nil, nil, False, CREATE_NEW_CONSOLE or NORMAL_PRIORITY_CLASS, nil, nil, StartupInfo, ProcessInfo) then Result := WAIT_FAILED else begin Result := S_OK; if wait then begin WaitForSingleObject(ProcessInfo.hProcess, INFINITE); GetExitCodeProcess(ProcessInfo.hProcess, Result); if ProcessInfo.hProcess <> 0 then CloseHandle(ProcessInfo.hProcess); if ProcessInfo.hThread <> 0 then CloseHandle(ProcessInfo.hThread); end else if ProcID <> nil then ProcID^ := ProcessInfo.dwProcessId; end; end; |
Re: Fehler in RunProcess Funktion?!
@DeddyH: bei Wait=False bleiben die Handle offen.
|
Re: Fehler in RunProcess Funktion?!
Okay, ihr habt recht... Himitsus Vorschlag schaut sehr gut aus...
|
Re: Fehler in RunProcess Funktion?!
Jaja, Sch**ß C&P. Dafür hatte ich immerhin Delphi-Tags gesetzt :tongue:
|
Alle Zeitangaben in WEZ +1. Es ist jetzt 14:52 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