使用 WMI 监控驱动器

发布于 2024-09-29 04:52:53 字数 1695 浏览 3 评论 0原文

我正在尝试监控本地电脑的驱动器。我对两个事件感兴趣:驱动器连接(USB 驱动器、CD-ROM、网络驱动器等)和断开连接时。我使用 ManagementOperationObserver 编写了一个快速概念证明,它部分有效。现在(使用下面的代码),我收到了各种事件。我只想获取驱动器连接和断开连接时的事件。有没有办法在 Wql 查询中指定这一点?

谢谢!

    private void button2_Click(object sender, EventArgs e)
    {
        t = new Thread(new ParameterizedThreadStart(o =>
        {
            WqlEventQuery q;
            ManagementOperationObserver observer = new ManagementOperationObserver();

            ManagementScope scope = new ManagementScope("root\\CIMV2");
            scope.Options.EnablePrivileges = true;

            q = new WqlEventQuery();
            q.EventClassName = "__InstanceOperationEvent";
            q.WithinInterval = new TimeSpan(0, 0, 3);
            q.Condition = @"TargetInstance ISA 'Win32_LogicalDisk' ";
            w = new ManagementEventWatcher(scope, q);

            w.EventArrived += new EventArrivedEventHandler(w_EventArrived);
            w.Start();
        }));

        t.Start();
    }

    void w_EventArrived(object sender, EventArrivedEventArgs e)
    {
        //Get the Event object and display its properties (all)
        foreach (PropertyData pd in e.NewEvent.Properties)
        {
            ManagementBaseObject mbo = null;
            if ((mbo = pd.Value as ManagementBaseObject) != null)
            {
                this.listBox1.BeginInvoke(new Action(() => listBox1.Items.Add("--------------Properties------------------")));
                foreach (PropertyData prop in mbo.Properties)
                    this.listBox1.BeginInvoke(new Action<PropertyData>(p => listBox1.Items.Add(p.Name + " - " + p.Value)), prop);
            }
        }
    }

I am trying to monitor drives a local PC. I am interested in two events: when the drive is connected (USB drive, CD-ROM, Network Drive, etc.) and disconnected. I wrote a quick proof of concept using the ManagementOperationObserver and it partially works. Right now (with the code below), I am getting all sort of events. I would like to get only events when a drive is connected and disconnected. Is there a way to specify this in the Wql Query?

Thanks!

    private void button2_Click(object sender, EventArgs e)
    {
        t = new Thread(new ParameterizedThreadStart(o =>
        {
            WqlEventQuery q;
            ManagementOperationObserver observer = new ManagementOperationObserver();

            ManagementScope scope = new ManagementScope("root\\CIMV2");
            scope.Options.EnablePrivileges = true;

            q = new WqlEventQuery();
            q.EventClassName = "__InstanceOperationEvent";
            q.WithinInterval = new TimeSpan(0, 0, 3);
            q.Condition = @"TargetInstance ISA 'Win32_LogicalDisk' ";
            w = new ManagementEventWatcher(scope, q);

            w.EventArrived += new EventArrivedEventHandler(w_EventArrived);
            w.Start();
        }));

        t.Start();
    }

    void w_EventArrived(object sender, EventArrivedEventArgs e)
    {
        //Get the Event object and display its properties (all)
        foreach (PropertyData pd in e.NewEvent.Properties)
        {
            ManagementBaseObject mbo = null;
            if ((mbo = pd.Value as ManagementBaseObject) != null)
            {
                this.listBox1.BeginInvoke(new Action(() => listBox1.Items.Add("--------------Properties------------------")));
                foreach (PropertyData prop in mbo.Properties)
                    this.listBox1.BeginInvoke(new Action<PropertyData>(p => listBox1.Items.Add(p.Name + " - " + p.Value)), prop);
            }
        }
    }

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

匿名。 2024-10-06 04:52:53

你快到了。要区分连接到计算机的驱动器和被删除的驱动器,您需要检查 e.NewEvent 是否是 __InstanceCreationEvent__InstanceDeletionEvent 分别。大致思路如下:

ManagementBaseObject baseObject = (ManagementBaseObject) e.NewEvent;

if (baseObject.ClassPath.ClassName.Equals("__InstanceCreationEvent"))
    Console.WriteLine("A drive was connected");
else if (baseObject.ClassPath.ClassName.Equals("__InstanceDeletionEvent"))
    Console.WriteLine("A drive was removed");

此外,您还可以通过 TargetInstance 属性获取 Win32_LogicalDisk 实例。

ManagementBaseObject logicalDisk = 
               (ManagementBaseObject) e.NewEvent["TargetInstance"];

Console.WriteLine("Drive type is {0}", 
                  logicalDisk.Properties["DriveType"].Value);

You're almost there. To distinguish between a drive being connected to a machine and a drive being removed, you need to check whether e.NewEvent is an instance of __InstanceCreationEvent or __InstanceDeletionEvent respectively. Something along these lines:

ManagementBaseObject baseObject = (ManagementBaseObject) e.NewEvent;

if (baseObject.ClassPath.ClassName.Equals("__InstanceCreationEvent"))
    Console.WriteLine("A drive was connected");
else if (baseObject.ClassPath.ClassName.Equals("__InstanceDeletionEvent"))
    Console.WriteLine("A drive was removed");

Furthermore, you can also get the Win32_LogicalDisk instance via the TargetInstance property.

ManagementBaseObject logicalDisk = 
               (ManagementBaseObject) e.NewEvent["TargetInstance"];

Console.WriteLine("Drive type is {0}", 
                  logicalDisk.Properties["DriveType"].Value);
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文