Browse Source

Relax the constraints on read_headers

They were really for fs_block_hashes; that still enforces
the full constraint.  Simplifies get_chunk.
patch-2
Neil Booth 7 years ago
parent
commit
49ee008346
  1. 14
      server/controller.py
  2. 30
      server/db.py

14
server/controller.py

@ -299,11 +299,11 @@ class Controller(ServerBase):
def electrum_header(self, height): def electrum_header(self, height):
'''Return the binary header at the given height.''' '''Return the binary header at the given height.'''
if not 0 <= height <= self.bp.db_height:
raise RPCError('height {:,d} out of range'.format(height))
if height in self.header_cache: if height in self.header_cache:
return self.header_cache[height] return self.header_cache[height]
header = self.bp.read_headers(height, 1) header, n = self.bp.read_headers(height, 1)
if n != 1:
raise RPCError('height {:,d} out of range'.format(height))
header = self.coin.electrum_header(header, height) header = self.coin.electrum_header(header, height)
self.header_cache[height] = header self.header_cache[height] = header
return header return header
@ -750,10 +750,10 @@ class Controller(ServerBase):
def get_chunk(self, index): def get_chunk(self, index):
'''Return header chunk as hex. Index is a non-negative integer.''' '''Return header chunk as hex. Index is a non-negative integer.'''
chunk_size = self.coin.CHUNK_SIZE chunk_size = self.coin.CHUNK_SIZE
next_height = self.bp.db_height + 1 start_height = index * chunk_size
start_height = min(index * chunk_size, next_height) count = chunk_size
count = min(next_height - start_height, chunk_size) headers, n = self.bp.read_headers(start_height, count).hex()
return self.bp.read_headers(start_height, count).hex() return headers
# Client RPC "blockchain" command handlers # Client RPC "blockchain" command handlers

30
server/db.py

@ -209,18 +209,25 @@ class DB(util.LoggedClass):
offset = prior_tx_count * 32 offset = prior_tx_count * 32
self.hashes_file.write(offset, hashes) self.hashes_file.write(offset, hashes)
def read_headers(self, start, count): def read_headers(self, start_height, count):
'''Requires count >= 0.''' '''Requires start_height >= 0, count >= 0. Reads as many headers as
are available starting at start_height up to count. This
would be zero if start_height is beyond self.db_height, for
example.
Returns a (binary, n) pair where binary is the concatenated
binary headers, and n is the count of headers returned.
'''
# Read some from disk # Read some from disk
disk_count = min(count, self.db_height + 1 - start) if start_height < 0 or count < 0:
if start < 0 or count < 0 or disk_count != count:
raise self.DBError('{:,d} headers starting at {:,d} not on disk' raise self.DBError('{:,d} headers starting at {:,d} not on disk'
.format(count, start)) .format(count, start_height))
disk_count = max(0, min(count, self.db_height + 1 - start_height))
if disk_count: if disk_count:
offset = self.header_offset(start) offset = self.header_offset(start_height)
size = self.header_offset(start + disk_count) - offset size = self.header_offset(start_height + disk_count) - offset
return self.headers_file.read(offset, size) return self.headers_file.read(offset, size), disk_count
return b'' return b'', 0
def fs_tx_hash(self, tx_num): def fs_tx_hash(self, tx_num):
'''Return a par (tx_hash, tx_height) for the given tx number. '''Return a par (tx_hash, tx_height) for the given tx number.
@ -234,7 +241,10 @@ class DB(util.LoggedClass):
return tx_hash, tx_height return tx_hash, tx_height
def fs_block_hashes(self, height, count): def fs_block_hashes(self, height, count):
headers_concat = self.read_headers(height, count) headers_concat, headers_count = self.read_headers(height, count)
if headers_count != count:
raise self.DBError('only got {:,d} headers starting at {:,d}, not '
'{:,d}'.format(headers_count, start, count))
offset = 0 offset = 0
headers = [] headers = []
for n in range(count): for n in range(count):

Loading…
Cancel
Save