Skip to content

Commit ed20ced

Browse files
committed
qt: shutdown backend on backend shutdown to release devices
Our hidraw udev rule: ``` KERNEL=="hidraw*", SUBSYSTEM=="hidraw", ATTRS{idVendor}=="03eb", ATTRS{idProduct}=="2403", TAG+="uaccess", TAG+="udev-acl", SYMLINK+="bitbox02-%n" ``` creates `/dev/bitbox02-N` symlinks (one per HID interface). The BitBoxApp uses libusb (default backend of karalabe/hid), not hidraw. However, when a device is opened, the corresponding symlink is removed, and restored when it is closed (presumably to ensure exclusive access). Howewer, we never closed the opened devices when the app closed, leading to the symlink being missing afterwards. This resulted in apps that use hidraw not being able to connect after the BitBoxApp connected first, like Sparrow. This commit calls the backend shutdown on app close, also closing the opened devices.
1 parent 634a5e8 commit ed20ced

File tree

7 files changed

+37
-2
lines changed

7 files changed

+37
-2
lines changed

CHANGELOG.md

+1
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66

77
# 4.47.1
88
- Linux: fix support for Wayland
9+
- Linux: release device upon app close, enabling other apps to connect to the BitBox after the BitBoxApp closes
910

1011
# 4.47.0
1112
- Bundle BitBox02 firmware version v9.22.0

backend/backend.go

+5
Original file line numberDiff line numberDiff line change
@@ -898,6 +898,11 @@ func (backend *Backend) Environment() Environment {
898898

899899
// Close shuts down the backend. After this, no other method should be called.
900900
func (backend *Backend) Close() error {
901+
backend.ratesUpdater.Stop()
902+
// Call this without `accountsAndKeystoreLock` as it eventually calls `DeregisterKeystore()`,
903+
// which acquires the same lock.
904+
backend.usbManager.Close()
905+
901906
defer backend.accountsAndKeystoreLock.Lock()()
902907

903908
errors := []string{}

backend/bridgecommon/bridgecommon.go

+2-1
Original file line numberDiff line numberDiff line change
@@ -363,8 +363,9 @@ func Shutdown() {
363363

364364
log := logging.Get().WithGroup("server")
365365
if globalShutdown != nil {
366+
log.Info("Shutdown about to be called")
366367
globalShutdown()
367-
log.Info("Shutdown called")
368+
log.Info("Shutdown finished")
368369
} else {
369370
log.Info("Shutdown called, but backend not running")
370371
}

backend/devices/usb/manager.go

+22
Original file line numberDiff line numberDiff line change
@@ -91,6 +91,7 @@ type Manager struct {
9191
onUnregister func(string)
9292

9393
updateCh chan struct{}
94+
quitCh chan struct{}
9495

9596
socksProxy socksproxy.SocksProxy
9697

@@ -118,6 +119,7 @@ func NewManager(
118119
onRegister: onRegister,
119120
onUnregister: onUnregister,
120121
updateCh: make(chan struct{}),
122+
quitCh: make(chan struct{}),
121123
socksProxy: socksProxy,
122124

123125
log: logging.Get().WithGroup("manager"),
@@ -272,6 +274,14 @@ func (manager *Manager) Update() {
272274
func (manager *Manager) listen() {
273275
for {
274276
select {
277+
case <-manager.quitCh:
278+
return
279+
default:
280+
}
281+
282+
select {
283+
case <-manager.quitCh:
284+
return
275285
case <-manager.updateCh:
276286
case <-time.After(time.Second):
277287
}
@@ -336,3 +346,15 @@ func (manager *Manager) Start() {
336346
go manager.listen()
337347
manager.Update()
338348
}
349+
350+
// Close closes and unregisters all devices.
351+
func (manager *Manager) Close() {
352+
manager.log.Info("Closing devices manager")
353+
close(manager.quitCh)
354+
for deviceID, device := range manager.devices {
355+
manager.log.WithField("device-id", deviceID).Info("manager: closing device")
356+
device.Close()
357+
delete(manager.devices, deviceID)
358+
manager.onUnregister(deviceID)
359+
}
360+
}

frontends/qt/libserver.h

+1-1
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ extern void handleURI(cchar_t* uri);
4949
extern void serve(cppHeapFree cppHeapFreeFn, pushNotificationsCallback pushNotificationsFn, responseCallback responseFn, notifyUserCallback notifyUserFn, cchar_t* preferredLocale, getSaveFilenameCallback getSaveFilenameFn);
5050
extern void systemOpen(cchar_t* url);
5151
extern void goLog(cchar_t* msg);
52-
52+
extern void backendShutdown();
5353
#ifdef __cplusplus
5454
}
5555
#endif

frontends/qt/main.cpp

+1
Original file line numberDiff line numberDiff line change
@@ -460,6 +460,7 @@ int main(int argc, char *argv[])
460460
delete view;
461461
view = nullptr;
462462
webClassMutex.unlock();
463+
backendShutdown();
463464
});
464465

465466
#if defined(_WIN32)

frontends/qt/server/server.go

+5
Original file line numberDiff line numberDiff line change
@@ -206,6 +206,11 @@ func goLog(msg *C.cchar_t) {
206206
logging.Get().WithGroup("qt-frontend").Info(goMsg)
207207
}
208208

209+
//export backendShutdown
210+
func backendShutdown() {
211+
bridgecommon.Shutdown()
212+
}
213+
209214
func authResult(ok bool) {
210215
bridgecommon.AuthResult(ok)
211216
}

0 commit comments

Comments
 (0)