summaryrefslogtreecommitdiffstats
path: root/sys/mips/rmi/msgring.h
blob: 6110f5f5b25b115471e348c1018b7f7ad671eb07 (plain)
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
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
/*-
 * Copyright (c) 2003-2009 RMI Corporation
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in the
 *    documentation and/or other materials provided with the distribution.
 * 3. Neither the name of RMI Corporation, nor the names of its contributors,
 *    may be used to endorse or promote products derived from this software
 *    without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
 * SUCH DAMAGE.
 *
 * RMI_BSD
 * $FreeBSD$
 */
#ifndef _RMI_MSGRING_H_
#define _RMI_MSGRING_H_

#include <sys/param.h>
#include <sys/systm.h>
#include <sys/types.h>

#include <machine/cpuregs.h>
#include <machine/cpufunc.h>
#include <mips/rmi/rmi_mips_exts.h>

#define	MSGRNG_TX_BUF_REG	0
#define	MSGRNG_RX_BUF_REG	1
#define	MSGRNG_MSG_STATUS_REG	2
#define	MSGRNG_MSG_CONFIG_REG	3
#define MSGRNG_MSG_BUCKSIZE_REG	4

#define	MSGRNG_CC_0_REG		16
#define	MSGRNG_CC_1_REG		17
#define	MSGRNG_CC_2_REG		18
#define	MSGRNG_CC_3_REG		19
#define	MSGRNG_CC_4_REG		20
#define	MSGRNG_CC_5_REG		21
#define	MSGRNG_CC_6_REG		22
#define	MSGRNG_CC_7_REG		23
#define	MSGRNG_CC_8_REG		24
#define	MSGRNG_CC_9_REG		25
#define	MSGRNG_CC_10_REG	26
#define	MSGRNG_CC_11_REG	27
#define	MSGRNG_CC_12_REG	28
#define	MSGRNG_CC_13_REG	29
#define	MSGRNG_CC_14_REG	30
#define	MSGRNG_CC_15_REG	31

/* Station IDs */
#define	MSGRNG_STNID_CPU0	0x00
#define	MSGRNG_STNID_CPU1	0x08
#define	MSGRNG_STNID_CPU2	0x10
#define	MSGRNG_STNID_CPU3	0x18
#define	MSGRNG_STNID_CPU4	0x20
#define	MSGRNG_STNID_CPU5	0x28
#define	MSGRNG_STNID_CPU6	0x30
#define	MSGRNG_STNID_CPU7	0x38
#define	MSGRNG_STNID_XGS0_TX	64
#define	MSGRNG_STNID_XMAC0_00_TX	64
#define	MSGRNG_STNID_XMAC0_01_TX	65
#define	MSGRNG_STNID_XMAC0_02_TX	66
#define	MSGRNG_STNID_XMAC0_03_TX	67
#define	MSGRNG_STNID_XMAC0_04_TX	68
#define	MSGRNG_STNID_XMAC0_05_TX	69
#define	MSGRNG_STNID_XMAC0_06_TX	70
#define	MSGRNG_STNID_XMAC0_07_TX	71
#define	MSGRNG_STNID_XMAC0_08_TX	72
#define	MSGRNG_STNID_XMAC0_09_TX	73
#define	MSGRNG_STNID_XMAC0_10_TX	74
#define	MSGRNG_STNID_XMAC0_11_TX	75
#define	MSGRNG_STNID_XMAC0_12_TX	76
#define	MSGRNG_STNID_XMAC0_13_TX	77
#define	MSGRNG_STNID_XMAC0_14_TX	78
#define	MSGRNG_STNID_XMAC0_15_TX	79

#define	MSGRNG_STNID_XGS1_TX		80
#define	MSGRNG_STNID_XMAC1_00_TX	80
#define	MSGRNG_STNID_XMAC1_01_TX	81
#define	MSGRNG_STNID_XMAC1_02_TX	82
#define	MSGRNG_STNID_XMAC1_03_TX	83
#define	MSGRNG_STNID_XMAC1_04_TX	84
#define	MSGRNG_STNID_XMAC1_05_TX	85
#define	MSGRNG_STNID_XMAC1_06_TX	86
#define	MSGRNG_STNID_XMAC1_07_TX	87
#define	MSGRNG_STNID_XMAC1_08_TX	88
#define	MSGRNG_STNID_XMAC1_09_TX	89
#define	MSGRNG_STNID_XMAC1_10_TX	90
#define	MSGRNG_STNID_XMAC1_11_TX	91
#define	MSGRNG_STNID_XMAC1_12_TX	92
#define	MSGRNG_STNID_XMAC1_13_TX	93
#define	MSGRNG_STNID_XMAC1_14_TX	94
#define	MSGRNG_STNID_XMAC1_15_TX	95

#define	MSGRNG_STNID_GMAC		96
#define	MSGRNG_STNID_GMACJFR_0		96
#define	MSGRNG_STNID_GMACRFR_0		97
#define	MSGRNG_STNID_GMACTX0		98
#define	MSGRNG_STNID_GMACTX1		99
#define	MSGRNG_STNID_GMACTX2		100
#define	MSGRNG_STNID_GMACTX3		101
#define	MSGRNG_STNID_GMACJFR_1		102
#define	MSGRNG_STNID_GMACRFR_1		103

#define	MSGRNG_STNID_DMA		104
#define	MSGRNG_STNID_DMA_0		104
#define	MSGRNG_STNID_DMA_1		105
#define	MSGRNG_STNID_DMA_2		106
#define	MSGRNG_STNID_DMA_3		107

#define	MSGRNG_STNID_XGS0FR		112
#define	MSGRNG_STNID_XMAC0JFR		112
#define	MSGRNG_STNID_XMAC0RFR		113

#define	MSGRNG_STNID_XGS1FR		114
#define	MSGRNG_STNID_XMAC1JFR		114
#define	MSGRNG_STNID_XMAC1RFR		115
#define	MSGRNG_STNID_SEC		120
#define	MSGRNG_STNID_SEC0		120
#define	MSGRNG_STNID_SEC1		121
#define	MSGRNG_STNID_SEC2		122
#define	MSGRNG_STNID_SEC3		123
#define	MSGRNG_STNID_PK0		124
#define	MSGRNG_STNID_SEC_RSA		124
#define	MSGRNG_STNID_SEC_RSVD0		125
#define	MSGRNG_STNID_SEC_RSVD1		126
#define	MSGRNG_STNID_SEC_RSVD2		127

#define	MSGRNG_STNID_GMAC1		80
#define	MSGRNG_STNID_GMAC1_FR_0		81
#define	MSGRNG_STNID_GMAC1_TX0		82
#define	MSGRNG_STNID_GMAC1_TX1		83
#define	MSGRNG_STNID_GMAC1_TX2		84
#define	MSGRNG_STNID_GMAC1_TX3		85
#define	MSGRNG_STNID_GMAC1_FR_1		87
#define	MSGRNG_STNID_GMAC0		96
#define	MSGRNG_STNID_GMAC0_FR_0		97
#define	MSGRNG_STNID_GMAC0_TX0		98
#define	MSGRNG_STNID_GMAC0_TX1		99
#define	MSGRNG_STNID_GMAC0_TX2		100
#define	MSGRNG_STNID_GMAC0_TX3		101
#define	MSGRNG_STNID_GMAC0_FR_1		103
#define	MSGRNG_STNID_CMP_0		108
#define	MSGRNG_STNID_CMP_1		109
#define	MSGRNG_STNID_CMP_2		110
#define	MSGRNG_STNID_CMP_3		111
#define	MSGRNG_STNID_PCIE_0		116
#define	MSGRNG_STNID_PCIE_1		117
#define	MSGRNG_STNID_PCIE_2		118
#define	MSGRNG_STNID_PCIE_3		119
#define	MSGRNG_STNID_XLS_PK0		121

#define	MSGRNG_CODE_MAC		0
#define	MSGRNG_CODE_XGMAC	2
#define	MSGRNG_CODE_SEC		0
#define	MSGRNG_CODE_BOOT_WAKEUP	200
#define	MSGRNG_CODE_SPI4	3

#define	msgrng_read_status()	read_c2_register32(MSGRNG_MSG_STATUS_REG, 0)
#define	msgrng_read_config()	read_c2_register32(MSGRNG_MSG_CONFIG_REG, 0)
#define	msgrng_write_config(v)	write_c2_register32(MSGRNG_MSG_CONFIG_REG, 0, v)
#define	msgrng_read_bucksize(b)	read_c2_register32(MSGRNG_MSG_BUCKSIZE_REG, b)
#define	msgrng_write_bucksize(b, v)	write_c2_register32(MSGRNG_MSG_BUCKSIZE_REG, b, v)
#define	msgrng_read_cc(r, s)	read_c2_register32(r, s)
#define	msgrng_write_cc(r, v, s)	write_c2_register32(r, s, v)

#define	msgrng_load_rx_msg0()	read_c2_register64(MSGRNG_RX_BUF_REG, 0)
#define	msgrng_load_rx_msg1()	read_c2_register64(MSGRNG_RX_BUF_REG, 1)
#define	msgrng_load_rx_msg2()	read_c2_register64(MSGRNG_RX_BUF_REG, 2)
#define	msgrng_load_rx_msg3()	read_c2_register64(MSGRNG_RX_BUF_REG, 3)

#define	msgrng_load_tx_msg0(v)	write_c2_register64(MSGRNG_TX_BUF_REG, 0, v)
#define	msgrng_load_tx_msg1(v)	write_c2_register64(MSGRNG_TX_BUF_REG, 1, v)
#define	msgrng_load_tx_msg2(v)	write_c2_register64(MSGRNG_TX_BUF_REG, 2, v)
#define	msgrng_load_tx_msg3(v)	write_c2_register64(MSGRNG_TX_BUF_REG, 3, v)

static __inline void 
msgrng_send(unsigned int stid)
{
	__asm__ volatile (
	    ".set	push\n"
	    ".set	noreorder\n"
	    "move	$8, %0\n"
	    "c2		0x80001\n"	/* msgsnd $8 */
	    ".set	pop\n"
	    :: "r" (stid): "$8"
	);
}

static __inline void 
msgrng_receive(unsigned int pri)
{
	__asm__ volatile (
	    ".set	push\n"
	    ".set	noreorder\n"
	    "move	$8, %0\n"
	    "c2		0x80002\n"    /* msgld $8 */
	    ".set	pop\n"
	    :: "r" (pri): "$8"
	);
}

static __inline void 
msgrng_wait(unsigned int mask)
{
	__asm__ volatile (
	    ".set	push\n"
	    ".set	noreorder\n"
	    "move	$8, %0\n"
	    "c2		0x80003\n"    /* msgwait $8 */
	    ".set	pop\n"
	    :: "r" (mask): "$8"
	);
}

static __inline uint32_t
msgrng_access_enable(void)
{
	uint32_t sr = mips_rd_status();

	mips_wr_status((sr & ~MIPS_SR_INT_IE) | MIPS_SR_COP_2_BIT);
	return (sr);
}

static __inline void
msgrng_restore(uint32_t sr)
{

	mips_wr_status(sr);
}

struct msgrng_msg {
	uint64_t msg0;
	uint64_t msg1;
	uint64_t msg2;
	uint64_t msg3;
};

static __inline int
message_send(unsigned int size, unsigned int code,
    unsigned int stid, struct msgrng_msg *msg)
{
	unsigned int dest = 0;
	unsigned long long status = 0;
	int i = 0;

	/* 
	 * Make sure that all the writes pending at the cpu are flushed.
	 * Any writes pending on CPU will not be see by devices. L1/L2
	 * caches are coherent with IO, so no cache flush needed.
	 */ 
	__asm __volatile ("sync");

	/* Load TX message buffers */
	msgrng_load_tx_msg0(msg->msg0);
	msgrng_load_tx_msg1(msg->msg1);
	msgrng_load_tx_msg2(msg->msg2);
	msgrng_load_tx_msg3(msg->msg3);
	dest = ((size - 1) << 16) | (code << 8) | stid;

	/*
	 * Retry a few times on credit fail, this should be a 
	 * transient condition, unless there is a configuration
	 * failure, or the receiver is stuck.
	 */
	for (i = 0; i < 8; i++) {
		msgrng_send(dest);
		status = msgrng_read_status();
		KASSERT((status & 0x2) == 0, ("Send pending fail!"));
		if ((status & 0x4) == 0)
			return (0);
	}

	/* If there is a credit failure, return error */
	return (status & 0x06);
}

static __inline int 
message_receive(int bucket, int *size, int *code, int *stid,
    struct msgrng_msg *msg)
{
	uint32_t status = 0, tmp = 0;
       
	msgrng_receive(bucket); 

	/* wait for load pending to clear */
	do {
           status = msgrng_read_status();
	} while ((status & 0x08) != 0);

	/* receive error bits */
	tmp = status & 0x30;
	if (tmp != 0)
		return (tmp);

	*size = ((status & 0xc0) >> 6) + 1;
	*code = (status & 0xff00) >> 8;
	*stid = (status & 0x7f0000) >> 16;
	msg->msg0 = msgrng_load_rx_msg0();
	msg->msg1 = msgrng_load_rx_msg1();
	msg->msg2 = msgrng_load_rx_msg2();
	msg->msg3 = msgrng_load_rx_msg3();
	return (0);
}

#define	MSGRNG_STN_RX_QSIZE	256
#define	MSGRNG_NSTATIONS	128
#define	MSGRNG_CORE_NBUCKETS	8

struct stn_cc {
	unsigned short counters[16][8];
};

struct bucket_size {
	unsigned short bucket[MSGRNG_NSTATIONS];
};

extern struct bucket_size bucket_sizes;

extern struct stn_cc cc_table_cpu_0;
extern struct stn_cc cc_table_cpu_1;
extern struct stn_cc cc_table_cpu_2;
extern struct stn_cc cc_table_cpu_3;
extern struct stn_cc cc_table_cpu_4;
extern struct stn_cc cc_table_cpu_5;
extern struct stn_cc cc_table_cpu_6;
extern struct stn_cc cc_table_cpu_7;
extern struct stn_cc cc_table_xgs_0;
extern struct stn_cc cc_table_xgs_1;
extern struct stn_cc cc_table_gmac;
extern struct stn_cc cc_table_dma;
extern struct stn_cc cc_table_sec;

extern struct bucket_size xls_bucket_sizes;

extern struct stn_cc xls_cc_table_cpu_0;
extern struct stn_cc xls_cc_table_cpu_1;
extern struct stn_cc xls_cc_table_cpu_2;
extern struct stn_cc xls_cc_table_cpu_3;
extern struct stn_cc xls_cc_table_gmac0;
extern struct stn_cc xls_cc_table_gmac1;
extern struct stn_cc xls_cc_table_cmp;
extern struct stn_cc xls_cc_table_pcie;
extern struct stn_cc xls_cc_table_dma;
extern struct stn_cc xls_cc_table_sec;

typedef void (*msgring_handler)(int, int, int, int, struct msgrng_msg *, void *);
int register_msgring_handler(int startb, int endb, msgring_handler action,
		    void *arg);
uint32_t xlr_msgring_handler(uint8_t bucket_mask, uint32_t max_messages);
void xlr_msgring_cpu_init(void);
void xlr_msgring_config(void);

#endif
OpenPOWER on IntegriCloud