summaryrefslogtreecommitdiffstats
path: root/c/src/lib/libbsp/sparc/shared/spw/grspw_rasta.c
blob: 6cd5698f44ea3c5b7dd7da85b2e44a9a7a514570 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
/* Select PCI driver */
#define GRSPW_PCI

#undef GRSPW_MAXDEVS
#undef DEBUG_SPACEWIRE_ONOFF
/*#define DEBUG_SPACEWIRE_ONOFF*/
/*
 * If USE_AT697_RAM is defined the RAM on the AT697 board will be used for DMA buffers (but rx message queue is always in AT697 ram).
 * USE_AT697_DMA specifies whether the messages will be fetched using DMA or PIO.
 *
 * RASTA_PCI_BASE is the base address of the GRPCI AHB slave
 *
  */

#define USE_AT697_RAM              1
#define USE_AT697_DMA              0
#define RASTA_PCI_BASE             0xe0000000
#define GRSPW_RASTA_MEM_OFF        0x21000

/* Make GRSPW driver use malloced or static memory
 */
#ifdef USE_AT697_RAM
#undef GRSPW_STATIC_MEM
#else
#define GRSPW_STATIC_MEM
#define GRSPW_CALC_MEMOFS(maxcores,corenum,ptr_mem_base,ptr_mem_end,ptr_bdtable_base) \
	grspw_rasta_calc_memoffs((maxcores),(corenum),(ptr_mem_base),(ptr_mem_end),(ptr_bdtable_base))
#endif

/* We have custom address tranlation for HW addresses */
#define GRSPW_ADR_TO

/* MEMAREA=>CPU used when reading descriptor buffer pointers,
 * they need to be translated from adresses used by GRSPW HW
 * into CPU readable addresses.
 *
 * NOT NEEDED AS GRSPW DRIVER USES INDEXES TO GET DESCRIPTOR
 * DATA POINTER ADDRESSES.
 */
#undef GRSPW_ADR_FROM

/* Set registered device name */
#define GRSPW_DEVNAME "/dev/grspwrasta0"
#define GRSPW_DEVNAME_NO(devstr,no) ((devstr)[15]='0'+(no))

/* Any non-static function will begin with */
#define GRSPW_PREFIX(name) grspwrasta##name

/* do nothing, assume that the interrupt handler is called
 * setup externally calling grspw_interrupt_handler.
 */
#define GRSPW_REG_INT(handler,irq,arg) \
  if ( grspw_rasta_int_reg ) \
    grspw_rasta_int_reg(handler,irq,arg);

#define GRSPW_DONT_BYPASS_CACHE

#ifdef GRSPW_ADR_TO
/* Translate a address within the Memory Region (memarea) into an Hardware
 * device address. This address is put into hardware registers or descriptors
 * so that the hardware can access the Memory Region.
 * Example:
 * An local AMBA access at 0xe0000000 will translate into PCI address 0x40000000,
 * the PCI address 0x40000000 will translate into CPU-AMBA address 0x40000000.
 */
static inline unsigned int memarea_to_hw(unsigned int addr) {
    return ((addr & 0x0fffffff) | RASTA_PCI_BASE);
}
#endif

void (*grspw_rasta_int_reg)(void *handler, int irq, void *arg) = 0;

#ifdef GRSPW_STATIC_MEM
static int grspw_rasta_calc_memoffs(int maxcores, int corenum, unsigned int *mem_base, unsigned int *mem_end, unsigned int *bdtable_base);
#endif

int grspw_rasta_interrupt_handler(unsigned int status);

void grspwrasta_interrupt_handler(int irq, void *pDev);

#include "grspw.c"

unsigned int grspw_rasta_memarea_address;

/* Register RASTA GRSPW driver.
 *
 * memarea     = preallocated memory somewhere, pointer to start of memory.
 */

int grspw_rasta_register(
 amba_confarea_type *bus,
 unsigned int ram_base
 )
{
	/* Setup configuration */

	/* if zero the malloc will be used */
	grspw_rasta_memarea_address = ram_base + GRSPW_RASTA_MEM_OFF;

	/* Register the driver */
	return GRSPW_PREFIX(_register)(bus);
}

#if 0
/* Call this from PCI interrupt handler, simply figures out
 * which GRSPW core was responsible for the IRQ (may be multiple).
 * v = status of the PCI/AMBA MCPU IRQ CTRL
 */
int grspw_rasta_interrupt_handler(unsigned int status)
{
        int minor;

        for(minor = 0; minor < spw_cores; minor++) {
                if (status & (1<<grspw_devs[minor].irq) ) {
                        grspw_interrupt(&grspw_devs[minor]);
                }
        }
}
#endif

void GRSPW_PREFIX(_interrupt_handler)(int irq, void *pDev)
{
  grspw_interrupt(pDev);
}


#ifdef GRSPW_STATIC_MEM
/*
 *  --------------------------------------- <-
 *  | Core1: BD TABLE 1 and 2             |
 *  | Core2: BD TABLE 1 and 2             |
 *  | Core3: BD TABLE 1 and 2             |
 *  |-------------------------------------|
 *  | Core1: rx data buf + rx header buf  |
 *  | Core2: rx data buf + rx header buf  |
 *  | Core3: rx data buf + rx header buf  |
 *  ---------------------------------------
 */
static int grspw_rasta_calc_memoffs(int maxcores, int corenum, unsigned int *mem_base, unsigned int *mem_end, unsigned int *bdtable_base)
{
	if ( maxcores > 3 )
		return -1;

	if ( bdtable_base )
		*bdtable_base = grspw_rasta_memarea_address + corenum*2*SPACEWIRE_BDTABLE_SIZE;

	if ( mem_base )
		*mem_base = grspw_rasta_memarea_address + coremax*2*SPACEWIRE_BDTABLE_SIZE + corenum*BUFMEM_PER_LINK;

	if ( mem_end )
		*mem_end = grspw_rasta_memarea_address + coremax*2*SPACEWIRE_BDTABLE_SIZE + (corenum+1)*BUFMEM_PER_LINK;

	return 0;
}
#endif