Skip to content

Commit 28f8dfa

Browse files
authored
Merge pull request #228 from shesek/202101-display-shwpkh
Fix checksum for nested sh(wpkh())
2 parents 48c0ff8 + ee0add3 commit 28f8dfa

File tree

3 files changed

+28
-12
lines changed

3 files changed

+28
-12
lines changed

src/descriptor/mod.rs

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1388,4 +1388,15 @@ pk(03f28773c2d975288bc7d1d205c3748651b075fbc6610e58cddeeddf8f19405aa8))";
13881388
// try to turn it back into a string with the secrets
13891389
assert_eq!(descriptor_str, descriptor.to_string_with_secret(&keymap));
13901390
}
1391+
1392+
#[test]
1393+
fn checksum_for_nested_sh() {
1394+
let descriptor_str = "sh(wpkh(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL))";
1395+
let descriptor: Descriptor<DescriptorPublicKey> = descriptor_str.parse().unwrap();
1396+
assert_eq!(descriptor.to_string(), "sh(wpkh(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL))#tjp2zm88");
1397+
1398+
let descriptor_str = "sh(wsh(pk(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL)))";
1399+
let descriptor: Descriptor<DescriptorPublicKey> = descriptor_str.parse().unwrap();
1400+
assert_eq!(descriptor.to_string(), "sh(wsh(pk(xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL)))#6c6hwr22");
1401+
}
13911402
}

src/descriptor/segwitv0.rs

Lines changed: 15 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -63,6 +63,14 @@ impl<Pk: MiniscriptKey> Wsh<Pk> {
6363
pub fn as_inner(&self) -> &WshInner<Pk> {
6464
&self.inner
6565
}
66+
67+
/// Get the descriptor without the checksum
68+
pub fn to_string_no_checksum(&self) -> String {
69+
match self.inner {
70+
WshInner::SortedMulti(ref smv) => format!("wsh({})", smv),
71+
WshInner::Ms(ref ms) => format!("wsh({})", ms),
72+
}
73+
}
6674
}
6775

6876
/// Wsh Inner
@@ -123,10 +131,7 @@ impl<Pk: MiniscriptKey> fmt::Debug for Wsh<Pk> {
123131

124132
impl<Pk: MiniscriptKey> fmt::Display for Wsh<Pk> {
125133
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
126-
let desc = match self.inner {
127-
WshInner::SortedMulti(ref smv) => format!("wsh({})", smv),
128-
WshInner::Ms(ref ms) => format!("wsh({})", ms),
129-
};
134+
let desc = self.to_string_no_checksum();
130135
let checksum = desc_checksum(&desc).map_err(|_| fmt::Error)?;
131136
write!(f, "{}#{}", &desc, &checksum)
132137
}
@@ -293,6 +298,11 @@ impl<Pk: MiniscriptKey> Wpkh<Pk> {
293298
pub fn as_inner(&self) -> &Pk {
294299
&self.pk
295300
}
301+
302+
/// Get the descriptor without the checksum
303+
pub fn to_string_no_checksum(&self) -> String {
304+
format!("wpkh({})", self.pk)
305+
}
296306
}
297307

298308
impl<Pk: MiniscriptKey> fmt::Debug for Wpkh<Pk> {
@@ -303,7 +313,7 @@ impl<Pk: MiniscriptKey> fmt::Debug for Wpkh<Pk> {
303313

304314
impl<Pk: MiniscriptKey> fmt::Display for Wpkh<Pk> {
305315
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
306-
let desc = format!("wpkh({})", self.pk);
316+
let desc = self.to_string_no_checksum();
307317
let checksum = desc_checksum(&desc).map_err(|_| fmt::Error)?;
308318
write!(f, "{}#{}", &desc, &checksum)
309319
}

src/descriptor/sh.rs

Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -82,13 +82,8 @@ impl<Pk: MiniscriptKey> fmt::Debug for Sh<Pk> {
8282
impl<Pk: MiniscriptKey> fmt::Display for Sh<Pk> {
8383
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
8484
let desc = match self.inner {
85-
// extra nesting because the impl of "{}" returns the checksum
86-
// which we don't want
87-
ShInner::Wsh(ref wsh) => match wsh.as_inner() {
88-
super::segwitv0::WshInner::SortedMulti(ref smv) => format!("sh(wsh({}))", smv),
89-
super::segwitv0::WshInner::Ms(ref ms) => format!("sh(wsh({}))", ms),
90-
},
91-
ShInner::Wpkh(ref pk) => format!("sh({})", pk),
85+
ShInner::Wsh(ref wsh) => format!("sh({})", wsh.to_string_no_checksum()),
86+
ShInner::Wpkh(ref pk) => format!("sh({})", pk.to_string_no_checksum()),
9287
ShInner::SortedMulti(ref smv) => format!("sh({})", smv),
9388
ShInner::Ms(ref ms) => format!("sh({})", ms),
9489
};

0 commit comments

Comments
 (0)