Announcement

Collapse
No announcement yet.

Multiple instances

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

  • Iain Johnstone
    replied
    Michael - on the Citrix thin client system, the app (in fact all apps) execute on the server. The client end can be any old PC/terminal because it is just a screen and a keyboard (basically), though most of the users do not know/understand this, which is just as well!. As this particular installation is on a local authority network, I am keen to keep all the 'housekeeping' within the app just in case it goes pear-shaped.

    Pierre & Mel - I will have a play with these suggestions. Fortunately I have a brother who is the ICT manager for a large London Borough that runs a Citrix systen, so I can get him to try out code before I attack the system at the other end of the country!


    Many thanks to you all

    Iain Johnstone

    Leave a comment:


  • Edwin Knoppert
    replied
    Not sure if it's so difficult to write a client/server app.
    There is DCOM and there is TCP..

    However, one can install an app twice isn't?
    If you are willing to accept this fact then imo there is a more simple option i spoke about before.
    You can let such an app seek a free spot in a file shared on a networkdevice.
    (you will get permissionsissues though)

    If you lock a single record in a random file you claim a single user this way.
    If the app is exitted (or crashes ) the record is released again.
    Seems a viable solution to me.

    Leave a comment:


  • Michael Mattias
    replied
    The problem is... each instance of your program is actually executing in the memory space of the client computer.

    So, the mutex approach could work if you do something like...
    Code:
    Enumerate all computers on the network
    For each computer
       Log on to that computer
       look for mutex or other object with known name
       If found
          increment user count
       end if
    Next
    If userCount > allowed
       message to user and terminate
    endif
    You'd have to put this code into the client application.

    Until there are no more crashes preventing update of the "user count file" I can't think of anything a whole lot better than this UNLESS you go to a true client-server application.. where each client must contact the server (which runs one instance on named machine) and that server application counts users and then responds to the starting client program that there is an insufficient number of licenses available for him to run right now.

    Hmmm... maybe there would be a market for such a product? There has to be a market.. meaning 'somewhere' there almost certainly exists an off-the-shelf solution.

    MCM

    Leave a comment:


  • Pierre Bellisle
    replied
    Iain,
    if you want to play with registered Window messages
    I'm pretty confident that you will acheive your goal.

    Code:
    #COMPILE EXE '#Win 8.04#
    #REGISTER NONE
    #DIM ALL
    #INCLUDE "Win32Api.inc" '#2005-01-27#
     
    %Label1      = 101
    %MaxInstance = 3
    '______________________________________________________________________________
     
    CALLBACK FUNCTION DlgProc
     STATIC WhosThere      AS DWORD
     STATIC ImHere         AS DWORD
     STATIC SetCount       AS DWORD
     STATIC InstancesCount AS DWORD
     
     SELECT CASE CBMSG
     
       CASE %WM_INITDIALOG
         WhosThere = RegisterWindowMessage("WhosThere")  'Message to provoke the "ImHere" response
         ImHere    = RegisterWindowMessage("ImHere")     'Message to count instances
         SetCount  = RegisterWindowMessage("SetCount")   'Message to show instances count
         PostMessage(%HWND_BROADCAST, WhosThere, 0, 0)   'Ask every instances to send a "ImHere" message
     
       CASE WhosThere                                    'An new instance want to count total instances
         PostMessage(%HWND_BROADCAST, ImHere, 0, 1)      'Send "ImHere" message with "1" to increment InstancesCount
     
       CASE ImHere                                       'Respond to an "ImHere" message
         IF CBLPARAM = 1 THEN                            'Increment InstancesCount if 1
           IF GetForeGroundWindow = CBHNDL THEN          'Are we foreground
             INCR InstancesCount                         'Increment InstancesCount
             PostMessage(%HWND_BROADCAST, SetCount, 0, InstancesCount) 'Set InstancesCount to every instance
           END IF
         ELSE
           DECR InstancesCount                           'Decrement InstancesCount
           PostMessage(%HWND_BROADCAST, SetCount, 0, InstancesCount) 'Set InstancesCount to every instance
         END IF
     
         IF InstancesCount > %MaxInstance THEN           'Check if maximum count is reached
           IF GetForeGroundWindow = CBHNDL THEN          'Supress only the foreground windows
             CONTROL SET TEXT CBHNDL, %Label1, "Sorry, no more than" & STR$(%MaxInstance) & _
                                               "instances," & $CRLF & "quitting now !"
             SLEEP 2000
             PostMessage(%HWND_BROADCAST, SetCount, 0, InstancesCount) 'Set InstancesCount to every instance
             DIALOG END CBHNDL                           'End application
           END IF
         END IF
     
       CASE SetCount
         InstancesCount = CBLPARAM                      'Set count total instances
         CONTROL SET TEXT CBHNDL, %Label1, FORMAT$(InstancesCount) & " instance(s)" 'Show result
     
       CASE %WM_DESTROY
         PostMessage(%HWND_BROADCAST, ImHere, 0, 0) 'Say we're leaving to decrement InstancesCount
     
      END SELECT
     
    END FUNCTION
    '______________________________________________________________________________
     
    FUNCTION PBMAIN()
     LOCAL hDlg AS DWORD
     
     DIALOG NEW %HWND_DESKTOP ,"Max 3 instance", , , 150, 70, _
       %WS_CAPTION OR %WS_MINIMIZEBOX OR %WS_SYSMENU, %WS_EX_TOPMOST TO hDlg
     SetClassLong hDlg, %GCL_HICON, LoadIcon(BYVAL %NULL, BYVAL %IDI_INFORMATION) 'Set a nice dialog icon
     
     CONTROL ADD LABEL, hDlg, %Label1, "Instances count", 10, 30, 130, 20, %SS_CENTER, 0
     
     DIALOG SHOW MODAL hDlg CALL DlgProc
     
    END FUNCTION
    '______________________________________________________________________________

    Leave a comment:


  • Mel Bishop
    replied
    Here is a routine that I use in my MP3 player found in the source code forum. It detects if the program is running on the same machine it's installed on.

    You may be able to modify it to suit your own particulars.
    Code:
    'in the main body of the program
        Title$ = "My running application                 '
        CONSOLE NAME Title$                              '
        TitleName = Title$                                  ' This MUST match the console
                                                                  ' name.
        IF Is_already_running(BYCOPY title$) THEN...
    
         
    FUNCTION Is_Already_Running(TitleName AS ASCIIZ) EXPORT AS LONG
        LOCAL hMutex AS LONG
        hMutex = CreateMutex(BYVAL %Null, 0, TitleName)
        IF hMutex = 0 THEN EXIT FUNCTION                ' Error in Mutex
        IF GetLastError = %ERROR_ALREADY_EXISTS OR FindWindow(TitleName, "") > 0 THEN
        FUNCTION = %TRUE
        END IF
        END FUNCTION
    I can't find where I got this routine from. My bad.
    Last edited by Mel Bishop; 9 Jan 2008, 03:45 PM.

    Leave a comment:


  • Iain Johnstone
    replied
    I am looking at a Citrix setup where the app runs on the server. What I have at present is a counter in a file that is incremented each time the program is run as a separate instance, and decremented when a session terminates. However, if the user just crashes out of the app, the counter is not decremented. If this happens over time, the counter will reach the maximum number of users even though they are not there! I an fully aware that this is not the best system, but it is all I have at the present, hence the question.

    Iain Johnstone

    Leave a comment:


  • George Bleck
    replied
    Couldn't each one create a similar but unique Mutex and then you can enumerate on the mutex names?

    Mutex = MutexSuffix + PID

    and then enumerate how many MutexSuffixes it sees?

    Leave a comment:


  • Michael Mattias
    replied
    >I bet there is an API call for this, but I cannot find one

    I'll bet there isn't anything; you generally do this counting via your application.

    "In theory" I suppose you could try logging on to the server, enumerating all the processes, getting the module names for those processes and looking at the file names for each process. If they are 'myprogram.exe' it's an instance of your program.

    Of course, you can beat this one easily enough.. just rename the exe.

    Then again, programs don't run "on a server", they run on the client.. unless you have a genuine client-server setup, in which case the server should count users in its own application logic.

    (e.g, you can run \\computername\path\programfile.exe from a client machine and it will not show up in an enumeration of processes on the server).

    MCM

    Leave a comment:


  • Iain Johnstone
    started a topic Multiple instances

    Multiple instances

    How can I detect how many instances of a given program are running on a server? I need this information to block additional users if the licenced number of users has been reached.

    I bet there is an API call for this, but I cannot find one!

    Iain Johnstone
Working...
X