2011-09-18 10 views
6

セマフォを使用して単純なルーチンを実装しようとしていますが、アプリケーションのインスタンスを3つしか実行できません。私は3つのミューテックスを使うことができましたが、これは今までこれを試した良いアプローチではありません。セマフォを使用するアプリケーションのインスタンスを3つしか許可しない

var 
    hSem:THandle; 
begin 
    hSem := CreateSemaphore(nil,3,3,'MySemp3'); 
    if hSem = 0 then 
    begin 
    ShowMessage('Application can be run only 3 times at once'); 
    Halt(1); 
    end; 

私はこれを正しく行うことができますか?

答えて

16

アプリケーションが終了した場合に自動的に行われないため、必ずセマフォを解放してください。

program Project72; 

{$APPTYPE CONSOLE} 

uses 
    Windows, 
    SysUtils; 

var 
    hSem: THandle; 

begin 
    try 
    hSem := CreateSemaphore(nil, 3, 3, 'C15F8F92-2620-4F3C-B8EA-A27285F870DC/myApp'); 
    Win32Check(hSem <> 0); 
    try 
     if WaitForSingleObject(hSem, 0) <> WAIT_OBJECT_0 then 
     Writeln('Cannot execute, 3 instances already running') 
     else begin 
     try 
      // place your code here 
      Writeln('Running, press Enter to stop ...'); 
      Readln; 
     finally ReleaseSemaphore(hSem, 1, nil); end; 
     end; 
    finally CloseHandle(hSem); end; 
    except 
    on E: Exception do 
     Writeln(E.ClassName, ': ', E.Message); 
    end; 
end. 
+0

偉大なコーダー、素晴らしい答え。ありがとう! – opc0de

+0

+1「SyncObjs.TSemaphore」は時間切れの待ち時間に対応していません。それとも、私は何かが恋しいですか? –

+0

D2007はSyncObjs.TSemaphoreも持っていません... XEでは正しいのですが、Linuxではタイムアウト0で待ちますが、Windowsでは待ちません。 Stupid – gabr

2
  1. あなたは、あなたがロックを解除しなければならない、それはあなたが、カウント終わり
  2. を得ることができるかどうかを確認するためにウェイト機能のいずれかを使用する必要があり
  3. を作成されたかどうかを確認しようとする必要があります&それは近い次回のユーザーを仕事とあなたのアプリ

乾杯

var 
    hSem: THandle; 
begin 
    hSem := OpenSemaphore(nil, SEMAPHORE_ALL_ACCESS, True, 'MySemp3'); 
    if hSem = 0 then 
    hSem := CreateSemaphore(nil, 3, 3,'MySemp3'); 

    if hSem = 0 then 
    begin 
    ShowMessage('... show the error'); 
    Halt(1); 
    Exit;  
    end; 

    if WaitForSingleObject(hSem, 0) <> WAIT_OBJECT_0 then 
    begin 
    CloseHandle(hSem); 
    ShowMessage('Application can be runed only 3 times at once'); 
    Halt(1); 
    Exit; 
    end; 

    try 
    your application.run codes.. 

    finally 
    ReleaseSemaphore(hSem, 1, nil); 
    CloseHandle(hSem); 
    end; 
を開くことができるように扱います
関連する問題