2009-10-16 12 views

risposta

20

controllare questi

Inno Setup: Detect instances running in any user session with AppMutex

Inno Setup: Is application running?

Inno Setup: Detect if an application is running

Ci sono diversi modi. Se il programma definisce utilizzare un mutex

[Setup] 
AppMutex=MyMutexName 

o per un mutex specificato nella sezione Code

function CheckForMutexes (Mutexes: String): Boolean; 

Si potrebbe anche usare

function FindWindowByClassName (const ClassName: String): Longint; 

per ottenere l'handle di finestra per nome della classe e mandalo messaggi

o scarica dal nome

function FindWindowByWindowName (const WindowName: String): Longint; 

O si utilizza uno dei diversi file DLL per questo specifico caso d'uso

o farlo te stesso dopo aver letto

How To Terminate an Application "Cleanly" in Win32

How To Enumerate Applications Using Win32 APIs (questo link alla versione tedesca, come per qualche motivo non riesco a trovare la versione inglese di KB175030

o provare la versione tradotta di Google del KB175030-DE

KB175030 DE -> EN

+1

Risposta stupenda. Molto accurato; grazie! L'opzione mutex globale impiegò 5 minuti per farlo bene! Niente di meglio. – max

+0

Hai una risposta per il file basato su rete che può essere aperto sulla memoria di un altro computer? – none

+0

L'ultima versione inglese di KB 175030 che ho trovato sulla Wayback Machine è stata presa a febbraio 2007: http://web.archive.org/web/20070216103757/http://support.microsoft.com/kb/175030. –

14

Abbiamo utilizzato un metodo diverso da quello descritto sopra. Poiché si tratta di una disinstallazione, è possibile eliminare l'applicazione e annullarla. Il modo più semplice, quando la u non può usare AppMutex: (in relazione alla Really killing a process in Windows)

[UninstallRun] 
Filename: "{cmd}"; Parameters: "/C ""taskkill /im <precessname>.exe /f /t" 

speranza che qualcuno vi aiuterà questo. Ho cercato a lungo per questo.

+0

Il 'taskkill' uccide più di un'istanza in esecuzione dello stesso processo? – TLama

+1

Provato con notepad.exe e sta funzionando molto bene. Ucciderà l'applicazione senza feedback. – kdoteu

+2

Grazie! Sì, uccide tutte le istanze a meno che non si esegua l'installazione con privilegi inferiori rispetto al processo elevato. [+ 1ed comunque :)] – TLama

6

Prova questa soluzione! Ho avuto problemi con altre soluzioni per chiudere l'app, ma Inno Setup pensava ancora che i file installati fossero bloccati.

Ricordate di definire le costanti:

#define MyAppName "AppName" 
#define MyAppExeName "AppName.exe" 

[Code] 
function InitializeUninstall(): Boolean; 
    var ErrorCode: Integer; 
begin 
    ShellExec('open','taskkill.exe','/f /im {#MyAppExeName}','',SW_HIDE,ewNoWait,ErrorCode); 
    ShellExec('open','tskill.exe',' {#MyAppName}','',SW_HIDE,ewNoWait,ErrorCode); 
    result := True; 
end; 

principali puntelli al original source of this solution.

+1

Questo è ottimo, una cosa che ho cambiato è stata l'utilizzo di una procedura diversa invece di "function InitializeUninstall(): Boolean;" dovuto al fatto che questa funzione uccide l'app anche se l'utente annulla il processo di disinstallazione mentre "procedura InitializeUninstallProgressForm;" verrà eseguito solo se confermerà la disinstallazione. –

3

Utilizzare il AppMutex directive per evitare che il programma di disinstallazione di procedere, quando un'applicazione è in esecuzione.

[Setup] 
AppMutex=MyProgMutex 

L'applicazione deve creare il mutex specificato dalla direttiva. Vedere la documentazione della direttiva AppMutex collegata per gli esempi.


Se si desidera avere il programma di disinstallazione uccidere l'applicazione, quando si è ancora in esecuzione, utilizzare questo codice invece:

function InitializeUninstall(): Boolean; 
var 
    ErrorCode: Integer; 
begin 
    if CheckForMutexes('MyProgMutex') and 
    (MsgBox('Application is running, do you want to close it?', 
      mbConfirmation, MB_OKCANCEL) = IDOK) then 
    begin 
    Exec('taskkill.exe', '/f /im MyProg.exe', '', SW_HIDE, 
     ewWaitUntilTerminated, ErrorCode); 
    end; 

    Result := True; 
end; 

Come con la direttiva AppMutex sopra, l'applicazione deve creare il mutex specificato nella chiamata CheckForMutexes.


Si noti che per l'installazione, non è necessario codificarlo. Il programma di installazione ha un gestore di riavvio integrato.
Vedere Kill process before (re)install using "taskkill /f /im" in Inno Setup.

Problemi correlati