Flash generator as function
parent
4d69d31fc8
commit
f34340cbdb
101
bit_to_flash.py
101
bit_to_flash.py
|
@ -2,13 +2,10 @@
|
|||
|
||||
import sys
|
||||
import textwrap
|
||||
import datetime
|
||||
|
||||
# Very basic bitstream to SVF converter, tested with the ULX3S WiFi interface
|
||||
|
||||
flash_page_size = 256
|
||||
erase_block_size = 64*1024
|
||||
|
||||
|
||||
def bitreverse(x):
|
||||
y = 0
|
||||
for i in range(8):
|
||||
|
@ -16,29 +13,30 @@ def bitreverse(x):
|
|||
y |= (1 << i)
|
||||
return y
|
||||
|
||||
with open(sys.argv[1], 'rb') as bitf:
|
||||
bs = bitf.read()
|
||||
# Autodetect IDCODE from bitstream
|
||||
idcode_cmd = bytes([0xE2, 0x00, 0x00, 0x00])
|
||||
idcode = None
|
||||
for i in range(len(bs) - 4):
|
||||
if bs[i:i+4] == idcode_cmd:
|
||||
idcode = bs[i+4] << 24
|
||||
idcode |= bs[i+5] << 16
|
||||
idcode |= bs[i+6] << 8
|
||||
idcode |= bs[i+7]
|
||||
break
|
||||
if idcode is None:
|
||||
print("Failed to find IDCODE in bitstream, check bitstream is valid")
|
||||
sys.exit(1)
|
||||
print("IDCODE in bitstream is 0x%08x" % idcode)
|
||||
bitf.seek(0)
|
||||
def convertBitToFlashFile(bitFile, FlashFile, flash_page_size = 256, address = 0, erase_block_size = 64*1024):
|
||||
with open(bitFile, 'rb') as bitf:
|
||||
bs = bitf.read()
|
||||
# Autodetect IDCODE from bitstream
|
||||
idcode_cmd = bytes([0xE2, 0x00, 0x00, 0x00])
|
||||
idcode = None
|
||||
for i in range(len(bs) - 4):
|
||||
if bs[i:i+4] == idcode_cmd:
|
||||
idcode = bs[i+4] << 24
|
||||
idcode |= bs[i+5] << 16
|
||||
idcode |= bs[i+6] << 8
|
||||
idcode |= bs[i+7]
|
||||
break
|
||||
if idcode is None:
|
||||
print("Failed to find IDCODE in bitstream, check bitstream is valid")
|
||||
sys.exit(1)
|
||||
print("IDCODE in bitstream is 0x%08x" % idcode)
|
||||
bitf.seek(0)
|
||||
|
||||
address = 0
|
||||
last_page = -1
|
||||
last_page = -1
|
||||
|
||||
with open(sys.argv[2], 'w') as svf:
|
||||
print("""
|
||||
with open(FlashFile, 'w') as svf:
|
||||
now = datetime.datetime.now()
|
||||
print(f"""// generated {now:%Y-%m-%d %H:%M}
|
||||
STATE RESET;
|
||||
HDR 0;
|
||||
HIR 0;
|
||||
|
@ -48,13 +46,13 @@ ENDDR DRPAUSE;
|
|||
ENDIR IRPAUSE;
|
||||
STATE IDLE;
|
||||
""", file=svf)
|
||||
print("""
|
||||
print("""
|
||||
SIR 8 TDI (E0);
|
||||
SDR 32 TDI (00000000)
|
||||
TDO ({:08X})
|
||||
MASK (FFFFFFFF);
|
||||
""".format(idcode), file=svf)
|
||||
print("""
|
||||
print("""
|
||||
SIR 8 TDI (1C);
|
||||
SDR 510 TDI (3FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
|
||||
FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF);
|
||||
|
@ -106,30 +104,30 @@ SDR 8 TDI(60);
|
|||
SDR 16 TDI(0080);
|
||||
RUNTEST 1.00E-0 SEC;
|
||||
|
||||
""", file=svf)
|
||||
while True:
|
||||
if((address // 0x10000) != last_page):
|
||||
last_page = (address // 0x10000)
|
||||
print(f"// CMD 0x06 Write Enable + 0xd8 Erase 64K at 0x{address:x}", file=svf)
|
||||
""", file=svf)
|
||||
while True:
|
||||
if((address // 0x10000) != last_page):
|
||||
last_page = (address // 0x10000)
|
||||
print(f"// CMD 0x06 Write Enable + 0xd8 Erase 64K at 0x{address:x}", file=svf)
|
||||
print("SDR 8 TDI (60);", file=svf)
|
||||
address_flipped = [bitreverse(x) for x in [0xd8,int(address // 0x10000),0x00,0x00]]
|
||||
hex_address= ["{:02X}".format(x) for x in reversed(address_flipped)]
|
||||
print("\n".join(textwrap.wrap("SDR {} TDI ({});".format(8*len(hex_address), "".join(hex_address)), 100)), file=svf)
|
||||
print("RUNTEST 3.00 SEC;\n", file=svf)
|
||||
|
||||
chunk = bitf.read(flash_page_size)
|
||||
if not chunk:
|
||||
break
|
||||
# Convert chunk to bit-reversed hex
|
||||
print(f"// CMD 0x06 Write Enable + 0x02 Write Chunk to 0x{address:x}", file=svf)
|
||||
br_chunk = [bitreverse(x) for x in bytes([0x02, int(address / 0x10000 % 0x100),int(address / 0x100 % 0x100),int(address % 0x100)]) + chunk]
|
||||
address += len(chunk)
|
||||
hex_chunk = ["{:02X}".format(x) for x in reversed(br_chunk)]
|
||||
print("SDR 8 TDI (60);", file=svf)
|
||||
address_flipped = [bitreverse(x) for x in [0xd8,int(address // 0x10000),0x00,0x00]]
|
||||
hex_address= ["{:02X}".format(x) for x in reversed(address_flipped)]
|
||||
print("\n".join(textwrap.wrap("SDR {} TDI ({});".format(8*len(hex_address), "".join(hex_address)), 100)), file=svf)
|
||||
print("RUNTEST 3.00 SEC;\n", file=svf)
|
||||
print("\n".join(textwrap.wrap("SDR {} TDI ({});".format(8*len(br_chunk), "".join(hex_chunk)), 100)), file=svf)
|
||||
print("RUNTEST 2.50E-2 SEC;\n", file=svf)
|
||||
|
||||
chunk = bitf.read(flash_page_size)
|
||||
if not chunk:
|
||||
break
|
||||
# Convert chunk to bit-reversed hex
|
||||
print(f"// CMD 0x06 Write Enable + 0x02 Write Chunk to 0x{address:x}", file=svf)
|
||||
br_chunk = [bitreverse(x) for x in bytes([0x02, int(address / 0x10000 % 0x100),int(address / 0x100 % 0x100),int(address % 0x100)]) + chunk]
|
||||
address += len(chunk)
|
||||
hex_chunk = ["{:02X}".format(x) for x in reversed(br_chunk)]
|
||||
print("SDR 8 TDI (60);", file=svf)
|
||||
print("\n".join(textwrap.wrap("SDR {} TDI ({});".format(8*len(br_chunk), "".join(hex_chunk)), 100)), file=svf)
|
||||
print("RUNTEST 2.50E-2 SEC;\n", file=svf)
|
||||
|
||||
print("""
|
||||
print("""
|
||||
// BYPASS
|
||||
SIR 8 TDI (FF);
|
||||
|
||||
|
@ -141,4 +139,7 @@ STATE IDLE;
|
|||
RUNTEST 32 TCK;
|
||||
RUNTEST 2.00E-2 SEC;
|
||||
STATE RESET;
|
||||
""", file=svf)
|
||||
""", file=svf)
|
||||
|
||||
if __name__ == "__main__":
|
||||
convertBitToFlashFile(sys.argv[1], sys.argv[2])
|
Loading…
Reference in New Issue