uartFlasher.py 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104
  1. #!/usr/bin/env python3
  2. import serial
  3. from time import sleep
  4. import sys
  5. import fileinput
  6. import threading
  7. stop_threads = False
  8. def writeThread(port):
  9. global stop_threads
  10. try:
  11. for line in fileinput.input():
  12. if stop_threads:
  13. exit()
  14. for c in line:
  15. port.write(c.encode('utf-8'))
  16. sleep(0.001) # give the FPGC time to process the UART in software
  17. except:
  18. exit()
  19. testReturnMode = False # mode where we do not use a serial monitor,
  20. # but instead wait for one byte and use it as return code of this program
  21. if len(sys.argv) > 1:
  22. if (sys.argv[1] == "testMode"):
  23. testReturnMode = True
  24. port = serial.Serial("/dev/ttyUSB0", baudrate=1000000, timeout=None)
  25. sleep(0.3) # give the FPGC time to reset, even though it also works without this delay
  26. # parse byte file
  27. ba = bytearray()
  28. with open("code.bin", "rb") as f:
  29. bytes_read = f.read()
  30. for b in bytes_read:
  31. ba.append(b)
  32. # combine each 4 bytes into a word
  33. n = 4
  34. wordList = [ba[i * n:(i + 1) * n] for i in range((len(ba) + n - 1) // n )]
  35. # size of program is in address 2
  36. fileSize = bytes(wordList[2])
  37. print(int.from_bytes(fileSize, "big"), flush=True)
  38. # write filesize
  39. port.write(fileSize)
  40. # read four bytes
  41. rcv = port.read(4)
  42. # to verify if communication works
  43. print(rcv, flush=True)
  44. # send all words
  45. doneSending = False
  46. wordCounter = 0
  47. while not doneSending:
  48. port.write(bytes(wordList[wordCounter]))
  49. wordCounter = wordCounter + 1
  50. if (wordCounter == int.from_bytes(fileSize, "big")):
  51. doneSending = True
  52. print("Done programming", flush=True)
  53. port.read(1) # should return 'd', though I'm not checking on it
  54. if testReturnMode:
  55. rcv = port.read(1)
  56. retval = int.from_bytes(rcv, "little")
  57. print("FPGC returned: ", retval)
  58. sys.exit(retval)
  59. else:
  60. print("\nSerial monitor:", flush=True)
  61. t1 = threading.Thread(target = writeThread, args=[port])
  62. t1.daemon = True
  63. t1.start()
  64. try:
  65. while True:
  66. bytesToRead = port.in_waiting
  67. if(bytesToRead > 0):
  68. rcv = port.read(1)
  69. try:
  70. print(rcv.decode("utf-8"), end = '', flush=True)
  71. except:
  72. print(rcv, end = '', flush=True)
  73. else:
  74. sleep(.01) # allow CPU to idle
  75. except KeyboardInterrupt:
  76. print("\nClosing Serial Monitor")
  77. stop_threads = True
  78. # t1.join()