{{category Command Prompt,nolink}} バッチで多重起動チェック・起動防止をする !!!多重起動チェック バッチファイルで多重起動をチェック・起動防止する。 よくある方法としては、以下の方法が見つかる。 * 方法1:バッチファイル自身を追記モードで開く。 * 方法2:ロックファイルを使う。 * 方法3:プロセスの有無をチェックする。 方法3のプロセス有無は、tsklist コマンドで実行されているコマンドをチェックする。 ただ、同時に実行された場合など、プロセスのチェックまでの隙間で、うまくチェックできない可能性ある。 また、方法1の場合、バッチファイル自身を追記で開きロックされるため、実行中はバッチファイル自体を変更できなくなる。 逆にエディタなどで開いてロックがされている場合も、実行中と判断される。 !!!方法1:自身を追記モードで開く バッチファイル自身に対して、リダイレクトの追記モードで開き、バッチファイルをロックする。 2つ目以降は、追記モードで開こうとするが、ロックがされているため、エラーとなり終わる。 @ECHO OFF CALL :MAIN %* 3>>"%~f0" EXIT /B :MAIN echo main start timeout 15 echo main end EXIT /B 0 2行目で、5行目以降(:MAIN 移行)のバッチを実行する。 その際、自身に対して追記で開こうとする(リダイレクトの追記だが、3番はないもないので、何も書かれない)。 この時すでに開かれていて、ロックがされていると、オープンに失敗してエラーとなり、終了する。 最後の「EXIT /B 0」が、バッチファイルのエラーレベルとなるが、多重起動で終了した場合、設定されず 0 が返る。 この多重起動で終了したかをエラーレベルで取得したい場合、「CALL :MAIN」で呼ぶ前に任意の値をセットしておく必要がある。 !!!方法3:プロセスの有無をチェックする プロセスの二重起動防止など tasklist コマンドでプロセスのリストを取得(UNIX の ps 代用)、findstr コマンドで文字列検索し(UNIX の grep 代用)、 findstr で文字列が見つかったかは ERRORLEVEL で返ってくる(見つかった場合は 0、ない場合は 1 が返る)。 tasklist | findstr sakura.exe if errorlevel 1 ( rem 起動していない )else( rem 起動してる ) !tasklist と findstr C:\>tasklist イメージ名 PID セッション名 セッション# メモリ使用量 ========================= ======== ================ =========== ============ System Idle Process 0 Services 0 8 K System 4 Services 0 6,716 K  :後略 C:\>tasklist | findstr sakura.exe C:\>echo %errorlevel% 1 C:\>tasklist | findstr sakura.exe sakura.exe 6352 Console 1 21,528 K sakura.exe 34304 Console 1 18,128 K C:\>echo %errorlevel% 0 C:\>