@covenance/dlc
Version:
Crypto and Bitcoin functions for Covenance DLC implementation
98 lines (89 loc) • 3.44 kB
text/typescript
import { Transaction } from '../btc';
import { Point } from '../crypto/secp256k1';
import { sighashForAdaptorSig } from './sighash';
import { createAdaptorSig, verifyAdaptorSig } from '../crypto/counterparty';
import { PrivKey, AdaptorSignature, Signature, PubKey } from '../crypto/types';
import { verifySig } from '../crypto/general';
import { be32 } from '../utils';
/**
* Creates an adaptor signature for a CET
* @param counterpartyPrivKey - The private key of the counterparty creating the signature
* @param oracleSigPoint - The oracle's signature point for the event outcome
* @param cet - The CET transaction to sign
* @param inputIndex - The index of the input to sign in the CET
* @param tapleafHash - The hash of the tapleaf
* @returns The adaptor signature for the CET
*/
export async function signCetWithAdaptorSig(
counterpartyPrivKey: PrivKey,
oracleSigPoint: Point,
cet: Transaction,
inputIndex: number,
tapleafHash: Buffer
): Promise<AdaptorSignature> {
// Get the sighash for the CET
const cetSighash = sighashForAdaptorSig(cet, inputIndex, tapleafHash);
// Create the adaptor signature using the sighash as the message
return createAdaptorSig(counterpartyPrivKey, oracleSigPoint, cetSighash);
}
/**
* Verifies an adaptor signature for a CET
* @param signature - The adaptor signature to verify
* @param counterpartyPubKey - The counterparty's public key
* @param oracleSigPoint - The oracle's signature point for the event outcome
* @param cet - The CET transaction that was signed
* @param inputIndex - The index of the input that was signed
* @param tapleafHash - The hash of the tapleaf
* @returns True if the signature is valid, false otherwise
*/
export async function verifyCetAdaptorSig(
signature: AdaptorSignature,
counterpartyPubKey: PubKey,
oracleSigPoint: Point,
cet: Transaction,
inputIndex: number,
tapleafHash: Buffer
): Promise<boolean> {
// Get the sighash for the CET
const cetSighash = sighashForAdaptorSig(cet, inputIndex, tapleafHash);
// Verify the signature using the sighash as the message
return verifyAdaptorSig(signature, counterpartyPubKey, cetSighash, oracleSigPoint);
}
/**
* Verifies a completed signature for a CET
* @param signature - The completed signature to verify
* @param counterpartyPubKey - The counterparty's public key
* @param cet - The CET transaction that was signed
* @param inputIndex - The index of the input that was signed
* @param tapleafHash - The hash of the tapleaf
* @returns True if the signature is valid, false otherwise
*/
export async function verifyCetSignature(
signature: Signature,
counterpartyPubKey: PubKey,
cet: Transaction,
inputIndex: number,
tapleafHash: Buffer
): Promise<boolean> {
// Get the sighash for the CET
const cetSighash = sighashForAdaptorSig(cet, inputIndex, tapleafHash);
// Verify the signature using the sighash as the message
return verifySig(signature, counterpartyPubKey, cetSighash);
}
/**
* Taproot/SegWit-v1 Schnorr signature serializer
* @param signature - The signature to serialize
* @param sighash - The sighash to serialize
* @returns The serialized signature
*/
export function sigToTaprootBuf(
{ R, s }: Signature,
sighash = 0x00
): Uint8Array {
const addFlag = sighash !== 0x00;
const out = new Uint8Array(addFlag ? 65 : 64);
be32(out, 0, R.x);
be32(out, 32, s);
if (addFlag) out[64] = sighash;
return out;
}