0568d1c8672bada76cfa9116ecc415aba6bb52d9
[openocd.git] / src / jtag / arm-jtag-ew.c
1 /***************************************************************************
2 * Copyright (C) 2009 by Dimitar Dimitrov <dinuxbg@gmail.com> *
3 * based on Dominic Rath's and Benedikt Sauter's usbprog.c *
4 * *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 2 of the License, or *
8 * (at your option) any later version. *
9 * *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
14 * *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19 ***************************************************************************/
20
21 #ifdef HAVE_CONFIG_H
22 #include "config.h"
23 #endif
24
25 #include "interface.h"
26 #include "commands.h"
27 #include <usb.h>
28
29
30 #define USB_VID 0x15ba
31 #define USB_PID 0x001e
32
33 #define ARMJTAGEW_EPT_BULK_OUT 0x01u
34 #define ARMJTAGEW_EPT_BULK_IN 0x82u
35
36 #define ARMJTAGEW_USB_TIMEOUT 2000
37
38 #define ARMJTAGEW_IN_BUFFER_SIZE (4*1024)
39 #define ARMJTAGEW_OUT_BUFFER_SIZE (4*1024)
40
41
42 /* USB command request codes. */
43 #define CMD_GET_VERSION 0x00
44 #define CMD_SELECT_DPIMPL 0x10
45 #define CMD_SET_TCK_FREQUENCY 0x11
46 #define CMD_GET_TCK_FREQUENCY 0x12
47 #define CMD_MEASURE_MAX_TCK_FREQ 0x15
48 #define CMD_MEASURE_RTCK_RESPONSE 0x16
49 #define CMD_TAP_SHIFT 0x17
50 #define CMD_SET_TAPHW_STATE 0x20
51 #define CMD_GET_TAPHW_STATE 0x21
52 #define CMD_TGPWR_SETUP 0x22
53
54 /* Global USB buffers */
55 static uint8_t usb_in_buffer[ARMJTAGEW_IN_BUFFER_SIZE];
56 static uint8_t usb_out_buffer[ARMJTAGEW_OUT_BUFFER_SIZE];
57
58 /* External interface functions */
59 static int armjtagew_execute_queue(void);
60 static int armjtagew_speed(int speed);
61 static int armjtagew_khz(int khz, int *jtag_speed);
62 static int armjtagew_register_commands(struct command_context *cmd_ctx);
63 static int armjtagew_init(void);
64 static int armjtagew_quit(void);
65
66 /* CLI command handler functions */
67 static int armjtagew_handle_armjtagew_info_command(struct command_context *cmd_ctx, char *cmd, char **args, int argc);
68
69 /* Queue command functions */
70 static void armjtagew_end_state(tap_state_t state);
71 static void armjtagew_state_move(void);
72 static void armjtagew_path_move(int num_states, tap_state_t *path);
73 static void armjtagew_runtest(int num_cycles);
74 static void armjtagew_scan(bool ir_scan, enum scan_type type, uint8_t *buffer, int scan_size, struct scan_command *command);
75 static void armjtagew_reset(int trst, int srst);
76 //static void armjtagew_simple_command(uint8_t command);
77 static int armjtagew_get_status(void);
78
79 /* tap buffer functions */
80 static void armjtagew_tap_init(void);
81 static int armjtagew_tap_execute(void);
82 static void armjtagew_tap_ensure_space(int scans, int bits);
83 static void armjtagew_tap_append_step(int tms, int tdi);
84 static void armjtagew_tap_append_scan(int length, uint8_t *buffer, struct scan_command *command);
85
86 /* ARM-JTAG-EW lowlevel functions */
87 struct armjtagew {
88 struct usb_dev_handle* usb_handle;
89 };
90
91 static struct armjtagew *armjtagew_usb_open(void);
92 static void armjtagew_usb_close(struct armjtagew *armjtagew);
93 static int armjtagew_usb_message(struct armjtagew *armjtagew, int out_length, int in_length);
94 static int armjtagew_usb_write(struct armjtagew *armjtagew, int out_length);
95 static int armjtagew_usb_read(struct armjtagew *armjtagew, int exp_in_length);
96
97 /* helper functions */
98 static int armjtagew_get_version_info(void);
99
100 #ifdef _DEBUG_USB_COMMS_
101 static void armjtagew_debug_buffer(uint8_t *buffer, int length);
102 #endif
103
104 static struct armjtagew* armjtagew_handle;
105
106
107
108 /***************************************************************************/
109 /* External interface implementation */
110
111 struct jtag_interface armjtagew_interface =
112 {
113 .name = "arm-jtag-ew",
114 .execute_queue = armjtagew_execute_queue,
115 .speed = armjtagew_speed,
116 .khz = armjtagew_khz,
117 .register_commands = armjtagew_register_commands,
118 .init = armjtagew_init,
119 .quit = armjtagew_quit
120 };
121
122
123 static int armjtagew_execute_queue(void)
124 {
125 struct jtag_command *cmd = jtag_command_queue;
126 int scan_size;
127 enum scan_type type;
128 uint8_t *buffer;
129
130 while (cmd != NULL)
131 {
132 switch (cmd->type)
133 {
134 case JTAG_RUNTEST:
135 DEBUG_JTAG_IO("runtest %i cycles, end in %i", cmd->cmd.runtest->num_cycles, \
136 cmd->cmd.runtest->end_state);
137
138 armjtagew_end_state(cmd->cmd.runtest->end_state);
139 armjtagew_runtest(cmd->cmd.runtest->num_cycles);
140 break;
141
142 case JTAG_STATEMOVE:
143 DEBUG_JTAG_IO("statemove end in %i", cmd->cmd.statemove->end_state);
144
145 armjtagew_end_state(cmd->cmd.statemove->end_state);
146 armjtagew_state_move();
147 break;
148
149 case JTAG_PATHMOVE:
150 DEBUG_JTAG_IO("pathmove: %i states, end in %i", \
151 cmd->cmd.pathmove->num_states, \
152 cmd->cmd.pathmove->path[cmd->cmd.pathmove->num_states - 1]);
153
154 armjtagew_path_move(cmd->cmd.pathmove->num_states, cmd->cmd.pathmove->path);
155 break;
156
157 case JTAG_SCAN:
158 DEBUG_JTAG_IO("scan end in %i", cmd->cmd.scan->end_state);
159
160 armjtagew_end_state(cmd->cmd.scan->end_state);
161
162 scan_size = jtag_build_buffer(cmd->cmd.scan, &buffer);
163 DEBUG_JTAG_IO("scan input, length = %d", scan_size);
164
165 #ifdef _DEBUG_USB_COMMS_
166 armjtagew_debug_buffer(buffer, (scan_size + 7) / 8);
167 #endif
168 type = jtag_scan_type(cmd->cmd.scan);
169 armjtagew_scan(cmd->cmd.scan->ir_scan, type, buffer, scan_size, cmd->cmd.scan);
170 break;
171
172 case JTAG_RESET:
173 DEBUG_JTAG_IO("reset trst: %i srst %i", cmd->cmd.reset->trst, cmd->cmd.reset->srst);
174
175 armjtagew_tap_execute();
176
177 if (cmd->cmd.reset->trst == 1)
178 {
179 tap_set_state(TAP_RESET);
180 }
181 armjtagew_reset(cmd->cmd.reset->trst, cmd->cmd.reset->srst);
182 break;
183
184 case JTAG_SLEEP:
185 DEBUG_JTAG_IO("sleep %i", cmd->cmd.sleep->us);
186 armjtagew_tap_execute();
187 jtag_sleep(cmd->cmd.sleep->us);
188 break;
189
190 default:
191 LOG_ERROR("BUG: unknown JTAG command type encountered");
192 exit(-1);
193 }
194 cmd = cmd->next;
195 }
196
197 return armjtagew_tap_execute();
198 }
199
200
201 /* Sets speed in kHz. */
202 static int armjtagew_speed(int speed)
203 {
204 int result;
205 int speed_real;
206
207
208 usb_out_buffer[0] = CMD_SET_TCK_FREQUENCY;
209 buf_set_u32(usb_out_buffer + 1, 0, 32, speed);
210
211 result = armjtagew_usb_message(armjtagew_handle, 4, 4);
212
213 if (result < 0)
214 {
215 LOG_ERROR("ARM-JTAG-EW setting speed failed (%d)", result);
216 return ERROR_JTAG_DEVICE_ERROR;
217 }
218
219 usb_out_buffer[0] = CMD_GET_TCK_FREQUENCY;
220 result = armjtagew_usb_message(armjtagew_handle, 1, 4);
221 speed_real = (int)buf_get_u32(usb_in_buffer,0,32);
222 if (result < 0)
223 {
224 LOG_ERROR("ARM-JTAG-EW getting speed failed (%d)", result);
225 return ERROR_JTAG_DEVICE_ERROR;
226 }
227 else
228 {
229 LOG_INFO("Requested speed %dkHz, emulator reported %dkHz.", speed, speed_real);
230 }
231
232 return ERROR_OK;
233 }
234
235
236 static int armjtagew_khz(int khz, int *jtag_speed)
237 {
238 *jtag_speed = khz;
239
240 return ERROR_OK;
241 }
242
243 static int armjtagew_register_commands(struct command_context *cmd_ctx)
244 {
245 register_command(cmd_ctx, NULL, "armjtagew_info", armjtagew_handle_armjtagew_info_command, COMMAND_EXEC,
246 "query armjtagew info");
247 return ERROR_OK;
248 }
249
250 static int armjtagew_init(void)
251 {
252 int check_cnt;
253
254 armjtagew_handle = armjtagew_usb_open();
255
256 if (armjtagew_handle == 0)
257 {
258 LOG_ERROR("Cannot find ARM-JTAG-EW Interface! Please check connection and permissions.");
259 return ERROR_JTAG_INIT_FAILED;
260 }
261
262 check_cnt = 0;
263 while (check_cnt < 3)
264 {
265 if (armjtagew_get_version_info() == ERROR_OK)
266 {
267 /* attempt to get status */
268 armjtagew_get_status();
269 break;
270 }
271
272 check_cnt++;
273 }
274
275 if (check_cnt == 3)
276 {
277 LOG_INFO("ARM-JTAG-EW initial read failed, don't worry");
278 }
279
280 LOG_INFO("ARM-JTAG-EW JTAG Interface ready");
281
282 armjtagew_reset(0, 0);
283 armjtagew_tap_init();
284
285 return ERROR_OK;
286 }
287
288 static int armjtagew_quit(void)
289 {
290 armjtagew_usb_close(armjtagew_handle);
291 return ERROR_OK;
292 }
293
294 /***************************************************************************/
295 /* Queue command implementations */
296
297 static void armjtagew_end_state(tap_state_t state)
298 {
299 if (tap_is_state_stable(state))
300 {
301 tap_set_end_state(state);
302 }
303 else
304 {
305 LOG_ERROR("BUG: %i is not a valid end state", state);
306 exit(-1);
307 }
308 }
309
310 /* Goes to the end state. */
311 static void armjtagew_state_move(void)
312 {
313 int i;
314 int tms = 0;
315 uint8_t tms_scan = tap_get_tms_path(tap_get_state(), tap_get_end_state());
316 int tms_count = tap_get_tms_path_len(tap_get_state(), tap_get_end_state());
317
318 for (i = 0; i < tms_count; i++)
319 {
320 tms = (tms_scan >> i) & 1;
321 armjtagew_tap_append_step(tms, 0);
322 }
323
324 tap_set_state(tap_get_end_state());
325 }
326
327 static void armjtagew_path_move(int num_states, tap_state_t *path)
328 {
329 int i;
330
331 for (i = 0; i < num_states; i++)
332 {
333 /*
334 * TODO: The ARM-JTAG-EW hardware delays TDI with 3 TCK cycles when in RTCK mode.
335 * Either handle that here, or update the documentation with examples
336 * how to fix that in the configuration files.
337 */
338 if (path[i] == tap_state_transition(tap_get_state(), false))
339 {
340 armjtagew_tap_append_step(0, 0);
341 }
342 else if (path[i] == tap_state_transition(tap_get_state(), true))
343 {
344 armjtagew_tap_append_step(1, 0);
345 }
346 else
347 {
348 LOG_ERROR("BUG: %s -> %s isn't a valid TAP transition", tap_state_name(tap_get_state()), tap_state_name(path[i]));
349 exit(-1);
350 }
351
352 tap_set_state(path[i]);
353 }
354
355 tap_set_end_state(tap_get_state());
356 }
357
358 static void armjtagew_runtest(int num_cycles)
359 {
360 int i;
361
362 tap_state_t saved_end_state = tap_get_end_state();
363
364 /* only do a state_move when we're not already in IDLE */
365 if (tap_get_state() != TAP_IDLE)
366 {
367 armjtagew_end_state(TAP_IDLE);
368 armjtagew_state_move();
369 }
370
371 /* execute num_cycles */
372 for (i = 0; i < num_cycles; i++)
373 {
374 armjtagew_tap_append_step(0, 0);
375 }
376
377 /* finish in end_state */
378 armjtagew_end_state(saved_end_state);
379 if (tap_get_state() != tap_get_end_state())
380 {
381 armjtagew_state_move();
382 }
383 }
384
385 static void armjtagew_scan(bool ir_scan, enum scan_type type, uint8_t *buffer, int scan_size, struct scan_command *command)
386 {
387 tap_state_t saved_end_state;
388
389 armjtagew_tap_ensure_space(1, scan_size + 8);
390
391 saved_end_state = tap_get_end_state();
392
393 /* Move to appropriate scan state */
394 armjtagew_end_state(ir_scan ? TAP_IRSHIFT : TAP_DRSHIFT);
395
396 armjtagew_state_move();
397 armjtagew_end_state(saved_end_state);
398
399 /* Scan */
400 armjtagew_tap_append_scan(scan_size, buffer, command);
401
402 /* We are in Exit1, go to Pause */
403 armjtagew_tap_append_step(0, 0);
404
405 tap_set_state(ir_scan ? TAP_IRPAUSE : TAP_DRPAUSE);
406
407 if (tap_get_state() != tap_get_end_state())
408 {
409 armjtagew_state_move();
410 }
411 }
412
413 static void armjtagew_reset(int trst, int srst)
414 {
415 const uint8_t trst_mask = (1u << 5);
416 const uint8_t srst_mask = (1u << 6);
417 uint8_t val = 0;
418 uint8_t outp_en = 0;
419 uint8_t change_mask = 0;
420 int result;
421
422 LOG_DEBUG("trst: %i, srst: %i", trst, srst);
423
424 if (srst == 0)
425 {
426 val |= srst_mask;
427 outp_en &= ~srst_mask; /* tristate */
428 change_mask |= srst_mask;
429 }
430 else if (srst == 1)
431 {
432 val &= ~srst_mask;
433 outp_en |= srst_mask;
434 change_mask |= srst_mask;
435 }
436
437 if (trst == 0)
438 {
439 val |= trst_mask;
440 outp_en &= ~trst_mask; /* tristate */
441 change_mask |= trst_mask;
442 }
443 else if (trst == 1)
444 {
445 val &= ~trst_mask;
446 outp_en |= trst_mask;
447 change_mask |= trst_mask;
448 }
449
450 usb_out_buffer[0] = CMD_SET_TAPHW_STATE;
451 usb_out_buffer[1] = val;
452 usb_out_buffer[2] = outp_en;
453 usb_out_buffer[3] = change_mask;
454 result = armjtagew_usb_write(armjtagew_handle, 4);
455 if (result != 4)
456 {
457 LOG_ERROR("ARM-JTAG-EW TRST/SRST pin set failed failed (%d)", result);
458 }
459 }
460
461
462 static int armjtagew_get_status(void)
463 {
464 int result;
465
466 usb_out_buffer[0] = CMD_GET_TAPHW_STATE;
467 result = armjtagew_usb_message(armjtagew_handle, 1, 12);
468
469 if (result == 0)
470 {
471 unsigned int u_tg = buf_get_u32(usb_in_buffer, 0, 16);
472 LOG_INFO("U_tg = %d mV, U_aux = %d mV, U_tgpwr = %d mV, I_tgpwr = %d mA, D1 = %d, Target power %s %s\n",
473 (int)(buf_get_u32(usb_in_buffer + 0, 0, 16)),
474 (int)(buf_get_u32(usb_in_buffer + 2, 0, 16)),
475 (int)(buf_get_u32(usb_in_buffer + 4, 0, 16)),
476 (int)(buf_get_u32(usb_in_buffer + 6, 0, 16)),
477 usb_in_buffer[9],
478 usb_in_buffer[11] ? "OVERCURRENT" : "OK",
479 usb_in_buffer[10] ? "enabled" : "disabled");
480
481 if (u_tg < 1500)
482 {
483 LOG_ERROR("Vref too low. Check Target Power\n");
484 }
485 }
486 else
487 {
488 LOG_ERROR("ARM-JTAG-EW command CMD_GET_TAPHW_STATE failed (%d)\n", result);
489 }
490
491 return ERROR_OK;
492 }
493
494 static int armjtagew_get_version_info(void)
495 {
496 int result;
497 char sn[16];
498 char auxinfo[257];
499
500 /* query hardware version */
501 usb_out_buffer[0] = CMD_GET_VERSION;
502 result = armjtagew_usb_message(armjtagew_handle, 1, 4 + 15 + 256);
503
504 if (result != 0)
505 {
506 LOG_ERROR("ARM-JTAG-EW command CMD_GET_VERSION failed (%d)\n", result);
507 return ERROR_JTAG_DEVICE_ERROR;
508 }
509
510
511 memcpy(sn, usb_in_buffer + 4, 15);
512 sn[15] = '\0';
513 memcpy(auxinfo, usb_in_buffer + 4+15, 256);
514 auxinfo[256] = '\0';
515
516 LOG_INFO("ARM-JTAG-EW firmware version %d.%d, hardware revision %c, SN=%s, Additional info: %s", \
517 usb_in_buffer[1], usb_in_buffer[0], \
518 isgraph(usb_in_buffer[2]) ? usb_in_buffer[2] : 'X', \
519 sn, auxinfo);
520 return ERROR_OK;
521 }
522
523 static int armjtagew_handle_armjtagew_info_command(struct command_context *cmd_ctx, char *cmd, char **args, int argc)
524 {
525 if (armjtagew_get_version_info() == ERROR_OK)
526 {
527 /* attempt to get status */
528 armjtagew_get_status();
529 }
530
531 return ERROR_OK;
532 }
533
534 /***************************************************************************/
535 /* ARM-JTAG-EW tap functions */
536
537 /* 2048 is the max value we can use here */
538 #define ARMJTAGEW_TAP_BUFFER_SIZE 2048
539
540 static int tap_length;
541 static uint8_t tms_buffer[ARMJTAGEW_TAP_BUFFER_SIZE];
542 static uint8_t tdi_buffer[ARMJTAGEW_TAP_BUFFER_SIZE];
543 static uint8_t tdo_buffer[ARMJTAGEW_TAP_BUFFER_SIZE];
544
545 struct pending_scan_result {
546 int first; /* First bit position in tdo_buffer to read */
547 int length; /* Number of bits to read */
548 struct scan_command *command; /* Corresponding scan command */
549 uint8_t *buffer;
550 };
551
552 #define MAX_PENDING_SCAN_RESULTS 256
553
554 static int pending_scan_results_length;
555 static struct pending_scan_result pending_scan_results_buffer[MAX_PENDING_SCAN_RESULTS];
556
557 static int last_tms;
558
559 static void armjtagew_tap_init(void)
560 {
561 tap_length = 0;
562 pending_scan_results_length = 0;
563 }
564
565 static void armjtagew_tap_ensure_space(int scans, int bits)
566 {
567 int available_scans = MAX_PENDING_SCAN_RESULTS - pending_scan_results_length;
568 int available_bits = ARMJTAGEW_TAP_BUFFER_SIZE * 8 - tap_length;
569
570 if (scans > available_scans || bits > available_bits)
571 {
572 armjtagew_tap_execute();
573 }
574 }
575
576 static void armjtagew_tap_append_step(int tms, int tdi)
577 {
578 last_tms = tms;
579 int index = tap_length / 8;
580
581 if (index < ARMJTAGEW_TAP_BUFFER_SIZE)
582 {
583 int bit_index = tap_length % 8;
584 uint8_t bit = 1 << bit_index;
585
586 if (tms)
587 {
588 tms_buffer[index] |= bit;
589 }
590 else
591 {
592 tms_buffer[index] &= ~bit;
593 }
594
595 if (tdi)
596 {
597 tdi_buffer[index] |= bit;
598 }
599 else
600 {
601 tdi_buffer[index] &= ~bit;
602 }
603
604 tap_length++;
605 }
606 else
607 {
608 LOG_ERROR("armjtagew_tap_append_step, overflow");
609 }
610 }
611
612 void armjtagew_tap_append_scan(int length, uint8_t *buffer, struct scan_command *command)
613 {
614 struct pending_scan_result *pending_scan_result = &pending_scan_results_buffer[pending_scan_results_length];
615 int i;
616
617 pending_scan_result->first = tap_length;
618 pending_scan_result->length = length;
619 pending_scan_result->command = command;
620 pending_scan_result->buffer = buffer;
621
622 for (i = 0; i < length; i++)
623 {
624 armjtagew_tap_append_step((i < length-1 ? 0 : 1), (buffer[i/8] >> (i%8)) & 1);
625 }
626 pending_scan_results_length++;
627 }
628
629 /* Pad and send a tap sequence to the device, and receive the answer.
630 * For the purpose of padding we assume that we are in idle or pause state. */
631 static int armjtagew_tap_execute(void)
632 {
633 int byte_length;
634 int tms_offset;
635 int tdi_offset;
636 int i;
637 int result;
638
639 if (tap_length > 0)
640 {
641 /* Pad last byte so that tap_length is divisible by 8 */
642 while (tap_length % 8 != 0)
643 {
644 /* More of the last TMS value keeps us in the same state,
645 * analogous to free-running JTAG interfaces. */
646 armjtagew_tap_append_step(last_tms, 0);
647 }
648
649 byte_length = tap_length / 8;
650
651 usb_out_buffer[0] = CMD_TAP_SHIFT;
652 buf_set_u32(usb_out_buffer + 1, 0, 16, byte_length);
653
654 tms_offset = 3;
655 for (i = 0; i < byte_length; i++)
656 {
657 usb_out_buffer[tms_offset + i] = flip_u32(tms_buffer[i],8);
658 }
659
660 tdi_offset = tms_offset + byte_length;
661 for (i = 0; i < byte_length; i++)
662 {
663 usb_out_buffer[tdi_offset + i] = flip_u32(tdi_buffer[i],8);
664 }
665
666 result = armjtagew_usb_message(armjtagew_handle, 3 + 2 * byte_length, byte_length + 4);
667
668 if (result == 0)
669 {
670 int stat;
671
672 stat = (int)buf_get_u32(usb_in_buffer + byte_length, 0, 32);
673 if (stat) {
674 LOG_ERROR("armjtagew_tap_execute, emulator returned error code %d for a CMD_TAP_SHIFT command", stat);
675 return ERROR_JTAG_QUEUE_FAILED;
676 }
677
678 for (i = 0; i < byte_length; i++)
679 {
680 tdo_buffer[i] = flip_u32(usb_in_buffer[i],8);
681 }
682
683 for (i = 0; i < pending_scan_results_length; i++)
684 {
685 struct pending_scan_result *pending_scan_result = &pending_scan_results_buffer[i];
686 uint8_t *buffer = pending_scan_result->buffer;
687 int length = pending_scan_result->length;
688 int first = pending_scan_result->first;
689 struct scan_command *command = pending_scan_result->command;
690
691 /* Copy to buffer */
692 buf_set_buf(tdo_buffer, first, buffer, 0, length);
693
694 DEBUG_JTAG_IO("pending scan result, length = %d", length);
695
696 #ifdef _DEBUG_USB_COMMS_
697 armjtagew_debug_buffer(buffer, byte_length);
698 #endif
699
700 if (jtag_read_buffer(buffer, command) != ERROR_OK)
701 {
702 armjtagew_tap_init();
703 return ERROR_JTAG_QUEUE_FAILED;
704 }
705
706 if (pending_scan_result->buffer != NULL)
707 {
708 free(pending_scan_result->buffer);
709 }
710 }
711 }
712 else
713 {
714 LOG_ERROR("armjtagew_tap_execute, wrong result %d, expected %d", result, byte_length);
715 return ERROR_JTAG_QUEUE_FAILED;
716 }
717
718 armjtagew_tap_init();
719 }
720
721 return ERROR_OK;
722 }
723
724 /*****************************************************************************/
725 /* JLink USB low-level functions */
726
727 static struct armjtagew* armjtagew_usb_open()
728 {
729 struct usb_bus *busses;
730 struct usb_bus *bus;
731 struct usb_device *dev;
732
733 struct armjtagew *result;
734
735 result = (struct armjtagew*) malloc(sizeof(struct armjtagew));
736
737 usb_init();
738 usb_find_busses();
739 usb_find_devices();
740
741 busses = usb_get_busses();
742
743 /* find armjtagew device in usb bus */
744
745 for (bus = busses; bus; bus = bus->next)
746 {
747 for (dev = bus->devices; dev; dev = dev->next)
748 {
749 if ((dev->descriptor.idVendor == USB_VID) && (dev->descriptor.idProduct == USB_PID))
750 {
751 result->usb_handle = usb_open(dev);
752
753 #if 0
754 /* usb_set_configuration required under win32 */
755 usb_set_configuration(result->usb_handle, dev->config[0].bConfigurationValue);
756 #endif
757 usb_claim_interface(result->usb_handle, 0);
758
759 #if 0
760 /*
761 * This makes problems under Mac OS X. And is not needed
762 * under Windows. Hopefully this will not break a linux build
763 */
764 usb_set_altinterface(result->usb_handle, 0);
765 #endif
766 return result;
767 }
768 }
769 }
770
771 free(result);
772 return NULL;
773 }
774
775 static void armjtagew_usb_close(struct armjtagew *armjtagew)
776 {
777 usb_close(armjtagew->usb_handle);
778 free(armjtagew);
779 }
780
781 /* Send a message and receive the reply. */
782 static int armjtagew_usb_message(struct armjtagew *armjtagew, int out_length, int in_length)
783 {
784 int result;
785
786 result = armjtagew_usb_write(armjtagew, out_length);
787 if (result == out_length)
788 {
789 result = armjtagew_usb_read(armjtagew, in_length);
790 if (result != in_length)
791 {
792 LOG_ERROR("usb_bulk_read failed (requested=%d, result=%d)", in_length, result);
793 return -1;
794 }
795 }
796 else
797 {
798 LOG_ERROR("usb_bulk_write failed (requested=%d, result=%d)", out_length, result);
799 return -1;
800 }
801 return 0;
802 }
803
804 /* Write data from out_buffer to USB. */
805 static int armjtagew_usb_write(struct armjtagew *armjtagew, int out_length)
806 {
807 int result;
808
809 if (out_length > ARMJTAGEW_OUT_BUFFER_SIZE)
810 {
811 LOG_ERROR("armjtagew_write illegal out_length=%d (max=%d)", out_length, ARMJTAGEW_OUT_BUFFER_SIZE);
812 return -1;
813 }
814
815 result = usb_bulk_write(armjtagew->usb_handle, ARMJTAGEW_EPT_BULK_OUT, \
816 (char*)usb_out_buffer, out_length, ARMJTAGEW_USB_TIMEOUT);
817
818 DEBUG_JTAG_IO("armjtagew_usb_write, out_length = %d, result = %d", out_length, result);
819
820 #ifdef _DEBUG_USB_COMMS_
821 armjtagew_debug_buffer(usb_out_buffer, out_length);
822 #endif
823 return result;
824 }
825
826 /* Read data from USB into in_buffer. */
827 static int armjtagew_usb_read(struct armjtagew *armjtagew, int exp_in_length)
828 {
829 int result = usb_bulk_read(armjtagew->usb_handle, ARMJTAGEW_EPT_BULK_IN, \
830 (char*)usb_in_buffer, exp_in_length, ARMJTAGEW_USB_TIMEOUT);
831
832 DEBUG_JTAG_IO("armjtagew_usb_read, result = %d", result);
833
834 #ifdef _DEBUG_USB_COMMS_
835 armjtagew_debug_buffer(usb_in_buffer, result);
836 #endif
837 return result;
838 }
839
840
841 #ifdef _DEBUG_USB_COMMS_
842 #define BYTES_PER_LINE 16
843
844 static void armjtagew_debug_buffer(uint8_t *buffer, int length)
845 {
846 char line[81];
847 char s[4];
848 int i;
849 int j;
850
851 for (i = 0; i < length; i += BYTES_PER_LINE)
852 {
853 snprintf(line, 5, "%04x", i);
854 for (j = i; j < i + BYTES_PER_LINE && j < length; j++)
855 {
856 snprintf(s, 4, " %02x", buffer[j]);
857 strcat(line, s);
858 }
859 LOG_DEBUG("%s", line);
860 }
861 }
862 #endif
863

Linking to existing account procedure

If you already have an account and want to add another login method you MUST first sign in with your existing account and then change URL to read https://review.openocd.org/login/?link to get to this page again but this time it'll work for linking. Thank you.

SSH host keys fingerprints

1024 SHA256:YKx8b7u5ZWdcbp7/4AeXNaqElP49m6QrwfXaqQGJAOk gerrit-code-review@openocd.zylin.com (DSA)
384 SHA256:jHIbSQa4REvwCFG4cq5LBlBLxmxSqelQPem/EXIrxjk gerrit-code-review@openocd.org (ECDSA)
521 SHA256:UAOPYkU9Fjtcao0Ul/Rrlnj/OsQvt+pgdYSZ4jOYdgs gerrit-code-review@openocd.org (ECDSA)
256 SHA256:A13M5QlnozFOvTllybRZH6vm7iSt0XLxbA48yfc2yfY gerrit-code-review@openocd.org (ECDSA)
256 SHA256:spYMBqEYoAOtK7yZBrcwE8ZpYt6b68Cfh9yEVetvbXg gerrit-code-review@openocd.org (ED25519)
+--[ED25519 256]--+
|=..              |
|+o..   .         |
|*.o   . .        |
|+B . . .         |
|Bo. = o S        |
|Oo.+ + =         |
|oB=.* = . o      |
| =+=.+   + E     |
|. .=o   . o      |
+----[SHA256]-----+
2048 SHA256:0Onrb7/PHjpo6iVZ7xQX2riKN83FJ3KGU0TvI0TaFG4 gerrit-code-review@openocd.zylin.com (RSA)