You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

544 lines
13 KiB

  1. /***************************************************************************
  2. * Copyright (C) 2006 by Dominic Rath *
  3. * Dominic.Rath@gmx.de *
  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, see <http://www.gnu.org/licenses/>. *
  17. ***************************************************************************/
  18. #ifdef HAVE_CONFIG_H
  19. #include "config.h"
  20. #endif
  21. #include <jtag/interface.h>
  22. #include <jtag/commands.h>
  23. #if 1
  24. #define _DEBUG_GW16012_IO_
  25. #endif
  26. /* system includes */
  27. /* -ino: 060521-1036 */
  28. #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
  29. #include <machine/sysarch.h>
  30. #include <machine/cpufunc.h>
  31. #define ioperm(startport, length, enable) \
  32. 386_set_ioperm((startport), (length), (enable))
  33. #else
  34. #endif /* __FreeBSD__, __FreeBSD_kernel__ */
  35. #if PARPORT_USE_PPDEV == 1
  36. #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
  37. #include <dev/ppbus/ppi.h>
  38. #include <dev/ppbus/ppbconf.h>
  39. #define PPRSTATUS PPIGSTATUS
  40. #define PPWDATA PPISDATA
  41. #else
  42. #include <linux/parport.h>
  43. #include <linux/ppdev.h>
  44. #endif
  45. #include <fcntl.h>
  46. #include <sys/ioctl.h>
  47. #else /* not PARPORT_USE_PPDEV */
  48. #ifndef _WIN32
  49. #include <sys/io.h>
  50. #endif
  51. #endif
  52. #if PARPORT_USE_GIVEIO == 1 && IS_CYGWIN == 1
  53. #include <windows.h>
  54. #endif
  55. /* configuration */
  56. uint16_t gw16012_port;
  57. /* interface variables
  58. */
  59. static uint8_t gw16012_msb;
  60. static uint8_t gw16012_control_value;
  61. #if PARPORT_USE_PPDEV == 1
  62. static int device_handle;
  63. #endif
  64. static void gw16012_data(uint8_t value)
  65. {
  66. value = (value & 0x7f) | gw16012_msb;
  67. gw16012_msb ^= 0x80; /* toggle MSB */
  68. #ifdef _DEBUG_GW16012_IO_
  69. LOG_DEBUG("%2.2x", value);
  70. #endif
  71. #if PARPORT_USE_PPDEV == 1
  72. ioctl(device_handle, PPWDATA, &value);
  73. #else
  74. #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
  75. outb(gw16012_port, value);
  76. #else
  77. outb(value, gw16012_port);
  78. #endif
  79. #endif
  80. }
  81. static void gw16012_control(uint8_t value)
  82. {
  83. if (value != gw16012_control_value) {
  84. gw16012_control_value = value;
  85. #ifdef _DEBUG_GW16012_IO_
  86. LOG_DEBUG("%2.2x", gw16012_control_value);
  87. #endif
  88. #if PARPORT_USE_PPDEV == 1
  89. ioctl(device_handle, PPWCONTROL, &gw16012_control_value);
  90. #else
  91. #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
  92. outb(gw16012_port + 2, gw16012_control_value);
  93. #else
  94. outb(gw16012_control_value, gw16012_port + 2);
  95. #endif
  96. #endif
  97. }
  98. }
  99. static void gw16012_input(uint8_t *value)
  100. {
  101. #if PARPORT_USE_PPDEV == 1
  102. ioctl(device_handle, PPRSTATUS, value);
  103. #else
  104. *value = inb(gw16012_port + 1);
  105. #endif
  106. #ifdef _DEBUG_GW16012_IO_
  107. LOG_DEBUG("%2.2x", *value);
  108. #endif
  109. }
  110. /* (1) assert or (0) deassert reset lines */
  111. static void gw16012_reset(int trst, int srst)
  112. {
  113. LOG_DEBUG("trst: %i, srst: %i", trst, srst);
  114. if (trst == 0)
  115. gw16012_control(0x0d);
  116. else if (trst == 1)
  117. gw16012_control(0x0c);
  118. if (srst == 0)
  119. gw16012_control(0x0a);
  120. else if (srst == 1)
  121. gw16012_control(0x0b);
  122. }
  123. static void gw16012_end_state(tap_state_t state)
  124. {
  125. if (tap_is_state_stable(state))
  126. tap_set_end_state(state);
  127. else {
  128. LOG_ERROR("BUG: %i is not a valid end state", state);
  129. exit(-1);
  130. }
  131. }
  132. static void gw16012_state_move(void)
  133. {
  134. int i = 0, tms = 0;
  135. uint8_t tms_scan = tap_get_tms_path(tap_get_state(), tap_get_end_state());
  136. int tms_count = tap_get_tms_path_len(tap_get_state(), tap_get_end_state());
  137. gw16012_control(0x0); /* single-bit mode */
  138. for (i = 0; i < tms_count; i++) {
  139. tms = (tms_scan >> i) & 1;
  140. gw16012_data(tms << 1); /* output next TMS bit */
  141. }
  142. tap_set_state(tap_get_end_state());
  143. }
  144. static void gw16012_path_move(struct pathmove_command *cmd)
  145. {
  146. int num_states = cmd->num_states;
  147. int state_count;
  148. state_count = 0;
  149. while (num_states) {
  150. gw16012_control(0x0); /* single-bit mode */
  151. if (tap_state_transition(tap_get_state(), false) == cmd->path[state_count])
  152. gw16012_data(0x0); /* TCK cycle with TMS low */
  153. else if (tap_state_transition(tap_get_state(), true) == cmd->path[state_count])
  154. gw16012_data(0x2); /* TCK cycle with TMS high */
  155. else {
  156. LOG_ERROR("BUG: %s -> %s isn't a valid TAP transition",
  157. tap_state_name(tap_get_state()), tap_state_name(cmd->path[state_count]));
  158. exit(-1);
  159. }
  160. tap_set_state(cmd->path[state_count]);
  161. state_count++;
  162. num_states--;
  163. }
  164. tap_set_end_state(tap_get_state());
  165. }
  166. static void gw16012_runtest(int num_cycles)
  167. {
  168. tap_state_t saved_end_state = tap_get_end_state();
  169. int i;
  170. /* only do a state_move when we're not already in IDLE */
  171. if (tap_get_state() != TAP_IDLE) {
  172. gw16012_end_state(TAP_IDLE);
  173. gw16012_state_move();
  174. }
  175. for (i = 0; i < num_cycles; i++) {
  176. gw16012_control(0x0); /* single-bit mode */
  177. gw16012_data(0x0); /* TMS cycle with TMS low */
  178. }
  179. gw16012_end_state(saved_end_state);
  180. if (tap_get_state() != tap_get_end_state())
  181. gw16012_state_move();
  182. }
  183. static void gw16012_scan(bool ir_scan, enum scan_type type, uint8_t *buffer, int scan_size)
  184. {
  185. int bits_left = scan_size;
  186. int bit_count = 0;
  187. tap_state_t saved_end_state = tap_get_end_state();
  188. uint8_t scan_out, scan_in;
  189. /* only if we're not already in the correct Shift state */
  190. if (!((!ir_scan && (tap_get_state() == TAP_DRSHIFT)) ||
  191. (ir_scan && (tap_get_state() == TAP_IRSHIFT)))) {
  192. if (ir_scan)
  193. gw16012_end_state(TAP_IRSHIFT);
  194. else
  195. gw16012_end_state(TAP_DRSHIFT);
  196. gw16012_state_move();
  197. gw16012_end_state(saved_end_state);
  198. }
  199. while (type == SCAN_OUT && ((bits_left - 1) > 7)) {
  200. gw16012_control(0x2); /* seven-bit mode */
  201. scan_out = buf_get_u32(buffer, bit_count, 7);
  202. gw16012_data(scan_out);
  203. bit_count += 7;
  204. bits_left -= 7;
  205. }
  206. gw16012_control(0x0); /* single-bit mode */
  207. while (bits_left-- > 0) {
  208. uint8_t tms = 0;
  209. scan_out = buf_get_u32(buffer, bit_count, 1);
  210. if (bits_left == 0) /* last bit */ {
  211. if ((ir_scan && (tap_get_end_state() == TAP_IRSHIFT))
  212. || (!ir_scan && (tap_get_end_state() == TAP_DRSHIFT)))
  213. tms = 0;
  214. else
  215. tms = 2;
  216. }
  217. gw16012_data(scan_out | tms);
  218. if (type != SCAN_OUT) {
  219. gw16012_input(&scan_in);
  220. buf_set_u32(buffer, bit_count, 1, ((scan_in & 0x08) >> 3));
  221. }
  222. bit_count++;
  223. }
  224. if (!((ir_scan && (tap_get_end_state() == TAP_IRSHIFT)) ||
  225. (!ir_scan && (tap_get_end_state() == TAP_DRSHIFT)))) {
  226. gw16012_data(0x0);
  227. if (ir_scan)
  228. tap_set_state(TAP_IRPAUSE);
  229. else
  230. tap_set_state(TAP_DRPAUSE);
  231. if (tap_get_state() != tap_get_end_state())
  232. gw16012_state_move();
  233. }
  234. }
  235. static int gw16012_execute_queue(void)
  236. {
  237. struct jtag_command *cmd = jtag_command_queue; /* currently processed command */
  238. int scan_size;
  239. enum scan_type type;
  240. uint8_t *buffer;
  241. int retval;
  242. /* return ERROR_OK, unless a jtag_read_buffer returns a failed check
  243. * that wasn't handled by a caller-provided error handler
  244. */
  245. retval = ERROR_OK;
  246. while (cmd) {
  247. switch (cmd->type) {
  248. case JTAG_RESET:
  249. #ifdef _DEBUG_JTAG_IO_
  250. LOG_DEBUG("reset trst: %i srst %i", cmd->cmd.reset->trst, cmd->cmd.reset->srst);
  251. #endif
  252. if (cmd->cmd.reset->trst == 1)
  253. tap_set_state(TAP_RESET);
  254. gw16012_reset(cmd->cmd.reset->trst, cmd->cmd.reset->srst);
  255. break;
  256. case JTAG_RUNTEST:
  257. #ifdef _DEBUG_JTAG_IO_
  258. LOG_DEBUG("runtest %i cycles, end in %i", cmd->cmd.runtest->num_cycles,
  259. cmd->cmd.runtest->end_state);
  260. #endif
  261. gw16012_end_state(cmd->cmd.runtest->end_state);
  262. gw16012_runtest(cmd->cmd.runtest->num_cycles);
  263. break;
  264. case JTAG_TLR_RESET:
  265. #ifdef _DEBUG_JTAG_IO_
  266. LOG_DEBUG("statemove end in %i", cmd->cmd.statemove->end_state);
  267. #endif
  268. gw16012_end_state(cmd->cmd.statemove->end_state);
  269. gw16012_state_move();
  270. break;
  271. case JTAG_PATHMOVE:
  272. #ifdef _DEBUG_JTAG_IO_
  273. LOG_DEBUG("pathmove: %i states, end in %i", cmd->cmd.pathmove->num_states,
  274. cmd->cmd.pathmove->path[cmd->cmd.pathmove->num_states - 1]);
  275. #endif
  276. gw16012_path_move(cmd->cmd.pathmove);
  277. break;
  278. case JTAG_SCAN:
  279. gw16012_end_state(cmd->cmd.scan->end_state);
  280. scan_size = jtag_build_buffer(cmd->cmd.scan, &buffer);
  281. type = jtag_scan_type(cmd->cmd.scan);
  282. #ifdef _DEBUG_JTAG_IO_
  283. LOG_DEBUG("%s scan (%i) %i bit end in %i", (cmd->cmd.scan->ir_scan) ? "ir" : "dr",
  284. type, scan_size, cmd->cmd.scan->end_state);
  285. #endif
  286. gw16012_scan(cmd->cmd.scan->ir_scan, type, buffer, scan_size);
  287. if (jtag_read_buffer(buffer, cmd->cmd.scan) != ERROR_OK)
  288. retval = ERROR_JTAG_QUEUE_FAILED;
  289. if (buffer)
  290. free(buffer);
  291. break;
  292. case JTAG_SLEEP:
  293. #ifdef _DEBUG_JTAG_IO_
  294. LOG_DEBUG("sleep %i", cmd->cmd.sleep->us);
  295. #endif
  296. jtag_sleep(cmd->cmd.sleep->us);
  297. break;
  298. default:
  299. LOG_ERROR("BUG: unknown JTAG command type encountered");
  300. exit(-1);
  301. }
  302. cmd = cmd->next;
  303. }
  304. return retval;
  305. }
  306. #if PARPORT_USE_GIVEIO == 1
  307. static int gw16012_get_giveio_access(void)
  308. {
  309. HANDLE h;
  310. OSVERSIONINFO version;
  311. version.dwOSVersionInfoSize = sizeof version;
  312. if (!GetVersionEx(&version)) {
  313. errno = EINVAL;
  314. return -1;
  315. }
  316. if (version.dwPlatformId != VER_PLATFORM_WIN32_NT)
  317. return 0;
  318. h = CreateFile("\\\\.\\giveio", GENERIC_READ, 0, NULL, OPEN_EXISTING,
  319. FILE_ATTRIBUTE_NORMAL, NULL);
  320. if (h == INVALID_HANDLE_VALUE) {
  321. errno = ENODEV;
  322. return -1;
  323. }
  324. CloseHandle(h);
  325. return 0;
  326. }
  327. #endif
  328. #if PARPORT_USE_PPDEV == 1
  329. #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
  330. #define GW16012_PPDEV_NAME "ppi"
  331. static int gw16012_init_ioctls(void)
  332. {
  333. int temp = 0;
  334. temp = ioctl(device_handle, PPCLAIM);
  335. if (temp < 0) {
  336. LOG_ERROR("cannot claim device");
  337. return ERROR_JTAG_INIT_FAILED;
  338. }
  339. temp = PARPORT_MODE_COMPAT;
  340. temp = ioctl(device_handle, PPSETMODE, &temp);
  341. if (temp < 0) {
  342. LOG_ERROR(" cannot set compatible mode to device");
  343. return ERROR_JTAG_INIT_FAILED;
  344. }
  345. temp = IEEE1284_MODE_COMPAT;
  346. temp = ioctl(device_handle, PPNEGOT, &temp);
  347. if (temp < 0) {
  348. LOG_ERROR("cannot set compatible 1284 mode to device");
  349. return ERROR_JTAG_INIT_FAILED;
  350. }
  351. return ERROR_OK;
  352. }
  353. #else
  354. #define GW16012_PPDEV_NAME "parport"
  355. static int gw16012_init_ioctls(void)
  356. {
  357. return ERROR_OK;
  358. }
  359. #endif /* defined(__FreeBSD__) || defined(__FreeBSD_kernel__) */
  360. static int gw16012_init_device(void)
  361. {
  362. const char *device_name = GW16012_PPDEV_NAME;
  363. char buffer[256];
  364. if (device_handle > 0) {
  365. LOG_ERROR("device is already opened");
  366. return ERROR_JTAG_INIT_FAILED;
  367. }
  368. snprintf(buffer, 256, "/dev/%s%d", device_name, gw16012_port);
  369. LOG_DEBUG("opening %s...", buffer);
  370. device_handle = open(buffer, O_WRONLY);
  371. if (device_handle < 0) {
  372. LOG_ERROR("cannot open device. check it exists and that user read and write rights are set");
  373. return ERROR_JTAG_INIT_FAILED;
  374. }
  375. LOG_DEBUG("...open");
  376. if (gw16012_init_ioctls() != ERROR_OK)
  377. return ERROR_JTAG_INIT_FAILED;
  378. return ERROR_OK;
  379. }
  380. #else /* PARPORT_USE_PPDEV */
  381. static int gw16012_init_device(void)
  382. {
  383. if (gw16012_port == 0) {
  384. gw16012_port = 0x378;
  385. LOG_WARNING("No gw16012 port specified, using default '0x378' (LPT1)");
  386. }
  387. LOG_DEBUG("requesting privileges for parallel port 0x%lx...", (long unsigned)(gw16012_port));
  388. #if PARPORT_USE_GIVEIO == 1
  389. if (gw16012_get_giveio_access() != 0) {
  390. #else /* PARPORT_USE_GIVEIO */
  391. if (ioperm(gw16012_port, 3, 1) != 0) {
  392. #endif /* PARPORT_USE_GIVEIO */
  393. LOG_ERROR("missing privileges for direct i/o");
  394. return ERROR_JTAG_INIT_FAILED;
  395. }
  396. LOG_DEBUG("...privileges granted");
  397. /* make sure parallel port is in right mode (clear tristate and interrupt */
  398. #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
  399. outb(gw16012_port + 2, 0x0);
  400. #else
  401. outb(0x0, gw16012_port + 2);
  402. #endif
  403. return ERROR_OK;
  404. }
  405. #endif /* PARPORT_USE_PPDEV */
  406. static int gw16012_init(void)
  407. {
  408. uint8_t status_port;
  409. if (gw16012_init_device() != ERROR_OK)
  410. return ERROR_JTAG_INIT_FAILED;
  411. gw16012_input(&status_port);
  412. gw16012_msb = (status_port & 0x80) ^ 0x80;
  413. gw16012_reset(0, 0);
  414. return ERROR_OK;
  415. }
  416. static int gw16012_quit(void)
  417. {
  418. return ERROR_OK;
  419. }
  420. COMMAND_HANDLER(gw16012_handle_parport_port_command)
  421. {
  422. if (CMD_ARGC == 1) {
  423. /* only if the port wasn't overwritten by cmdline */
  424. if (gw16012_port == 0)
  425. COMMAND_PARSE_NUMBER(u16, CMD_ARGV[0], gw16012_port);
  426. else {
  427. LOG_ERROR("The parport port was already configured!");
  428. return ERROR_FAIL;
  429. }
  430. }
  431. command_print(CMD_CTX, "parport port = %u", gw16012_port);
  432. return ERROR_OK;
  433. }
  434. static const struct command_registration gw16012_command_handlers[] = {
  435. {
  436. .name = "parport_port",
  437. .handler = gw16012_handle_parport_port_command,
  438. .mode = COMMAND_CONFIG,
  439. .help = "Display the address of the I/O port (e.g. 0x378) "
  440. "or the number of the '/dev/parport' device used. "
  441. "If a parameter is provided, first change that port.",
  442. .usage = "[port_number]",
  443. },
  444. COMMAND_REGISTRATION_DONE
  445. };
  446. struct jtag_interface gw16012_interface = {
  447. .name = "gw16012",
  448. .commands = gw16012_command_handlers,
  449. .init = gw16012_init,
  450. .quit = gw16012_quit,
  451. .execute_queue = gw16012_execute_queue,
  452. };