1 /***************************************************************************
2 * Copyright (C) 2006 by Dominic Rath *
3 * Dominic.Rath@gmx.de *
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. *
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. *
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 ***************************************************************************/
24 #include "replacements.h"
29 #define _DEBUG_GW16012_IO_
34 #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
36 #include <sys/types.h>
37 #include <machine/sysarch.h>
38 #include <machine/cpufunc.h>
39 #define ioperm(startport,length,enable)\
40 i386_set_ioperm((startport), (length), (enable))
48 #endif /* __FreeBSD__, __FreeBSD_kernel__ */
56 #if PARPORT_USE_PPDEV == 1
57 #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
58 #include <dev/ppbus/ppi.h>
59 #include <dev/ppbus/ppbconf.h>
60 #define PPRSTATUS PPIGSTATUS
61 #define PPWDATA PPISDATA
63 #include <linux/parport.h>
64 #include <linux/ppdev.h>
67 #include <sys/ioctl.h>
68 #else /* not PARPORT_USE_PPDEV */
74 #if PARPORT_USE_GIVEIO == 1
85 unsigned long gw16012_port
;
87 /* interface variables
89 static u8 gw16012_msb
= 0x0;
90 static u8 gw16012_control_value
= 0x0;
92 #if PARPORT_USE_PPDEV == 1
93 static int device_handle
;
96 int gw16012_execute_queue(void);
97 int gw16012_register_commands(struct command_context_s
*cmd_ctx
);
98 int gw16012_speed(int speed
);
99 int gw16012_init(void);
100 int gw16012_quit(void);
102 int gw16012_handle_parport_port_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
104 jtag_interface_t gw16012_interface
=
108 .execute_queue
= gw16012_execute_queue
,
110 .support_pathmove
= 0,
112 .speed
= gw16012_speed
,
113 .register_commands
= gw16012_register_commands
,
114 .init
= gw16012_init
,
115 .quit
= gw16012_quit
,
118 int gw16012_register_commands(struct command_context_s
*cmd_ctx
)
120 register_command(cmd_ctx
, NULL
, "parport_port", gw16012_handle_parport_port_command
,
121 COMMAND_CONFIG
, NULL
);
126 void gw16012_data(u8 value
)
128 value
= (value
& 0x7f) | gw16012_msb
;
129 gw16012_msb
^= 0x80; /* toggle MSB */
131 #ifdef _DEBUG_GW16012_IO_
132 DEBUG("%2.2x", value
);
135 #if PARPORT_USE_PPDEV == 1
136 ioctl(device_handle
, PPWDATA
, &value
);
138 #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
139 outb(gw16012_port
, value
);
141 outb(value
, gw16012_port
);
146 void gw16012_control(u8 value
)
148 if (value
!= gw16012_control_value
)
150 gw16012_control_value
= value
;
152 #ifdef _DEBUG_GW16012_IO_
153 DEBUG("%2.2x", gw16012_control_value
);
156 #if PARPORT_USE_PPDEV == 1
157 ioctl(device_handle
, PPWCONTROL
, &gw16012_control_value
);
159 #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
160 outb(gw16012_port
+ 2, gw16012_control_value
);
162 outb(gw16012_control_value
, gw16012_port
+ 2);
168 void gw16012_input(u8
*value
)
170 #if PARPORT_USE_PPDEV == 1
171 ioctl(device_handle
, PPRSTATUS
, value
);
173 *value
= inb(gw16012_port
+ 1);
176 #ifdef _DEBUG_GW16012_IO_
177 DEBUG("%2.2x", *value
);
181 /* (1) assert or (0) deassert reset lines */
182 void gw16012_reset(int trst
, int srst
)
184 DEBUG("trst: %i, srst: %i", trst
, srst
);
187 gw16012_control(0x0d);
189 gw16012_control(0x0c);
192 gw16012_control(0x0a);
194 gw16012_control(0x0b);
197 int gw16012_speed(int speed
)
203 void gw16012_end_state(state
)
205 if (tap_move_map
[state
] != -1)
209 ERROR("BUG: %i is not a valid end state", state
);
214 void gw16012_state_move(void)
217 u8 tms_scan
= TAP_MOVE(cur_state
, end_state
);
219 gw16012_control(0x0); /* single-bit mode */
221 for (i
= 0; i
< 7; i
++)
223 tms
= (tms_scan
>> i
) & 1;
224 gw16012_data(tms
<< 1); /* output next TMS bit */
227 cur_state
= end_state
;
230 void gw16012_path_move(pathmove_command_t
*cmd
)
232 int num_states
= cmd
->num_states
;
238 gw16012_control(0x0); /* single-bit mode */
239 if (tap_transitions
[cur_state
].low
== cmd
->path
[state_count
])
241 gw16012_data(0x0); /* TCK cycle with TMS low */
243 else if (tap_transitions
[cur_state
].high
== cmd
->path
[state_count
])
245 gw16012_data(0x2); /* TCK cycle with TMS high */
249 ERROR("BUG: %s -> %s isn't a valid TAP transition", tap_state_strings
[cur_state
], tap_state_strings
[cmd
->path
[state_count
]]);
253 cur_state
= cmd
->path
[state_count
];
258 end_state
= cur_state
;
261 void gw16012_runtest(int num_cycles
)
263 enum tap_state saved_end_state
= end_state
;
266 /* only do a state_move when we're not already in RTI */
267 if (cur_state
!= TAP_RTI
)
269 gw16012_end_state(TAP_RTI
);
270 gw16012_state_move();
273 for (i
= 0; i
< num_cycles
; i
++)
275 gw16012_control(0x0); /* single-bit mode */
276 gw16012_data(0x0); /* TMS cycle with TMS low */
279 gw16012_end_state(saved_end_state
);
280 if (cur_state
!= end_state
)
281 gw16012_state_move();
284 void gw16012_scan(int ir_scan
, enum scan_type type
, u8
*buffer
, int scan_size
)
286 int bits_left
= scan_size
;
288 enum tap_state saved_end_state
= end_state
;
289 u8 scan_out
, scan_in
;
291 /* only if we're not already in the correct Shift state */
292 if (!((!ir_scan
&& (cur_state
== TAP_SD
)) || (ir_scan
&& (cur_state
== TAP_SI
))))
295 gw16012_end_state(TAP_SI
);
297 gw16012_end_state(TAP_SD
);
299 gw16012_state_move();
300 gw16012_end_state(saved_end_state
);
303 while (type
== SCAN_OUT
&& ((bits_left
- 1) > 7))
305 gw16012_control(0x2); /* seven-bit mode */
306 scan_out
= buf_get_u32(buffer
, bit_count
, 7);
307 gw16012_data(scan_out
);
312 gw16012_control(0x0); /* single-bit mode */
313 while (bits_left
-- > 0)
317 scan_out
= buf_get_u32(buffer
, bit_count
, 1);
319 if (bits_left
== 0) /* last bit */
321 if ((ir_scan
&& (end_state
== TAP_SI
))
322 || (!ir_scan
&& (end_state
== TAP_SD
)))
332 gw16012_data(scan_out
| tms
);
334 if (type
!= SCAN_OUT
)
336 gw16012_input(&scan_in
);
337 buf_set_u32(buffer
, bit_count
, 1, ((scan_in
& 0x08) >> 3));
343 if (!((ir_scan
&& (end_state
== TAP_SI
)) ||
344 (!ir_scan
&& (end_state
== TAP_SD
))))
352 if (cur_state
!= end_state
)
353 gw16012_state_move();
357 int gw16012_execute_queue(void)
359 jtag_command_t
*cmd
= jtag_command_queue
; /* currently processed command */
365 /* return ERROR_OK, unless a jtag_read_buffer returns a failed check
366 * that wasn't handled by a caller-provided error handler
375 #ifdef _DEBUG_JTAG_IO_
376 DEBUG("end_state: %i", cmd
->cmd
.end_state
->end_state
);
378 if (cmd
->cmd
.end_state
->end_state
!= -1)
379 gw16012_end_state(cmd
->cmd
.end_state
->end_state
);
382 #ifdef _DEBUG_JTAG_IO_
383 DEBUG("reset trst: %i srst %i", cmd
->cmd
.reset
->trst
, cmd
->cmd
.reset
->srst
);
385 if (cmd
->cmd
.reset
->trst
== 1)
389 gw16012_reset(cmd
->cmd
.reset
->trst
, cmd
->cmd
.reset
->srst
);
392 #ifdef _DEBUG_JTAG_IO_
393 DEBUG("runtest %i cycles, end in %i", cmd
->cmd
.runtest
->num_cycles
, cmd
->cmd
.runtest
->end_state
);
395 if (cmd
->cmd
.runtest
->end_state
!= -1)
396 gw16012_end_state(cmd
->cmd
.runtest
->end_state
);
397 gw16012_runtest(cmd
->cmd
.runtest
->num_cycles
);
400 #ifdef _DEBUG_JTAG_IO_
401 DEBUG("statemove end in %i", cmd
->cmd
.statemove
->end_state
);
403 if (cmd
->cmd
.statemove
->end_state
!= -1)
404 gw16012_end_state(cmd
->cmd
.statemove
->end_state
);
405 gw16012_state_move();
408 #ifdef _DEBUG_JTAG_IO_
409 DEBUG("pathmove: %i states, end in %i", cmd
->cmd
.pathmove
->num_states
, cmd
->cmd
.pathmove
->path
[cmd
->cmd
.pathmove
->num_states
- 1]);
411 gw16012_path_move(cmd
->cmd
.pathmove
);
414 if (cmd
->cmd
.scan
->end_state
!= -1)
415 gw16012_end_state(cmd
->cmd
.scan
->end_state
);
416 scan_size
= jtag_build_buffer(cmd
->cmd
.scan
, &buffer
);
417 type
= jtag_scan_type(cmd
->cmd
.scan
);
418 #ifdef _DEBUG_JTAG_IO_
419 DEBUG("%s scan (%i) %i bit end in %i", (cmd
->cmd
.scan
->ir_scan
) ? "ir" : "dr",
420 type
, scan_size
, cmd
->cmd
.scan
->end_state
);
422 gw16012_scan(cmd
->cmd
.scan
->ir_scan
, type
, buffer
, scan_size
);
423 if (jtag_read_buffer(buffer
, cmd
->cmd
.scan
) != ERROR_OK
)
424 retval
= ERROR_JTAG_QUEUE_FAILED
;
429 #ifdef _DEBUG_JTAG_IO_
430 DEBUG("sleep %i", cmd
->cmd
.sleep
->us
);
432 jtag_sleep(cmd
->cmd
.sleep
->us
);
435 ERROR("BUG: unknown JTAG command type encountered");
444 #if PARPORT_USE_GIVEIO == 1
445 int gw16012_get_giveio_access()
448 OSVERSIONINFO version
;
450 version
.dwOSVersionInfoSize
= sizeof version
;
451 if (!GetVersionEx( &version
)) {
455 if (version
.dwPlatformId
!= VER_PLATFORM_WIN32_NT
)
458 h
= CreateFile( "\\\\.\\giveio", GENERIC_READ
, 0, NULL
, OPEN_EXISTING
, FILE_ATTRIBUTE_NORMAL
, NULL
);
459 if (h
== INVALID_HANDLE_VALUE
) {
470 int gw16012_init(void)
472 #if PARPORT_USE_PPDEV == 1
479 #if PARPORT_USE_PPDEV == 1
482 ERROR("device is already opened");
483 return ERROR_JTAG_INIT_FAILED
;
486 #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
487 DEBUG("opening /dev/ppi%d...", gw16012_port
);
489 snprintf(buffer
, 256, "/dev/ppi%d", gw16012_port
);
490 device_handle
= open(buffer
, O_WRONLY
);
492 DEBUG("opening /dev/parport%d...", gw16012_port
);
494 snprintf(buffer
, 256, "/dev/parport%d", gw16012_port
);
495 device_handle
= open(buffer
, O_WRONLY
);
499 ERROR("cannot open device. check it exists and that user read and write rights are set");
500 return ERROR_JTAG_INIT_FAILED
;
505 #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
506 i
=ioctl(device_handle
, PPCLAIM
);
509 ERROR("cannot claim device");
510 return ERROR_JTAG_INIT_FAILED
;
513 i
= PARPORT_MODE_COMPAT
;
514 i
= ioctl(device_handle
, PPSETMODE
, & i
);
517 ERROR(" cannot set compatible mode to device");
518 return ERROR_JTAG_INIT_FAILED
;
521 i
= IEEE1284_MODE_COMPAT
;
522 i
= ioctl(device_handle
, PPNEGOT
, & i
);
525 ERROR("cannot set compatible 1284 mode to device");
526 return ERROR_JTAG_INIT_FAILED
;
530 if (gw16012_port
== 0)
532 gw16012_port
= 0x378;
533 WARNING("No gw16012 port specified, using default '0x378' (LPT1)");
536 DEBUG("requesting privileges for parallel port 0x%lx...", gw16012_port
);
537 #if PARPORT_USE_GIVEIO == 1
538 if (gw16012_get_giveio_access() != 0)
539 #else /* PARPORT_USE_GIVEIO */
540 if (ioperm(gw16012_port
, 3, 1) != 0)
541 #endif /* PARPORT_USE_GIVEIO */
543 ERROR("missing privileges for direct i/o");
544 return ERROR_JTAG_INIT_FAILED
;
546 DEBUG("...privileges granted");
548 /* make sure parallel port is in right mode (clear tristate and interrupt */
549 #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
550 outb(gw16012_port
+ 2, 0x0);
552 outb(0x0, gw16012_port
+ 2);
554 #endif /* PARPORT_USE_PPDEV */
556 gw16012_input(&status_port
);
557 gw16012_msb
= (status_port
& 0x80) ^ 0x80;
559 gw16012_speed(jtag_speed
);
565 int gw16012_quit(void)
571 int gw16012_handle_parport_port_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
576 /* only if the port wasn't overwritten by cmdline */
577 if (gw16012_port
== 0)
578 gw16012_port
= strtoul(args
[0], NULL
, 0);
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)