forked from raspberrypi/pico-bootrom-rp2350
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathbin2hex
executable file
·72 lines (57 loc) · 2.69 KB
/
bin2hex
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
#!/usr/bin/env python3
help_str = """bin2hex: Convert flat binary files to Verilog-style hex files.
Output is little-endian, i.e. lower-addressed bytes are less significant in
the output words (further to the right). The word size can be specified, but
must be a multiple of 8 bits.
Start and end addresses can be specified, and the input will be padded if the
end address is past the end of the file. The default is to process the entire
file into hex. Address 0 is assumed to be the start of the file.
If multiple output files are specified, the output will be striped across them
word-for-word. Suitable for initialising striped SRAM like on RP2040.
"""
import sys
import re
import argparse
def bin2hex(wordsize, startaddr, endaddr, infile, outfiles):
if wordsize <= 0 or wordsize % 8 != 0:
sys.exit("Width must be a multiple of 8 (got {})".format(wordsize))
bytes_per_word = wordsize // 8
binimg = open(infile, 'rb').read()
if endaddr < 0:
endaddr = len(binimg)
if startaddr > endaddr:
sys.exit("Start address must not be greater than end address.")
if endaddr > len(binimg):
binimg = binimg + bytes(endaddr - len(binimg))
# Output is striped across multiple output files, with the first word
# going to the first file in the file list.
ofiles = [open(f,'w') for f in outfiles]
ofile_idx = 0
for chunk in range(startaddr, endaddr, bytes_per_word):
word = ''
for i in range(bytes_per_word):
word = ("%02X" % (binimg[chunk + i] if chunk + i < len(binimg) else 0)) + word
# Write to the output file, then rotate to next output file
ofiles[ofile_idx].write("%s\n" % word)
ofile_idx = (ofile_idx + 1) % len(outfiles)
for o in ofiles:
o.close()
# Allow hex, binary, decimal numbers etc on cmdline
def anyint(x):
try:
return int(x, 0)
except:
raise ValueError()
if __name__ == "__main__":
parser = argparse.ArgumentParser(epilog=help_str, formatter_class=argparse.RawDescriptionHelpFormatter)
parser.add_argument("-width", default=32, type=anyint,
help="Data per output line. Default is 32 bits.")
parser.add_argument("-start", type=anyint, default=0,
help="Address to start at. Default is 0, i.e. start of bin file.")
parser.add_argument("-end", type=anyint, default=-1,
help="Address to end at. Default is -1, meaning process the whole file.")
parser.add_argument("infile", help="input.bin")
parser.add_argument("outfile", nargs='+',
help="output hex files, can optionally stripe across multiple files")
args = parser.parse_args()
bin2hex(args.width, args.start, args.end, args.infile, args.outfile)