summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristian Pointner <equinox@spreadspace.org>2013-07-10 01:59:51 +0000
committerChristian Pointner <equinox@spreadspace.org>2013-07-10 01:59:51 +0000
commit57657a44bef969f2ef900a8aafd48e8313630b6c (patch)
tree1c22331ff5abb66133b13b08675c7415410c7f83
parentdrop requirment for intelhex library (diff)
reenabled read flash
git-svn-id: https://svn.spreadspace.org/pic/trunk@66 a09c6847-51d9-44de-8ef2-e725cf50f3c7
-rwxr-xr-xbootloader/downloader.py40
-rw-r--r--bootloader/ihexpic.py221
2 files changed, 132 insertions, 129 deletions
diff --git a/bootloader/downloader.py b/bootloader/downloader.py
index 260ff7e..27b15c3 100755
--- a/bootloader/downloader.py
+++ b/bootloader/downloader.py
@@ -42,13 +42,16 @@ def load_hex(file):
hexdata.load_from_file(fin)
return hexdata
-# TODO: re-add this as soon as write_hex_file works
-# def write_hex(file, hexdata):
-# fout = file
-# if fout == '-':
-# fout = sys.stdout
+def write_hex(file, codedata):
+ from ihexpic import IHexPic
+
+ fout = file
+ if fout == '-':
+ fout = sys.stdout
-# hexdata.write_hex_file(fout)
+ hexdata = IHexPic()
+ hexdata.load_from_dict(codedata)
+ hexdata.write_to_file(fout)
def get_lowest_flash_addr(hexdata, fss):
lowest_code_addr = hexdata.get_lowest_addr()
@@ -222,18 +225,17 @@ def write_flash(dev, id, file):
# print >> sys.stderr, "%05X: %s" % (segment[0], ''.join('%04X '%i for i in segment[1]))
cmd_write_flash_segment(dev, id, segment[0], segment[1])
-# TODO: re-add this as soon as write_hex_file works
-# def read_flash(dev, id, file):
-# codedata = {}
-# for addr in xrange(0, id['fs'], id['fss']):
-# data = cmd_read_flash_segment(dev, id, addr)
-# # print >> sys.stderr, "%05X: %s" % (addr, ''.join('%04X '%i for i in data))
-# a = addr
-# for d in data:
-# codedata[a] = d
-# a += 1
-
-# write_hex(file, codedata)
+def read_flash(dev, id, file):
+ codedata = {}
+ for addr in xrange(0, id['fs'], id['fss']):
+ data = cmd_read_flash_segment(dev, id, addr)
+# print >> sys.stderr, "%05X: %s" % (addr, ''.join('%04X '%i for i in data))
+ a = addr
+ for d in data:
+ if d != 0x3FFF:
+ codedata[a] = d
+ a += 1
+ write_hex(file, codedata)
def verify_flash(dev, id, file):
hexdata = load_hex(file)
@@ -260,7 +262,7 @@ def verify_flash(dev, id, file):
commands = {
'boot': boot,
'write': write_flash,
-# 'read': read_flash, # TODO: re-add this as soon as write_hex_file works
+ 'read': read_flash,
'verify': verify_flash
}
diff --git a/bootloader/ihexpic.py b/bootloader/ihexpic.py
index d6978de..77b2929 100644
--- a/bootloader/ihexpic.py
+++ b/bootloader/ihexpic.py
@@ -191,116 +191,117 @@ class IHexPic(object):
self._buf.update(s)
# TODO: fix this so it works with 16bit data
- # def write_to_file(self, f):
- # """Write data to file f in HEX format.
-
- # @param f filename or file-like object for writing
- # """
- # fwrite = getattr(f, "write", None)
- # if fwrite:
- # fobj = f
- # fclose = None
- # else:
- # fobj = file(f, 'w')
- # fwrite = fobj.write
- # fclose = fobj.close
-
- # # Translation table for uppercasing hex ascii string.
- # # timeit shows that using hexstr.translate(table)
- # # is faster than hexstr.upper():
- # # 0.452ms vs. 0.652ms (translate vs. upper)
- # if sys.version_info[0] >= 3:
- # table = bytes(range(256)).upper()
- # else:
- # table = ''.join(chr(i).upper() for i in range(256))
-
-
- # # data
- # addresses = self._buf.keys()
- # addresses.sort()
- # addr_len = len(addresses)
- # if addr_len:
- # minaddr = addresses[0]
- # maxaddr = addresses[-1]
-
- # if maxaddr > 65535:
- # need_offset_record = True
- # else:
- # need_offset_record = False
- # high_ofs = 0
-
- # cur_addr = minaddr
- # cur_ix = 0
-
- # while cur_addr <= maxaddr:
- # if need_offset_record:
- # bin = array('B', str('\0'*7))
- # bin[0] = 2 # reclen
- # bin[1] = 0 # offset msb
- # bin[2] = 0 # offset lsb
- # bin[3] = 4 # rectyp
- # high_ofs = int(cur_addr>>16)
- # b = divmod(high_ofs, 256)
- # bin[4] = b[0] # msb of high_ofs
- # bin[5] = b[1] # lsb of high_ofs
- # bin[6] = (-sum(bin)) & 0x0FF # chksum
- # fwrite(':' +
- # str(hexlify(bin.tostring()).translate(table)) +
- # '\n')
-
- # while True:
- # # produce one record
- # low_addr = cur_addr & 0x0FFFF
- # # chain_len off by 1
- # chain_len = min(15, 65535-low_addr, maxaddr-cur_addr)
-
- # # search continuous chain
- # stop_addr = cur_addr + chain_len
- # if chain_len:
- # ix = bisect_right(addresses, stop_addr,
- # cur_ix,
- # min(cur_ix+chain_len+1, addr_len))
- # chain_len = ix - cur_ix # real chain_len
- # # there could be small holes in the chain
- # # but we will catch them by try-except later
- # # so for big continuous files we will work
- # # at maximum possible speed
- # else:
- # chain_len = 1 # real chain_len
-
- # bin = array('B', str('\0'*(5+chain_len)))
- # b = divmod(low_addr, 256)
- # bin[1] = b[0] # msb of low_addr
- # bin[2] = b[1] # lsb of low_addr
- # bin[3] = 0 # rectype
- # try: # if there is small holes we'll catch them
- # for i in range(chain_len):
- # bin[4+i] = self._buf[cur_addr+i]
- # except KeyError:
- # # we catch a hole so we should shrink the chain
- # chain_len = i
- # bin = bin[:5+i]
- # bin[0] = chain_len
- # bin[4+chain_len] = (-sum(bin)) & 0x0FF # chksum
- # fwrite(':' +
- # str(hexlify(bin.tostring()).translate(table)) +
- # '\n')
-
- # # adjust cur_addr/cur_ix
- # cur_ix += chain_len
- # if cur_ix < addr_len:
- # cur_addr = addresses[cur_ix]
- # else:
- # cur_addr = maxaddr + 1
- # break
- # high_addr = int(cur_addr>>16)
- # if high_addr > high_ofs:
- # break
-
- # # end-of-file record
- # fwrite(":00000001FF\n")
- # if fclose:
- # fclose()
+ def write_to_file(self, f):
+ """Write data to file f in HEX format.
+
+ @param f filename or file-like object for writing
+ """
+ fwrite = getattr(f, "write", None)
+ if fwrite:
+ fobj = f
+ fclose = None
+ else:
+ fobj = file(f, 'w')
+ fwrite = fobj.write
+ fclose = fobj.close
+
+ # Translation table for uppercasing hex ascii string.
+ # timeit shows that using hexstr.translate(table)
+ # is faster than hexstr.upper():
+ # 0.452ms vs. 0.652ms (translate vs. upper)
+ if sys.version_info[0] >= 3:
+ table = bytes(range(256)).upper()
+ else:
+ table = ''.join(chr(i).upper() for i in range(256))
+
+
+ # data
+ addresses = self._buf.keys()
+ addresses.sort()
+ addr_len = len(addresses)
+ if addr_len:
+ minaddr = addresses[0]
+ maxaddr = addresses[-1]
+
+ if maxaddr > 65535/2:
+ need_offset_record = True
+ else:
+ need_offset_record = False
+ high_ofs = 0
+
+ cur_addr = minaddr
+ cur_ix = 0
+
+ while cur_addr <= maxaddr:
+ if need_offset_record:
+ bin = array('B', str('\0'*7))
+ bin[0] = 2 # reclen
+ bin[1] = 0 # offset msb
+ bin[2] = 0 # offset lsb
+ bin[3] = 4 # rectype
+ high_ofs = int(cur_addr>>16)
+ b = divmod(high_ofs*2, 256)
+ bin[4] = b[0] # msb of high_ofs
+ bin[5] = b[1] # lsb of high_ofs
+ bin[6] = (-sum(bin)) & 0x0FF # chksum
+ fwrite(':' +
+ str(hexlify(bin.tostring()).translate(table)) +
+ '\n')
+
+ while True:
+ # produce one record
+ low_addr = cur_addr & 0x0FFFF
+ # chain_len off by 1
+ chain_len = min(7, 65535-low_addr, maxaddr-cur_addr)
+
+ # search continuous chain
+ stop_addr = cur_addr + chain_len
+ if chain_len:
+ ix = bisect_right(addresses, stop_addr,
+ cur_ix,
+ min(cur_ix+chain_len+1, addr_len))
+ chain_len = ix - cur_ix # real chain_len
+ # there could be small holes in the chain
+ # but we will catch them by try-except later
+ # so for big continuous files we will work
+ # at maximum possible speed
+ else:
+ chain_len = 1 # real chain_len
+
+ bin = array('B', str('\0'*(5+(chain_len*2))))
+ b = divmod(low_addr*2, 256)
+ bin[1] = b[0] # msb of low_addr
+ bin[2] = b[1] # lsb of low_addr
+ bin[3] = 0 # rectype
+ try: # if there is small holes we'll catch them
+ for i in range(chain_len):
+ bin[4+(i*2)] = self._buf[cur_addr+i] & 0x00FF
+ bin[4+(i*2)+1] = self._buf[cur_addr+i] >> 8
+ except KeyError:
+ # we catch a hole so we should shrink the chain
+ chain_len = i
+ bin = bin[:5+(i*2)]
+ bin[0] = chain_len*2
+ bin[4+(chain_len*2)] = (-sum(bin)) & 0x0FF # chksum
+ fwrite(':' +
+ str(hexlify(bin.tostring()).translate(table)) +
+ '\n')
+
+ # adjust cur_addr/cur_ix
+ cur_ix += chain_len
+ if cur_ix < addr_len:
+ cur_addr = addresses[cur_ix]
+ else:
+ cur_addr = maxaddr + 1
+ break
+ high_addr = int(cur_addr>>16)
+ if high_addr > high_ofs:
+ break
+
+ # end-of-file record
+ fwrite(":00000001FF\n")
+ if fclose:
+ fclose()
def get_lowest_addr(self):
return sorted(self._buf.keys())[0]