1/*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21
22/*
23 * Copyright 2002 Sun Microsystems, Inc.  All rights reserved.
24 * Use is subject to license terms.
25 */
26
27#ifndef _SYS_AXQ_H
28#define	_SYS_AXQ_H
29
30#pragma ident	"%Z%%M%	%I%	%E% SMI"
31
32#ifdef	__cplusplus
33extern "C" {
34#endif
35
36/* AXQ register offset constant */
37#define	AXQ_REG_OFFSET		0x20
38#define	AXQ_REGOFF(idx)		((idx) * AXQ_REG_OFFSET)
39
40/*
41 * AXQ system register offsets
42 * Each Starcat AXQ asic instance is logically
43 * associated with each slot in the expander board.
44 * Slot 0 is the full slot (or full bandwidth slot)
45 * and Slot1 is the half slot (or half bandwidth slot).
46 * Some system registers are only accessible in certain
47 * slot type.
48 */
49
50/* domain control register (slot0 & slot1) */
51#define	AXQ_SLOT0_DOMCTRL	AXQ_REGOFF(0x1)
52#define	AXQ_SLOT1_DOMCTRL	AXQ_REGOFF(0x2)
53
54/* cpu2ssc intr register */
55#define	AXQ_SLOT_CPU2SSC_INTR	AXQ_REGOFF(0x3)
56
57/* performance counters (one set per slot) */
58#define	AXQ_SLOT0_PERFCNT_SEL	AXQ_REGOFF(0x9)
59#define	AXQ_SLOT0_PERFCNT0	AXQ_REGOFF(0xA)
60#define	AXQ_SLOT0_PERFCNT1	AXQ_REGOFF(0xB)
61#define	AXQ_SLOT0_PERFCNT2	AXQ_REGOFF(0xC)
62#define	AXQ_SLOT1_PERFCNT_SEL	AXQ_REGOFF(0x8)
63#define	AXQ_SLOT1_PERFCNT0	AXQ_REGOFF(0xD)
64#define	AXQ_SLOT1_PERFCNT1	AXQ_REGOFF(0xE)
65#define	AXQ_SLOT1_PERFCNT2	AXQ_REGOFF(0xF)
66
67/* CASM slots (for both slot0 & slot1) */
68#define	AXQ_CASM_SLOT_START	AXQ_REGOFF(0x10)
69#define	AXQ_CASM_SLOT_END	AXQ_REGOFF(0x21)
70
71/* CDC registers (only available in slot0) */
72#define	AXQ_SLOT0_CDC_ADR_TEST	AXQ_REGOFF(0x2C)
73#define	AXQ_SLOT0_CDC_CTL_TEST	AXQ_REGOFF(0x2D)
74#define	AXQ_SLOT0_CDC_DATA_WR3	AXQ_REGOFF(0x2E)
75#define	AXQ_SLOT0_CDC_DATA_WR2	AXQ_REGOFF(0x2F)
76#define	AXQ_SLOT0_CDC_DATA_WR1	AXQ_REGOFF(0x30)
77#define	AXQ_SLOT0_CDC_DATA_WR0	AXQ_REGOFF(0x31)
78#define	AXQ_SLOT0_CDC_CNT_TEST	AXQ_REGOFF(0x32)
79#define	AXQ_SLOT0_CDC_RD_DATA3	AXQ_REGOFF(0x33)
80#define	AXQ_SLOT0_CDC_RD_DATA2	AXQ_REGOFF(0x34)
81#define	AXQ_SLOT0_CDC_RD_DATA1	AXQ_REGOFF(0x35)
82#define	AXQ_SLOT0_CDC_RD_DATA0	AXQ_REGOFF(0x36)
83
84/* NASM registers */
85#define	AXQ_SLOT0_NASM		AXQ_REGOFF(0x37)
86#define	AXQ_SLOT1_NASM		AXQ_REGOFF(0x38)
87
88#define	AXQ_NASM_TYPE_IO		0
89#define	AXQ_NASM_TYPE_SLOT0_CMMU	1
90#define	AXQ_NASM_TYPE_WIB		2
91#define	AXQ_NASM_TYPE_WIB_STRIPED	3
92#define	AXQ_NASM_TYPE_SHIFT		5
93
94/* SDI Timeout register */
95#define	AXQ_SLOT_SDI_TIMEOUT_RD		AXQ_REGOFF(0x2A)
96#define	AXQ_SLOT_SDI_TIMEOUT_RDCLR	AXQ_REGOFF(0x2B)
97
98/*
99 * Bits for domain control register
100 */
101#define	AXQ_DOMCTRL_BUSY	0x1
102#define	AXQ_DOMCTRL_PAUSE	0x10
103#define	AXQ_DOMCTRL_PIOFIX	0x40
104
105/*
106 * Bits for CDC registers
107 */
108/* CDC control test register */
109#define	AXQ_CDC_TMODE_WR		0x20000
110#define	AXQ_CDC_TMODE_RDCMP		0x40000
111#define	AXQ_CDC_TMODE_WR_RDCMP0		0x60000
112#define	AXQ_CDC_TMODE_WR_RDCMP1		0x80000
113#define	AXQ_CDC_DATA_ECC_CHK_EN		0x10000
114#define	AXQ_CDC_ADR_PAR_CHK_EN		0x08000
115#define	AXQ_CDC_DATA_ECC_GEN_EN		0x04000
116#define	AXQ_CDC_ADR_PAR_GEN_EN		0x02000
117#define	AXQ_CDC_DATA2PAR_MUX_SEL_DATA	0x00800
118#define	AXQ_CDC_ADR2SRAM_MUX_SEL_TEST	0x00080
119#define	AXQ_CDC_ADR_INCR_XOR_CTRL	0x00010
120#define	AXQ_CDC_DIS			0x00001
121
122/* CDC Address Test register */
123#define	AXQ_CDC_ADR_TEST_EN		0x80000
124
125/* CDC counter test register */
126#define	AXQ_CDC_CNT_TEST_DONE		0x80000000
127
128/*
129 * Bits for CPU to SSC interrupt register
130 */
131#define	AXQ_CPU2SSC_INTR_PEND		0x80000000
132
133/*
134 * Each AXQ instance has one pcr (performance control
135 * register) controlling 3 pics (performance instru-
136 * mentation counter).  pic0 and pic1 are similar
137 * and have identical inputs to their muxes. pic2
138 * only counts the clock.
139 */
140
141/* Bit masks for selecting pic mux input */
142#define	FREEZE_CNT	0x0
143#define	COUNT_CLK	0x1
144#define	HA_INPUT_FIFO	0x2
145#define	HA_INTR_INFO	0x3
146#define	HA_PIO_FIFO	0x4
147#define	HA_ADR_FIFO_LK3	0x5
148#define	HA_ADR_FIFO_LK2	0x6
149#define	HA_ADR_FIFO_LK1	0x7
150#define	HA_ADR_FIFO_LK0	0x8
151#define	HA_DUMP_Q	0x9
152#define	HA_RD_F_STB_Q	0xA
153#define	HA_DP_WR_Q	0xB
154#define	HA_INT_Q	0xC
155#define	HA_WRB_Q	0xD
156#define	HA_WR_MP_Q	0xE
157#define	HA_WRTAG_Q	0xF
158#define	HA_WT_WAIT_FIFO	0x10
159#define	HA_WRB_STB_FIFO	0x11
160#define	HA_AP0_Q	0x12
161#define	HA_AP1_Q	0x13
162#define	HA_NEW_WR_Q	0x14
163#define	HA_DP_RD_Q	0x15
164#define	HA_UNLOCK_Q	0x16
165#define	HA_CDC_UPD_Q	0x17
166#define	HA_DS_Q		0x18
167#define	HA_UNLK_WAIT_Q	0x19
168#define	HA_RD_MP_Q	0x1A
169#define	L2_IO_Q		0x1B
170#define	L2_SB_Q		0x1C
171#define	L2_RA_Q		0x1D
172#define	L2_HA_Q		0x1E
173#define	L2_SA_Q		0x1F
174#define	RA_WAIT_FIFO	0x20
175#define	RA_WRB_INV_FIFO	0x21
176#define	RA_WRB_FIFO	0x22
177#define	RA_CC_PTR_FIFO	0x23
178#define	RA_IO_PTR_FIFO	0x24
179#define	RA_INT_PTR_FIFO	0x25
180#define	RA_RP_Q		0x26
181#define	RA_WRB_RP_Q	0x27
182#define	RA_DP_Q		0x28
183#define	RA_DP_STB_Q	0x29
184#define	RA_GTARG_Q	0x2A
185#define	SDC_RECV_Q	0x2B
186#define	SDC_REDIR_IO_Q	0x2C
187#define	SDC_REDIR_SB_Q	0x2D
188#define	SDC_OUTB_IO_Q	0x2E
189#define	SDC_OUTB_SB_Q	0x2F
190#define	SA_ADD1_INPUT_Q	0x30
191#define	SA_ADD2_INPUT_Q	0x31
192#define	SA_INV_Q	0x32
193#define	SA_NO_INV_Q	0x33
194#define	SA_INT_DP_Q	0x34
195#define	SA_DP_Q		0x35
196#define	SL_WRTAG_Q	0x36
197#define	SL_RTO_DP_Q	0x37
198#define	SYSREG_INPUT_Q	0x38
199#define	SDI_SYS_STATUS1	0x39
200#define	SDI_SYS_STATUS0	0x3A
201#define	CDC_HITS	0x3B
202#define	TOTAL_CDC_READ	0x3C
203#define	HA_WATRANID_SD	0x3D
204#define	HA_STB_SD	0x3E
205#define	HA_L2_IRQ_SD	0x3F
206#define	HA_SL_WRTAG_SD	0x40
207#define	AA_HOME_CC_FULL	0x41
208#define	AA_HOME_IO_FULL	0x42
209#define	AA_SLAVE_FULL	0x43
210#define	AA_RP_FULL	0x44
211
212/* Shift definitions into pcr for programming pics */
213#define	AXQ_PIC_SHIFT	7
214
215/* event constants */
216#define	AXQ_NUM_EVENTS		0x45
217#define	AXQ_PIC0_1_NUM_EVENTS	0x45
218#define	AXQ_PIC2_NUM_EVENTS	0x2
219#define	AXQ_NUM_PICS	3
220#define	AXQ_PIC_CLEAR_MASK	0x7F
221
222/* AXQ constants */
223#define	SLOT0_AXQ		0
224#define	SLOT1_AXQ		1
225#define	AXQ_MAX_EXP		18
226#define	AXQ_MAX_SLOT_PER_EXP	2
227#define	AXQ_CDC_SRAM_SIZE	0x40000
228#define	AXQ_CDC_FLUSH_WAIT	4
229#define	AXQ_INTR_PEND_WAIT	10
230#define	AXQ_NASM_SIZE		256
231
232/*
233 * Struct element describing a eventname and
234 * its pcr-mask.
235 */
236typedef struct axq_event_mask {
237	char	*event_name;
238	uint64_t pcr_mask;
239} axq_event_mask_t;
240
241/*
242 * NASM RAM system register for reading
243 */
244typedef union {
245	struct axq_nasm_read {
246		uint32_t pad	: 16;
247		uint32_t valid	: 1;
248		uint32_t addr	: 8;
249		uint32_t data	: 7;
250	} bit;
251	uint32_t val;
252} axq_nasm_read_u;
253
254/*
255 * NASM RAM system register for reading
256 */
257typedef union {
258	struct axq_nasm_write {
259		uint32_t pad	: 16;
260		uint32_t addr	: 8;
261		uint32_t rw	: 1;
262		uint32_t data	: 7;
263	} bit;
264	uint32_t val;
265} axq_nasm_write_u;
266
267
268/*
269 * Global data structure that is used to
270 * export certain axq registers in
271 * local space. Right now, the only
272 * register we want to access in local space
273 * is the cheetah2ssc interrupt reg. There
274 * could be more in future.
275 */
276struct axq_local_regs {
277	kmutex_t axq_local_lock;
278	int initflag;
279	caddr_t laddress;
280	ddi_acc_handle_t ac;
281	volatile uint32_t *axq_cpu2ssc_intr;
282};
283
284/*
285 * axq soft state data structure.
286 */
287struct axq_soft_state {
288	dev_info_t *dip;		/* devinfo of myself */
289	uint32_t portid;		/* port id */
290	uint32_t expid;			/* expander id */
291	uchar_t slotnum;		/* slot 0 or 1 */
292	caddr_t address;		/* mapped devnode addr property */
293	ddi_acc_handle_t ac0;		/* access handle for reg0 mapping */
294	uint64_t axq_phyaddr;		/* physical address of conf space */
295	kmutex_t axq_lock;		/* mutex protecting this softstate */
296
297	volatile uint32_t *axq_domain_ctrl;
298
299	/* CASM register slots */
300	volatile uint32_t *axq_casm_slot[18];
301
302	/* NASM register */
303	volatile uint32_t *axq_nasm;
304
305	/* CDC registers (only in slot0) */
306	volatile uint32_t *axq_cdc_addrtest;
307	volatile uint32_t *axq_cdc_ctrltest;
308	volatile uint32_t *axq_cdc_datawrite0;
309	volatile uint32_t *axq_cdc_datawrite1;
310	volatile uint32_t *axq_cdc_datawrite2;
311	volatile uint32_t *axq_cdc_datawrite3;
312	volatile uint32_t *axq_cdc_counter;
313	volatile uint32_t *axq_cdc_readdata0;
314	volatile uint32_t *axq_cdc_readdata1;
315	volatile uint32_t *axq_cdc_readdata2;
316	volatile uint32_t *axq_cdc_readdata3;
317
318	/* performance counters */
319	volatile uint32_t *axq_pcr;
320	volatile uint32_t *axq_pic0;
321	volatile uint32_t *axq_pic1;
322	volatile uint32_t *axq_pic2;
323	kstat_t *axq_counters_ksp;	/* perf counter kstat */
324
325	/* SDI timeout register */
326	volatile uint32_t *axq_sdi_timeout_rd;
327	volatile uint32_t *axq_sdi_timeout_rdclr;
328
329	uint32_t axq_cdc_state;		/* CDC state - enabled/disabled */
330	int paused;			/* AXQ_DOMCTRL_PAUSE asserted */
331
332#ifndef _AXQ_LOCAL_ACCESS_SUPPORTED
333	/*
334	 * No local access for cpu2ssc intr
335	 * Need to provide per instance explicit expander addressing
336	 */
337	volatile uint32_t *axq_cpu2ssc_intr;
338#endif /* _AXQ_LOCAL_ACCESS_SUPPORTED */
339};
340
341/*
342 * Public interface
343 */
344extern int axq_cdc_flush(uint32_t, int, int);
345extern int axq_cdc_flush_all();
346extern int axq_cdc_disable_flush_all();
347extern void axq_cdc_enable_all();
348extern int axq_iopause_enable_all(uint32_t *);
349extern void axq_iopause_disable_all();
350extern uint32_t axq_casm_read(uint32_t, uint32_t, int);
351extern int axq_casm_write(uint32_t, uint32_t, int, uint32_t);
352extern int axq_casm_write_all(int, uint32_t);
353extern int axq_do_casm_rename_script(uint64_t **, int, int);
354extern int axq_cpu2ssc_intr(uint8_t);
355extern uint32_t axq_read_sdi_timeout_reg(uint32_t, uint32_t, int);
356extern int axq_nasm_read(uint32_t expid, uint32_t slot, uint32_t nasm_entry,
357    uint32_t *data);
358extern int axq_nasm_write(uint32_t expid, uint32_t slot, uint32_t nasm_entry,
359    uint32_t data);
360extern int axq_nasm_write_all(uint32_t nasm_entry, uint32_t data);
361extern void axq_array_rw_enter(void);
362extern void axq_array_rw_exit(void);
363
364#ifdef	__cplusplus
365}
366#endif
367
368#endif	/* _SYS_AXQ_H */
369