LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Windows device driver function SetupDiGetClassDevsW

https://docs.microsoft.com/en-us/windows/win32/api/setupapi/nf-setupapi-setupdigetclassdevsw

 

WINSETUPAPI HDEVINFO SetupDiGetClassDevsW (

const GUID *ClassGuid,

PCWSTR Enumerator,

HWND hwndParent,

DWORD Flags

);

 

Any suggestion/pointer on how to define GUID *ClassGuid in LabVIEW?

0 Kudos
Message 1 of 8
(3,433 Views)

Well the C definition is

typedef struct _GUID {
  unsigned long  Data1;
  unsigned short Data2;
  unsigned short Data3;
  unsigned char  Data4[8];
} GUID;

So you could create a cluster with an uint32, uint16, uint16 and 8 * uint8 and pass that to the Call Library Node parameter configured as Adapt to Type.

 

But in essence it is simply 16 bytes of data, so you could also configure the parameter as Array of Bytes and pass in a 16 element array. It would make filling in the data a little more complex since we work here on an Intel Little Endian CPU and the GUID {3F2504E0-4F89-11D3-9A 0C 03 05 E8 2C 33 01} would need to be filled in as E0, 04, 25, 3F, 89, 4F, D3, 11, 0C, 9A, 03, 05, E8, 2C, 33, 01

Rolf Kalbermatter  My Blog
DEMO, Electronic and Mechanical Support department, room 36.LB00.390
0 Kudos
Message 2 of 8
(3,431 Views)

Can someone suggest why the handle returned seems like garbage data?

 

Thanks in advance!

0 Kudos
Message 3 of 8
(3,371 Views)

What do you consider garbage data? A handle is simply an identifier that could be a pointer, a magic index or whatever the software programmer is using to reference the data that is associated with it. The only special value for a this functions is INVALID_HANDLE_VALUE (-1 or 0xFFFFFFFF).. If this function returns that value then it failed, otherwise it was successful.

 

Unless it returns this special value, it was successful and its value is ok. You can't interpret its value but need to pass it to other SetupDi.... functions to do anything with it.

Rolf Kalbermatter  My Blog
DEMO, Electronic and Mechanical Support department, room 36.LB00.390
0 Kudos
Message 4 of 8
(3,366 Views)

The reason I was thinking it might be garbage or incorrect handle is that when I pass that handle to SetupDiEnumDeviceInterfaces it always returns 0 (basically unsuccessful) and the GetLastError is not giving much information either (error code 0 which is The operation completed successfully).

 

Thanks in advance for any debugging suggestions.

 

 

0 Kudos
Message 5 of 8
(3,344 Views)

Well, the fact that it does not return 0xFFFFFFFF means basically that it did not fail as you can read in MSDN. That SetupDiEnumDeviceInterfaces() returns 0 could be also caused by invalid parameters such as an invalid GUID.

 

Unfortunately there is a big problem with using GetLastError() within LabVIEW. Windows maintains a last error value per thread, but if you set the Call Library Node to run in any thread it is pure change that the SetupDiEnumDeviceInterfaces() and the GetLastError() execute in the same thread and even if they do LabVIEW might have used the same thread for other calls in between too that overwrite the last error value, and if they execute in different threads GetLastError() will return a different last error value.

 

And if you set the Call Library Node to execute in the UI thread you are almost certain that LabVIEW will schedule other UI thread Windows calls in between since the UI thread is used for the entire GUI updating too and anything that needs to to be executed in a single thread, and many of the Windows GDI functions that LabVIEW uses to draw the UI, also modify the last error value, so that you may read an entirely different last error value again than the one you would like.

 

There are only two solutions to this problem:

 

1) write an external DLL that calls both APIs directly after each other and call that function with the Call Library Node

 

2) Create a VI with subroutine priority that calls both the Windows API call and the GetLastError() call (and for that the Call Library Nodes need to be set to NOT execute in the UI thread). LabVIEW does not do thread switching in subroutine configured subVIs so you should be guaranteed that the two calls happen in the same thread and directly after each other. But you can't debug subroutine configured VIs anymore as single stepping and highlighting is disabled.

Rolf Kalbermatter  My Blog
DEMO, Electronic and Mechanical Support department, room 36.LB00.390
Message 6 of 8
(3,337 Views)

How do you configure and wire the Call Library Node for calling the Windows API call SetupDiEnumDeviceInterfaces(). Specifially, how do you handle the function parameter "PSP_DEVICE_INTERFACE_DATA DeviceInterfaceData", which is a pointer to a structure.



Mark Yedinak
Certified LabVIEW Architect
LabVIEW Champion

"Does anyone know where the love of God goes when the waves turn the minutes to hours?"
Wreck of the Edmund Fitzgerald - Gordon Lightfoot
0 Kudos
Message 7 of 8
(3,317 Views)

What Mark means among a few other things is this Remark in the MSDN documentation:

 

A SetupAPI function that takes an instance of the SP_DEVICE_INTERFACE_DATA structure as a parameter verifies whether the cbSize member of the supplied structure is equal to the size, in bytes, of the structure. If the cbSize member is not set correctly, the function will fail and set an error code of ERROR_INVALID_USER_BUFFER.

Rolf Kalbermatter  My Blog
DEMO, Electronic and Mechanical Support department, room 36.LB00.390
0 Kudos
Message 8 of 8
(3,302 Views)