Archive: uninstall: how to check if the application is running


uninstall: how to check if the application is running
  Hi!

Does anyone know how I can check if the application is running (or kill the task) before I can start the installer/uninstaller?

(the application is only in the system tray viewable)

regards
spiff_c99


That depends on your application. Usually you'll use FindWindow with your window's class name and if you get a good handle (check with IsWindow) then you'll know the application is running. To close it you'll have to send the right message using SendMessage which is usually WM_CLOSE (!include WinMessages.nsh to get it defined).


hy

I have almost the same problem, but i am realy a newbie in this matter:

I have running a process and i do not want to let the installer continue until the process was ended by the user.

I think FindWindow will not work, because the application has no Window.

The installer therefore has to check if the task is running and if so the installer has to abort!

Is this possible??

I would very much appreciate it if you could make me a example and tell me exactly where i have to insert it in the NSI-File.

Thank you very much for your help.
regards
linuxfreak


Not all windows are visible. Most application do have at least one window for processing messages. If the user must end this process on its own then there must be a window that receives messages. A tray icon requires a window. The best way to know how to close the application is to ask the author of the program or just sniff the window class with a program that shows you all of the available windows, which I can't find now. Maybe I'll write one of my own later ;)

Anyway, the best way is to just ask the author, or if open source look the window creation code and see what window class is used. If it is open source and you have no idea about what to look for give me a link and I'll have a look.


hy kichik

I have the information:

ClassName: ThunderRT6FormDC
WindowText: Share Spy

I could get this information with Win32Spy 0.2. Maybe this can help other users to find out their ClassNames.

Here's the code i think i need:

FindWindow $0 "ThunderRT6FormDC"
IntCmp $0 0 done
IsWindow $0 0 done

done:
Abort "Installation aborted!"
But still i don't know where to paste it in the nsi-File. Also i suppose i need to insert a second "goto" in case the application is not running...

Please help me! Thank you

PS: I coded this program in Visual Basic 6.0 and I don't know how to change its ClassName. Does anyone has an idea? :confused:


onInit

again:
FindWindow $0 "ThunderRT6FormDC" "Share Spy"
IsWindow $0 0 done
MessageBox MB_ABORTRETRYIGNORE
|MB_ICONSTOP "Close Share Spy..."
IDRETRY again IDIGNORE done
Abort

done:
>FunctionEnd
>
This code will try to find the window when the installer starts (.onInit) and if it finds will ask the user if to abort, ignore or retry.

I think ThunderRT6FormDC is a generic VB6 name. It will close other apps too.


But this one searches for the title too. It will be better of course to get your own class name, but I have no idea how to do that in VB6 ;)


@kichik
perfect!! Thank you very much. This is exactly what i was looking for!!

@Joost Verburg
Altough the solution from kichik is perfect and nothing more must be done, i don't like this generic classname. I searched the whole web for a solution, but couln't find anything. So if you have any idea, i'd be very thankful for any hint!

THX
linuxfreak


You can use a named mutex. CreateMutexA will return ERROR_ALREADY_EXISTS (which equals to decimal 183) if a mutex with the same name already exists anywhere in the system. So create a mutex with a certainly unique name in your application, and when your uninstaller can not create mutex with the same name, you can be sure - your application is running.


Thank you very much!
I could resolve my own problem with these answers.
:up:

@linuxfreak
You can't edit the classname in Visualbasic.
Visualbasic set the classname "ThunderRT6FormDC"
during the compilation process.

regards
spiff_c99


...or just sniff the window class with a program that shows you all of the available windows, which I can't find now. Maybe I'll write one of my own later ;)
Later has come :)

This one only works on Windows NT 4, 2000 and XP because it uses special API calls that are only available on those OSes to get the process EXE name. Maybe I'll create one that works with 9x too later... Comes with source code.


Originally posted by kichik
Quote:
Later has come... This one only works on Windows NT 4, 2000 and XP because it uses special API calls that are only available on those OSes to get the process EXE name. Maybe I'll create one that works with 9x too later...

...or just sniff the window class with a program that shows you all of the available windows, which I can't find now. Maybe I'll write one of my own later...


What about the Spy++ or WinSight32, which come respectively with Microsoft and Borland software development tools? Both work under NT and 9x Windows families.

Spy++ only comes with the commercial package afaik. I don't know about WinSight32, but if it's the replacement of Spy++ for Borland then I guess it's not free either. Spy++ doesn't do what my application does, and if WinSight32 is the same then that goes for it too. This tool is designed only for this job, it's small, fast, and doesn't crash every two minutes like Spy++ (could be it just doesn't like me though :p).


Spy++ doesn't do what my application does
Not sure :p

...and doesn't crash every two minutes like Spy++
I do not remember when Spy++ was crashing last time... Maybe past year.

You right about the commercial packages, but I think most of this forum members have one of these.

Spy++ doesn't list the windows on the system and categorizes them according to their process, module and class unless it has some secret switch I don't know of.

You'll be surprised how many of NSIS users don't have a commercial package...


Spy++ doesn't list the windows on the system and categorizes them according to their process, module and class unless it has some secret switch I don't know of.
From this point of view you probably right with the exception that Spy++ DOES list the windows on the system. At the same time it can do many other wonderful things :)

Perhaps I should take a look on Spy++ supplied with Visual Studio .NET

Well, that is what this tool has been created for ;)


I've found that using the "ThunderRT6FormDC" window handle also closed the VB IDE if I was still coding, making a minor change to "ThunderRT6Main"

Change this:

FindWindow $0 "ThunderRT6FormDC" # Closes All VB Windows

to this, where "MR Tech Systray" is the app title used:
FindWindow $0 "ThunderRT6Main" "MR Tech Systray"  # Only closes specific app instance

Hi,

I tried to use your code snippet to check a running application but got while compiling the script following error:

Invalid command: IDRETRY


complete function


Function un.onInit
!insertmacro MUI_UNGETLANGUAGE
again:
FindWindow $0 "ApplicationClass" "WindowName"
IsWindow $0 0 done
MessageBox MB_ABORTRETRYIGNORE|MB_ICONSTOP "Close Application..."
IDRETRY again IDIGNORE done
Abort

done:
FunctionEnd


Do I have to include a special library for this?

cheers,

Christoph

Hi,ripcurlx.

Error is caused by line-breaking mistake. A inattantive error? :)

MessageBox MB_ABORTRETRYIGNORE|MB_ICONSTOP "Close Application." \
IDRETRY again IDIGNORE done

thx - it´s always the same ;-)


Hi,

Concerning the FindWindow function, I understand it takes a class name and/or dialog caption.

When the application you're trying to find is available in many languages, it's just not possible to use the dialog caption, unless someone would iterate through possible strings and hope to get one translation correct.

Then for the class name, .NET class names tend to be a bit descriptive; e.g.: WindowsForms10.Window.8.app.0.378734a
Now, I don't mean to suggest that I understand the representation of the .NET class name, but something makes me believe they're tightly coupled to all sort of version and build numbers from inside .NET. Heck, maybe rebuilding the application changes the said class name.

Given my pessimistic view of FindWindow as a reliable way of finding if a said application is running, does anyone have an alternative ... better solution?


IMHO, the cleanest way to exit a running application while uninstalling is to send a DDE message to that application that tells it to Quit
(if you're the author of the application, you might need to implement a DDE server, which is not too hard if you're using MFC)
To send the DDE message in the uninstaller, you can use my nsisDDE plugin


you can also use it in the installer during an upgrade, to exit the application

if your application is limited to one instance, you can also use DDE messages to bring the currently running application to the foreground

It works perfectly well with Microsoft applications (like WinWord) that implements a DDE server.


Thanks for the info Wizou,

I had tought DDE mechanism deprecated, but it seems still supported.

I think I'll just create a dummy window in my app through WIN32 APIs RegisterClass and CreateWindow and then try to find THAT window from the NSIS script using ... FindWindow.
:)