github.com/btcsuite/btcd@v0.24.0/txscript/taproot.go (about)

     1  // Copyright (c) 2013-2022 The btcsuite developers
     2  // Use of this source code is governed by an ISC
     3  // license that can be found in the LICENSE file.
     4  
     5  package txscript
     6  
     7  import (
     8  	"bytes"
     9  	"fmt"
    10  
    11  	"github.com/btcsuite/btcd/btcec/v2"
    12  	"github.com/btcsuite/btcd/btcec/v2/schnorr"
    13  	"github.com/btcsuite/btcd/chaincfg/chainhash"
    14  	"github.com/btcsuite/btcd/wire"
    15  	secp "github.com/decred/dcrd/dcrec/secp256k1/v4"
    16  )
    17  
    18  // TapscriptLeafVersion represents the various possible versions of a tapscript
    19  // leaf version. Leaf versions are used to define, or introduce new script
    20  // semantics, under the base taproot execution model.
    21  //
    22  // TODO(roasbeef): add validation here as well re proper prefix, etc?
    23  type TapscriptLeafVersion uint8
    24  
    25  const (
    26  	// BaseLeafVersion is the base tapscript leaf version. The semantics of
    27  	// this version are defined in BIP 342.
    28  	BaseLeafVersion TapscriptLeafVersion = 0xc0
    29  )
    30  
    31  const (
    32  	// ControlBlockBaseSize is the base size of a control block. This
    33  	// includes the initial byte for the leaf version, and then serialized
    34  	// schnorr public key.
    35  	ControlBlockBaseSize = 33
    36  
    37  	// ControlBlockNodeSize is the size of a given merkle branch hash in
    38  	// the control block.
    39  	ControlBlockNodeSize = 32
    40  
    41  	// ControlBlockMaxNodeCount is the max number of nodes that can be
    42  	// included in a control block. This value represents a merkle tree of
    43  	// depth 2^128.
    44  	ControlBlockMaxNodeCount = 128
    45  
    46  	// ControlBlockMaxSize is the max possible size of a control block.
    47  	// This simulates revealing a leaf from the largest possible tapscript
    48  	// tree.
    49  	ControlBlockMaxSize = ControlBlockBaseSize + (ControlBlockNodeSize *
    50  		ControlBlockMaxNodeCount)
    51  )
    52  
    53  // VerifyTaprootKeySpend attempts to verify a top-level taproot key spend,
    54  // returning a non-nil error if the passed signature is invalid.  If a sigCache
    55  // is passed in, then the sig cache will be consulted to skip full verification
    56  // of a signature that has already been seen. Witness program here should be
    57  // the 32-byte x-only schnorr output public key.
    58  //
    59  // NOTE: The TxSigHashes MUST be passed in and fully populated.
    60  func VerifyTaprootKeySpend(witnessProgram []byte, rawSig []byte, tx *wire.MsgTx,
    61  	inputIndex int, prevOuts PrevOutputFetcher, hashCache *TxSigHashes,
    62  	sigCache *SigCache) error {
    63  
    64  	// First, we'll need to extract the public key from the witness
    65  	// program.
    66  	rawKey := witnessProgram
    67  
    68  	// Extract the annex if it exists, so we can compute the proper proper
    69  	// sighash below.
    70  	var annex []byte
    71  	witness := tx.TxIn[inputIndex].Witness
    72  	if isAnnexedWitness(witness) {
    73  		annex, _ = extractAnnex(witness)
    74  	}
    75  
    76  	// Now that we have the public key, we can create a new top-level
    77  	// keyspend verifier that'll handle all the sighash and schnorr
    78  	// specifics for us.
    79  	keySpendVerifier, err := newTaprootSigVerifier(
    80  		rawKey, rawSig, tx, inputIndex, prevOuts, sigCache,
    81  		hashCache, annex,
    82  	)
    83  	if err != nil {
    84  		return err
    85  	}
    86  
    87  	valid := keySpendVerifier.Verify()
    88  	if valid {
    89  		return nil
    90  	}
    91  
    92  	return scriptError(ErrTaprootSigInvalid, "")
    93  }
    94  
    95  // ControlBlock houses the structured witness input for a taproot spend. This
    96  // includes the internal taproot key, the leaf version, and finally a nearly
    97  // complete merkle inclusion proof for the main taproot commitment.
    98  //
    99  // TODO(roasbeef): method to serialize control block that commits to even
   100  // y-bit, which pops up everywhere even tho 32 byte keys
   101  type ControlBlock struct {
   102  	// InternalKey is the internal public key in the taproot commitment.
   103  	InternalKey *btcec.PublicKey
   104  
   105  	// OutputKeyYIsOdd denotes if the y coordinate of the output key (the
   106  	// key placed in the actual taproot output is odd.
   107  	OutputKeyYIsOdd bool
   108  
   109  	// LeafVersion is the specified leaf version of the tapscript leaf that
   110  	// the InclusionProof below is based off of.
   111  	LeafVersion TapscriptLeafVersion
   112  
   113  	// InclusionProof is a series of merkle branches that when hashed
   114  	// pairwise, starting with the revealed script, will yield the taproot
   115  	// commitment root.
   116  	InclusionProof []byte
   117  }
   118  
   119  // ToBytes returns the control block in a format suitable for using as part of
   120  // a witness spending a tapscript output.
   121  func (c *ControlBlock) ToBytes() ([]byte, error) {
   122  	var b bytes.Buffer
   123  
   124  	// The first byte of the control block is the leaf version byte XOR'd with
   125  	// the parity of the y coordinate of the public key.
   126  	yParity := byte(0)
   127  	if c.OutputKeyYIsOdd {
   128  		yParity = 1
   129  	}
   130  
   131  	// The first byte is a combination of the leaf version, using the lowest
   132  	// bit to encode the single bit that denotes if the yo coordinate if odd or
   133  	// even.
   134  	leafVersionAndParity := byte(c.LeafVersion) | yParity
   135  	if err := b.WriteByte(leafVersionAndParity); err != nil {
   136  		return nil, err
   137  	}
   138  
   139  	// Next, we encode the raw 32 byte schnorr public key
   140  	if _, err := b.Write(schnorr.SerializePubKey(c.InternalKey)); err != nil {
   141  		return nil, err
   142  	}
   143  
   144  	// Finally, we'll write out the inclusion proof as is, without any length
   145  	// prefix.
   146  	if _, err := b.Write(c.InclusionProof); err != nil {
   147  		return nil, err
   148  	}
   149  
   150  	return b.Bytes(), nil
   151  }
   152  
   153  // RootHash calculates the root hash of a tapscript given the revealed script.
   154  func (c *ControlBlock) RootHash(revealedScript []byte) []byte {
   155  	// We'll start by creating a new tapleaf from the revealed script,
   156  	// this'll serve as the initial hash we'll use to incrementally
   157  	// reconstruct the merkle root using the control block elements.
   158  	merkleAccumulator := NewTapLeaf(c.LeafVersion, revealedScript).TapHash()
   159  
   160  	// Now that we have our initial hash, we'll parse the control block one
   161  	// node at a time to build up our merkle accumulator into the taproot
   162  	// commitment.
   163  	//
   164  	// The control block is a series of nodes that serve as an inclusion
   165  	// proof as we can start hashing with our leaf, with each internal
   166  	// branch, until we reach the root.
   167  	numNodes := len(c.InclusionProof) / ControlBlockNodeSize
   168  	for nodeOffset := 0; nodeOffset < numNodes; nodeOffset++ {
   169  		// Extract the new node using our index to serve as a 32-byte
   170  		// offset.
   171  		leafOffset := 32 * nodeOffset
   172  		nextNode := c.InclusionProof[leafOffset : leafOffset+32]
   173  
   174  		merkleAccumulator = tapBranchHash(merkleAccumulator[:], nextNode)
   175  	}
   176  
   177  	return merkleAccumulator[:]
   178  }
   179  
   180  // ParseControlBlock attempts to parse the raw bytes of a control block. An
   181  // error is returned if the control block isn't well formed, or can't be
   182  // parsed.
   183  func ParseControlBlock(ctrlBlock []byte) (*ControlBlock, error) {
   184  	// The control block minimally must contain 33 bytes (for the leaf
   185  	// version and internal key) along with at least a single value
   186  	// comprising the merkle proof. If not, then it's invalid.
   187  	switch {
   188  	// The control block must minimally have 33 bytes for the internal
   189  	// public key and script leaf version.
   190  	case len(ctrlBlock) < ControlBlockBaseSize:
   191  		str := fmt.Sprintf("min size is %v bytes, control block "+
   192  			"is %v bytes", ControlBlockBaseSize, len(ctrlBlock))
   193  		return nil, scriptError(ErrControlBlockTooSmall, str)
   194  
   195  	// The control block can't be larger than a proof for the largest
   196  	// possible tapscript merkle tree with 2^128 leaves.
   197  	case len(ctrlBlock) > ControlBlockMaxSize:
   198  		str := fmt.Sprintf("max size is %v, control block is %v bytes",
   199  			ControlBlockMaxSize, len(ctrlBlock))
   200  		return nil, scriptError(ErrControlBlockTooLarge, str)
   201  
   202  	// Ignoring the fixed sized portion, we expect the total number of
   203  	// remaining bytes to be a multiple of the node size, which is 32
   204  	// bytes.
   205  	case (len(ctrlBlock)-ControlBlockBaseSize)%ControlBlockNodeSize != 0:
   206  		str := fmt.Sprintf("control block proof is not a multiple "+
   207  			"of 32: %v", len(ctrlBlock)-ControlBlockBaseSize)
   208  		return nil, scriptError(ErrControlBlockInvalidLength, str)
   209  	}
   210  
   211  	// With the basic sanity checking complete, we can now parse the
   212  	// control block.
   213  	leafVersion := TapscriptLeafVersion(ctrlBlock[0] & TaprootLeafMask)
   214  
   215  	// Extract the parity of the y coordinate of the internal key.
   216  	var yIsOdd bool
   217  	if ctrlBlock[0]&0x01 == 0x01 {
   218  		yIsOdd = true
   219  	}
   220  
   221  	// Next, we'll parse the public key, which is the 32 bytes following
   222  	// the leaf version.
   223  	rawKey := ctrlBlock[1:33]
   224  	pubKey, err := schnorr.ParsePubKey(rawKey)
   225  	if err != nil {
   226  		return nil, err
   227  	}
   228  
   229  	// The rest of the bytes are the control block itself, which encodes a
   230  	// merkle proof of inclusion.
   231  	proofBytes := ctrlBlock[33:]
   232  
   233  	return &ControlBlock{
   234  		InternalKey:     pubKey,
   235  		OutputKeyYIsOdd: yIsOdd,
   236  		LeafVersion:     leafVersion,
   237  		InclusionProof:  proofBytes,
   238  	}, nil
   239  }
   240  
   241  // ComputeTaprootOutputKey calculates a top-level taproot output key given an
   242  // internal key, and tapscript merkle root. The final key is derived as:
   243  // taprootKey = internalKey + (h_tapTweak(internalKey || merkleRoot)*G).
   244  func ComputeTaprootOutputKey(pubKey *btcec.PublicKey,
   245  	scriptRoot []byte) *btcec.PublicKey {
   246  
   247  	// This routine only operates on x-only public keys where the public
   248  	// key always has an even y coordinate, so we'll re-parse it as such.
   249  	internalKey, _ := schnorr.ParsePubKey(schnorr.SerializePubKey(pubKey))
   250  
   251  	// First, we'll compute the tap tweak hash that commits to the internal
   252  	// key and the merkle script root.
   253  	tapTweakHash := chainhash.TaggedHash(
   254  		chainhash.TagTapTweak, schnorr.SerializePubKey(internalKey),
   255  		scriptRoot,
   256  	)
   257  
   258  	// With the tap tweek computed,  we'll need to convert the merkle root
   259  	// into something in the domain we can manipulate: a scalar value mod
   260  	// N.
   261  	var tweakScalar btcec.ModNScalar
   262  	tweakScalar.SetBytes((*[32]byte)(tapTweakHash))
   263  
   264  	// Next, we'll need to convert the internal key to jacobian coordinates
   265  	// as the routines we need only operate on this type.
   266  	var internalPoint btcec.JacobianPoint
   267  	internalKey.AsJacobian(&internalPoint)
   268  
   269  	// With our intermediate data obtained, we'll now compute:
   270  	//
   271  	// taprootKey = internalPoint + (tapTweak*G).
   272  	var tPoint, taprootKey btcec.JacobianPoint
   273  	btcec.ScalarBaseMultNonConst(&tweakScalar, &tPoint)
   274  	btcec.AddNonConst(&internalPoint, &tPoint, &taprootKey)
   275  
   276  	// Finally, we'll convert the key back to affine coordinates so we can
   277  	// return the format of public key we usually use.
   278  	taprootKey.ToAffine()
   279  
   280  	return btcec.NewPublicKey(&taprootKey.X, &taprootKey.Y)
   281  }
   282  
   283  // ComputeTaprootKeyNoScript calculates the top-level taproot output key given
   284  // an internal key, and a desire that the only way an output can be spent is
   285  // with the keyspend path. This is useful for normal wallet operations that
   286  // don't need any other additional spending conditions.
   287  func ComputeTaprootKeyNoScript(internalKey *btcec.PublicKey) *btcec.PublicKey {
   288  	// We'll compute a custom tap tweak hash that just commits to the key,
   289  	// rather than an actual root hash.
   290  	fakeScriptroot := []byte{}
   291  
   292  	return ComputeTaprootOutputKey(internalKey, fakeScriptroot)
   293  }
   294  
   295  // TweakTaprootPrivKey applies the same operation as ComputeTaprootOutputKey,
   296  // but on the private key instead. The final key is derived as: privKey +
   297  // h_tapTweak(internalKey || merkleRoot) % N, where N is the order of the
   298  // secp256k1 curve, and merkleRoot is the root hash of the tapscript tree.
   299  func TweakTaprootPrivKey(privKey btcec.PrivateKey,
   300  	scriptRoot []byte) *btcec.PrivateKey {
   301  
   302  	// If the corresponding public key has an odd y coordinate, then we'll
   303  	// negate the private key as specified in BIP 341.
   304  	privKeyScalar := privKey.Key
   305  	pubKeyBytes := privKey.PubKey().SerializeCompressed()
   306  	if pubKeyBytes[0] == secp.PubKeyFormatCompressedOdd {
   307  		privKeyScalar.Negate()
   308  	}
   309  
   310  	// Next, we'll compute the tap tweak hash that commits to the internal
   311  	// key and the merkle script root. We'll snip off the extra parity byte
   312  	// from the compressed serialization and use that directly.
   313  	schnorrKeyBytes := pubKeyBytes[1:]
   314  	tapTweakHash := chainhash.TaggedHash(
   315  		chainhash.TagTapTweak, schnorrKeyBytes, scriptRoot,
   316  	)
   317  
   318  	// Map the private key to a ModNScalar which is needed to perform
   319  	// operation mod the curve order.
   320  	var tweakScalar btcec.ModNScalar
   321  	tweakScalar.SetBytes((*[32]byte)(tapTweakHash))
   322  
   323  	// Now that we have the private key in its may negated form, we'll add
   324  	// the script root as a tweak. As we're using a ModNScalar all
   325  	// operations are already normalized mod the curve order.
   326  	privTweak := privKeyScalar.Add(&tweakScalar)
   327  
   328  	return btcec.PrivKeyFromScalar(privTweak)
   329  }
   330  
   331  // VerifyTaprootLeafCommitment attempts to verify a taproot commitment of the
   332  // revealed script within the taprootWitnessProgram (a schnorr public key)
   333  // given the required information included in the control block. An error is
   334  // returned if the reconstructed taproot commitment (a function of the merkle
   335  // root and the internal key) doesn't match the passed witness program.
   336  func VerifyTaprootLeafCommitment(controlBlock *ControlBlock,
   337  	taprootWitnessProgram []byte, revealedScript []byte) error {
   338  
   339  	// First, we'll calculate the root hash from the given proof and
   340  	// revealed script.
   341  	rootHash := controlBlock.RootHash(revealedScript)
   342  
   343  	// Next, we'll construct the final commitment (creating the external or
   344  	// taproot output key) as a function of this commitment and the
   345  	// included internal key: taprootKey = internalKey + (tPoint*G).
   346  	taprootKey := ComputeTaprootOutputKey(
   347  		controlBlock.InternalKey, rootHash,
   348  	)
   349  
   350  	// If we convert the taproot key to a witness program (we just need to
   351  	// serialize the public key), then it should exactly match the witness
   352  	// program passed in.
   353  	expectedWitnessProgram := schnorr.SerializePubKey(taprootKey)
   354  	if !bytes.Equal(expectedWitnessProgram, taprootWitnessProgram) {
   355  
   356  		return scriptError(ErrTaprootMerkleProofInvalid, "")
   357  	}
   358  
   359  	// Finally, we'll verify that the parity of the y coordinate of the
   360  	// public key we've derived matches the control block.
   361  	derivedYIsOdd := (taprootKey.SerializeCompressed()[0] ==
   362  		secp.PubKeyFormatCompressedOdd)
   363  	if controlBlock.OutputKeyYIsOdd != derivedYIsOdd {
   364  		str := fmt.Sprintf("control block y is odd: %v, derived "+
   365  			"parity is odd: %v", controlBlock.OutputKeyYIsOdd,
   366  			derivedYIsOdd)
   367  		return scriptError(ErrTaprootOutputKeyParityMismatch, str)
   368  	}
   369  
   370  	// Otherwise, if we reach here, the commitment opening is valid and
   371  	// execution can continue.
   372  	return nil
   373  }
   374  
   375  // TapNode represents an abstract node in a tapscript merkle tree. A node is
   376  // either a branch or a leaf.
   377  type TapNode interface {
   378  	// TapHash returns the hash of the node. This will either be a tagged
   379  	// hash derived from a branch, or a leaf.
   380  	TapHash() chainhash.Hash
   381  
   382  	// Left returns the left node. If this is a leaf node, this may be nil.
   383  	Left() TapNode
   384  
   385  	// Right returns the right node. If this is a leaf node, this may be
   386  	// nil.
   387  	Right() TapNode
   388  }
   389  
   390  // TapLeaf represents a leaf in a tapscript tree. A leaf has two components:
   391  // the leaf version, and the script associated with that leaf version.
   392  type TapLeaf struct {
   393  	// LeafVersion is the leaf version of this leaf.
   394  	LeafVersion TapscriptLeafVersion
   395  
   396  	// Script is the script to be validated based on the specified leaf
   397  	// version.
   398  	Script []byte
   399  }
   400  
   401  // Left rights the left node for this leaf. As this is a leaf the left node is
   402  // nil.
   403  func (t TapLeaf) Left() TapNode {
   404  	return nil
   405  }
   406  
   407  // Right rights the right node for this leaf. As this is a leaf the right node
   408  // is nil.
   409  func (t TapLeaf) Right() TapNode {
   410  	return nil
   411  }
   412  
   413  // NewBaseTapLeaf returns a new TapLeaf for the specified script, using the
   414  // current base leaf version (BIP 342).
   415  func NewBaseTapLeaf(script []byte) TapLeaf {
   416  	return TapLeaf{
   417  		Script:      script,
   418  		LeafVersion: BaseLeafVersion,
   419  	}
   420  }
   421  
   422  // NewTapLeaf returns a new TapLeaf with the given leaf version and script to
   423  // be committed to.
   424  func NewTapLeaf(leafVersion TapscriptLeafVersion, script []byte) TapLeaf {
   425  	return TapLeaf{
   426  		LeafVersion: leafVersion,
   427  		Script:      script,
   428  	}
   429  }
   430  
   431  // TapHash returns the hash digest of the target taproot script leaf. The
   432  // digest is computed as: h_tapleaf(leafVersion || compactSizeof(script) ||
   433  // script).
   434  func (t TapLeaf) TapHash() chainhash.Hash {
   435  	// TODO(roasbeef): cache these and the branch due to the recursive
   436  	// call, so memoize
   437  
   438  	// The leaf encoding is: leafVersion || compactSizeof(script) ||
   439  	// script, where compactSizeof returns the compact size needed to
   440  	// encode the value.
   441  	var leafEncoding bytes.Buffer
   442  
   443  	_ = leafEncoding.WriteByte(byte(t.LeafVersion))
   444  	_ = wire.WriteVarBytes(&leafEncoding, 0, t.Script)
   445  
   446  	return *chainhash.TaggedHash(chainhash.TagTapLeaf, leafEncoding.Bytes())
   447  }
   448  
   449  // TapBranch represents an internal branch in the tapscript tree. The left or
   450  // right nodes may either be another branch, leaves, or a combination of both.
   451  type TapBranch struct {
   452  	// leftNode is the left node, this cannot be nil.
   453  	leftNode TapNode
   454  
   455  	// rightNode is the right node, this cannot be nil.
   456  	rightNode TapNode
   457  }
   458  
   459  // NewTapBranch creates a new internal branch from a left and right node.
   460  func NewTapBranch(l, r TapNode) TapBranch {
   461  
   462  	return TapBranch{
   463  		leftNode:  l,
   464  		rightNode: r,
   465  	}
   466  }
   467  
   468  // Left is the left node of the branch, this might be a leaf or another
   469  // branch.
   470  func (t TapBranch) Left() TapNode {
   471  	return t.leftNode
   472  }
   473  
   474  // Right is the right node of a branch, this might be a leaf or another branch.
   475  func (t TapBranch) Right() TapNode {
   476  	return t.rightNode
   477  }
   478  
   479  // TapHash returns the hash digest of the taproot internal branch given a left
   480  // and right node. The final hash digest is: h_tapbranch(leftNode ||
   481  // rightNode), where leftNode is the lexicographically smaller of the two nodes.
   482  func (t TapBranch) TapHash() chainhash.Hash {
   483  	leftHash := t.leftNode.TapHash()
   484  	rightHash := t.rightNode.TapHash()
   485  	return tapBranchHash(leftHash[:], rightHash[:])
   486  }
   487  
   488  // tapBranchHash takes the raw tap hashes of the right and left nodes and
   489  // hashes them into a branch. See The TapBranch method for the specifics.
   490  func tapBranchHash(l, r []byte) chainhash.Hash {
   491  	if bytes.Compare(l[:], r[:]) > 0 {
   492  		l, r = r, l
   493  	}
   494  
   495  	return *chainhash.TaggedHash(
   496  		chainhash.TagTapBranch, l[:], r[:],
   497  	)
   498  }
   499  
   500  // TapscriptProof is a proof of inclusion that a given leaf (a script and leaf
   501  // version) is included within a top-level taproot output commitment.
   502  type TapscriptProof struct {
   503  	// TapLeaf is the leaf that we want to prove inclusion for.
   504  	TapLeaf
   505  
   506  	// RootNode is the root of the tapscript tree, this will be used to
   507  	// compute what the final output key looks like.
   508  	RootNode TapNode
   509  
   510  	// InclusionProof is the tail end of the control block that contains
   511  	// the series of hashes (the sibling hashes up the tree), that when
   512  	// hashed together allow us to re-derive the top level taproot output.
   513  	InclusionProof []byte
   514  }
   515  
   516  // ToControlBlock maps the tapscript proof into a fully valid control block
   517  // that can be used as a witness item for a tapscript spend.
   518  func (t *TapscriptProof) ToControlBlock(internalKey *btcec.PublicKey) ControlBlock {
   519  	// Compute the total level output commitment based on the populated
   520  	// root node.
   521  	rootHash := t.RootNode.TapHash()
   522  	taprootKey := ComputeTaprootOutputKey(
   523  		internalKey, rootHash[:],
   524  	)
   525  
   526  	// With the commitment computed we can obtain the bit that denotes if
   527  	// the resulting key has an odd y coordinate or not.
   528  	var outputKeyYIsOdd bool
   529  	if taprootKey.SerializeCompressed()[0] ==
   530  		secp.PubKeyFormatCompressedOdd {
   531  
   532  		outputKeyYIsOdd = true
   533  	}
   534  
   535  	return ControlBlock{
   536  		InternalKey:     internalKey,
   537  		OutputKeyYIsOdd: outputKeyYIsOdd,
   538  		LeafVersion:     t.TapLeaf.LeafVersion,
   539  		InclusionProof:  t.InclusionProof,
   540  	}
   541  }
   542  
   543  // IndexedTapScriptTree reprints a fully contracted tapscript tree. The
   544  // RootNode can be used to traverse down the full tree. In addition, complete
   545  // inclusion proofs for each leaf are included as well, with an index into the
   546  // slice of proof based on the tap leaf hash of a given leaf.
   547  type IndexedTapScriptTree struct {
   548  	// RootNode is the root of the tapscript tree. RootNode.TapHash() can
   549  	// be used to extract the hash needed to derive the taptweak committed
   550  	// to in the taproot output.
   551  	RootNode TapNode
   552  
   553  	// LeafMerkleProofs is a slice that houses the series of merkle
   554  	// inclusion proofs for each leaf based on the input order of the
   555  	// leaves.
   556  	LeafMerkleProofs []TapscriptProof
   557  
   558  	// LeafProofIndex maps the TapHash() of a given leaf node to the index
   559  	// within the LeafMerkleProofs array above. This can be used to
   560  	// retrieve the inclusion proof for a given script when constructing
   561  	// the witness stack and control block for spending a tapscript path.
   562  	LeafProofIndex map[chainhash.Hash]int
   563  }
   564  
   565  // NewIndexedTapScriptTree creates a new empty tapscript tree that has enough
   566  // space to hold information for the specified amount of leaves.
   567  func NewIndexedTapScriptTree(numLeaves int) *IndexedTapScriptTree {
   568  	return &IndexedTapScriptTree{
   569  		LeafMerkleProofs: make([]TapscriptProof, numLeaves),
   570  		LeafProofIndex:   make(map[chainhash.Hash]int, numLeaves),
   571  	}
   572  }
   573  
   574  // hashTapNodes takes a left and right now, and returns the left and right tap
   575  // hashes, along with the new combined node. If both nodes are nil, nil
   576  // pointers are returned. If the right now is nil, then the left node is passed
   577  // in, which effectively will "lift" the node up in the tree as long as it
   578  // doesn't have any siblings.
   579  func hashTapNodes(left, right TapNode) (*chainhash.Hash, *chainhash.Hash, TapNode) {
   580  	switch {
   581  	// If there's no left child, then this is a "nil" portion of the array
   582  	// tree, so well thread thru nil.
   583  	case left == nil:
   584  		return nil, nil, nil
   585  
   586  	// If there's no right child, then this is a single node that'll be
   587  	// passed all the way up the tree as it has no children.
   588  	case right == nil:
   589  		return nil, nil, left
   590  	}
   591  
   592  	// The result of hashing two nodes will always be a branch, so we start
   593  	// with that.
   594  	leftHash := left.TapHash()
   595  	rightHash := right.TapHash()
   596  
   597  	return &leftHash, &rightHash, NewTapBranch(left, right)
   598  }
   599  
   600  // leafDescendants is a recursive algorithm that returns all the leaf nodes
   601  // that are a decedents of this tree. This is used to collect the series of
   602  // nodes we need to extend the inclusion proof of each time we go up in the
   603  // tree.
   604  func leafDescendants(node TapNode) []TapNode {
   605  	// A leaf node has no decedents, so we just return it directly.
   606  	if node.Left() == nil && node.Right() == nil {
   607  		return []TapNode{node}
   608  	}
   609  
   610  	// Otherwise, get the descendants of the left and right sub-trees to
   611  	// return.
   612  	leftLeaves := leafDescendants(node.Left())
   613  	rightLeaves := leafDescendants(node.Right())
   614  
   615  	return append(leftLeaves, rightLeaves...)
   616  }
   617  
   618  // AssembleTaprootScriptTree constructs a new fully indexed tapscript tree
   619  // given a series of leaf nodes. A combination of a recursive data structure,
   620  // and an array-based representation are used to both generate the tree and
   621  // also accumulate all the necessary inclusion proofs in the same path. See the
   622  // comment of blockchain.BuildMerkleTreeStore for further details.
   623  func AssembleTaprootScriptTree(leaves ...TapLeaf) *IndexedTapScriptTree {
   624  	// If there's only a single leaf, then that becomes our root.
   625  	if len(leaves) == 1 {
   626  		// A lone leaf has no additional inclusion proof, as a verifier
   627  		// will just hash the leaf as the sole branch.
   628  		leaf := leaves[0]
   629  		return &IndexedTapScriptTree{
   630  			RootNode: leaf,
   631  			LeafProofIndex: map[chainhash.Hash]int{
   632  				leaf.TapHash(): 0,
   633  			},
   634  			LeafMerkleProofs: []TapscriptProof{
   635  				{
   636  					TapLeaf:        leaf,
   637  					RootNode:       leaf,
   638  					InclusionProof: nil,
   639  				},
   640  			},
   641  		}
   642  	}
   643  
   644  	// We'll start out by populating the leaf index which maps a leave's
   645  	// taphash to its index within the tree.
   646  	scriptTree := NewIndexedTapScriptTree(len(leaves))
   647  	for i, leaf := range leaves {
   648  		leafHash := leaf.TapHash()
   649  		scriptTree.LeafProofIndex[leafHash] = i
   650  	}
   651  
   652  	var branches []TapBranch
   653  	for i := 0; i < len(leaves); i += 2 {
   654  		// If there's only a single leaf left, then we'll merge this
   655  		// with the last branch we have.
   656  		if i == len(leaves)-1 {
   657  			branchToMerge := branches[len(branches)-1]
   658  			leaf := leaves[i]
   659  			newBranch := NewTapBranch(branchToMerge, leaf)
   660  
   661  			branches[len(branches)-1] = newBranch
   662  
   663  			// The leaf includes the existing branch within its
   664  			// inclusion proof.
   665  			branchHash := branchToMerge.TapHash()
   666  
   667  			scriptTree.LeafMerkleProofs[i].TapLeaf = leaf
   668  			scriptTree.LeafMerkleProofs[i].InclusionProof = append(
   669  				scriptTree.LeafMerkleProofs[i].InclusionProof,
   670  				branchHash[:]...,
   671  			)
   672  
   673  			// We'll also add this right hash to the inclusion of
   674  			// the left and right nodes of the branch.
   675  			lastLeafHash := leaf.TapHash()
   676  
   677  			leftLeafHash := branchToMerge.Left().TapHash()
   678  			leftLeafIndex := scriptTree.LeafProofIndex[leftLeafHash]
   679  			scriptTree.LeafMerkleProofs[leftLeafIndex].InclusionProof = append(
   680  				scriptTree.LeafMerkleProofs[leftLeafIndex].InclusionProof,
   681  				lastLeafHash[:]...,
   682  			)
   683  
   684  			rightLeafHash := branchToMerge.Right().TapHash()
   685  			rightLeafIndex := scriptTree.LeafProofIndex[rightLeafHash]
   686  			scriptTree.LeafMerkleProofs[rightLeafIndex].InclusionProof = append(
   687  				scriptTree.LeafMerkleProofs[rightLeafIndex].InclusionProof,
   688  				lastLeafHash[:]...,
   689  			)
   690  
   691  			continue
   692  		}
   693  
   694  		// While we still have leaves left, we'll combine two of them
   695  		// into a new branch node.
   696  		left, right := leaves[i], leaves[i+1]
   697  		nextBranch := NewTapBranch(left, right)
   698  		branches = append(branches, nextBranch)
   699  
   700  		// The left node will use the right node as part of its
   701  		// inclusion proof, and vice versa.
   702  		leftHash := left.TapHash()
   703  		rightHash := right.TapHash()
   704  
   705  		scriptTree.LeafMerkleProofs[i].TapLeaf = left
   706  		scriptTree.LeafMerkleProofs[i].InclusionProof = append(
   707  			scriptTree.LeafMerkleProofs[i].InclusionProof,
   708  			rightHash[:]...,
   709  		)
   710  
   711  		scriptTree.LeafMerkleProofs[i+1].TapLeaf = right
   712  		scriptTree.LeafMerkleProofs[i+1].InclusionProof = append(
   713  			scriptTree.LeafMerkleProofs[i+1].InclusionProof,
   714  			leftHash[:]...,
   715  		)
   716  	}
   717  
   718  	// In this second phase, we'll merge all the leaf branches we have one
   719  	// by one until we have our final root.
   720  	var rootNode TapNode
   721  	for len(branches) != 0 {
   722  		// When we only have a single branch left, then that becomes
   723  		// our root.
   724  		if len(branches) == 1 {
   725  			rootNode = branches[0]
   726  			break
   727  		}
   728  
   729  		left, right := branches[0], branches[1]
   730  
   731  		newBranch := NewTapBranch(left, right)
   732  
   733  		branches = branches[2:]
   734  
   735  		branches = append(branches, newBranch)
   736  
   737  		// Accumulate the sibling hash of this new branch for all the
   738  		// leaves that are its children.
   739  		leftLeafDescendants := leafDescendants(left)
   740  		rightLeafDescendants := leafDescendants(right)
   741  
   742  		leftHash, rightHash := left.TapHash(), right.TapHash()
   743  
   744  		// For each left hash that's a leaf descendants, well add the
   745  		// right sibling as that sibling is needed to construct the new
   746  		// internal branch we just created. We also do the same for the
   747  		// siblings of the right node.
   748  		for _, leftLeaf := range leftLeafDescendants {
   749  			leafHash := leftLeaf.TapHash()
   750  			leafIndex := scriptTree.LeafProofIndex[leafHash]
   751  
   752  			scriptTree.LeafMerkleProofs[leafIndex].InclusionProof = append(
   753  				scriptTree.LeafMerkleProofs[leafIndex].InclusionProof,
   754  				rightHash[:]...,
   755  			)
   756  		}
   757  		for _, rightLeaf := range rightLeafDescendants {
   758  			leafHash := rightLeaf.TapHash()
   759  			leafIndex := scriptTree.LeafProofIndex[leafHash]
   760  
   761  			scriptTree.LeafMerkleProofs[leafIndex].InclusionProof = append(
   762  				scriptTree.LeafMerkleProofs[leafIndex].InclusionProof,
   763  				leftHash[:]...,
   764  			)
   765  		}
   766  	}
   767  
   768  	// Populate the top level root node pointer, as well as the pointer in
   769  	// each proof.
   770  	scriptTree.RootNode = rootNode
   771  	for i := range scriptTree.LeafMerkleProofs {
   772  		scriptTree.LeafMerkleProofs[i].RootNode = rootNode
   773  	}
   774  
   775  	return scriptTree
   776  }
   777  
   778  // PayToTaprootScript creates a pk script for a pay-to-taproot output key.
   779  func PayToTaprootScript(taprootKey *btcec.PublicKey) ([]byte, error) {
   780  	return NewScriptBuilder().
   781  		AddOp(OP_1).
   782  		AddData(schnorr.SerializePubKey(taprootKey)).
   783  		Script()
   784  }