aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--contrib/misc/example-linearize.cfg12
-rwxr-xr-xcontrib/misc/linearize.py129
2 files changed, 141 insertions, 0 deletions
diff --git a/contrib/misc/example-linearize.cfg b/contrib/misc/example-linearize.cfg
new file mode 100644
index 0000000000..9e5aa404c2
--- /dev/null
+++ b/contrib/misc/example-linearize.cfg
@@ -0,0 +1,12 @@
+
+# bitcoind RPC settings
+rpcuser=someuser
+rpcpass=somepassword
+host=127.0.0.1
+port=8332
+
+# bootstrap.dat settings
+netmagic=f9beb4d9
+max_height=250000
+output=bootstrap.dat
+
diff --git a/contrib/misc/linearize.py b/contrib/misc/linearize.py
new file mode 100755
index 0000000000..b4f02b7954
--- /dev/null
+++ b/contrib/misc/linearize.py
@@ -0,0 +1,129 @@
+#!/usr/bin/python
+#
+# linearize.py: Construct a linear, no-fork, best version of the blockchain.
+#
+#
+# Copyright (c) 2013 The Bitcoin developers
+# Distributed under the MIT/X11 software license, see the accompanying
+# file COPYING or http://www.opensource.org/licenses/mit-license.php.
+#
+
+import json
+import struct
+import re
+import base64
+import httplib
+import sys
+
+ERR_SLEEP = 15
+MAX_NONCE = 1000000L
+
+settings = {}
+
+class BitcoinRPC:
+ OBJID = 1
+
+ def __init__(self, host, port, username, password):
+ authpair = "%s:%s" % (username, password)
+ self.authhdr = "Basic %s" % (base64.b64encode(authpair))
+ self.conn = httplib.HTTPConnection(host, port, False, 30)
+ def rpc(self, method, params=None):
+ self.OBJID += 1
+ obj = { 'version' : '1.1',
+ 'method' : method,
+ 'id' : self.OBJID }
+ if params is None:
+ obj['params'] = []
+ else:
+ obj['params'] = params
+ self.conn.request('POST', '/', json.dumps(obj),
+ { 'Authorization' : self.authhdr,
+ 'Content-type' : 'application/json' })
+
+ resp = self.conn.getresponse()
+ if resp is None:
+ print "JSON-RPC: no response"
+ return None
+
+ body = resp.read()
+ resp_obj = json.loads(body)
+ if resp_obj is None:
+ print "JSON-RPC: cannot JSON-decode body"
+ return None
+ if 'error' in resp_obj and resp_obj['error'] != None:
+ return resp_obj['error']
+ if 'result' not in resp_obj:
+ print "JSON-RPC: no result in object"
+ return None
+
+ return resp_obj['result']
+ def getblock(self, hash, verbose=True):
+ return self.rpc('getblock', [hash, verbose])
+ def getblockhash(self, index):
+ return self.rpc('getblockhash', [index])
+
+def getblock(rpc, settings, n):
+ hash = rpc.getblockhash(n)
+ hexdata = rpc.getblock(hash, False)
+ data = hexdata.decode('hex')
+
+ return data
+
+def get_blocks(settings):
+ rpc = BitcoinRPC(settings['host'], settings['port'],
+ settings['rpcuser'], settings['rpcpass'])
+
+ outf = open(settings['output'], 'wb')
+
+ for height in xrange(settings['max_height']+1):
+ data = getblock(rpc, settings, height)
+
+ outhdr = settings['netmagic']
+ outhdr += struct.pack("<i", len(data))
+
+ outf.write(outhdr)
+ outf.write(data)
+
+ if (height % 1000) == 0:
+ sys.stdout.write("Wrote block " + str(height) + "\n")
+
+if __name__ == '__main__':
+ if len(sys.argv) != 2:
+ print "Usage: mkbootstrap.py CONFIG-FILE"
+ sys.exit(1)
+
+ f = open(sys.argv[1])
+ for line in f:
+ # skip comment lines
+ m = re.search('^\s*#', line)
+ if m:
+ continue
+
+ # parse key=value lines
+ m = re.search('^(\w+)\s*=\s*(\S.*)$', line)
+ if m is None:
+ continue
+ settings[m.group(1)] = m.group(2)
+ f.close()
+
+ if 'netmagic' not in settings:
+ settings['netmagic'] = 'f9beb4d9'
+ if 'output' not in settings:
+ settings['output'] = 'bootstrap.dat'
+ if 'host' not in settings:
+ settings['host'] = '127.0.0.1'
+ if 'port' not in settings:
+ settings['port'] = 8332
+ if 'max_height' not in settings:
+ settings['max_height'] = 250000
+ if 'rpcuser' not in settings or 'rpcpass' not in settings:
+ print "Missing username and/or password in cfg file"
+ sys.exit(1)
+
+ settings['netmagic'] = settings['netmagic'].decode('hex')
+ settings['port'] = int(settings['port'])
+ settings['max_height'] = int(settings['max_height'])
+
+ get_blocks(settings)
+
+