Skip to content

Commit e88f972

Browse files
authored
Accomodate Updated BIP 78 Spec (payjoin#505)
See payjoin#480 `InternalInputContributionError` has only one error variant as a result of this, which means it's a smell to clean up in payjoin#403 One thing I note is that the BIP says "Our recommendation for <code>maxadditionalfeecontribution=</code> is <code>originalPSBTFeeRate * 110</code>." and our actual use is `let recommended_additional_fee = min_fee_rate * input_weight;` where input_weight is 110 only where mixed inputs appear. I did not remove the `expected_input_weight` function for a blanket 110 recommendation, which I believe is in line with actual incentives to use a matching input. but I could go either way.
2 parents dad5c1f + ab12170 commit e88f972

File tree

8 files changed

+4
-248
lines changed

8 files changed

+4
-248
lines changed

payjoin/src/receive/error.rs

-15
Original file line numberDiff line numberDiff line change
@@ -337,28 +337,13 @@ pub struct InputContributionError(InternalInputContributionError);
337337

338338
#[derive(Debug)]
339339
pub(crate) enum InternalInputContributionError {
340-
/// The address type could not be determined
341-
AddressType(crate::psbt::AddressTypeError),
342-
/// The original PSBT has no inputs
343-
NoSenderInputs,
344-
/// The proposed receiver inputs would introduce mixed input script types
345-
MixedInputScripts(bitcoin::AddressType, bitcoin::AddressType),
346340
/// Total input value is not enough to cover additional output value
347341
ValueTooLow,
348342
}
349343

350344
impl fmt::Display for InputContributionError {
351345
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
352346
match &self.0 {
353-
InternalInputContributionError::AddressType(e) =>
354-
write!(f, "The address type could not be determined: {}", e),
355-
InternalInputContributionError::NoSenderInputs =>
356-
write!(f, "The original PSBT has no inputs"),
357-
InternalInputContributionError::MixedInputScripts(type_a, type_b) => write!(
358-
f,
359-
"The proposed receiver inputs would introduce mixed input script types: {}; {}.",
360-
type_a, type_b
361-
),
362347
InternalInputContributionError::ValueTooLow =>
363348
write!(f, "Total input value is not enough to cover additional output value"),
364349
}

payjoin/src/receive/mod.rs

-6
Original file line numberDiff line numberDiff line change
@@ -36,12 +36,6 @@ impl InputPair {
3636
Ok(input_pair)
3737
}
3838

39-
pub(crate) fn address_type(&self) -> AddressType {
40-
InternalInputPair::from(self)
41-
.address_type()
42-
.expect("address type should have been validated in InputPair::new")
43-
}
44-
4539
pub(crate) fn previous_txout(&self) -> TxOut {
4640
InternalInputPair::from(self)
4741
.previous_txout()

payjoin/src/receive/v1/mod.rs

-47
Original file line numberDiff line numberDiff line change
@@ -495,18 +495,11 @@ impl WantsInputs {
495495
.first()
496496
.map(|input| input.sequence)
497497
.unwrap_or_default();
498-
let uniform_sender_input_type = self.uniform_sender_input_type()?;
499498

500499
// Insert contributions at random indices for privacy
501500
let mut rng = rand::thread_rng();
502501
let mut receiver_input_amount = Amount::ZERO;
503502
for input_pair in inputs.into_iter() {
504-
let input_type = input_pair.address_type();
505-
if self.params.v == 1 {
506-
// v1 payjoin proposals must not introduce mixed input script types
507-
self.check_mixed_input_types(input_type, uniform_sender_input_type)?;
508-
}
509-
510503
receiver_input_amount += input_pair.previous_txout().value;
511504
let index = rng.gen_range(0..=self.payjoin_psbt.unsigned_tx.input.len());
512505
payjoin_psbt.inputs.insert(index, input_pair.psbtin);
@@ -533,46 +526,6 @@ impl WantsInputs {
533526
})
534527
}
535528

536-
/// Check for mixed input types and throw an error if conditions are met
537-
fn check_mixed_input_types(
538-
&self,
539-
receiver_input_type: bitcoin::AddressType,
540-
uniform_sender_input_type: Option<bitcoin::AddressType>,
541-
) -> Result<(), InputContributionError> {
542-
if let Some(uniform_sender_input_type) = uniform_sender_input_type {
543-
if receiver_input_type != uniform_sender_input_type {
544-
return Err(InternalInputContributionError::MixedInputScripts(
545-
receiver_input_type,
546-
uniform_sender_input_type,
547-
)
548-
.into());
549-
}
550-
}
551-
Ok(())
552-
}
553-
554-
/// Check if the sender's inputs are all of the same type
555-
///
556-
/// Returns `None` if the sender inputs are not all of the same type
557-
fn uniform_sender_input_type(
558-
&self,
559-
) -> Result<Option<bitcoin::AddressType>, InputContributionError> {
560-
let mut sender_inputs = self.original_psbt.input_pairs();
561-
let first_input_type = sender_inputs
562-
.next()
563-
.ok_or(InternalInputContributionError::NoSenderInputs)?
564-
.address_type()
565-
.map_err(InternalInputContributionError::AddressType)?;
566-
for input in sender_inputs {
567-
if input.address_type().map_err(InternalInputContributionError::AddressType)?
568-
!= first_input_type
569-
{
570-
return Ok(None);
571-
}
572-
}
573-
Ok(Some(first_input_type))
574-
}
575-
576529
// Compute the minimum amount that the receiver must contribute to the transaction as input
577530
fn receiver_min_input_amount(&self) -> Amount {
578531
let output_amount = self

payjoin/src/send/error.rs

+1-10
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ use std::fmt::{self, Display};
22

33
use bitcoin::locktime::absolute::LockTime;
44
use bitcoin::transaction::Version;
5-
use bitcoin::{AddressType, Sequence};
5+
use bitcoin::Sequence;
66

77
/// Error building a Sender from a SenderBuilder.
88
///
@@ -147,16 +147,13 @@ pub(crate) enum InternalProposalError {
147147
VersionsDontMatch { proposed: Version, original: Version },
148148
LockTimesDontMatch { proposed: LockTime, original: LockTime },
149149
SenderTxinSequenceChanged { proposed: Sequence, original: Sequence },
150-
SenderTxinContainsNonWitnessUtxo,
151-
SenderTxinContainsWitnessUtxo,
152150
SenderTxinContainsFinalScriptSig,
153151
SenderTxinContainsFinalScriptWitness,
154152
TxInContainsKeyPaths,
155153
ContainsPartialSigs,
156154
ReceiverTxinNotFinalized,
157155
ReceiverTxinMissingUtxoInfo,
158156
MixedSequence,
159-
MixedInputTypes { proposed: AddressType, original: AddressType },
160157
MissingOrShuffledInputs,
161158
TxOutContainsKeyPaths,
162159
FeeContributionExceedsMaximum,
@@ -188,16 +185,13 @@ impl fmt::Display for InternalProposalError {
188185
VersionsDontMatch { proposed, original, } => write!(f, "proposed transaction version {} doesn't match the original {}", proposed, original),
189186
LockTimesDontMatch { proposed, original, } => write!(f, "proposed transaction lock time {} doesn't match the original {}", proposed, original),
190187
SenderTxinSequenceChanged { proposed, original, } => write!(f, "proposed transaction sequence number {} doesn't match the original {}", proposed, original),
191-
SenderTxinContainsNonWitnessUtxo => write!(f, "an input in proposed transaction belonging to the sender contains non-witness UTXO information"),
192-
SenderTxinContainsWitnessUtxo => write!(f, "an input in proposed transaction belonging to the sender contains witness UTXO information"),
193188
SenderTxinContainsFinalScriptSig => write!(f, "an input in proposed transaction belonging to the sender contains finalized non-witness signature"),
194189
SenderTxinContainsFinalScriptWitness => write!(f, "an input in proposed transaction belonging to the sender contains finalized witness signature"),
195190
TxInContainsKeyPaths => write!(f, "proposed transaction inputs contain key paths"),
196191
ContainsPartialSigs => write!(f, "an input in proposed transaction belonging to the sender contains partial signatures"),
197192
ReceiverTxinNotFinalized => write!(f, "an input in proposed transaction belonging to the receiver is not finalized"),
198193
ReceiverTxinMissingUtxoInfo => write!(f, "an input in proposed transaction belonging to the receiver is missing UTXO information"),
199194
MixedSequence => write!(f, "inputs of proposed transaction contain mixed sequence numbers"),
200-
MixedInputTypes { proposed, original, } => write!(f, "proposed transaction contains input of type {:?} while original contains inputs of type {:?}", proposed, original),
201195
MissingOrShuffledInputs => write!(f, "proposed transaction is missing inputs of the sender or they are shuffled"),
202196
TxOutContainsKeyPaths => write!(f, "proposed transaction outputs contain key paths"),
203197
FeeContributionExceedsMaximum => write!(f, "fee contribution exceeds allowed maximum"),
@@ -225,16 +219,13 @@ impl std::error::Error for InternalProposalError {
225219
VersionsDontMatch { proposed: _, original: _ } => None,
226220
LockTimesDontMatch { proposed: _, original: _ } => None,
227221
SenderTxinSequenceChanged { proposed: _, original: _ } => None,
228-
SenderTxinContainsNonWitnessUtxo => None,
229-
SenderTxinContainsWitnessUtxo => None,
230222
SenderTxinContainsFinalScriptSig => None,
231223
SenderTxinContainsFinalScriptWitness => None,
232224
TxInContainsKeyPaths => None,
233225
ContainsPartialSigs => None,
234226
ReceiverTxinNotFinalized => None,
235227
ReceiverTxinMissingUtxoInfo => None,
236228
MixedSequence => None,
237-
MixedInputTypes { .. } => None,
238229
MissingOrShuffledInputs => None,
239230
TxOutContainsKeyPaths => None,
240231
FeeContributionExceedsMaximum => None,

payjoin/src/send/mod.rs

-14
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,6 @@ pub struct PsbtContext {
3838
fee_contribution: Option<(bitcoin::Amount, usize)>,
3939
min_fee_rate: FeeRate,
4040
payee: ScriptBuf,
41-
allow_mixed_input_scripts: bool,
4241
}
4342

4443
macro_rules! check_eq {
@@ -145,11 +144,6 @@ impl PsbtContext {
145144
original.txin.sequence,
146145
SenderTxinSequenceChanged
147146
);
148-
ensure!(
149-
proposed.psbtin.non_witness_utxo.is_none(),
150-
SenderTxinContainsNonWitnessUtxo
151-
);
152-
ensure!(proposed.psbtin.witness_utxo.is_none(), SenderTxinContainsWitnessUtxo);
153147
ensure!(
154148
proposed.psbtin.final_script_sig.is_none(),
155149
SenderTxinContainsFinalScriptSig
@@ -180,13 +174,6 @@ impl PsbtContext {
180174
ReceiverTxinMissingUtxoInfo
181175
);
182176
ensure!(proposed.txin.sequence == original.txin.sequence, MixedSequence);
183-
if !self.allow_mixed_input_scripts {
184-
check_eq!(
185-
proposed.address_type()?,
186-
original.address_type()?,
187-
MixedInputTypes
188-
);
189-
}
190177
}
191178
}
192179
}
@@ -448,7 +435,6 @@ pub(crate) mod test {
448435
fee_contribution: Some((bitcoin::Amount::from_sat(182), 0)),
449436
min_fee_rate: FeeRate::ZERO,
450437
payee,
451-
allow_mixed_input_scripts: false,
452438
}
453439
}
454440

payjoin/src/send/v1.rs

-1
Original file line numberDiff line numberDiff line change
@@ -245,7 +245,6 @@ impl Sender {
245245
fee_contribution: self.fee_contribution,
246246
payee: self.payee.clone(),
247247
min_fee_rate: self.min_fee_rate,
248-
allow_mixed_input_scripts: false,
249248
},
250249
},
251250
))

payjoin/src/send/v2/mod.rs

-1
Original file line numberDiff line numberDiff line change
@@ -177,7 +177,6 @@ impl Sender {
177177
fee_contribution: self.v1.fee_contribution,
178178
payee: self.v1.payee.clone(),
179179
min_fee_rate: self.v1.min_fee_rate,
180-
allow_mixed_input_scripts: true,
181180
},
182181
hpke_ctx,
183182
ohttp_ctx,

0 commit comments

Comments
 (0)