summaryrefslogtreecommitdiffstats
path: root/fpga/xilinx
diff options
context:
space:
mode:
authorTimothy Pearson <kb9vqf@pearsoncomputing.net>2012-10-04 17:03:18 -0500
committerTimothy Pearson <kb9vqf@pearsoncomputing.net>2012-10-04 17:03:18 -0500
commit9c6d284d49dd8849e3c0ebb614df72aa96f910f9 (patch)
tree8ba1bea20903f5da425b102708c3af2c5b1d334c /fpga/xilinx
parent7643298424eaca1c10dd7ed577b3b77246bbf441 (diff)
downloadulab-9c6d284d49dd8849e3c0ebb614df72aa96f910f9.tar.gz
ulab-9c6d284d49dd8849e3c0ebb614df72aa96f910f9.zip
Initial rpi jtag support
Diffstat (limited to 'fpga/xilinx')
-rw-r--r--fpga/xilinx/programmer/svfplayer/xsvf-rpi.c199
1 files changed, 93 insertions, 106 deletions
diff --git a/fpga/xilinx/programmer/svfplayer/xsvf-rpi.c b/fpga/xilinx/programmer/svfplayer/xsvf-rpi.c
index c46e4d7..45d8c78 100644
--- a/fpga/xilinx/programmer/svfplayer/xsvf-rpi.c
+++ b/fpga/xilinx/programmer/svfplayer/xsvf-rpi.c
@@ -1,6 +1,7 @@
/*
* Lib(X)SVF - A library for implementing SVF and XSVF JTAG players
*
+ * Copyright (C) 2012 Timothy Pearson <kb9vqf@pearsoncomputing.net>
* Copyright (C) 2009 RIEGL Research ForschungsGmbH
* Copyright (C) 2009 Clifford Wolf <clifford@clifford.at>
*
@@ -30,104 +31,127 @@
/** BEGIN: Low-Level I/O Implementation **/
-#ifdef XSVFTOOL_RLMS_VLINE
-
-// Simple example with MPC8349E GPIO pins
-// (RIEGL LMS V-Line motherboard)
+// Raspberry PI GPIO driver
+// TMS: 18
+// TDI: 23
+// TDO: 24
+// TCK: 25
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/mman.h>
#include <fcntl.h>
-#define IO_PORT_ADDR 0xE0000C00
+#define BCM2708_PERI_BASE 0x20000000
+#define GPIO_BASE (BCM2708_PERI_BASE + 0x200000) /* GPIO controller */
-struct io_layout {
- unsigned long tdi:1;
- unsigned long tdo:1;
- unsigned long tms:1;
- unsigned long tck:1;
- unsigned long reserved:28;
-};
+#define PAGE_SIZE (4*1024)
+#define BLOCK_SIZE (4*1024)
+
+int mem_fd;
+char *gpio_mem, *gpio_map;
+char *spi0_mem, *spi0_map;
+
+// I/O access
+volatile unsigned *gpio;
-static volatile struct io_layout *io_direction;
-static volatile struct io_layout *io_opendrain;
-static volatile struct io_layout *io_data;
+// GPIO setup macros. Always use INP_GPIO(x) before using OUT_GPIO(x) or SET_GPIO_ALT(x,y)
+#define INP_GPIO(g) *(gpio+((g)/10)) &= ~(7<<(((g)%10)*3))
+#define OUT_GPIO(g) *(gpio+((g)/10)) |= (1<<(((g)%10)*3))
+#define SET_GPIO_ALT(g,a) *(gpio+(((g)/10))) |= (((a)<=3?(a)+4:(a)==4?3:2)<<(((g)%10)*3))
+
+#define GPIO_SET *(gpio+7) // sets bits which are 1 ignores bits which are 0
+#define GPIO_CLR *(gpio+10) // clears bits which are 1 ignores bits which are 0
+
+#define GPLEV0 *(gpio+13)
static void io_setup(void)
{
- /* open /dev/mem device file */
- int fd = open("/dev/mem", O_RDWR);
- if (fd < 0) {
- fprintf(stderr, "Can't open /dev/mem: %s\n", strerror(errno));
- exit(1);
+ /* open /dev/mem */
+ if ((mem_fd = open("/dev/mem", O_RDWR|O_SYNC) ) < 0) {
+ printf("can't open /dev/mem \n");
+ exit (-1);
}
-
- /* calculate offsets to page and within page */
- unsigned long psize = getpagesize();
- unsigned long off_inpage = IO_PORT_ADDR % psize;
- unsigned long off_topage = IO_PORT_ADDR - off_inpage;
- unsigned long mapsize = off_inpage + sizeof(struct io_layout) * 3;
-
- /* map it into logical memory */
- void *io_addr_map = mmap(0, mapsize, PROT_WRITE, MAP_SHARED, fd, off_topage);
- if (io_addr_map == MAP_FAILED) {
- fprintf(stderr, "Can't map physical memory: %s\n", strerror(errno));
- exit(1);
+
+ /* mmap GPIO */
+
+ // Allocate MAP block
+ if ((gpio_mem = malloc(BLOCK_SIZE + (PAGE_SIZE-1))) == NULL) {
+ printf("allocation error \n");
+ exit (-1);
}
+
+ // Make sure pointer is on 4K boundary
+ if ((unsigned long)gpio_mem % PAGE_SIZE) {
+ gpio_mem += PAGE_SIZE - ((unsigned long)gpio_mem % PAGE_SIZE);
+ }
+
+ // Now map it
+ gpio_map = (unsigned char *)mmap(
+ (caddr_t)gpio_mem,
+ BLOCK_SIZE,
+ PROT_READ|PROT_WRITE,
+ MAP_SHARED|MAP_FIXED,
+ mem_fd,
+ GPIO_BASE
+ );
+
+ if ((long)gpio_map < 0) {
+ printf("mmap error %d\n", (int)gpio_map);
+ exit (-1);
+ }
+
+ // Always use volatile pointer!
+ gpio = (volatile unsigned *)gpio_map;
+
+ // Set GPIO pins 18, 23, 25 to output
+ INP_GPIO(18); // must use INP_GPIO before we can use OUT_GPIO
+ INP_GPIO(23); // must use INP_GPIO before we can use OUT_GPIO
+ INP_GPIO(25); // must use INP_GPIO before we can use OUT_GPIO
- /* calculate register addresses */
- io_direction = io_addr_map + off_inpage;
- io_opendrain = io_addr_map + off_inpage + 4;
- io_data = io_addr_map + off_inpage + 8;
-
- /* set direction reg */
- io_direction->tms = 1;
- io_direction->tck = 1;
- io_direction->tdo = 0;
- io_direction->tdi = 1;
-
- /* set open drain reg */
- io_opendrain->tms = 0;
- io_opendrain->tck = 0;
- io_opendrain->tdo = 0;
- io_opendrain->tdi = 0;
-
-#ifdef HAVE_TRST
- /* for boards with TRST, must be driven high */
- io_data->trst = 1;
- io_direction->trst = 1;
- io_opendrain->trst = 0;
-#endif
+ OUT_GPIO(18); // output
+ OUT_GPIO(23); // output
+ INP_GPIO(24); // input
+ OUT_GPIO(25); // output
}
static void io_shutdown(void)
{
- /* set all to z-state */
- io_direction->tms = 0;
- io_direction->tck = 0;
- io_direction->tdo = 0;
- io_direction->tdi = 0;
-
-#ifdef HAVE_TRST
- /* for boards with TRST, assuming there is a pull-down resistor */
- io_direction->trst = 0;
-#endif
+ INP_GPIO(18);
+ INP_GPIO(23);
+ INP_GPIO(24);
+ INP_GPIO(25);
}
static void io_tms(int val)
{
- io_data->tms = val;
+ if (val) {
+ GPIO_SET = 1<<18;
+ }
+ else {
+ GPIO_CLR = 1<<18;
+ }
}
static void io_tdi(int val)
{
- io_data->tdi = val;
+ if (val) {
+ GPIO_SET = 1<<23;
+ }
+ else {
+ GPIO_CLR = 1<<23;
+ }
}
static void io_tck(int val)
{
- io_data->tck = val;
+ if (val) {
+ GPIO_SET = 1<<25;
+ }
+ else {
+ GPIO_CLR = 1<<25;
+ }
+
// usleep(1);
}
@@ -143,46 +167,9 @@ static void io_trst(int val)
static int io_tdo()
{
- return io_data->tdo ? 1 : 0;
-}
-
-#else
-
-static void io_setup(void)
-{
-}
-
-static void io_shutdown(void)
-{
+ return (GPLEV0 & (1<<24)) ? 1 : 0;
}
-static void io_tms(int val)
-{
-}
-
-static void io_tdi(int val)
-{
-}
-
-static void io_tck(int val)
-{
-}
-
-static void io_sck(int val)
-{
-}
-
-static void io_trst(int val)
-{
-}
-
-static int io_tdo()
-{
- return -1;
-}
-
-#endif
-
/** END: Low-Level I/O Implementation **/