根据盘符获取硬件编号

心得体会 专栏收录该内容
9 篇文章 0 订阅

  1. unit USBLib;
  2. //----------------------------------------------------------------------------
  3. //                                                                            
  4. //                               根据盘符获取硬件编号                         
  5. //调用方法:                                                                  
  6. //  GetHardwardIDs(X) * X表示盘符                                             
  7. //                                                                            
  8. //返回内容格式(最后一段是序列号):                                            
  9. //  USB/VID_0ED1&PID_6680/5&731544B&0&1                                       
  10. //                                                                            
  11. //参考资料                                                                    
  12. // 1、VC 如何获得U盘的详细信息                                                
  13. //      http://blog.csdn.net/jakeyjia/archive/2006/12/01/1424111.aspx         
  14. // 2、VB 卸载USB设备/解锁文件收藏                                             
  15. //    http://blog.csdn.net/chenhui530/archive/2007/12/13/1932917.aspx         
  16. // 3、MSDN Library for Visual Studio 2005                                     
  17. //                                                                            
  18. //编译环境:                                                                  
  19. //  1、本单元使用了jcl代码库中的Setupapi及CfgMgr32单元                        
  20. //     http://sourceforge.net/projects/jcl/                                   
  21. //     http://jvcl.sourceforge.net/                                           
  22. //  2、Delphi 7.0                                                             
  23. //                                                                            
  24. //特别鸣谢:                                                                  
  25. //  zswang http://blog.csdn.net/zswang/                                       
  26. //  ly_liuyang http://blog.csdn.net/ly_liuyang/                               
  27. //感谢xzhifei(饭桶)前期做出的努力 http://blog.csdn.net/xzhifei/               
  28. //                                                                            
  29. //本单元由coolslob(coolslob@163.com)编写,没有版权,可任意传播                  
  30. //但寄望于使用者对于由此及由此衍生的技术资料能与大家分享!!!  
  31. //同时也向zswang多年来的无私精神致敬,自愧遥不可及:(                            
  32. //                                                                            
  33. //最后修改:                                                                  
  34. //  2008-11-03 00:51:00                                                       
  35. //                                                                            
  36. //----------------------------------------------------------------------------

  37. interface
  38. uses Windows, SysUtils, SetupApi, CfgMgr32;
  39. const
  40.   IOCTL_STORAGE_GET_DEVICE_NUMBER = 2953344;
  41.   
  42. type
  43.   DEVICE_TYPE = DWORD;
  44.   
  45.   STORAGE_DEVICE_NUMBER = record
  46.     DeviceType: DEVICE_TYPE;
  47.     DeviceNumber: ULONG;
  48.     PartitionNumber: ULONG;
  49.   end;
  50.   PSTORAGE_DEVICE_NUMBER = ^STORAGE_DEVICE_NUMBER;
  51. /// <summary>
  52. /// 根据盘符取硬件编号, 包括PID,VID,序列号
  53. /// </summary>
  54. /// <param name="Drive"></param>
  55. /// <returns></returns>
  56. function GetHardwardIDs(const Drive: Char): string;
  57. /// <summary>
  58. /// 根据设备号取设备实例,函数名是GetDeviceInstanceByDeviceNumber的简称
  59. /// </summary>
  60. /// <param name="Num"></param>
  61. /// <returns></returns>
  62. function GetDevInstByNum(Num: Integer): DEVINST;
  63. /// <summary>
  64. /// 根据盘符取设备号
  65. /// </summary>
  66. /// <param name="ADrive"></param>
  67. /// <returns></returns>
  68. function GetDeviceNumberByDrive(const ADrive: Char): Integer;
  69. implementation
  70. /// <summary>
  71. /// 根据设备路径获取设备号
  72. /// </summary>
  73. /// <param name="DevicePath">设备路径</param>
  74. /// <returns>失败返回-1</returns>
  75. function GetDeviceNumberByPath(const DevicePath: string): Integer;
  76. var
  77.   h: THandle;
  78.   sdn: STORAGE_DEVICE_NUMBER;
  79.   dwBytesReturned: DWORD;
  80.   Res: BOOL;
  81. begin
  82.   Result := -1;
  83.   h := CreateFile(PChar(DevicePath),
  84.                        0,
  85.                        FILE_SHARE_READ or FILE_SHARE_WRITE,
  86.                        nil, OPEN_EXISTING, 00);
  87.   if ( h <> INVALID_HANDLE_VALUE ) then
  88.   begin
  89.     dwBytesReturned := 0;
  90.     res := DeviceIoControl(h,
  91.                            IOCTL_STORAGE_GET_DEVICE_NUMBER,
  92.                            nil0, @sdn, sizeof(sdn),
  93.                            dwBytesReturned, nil);
  94.     if (res) then
  95.       Result := sdn.DeviceNumber;
  96.     CloseHandle(h);//关闭句柄
  97.   end;
  98. end;
  99. //
  100. function GetDevInstByNum(Num: Integer): DEVINST;
  101. const
  102.   USBGUID: TGUID = '{53f56307-b6bf-11d0-94f2-00a0c91efb8b}';
  103. var
  104. //  USBGuid: TGUID;
  105.   USBHandle: HDEVINFO;
  106.   Devn: Integer;
  107.   DevData: TSPDevInfoData;
  108.   interfaceData: TSPDeviceInterfaceData;
  109.   detailData: PSPDeviceInterfaceDetailData;
  110.   BytesReturned: DWORD;
  111.   DevicePath: String;
  112. begin
  113.   Result := INVALID_HANDLE_VALUE;
  114.   USBHandle := SetupDiGetClassDevsA(@USBGuid, nil0, DIGCF_PRESENT Or DIGCF_DEVICEINTERFACE);
  115.   if USBHandle = Pointer(INVALID_HANDLE_VALUE) then Exit;
  116.   Devn := 0;
  117.   while True do
  118.   begin
  119.     interfaceData.cbSize := SizeOf(TSPDeviceInterfaceData);
  120.     if not SetupDiEnumDeviceInterfaces(USBHandle, Nil, USBGuid, Devn, interfaceData) then
  121.       Break;
  122.     DevData.cbSize := SizeOf(DevData);
  123.     BytesReturned := 0;
  124.     SetupDiGetDeviceInterfaceDetailA(USBHandle, @interfaceData, Nil, 0, BytesReturned, @DevData);
  125.     if (BytesReturned <> 0) And (GetLastError = ERROR_INSUFFICIENT_BUFFER) then
  126.     begin
  127.       detailData := AllocMem(BytesReturned);
  128.       try
  129.         detailData.cbSize := SizeOf(TSPDeviceInterfaceDetailData);
  130.         if SetupDiGetDeviceInterfaceDetailA(USBHandle, @interfaceData, detailData, BytesReturned, BytesReturned, @DevData) Then
  131.         begin
  132.           DevicePath := StrPas(PChar(@detailData.DevicePath));
  133.           if Num = GetDeviceNumberByPath(DevicePath) then
  134.           begin
  135.             Result := DevData.DevInst;
  136.             Break;
  137.           end;
  138.         end;
  139.         
  140.       finally
  141.         FreeMem(detailData);
  142.       end;//try finally end
  143.     end;
  144.     Inc(Devn);
  145.   end;
  146.   SetupDiDestroyDeviceInfoList(USBHandle);
  147. end;
  148. function GetDeviceNumberByDrive(const ADrive: Char): Integer;
  149. const
  150.   DevicePath = '//?/%s:';
  151. begin
  152.   Result := GetDeviceNumberByPath(Format(DevicePath, [ADrive]));
  153. end;
  154. function GetHardwardIDs(const Drive: Char): string;
  155. var
  156.   Buffer: array[0..MAX_PATH1of Char;
  157.   hDevInst, DevInstParent: DEVINST;
  158.   Num: Integer;
  159. begin
  160.   Result := '';
  161.   
  162.   //根据设备取得设备号
  163.   Num := GetDeviceNumberByDrive(Drive);
  164.   if Num = -1 then Exit;
  165.   hDevInst := GetDevInstByNum(Num);
  166.   if hDevInst = INVALID_HANDLE_VALUE then Exit;
  167.   
  168.   FillChar(Buffer, MAX_PATH0);
  169.   CM_Get_Parent(DevInstParent, hDevInst, 0);
  170.   CM_Get_Device_ID(DevInstParent, Buffer, MAX_PATH, 0);
  171.   
  172.   Result := StrPas(Buffer);
  173. end;
  174. initialization
  175.   LoadSetupApi;
  176.   CfgMgr32.LoadConfigManagerApi;
  177. finalization
  178.   Setupapi.UnloadSetupApi;
  179.   CfgMgr32.UnloadConfigManagerApi;
  180. end.
  • 0
    点赞
  • 6
    评论
  • 0
    收藏
  • 一键三连
    一键三连
  • 扫一扫,分享海报

©️2021 CSDN 皮肤主题: 大白 设计师:CSDN官方博客 返回首页
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值