Check if program already running


I'm trying to write a program that the user can only run if an instance of it is not already in processes.

BTW, this program is written in C, I'm not sure where to start

 I could create some kind of temp file, which indicates if its running, but I'm thinking theres a more elegant solution.

Thoughts appreciated

Who is Participating?
cookreConnect With a Mentor Commented:
A common way is to try to get a mutex when the program starts:

DWORD      TempError;
char       WIB[16];      // Who I Be (known as)
char       MyGUID[64];   // How do YOU spell GUIDGEN?
char       MyCLSID[128]; // WIB+MyGUID

strcpy(MyGUID,A GUID you can get from GUIDGEN like "a4a20e1a-b5e1-4a72-bef8-2121b014e33e");
strcpy(WIB,"I use my program name here");
so the CLSID I use to get the mutex is the same as is passed to RegisterClassEx(), if it's a Windows program.

if (Mutie==NULL)
   // nasty occured
    // code is already running elsewhere
Another common method used by some software developers, is to create 'something' while the program is running, then get the program to check if this 'something' already exists, if it does, then an instance already exists. For an example of a 'something', it's quite common to use:

   ~ A temporary file  (but lock it)
   ~ A ServerSocket on a specific (and rarely used) port
   ~ A registry key (similar method to the file)

The first and last suggestions are those which I use most frequently, as the ServerSocket method can cause quite a few problems, for example, sometimes even after a program has been closed, it can take up to a few minutes before any Socket connections are released -- this would this mean that you cannot load your program up again, for up to a few minutes!
Then there's the firewall problems, people can prevent ServerSocket connections (or block streamed data to a specific port, even on a local machine) with the use of a firewall; so if someone wanted to run multiple instances, then they can quite easily achieve this, if you used a Socket method.

I hope that gives you some ideas.

How do you get a registry key to go away if the program dies unexpectedly?

At least no one has mentioned hInstance :)
Cloud Class® Course: Amazon Web Services - Basic

Are you thinking about creating an Amazon Web Services account for your business? Not sure where to start? In this course you’ll get an overview of the history of AWS and take a tour of their user interface.

But if it's not a Windows Program, then you can't use hInstance, can you (without Native)?

Surely, what you could do however, is simply get a list of all running processes, if your applications process exists, then it's already running... You usually have to use something like C/C++ to list the running processes, but you can achieve this in any language, by calling a program which lists of running processes (such as PSKILL.exe []), then catch it's output, and search the output for your process name... this can even be achieved in MS-DOS!

Sorry, you wouldn't use PSKILL.exe - lol - you would use PSLIST.exe:

>>>But if it's not a...
Lordy, no.  Even MS recommends against using it.

Enumerating processes is fun, but is fooled by a change in exe file name.
Eduard GherguLeader SibiuCommented:
You can use also the win 32 api functions FindWindow (or FindWindowEx if necessary).
>>  >>>But if it's not a...
>>  Lordy, no.  Even MS recommends against using it.

Oh right :-) lol. There, I've learnt something new.  ;-)

>> You can use also the win 32 api functions FindWindow (or FindWindowEx if necessary).

But, isn't this once again assuming that this application is a Windows Program? I'm not sure if that would work unless the application Registers a Window first.. Haven't done much Win32 however, so you'll have to verify this.

Mike, it's all very circumstantial; I think that you should stick with a simple and 'traditional' technique, rather than resorting to all these Win32 Functions, etc.

One idea, which supports if the program is instantly closed, and it doesn't get to finish up anything before exiting, is:

Firstly, you must multithread the application; then, you get this extra thread to write the current time to a file (overwriting any existing data), every # seconds (perhaps, every 4 seconds?).
Now, when someone starts up your application, it firstly checks to see if this file exists, and if it does, then it checks the time in the file, and compares it to the current system time; if it's within 5 seconds of the current time, then it closes, otherwise, it checks one last time (just to be sure) then starts up....

This is a nice little technique I think :-)   ...   But, heck, you may find it easier to use the FindWindow/Ex Function, or cookre's suggestion ;)

You can try this, it will look at the running applications and use the title of the running application as a comparison...

Call FindApp("Microsoft Outlook")

Public Sub FindApp(ByVal argStrAppToFind As String)

            Dim PrevHndl As Long
            'Variable to hold individual Process.
            Dim objProcess As New Process
            'Collection of all the Processes running on local machine.
            Dim objProcesses() As Process
            'Get all processes into the collection.
            objProcesses = Process.GetProcesses()

            For Each objProcess In objProcesses
                'Check and exit for loop if program is running already.
                If UCase(objProcess.MainWindowTitle) = UCase(argStrAppToFind) Then
                    'Already running.
                    PrevHndl = objProcess.MainWindowHandle.ToInt32()
                    Exit For
                End If

        End Try

    End Sub

Here's something a bit more basic...

       Dim cp As Process = System.Diagnostics.Process.GetCurrentProcess()
        Dim p As Process = New System.Diagnostics.Process
        Dim Prs As Process() = Process.GetProcesses()

        'Get a pointer to the current process.
        For Each pr As Process In Prs
            If pr.ProcessName = "Notepad" Then
                Exit Function
            End If

Hope this helps
I've already suggested this method of achieving this; and the author stated in the original question that he's using 'C', so I doubt that VB code is going to help him much.
Well convert it to C, if the question is still open tommorrow and I have time I'll  knock something up cheers ; )
Question has a verified solution.

Are you are experiencing a similar issue? Get a personalized answer when you ask a related question.

Have a better answer? Share it in a comment.

All Courses

From novice to tech pro — start learning today.