usb_device_si.cpp 4.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178
  1. /*
  2. * Dynastream Innovations Inc.
  3. * Cochrane, AB, CANADA
  4. *
  5. * Copyright © 1998-2008 Dynastream Innovations Inc.
  6. * All rights reserved. This software may not be reproduced by
  7. * any means without express written approval of Dynastream
  8. * Innovations Inc.
  9. */
  10. #include "types.h"
  11. #if defined(DSI_TYPES_WINDOWS)
  12. #if defined(_MSC_VER)
  13. #include "WinDevice.h"
  14. #endif
  15. #include "usb_device_si.hpp"
  16. #include "macros.h"
  17. #include <windows.h>
  18. #include <memory>
  19. using namespace std;
  20. USBDeviceSI::USBDeviceSI(UCHAR ucDeviceNumber_)
  21. :
  22. ucDeviceNumber(ucDeviceNumber_),
  23. usVid(0),
  24. usPid(0),
  25. ulSerialNumber(0)
  26. {
  27. //initialize array
  28. szProductDescription[0] = '\0';
  29. szSerialString[0] = '\0';
  30. auto_ptr<const SiLabsLibrary> pclAutoSiLibrary(NULL);
  31. if(SiLabsLibrary::Load(pclAutoSiLibrary) == FALSE)
  32. return;
  33. const SiLabsLibrary& clSiLibrary = *pclAutoSiLibrary;
  34. char acTempString[SI_MAX_DEVICE_STRLEN];
  35. //Get device VID
  36. if(clSiLibrary.GetProductString(ucDeviceNumber_, acTempString, SI_RETURN_VID) == SI_SUCCESS)
  37. {
  38. usVid = (USHORT)strtoul(acTempString, NULL, 16);
  39. }
  40. else
  41. usVid = 0;
  42. //Get device PID
  43. if(clSiLibrary.GetProductString(ucDeviceNumber_, acTempString, SI_RETURN_PID) == SI_SUCCESS)
  44. {
  45. usPid = (USHORT)strtoul(acTempString, NULL, 16);
  46. }
  47. else
  48. usPid = 0;
  49. if(clSiLibrary.GetProductString(ucDeviceNumber_, szSerialString, SI_RETURN_SERIAL_NUMBER) == SI_SUCCESS)
  50. {
  51. USBDeviceSI::GetDeviceSerialNumber(ulSerialNumber);
  52. }
  53. else
  54. {
  55. szSerialString[0] = '\0';
  56. ulSerialNumber = 0;
  57. }
  58. if(clSiLibrary.GetProductString(ucDeviceNumber_, szProductDescription, SI_RETURN_DESCRIPTION) == SI_SUCCESS) //!!null terminated?
  59. {
  60. }
  61. else
  62. {
  63. szProductDescription[0] = '\0';
  64. }
  65. /*
  66. if(clSiLibrary.GetProductString(ucDeviceNumber_, acTempString, SI_RETURN_LINK_NAME) != SI_SUCCESS)
  67. {
  68. szLinkName[0] = '\0';
  69. }
  70. */
  71. /* //!!What do these give us?
  72. CP210x_RETURN_SERIAL_NUMBER 0x00
  73. CP210x_RETURN_DESCRIPTION 0x01
  74. CP210x_RETURN_FULL_PATH 0x02
  75. */
  76. return;
  77. }
  78. USBDeviceSI::USBDeviceSI(const USBDeviceSI& clDevice_)
  79. :
  80. ucDeviceNumber(clDevice_.ucDeviceNumber),
  81. usVid(clDevice_.usVid),
  82. usPid(clDevice_.usPid),
  83. ulSerialNumber(clDevice_.ulSerialNumber)
  84. {
  85. STRNCPY((char*)szProductDescription, (char*)clDevice_.szProductDescription, sizeof(szProductDescription));
  86. memcpy(szSerialString, clDevice_.szSerialString, sizeof(szSerialString));
  87. return;
  88. }
  89. USBDeviceSI& USBDeviceSI::operator=(const USBDeviceSI& clDevice_)
  90. {
  91. if(this == &clDevice_)
  92. return *this;
  93. ucDeviceNumber = clDevice_.ucDeviceNumber;
  94. usVid = clDevice_.usVid;
  95. usPid = clDevice_.usPid;
  96. ulSerialNumber = clDevice_.ulSerialNumber;
  97. STRNCPY((char*)szProductDescription, (char*)clDevice_.szProductDescription, sizeof(szProductDescription));
  98. memcpy(szSerialString, clDevice_.szSerialString, sizeof(szSerialString));
  99. return *this;
  100. }
  101. BOOL USBDeviceSI::GetProductDescription(UCHAR* pucProductDescription_, USHORT usBufferSize_) const
  102. {
  103. return(STRNCPY((char*) pucProductDescription_, (char*) szProductDescription, usBufferSize_));
  104. }
  105. BOOL USBDeviceSI::GetSerialString(UCHAR* pucSerialString_, USHORT usBufferSize_) const
  106. {
  107. if(sizeof(szSerialString) > usBufferSize_)
  108. {
  109. memcpy(pucSerialString_, szSerialString, usBufferSize_);
  110. return FALSE;
  111. }
  112. memcpy(pucSerialString_, szSerialString, sizeof(szSerialString));
  113. return TRUE;
  114. }
  115. BOOL USBDeviceSI::USBReset() const //!!make static?
  116. {
  117. #if defined(_MSC_VER)
  118. // !! Borland builder chokes on cfgmgr32
  119. TCHAR line1[64];
  120. TCHAR* argv_[2];
  121. //Only do the soft reset if we fail to open a device or it seems like theres no devices to open (device in a "hosed" state)
  122. //The soft reset will have no effect on devices currently opened by other applications.
  123. argv_[0] = line1;
  124. SNPRINTF(&(line1[0]),sizeof(line1), "@USB\\VID_%04X&PID_%04X\\*", usVid, usPid);
  125. WinDevice_Disable(1,argv_);
  126. WinDevice_Enable(1,argv_);
  127. #endif
  128. return TRUE;
  129. }
  130. //The serial number actually is not limited to a ULONG by USB specs,
  131. //so, our range here is determined by whatever we do in our products.
  132. //For now we have it defined as 1 to (ULONG_MAX-1)
  133. BOOL USBDeviceSI::GetDeviceSerialNumber(ULONG& ulSerialNumber_)
  134. {
  135. ULONG ulSerial = strtoul((char*)szSerialString, NULL, 10);
  136. if(ulSerial == 0 || ulSerial == ULONG_MAX)
  137. return FALSE;
  138. if((ulSerial > 10000) && (ulSerial < 10255)) //The real serial number is kept in the string
  139. memcpy(&ulSerial, &(szSerialString[56]), 4);
  140. ulSerialNumber_ = ulSerial;
  141. return TRUE;
  142. }
  143. #endif //defined(DSI_TYPES_WINDOWS)