remote/jtagtap_tdi_tdo_seq: Split up large transactions.
FIXME: One remote transaction still can only do up to 64 ticks, leaving room for speed enhancement with larger transactions. Firmware assumes (1LL << 65) == 0LL !
This commit is contained in:
parent
8084a75634
commit
e1a1865de9
|
@ -104,35 +104,53 @@ static void jtagtap_tms_seq(uint32_t MS, int ticks)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* At least up to v1.7.1-233, remote handles only up to 32 ticks in one
|
||||||
|
* call. Break up large calls.
|
||||||
|
*
|
||||||
|
* FIXME: Provide and test faster call and keep fallback
|
||||||
|
* for old firmware
|
||||||
|
*/
|
||||||
static void jtagtap_tdi_tdo_seq(
|
static void jtagtap_tdi_tdo_seq(
|
||||||
uint8_t *DO, const uint8_t final_tms, const uint8_t *DI, int ticks)
|
uint8_t *DO, const uint8_t final_tms, const uint8_t *DI, int ticks)
|
||||||
{
|
{
|
||||||
uint8_t construct[REMOTE_MAX_MSG_SIZE];
|
uint8_t construct[REMOTE_MAX_MSG_SIZE];
|
||||||
int s;
|
int s;
|
||||||
|
|
||||||
uint64_t DIl=*(uint64_t *)DI;
|
if(!ticks || (!DI && !DO))
|
||||||
|
return;
|
||||||
|
uint64_t *DIl = (uint64_t *)DI;
|
||||||
|
uint64_t *DOl = (uint64_t *)DO;
|
||||||
|
while (ticks) {
|
||||||
|
int chunk;
|
||||||
|
if (ticks < 65)
|
||||||
|
chunk = ticks;
|
||||||
|
else {
|
||||||
|
chunk = 64;
|
||||||
|
}
|
||||||
|
ticks -= chunk;
|
||||||
|
uint64_t dil;
|
||||||
|
if (DI)
|
||||||
|
dil = *DIl++;
|
||||||
|
else
|
||||||
|
dil = 0;
|
||||||
|
/* Reduce the length of DI according to the bits we're transmitting */
|
||||||
|
if (chunk < 64)
|
||||||
|
dil &= ((1LL << chunk) - 1);
|
||||||
|
s = snprintf((char *)construct, REMOTE_MAX_MSG_SIZE,
|
||||||
|
"!J%c%02x%" PRIx64 "%c",
|
||||||
|
(!ticks && final_tms) ?
|
||||||
|
REMOTE_TDITDO_TMS : REMOTE_TDITDO_NOTMS,
|
||||||
|
chunk, dil, REMOTE_EOM);
|
||||||
|
platform_buffer_write(construct,s);
|
||||||
|
|
||||||
if(!ticks || !DI) return;
|
s = platform_buffer_read(construct, REMOTE_MAX_MSG_SIZE);
|
||||||
|
if ((!s) || (construct[0] == REMOTE_RESP_ERR)) {
|
||||||
/* Reduce the length of DI according to the bits we're transmitting */
|
DEBUG_WARN("jtagtap_tms_seq failed, error %s\n",
|
||||||
DIl &= (1LL << (ticks + 1))-1;
|
s ? (char *)&(construct[1]) : "unknown");
|
||||||
|
exit(-1);
|
||||||
s = snprintf((char *)construct, REMOTE_MAX_MSG_SIZE,
|
}
|
||||||
REMOTE_JTAG_TDIDO_STR,
|
if (DO)
|
||||||
final_tms ? REMOTE_TDITDO_TMS : REMOTE_TDITDO_NOTMS,
|
*DOl++ = remotehston(-1, (char *)&construct[1]);
|
||||||
ticks, DIl);
|
|
||||||
platform_buffer_write(construct,s);
|
|
||||||
|
|
||||||
s = platform_buffer_read(construct, REMOTE_MAX_MSG_SIZE);
|
|
||||||
if ((!s) || (construct[0] == REMOTE_RESP_ERR)) {
|
|
||||||
DEBUG_WARN("jtagtap_tms_seq failed, error %s\n",
|
|
||||||
s ? (char *)&(construct[1]) : "unknown");
|
|
||||||
exit(-1);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (DO) {
|
|
||||||
uint64_t DOl = remotehston(-1, (char *)&construct[1]);
|
|
||||||
*(uint64_t *)DO = DOl;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue