Add isStandard to Address (#4353)

This commit is contained in:
benthecarman 2022-05-27 08:04:18 -05:00 committed by GitHub
parent bf88d0d93f
commit 676c0b4261
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 35 additions and 0 deletions

View file

@ -210,6 +210,21 @@ class Bech32mTest extends BitcoinSUnitTest {
}
}
it must "validate addresses as non standard" in {
// Taproot address with invalid x-only pubkey
assert(
!Bech32mAddress
.fromString(
"bc1pvkpqgqe7g6sl4rxwhpqp8nlz6dmv5uk47k2nr9yhh9ds32ny49cqdcghmx")
.isStandard)
// segwit v2 address
assert(
!Bech32mAddress
.fromString("bc1zw508d6qejxtdg4y5r3zarvaryvaxxpcs")
.isStandard)
}
@tailrec
private def pickReplacementChar(oldChar: Char): Char = {
val rand = Math.abs(Random.nextInt())

View file

@ -36,6 +36,13 @@ sealed abstract class Address {
override def toString: String = value
def descriptor: String = s"addr($value)"
/** Checks if the address currently follows the standardness rules of bitcoin
* and will be relayed by network.
*
* Currently this just means verifying the address is not of a [[UnassignedWitnessScriptPubKey]]
*/
def isStandard: Boolean
}
sealed abstract class BitcoinAddress extends Address
@ -54,6 +61,7 @@ sealed abstract class P2PKHAddress extends BitcoinAddress {
override def scriptPubKey: P2PKHScriptPubKey = P2PKHScriptPubKey(hash)
override def isStandard: Boolean = true
}
sealed abstract class P2SHAddress extends BitcoinAddress {
@ -69,6 +77,8 @@ sealed abstract class P2SHAddress extends BitcoinAddress {
override def scriptPubKey: P2SHScriptPubKey = P2SHScriptPubKey(hash)
override def hash: Sha256Hash160Digest
override def isStandard: Boolean = true
}
/** https://github.com/bitcoin/bips/blob/master/bip-0173.mediawiki
@ -109,6 +119,8 @@ sealed abstract class Bech32Address extends BitcoinAddress {
def verifyChecksum: Boolean = {
Bech32.verifyChecksum(hrp.expand, data ++ checksum, Bech32Encoding.Bech32)
}
override def isStandard: Boolean = true
}
object Bech32Address extends AddressFactory[Bech32Address] {
@ -246,6 +258,14 @@ sealed abstract class Bech32mAddress extends BitcoinAddress {
def verifyChecksum: Boolean = {
Bech32.verifyChecksum(hrp.expand, data ++ checksum, Bech32Encoding.Bech32m)
}
override def isStandard: Boolean = {
scriptPubKey match {
case _: WitnessScriptPubKeyV0 => false // shouldn't be possible
case _: TaprootScriptPubKey => true
case _: UnassignedWitnessScriptPubKey => false
}
}
}
object Bech32mAddress extends AddressFactory[Bech32mAddress] {