Skip to content

Commit

Permalink
Clean up
Browse files Browse the repository at this point in the history
  • Loading branch information
sstone committed Sep 21, 2021
1 parent 0e5ebe0 commit fa13e6f
Show file tree
Hide file tree
Showing 2 changed files with 16 additions and 26 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -288,6 +288,7 @@ private class ReplaceableTxPublisher(nodeParams: NodeParams,
case claimAnchorTx: ClaimLocalAnchorOutputTx =>
val claimAnchorSig = keyManager.sign(claimAnchorTx, keyManager.fundingPublicKey(cmd.commitments.localParams.fundingKeyPath), TxOwner.Local, cmd.commitments.commitmentFormat)
val signedClaimAnchorTx = addSigs(claimAnchorTx, claimAnchorSig)
// update our psbt with our signature for our input, and ask bitcoin core to sign its input
val psbt1 = psbt.finalize(0, signedClaimAnchorTx.tx.txIn(0).witness).get
context.pipeToSelf(bitcoinClient.processPsbt(psbt1).map(processPbbtResponse => {
// all inputs should be signed now
Expand Down Expand Up @@ -399,9 +400,11 @@ private class ReplaceableTxPublisher(nodeParams: NodeParams,
val dummyChangeAmount = weight2fee(anchorFeerate, claimAnchorOutputMinWeight) + dustLimit
val address = publicKeyScriptToAddress(Script.pay2wpkh(PlaceHolderPubKey), nodeParams.chainHash)

// merge outptuts if needed to get a PSBT with a single output
def makeSingleOutput(fundPsbtResponse: FundPsbtResponse): Future[Psbt] = {
fundPsbtResponse.changePosition match {
case Some(changePos) =>
// add our main output to the change output
val changeOutput = fundPsbtResponse.psbt.global.tx.txOut(changePos)
val changeOutput1 = changeOutput.copy(amount = changeOutput.amount + dummyChangeAmount)
val psbt1 = fundPsbtResponse.psbt.copy(
Expand All @@ -410,6 +413,7 @@ private class ReplaceableTxPublisher(nodeParams: NodeParams,
)
Future.successful(psbt1)
case None =>
// replace our main output with a dummy change output
bitcoinClient.getChangeAddress().map(pubkeyHash => {
val changeOutput1 = TxOut(dummyChangeAmount, Script.pay2wpkh(pubkeyHash))
fundPsbtResponse.psbt.copy(
Expand All @@ -420,11 +424,12 @@ private class ReplaceableTxPublisher(nodeParams: NodeParams,
}

for {
fundPsbtResponse <- bitcoinClient.fundPsbt(Seq(computeP2WpkhAddress(PlaceHolderPubKey, nodeParams.chainHash) -> dummyChangeAmount), 0, FundPsbtOptions(anchorFeerate, lockUtxos = true, changePosition = Some(1)))
fundPsbtResponse <- bitcoinClient.fundPsbt(Seq(address -> dummyChangeAmount), 0, FundPsbtOptions(anchorFeerate, lockUtxos = true, changePosition = Some(1)))
psbt <- makeSingleOutput(fundPsbtResponse)
// NB: we insert the anchor input in the *first* position because our signing helpers only sign input #0.
unsignedTx = txInfo.copy(tx = psbt.global.tx.copy(txIn = txInfo.tx.txIn.head +: psbt.global.tx.txIn))
adjustedTx = adjustAnchorOutputChange(unsignedTx, commitTx, fundPsbtResponse.amountIn + AnchorOutputsCommitmentFormat.anchorAmount, commitFeerate, targetFeerate, dustLimit)
// add a PSBT input for our input (i.e the one that spends our own anchor/htlc output and that we'll need to sign
psbtInput = Psbt.PartiallySignedInput.empty.copy(
witnessUtxo = Some(txInfo.input.txOut),
witnessScript = Some(Script.parse(txInfo.input.redeemScript))
Expand All @@ -435,27 +440,6 @@ private class ReplaceableTxPublisher(nodeParams: NodeParams,
} yield {
(adjustedTx, psbt1)
}

// val txNotFunded = Transaction(2, Nil, TxOut(dummyChangeAmount, Script.pay2wpkh(PlaceHolderPubKey)) :: Nil, 0)
// bitcoinClient.fundTransaction(txNotFunded, FundTransactionOptions(anchorFeerate, lockUtxos = true)).flatMap(fundTxResponse => {
// // We merge the outputs if there's more than one.
// fundTxResponse.changePosition match {
// case Some(changePos) =>
// val changeOutput = fundTxResponse.tx.txOut(changePos)
// val txSingleOutput = fundTxResponse.tx.copy(txOut = Seq(changeOutput.copy(amount = changeOutput.amount + dummyChangeAmount)))
// Future.successful(fundTxResponse.copy(tx = txSingleOutput))
// case None =>
// bitcoinClient.getChangeAddress().map(pubkeyHash => {
// val txSingleOutput = fundTxResponse.tx.copy(txOut = Seq(TxOut(dummyChangeAmount, Script.pay2wpkh(pubkeyHash))))
// fundTxResponse.copy(tx = txSingleOutput)
// })
// }
// }).map(fundTxResponse => {
// require(fundTxResponse.tx.txOut.size == 1, "funded transaction should have a single change output")
// // NB: we insert the anchor input in the *first* position because our signing helpers only sign input #0.
// val unsignedTx = txInfo.copy(tx = fundTxResponse.tx.copy(txIn = txInfo.tx.txIn.head +: fundTxResponse.tx.txIn))
// adjustAnchorOutputChange(unsignedTx, commitTx, fundTxResponse.amountIn + AnchorOutputsCommitmentFormat.anchorAmount, commitFeerate, targetFeerate, dustLimit) -> Psbt(unsignedTx.tx)
// })
}

private def addInputs(txInfo: HtlcTx, targetFeerate: FeeratePerKw, commitments: Commitments): Future[(HtlcTx, Psbt)] = {
Expand Down
14 changes: 10 additions & 4 deletions eclair-core/src/main/scala/fr/acinq/eclair/package.scala
Original file line number Diff line number Diff line change
Expand Up @@ -95,29 +95,35 @@ package object eclair {
}
}

/**
*
* @param scriptPubKey public key script
* @param chainHash hash of the chain we're on
* @return the address the this public key script on this chain
*/
def publicKeyScriptToAddress(scriptPubKey: Seq[ScriptElt], chainHash: ByteVector32): String = {
val base58PubkeyPrefix = chainHash match {
case Block.LivenetGenesisBlock.hash => Base58.Prefix.PubkeyAddress
case Block.TestnetGenesisBlock.hash | Block.RegtestGenesisBlock.hash => Base58.Prefix.PubkeyAddressTestnet
case _ => ???
case _ => throw new IllegalArgumentException(s"invalid chain hash $chainHash")
}
val base58ScriptPrefix = chainHash match {
case Block.LivenetGenesisBlock.hash => Base58.Prefix.ScriptAddress
case Block.TestnetGenesisBlock.hash | Block.RegtestGenesisBlock.hash => Base58.Prefix.ScriptAddressTestnet
case _ => ???
case _ => throw new IllegalArgumentException(s"invalid chain hash $chainHash")
}
val hrp = chainHash match {
case Block.LivenetGenesisBlock.hash => "bc"
case Block.TestnetGenesisBlock.hash => "tb"
case Block.RegtestGenesisBlock.hash => "bcrt"
case _ => ???
case _ => throw new IllegalArgumentException(s"invalid chain hash $chainHash")
}
scriptPubKey match {
case OP_DUP :: OP_HASH160 :: OP_PUSHDATA(pubKeyHash, _) :: OP_EQUALVERIFY :: OP_CHECKSIG :: Nil => Base58Check.encode(base58PubkeyPrefix, pubKeyHash)
case OP_HASH160 :: OP_PUSHDATA(scriptHash, _) :: OP_EQUAL :: Nil => Base58Check.encode(base58ScriptPrefix, scriptHash)
case OP_0 :: OP_PUSHDATA(pubKeyHash, _) :: Nil if pubKeyHash.length == 20 => Bech32.encodeWitnessAddress(hrp, 0, pubKeyHash)
case OP_0 :: OP_PUSHDATA(scriptHash, _) :: Nil if scriptHash.length == 32 => Bech32.encodeWitnessAddress(hrp, 0, scriptHash)
case _ => ???
case _ => throw new IllegalArgumentException(s"invalid pubkey script $scriptPubKey")
}
}

Expand Down

0 comments on commit fa13e6f

Please sign in to comment.