mirror of
https://github.com/pezkuwichain/pezkuwi-wallet-android.git
synced 2026-07-22 18:25:50 +00:00
fix: reuse TronAddress.kt's existing Base58Check instead of duplicating it
CI caught a redeclaration - Base58Check is already a chain-agnostic object in this same package (TronAddress.kt), used for Tron's own Base58Check addresses. Bitcoin's legacy addresses are the same shape (1 version byte + 20-byte hash), just a different version byte - reuse it directly.
This commit is contained in:
@@ -1,53 +0,0 @@
|
|||||||
package io.novafoundation.nova.common.utils
|
|
||||||
|
|
||||||
import java.math.BigInteger
|
|
||||||
|
|
||||||
private const val BASE58_ALPHABET = "123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz"
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Base58Check - the legacy encoding used by Bitcoin's P2PKH (`1...`) and P2SH (`3...`) addresses, as opposed to
|
|
||||||
* native SegWit's bech32. Needed only to recognize/decode EXTERNAL destination addresses for sending (many
|
|
||||||
* exchanges, including at least one confirmed live, only offer a P2SH withdrawal address with no way to pick a
|
|
||||||
* native SegWit one) - this app's OWN address (derivation, receiving, `bitcoinAddressToAccountId()`) remains
|
|
||||||
* native SegWit only, unaffected by this.
|
|
||||||
*/
|
|
||||||
object Base58Check {
|
|
||||||
|
|
||||||
class Decoded(val version: Int, val payload: ByteArray)
|
|
||||||
|
|
||||||
fun decode(address: String): Decoded {
|
|
||||||
val full = base58Decode(address)
|
|
||||||
require(full.size == 25) { "Base58Check payload must be 25 bytes, got ${full.size}" }
|
|
||||||
|
|
||||||
val versionAndPayload = full.copyOfRange(0, 21)
|
|
||||||
val checksum = full.copyOfRange(21, 25)
|
|
||||||
val expectedChecksum = versionAndPayload.sha256d().copyOfRange(0, 4)
|
|
||||||
|
|
||||||
require(checksum.contentEquals(expectedChecksum)) { "Base58Check checksum mismatch" }
|
|
||||||
|
|
||||||
return Decoded(version = versionAndPayload[0].toInt() and 0xff, payload = versionAndPayload.copyOfRange(1, 21))
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun base58Decode(input: String): ByteArray {
|
|
||||||
require(input.isNotEmpty()) { "Base58 input must not be empty" }
|
|
||||||
|
|
||||||
var value = BigInteger.ZERO
|
|
||||||
val base = BigInteger.valueOf(58)
|
|
||||||
|
|
||||||
for (c in input) {
|
|
||||||
val digit = BASE58_ALPHABET.indexOf(c)
|
|
||||||
require(digit >= 0) { "Invalid base58 character: $c" }
|
|
||||||
value = value.multiply(base).add(BigInteger.valueOf(digit.toLong()))
|
|
||||||
}
|
|
||||||
|
|
||||||
val bytes = value.toByteArray().let {
|
|
||||||
// BigInteger.toByteArray() may prepend a 0x00 sign-disambiguation byte - strip it, it is not part of the data.
|
|
||||||
if (it.size > 1 && it[0] == 0.toByte()) it.copyOfRange(1, it.size) else it
|
|
||||||
}
|
|
||||||
|
|
||||||
// Each leading '1' character encodes a leading zero byte that BigInteger's conversion would otherwise drop.
|
|
||||||
val leadingZeros = input.takeWhile { it == '1' }.length
|
|
||||||
|
|
||||||
return ByteArray(leadingZeros) + bytes
|
|
||||||
}
|
|
||||||
}
|
|
||||||
+10
-4
@@ -33,12 +33,18 @@ fun String.decodeBitcoinDestination(): BitcoinDestination {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Base58Check itself is chain-agnostic (see TronAddress.kt) - a Bitcoin legacy address is 1 version byte +
|
||||||
|
// 20-byte hash, same shape as Tron's own address, just a different version byte and no fixed prefix meaning.
|
||||||
val decoded = Base58Check.decode(this)
|
val decoded = Base58Check.decode(this)
|
||||||
|
require(decoded.size == 21) { "Not a valid Bitcoin legacy address: $this" }
|
||||||
|
|
||||||
return when (decoded.version) {
|
val version = decoded[0].toInt() and 0xff
|
||||||
P2PKH_VERSION -> BitcoinDestination.P2pkh(decoded.payload)
|
val hash = decoded.copyOfRange(1, decoded.size)
|
||||||
P2SH_VERSION -> BitcoinDestination.P2sh(decoded.payload)
|
|
||||||
else -> error("Unsupported Bitcoin address version byte: ${decoded.version}")
|
return when (version) {
|
||||||
|
P2PKH_VERSION -> BitcoinDestination.P2pkh(hash)
|
||||||
|
P2SH_VERSION -> BitcoinDestination.P2sh(hash)
|
||||||
|
else -> error("Unsupported Bitcoin address version byte: $version")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user