rm /blog

IT系技術職のおっさんがIT技術とかライブとか日常とか雑多に語るブログです。* 本ブログに書かれている内容は個人の意見・感想であり、特定の組織に属するものではありません。/All opinions are my own.*

【Windows】openfilesコマンド

UnixにおけるfuserコマンドWindows版みたいのねーかなーと思ってググったら「openfiles」ってコマンドを見つけた。
参考URL:
http://www.atmarkit.co.jp/ait/articles/0306/14/news002.html


 

 


ちなみにまず前提で以下のコマンドによる設定変更が必要になる。(再起動要)

openfiles /local on


fuserコマンドが、引数にファイルを指定する(つまり、特定のファイルを掴んでいるプロセスを探す)のに対し、
openfilesコマンドは、引数なしで起動でき、「今掴まれているファイルとそれを掴んでいるプロセス」を一覧表示してくれる。
なので、fuser的に使うには、パイプで繋いで、対象となるファイルをfindstrで引っかけるのがいいんだろう。
(openfiles自体のオプションでも備わってそうだがやり方知らない)

openfiles | findstr "test.txt"


実行すると以下のような結果↓になるが

232   sakura.exe           C:\temp\test.txt

このうち、左端にある「232」ってのがファイルID。
真ん中がプロセスのイメージ名。(taskkillの/imオプションで渡すと殺せる)
右端がファイル名。
この場合だと、「232」番のファイルIDである「C:\temp\test.txt」「sakura.exe」が掴んでいる、
という事実が読み取れる。

このとき、以下のコマンドを実行することで、「C:\temp\test.txt」を掴んでいるプロセスだけを殺して解放することができる。

openfiles /disconnect /op "C:\temp\test.txt" /ID 232

 




ちなみに、左端は「ファイルID」であって「プロセスID」ではない。
なので、taskkillコマンドの/pidオプションにこの値を渡しても失敗する、
というか空振り失敗で済めばまだいいが、
最悪死んでほしくないプロセスを殺してしまう可能性があるのでやめたほうがいい。
(偶然同じ数字のPIDがいた場合はマジに殺してしまうから)

あと、↑に書いたとおり、真ん中がイメージ名としてもうわかっているので、
少し乱暴だがここまでわかれば極論

taskkill /f /im "sakurae.exe"

で殺すことができる。
(少なくとも「C:\temp\test.txt」を掴んでいるプロセスを解放はできる)
しかしこれをやるとsakura.exe自体を抹殺するため、
sakura.exeが掴んでいる「C:\temp\test.txt」以外のファイルも全部解放されるものの、
その中に死んでほしくなかったプロセスがあった場合は冒険の書は消えてしまいました」状態に陥る。
特定のファイルを掴んでいるプロセスだけを殺すという意図であれば
素直に↑のopenfiles /disconnectを使ったほうが良いと思われる。