>parameter lcApplicationTitle >local lnHwnd >DECLARE INTEGER FindWindow IN Win32API; >STRING @lpClassName, ; >STRING @lpWindowName >lnHWnd = FindWindow(0, @lcApplicationTitle) > >RETURN lnHWnd >>
>THISFORM.killapp(THISFORM.nShwnd, .F., .T., .T., 100) >>
>***** KillApp **************************************************************** >* Reliable procedure of shutdown of application. Tries to shutdown application by normal way >* sending WM_Quit event to its thread. If this will not help within 5 seconds (or specified), >* application will be terminated by API TerminateProcess function >* Parameters: >* pnHWND - main Window handle >* plKillImmediate - if .T., application will be killed without any waiting or messages sending. Next two parameters will be ignored in this case >* plWaitShutdown - if .T., procedure will wait max.10 seconds until application shutdown. >* plKillWhenNoShutdown - if .T., App will be killed anyway when shutdown time passed and App still in memory >* pnShutdownTimeOut - optional, number of miliseconds to wait until application shutdown by normal way. Between 100 and 60000. >* pnProcessID - optional, ID of process to be killed. Will be used if main window already does not exists (some App crashes causes such situation) >* pcProcessCreationTime - optional, process creation time to verify if passed process ID is not an ID of another new process > >* KillApp Method >LPARAMETER pnHWND, plKillImmediate, plWaitShutdown, plKillWhenNoShutdown, pnShutdownTimeOut, pnProcessID, pcProcessCreationTime > >IF !VARTYPE(m.pnShutdownTimeOut) == "N" > m.pnShutdownTimeOut = 5000 >ELSE > IF m.pnShutdownTimeOut < 100 > m.pnShutdownTimeOut = 100 > ENDIF > IF m.pnShutdownTimeOut > 60000 > m.pnShutdownTimeOut = 60000 > ENDIF >ENDIF >#DEFINE WM_QUIT 0x12 >#define PROCESS_TERMINATE 0x1 >DECLARE INTEGER PostThreadMessage IN Win32API INTEGER Hthrd, INTEGER nMessage, short Param1, LONG Param2 >DECLARE INTEGER GetWindowThreadProcessId IN Win32API INTEGER HWND, INTEGER @pID >DECLARE INTEGER TerminateProcess IN Win32API INTEGER PID, INTEGER TermCode >DECLARE INTEGER OpenProcess IN Win32API INTEGER fdwAccess, INTEGER fInherit, INTEGER IDProcess >DECLARE INTEGER Sleep IN Win32API INTEGER cMilliseconds >DECLARE INTEGER GetProcessTimes IN Win32API INTEGER HProc, STRING @lpCreation, STRING @lpExit, STRING @lpKernel, STRING @lpUser > >LOCAL nTries, nThreadID, nProcessID >m.nProcessID = 0 >m.nThreadID = GetWindowThreadProcessId(m.pnHWND,@m.nProcessID) >IF m.nThreadID = 0 OR m.nProcessID = 0 > IF VARTYPE(m.pnProcessID) == "N" > * check if process exists in memory and creation time is same > LOCAL lcTime, rrr > m.lcTime = SPACE(8) > m.rrr = SPACE(8) > IF GetProcessTimes(OpenProcess(PROCESS_QUERY_INFORMATION, 0, m.pnProcessID),@m.lcTime,@m.rrr,@m.rrr,@m.rrr)>0 > IF m.lcTime == m.pcProcessCreationTime > m.nProcessID = m.pnProcessID > m.plKillImmediate = .T. > ELSE > RETURN > ENDIF > ELSE > RETURN > ENDIF > ELSE > * just exit if App already released > RETURN > ENDIF >ENDIF > >IF !m.plKillImmediate > * try to close main App window by sending WM_Quit event just into its thread > m.nTries = m.pnShutdownTimeOut/10 > DO WHILE m.nTries > 0 > IF PostThreadMessage(m.nThreadID, WM_QUIT, 0, 0) > 0 > m.nThreadID = GetWindowThreadProcessId(m.pnHWND,@m.nProcessID) > IF m.nThreadID = 0 OR m.nProcessID = 0 > * just exit if App released > RETURN > ENDIF > ELSE > * check if App is in memory > m.nThreadID = GetWindowThreadProcessId(m.pnHWND,@m.nProcessID) > IF m.nThreadID = 0 OR m.nProcessID = 0 > RETURN > ENDIF > * otherwise, kill it, because it does not respond to messages > m.nTries = 0 > m.plKillWhenNoShutdown = .T. > ENDIF > > Sleep(10) > m.nTries = m.nTries - 1 > ENDDO > > IF !m.plKillWhenNoShutdown > RETURN > ENDIF >ENDIF > >* if we're here, then we just need to kill it >TerminateProcess(OpenProcess(PROCESS_TERMINATE,0,m.nProcessID),-1) > >RETURN >>