@onekeyfe/hd-core 1.2.0-alpha.66 → 1.2.0-alpha.67

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.
Files changed (315) hide show
  1. package/__tests__/AllNetworkGetAddressBase.tracing.test.ts +0 -313
  2. package/__tests__/DeviceCommands.test.ts +13 -59
  3. package/__tests__/DeviceEventRegistration.test.ts +0 -6
  4. package/__tests__/check-all-firmware-release-protocol-v2.test.ts +3 -198
  5. package/__tests__/connectSettings.test.ts +47 -5
  6. package/__tests__/device-initialize-timeout.test.ts +56 -0
  7. package/__tests__/device-lifecycle-events.test.ts +3 -105
  8. package/__tests__/device-pool-state.test.ts +0 -22
  9. package/__tests__/device-settings.test.ts +18 -39
  10. package/__tests__/device-state-contract.test.ts +0 -1
  11. package/__tests__/device-state-mapper.test.ts +1 -13
  12. package/__tests__/device-utils.test.ts +1 -48
  13. package/__tests__/deviceSettings.test.ts +1 -11
  14. package/__tests__/firmware-update/check-all-firmware-release.test.ts +175 -0
  15. package/__tests__/firmware-update/device-update-bootloader.test.ts +87 -0
  16. package/__tests__/firmware-update/firmware-artifact-source.test.ts +119 -0
  17. package/__tests__/firmware-update/firmware-host-binding.test.ts +70 -0
  18. package/__tests__/firmware-update/firmware-preparation-error.test.ts +27 -0
  19. package/__tests__/firmware-update/firmware-update-bootloader-poll.test.ts +200 -0
  20. package/__tests__/firmware-update/firmware-update-capabilities.test.ts +13 -0
  21. package/__tests__/firmware-update/firmware-update-plan-bootloader-identity.test.ts +394 -0
  22. package/__tests__/firmware-update/firmware-update-plan.test.ts +593 -0
  23. package/__tests__/firmware-update/firmware-update-prepared-plan.test.ts +231 -0
  24. package/__tests__/firmware-update/firmware-update-v2-download-before-boot.test.ts +59 -31
  25. package/__tests__/firmware-update/firmware-update-v3-reconnect.test.ts +58 -0
  26. package/__tests__/firmware-update/firmware-upload-source.test.ts +70 -0
  27. package/__tests__/get-device-state.test.ts +12 -132
  28. package/__tests__/homescreen.test.ts +1 -41
  29. package/__tests__/kaspa-use-tweak-pro2.test.ts +2 -2
  30. package/__tests__/kaspaSignTransaction.test.ts +26 -3
  31. package/__tests__/logBlockEvent.test.ts +1 -1
  32. package/__tests__/method-protocol-support.test.ts +0 -19
  33. package/__tests__/open-wallet-session.test.ts +37 -568
  34. package/__tests__/protocol-v2-unlock-policy.test.ts +37 -300
  35. package/__tests__/protocol-v2.test.ts +1153 -1458
  36. package/__tests__/protocolV2FileWrite.test.ts +0 -152
  37. package/__tests__/protocolV2UiInteraction.test.ts +0 -63
  38. package/__tests__/public-pro2-api-boundary.test.ts +0 -1
  39. package/__tests__/search-devices.test.ts +3 -12
  40. package/__tests__/tron-sign-message-init.test.ts +2 -2
  41. package/dist/api/BaseMethod.d.ts +1 -3
  42. package/dist/api/BaseMethod.d.ts.map +1 -1
  43. package/dist/api/CheckAllFirmwareRelease.d.ts +1 -2
  44. package/dist/api/CheckAllFirmwareRelease.d.ts.map +1 -1
  45. package/dist/api/FirmwareUpdate.d.ts.map +1 -1
  46. package/dist/api/FirmwareUpdateV2.d.ts +10 -0
  47. package/dist/api/FirmwareUpdateV2.d.ts.map +1 -1
  48. package/dist/api/FirmwareUpdateV3.d.ts +7 -3
  49. package/dist/api/FirmwareUpdateV3.d.ts.map +1 -1
  50. package/dist/api/FirmwareUpdateV4.d.ts +27 -13
  51. package/dist/api/FirmwareUpdateV4.d.ts.map +1 -1
  52. package/dist/api/GetPassphraseState.d.ts.map +1 -1
  53. package/dist/api/OpenWalletSession.d.ts.map +1 -1
  54. package/dist/api/SearchDevices.d.ts.map +1 -1
  55. package/dist/api/allnetwork/AllNetworkGetAddressBase.d.ts.map +1 -1
  56. package/dist/api/device/DeviceSettings.d.ts.map +1 -1
  57. package/dist/api/device/DeviceUnlock.d.ts +2 -2
  58. package/dist/api/device/DeviceUnlock.d.ts.map +1 -1
  59. package/dist/api/device/DeviceUpdateBootloader.d.ts +5 -1
  60. package/dist/api/device/DeviceUpdateBootloader.d.ts.map +1 -1
  61. package/dist/api/firmware/FirmwareArtifactSource.d.ts +25 -0
  62. package/dist/api/firmware/FirmwareArtifactSource.d.ts.map +1 -0
  63. package/dist/api/firmware/FirmwareHostBinding.d.ts +6 -0
  64. package/dist/api/firmware/FirmwareHostBinding.d.ts.map +1 -0
  65. package/dist/api/firmware/FirmwarePreparationError.d.ts +3 -0
  66. package/dist/api/firmware/FirmwarePreparationError.d.ts.map +1 -0
  67. package/dist/api/firmware/FirmwareUpdateBaseMethod.d.ts +11 -4
  68. package/dist/api/firmware/FirmwareUpdateBaseMethod.d.ts.map +1 -1
  69. package/dist/api/firmware/FirmwareUpdateCapabilities.d.ts +3 -0
  70. package/dist/api/firmware/FirmwareUpdateCapabilities.d.ts.map +1 -0
  71. package/dist/api/firmware/FirmwareUpdatePlan.d.ts +25 -0
  72. package/dist/api/firmware/FirmwareUpdatePlan.d.ts.map +1 -0
  73. package/dist/api/firmware/FirmwareUpdatePreparedPlan.d.ts +32 -0
  74. package/dist/api/firmware/FirmwareUpdatePreparedPlan.d.ts.map +1 -0
  75. package/dist/api/firmware/getBinary.d.ts +7 -0
  76. package/dist/api/firmware/getBinary.d.ts.map +1 -1
  77. package/dist/api/firmware/progressThrottle.d.ts +3 -0
  78. package/dist/api/firmware/progressThrottle.d.ts.map +1 -0
  79. package/dist/api/firmware/updateBootloader.d.ts +2 -0
  80. package/dist/api/firmware/updateBootloader.d.ts.map +1 -1
  81. package/dist/api/firmware/uploadFirmware.d.ts +9 -1
  82. package/dist/api/firmware/uploadFirmware.d.ts.map +1 -1
  83. package/dist/api/helpers/protocolV2FileWrite.d.ts +0 -9
  84. package/dist/api/helpers/protocolV2FileWrite.d.ts.map +1 -1
  85. package/dist/api/index.d.ts +0 -2
  86. package/dist/api/index.d.ts.map +1 -1
  87. package/dist/api/kaspa/KaspaGetAddress.d.ts +1 -1
  88. package/dist/api/kaspa/KaspaSignTransaction.d.ts +1 -1
  89. package/dist/api/kaspa/KaspaSignTransaction.d.ts.map +1 -1
  90. package/dist/api/polkadot/PolkadotGetAddress.d.ts +1 -1
  91. package/dist/api/polkadot/networks.d.ts +1 -1
  92. package/dist/api/protocol-v2/ProtocolInfoRequest.d.ts.map +1 -1
  93. package/dist/api/protocol-v2/helpers.d.ts.map +1 -1
  94. package/dist/api/solana/SolSignMessage.d.ts +1 -1
  95. package/dist/api/solana/SolSignOffchainMessage.d.ts +1 -1
  96. package/dist/api/solana/SolSignTransaction.d.ts +2 -2
  97. package/dist/api/stellar/StellarSignTransaction.d.ts +1 -1
  98. package/dist/api/sui/SuiGetAddress.d.ts +1 -1
  99. package/dist/api/sui/SuiGetPublicKey.d.ts +1 -1
  100. package/dist/api/sui/SuiSignMessage.d.ts +1 -1
  101. package/dist/api/sui/SuiSignTransaction.d.ts +1 -1
  102. package/dist/api/ton/TonGetAddress.d.ts +1 -1
  103. package/dist/api/ton/TonSignMessage.d.ts +1 -1
  104. package/dist/api/ton/TonSignProof.d.ts +1 -1
  105. package/dist/api/tron/TronSignMessage.d.ts +2 -2
  106. package/dist/api/tron/TronSignTransaction.d.ts +1 -1
  107. package/dist/core/deviceEventRegistration.d.ts +0 -2
  108. package/dist/core/deviceEventRegistration.d.ts.map +1 -1
  109. package/dist/core/index.d.ts.map +1 -1
  110. package/dist/data-manager/DataManager.d.ts +4 -9
  111. package/dist/data-manager/DataManager.d.ts.map +1 -1
  112. package/dist/data-manager/TransportManager.d.ts.map +1 -1
  113. package/dist/data-manager/connectSettings.d.ts.map +1 -1
  114. package/dist/device/Device.d.ts +6 -29
  115. package/dist/device/Device.d.ts.map +1 -1
  116. package/dist/device/DeviceCommands.d.ts +4 -4
  117. package/dist/device/DeviceCommands.d.ts.map +1 -1
  118. package/dist/device/DeviceConnector.d.ts +1 -2
  119. package/dist/device/DeviceConnector.d.ts.map +1 -1
  120. package/dist/device/DevicePool.d.ts.map +1 -1
  121. package/dist/deviceProfile/protocolV2DeviceIdentity.d.ts.map +1 -1
  122. package/dist/events/device.d.ts +0 -4
  123. package/dist/events/device.d.ts.map +1 -1
  124. package/dist/events/logBlockEvent.d.ts.map +1 -1
  125. package/dist/events/ui-promise.d.ts +2 -4
  126. package/dist/events/ui-promise.d.ts.map +1 -1
  127. package/dist/events/ui-request.d.ts +2 -31
  128. package/dist/events/ui-request.d.ts.map +1 -1
  129. package/dist/events/ui-response.d.ts +2 -10
  130. package/dist/events/ui-response.d.ts.map +1 -1
  131. package/dist/index.d.ts +247 -243
  132. package/dist/index.d.ts.map +1 -1
  133. package/dist/index.js +3773 -3054
  134. package/dist/inject.d.ts +1 -6
  135. package/dist/inject.d.ts.map +1 -1
  136. package/dist/lowLevelInject.d.ts.map +1 -1
  137. package/dist/protocols/protocol-v2/features.d.ts +4 -0
  138. package/dist/protocols/protocol-v2/features.d.ts.map +1 -1
  139. package/dist/protocols/protocol-v2/firmware.d.ts.map +1 -1
  140. package/dist/protocols/protocol-v2/lockedError.d.ts +2 -0
  141. package/dist/protocols/protocol-v2/lockedError.d.ts.map +1 -0
  142. package/dist/protocols/protocol-v2/uiInteraction.d.ts +4 -7
  143. package/dist/protocols/protocol-v2/uiInteraction.d.ts.map +1 -1
  144. package/dist/protocols/protocol-v2/unlockPolicy.d.ts +3 -1
  145. package/dist/protocols/protocol-v2/unlockPolicy.d.ts.map +1 -1
  146. package/dist/protocols/protocol-v2/unlockRetry.d.ts +10 -0
  147. package/dist/protocols/protocol-v2/unlockRetry.d.ts.map +1 -0
  148. package/dist/protocols/protocol-v2/walletSession.d.ts +1 -6
  149. package/dist/protocols/protocol-v2/walletSession.d.ts.map +1 -1
  150. package/dist/topLevelInject.d.ts.map +1 -1
  151. package/dist/types/api/checkAllFirmwareRelease.d.ts +5 -3
  152. package/dist/types/api/checkAllFirmwareRelease.d.ts.map +1 -1
  153. package/dist/types/api/deviceUnlock.d.ts +1 -5
  154. package/dist/types/api/deviceUnlock.d.ts.map +1 -1
  155. package/dist/types/api/deviceUpdateBootloader.d.ts +6 -0
  156. package/dist/types/api/deviceUpdateBootloader.d.ts.map +1 -1
  157. package/dist/types/api/export.d.ts +4 -2
  158. package/dist/types/api/export.d.ts.map +1 -1
  159. package/dist/types/api/firmwareUpdate.d.ts +70 -4
  160. package/dist/types/api/firmwareUpdate.d.ts.map +1 -1
  161. package/dist/types/api/firmwareUpdateCapabilities.d.ts +9 -0
  162. package/dist/types/api/firmwareUpdateCapabilities.d.ts.map +1 -0
  163. package/dist/types/api/firmwareUpdatePlan.d.ts +28 -0
  164. package/dist/types/api/firmwareUpdatePlan.d.ts.map +1 -0
  165. package/dist/types/api/firmwareUpdatePreparedPlan.d.ts +42 -0
  166. package/dist/types/api/firmwareUpdatePreparedPlan.d.ts.map +1 -0
  167. package/dist/types/api/index.d.ts +10 -7
  168. package/dist/types/api/index.d.ts.map +1 -1
  169. package/dist/types/api/protocolV2.d.ts +0 -3
  170. package/dist/types/api/protocolV2.d.ts.map +1 -1
  171. package/dist/types/device.d.ts +2 -2
  172. package/dist/types/device.d.ts.map +1 -1
  173. package/dist/types/params.d.ts +0 -1
  174. package/dist/types/params.d.ts.map +1 -1
  175. package/dist/types/settings.d.ts +21 -38
  176. package/dist/types/settings.d.ts.map +1 -1
  177. package/dist/utils/deviceFeaturesCompat.d.ts +1 -0
  178. package/dist/utils/deviceFeaturesCompat.d.ts.map +1 -1
  179. package/dist/utils/deviceFeaturesUtils.d.ts +0 -4
  180. package/dist/utils/deviceFeaturesUtils.d.ts.map +1 -1
  181. package/dist/utils/deviceInfoUtils.d.ts.map +1 -1
  182. package/dist/utils/deviceSettings.d.ts.map +1 -1
  183. package/dist/utils/homescreen.d.ts +0 -4
  184. package/dist/utils/homescreen.d.ts.map +1 -1
  185. package/dist/utils/index.d.ts +1 -1
  186. package/dist/utils/index.d.ts.map +1 -1
  187. package/dist/utils/patch.d.ts +1 -1
  188. package/dist/utils/patch.d.ts.map +1 -1
  189. package/dist/utils/pro2Wallpaper.d.ts +0 -10
  190. package/dist/utils/pro2Wallpaper.d.ts.map +1 -1
  191. package/package.json +4 -4
  192. package/src/api/BaseMethod.ts +10 -8
  193. package/src/api/CheckAllFirmwareRelease.ts +60 -59
  194. package/src/api/FirmwareUpdate.ts +15 -7
  195. package/src/api/FirmwareUpdateV2.ts +298 -126
  196. package/src/api/FirmwareUpdateV3.ts +265 -63
  197. package/src/api/FirmwareUpdateV4.ts +1017 -602
  198. package/src/api/GetPassphraseState.ts +1 -7
  199. package/src/api/OpenWalletSession.ts +17 -71
  200. package/src/api/SearchDevices.ts +1 -3
  201. package/src/api/allnetwork/AllNetworkGetAddress.ts +21 -21
  202. package/src/api/allnetwork/AllNetworkGetAddressBase.ts +11 -36
  203. package/src/api/device/DeviceSettings.ts +4 -5
  204. package/src/api/device/DeviceUnlock.ts +3 -8
  205. package/src/api/device/DeviceUpdateBootloader.ts +125 -6
  206. package/src/api/firmware/FirmwareArtifactSource.ts +278 -0
  207. package/src/api/firmware/FirmwareHostBinding.ts +100 -0
  208. package/src/api/firmware/FirmwarePreparationError.ts +12 -0
  209. package/src/api/firmware/FirmwareUpdateBaseMethod.ts +83 -27
  210. package/src/api/firmware/FirmwareUpdateCapabilities.ts +9 -0
  211. package/src/api/firmware/FirmwareUpdatePlan.ts +772 -0
  212. package/src/api/firmware/FirmwareUpdatePreparedPlan.ts +449 -0
  213. package/src/api/firmware/progressThrottle.ts +44 -0
  214. package/src/api/firmware/updateBootloader.ts +19 -4
  215. package/src/api/firmware/uploadFirmware.ts +144 -39
  216. package/src/api/helpers/protocolV2FileWrite.ts +63 -202
  217. package/src/api/index.ts +0 -2
  218. package/src/api/kaspa/KaspaGetAddress.ts +1 -1
  219. package/src/api/kaspa/KaspaSignTransaction.ts +13 -2
  220. package/src/api/polkadot/networks.ts +3 -3
  221. package/src/api/protocol-v2/ProtocolInfoRequest.ts +1 -3
  222. package/src/api/protocol-v2/helpers.ts +1 -1
  223. package/src/api/solana/SolSignMessage.ts +1 -1
  224. package/src/api/solana/SolSignOffchainMessage.ts +1 -1
  225. package/src/api/solana/SolSignTransaction.ts +2 -2
  226. package/src/api/sui/SuiGetAddress.ts +1 -1
  227. package/src/api/sui/SuiGetPublicKey.ts +1 -1
  228. package/src/api/sui/SuiSignMessage.ts +1 -1
  229. package/src/api/sui/SuiSignTransaction.ts +1 -1
  230. package/src/api/ton/TonGetAddress.ts +1 -1
  231. package/src/api/ton/TonSignMessage.ts +1 -1
  232. package/src/api/ton/TonSignProof.ts +1 -1
  233. package/src/api/tron/TronSignMessage.ts +2 -2
  234. package/src/api/tron/TronSignTransaction.ts +1 -1
  235. package/src/core/deviceEventRegistration.ts +0 -4
  236. package/src/core/index.ts +111 -213
  237. package/src/data/messages/messages-protocol-v2.json +0 -25
  238. package/src/data-manager/DataManager.ts +41 -113
  239. package/src/data-manager/TransportManager.ts +0 -6
  240. package/src/data-manager/connectSettings.ts +11 -0
  241. package/src/device/Device.ts +49 -274
  242. package/src/device/DeviceCommands.ts +4 -31
  243. package/src/device/DeviceConnector.ts +13 -33
  244. package/src/device/DevicePool.ts +7 -21
  245. package/src/deviceProfile/buildDeviceFeatures.ts +2 -2
  246. package/src/deviceProfile/protocolV2DeviceIdentity.ts +0 -3
  247. package/src/events/device.ts +0 -4
  248. package/src/events/logBlockEvent.ts +0 -1
  249. package/src/events/ui-promise.ts +2 -4
  250. package/src/events/ui-request.ts +2 -36
  251. package/src/events/ui-response.ts +2 -12
  252. package/src/index.ts +5 -0
  253. package/src/inject.ts +24 -60
  254. package/src/lowLevelInject.ts +8 -7
  255. package/src/protocols/protocol-v2/features.ts +7 -10
  256. package/src/protocols/protocol-v2/firmware.ts +0 -2
  257. package/src/protocols/protocol-v2/lockedError.ts +10 -0
  258. package/src/protocols/protocol-v2/uiInteraction.ts +6 -46
  259. package/src/protocols/protocol-v2/unlockPolicy.ts +105 -1
  260. package/src/protocols/protocol-v2/unlockRetry.ts +109 -0
  261. package/src/protocols/protocol-v2/walletSession.ts +36 -214
  262. package/src/topLevelInject.ts +8 -7
  263. package/src/types/api/checkAllFirmwareRelease.ts +5 -3
  264. package/src/types/api/deviceUnlock.ts +1 -12
  265. package/src/types/api/deviceUpdateBootloader.ts +6 -0
  266. package/src/types/api/export.ts +18 -1
  267. package/src/types/api/firmwareUpdate.ts +78 -6
  268. package/src/types/api/firmwareUpdateCapabilities.ts +9 -0
  269. package/src/types/api/firmwareUpdatePlan.ts +38 -0
  270. package/src/types/api/firmwareUpdatePreparedPlan.ts +53 -0
  271. package/src/types/api/index.ts +14 -13
  272. package/src/types/api/protocolV2.ts +0 -13
  273. package/src/types/device.ts +3 -15
  274. package/src/types/params.ts +1 -7
  275. package/src/types/settings.ts +22 -60
  276. package/src/utils/deviceFeaturesCompat.ts +6 -5
  277. package/src/utils/deviceFeaturesUtils.ts +3 -14
  278. package/src/utils/deviceInfoUtils.ts +0 -2
  279. package/src/utils/deviceSettings.ts +0 -3
  280. package/src/utils/homescreen.ts +6 -32
  281. package/src/utils/index.ts +1 -6
  282. package/src/utils/pro2Wallpaper.ts +8 -35
  283. package/__tests__/core-initialization.test.ts +0 -23
  284. package/__tests__/device-connector-protocol.test.ts +0 -81
  285. package/__tests__/deviceUploadNft.test.ts +0 -316
  286. package/__tests__/pro2Nft.test.ts +0 -108
  287. package/__tests__/protocol-binding.test.ts +0 -89
  288. package/__tests__/protocol-v2-resources.test.ts +0 -340
  289. package/__tests__/protocol-v2-ui-lifecycle.test.ts +0 -91
  290. package/__tests__/uiProgressThrottle.test.ts +0 -74
  291. package/__tests__/uiPromiseRegistry.test.ts +0 -115
  292. package/dist/api/DetectDeviceConnectProtocol.d.ts +0 -7
  293. package/dist/api/DetectDeviceConnectProtocol.d.ts.map +0 -1
  294. package/dist/api/protocol-v2/DeviceUploadNft.d.ts +0 -31
  295. package/dist/api/protocol-v2/DeviceUploadNft.d.ts.map +0 -1
  296. package/dist/core/uiPromiseRegistry.d.ts +0 -6
  297. package/dist/core/uiPromiseRegistry.d.ts.map +0 -1
  298. package/dist/protocols/protocol-v2/resources.d.ts +0 -30
  299. package/dist/protocols/protocol-v2/resources.d.ts.map +0 -1
  300. package/dist/protocols/protocol-v2/unlockPolicyRunner.d.ts +0 -22
  301. package/dist/protocols/protocol-v2/unlockPolicyRunner.d.ts.map +0 -1
  302. package/dist/types/api/detectDeviceConnectProtocol.d.ts +0 -4
  303. package/dist/types/api/detectDeviceConnectProtocol.d.ts.map +0 -1
  304. package/dist/utils/pro2Nft.d.ts +0 -31
  305. package/dist/utils/pro2Nft.d.ts.map +0 -1
  306. package/dist/utils/uiProgressThrottle.d.ts +0 -3
  307. package/dist/utils/uiProgressThrottle.d.ts.map +0 -1
  308. package/src/api/DetectDeviceConnectProtocol.ts +0 -18
  309. package/src/api/protocol-v2/DeviceUploadNft.ts +0 -197
  310. package/src/core/uiPromiseRegistry.ts +0 -63
  311. package/src/protocols/protocol-v2/resources.ts +0 -390
  312. package/src/protocols/protocol-v2/unlockPolicyRunner.ts +0 -131
  313. package/src/types/api/detectDeviceConnectProtocol.ts +0 -6
  314. package/src/utils/pro2Nft.ts +0 -142
  315. package/src/utils/uiProgressThrottle.ts +0 -63
@@ -14,18 +14,45 @@ import { BaseMethod } from './BaseMethod';
14
14
  import { validateParams } from './helpers/paramsValidator';
15
15
  import { DevicePool } from '../device/DevicePool';
16
16
  import { getBinary, getInfo, getSysResourceBinary } from './firmware/getBinary';
17
- import { updateResources, uploadFirmware } from './firmware/uploadFirmware';
18
- import { LoggerNames, getLogger, wait } from '../utils';
17
+ import { normalizeFirmwarePreparationError } from './firmware/FirmwarePreparationError';
18
+ import {
19
+ updateResources,
20
+ updateResourcesFromSources,
21
+ uploadFirmwareFromSource,
22
+ } from './firmware/uploadFirmware';
23
+ import { BOOTLOADER_POLL_INITIALIZE_TIMEOUT_MS } from './firmware/FirmwareUpdateBaseMethod';
24
+ import { LoggerNames, getDeviceType, getDeviceUUID, getLogger, wait } from '../utils';
25
+ import { resolveDeviceBootloaderMode } from '../utils/deviceFeaturesCompat';
19
26
  import { FirmwareUpdateTipMessage, createUiMessage } from '../events/ui-request';
20
27
  import { DeviceModelToTypes } from '../types';
21
28
  import { DataManager } from '../data-manager';
22
29
  import { DEVICE } from '../events';
30
+ import { type FirmwareByteSource, openFirmwareByteSource } from './firmware/FirmwareArtifactSource';
31
+ import { resolveFirmwareUpdateHostBinding } from './firmware/FirmwareHostBinding';
32
+ import {
33
+ assertFirmwareUpdatePreparedPlanBinding,
34
+ assertFirmwareUpdatePreparedPlanDeviceIdentity,
35
+ getFirmwareUpdateResourceName,
36
+ } from './firmware/FirmwareUpdatePreparedPlan';
23
37
 
24
38
  import type { Features, KnownDevice } from '../types';
25
39
  import type { FirmwareBinary } from './firmware/getBinary';
40
+ import type {
41
+ FirmwareArtifactReader,
42
+ FirmwareArtifactReference,
43
+ } from '../types/api/firmwareUpdate';
44
+ import type { FirmwareUpdatePreparedPlan } from '../types/api/firmwareUpdatePreparedPlan';
26
45
 
27
46
  type Params = {
28
47
  binary?: ArrayBuffer;
48
+ artifact?: FirmwareArtifactReference;
49
+ resourceEntries?: Array<{
50
+ entryName: string;
51
+ artifact: FirmwareArtifactReference;
52
+ }>;
53
+ artifactReader?: FirmwareArtifactReader;
54
+ preparedPlan?: FirmwareUpdatePreparedPlan;
55
+ platform?: FirmwareUpdatePreparedPlan['platform'];
29
56
  version?: number[];
30
57
  updateType: 'firmware' | 'ble';
31
58
  forcedUpdateRes?: boolean;
@@ -106,6 +133,13 @@ const normalizeFirmwareBinary = (binary: unknown): FirmwareBinary | undefined =>
106
133
  return normalized.buffer;
107
134
  };
108
135
 
136
+ const toArrayBuffer = (binary: FirmwareBinary): ArrayBuffer => {
137
+ if (binary instanceof ArrayBuffer) {
138
+ return binary;
139
+ }
140
+ return new Uint8Array(binary.buffer, binary.byteOffset, binary.byteLength).slice().buffer;
141
+ };
142
+
109
143
  export default class FirmwareUpdateV2 extends BaseMethod<Params> {
110
144
  checkPromise: Deferred<any> | null = null;
111
145
 
@@ -152,6 +186,32 @@ export default class FirmwareUpdateV2 extends BaseMethod<Params> {
152
186
  binary: payload.binary,
153
187
  };
154
188
  }
189
+
190
+ if ('artifact' in payload) {
191
+ const hostBinding = resolveFirmwareUpdateHostBinding(payload.hostBindingGeneration);
192
+ const target = payload.isUpdateBootloader ? 'bootloader' : payload.updateType;
193
+ const resourceBindings = (payload.resourceEntries ?? []).map(
194
+ (entry: { entryName: string; artifact: FirmwareArtifactReference }) => ({
195
+ target: 'resource' as const,
196
+ entryName: entry.entryName,
197
+ artifact: entry.artifact,
198
+ })
199
+ );
200
+ assertFirmwareUpdatePreparedPlanBinding({
201
+ preparedPlan: payload.preparedPlan,
202
+ executor: 'v2',
203
+ platform: payload.platform,
204
+ scopeTargets: [target, ...(target === 'firmware' ? (['resource'] as const) : [])],
205
+ bindings: [{ target, artifact: payload.artifact }, ...resourceBindings],
206
+ });
207
+ this.params = {
208
+ ...this.params,
209
+ preparedPlan: payload.preparedPlan,
210
+ artifact: payload.artifact,
211
+ resourceEntries: payload.resourceEntries,
212
+ artifactReader: hostBinding.artifactReader,
213
+ };
214
+ }
155
215
  }
156
216
 
157
217
  postTipMessage = (message: string) => {
@@ -187,6 +247,10 @@ export default class FirmwareUpdateV2 extends BaseMethod<Params> {
187
247
  this.checkPromise = createDeferred();
188
248
  const env = DataManager.getSettings('env');
189
249
  const isBleReconnect = connectId && DataManager.isBleConnect(env);
250
+ // Tracks the in-flight BLE probe so interval ticks never overlap: a superseded
251
+ // Initialize left pending on the V1 transport is exactly what later times out
252
+ // and used to tear down the connection mid-firmware-upload.
253
+ let bleProbeInFlight = false;
190
254
 
191
255
  Log.log('FirmwareUpdateV2 [checkDeviceToBootloader] isBleReconnect: ', isBleReconnect);
192
256
 
@@ -234,14 +298,18 @@ export default class FirmwareUpdateV2 extends BaseMethod<Params> {
234
298
  }
235
299
 
236
300
  if (isBleReconnect) {
301
+ if (bleProbeInFlight) return;
302
+ bleProbeInFlight = true;
237
303
  try {
238
304
  await this.device.deviceConnector?.acquire(
239
305
  this.device.originalDescriptor.id,
240
306
  null,
241
- true,
242
- this.payload.connectProtocol ?? this.device.originalDescriptor.protocolType
307
+ true
243
308
  );
244
- await this.device.initialize();
309
+ // Bound each probe so a request the rebooting device never received
310
+ // frees the slot for the next tick instead of hanging into the
311
+ // 30s reboot budget.
312
+ await this.device.initialize({ timeoutMs: BOOTLOADER_POLL_INITIALIZE_TIMEOUT_MS });
245
313
  if (this.device.isBootloader()) {
246
314
  clearInterval(intervalTimer);
247
315
  this.checkPromise?.resolve(true);
@@ -249,6 +317,8 @@ export default class FirmwareUpdateV2 extends BaseMethod<Params> {
249
317
  } catch (e) {
250
318
  // ignore error because of device is not connected
251
319
  Log.log('catch Bluetooth error when device is restarting: ', e);
320
+ } finally {
321
+ bleProbeInFlight = false;
252
322
  }
253
323
  } else {
254
324
  await this._checkDeviceInBootloaderMode(connectId, intervalTimer, timeoutTimer);
@@ -273,9 +343,7 @@ export default class FirmwareUpdateV2 extends BaseMethod<Params> {
273
343
  ) {
274
344
  const deviceDiff = await this.device.deviceConnector?.enumerate();
275
345
  const devicesDescriptor = deviceDiff?.descriptors ?? [];
276
- const { deviceList } = await DevicePool.getDevices(devicesDescriptor, connectId, {
277
- connectProtocol: this.payload.connectProtocol ?? this.device.originalDescriptor.protocolType,
278
- });
346
+ const { deviceList } = await DevicePool.getDevices(devicesDescriptor, connectId);
279
347
 
280
348
  if (deviceList.length === 1 && deviceList[0]?.isBootloader()) {
281
349
  // should update current device from cache
@@ -344,151 +412,255 @@ export default class FirmwareUpdateV2 extends BaseMethod<Params> {
344
412
  const { features, commands } = device;
345
413
  const deviceType = device.getCurrentDeviceType();
346
414
 
415
+ // Protocol V2 (Pro2) uses DeviceFirmwareUpdate and must not enter this legacy flow.
416
+ if (device.isProtocolV2()) {
417
+ throw ERRORS.TypedError(
418
+ HardwareErrorCode.RuntimeError,
419
+ 'Protocol V2 firmware update must use firmwareUpdateV4'
420
+ );
421
+ }
422
+ if (params.preparedPlan) {
423
+ assertFirmwareUpdatePreparedPlanDeviceIdentity({
424
+ preparedPlan: params.preparedPlan,
425
+ deviceIdentity: getDeviceUUID(features) || undefined,
426
+ bootloaderMode: resolveDeviceBootloaderMode(features),
427
+ deviceModel: String(getDeviceType(features)),
428
+ });
429
+ }
430
+
347
431
  const deviceFirmwareType = device.getCurrentFirmwareType();
348
432
  const firmwareType = params.firmwareType ?? deviceFirmwareType;
349
433
 
350
434
  this.checkVersionForCopyTouchResource(features, firmwareType);
351
435
 
352
- let preparedBinary: FirmwareBinary | undefined;
353
- const acquireFirmwareBinary = async (): Promise<FirmwareBinary> => {
354
- try {
355
- if (preparedBinary) {
356
- return preparedBinary;
357
- }
358
-
359
- if (params.binary !== undefined) {
360
- preparedBinary = normalizeFirmwareBinary(params.binary);
361
- if (!preparedBinary) {
362
- throw new Error('firmware binary is empty or invalid');
436
+ let preparedSource: FirmwareByteSource | undefined;
437
+ try {
438
+ const acquireFirmwareSource = async (): Promise<FirmwareByteSource> => {
439
+ try {
440
+ if (preparedSource) {
441
+ return preparedSource;
363
442
  }
364
- return preparedBinary;
365
- }
366
443
 
367
- if (!device.features) {
368
- throw ERRORS.TypedError(
369
- HardwareErrorCode.RuntimeError,
370
- 'no features found for this device'
371
- );
372
- }
373
-
374
- this.postTipMessage('DownloadFirmware');
375
- const firmware = await getBinary({
376
- features: device.features,
377
- version: params.version,
378
- updateType: params.updateType,
379
- isUpdateBootloader: params.isUpdateBootloader,
380
- firmwareType,
381
- requestOptions: FIRMWARE_DOWNLOAD_REQUEST_OPTIONS,
382
- });
383
- preparedBinary = normalizeFirmwareBinary(firmware.binary);
384
- if (!preparedBinary) {
385
- throw new Error('downloaded firmware binary is empty or invalid');
386
- }
387
- this.postTipMessage('DownloadFirmwareSuccess');
388
- return preparedBinary;
389
- } catch (err) {
390
- throw ERRORS.TypedError(HardwareErrorCode.FirmwareUpdateDownloadFailed, err.message ?? err);
391
- }
392
- };
444
+ if (params.binary !== undefined) {
445
+ const binary = normalizeFirmwareBinary(params.binary);
446
+ if (!binary) {
447
+ throw new Error('firmware binary is empty or invalid');
448
+ }
449
+ const source = await openFirmwareByteSource({
450
+ binary: toArrayBuffer(binary),
451
+ });
452
+ if (!source) {
453
+ throw new Error('firmware binary is empty or invalid');
454
+ }
455
+ preparedSource = source;
456
+ return source;
457
+ }
393
458
 
394
- if (!device.isBootloader() && features) {
395
- const serialNo = device.getCurrentSerialNo();
396
- // should go to bootloader mode manually
397
- if (this.isEnteredManuallyBoot()) {
398
- return Promise.reject(ERRORS.TypedError(HardwareErrorCode.FirmwareUpdateManuallyEnterBoot));
399
- }
459
+ if (params.artifact) {
460
+ const source = await openFirmwareByteSource({
461
+ artifact: params.artifact,
462
+ reader: params.artifactReader,
463
+ });
464
+ if (!source) {
465
+ throw new Error('firmware artifact is not prepared');
466
+ }
467
+ preparedSource = source;
468
+ return source;
469
+ }
400
470
 
401
- // check & upgrade firmware resource
402
- if (this.isSupportResourceUpdate(params.updateType)) {
403
- this.postTipMessage('CheckLatestUiResource');
404
- const resourceUrl = DataManager.getSysResourcesLatestRelease({
405
- features,
406
- forcedUpdateRes: params.forcedUpdateRes,
407
- firmwareType,
408
- });
409
- if (resourceUrl) {
410
- this.postTipMessage('DownloadLatestUiResource');
411
- const resource = await getSysResourceBinary(resourceUrl);
412
- this.postTipMessage('DownloadLatestUiResourceSuccess');
413
- if (resource) {
414
- await updateResources(
415
- this.device.getCommands().typedCall.bind(this.device.getCommands()),
416
- this.postMessage,
417
- device,
418
- resource.binary
471
+ if (!device.features) {
472
+ throw ERRORS.TypedError(
473
+ HardwareErrorCode.RuntimeError,
474
+ 'no features found for this device'
419
475
  );
420
476
  }
421
- }
422
- }
423
-
424
- // check if the device commands has been disposed
425
- this.device?.commands?.checkDisposed();
426
477
 
427
- // A failed firmware download must leave the device in normal mode.
428
- await acquireFirmwareBinary();
478
+ if (
479
+ params.artifactReader ||
480
+ DataManager.getSettings('firmwareManifestMode') === 'external-only'
481
+ ) {
482
+ throw ERRORS.TypedError(
483
+ HardwareErrorCode.RuntimeError,
484
+ 'Firmware must be prepared by the external firmware host',
485
+ {
486
+ firmwareUpdateCode: 'FirmwareArtifactsNotPrepared',
487
+ artifactName: 'firmware',
488
+ }
489
+ );
490
+ }
429
491
 
430
- // The request may outlive the current transport command instance.
431
- this.device?.commands?.checkDisposed();
492
+ this.postTipMessage('DownloadFirmware');
493
+ const firmware = await getBinary({
494
+ features: device.features,
495
+ version: params.version,
496
+ updateType: params.updateType,
497
+ isUpdateBootloader: params.isUpdateBootloader,
498
+ firmwareType,
499
+ requestOptions: FIRMWARE_DOWNLOAD_REQUEST_OPTIONS,
500
+ });
501
+ const binary = normalizeFirmwareBinary(firmware.binary);
502
+ if (!binary) {
503
+ throw new Error('downloaded firmware binary is empty or invalid');
504
+ }
505
+ const source = await openFirmwareByteSource({
506
+ binary: toArrayBuffer(binary),
507
+ });
508
+ if (!source) {
509
+ throw new Error('downloaded firmware binary is empty or invalid');
510
+ }
511
+ preparedSource = source;
512
+ this.postTipMessage('DownloadFirmwareSuccess');
513
+ return source;
514
+ } catch (err) {
515
+ throw normalizeFirmwarePreparationError(err);
516
+ }
517
+ };
432
518
 
433
- // auto go to bootloader mode
434
- try {
435
- this.postTipMessage('AutoRebootToBootloader');
436
- const bootRes = await commands.typedCall('DeviceBackToBoot', 'Success');
437
- // @ts-expect-error
438
- if (bootRes.type === 'CallMethodError') {
439
- throw ERRORS.TypedError(HardwareErrorCode.FirmwareUpdateAutoEnterBootFailure);
519
+ if (!device.isBootloader() && features) {
520
+ const serialNo = device.getCurrentSerialNo();
521
+ // should go to bootloader mode manually
522
+ if (this.isEnteredManuallyBoot()) {
523
+ throw ERRORS.TypedError(HardwareErrorCode.FirmwareUpdateManuallyEnterBoot);
440
524
  }
441
- this.postTipMessage('GoToBootloaderSuccess');
442
- this.checkDeviceToBootloader(this.payload.connectId);
443
525
 
444
- // force clean classic device cache so that the device can initialize again
445
- if (DeviceModelToTypes.model_classic.includes(deviceType)) {
446
- DevicePool.clearDeviceCache(serialNo);
526
+ // All network-backed input must be ready before the first device mutation.
527
+ await acquireFirmwareSource();
528
+
529
+ // check & upgrade firmware resource
530
+ if (this.isSupportResourceUpdate(params.updateType)) {
531
+ this.postTipMessage('CheckLatestUiResource');
532
+ const resourceUrl = DataManager.getSysResourcesLatestRelease({
533
+ features,
534
+ forcedUpdateRes: params.forcedUpdateRes,
535
+ firmwareType,
536
+ });
537
+ if (resourceUrl) {
538
+ this.postTipMessage('DownloadLatestUiResource');
539
+ if (params.resourceEntries?.length) {
540
+ const sources: Array<{
541
+ entryName: string;
542
+ source: FirmwareByteSource;
543
+ }> = [];
544
+ try {
545
+ for (const entry of params.resourceEntries) {
546
+ const resourceName = getFirmwareUpdateResourceName(entry.entryName);
547
+ const source = await openFirmwareByteSource({
548
+ artifact: entry.artifact,
549
+ reader: params.artifactReader,
550
+ });
551
+ if (!source) {
552
+ throw new Error('Firmware resource entry is not prepared');
553
+ }
554
+ sources.push({ entryName: resourceName, source });
555
+ }
556
+ await updateResourcesFromSources(
557
+ this.device.getCommands().typedCall.bind(this.device.getCommands()),
558
+ this.postMessage,
559
+ device,
560
+ sources.map(entry => ({
561
+ entryName: entry.entryName,
562
+ source: entry.source,
563
+ }))
564
+ );
565
+ } finally {
566
+ await Promise.all(
567
+ sources.map(entry => entry.source.close().catch(() => undefined))
568
+ );
569
+ }
570
+ this.postTipMessage('DownloadLatestUiResourceSuccess');
571
+ } else {
572
+ if (
573
+ params.artifactReader ||
574
+ DataManager.getSettings('firmwareManifestMode') === 'external-only'
575
+ ) {
576
+ throw ERRORS.TypedError(
577
+ HardwareErrorCode.RuntimeError,
578
+ 'Firmware resource must be prepared by the external firmware host',
579
+ {
580
+ firmwareUpdateCode: 'FirmwareArtifactsNotPrepared',
581
+ artifactName: 'resource',
582
+ }
583
+ );
584
+ }
585
+ const resourceBinary: ArrayBuffer | Buffer = (await getSysResourceBinary(resourceUrl))
586
+ .binary;
587
+ this.postTipMessage('DownloadLatestUiResourceSuccess');
588
+ await updateResources(
589
+ this.device.getCommands().typedCall.bind(this.device.getCommands()),
590
+ this.postMessage,
591
+ device,
592
+ resourceBinary
593
+ );
594
+ }
595
+ }
447
596
  }
448
- delete DevicePool.devicesCache[''];
449
- await this.checkPromise?.promise;
450
- this.checkPromise = null;
451
597
 
452
- // check if the device commands has been disposed
598
+ // The request may outlive the current transport command instance.
453
599
  this.device?.commands?.checkDisposed();
454
600
 
455
- /**
456
- * Touch 1 with bootloader v2.5.0 issue: BLE chip need more time for looking up name, here change the delay time to 3000ms after rebooting.
457
- */
458
- const isTouch = DeviceModelToTypes.model_touch.includes(deviceType);
459
- await wait(isTouch ? 3000 : 1500);
460
- } catch (e) {
461
- if (e instanceof HardwareError) {
462
- return Promise.reject(e);
601
+ // auto go to bootloader mode
602
+ try {
603
+ this.postTipMessage('AutoRebootToBootloader');
604
+ const bootRes = await commands.typedCall('DeviceBackToBoot', 'Success');
605
+ // @ts-expect-error
606
+ if (bootRes.type === 'CallMethodError') {
607
+ throw ERRORS.TypedError(HardwareErrorCode.FirmwareUpdateAutoEnterBootFailure);
608
+ }
609
+ this.postTipMessage('GoToBootloaderSuccess');
610
+ this.checkDeviceToBootloader(this.payload.connectId);
611
+
612
+ // force clean classic device cache so that the device can initialize again
613
+ if (DeviceModelToTypes.model_classic.includes(deviceType)) {
614
+ DevicePool.clearDeviceCache(serialNo);
615
+ }
616
+ delete DevicePool.devicesCache[''];
617
+ await this.checkPromise?.promise;
618
+ this.checkPromise = null;
619
+
620
+ // check if the device commands has been disposed
621
+ this.device?.commands?.checkDisposed();
622
+
623
+ /**
624
+ * Touch 1 with bootloader v2.5.0 issue: BLE chip need more time for looking up name, here change the delay time to 3000ms after rebooting.
625
+ */
626
+ const isTouch = DeviceModelToTypes.model_touch.includes(deviceType);
627
+ await wait(isTouch ? 3000 : 1500);
628
+ } catch (e) {
629
+ if (e instanceof HardwareError) {
630
+ return Promise.reject(e);
631
+ }
632
+ console.log('auto go to bootloader mode failed: ', e);
633
+ return Promise.reject(
634
+ ERRORS.TypedError(HardwareErrorCode.FirmwareUpdateAutoEnterBootFailure)
635
+ );
463
636
  }
464
- console.log('auto go to bootloader mode failed: ', e);
465
- return Promise.reject(
466
- ERRORS.TypedError(HardwareErrorCode.FirmwareUpdateAutoEnterBootFailure)
467
- );
468
637
  }
469
- }
470
638
 
471
- // Devices already in bootloader mode still acquire through the same helper.
472
- const binary = await acquireFirmwareBinary();
639
+ // Devices already in bootloader mode still acquire through the same helper.
640
+ const source = await acquireFirmwareSource();
473
641
 
474
- // check if the device commands has been disposed
475
- this.device?.commands?.checkDisposed();
642
+ // check if the device commands has been disposed
643
+ this.device?.commands?.checkDisposed();
476
644
 
477
- await this.device.acquire();
645
+ await this.device.acquire();
478
646
 
479
- const response = await uploadFirmware(
480
- params.updateType,
481
- this.device.getCommands().typedCall.bind(this.device.getCommands()),
482
- this.postMessage,
483
- device,
484
- { payload: binary, rebootOnSuccess: true },
485
- params.isUpdateBootloader
486
- );
647
+ const response = await uploadFirmwareFromSource(
648
+ params.updateType,
649
+ this.device.getCommands().typedCall.bind(this.device.getCommands()),
650
+ this.postMessage,
651
+ device,
652
+ source,
653
+ true,
654
+ params.isUpdateBootloader
655
+ );
487
656
 
488
- if (this.connectId) {
489
- DevicePool.clearDeviceCache(this.connectId);
490
- }
657
+ if (this.connectId) {
658
+ DevicePool.clearDeviceCache(this.connectId);
659
+ }
491
660
 
492
- return response;
661
+ return response;
662
+ } finally {
663
+ await preparedSource?.close().catch(() => undefined);
664
+ }
493
665
  }
494
666
  }