| 568 | } |
| 569 | |
| 570 | void privkey_from_prepriv(unsigned char *privkey, const unsigned char *prepriv, int preprivlen, unsigned char *privpriv = NULL) // derive private key from even more secret bulk of entropy |
| 571 | { |
| 572 | uchar temp[SHA512SIZE], pub[32], testpriv[32]; |
| 573 | sha512(temp, prepriv, preprivlen); |
| 574 | int esc, minesc = 32, minescpos = 0; |
| 575 | loopi(33) |
| 576 | { // find privte key with the public key with the least getint() escape codes (yes, that decreases the keyrange. sue me.) |
| 577 | ed25519_pubkey_from_private(testpriv, temp + i); |
| 578 | ed25519_pubkey_from_private(pub, testpriv); |
| 579 | esc = 0; |
| 580 | loopj(32) if((pub[j] & 0xfe) == 0x80) esc++; |
| 581 | if(esc < minesc) { minesc = esc; minescpos = i; } |
| 582 | if(esc == 0) break; |
| 583 | } |
| 584 | ed25519_pubkey_from_private(privkey, temp + minescpos); // (the resulting private key is actually itself a public key of a private derived from prepriv) |
| 585 | if(privpriv) memcpy(privpriv, temp + minescpos, 32); |
| 586 | } |
| 587 | |
| 588 | void ed25519_sign(uchar *sm, int *smlen, const uchar *m, int mlen, const uchar *sk) |
| 589 | { // sk: 32-byte private key + 32-byte public key |