2012-06-05 163 views
5

在我的Inno Setup脚本中,我正在执行第三方可执行文件。我使用如下的Exec()功能:Inno Setup Exec()函数等待有限时间

Exec(ExpandConstant('{app}\SomeExe.exe'), '', '', SW_HIDE, ewWaitUntilTerminated, ErrorCode); 

通过提ewWaitUntilTerminated这里等到SomeExe.exe不退出。我只想等10秒。

有没有解决方案?

+0

,哪些是你会是10秒后做什么? – TLama

+0

也许他想杀死这个过程?我想你可以正常执行并创建简单的定时器,在10秒后杀死进程。 – Slappy

+0

@Slappy,你可以使用例如['Sleep'](http://msdn.microsoft.com/en-us/library/windows/desktop/ms686298%28v=vs.85%29.aspx)函数,然后终止进程。问题是你不知道什么过程,并且据我所知,从可用的InnoSetup函数中,没有人返回执行进程句柄,这是进程终止所需的。而如果你想知道进程句柄,这是更好地使用['WaitForSingleObject'(http://msdn.microsoft.com/en-us/library/windows/desktop/ms687032%28v=vs.85%29。 aspx)函数等待。请参阅下面的代码示例。 – TLama

回答

7

假设你想执行外部应用程序,等待其终止在指定的时间,如果它不是由本身的设置杀死它终止试试下面的代码。到这里使用的魔法常量,3000用作WaitForSingleObject函数的参数是设置多长时间等待进程终止以毫秒为单位的时间。如果它不能在那个时候自行终止,它是由TerminateProcess功能,其中666值是进程退出代码(在这种情况下,很邪恶:-)

[Code] 
#IFDEF UNICODE 
    #DEFINE AW "W" 
#ELSE 
    #DEFINE AW "A" 
#ENDIF 

const 
    WAIT_TIMEOUT = $00000102; 
    SEE_MASK_NOCLOSEPROCESS = $00000040; 

type 
    TShellExecuteInfo = record 
    cbSize: DWORD; 
    fMask: Cardinal; 
    Wnd: HWND; 
    lpVerb: string; 
    lpFile: string; 
    lpParameters: string; 
    lpDirectory: string; 
    nShow: Integer; 
    hInstApp: THandle;  
    lpIDList: DWORD; 
    lpClass: string; 
    hkeyClass: THandle; 
    dwHotKey: DWORD; 
    hMonitor: THandle; 
    hProcess: THandle; 
    end; 

function ShellExecuteEx(var lpExecInfo: TShellExecuteInfo): BOOL; 
    external 'ShellExecuteEx{#AW}@shell32.dll stdcall'; 
function WaitForSingleObject(hHandle: THandle; dwMilliseconds: DWORD): DWORD; 
    external '[email protected] stdcall'; 
function TerminateProcess(hProcess: THandle; uExitCode: UINT): BOOL; 
    external '[email protected] stdcall'; 

function NextButtonClick(CurPageID: Integer): Boolean; 
var 
    ExecInfo: TShellExecuteInfo; 
begin 
    Result := True; 

    if CurPageID = wpWelcome then 
    begin 
    ExecInfo.cbSize := SizeOf(ExecInfo); 
    ExecInfo.fMask := SEE_MASK_NOCLOSEPROCESS; 
    ExecInfo.Wnd := 0; 
    ExecInfo.lpFile := 'calc.exe'; 
    ExecInfo.nShow := SW_HIDE; 

    if ShellExecuteEx(ExecInfo) then 
    begin 
     if WaitForSingleObject(ExecInfo.hProcess, 3000) = WAIT_TIMEOUT then 
     begin 
     TerminateProcess(ExecInfo.hProcess, 666); 
     MsgBox('You just killed a little kitty!', mbError, MB_OK); 
     end 
     else 
     MsgBox('The process was terminated in time!', mbInformation, MB_OK); 
    end; 
    end; 
end; 

我有代码丧生在Windows 7 Inno Setup的5.4.3 Unicode和ANSI版本测试(感谢kobik他的主意,使用条件规定了从this post Windows API函数的声明)

+0

这是一个不错的解决方案! – GTAVLover