@nordicsemiconductor/pc-nrfconnect-shared 121.0.0 → 123.0.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 +85 -0
- package/coverage/cobertura-coverage.xml +2276 -1778
- package/ipc/launcherConfig.ts +25 -0
- package/ipc/openWindow.ts +17 -1
- package/ipc/schema/packageJson.ts +26 -22
- package/main/index.ts +11 -5
- package/mocks/packageJsonMock.ts +1 -1
- package/nrfutil/device/__mocks__/device.ts +2 -0
- package/nrfutil/device/batch.ts +19 -9
- package/nrfutil/device/common.ts +32 -46
- package/nrfutil/device/device.ts +2 -0
- package/nrfutil/device/deviceInfo.ts +70 -0
- package/nrfutil/device/erase.ts +2 -2
- package/nrfutil/device/firmwareRead.ts +2 -2
- package/nrfutil/device/getCoreInfo.ts +2 -2
- package/nrfutil/device/getFwInfo.ts +2 -2
- package/nrfutil/device/getProtectionStatus.ts +2 -2
- package/nrfutil/device/list.ts +5 -31
- package/nrfutil/device/program.ts +4 -4
- package/nrfutil/device/recover.ts +2 -2
- package/nrfutil/device/reset.ts +2 -2
- package/nrfutil/device/setMcuState.ts +2 -5
- package/nrfutil/device/setProtectionStatus.ts +2 -2
- package/nrfutil/index.ts +1 -1
- package/nrfutil/moduleVersion.ts +22 -2
- package/nrfutil/sandbox.ts +52 -32
- package/nrfutil/sandboxTypes.ts +15 -1
- package/package.json +3 -2
- package/scripts/check-app-properties.ts +6 -6
- package/scripts/esbuild.ts +3 -3
- package/scripts/nordic-publish.js +23 -23
- package/scripts/nordic-publish.ts +3 -3
- package/scripts/release-shared.ts +2 -2
- package/src/About/ApplicationCard.tsx +3 -5
- package/src/About/DeviceCard.tsx +6 -5
- package/src/About/SupportCard.tsx +2 -2
- package/src/App/App.test.tsx +7 -0
- package/src/App/App.tsx +14 -27
- package/src/Device/DeviceSelector/BasicDeviceInfo.tsx +12 -6
- package/src/Device/DeviceSelector/DeviceList/AnimatedList.tsx +1 -1
- package/src/Device/DeviceSelector/DeviceList/Device.tsx +7 -5
- package/src/Device/DeviceSelector/DeviceList/DeviceList.tsx +23 -5
- package/src/Device/DeviceSelector/DeviceList/EditDeviceButtons.tsx +7 -6
- package/src/Device/DeviceSelector/DeviceList/MoreDeviceInfo.tsx +26 -30
- package/src/Device/DeviceSelector/DeviceList/edit-device-buttons.scss +1 -2
- package/src/Device/DeviceSelector/DeviceSelector.test.tsx +17 -37
- package/src/Device/DeviceSelector/DeviceSelector.tsx +64 -21
- package/src/Device/DeviceSelector/Favorite.tsx +10 -10
- package/src/Device/DeviceSelector/basic-device-info.scss +0 -12
- package/src/Device/deviceInfo/deviceInfo.ts +2 -2
- package/src/Device/deviceLister.ts +111 -59
- package/src/Device/deviceSetup.ts +30 -13
- package/src/Device/deviceSlice.ts +157 -84
- package/src/Device/jprogOperations.ts +56 -27
- package/src/Device/sdfuOperations.ts +25 -31
- package/src/ErrorBoundary/ErrorBoundary.tsx +7 -13
- package/src/Feedback/sendFeedback.ts +2 -4
- package/src/InlineInput/NumberInlineInput.tsx +1 -1
- package/src/InlineInput/NumberInputWithDropdown.tsx +1 -2
- package/src/index.ts +4 -0
- package/src/logging/sendInitialLogMessages.ts +15 -13
- package/src/utils/appDetails.ts +22 -0
- package/src/utils/appDirs.ts +4 -4
- package/src/utils/launcherConfig.ts +17 -0
- package/src/utils/logLibVersions.ts +1 -1
- package/src/utils/packageJson.ts +52 -10
- package/src/utils/persistentStore.ts +21 -14
- package/src/utils/systemReport.ts +4 -6
- package/src/utils/usageData.ts +75 -167
- package/src/utils/usageDataCommon.ts +59 -0
- package/src/utils/usageDataMain.ts +117 -0
- package/src/utils/usageDataRenderer.ts +126 -0
- package/src/utils/useHotKey.ts +2 -2
- package/typings/generated/ipc/launcherConfig.d.ts +14 -0
- package/typings/generated/ipc/launcherConfig.d.ts.map +1 -0
- package/typings/generated/ipc/openWindow.d.ts +10 -4
- package/typings/generated/ipc/openWindow.d.ts.map +1 -1
- package/typings/generated/ipc/schema/packageJson.d.ts +34 -52
- package/typings/generated/ipc/schema/packageJson.d.ts.map +1 -1
- package/typings/generated/main/index.d.ts +8 -2
- package/typings/generated/main/index.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/__mocks__/device.d.ts +1 -0
- package/typings/generated/nrfutil/device/__mocks__/device.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/batch.d.ts +3 -2
- package/typings/generated/nrfutil/device/batch.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/common.d.ts +7 -34
- package/typings/generated/nrfutil/device/common.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/device.d.ts +14 -13
- package/typings/generated/nrfutil/device/device.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/deviceInfo.d.ts +40 -0
- package/typings/generated/nrfutil/device/deviceInfo.d.ts.map +1 -0
- package/typings/generated/nrfutil/device/erase.d.ts +2 -2
- package/typings/generated/nrfutil/device/erase.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/firmwareRead.d.ts +2 -2
- package/typings/generated/nrfutil/device/firmwareRead.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/getCoreInfo.d.ts +2 -2
- package/typings/generated/nrfutil/device/getCoreInfo.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/getFwInfo.d.ts +2 -2
- package/typings/generated/nrfutil/device/getFwInfo.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/getProtectionStatus.d.ts +2 -2
- package/typings/generated/nrfutil/device/getProtectionStatus.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/list.d.ts +3 -3
- package/typings/generated/nrfutil/device/list.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/program.d.ts +2 -2
- package/typings/generated/nrfutil/device/program.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/recover.d.ts +2 -2
- package/typings/generated/nrfutil/device/recover.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/reset.d.ts +2 -2
- package/typings/generated/nrfutil/device/reset.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/setMcuState.d.ts +2 -2
- package/typings/generated/nrfutil/device/setMcuState.d.ts.map +1 -1
- package/typings/generated/nrfutil/device/setProtectionStatus.d.ts +2 -2
- package/typings/generated/nrfutil/device/setProtectionStatus.d.ts.map +1 -1
- package/typings/generated/nrfutil/index.d.ts +2 -1
- package/typings/generated/nrfutil/index.d.ts.map +1 -1
- package/typings/generated/nrfutil/moduleVersion.d.ts +4 -0
- package/typings/generated/nrfutil/moduleVersion.d.ts.map +1 -1
- package/typings/generated/nrfutil/sandbox.d.ts +2 -2
- package/typings/generated/nrfutil/sandbox.d.ts.map +1 -1
- package/typings/generated/nrfutil/sandboxTypes.d.ts +10 -1
- package/typings/generated/nrfutil/sandboxTypes.d.ts.map +1 -1
- package/typings/generated/src/About/ApplicationCard.d.ts.map +1 -1
- package/typings/generated/src/About/DeviceCard.d.ts.map +1 -1
- package/typings/generated/src/App/App.d.ts +0 -1
- package/typings/generated/src/App/App.d.ts.map +1 -1
- package/typings/generated/src/Device/DeviceSelector/BasicDeviceInfo.d.ts.map +1 -1
- package/typings/generated/src/Device/DeviceSelector/DeviceList/Device.d.ts +0 -1
- package/typings/generated/src/Device/DeviceSelector/DeviceList/Device.d.ts.map +1 -1
- package/typings/generated/src/Device/DeviceSelector/DeviceList/DeviceList.d.ts.map +1 -1
- package/typings/generated/src/Device/DeviceSelector/DeviceList/EditDeviceButtons.d.ts.map +1 -1
- package/typings/generated/src/Device/DeviceSelector/DeviceList/MoreDeviceInfo.d.ts +0 -1
- package/typings/generated/src/Device/DeviceSelector/DeviceList/MoreDeviceInfo.d.ts.map +1 -1
- package/typings/generated/src/Device/DeviceSelector/DeviceSelector.d.ts.map +1 -1
- package/typings/generated/src/Device/DeviceSelector/Favorite.d.ts +0 -1
- package/typings/generated/src/Device/DeviceSelector/Favorite.d.ts.map +1 -1
- package/typings/generated/src/Device/deviceLister.d.ts +1 -15
- package/typings/generated/src/Device/deviceLister.d.ts.map +1 -1
- package/typings/generated/src/Device/deviceSetup.d.ts +7 -6
- package/typings/generated/src/Device/deviceSetup.d.ts.map +1 -1
- package/typings/generated/src/Device/deviceSlice.d.ts +16 -15
- package/typings/generated/src/Device/deviceSlice.d.ts.map +1 -1
- package/typings/generated/src/Device/jprogOperations.d.ts.map +1 -1
- package/typings/generated/src/Device/sdfuOperations.d.ts.map +1 -1
- package/typings/generated/src/ErrorBoundary/ErrorBoundary.d.ts.map +1 -1
- package/typings/generated/src/Feedback/sendFeedback.d.ts.map +1 -1
- package/typings/generated/src/InlineInput/NumberInlineInput.d.ts +1 -1
- package/typings/generated/src/InlineInput/NumberInlineInput.d.ts.map +1 -1
- package/typings/generated/src/InlineInput/NumberInputWithDropdown.d.ts.map +1 -1
- package/typings/generated/src/index.d.ts +3 -1
- package/typings/generated/src/index.d.ts.map +1 -1
- package/typings/generated/src/logging/sendInitialLogMessages.d.ts.map +1 -1
- package/typings/generated/src/utils/appDetails.d.ts +4 -0
- package/typings/generated/src/utils/appDetails.d.ts.map +1 -0
- package/typings/generated/src/utils/appDirs.d.ts +1 -1
- package/typings/generated/src/utils/appDirs.d.ts.map +1 -1
- package/typings/generated/src/utils/launcherConfig.d.ts +4 -0
- package/typings/generated/src/utils/launcherConfig.d.ts.map +1 -0
- package/typings/generated/src/utils/packageJson.d.ts +30 -7
- package/typings/generated/src/utils/packageJson.d.ts.map +1 -1
- package/typings/generated/src/utils/persistentStore.d.ts +3 -2
- package/typings/generated/src/utils/persistentStore.d.ts.map +1 -1
- package/typings/generated/src/utils/systemReport.d.ts +1 -1
- package/typings/generated/src/utils/systemReport.d.ts.map +1 -1
- package/typings/generated/src/utils/usageData.d.ts +8 -65
- package/typings/generated/src/utils/usageData.d.ts.map +1 -1
- package/typings/generated/src/utils/usageDataCommon.d.ts +27 -0
- package/typings/generated/src/utils/usageDataCommon.d.ts.map +1 -0
- package/typings/generated/src/utils/usageDataMain.d.ts +10 -0
- package/typings/generated/src/utils/usageDataMain.d.ts.map +1 -0
- package/typings/generated/src/utils/usageDataRenderer.d.ts +10 -0
- package/typings/generated/src/utils/usageDataRenderer.d.ts.map +1 -0
- package/src/Device/DeviceSelector/DeviceList/device.scss +0 -28
- package/src/Device/DeviceSelector/DeviceList/more-device-info.scss +0 -33
- package/src/Device/DeviceSelector/favorite.scss +0 -17
|
@@ -4,10 +4,14 @@
|
|
|
4
4
|
* SPDX-License-Identifier: LicenseRef-Nordic-4-Clause
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
|
-
import React, { useCallback, useEffect, useState } from 'react';
|
|
7
|
+
import React, { useCallback, useEffect, useRef, useState } from 'react';
|
|
8
8
|
import { useDispatch, useSelector } from 'react-redux';
|
|
9
9
|
|
|
10
|
+
import { NrfutilDeviceLib } from '../../../nrfutil';
|
|
10
11
|
import { DeviceTraits } from '../../../nrfutil/device/common';
|
|
12
|
+
import logger from '../../logging';
|
|
13
|
+
import usageData from '../../utils/usageData';
|
|
14
|
+
import { simplifyDeviceForLogging } from '../../utils/usageDataCommon';
|
|
11
15
|
import useHotKey from '../../utils/useHotKey';
|
|
12
16
|
import {
|
|
13
17
|
clearWaitForDevice,
|
|
@@ -21,8 +25,10 @@ import {
|
|
|
21
25
|
deselectDevice,
|
|
22
26
|
Device,
|
|
23
27
|
deviceIsSelected as deviceIsSelectedSelector,
|
|
28
|
+
isDeviceWithSerialNumber,
|
|
24
29
|
selectDevice,
|
|
25
|
-
|
|
30
|
+
selectedDevice,
|
|
31
|
+
setSelectedDeviceInfo,
|
|
26
32
|
} from '../deviceSlice';
|
|
27
33
|
import DeviceList from './DeviceList/DeviceList';
|
|
28
34
|
import SelectDevice from './SelectDevice';
|
|
@@ -54,36 +60,73 @@ export default ({
|
|
|
54
60
|
const [deviceListVisible, setDeviceListVisible] = useState(false);
|
|
55
61
|
|
|
56
62
|
const deviceIsSelected = useSelector(deviceIsSelectedSelector);
|
|
57
|
-
const
|
|
63
|
+
const currentDevice = useSelector(selectedDevice);
|
|
58
64
|
const waitingToAutoReconnect = useSelector(getWaitingToAutoReselect);
|
|
59
65
|
const showSelectedDevice = deviceIsSelected || waitingToAutoReconnect;
|
|
60
66
|
|
|
61
|
-
const doDeselectDevice = useCallback(
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
+
const doDeselectDevice = useCallback(
|
|
68
|
+
(device?: Device) => {
|
|
69
|
+
if (device) {
|
|
70
|
+
usageData.sendUsageData(
|
|
71
|
+
'device deselected ',
|
|
72
|
+
simplifyDeviceForLogging(device)
|
|
73
|
+
);
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
dispatch(clearWaitForDevice());
|
|
77
|
+
dispatch(setAutoSelectDevice(undefined));
|
|
78
|
+
onDeviceDeselected();
|
|
79
|
+
dispatch(deselectDevice());
|
|
80
|
+
},
|
|
81
|
+
[dispatch, onDeviceDeselected]
|
|
82
|
+
);
|
|
83
|
+
|
|
84
|
+
const abortController = useRef<AbortController>();
|
|
67
85
|
|
|
68
86
|
// Ensure that useCallback is
|
|
69
87
|
// not updated frequently as this
|
|
70
88
|
// will have a side effect to stop and start the hotplug events
|
|
71
89
|
const doSelectDevice = useCallback(
|
|
72
|
-
(device: Device, autoReselected: boolean) => {
|
|
90
|
+
async (device: Device, autoReselected: boolean) => {
|
|
73
91
|
dispatch(clearWaitForDevice());
|
|
74
92
|
setDeviceListVisible(false);
|
|
75
93
|
dispatch(selectDevice(device));
|
|
76
94
|
dispatch(setAutoSelectDevice(device));
|
|
77
95
|
onDeviceSelected(device, autoReselected);
|
|
96
|
+
|
|
97
|
+
abortController.current?.abort();
|
|
98
|
+
abortController.current = new AbortController();
|
|
99
|
+
const deviceInfo = await NrfutilDeviceLib.deviceInfo(
|
|
100
|
+
device,
|
|
101
|
+
undefined,
|
|
102
|
+
undefined,
|
|
103
|
+
abortController.current
|
|
104
|
+
);
|
|
105
|
+
abortController.current = undefined;
|
|
106
|
+
setSelectedDeviceInfo(deviceInfo);
|
|
107
|
+
|
|
108
|
+
usageData.sendUsageData('device selected', {
|
|
109
|
+
device: simplifyDeviceForLogging(device),
|
|
110
|
+
deviceInfo,
|
|
111
|
+
});
|
|
112
|
+
|
|
78
113
|
if (deviceSetupConfig) {
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
114
|
+
if (isDeviceWithSerialNumber(device)) {
|
|
115
|
+
dispatch(
|
|
116
|
+
setupDevice(
|
|
117
|
+
device,
|
|
118
|
+
deviceSetupConfig,
|
|
119
|
+
onDeviceIsReady,
|
|
120
|
+
doDeselectDevice,
|
|
121
|
+
deviceInfo
|
|
122
|
+
)
|
|
123
|
+
);
|
|
124
|
+
} else {
|
|
125
|
+
logger.warn(
|
|
126
|
+
`Selected device has no serial number. Device setup is not supported`
|
|
127
|
+
);
|
|
128
|
+
onDeviceIsReady(device);
|
|
129
|
+
}
|
|
87
130
|
}
|
|
88
131
|
},
|
|
89
132
|
[
|
|
@@ -133,7 +176,7 @@ export default ({
|
|
|
133
176
|
<div className="core19-device-selector">
|
|
134
177
|
{showSelectedDevice ? (
|
|
135
178
|
<SelectedDevice
|
|
136
|
-
doDeselectDevice={doDeselectDevice}
|
|
179
|
+
doDeselectDevice={() => doDeselectDevice(currentDevice)}
|
|
137
180
|
toggleDeviceListVisible={toggleDeviceListVisible}
|
|
138
181
|
/>
|
|
139
182
|
) : (
|
|
@@ -145,13 +188,13 @@ export default ({
|
|
|
145
188
|
<DeviceList
|
|
146
189
|
isVisible={deviceListVisible}
|
|
147
190
|
doSelectDevice={(device, autoReselected) => {
|
|
148
|
-
if (device.
|
|
191
|
+
if (device.id === currentDevice?.id) {
|
|
149
192
|
setDeviceListVisible(false);
|
|
150
193
|
return;
|
|
151
194
|
}
|
|
152
195
|
|
|
153
196
|
if (deviceIsSelected) {
|
|
154
|
-
doDeselectDevice();
|
|
197
|
+
doDeselectDevice(currentDevice);
|
|
155
198
|
}
|
|
156
199
|
|
|
157
200
|
doSelectDevice(device, autoReselected);
|
|
@@ -8,19 +8,18 @@ import React, { FC } from 'react';
|
|
|
8
8
|
import { useDispatch } from 'react-redux';
|
|
9
9
|
|
|
10
10
|
import PseudoButton from '../../PseudoButton/PseudoButton';
|
|
11
|
+
import classNames from '../../utils/classNames';
|
|
11
12
|
import { Device, toggleDeviceFavorited } from '../deviceSlice';
|
|
12
13
|
|
|
13
|
-
import './favorite.scss';
|
|
14
|
-
|
|
15
14
|
export const MakeDeviceFavorite: FC<{ device: Device }> = ({ device }) => {
|
|
16
15
|
const dispatch = useDispatch();
|
|
17
16
|
|
|
18
17
|
const toggleFavorite = () => {
|
|
19
|
-
dispatch(toggleDeviceFavorited(device
|
|
18
|
+
dispatch(toggleDeviceFavorited(device));
|
|
20
19
|
};
|
|
21
20
|
|
|
22
21
|
return (
|
|
23
|
-
<PseudoButton className="
|
|
22
|
+
<PseudoButton className="tw-mr-[1ex]" onClick={toggleFavorite}>
|
|
24
23
|
<span
|
|
25
24
|
className={`mdi star ${
|
|
26
25
|
device.favorite ? 'mdi-star-off' : 'mdi-star'
|
|
@@ -35,15 +34,16 @@ export const FavoriteIndicator: FC<{ device: Device }> = ({ device }) => {
|
|
|
35
34
|
const dispatch = useDispatch();
|
|
36
35
|
|
|
37
36
|
const toggleFavorite = () => {
|
|
38
|
-
dispatch(toggleDeviceFavorited(device
|
|
37
|
+
dispatch(toggleDeviceFavorited(device));
|
|
39
38
|
};
|
|
40
39
|
|
|
41
|
-
return (
|
|
40
|
+
return device.serialNumber ? (
|
|
42
41
|
<PseudoButton
|
|
43
|
-
className={
|
|
44
|
-
device.favorite
|
|
45
|
-
|
|
42
|
+
className={classNames(
|
|
43
|
+
!device.favorite && 'tw-invisible group-hover:tw-visible',
|
|
44
|
+
`mdi ${device.favorite ? 'mdi-star' : 'mdi-star-outline'}`
|
|
45
|
+
)}
|
|
46
46
|
onClick={toggleFavorite}
|
|
47
47
|
/>
|
|
48
|
-
);
|
|
48
|
+
) : null;
|
|
49
49
|
};
|
|
@@ -16,9 +16,6 @@
|
|
|
16
16
|
.details {
|
|
17
17
|
width: inherit;
|
|
18
18
|
|
|
19
|
-
display: flex;
|
|
20
|
-
flex-direction: column;
|
|
21
|
-
|
|
22
19
|
line-height: 1;
|
|
23
20
|
|
|
24
21
|
.name {
|
|
@@ -49,14 +46,5 @@
|
|
|
49
46
|
text-overflow: ellipsis;
|
|
50
47
|
}
|
|
51
48
|
}
|
|
52
|
-
|
|
53
|
-
.toggles {
|
|
54
|
-
display: flex;
|
|
55
|
-
flex-direction: column;
|
|
56
|
-
align-items: center;
|
|
57
|
-
|
|
58
|
-
width: 44px;
|
|
59
|
-
margin-right: 10px;
|
|
60
|
-
}
|
|
61
49
|
}
|
|
62
50
|
}
|
|
@@ -199,7 +199,7 @@ const devicesByPca: { [P in KnownDevicePCA]: DeviceInfo } = {
|
|
|
199
199
|
|
|
200
200
|
const deviceByPca = (device: Device) =>
|
|
201
201
|
devicesByPca[
|
|
202
|
-
String(device.
|
|
202
|
+
String(device.devkit?.boardVersion).toUpperCase() as KnownDevicePCA
|
|
203
203
|
];
|
|
204
204
|
|
|
205
205
|
const NORDIC_VENDOR_ID = '1915';
|
|
@@ -252,7 +252,7 @@ export const displayedDeviceName = (
|
|
|
252
252
|
return device.nickname;
|
|
253
253
|
}
|
|
254
254
|
|
|
255
|
-
return deviceInfo(device).name || device.
|
|
255
|
+
return deviceInfo(device).name || device.devkit?.boardVersion || 'Unknown';
|
|
256
256
|
};
|
|
257
257
|
|
|
258
258
|
export const productPageUrl = (device: Device) =>
|
|
@@ -4,14 +4,12 @@
|
|
|
4
4
|
* SPDX-License-Identifier: LicenseRef-Nordic-4-Clause
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
|
-
import {
|
|
8
|
-
DeviceTraits,
|
|
9
|
-
NrfutilDevice,
|
|
10
|
-
NrfutilDeviceWithSerialnumber,
|
|
11
|
-
} from '../../nrfutil/device/common';
|
|
7
|
+
import { DeviceTraits, NrfutilDevice } from '../../nrfutil/device/common';
|
|
12
8
|
import NrfutilDeviceLib from '../../nrfutil/device/device';
|
|
13
9
|
import logger from '../logging';
|
|
14
10
|
import type { AppThunk, RootState } from '../store';
|
|
11
|
+
import usageData from '../utils/usageData';
|
|
12
|
+
import { simplifyDeviceForLogging } from '../utils/usageDataCommon';
|
|
15
13
|
import {
|
|
16
14
|
clearWaitForDevice,
|
|
17
15
|
clearWaitForDeviceTimeout,
|
|
@@ -23,7 +21,13 @@ import {
|
|
|
23
21
|
WaitForDevice,
|
|
24
22
|
} from './deviceAutoSelectSlice';
|
|
25
23
|
import { closeDeviceSetupDialog } from './deviceSetupSlice';
|
|
26
|
-
import {
|
|
24
|
+
import {
|
|
25
|
+
addDevice,
|
|
26
|
+
Device,
|
|
27
|
+
removeDevice,
|
|
28
|
+
selectDevice,
|
|
29
|
+
setSelectedDeviceInfo,
|
|
30
|
+
} from './deviceSlice';
|
|
27
31
|
import { isDeviceInDFUBootloader } from './sdfuOperations';
|
|
28
32
|
|
|
29
33
|
let stopNrfutilDevice: (callback?: () => void) => void;
|
|
@@ -52,6 +56,11 @@ const shouldAutoReselect = (
|
|
|
52
56
|
// device is still connected
|
|
53
57
|
if (disconnectionTime === undefined) return false;
|
|
54
58
|
|
|
59
|
+
// device does not have sn
|
|
60
|
+
if (!addedDevice.serialNumber) {
|
|
61
|
+
return false;
|
|
62
|
+
}
|
|
63
|
+
|
|
55
64
|
// The device that was selected when disconnection occurred is not yet connected
|
|
56
65
|
if (addedDevice.serialNumber !== autoReselectDevice.serialNumber) {
|
|
57
66
|
return false;
|
|
@@ -100,28 +109,6 @@ const initAutoReconnectTimeout =
|
|
|
100
109
|
);
|
|
101
110
|
};
|
|
102
111
|
|
|
103
|
-
/**
|
|
104
|
-
* Wrap the device form nrfutil-device to make the Device type consistent
|
|
105
|
-
*
|
|
106
|
-
* @param {NrfutilDevice} device The input device from nrfutil-device
|
|
107
|
-
* @returns {NrfutilDevice} The updated device
|
|
108
|
-
*/
|
|
109
|
-
export const wrapDeviceFromNrfdl = (device: NrfutilDevice): Device => ({
|
|
110
|
-
...device,
|
|
111
|
-
boardVersion: device.jlink?.boardVersion ?? undefined,
|
|
112
|
-
serialport: device.serialPorts?.[0] ?? undefined,
|
|
113
|
-
serialNumber: device.serialNumber ?? `fallback-serialnumber-${device.id}`,
|
|
114
|
-
});
|
|
115
|
-
|
|
116
|
-
/**
|
|
117
|
-
* Wrap the device form nrfutil-device to make the Device type consistent
|
|
118
|
-
*
|
|
119
|
-
* @param {NrfutilDevice[]} devices The input devices from nrfutil-device
|
|
120
|
-
* @returns {NrfutilDevice[]} The updated devices
|
|
121
|
-
*/
|
|
122
|
-
export const wrapDevicesFromNrfdl = (devices: NrfutilDevice[]): Device[] =>
|
|
123
|
-
devices.map(wrapDeviceFromNrfdl);
|
|
124
|
-
|
|
125
112
|
export const hasValidDeviceTraits = (
|
|
126
113
|
deviceTraits: DeviceTraits,
|
|
127
114
|
requiredTraits: DeviceTraits
|
|
@@ -144,7 +131,7 @@ const removeDeviceFromList =
|
|
|
144
131
|
(dispatch, getState) => {
|
|
145
132
|
if (
|
|
146
133
|
removedDevice.serialNumber !==
|
|
147
|
-
getState().device.
|
|
134
|
+
getState().device.selectedDevice?.serialNumber
|
|
148
135
|
) {
|
|
149
136
|
dispatch(removeDevice(removedDevice));
|
|
150
137
|
onDeviceDisconnected(removedDevice);
|
|
@@ -176,22 +163,27 @@ export const startWatchingDevices =
|
|
|
176
163
|
doSelectDevice: (device: Device, autoReselected: boolean) => void
|
|
177
164
|
): AppThunk<RootState, void> =>
|
|
178
165
|
(dispatch, getState) => {
|
|
179
|
-
const onDeviceArrived = (device:
|
|
166
|
+
const onDeviceArrived = async (device: NrfutilDevice) => {
|
|
180
167
|
if (hasValidDeviceTraits(device.traits, deviceListing)) {
|
|
181
|
-
|
|
168
|
+
usageData.sendUsageData(
|
|
169
|
+
'device connected',
|
|
170
|
+
simplifyDeviceForLogging(device)
|
|
171
|
+
);
|
|
182
172
|
if (
|
|
183
|
-
device.
|
|
184
|
-
|
|
173
|
+
!getState().device.devices.find(
|
|
174
|
+
d =>
|
|
175
|
+
d.id === device.id ||
|
|
176
|
+
(device.serialNumber && // we want to disregard comparing devices with no sn
|
|
177
|
+
d.serialNumber === device.serialNumber)
|
|
178
|
+
)
|
|
185
179
|
) {
|
|
186
180
|
onDeviceConnected(device);
|
|
187
181
|
}
|
|
188
182
|
|
|
189
|
-
const sn = getState().device.selectedSerialNumber;
|
|
190
183
|
const disconnectionTime =
|
|
191
184
|
getState().deviceAutoSelect.disconnectionTime;
|
|
192
185
|
const autoSelectDevice = getState().deviceAutoSelect.device;
|
|
193
|
-
const selectedDevice =
|
|
194
|
-
sn !== null ? getState().device.devices.get(sn) : undefined;
|
|
186
|
+
const selectedDevice = getState().device.selectedDevice;
|
|
195
187
|
|
|
196
188
|
const result = shouldAutoReselect(
|
|
197
189
|
device,
|
|
@@ -202,17 +194,32 @@ export const startWatchingDevices =
|
|
|
202
194
|
);
|
|
203
195
|
|
|
204
196
|
dispatch(addDevice(device));
|
|
205
|
-
const deviceWithPersistedData = getState().device.devices.
|
|
206
|
-
device.serialNumber
|
|
197
|
+
const deviceWithPersistedData = getState().device.devices.find(
|
|
198
|
+
d => d.serialNumber === device.serialNumber
|
|
207
199
|
);
|
|
208
200
|
|
|
209
201
|
if (!deviceWithPersistedData) return;
|
|
210
202
|
|
|
211
|
-
|
|
203
|
+
// We might get multiple events with the same info so no to trigger auto reconnect multiple times we
|
|
204
|
+
// only do it once per device id
|
|
205
|
+
if (
|
|
206
|
+
result &&
|
|
207
|
+
getState().deviceAutoSelect.lastArrivedDeviceId !==
|
|
208
|
+
deviceWithPersistedData.id
|
|
209
|
+
) {
|
|
210
|
+
dispatch(
|
|
211
|
+
setLastArrivedDeviceId(deviceWithPersistedData.id)
|
|
212
|
+
);
|
|
213
|
+
|
|
214
|
+
const deviceInfo = await NrfutilDeviceLib.deviceInfo(
|
|
215
|
+
device
|
|
216
|
+
);
|
|
217
|
+
|
|
212
218
|
logger.info(
|
|
213
219
|
`Auto Reconnecting Device SN: ${deviceWithPersistedData.serialNumber}`
|
|
214
220
|
);
|
|
215
221
|
doSelectDevice(deviceWithPersistedData, true);
|
|
222
|
+
dispatch(setSelectedDeviceInfo(deviceInfo));
|
|
216
223
|
} else if (
|
|
217
224
|
deviceWithPersistedData.serialNumber ===
|
|
218
225
|
getState().deviceAutoSelect.device?.serialNumber
|
|
@@ -220,6 +227,10 @@ export const startWatchingDevices =
|
|
|
220
227
|
const waitForDevice =
|
|
221
228
|
getState().deviceAutoSelect.waitForDevice;
|
|
222
229
|
|
|
230
|
+
const deviceInfo = await NrfutilDeviceLib.deviceInfo(
|
|
231
|
+
device
|
|
232
|
+
);
|
|
233
|
+
|
|
223
234
|
// Device lib might fail to advertise that a device has left before it rejoins (Mainly OSx)
|
|
224
235
|
// but we still need to trigger the onSuccess if a device 'reappeared' with a different 'id'
|
|
225
236
|
// and there is an outstanding waitForDevice Request. In this case the disconnectionTime was
|
|
@@ -245,8 +256,7 @@ export const startWatchingDevices =
|
|
|
245
256
|
deviceWithPersistedData
|
|
246
257
|
)) ||
|
|
247
258
|
(waitForDevice.when === 'applicationMode' &&
|
|
248
|
-
|
|
249
|
-
null) ||
|
|
259
|
+
deviceInfo?.dfuTriggerVersion) ||
|
|
250
260
|
(selectedDevice &&
|
|
251
261
|
waitForDevice.when === 'sameTraits' &&
|
|
252
262
|
hasSameDeviceTraits(
|
|
@@ -269,6 +279,9 @@ export const startWatchingDevices =
|
|
|
269
279
|
clearWaitForDeviceTimeout(waitForDevice.once)
|
|
270
280
|
);
|
|
271
281
|
|
|
282
|
+
dispatch(selectDevice(deviceWithPersistedData));
|
|
283
|
+
dispatch(setSelectedDeviceInfo(deviceInfo));
|
|
284
|
+
|
|
272
285
|
if (waitForDevice.onSuccess)
|
|
273
286
|
waitForDevice.onSuccess(
|
|
274
287
|
deviceWithPersistedData
|
|
@@ -288,8 +301,9 @@ export const startWatchingDevices =
|
|
|
288
301
|
const waitForDevice =
|
|
289
302
|
getState().deviceAutoSelect.waitForDevice;
|
|
290
303
|
if (
|
|
304
|
+
device.serialNumber && // we want to disregard comparing devices with no sn
|
|
291
305
|
device.serialNumber ===
|
|
292
|
-
|
|
306
|
+
getState().deviceAutoSelect.device?.serialNumber
|
|
293
307
|
) {
|
|
294
308
|
if (waitForDevice) {
|
|
295
309
|
dispatch(setArrivedButWrongWhen(undefined));
|
|
@@ -334,7 +348,10 @@ export const startWatchingDevices =
|
|
|
334
348
|
stopWatchingDevices(async () => {
|
|
335
349
|
const operation = await NrfutilDeviceLib.list(
|
|
336
350
|
deviceListing,
|
|
337
|
-
d =>
|
|
351
|
+
d => {
|
|
352
|
+
d.forEach(onDeviceArrived);
|
|
353
|
+
dispatch(autoSelectDeviceCLI(doSelectDevice));
|
|
354
|
+
},
|
|
338
355
|
error => {
|
|
339
356
|
logger.error(error);
|
|
340
357
|
},
|
|
@@ -346,28 +363,63 @@ export const startWatchingDevices =
|
|
|
346
363
|
callback?.();
|
|
347
364
|
});
|
|
348
365
|
};
|
|
349
|
-
|
|
350
|
-
if (!autoSelectDeviceCLISerialUsed) {
|
|
351
|
-
const autoSelectSN = getAutoSelectDeviceCLISerial();
|
|
352
|
-
|
|
353
|
-
if (autoSelectSN !== undefined) {
|
|
354
|
-
const autoSelectDevice =
|
|
355
|
-
getState().device.devices.get(autoSelectSN);
|
|
356
|
-
|
|
357
|
-
if (autoSelectDevice)
|
|
358
|
-
doSelectDevice(autoSelectDevice, true);
|
|
359
|
-
}
|
|
360
|
-
autoSelectDeviceCLISerialUsed = true;
|
|
361
|
-
}
|
|
362
366
|
});
|
|
363
367
|
};
|
|
364
368
|
|
|
365
|
-
const
|
|
369
|
+
const getAutoSelectDeviceCLIProperty = (
|
|
370
|
+
property: string,
|
|
371
|
+
findDevice: (value: string) => Device | undefined
|
|
372
|
+
) => {
|
|
366
373
|
const { argv } = process;
|
|
367
|
-
const
|
|
368
|
-
return
|
|
374
|
+
const index = argv.findIndex(arg => arg === property);
|
|
375
|
+
return index > -1
|
|
376
|
+
? { index, device: findDevice(argv[index + 1]) }
|
|
377
|
+
: undefined;
|
|
369
378
|
};
|
|
370
379
|
|
|
380
|
+
const getAutoSelectDevice = (devices: Device[]) => {
|
|
381
|
+
const serialNumber = getAutoSelectDeviceCLIProperty('--deviceSerial', sn =>
|
|
382
|
+
devices.find(device => device.serialNumber === sn)
|
|
383
|
+
);
|
|
384
|
+
const serialPort = getAutoSelectDeviceCLIProperty('--comPort', portPath =>
|
|
385
|
+
devices.find(device =>
|
|
386
|
+
device.serialPorts?.find(port => port.comName === portPath)
|
|
387
|
+
)
|
|
388
|
+
);
|
|
389
|
+
|
|
390
|
+
if (serialNumber && serialPort) {
|
|
391
|
+
if (serialNumber.index > serialPort.index) {
|
|
392
|
+
return serialPort.device;
|
|
393
|
+
}
|
|
394
|
+
|
|
395
|
+
return serialNumber.device;
|
|
396
|
+
}
|
|
397
|
+
|
|
398
|
+
if (serialNumber) {
|
|
399
|
+
return serialNumber.device;
|
|
400
|
+
}
|
|
401
|
+
|
|
402
|
+
if (serialPort) {
|
|
403
|
+
return serialPort.device;
|
|
404
|
+
}
|
|
405
|
+
};
|
|
406
|
+
|
|
407
|
+
const autoSelectDeviceCLI =
|
|
408
|
+
(
|
|
409
|
+
doSelectDevice: (device: Device, autoReselected: boolean) => void
|
|
410
|
+
): AppThunk<RootState> =>
|
|
411
|
+
(_, getState) => {
|
|
412
|
+
if (!autoSelectDeviceCLISerialUsed) {
|
|
413
|
+
const autoSelectDevice = getAutoSelectDevice(
|
|
414
|
+
getState().device.devices
|
|
415
|
+
);
|
|
416
|
+
|
|
417
|
+
if (autoSelectDevice) doSelectDevice(autoSelectDevice, true);
|
|
418
|
+
|
|
419
|
+
autoSelectDeviceCLISerialUsed = true;
|
|
420
|
+
}
|
|
421
|
+
};
|
|
422
|
+
|
|
371
423
|
export const stopWatchingDevices = (callback?: () => void) => {
|
|
372
424
|
if (stopNrfutilDevice) stopNrfutilDevice(callback);
|
|
373
425
|
else callback?.();
|
|
@@ -3,6 +3,7 @@
|
|
|
3
3
|
*
|
|
4
4
|
* SPDX-License-Identifier: LicenseRef-Nordic-4-Clause
|
|
5
5
|
*/
|
|
6
|
+
import { DeviceInfo } from '../../nrfutil/device/deviceInfo';
|
|
6
7
|
import logger from '../logging';
|
|
7
8
|
import describeError from '../logging/describeError';
|
|
8
9
|
import { AppThunk, RootState } from '../store';
|
|
@@ -12,7 +13,7 @@ import {
|
|
|
12
13
|
setDeviceSetupProgress,
|
|
13
14
|
setDeviceSetupProgressMessage,
|
|
14
15
|
} from './deviceSetupSlice';
|
|
15
|
-
import { Device } from './deviceSlice';
|
|
16
|
+
import { Device, DeviceWithSerialNumber } from './deviceSlice';
|
|
16
17
|
import { InitPacket } from './initPacket';
|
|
17
18
|
|
|
18
19
|
export interface DfuEntry {
|
|
@@ -33,15 +34,24 @@ export interface JprogEntry {
|
|
|
33
34
|
}
|
|
34
35
|
|
|
35
36
|
export interface DeviceSetup {
|
|
36
|
-
supportsProgrammingMode: (
|
|
37
|
-
|
|
37
|
+
supportsProgrammingMode: (
|
|
38
|
+
device: Device,
|
|
39
|
+
deviceInfo?: DeviceInfo
|
|
40
|
+
) => boolean; // Return true if this device can be programed using this interface e.g. MCU Boot or DFU
|
|
41
|
+
getFirmwareOptions: (
|
|
42
|
+
device: Device,
|
|
43
|
+
deviceInfo?: DeviceInfo
|
|
44
|
+
) => {
|
|
38
45
|
key: string;
|
|
39
46
|
description?: string;
|
|
40
47
|
programDevice: (
|
|
41
48
|
onProgress: (progress: number, message?: string) => void
|
|
42
49
|
) => AppThunk<RootState, Promise<Device>>;
|
|
43
50
|
}[]; // The list of all firmware that can be applied for this device with the program function for that fw item
|
|
44
|
-
isExpectedFirmware: (
|
|
51
|
+
isExpectedFirmware: (
|
|
52
|
+
device: Device,
|
|
53
|
+
deviceInfo?: DeviceInfo
|
|
54
|
+
) => AppThunk<
|
|
45
55
|
RootState,
|
|
46
56
|
Promise<{
|
|
47
57
|
device: Device;
|
|
@@ -66,6 +76,7 @@ export const prepareDevice =
|
|
|
66
76
|
deviceSetupConfig: DeviceSetupConfig,
|
|
67
77
|
onSuccess: (device: Device) => void,
|
|
68
78
|
onFail: (reason?: unknown) => void,
|
|
79
|
+
deviceInfo: DeviceInfo | undefined,
|
|
69
80
|
checkCurrentFirmwareVersion = true,
|
|
70
81
|
requireUserConfirmation = true
|
|
71
82
|
): AppThunk<RootState, Promise<void>> =>
|
|
@@ -74,18 +85,22 @@ export const prepareDevice =
|
|
|
74
85
|
onSuccess(d);
|
|
75
86
|
dispatch(closeDeviceSetupDialog());
|
|
76
87
|
};
|
|
88
|
+
|
|
77
89
|
const validDeviceSetups = deviceSetupConfig.deviceSetups.filter(
|
|
78
|
-
deviceSetup =>
|
|
90
|
+
deviceSetup =>
|
|
91
|
+
deviceSetup.supportsProgrammingMode(device, deviceInfo)
|
|
79
92
|
);
|
|
80
93
|
|
|
81
94
|
const possibleFirmware = validDeviceSetups
|
|
82
|
-
.map(deviceSetup =>
|
|
95
|
+
.map(deviceSetup =>
|
|
96
|
+
deviceSetup.getFirmwareOptions(device, deviceInfo)
|
|
97
|
+
)
|
|
83
98
|
.flat();
|
|
84
99
|
|
|
85
100
|
if (possibleFirmware.length === 0) {
|
|
86
101
|
logger.info(
|
|
87
102
|
`Connected to device with serial number: ${device.serialNumber} ` +
|
|
88
|
-
`and family: ${device.
|
|
103
|
+
`and family: ${device.devkit?.deviceFamily || 'Unknown'} `
|
|
89
104
|
);
|
|
90
105
|
if (deviceSetupConfig.allowCustomDevice) {
|
|
91
106
|
logger.info(
|
|
@@ -110,7 +125,7 @@ export const prepareDevice =
|
|
|
110
125
|
try {
|
|
111
126
|
// eslint-disable-next-line no-await-in-loop
|
|
112
127
|
const result = await dispatch(
|
|
113
|
-
deviceSetup.isExpectedFirmware(device)
|
|
128
|
+
deviceSetup.isExpectedFirmware(device, deviceInfo)
|
|
114
129
|
);
|
|
115
130
|
device = result.device;
|
|
116
131
|
if (result.validFirmware) {
|
|
@@ -224,10 +239,11 @@ export const prepareDevice =
|
|
|
224
239
|
|
|
225
240
|
export const setupDevice =
|
|
226
241
|
(
|
|
227
|
-
device:
|
|
242
|
+
device: DeviceWithSerialNumber,
|
|
228
243
|
deviceSetupConfig: DeviceSetupConfig,
|
|
229
244
|
onDeviceIsReady: (device: Device) => void,
|
|
230
|
-
doDeselectDevice: () => void
|
|
245
|
+
doDeselectDevice: (device?: Device) => void,
|
|
246
|
+
deviceInfo: DeviceInfo | undefined
|
|
231
247
|
): AppThunk<RootState> =>
|
|
232
248
|
(dispatch, getState) =>
|
|
233
249
|
dispatch(
|
|
@@ -242,7 +258,7 @@ export const setupDevice =
|
|
|
242
258
|
// while that is still in progress select some other device
|
|
243
259
|
// if both were to call onDeviceIsReady the app might have unexpected side effects
|
|
244
260
|
if (
|
|
245
|
-
getState().device.
|
|
261
|
+
getState().device.selectedDevice?.serialNumber ===
|
|
246
262
|
d.serialNumber
|
|
247
263
|
) {
|
|
248
264
|
onDeviceIsReady(d);
|
|
@@ -254,7 +270,8 @@ export const setupDevice =
|
|
|
254
270
|
`Error while setting up device ${device.serialNumber}`
|
|
255
271
|
);
|
|
256
272
|
logger.error(describeError(error));
|
|
257
|
-
doDeselectDevice();
|
|
258
|
-
}
|
|
273
|
+
doDeselectDevice(getState().device.selectedDevice);
|
|
274
|
+
},
|
|
275
|
+
deviceInfo
|
|
259
276
|
)
|
|
260
277
|
);
|