Script 'mail_helper' called by obssrc Hello community, here is the log from the commit of package qt6-serialport for openSUSE:Factory checked in at 2024-12-05 17:05:41 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/qt6-serialport (Old) and /work/SRC/openSUSE:Factory/.qt6-serialport.new.28523 (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "qt6-serialport" Thu Dec 5 17:05:41 2024 rev:26 rq:1228208 version:6.8.1 Changes: -------- --- /work/SRC/openSUSE:Factory/qt6-serialport/qt6-serialport.changes 2024-10-17 18:38:04.203080800 +0200 +++ /work/SRC/openSUSE:Factory/.qt6-serialport.new.28523/qt6-serialport.changes 2024-12-05 17:06:44.644827626 +0100 @@ -1,0 +2,6 @@ +Mon Dec 2 13:02:12 UTC 2024 - Christophe Marin <christo...@krop.fr> + +- Update to 6.8.1: + * https://www.qt.io/blog/qt-6.8.1-released + +------------------------------------------------------------------- Old: ---- qtserialport-everywhere-src-6.8.0.tar.xz New: ---- qtserialport-everywhere-src-6.8.1.tar.xz ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ qt6-serialport.spec ++++++ --- /var/tmp/diff_new_pack.VL5Rs2/_old 2024-12-05 17:06:46.016885084 +0100 +++ /var/tmp/diff_new_pack.VL5Rs2/_new 2024-12-05 17:06:46.028885586 +0100 @@ -16,7 +16,7 @@ # -%define real_version 6.8.0 +%define real_version 6.8.1 %define short_version 6.8 %define tar_name qtserialport-everywhere-src %define tar_suffix %{nil} @@ -27,7 +27,7 @@ %endif # Name: qt6-serialport%{?pkg_suffix} -Version: 6.8.0 +Version: 6.8.1 Release: 0 Summary: Qt 6 SerialPort library License: LGPL-3.0-only OR (GPL-2.0-only OR GPL-3.0-or-later) @@ -85,7 +85,8 @@ %autosetup -p1 -n %{tar_name}-%{real_version}%{tar_suffix} %build -%cmake_qt6 +%cmake_qt6 \ + -DQT_GENERATE_SBOM:BOOL=FALSE %{qt6_build} ++++++ qtserialport-everywhere-src-6.8.0.tar.xz -> qtserialport-everywhere-src-6.8.1.tar.xz ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/qtserialport-everywhere-src-6.8.0/.cmake.conf new/qtserialport-everywhere-src-6.8.1/.cmake.conf --- old/qtserialport-everywhere-src-6.8.0/.cmake.conf 2024-10-02 10:28:59.000000000 +0200 +++ new/qtserialport-everywhere-src-6.8.1/.cmake.conf 2024-11-19 12:13:56.000000000 +0100 @@ -1,4 +1,4 @@ -set(QT_REPO_MODULE_VERSION "6.8.0") +set(QT_REPO_MODULE_VERSION "6.8.1") set(QT_REPO_MODULE_PRERELEASE_VERSION_SEGMENT "alpha1") set(QT_EXTRA_INTERNAL_TARGET_DEFINES "QT_NO_AS_CONST=1") list(APPEND QT_EXTRA_INTERNAL_TARGET_DEFINES "QT_NO_FOREACH=1") diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/qtserialport-everywhere-src-6.8.0/.tag new/qtserialport-everywhere-src-6.8.1/.tag --- old/qtserialport-everywhere-src-6.8.0/.tag 2024-10-02 10:28:59.000000000 +0200 +++ new/qtserialport-everywhere-src-6.8.1/.tag 2024-11-19 12:13:56.000000000 +0100 @@ -1 +1 @@ -fc0a965d5bada8296595fcefacebc235dccf1a75 +88467a588d7c312d0c24adc6edd2a96e199cf760 diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/qtserialport-everywhere-src-6.8.0/LICENSES/Qt-GPL-exception-1.0.txt new/qtserialport-everywhere-src-6.8.1/LICENSES/Qt-GPL-exception-1.0.txt --- old/qtserialport-everywhere-src-6.8.0/LICENSES/Qt-GPL-exception-1.0.txt 2024-10-02 10:28:59.000000000 +0200 +++ new/qtserialport-everywhere-src-6.8.1/LICENSES/Qt-GPL-exception-1.0.txt 1970-01-01 01:00:00.000000000 +0100 @@ -1,22 +0,0 @@ -The Qt Company GPL Exception 1.0 - -Exception 1: - -As a special exception you may create a larger work which contains the -output of this application and distribute that work under terms of your -choice, so long as the work is not otherwise derived from or based on -this application and so long as the work does not in itself generate -output that contains the output from this application in its original -or modified form. - -Exception 2: - -As a special exception, you have permission to combine this application -with Plugins licensed under the terms of your choice, to produce an -executable, and to copy and distribute the resulting executable under -the terms of your choice. However, the executable must be accompanied -by a prominent notice offering all users of the executable the entire -source code to this application, excluding the source code of the -independent modules, but including any changes you have made to this -application, under the terms of this license. - diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/qtserialport-everywhere-src-6.8.0/REUSE.toml new/qtserialport-everywhere-src-6.8.1/REUSE.toml --- old/qtserialport-everywhere-src-6.8.0/REUSE.toml 1970-01-01 01:00:00.000000000 +0100 +++ new/qtserialport-everywhere-src-6.8.1/REUSE.toml 2024-11-19 12:13:56.000000000 +0100 @@ -0,0 +1,58 @@ +version = 1 + +[[annotations]] +path = ["tests/**.txt"] +precedence = "closest" +SPDX-FileCopyrightText = "Copyright (C) 2024 The Qt Company Ltd." +SPDX-License-Identifier = "LicenseRef-Qt-Commercial OR GPL-3.0-only" + +[[annotations]] +path = ["**.pro", "**.qrc", "**CMakeLists.txt", ".cmake.conf", "**.yaml", + "**.json", "**.cfg", "**.cmake"] +precedence = "closest" +comment = "build system" +SPDX-FileCopyrightText = "Copyright (C) 2024 The Qt Company Ltd." +SPDX-License-Identifier = "BSD-3-Clause" + +[[annotations]] +path = [".tag", "**/.gitattributes", "**.gitignore"] +precedence = "closest" +comment = "build system" +SPDX-FileCopyrightText = "Copyright (C) 2024 The Qt Company Ltd." +SPDX-License-Identifier = "BSD-3-Clause" + +[[annotations]] +path = ["**/doc/images/**", "examples/**"] +comment = "this must be after the build system table because example and snippets take precedence over build system" +precedence = "closest" +SPDX-FileCopyrightText = "Copyright (C) 2024 The Qt Company Ltd." +SPDX-License-Identifier = "LicenseRef-Qt-Commercial OR BSD-3-Clause" + +[[annotations]] +path = ["**/README*", "**.qdocconf", "src/serialport/doc/style/style.css"] +comment = "documentation" +precedence = "closest" +SPDX-FileCopyrightText = "Copyright (C) 2024 The Qt Company Ltd." +SPDX-License-Identifier = "LicenseRef-Qt-Commercial OR GFDL-1.3-no-invariants-only" + +[[annotations]] +path = ["**.toml", "licenseRule.json"] +precedence = "override" +comment = "documentation" +SPDX-FileCopyrightText = "Copyright (C) 2024 The Qt Company Ltd." +SPDX-License-Identifier = "LicenseRef-Qt-Commercial OR GFDL-1.3-no-invariants-only" + +[[annotations]] +path = ["**/qt_attribution.json"] +precedence = "override" +comment = "not necessary but ready if such a file is added. documentation" +SPDX-FileCopyrightText = "Copyright (C) 2024 The Qt Company Ltd." +SPDX-License-Identifier = "LicenseRef-Qt-Commercial OR GFDL-1.3-no-invariants-only" + +[[annotations]] +path = ["**LICENSE*"] +precedence = "override" +comment = "License file." +SPDX-FileCopyrightText = "None" +SPDX-License-Identifier = "CC0-1.0" + diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/qtserialport-everywhere-src-6.8.0/dependencies.yaml new/qtserialport-everywhere-src-6.8.1/dependencies.yaml --- old/qtserialport-everywhere-src-6.8.0/dependencies.yaml 2024-10-02 10:28:59.000000000 +0200 +++ new/qtserialport-everywhere-src-6.8.1/dependencies.yaml 2024-11-19 12:13:56.000000000 +0100 @@ -1,4 +1,4 @@ dependencies: ../qtbase: - ref: b839e9b36db3a4e50dfb34521d8ef8de1fd01969 + ref: 0db4321f2f13c6870283f3fcc0f1a462fd7cf663 required: true diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/qtserialport-everywhere-src-6.8.0/dist/REUSE.toml new/qtserialport-everywhere-src-6.8.1/dist/REUSE.toml --- old/qtserialport-everywhere-src-6.8.0/dist/REUSE.toml 1970-01-01 01:00:00.000000000 +0100 +++ new/qtserialport-everywhere-src-6.8.1/dist/REUSE.toml 2024-11-19 12:13:56.000000000 +0100 @@ -0,0 +1,8 @@ +version = 1 + +[[annotations]] +path = ["*"] +precedence = "override" +comment = "Licensed as documentation." +SPDX-FileCopyrightText = "Copyright (C) 2024 The Qt Company Ltd." +SPDX-License-Identifier = "LicenseRef-Qt-Commercial OR GFDL-1.3-no-invariants-only" diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/qtserialport-everywhere-src-6.8.0/src/serialport/qserialportinfo_osx.cpp new/qtserialport-everywhere-src-6.8.1/src/serialport/qserialportinfo_osx.cpp --- old/qtserialport-everywhere-src-6.8.0/src/serialport/qserialportinfo_osx.cpp 2024-10-02 10:28:59.000000000 +0200 +++ new/qtserialport-everywhere-src-6.8.1/src/serialport/qserialportinfo_osx.cpp 2024-11-19 12:13:56.000000000 +0100 @@ -123,7 +123,7 @@ CFSTR(kIOSerialBSDAllTypes)); io_iterator_t serialPortIterator = 0; - if (::IOServiceGetMatchingServices(kIOMasterPortDefault, serialPortDictionary, + if (::IOServiceGetMatchingServices(kIOMainPortDefault, serialPortDictionary, &serialPortIterator) != KERN_SUCCESS) { return QList<QSerialPortInfo>(); } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/qtserialport-everywhere-src-6.8.0/src/serialport/qserialportinfo_win.cpp new/qtserialport-everywhere-src-6.8.1/src/serialport/qserialportinfo_win.cpp --- old/qtserialport-everywhere-src-6.8.0/src/serialport/qserialportinfo_win.cpp 2024-10-02 10:28:59.000000000 +0200 +++ new/qtserialport-everywhere-src-6.8.1/src/serialport/qserialportinfo_win.cpp 2024-11-19 12:13:56.000000000 +0100 @@ -10,6 +10,8 @@ #include <QtCore/quuid.h> #include <QtCore/qpair.h> #include <QtCore/qstringlist.h> +#include <QtCore/private/qwinregistry_p.h> +#include <QtCore/private/quniquehandle_types_p.h> #include <vector> @@ -18,6 +20,9 @@ #include <winioctl.h> // for GUID_DEVINTERFACE_COMPORT #include <setupapi.h> #include <cfgmgr32.h> +#include <usbioctl.h> +#include <usbiodef.h> +#include <ioapiset.h> #ifdef QT_NO_REDEFINE_GUID_DEVINTERFACE_MODEM # include <ntddmodm.h> // for GUID_DEVINTERFACE_MODEM @@ -27,11 +32,32 @@ QT_BEGIN_NAMESPACE +namespace { + +struct DevInfoHandleTraits +{ + using Type = HDEVINFO; + static Type invalidValue() noexcept + { + return INVALID_HANDLE_VALUE; + } + static bool close(Type handle) noexcept + { + return SetupDiDestroyDeviceInfoList(handle) == TRUE; + } +}; + +using DevInfoHandle = QUniqueHandle<DevInfoHandleTraits>; + +} // namespace + static QStringList portNamesFromHardwareDeviceMap() { - HKEY hKey = nullptr; - if (::RegOpenKeyEx(HKEY_LOCAL_MACHINE, L"HARDWARE\\DEVICEMAP\\SERIALCOMM", 0, KEY_QUERY_VALUE, &hKey) != ERROR_SUCCESS) - return QStringList(); + const QWinRegistryKey key{ HKEY_LOCAL_MACHINE, L"HARDWARE\\DEVICEMAP\\SERIALCOMM", 0, + KEY_QUERY_VALUE }; + + if (!key.isValid()) + return { }; QStringList result; DWORD index = 0; @@ -45,7 +71,7 @@ DWORD bytesRequired = MAX_PATH; for (;;) { DWORD requiredValueNameChars = MaximumValueNameInChars; - const LONG ret = ::RegEnumValue(hKey, index, &outputValueName[0], &requiredValueNameChars, + const LONG ret = ::RegEnumValue(key, index, &outputValueName[0], &requiredValueNameChars, nullptr, nullptr, reinterpret_cast<PBYTE>(&outputBuffer[0]), &bytesRequired); if (ret == ERROR_MORE_DATA) { outputBuffer.resize(bytesRequired / sizeof(wchar_t) + 2, 0); @@ -56,7 +82,6 @@ break; } } - ::RegCloseKey(hKey); return result; } @@ -83,6 +108,233 @@ return QString::fromWCharArray(&outputBuffer[0]); } +static QString getStringDescriptor(HANDLE hHubDevice, ULONG connectionIndex, + UCHAR descriptorIndex, USHORT languageID) +{ + + constexpr DWORD bufferSize = sizeof(USB_DESCRIPTOR_REQUEST) + MAXIMUM_USB_STRING_LENGTH; + std::array<UCHAR, bufferSize> buffer{}; + auto request = reinterpret_cast<PUSB_DESCRIPTOR_REQUEST>(buffer.data()); + + request->ConnectionIndex = connectionIndex; + request->SetupPacket.wValue = (USB_STRING_DESCRIPTOR_TYPE << 8) | descriptorIndex; + request->SetupPacket.wIndex = languageID; + request->SetupPacket.wLength = MAXIMUM_USB_STRING_LENGTH; + + ULONG bytesReturned = 0; + BOOL success = DeviceIoControl(hHubDevice, IOCTL_USB_GET_DESCRIPTOR_FROM_NODE_CONNECTION, + request, bufferSize, request, bufferSize, &bytesReturned, + nullptr); + + if (!success) + return {}; + + constexpr ULONG minExpectedSize = sizeof(USB_DESCRIPTOR_REQUEST) + + sizeof(USB_STRING_DESCRIPTOR); + + if (bytesReturned < minExpectedSize) + return {}; + + const auto stringDesc = reinterpret_cast<PUSB_STRING_DESCRIPTOR>(request->Data); + + if (stringDesc->bDescriptorType != USB_STRING_DESCRIPTOR_TYPE) + return {}; + + if (stringDesc->bLength != bytesReturned - sizeof(USB_DESCRIPTOR_REQUEST)) + return {}; + + if (stringDesc->bLength % 2 != 0) + return {}; + + // Offset per USB 2.0 standard, section 9.6.7 table 9-16. + // bLength appears to include the size of the first 2 bytes of the descriptor + constexpr int stringOffset = 2; + const int numWideChars = (stringDesc->bLength - stringOffset) / sizeof(wchar_t); + return QString::fromWCharArray(stringDesc->bString, numWideChars); +} + +static std::vector<wchar_t> getDevicePath(DEVINST devInst) +{ + unsigned long devIdSize; + + if (::CM_Get_Device_ID_Size(&devIdSize, devInst, 0) != CR_SUCCESS) { + return {}; + } + + std::vector<wchar_t> buffer(devIdSize + 1); + + if (::CM_Get_Device_ID(devInst, buffer.data(), devIdSize, 0) != CR_SUCCESS) { + return {}; + } + + return buffer; +} + +// Returns true if a hub is found, false if we gave up and didn't find one +// Passes devLocation by ref - port number on the hub of the device we need info for. +// Passes buffer by ref - path to the device we need to query to get information +static bool getUSBLocationAndPath(DWORD devInst, int &devLocation, std::vector<wchar_t> &buffer) +{ + bool hubFound = false; + int count = 0; + QString devLocationStr; + std::vector<wchar_t> devicePath = {}; + + + // In order to find the actual information we want to find in subsequent function calls, + // We have to get the port number on the hub of the device we want from that device, + // and we have to get the path to the hub device. Both are required to get + // any of the usb data we want. So we loop through starting with the passed-in + // device instance, and we return (via out arguments) the port of the device connected + // to the hub, and the path to the hub itself. + + while (!hubFound && (count < 3)) { + DEVINST parentDevInst; + if (count == 0) { + parentDevInst = devInst; + } else { + if (::CM_Get_Parent(&parentDevInst, devInst, 0) != CR_SUCCESS) { + return false; + } + } + + devicePath = getDevicePath(parentDevInst); + + if (devicePath.empty()) + return false; + + // Get info for this device. If it's a composite device we'll have to go up another level. + + const DevInfoHandle currDeviceInformation{ ::SetupDiGetClassDevsW( + nullptr, devicePath.data(), nullptr, + DIGCF_ALLCLASSES | DIGCF_PRESENT | DIGCF_DEVICEINTERFACE) }; + + if (!currDeviceInformation) + return false; + + SP_DEVINFO_DATA currDeviceInfoData = {}; + currDeviceInfoData.cbSize = sizeof(currDeviceInfoData); + + // There should only be one since we're getting info for the parent device + if (!::SetupDiEnumDeviceInfo(currDeviceInformation.get(), 0, &currDeviceInfoData)) { + return false; + } + + // Find out if this device is a hub device, if so, we're done + const QString devDescription = deviceRegistryProperty(currDeviceInformation.get(), + &currDeviceInfoData, + SPDRP_DEVICEDESC); + + if (devDescription.contains(L"Hub")) { + hubFound = true; + } else { + devInst = parentDevInst; + devLocationStr = deviceRegistryProperty(currDeviceInformation.get(), + &currDeviceInfoData, + SPDRP_LOCATION_INFORMATION); + count++; + } + } + + if (count == 3) + // didn't find what we were looking for. Give up. + return false; + + if (!hubFound) + return false; + + const QString portString(L"Port_#"); + + if (devLocationStr.contains(portString)) { + devLocationStr.remove(portString); + devLocation = devLocationStr.left(devLocationStr.indexOf(u'.')).toInt(); + } else { + return false; + } + + // Build the path based on information found here: + // https://stackoverflow.com/questions/ + // 8007468/how-do-i-obtain-usb-device-descriptor-given-a-device-path/32641140#32641140 + QString devPath = QString::fromStdWString(devicePath.data()); + QString hubUuidStr = u'#' + QUuid(GUID_DEVINTERFACE_USB_HUB).toString(); + + devPath.replace(u'\\', u'#'); + devPath.prepend(L"\\\\?\\"); + devPath.append(hubUuidStr); // GUID for hub devices + buffer.resize(devPath.size()+1, 0); + devPath.toWCharArray(buffer.data()); + + return true; +} + +struct UsbData +{ + QString iManufacturer; + QString iProduct; +}; + +static UsbData getUSBDataFromDevice(DWORD devInst) +{ + std::vector<wchar_t> buffer; + int devLocation; + + if (!getUSBLocationAndPath(devInst, devLocation, buffer)) + return {}; + + // Open the Hub device. To get the information we want, we have to open the Hub device, + // and pass in the port number in the argument structure. + + const QUniqueWin32Handle fileHandle{ ::CreateFile(buffer.data(), GENERIC_READ, FILE_SHARE_READ, + nullptr, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, + nullptr) }; + + if (!fileHandle) + return {}; + + // Some of the following code was from Microsoft's sample usbview code + constexpr ULONG size = sizeof(USB_NODE_CONNECTION_INFORMATION); + std::array<UCHAR, size> connectionInfoData; + + // Set the port number of the device on the hub for the DeviceIoControl call. + auto connectionInfo = + reinterpret_cast<PUSB_NODE_CONNECTION_INFORMATION>(connectionInfoData.data()); + connectionInfo->ConnectionIndex = devLocation; + + ULONG dataSize = 0; + if (!::DeviceIoControl(fileHandle.get(), IOCTL_USB_GET_NODE_CONNECTION_INFORMATION, + connectionInfo, size, connectionInfo, size, &dataSize, nullptr)) { + return {}; + } + + // Get the language information, but we're only going to use the first one since we're going to + // use this information for the manufacturer returned to Qt's caller, and there's only 1 allowed + // there + + QString usbStringData = getStringDescriptor(fileHandle.get(), + connectionInfo->ConnectionIndex, + 0, 0); + + if (usbStringData.isEmpty()) + return {}; + + USHORT languageIDs = usbStringData[0].unicode(); + UsbData usbData; + + if (connectionInfo->DeviceDescriptor.iManufacturer != 0) + usbData.iManufacturer = getStringDescriptor(fileHandle.get(), + connectionInfo->ConnectionIndex, + connectionInfo->DeviceDescriptor.iManufacturer, + languageIDs); + + if (connectionInfo->DeviceDescriptor.iProduct != 0) + usbData.iProduct = getStringDescriptor(fileHandle.get(), + connectionInfo->ConnectionIndex, + connectionInfo->DeviceDescriptor.iProduct, + languageIDs); + + return usbData; +} + static QString deviceInstanceIdentifier(DEVINST deviceInstanceNumber) { std::vector<wchar_t> outputBuffer(MAX_DEVICE_ID_LEN + 1, 0); @@ -122,15 +374,13 @@ L"PortNumber\0" }; - enum { KeyTokensCount = sizeof(keyTokens) / sizeof(keyTokens[0]) }; - QString portName; - for (int i = 0; i < KeyTokensCount; ++i) { + for (auto keyToken : keyTokens) { DWORD dataType = 0; std::vector<wchar_t> outputBuffer(MAX_PATH + 1, 0); DWORD bytesRequired = MAX_PATH; for (;;) { - const LONG ret = ::RegQueryValueEx(key, keyTokens[i], nullptr, &dataType, + const LONG ret = ::RegQueryValueEx(key, keyToken, nullptr, &dataType, reinterpret_cast<PBYTE>(&outputBuffer[0]), &bytesRequired); if (ret == ERROR_MORE_DATA) { outputBuffer.resize(bytesRequired / sizeof(wchar_t) + 2, 0); @@ -255,22 +505,20 @@ { GUID_DEVINTERFACE_MODEM, DIGCF_PRESENT | DIGCF_DEVICEINTERFACE } }; - enum { SetupTokensCount = sizeof(setupTokens) / sizeof(setupTokens[0]) }; - QList<QSerialPortInfo> serialPortInfoList; - for (int i = 0; i < SetupTokensCount; ++i) { - const HDEVINFO deviceInfoSet = ::SetupDiGetClassDevs(&setupTokens[i].guid, nullptr, nullptr, setupTokens[i].flags); - if (deviceInfoSet == INVALID_HANDLE_VALUE) + for (const auto& setupToken : setupTokens) { + const DevInfoHandle deviceInfoSet{ ::SetupDiGetClassDevs(&setupToken.guid, nullptr, + nullptr, setupToken.flags) }; + if (!deviceInfoSet) return serialPortInfoList; - SP_DEVINFO_DATA deviceInfoData; - ::memset(&deviceInfoData, 0, sizeof(deviceInfoData)); + SP_DEVINFO_DATA deviceInfoData{}; deviceInfoData.cbSize = sizeof(deviceInfoData); DWORD index = 0; - while (::SetupDiEnumDeviceInfo(deviceInfoSet, index++, &deviceInfoData)) { - const QString portName = devicePortName(deviceInfoSet, &deviceInfoData); + while (::SetupDiEnumDeviceInfo(deviceInfoSet.get(), index++, &deviceInfoData)) { + const QString portName = devicePortName(deviceInfoSet.get(), &deviceInfoData); if (portName.isEmpty() || portName.contains(QLatin1String("LPT"))) continue; @@ -281,8 +529,8 @@ priv.portName = portName; priv.device = QSerialPortInfoPrivate::portNameToSystemLocation(portName); - priv.description = deviceDescription(deviceInfoSet, &deviceInfoData); - priv.manufacturer = deviceManufacturer(deviceInfoSet, &deviceInfoData); + priv.description = deviceDescription(deviceInfoSet.get(), &deviceInfoData); + priv.manufacturer = deviceManufacturer(deviceInfoSet.get(), &deviceInfoData); const QString instanceIdentifier = deviceInstanceIdentifier(deviceInfoData.DevInst); @@ -293,9 +541,21 @@ priv.productIdentifier = deviceProductIdentifier(instanceIdentifier, priv.hasProductIdentifier); + // This makes Windows return the same data that linux does for Manufacturer and Product + if (instanceIdentifier.startsWith(L"USB\\") && priv.hasVendorIdentifier && + priv.hasProductIdentifier) { + UsbData usbStrings = getUSBDataFromDevice(deviceInfoData.DevInst); + + if (!usbStrings.iManufacturer.isEmpty()) + priv.manufacturer = usbStrings.iManufacturer; + + if (!usbStrings.iProduct.isEmpty()) + priv.description = usbStrings.iProduct; + // End of making Windows return the same data as Linux + } + serialPortInfoList.append(priv); } - ::SetupDiDestroyDeviceInfoList(deviceInfoSet); } const auto portNames = portNamesFromHardwareDeviceMap();