mirror of
https://github.com/lightningnetwork/lnd.git
synced 2025-03-26 01:33:02 +01:00
multi: add p2tr tapscript key path signing capabilities
This commit is contained in:
parent
78db46be7e
commit
ef98f2df8a
@ -61,6 +61,11 @@ type SignDescriptor struct {
|
||||
// script (PkScript).
|
||||
WitnessScript []byte
|
||||
|
||||
// TaprootKeySpend indicates that instead of a witness script being
|
||||
// spent by the signature that results from this signing request, a
|
||||
// taproot key spend is performed instead.
|
||||
TaprootKeySpend bool
|
||||
|
||||
// Output is the target output which should be signed. The PkScript and
|
||||
// Value fields within the output should be properly populated,
|
||||
// otherwise an invalid signature may be generated.
|
||||
|
@ -2,6 +2,7 @@ package input
|
||||
|
||||
import (
|
||||
"github.com/btcsuite/btcd/blockchain"
|
||||
"github.com/btcsuite/btcd/txscript"
|
||||
"github.com/btcsuite/btcd/wire"
|
||||
"github.com/btcsuite/btcwallet/waddrmgr"
|
||||
)
|
||||
@ -643,6 +644,27 @@ func (twe *TxWeightEstimator) AddTapscriptInput(leafWitnessSize int,
|
||||
return twe
|
||||
}
|
||||
|
||||
// AddTaprootKeySpendInput updates the weight estimate to account for an
|
||||
// additional input spending a segwit v1 pay-to-taproot output using the key
|
||||
// spend path. This accepts the sighash type being used since that has an
|
||||
// influence on the total size of the signature.
|
||||
func (twe *TxWeightEstimator) AddTaprootKeySpendInput(
|
||||
hashType txscript.SigHashType) *TxWeightEstimator {
|
||||
|
||||
twe.inputSize += InputSize
|
||||
|
||||
if hashType == txscript.SigHashDefault {
|
||||
twe.inputWitnessSize += TaprootKeyPathWitnessSize
|
||||
} else {
|
||||
twe.inputWitnessSize += TaprootKeyPathCustomSighashWitnessSize
|
||||
}
|
||||
|
||||
twe.inputCount++
|
||||
twe.hasWitness = true
|
||||
|
||||
return twe
|
||||
}
|
||||
|
||||
// AddNestedP2WKHInput updates the weight estimate to account for an additional
|
||||
// input spending a P2SH output with a nested P2WKH redeem script.
|
||||
func (twe *TxWeightEstimator) AddNestedP2WKHInput() *TxWeightEstimator {
|
||||
|
@ -228,8 +228,11 @@ type SignDescriptor struct {
|
||||
//tweakPriv*sha256(tweakPub || pubKey)) mod N
|
||||
DoubleTweak []byte `protobuf:"bytes,3,opt,name=double_tweak,json=doubleTweak,proto3" json:"double_tweak,omitempty"`
|
||||
//
|
||||
//The full script required to properly redeem the output. This field will
|
||||
//only be populated if a p2wsh or a p2sh output is being signed.
|
||||
//The full script required to properly redeem the output. This field will
|
||||
//only be populated if a p2tr, p2wsh or a p2sh output is being signed. In case
|
||||
//taproot_key_spend is set to true then this value must correspond to the
|
||||
//taproot root hash (in case of a tapscript output) or the tap hashed internal
|
||||
//public key (in case of a BIP-0086 output).
|
||||
WitnessScript []byte `protobuf:"bytes,4,opt,name=witness_script,json=witnessScript,proto3" json:"witness_script,omitempty"`
|
||||
//
|
||||
//A description of the output being spent. The value and script MUST be
|
||||
@ -242,6 +245,12 @@ type SignDescriptor struct {
|
||||
//
|
||||
//The target input within the transaction that should be signed.
|
||||
InputIndex int32 `protobuf:"varint,8,opt,name=input_index,json=inputIndex,proto3" json:"input_index,omitempty"`
|
||||
//
|
||||
//Indicates that this should produce a signature that can be used for the key
|
||||
//spend path of a taproot input. This requires the witness_script field to be
|
||||
//set to the taproot root hash (in case of a tapscript output) or the tap
|
||||
//hashed internal public key (in case of a BIP-0086 output).
|
||||
TaprootKeySpend bool `protobuf:"varint,9,opt,name=taproot_key_spend,json=taprootKeySpend,proto3" json:"taproot_key_spend,omitempty"`
|
||||
}
|
||||
|
||||
func (x *SignDescriptor) Reset() {
|
||||
@ -325,6 +334,13 @@ func (x *SignDescriptor) GetInputIndex() int32 {
|
||||
return 0
|
||||
}
|
||||
|
||||
func (x *SignDescriptor) GetTaprootKeySpend() bool {
|
||||
if x != nil {
|
||||
return x.TaprootKeySpend
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
type SignReq struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
@ -934,7 +950,7 @@ var file_signrpc_signer_proto_rawDesc = []byte{
|
||||
0x54, 0x78, 0x4f, 0x75, 0x74, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x01,
|
||||
0x20, 0x01, 0x28, 0x03, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x1b, 0x0a, 0x09, 0x70,
|
||||
0x6b, 0x5f, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x08,
|
||||
0x70, 0x6b, 0x53, 0x63, 0x72, 0x69, 0x70, 0x74, 0x22, 0x93, 0x02, 0x0a, 0x0e, 0x53, 0x69, 0x67,
|
||||
0x70, 0x6b, 0x53, 0x63, 0x72, 0x69, 0x70, 0x74, 0x22, 0xbf, 0x02, 0x0a, 0x0e, 0x53, 0x69, 0x67,
|
||||
0x6e, 0x44, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x6f, 0x72, 0x12, 0x31, 0x0a, 0x08, 0x6b,
|
||||
0x65, 0x79, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x16, 0x2e,
|
||||
0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x4b, 0x65, 0x79, 0x44, 0x65, 0x73, 0x63, 0x72,
|
||||
@ -951,88 +967,91 @@ var file_signrpc_signer_proto_rawDesc = []byte{
|
||||
0x70, 0x75, 0x74, 0x12, 0x18, 0x0a, 0x07, 0x73, 0x69, 0x67, 0x68, 0x61, 0x73, 0x68, 0x18, 0x07,
|
||||
0x20, 0x01, 0x28, 0x0d, 0x52, 0x07, 0x73, 0x69, 0x67, 0x68, 0x61, 0x73, 0x68, 0x12, 0x1f, 0x0a,
|
||||
0x0b, 0x69, 0x6e, 0x70, 0x75, 0x74, 0x5f, 0x69, 0x6e, 0x64, 0x65, 0x78, 0x18, 0x08, 0x20, 0x01,
|
||||
0x28, 0x05, 0x52, 0x0a, 0x69, 0x6e, 0x70, 0x75, 0x74, 0x49, 0x6e, 0x64, 0x65, 0x78, 0x22, 0x96,
|
||||
0x01, 0x0a, 0x07, 0x53, 0x69, 0x67, 0x6e, 0x52, 0x65, 0x71, 0x12, 0x20, 0x0a, 0x0c, 0x72, 0x61,
|
||||
0x77, 0x5f, 0x74, 0x78, 0x5f, 0x62, 0x79, 0x74, 0x65, 0x73, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c,
|
||||
0x52, 0x0a, 0x72, 0x61, 0x77, 0x54, 0x78, 0x42, 0x79, 0x74, 0x65, 0x73, 0x12, 0x36, 0x0a, 0x0a,
|
||||
0x73, 0x69, 0x67, 0x6e, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b,
|
||||
0x32, 0x17, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x53, 0x69, 0x67, 0x6e, 0x44,
|
||||
0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x6f, 0x72, 0x52, 0x09, 0x73, 0x69, 0x67, 0x6e, 0x44,
|
||||
0x65, 0x73, 0x63, 0x73, 0x12, 0x31, 0x0a, 0x0c, 0x70, 0x72, 0x65, 0x76, 0x5f, 0x6f, 0x75, 0x74,
|
||||
0x70, 0x75, 0x74, 0x73, 0x18, 0x03, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0e, 0x2e, 0x73, 0x69, 0x67,
|
||||
0x6e, 0x72, 0x70, 0x63, 0x2e, 0x54, 0x78, 0x4f, 0x75, 0x74, 0x52, 0x0b, 0x70, 0x72, 0x65, 0x76,
|
||||
0x4f, 0x75, 0x74, 0x70, 0x75, 0x74, 0x73, 0x22, 0x25, 0x0a, 0x08, 0x53, 0x69, 0x67, 0x6e, 0x52,
|
||||
0x65, 0x73, 0x70, 0x12, 0x19, 0x0a, 0x08, 0x72, 0x61, 0x77, 0x5f, 0x73, 0x69, 0x67, 0x73, 0x18,
|
||||
0x01, 0x20, 0x03, 0x28, 0x0c, 0x52, 0x07, 0x72, 0x61, 0x77, 0x53, 0x69, 0x67, 0x73, 0x22, 0x46,
|
||||
0x0a, 0x0b, 0x49, 0x6e, 0x70, 0x75, 0x74, 0x53, 0x63, 0x72, 0x69, 0x70, 0x74, 0x12, 0x18, 0x0a,
|
||||
0x07, 0x77, 0x69, 0x74, 0x6e, 0x65, 0x73, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0c, 0x52, 0x07,
|
||||
0x77, 0x69, 0x74, 0x6e, 0x65, 0x73, 0x73, 0x12, 0x1d, 0x0a, 0x0a, 0x73, 0x69, 0x67, 0x5f, 0x73,
|
||||
0x63, 0x72, 0x69, 0x70, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x09, 0x73, 0x69, 0x67,
|
||||
0x53, 0x63, 0x72, 0x69, 0x70, 0x74, 0x22, 0x4c, 0x0a, 0x0f, 0x49, 0x6e, 0x70, 0x75, 0x74, 0x53,
|
||||
0x63, 0x72, 0x69, 0x70, 0x74, 0x52, 0x65, 0x73, 0x70, 0x12, 0x39, 0x0a, 0x0d, 0x69, 0x6e, 0x70,
|
||||
0x75, 0x74, 0x5f, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b,
|
||||
0x32, 0x14, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x49, 0x6e, 0x70, 0x75, 0x74,
|
||||
0x53, 0x63, 0x72, 0x69, 0x70, 0x74, 0x52, 0x0c, 0x69, 0x6e, 0x70, 0x75, 0x74, 0x53, 0x63, 0x72,
|
||||
0x69, 0x70, 0x74, 0x73, 0x22, 0x92, 0x01, 0x0a, 0x0e, 0x53, 0x69, 0x67, 0x6e, 0x4d, 0x65, 0x73,
|
||||
0x73, 0x61, 0x67, 0x65, 0x52, 0x65, 0x71, 0x12, 0x10, 0x0a, 0x03, 0x6d, 0x73, 0x67, 0x18, 0x01,
|
||||
0x20, 0x01, 0x28, 0x0c, 0x52, 0x03, 0x6d, 0x73, 0x67, 0x12, 0x2c, 0x0a, 0x07, 0x6b, 0x65, 0x79,
|
||||
0x5f, 0x6c, 0x6f, 0x63, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x73, 0x69, 0x67,
|
||||
0x6e, 0x72, 0x70, 0x63, 0x2e, 0x4b, 0x65, 0x79, 0x4c, 0x6f, 0x63, 0x61, 0x74, 0x6f, 0x72, 0x52,
|
||||
0x06, 0x6b, 0x65, 0x79, 0x4c, 0x6f, 0x63, 0x12, 0x1f, 0x0a, 0x0b, 0x64, 0x6f, 0x75, 0x62, 0x6c,
|
||||
0x65, 0x5f, 0x68, 0x61, 0x73, 0x68, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0a, 0x64, 0x6f,
|
||||
0x75, 0x62, 0x6c, 0x65, 0x48, 0x61, 0x73, 0x68, 0x12, 0x1f, 0x0a, 0x0b, 0x63, 0x6f, 0x6d, 0x70,
|
||||
0x61, 0x63, 0x74, 0x5f, 0x73, 0x69, 0x67, 0x18, 0x04, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0a, 0x63,
|
||||
0x6f, 0x6d, 0x70, 0x61, 0x63, 0x74, 0x53, 0x69, 0x67, 0x22, 0x2f, 0x0a, 0x0f, 0x53, 0x69, 0x67,
|
||||
0x6e, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x65, 0x73, 0x70, 0x12, 0x1c, 0x0a, 0x09,
|
||||
0x73, 0x69, 0x67, 0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52,
|
||||
0x09, 0x73, 0x69, 0x67, 0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x22, 0x5a, 0x0a, 0x10, 0x56, 0x65,
|
||||
0x72, 0x69, 0x66, 0x79, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x65, 0x71, 0x12, 0x10,
|
||||
0x0a, 0x03, 0x6d, 0x73, 0x67, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x03, 0x6d, 0x73, 0x67,
|
||||
0x12, 0x1c, 0x0a, 0x09, 0x73, 0x69, 0x67, 0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x18, 0x02, 0x20,
|
||||
0x01, 0x28, 0x0c, 0x52, 0x09, 0x73, 0x69, 0x67, 0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x12, 0x16,
|
||||
0x0a, 0x06, 0x70, 0x75, 0x62, 0x6b, 0x65, 0x79, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x06,
|
||||
0x70, 0x75, 0x62, 0x6b, 0x65, 0x79, 0x22, 0x29, 0x0a, 0x11, 0x56, 0x65, 0x72, 0x69, 0x66, 0x79,
|
||||
0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x65, 0x73, 0x70, 0x12, 0x14, 0x0a, 0x05, 0x76,
|
||||
0x61, 0x6c, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x69,
|
||||
0x64, 0x22, 0xa2, 0x01, 0x0a, 0x10, 0x53, 0x68, 0x61, 0x72, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x52,
|
||||
0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x29, 0x0a, 0x10, 0x65, 0x70, 0x68, 0x65, 0x6d, 0x65,
|
||||
0x72, 0x61, 0x6c, 0x5f, 0x70, 0x75, 0x62, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c,
|
||||
0x52, 0x0f, 0x65, 0x70, 0x68, 0x65, 0x6d, 0x65, 0x72, 0x61, 0x6c, 0x50, 0x75, 0x62, 0x6b, 0x65,
|
||||
0x79, 0x12, 0x30, 0x0a, 0x07, 0x6b, 0x65, 0x79, 0x5f, 0x6c, 0x6f, 0x63, 0x18, 0x02, 0x20, 0x01,
|
||||
0x28, 0x0b, 0x32, 0x13, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x4b, 0x65, 0x79,
|
||||
0x4c, 0x6f, 0x63, 0x61, 0x74, 0x6f, 0x72, 0x42, 0x02, 0x18, 0x01, 0x52, 0x06, 0x6b, 0x65, 0x79,
|
||||
0x4c, 0x6f, 0x63, 0x12, 0x31, 0x0a, 0x08, 0x6b, 0x65, 0x79, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x18,
|
||||
0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e,
|
||||
0x4b, 0x65, 0x79, 0x44, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x6f, 0x72, 0x52, 0x07, 0x6b,
|
||||
0x65, 0x79, 0x44, 0x65, 0x73, 0x63, 0x22, 0x32, 0x0a, 0x11, 0x53, 0x68, 0x61, 0x72, 0x65, 0x64,
|
||||
0x4b, 0x65, 0x79, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x1d, 0x0a, 0x0a, 0x73,
|
||||
0x68, 0x61, 0x72, 0x65, 0x64, 0x5f, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52,
|
||||
0x09, 0x73, 0x68, 0x61, 0x72, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x32, 0xd4, 0x02, 0x0a, 0x06, 0x53,
|
||||
0x69, 0x67, 0x6e, 0x65, 0x72, 0x12, 0x34, 0x0a, 0x0d, 0x53, 0x69, 0x67, 0x6e, 0x4f, 0x75, 0x74,
|
||||
0x70, 0x75, 0x74, 0x52, 0x61, 0x77, 0x12, 0x10, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63,
|
||||
0x2e, 0x53, 0x69, 0x67, 0x6e, 0x52, 0x65, 0x71, 0x1a, 0x11, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72,
|
||||
0x70, 0x63, 0x2e, 0x53, 0x69, 0x67, 0x6e, 0x52, 0x65, 0x73, 0x70, 0x12, 0x40, 0x0a, 0x12, 0x43,
|
||||
0x6f, 0x6d, 0x70, 0x75, 0x74, 0x65, 0x49, 0x6e, 0x70, 0x75, 0x74, 0x53, 0x63, 0x72, 0x69, 0x70,
|
||||
0x74, 0x12, 0x10, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x53, 0x69, 0x67, 0x6e,
|
||||
0x52, 0x65, 0x71, 0x1a, 0x18, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x49, 0x6e,
|
||||
0x70, 0x75, 0x74, 0x53, 0x63, 0x72, 0x69, 0x70, 0x74, 0x52, 0x65, 0x73, 0x70, 0x12, 0x40, 0x0a,
|
||||
0x0b, 0x53, 0x69, 0x67, 0x6e, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x17, 0x2e, 0x73,
|
||||
0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x53, 0x69, 0x67, 0x6e, 0x4d, 0x65, 0x73, 0x73, 0x61,
|
||||
0x67, 0x65, 0x52, 0x65, 0x71, 0x1a, 0x18, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e,
|
||||
0x53, 0x69, 0x67, 0x6e, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x65, 0x73, 0x70, 0x12,
|
||||
0x46, 0x0a, 0x0d, 0x56, 0x65, 0x72, 0x69, 0x66, 0x79, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65,
|
||||
0x12, 0x19, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x56, 0x65, 0x72, 0x69, 0x66,
|
||||
0x79, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x65, 0x71, 0x1a, 0x1a, 0x2e, 0x73, 0x69,
|
||||
0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x56, 0x65, 0x72, 0x69, 0x66, 0x79, 0x4d, 0x65, 0x73, 0x73,
|
||||
0x61, 0x67, 0x65, 0x52, 0x65, 0x73, 0x70, 0x12, 0x48, 0x0a, 0x0f, 0x44, 0x65, 0x72, 0x69, 0x76,
|
||||
0x65, 0x53, 0x68, 0x61, 0x72, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x12, 0x19, 0x2e, 0x73, 0x69, 0x67,
|
||||
0x6e, 0x72, 0x70, 0x63, 0x2e, 0x53, 0x68, 0x61, 0x72, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x52, 0x65,
|
||||
0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1a, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e,
|
||||
0x53, 0x68, 0x61, 0x72, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73,
|
||||
0x65, 0x42, 0x2f, 0x5a, 0x2d, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f,
|
||||
0x6c, 0x69, 0x67, 0x68, 0x74, 0x6e, 0x69, 0x6e, 0x67, 0x6e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b,
|
||||
0x2f, 0x6c, 0x6e, 0x64, 0x2f, 0x6c, 0x6e, 0x72, 0x70, 0x63, 0x2f, 0x73, 0x69, 0x67, 0x6e, 0x72,
|
||||
0x70, 0x63, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
|
||||
0x28, 0x05, 0x52, 0x0a, 0x69, 0x6e, 0x70, 0x75, 0x74, 0x49, 0x6e, 0x64, 0x65, 0x78, 0x12, 0x2a,
|
||||
0x0a, 0x11, 0x74, 0x61, 0x70, 0x72, 0x6f, 0x6f, 0x74, 0x5f, 0x6b, 0x65, 0x79, 0x5f, 0x73, 0x70,
|
||||
0x65, 0x6e, 0x64, 0x18, 0x09, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0f, 0x74, 0x61, 0x70, 0x72, 0x6f,
|
||||
0x6f, 0x74, 0x4b, 0x65, 0x79, 0x53, 0x70, 0x65, 0x6e, 0x64, 0x22, 0x96, 0x01, 0x0a, 0x07, 0x53,
|
||||
0x69, 0x67, 0x6e, 0x52, 0x65, 0x71, 0x12, 0x20, 0x0a, 0x0c, 0x72, 0x61, 0x77, 0x5f, 0x74, 0x78,
|
||||
0x5f, 0x62, 0x79, 0x74, 0x65, 0x73, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x0a, 0x72, 0x61,
|
||||
0x77, 0x54, 0x78, 0x42, 0x79, 0x74, 0x65, 0x73, 0x12, 0x36, 0x0a, 0x0a, 0x73, 0x69, 0x67, 0x6e,
|
||||
0x5f, 0x64, 0x65, 0x73, 0x63, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x17, 0x2e, 0x73,
|
||||
0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x53, 0x69, 0x67, 0x6e, 0x44, 0x65, 0x73, 0x63, 0x72,
|
||||
0x69, 0x70, 0x74, 0x6f, 0x72, 0x52, 0x09, 0x73, 0x69, 0x67, 0x6e, 0x44, 0x65, 0x73, 0x63, 0x73,
|
||||
0x12, 0x31, 0x0a, 0x0c, 0x70, 0x72, 0x65, 0x76, 0x5f, 0x6f, 0x75, 0x74, 0x70, 0x75, 0x74, 0x73,
|
||||
0x18, 0x03, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0e, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63,
|
||||
0x2e, 0x54, 0x78, 0x4f, 0x75, 0x74, 0x52, 0x0b, 0x70, 0x72, 0x65, 0x76, 0x4f, 0x75, 0x74, 0x70,
|
||||
0x75, 0x74, 0x73, 0x22, 0x25, 0x0a, 0x08, 0x53, 0x69, 0x67, 0x6e, 0x52, 0x65, 0x73, 0x70, 0x12,
|
||||
0x19, 0x0a, 0x08, 0x72, 0x61, 0x77, 0x5f, 0x73, 0x69, 0x67, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28,
|
||||
0x0c, 0x52, 0x07, 0x72, 0x61, 0x77, 0x53, 0x69, 0x67, 0x73, 0x22, 0x46, 0x0a, 0x0b, 0x49, 0x6e,
|
||||
0x70, 0x75, 0x74, 0x53, 0x63, 0x72, 0x69, 0x70, 0x74, 0x12, 0x18, 0x0a, 0x07, 0x77, 0x69, 0x74,
|
||||
0x6e, 0x65, 0x73, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0c, 0x52, 0x07, 0x77, 0x69, 0x74, 0x6e,
|
||||
0x65, 0x73, 0x73, 0x12, 0x1d, 0x0a, 0x0a, 0x73, 0x69, 0x67, 0x5f, 0x73, 0x63, 0x72, 0x69, 0x70,
|
||||
0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x09, 0x73, 0x69, 0x67, 0x53, 0x63, 0x72, 0x69,
|
||||
0x70, 0x74, 0x22, 0x4c, 0x0a, 0x0f, 0x49, 0x6e, 0x70, 0x75, 0x74, 0x53, 0x63, 0x72, 0x69, 0x70,
|
||||
0x74, 0x52, 0x65, 0x73, 0x70, 0x12, 0x39, 0x0a, 0x0d, 0x69, 0x6e, 0x70, 0x75, 0x74, 0x5f, 0x73,
|
||||
0x63, 0x72, 0x69, 0x70, 0x74, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x14, 0x2e, 0x73,
|
||||
0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x49, 0x6e, 0x70, 0x75, 0x74, 0x53, 0x63, 0x72, 0x69,
|
||||
0x70, 0x74, 0x52, 0x0c, 0x69, 0x6e, 0x70, 0x75, 0x74, 0x53, 0x63, 0x72, 0x69, 0x70, 0x74, 0x73,
|
||||
0x22, 0x92, 0x01, 0x0a, 0x0e, 0x53, 0x69, 0x67, 0x6e, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65,
|
||||
0x52, 0x65, 0x71, 0x12, 0x10, 0x0a, 0x03, 0x6d, 0x73, 0x67, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c,
|
||||
0x52, 0x03, 0x6d, 0x73, 0x67, 0x12, 0x2c, 0x0a, 0x07, 0x6b, 0x65, 0x79, 0x5f, 0x6c, 0x6f, 0x63,
|
||||
0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63,
|
||||
0x2e, 0x4b, 0x65, 0x79, 0x4c, 0x6f, 0x63, 0x61, 0x74, 0x6f, 0x72, 0x52, 0x06, 0x6b, 0x65, 0x79,
|
||||
0x4c, 0x6f, 0x63, 0x12, 0x1f, 0x0a, 0x0b, 0x64, 0x6f, 0x75, 0x62, 0x6c, 0x65, 0x5f, 0x68, 0x61,
|
||||
0x73, 0x68, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0a, 0x64, 0x6f, 0x75, 0x62, 0x6c, 0x65,
|
||||
0x48, 0x61, 0x73, 0x68, 0x12, 0x1f, 0x0a, 0x0b, 0x63, 0x6f, 0x6d, 0x70, 0x61, 0x63, 0x74, 0x5f,
|
||||
0x73, 0x69, 0x67, 0x18, 0x04, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0a, 0x63, 0x6f, 0x6d, 0x70, 0x61,
|
||||
0x63, 0x74, 0x53, 0x69, 0x67, 0x22, 0x2f, 0x0a, 0x0f, 0x53, 0x69, 0x67, 0x6e, 0x4d, 0x65, 0x73,
|
||||
0x73, 0x61, 0x67, 0x65, 0x52, 0x65, 0x73, 0x70, 0x12, 0x1c, 0x0a, 0x09, 0x73, 0x69, 0x67, 0x6e,
|
||||
0x61, 0x74, 0x75, 0x72, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x09, 0x73, 0x69, 0x67,
|
||||
0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x22, 0x5a, 0x0a, 0x10, 0x56, 0x65, 0x72, 0x69, 0x66, 0x79,
|
||||
0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x65, 0x71, 0x12, 0x10, 0x0a, 0x03, 0x6d, 0x73,
|
||||
0x67, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x03, 0x6d, 0x73, 0x67, 0x12, 0x1c, 0x0a, 0x09,
|
||||
0x73, 0x69, 0x67, 0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0c, 0x52,
|
||||
0x09, 0x73, 0x69, 0x67, 0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x12, 0x16, 0x0a, 0x06, 0x70, 0x75,
|
||||
0x62, 0x6b, 0x65, 0x79, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x06, 0x70, 0x75, 0x62, 0x6b,
|
||||
0x65, 0x79, 0x22, 0x29, 0x0a, 0x11, 0x56, 0x65, 0x72, 0x69, 0x66, 0x79, 0x4d, 0x65, 0x73, 0x73,
|
||||
0x61, 0x67, 0x65, 0x52, 0x65, 0x73, 0x70, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x69, 0x64,
|
||||
0x18, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x69, 0x64, 0x22, 0xa2, 0x01,
|
||||
0x0a, 0x10, 0x53, 0x68, 0x61, 0x72, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x52, 0x65, 0x71, 0x75, 0x65,
|
||||
0x73, 0x74, 0x12, 0x29, 0x0a, 0x10, 0x65, 0x70, 0x68, 0x65, 0x6d, 0x65, 0x72, 0x61, 0x6c, 0x5f,
|
||||
0x70, 0x75, 0x62, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x0f, 0x65, 0x70,
|
||||
0x68, 0x65, 0x6d, 0x65, 0x72, 0x61, 0x6c, 0x50, 0x75, 0x62, 0x6b, 0x65, 0x79, 0x12, 0x30, 0x0a,
|
||||
0x07, 0x6b, 0x65, 0x79, 0x5f, 0x6c, 0x6f, 0x63, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x13,
|
||||
0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x4b, 0x65, 0x79, 0x4c, 0x6f, 0x63, 0x61,
|
||||
0x74, 0x6f, 0x72, 0x42, 0x02, 0x18, 0x01, 0x52, 0x06, 0x6b, 0x65, 0x79, 0x4c, 0x6f, 0x63, 0x12,
|
||||
0x31, 0x0a, 0x08, 0x6b, 0x65, 0x79, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x18, 0x03, 0x20, 0x01, 0x28,
|
||||
0x0b, 0x32, 0x16, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x4b, 0x65, 0x79, 0x44,
|
||||
0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x6f, 0x72, 0x52, 0x07, 0x6b, 0x65, 0x79, 0x44, 0x65,
|
||||
0x73, 0x63, 0x22, 0x32, 0x0a, 0x11, 0x53, 0x68, 0x61, 0x72, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x52,
|
||||
0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x1d, 0x0a, 0x0a, 0x73, 0x68, 0x61, 0x72, 0x65,
|
||||
0x64, 0x5f, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x09, 0x73, 0x68, 0x61,
|
||||
0x72, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x32, 0xd4, 0x02, 0x0a, 0x06, 0x53, 0x69, 0x67, 0x6e, 0x65,
|
||||
0x72, 0x12, 0x34, 0x0a, 0x0d, 0x53, 0x69, 0x67, 0x6e, 0x4f, 0x75, 0x74, 0x70, 0x75, 0x74, 0x52,
|
||||
0x61, 0x77, 0x12, 0x10, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x53, 0x69, 0x67,
|
||||
0x6e, 0x52, 0x65, 0x71, 0x1a, 0x11, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x53,
|
||||
0x69, 0x67, 0x6e, 0x52, 0x65, 0x73, 0x70, 0x12, 0x40, 0x0a, 0x12, 0x43, 0x6f, 0x6d, 0x70, 0x75,
|
||||
0x74, 0x65, 0x49, 0x6e, 0x70, 0x75, 0x74, 0x53, 0x63, 0x72, 0x69, 0x70, 0x74, 0x12, 0x10, 0x2e,
|
||||
0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x53, 0x69, 0x67, 0x6e, 0x52, 0x65, 0x71, 0x1a,
|
||||
0x18, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x49, 0x6e, 0x70, 0x75, 0x74, 0x53,
|
||||
0x63, 0x72, 0x69, 0x70, 0x74, 0x52, 0x65, 0x73, 0x70, 0x12, 0x40, 0x0a, 0x0b, 0x53, 0x69, 0x67,
|
||||
0x6e, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x17, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72,
|
||||
0x70, 0x63, 0x2e, 0x53, 0x69, 0x67, 0x6e, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x65,
|
||||
0x71, 0x1a, 0x18, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x53, 0x69, 0x67, 0x6e,
|
||||
0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x65, 0x73, 0x70, 0x12, 0x46, 0x0a, 0x0d, 0x56,
|
||||
0x65, 0x72, 0x69, 0x66, 0x79, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x19, 0x2e, 0x73,
|
||||
0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x56, 0x65, 0x72, 0x69, 0x66, 0x79, 0x4d, 0x65, 0x73,
|
||||
0x73, 0x61, 0x67, 0x65, 0x52, 0x65, 0x71, 0x1a, 0x1a, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70,
|
||||
0x63, 0x2e, 0x56, 0x65, 0x72, 0x69, 0x66, 0x79, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52,
|
||||
0x65, 0x73, 0x70, 0x12, 0x48, 0x0a, 0x0f, 0x44, 0x65, 0x72, 0x69, 0x76, 0x65, 0x53, 0x68, 0x61,
|
||||
0x72, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x12, 0x19, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63,
|
||||
0x2e, 0x53, 0x68, 0x61, 0x72, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73,
|
||||
0x74, 0x1a, 0x1a, 0x2e, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x2e, 0x53, 0x68, 0x61, 0x72,
|
||||
0x65, 0x64, 0x4b, 0x65, 0x79, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x42, 0x2f, 0x5a,
|
||||
0x2d, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x6c, 0x69, 0x67, 0x68,
|
||||
0x74, 0x6e, 0x69, 0x6e, 0x67, 0x6e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b, 0x2f, 0x6c, 0x6e, 0x64,
|
||||
0x2f, 0x6c, 0x6e, 0x72, 0x70, 0x63, 0x2f, 0x73, 0x69, 0x67, 0x6e, 0x72, 0x70, 0x63, 0x62, 0x06,
|
||||
0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
|
||||
}
|
||||
|
||||
var (
|
||||
|
@ -129,8 +129,11 @@ message SignDescriptor {
|
||||
bytes double_tweak = 3;
|
||||
|
||||
/*
|
||||
The full script required to properly redeem the output. This field will
|
||||
only be populated if a p2wsh or a p2sh output is being signed.
|
||||
The full script required to properly redeem the output. This field will
|
||||
only be populated if a p2tr, p2wsh or a p2sh output is being signed. In case
|
||||
taproot_key_spend is set to true then this value must correspond to the
|
||||
taproot root hash (in case of a tapscript output) or the tap hashed internal
|
||||
public key (in case of a BIP-0086 output).
|
||||
*/
|
||||
bytes witness_script = 4;
|
||||
|
||||
@ -150,6 +153,14 @@ message SignDescriptor {
|
||||
The target input within the transaction that should be signed.
|
||||
*/
|
||||
int32 input_index = 8;
|
||||
|
||||
/*
|
||||
Indicates that this should produce a signature that can be used for the key
|
||||
spend path of a taproot input. This requires the witness_script field to be
|
||||
set to the taproot root hash (in case of a tapscript output) or the tap
|
||||
hashed internal public key (in case of a BIP-0086 output).
|
||||
*/
|
||||
bool taproot_key_spend = 9;
|
||||
}
|
||||
|
||||
message SignReq {
|
||||
|
@ -325,7 +325,7 @@
|
||||
"witness_script": {
|
||||
"type": "string",
|
||||
"format": "byte",
|
||||
"description": "The full script required to properly redeem the output. This field will\nonly be populated if a p2wsh or a p2sh output is being signed."
|
||||
"description": "The full script required to properly redeem the output. This field will\nonly be populated if a p2tr, p2wsh or a p2sh output is being signed. In case\ntaproot_key_spend is set to true then this value must correspond to the\ntaproot root hash (in case of a tapscript output) or the tap hashed internal\npublic key (in case of a BIP-0086 output)."
|
||||
},
|
||||
"output": {
|
||||
"$ref": "#/definitions/signrpcTxOut",
|
||||
@ -340,6 +340,10 @@
|
||||
"type": "integer",
|
||||
"format": "int32",
|
||||
"description": "The target input within the transaction that should be signed."
|
||||
},
|
||||
"taproot_key_spend": {
|
||||
"type": "boolean",
|
||||
"description": "Indicates that this should produce a signature that can be used for the key\nspend path of a taproot input. This requires the witness_script field to be\nset to the taproot root hash (in case of a tapscript output) or the tap\nhashed internal public key (in case of a BIP-0086 output)."
|
||||
}
|
||||
}
|
||||
},
|
||||
|
@ -341,9 +341,9 @@ func (s *Server) SignOutputRaw(_ context.Context, in *SignReq) (*SignResp,
|
||||
// output. We'll send it in the WitnessScript field, the
|
||||
// SignOutputRaw RPC will know what to do with it when creating
|
||||
// the sighash.
|
||||
if len(signDesc.WitnessScript) == 0 {
|
||||
if len(signDesc.WitnessScript) == 0 && !signDesc.TaprootKeySpend {
|
||||
return nil, fmt.Errorf("witness script MUST be " +
|
||||
"specified")
|
||||
"specified for non-taproot-key-spends")
|
||||
}
|
||||
|
||||
// If the users provided a double tweak, then we'll need to
|
||||
@ -363,9 +363,10 @@ func (s *Server) SignOutputRaw(_ context.Context, in *SignReq) (*SignResp,
|
||||
KeyLocator: keyLoc,
|
||||
PubKey: targetPubKey,
|
||||
},
|
||||
SingleTweak: signDesc.SingleTweak,
|
||||
DoubleTweak: tweakPrivKey,
|
||||
WitnessScript: signDesc.WitnessScript,
|
||||
SingleTweak: signDesc.SingleTweak,
|
||||
DoubleTweak: tweakPrivKey,
|
||||
WitnessScript: signDesc.WitnessScript,
|
||||
TaprootKeySpend: signDesc.TaprootKeySpend,
|
||||
Output: &wire.TxOut{
|
||||
Value: signDesc.Output.Value,
|
||||
PkScript: signDesc.Output.PkScript,
|
||||
|
@ -3,6 +3,7 @@ package itest
|
||||
import (
|
||||
"bytes"
|
||||
"context"
|
||||
"crypto/sha256"
|
||||
"encoding/hex"
|
||||
"testing"
|
||||
|
||||
@ -30,6 +31,7 @@ func testTaproot(net *lntest.NetworkHarness, t *harnessTest) {
|
||||
|
||||
testTaprootKeySpend(ctxt, t, net)
|
||||
testTaprootScriptSpend(ctxt, t, net)
|
||||
testTaprootKeySpendRPC(ctxt, t, net)
|
||||
}
|
||||
|
||||
// testTaprootKeySpend tests sending to and spending from p2tr key spend only
|
||||
@ -257,6 +259,147 @@ func testTaprootScriptSpend(ctxt context.Context, t *harnessTest,
|
||||
mineBlocks(t, net, 1, 1)
|
||||
}
|
||||
|
||||
// testTaprootKeySpendRPC tests that a tapscript address can also be spent using
|
||||
// the key spend path through the RPC.
|
||||
func testTaprootKeySpendRPC(ctxt context.Context, t *harnessTest,
|
||||
net *lntest.NetworkHarness) {
|
||||
|
||||
// For the next step, we need a public key. Let's use a special family
|
||||
// for this.
|
||||
const taprootKeyFamily = 77
|
||||
keyDesc, err := net.Alice.WalletKitClient.DeriveNextKey(
|
||||
ctxt, &walletrpc.KeyReq{
|
||||
KeyFamily: taprootKeyFamily,
|
||||
},
|
||||
)
|
||||
require.NoError(t.t, err)
|
||||
|
||||
internalKey, err := btcec.ParsePubKey(keyDesc.RawKeyBytes)
|
||||
require.NoError(t.t, err)
|
||||
|
||||
// We want to make sure we can still use a tweaked key, even if it ends
|
||||
// up being essentially double tweaked because of the taproot root hash.
|
||||
dummyKeyTweak := sha256.Sum256([]byte("this is a key tweak"))
|
||||
internalKey = input.TweakPubKeyWithTweak(internalKey, dummyKeyTweak[:])
|
||||
|
||||
// Let's create a taproot script output now. This is a hash lock with a
|
||||
// simple preimage of "foobar".
|
||||
leaf1 := testScriptHashLock(t.t, []byte("foobar"))
|
||||
|
||||
rootHash := leaf1.TapHash()
|
||||
taprootKey := txscript.ComputeTaprootOutputKey(internalKey, rootHash[:])
|
||||
|
||||
tapScriptAddr, err := btcutil.NewAddressTaproot(
|
||||
schnorr.SerializePubKey(taprootKey), harnessNetParams,
|
||||
)
|
||||
require.NoError(t.t, err)
|
||||
p2trPkScript, err := txscript.PayToAddrScript(tapScriptAddr)
|
||||
require.NoError(t.t, err)
|
||||
|
||||
// Send some coins to the generated tapscript address.
|
||||
_, err = net.Alice.SendCoins(ctxt, &lnrpc.SendCoinsRequest{
|
||||
Addr: tapScriptAddr.String(),
|
||||
Amount: 800_000,
|
||||
})
|
||||
require.NoError(t.t, err)
|
||||
|
||||
// Wait until the TX is found in the mempool.
|
||||
txid, err := waitForTxInMempool(net.Miner.Client, minerMempoolTimeout)
|
||||
require.NoError(t.t, err)
|
||||
|
||||
p2trOutputIndex := getOutputIndex(
|
||||
t, net.Miner, txid, tapScriptAddr.String(),
|
||||
)
|
||||
|
||||
// Clear the mempool.
|
||||
mineBlocks(t, net, 1, 1)
|
||||
|
||||
// Spend the output again, this time back to a p2wkh address.
|
||||
p2wkhAddr, p2wkhPkScript := newAddrWithScript(
|
||||
ctxt, t.t, net.Alice, lnrpc.AddressType_WITNESS_PUBKEY_HASH,
|
||||
)
|
||||
|
||||
// Create fee estimation for a p2tr input and p2wkh output.
|
||||
feeRate := chainfee.SatPerKWeight(12500)
|
||||
estimator := input.TxWeightEstimator{}
|
||||
estimator.AddTaprootKeySpendInput(txscript.SigHashDefault)
|
||||
estimator.AddP2WKHOutput()
|
||||
estimatedWeight := int64(estimator.Weight())
|
||||
requiredFee := feeRate.FeeForWeight(estimatedWeight)
|
||||
|
||||
tx := wire.NewMsgTx(2)
|
||||
tx.TxIn = []*wire.TxIn{{
|
||||
PreviousOutPoint: wire.OutPoint{
|
||||
Hash: *txid,
|
||||
Index: uint32(p2trOutputIndex),
|
||||
},
|
||||
}}
|
||||
value := int64(800_000 - requiredFee)
|
||||
tx.TxOut = []*wire.TxOut{{
|
||||
PkScript: p2wkhPkScript,
|
||||
Value: value,
|
||||
}}
|
||||
|
||||
var buf bytes.Buffer
|
||||
require.NoError(t.t, tx.Serialize(&buf))
|
||||
|
||||
utxoInfo := []*signrpc.TxOut{{
|
||||
PkScript: p2trPkScript,
|
||||
Value: 800_000,
|
||||
}}
|
||||
signResp, err := net.Alice.SignerClient.SignOutputRaw(
|
||||
ctxt, &signrpc.SignReq{
|
||||
RawTxBytes: buf.Bytes(),
|
||||
SignDescs: []*signrpc.SignDescriptor{{
|
||||
Output: utxoInfo[0],
|
||||
InputIndex: 0,
|
||||
KeyDesc: keyDesc,
|
||||
SingleTweak: dummyKeyTweak[:],
|
||||
Sighash: uint32(txscript.SigHashDefault),
|
||||
WitnessScript: rootHash[:],
|
||||
TaprootKeySpend: true,
|
||||
}},
|
||||
PrevOutputs: utxoInfo,
|
||||
},
|
||||
)
|
||||
require.NoError(t.t, err)
|
||||
|
||||
tx.TxIn[0].Witness = wire.TxWitness{
|
||||
signResp.RawSigs[0],
|
||||
}
|
||||
|
||||
buf.Reset()
|
||||
require.NoError(t.t, tx.Serialize(&buf))
|
||||
|
||||
// Since Schnorr signatures are fixed size, we must be able to estimate
|
||||
// the size of this transaction exactly.
|
||||
txWeight := blockchain.GetTransactionWeight(btcutil.NewTx(tx))
|
||||
require.Equal(t.t, txWeight, estimatedWeight)
|
||||
|
||||
_, err = net.Alice.WalletKitClient.PublishTransaction(
|
||||
ctxt, &walletrpc.Transaction{
|
||||
TxHex: buf.Bytes(),
|
||||
},
|
||||
)
|
||||
require.NoError(t.t, err)
|
||||
|
||||
// Wait until the spending tx is found.
|
||||
txid, err = waitForTxInMempool(net.Miner.Client, minerMempoolTimeout)
|
||||
require.NoError(t.t, err)
|
||||
p2wpkhOutputIndex := getOutputIndex(
|
||||
t, net.Miner, txid, p2wkhAddr.String(),
|
||||
)
|
||||
op := &lnrpc.OutPoint{
|
||||
TxidBytes: txid[:],
|
||||
OutputIndex: uint32(p2wpkhOutputIndex),
|
||||
}
|
||||
assertWalletUnspent(t, net.Alice, op)
|
||||
|
||||
// Mine another block to clean up the mempool and to make sure the spend
|
||||
// tx is actually included in a block.
|
||||
mineBlocks(t, net, 1, 1)
|
||||
}
|
||||
|
||||
// testScriptHashLock returns a simple bitcoin script that locks the funds to
|
||||
// a hash lock of the given preimage.
|
||||
func testScriptHashLock(t *testing.T, preimage []byte) txscript.TapLeaf {
|
||||
|
@ -363,17 +363,38 @@ func (b *BtcWallet) SignOutputRaw(tx *wire.MsgTx,
|
||||
sigHashes := txscript.NewTxSigHashes(
|
||||
tx, signDesc.PrevOutputFetcher,
|
||||
)
|
||||
leaf := txscript.TapLeaf{
|
||||
LeafVersion: txscript.BaseLeafVersion,
|
||||
Script: witnessScript,
|
||||
}
|
||||
rawSig, err := txscript.RawTxInTapscriptSignature(
|
||||
tx, sigHashes, signDesc.InputIndex,
|
||||
signDesc.Output.Value, signDesc.Output.PkScript,
|
||||
leaf, signDesc.HashType, privKey,
|
||||
)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
|
||||
// Are we spending a script path or the key path? The API is
|
||||
// slightly different, so we need to account for that to get the
|
||||
// raw signature.
|
||||
var rawSig []byte
|
||||
if signDesc.TaprootKeySpend {
|
||||
// This function tweaks the private key using the tap
|
||||
// root key supplied as the tweak. So we pass in the
|
||||
// original private key to avoid it being double
|
||||
// tweaked!
|
||||
rawSig, err = txscript.RawTxInTaprootSignature(
|
||||
tx, sigHashes, signDesc.InputIndex,
|
||||
signDesc.Output.Value, signDesc.Output.PkScript,
|
||||
signDesc.WitnessScript, signDesc.HashType,
|
||||
privKey,
|
||||
)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
} else {
|
||||
leaf := txscript.TapLeaf{
|
||||
LeafVersion: txscript.BaseLeafVersion,
|
||||
Script: witnessScript,
|
||||
}
|
||||
rawSig, err = txscript.RawTxInTapscriptSignature(
|
||||
tx, sigHashes, signDesc.InputIndex,
|
||||
signDesc.Output.Value, signDesc.Output.PkScript,
|
||||
leaf, signDesc.HashType, privKey,
|
||||
)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
}
|
||||
|
||||
sig, err := schnorr.ParseSignature(rawSig)
|
||||
|
Loading…
x
Reference in New Issue
Block a user