aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/jtag/drivers/ftdi.c123
-rw-r--r--src/jtag/drivers/mpsse.c136
-rw-r--r--src/jtag/drivers/mpsse.h22
3 files changed, 128 insertions, 153 deletions
diff --git a/src/jtag/drivers/ftdi.c b/src/jtag/drivers/ftdi.c
index 11a7414f..4566ed3c 100644
--- a/src/jtag/drivers/ftdi.c
+++ b/src/jtag/drivers/ftdi.c
@@ -140,7 +140,6 @@ static struct signal *create_signal(const char *name)
static int ftdi_set_signal(const struct signal *s, char value)
{
- int retval;
bool data;
bool oe;
@@ -181,13 +180,8 @@ static int ftdi_set_signal(const struct signal *s, char value)
else
output = oe ? output | s->oe_mask : output & ~s->oe_mask;
- retval = mpsse_set_data_bits_low_byte(mpsse_ctx, output & 0xff, direction & 0xff);
- if (retval == ERROR_OK)
- retval = mpsse_set_data_bits_high_byte(mpsse_ctx, output >> 8, direction >> 8);
- if (retval != ERROR_OK) {
- LOG_ERROR("couldn't initialize FTDI GPIO");
- return ERROR_JTAG_INIT_FAILED;
- }
+ mpsse_set_data_bits_low_byte(mpsse_ctx, output & 0xff, direction & 0xff);
+ mpsse_set_data_bits_high_byte(mpsse_ctx, output >> 8, direction >> 8);
return ERROR_OK;
}
@@ -201,7 +195,7 @@ static int ftdi_set_signal(const struct signal *s, char value)
*
* @param goal_state is the destination state for the move.
*/
-static int move_to_state(tap_state_t goal_state)
+static void move_to_state(tap_state_t goal_state)
{
tap_state_t start_state = tap_get_state();
@@ -220,7 +214,7 @@ static int move_to_state(tap_state_t goal_state)
for (int i = 0; i < tms_count; i++)
tap_set_state(tap_state_transition(tap_get_state(), (tms_bits >> i) & 1));
- return mpsse_clock_tms_cs_out(mpsse_ctx,
+ mpsse_clock_tms_cs_out(mpsse_ctx,
(uint8_t *)&tms_bits,
0,
tms_count,
@@ -268,9 +262,8 @@ static void ftdi_end_state(tap_state_t state)
}
}
-static int ftdi_execute_runtest(struct jtag_command *cmd)
+static void ftdi_execute_runtest(struct jtag_command *cmd)
{
- int retval = ERROR_OK;
int i;
uint8_t zero = 0;
@@ -283,10 +276,10 @@ static int ftdi_execute_runtest(struct jtag_command *cmd)
/* TODO: Reuse ftdi_execute_stableclocks */
i = cmd->cmd.runtest->num_cycles;
- while (i > 0 && retval == ERROR_OK) {
+ while (i > 0) {
/* there are no state transitions in this code, so omit state tracking */
unsigned this_len = i > 7 ? 7 : i;
- retval = mpsse_clock_tms_cs_out(mpsse_ctx, &zero, 0, this_len, false, JTAG_MODE);
+ mpsse_clock_tms_cs_out(mpsse_ctx, &zero, 0, this_len, false, JTAG_MODE);
i -= this_len;
}
@@ -298,13 +291,10 @@ static int ftdi_execute_runtest(struct jtag_command *cmd)
DEBUG_JTAG_IO("runtest: %i, end in %s",
cmd->cmd.runtest->num_cycles,
tap_state_name(tap_get_end_state()));
- return retval;
}
-static int ftdi_execute_statemove(struct jtag_command *cmd)
+static void ftdi_execute_statemove(struct jtag_command *cmd)
{
- int retval = ERROR_OK;
-
DEBUG_JTAG_IO("statemove end in %s",
tap_state_name(cmd->cmd.statemove->end_state));
@@ -313,20 +303,18 @@ static int ftdi_execute_statemove(struct jtag_command *cmd)
/* shortest-path move to desired end state */
if (tap_get_state() != tap_get_end_state() || tap_get_end_state() == TAP_RESET)
move_to_state(tap_get_end_state());
-
- return retval;
}
/**
* Clock a bunch of TMS (or SWDIO) transitions, to change the JTAG
* (or SWD) state machine. REVISIT: Not the best method, perhaps.
*/
-static int ftdi_execute_tms(struct jtag_command *cmd)
+static void ftdi_execute_tms(struct jtag_command *cmd)
{
DEBUG_JTAG_IO("TMS: %d bits", cmd->cmd.tms->num_bits);
/* TODO: Missing tap state tracking, also missing from ft2232.c! */
- return mpsse_clock_tms_cs_out(mpsse_ctx,
+ mpsse_clock_tms_cs_out(mpsse_ctx,
cmd->cmd.tms->bits,
0,
cmd->cmd.tms->num_bits,
@@ -334,10 +322,8 @@ static int ftdi_execute_tms(struct jtag_command *cmd)
JTAG_MODE);
}
-static int ftdi_execute_pathmove(struct jtag_command *cmd)
+static void ftdi_execute_pathmove(struct jtag_command *cmd)
{
- int retval = ERROR_OK;
-
tap_state_t *path = cmd->cmd.pathmove->path;
int num_states = cmd->cmd.pathmove->num_states;
@@ -352,7 +338,7 @@ static int ftdi_execute_pathmove(struct jtag_command *cmd)
DEBUG_JTAG_IO("-");
/* this loop verifies that the path is legal and logs each state in the path */
- while (num_states-- && retval == ERROR_OK) {
+ while (num_states--) {
/* either TMS=0 or TMS=1 must work ... */
if (tap_state_transition(tap_get_state(), false)
@@ -375,7 +361,7 @@ static int ftdi_execute_pathmove(struct jtag_command *cmd)
state_count++;
if (bit_count == 7 || num_states == 0) {
- retval = mpsse_clock_tms_cs_out(mpsse_ctx,
+ mpsse_clock_tms_cs_out(mpsse_ctx,
&tms_byte,
0,
bit_count,
@@ -385,14 +371,10 @@ static int ftdi_execute_pathmove(struct jtag_command *cmd)
}
}
tap_set_end_state(tap_get_state());
-
- return retval;
}
-static int ftdi_execute_scan(struct jtag_command *cmd)
+static void ftdi_execute_scan(struct jtag_command *cmd)
{
- int retval = ERROR_OK;
-
DEBUG_JTAG_IO("%s type:%d", cmd->cmd.scan->ir_scan ? "IRSCAN" : "DRSCAN",
jtag_scan_type(cmd->cmd.scan));
@@ -405,7 +387,7 @@ static int ftdi_execute_scan(struct jtag_command *cmd)
if (cmd->cmd.scan->num_fields == 0) {
LOG_DEBUG("empty scan, doing nothing");
- return retval;
+ return;
}
if (cmd->cmd.scan->ir_scan) {
@@ -444,7 +426,7 @@ static int ftdi_execute_scan(struct jtag_command *cmd)
if (field->out_value)
bit_copy(&last_bit, 0, field->out_value, field->num_bits - 1, 1);
uint8_t tms_bits = 0x01;
- retval = mpsse_clock_tms_cs(mpsse_ctx,
+ mpsse_clock_tms_cs(mpsse_ctx,
&tms_bits,
0,
field->in_value,
@@ -453,7 +435,7 @@ static int ftdi_execute_scan(struct jtag_command *cmd)
last_bit,
JTAG_MODE);
tap_set_state(tap_state_transition(tap_get_state(), 1));
- retval = mpsse_clock_tms_cs_out(mpsse_ctx,
+ mpsse_clock_tms_cs_out(mpsse_ctx,
&tms_bits,
1,
1,
@@ -468,10 +450,6 @@ static int ftdi_execute_scan(struct jtag_command *cmd)
0,
field->num_bits,
JTAG_MODE);
- if (retval != ERROR_OK) {
- LOG_ERROR("failed to add field %d in scan", i);
- return retval;
- }
}
if (tap_get_state() != tap_get_end_state())
@@ -480,11 +458,9 @@ static int ftdi_execute_scan(struct jtag_command *cmd)
DEBUG_JTAG_IO("%s scan, %i bits, end in %s",
(cmd->cmd.scan->ir_scan) ? "IR" : "DR", scan_size,
tap_state_name(tap_get_end_state()));
- return retval;
-
}
-static int ftdi_execute_reset(struct jtag_command *cmd)
+static void ftdi_execute_reset(struct jtag_command *cmd)
{
DEBUG_JTAG_IO("reset trst: %i srst %i",
cmd->cmd.reset->trst, cmd->cmd.reset->srst);
@@ -516,27 +492,21 @@ static int ftdi_execute_reset(struct jtag_command *cmd)
DEBUG_JTAG_IO("trst: %i, srst: %i",
cmd->cmd.reset->trst, cmd->cmd.reset->srst);
- return ERROR_OK;
}
-static int ftdi_execute_sleep(struct jtag_command *cmd)
+static void ftdi_execute_sleep(struct jtag_command *cmd)
{
- int retval = ERROR_OK;
-
DEBUG_JTAG_IO("sleep %" PRIi32, cmd->cmd.sleep->us);
- retval = mpsse_flush(mpsse_ctx);
+ mpsse_flush(mpsse_ctx);
jtag_sleep(cmd->cmd.sleep->us);
DEBUG_JTAG_IO("sleep %" PRIi32 " usec while in %s",
cmd->cmd.sleep->us,
tap_state_name(tap_get_state()));
- return retval;
}
-static int ftdi_execute_stableclocks(struct jtag_command *cmd)
+static void ftdi_execute_stableclocks(struct jtag_command *cmd)
{
- int retval = ERROR_OK;
-
/* this is only allowed while in a stable state. A check for a stable
* state was done in jtag_add_clocks()
*/
@@ -547,60 +517,53 @@ static int ftdi_execute_stableclocks(struct jtag_command *cmd)
/* TODO: Use mpsse_clock_data with in=out=0 for this, if TMS can be set to
* the correct level and remain there during the scan */
- while (num_cycles > 0 && retval == ERROR_OK) {
+ while (num_cycles > 0) {
/* there are no state transitions in this code, so omit state tracking */
unsigned this_len = num_cycles > 7 ? 7 : num_cycles;
- retval = mpsse_clock_tms_cs_out(mpsse_ctx, &tms, 0, this_len, false, JTAG_MODE);
+ mpsse_clock_tms_cs_out(mpsse_ctx, &tms, 0, this_len, false, JTAG_MODE);
num_cycles -= this_len;
}
DEBUG_JTAG_IO("clocks %i while in %s",
cmd->cmd.stableclocks->num_cycles,
tap_state_name(tap_get_state()));
- return retval;
}
-static int ftdi_execute_command(struct jtag_command *cmd)
+static void ftdi_execute_command(struct jtag_command *cmd)
{
- int retval;
-
switch (cmd->type) {
case JTAG_RESET:
- retval = ftdi_execute_reset(cmd);
+ ftdi_execute_reset(cmd);
break;
case JTAG_RUNTEST:
- retval = ftdi_execute_runtest(cmd);
+ ftdi_execute_runtest(cmd);
break;
case JTAG_TLR_RESET:
- retval = ftdi_execute_statemove(cmd);
+ ftdi_execute_statemove(cmd);
break;
case JTAG_PATHMOVE:
- retval = ftdi_execute_pathmove(cmd);
+ ftdi_execute_pathmove(cmd);
break;
case JTAG_SCAN:
- retval = ftdi_execute_scan(cmd);
+ ftdi_execute_scan(cmd);
break;
case JTAG_SLEEP:
- retval = ftdi_execute_sleep(cmd);
+ ftdi_execute_sleep(cmd);
break;
case JTAG_STABLECLOCKS:
- retval = ftdi_execute_stableclocks(cmd);
+ ftdi_execute_stableclocks(cmd);
break;
case JTAG_TMS:
- retval = ftdi_execute_tms(cmd);
+ ftdi_execute_tms(cmd);
break;
default:
LOG_ERROR("BUG: unknown JTAG command type encountered: %d", cmd->type);
- retval = ERROR_JTAG_QUEUE_FAILED;
break;
}
- return retval;
}
static int ftdi_execute_queue(void)
{
- int retval = ERROR_OK;
-
/* blink, if the current layout has that feature */
struct signal *led = find_signal_by_name("LED");
if (led)
@@ -608,14 +571,13 @@ static int ftdi_execute_queue(void)
for (struct jtag_command *cmd = jtag_command_queue; cmd; cmd = cmd->next) {
/* fill the write buffer with the desired command */
- if (ftdi_execute_command(cmd) != ERROR_OK)
- retval = ERROR_JTAG_QUEUE_FAILED;
+ ftdi_execute_command(cmd);
}
if (led)
ftdi_set_signal(led, '0');
- retval = mpsse_flush(mpsse_ctx);
+ int retval = mpsse_flush(mpsse_ctx);
if (retval != ERROR_OK)
LOG_ERROR("error while flushing MPSSE queue: %d", retval);
@@ -624,8 +586,6 @@ static int ftdi_execute_queue(void)
static int ftdi_initialize(void)
{
- int retval;
-
if (tap_get_tms_path_len(TAP_IRPAUSE, TAP_IRPAUSE) == 7)
LOG_DEBUG("ftdi interface using 7 step jtag state transitions");
else
@@ -641,19 +601,10 @@ static int ftdi_initialize(void)
if (!mpsse_ctx)
return ERROR_JTAG_INIT_FAILED;
- retval = mpsse_set_data_bits_low_byte(mpsse_ctx, output & 0xff, direction & 0xff);
- if (retval == ERROR_OK)
- retval = mpsse_set_data_bits_high_byte(mpsse_ctx, output >> 8, direction >> 8);
- if (retval != ERROR_OK) {
- LOG_ERROR("couldn't initialize FTDI with configured layout");
- return ERROR_JTAG_INIT_FAILED;
- }
+ mpsse_set_data_bits_low_byte(mpsse_ctx, output & 0xff, direction & 0xff);
+ mpsse_set_data_bits_high_byte(mpsse_ctx, output >> 8, direction >> 8);
- retval = mpsse_loopback_config(mpsse_ctx, false);
- if (retval != ERROR_OK) {
- LOG_ERROR("couldn't write to FTDI to disable loopback");
- return ERROR_JTAG_INIT_FAILED;
- }
+ mpsse_loopback_config(mpsse_ctx, false);
return mpsse_flush(mpsse_ctx);
}
diff --git a/src/jtag/drivers/mpsse.c b/src/jtag/drivers/mpsse.c
index 82703bf3..59927a0f 100644
--- a/src/jtag/drivers/mpsse.c
+++ b/src/jtag/drivers/mpsse.c
@@ -86,6 +86,7 @@ struct mpsse_ctx {
uint8_t *read_chunk;
unsigned read_chunk_size;
struct bit_copy_queue read_queue;
+ int retval;
};
/* Returns true if the string descriptor indexed by str_index in device matches string */
@@ -362,6 +363,7 @@ void mpsse_purge(struct mpsse_ctx *ctx)
LOG_DEBUG("-");
ctx->write_count = 0;
ctx->read_count = 0;
+ ctx->retval = ERROR_OK;
bit_copy_discard(&ctx->read_queue);
err = libusb_control_transfer(ctx->usb_dev, FTDI_DEVICE_OUT_REQTYPE, SIO_RESET_REQUEST,
SIO_RESET_PURGE_RX, ctx->index, NULL, 0, ctx->usb_write_timeout);
@@ -417,24 +419,28 @@ static unsigned buffer_add_read(struct mpsse_ctx *ctx, uint8_t *in, unsigned in_
return bit_count;
}
-int mpsse_clock_data_out(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset,
+void mpsse_clock_data_out(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset,
unsigned length, uint8_t mode)
{
- return mpsse_clock_data(ctx, out, out_offset, 0, 0, length, mode);
+ mpsse_clock_data(ctx, out, out_offset, 0, 0, length, mode);
}
-int mpsse_clock_data_in(struct mpsse_ctx *ctx, uint8_t *in, unsigned in_offset, unsigned length,
+void mpsse_clock_data_in(struct mpsse_ctx *ctx, uint8_t *in, unsigned in_offset, unsigned length,
uint8_t mode)
{
- return mpsse_clock_data(ctx, 0, 0, in, in_offset, length, mode);
+ mpsse_clock_data(ctx, 0, 0, in, in_offset, length, mode);
}
-int mpsse_clock_data(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset, uint8_t *in,
+void mpsse_clock_data(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset, uint8_t *in,
unsigned in_offset, unsigned length, uint8_t mode)
{
/* TODO: Fix MSB first modes */
DEBUG_IO("%s%s %d bits", in ? "in" : "", out ? "out" : "", length);
- int retval = ERROR_OK;
+
+ if (ctx->retval != ERROR_OK) {
+ DEBUG_IO("Ignoring command due to previous error");
+ return;
+ }
/* TODO: On H chips, use command 0x8E/0x8F if in and out are both 0 */
if (out || (!out && !in))
@@ -446,7 +452,7 @@ int mpsse_clock_data(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_off
/* Guarantee buffer space enough for a minimum size transfer */
if (buffer_write_space(ctx) + (length < 8) < (out || (!out && !in) ? 4 : 3)
|| (in && buffer_read_space(ctx) < 1))
- retval = mpsse_flush(ctx);
+ ctx->retval = mpsse_flush(ctx);
if (length < 8) {
/* Transfer remaining bits in bit mode */
@@ -494,21 +500,24 @@ int mpsse_clock_data(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_off
}
}
}
- return retval;
}
-int mpsse_clock_tms_cs_out(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset,
+void mpsse_clock_tms_cs_out(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset,
unsigned length, bool tdi, uint8_t mode)
{
- return mpsse_clock_tms_cs(ctx, out, out_offset, 0, 0, length, tdi, mode);
+ mpsse_clock_tms_cs(ctx, out, out_offset, 0, 0, length, tdi, mode);
}
-int mpsse_clock_tms_cs(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset, uint8_t *in,
+void mpsse_clock_tms_cs(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset, uint8_t *in,
unsigned in_offset, unsigned length, bool tdi, uint8_t mode)
{
DEBUG_IO("%sout %d bits, tdi=%d", in ? "in" : "", length, tdi);
assert(out);
- int retval = ERROR_OK;
+
+ if (ctx->retval != ERROR_OK) {
+ DEBUG_IO("Ignoring command due to previous error");
+ return;
+ }
mode |= 0x42;
if (in)
@@ -517,7 +526,7 @@ int mpsse_clock_tms_cs(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_o
while (length > 0) {
/* Guarantee buffer space enough for a minimum size transfer */
if (buffer_write_space(ctx) < 3 || (in && buffer_read_space(ctx) < 1))
- retval = mpsse_flush(ctx);
+ ctx->retval = mpsse_flush(ctx);
/* Byte transfer */
unsigned this_bits = length;
@@ -548,99 +557,109 @@ int mpsse_clock_tms_cs(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_o
length -= this_bits;
}
}
- return retval;
}
-int mpsse_set_data_bits_low_byte(struct mpsse_ctx *ctx, uint8_t data, uint8_t dir)
+void mpsse_set_data_bits_low_byte(struct mpsse_ctx *ctx, uint8_t data, uint8_t dir)
{
DEBUG_IO("-");
- int retval = ERROR_OK;
+
+ if (ctx->retval != ERROR_OK) {
+ DEBUG_IO("Ignoring command due to previous error");
+ return;
+ }
if (buffer_write_space(ctx) < 3)
- retval = mpsse_flush(ctx);
+ ctx->retval = mpsse_flush(ctx);
buffer_write_byte(ctx, 0x80);
buffer_write_byte(ctx, data);
buffer_write_byte(ctx, dir);
-
- return retval;
}
-int mpsse_set_data_bits_high_byte(struct mpsse_ctx *ctx, uint8_t data, uint8_t dir)
+void mpsse_set_data_bits_high_byte(struct mpsse_ctx *ctx, uint8_t data, uint8_t dir)
{
DEBUG_IO("-");
- int retval = ERROR_OK;
+
+ if (ctx->retval != ERROR_OK) {
+ DEBUG_IO("Ignoring command due to previous error");
+ return;
+ }
if (buffer_write_space(ctx) < 3)
- retval = mpsse_flush(ctx);
+ ctx->retval = mpsse_flush(ctx);
buffer_write_byte(ctx, 0x82);
buffer_write_byte(ctx, data);
buffer_write_byte(ctx, dir);
-
- return retval;
}
-int mpsse_read_data_bits_low_byte(struct mpsse_ctx *ctx, uint8_t *data)
+void mpsse_read_data_bits_low_byte(struct mpsse_ctx *ctx, uint8_t *data)
{
DEBUG_IO("-");
- int retval = ERROR_OK;
+
+ if (ctx->retval != ERROR_OK) {
+ DEBUG_IO("Ignoring command due to previous error");
+ return;
+ }
if (buffer_write_space(ctx) < 1)
- retval = mpsse_flush(ctx);
+ ctx->retval = mpsse_flush(ctx);
buffer_write_byte(ctx, 0x81);
buffer_add_read(ctx, data, 0, 8, 0);
-
- return retval;
}
-int mpsse_read_data_bits_high_byte(struct mpsse_ctx *ctx, uint8_t *data)
+void mpsse_read_data_bits_high_byte(struct mpsse_ctx *ctx, uint8_t *data)
{
DEBUG_IO("-");
- int retval = ERROR_OK;
+
+ if (ctx->retval != ERROR_OK) {
+ DEBUG_IO("Ignoring command due to previous error");
+ return;
+ }
if (buffer_write_space(ctx) < 1)
- retval = mpsse_flush(ctx);
+ ctx->retval = mpsse_flush(ctx);
buffer_write_byte(ctx, 0x83);
buffer_add_read(ctx, data, 0, 8, 0);
-
- return retval;
}
-static int single_byte_boolean_helper(struct mpsse_ctx *ctx, bool var, uint8_t val_if_true,
+static void single_byte_boolean_helper(struct mpsse_ctx *ctx, bool var, uint8_t val_if_true,
uint8_t val_if_false)
{
- int retval = ERROR_OK;
+ if (ctx->retval != ERROR_OK) {
+ DEBUG_IO("Ignoring command due to previous error");
+ return;
+ }
if (buffer_write_space(ctx) < 1)
- retval = mpsse_flush(ctx);
+ ctx->retval = mpsse_flush(ctx);
buffer_write_byte(ctx, var ? val_if_true : val_if_false);
-
- return retval;
}
-int mpsse_loopback_config(struct mpsse_ctx *ctx, bool enable)
+void mpsse_loopback_config(struct mpsse_ctx *ctx, bool enable)
{
LOG_DEBUG("%s", enable ? "on" : "off");
- return single_byte_boolean_helper(ctx, enable, 0x84, 0x85);
+ single_byte_boolean_helper(ctx, enable, 0x84, 0x85);
}
-int mpsse_set_divisor(struct mpsse_ctx *ctx, uint16_t divisor)
+void mpsse_set_divisor(struct mpsse_ctx *ctx, uint16_t divisor)
{
LOG_DEBUG("%d", divisor);
- int retval = ERROR_OK;
+
+ if (ctx->retval != ERROR_OK) {
+ DEBUG_IO("Ignoring command due to previous error");
+ return;
+ }
if (buffer_write_space(ctx) < 3)
- retval = mpsse_flush(ctx);
+ ctx->retval = mpsse_flush(ctx);
buffer_write_byte(ctx, 0x86);
buffer_write_byte(ctx, divisor & 0xff);
buffer_write_byte(ctx, divisor >> 8);
-
- return retval;
}
int mpsse_divide_by_5_config(struct mpsse_ctx *ctx, bool enable)
@@ -649,8 +668,9 @@ int mpsse_divide_by_5_config(struct mpsse_ctx *ctx, bool enable)
return ERROR_FAIL;
LOG_DEBUG("%s", enable ? "on" : "off");
+ single_byte_boolean_helper(ctx, enable, 0x8b, 0x8a);
- return single_byte_boolean_helper(ctx, enable, 0x8b, 0x8a);
+ return ERROR_OK;
}
int mpsse_rtck_config(struct mpsse_ctx *ctx, bool enable)
@@ -659,8 +679,9 @@ int mpsse_rtck_config(struct mpsse_ctx *ctx, bool enable)
return ERROR_FAIL;
LOG_DEBUG("%s", enable ? "on" : "off");
+ single_byte_boolean_helper(ctx, enable, 0x96, 0x97);
- return single_byte_boolean_helper(ctx, enable, 0x96, 0x97);
+ return ERROR_OK;
}
int mpsse_set_frequency(struct mpsse_ctx *ctx, int frequency)
@@ -674,10 +695,7 @@ int mpsse_set_frequency(struct mpsse_ctx *ctx, int frequency)
mpsse_rtck_config(ctx, false); /* just try */
- if (frequency > 60000000 / 2 / 65536 && mpsse_is_high_speed(ctx)) {
- int retval = mpsse_divide_by_5_config(ctx, false);
- if (retval != ERROR_OK)
- return retval;
+ if (frequency > 60000000 / 2 / 65536 && mpsse_divide_by_5_config(ctx, false) == ERROR_OK) {
base_clock = 60000000;
} else {
mpsse_divide_by_5_config(ctx, true); /* just try */
@@ -689,9 +707,7 @@ int mpsse_set_frequency(struct mpsse_ctx *ctx, int frequency)
divisor = 65535;
assert(divisor >= 0);
- int retval = mpsse_set_divisor(ctx, divisor);
- if (retval != ERROR_OK)
- return retval;
+ mpsse_set_divisor(ctx, divisor);
frequency = base_clock / 2 / (1 + divisor);
LOG_DEBUG("actually %d Hz", frequency);
@@ -767,10 +783,18 @@ static LIBUSB_CALL void write_cb(struct libusb_transfer *transfer)
int mpsse_flush(struct mpsse_ctx *ctx)
{
+ int retval = ctx->retval;
+
+ if (retval != ERROR_OK) {
+ DEBUG_IO("Ignoring flush due to previous error");
+ assert(ctx->write_count == 0 && ctx->read_count == 0);
+ ctx->retval = ERROR_OK;
+ return retval;
+ }
+
DEBUG_IO("write %d%s, read %d", ctx->write_count, ctx->read_count ? "+1" : "",
ctx->read_count);
assert(ctx->write_count > 0 || ctx->read_count == 0); /* No read data without write data */
- int retval = ERROR_OK;
if (ctx->write_count == 0)
return retval;
diff --git a/src/jtag/drivers/mpsse.h b/src/jtag/drivers/mpsse.h
index 625d118f..3e287f75 100644
--- a/src/jtag/drivers/mpsse.h
+++ b/src/jtag/drivers/mpsse.h
@@ -50,22 +50,22 @@ bool mpsse_is_high_speed(struct mpsse_ctx *ctx);
/* Command queuing. These correspond to the MPSSE commands with the same names, but no need to care
* about bit/byte transfer or data length limitation. Read data is guaranteed to be available only
* after the following mpsse_flush(). */
-int mpsse_clock_data_out(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset,
+void mpsse_clock_data_out(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset,
unsigned length, uint8_t mode);
-int mpsse_clock_data_in(struct mpsse_ctx *ctx, uint8_t *in, unsigned in_offset, unsigned length,
+void mpsse_clock_data_in(struct mpsse_ctx *ctx, uint8_t *in, unsigned in_offset, unsigned length,
uint8_t mode);
-int mpsse_clock_data(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset, uint8_t *in,
+void mpsse_clock_data(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset, uint8_t *in,
unsigned in_offset, unsigned length, uint8_t mode);
-int mpsse_clock_tms_cs_out(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset,
+void mpsse_clock_tms_cs_out(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset,
unsigned length, bool tdi, uint8_t mode);
-int mpsse_clock_tms_cs(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset, uint8_t *in,
+void mpsse_clock_tms_cs(struct mpsse_ctx *ctx, const uint8_t *out, unsigned out_offset, uint8_t *in,
unsigned in_offset, unsigned length, bool tdi, uint8_t mode);
-int mpsse_set_data_bits_low_byte(struct mpsse_ctx *ctx, uint8_t data, uint8_t dir);
-int mpsse_set_data_bits_high_byte(struct mpsse_ctx *ctx, uint8_t data, uint8_t dir);
-int mpsse_read_data_bits_low_byte(struct mpsse_ctx *ctx, uint8_t *data);
-int mpsse_read_data_bits_high_byte(struct mpsse_ctx *ctx, uint8_t *data);
-int mpsse_loopback_config(struct mpsse_ctx *ctx, bool enable);
-int mpsse_set_divisor(struct mpsse_ctx *ctx, uint16_t divisor);
+void mpsse_set_data_bits_low_byte(struct mpsse_ctx *ctx, uint8_t data, uint8_t dir);
+void mpsse_set_data_bits_high_byte(struct mpsse_ctx *ctx, uint8_t data, uint8_t dir);
+void mpsse_read_data_bits_low_byte(struct mpsse_ctx *ctx, uint8_t *data);
+void mpsse_read_data_bits_high_byte(struct mpsse_ctx *ctx, uint8_t *data);
+void mpsse_loopback_config(struct mpsse_ctx *ctx, bool enable);
+void mpsse_set_divisor(struct mpsse_ctx *ctx, uint16_t divisor);
int mpsse_divide_by_5_config(struct mpsse_ctx *ctx, bool enable);
int mpsse_rtck_config(struct mpsse_ctx *ctx, bool enable);