mirror of
https://github.com/ElementsProject/lightning.git
synced 2025-01-18 13:25:43 +01:00
hsmd: create an hsm variant to sign a bolt12 invoice using a tweak on our key.
The current interface, if given a tweak, uses a *different secret key* and tweaks it. This was an early experiment: we will switch to using a secret tweak for invoice_requests like we do for invoice path ids. To make sure there's no funny business, *hsmd* hashes to form the tweak (i.e. no zero tweaks!). Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
This commit is contained in:
parent
09401e34b6
commit
e8a38f111d
@ -26,6 +26,7 @@
|
||||
* v5 with dev_preinit: b93e18534a468a4aa9f7015db42e9c363c32aeee5f9146b36dc953ebbdc3d33c
|
||||
* v5 with preapprove_check: 0ed6dd4ea2c02b67c51b1420b3d07ab2227a4c06ce7e2942d946967687e9baf7
|
||||
* v6 no secret from get_per_commitment_point: 0cad1790beb3473d64355f4cb4f64daa80c28c8a241998b7ef0223385d7ffff9
|
||||
* v6 with sign_bolt12_2 (tweak using node id): 8fcb731279a10af3f95aeb8be1da6b2ced76a1984afa18c5f46a03515d70ea0e
|
||||
*/
|
||||
#define HSM_MIN_VERSION 5
|
||||
#define HSM_MAX_VERSION 6
|
||||
|
@ -26,6 +26,7 @@ HSMD_COMMON_OBJS := \
|
||||
common/base32.o \
|
||||
common/bigsize.o \
|
||||
common/bip32.o \
|
||||
common/bolt12_id.o \
|
||||
common/bolt12_merkle.o \
|
||||
common/channel_id.o \
|
||||
common/daemon.o \
|
||||
|
@ -691,6 +691,7 @@ static struct io_plan *handle_client(struct io_conn *conn, struct client *c)
|
||||
case WIRE_HSMD_SIGN_MESSAGE:
|
||||
case WIRE_HSMD_SIGN_OPTION_WILL_FUND_OFFER:
|
||||
case WIRE_HSMD_SIGN_BOLT12:
|
||||
case WIRE_HSMD_SIGN_BOLT12_2:
|
||||
case WIRE_HSMD_PREAPPROVE_INVOICE:
|
||||
case WIRE_HSMD_PREAPPROVE_KEYSEND:
|
||||
case WIRE_HSMD_PREAPPROVE_INVOICE_CHECK:
|
||||
@ -746,6 +747,7 @@ static struct io_plan *handle_client(struct io_conn *conn, struct client *c)
|
||||
case WIRE_HSMD_SIGN_MESSAGE_REPLY:
|
||||
case WIRE_HSMD_GET_OUTPUT_SCRIPTPUBKEY_REPLY:
|
||||
case WIRE_HSMD_SIGN_BOLT12_REPLY:
|
||||
case WIRE_HSMD_SIGN_BOLT12_2_REPLY:
|
||||
case WIRE_HSMD_PREAPPROVE_INVOICE_REPLY:
|
||||
case WIRE_HSMD_PREAPPROVE_KEYSEND_REPLY:
|
||||
case WIRE_HSMD_PREAPPROVE_INVOICE_CHECK_REPLY:
|
||||
|
@ -378,6 +378,21 @@ msgdata,hsmd_sign_bolt12,publictweak,u8,publictweaklen
|
||||
msgtype,hsmd_sign_bolt12_reply,125
|
||||
msgdata,hsmd_sign_bolt12_reply,sig,bip340sig,
|
||||
|
||||
# Sign a bolt12-style merkle hash (modern)
|
||||
msgtype,hsmd_sign_bolt12_2,41
|
||||
msgdata,hsmd_sign_bolt12_2,messagename,wirestring,
|
||||
msgdata,hsmd_sign_bolt12_2,fieldname,wirestring,
|
||||
msgdata,hsmd_sign_bolt12_2,merkleroot,sha256,
|
||||
# This is for signing with an alias (temporary key), used if *publictweak* not empty.
|
||||
# derive_secret with info, then tweak privkey with SHA256(derived_secret || publictweak).
|
||||
msgdata,hsmd_sign_bolt12_2,infolen,u16,
|
||||
msgdata,hsmd_sign_bolt12_2,info,u8,infolen
|
||||
msgdata,hsmd_sign_bolt12_2,publictweaklen,u16,
|
||||
msgdata,hsmd_sign_bolt12_2,publictweak,u8,publictweaklen
|
||||
|
||||
msgtype,hsmd_sign_bolt12_2_reply,141
|
||||
msgdata,hsmd_sign_bolt12_2_reply,sig,bip340sig,
|
||||
|
||||
# Sign an option_will_fund offer hash
|
||||
msgtype,hsmd_sign_option_will_fund_offer,26
|
||||
msgdata,hsmd_sign_option_will_fund_offer,funding_pubkey,pubkey,
|
||||
|
Can't render this file because it contains an unexpected character in line 169 and column 43.
|
@ -3,6 +3,7 @@
|
||||
#include <ccan/array_size/array_size.h>
|
||||
#include <ccan/crypto/hkdf_sha256/hkdf_sha256.h>
|
||||
#include <ccan/tal/str/str.h>
|
||||
#include <common/bolt12_id.h>
|
||||
#include <common/bolt12_merkle.h>
|
||||
#include <common/hash_u5.h>
|
||||
#include <common/key_derive.h>
|
||||
@ -136,6 +137,7 @@ bool hsmd_check_client_capabilities(struct hsmd_client *client,
|
||||
case WIRE_HSMD_SIGN_MESSAGE:
|
||||
case WIRE_HSMD_GET_OUTPUT_SCRIPTPUBKEY:
|
||||
case WIRE_HSMD_SIGN_BOLT12:
|
||||
case WIRE_HSMD_SIGN_BOLT12_2:
|
||||
case WIRE_HSMD_PREAPPROVE_INVOICE:
|
||||
case WIRE_HSMD_PREAPPROVE_KEYSEND:
|
||||
case WIRE_HSMD_PREAPPROVE_INVOICE_CHECK:
|
||||
@ -181,6 +183,7 @@ bool hsmd_check_client_capabilities(struct hsmd_client *client,
|
||||
case WIRE_HSMD_SIGN_MESSAGE_REPLY:
|
||||
case WIRE_HSMD_GET_OUTPUT_SCRIPTPUBKEY_REPLY:
|
||||
case WIRE_HSMD_SIGN_BOLT12_REPLY:
|
||||
case WIRE_HSMD_SIGN_BOLT12_2_REPLY:
|
||||
case WIRE_HSMD_PREAPPROVE_INVOICE_REPLY:
|
||||
case WIRE_HSMD_PREAPPROVE_KEYSEND_REPLY:
|
||||
case WIRE_HSMD_PREAPPROVE_INVOICE_CHECK_REPLY:
|
||||
@ -783,6 +786,64 @@ static u8 *handle_sign_bolt12(struct hsmd_client *c, const u8 *msg_in)
|
||||
return towire_hsmd_sign_bolt12_reply(NULL, &sig);
|
||||
}
|
||||
|
||||
/*~ lightningd asks us to sign a bolt12 (e.g. offer): modern version */
|
||||
static u8 *handle_sign_bolt12_2(struct hsmd_client *c, const u8 *msg_in)
|
||||
{
|
||||
char *messagename, *fieldname;
|
||||
struct sha256 merkle, sha;
|
||||
struct bip340sig sig;
|
||||
secp256k1_keypair kp;
|
||||
u8 *info;
|
||||
u8 *tweakmessage;
|
||||
|
||||
if (!fromwire_hsmd_sign_bolt12_2(tmpctx, msg_in,
|
||||
&messagename, &fieldname, &merkle,
|
||||
&info, &tweakmessage))
|
||||
return hsmd_status_malformed_request(c, msg_in);
|
||||
|
||||
sighash_from_merkle(messagename, fieldname, &merkle, &sha);
|
||||
|
||||
if (tweakmessage) {
|
||||
struct secret base_secret;
|
||||
struct sha256 tweak;
|
||||
struct privkey tweakedkey;
|
||||
|
||||
/* See handle_derive_secret: this gives a base secret. */
|
||||
hkdf_sha256(&base_secret, sizeof(base_secret), NULL, 0,
|
||||
&secretstuff.derived_secret,
|
||||
sizeof(secretstuff.derived_secret),
|
||||
info, tal_bytelen(info));
|
||||
|
||||
/* This is simply SHA256(secret || tweakmessage) */
|
||||
bolt12_alias_tweak(&base_secret,
|
||||
tweakmessage, tal_bytelen(tweakmessage),
|
||||
&tweak);
|
||||
|
||||
node_key(&tweakedkey, NULL);
|
||||
if (secp256k1_ec_seckey_tweak_add(secp256k1_ctx,
|
||||
tweakedkey.secret.data,
|
||||
tweak.u.u8) != 1)
|
||||
hsmd_status_failed(STATUS_FAIL_INTERNAL_ERROR,
|
||||
"Couldn't tweak key.");
|
||||
if (secp256k1_keypair_create(secp256k1_ctx, &kp,
|
||||
tweakedkey.secret.data) != 1)
|
||||
hsmd_status_failed(STATUS_FAIL_INTERNAL_ERROR,
|
||||
"Failed to derive tweaked keypair");
|
||||
} else {
|
||||
node_schnorrkey(&kp);
|
||||
}
|
||||
|
||||
if (!secp256k1_schnorrsig_sign32(secp256k1_ctx, sig.u8,
|
||||
sha.u.u8,
|
||||
&kp,
|
||||
NULL)) {
|
||||
return hsmd_status_bad_request_fmt(c, msg_in,
|
||||
"Failed to sign bolt12");
|
||||
}
|
||||
|
||||
return towire_hsmd_sign_bolt12_2_reply(NULL, &sig);
|
||||
}
|
||||
|
||||
/*~ lightningd asks us to approve an invoice. This stub implementation
|
||||
* is overriden by fully validating signers that need to track invoice
|
||||
* payments. */
|
||||
@ -2075,6 +2136,8 @@ u8 *hsmd_handle_client_message(const tal_t *ctx, struct hsmd_client *client,
|
||||
return handle_sign_option_will_fund_offer(client, msg);
|
||||
case WIRE_HSMD_SIGN_BOLT12:
|
||||
return handle_sign_bolt12(client, msg);
|
||||
case WIRE_HSMD_SIGN_BOLT12_2:
|
||||
return handle_sign_bolt12_2(client, msg);
|
||||
case WIRE_HSMD_PREAPPROVE_INVOICE:
|
||||
case WIRE_HSMD_PREAPPROVE_INVOICE_CHECK:
|
||||
return handle_preapprove_invoice(client, msg);
|
||||
@ -2167,6 +2230,7 @@ u8 *hsmd_handle_client_message(const tal_t *ctx, struct hsmd_client *client,
|
||||
case WIRE_HSMD_SIGN_MESSAGE_REPLY:
|
||||
case WIRE_HSMD_GET_OUTPUT_SCRIPTPUBKEY_REPLY:
|
||||
case WIRE_HSMD_SIGN_BOLT12_REPLY:
|
||||
case WIRE_HSMD_SIGN_BOLT12_2_REPLY:
|
||||
case WIRE_HSMD_PREAPPROVE_INVOICE_REPLY:
|
||||
case WIRE_HSMD_PREAPPROVE_KEYSEND_REPLY:
|
||||
case WIRE_HSMD_PREAPPROVE_INVOICE_CHECK_REPLY:
|
||||
@ -2197,6 +2261,7 @@ u8 *hsmd_init(struct secret hsm_secret, const u64 hsmd_version,
|
||||
WIRE_HSMD_CHECK_OUTPOINT,
|
||||
WIRE_HSMD_FORGET_CHANNEL,
|
||||
WIRE_HSMD_REVOKE_COMMITMENT_TX,
|
||||
WIRE_HSMD_SIGN_BOLT12_2,
|
||||
WIRE_HSMD_PREAPPROVE_INVOICE_CHECK,
|
||||
WIRE_HSMD_PREAPPROVE_KEYSEND_CHECK,
|
||||
};
|
||||
|
Loading…
Reference in New Issue
Block a user