windows – USBデバイスの接続を検出してスケジュールされたタスクを起動する

event-log scheduled-tasks usb-storage windows windows-task-scheduler

Win 7ではオートラン(オートプレイ?)の制限で接続時にUSBドライブからアプリケーションを起動できないという話があったと思います。しかし、イベントタイプのトリガーを持つスケジュールタスクを作成することは可能です。確かにドライブが接続されたときにイベントが発生しなければなりませんが、USBデバイスが接続されたときにイベントタイプのトリガーを持つスケジュールタスクを作成することは可能です

誰かどのイベントIDを使えばいいのか、ちょっとした見当がつきますか?あるいは、少なくともイベントの種類は?イベントビューアのどこでイベントを見つけることができますか?

  27  None  2010-12-07


ベストアンサー

スレッド タスクスケジューラ。どのように自動的に私のUSBフラッシュドライブを同期するには?は、タスクスケジューラと一緒にPowerShellを使用しているモノトーンと呼ばれるユーザーによるこの答えを持っています

私もあなたと同じ疑問を持ち、Scripting Guy Blog こちらこちら のテクニックを使って powershell (Windows 組み込みのスクリプト) を使って何かを解決しました。スクリプトはバックグラウンドプロセスとして継続的に実行され、システムログオン時にタスクスケジューラで起動することができます。新しいドライブが差し込まれるたびに通知され、何かをしてくれます(ここではタスクではなくスクリプトを設定します)。基本的には次のプラグインされたドライブを待っている間に一時停止されるので、あまりリソースを消費することはないはずです。ここで、私は行きます

1) スタートメニューのアクセサリ/Windows Powershell の下にある Powershell ISE を起動します。 2) 以下をコピーして Powershell に貼り付けます

#Requires -version 2.0
Register-WmiEvent -Class win32_VolumeChangeEvent -SourceIdentifier volumeChange
write-host (get-date -format s) " Beginning script..."
do{
$newEvent = Wait-Event -SourceIdentifier volumeChange
$eventType = $newEvent.SourceEventArgs.NewEvent.EventType
$eventTypeName = switch($eventType)
{
1 {"Configuration changed"}
2 {"Device arrival"}
3 {"Device removal"}
4 {"docking"}
}
write-host (get-date -format s) " Event detected = " $eventTypeName
if ($eventType -eq 2)
{
$driveLetter = $newEvent.SourceEventArgs.NewEvent.DriveName
$driveLabel = ([wmi]"Win32_LogicalDisk='$driveLetter'").VolumeName
write-host (get-date -format s) " Drive name = " $driveLetter
write-host (get-date -format s) " Drive label = " $driveLabel
# Execute process if drive matches specified condition(s)
if ($driveLetter -eq 'Z:' -and $driveLabel -eq 'Mirror')
{
write-host (get-date -format s) " Starting task in 3 seconds..."
start-sleep -seconds 3
start-process "Z:\sync.bat"
}
}
Remove-Event -SourceIdentifier volumeChange
} while (1-eq1) #Loop until next event
Unregister-Event -SourceIdentifier volumeChange

3) 上のスクリプトを修正して、どのドライブを探して何を実行するかを伝える必要があります。変更するのは2行です

if ($driveLetter -eq 'Z:' -and $driveLabel -eq 'Mirror')

Mirror」という名前の私のUSBハードドライブはZ:ドライブに設定されています。文字を気にしなければ if ($driveLabel -eq 'MyDiskLabel') でいいんですよね

start-process "Z:\sync.bat"

やりたいタスクのパスを指定します。私の例では、3-4個のバックアップタスクのコマンドラインを起動するバッチファイルをUSBドライブに作成しています

4) スクリプトが終わったら、スクリプトをどこかに保存し(拡張子 .ps1)、タスクスケジューラでタスクを作成してバックグラウンドでスクリプトを実行させます。私の場合は以下のようになります

  • トリガー。ログオン時
  • アクション。プログラムを開始します
  • Program/script: powershell
  • 引数を追加します。-ExecutionPolicy Unrestricted -File "D:\Stuff\Backup script.ps1"

5) Voilà!

6)余分なもの

スクリプトウィンドウを非表示にしたい場合は、これらの引数を使用します

  • 引数を追加します。 -WindowStyle Hidden -ExecutionPolicy Unrestricted -File "D:\Stuff\Backup script.ps1"

スクリプトのメッセージをログファイルに出力したい場合 (スクリプトが起動するたびに、つまりログオン時に上書きされます)、以下のタスクアクションを使用します

  • Program/script: cmd
  • 引数を追加します。 /c powershell -WindowStyle Hidden -ExecutionPolicy Unrestricted -File "D:\Stuff\Backup script.ps1" > "D:\Stuff\script log.txt”

実行中の隠しスクリプトを終了させたいときはいつでも、タスクマネージャーで「Powershell」プロセスを終了させることができます

唯一の欠点は、ドライブがすでに接続されている状態でコンピュータを起動しても何も実行されないことです。(スクリプトは最初に最初のチェックを行うように変更することもできますが、今日はもう十分です!)

18  harrymc  2014-11-26


すでにこの議論で説明したように(ただし、それはUSBドライブを削除するときにプログラムを実行することについてでした)、USB Safely Removeは、無料ではありませんが、USBデバイスに関するいくつかのイベントがトリガーされたときにプログラムを実行することができます

類似のソフトウェアと区別するもう一つのUSB Safely Remove機能は、デバイスを接続した後だけでなく、取り外す前に任意のアプリケーションを起動することです。自動実行機能では、リムーバブルハードドライブを切り離す前にデータのバックアップを設定したり、ペンドライブの内容でTotal Commanderを実行したり、USBメディアを切り離す前に暗号化されたTrueCryptドライブを自動的にアンマウントしたりと、様々なことが可能だ

enter image description here

もちろん、これはスケジュールタスクを使うということではないので、完全な答えにはなっていませんが、USBメモリを差し込んだときに特定のプログラムを実行するという目的は同じだと思います

6  Snark  2011-05-25


EventVwrを使えばかなり簡単にできるはずです

  1. 欲しいイベントを見つける – USB大容量記憶装置を接続すると、以下のイベントが発生しました(アプリケーションカテゴリの下):20001, 20003, 7036、その他いくつかのあまり関連性のないイベントです。誤検出を避けるために、他のUSBデバイスのイベントに対してこれらのイベントをテストすることを確認してください

  2. イベントを右クリックして、”このイベントにタスクを添付 “をクリックします(Windows Vista以上でのみ関連します – XPの場合はCLI EventTriggerがあります)、”プログラムを開始 “を選択して、実行したいスクリプトにポイントします

  3. スクリプトにイベントパラメータを渡すには、この記事を参照してください。イベント20001と20003の下に、新しいストレージへのUNCパスを見つけることができます。Sysinternals Junctionユーティリティを使用して、UNCパスへのリンクを作成することができます

5  EliadTech  2013-10-14


これで動作させることができました。アプリケーションとサービスのログ、Microsoft-Windows-DriverFrameworks-UserModeで、usbに接続された電話機のイベント1003を見つけました

イベントの完全なxml

- <Event xmlns="http://schemas.microsoft.com/win/2004/08/events/event">
- <System>
<Provider Name="Microsoft-Windows-DriverFrameworks-UserMode" Guid="{2E35AAEB-857F-4BEB-A418-2E6C0E54D988}" />
<EventID>1003</EventID>
<Version>1</Version>
<Level>4</Level>
<Task>17</Task>
<Opcode>1</Opcode>
<Keywords>0x8000000000000000</Keywords>
<TimeCreated SystemTime="2016-08-19T01:42:06.292278900Z" />
<EventRecordID>17516</EventRecordID>
<Correlation />
<Execution ProcessID="456" ThreadID="2932" />
<Channel>Microsoft-Windows-DriverFrameworks-UserMode/Operational</Channel>
<Computer>5CG6070VFK-W7.nikonprecision.com</Computer>
<Security UserID="S-1-5-18" />
</System>
- <UserData>
- <UMDFDriverManagerHostCreateStart lifetime="{AFEC92AD-6015-4AB4-86AE-F34CEE06A977}" xmlns:auto-ns2="http://schemas.microsoft.com/win/2004/08/events" xmlns="http://www.microsoft.com/DriverFrameworks/UserMode/Event">
<HostGuid>{193a1820-d9ac-4997-8c55-be817523f6aa}</HostGuid>
<DeviceInstanceId>USB.VID_04E8&PID_6860&MS_COMP_MTP&SAMSUNG_ANDROID.6&3400EB54&1&0000</DeviceInstanceId>
</UMDFDriverManagerHostCreateStart>
</UserData>
</Event>

そして、私のタスクのためのカスタムイベントフィルター

<QueryList>
<Query Id="0" Path="Microsoft-Windows-DriverFrameworks-UserMode/Operational">
<Select Path="Microsoft-Windows-DriverFrameworks-UserMode/Operational">*[System[Provider[@Name='Microsoft-Windows-DriverFrameworks-UserMode'] and EventID=1003]] and *[UserData[UMDFDriverManagerHostCreateStart[DeviceInstanceId="USB.VID_04E8&amp;PID_6860&amp;MS_COMP_MTP&amp;SAMSUNG_ANDROID.6&amp;3400EB54&amp;1&amp;0000"]]]</Select>
</Query>
</QueryList>

同様に、特定のUSBドライブについては、イベント2100、2101、2105、2106であった

- <Event xmlns="http://schemas.microsoft.com/win/2004/08/events/event">
- <System>
<Provider Name="Microsoft-Windows-DriverFrameworks-UserMode" Guid="{2E35AAEB-857F-4BEB-A418-2E6C0E54D988}" />
<EventID>2101</EventID>
<Version>1</Version>
<Level>4</Level>
<Task>37</Task>
<Opcode>2</Opcode>
<Keywords>0x8000000000000000</Keywords>
<TimeCreated SystemTime="2016-08-19T01:52:37.922289600Z" />
<EventRecordID>17662</EventRecordID>
<Correlation />
<Execution ProcessID="10956" ThreadID="11892" />
<Channel>Microsoft-Windows-DriverFrameworks-UserMode/Operational</Channel>
<Computer>5CG6070VFK-W7.nikonprecision.com</Computer>
<Security UserID="S-1-5-19" />
</System>
- <UserData>
- <UMDFHostDeviceRequest instance="WPDBUSENUMROOT\UMB\2&37C186B&0&STORAGE#VOLUME#_??_USBSTOR#DISK&VEN_SANDISK&PROD_SANDISK_CRUZER&REV_8.02#0774230A28933B7E&0#" lifetime="{4493DBFB-81E8-4277-933D-955C4DDDD482}" xmlns:auto-ns2="http://schemas.microsoft.com/win/2004/08/events" xmlns="http://www.microsoft.com/DriverFrameworks/UserMode/Event">
- <Request major="27" minor="20">
<Argument>0x0</Argument>
<Argument>0x141b</Argument>
<Argument>0x0</Argument>
<Argument>0x0</Argument>
</Request>
<Status>0</Status>
</UMDFHostDeviceRequest>
</UserData>
</Event>

usbドライブを接続すると、イベント2101が3回、微妙に異なる"<request>"タグで発生するようです

<Request major="27" minor="20">
<Request major="27" minor="9">
<Request major="27" minor="0">

これが何を意味するのかわかりませんが、ここでは複数のトリガーを避けるために1つだけにフィルターをかけています。(これはこの特定のUSBドライブに対してのみトリガされます)

<QueryList>
<Query Id="0" Path="Microsoft-Windows-DriverFrameworks-UserMode/Operational">
<Select Path="Microsoft-Windows-DriverFrameworks-UserMode/Operational">*[System[Provider[@Name='Microsoft-Windows-DriverFrameworks-UserMode'] and  EventID=2101]] and *[UserData[UMDFHostDeviceRequest[@instance="WPDBUSENUMROOT\UMB\2&amp;37C186B&amp;0&amp;STORAGE#VOLUME#_??_USBSTOR#DISK&amp;VEN_SANDISK&amp;PROD_SANDISK_CRUZER&amp;REV_8.02#0774230A28933B7E&amp;0#" and Request[@major="27" and @minor="20"]]]]</Select>
</Query>
</QueryList>

アンパサンドは&amp;のようにエスケープしなければならないことに注意してください

2  garbb  2016-08-19


他の人が言っているように、Service Control Managerからのシステムログイベント7036が、USBドライブの挿入と確実に相関する唯一のイベントのようです。私は、USB ドライブを挿入して、以下の powershell コマンドを実行して、過去 1 時間のすべてのソースからのすべてのイベントログエントリをリストアップすることによってこれを確認しました

get-winevent | where {$_.timecreated -ge (get-date) - (new-timespan -hour 1)}

残念ながら、イベント7036はサービスコントロールマネージャが正常にサービスを開始または停止するたびに生成されるため、追加のフィルタリングが必要となります

Event Viewer / Task Scheduler の GUI で利用可能なフィルタリングは非常に基本的なもので、イベントデータに対するフィルタリングはできません。これは EventData の “param1” と “param2” に保持されています。そのため、以下の XPath フィルタを使用して、関連するサービスの起動のみをキャプチャすることができます

<QueryList>
<Query Id="0" Path="System">
<Select Path="System">*[System[Provider[@Name='Service Control Manager'] and (Level=4 or Level=0) and (band(Keywords,36028797018963968)) and (EventID=7036)]]
and
*[EventData[
Data[@Name="param1"]="Portable Device Enumerator Service" and
Data[@Name="param2"]="running"
]
]
</Select>
</Query>
</QueryList>

そこからスクリプトを実行することができます。理想的には、挿入されたUSBドライブが目的のものであるかどうかをチェックするために、いくつかの追加ロジックを配置することができます

1  sahmeepee  2013-11-02


Applications and Service Logs-Microsoft-Windows-NTFS_Operational の下にあるイベントログから、もっと良い (IMO) イベントを見つけました。Eventid 4.以下のようになっています

イベントID 4 NTFSボリュームが正常にマウントされました

       Volume GUID: {55bf0ee3-d507-4031-a60a-22e5892ebf37}
Volume Name: E:
Volume Label: AirGapDrive A
Device Name: \Device\HarddiskVolume51

そこからスケジュールされたタスクトリガーを作成し、ボリューム名やラベルでフィルタリングすることができます。このイベントはWindows Server 2019のボックスで発見されましたが、なぜか私のWindows 10(1809)のデスクトップでは表示されません。サーバーのみのイベントかもしれません

1  RyanG  2019-02-27


タイトルとURLをコピーしました