From: Greg Davill Date: Sun, 19 Apr 2020 05:30:11 +0000 (+0930) Subject: shift out bytes instead of bits, when possible X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=31843cbeab1eeb8495ae51656c79e96fb4afff58;p=ecpprog.git shift out bytes instead of bits, when possible --- diff --git a/ecpprog/ecpprog.c b/ecpprog/ecpprog.c index e058a38..0d61c51 100644 --- a/ecpprog/ecpprog.c +++ b/ecpprog/ecpprog.c @@ -133,7 +133,6 @@ void xfer_spi(uint8_t* data, uint32_t len){ } void send_spi(uint8_t* data, uint32_t len){ - uint8_t unused[len]; /* Flip bit order of all bytes */ for(int i = 0; i < len; i++){ @@ -142,9 +141,15 @@ void send_spi(uint8_t* data, uint32_t len){ jtag_go_to_state(STATE_SHIFT_DR); /* Stay in SHIFT-DR state, this keep CS low */ - jtag_tap_shift(data, unused, len * 8, false); + jtag_tap_shift(data, data, len * 8, false); + + /* Flip bit order of all bytes */ + for(int i = 0; i < len; i++){ + data[i] = bit_reverse(data[i]); + } } + // --------------------------------------------------------- // FLASH function implementations // --------------------------------------------------------- @@ -315,6 +320,30 @@ static void flash_prog(int addr, uint8_t *data, int n) fprintf(stderr, "%02x%c", data[i], i == n - 1 || i % 32 == 31 ? '\n' : ' '); } + +static void flash_start_read(int addr) +{ + if (verbose) + fprintf(stderr, "Start Read 0x%06X\n", addr); + + uint8_t command[4] = { FC_RD, (uint8_t)(addr >> 16), (uint8_t)(addr >> 8), (uint8_t)addr }; + + send_spi(command, 4); +} + +static void flash_continue_read(uint8_t *data, int n) +{ + if (verbose) + fprintf(stderr, "Contiune Read +0x%03X..\n", n); + + memset(data, 0, n); + send_spi(data, n); + + if (verbose) + for (int i = 0; i < n; i++) + fprintf(stderr, "%02x%c", data[i], i == n - 1 || i % 32 == 31 ? '\n' : ' '); +} + static void flash_read(int addr, uint8_t *data, int n) { if (verbose) @@ -1039,10 +1068,12 @@ int main(int argc, char **argv) if (read_mode) { fprintf(stderr, "reading..\n"); - for (int addr = 0; addr < read_size; addr += 256) { - uint8_t buffer[256]; - flash_read(rw_offset + addr, buffer, 256); - fwrite(buffer, read_size - addr > 256 ? 256 : read_size - addr, 1, f); + + flash_start_read(rw_offset); + for (int addr = 0; addr < read_size; addr += 4096) { + uint8_t buffer[4096]; + flash_continue_read(buffer, 4096); + fwrite(buffer, read_size - addr > 4096 ? 4096 : read_size - addr, 1, f); } } else if (!erase_mode && !disable_verify) { fprintf(stderr, "reading..\n"); diff --git a/ecpprog/jtag_tap.c b/ecpprog/jtag_tap.c index 44781f5..cda86fd 100644 --- a/ecpprog/jtag_tap.c +++ b/ecpprog/jtag_tap.c @@ -6,6 +6,7 @@ */ #include +#include #include #include #include @@ -145,7 +146,7 @@ extern struct ftdi_context mpsse_ftdic; static inline void jtag_pulse_clock_and_read_tdo(bool tms, bool tdi) { - *ptr++ = MC_DATA_TMS | MC_DATA_IN | MC_DATA_LSB | MC_DATA_BITS; + *ptr++ = MC_DATA_TMS | MC_DATA_IN | MC_DATA_LSB | MC_DATA_BITS | MC_DATA_OCN; *ptr++ = 0; *ptr++ = (tdi ? 0x80 : 0) | (tms ? 0x01 : 0); rx_cnt++; @@ -185,6 +186,34 @@ static void _jtag_tap_shift( output_data[i] = data[7+i*8]; } + +static void jtag_shift_bytes( + uint8_t *input_data, + uint8_t *output_data, + uint32_t data_bits, + bool must_end) +{ + + /* Sanity check */ + if(data_bits % 8 != 0){ + printf("Error %u is not a byte multiple\n", data_bits); + } + //printf("jtag_shift_bytes(0x%08x,0x%08x,%u,%s);\n",input_data, output_data, data_bits, must_end ? "true" : "false"); + uint32_t byte_count = data_bits / 8; + + + + data[0] = MC_DATA_OUT | MC_DATA_IN | MC_DATA_LSB | MC_DATA_OCN; + data[1] = (byte_count - 1); + data[2] = (byte_count - 1) >> 8; + memcpy(data + 3, input_data, byte_count); + + mpsse_xfer(data, byte_count + 3, byte_count); + + memcpy(output_data, data, byte_count); +} + + #define MIN(a,b) (a < b) ? a : b void jtag_tap_shift( @@ -193,19 +222,35 @@ void jtag_tap_shift( uint32_t data_bits, bool must_end) { + /* if 'must_end' the send last byte seperately + * This way we toggle TMS on the last clock cycle */ + if(must_end) + data_bits -= 8; + uint32_t data_bits_sent = 0; - while(data_bits_sent != data_bits){ - - uint32_t _data_bits = MIN(256, data_bits); - bool last = (data_bits_sent + _data_bits) == data_bits; + if(data_bits){ + while(data_bits_sent != data_bits){ + + uint32_t _data_bits = MIN(4096 + 2048 + 1024, data_bits - data_bits_sent); + + jtag_shift_bytes( + input_data + data_bits_sent/8, + output_data + data_bits_sent/8, + _data_bits, + false + ); + data_bits_sent += _data_bits; + } + } + /* Send our last byte */ + if(must_end){ _jtag_tap_shift( input_data + data_bits_sent/8, output_data + data_bits_sent/8, - _data_bits, - last & must_end + 8, + must_end ); - data_bits_sent += _data_bits; } } diff --git a/ecpprog/mpsse.c b/ecpprog/mpsse.c index 5833c65..c2e6d87 100644 --- a/ecpprog/mpsse.c +++ b/ecpprog/mpsse.c @@ -221,15 +221,17 @@ void mpsse_init(int ifnum, const char *devstr, bool slow_clock) mpsse_error(2); } + mpsse_send_byte(MC_TCK_X5); + if (slow_clock) { // set 50 kHz clock mpsse_send_byte(MC_SET_CLK_DIV); - mpsse_send_byte(119); + mpsse_send_byte(29); mpsse_send_byte(0x00); } else { // set 6 MHz clock mpsse_send_byte(MC_SET_CLK_DIV); - mpsse_send_byte(4); + mpsse_send_byte(1); mpsse_send_byte(0x00); }