zy1000: some background info on the zy1000 file.
[openocd-genbsdl] / src / jtag / zy1000 / zy1000.c
1 /***************************************************************************
2  *   Copyright (C) 2007-2009 by Ã˜yvind Harboe                              *
3  *                                                                         *
4  *   This program is free software; you can redistribute it and/or modify  *
5  *   it under the terms of the GNU General Public License as published by  *
6  *   the Free Software Foundation; either version 2 of the License, or     *
7  *   (at your option) any later version.                                   *
8  *                                                                         *
9  *   This program is distributed in the hope that it will be useful,       *
10  *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
11  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
12  *   GNU General Public License for more details.                          *
13  *                                                                         *
14  *   You should have received a copy of the GNU General Public License     *
15  *   along with this program; if not, write to the                         *
16  *   Free Software Foundation, Inc.,                                       *
17  *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
18  ***************************************************************************/
19
20 /* This file supports the zy1000 debugger: http://www.zylin.com/zy1000.html
21  *
22  * The zy1000 is a standalone debugger that has a web interface and
23  * requires no drivers on the developer host as all communication
24  * is via TCP/IP. The zy1000 gets it performance(~400-700kBytes/s
25  * DCC downloads @ 16MHz target) as it has an FPGA to hardware
26  * accelerate the JTAG commands, while offering *very* low latency
27  * between OpenOCD and the FPGA registers.
28  *
29  * The disadvantage of the zy1000 is that it has a feeble CPU compared to
30  * a PC(ca. 50-500 DMIPS depending on how one counts it), whereas a PC
31  * is on the order of 10000 DMIPS(i.e. at a factor of 20-200).
32  *
33  * The zy1000 revc hardware is using an Altera Nios CPU, whereas the
34  * revb is using ARM7 + Xilinx.
35  *
36  * See Zylin web pages or contact Zylin for more information.
37  *
38  * The reason this code is in OpenOCD rather than OpenOCD linked with the
39  * ZY1000 code is that OpenOCD is the long road towards getting
40  * libopenocd into place. libopenocd will support both low performance,
41  * low latency systems(embedded) and high performance high latency
42  * systems(PCs).
43  */
44 #ifdef HAVE_CONFIG_H
45 #include "config.h"
46 #endif
47
48 #include <target/embeddedice.h>
49 #include <jtag/minidriver.h>
50 #include <jtag/interface.h>
51 #include "zy1000_version.h"
52
53 #include <cyg/hal/hal_io.h>             // low level i/o
54 #include <cyg/hal/hal_diag.h>
55
56 #include <time.h>
57
58 #define ZYLIN_VERSION GIT_ZY1000_VERSION
59 #define ZYLIN_DATE __DATE__
60 #define ZYLIN_TIME __TIME__
61 #define ZYLIN_OPENOCD GIT_OPENOCD_VERSION
62 #define ZYLIN_OPENOCD_VERSION "ZY1000 " ZYLIN_VERSION " " ZYLIN_DATE
63
64
65 static int zy1000_khz(int khz, int *jtag_speed)
66 {
67         if (khz == 0)
68         {
69                 *jtag_speed = 0;
70         }
71         else
72         {
73                 *jtag_speed = 64000/khz;
74         }
75         return ERROR_OK;
76 }
77
78 static int zy1000_speed_div(int speed, int *khz)
79 {
80         if (speed == 0)
81         {
82                 *khz = 0;
83         }
84         else
85         {
86                 *khz = 64000/speed;
87         }
88
89         return ERROR_OK;
90 }
91
92 static bool readPowerDropout(void)
93 {
94         cyg_uint32 state;
95         // sample and clear power dropout
96         HAL_WRITE_UINT32(ZY1000_JTAG_BASE + 0x10, 0x80);
97         HAL_READ_UINT32(ZY1000_JTAG_BASE + 0x10, state);
98         bool powerDropout;
99         powerDropout = (state & 0x80) != 0;
100         return powerDropout;
101 }
102
103
104 static bool readSRST(void)
105 {
106         cyg_uint32 state;
107         // sample and clear SRST sensing
108         HAL_WRITE_UINT32(ZY1000_JTAG_BASE + 0x10, 0x00000040);
109         HAL_READ_UINT32(ZY1000_JTAG_BASE + 0x10, state);
110         bool srstAsserted;
111         srstAsserted = (state & 0x40) != 0;
112         return srstAsserted;
113 }
114
115 static int zy1000_srst_asserted(int *srst_asserted)
116 {
117         *srst_asserted = readSRST();
118         return ERROR_OK;
119 }
120
121 static int zy1000_power_dropout(int *dropout)
122 {
123         *dropout = readPowerDropout();
124         return ERROR_OK;
125 }
126
127 void zy1000_reset(int trst, int srst)
128 {
129         LOG_DEBUG("zy1000 trst=%d, srst=%d", trst, srst);
130         if (!srst)
131         {
132                 ZY1000_POKE(ZY1000_JTAG_BASE + 0x14, 0x00000001);
133         }
134         else
135         {
136                 /* Danger!!! if clk != 0 when in
137                  * idle in TAP_IDLE, reset halt on str912 will fail.
138                  */
139                 ZY1000_POKE(ZY1000_JTAG_BASE + 0x10, 0x00000001);
140         }
141
142         if (!trst)
143         {
144                 ZY1000_POKE(ZY1000_JTAG_BASE + 0x14, 0x00000002);
145         }
146         else
147         {
148                 /* assert reset */
149                 ZY1000_POKE(ZY1000_JTAG_BASE + 0x10, 0x00000002);
150         }
151
152         if (trst||(srst && (jtag_get_reset_config() & RESET_SRST_PULLS_TRST)))
153         {
154                 waitIdle();
155                 /* we're now in the RESET state until trst is deasserted */
156                 ZY1000_POKE(ZY1000_JTAG_BASE + 0x20, TAP_RESET);
157         } else
158         {
159                 /* We'll get RCLK failure when we assert TRST, so clear any false positives here */
160                 ZY1000_POKE(ZY1000_JTAG_BASE + 0x14, 0x400);
161         }
162
163         /* wait for srst to float back up */
164         if (!srst)
165         {
166                 int i;
167                 for (i = 0; i < 1000; i++)
168                 {
169                         // We don't want to sense our own reset, so we clear here.
170                         // There is of course a timing hole where we could loose
171                         // a "real" reset.
172                         if (!readSRST())
173                                 break;
174
175                         /* wait 1ms */
176                         alive_sleep(1);
177                 }
178
179                 if (i == 1000)
180                 {
181                         LOG_USER("SRST didn't deassert after %dms", i);
182                 } else if (i > 1)
183                 {
184                         LOG_USER("SRST took %dms to deassert", i);
185                 }
186         }
187 }
188
189 int zy1000_speed(int speed)
190 {
191         if (speed == 0)
192         {
193                 /*0 means RCLK*/
194                 speed = 0;
195                 ZY1000_POKE(ZY1000_JTAG_BASE + 0x10, 0x100);
196                 LOG_DEBUG("jtag_speed using RCLK");
197         }
198         else
199         {
200                 if (speed > 8190 || speed < 2)
201                 {
202                         LOG_USER("valid ZY1000 jtag_speed=[8190,2]. Divisor is 64MHz / even values between 8190-2, i.e. min 7814Hz, max 32MHz");
203                         return ERROR_INVALID_ARGUMENTS;
204                 }
205
206                 LOG_USER("jtag_speed %d => JTAG clk=%f", speed, 64.0/(float)speed);
207                 ZY1000_POKE(ZY1000_JTAG_BASE + 0x14, 0x100);
208                 ZY1000_POKE(ZY1000_JTAG_BASE + 0x1c, speed&~1);
209         }
210         return ERROR_OK;
211 }
212
213 static bool savePower;
214
215
216 static void setPower(bool power)
217 {
218         savePower = power;
219         if (power)
220         {
221                 HAL_WRITE_UINT32(ZY1000_JTAG_BASE + 0x14, 0x8);
222         } else
223         {
224                 HAL_WRITE_UINT32(ZY1000_JTAG_BASE + 0x10, 0x8);
225         }
226 }
227
228 COMMAND_HANDLER(handle_power_command)
229 {
230         switch (CMD_ARGC)
231         {
232         case 1: {
233                 bool enable;
234                 COMMAND_PARSE_ON_OFF(CMD_ARGV[0], enable);
235                 setPower(enable);
236                 // fall through
237         }
238         case 0:
239                 LOG_INFO("Target power %s", savePower ? "on" : "off");
240                 break;
241         default:
242                 return ERROR_INVALID_ARGUMENTS;
243         }
244
245         return ERROR_OK;
246 }
247
248
249 /* Give TELNET a way to find out what version this is */
250 static int jim_zy1000_version(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
251 {
252         if ((argc < 1) || (argc > 3))
253                 return JIM_ERR;
254         const char *version_str = NULL;
255
256         if (argc == 1)
257         {
258                 version_str = ZYLIN_OPENOCD_VERSION;
259         } else
260         {
261                 const char *str = Jim_GetString(argv[1], NULL);
262                 const char *str2 = NULL;
263                 if (argc > 2)
264                         str2 = Jim_GetString(argv[2], NULL);
265                 if (strcmp("openocd", str) == 0)
266                 {
267                         version_str = ZYLIN_OPENOCD;
268                 }
269                 else if (strcmp("zy1000", str) == 0)
270                 {
271                         version_str = ZYLIN_VERSION;
272                 }
273                 else if (strcmp("date", str) == 0)
274                 {
275                         version_str = ZYLIN_DATE;
276                 }
277                 else if (strcmp("time", str) == 0)
278                 {
279                         version_str = ZYLIN_TIME;
280                 }
281                 else if (strcmp("pcb", str) == 0)
282                 {
283 #ifdef CYGPKG_HAL_NIOS2
284                         version_str="c";
285 #else
286                         version_str="b";
287 #endif
288                 }
289 #ifdef CYGPKG_HAL_NIOS2
290                 else if (strcmp("fpga", str) == 0)
291                 {
292
293                         /* return a list of 32 bit integers to describe the expected
294                          * and actual FPGA
295                          */
296                         static char *fpga_id = "0x12345678 0x12345678 0x12345678 0x12345678";
297                         cyg_uint32 id, timestamp;
298                         HAL_READ_UINT32(SYSID_BASE, id);
299                         HAL_READ_UINT32(SYSID_BASE+4, timestamp);
300                         sprintf(fpga_id, "0x%08x 0x%08x 0x%08x 0x%08x", id, timestamp, SYSID_ID, SYSID_TIMESTAMP);
301                         version_str = fpga_id;
302                         if ((argc>2) && (strcmp("time", str2) == 0))
303                         {
304                             time_t last_mod = timestamp;
305                             char * t = ctime (&last_mod) ;
306                             t[strlen(t)-1] = 0;
307                             version_str = t;
308                         }
309                 }
310 #endif
311
312                 else
313                 {
314                         return JIM_ERR;
315                 }
316         }
317
318         Jim_SetResult(interp, Jim_NewStringObj(interp, version_str, -1));
319
320         return JIM_OK;
321 }
322
323
324 #ifdef CYGPKG_HAL_NIOS2
325 static int jim_zy1000_writefirmware(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
326 {
327         if (argc != 2)
328                 return JIM_ERR;
329
330         int length;
331         int stat;
332         const char *str = Jim_GetString(argv[1], &length);
333
334         /* BUG!!!! skip header! */
335         void *firmware_address=0x4000000;
336         int firmware_length=0x100000;
337
338         if (length>firmware_length)
339                 return JIM_ERR;
340
341         void *err_addr;
342
343     if ((stat = flash_erase((void *)firmware_address, firmware_length, (void **)&err_addr)) != 0)
344     {
345         return JIM_ERR;
346     }
347
348     if ((stat = flash_program(firmware_address, str, length, (void **)&err_addr)) != 0)
349         return JIM_ERR;
350
351     return JIM_OK;
352 }
353 #endif
354
355 static int
356 zylinjtag_Jim_Command_powerstatus(Jim_Interp *interp,
357                                                                    int argc,
358                 Jim_Obj * const *argv)
359 {
360         if (argc != 1)
361         {
362                 Jim_WrongNumArgs(interp, 1, argv, "powerstatus");
363                 return JIM_ERR;
364         }
365
366         cyg_uint32 status;
367         ZY1000_PEEK(ZY1000_JTAG_BASE + 0x10, status);
368
369         Jim_SetResult(interp, Jim_NewIntObj(interp, (status&0x80) != 0));
370
371         return JIM_OK;
372 }
373
374
375
376
377 int zy1000_init(void)
378 {
379         LOG_USER("%s", ZYLIN_OPENOCD_VERSION);
380
381         ZY1000_POKE(ZY1000_JTAG_BASE + 0x10, 0x30); // Turn on LED1 & LED2
382
383         setPower(true); // on by default
384
385
386          /* deassert resets. Important to avoid infinite loop waiting for SRST to deassert */
387         zy1000_reset(0, 0);
388         zy1000_speed(jtag_get_speed());
389
390         return ERROR_OK;
391 }
392
393 int zy1000_quit(void)
394 {
395
396         return ERROR_OK;
397 }
398
399
400
401 int interface_jtag_execute_queue(void)
402 {
403         cyg_uint32 empty;
404
405         waitIdle();
406         ZY1000_PEEK(ZY1000_JTAG_BASE + 0x10, empty);
407         /* clear JTAG error register */
408         ZY1000_POKE(ZY1000_JTAG_BASE + 0x14, 0x400);
409
410         if ((empty&0x400) != 0)
411         {
412                 LOG_WARNING("RCLK timeout");
413                 /* the error is informative only as we don't want to break the firmware if there
414                  * is a false positive.
415                  */
416 //              return ERROR_FAIL;
417         }
418         return ERROR_OK;
419 }
420
421
422
423
424
425 static cyg_uint32 getShiftValue(void)
426 {
427         cyg_uint32 value;
428         waitIdle();
429         ZY1000_PEEK(ZY1000_JTAG_BASE + 0xc, value);
430         VERBOSE(LOG_INFO("getShiftValue %08x", value));
431         return value;
432 }
433 #if 0
434 static cyg_uint32 getShiftValueFlip(void)
435 {
436         cyg_uint32 value;
437         waitIdle();
438         ZY1000_PEEK(ZY1000_JTAG_BASE + 0x18, value);
439         VERBOSE(LOG_INFO("getShiftValue %08x (flipped)", value));
440         return value;
441 }
442 #endif
443
444 #if 0
445 static void shiftValueInnerFlip(const tap_state_t state, const tap_state_t endState, int repeat, cyg_uint32 value)
446 {
447         VERBOSE(LOG_INFO("shiftValueInner %s %s %d %08x (flipped)", tap_state_name(state), tap_state_name(endState), repeat, value));
448         cyg_uint32 a,b;
449         a = state;
450         b = endState;
451         ZY1000_POKE(ZY1000_JTAG_BASE + 0xc, value);
452         ZY1000_POKE(ZY1000_JTAG_BASE + 0x8, (1 << 15) | (repeat << 8) | (a << 4) | b);
453         VERBOSE(getShiftValueFlip());
454 }
455 #endif
456
457 static void gotoEndState(tap_state_t end_state)
458 {
459         setCurrentState(end_state);
460 }
461
462 static __inline void scanFields(int num_fields, const struct scan_field *fields, tap_state_t shiftState, int pause)
463 {
464         int i;
465         int j;
466         int k;
467
468         for (i = 0; i < num_fields; i++)
469         {
470                 cyg_uint32 value;
471
472                 uint8_t *inBuffer = NULL;
473
474
475                 // figure out where to store the input data
476                 int num_bits = fields[i].num_bits;
477                 if (fields[i].in_value != NULL)
478                 {
479                         inBuffer = fields[i].in_value;
480                 }
481
482                 // here we shuffle N bits out/in
483                 j = 0;
484                 while (j < num_bits)
485                 {
486                         tap_state_t pause_state;
487                         int l;
488                         k = num_bits-j;
489                         pause_state = (shiftState == TAP_DRSHIFT)?TAP_DRSHIFT:TAP_IRSHIFT;
490                         if (k > 32)
491                         {
492                                 k = 32;
493                                 /* we have more to shift out */
494                         } else if (pause&&(i == num_fields-1))
495                         {
496                                 /* this was the last to shift out this time */
497                                 pause_state = (shiftState==TAP_DRSHIFT)?TAP_DRPAUSE:TAP_IRPAUSE;
498                         }
499
500                         // we have (num_bits + 7)/8 bytes of bits to toggle out.
501                         // bits are pushed out LSB to MSB
502                         value = 0;
503                         if (fields[i].out_value != NULL)
504                         {
505                                 for (l = 0; l < k; l += 8)
506                                 {
507                                         value|=fields[i].out_value[(j + l)/8]<<l;
508                                 }
509                         }
510                         /* mask away unused bits for easier debugging */
511                         if (k < 32)
512                         {
513                                 value&=~(((uint32_t)0xffffffff) << k);
514                         } else
515                         {
516                                 /* Shifting by >= 32 is not defined by the C standard
517                                  * and will in fact shift by &0x1f bits on nios */
518                         }
519
520                         shiftValueInner(shiftState, pause_state, k, value);
521
522                         if (inBuffer != NULL)
523                         {
524                                 // data in, LSB to MSB
525                                 value = getShiftValue();
526                                 // we're shifting in data to MSB, shift data to be aligned for returning the value
527                                 value >>= 32-k;
528
529                                 for (l = 0; l < k; l += 8)
530                                 {
531                                         inBuffer[(j + l)/8]=(value >> l)&0xff;
532                                 }
533                         }
534                         j += k;
535                 }
536         }
537 }
538
539 int interface_jtag_add_ir_scan(int num_fields, const struct scan_field *fields, tap_state_t state)
540 {
541
542         int j;
543         int scan_size = 0;
544         struct jtag_tap *tap, *nextTap;
545         for (tap = jtag_tap_next_enabled(NULL); tap!= NULL; tap = nextTap)
546         {
547                 nextTap = jtag_tap_next_enabled(tap);
548                 int pause = (nextTap==NULL);
549
550                 int found = 0;
551
552                 scan_size = tap->ir_length;
553
554                 /* search the list */
555                 for (j = 0; j < num_fields; j++)
556                 {
557                         if (tap == fields[j].tap)
558                         {
559                                 found = 1;
560
561                                 scanFields(1, fields + j, TAP_IRSHIFT, pause);
562                                 /* update device information */
563                                 buf_cpy(fields[j].out_value, tap->cur_instr, scan_size);
564
565                                 tap->bypass = 0;
566                                 break;
567                         }
568                 }
569
570                 if (!found)
571                 {
572                         /* if a device isn't listed, set it to BYPASS */
573                         uint8_t ones[]={0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff};
574
575                         struct scan_field tmp;
576                         memset(&tmp, 0, sizeof(tmp));
577                         tmp.out_value = ones;
578                         tmp.num_bits = scan_size;
579                         scanFields(1, &tmp, TAP_IRSHIFT, pause);
580                         /* update device information */
581                         buf_cpy(tmp.out_value, tap->cur_instr, scan_size);
582                         tap->bypass = 1;
583                 }
584         }
585         gotoEndState(state);
586
587         return ERROR_OK;
588 }
589
590
591
592
593
594 int interface_jtag_add_plain_ir_scan(int num_fields, const struct scan_field *fields, tap_state_t state)
595 {
596         scanFields(num_fields, fields, TAP_IRSHIFT, 1);
597         gotoEndState(state);
598
599         return ERROR_OK;
600 }
601
602 int interface_jtag_add_dr_scan(int num_fields, const struct scan_field *fields, tap_state_t state)
603 {
604
605         int j;
606         struct jtag_tap *tap, *nextTap;
607         for (tap = jtag_tap_next_enabled(NULL); tap!= NULL; tap = nextTap)
608         {
609                 nextTap = jtag_tap_next_enabled(tap);
610                 int found = 0;
611                 int pause = (nextTap==NULL);
612
613                 for (j = 0; j < num_fields; j++)
614                 {
615                         if (tap == fields[j].tap)
616                         {
617                                 found = 1;
618
619                                 scanFields(1, fields+j, TAP_DRSHIFT, pause);
620                         }
621                 }
622                 if (!found)
623                 {
624                         struct scan_field tmp;
625                         /* program the scan field to 1 bit length, and ignore it's value */
626                         tmp.num_bits = 1;
627                         tmp.out_value = NULL;
628                         tmp.in_value = NULL;
629
630                         scanFields(1, &tmp, TAP_DRSHIFT, pause);
631                 }
632                 else
633                 {
634                 }
635         }
636         gotoEndState(state);
637         return ERROR_OK;
638 }
639
640 int interface_jtag_add_plain_dr_scan(int num_fields, const struct scan_field *fields, tap_state_t state)
641 {
642         scanFields(num_fields, fields, TAP_DRSHIFT, 1);
643         gotoEndState(state);
644         return ERROR_OK;
645 }
646
647
648 int interface_jtag_add_tlr()
649 {
650         setCurrentState(TAP_RESET);
651         return ERROR_OK;
652 }
653
654
655
656
657 int interface_jtag_add_reset(int req_trst, int req_srst)
658 {
659         zy1000_reset(req_trst, req_srst);
660         return ERROR_OK;
661 }
662
663 static int zy1000_jtag_add_clocks(int num_cycles, tap_state_t state, tap_state_t clockstate)
664 {
665         /* num_cycles can be 0 */
666         setCurrentState(clockstate);
667
668         /* execute num_cycles, 32 at the time. */
669         int i;
670         for (i = 0; i < num_cycles; i += 32)
671         {
672                 int num;
673                 num = 32;
674                 if (num_cycles-i < num)
675                 {
676                         num = num_cycles-i;
677                 }
678                 shiftValueInner(clockstate, clockstate, num, 0);
679         }
680
681 #if !TEST_MANUAL()
682         /* finish in end_state */
683         setCurrentState(state);
684 #else
685         tap_state_t t = TAP_IDLE;
686         /* test manual drive code on any target */
687         int tms;
688         uint8_t tms_scan = tap_get_tms_path(t, state);
689         int tms_count = tap_get_tms_path_len(tap_get_state(), tap_get_end_state());
690
691         for (i = 0; i < tms_count; i++)
692         {
693                 tms = (tms_scan >> i) & 1;
694                 waitIdle();
695                 ZY1000_POKE(ZY1000_JTAG_BASE + 0x28,  tms);
696         }
697         waitIdle();
698         ZY1000_POKE(ZY1000_JTAG_BASE + 0x20, state);
699 #endif
700
701
702         return ERROR_OK;
703 }
704
705 int interface_jtag_add_runtest(int num_cycles, tap_state_t state)
706 {
707         return zy1000_jtag_add_clocks(num_cycles, state, TAP_IDLE);
708 }
709
710 int interface_jtag_add_clocks(int num_cycles)
711 {
712         return zy1000_jtag_add_clocks(num_cycles, cmd_queue_cur_state, cmd_queue_cur_state);
713 }
714
715 int interface_jtag_add_sleep(uint32_t us)
716 {
717         jtag_sleep(us);
718         return ERROR_OK;
719 }
720
721 int interface_jtag_add_pathmove(int num_states, const tap_state_t *path)
722 {
723         int state_count;
724         int tms = 0;
725
726         /*wait for the fifo to be empty*/
727         waitIdle();
728
729         state_count = 0;
730
731         tap_state_t cur_state = cmd_queue_cur_state;
732
733         while (num_states)
734         {
735                 if (tap_state_transition(cur_state, false) == path[state_count])
736                 {
737                         tms = 0;
738                 }
739                 else if (tap_state_transition(cur_state, true) == path[state_count])
740                 {
741                         tms = 1;
742                 }
743                 else
744                 {
745                         LOG_ERROR("BUG: %s -> %s isn't a valid TAP transition", tap_state_name(cur_state), tap_state_name(path[state_count]));
746                         exit(-1);
747                 }
748
749                 waitIdle();
750                 ZY1000_POKE(ZY1000_JTAG_BASE + 0x28,  tms);
751
752                 cur_state = path[state_count];
753                 state_count++;
754                 num_states--;
755         }
756
757         waitIdle();
758         ZY1000_POKE(ZY1000_JTAG_BASE + 0x20,  cur_state);
759         return ERROR_OK;
760 }
761
762
763
764 void embeddedice_write_dcc(struct jtag_tap *tap, int reg_addr, uint8_t *buffer, int little, int count)
765 {
766 //      static int const reg_addr = 0x5;
767         tap_state_t end_state = jtag_get_end_state();
768         if (jtag_tap_next_enabled(jtag_tap_next_enabled(NULL)) == NULL)
769         {
770                 /* better performance via code duplication */
771                 if (little)
772                 {
773                         int i;
774                         for (i = 0; i < count; i++)
775                         {
776                                 shiftValueInner(TAP_DRSHIFT, TAP_DRSHIFT, 32, fast_target_buffer_get_u32(buffer, 1));
777                                 shiftValueInner(TAP_DRSHIFT, end_state, 6, reg_addr | (1 << 5));
778                                 buffer += 4;
779                         }
780                 } else
781                 {
782                         int i;
783                         for (i = 0; i < count; i++)
784                         {
785                                 shiftValueInner(TAP_DRSHIFT, TAP_DRSHIFT, 32, fast_target_buffer_get_u32(buffer, 0));
786                                 shiftValueInner(TAP_DRSHIFT, end_state, 6, reg_addr | (1 << 5));
787                                 buffer += 4;
788                         }
789                 }
790         }
791         else
792         {
793                 int i;
794                 for (i = 0; i < count; i++)
795                 {
796                         embeddedice_write_reg_inner(tap, reg_addr, fast_target_buffer_get_u32(buffer, little));
797                         buffer += 4;
798                 }
799         }
800 }
801
802
803 static const struct command_registration zy1000_commands[] = {
804         {
805                 .name = "power",
806                 .handler = &handle_power_command,
807                 .mode = COMMAND_ANY,
808                 .help = "turn power switch to target on/off. No arguments - print status.",
809                 .usage = "power <on/off>",
810         },
811         {
812                 .name = "zy1000_version",
813                 .mode = COMMAND_ANY,
814                 .jim_handler = &jim_zy1000_version,
815                 .help = "print version info for zy1000",
816         },
817         {
818                 .name = "powerstatus",
819                 .mode = COMMAND_ANY,
820                 .jim_handler = & zylinjtag_Jim_Command_powerstatus,
821                 .help = "print power status of target",
822         },
823 #ifdef CYGPKG_HAL_NIOS2
824         {
825                 .name = "updatezy1000firmware",
826                 .mode = COMMAND_ANY,
827                 .jim_handler = &jim_zy1000_writefirmware,
828                 .help = "writes firmware to flash",
829         },
830 #endif
831         COMMAND_REGISTRATION_DONE
832 };
833
834
835
836 struct jtag_interface zy1000_interface =
837 {
838         .name = "ZY1000",
839         .execute_queue = NULL,
840         .speed = zy1000_speed,
841         .commands = zy1000_commands,
842         .init = zy1000_init,
843         .quit = zy1000_quit,
844         .khz = zy1000_khz,
845         .speed_div = zy1000_speed_div,
846         .power_dropout = zy1000_power_dropout,
847         .srst_asserted = zy1000_srst_asserted,
848 };
849