usb 1.8.1-libusb.4 → 1.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +63 -0
- package/{Readme.md → README.md} +6 -0
- package/package.json +2 -2
- package/prebuilds/android-arm/node.napi.armv7.node +0 -0
- package/prebuilds/android-arm64/node.napi.armv8.node +0 -0
- package/prebuilds/darwin-x64+arm64/node.napi.node +0 -0
- package/prebuilds/linux-arm/node.napi.armv6.node +0 -0
- package/prebuilds/linux-arm/node.napi.armv7.node +0 -0
- package/prebuilds/linux-arm64/node.napi.armv8.node +0 -0
- package/prebuilds/linux-ia32/node.napi.node +0 -0
- package/prebuilds/linux-x64/node.napi.glibc.node +0 -0
- package/prebuilds/linux-x64/node.napi.musl.node +0 -0
- package/prebuilds/win32-ia32/node.napi.node +0 -0
- package/prebuilds/win32-x64/node.napi.node +0 -0
- package/src/device.cc +2 -3
- package/src/node_usb.cc +42 -1
- package/src/uv_async_queue.h +33 -25
- package/usb.js +37 -34
package/CHANGELOG.md
ADDED
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
## [1.9.0] - 2021-11-08
|
|
4
|
+
|
|
5
|
+
### Changed
|
|
6
|
+
- Changed libusb dependency to upstream v1.0.23 - [`453`](https://github.com/node-usb/node-usb/pull/453) ([Rob Moran](https://github.com/thegecko))
|
|
7
|
+
|
|
8
|
+
## [1.8.1] - 2021-11-08
|
|
9
|
+
|
|
10
|
+
### Added
|
|
11
|
+
- Added functionality to ref/unref the hotplug events - [`455`](https://github.com/node-usb/node-usb/pull/455) ([Guilherme Francescon](https://github.com/gfcittolin))
|
|
12
|
+
- Added CHANGELOG - [`454`](https://github.com/node-usb/node-usb/pull/454) ([Rob Moran](https://github.com/thegecko))
|
|
13
|
+
|
|
14
|
+
### Fixed
|
|
15
|
+
- Fixed delay when exiting program - [`455`](https://github.com/node-usb/node-usb/pull/455) ([Rob Moran](https://github.com/thegecko))
|
|
16
|
+
|
|
17
|
+
## [1.8.0] - 2021-10-14
|
|
18
|
+
|
|
19
|
+
### Added
|
|
20
|
+
- Added prebuildify and GitHub action for native binaries - [`450`](https://github.com/node-usb/node-usb/pull/450) ([Rob Moran](https://github.com/thegecko))
|
|
21
|
+
|
|
22
|
+
### Fixed
|
|
23
|
+
- Fixed crash after wake on Windows when using Electron - [`451`](https://github.com/node-usb/node-usb/pull/451) ([Rob Moran](https://github.com/thegecko))
|
|
24
|
+
- Fixed invalid initial refs - [`445`](https://github.com/node-usb/node-usb/pull/445) ([Alba Mendez](https://github.com/mildsunrise))
|
|
25
|
+
|
|
26
|
+
### Changed
|
|
27
|
+
- Changed GitHub organisation to [node-usb](https://github.com/node-usb) - [`447`](https://github.com/node-usb/node-usb/pull/447) ([Rob Moran](https://github.com/thegecko))
|
|
28
|
+
|
|
29
|
+
## [1.7.2] - 2021-08-30
|
|
30
|
+
|
|
31
|
+
### Fixed
|
|
32
|
+
- Fixed crash when exiting on MacOS with Electron 9 - [`440`](https://github.com/node-usb/node-usb/pull/440) ([Daniel Main](https://github.com/danielmain))
|
|
33
|
+
|
|
34
|
+
### Changed
|
|
35
|
+
- **Breaking:** Changed minimum Node.js version to `10` - [`428`](https://github.com/node-usb/node-usb/pull/428) ([Rob Moran](https://github.com/thegecko))
|
|
36
|
+
|
|
37
|
+
## [1.7.1] - 2021-05-08
|
|
38
|
+
|
|
39
|
+
### Fixed
|
|
40
|
+
- Fixed compiler warnings - [`419`](https://github.com/node-usb/node-usb/pull/419) ([Joel Purra](https://github.com/joelpurra))
|
|
41
|
+
|
|
42
|
+
## [1.7.0] - 2021-04-10
|
|
43
|
+
|
|
44
|
+
### Changed
|
|
45
|
+
- Changed native support to use Node Addon API - [`399`](https://github.com/node-usb/node-usb/pull/399) ([Georg Vienna](https://github.com/geovie))
|
|
46
|
+
|
|
47
|
+
## [1.6.5] - 2021-02-14
|
|
48
|
+
|
|
49
|
+
### Changed
|
|
50
|
+
- Changed prebuild for Electron 12 beta to nightly - [`410`](https://github.com/node-usb/node-usb/pull/410) ([Piotr Rogowski](https://github.com/karniv00l))
|
|
51
|
+
|
|
52
|
+
### Removed
|
|
53
|
+
- Removed `portNumbers` test on arm64 - [`408`](https://github.com/node-usb/node-usb/pull/408) ([Rob Moran](https://github.com/thegecko))
|
|
54
|
+
|
|
55
|
+
## [1.6.4] - 2021-01-30
|
|
56
|
+
|
|
57
|
+
### Added
|
|
58
|
+
- Added prebuild for Electron 10 and 12 beta - [`407`](https://github.com/node-usb/node-usb/pull/407) ([Rob Moran](https://github.com/thegecko))
|
|
59
|
+
- Added prebuild for Electron 9 - [`362`](https://github.com/node-usb/node-usb/pull/362) (Luke Whyte)
|
|
60
|
+
|
|
61
|
+
### Changed
|
|
62
|
+
- Changed to GitHub Actions for prebuild workflow - [`404`](https://github.com/node-usb/node-usb/pull/404) ([Rob Moran](https://github.com/thegecko))
|
|
63
|
+
- Changed Node.js 13 prebuild target to Node.js 14 - [`374`](https://github.com/node-usb/node-usb/pull/374) ([Micah Zoltu](https://github.com/MicahZoltu))
|
package/{Readme.md → README.md}
RENAMED
|
@@ -304,6 +304,12 @@ Attaches a callback to plugging in a `device`.
|
|
|
304
304
|
### usb.on('detach', function(device) { ... });
|
|
305
305
|
Attaches a callback to unplugging a `device`.
|
|
306
306
|
|
|
307
|
+
### usb.refHotplugEvents();
|
|
308
|
+
Restore (re-reference) the hotplug events unreferenced by `unrefHotplugEvents()`
|
|
309
|
+
|
|
310
|
+
### usb.unrefHotplugEvents();
|
|
311
|
+
Listening to events will prevent the process to exit. By calling this function, hotplug events will be unreferenced by the event loop, allowing the process to exit even when listening for the `attach` and `detach` events.
|
|
312
|
+
|
|
307
313
|
|
|
308
314
|
Development and testing
|
|
309
315
|
=======================
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "usb",
|
|
3
3
|
"description": "Library to access USB devices",
|
|
4
|
-
"version": "1.
|
|
4
|
+
"version": "1.9.0",
|
|
5
5
|
"engines": {
|
|
6
6
|
"node": ">=10.16.0"
|
|
7
7
|
},
|
|
@@ -55,7 +55,7 @@
|
|
|
55
55
|
},
|
|
56
56
|
"devDependencies": {
|
|
57
57
|
"coffeescript": "~2.4.1",
|
|
58
|
-
"mocha": "^
|
|
58
|
+
"mocha": "^9.1.3",
|
|
59
59
|
"node-gyp": "^7.1.2",
|
|
60
60
|
"prebuildify": "^4.2.1",
|
|
61
61
|
"prebuildify-ci": "^1.0.5",
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
package/src/device.cc
CHANGED
|
@@ -21,6 +21,8 @@ Device::Device(const Napi::CallbackInfo & info) : Napi::ObjectWrap<Device>(info)
|
|
|
21
21
|
byPtr.insert(std::make_pair(device, this));
|
|
22
22
|
#ifndef USE_POLL
|
|
23
23
|
completionQueue.start(info.Env());
|
|
24
|
+
// Unref threadsafe function immediately to avoid delay in program exit
|
|
25
|
+
completionQueue.unref(info.Env());
|
|
24
26
|
#endif
|
|
25
27
|
DEBUG_LOG("Created device %p", this);
|
|
26
28
|
Constructor(info);
|
|
@@ -28,9 +30,6 @@ Device::Device(const Napi::CallbackInfo & info) : Napi::ObjectWrap<Device>(info)
|
|
|
28
30
|
|
|
29
31
|
Device::~Device(){
|
|
30
32
|
DEBUG_LOG("Freed device %p", this);
|
|
31
|
-
#ifndef USE_POLL
|
|
32
|
-
completionQueue.stop();
|
|
33
|
-
#endif
|
|
34
33
|
byPtr.erase(device);
|
|
35
34
|
libusb_close(device_handle);
|
|
36
35
|
libusb_unref_device(device);
|
package/src/node_usb.cc
CHANGED
|
@@ -4,8 +4,11 @@
|
|
|
4
4
|
|
|
5
5
|
Napi::Value SetDebugLevel(const Napi::CallbackInfo& info);
|
|
6
6
|
Napi::Value GetDeviceList(const Napi::CallbackInfo& info);
|
|
7
|
+
Napi::Value GetLibusbCapability(const Napi::CallbackInfo& info);
|
|
7
8
|
Napi::Value EnableHotplugEvents(const Napi::CallbackInfo& info);
|
|
8
9
|
Napi::Value DisableHotplugEvents(const Napi::CallbackInfo& info);
|
|
10
|
+
Napi::Value RefHotplugEvents(const Napi::CallbackInfo& info);
|
|
11
|
+
Napi::Value UnrefHotplugEvents(const Napi::CallbackInfo& info);
|
|
9
12
|
void initConstants(Napi::Object target);
|
|
10
13
|
|
|
11
14
|
libusb_context* usb_context;
|
|
@@ -16,6 +19,7 @@ struct HotPlug {
|
|
|
16
19
|
|
|
17
20
|
#ifdef USE_POLL
|
|
18
21
|
#include <poll.h>
|
|
22
|
+
#include <uv.h>
|
|
19
23
|
#include <sys/time.h>
|
|
20
24
|
|
|
21
25
|
std::map<int, uv_poll_t*> pollByFD;
|
|
@@ -94,8 +98,11 @@ Napi::Object Init(Napi::Env env, Napi::Object exports) {
|
|
|
94
98
|
|
|
95
99
|
exports.Set("setDebugLevel", Napi::Function::New(env, SetDebugLevel));
|
|
96
100
|
exports.Set("getDeviceList", Napi::Function::New(env, GetDeviceList));
|
|
101
|
+
exports.Set("_getLibusbCapability", Napi::Function::New(env, GetLibusbCapability));
|
|
97
102
|
exports.Set("_enableHotplugEvents", Napi::Function::New(env, EnableHotplugEvents));
|
|
98
103
|
exports.Set("_disableHotplugEvents", Napi::Function::New(env, DisableHotplugEvents));
|
|
104
|
+
exports.Set("refHotplugEvents", Napi::Function::New(env, RefHotplugEvents));
|
|
105
|
+
exports.Set("unrefHotplugEvents", Napi::Function::New(env, UnrefHotplugEvents));
|
|
99
106
|
return exports;
|
|
100
107
|
}
|
|
101
108
|
|
|
@@ -128,6 +135,17 @@ Napi::Value GetDeviceList(const Napi::CallbackInfo& info) {
|
|
|
128
135
|
return arr;
|
|
129
136
|
}
|
|
130
137
|
|
|
138
|
+
Napi::Value GetLibusbCapability(const Napi::CallbackInfo& info) {
|
|
139
|
+
Napi::Env env = info.Env();
|
|
140
|
+
|
|
141
|
+
if (info.Length() != 1 || !info[0].IsNumber()) {
|
|
142
|
+
THROW_BAD_ARGS("Usb::GetLibusbCapability argument is invalid!")
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
int res = libusb_has_capability(info[0].As<Napi::Number>().Int32Value());
|
|
146
|
+
return Napi::Number::New(env, res);
|
|
147
|
+
}
|
|
148
|
+
|
|
131
149
|
Napi::ObjectReference hotplugThis;
|
|
132
150
|
|
|
133
151
|
void handleHotplug(HotPlug* info){
|
|
@@ -199,10 +217,27 @@ Napi::Value DisableHotplugEvents(const Napi::CallbackInfo& info) {
|
|
|
199
217
|
return env.Undefined();
|
|
200
218
|
}
|
|
201
219
|
|
|
220
|
+
Napi::Value RefHotplugEvents(const Napi::CallbackInfo& info) {
|
|
221
|
+
Napi::Env env = info.Env();
|
|
222
|
+
Napi::HandleScope scope(env);
|
|
223
|
+
if (hotplugEnabled) {
|
|
224
|
+
hotplugQueue.ref(env);
|
|
225
|
+
}
|
|
226
|
+
return env.Undefined();
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
Napi::Value UnrefHotplugEvents(const Napi::CallbackInfo& info) {
|
|
230
|
+
Napi::Env env = info.Env();
|
|
231
|
+
Napi::HandleScope scope(env);
|
|
232
|
+
if (hotplugEnabled) {
|
|
233
|
+
hotplugQueue.unref(env);
|
|
234
|
+
}
|
|
235
|
+
return env.Undefined();
|
|
236
|
+
}
|
|
237
|
+
|
|
202
238
|
#define DEFINE_CONSTANT(OBJ, VALUE) \
|
|
203
239
|
OBJ.DefineProperty(Napi::PropertyDescriptor::Value(#VALUE, Napi::Number::New(OBJ.Env(), VALUE), static_cast<napi_property_attributes>(napi_enumerable | napi_configurable)));
|
|
204
240
|
|
|
205
|
-
|
|
206
241
|
void initConstants(Napi::Object target){
|
|
207
242
|
DEFINE_CONSTANT(target, LIBUSB_CLASS_PER_INTERFACE);
|
|
208
243
|
DEFINE_CONSTANT(target, LIBUSB_CLASS_AUDIO);
|
|
@@ -282,6 +317,12 @@ void initConstants(Napi::Object target){
|
|
|
282
317
|
DEFINE_CONSTANT(target, LIBUSB_CONTROL_SETUP_SIZE);
|
|
283
318
|
DEFINE_CONSTANT(target, LIBUSB_DT_BOS_SIZE);
|
|
284
319
|
|
|
320
|
+
// libusb_capability
|
|
321
|
+
DEFINE_CONSTANT(target, LIBUSB_CAP_HAS_CAPABILITY);
|
|
322
|
+
DEFINE_CONSTANT(target, LIBUSB_CAP_HAS_HOTPLUG);
|
|
323
|
+
DEFINE_CONSTANT(target, LIBUSB_CAP_HAS_HID_ACCESS);
|
|
324
|
+
DEFINE_CONSTANT(target, LIBUSB_CAP_SUPPORTS_DETACH_KERNEL_DRIVER);
|
|
325
|
+
|
|
285
326
|
// libusb_error
|
|
286
327
|
// Input/output error
|
|
287
328
|
DEFINE_CONSTANT(target, LIBUSB_ERROR_IO);
|
package/src/uv_async_queue.h
CHANGED
|
@@ -3,31 +3,39 @@
|
|
|
3
3
|
|
|
4
4
|
template <class T>
|
|
5
5
|
class UVQueue{
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
6
|
+
public:
|
|
7
|
+
typedef void (*fptr)(T);
|
|
8
|
+
|
|
9
|
+
Napi::ThreadSafeFunction tsfn;
|
|
10
|
+
|
|
11
|
+
UVQueue(fptr cb): callback(cb) {}
|
|
12
|
+
|
|
13
|
+
void start(Napi::Env env) {
|
|
14
|
+
Napi::Function empty_func = Napi::Function::New(env, [](const Napi::CallbackInfo& cb) {});
|
|
15
|
+
tsfn = Napi::ThreadSafeFunction::New(env, empty_func, "libusb", 0, 1);
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
void stop() {
|
|
19
|
+
tsfn.Release();
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
void ref(Napi::Env env) {
|
|
23
|
+
tsfn.Ref(env);
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
void unref(Napi::Env env) {
|
|
27
|
+
tsfn.Unref(env);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
void post(T value){
|
|
31
|
+
auto cb = callback;
|
|
32
|
+
tsfn.BlockingCall( value, [cb](Napi::Env _env, Napi::Function _jsCallback, T val) {
|
|
33
|
+
cb(val);
|
|
34
|
+
});
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
private:
|
|
38
|
+
fptr callback;
|
|
31
39
|
};
|
|
32
40
|
|
|
33
41
|
#endif
|
package/usb.js
CHANGED
|
@@ -1,9 +1,6 @@
|
|
|
1
1
|
var usb = exports = module.exports = require('node-gyp-build')(__dirname);
|
|
2
2
|
var events = require('events');
|
|
3
3
|
var util = require('util');
|
|
4
|
-
var os = require('os');
|
|
5
|
-
|
|
6
|
-
var isWindows = os.platform() === 'win32';
|
|
7
4
|
|
|
8
5
|
var isBuffer = function(obj) {
|
|
9
6
|
return obj && obj instanceof Uint8Array
|
|
@@ -17,6 +14,8 @@ if (usb.INIT_ERROR) {
|
|
|
17
14
|
usb.getDeviceList = function () { return []; };
|
|
18
15
|
usb._enableHotplugEvents = function () { };
|
|
19
16
|
usb._disableHotplugEvents = function () { };
|
|
17
|
+
usb.refHotplugEvents = function () { };
|
|
18
|
+
usb.unrefHotplugEvents = function () { };
|
|
20
19
|
}
|
|
21
20
|
|
|
22
21
|
Object.keys(events.EventEmitter.prototype).forEach(function (key) {
|
|
@@ -511,35 +510,16 @@ OutEndpoint.prototype.transferWithZLP = function (buf, cb) {
|
|
|
511
510
|
}
|
|
512
511
|
}
|
|
513
512
|
|
|
514
|
-
var hotplugListeners = 0;
|
|
515
|
-
exports.on('newListener', function(name) {
|
|
516
|
-
if (name !== 'attach' && name !== 'detach') return;
|
|
517
|
-
if (++hotplugListeners === 1) {
|
|
518
|
-
if (isWindows) {
|
|
519
|
-
exports._pollHotplug(true);
|
|
520
|
-
} else {
|
|
521
|
-
usb._enableHotplugEvents();
|
|
522
|
-
}
|
|
523
|
-
}
|
|
524
|
-
});
|
|
525
|
-
|
|
526
|
-
exports.on('removeListener', function(name) {
|
|
527
|
-
if (name !== 'attach' && name !== 'detach') return;
|
|
528
|
-
if (--hotplugListeners === 0) {
|
|
529
|
-
if (isWindows) {
|
|
530
|
-
exports._pollingHotplug = false;
|
|
531
|
-
} else {
|
|
532
|
-
usb._disableHotplugEvents();
|
|
533
|
-
}
|
|
534
|
-
}
|
|
535
|
-
});
|
|
536
|
-
|
|
537
513
|
// Polling mechanism for discovering device changes until this is fixed:
|
|
538
514
|
// https://github.com/libusb/libusb/issues/86
|
|
539
|
-
exports.
|
|
515
|
+
exports._pollTimeout = 500;
|
|
516
|
+
var hotplugSupported = usb._getLibusbCapability(usb.LIBUSB_CAP_HAS_HOTPLUG) > 0;
|
|
517
|
+
var pollingHotplug = false;
|
|
518
|
+
var pollDevices = [];
|
|
519
|
+
function pollHotplug(start) {
|
|
540
520
|
if (start) {
|
|
541
|
-
|
|
542
|
-
} else if (!
|
|
521
|
+
pollingHotplug = true;
|
|
522
|
+
} else if (!pollingHotplug) {
|
|
543
523
|
return;
|
|
544
524
|
}
|
|
545
525
|
|
|
@@ -548,14 +528,14 @@ exports._pollHotplug = function(start) {
|
|
|
548
528
|
if (!start) {
|
|
549
529
|
// Find attached devices
|
|
550
530
|
for (var device of devices) {
|
|
551
|
-
var found =
|
|
531
|
+
var found = pollDevices.find(item => item.deviceAddress === device.deviceAddress);
|
|
552
532
|
if (!found) {
|
|
553
533
|
usb.emit('attach', device);
|
|
554
534
|
}
|
|
555
535
|
}
|
|
556
536
|
|
|
557
537
|
// Find detached devices
|
|
558
|
-
for (var device of
|
|
538
|
+
for (var device of pollDevices) {
|
|
559
539
|
var found = devices.find(item => item.deviceAddress === device.deviceAddress);
|
|
560
540
|
if (!found) {
|
|
561
541
|
usb.emit('detach', device);
|
|
@@ -563,8 +543,31 @@ exports._pollHotplug = function(start) {
|
|
|
563
543
|
}
|
|
564
544
|
}
|
|
565
545
|
|
|
566
|
-
|
|
546
|
+
pollDevices = devices;
|
|
567
547
|
setTimeout(() => {
|
|
568
|
-
|
|
569
|
-
},
|
|
548
|
+
pollHotplug();
|
|
549
|
+
}, exports._pollTimeout);
|
|
570
550
|
}
|
|
551
|
+
|
|
552
|
+
var hotplugListeners = 0;
|
|
553
|
+
exports.on('newListener', function(name) {
|
|
554
|
+
if (name !== 'attach' && name !== 'detach') return;
|
|
555
|
+
if (++hotplugListeners === 1) {
|
|
556
|
+
if (hotplugSupported) {
|
|
557
|
+
usb._enableHotplugEvents();
|
|
558
|
+
} else {
|
|
559
|
+
pollHotplug(true);
|
|
560
|
+
}
|
|
561
|
+
}
|
|
562
|
+
});
|
|
563
|
+
|
|
564
|
+
exports.on('removeListener', function(name) {
|
|
565
|
+
if (name !== 'attach' && name !== 'detach') return;
|
|
566
|
+
if (--hotplugListeners === 0) {
|
|
567
|
+
if (hotplugSupported) {
|
|
568
|
+
usb._disableHotplugEvents();
|
|
569
|
+
} else {
|
|
570
|
+
pollingHotplug = false;
|
|
571
|
+
}
|
|
572
|
+
}
|
|
573
|
+
});
|