Documentation

Overview

Package psbt is an implementation of Partially Signed Bitcoin Transactions (PSBT). The format is defined in BIP 174: https://github.com/bitcoin/bips/blob/master/bip-0174.mediawiki

Index

Constants

View Source
const (

	// Global known key types
	PsbtGlobalUnsignedTx psbtKeyType = 0

	// TxIn section known key types
	PsbtInNonWitnessUtxo     psbtKeyType = 0
	PsbtInWitnessUtxo        psbtKeyType = 1
	PsbtInPartialSig         psbtKeyType = 2
	PsbtInSighashType        psbtKeyType = 3
	PsbtInRedeemScript       psbtKeyType = 4
	PsbtInWitnessScript      psbtKeyType = 5
	PsbtInBip32Derivation    psbtKeyType = 6
	PsbtInFinalScriptSig     psbtKeyType = 7
	PsbtInFinalScriptWitness psbtKeyType = 8

	// TxOut section known key types
	PsbtOutRedeemScript    psbtKeyType = 0
	PsbtOutWitnessScript   psbtKeyType = 1
	PsbtOutBip32Derivation psbtKeyType = 2
)

The below are the known key types as per the BIP. Unknown types may be accepted but will not be processed.

View Source
const MaxPsbtValueLength = 4000000

MaxPsbtValueLength is the size of the largest transaction serialization that could be passed in a NonWitnessUtxo field. This is definitely less than 4M.

Variables

View Source
var (

	// ErrInvalidPsbtFormat is a generic error for any situation in which a
	// provided Psbt serialization does not conform to the rules of BIP174.
	ErrInvalidPsbtFormat = errors.New("Invalid PSBT serialization format")

	// ErrDuplicateKey indicates that a passed Psbt serialization is invalid
	// due to having the same key repeated in the same key-value pair.
	ErrDuplicateKey = errors.New("Invalid Psbt due to duplicate key")

	// ErrInvalidKeydata indicates that a key-value pair in the PSBT
	// serialization contains data in the key which is not valid.
	ErrInvalidKeydata = errors.New("Invalid key data")

	// ErrInvalidMagicBytes indicates that a passed Psbt serialization is invalid
	// due to having incorrect magic bytes.
	ErrInvalidMagicBytes = errors.New("Invalid Psbt due to incorrect magic bytes")

	// ErrInvalidRawTxSigned indicates that the raw serialized transaction in the
	// global section of the passed Psbt serialization is invalid because it
	// contains scriptSigs/witnesses (i.e. is fully or partially signed), which
	// is not allowed by BIP174.
	ErrInvalidRawTxSigned = errors.New("Invalid Psbt, raw transaction must " +
		"be unsigned.")

	// ErrInvalidPrevOutNonWitnessTransaction indicates that the transaction
	// hash (i.e. SHA256^2) of the fully serialized previous transaction
	// provided in the NonWitnessUtxo key-value field doesn't match the prevout
	// hash in the UnsignedTx field in the PSBT itself.
	ErrInvalidPrevOutNonWitnessTransaction = errors.New("Prevout hash does " +
		"not match the provided non-witness utxo serialization")

	// ErrInvalidSignatureForInput indicates that the signature the user is
	// trying to append to the PSBT is invalid, either because it does
	// not correspond to the previous transaction hash, or redeem script,
	// or witness script.
	// NOTE this does not include ECDSA signature checking.
	ErrInvalidSignatureForInput = errors.New("Signature does not correspond " +
		"to this input")

	// ErrInputAlreadyFinalized indicates that the PSBT passed to a Finalizer
	// already contains the finalized scriptSig or witness.
	ErrInputAlreadyFinalized = errors.New("Cannot finalize PSBT, finalized " +
		"scriptSig or scriptWitnes already exists")

	// ErrIncompletePSBT indicates that the Extractor object
	// was unable to successfully extract the passed Psbt struct because
	// it is not complete
	ErrIncompletePSBT = errors.New("PSBT cannot be extracted as it is " +
		"incomplete")

	// ErrNotFinalizable indicates that the PSBT struct does not have
	// sufficient data (e.g. signatures) for finalization
	ErrNotFinalizable = errors.New("PSBT is not finalizable")

	// ErrInvalidSigHashFlags indicates that a signature added to the PSBT
	// uses Sighash flags that are not in accordance with the requirement
	// according to the entry in PsbtInSighashType, or otherwise not the
	// default value (SIGHASH_ALL)
	ErrInvalidSigHashFlags = errors.New("Invalid Sighash Flags")

	// ErrUnsupportedScriptType indicates that the redeem script or
	// scriptwitness given is not supported by this codebase, or is otherwise
	// not valid.
	ErrUnsupportedScriptType = errors.New("Unsupported script type")
)

Functions

func Extract

func Extract(p *Psbt) ([]byte, error)

Extract takes a finalized psbt and outputs a network serialization

func Finalize

func Finalize(p *Psbt, inIndex int) error

Finalize assumes that the provided Psbt struct has all partial signatures and redeem scripts/witness scripts already prepared for the specified input, and so removes all temporary data and replaces them with completed scriptSig and witness fields, which are stored in key-types 07 and 08. The witness/ non-witness utxo fields in the inputs (key-types 00 and 01) are left intact as they may be needed for validation (?). If there is any invalid or incomplete data, an error is returned.

func FinalizeNonWitness

func FinalizeNonWitness(p *Psbt, inIndex int) error

FinalizeNonWitness attempts to create PsbtInFinalScriptSig field for input at index inIndex, and removes all other fields except for the utxo field, for an input of type non-witness, or returns an error.

func FinalizeWitness

func FinalizeWitness(p *Psbt, inIndex int) error

FinalizeWitness attempts to create PsbtInFinalScriptSig field and PsbtInFinalScriptWitness field for input at index inIndex, and removes all other fields except for the utxo field, for an input of type witness, or returns an error.

func MaybeFinalize

func MaybeFinalize(p *Psbt, inIndex int) (bool, error)

MaybeFinalize attempts to finalize the input at index inIndex in the PSBT p, returning true with no error if it succeeds, OR if the input has already been finalized.

func MaybeFinalizeAll

func MaybeFinalizeAll(p *Psbt) error

MaybeFinalizeAll attempts to finalize all inputs of the Psbt that are not already finalized, and returns an error if it fails to do so.

func SerializeBIP32Derivation

func SerializeBIP32Derivation(masterKeyFingerprint uint32,
	bip32Path []uint32) []byte

SerializeBIP32Derivation takes a master key fingerprint as defined in BIP32, along with a path specified as a list of uint32 values, and returns a bytestring specifying the derivation in the format required by BIP174: // master key fingerprint (4) || child index (4) || child index (4) || ...

Types

type Bip32Derivation

type Bip32Derivation struct {
	PubKey               []byte
	MasterKeyFingerprint uint32
	Bip32Path            []uint32
}

Bip32Derivation encapsulates the data for the input and output Bip32Derivation key-value fields.

type Bip32Sorter

type Bip32Sorter []*Bip32Derivation

Bip32Sorter implements sort.Interface.

func (Bip32Sorter) Len

func (s Bip32Sorter) Len() int

func (Bip32Sorter) Less

func (s Bip32Sorter) Less(i, j int) bool

func (Bip32Sorter) Swap

func (s Bip32Sorter) Swap(i, j int)

type Creator

type Creator struct {
	Cpsbt *Psbt
}

Creator holds a reference to a created Psbt struct.

type PInput

type PInput struct {
	NonWitnessUtxo     *wire.MsgTx
	WitnessUtxo        *wire.TxOut
	PartialSigs        []*PartialSig
	SighashType        txscript.SigHashType
	RedeemScript       []byte
	WitnessScript      []byte
	Bip32Derivation    []*Bip32Derivation
	FinalScriptSig     []byte
	FinalScriptWitness []byte
	Unknowns           []*Unknown
}

PInput is a struct encapsulating all the data that can be attached to any specific input of the PSBT.

func NewPsbtInput

func NewPsbtInput(nonWitnessUtxo *wire.MsgTx,
	witnessUtxo *wire.TxOut) *PInput

NewPsbtInput creates an instance of PsbtInput given either a nonWitnessUtxo or a witnessUtxo. NOTE only one of the two arguments should be specified, with the other being `nil`; otherwise the created PsbtInput object will fail IsSane() checks and will not be usable.

func (*PInput) IsSane

func (pi *PInput) IsSane() bool

IsSane returns true only if there are no conflicting values in the Psbt PInput. It checks that witness and non-witness utxo entries do not both exist, and that witnessScript entries are only added to witness inputs.

type POutput

type POutput struct {
	RedeemScript    []byte
	WitnessScript   []byte
	Bip32Derivation []*Bip32Derivation
}

POutput is a struct encapsulating all the data that can be attached to any specific output of the PSBT.

func NewPsbtOutput

func NewPsbtOutput(redeemScript []byte, witnessScript []byte,
	bip32Derivation []*Bip32Derivation) *POutput

NewPsbtOutput creates an instance of PsbtOutput; the three parameters redeemScript, witnessScript and Bip32Derivation are all allowed to be `nil`.

type PartialSig

type PartialSig struct {
	PubKey    []byte
	Signature []byte
}

PartialSig encapsulate a (BTC public key, ECDSA signature) pair, note that the fields are stored as byte slices, not btcec.PublicKey or btcec.Signature (because manipulations will be with the former not the latter, here); compliance with consensus serialization is enforced with .checkValid()

type PartialSigSorter

type PartialSigSorter []*PartialSig

PartialSigSorter implements sort.Interface.

func (PartialSigSorter) Len

func (s PartialSigSorter) Len() int

func (PartialSigSorter) Less

func (s PartialSigSorter) Less(i, j int) bool

func (PartialSigSorter) Swap

func (s PartialSigSorter) Swap(i, j int)

type Psbt

type Psbt struct {
	UnsignedTx *wire.MsgTx // Deserialization of unsigned tx
	Inputs     []PInput
	Outputs    []POutput
	Unknowns   []Unknown // Data of unknown type at global scope
}

Psbt is a set of 1 + N + M key-value pair lists, 1 global, defining the unsigned transaction structure with N inputs and M outputs. These key-value pairs can contain scripts, signatures, key derivations and other transaction-defining data.

func NewPsbt

func NewPsbt(psbtBytes []byte, b64 bool) (*Psbt, error)

NewPsbt returns a new instance of a Psbt struct created by reading from a byte slice. If the format is invalid, an error is returned. If the argument b64 is true, the passed byte slice is decoded from base64 encoding before processing. NOTE To create a Psbt from one's own data, rather than reading in a serialization from a counterparty, one should use a psbt.Creator.

func NewPsbtFromUnsignedTx

func NewPsbtFromUnsignedTx(tx *wire.MsgTx) (*Psbt, error)

NewPsbtFromUnsignedTx creates a new Psbt struct, without any signatures (i.e. only the global section is non-empty).

func (*Psbt) B64Encode

func (p *Psbt) B64Encode() (string, error)

B64Encode returns the base64 encoding of the serialization of the current PSBT, or an error if the encoding fails.

func (*Psbt) IsComplete

func (p *Psbt) IsComplete() bool

IsComplete returns true only if all of the inputs are finalized; this is particularly important in that it decides whether the final extraction to a network serialized signed transaction will be possible.

func (*Psbt) SanityCheck

func (p *Psbt) SanityCheck() error

SanityCheck checks conditions on a PSBT to ensure that it obeys the rules of BIP174, and returns true if so, false if not.

func (*Psbt) Serialize

func (p *Psbt) Serialize() ([]byte, error)

Serialize creates a binary serialization of the referenced Psbt struct with lexicographical ordering (by key) of the subsections

type Unknown

type Unknown struct {
	Key   []byte
	Value []byte
}

Unknown is a struct encapsulating a key-value pair for which the key type is unknown by this package; these fields are allowed in both the 'Global' and the 'Input' section of a PSBT.

type Updater

type Updater struct {
	Upsbt *Psbt
}

Updater encapsulates the role 'Updater' as specified in BIP174; it accepts Psbt structs and has methods to add fields to the inputs and outputs.

func NewUpdater

func NewUpdater(p *Psbt) (*Updater, error)

NewUpdater returns a new instance of Updater, if the passed Psbt struct is in a valid form, else an error.

func (*Updater) AddInBip32Derivation

func (p *Updater) AddInBip32Derivation(masterKeyFingerprint uint32,
	bip32Path []uint32, pubKeyData []byte, inIndex int) error

AddInBip32Derivation takes a master key fingerprint as defined in BIP32, a BIP32 path as a slice of uint32 values, and a serialized pubkey as a byte slice, along with the integer index of the input, and inserts this data into that input. NOTE that this can be called multiple times for the same input. An error is returned if addition of this key-value pair to the Psbt fails.

func (*Updater) AddInNonWitnessUtxo

func (p *Updater) AddInNonWitnessUtxo(tx *wire.MsgTx, inIndex int) error

AddInNonWitnessUtxo adds the utxo information for an input which is non-witness. This requires provision of a full transaction (which is the source of the corresponding prevOut), and the input index. If addition of this key-value pair to the Psbt fails, an error is returned.

func (*Updater) AddInRedeemScript

func (p *Updater) AddInRedeemScript(redeemScript []byte,
	inIndex int) error

AddInRedeemScript adds the redeem script information for an input. The redeem script is passed serialized, as a byte slice, along with the index of the input. An error is returned if addition of this key-value pair to the Psbt fails.

func (*Updater) AddInSighashType

func (p *Updater) AddInSighashType(sighashType txscript.SigHashType,
	inIndex int) error

AddInSighashType adds the sighash type information for an input. The sighash type is passed as a 32 bit unsigned integer, along with the index for the input. An error is returned if addition of this key-value pair to the Psbt fails.

func (*Updater) AddInWitnessScript

func (p *Updater) AddInWitnessScript(witnessScript []byte,
	inIndex int) error

AddInWitnessScript adds the witness script information for an input. The witness script is passed serialized, as a byte slice, along with the index of the input. An error is returned if addition of this key-value pair to the Psbt fails.

func (*Updater) AddInWitnessUtxo

func (p *Updater) AddInWitnessUtxo(txout *wire.TxOut, inIndex int) error

AddInWitnessUtxo adds the utxo information for an input which is witness. This requires provision of a full transaction *output* (which is the source of the corresponding prevOut); not the full transaction because BIP143 means the output information is sufficient, and the input index. If addition of this key-value pair to the Psbt fails, an error is returned.

func (*Updater) AddOutBip32Derivation

func (p *Updater) AddOutBip32Derivation(masterKeyFingerprint uint32,
	bip32Path []uint32, pubKeyData []byte, outIndex int) error

AddOutBip32Derivation takes a master key fingerprint as defined in BIP32, a BIP32 path as a slice of uint32 values, and a serialized pubkey as a byte slice, along with the integer index of the output, and inserts this data into that output. NOTE that this can be called multiple times for the same output. An error is returned if addition of this key-value pair to the Psbt fails.

func (*Updater) AddOutRedeemScript

func (p *Updater) AddOutRedeemScript(redeemScript []byte,
	outIndex int) error

AddOutRedeemScript takes a redeem script as a byte slice and appends it to the output at index outIndex.

func (*Updater) AddOutWitnessScript

func (p *Updater) AddOutWitnessScript(witnessScript []byte,
	outIndex int) error

AddOutWitnessScript takes a witness script as a byte slice and appends it to the output at index outIndex.

func (*Updater) Sign

func (u *Updater) Sign(inIndex int, sig []byte, pubKey []byte,
	redeemScript []byte, witnessScript []byte) (int, error)

Sign allows the caller to sign a PSBT at a particular input; they must provide a signature and a pubkey, both as byte slices; they can also optionally provide both witnessScript and/or redeemScript, otherwise these arguments must be set as nil (and in that case, they must already be present in the PSBT if required for signing to succeed).

Return value: 0 indicates that the partial signature was successfully attached. 1 indicates that this input is already finalized, so the provided signature was *not* attached -1 indicates that the provided signature data was not valid. In this case an error will also be returned.

This serves as a wrapper around Updater.addPartialSignature; it ensures that the redeemScript and witnessScript are updated as needed (note that the Updater is allowed to add redeemScripts and witnessScripts independently, before signing), and ensures that the right form of utxo field (NonWitnessUtxo or WitnessUtxo) is included in the input so that signature insertion (and then finalization) can take place.