Bitcoin Forum
May 10, 2024, 02:22:16 PM *
News: Latest Bitcoin Core release: 27.0 [Torrent]
 
   Home   Help Search Login Register More  
Pages: [1]
  Print  
Author Topic: [Solved]BouncyCastle - How to generate Bitcoin compatible keys, signatures...  (Read 6600 times)
0x6763
Guest

January 27, 2011, 09:32:33 PM
Last edit: January 28, 2011, 04:52:00 AM by 0x6763
 #1

So far, dirtyfilthy and I are using practically the same code for decoding public keys, generating key pairs, signing with private keys, and verifying signatures.  Here is the code: http://bitcointalk.org/index.php?topic=2957.msg41493#msg41493

But after finally making sure that I'm giving everything the correct data, getting the correct hashes, cross-checking it all with the data and hashes generated by the official bitcoin client, etc., our signature verification still isn't working.  It could either be that I'm not converting the bytes of the key to an ECPublicKey object correctly, or (what I think is slightly more likely) that I'm not using the right code for signature verification.  I don't know anything about BouncyCastle (and can't find much in the way of documentation outside of the partial Javadocs) or about the low-level details of ECDSA (or public key crypto in general), which makes it much harder to even know where to look.

And I still haven't even tried to generate key pairs or create new transactions to see if the official Bitcoin client verifies them correctly, yet, so I don't know if that code is ok or not, either.

Is there anyone with any Bitcoin and BouncyCastle experience that can help with this?

Thanks
1715350936
Hero Member
*
Offline Offline

Posts: 1715350936

View Profile Personal Message (Offline)

Ignore
1715350936
Reply with quote  #2

1715350936
Report to moderator
1715350936
Hero Member
*
Offline Offline

Posts: 1715350936

View Profile Personal Message (Offline)

Ignore
1715350936
Reply with quote  #2

1715350936
Report to moderator
Each block is stacked on top of the previous one. Adding another block to the top makes all lower blocks more difficult to remove: there is more "weight" above each block. A transaction in a block 6 blocks deep (6 confirmations) will be very difficult to remove.
Advertised sites are not endorsed by the Bitcoin Forum. They may be unsafe, untrustworthy, or illegal in your jurisdiction.
1715350936
Hero Member
*
Offline Offline

Posts: 1715350936

View Profile Personal Message (Offline)

Ignore
1715350936
Reply with quote  #2

1715350936
Report to moderator
1715350936
Hero Member
*
Offline Offline

Posts: 1715350936

View Profile Personal Message (Offline)

Ignore
1715350936
Reply with quote  #2

1715350936
Report to moderator
1715350936
Hero Member
*
Offline Offline

Posts: 1715350936

View Profile Personal Message (Offline)

Ignore
1715350936
Reply with quote  #2

1715350936
Report to moderator
0x6763
Guest

January 27, 2011, 11:32:31 PM
 #2

I posted to the BouncyCastle mailing list, too: http://www.bouncycastle.org/devmailarchive/msg11643.html
Hal
VIP
Sr. Member
*
expert
Offline Offline

Activity: 314
Merit: 3853



View Profile
January 28, 2011, 12:05:46 AM
 #3

Here's what I would suggest. Create a new key pair in your code. Hash and sign something like 'abc'. Then see if you can verify the signature. If it works, publish the key and signature here. I can try to verify the sig with OpenSSL. I was successful at verifying a Bitcoin signature, so this might reveal differences in the two libraries.

Hal Finney
0x6763
Guest

January 28, 2011, 12:23:51 AM
 #4

Here's what I would suggest. Create a new key pair in your code. Hash and sign something like 'abc'. Then see if you can verify the signature. If it works, publish the key and signature here. I can try to verify the sig with OpenSSL. I was successful at verifying a Bitcoin signature, so this might reveal differences in the two libraries.

I used "abc".

Code:
data: 616263
public key: 04cc2fcc1e68683f61ccc34b83737580bcc574dee4c0ec3c93fcbe8a0fce990187a92ecc95631f90229e853c209d865cd3f69a45a0c346c1a22d06f5103a5d78b5
signature: 3046022100cb4a3dc8cc0a149ef4e29b0501b84689514693c7a0a76107c13f3ecb0ef843d8022100bbc2b4b6b1879fbfa3883d0256fca1358884e215094dee36957759f6407b7502

And I'm able to verify this and other stuff generated by my code...just can't verify stuff from bitcoin, nor do I know if bitcoin will verify this.

Thanks!
Hal
VIP
Sr. Member
*
expert
Offline Offline

Activity: 314
Merit: 3853



View Profile
January 28, 2011, 02:04:13 AM
 #5

Well my attempt to verify that sig in openssl failed, it didn't verify. That's no surprise since the two methods also disagreed about the validity of the bitcoin sig. I hoped I'd see something wrong in the data structures, but I didn't. Your pubkey is a valid EC point on the secp256k1 curve. The signature appears to be properly formatted.

I'll see if I can think of anything else...

Hal Finney
0x6763
Guest

January 28, 2011, 02:34:51 AM
 #6

I wonder if they're using different encodings?  I'm looking at this doc page for the OpenSSL ECDSA stuff (http://www.openssl.org/docs/crypto/ecdsa.html), and there's a lot mentioned about DER encoding...I'm not sure, but I'm guessing Bitcoin is using DER, but I can't say whether or not the Java and BouncyCastle code is using DER or a different encoding.
dirtyfilthy
Member
**
Offline Offline

Activity: 77
Merit: 10


View Profile
January 28, 2011, 02:56:40 AM
 #7

Bitcoin uses a raw format that is not DER encoded, what code are you using to pump out that key? you want to use pubkey.encode() to get the DER version.
0x6763
Guest

January 28, 2011, 03:21:35 AM
 #8

Bitcoin uses a raw format that is not DER encoded, what code are you using to pump out that key? you want to use pubkey.encode() to get the DER version.

I believe I am using all the same code that you posted here: http://bitcointalk.org/index.php?topic=2957.msg41493#msg41493

What do you know about the signatures?  Are they encoded in some way in Bitcoin or BouncyCastle?
Hal
VIP
Sr. Member
*
expert
Offline Offline

Activity: 314
Merit: 3853



View Profile
January 28, 2011, 03:48:22 AM
 #9

Signatures are DER encoded in Bitcoin, and your signature above is in the same format. 30 is a sequence of values, in this case the two ECDSA components, called r and s. 46 is the length of the sequence. Then 02 means integer, 21 is the length, followed by 0x21 bytes which is the r value. Then there's another 02 and length for the s value. If the high bit of r or s is set, they get 00 prepended so it's clear they're positive. Bitcoin sigs have exactly the same format as you can see in any blockexplorer.com dump.

Hal Finney
0x6763
Guest

January 28, 2011, 04:51:28 AM
 #10

Finally! I figured it out!  Grin

The different methods for signing, verification, and I'm assuming the other method calls (EDIT: only the signing and verification methods) with the string "ECDSA" need to use "NONEwithECDSA" instead.  Now transactions are verifying for me!

I just happened to see "NONEwithECDSA" in section 2.4.3 of the BouncyCastle release notes page: http://www.bouncycastle.org/releasenotes.html
After seeing stuff about different DSA algorithms using SHA-1 and stuff, I wondered if maybe that was the problem and specifying NONEwithECDSA would prevent that.  No idea if that's the reason why it wasn't working, but now it is!

Thanks for all your help everyone!
Mike Hearn
Legendary
*
expert
Offline Offline

Activity: 1526
Merit: 1129


View Profile
January 28, 2011, 09:59:42 AM
 #11

Good to hear you have it figured out. I guess that explains the difference ... I didn't use JCE so I never had to specify that magic string.

Next up, successfully receive and send some coins with your implementation Wink
Cdecker
Hero Member
*****
Offline Offline

Activity: 489
Merit: 504



View Profile WWW
January 28, 2011, 12:31:32 PM
 #12

So referring to your code from the other post you'd simply replace the "ECDSA" String in the methods signData and verifySignedData with "NONEwithECDSA"?

Want to see what developers are chatting about? http://bitcoinstats.com/irc/bitcoin-dev/logs/
Bitcoin-OTC Rating
0x6763
Guest

January 28, 2011, 01:02:24 PM
 #13

So referring to your code from the other post you'd simply replace the "ECDSA" String in the methods signData and verifySignedData with "NONEwithECDSA"?

Yes.

There are a lot of choices like "SHA1withECDSA", "SHA256withECDSA", etc., and I'm guessing it's using one of these by default when signing and verifying, so we need "NONEwithECDSA" when signing and verifying.
Mike Hearn
Legendary
*
expert
Offline Offline

Activity: 1526
Merit: 1129


View Profile
January 28, 2011, 01:21:22 PM
 #14

Yes, because you are already doing the hashing yourself. If you don't specify NONEwithECDSA then the implementation will hash a second time and calculate the wrong result.
Pages: [1]
  Print  
 
Jump to:  

Powered by MySQL Powered by PHP Powered by SMF 1.1.19 | SMF © 2006-2009, Simple Machines Valid XHTML 1.0! Valid CSS!