OpenCores
URL https://opencores.org/ocsvn/adv_debug_sys/adv_debug_sys/trunk

Subversion Repositories adv_debug_sys

[/] [adv_debug_sys/] [trunk/] [Software/] [adv_jtag_bridge/] [cable_common.c] - Blame information for rev 14

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 4 nyawn
/* cable_common.c -- Interface to the low-level cable drivers
2
   Copyright (C) 2001 Marko Mlinar, markom@opencores.org
3
   Copyright (C) 2004 György Jeney, nog@sdf.lonestar.org
4
   Copyright (C) 2008 Nathan Yawn, nathan.yawn@opencores.org
5
 
6
   This program is free software; you can redistribute it and/or modify
7
   it under the terms of the GNU General Public License as published by
8
   the Free Software Foundation; either version 2 of the License, or
9
   (at your option) any later version.
10
 
11
   This program is distributed in the hope that it will be useful,
12
   but WITHOUT ANY WARRANTY; without even the implied warranty of
13
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
   GNU General Public License for more details.
15
 
16
   You should have received a copy of the GNU General Public License
17
   along with this program; if not, write to the Free Software
18
   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
19
 
20
 
21
 
22
#include <stdio.h>
23
#include <string.h>
24
 
25
 
26
#include "cable_common.h"
27
#include "cable_parallel.h"
28
#include "cable_sim.h"
29
#include "cable_usbblaster.h"
30
#include "cable_xpc_dlc9.h"
31
#include "errcodes.h"
32
 
33
#define debug(...)   //fprintf(stderr, __VA_ARGS__ )
34
 
35 14 nyawn
static struct jtag_cable {
36 4 nyawn
  const char *name;
37
  int (*inout_func)(uint8_t, uint8_t *);
38
  int (*out_func)(uint8_t);
39
  int (*init_func)();
40
  void (*wait_func)();
41
  int (*opt_func)(int, char *);
42
  int (*bit_out_func)(uint8_t);
43
  int (*bit_inout_func)(uint8_t, uint8_t *);
44
  int (*stream_out_func)(uint32_t *, int, int);
45
  int (*stream_inout_func)(uint32_t *, uint32_t *, int, int);
46
  const char *opts;
47
  const char *help;
48
} jtag_cables[] = {
49
  { "rtl_sim",
50
    cable_rtl_sim_inout,
51
    cable_rtl_sim_out,
52
    cable_rtl_sim_init,
53
    NULL,
54
    cable_rtl_sim_opt,
55
    cable_common_write_bit,
56
    cable_common_read_write_bit,
57
    cable_common_write_stream,
58
    cable_common_read_stream,
59
    "d:",
60
    "-d [directory] Directory in which gdb_in.dat/gdb_out.dat may be found\n" },
61
  { "vpi",
62
    cable_vpi_inout,
63
    cable_vpi_out,
64
    cable_vpi_init,
65
    cable_vpi_wait,
66
    cable_vpi_opt,
67
    cable_common_write_bit,
68
    cable_common_read_write_bit,
69
    cable_common_write_stream,
70
    cable_common_read_stream,
71
    "s:p:",
72
    "-p [port] Port number that the VPI module is listening on\n\t-s [server] Server that the VPI module is running on\n" },
73
  { "xpc3",
74
    cable_xpc3_inout,
75
    cable_xpc3_out,
76
    cable_parallel_init,
77
    cable_parallel_phys_wait,
78
    cable_parallel_opt,
79
    cable_common_write_bit,
80
    cable_common_read_write_bit,
81
    cable_common_write_stream,
82
    cable_common_read_stream,
83
    "p:",
84
    "-p [port] Which port to use when communicating with the parport hardware (eg. 0x378)\n" },
85
  { "xess",
86
    cable_xess_inout,
87
    cable_xess_out,
88
    cable_parallel_init,
89
    cable_parallel_phys_wait,
90
    cable_parallel_opt,
91
    cable_common_write_bit,
92
    cable_common_read_write_bit,
93
    cable_common_write_stream,
94
    cable_common_read_stream,
95
    "p:",
96
    "-p [port] Which port to use when communicating with the parport hardware (eg. 0x378)\n" },
97
  { "usbblaster",
98
    cable_usbblaster_inout,
99
    cable_usbblaster_out,
100
    cable_usbblaster_init,
101
    NULL,
102
    cable_usbblaster_opt,
103
    cable_common_write_bit,
104
    cable_common_read_write_bit,
105
    cable_usbblaster_write_stream,
106
    cable_usbblaster_read_stream,
107
    "",
108
    "no options\n" },
109
  { "xpc_usb",
110
    cable_xpcusb_inout,
111
    cable_xpcusb_out,
112
    cable_xpcusb_init,
113
    NULL,
114
    cable_xpcusb_opt,
115
    cable_common_write_bit,
116
    cable_xpcusb_read_write_bit,
117
    cable_common_write_stream,
118
    cable_common_read_stream,
119
    "",
120
    "no options\n" },
121
  { NULL, NULL, NULL, NULL } };
122
 
123
static struct jtag_cable *jtag_cable_in_use = NULL; /* The currently selected cable */
124
 
125
 
126
/////////////////////////////////////////////////////////////////////////////////////
127
// Cable subsystem / init functions
128
 
129
 
130
/* Selects a cable for use */
131
int cable_select(const char *cable)
132
{
133
  int i;
134
 
135
  for(i = 0; jtag_cables[i].name; i++) {
136
    if(!strcmp(cable, jtag_cables[i].name)) {
137
      jtag_cable_in_use = &jtag_cables[i];
138
      return APP_ERR_NONE;
139
    }
140
  }
141
 
142
  return APP_ERR_CABLE_INVALID;
143
}
144
 
145
/* Calls the init function of the cable
146
 */
147
int cable_init()
148
{
149
  return jtag_cable_in_use->init_func();
150
}
151
 
152
/* Parses command-line options specific to the selected cable */
153
int cable_parse_opt(int c, char *str)
154
{
155
  return jtag_cable_in_use->opt_func(c, str);
156
}
157
 
158
const char *cable_get_args()
159
{
160
  if(jtag_cable_in_use != NULL)
161
    return jtag_cable_in_use->opts;
162
  else
163
    return NULL;
164
}
165
 
166
/* Prints a (short) useage message for each available cable */
167
void cable_print_help()
168
{
169
  int i;
170
  printf("Available cables: ");
171
 
172
  for(i = 0; jtag_cables[i].name; i++) {
173
    if(i)
174
      printf(", ");
175 14 nyawn
    printf("%s", jtag_cables[i].name);
176 4 nyawn
  }
177
 
178
  printf("\n\nOptions availible for the cables:\n");
179
  for(i = 0; jtag_cables[i].name; i++) {
180
    if(!jtag_cables[i].help)
181
      continue;
182
    printf("  %s:\n    %s", jtag_cables[i].name, jtag_cables[i].help);
183
  }
184
}
185
 
186
 
187
/////////////////////////////////////////////////////////////////////////////////
188
// Cable API Functions
189
 
190
int cable_write_stream(uint32_t *stream, int len_bits, int set_last_bit) {
191
  return jtag_cable_in_use->stream_out_func(stream, len_bits, set_last_bit);
192
}
193
 
194
int cable_read_write_stream(uint32_t *outstream, uint32_t *instream, int len_bits, int set_last_bit) {
195
  return jtag_cable_in_use->stream_inout_func(outstream, instream, len_bits, set_last_bit);
196
}
197
 
198
int cable_write_bit(uint8_t packet) {
199
  return jtag_cable_in_use->bit_out_func(packet);
200
}
201
 
202
int cable_read_write_bit(uint8_t packet_out, uint8_t *bit_in) {
203
  return jtag_cable_in_use->bit_inout_func(packet_out, bit_in);
204
}
205
 
206
 
207
/////////////////////////////////////////////////////////////////////////////////////
208
// Common functions which may or may not be used by individual drivers
209
 
210
 
211
/* Note that these make no assumption as to the starting state of the clock,
212
 * and they leave the clock HIGH.  But, these need to interface with other routines (like
213
 * the byte-shift mode in the USB-Blaster), which begin by assuming that a new
214
 * data bit is available at TDO, which only happens after a FALLING edge of TCK.
215
 * So, routines which assume new data is available will need to start by dropping
216
 * the clock.
217
 */
218
int cable_common_write_bit(uint8_t packet) {
219
  uint8_t data = TRST_BIT;  // TRST is active low, don't clear unless /set/ in 'packet'
220
  int err = APP_ERR_NONE;
221
 
222
  /* Write data, drop clock */
223
  if(packet & TDO) data |= TDI_BIT;
224
  if(packet & TMS) data |= TMS_BIT;
225
  if(packet & TRST) data &= ~TRST_BIT;
226
 
227
  err |= jtag_cable_in_use->out_func(data);
228
  if (jtag_cable_in_use->wait_func != NULL) jtag_cable_in_use->wait_func();
229
 
230
  /* raise clock, to do write */
231
  err |= jtag_cable_in_use->out_func(data | TCLK_BIT);
232
   if (jtag_cable_in_use->wait_func != NULL) jtag_cable_in_use->wait_func();
233
 
234
  return err;
235
}
236
 
237
int cable_common_read_write_bit(uint8_t packet_out, uint8_t *bit_in) {
238
  uint8_t data = TRST_BIT;  //  TRST is active low, don't clear unless /set/ in 'packet'
239
  int err = APP_ERR_NONE;
240
 
241
  /* Write data, drop clock */
242
  if(packet_out & TDO) data |= TDI_BIT;
243
  if(packet_out & TMS) data |= TMS_BIT;
244
  if(packet_out & TRST) data &= ~TRST_BIT;
245
 
246
  err |= jtag_cable_in_use->out_func(data);  // drop the clock to make data available, set the out data
247
  if (jtag_cable_in_use->wait_func != NULL) jtag_cable_in_use->wait_func();
248
  err |= jtag_cable_in_use->inout_func((data | TCLK_BIT), bit_in);  // read in bit, clock high for out bit.
249
  if (jtag_cable_in_use->wait_func != NULL) jtag_cable_in_use->wait_func();
250
 
251
  return err;
252
}
253
 
254
 
255
/* Writes bitstream via bit-bang. Can be used by any driver which does not have a high-speed transfer function.
256
 * Transfers LSB to MSB of stream[0], then LSB to MSB of stream[1], etc.
257
 */
258
int cable_common_write_stream(uint32_t *stream, int len_bits, int set_last_bit) {
259
  int i;
260
  int index = 0;
261
  int bits_this_index = 0;
262
  uint8_t out;
263
  int err = APP_ERR_NONE;
264
 
265
  debug("writeSrrm%d(", len_bits);
266
  for(i = 0; i < len_bits - 1; i++) {
267
    out = (stream[index] >> bits_this_index) & 1;
268
    err |= cable_write_bit(out);
269
    debug("%i", out);
270
    bits_this_index++;
271
    if(bits_this_index >= 32) {
272
      index++;
273
      bits_this_index = 0;
274
    }
275
  }
276
 
277
  out = (stream[index] >>(len_bits - 1)) & 0x1;
278
  if(set_last_bit) out |= TMS;
279
  err |= cable_write_bit(out);
280
  debug("%i)\n", out);
281
  return err;
282
}
283
 
284
/* Gets bitstream via bit-bang.  Can be used by any driver which does not have a high-speed transfer function.
285
 * Transfers LSB to MSB of stream[0], then LSB to MSB of stream[1], etc.
286
 */
287
int cable_common_read_stream(uint32_t *outstream, uint32_t *instream, int len_bits, int set_last_bit) {
288
  int i;
289
  int index = 0;
290
  int bits_this_index = 0;
291
  uint8_t inval, outval;
292
  int err = APP_ERR_NONE;
293
 
294
  instream[0] = 0;
295
 
296
  debug("readStrm%d(", len_bits);
297
  for(i = 0; i < (len_bits - 1); i++) {
298
    outval = (outstream[index] >> bits_this_index) & 0x1;
299
    err |= cable_read_write_bit(outval, &inval);
300
    debug("%i", inval);
301
    instream[index] |= (inval << bits_this_index);
302
    bits_this_index++;
303
    if(bits_this_index >= 32) {
304
      index++;
305
      bits_this_index = 0;
306
      instream[index] = 0;  // It's safe to do this, because there's always at least one more bit
307
    }
308
  }
309
 
310
  if (set_last_bit)
311
    outval = ((outstream[index] >> (len_bits - 1)) & 1) | TMS;
312
  else
313
    outval = (outstream[index] >> (len_bits - 1)) & 1;
314
 
315
  err |= cable_read_write_bit(outval, &inval);
316
  debug("%i", inval);
317
  instream[index] |= (inval << bits_this_index);
318
 
319
  debug(") = 0x%lX\n", instream[0]);
320
 
321
  return err;
322
}
323
 
324
 
325
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.