math to make a full private key have a mini private key equivalent

2

When creating a private key, how would I ensure that there is a mini private key equivalent, which could be substituted in place of the the full private key? What math would I have to use to create such a private key for bitcoins?

Gemohn Herbile

Posted 2015-04-19T19:10:33.157

Reputation: 101

Answers

2

You can't create a minikey for a private key - you need to create a private key once you've created a minikey.

You need to ensure that the SHA256 of the mini key plus a question mark after it has a hash starting with 00.

Or, in Python:

sha256(candidate + "?")[0] == chr(0)

The following Python program will generate mini keys:

import hashlib
from binascii import hexlify as hx
import random
rand = random.SystemRandom()

B58_ALPHA = "123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz"

def sha256(s):
    return hashlib.sha256(s).digest()

def gen_candidate():
    candidate = "S"
    for i in xrange(29):
        candidate = candidate + rand.choice(B58_ALPHA)
    return candidate

def test_candidate(candidate):
    return sha256(candidate + "?")[0] == chr(0)

while True:
    c = gen_candidate()
    if test_candidate(c):
        print c, hx(sha256(c))

Nick ODell

Posted 2015-04-19T19:10:33.157

Reputation: 26 536

2Pretty please use random.SystemRandom().choice() instead of random.choice(), even if it's just an example. We've been down the road of insecure RNGs before, and I'm sure you wouldn't want to contribute to that ;)Christopher Gurnee 2015-04-19T23:52:01.383

@ChristopherGurnee Good point.Nick ODell 2015-04-20T00:27:02.777

Yes, I have heard to use specific random generators before when making random numbers/strings that should be kept secret because if you use a well-known algorithm with few possibilities for the seed, your number could much more easily be guessed at.Gemohn Herbile 2015-04-20T12:37:14.800

For this particular example, for generating a single private key, it's actually OK to use random.choice() if a recent version of Python is used because the random module is well seeded from the OS's entropy source. For older versions of Python, or when generating many private keys at once (around 120 or more), using the base random module is very dangerous. It's always safer to just use SystemRandom() in crypto code.Christopher Gurnee 2015-04-20T15:00:09.917

@ChristopherGurnee it's actually OK to use random.choice() That's actually not true. Even though the RNG is securely seeded, it uses the Wichmann-Hill algorithm to actually generate numbers.Nick ODell 2015-04-20T17:36:48.030

1@NickODell It hasn't used WH for a few years now—it uses Mersenne Twister, specifically the 19937 variant. This isn't a CSPRNG either, and it's been shown that once you have 19937 bits of output (about 120 mini private keys' worth) you can predict all future output. Generating a small fraction of that is likely to be unpredictable assuming the seed contains enough entropy, although I don't think there's research on determining when (before gathering all 19937 bits) MT becomes feasibly predictable (which still makes it a bad idea I'll grant you!).Christopher Gurnee 2015-04-20T18:01:42.750

Shouldn't the loop be for i in xrange(29): since well-formed minikeys are 30 Base58 characters starting with S?

andebauchery 2016-04-19T06:54:48.523

@andebauchery Thanks for the catch. Not sure what I was thinking.Nick ODell 2016-04-19T14:48:13.400