Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion modules/hdwallet
2 changes: 1 addition & 1 deletion modules/keepkey-firmware
Submodule keepkey-firmware updated 98 files
+94 −29 .github/workflows/ci.yml
+46 −13 .github/workflows/release.yml
+4 −4 .gitmodules
+60 −7 CMakeLists.txt
+0 −42 Makefile
+12 −6 deps/crypto/CMakeLists.txt
+1 −1 deps/crypto/trezor-firmware
+1 −1 deps/device-protocol
+1 −1 deps/python-keepkey
+0 −305 docs/coin-integration/README.md
+0 −297 docs/coin-integration/zcash-clearsign-handoff.md
+0 −425 docs/coin-integration/zcash-on-device-ua.md
+0 −322 docs/coin-integration/zcash-pczt-clearsign.md
+94 −0 docs/firmware/reviews/7.15.0-review-round2-remediation.md
+0 −146 docs/zoo/reports/zcash-report.md
+4 −0 include/keepkey/board/confirm_sm.h
+15 −0 include/keepkey/board/layout.h
+6 −0 include/keepkey/board/messages.h
+2 −0 include/keepkey/firmware/app_confirm.h
+2 −0 include/keepkey/firmware/app_layout.h
+22 −0 include/keepkey/firmware/bip85.h
+2 −0 include/keepkey/firmware/coins.def
+2 −0 include/keepkey/firmware/coins.h
+1 −0 include/keepkey/firmware/ethereum.h
+11 −5 include/keepkey/firmware/ethereum_contracts/thortx.h
+4 −0 include/keepkey/firmware/ethereum_tokens.h
+7 −1 include/keepkey/firmware/fsm.h
+21 −1 include/keepkey/firmware/hive.h
+9 −0 include/keepkey/firmware/mayachain.h
+10 −0 include/keepkey/firmware/reset.h
+207 −0 include/keepkey/firmware/signed_metadata.h
+4 −0 include/keepkey/firmware/solana.h
+19 −1 include/keepkey/firmware/storage.h
+5 −0 include/keepkey/firmware/thorchain.h
+1 −0 include/keepkey/firmware/tiny-json.h
+55 −0 include/keepkey/firmware/tron.h
+3 −0 include/keepkey/transport/messages-ethereum.options
+6 −0 include/keepkey/transport/messages-hive.options
+6 −1 include/keepkey/transport/messages-ripple.options
+39 −12 lib/board/confirm_sm.c
+133 −3 lib/board/layout.c
+90 −40 lib/board/messages.c
+6 −0 lib/board/udp.c
+29 −20 lib/board/usb.c
+39 −28 lib/firmware/CMakeLists.txt
+2 −0 lib/firmware/app_confirm.c
+2 −0 lib/firmware/app_layout.c
+105 −0 lib/firmware/bip85.c
+2 −0 lib/firmware/coins.c
+32 −26 lib/firmware/eip712.c
+138 −41 lib/firmware/ethereum.c
+21 −1 lib/firmware/ethereum_contracts.c
+2 −1 lib/firmware/ethereum_contracts/saproxy.c
+23 −4 lib/firmware/ethereum_contracts/thortx.c
+2 −1 lib/firmware/ethereum_contracts/zxappliquid.c
+14 −7 lib/firmware/ethereum_contracts/zxliquidtx.c
+19 −1 lib/firmware/ethereum_contracts/zxswap.c
+4 −0 lib/firmware/ethereum_contracts/zxtransERC20.c
+39 −5 lib/firmware/fsm.c
+142 −0 lib/firmware/fsm_msg_bip85.h
+49 −1 lib/firmware/fsm_msg_common.h
+131 −8 lib/firmware/fsm_msg_ethereum.h
+202 −11 lib/firmware/fsm_msg_hive.h
+51 −8 lib/firmware/fsm_msg_mayachain.h
+74 −13 lib/firmware/fsm_msg_solana.h
+15 −2 lib/firmware/fsm_msg_thorchain.h
+14 −0 lib/firmware/fsm_msg_ton.h
+117 −14 lib/firmware/fsm_msg_tron.h
+40 −6 lib/firmware/fsm_msg_zcash.h
+69 −13 lib/firmware/hive.c
+151 −70 lib/firmware/mayachain.c
+21 −2 lib/firmware/messagemap.def
+50 −19 lib/firmware/recovery_cipher.c
+24 −10 lib/firmware/reset.c
+997 −0 lib/firmware/signed_metadata.c
+44 −11 lib/firmware/solana.c
+222 −4 lib/firmware/storage.c
+43 −0 lib/firmware/storage.h
+2 −1 lib/firmware/storage_versions.inc
+119 −65 lib/firmware/thorchain.c
+9 −0 lib/firmware/transaction.c
+359 −0 lib/firmware/tron.c
+36 −51 lib/transport/CMakeLists.txt
+7 −2 scripts/emulator/python-keepkey-tests.sh
+124 −0 tools/check_sram_budget.py
+3 −1 tools/firmware/CMakeLists.txt
+10 −0 tools/firmware/keepkey.ld
+12 −21 tools/firmware/keepkey_main.c
+10 −0 tools/sram-budgets.json
+15 −12 unittests/crypto/CMakeLists.txt
+26 −11 unittests/firmware/CMakeLists.txt
+11 −0 unittests/firmware/coins.cpp
+173 −0 unittests/firmware/mayachain.cpp
+1,185 −0 unittests/firmware/signed_metadata.cpp
+141 −5 unittests/firmware/solana.cpp
+434 −187 unittests/firmware/storage.cpp
+286 −16 unittests/firmware/thorchain.cpp
+495 −0 unittests/firmware/tron.cpp
38 changes: 38 additions & 0 deletions projects/keepkey-vault/src/bun/rest-api.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2067,6 +2067,44 @@ export function startRestApi(engine: EngineController, auth: AuthStore, port = 1
return json({ address })
}

if (path === '/hive/sign-message' && method === 'POST') {
auth.requireAuth(req)
// Same gates as /addresses/hive: feature flag + firmware ≥ 7.15.0
if (getSetting('hive_enabled') !== '1') return json({ error: 'Hive is disabled' }, 403)
const fwBlock = requireChainSupport('hive')
if (fwBlock) return fwBlock
const wallet = requireWallet(engine)
const body = await parseRequest(req, S.HiveSignMessageRequest)
const messageBytes = body.is_text === false
? Buffer.from(body.message.replace(/^0x/, ''), 'hex')
: Buffer.from(body.message, 'utf8')
if (messageBytes.length === 0 || messageBytes.length > 1024) {
throw new HttpError(400, 'Hive message must be 1–1024 bytes')
}
// Default to the posting role — Keychain signBuffer is overwhelmingly
// dApp login, which verifies against the account's posting authority.
const addressNList = body.addressNList || body.address_n || hiveRolePath('posting', 0)
const result = await emuWrap(() => (wallet as any).hiveSignMessage({
addressNList,
message: new Uint8Array(messageBytes),
}), { operation: 'hiveSignMessage', chain: 'HIVE' })
if (!result?.signature) throw new HttpError(500, 'Hive sign-message: device returned no signature')
const sigBytes = result.signature instanceof Uint8Array ? Buffer.from(result.signature) : Buffer.from(String(result.signature), 'hex')
const pubBytes = result.publicKey instanceof Uint8Array ? Buffer.from(result.publicKey) : Buffer.from(String(result.publicKey), 'hex')
// STM encoding: 'STM' + base58(pub33 || ripemd160(pub33)[0:4])
let stm = ''
if (pubBytes.length === 33) {
const { ripemd160 } = await import('@noble/hashes/ripemd160')
const bs58 = (await import('bs58')).default
const checksum = Buffer.from(ripemd160(pubBytes)).subarray(0, 4)
stm = 'STM' + bs58.encode(Buffer.concat([pubBytes, checksum]))
}
return json({
signature: sigBytes.toString('hex'),
public_key: stm,
})
}

if (path === '/hive/sign-transfer' && method === 'POST') {
auth.requireAuth(req)
// Same gates as /addresses/hive: feature flag + firmware ≥ 7.15.0
Expand Down
10 changes: 10 additions & 0 deletions projects/keepkey-vault/src/bun/schemas.ts
Original file line number Diff line number Diff line change
Expand Up @@ -184,6 +184,16 @@ export const TonSignRequest = z.object({
amount: z.string().optional(), // amount in nanoTON — enables clear-sign on device
}).strip()

/** POST /hive/sign-message — Keychain signBuffer: sign SHA256(message bytes) on-device (fw 7.15.0+) */
export const HiveSignMessageRequest = z.object({
/** SLIP-0048 path; defaults to posting role m/48'/13'/4'/0'/0' (dApp login) */
address_n: z.array(z.number().int()).optional(),
addressNList: z.array(z.number().int()).optional(),
/** Message payload. Default: UTF-8 text. If is_text=false, hex (optional 0x). */
message: z.string().min(1),
is_text: z.boolean().optional(),
}).strip()

/** POST /hive/sign-transfer — Graphene transfer op, serialized + signed on-device (fw 7.15.0+) */
export const HiveSignTransferRequest = z.object({
/** SLIP-0048 path; defaults to active role m/48'/13'/1'/0'/0' */
Expand Down
3 changes: 2 additions & 1 deletion projects/keepkey-vault/src/bun/signing-routes.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
export const SIGNING_ROUTES = new Set([
'/eth/sign-transaction', '/eth/sign-typed-data', '/eth/sign',
'/utxo/sign-transaction', '/xrp/sign-transaction', '/solana/sign-transaction', '/solana/sign-message', '/tron/sign-transaction', '/ton/sign-transaction',
'/hive/sign-transfer',
'/hive/sign-transfer', '/hive/sign-message',
// Message / off-chain signing. The firmware always confirms these on its
// OLED, but that is the device surface only — without these in the set a
// REST caller reaches the device with no in-Vault review. Gate them so the
Expand Down Expand Up @@ -69,6 +69,7 @@ export function requiredSigningFields(path: string): string[] | null {
'/tron/sign-transaction': ['raw_tx', 'rawTx', 'to_address', 'amount'],
'/ton/sign-transaction': ['raw_tx', 'rawTx', 'to_address', 'amount'],
'/hive/sign-transfer': ['from', 'to', 'amount'],
'/hive/sign-message': ['message'],
'/tron/sign-message': ['message'],
'/tron/sign-typed-hash': ['domain_separator_hash'],
'/ton/sign-message': ['message'],
Expand Down