diff --git a/src/gowin.cpp b/src/gowin.cpp index de87e1b..b677579 100644 --- a/src/gowin.cpp +++ b/src/gowin.cpp @@ -194,8 +194,6 @@ void Gowin::reset() void Gowin::programFlash() { - int status; - uint8_t *data = _fs->getData(); int length = _fs->getLength(); @@ -240,16 +238,7 @@ void Gowin::programFlash() usleep(2*150*1000); /* check if file checksum == checksum in FPGA */ - if (!skip_checksum) { - status = readUserCode(); - int checksum = static_cast(_fs)->checksum(); - if (checksum != status) { - printError("CRC check : FAIL"); - printf("%04x %04x\n", checksum, status); - } else { - printSuccess("CRC check: Success"); - } - } + checkCRC(); if (_verbose) displayReadReg(readStatusReg()); @@ -258,7 +247,6 @@ void Gowin::programFlash() void Gowin::program(unsigned int offset, bool unprotect_flash) { uint8_t *data; - uint32_t status; int length; if (_mode == NONE_MODE || !_fs) @@ -329,21 +317,57 @@ void Gowin::program(unsigned int offset, bool unprotect_flash) if (!DisableCfg()) return; - /* check if file checksum == checksum in FPGA */ - if (!skip_checksum) { - status = readUserCode(); - uint32_t checksum = static_cast(_fs)->checksum(); - if (checksum != status) { - printError("SRAM Flash: FAIL"); - printf("%04x %04x\n", checksum, status); - } else { - printSuccess("SRAM Flash: Success"); - } - } + /* ocheck if file checksum == checksum in FPGA */ + checkCRC(); if (_verbose) displayReadReg(readStatusReg()); } +void Gowin::checkCRC() +{ + if (!skip_checksum) + return; + + bool is_match = true; + char mess[256]; + uint32_t status = readUserCode(); + uint16_t checksum = static_cast(_fs)->checksum(); + string hdr = ""; + try { + hdr = _fs->getHeaderVal("checkSum"); + } catch (std::exception &e) { + if (_verbose) + printError(e.what()); + } + if (static_cast(0xffff & status) != checksum) { + /* no match: + * user code register contains checksum or + * user_code when: + * set_option -user_code + * is used: try to compare with this value + */ + if (hdr.empty()) { + is_match = false; + snprintf(mess, 256, "Read: 0x%08x checksum: 0x%04x\n", + status, checksum); + } else { + uint32_t user_code = strtol(hdr.c_str(), NULL, 16); + if (status != user_code) { + is_match = false; + snprintf(mess, 256, + "Read 0x%08x (checksum: 0x%08x, user_code: 0x%08x)\n", + status, checksum, user_code); + } + } + } + if (is_match) { + printSuccess("CRC check: Success"); + } else { + printError("CRC check : FAIL"); + printError(mess); + } +} + bool Gowin::EnableCfg() { wr_rd(CONFIG_ENABLE, NULL, 0, NULL, 0); diff --git a/src/gowin.hpp b/src/gowin.hpp index 9c72664..07b35ec 100644 --- a/src/gowin.hpp +++ b/src/gowin.hpp @@ -55,10 +55,15 @@ class Gowin: public Device, SPIInterface { void displayReadReg(uint32_t dev); uint32_t readStatusReg(); uint32_t readUserCode(); + /*! + * \brief compare usercode register with fs checksum and/or + * .fs usercode field + */ + void checkCRC(); ConfigBitstreamParser *_fs; bool is_gw1n1; bool is_gw2a; - bool skip_checksum; + bool skip_checksum; /**< bypass checksum verification (GW2A) */ bool _external_flash; /**< select between int or ext flash */ uint8_t _spi_sck; /**< clk signal offset in bscan SPI */ uint8_t _spi_cs; /**< cs signal offset in bscan SPI */