如何确定哪些 USB 设备已连接到计算机上?

来源:百度文库 编辑:神马文学网 时间:2024/05/01 09:54:05
问:
您好,脚本专家!如何确定哪些 USB 设备已连接到计算机上?
-- WM
答:
您好,WM。您是否经常观看大量电视节目,而不像我们脚本专家一样,在业余时间阅读 Shakespeare 的著作、解答微分方程式或进行其他趋向于开发智力的活动?不过,正如有人曾经告诉过我们的那样,每当电视节目中出现危急关头时,一个主要人物就会抓起一个手提式扩音器大喊,试图让人群平静下来。“保持安静!”此人对人群大喊道。“没有必要惊慌。一切都很正常。”
许多时候,我们脚本专家也希望自己能有一个扩音器,而这里就有一个。您能确定哪些 USB 设备已连接到计算机上吗?是的,尽管看到“如何”时您可能开始有点儿惊慌,但您必须去解决这个问题。保持镇静。没有必要惊慌。
您说的没错:我们应该去演自己的电视剧,不是吗?
我们在此面临的问题是没有专用于 USB 设备的动态类:您不能像使用 Win32_Services 返回计算机上所有服务的集合一样,来返回 USB 设备的集合。您必须使用 WMI 关联类 (Win32_USBControllerDevice),将 USB 控制器与 USB 设备相关联。使用该信息,您可以识别关联中的相关实体(恰好就是与 USB 控制器关联的设备),然后可以查询 Win32_PNPEntity 以获得有关设备自身的信息。(遗憾的是,Win32_USBControllerDevice 除了返回有点儿模糊不清的设备 ID 之外,不会返回有关设备的任何其他信息。)
感到困惑不解吗?别沮丧;我们还不完全确定我们已经理解它。那么,咱们商量一下吧:我们将脚本展示给您,然后您可以自己决定是否需要解释此脚本的工作原理:
strComputer = "."Set objWMIService = GetObject("winmgmts:\\" & strComputer & "\root\cimv2")Set colDevices = objWMIService.ExecQuery _("Select * From Win32_USBControllerDevice")For Each objDevice in colDevicesstrDeviceName = objDevice.DependentstrQuotes = Chr(34)strDeviceName = Replace(strDeviceName, strQuotes, "")arrDeviceNames = Split(strDeviceName, "=")strDeviceName = arrDeviceNames(1)Set colUSBDevices = objWMIService.ExecQuery _("Select * From Win32_PnPEntity Where DeviceID = ‘" & strDeviceName & "‘")For Each objUSBDevice in colUSBDevicesWscript.Echo objUSBDevice.DescriptionNextNext
噢,很好,您仍然与我们的意见一致。正如您看到的,此脚本首先对 Win32_USBControllerDevice 进行了查询;此操作返回了所有 USB 控制器以及当前与它们相关联的设备的集合。这是个好消息。但还有一个坏消息:我们需要隔离集合中各个项的相应实体,即一个表示 USB 设备的实体。为什么这是个坏消息呢?之所以这么说,是因为相应的属性值可能看起来与以下内容类似:
\\TOMSERVO\root\cimv2:Win32_PnPEntity.DeviceID="USB\\VID_045E&PID_0029\\5&236EE205&0&2"
讨厌!我们需要执行的操作就是以某种方式隔离实际的设备 ID;在此例中为“USB\\VID_045E&PID_0029\\5&236EE205&0&2”。当我们获得该值后,就可以查询 Win32_PNPEntity 类以获取有关该设备的信息。
那么我们如何隔离设备 ID 呢?哦,大概有无数种方法可以实现此目的;我们选择一种我们认为比较容易的方法来操作吧。(此方法将给您提供一些关于其他方法是什么样子的提示。)
首先,我们将相应属性的值存储在一个名为 strDeviceName 的变量中。然后,我们使用 VBScript Replace 函数将双引号 – 我们使用 Chr(34) 表示双引号 – 从字符串中删除。这样将得到与以下类似的值:
\\TOMSERVO\root\cimv2:Win32_PnPEntity.DeviceID=USB\\VID_045E&PID_0029\\5&236EE205&0&2
信不信由您,删除这些双引号后就基本上大功告成了。如果仔细地检查其余的值,您将注意到它们基本上分为两个部分,这两个部分被一个等号分隔开了。等号的左边是类和属性的 WMI 路径,等号的右边是设备 ID。这和我们有什么关系呢?现在我们可以使用 VBScript Split 函数来拆分等号上的值,然后创建由两个项组成的数组。第 1 项将是 WMI 路径,第 2 项将是 – 答对了! – 设备 ID。这两行代码创建数组,然后将数组中第 2 项的值(设备 ID)分配给变量 strDeviceName:
arrDeviceNames = Split(strDeviceName, "=")strDeviceName = arrDeviceNames(1)
现在我们就得到了连接到计算机的第一个 USB 设备的设备 ID。有了设备 ID,我们就可以查询 Win32_PNPEntity 类以获得有关分配了设备 ID 的 USB 设备的信息。这就是下面的代码执行的操作:
Set colUSBDevices = objWMIService.ExecQuery _("Select * From Win32_PnPEntity Where DeviceID = ‘" & strDeviceName & "‘")
这个查询将返回有关实际设备自身的信息。在此脚本中,尽管很容易回显所有在 Win32_PNPEntity 类中找到的属性的值,但我们只回显了每个设备的 Description 属性的值。然后,为 Win32_USBControllerDevice 集合中的各个项循环并重复此过程。
运行此脚本时,我们将获得与以下类似的信息(当然,这取决于当前与计算机相连的设备):
USB Root HubMicrosoft USB IntelliMouse WebMicrosoft USB IntelliMouse WebUSB Mass Storage DeviceDisk driveGeneric volumeUSB Root HubUSB Root Hub
此脚本并不完美;USB 大容量存储设备、磁盘驱动器和通用卷均指同一个 USB keychain 驱动器。但至少它可以让您大概了解哪些设备连接到了(或没有连接到)计算机上。
就像我们刚才所说的:没有必要惊慌。一切都很正常。