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 2010 Sun Microsystems, Inc.  All rights reserved.
24  * Use is subject to license terms.
25  */
26 
27 #ifndef _SI3124VAR_H
28 #define	_SI3124VAR_H
29 
30 #ifdef	__cplusplus
31 extern "C" {
32 #endif
33 
34 #define	SI3124_MAX_PORTS		4
35 #define	SI3132_MAX_PORTS		2
36 #define	SI_MAX_PORTS			SI3124_MAX_PORTS
37 
38 #define	SI_SUCCESS			(0)	/* successful return */
39 #define	SI_TIMEOUT			(1)	/* timed out */
40 #define	SI_FAILURE			(-1)	/* unsuccessful return */
41 
42 #define	SI_MAX_SGT_TABLES_PER_PRB	10
43 
44 /*
45  * While the si_sge_t and si_sgt_t correspond to the actual SGE and SGT
46  * definitions as per the datasheet, the si_sgblock_t (i.e scatter gather
47  * block) is a logical data structure which holds multiple SGT tables.
48  * The idea is to use multiple chained SGT tables per each PRB request.
49  */
50 
51 typedef struct si_sgblock {
52 	si_sgt_t sgb_sgt[SI_MAX_SGT_TABLES_PER_PRB];
53 } si_sgblock_t;
54 
55 /*
56  * Each SGT (Scatter Gather Table) has 4 SGEs (Scatter Gather Entries).
57  * But each SGT effectively can host only 3 SGEs since the last SGE entry
58  * is used to hold a link to the next SGT in the chain. However the last
59  * SGT in the chain can host all the 4 entries since it does not need to
60  * link any more.
61  */
62 #define	SI_MAX_SGL_LENGTH	(3*SI_MAX_SGT_TABLES_PER_PRB)+1
63 
64 typedef struct si_portmult_state {
65 	int sipm_num_ports;
66 	uint8_t sipm_port_type[15];
67 	/* one of PORT_TYPE_[NODEV | MULTIPLIER | ATAPI | DISK | UNKNOWN] */
68 
69 	/*
70 	 * sipm_port_type[] is good enough to capture the state of ports
71 	 * behind the multiplier. Since any of the port behind a multiplier
72 	 * is accessed through the same main controller port, we don't need
73 	 * additional si_port_state_t here.
74 	 */
75 
76 } si_portmult_state_t;
77 
78 
79 /* The following are for port types */
80 #define	PORT_TYPE_NODEV		0x0
81 #define	PORT_TYPE_MULTIPLIER	0x1
82 #define	PORT_TYPE_ATAPI		0x2
83 #define	PORT_TYPE_DISK		0x3
84 #define	PORT_TYPE_UNKNOWN	0x4
85 
86 /* The following are for active state */
87 #define	PORT_INACTIVE		0x0
88 #define	PORT_ACTIVE		0x1
89 
90 typedef struct si_port_state {
91 	uint8_t siport_port_type;
92 	/* one of PORT_TYPE_[NODEV | MULTIPLIER | ATAPI | DISK | UNKNOWN] */
93 
94 	uint8_t siport_active;		/* one of ACTIVE or INACTIVE */
95 
96 	si_portmult_state_t siport_portmult_state;
97 
98 	si_prb_t *siport_prbpool; 	/* These are 31 incore PRBs */
99 	uint64_t siport_prbpool_physaddr;
100 	ddi_dma_handle_t siport_prbpool_dma_handle;
101 	ddi_acc_handle_t siport_prbpool_acc_handle;
102 
103 
104 	si_sgblock_t *siport_sgbpool; 	/* These are 31 incore sg blocks */
105 	uint64_t siport_sgbpool_physaddr;
106 	ddi_dma_handle_t siport_sgbpool_dma_handle;
107 	ddi_acc_handle_t siport_sgbpool_acc_handle;
108 
109 	kmutex_t siport_mutex; 		/* main per port mutex */
110 	uint32_t siport_pending_tags;	/* remembers the pending tags */
111 	sata_pkt_t *siport_slot_pkts[SI_NUM_SLOTS];
112 
113 	/*
114 	 * While the reset is in progress, we don't accept any more commands
115 	 * until we receive the command with SATA_CLEAR_DEV_RESET_STATE flag.
116 	 * However any commands with SATA_IGNORE_DEV_RESET_STATE are allowed in
117 	 * during such blockage.
118 	 */
119 	int siport_reset_in_progress;
120 
121 	/*
122 	 * We mop the commands for either abort, reset, timeout or
123 	 * error handling cases. This counts how many mops are in progress.
124 	 * It is also used to return BUSY in tran_start if a mop is going on.
125 	 */
126 	int mopping_in_progress;
127 
128 	/* error recovery related info */
129 	uint32_t siport_err_tags_SDBERROR;
130 	uint32_t siport_err_tags_nonSDBERROR;
131 	int siport_pending_ncq_count;
132 
133 } si_port_state_t;
134 
135 /* Warlock annotation */
136 _NOTE(MUTEX_PROTECTS_DATA(si_port_state_t::siport_mutex, si_port_state_t))
137 _NOTE(READ_ONLY_DATA(si_port_state_t::siport_prbpool_dma_handle))
138 _NOTE(READ_ONLY_DATA(si_port_state_t::siport_sgbpool_dma_handle))
139 
140 
141 typedef struct si_ctl_state {
142 
143 	dev_info_t *sictl_devinfop;
144 
145 	int sictl_num_ports;	/* number of controller ports */
146 	si_port_state_t *sictl_ports[SI_MAX_PORTS];
147 
148 	int sictl_devid; /* whether it is 3124 or 3132 */
149 	int sictl_flags; /* some important state of controller */
150 	int sictl_power_level;
151 
152 	/* pci config space handle */
153 	ddi_acc_handle_t sictl_pci_conf_handle;
154 
155 	/* mapping into bar 0 */
156 	ddi_acc_handle_t sictl_global_acc_handle;
157 	uintptr_t sictl_global_addr;
158 
159 	/* mapping into bar 1 */
160 	ddi_acc_handle_t sictl_port_acc_handle;
161 	uintptr_t sictl_port_addr;
162 
163 	struct sata_hba_tran *sictl_sata_hba_tran;
164 	timeout_id_t sictl_timeout_id;
165 
166 	kmutex_t sictl_mutex; 			/* per controller mutex */
167 
168 	ddi_intr_handle_t *sictl_htable;	/* For array of interrupts */
169 	int sictl_intr_type;			/* What type of interrupt */
170 	int sictl_intr_cnt;			/* # of intrs count returned */
171 	size_t sictl_intr_size;			/* Size of intr array */
172 	uint_t sictl_intr_pri;			/* Interrupt priority */
173 	int sictl_intr_cap;			/* Interrupt capabilities */
174 
175 } si_ctl_state_t;
176 
177 /* Warlock annotation */
178 _NOTE(MUTEX_PROTECTS_DATA(si_ctl_state_t::sictl_mutex,
179 					si_ctl_state_t::sictl_ports))
180 _NOTE(MUTEX_PROTECTS_DATA(si_ctl_state_t::sictl_mutex,
181 					si_ctl_state_t::sictl_power_level))
182 _NOTE(MUTEX_PROTECTS_DATA(si_ctl_state_t::sictl_mutex,
183 					si_ctl_state_t::sictl_flags))
184 _NOTE(MUTEX_PROTECTS_DATA(si_ctl_state_t::sictl_mutex,
185 					si_ctl_state_t::sictl_timeout_id))
186 /*
187  * flags for si_flags
188  */
189 #define	SI_PM			0x01
190 #define	SI_ATTACH		0x02
191 #define	SI_DETACH		0x04
192 #define	SI_NO_TIMEOUTS		0x08
193 #define	SI_FRAMEWORK_ATTACHED	0x10	/* are we attached to framework ? */
194 
195 /* progress values for si_attach */
196 #define	ATTACH_PROGRESS_NONE			(1<<0)
197 #define	ATTACH_PROGRESS_STATEP_ALLOC		(1<<1)
198 #define	ATTACH_PROGRESS_CONF_HANDLE		(1<<2)
199 #define	ATTACH_PROGRESS_BAR0_MAP		(1<<3)
200 #define	ATTACH_PROGRESS_BAR1_MAP		(1<<4)
201 #define	ATTACH_PROGRESS_INTR_ADDED		(1<<5)
202 #define	ATTACH_PROGRESS_MUTEX_INIT		(1<<6)
203 #define	ATTACH_PROGRESS_HW_INIT			(1<<7)
204 
205 #define	SI_10MS_TICKS	(drv_usectohz(10000))	/* ticks in 10 millisec */
206 #define	SI_1MS_TICKS	(drv_usectohz(1000))	/* ticks in 1 millisec */
207 #define	SI_1MS_USECS	(1000)			/* usecs in 1 millisec */
208 #define	SI_POLLRATE_SOFT_RESET		1000
209 #define	SI_POLLRATE_SSTATUS		10
210 #define	SI_POLLRATE_PORTREADY		50
211 #define	SI_POLLRATE_SLOTSTATUS		50
212 #define	SI_POLLRATE_RECOVERPORTMULT	1000
213 
214 #define	PORTMULT_CONTROL_PORT		0xf
215 
216 /* clearing & setting the n'th bit in a given tag */
217 #define	CLEAR_BIT(tag, bit)	(tag &= ~(0x1<<bit))
218 #define	SET_BIT(tag, bit)	(tag |= (0x1<<bit))
219 
220 #if DEBUG
221 
222 #define	SI_DEBUG	1
223 
224 #define	SIDBG_TEST	0x0001
225 #define	SIDBG_INIT	0x0002
226 #define	SIDBG_ENTRY	0x0004
227 #define	SIDBG_DUMP_PRB	0x0008
228 #define	SIDBG_EVENT	0x0010
229 #define	SIDBG_POLL_LOOP	0x0020
230 #define	SIDBG_PKTCOMP	0x0040
231 #define	SIDBG_TIMEOUT	0x0080
232 #define	SIDBG_INFO	0x0100
233 #define	SIDBG_VERBOSE	0x0200
234 #define	SIDBG_INTR	0x0400
235 #define	SIDBG_ERRS	0x0800
236 #define	SIDBG_COOKIES	0x1000
237 #define	SIDBG_POWER	0x2000
238 
239 extern int si_debug_flag;
240 
241 #define	SIDBG0(flag, softp, format) \
242 	if (si_debug_flags & (flag)) { \
243 		si_log(softp, CE_WARN, format); \
244 	}
245 
246 #define	SIDBG1(flag, softp, format, arg1) \
247 	if (si_debug_flags & (flag)) { \
248 		si_log(softp, CE_WARN, format, arg1); \
249 	}
250 
251 #define	SIDBG2(flag, softp, format, arg1, arg2) \
252 	if (si_debug_flags & (flag)) { \
253 		si_log(softp, CE_WARN, format, arg1, arg2); \
254 	}
255 
256 #define	SIDBG3(flag, softp, format, arg1, arg2, arg3) \
257 	if (si_debug_flags & (flag)) { \
258 		si_log(softp, CE_WARN, format, arg1, arg2, arg3); \
259 	}
260 
261 #define	SIDBG4(flag, softp, format, arg1, arg2, arg3, arg4) \
262 	if (si_debug_flags & (flag)) { \
263 		si_log(softp, CE_WARN, format, arg1, arg2, arg3, arg4); \
264 	}
265 #else
266 
267 #define	SIDBG0(flag, dip, frmt)
268 #define	SIDBG1(flag, dip, frmt, arg1)
269 #define	SIDBG2(flag, dip, frmt, arg1, arg2)
270 #define	SIDBG3(flag, dip, frmt, arg1, arg2, arg3)
271 #define	SIDBG4(flag, dip, frmt, arg1, arg2, arg3, arg4)
272 
273 #endif /* DEBUG */
274 
275 /* Flags controlling the reset behavior */
276 #define	SI_PORT_RESET		0x1	/* Reset the port */
277 #define	SI_DEVICE_RESET		0x2	/* Reset the device, not the port */
278 #define	SI_RESET_NO_EVENTS_UP	0x4	/* Don't send reset events up */
279 
280 #ifdef	__cplusplus
281 }
282 #endif
283 
284 #endif /* _SI3124VAR_H */
285