Correct libusb usage on FreeBSD (#10736)

Change type of Handle on FreeBSD. On FreeBSD the libusb_hotplug_register_callback() function uses a pointer to a struct as a handle.

---------

Co-authored-by: Janek Bevendorff <janek@keepassxc.org>
This commit is contained in:
Guido Falsi 2024-06-19 22:50:56 +02:00 committed by GitHub
parent 5f2ee86d72
commit f4b91c17a9
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 21 additions and 11 deletions

View File

@ -57,7 +57,7 @@ DeviceListener::registerHotplugCallback(bool arrived, bool left, int vendorId, i
void DeviceListener::deregisterHotplugCallback(Handle handle)
{
#if defined(Q_OS_UNIX) && !defined(Q_OS_MACOS)
m_listeners[0]->deregisterHotplugCallback(static_cast<int>(handle));
m_listeners[0]->deregisterHotplugCallback(handle);
#else
if (m_listeners.contains(handle)) {
m_listeners[handle]->deregisterHotplugCallback();

View File

@ -20,6 +20,7 @@
#include <QPointer>
#include <QtConcurrent>
#include <QtGlobal>
#include <libusb.h>
DeviceListenerLibUsb::DeviceListenerLibUsb(QWidget* parent)
@ -49,7 +50,8 @@ namespace
}
} // namespace
int DeviceListenerLibUsb::registerHotplugCallback(bool arrived, bool left, int vendorId, int productId, const QUuid*)
DeviceListenerLibUsb::Handle
DeviceListenerLibUsb::registerHotplugCallback(bool arrived, bool left, int vendorId, int productId, const QUuid*)
{
if (!m_ctx) {
if (libusb_init(reinterpret_cast<libusb_context**>(&m_ctx)) != LIBUSB_SUCCESS) {
@ -66,7 +68,8 @@ int DeviceListenerLibUsb::registerHotplugCallback(bool arrived, bool left, int v
events |= LIBUSB_HOTPLUG_EVENT_DEVICE_LEFT;
}
int handle = 0;
Handle handle = 0;
auto* handleNative = reinterpret_cast<libusb_hotplug_callback_handle*>(&handle);
const QPointer that = this;
const int ret = libusb_hotplug_register_callback(
static_cast<libusb_context*>(m_ctx),
@ -77,14 +80,14 @@ int DeviceListenerLibUsb::registerHotplugCallback(bool arrived, bool left, int v
LIBUSB_HOTPLUG_MATCH_ANY,
[](libusb_context* ctx, libusb_device* device, libusb_hotplug_event event, void* userData) -> int {
if (!ctx) {
return 0;
return true;
}
emit static_cast<DeviceListenerLibUsb*>(userData)->devicePlugged(
event == LIBUSB_HOTPLUG_EVENT_DEVICE_ARRIVED, ctx, device);
return 0;
return false;
},
that,
&handle);
handleNative);
if (ret != LIBUSB_SUCCESS) {
qWarning("Failed to register USB listener callback.");
handle = 0;
@ -102,12 +105,17 @@ int DeviceListenerLibUsb::registerHotplugCallback(bool arrived, bool left, int v
return handle;
}
void DeviceListenerLibUsb::deregisterHotplugCallback(int handle)
void DeviceListenerLibUsb::deregisterHotplugCallback(Handle handle)
{
if (!m_ctx || !m_callbackHandles.contains(handle)) {
return;
}
libusb_hotplug_deregister_callback(static_cast<libusb_context*>(m_ctx), handle);
#ifdef Q_OS_FREEBSD
auto* handleNative = reinterpret_cast<libusb_hotplug_callback_handle>(handle);
#else
auto handleNative = static_cast<libusb_hotplug_callback_handle>(handle);
#endif
libusb_hotplug_deregister_callback(static_cast<libusb_context*>(m_ctx), handleNative);
m_callbackHandles.remove(handle);
if (m_callbackHandles.isEmpty() && m_usbEvents.isRunning()) {

View File

@ -32,12 +32,14 @@ class DeviceListenerLibUsb : public QObject
Q_OBJECT
public:
typedef qintptr Handle;
explicit DeviceListenerLibUsb(QWidget* parent);
DeviceListenerLibUsb(const DeviceListenerLibUsb&) = delete;
~DeviceListenerLibUsb() override;
int registerHotplugCallback(bool arrived, bool left, int vendorId = -1, int productId = -1, const QUuid* = nullptr);
void deregisterHotplugCallback(int handle);
Handle
registerHotplugCallback(bool arrived, bool left, int vendorId = -1, int productId = -1, const QUuid* = nullptr);
void deregisterHotplugCallback(Handle handle);
void deregisterAllHotplugCallbacks();
signals:
@ -45,7 +47,7 @@ signals:
private:
void* m_ctx;
QSet<int> m_callbackHandles;
QSet<Handle> m_callbackHandles;
QFuture<void> m_usbEvents;
QAtomicInt m_completed;
};