Closed VzxPLnHqr closed 1 year ago
Ok, bare minimum tests pass. Can now send to and spend from taproot addresses. Key path only for now.
After shamelessly translating https://github.com/ACINQ/bitcoin-kmp/pull/40/commits/490bc0b4ac8f3850c09cb3d45a3d576b4960cb44#diff-435ce1291e658c59f775198e6107e93ae7803597ffeceede7066b51543e22cf3 over to Scala, we can now create and spend from tapscript transactions (keypath as well as script path).
Putting some notes here for us for when we get around to better documenting the taproot features of scoin
as they currently exist in this pull request:
There are two schnorr signing methods Crypto.signSchnorr(...)
and Crypto.signSchnorrWithTweak
:
def signSchnorr(
data: ByteVector32,
privateKey: PrivateKey,
auxrand32: Option[ByteVector32] = None
): ByteVector64
def signSchnorrWithTweak(
data: ByteVector32,
privateKey: PrivateKey,
merkleRoot: Option[ByteVector32],
auxrand32: Option[ByteVector32] = None
): ByteVector64
signSchnorrWithTweak
is used when spending with the "taproot" path -- before signing, the private key is "tweaked" by the provided merkleRoot
. As such, in order to sign, the signer must still know the merkle root of the tapscript tree.
signSchnorr
is used in all the other circumstances (at least so far in this codebase).
I was having a hard time figuring out why a bunch of the tests were failing in scoinNative
but passing in scoinJS
and scoinJVM
. Probably something to do with the wiring of how the c-library libsecp256k1
is used by the fiatjaf/sn-secp256k1
project, which in turn is used here by scoin
.
Not all the wiring is messed up, because some calls seem to work fine, such as PublicKey#toUncompressedBin
, and probably many others. But point addition was not seeming to give me the correct results. I think things were maybe getting tweaked twice or something.
So, in order to make progress, I ended up just naively implementing the ecc operations we need using BigInt
and modular arithmetic. I put it in a package scoin.inefficient
, but maybe it should be called scoin.reckless
?
commit 8478e77 adds a platform-independent and very untested implementation of the ecc math operations (point addition, point doubling, and multiplying a point by a scalar) ... reckless? yes, but it did pass all the existing tests at least.
Right now it is only used in the scoinNative
project. Signing (both schnorr and ecdsa) and anything pertaining to random number generation was not changed.
When we get the other wiring figured out we can just delete it if it is not useful. Or maybe we leave it and people will find it helpful for learning the ecc math.
Please do not merge until I get these tests passing. Opening this PR now though so we have a place to discuss the code as I will probably get stuck soon.