Detect plugged USB devices using WqlEventQuery and retrive their descriptive information

4.9k Views Asked by At

I have play around about WqlEventQuery in purpose to identify a device plugged in USB

var query = new WqlEventQuery();
query.EventClassName = "__InstanceOperationEvent";
query.WithinInterval = new TimeSpan(0, 0, 2);
query.Condition = @"TargetInstance ISA 'Win32_USBControllerdevice'";

using (var watcher = new ManagementEventWatcher(query))
{
   watcher.EventArrived += WatcherEvent;
   watcher.Start();

   ... Wait condition ...

   watcher.Stop();
}

then I tried to look for device property in the watcher event handler

    foreach (var mbo in e.NewEvent.Properties.Cast<PropertyData>().Where(i => i.Value != null && i.Value is ManagementBaseObject).Select(pdData => (ManagementBaseObject)pdData.Value).Where(mbo => mbo != null))
    {
       if (mbo.ClassPath.ClassName == "Win32_USBControllerDevice")
       {
           foreach (var prop in mbo.SystemProperties)
           {
               ... look for the property content
           }
       }
    }

but could not found a place where I could extract information about plugged device. So when I am plugging a phone over the USB Port. I want to extract information that states that is a phone of a particular model from the particular producer and so on.

Am I am going the right things in purpose to get this information? should I try something different or more effective in this regards?

Thanks!

3

There are 3 best solutions below

1
On

This below is the query:-We should should use 'Win32_PnPEntity' instead of USB in this Case:-

WqlEventQuery insertQuery = new WqlEventQuery("SELECT * FROM __InstanceCreationEvent  WITHIN 2 WHERE TargetInstance ISA 'Win32_PnPEntity'");

ManagementEventWatcher insertWatcher = new ManagementEventWatcher(insertQuery);
insertWatcher.EventArrived += new EventArrivedEventHandler(DeviceInsertedEvent);
                             
insertWatcher.Start();
           
insertWatcher.WaitForNextEvent();

So this is how the handler looks like:-

private void DeviceInsertedEvent(object sender, EventArrivedEventArgs e)
{
      
    ManagementBaseObject instance = (ManagementBaseObject)e.NewEvent["TargetInstance"];

    foreach (var property in instance.Properties)
    {
        try
        {
            string name = property.Value.ToString();//name of your device
            string deviceId = instance.GetPropertyValue("PNPDeviceID").ToString();
            if (name == "something")
            {
                ....your code.....
            }
        }
        catch
        {
        }
    }
}
0
On

Try looking at Win32_PnPEntity. I believe that the Win32_USBControllerdevice is a "meta level" element.

0
On

I know I am late to this party but maybe my answer is helpfull for someone. I don't recommend to watch on the '__InstanceCreationEvent' especially if you are using a complex query. I experienced really bad performance with such queries. Not my application was slow but it caused the WMI service on the pc to run on 80% of cpu.

I recommend to watch on some simpler events such on 'Win32_DeviceChangeEvent' to detect a USB Device to be changed. If that event is fired you use the 'ManagementObjectSearcher' class to actually check if you desired device is connected.

If you don't have the chance to use a different Event, then try to use the smallest necessary scope and define your query precisely.