xref: /dragonfly/sys/dev/raid/aac/aac.c (revision 19380330)
1 /*-
2  * Copyright (c) 2000 Michael Smith
3  * Copyright (c) 2001 Scott Long
4  * Copyright (c) 2000 BSDi
5  * Copyright (c) 2001 Adaptec, Inc.
6  * All rights reserved.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions
10  * are met:
11  * 1. Redistributions of source code must retain the above copyright
12  *    notice, this list of conditions and the following disclaimer.
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in the
15  *    documentation and/or other materials provided with the distribution.
16  *
17  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
18  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
21  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
27  * SUCH DAMAGE.
28  *
29  * $FreeBSD: src/sys/dev/aac/aac.c,v 1.170 2012/02/13 16:48:49 emaste Exp $
30  */
31 
32 /*
33  * Driver for the Adaptec 'FSA' family of PCI/SCSI RAID adapters.
34  */
35 #define AAC_DRIVERNAME			"aac"
36 
37 #include "opt_aac.h"
38 
39 /* #include <stddef.h> */
40 #include <sys/param.h>
41 #include <sys/systm.h>
42 #include <sys/malloc.h>
43 #include <sys/kernel.h>
44 #include <sys/kthread.h>
45 #include <sys/poll.h>
46 
47 #include <sys/bus.h>
48 #include <sys/conf.h>
49 #include <sys/signalvar.h>
50 #include <sys/time.h>
51 #include <sys/eventhandler.h>
52 #include <sys/rman.h>
53 
54 #include <sys/bus_dma.h>
55 #include <sys/device.h>
56 #include <sys/mplock2.h>
57 
58 #include <bus/pci/pcireg.h>
59 #include <bus/pci/pcivar.h>
60 
61 #include <dev/raid/aac/aacreg.h>
62 #include <dev/raid/aac/aac_ioctl.h>
63 #include <dev/raid/aac/aacvar.h>
64 #include <dev/raid/aac/aac_tables.h>
65 
66 static void	aac_startup(void *arg);
67 static void	aac_add_container(struct aac_softc *sc,
68 				  struct aac_mntinforesp *mir, int f);
69 static void	aac_get_bus_info(struct aac_softc *sc);
70 static void	aac_daemon(void *arg);
71 
72 /* Command Processing */
73 static void	aac_timeout(struct aac_softc *sc);
74 static void	aac_complete(void *context, int pending);
75 static int	aac_bio_command(struct aac_softc *sc, struct aac_command **cmp);
76 static void	aac_bio_complete(struct aac_command *cm);
77 static int	aac_wait_command(struct aac_command *cm);
78 static void	aac_command_thread(void *arg);
79 
80 /* Command Buffer Management */
81 static void	aac_map_command_sg(void *arg, bus_dma_segment_t *segs,
82 				   int nseg, int error);
83 static void	aac_map_command_helper(void *arg, bus_dma_segment_t *segs,
84 				       int nseg, int error);
85 static int	aac_alloc_commands(struct aac_softc *sc);
86 static void	aac_free_commands(struct aac_softc *sc);
87 static void	aac_unmap_command(struct aac_command *cm);
88 
89 /* Hardware Interface */
90 static int	aac_alloc(struct aac_softc *sc);
91 static void	aac_common_map(void *arg, bus_dma_segment_t *segs, int nseg,
92 			       int error);
93 static int	aac_check_firmware(struct aac_softc *sc);
94 static int	aac_init(struct aac_softc *sc);
95 static int	aac_sync_command(struct aac_softc *sc, u_int32_t command,
96 				 u_int32_t arg0, u_int32_t arg1, u_int32_t arg2,
97 				 u_int32_t arg3, u_int32_t *sp);
98 static int	aac_setup_intr(struct aac_softc *sc);
99 static int	aac_enqueue_fib(struct aac_softc *sc, int queue,
100 				struct aac_command *cm);
101 static int	aac_dequeue_fib(struct aac_softc *sc, int queue,
102 				u_int32_t *fib_size, struct aac_fib **fib_addr);
103 static int	aac_enqueue_response(struct aac_softc *sc, int queue,
104 				     struct aac_fib *fib);
105 
106 /* StrongARM interface */
107 static int	aac_sa_get_fwstatus(struct aac_softc *sc);
108 static void	aac_sa_qnotify(struct aac_softc *sc, int qbit);
109 static int	aac_sa_get_istatus(struct aac_softc *sc);
110 static void	aac_sa_clear_istatus(struct aac_softc *sc, int mask);
111 static void	aac_sa_set_mailbox(struct aac_softc *sc, u_int32_t command,
112 				   u_int32_t arg0, u_int32_t arg1,
113 				   u_int32_t arg2, u_int32_t arg3);
114 static int	aac_sa_get_mailbox(struct aac_softc *sc, int mb);
115 static void	aac_sa_set_interrupts(struct aac_softc *sc, int enable);
116 
117 struct aac_interface aac_sa_interface = {
118 	aac_sa_get_fwstatus,
119 	aac_sa_qnotify,
120 	aac_sa_get_istatus,
121 	aac_sa_clear_istatus,
122 	aac_sa_set_mailbox,
123 	aac_sa_get_mailbox,
124 	aac_sa_set_interrupts,
125 	NULL, NULL, NULL
126 };
127 
128 /* i960Rx interface */
129 static int	aac_rx_get_fwstatus(struct aac_softc *sc);
130 static void	aac_rx_qnotify(struct aac_softc *sc, int qbit);
131 static int	aac_rx_get_istatus(struct aac_softc *sc);
132 static void	aac_rx_clear_istatus(struct aac_softc *sc, int mask);
133 static void	aac_rx_set_mailbox(struct aac_softc *sc, u_int32_t command,
134 				   u_int32_t arg0, u_int32_t arg1,
135 				   u_int32_t arg2, u_int32_t arg3);
136 static int	aac_rx_get_mailbox(struct aac_softc *sc, int mb);
137 static void	aac_rx_set_interrupts(struct aac_softc *sc, int enable);
138 static int aac_rx_send_command(struct aac_softc *sc, struct aac_command *cm);
139 static int aac_rx_get_outb_queue(struct aac_softc *sc);
140 static void aac_rx_set_outb_queue(struct aac_softc *sc, int index);
141 
142 struct aac_interface aac_rx_interface = {
143 	aac_rx_get_fwstatus,
144 	aac_rx_qnotify,
145 	aac_rx_get_istatus,
146 	aac_rx_clear_istatus,
147 	aac_rx_set_mailbox,
148 	aac_rx_get_mailbox,
149 	aac_rx_set_interrupts,
150 	aac_rx_send_command,
151 	aac_rx_get_outb_queue,
152 	aac_rx_set_outb_queue
153 };
154 
155 /* Rocket/MIPS interface */
156 static int	aac_rkt_get_fwstatus(struct aac_softc *sc);
157 static void	aac_rkt_qnotify(struct aac_softc *sc, int qbit);
158 static int	aac_rkt_get_istatus(struct aac_softc *sc);
159 static void	aac_rkt_clear_istatus(struct aac_softc *sc, int mask);
160 static void	aac_rkt_set_mailbox(struct aac_softc *sc, u_int32_t command,
161 				    u_int32_t arg0, u_int32_t arg1,
162 				    u_int32_t arg2, u_int32_t arg3);
163 static int	aac_rkt_get_mailbox(struct aac_softc *sc, int mb);
164 static void	aac_rkt_set_interrupts(struct aac_softc *sc, int enable);
165 static int aac_rkt_send_command(struct aac_softc *sc, struct aac_command *cm);
166 static int aac_rkt_get_outb_queue(struct aac_softc *sc);
167 static void aac_rkt_set_outb_queue(struct aac_softc *sc, int index);
168 
169 struct aac_interface aac_rkt_interface = {
170 	aac_rkt_get_fwstatus,
171 	aac_rkt_qnotify,
172 	aac_rkt_get_istatus,
173 	aac_rkt_clear_istatus,
174 	aac_rkt_set_mailbox,
175 	aac_rkt_get_mailbox,
176 	aac_rkt_set_interrupts,
177 	aac_rkt_send_command,
178 	aac_rkt_get_outb_queue,
179 	aac_rkt_set_outb_queue
180 };
181 
182 /* Debugging and Diagnostics */
183 static void	aac_describe_controller(struct aac_softc *sc);
184 static char	*aac_describe_code(struct aac_code_lookup *table,
185 				   u_int32_t code);
186 
187 /* Management Interface */
188 static d_open_t		aac_open;
189 static d_close_t	aac_close;
190 static d_ioctl_t	aac_ioctl;
191 static d_kqfilter_t	aac_kqfilter;
192 static void		aac_filter_detach(struct knote *kn);
193 static int		aac_filter_read(struct knote *kn, long hint);
194 static int		aac_ioctl_sendfib(struct aac_softc *sc, caddr_t ufib);
195 static int		aac_ioctl_send_raw_srb(struct aac_softc *sc, caddr_t arg);
196 static void		aac_handle_aif(struct aac_softc *sc,
197 					   struct aac_fib *fib);
198 static int		aac_rev_check(struct aac_softc *sc, caddr_t udata);
199 static int		aac_open_aif(struct aac_softc *sc, caddr_t arg);
200 static int		aac_close_aif(struct aac_softc *sc, caddr_t arg);
201 static int		aac_getnext_aif(struct aac_softc *sc, caddr_t arg);
202 static int		aac_return_aif(struct aac_softc *sc,
203 					struct aac_fib_context *ctx, caddr_t uptr);
204 static int		aac_query_disk(struct aac_softc *sc, caddr_t uptr);
205 static int		aac_get_pci_info(struct aac_softc *sc, caddr_t uptr);
206 static int		aac_supported_features(struct aac_softc *sc, caddr_t uptr);
207 static void		aac_ioctl_event(struct aac_softc *sc,
208 					struct aac_event *event, void *arg);
209 static struct aac_mntinforesp *
210 	aac_get_container_info(struct aac_softc *sc, struct aac_fib *fib, int cid);
211 
212 static struct dev_ops aac_ops = {
213 	{ "aac", 0, 0 },
214 	.d_open =	aac_open,
215 	.d_close =	aac_close,
216 	.d_ioctl =	aac_ioctl,
217 	.d_kqfilter =	aac_kqfilter
218 };
219 
220 static MALLOC_DEFINE(M_AACBUF, "aacbuf", "Buffers for the AAC driver");
221 
222 /* sysctl node */
223 static SYSCTL_NODE(_hw, OID_AUTO, aac, CTLFLAG_RD, 0, "AAC driver parameters");
224 
225 /*
226  * Device Interface
227  */
228 
229 /*
230  * Initialize the controller and softc
231  */
232 int
233 aac_attach(struct aac_softc *sc)
234 {
235 	int error, unit;
236 
237 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
238 
239 	/*
240 	 * Initialize per-controller queues.
241 	 */
242 	aac_initq_free(sc);
243 	aac_initq_ready(sc);
244 	aac_initq_busy(sc);
245 	aac_initq_bio(sc);
246 
247 	/*
248 	 * Initialize command-completion task.
249 	 */
250 	TASK_INIT(&sc->aac_task_complete, 0, aac_complete, sc);
251 
252 	/* mark controller as suspended until we get ourselves organised */
253 	sc->aac_state |= AAC_STATE_SUSPEND;
254 
255 	/*
256 	 * Check that the firmware on the card is supported.
257 	 */
258 	if ((error = aac_check_firmware(sc)) != 0)
259 		return(error);
260 
261 	/*
262 	 * Initialize locks
263 	 */
264 	lockinit(&sc->aac_aifq_lock, "AAC AIF lock", 0, LK_CANRECURSE);
265 	lockinit(&sc->aac_io_lock, "AAC I/O lock", 0, LK_CANRECURSE);
266 	lockinit(&sc->aac_container_lock, "AAC container lock", 0, LK_CANRECURSE);
267 	TAILQ_INIT(&sc->aac_container_tqh);
268 	TAILQ_INIT(&sc->aac_ev_cmfree);
269 
270 	/* Initialize the clock daemon callout. */
271 	callout_init(&sc->aac_daemontime);
272 
273 	/*
274 	 * Initialize the adapter.
275 	 */
276 	if ((error = aac_alloc(sc)) != 0)
277 		return(error);
278 	if ((error = aac_init(sc)) != 0)
279 		return(error);
280 
281 	/*
282 	 * Allocate and connect our interrupt.
283 	 */
284 	if ((error = aac_setup_intr(sc)) != 0)
285 		return(error);
286 
287 	/*
288 	 * Print a little information about the controller.
289 	 */
290 	aac_describe_controller(sc);
291 
292 	/*
293 	 * Add sysctls.
294 	 */
295 	sysctl_ctx_init(&sc->aac_sysctl_ctx);
296 	sc->aac_sysctl_tree = SYSCTL_ADD_NODE(&sc->aac_sysctl_ctx,
297 	    SYSCTL_STATIC_CHILDREN(_hw), OID_AUTO,
298 	    device_get_nameunit(sc->aac_dev), CTLFLAG_RD, 0, "");
299 	if (sc->aac_sysctl_tree == NULL) {
300 		device_printf(sc->aac_dev, "can't add sysctl node\n");
301 		return (EINVAL);
302 	}
303 	SYSCTL_ADD_INT(&sc->aac_sysctl_ctx,
304 	    SYSCTL_CHILDREN(sc->aac_sysctl_tree),
305 	    OID_AUTO, "firmware_build", CTLFLAG_RD,
306 	    &sc->aac_revision.buildNumber, 0,
307 	    "firmware build number");
308 
309 	/*
310 	 * Register to probe our containers later.
311 	 */
312 	sc->aac_ich.ich_func = aac_startup;
313 	sc->aac_ich.ich_arg = sc;
314 	sc->aac_ich.ich_desc = "aac";
315 	if (config_intrhook_establish(&sc->aac_ich) != 0) {
316 		device_printf(sc->aac_dev,
317 			      "can't establish configuration hook\n");
318 		return(ENXIO);
319 	}
320 
321 	/*
322 	 * Make the control device.
323 	 */
324 	unit = device_get_unit(sc->aac_dev);
325 	sc->aac_dev_t = make_dev(&aac_ops, unit, UID_ROOT, GID_OPERATOR,
326 				 0640, "aac%d", unit);
327 	(void)make_dev_alias(sc->aac_dev_t, "afa%d", unit);
328 	(void)make_dev_alias(sc->aac_dev_t, "hpn%d", unit);
329 	sc->aac_dev_t->si_drv1 = sc;
330 
331 	/* Create the AIF thread */
332 	if (kthread_create(aac_command_thread, sc,
333 			   &sc->aifthread, "aac%daif", unit))
334 		panic("Could not create AIF thread");
335 
336 	/* Register the shutdown method to only be called post-dump */
337 	if ((sc->eh = EVENTHANDLER_REGISTER(shutdown_final, aac_shutdown,
338 	    sc->aac_dev, SHUTDOWN_PRI_DEFAULT)) == NULL)
339 		device_printf(sc->aac_dev,
340 			      "shutdown event registration failed\n");
341 
342 	/* Register with CAM for the non-DASD devices */
343 	if ((sc->flags & AAC_FLAGS_ENABLE_CAM) != 0) {
344 		TAILQ_INIT(&sc->aac_sim_tqh);
345 		aac_get_bus_info(sc);
346 	}
347 
348 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
349 	callout_reset(&sc->aac_daemontime, 60 * hz, aac_daemon, sc);
350 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
351 
352 	return(0);
353 }
354 
355 static void
356 aac_daemon(void *arg)
357 {
358 	struct timeval tv;
359 	struct aac_softc *sc;
360 	struct aac_fib *fib;
361 
362 	sc = arg;
363 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
364 
365 	if (callout_pending(&sc->aac_daemontime) ||
366 	    callout_active(&sc->aac_daemontime) == 0)
367 		return;
368 	getmicrotime(&tv);
369 	aac_alloc_sync_fib(sc, &fib);
370 	*(uint32_t *)fib->data = tv.tv_sec;
371 	aac_sync_fib(sc, SendHostTime, 0, fib, sizeof(uint32_t));
372 	aac_release_sync_fib(sc);
373 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
374 	callout_reset(&sc->aac_daemontime, 30 * 60 * hz, aac_daemon, sc);
375 }
376 
377 void
378 aac_add_event(struct aac_softc *sc, struct aac_event *event)
379 {
380 
381 	switch (event->ev_type & AAC_EVENT_MASK) {
382 	case AAC_EVENT_CMFREE:
383 		TAILQ_INSERT_TAIL(&sc->aac_ev_cmfree, event, ev_links);
384 		break;
385 	default:
386 		device_printf(sc->aac_dev, "aac_add event: unknown event %d\n",
387 		    event->ev_type);
388 		break;
389 	}
390 
391 	return;
392 }
393 
394 /*
395  * Request information of container #cid
396  */
397 static struct aac_mntinforesp *
398 aac_get_container_info(struct aac_softc *sc, struct aac_fib *fib, int cid)
399 {
400 	struct aac_mntinfo *mi;
401 
402 	mi = (struct aac_mntinfo *)&fib->data[0];
403 	/* use 64-bit LBA if enabled */
404 	mi->Command = (sc->flags & AAC_FLAGS_LBA_64BIT) ?
405 	    VM_NameServe64 : VM_NameServe;
406 	mi->MntType = FT_FILESYS;
407 	mi->MntCount = cid;
408 
409 	if (aac_sync_fib(sc, ContainerCommand, 0, fib,
410 			 sizeof(struct aac_mntinfo))) {
411 		device_printf(sc->aac_dev, "Error probing container %d\n", cid);
412 		return (NULL);
413 	}
414 
415 	return ((struct aac_mntinforesp *)&fib->data[0]);
416 }
417 
418 /*
419  * Probe for containers, create disks.
420  */
421 static void
422 aac_startup(void *arg)
423 {
424 	struct aac_softc *sc;
425 	struct aac_fib *fib;
426 	struct aac_mntinforesp *mir;
427 	int count = 0, i = 0;
428 
429 	sc = (struct aac_softc *)arg;
430 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
431 
432 	/* disconnect ourselves from the intrhook chain */
433 	config_intrhook_disestablish(&sc->aac_ich);
434 
435 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
436 	aac_alloc_sync_fib(sc, &fib);
437 
438 	/* loop over possible containers */
439 	do {
440 		if ((mir = aac_get_container_info(sc, fib, i)) == NULL)
441 			continue;
442 		if (i == 0)
443 			count = mir->MntRespCount;
444 		aac_add_container(sc, mir, 0);
445 		i++;
446 	} while ((i < count) && (i < AAC_MAX_CONTAINERS));
447 
448 	aac_release_sync_fib(sc);
449 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
450 
451 	/* poke the bus to actually attach the child devices */
452 	if (bus_generic_attach(sc->aac_dev))
453 		device_printf(sc->aac_dev, "bus_generic_attach failed\n");
454 
455 	/* mark the controller up */
456 	sc->aac_state &= ~AAC_STATE_SUSPEND;
457 
458 	/* enable interrupts now */
459 	AAC_UNMASK_INTERRUPTS(sc);
460 }
461 
462 /*
463  * Create a device to represent a new container
464  */
465 static void
466 aac_add_container(struct aac_softc *sc, struct aac_mntinforesp *mir, int f)
467 {
468 	struct aac_container *co;
469 	device_t child;
470 
471 	/*
472 	 * Check container volume type for validity.  Note that many of
473 	 * the possible types may never show up.
474 	 */
475 	if ((mir->Status == ST_OK) && (mir->MntTable[0].VolType != CT_NONE)) {
476 		co = (struct aac_container *)kmalloc(sizeof *co, M_AACBUF,
477 		       M_INTWAIT | M_ZERO);
478 		fwprintf(sc, HBA_FLAGS_DBG_INIT_B, "id %x  name '%.16s'  size %u  type %d",
479 		      mir->MntTable[0].ObjectId,
480 		      mir->MntTable[0].FileSystemName,
481 		      mir->MntTable[0].Capacity, mir->MntTable[0].VolType);
482 
483 		if ((child = device_add_child(sc->aac_dev, "aacd", -1)) == NULL)
484 			device_printf(sc->aac_dev, "device_add_child failed\n");
485 		else
486 			device_set_ivars(child, co);
487 		device_set_desc(child, aac_describe_code(aac_container_types,
488 				mir->MntTable[0].VolType));
489 		co->co_disk = child;
490 		co->co_found = f;
491 		bcopy(&mir->MntTable[0], &co->co_mntobj,
492 		      sizeof(struct aac_mntobj));
493 		lockmgr(&sc->aac_container_lock, LK_EXCLUSIVE);
494 		TAILQ_INSERT_TAIL(&sc->aac_container_tqh, co, co_link);
495 		lockmgr(&sc->aac_container_lock, LK_RELEASE);
496 	}
497 }
498 
499 /*
500  * Allocate resources associated with (sc)
501  */
502 static int
503 aac_alloc(struct aac_softc *sc)
504 {
505 
506 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
507 
508 	/*
509 	 * Create DMA tag for mapping buffers into controller-addressable space.
510 	 */
511 	if (bus_dma_tag_create(sc->aac_parent_dmat, 	/* parent */
512 			       1, 0, 			/* algnmnt, boundary */
513 			       (sc->flags & AAC_FLAGS_SG_64BIT) ?
514 			       BUS_SPACE_MAXADDR :
515 			       BUS_SPACE_MAXADDR_32BIT,	/* lowaddr */
516 			       BUS_SPACE_MAXADDR, 	/* highaddr */
517 			       NULL, NULL, 		/* filter, filterarg */
518 			       MAXBSIZE,		/* maxsize */
519 			       sc->aac_sg_tablesize,	/* nsegments */
520 			       MAXBSIZE,		/* maxsegsize */
521 			       BUS_DMA_ALLOCNOW,	/* flags */
522 			       &sc->aac_buffer_dmat)) {
523 		device_printf(sc->aac_dev, "can't allocate buffer DMA tag\n");
524 		return (ENOMEM);
525 	}
526 
527 	/*
528 	 * Create DMA tag for mapping FIBs into controller-addressable space..
529 	 */
530 	if (bus_dma_tag_create(sc->aac_parent_dmat,	/* parent */
531 			       1, 0, 			/* algnmnt, boundary */
532 			       (sc->flags & AAC_FLAGS_4GB_WINDOW) ?
533 			       BUS_SPACE_MAXADDR_32BIT :
534 			       0x7fffffff,		/* lowaddr */
535 			       BUS_SPACE_MAXADDR, 	/* highaddr */
536 			       NULL, NULL, 		/* filter, filterarg */
537 			       sc->aac_max_fibs_alloc *
538 			       sc->aac_max_fib_size,  /* maxsize */
539 			       1,			/* nsegments */
540 			       sc->aac_max_fibs_alloc *
541 			       sc->aac_max_fib_size,	/* maxsize */
542 			       0,			/* flags */
543 			       &sc->aac_fib_dmat)) {
544 		device_printf(sc->aac_dev, "can't allocate FIB DMA tag\n");
545 		return (ENOMEM);
546 	}
547 
548 	/*
549 	 * Create DMA tag for the common structure and allocate it.
550 	 */
551 	if (bus_dma_tag_create(sc->aac_parent_dmat, 	/* parent */
552 			       1, 0,			/* algnmnt, boundary */
553 			       (sc->flags & AAC_FLAGS_4GB_WINDOW) ?
554 			       BUS_SPACE_MAXADDR_32BIT :
555 			       0x7fffffff,		/* lowaddr */
556 			       BUS_SPACE_MAXADDR, 	/* highaddr */
557 			       NULL, NULL, 		/* filter, filterarg */
558 			       8192 + sizeof(struct aac_common), /* maxsize */
559 			       1,			/* nsegments */
560 			       BUS_SPACE_MAXSIZE_32BIT,	/* maxsegsize */
561 			       0,			/* flags */
562 			       &sc->aac_common_dmat)) {
563 		device_printf(sc->aac_dev,
564 			      "can't allocate common structure DMA tag\n");
565 		return (ENOMEM);
566 	}
567 	if (bus_dmamem_alloc(sc->aac_common_dmat, (void **)&sc->aac_common,
568 			     BUS_DMA_NOWAIT, &sc->aac_common_dmamap)) {
569 		device_printf(sc->aac_dev, "can't allocate common structure\n");
570 		return (ENOMEM);
571 	}
572 
573 	/*
574 	 * Work around a bug in the 2120 and 2200 that cannot DMA commands
575 	 * below address 8192 in physical memory.
576 	 * XXX If the padding is not needed, can it be put to use instead
577 	 * of ignored?
578 	 */
579 	(void)bus_dmamap_load(sc->aac_common_dmat, sc->aac_common_dmamap,
580 			sc->aac_common, 8192 + sizeof(*sc->aac_common),
581 			aac_common_map, sc, 0);
582 
583 	if (sc->aac_common_busaddr < 8192) {
584 		sc->aac_common = (struct aac_common *)
585 		    ((uint8_t *)sc->aac_common + 8192);
586 		sc->aac_common_busaddr += 8192;
587 	}
588 	bzero(sc->aac_common, sizeof(*sc->aac_common));
589 
590 	/* Allocate some FIBs and associated command structs */
591 	TAILQ_INIT(&sc->aac_fibmap_tqh);
592 	sc->aac_commands = kmalloc(sc->aac_max_fibs * sizeof(struct aac_command),
593 				  M_AACBUF, M_WAITOK|M_ZERO);
594 	while (sc->total_fibs < sc->aac_max_fibs) {
595 		if (aac_alloc_commands(sc) != 0)
596 			break;
597 	}
598 	if (sc->total_fibs == 0)
599 		return (ENOMEM);
600 
601 	return (0);
602 }
603 
604 /*
605  * Free all of the resources associated with (sc)
606  *
607  * Should not be called if the controller is active.
608  */
609 void
610 aac_free(struct aac_softc *sc)
611 {
612 
613 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
614 
615 	/* remove the control device */
616 	if (sc->aac_dev_t != NULL)
617 		destroy_dev(sc->aac_dev_t);
618 
619 	/* throw away any FIB buffers, discard the FIB DMA tag */
620 	aac_free_commands(sc);
621 	if (sc->aac_fib_dmat)
622 		bus_dma_tag_destroy(sc->aac_fib_dmat);
623 
624 	kfree(sc->aac_commands, M_AACBUF);
625 
626 	/* destroy the common area */
627 	if (sc->aac_common) {
628 		bus_dmamap_unload(sc->aac_common_dmat, sc->aac_common_dmamap);
629 		bus_dmamem_free(sc->aac_common_dmat, sc->aac_common,
630 				sc->aac_common_dmamap);
631 	}
632 	if (sc->aac_common_dmat)
633 		bus_dma_tag_destroy(sc->aac_common_dmat);
634 
635 	/* disconnect the interrupt handler */
636 	if (sc->aac_intr)
637 		bus_teardown_intr(sc->aac_dev, sc->aac_irq, sc->aac_intr);
638 	if (sc->aac_irq != NULL)
639 		bus_release_resource(sc->aac_dev, SYS_RES_IRQ, sc->aac_irq_rid,
640 				     sc->aac_irq);
641 
642 	/* destroy data-transfer DMA tag */
643 	if (sc->aac_buffer_dmat)
644 		bus_dma_tag_destroy(sc->aac_buffer_dmat);
645 
646 	/* destroy the parent DMA tag */
647 	if (sc->aac_parent_dmat)
648 		bus_dma_tag_destroy(sc->aac_parent_dmat);
649 
650 	/* release the register window mapping */
651 	if (sc->aac_regs_res0 != NULL)
652 		bus_release_resource(sc->aac_dev, SYS_RES_MEMORY,
653 				     sc->aac_regs_rid0, sc->aac_regs_res0);
654 	if (sc->aac_hwif == AAC_HWIF_NARK && sc->aac_regs_res1 != NULL)
655 		bus_release_resource(sc->aac_dev, SYS_RES_MEMORY,
656 				     sc->aac_regs_rid1, sc->aac_regs_res1);
657 	dev_ops_remove_minor(&aac_ops, device_get_unit(sc->aac_dev));
658 
659 	sysctl_ctx_free(&sc->aac_sysctl_ctx);
660 }
661 
662 /*
663  * Disconnect from the controller completely, in preparation for unload.
664  */
665 int
666 aac_detach(device_t dev)
667 {
668 	struct aac_softc *sc;
669 	struct aac_container *co;
670 	struct aac_sim	*sim;
671 	int error;
672 
673 	sc = device_get_softc(dev);
674 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
675 
676 #if 0 /* XXX swildner */
677 	callout_drain(&sc->aac_daemontime);
678 #else
679 	callout_stop(&sc->aac_daemontime);
680 #endif
681 
682 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
683 	while (sc->aifflags & AAC_AIFFLAGS_RUNNING) {
684 		sc->aifflags |= AAC_AIFFLAGS_EXIT;
685 		wakeup(sc->aifthread);
686 		lksleep(sc->aac_dev, &sc->aac_io_lock, 0, "aacdch", 0);
687 	}
688 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
689 	KASSERT((sc->aifflags & AAC_AIFFLAGS_RUNNING) == 0,
690 	    ("%s: invalid detach state", __func__));
691 
692 	/* Remove the child containers */
693 	while ((co = TAILQ_FIRST(&sc->aac_container_tqh)) != NULL) {
694 		error = device_delete_child(dev, co->co_disk);
695 		if (error)
696 			return (error);
697 		TAILQ_REMOVE(&sc->aac_container_tqh, co, co_link);
698 		kfree(co, M_AACBUF);
699 	}
700 
701 	/* Remove the CAM SIMs */
702 	while ((sim = TAILQ_FIRST(&sc->aac_sim_tqh)) != NULL) {
703 		TAILQ_REMOVE(&sc->aac_sim_tqh, sim, sim_link);
704 		error = device_delete_child(dev, sim->sim_dev);
705 		if (error)
706 			return (error);
707 		kfree(sim, M_AACBUF);
708 	}
709 
710 	if ((error = aac_shutdown(dev)))
711 		return(error);
712 
713 	EVENTHANDLER_DEREGISTER(shutdown_final, sc->eh);
714 
715 	aac_free(sc);
716 
717 	lockuninit(&sc->aac_aifq_lock);
718 	lockuninit(&sc->aac_io_lock);
719 	lockuninit(&sc->aac_container_lock);
720 
721 	return(0);
722 }
723 
724 /*
725  * Bring the controller down to a dormant state and detach all child devices.
726  *
727  * This function is called before detach or system shutdown.
728  *
729  * Note that we can assume that the bioq on the controller is empty, as we won't
730  * allow shutdown if any device is open.
731  */
732 int
733 aac_shutdown(device_t dev)
734 {
735 	struct aac_softc *sc;
736 	struct aac_fib *fib;
737 	struct aac_close_command *cc;
738 
739 	sc = device_get_softc(dev);
740 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
741 
742 	sc->aac_state |= AAC_STATE_SUSPEND;
743 
744 	/*
745 	 * Send a Container shutdown followed by a HostShutdown FIB to the
746 	 * controller to convince it that we don't want to talk to it anymore.
747 	 * We've been closed and all I/O completed already
748 	 */
749 	device_printf(sc->aac_dev, "shutting down controller...");
750 
751 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
752 	aac_alloc_sync_fib(sc, &fib);
753 	cc = (struct aac_close_command *)&fib->data[0];
754 
755 	bzero(cc, sizeof(struct aac_close_command));
756 	cc->Command = VM_CloseAll;
757 	cc->ContainerId = 0xffffffff;
758 	if (aac_sync_fib(sc, ContainerCommand, 0, fib,
759 	    sizeof(struct aac_close_command)))
760 		kprintf("FAILED.\n");
761 	else
762 		kprintf("done\n");
763 #if 0
764 	else {
765 		fib->data[0] = 0;
766 		/*
767 		 * XXX Issuing this command to the controller makes it shut down
768 		 * but also keeps it from coming back up without a reset of the
769 		 * PCI bus.  This is not desirable if you are just unloading the
770 		 * driver module with the intent to reload it later.
771 		 */
772 		if (aac_sync_fib(sc, FsaHostShutdown, AAC_FIBSTATE_SHUTDOWN,
773 		    fib, 1)) {
774 			kprintf("FAILED.\n");
775 		} else {
776 			kprintf("done.\n");
777 		}
778 	}
779 #endif
780 
781 	AAC_MASK_INTERRUPTS(sc);
782 	aac_release_sync_fib(sc);
783 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
784 
785 	return(0);
786 }
787 
788 /*
789  * Bring the controller to a quiescent state, ready for system suspend.
790  */
791 int
792 aac_suspend(device_t dev)
793 {
794 	struct aac_softc *sc;
795 
796 	sc = device_get_softc(dev);
797 
798 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
799 	sc->aac_state |= AAC_STATE_SUSPEND;
800 
801 	AAC_MASK_INTERRUPTS(sc);
802 	return(0);
803 }
804 
805 /*
806  * Bring the controller back to a state ready for operation.
807  */
808 int
809 aac_resume(device_t dev)
810 {
811 	struct aac_softc *sc;
812 
813 	sc = device_get_softc(dev);
814 
815 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
816 	sc->aac_state &= ~AAC_STATE_SUSPEND;
817 	AAC_UNMASK_INTERRUPTS(sc);
818 	return(0);
819 }
820 
821 /*
822  * Interrupt handler for NEW_COMM interface.
823  */
824 void
825 aac_new_intr(void *arg)
826 {
827 	struct aac_softc *sc;
828 	u_int32_t index, fast;
829 	struct aac_command *cm;
830 	struct aac_fib *fib;
831 	int i;
832 
833 	sc = (struct aac_softc *)arg;
834 
835 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
836 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
837 	while (1) {
838 		index = AAC_GET_OUTB_QUEUE(sc);
839 		if (index == 0xffffffff)
840 			index = AAC_GET_OUTB_QUEUE(sc);
841 		if (index == 0xffffffff)
842 			break;
843 		if (index & 2) {
844 			if (index == 0xfffffffe) {
845 				/* XXX This means that the controller wants
846 				 * more work.  Ignore it for now.
847 				 */
848 				continue;
849 			}
850 			/* AIF */
851 			fib = (struct aac_fib *)kmalloc(sizeof *fib, M_AACBUF,
852 				   M_INTWAIT | M_ZERO);
853 			index &= ~2;
854 			for (i = 0; i < sizeof(struct aac_fib)/4; ++i)
855 				((u_int32_t *)fib)[i] = AAC_MEM1_GETREG4(sc, index + i*4);
856 			aac_handle_aif(sc, fib);
857 			kfree(fib, M_AACBUF);
858 
859 			/*
860 			 * AIF memory is owned by the adapter, so let it
861 			 * know that we are done with it.
862 			 */
863 			AAC_SET_OUTB_QUEUE(sc, index);
864 			AAC_CLEAR_ISTATUS(sc, AAC_DB_RESPONSE_READY);
865 		} else {
866 			fast = index & 1;
867 			cm = sc->aac_commands + (index >> 2);
868 			fib = cm->cm_fib;
869 			if (fast) {
870 				fib->Header.XferState |= AAC_FIBSTATE_DONEADAP;
871 				*((u_int32_t *)(fib->data)) = AAC_ERROR_NORMAL;
872 			}
873 			aac_remove_busy(cm);
874  			aac_unmap_command(cm);
875 			cm->cm_flags |= AAC_CMD_COMPLETED;
876 
877 			/* is there a completion handler? */
878 			if (cm->cm_complete != NULL) {
879 				cm->cm_complete(cm);
880 			} else {
881 				/* assume that someone is sleeping on this
882 				 * command
883 				 */
884 				wakeup(cm);
885 			}
886 			sc->flags &= ~AAC_QUEUE_FRZN;
887 		}
888 	}
889 	/* see if we can start some more I/O */
890 	if ((sc->flags & AAC_QUEUE_FRZN) == 0)
891 		aac_startio(sc);
892 
893 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
894 }
895 
896 /*
897  * Interrupt filter for !NEW_COMM interface.
898  */
899 void
900 aac_filter(void *arg)
901 {
902 	struct aac_softc *sc;
903 	u_int16_t reason;
904 
905 	sc = (struct aac_softc *)arg;
906 
907 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
908 	/*
909 	 * Read the status register directly.  This is faster than taking the
910 	 * driver lock and reading the queues directly.  It also saves having
911 	 * to turn parts of the driver lock into a spin mutex, which would be
912 	 * ugly.
913 	 */
914 	reason = AAC_GET_ISTATUS(sc);
915 	AAC_CLEAR_ISTATUS(sc, reason);
916 
917 	/* handle completion processing */
918 	if (reason & AAC_DB_RESPONSE_READY)
919 		taskqueue_enqueue(taskqueue_swi, &sc->aac_task_complete);
920 
921 	/* controller wants to talk to us */
922 	if (reason & (AAC_DB_PRINTF | AAC_DB_COMMAND_READY)) {
923 		/*
924 		 * XXX Make sure that we don't get fooled by strange messages
925 		 * that start with a NULL.
926 		 */
927 		if ((reason & AAC_DB_PRINTF) &&
928 			(sc->aac_common->ac_printf[0] == 0))
929 			sc->aac_common->ac_printf[0] = 32;
930 
931 		/*
932 		 * This might miss doing the actual wakeup.  However, the
933 		 * lksleep that this is waking up has a timeout, so it will
934 		 * wake up eventually.  AIFs and printfs are low enough
935 		 * priority that they can handle hanging out for a few seconds
936 		 * if needed.
937 		 */
938 		wakeup(sc->aifthread);
939 	}
940 }
941 
942 /*
943  * Command Processing
944  */
945 
946 /*
947  * Start as much queued I/O as possible on the controller
948  */
949 void
950 aac_startio(struct aac_softc *sc)
951 {
952 	struct aac_command *cm;
953 	int error;
954 
955 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
956 
957 	for (;;) {
958 		/*
959 		 * This flag might be set if the card is out of resources.
960 		 * Checking it here prevents an infinite loop of deferrals.
961 		 */
962 		if (sc->flags & AAC_QUEUE_FRZN)
963 			break;
964 
965 		/*
966 		 * Try to get a command that's been put off for lack of
967 		 * resources
968 		 */
969 		cm = aac_dequeue_ready(sc);
970 
971 		/*
972 		 * Try to build a command off the bio queue (ignore error
973 		 * return)
974 		 */
975 		if (cm == NULL)
976 			aac_bio_command(sc, &cm);
977 
978 		/* nothing to do? */
979 		if (cm == NULL)
980 			break;
981 
982 		/* don't map more than once */
983 		if (cm->cm_flags & AAC_CMD_MAPPED)
984 			panic("aac: command %p already mapped", cm);
985 
986 		/*
987 		 * Set up the command to go to the controller.  If there are no
988 		 * data buffers associated with the command then it can bypass
989 		 * busdma.
990 		 */
991 		if (cm->cm_datalen != 0) {
992 			error = bus_dmamap_load(sc->aac_buffer_dmat,
993 						cm->cm_datamap, cm->cm_data,
994 						cm->cm_datalen,
995 						aac_map_command_sg, cm, 0);
996 			if (error == EINPROGRESS) {
997 				fwprintf(sc, HBA_FLAGS_DBG_COMM_B, "freezing queue\n");
998 				sc->flags |= AAC_QUEUE_FRZN;
999 				error = 0;
1000 			} else if (error != 0)
1001 				panic("aac_startio: unexpected error %d from "
1002 				      "busdma", error);
1003 		} else
1004 			aac_map_command_sg(cm, NULL, 0, 0);
1005 	}
1006 }
1007 
1008 /*
1009  * Handle notification of one or more FIBs coming from the controller.
1010  */
1011 static void
1012 aac_command_thread(void *arg)
1013 {
1014 	struct aac_softc *sc = arg;
1015 	struct aac_fib *fib;
1016 	u_int32_t fib_size;
1017 	int size, retval;
1018 
1019 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1020 
1021 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
1022 	sc->aifflags = AAC_AIFFLAGS_RUNNING;
1023 
1024 	while ((sc->aifflags & AAC_AIFFLAGS_EXIT) == 0) {
1025 
1026 		retval = 0;
1027 		if ((sc->aifflags & AAC_AIFFLAGS_PENDING) == 0)
1028 			retval = lksleep(sc->aifthread, &sc->aac_io_lock, 0,
1029 					"aifthd", AAC_PERIODIC_INTERVAL * hz);
1030 
1031 		/*
1032 		 * First see if any FIBs need to be allocated.  This needs
1033 		 * to be called without the driver lock because contigmalloc
1034 		 * can sleep.
1035 		 */
1036 		if ((sc->aifflags & AAC_AIFFLAGS_ALLOCFIBS) != 0) {
1037 			lockmgr(&sc->aac_io_lock, LK_RELEASE);
1038 			aac_alloc_commands(sc);
1039 			lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
1040 			sc->aifflags &= ~AAC_AIFFLAGS_ALLOCFIBS;
1041 			aac_startio(sc);
1042 		}
1043 
1044 		/*
1045 		 * While we're here, check to see if any commands are stuck.
1046 		 * This is pretty low-priority, so it's ok if it doesn't
1047 		 * always fire.
1048 		 */
1049 		if (retval == EWOULDBLOCK)
1050 			aac_timeout(sc);
1051 
1052 		/* Check the hardware printf message buffer */
1053 		if (sc->aac_common->ac_printf[0] != 0)
1054 			aac_print_printf(sc);
1055 
1056 		/* Also check to see if the adapter has a command for us. */
1057 		if (sc->flags & AAC_FLAGS_NEW_COMM)
1058 			continue;
1059 		for (;;) {
1060 			if (aac_dequeue_fib(sc, AAC_HOST_NORM_CMD_QUEUE,
1061 					   &fib_size, &fib))
1062 				break;
1063 
1064 			AAC_PRINT_FIB(sc, fib);
1065 
1066 			switch (fib->Header.Command) {
1067 			case AifRequest:
1068 				aac_handle_aif(sc, fib);
1069 				break;
1070 			default:
1071 				device_printf(sc->aac_dev, "unknown command "
1072 					      "from controller\n");
1073 				break;
1074 			}
1075 
1076 			if ((fib->Header.XferState == 0) ||
1077 			    (fib->Header.StructType != AAC_FIBTYPE_TFIB)) {
1078 				break;
1079 			}
1080 
1081 			/* Return the AIF to the controller. */
1082 			if (fib->Header.XferState & AAC_FIBSTATE_FROMADAP) {
1083 				fib->Header.XferState |= AAC_FIBSTATE_DONEHOST;
1084 				*(AAC_FSAStatus*)fib->data = ST_OK;
1085 
1086 				/* XXX Compute the Size field? */
1087 				size = fib->Header.Size;
1088 				if (size > sizeof(struct aac_fib)) {
1089 					size = sizeof(struct aac_fib);
1090 					fib->Header.Size = size;
1091 				}
1092 				/*
1093 				 * Since we did not generate this command, it
1094 				 * cannot go through the normal
1095 				 * enqueue->startio chain.
1096 				 */
1097 				aac_enqueue_response(sc,
1098 						 AAC_ADAP_NORM_RESP_QUEUE,
1099 						 fib);
1100 			}
1101 		}
1102 	}
1103 	sc->aifflags &= ~AAC_AIFFLAGS_RUNNING;
1104 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
1105 	wakeup(sc->aac_dev);
1106 }
1107 
1108 /*
1109  * Process completed commands.
1110  */
1111 static void
1112 aac_complete(void *context, int pending)
1113 {
1114 	struct aac_softc *sc;
1115 	struct aac_command *cm;
1116 	struct aac_fib *fib;
1117 	u_int32_t fib_size;
1118 
1119 	sc = (struct aac_softc *)context;
1120 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1121 
1122 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
1123 
1124 	/* pull completed commands off the queue */
1125 	for (;;) {
1126 		/* look for completed FIBs on our queue */
1127 		if (aac_dequeue_fib(sc, AAC_HOST_NORM_RESP_QUEUE, &fib_size,
1128 							&fib))
1129 			break;	/* nothing to do */
1130 
1131 		/* get the command, unmap and hand off for processing */
1132 		cm = sc->aac_commands + fib->Header.SenderData;
1133 		if (cm == NULL) {
1134 			AAC_PRINT_FIB(sc, fib);
1135 			break;
1136 		}
1137 		if ((cm->cm_flags & AAC_CMD_TIMEDOUT) != 0)
1138 			device_printf(sc->aac_dev,
1139 			    "COMMAND %p COMPLETED AFTER %d SECONDS\n",
1140 			    cm, (int)(time_second-cm->cm_timestamp));
1141 
1142 		aac_remove_busy(cm);
1143 
1144 		aac_unmap_command(cm);
1145 		cm->cm_flags |= AAC_CMD_COMPLETED;
1146 
1147 		/* is there a completion handler? */
1148 		if (cm->cm_complete != NULL) {
1149 			cm->cm_complete(cm);
1150 		} else {
1151 			/* assume that someone is sleeping on this command */
1152 			wakeup(cm);
1153 		}
1154 	}
1155 
1156 	/* see if we can start some more I/O */
1157 	sc->flags &= ~AAC_QUEUE_FRZN;
1158 	aac_startio(sc);
1159 
1160 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
1161 }
1162 
1163 /*
1164  * Handle a bio submitted from a disk device.
1165  */
1166 void
1167 aac_submit_bio(struct aac_disk *ad, struct bio *bio)
1168 {
1169 	struct aac_softc *sc;
1170 
1171 	bio->bio_driver_info = ad;
1172 	sc = ad->ad_controller;
1173 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1174 
1175 	/* queue the BIO and try to get some work done */
1176 	aac_enqueue_bio(sc, bio);
1177 	aac_startio(sc);
1178 }
1179 
1180 /*
1181  * Get a bio and build a command to go with it.
1182  */
1183 static int
1184 aac_bio_command(struct aac_softc *sc, struct aac_command **cmp)
1185 {
1186 	struct aac_command *cm;
1187 	struct aac_fib *fib;
1188 	struct aac_disk *ad;
1189 	struct bio *bio;
1190 	struct buf *bp;
1191 
1192 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1193 
1194 	/* get the resources we will need */
1195 	cm = NULL;
1196 	bio = NULL;
1197 	if (aac_alloc_command(sc, &cm))	/* get a command */
1198 		goto fail;
1199 	if ((bio = aac_dequeue_bio(sc)) == NULL)
1200 		goto fail;
1201 
1202 	/* fill out the command */
1203 	bp = bio->bio_buf;
1204 	cm->cm_data = (void *)bp->b_data;
1205 	cm->cm_datalen = bp->b_bcount;
1206 	cm->cm_complete = aac_bio_complete;
1207 	cm->cm_private = bio;
1208 	cm->cm_timestamp = time_second;
1209 
1210 	/* build the FIB */
1211 	fib = cm->cm_fib;
1212 	fib->Header.Size = sizeof(struct aac_fib_header);
1213 	fib->Header.XferState =
1214 		AAC_FIBSTATE_HOSTOWNED   |
1215 		AAC_FIBSTATE_INITIALISED |
1216 		AAC_FIBSTATE_EMPTY	 |
1217 		AAC_FIBSTATE_FROMHOST	 |
1218 		AAC_FIBSTATE_REXPECTED   |
1219 		AAC_FIBSTATE_NORM	 |
1220 		AAC_FIBSTATE_ASYNC	 |
1221 		AAC_FIBSTATE_FAST_RESPONSE;
1222 
1223 	/* build the read/write request */
1224 	ad = (struct aac_disk *)bio->bio_driver_info;
1225 
1226 	if (sc->flags & AAC_FLAGS_RAW_IO) {
1227 		struct aac_raw_io *raw;
1228 		raw = (struct aac_raw_io *)&fib->data[0];
1229 		fib->Header.Command = RawIo;
1230 		raw->BlockNumber = bio->bio_offset / AAC_BLOCK_SIZE;
1231 		raw->ByteCount = bp->b_bcount;
1232 		raw->ContainerId = ad->ad_container->co_mntobj.ObjectId;
1233 		raw->BpTotal = 0;
1234 		raw->BpComplete = 0;
1235 		fib->Header.Size += sizeof(struct aac_raw_io);
1236 		cm->cm_sgtable = (struct aac_sg_table *)&raw->SgMapRaw;
1237 		if (bp->b_cmd == BUF_CMD_READ) {
1238 			raw->Flags = 1;
1239 			cm->cm_flags |= AAC_CMD_DATAIN;
1240 		} else {
1241 			raw->Flags = 0;
1242 			cm->cm_flags |= AAC_CMD_DATAOUT;
1243 		}
1244 	} else if ((sc->flags & AAC_FLAGS_SG_64BIT) == 0) {
1245 		fib->Header.Command = ContainerCommand;
1246 		if (bp->b_cmd == BUF_CMD_READ) {
1247 			struct aac_blockread *br;
1248 			br = (struct aac_blockread *)&fib->data[0];
1249 			br->Command = VM_CtBlockRead;
1250 			br->ContainerId = ad->ad_container->co_mntobj.ObjectId;
1251 			br->BlockNumber = bio->bio_offset / AAC_BLOCK_SIZE;
1252 			br->ByteCount = bp->b_bcount;
1253 			fib->Header.Size += sizeof(struct aac_blockread);
1254 			cm->cm_sgtable = &br->SgMap;
1255 			cm->cm_flags |= AAC_CMD_DATAIN;
1256 		} else {
1257 			struct aac_blockwrite *bw;
1258 			bw = (struct aac_blockwrite *)&fib->data[0];
1259 			bw->Command = VM_CtBlockWrite;
1260 			bw->ContainerId = ad->ad_container->co_mntobj.ObjectId;
1261 			bw->BlockNumber = bio->bio_offset / AAC_BLOCK_SIZE;
1262 			bw->ByteCount = bp->b_bcount;
1263 			bw->Stable = CUNSTABLE;
1264 			fib->Header.Size += sizeof(struct aac_blockwrite);
1265 			cm->cm_flags |= AAC_CMD_DATAOUT;
1266 			cm->cm_sgtable = &bw->SgMap;
1267 		}
1268 	} else {
1269 		fib->Header.Command = ContainerCommand64;
1270 		if (bp->b_cmd == BUF_CMD_READ) {
1271 			struct aac_blockread64 *br;
1272 			br = (struct aac_blockread64 *)&fib->data[0];
1273 			br->Command = VM_CtHostRead64;
1274 			br->ContainerId = ad->ad_container->co_mntobj.ObjectId;
1275 			br->SectorCount = bp->b_bcount / AAC_BLOCK_SIZE;
1276 			br->BlockNumber = bio->bio_offset / AAC_BLOCK_SIZE;
1277 			br->Pad = 0;
1278 			br->Flags = 0;
1279 			fib->Header.Size += sizeof(struct aac_blockread64);
1280 			cm->cm_flags |= AAC_CMD_DATAIN;
1281 			cm->cm_sgtable = (struct aac_sg_table *)&br->SgMap64;
1282 		} else {
1283 			struct aac_blockwrite64 *bw;
1284 			bw = (struct aac_blockwrite64 *)&fib->data[0];
1285 			bw->Command = VM_CtHostWrite64;
1286 			bw->ContainerId = ad->ad_container->co_mntobj.ObjectId;
1287 			bw->SectorCount = bp->b_bcount / AAC_BLOCK_SIZE;
1288 			bw->BlockNumber = bio->bio_offset / AAC_BLOCK_SIZE;
1289 			bw->Pad = 0;
1290 			bw->Flags = 0;
1291 			fib->Header.Size += sizeof(struct aac_blockwrite64);
1292 			cm->cm_flags |= AAC_CMD_DATAOUT;
1293 			cm->cm_sgtable = (struct aac_sg_table *)&bw->SgMap64;
1294 		}
1295 	}
1296 
1297 	*cmp = cm;
1298 	return(0);
1299 
1300 fail:
1301 	if (bio != NULL)
1302 		aac_enqueue_bio(sc, bio);
1303 	if (cm != NULL)
1304 		aac_release_command(cm);
1305 	return(ENOMEM);
1306 }
1307 
1308 /*
1309  * Handle a bio-instigated command that has been completed.
1310  */
1311 static void
1312 aac_bio_complete(struct aac_command *cm)
1313 {
1314 	struct aac_blockread_response *brr;
1315 	struct aac_blockwrite_response *bwr;
1316 	struct bio *bio;
1317 	struct buf *bp;
1318 	const char *code;
1319 	AAC_FSAStatus status;
1320 
1321 	/* fetch relevant status and then release the command */
1322 	bio = (struct bio *)cm->cm_private;
1323 	bp = bio->bio_buf;
1324 	if (bp->b_cmd == BUF_CMD_READ) {
1325 		brr = (struct aac_blockread_response *)&cm->cm_fib->data[0];
1326 		status = brr->Status;
1327 	} else {
1328 		bwr = (struct aac_blockwrite_response *)&cm->cm_fib->data[0];
1329 		status = bwr->Status;
1330 	}
1331 	aac_release_command(cm);
1332 
1333 	/* fix up the bio based on status */
1334 	if (status == ST_OK) {
1335 		bp->b_resid = 0;
1336 		code = NULL;
1337 	} else {
1338 		bp->b_error = EIO;
1339 		bp->b_flags |= B_ERROR;
1340 		/* pass an error string out to the disk layer */
1341 		code = aac_describe_code(aac_command_status_table, status);
1342 	}
1343 	aac_biodone(bio, code);
1344 }
1345 
1346 /*
1347  * Submit a command to the controller, return when it completes.
1348  * XXX This is very dangerous!  If the card has gone out to lunch, we could
1349  *     be stuck here forever.  At the same time, signals are not caught
1350  *     because there is a risk that a signal could wakeup the sleep before
1351  *     the card has a chance to complete the command.  Since there is no way
1352  *     to cancel a command that is in progress, we can't protect against the
1353  *     card completing a command late and spamming the command and data
1354  *     memory.  So, we are held hostage until the command completes.
1355  */
1356 static int
1357 aac_wait_command(struct aac_command *cm)
1358 {
1359 	struct aac_softc *sc;
1360 	int error;
1361 
1362 	sc = cm->cm_sc;
1363 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1364 
1365 	/* Put the command on the ready queue and get things going */
1366 	aac_enqueue_ready(cm);
1367 	aac_startio(sc);
1368 	error = lksleep(cm, &sc->aac_io_lock, 0, "aacwait", 0);
1369 	return(error);
1370 }
1371 
1372 /*
1373  *Command Buffer Management
1374  */
1375 
1376 /*
1377  * Allocate a command.
1378  */
1379 int
1380 aac_alloc_command(struct aac_softc *sc, struct aac_command **cmp)
1381 {
1382 	struct aac_command *cm;
1383 
1384 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1385 
1386 	if ((cm = aac_dequeue_free(sc)) == NULL) {
1387 		if (sc->total_fibs < sc->aac_max_fibs) {
1388 			lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
1389 			sc->aifflags |= AAC_AIFFLAGS_ALLOCFIBS;
1390 			lockmgr(&sc->aac_io_lock, LK_RELEASE);
1391 			wakeup(sc->aifthread);
1392 		}
1393 		return (EBUSY);
1394 	}
1395 
1396 	*cmp = cm;
1397 	return(0);
1398 }
1399 
1400 /*
1401  * Release a command back to the freelist.
1402  */
1403 void
1404 aac_release_command(struct aac_command *cm)
1405 {
1406 	struct aac_event *event;
1407 	struct aac_softc *sc;
1408 
1409 	sc = cm->cm_sc;
1410 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1411 
1412 	/* (re)initialize the command/FIB */
1413 	cm->cm_sgtable = NULL;
1414 	cm->cm_flags = 0;
1415 	cm->cm_complete = NULL;
1416 	cm->cm_private = NULL;
1417 	cm->cm_queue = AAC_ADAP_NORM_CMD_QUEUE;
1418 	cm->cm_fib->Header.XferState = AAC_FIBSTATE_EMPTY;
1419 	cm->cm_fib->Header.StructType = AAC_FIBTYPE_TFIB;
1420 	cm->cm_fib->Header.Flags = 0;
1421 	cm->cm_fib->Header.SenderSize = cm->cm_sc->aac_max_fib_size;
1422 
1423 	/*
1424 	 * These are duplicated in aac_start to cover the case where an
1425 	 * intermediate stage may have destroyed them.  They're left
1426 	 * initialized here for debugging purposes only.
1427 	 */
1428 	cm->cm_fib->Header.ReceiverFibAddress = (u_int32_t)cm->cm_fibphys;
1429 	cm->cm_fib->Header.SenderData = 0;
1430 
1431 	aac_enqueue_free(cm);
1432 
1433 	if ((event = TAILQ_FIRST(&sc->aac_ev_cmfree)) != NULL) {
1434 		TAILQ_REMOVE(&sc->aac_ev_cmfree, event, ev_links);
1435 		event->ev_callback(sc, event, event->ev_arg);
1436 	}
1437 }
1438 
1439 /*
1440  * Map helper for command/FIB allocation.
1441  */
1442 static void
1443 aac_map_command_helper(void *arg, bus_dma_segment_t *segs, int nseg, int error)
1444 {
1445 	uint64_t	*fibphys;
1446 
1447 	fibphys = (uint64_t *)arg;
1448 
1449 	*fibphys = segs[0].ds_addr;
1450 }
1451 
1452 /*
1453  * Allocate and initialize commands/FIBs for this adapter.
1454  */
1455 static int
1456 aac_alloc_commands(struct aac_softc *sc)
1457 {
1458 	struct aac_command *cm;
1459 	struct aac_fibmap *fm;
1460 	uint64_t fibphys;
1461 	int i, error;
1462 
1463 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1464 
1465 	if (sc->total_fibs + sc->aac_max_fibs_alloc > sc->aac_max_fibs)
1466 		return (ENOMEM);
1467 
1468 	fm = kmalloc(sizeof(struct aac_fibmap), M_AACBUF, M_INTWAIT | M_ZERO);
1469 
1470 	/* allocate the FIBs in DMAable memory and load them */
1471 	if (bus_dmamem_alloc(sc->aac_fib_dmat, (void **)&fm->aac_fibs,
1472 			     BUS_DMA_NOWAIT, &fm->aac_fibmap)) {
1473 		device_printf(sc->aac_dev,
1474 			      "Not enough contiguous memory available.\n");
1475 		kfree(fm, M_AACBUF);
1476 		return (ENOMEM);
1477 	}
1478 
1479 	/* Ignore errors since this doesn't bounce */
1480 	(void)bus_dmamap_load(sc->aac_fib_dmat, fm->aac_fibmap, fm->aac_fibs,
1481 			      sc->aac_max_fibs_alloc * sc->aac_max_fib_size,
1482 			      aac_map_command_helper, &fibphys, 0);
1483 
1484 	/* initialize constant fields in the command structure */
1485 	bzero(fm->aac_fibs, sc->aac_max_fibs_alloc * sc->aac_max_fib_size);
1486 	for (i = 0; i < sc->aac_max_fibs_alloc; i++) {
1487 		cm = sc->aac_commands + sc->total_fibs;
1488 		fm->aac_commands = cm;
1489 		cm->cm_sc = sc;
1490 		cm->cm_fib = (struct aac_fib *)
1491 			((u_int8_t *)fm->aac_fibs + i*sc->aac_max_fib_size);
1492 		cm->cm_fibphys = fibphys + i*sc->aac_max_fib_size;
1493 		cm->cm_index = sc->total_fibs;
1494 
1495 		if ((error = bus_dmamap_create(sc->aac_buffer_dmat, 0,
1496 					       &cm->cm_datamap)) != 0)
1497 			break;
1498 		lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
1499 		aac_release_command(cm);
1500 		sc->total_fibs++;
1501 		lockmgr(&sc->aac_io_lock, LK_RELEASE);
1502 	}
1503 
1504 	if (i > 0) {
1505 		lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
1506 		TAILQ_INSERT_TAIL(&sc->aac_fibmap_tqh, fm, fm_link);
1507 		fwprintf(sc, HBA_FLAGS_DBG_COMM_B, "total_fibs= %d\n", sc->total_fibs);
1508 		lockmgr(&sc->aac_io_lock, LK_RELEASE);
1509 		return (0);
1510 	}
1511 
1512 	bus_dmamap_unload(sc->aac_fib_dmat, fm->aac_fibmap);
1513 	bus_dmamem_free(sc->aac_fib_dmat, fm->aac_fibs, fm->aac_fibmap);
1514 	kfree(fm, M_AACBUF);
1515 	return (ENOMEM);
1516 }
1517 
1518 /*
1519  * Free FIBs owned by this adapter.
1520  */
1521 static void
1522 aac_free_commands(struct aac_softc *sc)
1523 {
1524 	struct aac_fibmap *fm;
1525 	struct aac_command *cm;
1526 	int i;
1527 
1528 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1529 
1530 	while ((fm = TAILQ_FIRST(&sc->aac_fibmap_tqh)) != NULL) {
1531 
1532 		TAILQ_REMOVE(&sc->aac_fibmap_tqh, fm, fm_link);
1533 		/*
1534 		 * We check against total_fibs to handle partially
1535 		 * allocated blocks.
1536 		 */
1537 		for (i = 0; i < sc->aac_max_fibs_alloc && sc->total_fibs--; i++) {
1538 			cm = fm->aac_commands + i;
1539 			bus_dmamap_destroy(sc->aac_buffer_dmat, cm->cm_datamap);
1540 		}
1541 		bus_dmamap_unload(sc->aac_fib_dmat, fm->aac_fibmap);
1542 		bus_dmamem_free(sc->aac_fib_dmat, fm->aac_fibs, fm->aac_fibmap);
1543 		kfree(fm, M_AACBUF);
1544 	}
1545 }
1546 
1547 /*
1548  * Command-mapping helper function - populate this command's s/g table.
1549  */
1550 static void
1551 aac_map_command_sg(void *arg, bus_dma_segment_t *segs, int nseg, int error)
1552 {
1553 	struct aac_softc *sc;
1554 	struct aac_command *cm;
1555 	struct aac_fib *fib;
1556 	int i;
1557 
1558 	cm = (struct aac_command *)arg;
1559 	sc = cm->cm_sc;
1560 	fib = cm->cm_fib;
1561 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1562 
1563 	/* copy into the FIB */
1564 	if (cm->cm_sgtable != NULL) {
1565 		if (fib->Header.Command == RawIo) {
1566 			struct aac_sg_tableraw *sg;
1567 			sg = (struct aac_sg_tableraw *)cm->cm_sgtable;
1568 			sg->SgCount = nseg;
1569 			for (i = 0; i < nseg; i++) {
1570 				sg->SgEntryRaw[i].SgAddress = segs[i].ds_addr;
1571 				sg->SgEntryRaw[i].SgByteCount = segs[i].ds_len;
1572 				sg->SgEntryRaw[i].Next = 0;
1573 				sg->SgEntryRaw[i].Prev = 0;
1574 				sg->SgEntryRaw[i].Flags = 0;
1575 			}
1576 			/* update the FIB size for the s/g count */
1577 			fib->Header.Size += nseg*sizeof(struct aac_sg_entryraw);
1578 		} else if ((cm->cm_sc->flags & AAC_FLAGS_SG_64BIT) == 0) {
1579 			struct aac_sg_table *sg;
1580 			sg = cm->cm_sgtable;
1581 			sg->SgCount = nseg;
1582 			for (i = 0; i < nseg; i++) {
1583 				sg->SgEntry[i].SgAddress = segs[i].ds_addr;
1584 				sg->SgEntry[i].SgByteCount = segs[i].ds_len;
1585 			}
1586 			/* update the FIB size for the s/g count */
1587 			fib->Header.Size += nseg*sizeof(struct aac_sg_entry);
1588 		} else {
1589 			struct aac_sg_table64 *sg;
1590 			sg = (struct aac_sg_table64 *)cm->cm_sgtable;
1591 			sg->SgCount = nseg;
1592 			for (i = 0; i < nseg; i++) {
1593 				sg->SgEntry64[i].SgAddress = segs[i].ds_addr;
1594 				sg->SgEntry64[i].SgByteCount = segs[i].ds_len;
1595 			}
1596 			/* update the FIB size for the s/g count */
1597 			fib->Header.Size += nseg*sizeof(struct aac_sg_entry64);
1598 		}
1599 	}
1600 
1601 	/* Fix up the address values in the FIB.  Use the command array index
1602 	 * instead of a pointer since these fields are only 32 bits.  Shift
1603 	 * the SenderFibAddress over to make room for the fast response bit
1604 	 * and for the AIF bit
1605 	 */
1606 	cm->cm_fib->Header.SenderFibAddress = (cm->cm_index << 2);
1607 	cm->cm_fib->Header.ReceiverFibAddress = (u_int32_t)cm->cm_fibphys;
1608 
1609 	/* save a pointer to the command for speedy reverse-lookup */
1610 	cm->cm_fib->Header.SenderData = cm->cm_index;
1611 
1612 	if (cm->cm_flags & AAC_CMD_DATAIN)
1613 		bus_dmamap_sync(sc->aac_buffer_dmat, cm->cm_datamap,
1614 				BUS_DMASYNC_PREREAD);
1615 	if (cm->cm_flags & AAC_CMD_DATAOUT)
1616 		bus_dmamap_sync(sc->aac_buffer_dmat, cm->cm_datamap,
1617 				BUS_DMASYNC_PREWRITE);
1618 	cm->cm_flags |= AAC_CMD_MAPPED;
1619 
1620 	if (sc->flags & AAC_FLAGS_NEW_COMM) {
1621 		int count = 10000000L;
1622 		while (AAC_SEND_COMMAND(sc, cm) != 0) {
1623 			if (--count == 0) {
1624 				aac_unmap_command(cm);
1625 				sc->flags |= AAC_QUEUE_FRZN;
1626 				aac_requeue_ready(cm);
1627 			}
1628 			DELAY(5);			/* wait 5 usec. */
1629 		}
1630 	} else {
1631 		/* Put the FIB on the outbound queue */
1632 		if (aac_enqueue_fib(sc, cm->cm_queue, cm) == EBUSY) {
1633 			aac_unmap_command(cm);
1634 			sc->flags |= AAC_QUEUE_FRZN;
1635 			aac_requeue_ready(cm);
1636 		}
1637 	}
1638 
1639 	return;
1640 }
1641 
1642 /*
1643  * Unmap a command from controller-visible space.
1644  */
1645 static void
1646 aac_unmap_command(struct aac_command *cm)
1647 {
1648 	struct aac_softc *sc;
1649 
1650 	sc = cm->cm_sc;
1651 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1652 
1653 	if (!(cm->cm_flags & AAC_CMD_MAPPED))
1654 		return;
1655 
1656 	if (cm->cm_datalen != 0) {
1657 		if (cm->cm_flags & AAC_CMD_DATAIN)
1658 			bus_dmamap_sync(sc->aac_buffer_dmat, cm->cm_datamap,
1659 					BUS_DMASYNC_POSTREAD);
1660 		if (cm->cm_flags & AAC_CMD_DATAOUT)
1661 			bus_dmamap_sync(sc->aac_buffer_dmat, cm->cm_datamap,
1662 					BUS_DMASYNC_POSTWRITE);
1663 
1664 		bus_dmamap_unload(sc->aac_buffer_dmat, cm->cm_datamap);
1665 	}
1666 	cm->cm_flags &= ~AAC_CMD_MAPPED;
1667 }
1668 
1669 /*
1670  * Hardware Interface
1671  */
1672 
1673 /*
1674  * Initialize the adapter.
1675  */
1676 static void
1677 aac_common_map(void *arg, bus_dma_segment_t *segs, int nseg, int error)
1678 {
1679 	struct aac_softc *sc;
1680 
1681 	sc = (struct aac_softc *)arg;
1682 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1683 
1684 	sc->aac_common_busaddr = segs[0].ds_addr;
1685 }
1686 
1687 static int
1688 aac_check_firmware(struct aac_softc *sc)
1689 {
1690 	u_int32_t code, major, minor, options = 0, atu_size = 0;
1691 	int status;
1692 	time_t then;
1693 
1694 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1695 	/*
1696 	 * Wait for the adapter to come ready.
1697 	 */
1698 	then = time_second;
1699 	do {
1700 		code = AAC_GET_FWSTATUS(sc);
1701 		if (code & AAC_SELF_TEST_FAILED) {
1702 			device_printf(sc->aac_dev, "FATAL: selftest failed\n");
1703 			return(ENXIO);
1704 		}
1705 		if (code & AAC_KERNEL_PANIC) {
1706 			device_printf(sc->aac_dev,
1707 				      "FATAL: controller kernel panic");
1708 			return(ENXIO);
1709 		}
1710 		if (time_second > (then + AAC_BOOT_TIMEOUT)) {
1711 			device_printf(sc->aac_dev,
1712 				      "FATAL: controller not coming ready, "
1713 					   "status %x\n", code);
1714 			return(ENXIO);
1715 		}
1716 	} while (!(code & AAC_UP_AND_RUNNING));
1717 
1718 	/*
1719 	 * Retrieve the firmware version numbers.  Dell PERC2/QC cards with
1720 	 * firmware version 1.x are not compatible with this driver.
1721 	 */
1722 	if (sc->flags & AAC_FLAGS_PERC2QC) {
1723 		if (aac_sync_command(sc, AAC_MONKER_GETKERNVER, 0, 0, 0, 0,
1724 				     NULL)) {
1725 			device_printf(sc->aac_dev,
1726 				      "Error reading firmware version\n");
1727 			return (EIO);
1728 		}
1729 
1730 		/* These numbers are stored as ASCII! */
1731 		major = (AAC_GET_MAILBOX(sc, 1) & 0xff) - 0x30;
1732 		minor = (AAC_GET_MAILBOX(sc, 2) & 0xff) - 0x30;
1733 		if (major == 1) {
1734 			device_printf(sc->aac_dev,
1735 			    "Firmware version %d.%d is not supported.\n",
1736 			    major, minor);
1737 			return (EINVAL);
1738 		}
1739 	}
1740 
1741 	/*
1742 	 * Retrieve the capabilities/supported options word so we know what
1743 	 * work-arounds to enable.  Some firmware revs don't support this
1744 	 * command.
1745 	 */
1746 	if (aac_sync_command(sc, AAC_MONKER_GETINFO, 0, 0, 0, 0, &status)) {
1747 		if (status != AAC_SRB_STS_INVALID_REQUEST) {
1748 			device_printf(sc->aac_dev,
1749 			     "RequestAdapterInfo failed\n");
1750 			return (EIO);
1751 		}
1752 	} else {
1753 		options = AAC_GET_MAILBOX(sc, 1);
1754 		atu_size = AAC_GET_MAILBOX(sc, 2);
1755 		sc->supported_options = options;
1756 
1757 		if ((options & AAC_SUPPORTED_4GB_WINDOW) != 0 &&
1758 		    (sc->flags & AAC_FLAGS_NO4GB) == 0)
1759 			sc->flags |= AAC_FLAGS_4GB_WINDOW;
1760 		if (options & AAC_SUPPORTED_NONDASD)
1761 			sc->flags |= AAC_FLAGS_ENABLE_CAM;
1762 		if ((options & AAC_SUPPORTED_SGMAP_HOST64) != 0
1763 		     && (sizeof(bus_addr_t) > 4)) {
1764 			device_printf(sc->aac_dev,
1765 			    "Enabling 64-bit address support\n");
1766 			sc->flags |= AAC_FLAGS_SG_64BIT;
1767 		}
1768 		if ((options & AAC_SUPPORTED_NEW_COMM)
1769 		 && sc->aac_if.aif_send_command)
1770 			sc->flags |= AAC_FLAGS_NEW_COMM;
1771 		if (options & AAC_SUPPORTED_64BIT_ARRAYSIZE)
1772 			sc->flags |= AAC_FLAGS_ARRAY_64BIT;
1773 	}
1774 
1775 	/* Check for broken hardware that does a lower number of commands */
1776 	sc->aac_max_fibs = (sc->flags & AAC_FLAGS_256FIBS ? 256:512);
1777 
1778 	/* Remap mem. resource, if required */
1779 	if ((sc->flags & AAC_FLAGS_NEW_COMM) &&
1780 		atu_size > rman_get_size(sc->aac_regs_res1)) {
1781 		bus_release_resource(
1782 			sc->aac_dev, SYS_RES_MEMORY,
1783 			sc->aac_regs_rid1, sc->aac_regs_res1);
1784 		sc->aac_regs_res1 = bus_alloc_resource(
1785 			sc->aac_dev, SYS_RES_MEMORY, &sc->aac_regs_rid1,
1786 			0ul, ~0ul, atu_size, RF_ACTIVE);
1787 		if (sc->aac_regs_res1 == NULL) {
1788 			sc->aac_regs_res1 = bus_alloc_resource_any(
1789 				sc->aac_dev, SYS_RES_MEMORY,
1790 				&sc->aac_regs_rid1, RF_ACTIVE);
1791 			if (sc->aac_regs_res1 == NULL) {
1792 				device_printf(sc->aac_dev,
1793 				    "couldn't allocate register window\n");
1794 				return (ENXIO);
1795 			}
1796 			sc->flags &= ~AAC_FLAGS_NEW_COMM;
1797 		}
1798 		sc->aac_btag1 = rman_get_bustag(sc->aac_regs_res1);
1799 		sc->aac_bhandle1 = rman_get_bushandle(sc->aac_regs_res1);
1800 
1801 		if (sc->aac_hwif == AAC_HWIF_NARK) {
1802 			sc->aac_regs_res0 = sc->aac_regs_res1;
1803 			sc->aac_regs_rid0 = sc->aac_regs_rid1;
1804 			sc->aac_btag0 = sc->aac_btag1;
1805 			sc->aac_bhandle0 = sc->aac_bhandle1;
1806 		}
1807 	}
1808 
1809 	/* Read preferred settings */
1810 	sc->aac_max_fib_size = sizeof(struct aac_fib);
1811 	sc->aac_max_sectors = 128;				/* 64KB */
1812 	if (sc->flags & AAC_FLAGS_SG_64BIT)
1813 		sc->aac_sg_tablesize = (AAC_FIB_DATASIZE
1814 		 - sizeof(struct aac_blockwrite64))
1815 		 / sizeof(struct aac_sg_entry64);
1816 	else
1817 		sc->aac_sg_tablesize = (AAC_FIB_DATASIZE
1818 		 - sizeof(struct aac_blockwrite))
1819 		 / sizeof(struct aac_sg_entry);
1820 
1821 	if (!aac_sync_command(sc, AAC_MONKER_GETCOMMPREF, 0, 0, 0, 0, NULL)) {
1822 		options = AAC_GET_MAILBOX(sc, 1);
1823 		sc->aac_max_fib_size = (options & 0xFFFF);
1824 		sc->aac_max_sectors = (options >> 16) << 1;
1825 		options = AAC_GET_MAILBOX(sc, 2);
1826 		sc->aac_sg_tablesize = (options >> 16);
1827 		options = AAC_GET_MAILBOX(sc, 3);
1828 		sc->aac_max_fibs = (options & 0xFFFF);
1829 	}
1830 	if (sc->aac_max_fib_size > PAGE_SIZE)
1831 		sc->aac_max_fib_size = PAGE_SIZE;
1832 	sc->aac_max_fibs_alloc = PAGE_SIZE / sc->aac_max_fib_size;
1833 
1834 	if (sc->aac_max_fib_size > sizeof(struct aac_fib)) {
1835 		sc->flags |= AAC_FLAGS_RAW_IO;
1836 		device_printf(sc->aac_dev, "Enable Raw I/O\n");
1837 	}
1838 	if ((sc->flags & AAC_FLAGS_RAW_IO) &&
1839 	    (sc->flags & AAC_FLAGS_ARRAY_64BIT)) {
1840 		sc->flags |= AAC_FLAGS_LBA_64BIT;
1841 		device_printf(sc->aac_dev, "Enable 64-bit array\n");
1842 	}
1843 
1844 	return (0);
1845 }
1846 
1847 static int
1848 aac_init(struct aac_softc *sc)
1849 {
1850 	struct aac_adapter_init	*ip;
1851 	u_int32_t qoffset;
1852 	int error;
1853 
1854 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
1855 
1856 	/*
1857 	 * Fill in the init structure.  This tells the adapter about the
1858 	 * physical location of various important shared data structures.
1859 	 */
1860 	ip = &sc->aac_common->ac_init;
1861 	ip->InitStructRevision = AAC_INIT_STRUCT_REVISION;
1862 	if (sc->aac_max_fib_size > sizeof(struct aac_fib)) {
1863 		ip->InitStructRevision = AAC_INIT_STRUCT_REVISION_4;
1864 		sc->flags |= AAC_FLAGS_RAW_IO;
1865 	}
1866 	ip->MiniPortRevision = AAC_INIT_STRUCT_MINIPORT_REVISION;
1867 
1868 	ip->AdapterFibsPhysicalAddress = sc->aac_common_busaddr +
1869 					 offsetof(struct aac_common, ac_fibs);
1870 	ip->AdapterFibsVirtualAddress = 0;
1871 	ip->AdapterFibsSize = AAC_ADAPTER_FIBS * sizeof(struct aac_fib);
1872 	ip->AdapterFibAlign = sizeof(struct aac_fib);
1873 
1874 	ip->PrintfBufferAddress = sc->aac_common_busaddr +
1875 				  offsetof(struct aac_common, ac_printf);
1876 	ip->PrintfBufferSize = AAC_PRINTF_BUFSIZE;
1877 
1878 	/*
1879 	 * The adapter assumes that pages are 4K in size, except on some
1880 	 * broken firmware versions that do the page->byte conversion twice,
1881 	 * therefore 'assuming' that this value is in 16MB units (2^24).
1882 	 * Round up since the granularity is so high.
1883 	 */
1884 	ip->HostPhysMemPages = ctob(physmem) / AAC_PAGE_SIZE;
1885 	if (sc->flags & AAC_FLAGS_BROKEN_MEMMAP) {
1886 		ip->HostPhysMemPages =
1887 		    (ip->HostPhysMemPages + AAC_PAGE_SIZE) / AAC_PAGE_SIZE;
1888 	}
1889 	ip->HostElapsedSeconds = time_second;	/* reset later if invalid */
1890 
1891 	ip->InitFlags = 0;
1892 	if (sc->flags & AAC_FLAGS_NEW_COMM) {
1893 		ip->InitFlags |= AAC_INITFLAGS_NEW_COMM_SUPPORTED;
1894 		device_printf(sc->aac_dev, "New comm. interface enabled\n");
1895 	}
1896 
1897 	ip->MaxIoCommands = sc->aac_max_fibs;
1898 	ip->MaxIoSize = sc->aac_max_sectors << 9;
1899 	ip->MaxFibSize = sc->aac_max_fib_size;
1900 
1901 	/*
1902 	 * Initialize FIB queues.  Note that it appears that the layout of the
1903 	 * indexes and the segmentation of the entries may be mandated by the
1904 	 * adapter, which is only told about the base of the queue index fields.
1905 	 *
1906 	 * The initial values of the indices are assumed to inform the adapter
1907 	 * of the sizes of the respective queues, and theoretically it could
1908 	 * work out the entire layout of the queue structures from this.  We
1909 	 * take the easy route and just lay this area out like everyone else
1910 	 * does.
1911 	 *
1912 	 * The Linux driver uses a much more complex scheme whereby several
1913 	 * header records are kept for each queue.  We use a couple of generic
1914 	 * list manipulation functions which 'know' the size of each list by
1915 	 * virtue of a table.
1916 	 */
1917 	qoffset = offsetof(struct aac_common, ac_qbuf) + AAC_QUEUE_ALIGN;
1918 	qoffset &= ~(AAC_QUEUE_ALIGN - 1);
1919 	sc->aac_queues =
1920 	    (struct aac_queue_table *)((uintptr_t)sc->aac_common + qoffset);
1921 	ip->CommHeaderAddress = sc->aac_common_busaddr + qoffset;
1922 
1923 	sc->aac_queues->qt_qindex[AAC_HOST_NORM_CMD_QUEUE][AAC_PRODUCER_INDEX] =
1924 		AAC_HOST_NORM_CMD_ENTRIES;
1925 	sc->aac_queues->qt_qindex[AAC_HOST_NORM_CMD_QUEUE][AAC_CONSUMER_INDEX] =
1926 		AAC_HOST_NORM_CMD_ENTRIES;
1927 	sc->aac_queues->qt_qindex[AAC_HOST_HIGH_CMD_QUEUE][AAC_PRODUCER_INDEX] =
1928 		AAC_HOST_HIGH_CMD_ENTRIES;
1929 	sc->aac_queues->qt_qindex[AAC_HOST_HIGH_CMD_QUEUE][AAC_CONSUMER_INDEX] =
1930 		AAC_HOST_HIGH_CMD_ENTRIES;
1931 	sc->aac_queues->qt_qindex[AAC_ADAP_NORM_CMD_QUEUE][AAC_PRODUCER_INDEX] =
1932 		AAC_ADAP_NORM_CMD_ENTRIES;
1933 	sc->aac_queues->qt_qindex[AAC_ADAP_NORM_CMD_QUEUE][AAC_CONSUMER_INDEX] =
1934 		AAC_ADAP_NORM_CMD_ENTRIES;
1935 	sc->aac_queues->qt_qindex[AAC_ADAP_HIGH_CMD_QUEUE][AAC_PRODUCER_INDEX] =
1936 		AAC_ADAP_HIGH_CMD_ENTRIES;
1937 	sc->aac_queues->qt_qindex[AAC_ADAP_HIGH_CMD_QUEUE][AAC_CONSUMER_INDEX] =
1938 		AAC_ADAP_HIGH_CMD_ENTRIES;
1939 	sc->aac_queues->qt_qindex[AAC_HOST_NORM_RESP_QUEUE][AAC_PRODUCER_INDEX]=
1940 		AAC_HOST_NORM_RESP_ENTRIES;
1941 	sc->aac_queues->qt_qindex[AAC_HOST_NORM_RESP_QUEUE][AAC_CONSUMER_INDEX]=
1942 		AAC_HOST_NORM_RESP_ENTRIES;
1943 	sc->aac_queues->qt_qindex[AAC_HOST_HIGH_RESP_QUEUE][AAC_PRODUCER_INDEX]=
1944 		AAC_HOST_HIGH_RESP_ENTRIES;
1945 	sc->aac_queues->qt_qindex[AAC_HOST_HIGH_RESP_QUEUE][AAC_CONSUMER_INDEX]=
1946 		AAC_HOST_HIGH_RESP_ENTRIES;
1947 	sc->aac_queues->qt_qindex[AAC_ADAP_NORM_RESP_QUEUE][AAC_PRODUCER_INDEX]=
1948 		AAC_ADAP_NORM_RESP_ENTRIES;
1949 	sc->aac_queues->qt_qindex[AAC_ADAP_NORM_RESP_QUEUE][AAC_CONSUMER_INDEX]=
1950 		AAC_ADAP_NORM_RESP_ENTRIES;
1951 	sc->aac_queues->qt_qindex[AAC_ADAP_HIGH_RESP_QUEUE][AAC_PRODUCER_INDEX]=
1952 		AAC_ADAP_HIGH_RESP_ENTRIES;
1953 	sc->aac_queues->qt_qindex[AAC_ADAP_HIGH_RESP_QUEUE][AAC_CONSUMER_INDEX]=
1954 		AAC_ADAP_HIGH_RESP_ENTRIES;
1955 	sc->aac_qentries[AAC_HOST_NORM_CMD_QUEUE] =
1956 		&sc->aac_queues->qt_HostNormCmdQueue[0];
1957 	sc->aac_qentries[AAC_HOST_HIGH_CMD_QUEUE] =
1958 		&sc->aac_queues->qt_HostHighCmdQueue[0];
1959 	sc->aac_qentries[AAC_ADAP_NORM_CMD_QUEUE] =
1960 		&sc->aac_queues->qt_AdapNormCmdQueue[0];
1961 	sc->aac_qentries[AAC_ADAP_HIGH_CMD_QUEUE] =
1962 		&sc->aac_queues->qt_AdapHighCmdQueue[0];
1963 	sc->aac_qentries[AAC_HOST_NORM_RESP_QUEUE] =
1964 		&sc->aac_queues->qt_HostNormRespQueue[0];
1965 	sc->aac_qentries[AAC_HOST_HIGH_RESP_QUEUE] =
1966 		&sc->aac_queues->qt_HostHighRespQueue[0];
1967 	sc->aac_qentries[AAC_ADAP_NORM_RESP_QUEUE] =
1968 		&sc->aac_queues->qt_AdapNormRespQueue[0];
1969 	sc->aac_qentries[AAC_ADAP_HIGH_RESP_QUEUE] =
1970 		&sc->aac_queues->qt_AdapHighRespQueue[0];
1971 
1972 	/*
1973 	 * Do controller-type-specific initialisation
1974 	 */
1975 	switch (sc->aac_hwif) {
1976 	case AAC_HWIF_I960RX:
1977 		AAC_MEM0_SETREG4(sc, AAC_RX_ODBR, ~0);
1978 		break;
1979 	case AAC_HWIF_RKT:
1980 		AAC_MEM0_SETREG4(sc, AAC_RKT_ODBR, ~0);
1981 		break;
1982 	default:
1983 		break;
1984 	}
1985 
1986 	/*
1987 	 * Give the init structure to the controller.
1988 	 */
1989 	if (aac_sync_command(sc, AAC_MONKER_INITSTRUCT,
1990 			     sc->aac_common_busaddr +
1991 			     offsetof(struct aac_common, ac_init), 0, 0, 0,
1992 			     NULL)) {
1993 		device_printf(sc->aac_dev,
1994 			      "error establishing init structure\n");
1995 		error = EIO;
1996 		goto out;
1997 	}
1998 
1999 	error = 0;
2000 out:
2001 	return(error);
2002 }
2003 
2004 static int
2005 aac_setup_intr(struct aac_softc *sc)
2006 {
2007 	sc->aac_irq_rid = 0;
2008 	if ((sc->aac_irq = bus_alloc_resource_any(sc->aac_dev, SYS_RES_IRQ,
2009 						  &sc->aac_irq_rid,
2010 						  RF_SHAREABLE |
2011 						  RF_ACTIVE)) == NULL) {
2012 		device_printf(sc->aac_dev, "can't allocate interrupt\n");
2013 		return (EINVAL);
2014 	}
2015 	if (sc->flags & AAC_FLAGS_NEW_COMM) {
2016 		if (bus_setup_intr(sc->aac_dev, sc->aac_irq,
2017 				   INTR_MPSAFE,
2018 				   aac_new_intr, sc, &sc->aac_intr, NULL)) {
2019 			device_printf(sc->aac_dev, "can't set up interrupt\n");
2020 			return (EINVAL);
2021 		}
2022 	} else {
2023 		if (bus_setup_intr(sc->aac_dev, sc->aac_irq,
2024 				   0, aac_filter,
2025 				   sc, &sc->aac_intr, NULL)) {
2026 			device_printf(sc->aac_dev,
2027 				      "can't set up interrupt filter\n");
2028 			return (EINVAL);
2029 		}
2030 	}
2031 	return (0);
2032 }
2033 
2034 /*
2035  * Send a synchronous command to the controller and wait for a result.
2036  * Indicate if the controller completed the command with an error status.
2037  */
2038 static int
2039 aac_sync_command(struct aac_softc *sc, u_int32_t command,
2040 		 u_int32_t arg0, u_int32_t arg1, u_int32_t arg2, u_int32_t arg3,
2041 		 u_int32_t *sp)
2042 {
2043 	time_t then;
2044 	u_int32_t status;
2045 
2046 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2047 
2048 	/* populate the mailbox */
2049 	AAC_SET_MAILBOX(sc, command, arg0, arg1, arg2, arg3);
2050 
2051 	/* ensure the sync command doorbell flag is cleared */
2052 	AAC_CLEAR_ISTATUS(sc, AAC_DB_SYNC_COMMAND);
2053 
2054 	/* then set it to signal the adapter */
2055 	AAC_QNOTIFY(sc, AAC_DB_SYNC_COMMAND);
2056 
2057 	/* spin waiting for the command to complete */
2058 	then = time_second;
2059 	do {
2060 		if (time_second > (then + AAC_IMMEDIATE_TIMEOUT)) {
2061 			fwprintf(sc, HBA_FLAGS_DBG_ERROR_B, "timed out");
2062 			return(EIO);
2063 		}
2064 	} while (!(AAC_GET_ISTATUS(sc) & AAC_DB_SYNC_COMMAND));
2065 
2066 	/* clear the completion flag */
2067 	AAC_CLEAR_ISTATUS(sc, AAC_DB_SYNC_COMMAND);
2068 
2069 	/* get the command status */
2070 	status = AAC_GET_MAILBOX(sc, 0);
2071 	if (sp != NULL)
2072 		*sp = status;
2073 
2074 	if (status != AAC_SRB_STS_SUCCESS)
2075 		return (-1);
2076 	return(0);
2077 }
2078 
2079 int
2080 aac_sync_fib(struct aac_softc *sc, u_int32_t command, u_int32_t xferstate,
2081 		 struct aac_fib *fib, u_int16_t datasize)
2082 {
2083 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2084 #if 0 /* XXX swildner */
2085 	KKASSERT(lockstatus(&sc->aac_io_lock, curthread) != 0);
2086 #endif
2087 
2088 	if (datasize > AAC_FIB_DATASIZE)
2089 		return(EINVAL);
2090 
2091 	/*
2092 	 * Set up the sync FIB
2093 	 */
2094 	fib->Header.XferState = AAC_FIBSTATE_HOSTOWNED |
2095 				AAC_FIBSTATE_INITIALISED |
2096 				AAC_FIBSTATE_EMPTY;
2097 	fib->Header.XferState |= xferstate;
2098 	fib->Header.Command = command;
2099 	fib->Header.StructType = AAC_FIBTYPE_TFIB;
2100 	fib->Header.Size = sizeof(struct aac_fib_header) + datasize;
2101 	fib->Header.SenderSize = sizeof(struct aac_fib);
2102 	fib->Header.SenderFibAddress = 0;	/* Not needed */
2103 	fib->Header.ReceiverFibAddress = sc->aac_common_busaddr +
2104 					 offsetof(struct aac_common,
2105 						  ac_sync_fib);
2106 
2107 	/*
2108 	 * Give the FIB to the controller, wait for a response.
2109 	 */
2110 	if (aac_sync_command(sc, AAC_MONKER_SYNCFIB,
2111 			     fib->Header.ReceiverFibAddress, 0, 0, 0, NULL)) {
2112 		fwprintf(sc, HBA_FLAGS_DBG_ERROR_B, "IO error");
2113 		return(EIO);
2114 	}
2115 
2116 	return (0);
2117 }
2118 
2119 /*
2120  * Adapter-space FIB queue manipulation
2121  *
2122  * Note that the queue implementation here is a little funky; neither the PI or
2123  * CI will ever be zero.  This behaviour is a controller feature.
2124  */
2125 static struct {
2126 	int		size;
2127 	int		notify;
2128 } aac_qinfo[] = {
2129 	{AAC_HOST_NORM_CMD_ENTRIES, AAC_DB_COMMAND_NOT_FULL},
2130 	{AAC_HOST_HIGH_CMD_ENTRIES, 0},
2131 	{AAC_ADAP_NORM_CMD_ENTRIES, AAC_DB_COMMAND_READY},
2132 	{AAC_ADAP_HIGH_CMD_ENTRIES, 0},
2133 	{AAC_HOST_NORM_RESP_ENTRIES, AAC_DB_RESPONSE_NOT_FULL},
2134 	{AAC_HOST_HIGH_RESP_ENTRIES, 0},
2135 	{AAC_ADAP_NORM_RESP_ENTRIES, AAC_DB_RESPONSE_READY},
2136 	{AAC_ADAP_HIGH_RESP_ENTRIES, 0}
2137 };
2138 
2139 /*
2140  * Atomically insert an entry into the nominated queue, returns 0 on success or
2141  * EBUSY if the queue is full.
2142  *
2143  * Note: it would be more efficient to defer notifying the controller in
2144  *	 the case where we may be inserting several entries in rapid succession,
2145  *	 but implementing this usefully may be difficult (it would involve a
2146  *	 separate queue/notify interface).
2147  */
2148 static int
2149 aac_enqueue_fib(struct aac_softc *sc, int queue, struct aac_command *cm)
2150 {
2151 	u_int32_t pi, ci;
2152 	int error;
2153 	u_int32_t fib_size;
2154 	u_int32_t fib_addr;
2155 
2156 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2157 
2158 	fib_size = cm->cm_fib->Header.Size;
2159 	fib_addr = cm->cm_fib->Header.ReceiverFibAddress;
2160 
2161 	/* get the producer/consumer indices */
2162 	pi = sc->aac_queues->qt_qindex[queue][AAC_PRODUCER_INDEX];
2163 	ci = sc->aac_queues->qt_qindex[queue][AAC_CONSUMER_INDEX];
2164 
2165 	/* wrap the queue? */
2166 	if (pi >= aac_qinfo[queue].size)
2167 		pi = 0;
2168 
2169 	/* check for queue full */
2170 	if ((pi + 1) == ci) {
2171 		error = EBUSY;
2172 		goto out;
2173 	}
2174 
2175 	/*
2176 	 * To avoid a race with its completion interrupt, place this command on
2177 	 * the busy queue prior to advertising it to the controller.
2178 	 */
2179 	aac_enqueue_busy(cm);
2180 
2181 	/* populate queue entry */
2182 	(sc->aac_qentries[queue] + pi)->aq_fib_size = fib_size;
2183 	(sc->aac_qentries[queue] + pi)->aq_fib_addr = fib_addr;
2184 
2185 	/* update producer index */
2186 	sc->aac_queues->qt_qindex[queue][AAC_PRODUCER_INDEX] = pi + 1;
2187 
2188 	/* notify the adapter if we know how */
2189 	if (aac_qinfo[queue].notify != 0)
2190 		AAC_QNOTIFY(sc, aac_qinfo[queue].notify);
2191 
2192 	error = 0;
2193 
2194 out:
2195 	return(error);
2196 }
2197 
2198 /*
2199  * Atomically remove one entry from the nominated queue, returns 0 on
2200  * success or ENOENT if the queue is empty.
2201  */
2202 static int
2203 aac_dequeue_fib(struct aac_softc *sc, int queue, u_int32_t *fib_size,
2204 		struct aac_fib **fib_addr)
2205 {
2206 	u_int32_t pi, ci;
2207 	u_int32_t fib_index;
2208 	int error;
2209 	int notify;
2210 
2211 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2212 
2213 	/* get the producer/consumer indices */
2214 	pi = sc->aac_queues->qt_qindex[queue][AAC_PRODUCER_INDEX];
2215 	ci = sc->aac_queues->qt_qindex[queue][AAC_CONSUMER_INDEX];
2216 
2217 	/* check for queue empty */
2218 	if (ci == pi) {
2219 		error = ENOENT;
2220 		goto out;
2221 	}
2222 
2223 	/* wrap the pi so the following test works */
2224 	if (pi >= aac_qinfo[queue].size)
2225 		pi = 0;
2226 
2227 	notify = 0;
2228 	if (ci == pi + 1)
2229 		notify++;
2230 
2231 	/* wrap the queue? */
2232 	if (ci >= aac_qinfo[queue].size)
2233 		ci = 0;
2234 
2235 	/* fetch the entry */
2236 	*fib_size = (sc->aac_qentries[queue] + ci)->aq_fib_size;
2237 
2238 	switch (queue) {
2239 	case AAC_HOST_NORM_CMD_QUEUE:
2240 	case AAC_HOST_HIGH_CMD_QUEUE:
2241 		/*
2242 		 * The aq_fib_addr is only 32 bits wide so it can't be counted
2243 		 * on to hold an address.  For AIF's, the adapter assumes
2244 		 * that it's giving us an address into the array of AIF fibs.
2245 		 * Therefore, we have to convert it to an index.
2246 		 */
2247 		fib_index = (sc->aac_qentries[queue] + ci)->aq_fib_addr /
2248 			sizeof(struct aac_fib);
2249 		*fib_addr = &sc->aac_common->ac_fibs[fib_index];
2250 		break;
2251 
2252 	case AAC_HOST_NORM_RESP_QUEUE:
2253 	case AAC_HOST_HIGH_RESP_QUEUE:
2254 	{
2255 		struct aac_command *cm;
2256 
2257 		/*
2258 		 * As above, an index is used instead of an actual address.
2259 		 * Gotta shift the index to account for the fast response
2260 		 * bit.  No other correction is needed since this value was
2261 		 * originally provided by the driver via the SenderFibAddress
2262 		 * field.
2263 		 */
2264 		fib_index = (sc->aac_qentries[queue] + ci)->aq_fib_addr;
2265 		cm = sc->aac_commands + (fib_index >> 2);
2266 		*fib_addr = cm->cm_fib;
2267 
2268 		/*
2269 		 * Is this a fast response? If it is, update the fib fields in
2270 		 * local memory since the whole fib isn't DMA'd back up.
2271 		 */
2272 		if (fib_index & 0x01) {
2273 			(*fib_addr)->Header.XferState |= AAC_FIBSTATE_DONEADAP;
2274 			*((u_int32_t*)((*fib_addr)->data)) = AAC_ERROR_NORMAL;
2275 		}
2276 		break;
2277 	}
2278 	default:
2279 		panic("Invalid queue in aac_dequeue_fib()");
2280 		break;
2281 	}
2282 
2283 	/* update consumer index */
2284 	sc->aac_queues->qt_qindex[queue][AAC_CONSUMER_INDEX] = ci + 1;
2285 
2286 	/* if we have made the queue un-full, notify the adapter */
2287 	if (notify && (aac_qinfo[queue].notify != 0))
2288 		AAC_QNOTIFY(sc, aac_qinfo[queue].notify);
2289 	error = 0;
2290 
2291 out:
2292 	return(error);
2293 }
2294 
2295 /*
2296  * Put our response to an Adapter Initialed Fib on the response queue
2297  */
2298 static int
2299 aac_enqueue_response(struct aac_softc *sc, int queue, struct aac_fib *fib)
2300 {
2301 	u_int32_t pi, ci;
2302 	int error;
2303 	u_int32_t fib_size;
2304 	u_int32_t fib_addr;
2305 
2306 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2307 
2308 	/* Tell the adapter where the FIB is */
2309 	fib_size = fib->Header.Size;
2310 	fib_addr = fib->Header.SenderFibAddress;
2311 	fib->Header.ReceiverFibAddress = fib_addr;
2312 
2313 	/* get the producer/consumer indices */
2314 	pi = sc->aac_queues->qt_qindex[queue][AAC_PRODUCER_INDEX];
2315 	ci = sc->aac_queues->qt_qindex[queue][AAC_CONSUMER_INDEX];
2316 
2317 	/* wrap the queue? */
2318 	if (pi >= aac_qinfo[queue].size)
2319 		pi = 0;
2320 
2321 	/* check for queue full */
2322 	if ((pi + 1) == ci) {
2323 		error = EBUSY;
2324 		goto out;
2325 	}
2326 
2327 	/* populate queue entry */
2328 	(sc->aac_qentries[queue] + pi)->aq_fib_size = fib_size;
2329 	(sc->aac_qentries[queue] + pi)->aq_fib_addr = fib_addr;
2330 
2331 	/* update producer index */
2332 	sc->aac_queues->qt_qindex[queue][AAC_PRODUCER_INDEX] = pi + 1;
2333 
2334 	/* notify the adapter if we know how */
2335 	if (aac_qinfo[queue].notify != 0)
2336 		AAC_QNOTIFY(sc, aac_qinfo[queue].notify);
2337 
2338 	error = 0;
2339 
2340 out:
2341 	return(error);
2342 }
2343 
2344 /*
2345  * Check for commands that have been outstanding for a suspiciously long time,
2346  * and complain about them.
2347  */
2348 static void
2349 aac_timeout(struct aac_softc *sc)
2350 {
2351 	struct aac_command *cm;
2352 	time_t deadline;
2353 	int timedout, code;
2354 
2355 	/*
2356 	 * Traverse the busy command list, bitch about late commands once
2357 	 * only.
2358 	 */
2359 	timedout = 0;
2360 	deadline = time_second - AAC_CMD_TIMEOUT;
2361 	TAILQ_FOREACH(cm, &sc->aac_busy, cm_link) {
2362 		if ((cm->cm_timestamp  < deadline)
2363 		    && !(cm->cm_flags & AAC_CMD_TIMEDOUT)) {
2364 			cm->cm_flags |= AAC_CMD_TIMEDOUT;
2365 			device_printf(sc->aac_dev,
2366 			    "COMMAND %p (TYPE %d) TIMEOUT AFTER %d SECONDS\n",
2367 			    cm, cm->cm_fib->Header.Command,
2368 			    (int)(time_second-cm->cm_timestamp));
2369 			AAC_PRINT_FIB(sc, cm->cm_fib);
2370 			timedout++;
2371 		}
2372 	}
2373 
2374 	if (timedout) {
2375 		code = AAC_GET_FWSTATUS(sc);
2376 		if (code != AAC_UP_AND_RUNNING) {
2377 			device_printf(sc->aac_dev, "WARNING! Controller is no "
2378 				      "longer running! code= 0x%x\n", code);
2379 		}
2380 	}
2381 	return;
2382 }
2383 
2384 /*
2385  * Interface Function Vectors
2386  */
2387 
2388 /*
2389  * Read the current firmware status word.
2390  */
2391 static int
2392 aac_sa_get_fwstatus(struct aac_softc *sc)
2393 {
2394 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2395 
2396 	return(AAC_MEM0_GETREG4(sc, AAC_SA_FWSTATUS));
2397 }
2398 
2399 static int
2400 aac_rx_get_fwstatus(struct aac_softc *sc)
2401 {
2402 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2403 
2404 	return(AAC_MEM0_GETREG4(sc, sc->flags & AAC_FLAGS_NEW_COMM ?
2405 	    AAC_RX_OMR0 : AAC_RX_FWSTATUS));
2406 }
2407 
2408 static int
2409 aac_rkt_get_fwstatus(struct aac_softc *sc)
2410 {
2411 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2412 
2413 	return(AAC_MEM0_GETREG4(sc, sc->flags & AAC_FLAGS_NEW_COMM ?
2414 	    AAC_RKT_OMR0 : AAC_RKT_FWSTATUS));
2415 }
2416 
2417 /*
2418  * Notify the controller of a change in a given queue
2419  */
2420 
2421 static void
2422 aac_sa_qnotify(struct aac_softc *sc, int qbit)
2423 {
2424 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2425 
2426 	AAC_MEM0_SETREG2(sc, AAC_SA_DOORBELL1_SET, qbit);
2427 }
2428 
2429 static void
2430 aac_rx_qnotify(struct aac_softc *sc, int qbit)
2431 {
2432 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2433 
2434 	AAC_MEM0_SETREG4(sc, AAC_RX_IDBR, qbit);
2435 }
2436 
2437 static void
2438 aac_rkt_qnotify(struct aac_softc *sc, int qbit)
2439 {
2440 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2441 
2442 	AAC_MEM0_SETREG4(sc, AAC_RKT_IDBR, qbit);
2443 }
2444 
2445 /*
2446  * Get the interrupt reason bits
2447  */
2448 static int
2449 aac_sa_get_istatus(struct aac_softc *sc)
2450 {
2451 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2452 
2453 	return(AAC_MEM0_GETREG2(sc, AAC_SA_DOORBELL0));
2454 }
2455 
2456 static int
2457 aac_rx_get_istatus(struct aac_softc *sc)
2458 {
2459 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2460 
2461 	return(AAC_MEM0_GETREG4(sc, AAC_RX_ODBR));
2462 }
2463 
2464 static int
2465 aac_rkt_get_istatus(struct aac_softc *sc)
2466 {
2467 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2468 
2469 	return(AAC_MEM0_GETREG4(sc, AAC_RKT_ODBR));
2470 }
2471 
2472 /*
2473  * Clear some interrupt reason bits
2474  */
2475 static void
2476 aac_sa_clear_istatus(struct aac_softc *sc, int mask)
2477 {
2478 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2479 
2480 	AAC_MEM0_SETREG2(sc, AAC_SA_DOORBELL0_CLEAR, mask);
2481 }
2482 
2483 static void
2484 aac_rx_clear_istatus(struct aac_softc *sc, int mask)
2485 {
2486 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2487 
2488 	AAC_MEM0_SETREG4(sc, AAC_RX_ODBR, mask);
2489 }
2490 
2491 static void
2492 aac_rkt_clear_istatus(struct aac_softc *sc, int mask)
2493 {
2494 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2495 
2496 	AAC_MEM0_SETREG4(sc, AAC_RKT_ODBR, mask);
2497 }
2498 
2499 /*
2500  * Populate the mailbox and set the command word
2501  */
2502 static void
2503 aac_sa_set_mailbox(struct aac_softc *sc, u_int32_t command,
2504 		u_int32_t arg0, u_int32_t arg1, u_int32_t arg2, u_int32_t arg3)
2505 {
2506 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2507 
2508 	AAC_MEM1_SETREG4(sc, AAC_SA_MAILBOX, command);
2509 	AAC_MEM1_SETREG4(sc, AAC_SA_MAILBOX + 4, arg0);
2510 	AAC_MEM1_SETREG4(sc, AAC_SA_MAILBOX + 8, arg1);
2511 	AAC_MEM1_SETREG4(sc, AAC_SA_MAILBOX + 12, arg2);
2512 	AAC_MEM1_SETREG4(sc, AAC_SA_MAILBOX + 16, arg3);
2513 }
2514 
2515 static void
2516 aac_rx_set_mailbox(struct aac_softc *sc, u_int32_t command,
2517 		u_int32_t arg0, u_int32_t arg1, u_int32_t arg2, u_int32_t arg3)
2518 {
2519 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2520 
2521 	AAC_MEM1_SETREG4(sc, AAC_RX_MAILBOX, command);
2522 	AAC_MEM1_SETREG4(sc, AAC_RX_MAILBOX + 4, arg0);
2523 	AAC_MEM1_SETREG4(sc, AAC_RX_MAILBOX + 8, arg1);
2524 	AAC_MEM1_SETREG4(sc, AAC_RX_MAILBOX + 12, arg2);
2525 	AAC_MEM1_SETREG4(sc, AAC_RX_MAILBOX + 16, arg3);
2526 }
2527 
2528 static void
2529 aac_rkt_set_mailbox(struct aac_softc *sc, u_int32_t command, u_int32_t arg0,
2530 		    u_int32_t arg1, u_int32_t arg2, u_int32_t arg3)
2531 {
2532 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2533 
2534 	AAC_MEM1_SETREG4(sc, AAC_RKT_MAILBOX, command);
2535 	AAC_MEM1_SETREG4(sc, AAC_RKT_MAILBOX + 4, arg0);
2536 	AAC_MEM1_SETREG4(sc, AAC_RKT_MAILBOX + 8, arg1);
2537 	AAC_MEM1_SETREG4(sc, AAC_RKT_MAILBOX + 12, arg2);
2538 	AAC_MEM1_SETREG4(sc, AAC_RKT_MAILBOX + 16, arg3);
2539 }
2540 
2541 /*
2542  * Fetch the immediate command status word
2543  */
2544 static int
2545 aac_sa_get_mailbox(struct aac_softc *sc, int mb)
2546 {
2547 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2548 
2549 	return(AAC_MEM1_GETREG4(sc, AAC_SA_MAILBOX + (mb * 4)));
2550 }
2551 
2552 static int
2553 aac_rx_get_mailbox(struct aac_softc *sc, int mb)
2554 {
2555 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2556 
2557 	return(AAC_MEM1_GETREG4(sc, AAC_RX_MAILBOX + (mb * 4)));
2558 }
2559 
2560 static int
2561 aac_rkt_get_mailbox(struct aac_softc *sc, int mb)
2562 {
2563 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2564 
2565 	return(AAC_MEM1_GETREG4(sc, AAC_RKT_MAILBOX + (mb * 4)));
2566 }
2567 
2568 /*
2569  * Set/clear interrupt masks
2570  */
2571 static void
2572 aac_sa_set_interrupts(struct aac_softc *sc, int enable)
2573 {
2574 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "%sable interrupts", enable ? "en" : "dis");
2575 
2576 	if (enable) {
2577 		AAC_MEM0_SETREG2((sc), AAC_SA_MASK0_CLEAR, AAC_DB_INTERRUPTS);
2578 	} else {
2579 		AAC_MEM0_SETREG2((sc), AAC_SA_MASK0_SET, ~0);
2580 	}
2581 }
2582 
2583 static void
2584 aac_rx_set_interrupts(struct aac_softc *sc, int enable)
2585 {
2586 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "%sable interrupts", enable ? "en" : "dis");
2587 
2588 	if (enable) {
2589 		if (sc->flags & AAC_FLAGS_NEW_COMM)
2590 			AAC_MEM0_SETREG4(sc, AAC_RX_OIMR, ~AAC_DB_INT_NEW_COMM);
2591 		else
2592 			AAC_MEM0_SETREG4(sc, AAC_RX_OIMR, ~AAC_DB_INTERRUPTS);
2593 	} else {
2594 		AAC_MEM0_SETREG4(sc, AAC_RX_OIMR, ~0);
2595 	}
2596 }
2597 
2598 static void
2599 aac_rkt_set_interrupts(struct aac_softc *sc, int enable)
2600 {
2601 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "%sable interrupts", enable ? "en" : "dis");
2602 
2603 	if (enable) {
2604 		if (sc->flags & AAC_FLAGS_NEW_COMM)
2605 			AAC_MEM0_SETREG4(sc, AAC_RKT_OIMR, ~AAC_DB_INT_NEW_COMM);
2606 		else
2607 			AAC_MEM0_SETREG4(sc, AAC_RKT_OIMR, ~AAC_DB_INTERRUPTS);
2608 	} else {
2609 		AAC_MEM0_SETREG4(sc, AAC_RKT_OIMR, ~0);
2610 	}
2611 }
2612 
2613 /*
2614  * New comm. interface: Send command functions
2615  */
2616 static int
2617 aac_rx_send_command(struct aac_softc *sc, struct aac_command *cm)
2618 {
2619 	u_int32_t index, device;
2620 
2621 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "send command (new comm.)");
2622 
2623 	index = AAC_MEM0_GETREG4(sc, AAC_RX_IQUE);
2624 	if (index == 0xffffffffL)
2625 		index = AAC_MEM0_GETREG4(sc, AAC_RX_IQUE);
2626 	if (index == 0xffffffffL)
2627 		return index;
2628 	aac_enqueue_busy(cm);
2629 	device = index;
2630 	AAC_MEM1_SETREG4(sc, device, (u_int32_t)(cm->cm_fibphys & 0xffffffffUL));
2631 	device += 4;
2632 	AAC_MEM1_SETREG4(sc, device, (u_int32_t)(cm->cm_fibphys >> 32));
2633 	device += 4;
2634 	AAC_MEM1_SETREG4(sc, device, cm->cm_fib->Header.Size);
2635 	AAC_MEM0_SETREG4(sc, AAC_RX_IQUE, index);
2636 	return 0;
2637 }
2638 
2639 static int
2640 aac_rkt_send_command(struct aac_softc *sc, struct aac_command *cm)
2641 {
2642 	u_int32_t index, device;
2643 
2644 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "send command (new comm.)");
2645 
2646 	index = AAC_MEM0_GETREG4(sc, AAC_RKT_IQUE);
2647 	if (index == 0xffffffffL)
2648 		index = AAC_MEM0_GETREG4(sc, AAC_RKT_IQUE);
2649 	if (index == 0xffffffffL)
2650 		return index;
2651 	aac_enqueue_busy(cm);
2652 	device = index;
2653 	AAC_MEM1_SETREG4(sc, device, (u_int32_t)(cm->cm_fibphys & 0xffffffffUL));
2654 	device += 4;
2655 	AAC_MEM1_SETREG4(sc, device, (u_int32_t)(cm->cm_fibphys >> 32));
2656 	device += 4;
2657 	AAC_MEM1_SETREG4(sc, device, cm->cm_fib->Header.Size);
2658 	AAC_MEM0_SETREG4(sc, AAC_RKT_IQUE, index);
2659 	return 0;
2660 }
2661 
2662 /*
2663  * New comm. interface: get, set outbound queue index
2664  */
2665 static int
2666 aac_rx_get_outb_queue(struct aac_softc *sc)
2667 {
2668 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2669 
2670 	return(AAC_MEM0_GETREG4(sc, AAC_RX_OQUE));
2671 }
2672 
2673 static int
2674 aac_rkt_get_outb_queue(struct aac_softc *sc)
2675 {
2676 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2677 
2678 	return(AAC_MEM0_GETREG4(sc, AAC_RKT_OQUE));
2679 }
2680 
2681 static void
2682 aac_rx_set_outb_queue(struct aac_softc *sc, int index)
2683 {
2684 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2685 
2686 	AAC_MEM0_SETREG4(sc, AAC_RX_OQUE, index);
2687 }
2688 
2689 static void
2690 aac_rkt_set_outb_queue(struct aac_softc *sc, int index)
2691 {
2692 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2693 
2694 	AAC_MEM0_SETREG4(sc, AAC_RKT_OQUE, index);
2695 }
2696 
2697 /*
2698  * Debugging and Diagnostics
2699  */
2700 
2701 /*
2702  * Print some information about the controller.
2703  */
2704 static void
2705 aac_describe_controller(struct aac_softc *sc)
2706 {
2707 	struct aac_fib *fib;
2708 	struct aac_adapter_info	*info;
2709 	char *adapter_type = "Adaptec RAID controller";
2710 
2711 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2712 
2713 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
2714 	aac_alloc_sync_fib(sc, &fib);
2715 
2716 	fib->data[0] = 0;
2717 	if (aac_sync_fib(sc, RequestAdapterInfo, 0, fib, 1)) {
2718 		device_printf(sc->aac_dev, "RequestAdapterInfo failed\n");
2719 		aac_release_sync_fib(sc);
2720 		lockmgr(&sc->aac_io_lock, LK_RELEASE);
2721 		return;
2722 	}
2723 
2724 	/* save the kernel revision structure for later use */
2725 	info = (struct aac_adapter_info *)&fib->data[0];
2726 	sc->aac_revision = info->KernelRevision;
2727 
2728 	if (bootverbose) {
2729 		device_printf(sc->aac_dev, "%s %dMHz, %dMB memory "
2730 		    "(%dMB cache, %dMB execution), %s\n",
2731 		    aac_describe_code(aac_cpu_variant, info->CpuVariant),
2732 		    info->ClockSpeed, info->TotalMem / (1024 * 1024),
2733 		    info->BufferMem / (1024 * 1024),
2734 		    info->ExecutionMem / (1024 * 1024),
2735 		    aac_describe_code(aac_battery_platform,
2736 		    info->batteryPlatform));
2737 
2738 		device_printf(sc->aac_dev,
2739 		    "Kernel %d.%d-%d, Build %d, S/N %6X\n",
2740 		    info->KernelRevision.external.comp.major,
2741 		    info->KernelRevision.external.comp.minor,
2742 		    info->KernelRevision.external.comp.dash,
2743 		    info->KernelRevision.buildNumber,
2744 		    (u_int32_t)(info->SerialNumber & 0xffffff));
2745 
2746 		device_printf(sc->aac_dev, "Supported Options=%b\n",
2747 			      sc->supported_options,
2748 			      "\20"
2749 			      "\1SNAPSHOT"
2750 			      "\2CLUSTERS"
2751 			      "\3WCACHE"
2752 			      "\4DATA64"
2753 			      "\5HOSTTIME"
2754 			      "\6RAID50"
2755 			      "\7WINDOW4GB"
2756 			      "\10SCSIUPGD"
2757 			      "\11SOFTERR"
2758 			      "\12NORECOND"
2759 			      "\13SGMAP64"
2760 			      "\14ALARM"
2761 			      "\15NONDASD"
2762 			      "\16SCSIMGT"
2763 			      "\17RAIDSCSI"
2764 			      "\21ADPTINFO"
2765 			      "\22NEWCOMM"
2766 			      "\23ARRAY64BIT"
2767 			      "\24HEATSENSOR");
2768 	}
2769 
2770 	if (sc->supported_options & AAC_SUPPORTED_SUPPLEMENT_ADAPTER_INFO) {
2771 		fib->data[0] = 0;
2772 		if (aac_sync_fib(sc, RequestSupplementAdapterInfo, 0, fib, 1))
2773 			device_printf(sc->aac_dev,
2774 			    "RequestSupplementAdapterInfo failed\n");
2775 		else
2776 			adapter_type = ((struct aac_supplement_adapter_info *)
2777 			    &fib->data[0])->AdapterTypeText;
2778 	}
2779 	device_printf(sc->aac_dev, "%s, aac driver %d.%d.%d-%d\n",
2780 		adapter_type,
2781 		AAC_DRIVER_MAJOR_VERSION, AAC_DRIVER_MINOR_VERSION,
2782 		AAC_DRIVER_BUGFIX_LEVEL, AAC_DRIVER_BUILD);
2783 
2784 	aac_release_sync_fib(sc);
2785 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
2786 }
2787 
2788 /*
2789  * Look up a text description of a numeric error code and return a pointer to
2790  * same.
2791  */
2792 static char *
2793 aac_describe_code(struct aac_code_lookup *table, u_int32_t code)
2794 {
2795 	int i;
2796 
2797 	for (i = 0; table[i].string != NULL; i++)
2798 		if (table[i].code == code)
2799 			return(table[i].string);
2800 	return(table[i + 1].string);
2801 }
2802 
2803 /*
2804  * Management Interface
2805  */
2806 
2807 static int
2808 aac_open(struct dev_open_args *ap)
2809 {
2810 	cdev_t dev = ap->a_head.a_dev;
2811 	struct aac_softc *sc;
2812 
2813 	sc = dev->si_drv1;
2814 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2815 	device_busy(sc->aac_dev);
2816 
2817 	return 0;
2818 }
2819 
2820 static int
2821 aac_ioctl(struct dev_ioctl_args *ap)
2822 {
2823 	caddr_t arg = ap->a_data;
2824 	cdev_t dev = ap->a_head.a_dev;
2825 	u_long cmd = ap->a_cmd;
2826 	union aac_statrequest *as;
2827 	struct aac_softc *sc;
2828 	int error = 0;
2829 
2830 	as = (union aac_statrequest *)arg;
2831 	sc = dev->si_drv1;
2832 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
2833 
2834 	switch (cmd) {
2835 	case AACIO_STATS:
2836 		switch (as->as_item) {
2837 		case AACQ_FREE:
2838 		case AACQ_BIO:
2839 		case AACQ_READY:
2840 		case AACQ_BUSY:
2841 			bcopy(&sc->aac_qstat[as->as_item], &as->as_qstat,
2842 			      sizeof(struct aac_qstat));
2843 			break;
2844 		default:
2845 			error = ENOENT;
2846 			break;
2847 		}
2848 	break;
2849 
2850 	case FSACTL_SENDFIB:
2851 	case FSACTL_SEND_LARGE_FIB:
2852 		arg = *(caddr_t*)arg;
2853 	case FSACTL_LNX_SENDFIB:
2854 	case FSACTL_LNX_SEND_LARGE_FIB:
2855 		fwprintf(sc, HBA_FLAGS_DBG_IOCTL_COMMANDS_B, "FSACTL_SENDFIB");
2856 		error = aac_ioctl_sendfib(sc, arg);
2857 		break;
2858 	case FSACTL_SEND_RAW_SRB:
2859 		arg = *(caddr_t*)arg;
2860 	case FSACTL_LNX_SEND_RAW_SRB:
2861 		fwprintf(sc, HBA_FLAGS_DBG_IOCTL_COMMANDS_B, "FSACTL_SEND_RAW_SRB");
2862 		error = aac_ioctl_send_raw_srb(sc, arg);
2863 		break;
2864 	case FSACTL_AIF_THREAD:
2865 	case FSACTL_LNX_AIF_THREAD:
2866 		fwprintf(sc, HBA_FLAGS_DBG_IOCTL_COMMANDS_B, "FSACTL_AIF_THREAD");
2867 		error = EINVAL;
2868 		break;
2869 	case FSACTL_OPEN_GET_ADAPTER_FIB:
2870 		arg = *(caddr_t*)arg;
2871 	case FSACTL_LNX_OPEN_GET_ADAPTER_FIB:
2872 		fwprintf(sc, HBA_FLAGS_DBG_IOCTL_COMMANDS_B, "FSACTL_OPEN_GET_ADAPTER_FIB");
2873 		error = aac_open_aif(sc, arg);
2874 		break;
2875 	case FSACTL_GET_NEXT_ADAPTER_FIB:
2876 		arg = *(caddr_t*)arg;
2877 	case FSACTL_LNX_GET_NEXT_ADAPTER_FIB:
2878 		fwprintf(sc, HBA_FLAGS_DBG_IOCTL_COMMANDS_B, "FSACTL_GET_NEXT_ADAPTER_FIB");
2879 		error = aac_getnext_aif(sc, arg);
2880 		break;
2881 	case FSACTL_CLOSE_GET_ADAPTER_FIB:
2882 		arg = *(caddr_t*)arg;
2883 	case FSACTL_LNX_CLOSE_GET_ADAPTER_FIB:
2884 		fwprintf(sc, HBA_FLAGS_DBG_IOCTL_COMMANDS_B, "FSACTL_CLOSE_GET_ADAPTER_FIB");
2885 		error = aac_close_aif(sc, arg);
2886 		break;
2887 	case FSACTL_MINIPORT_REV_CHECK:
2888 		arg = *(caddr_t*)arg;
2889 	case FSACTL_LNX_MINIPORT_REV_CHECK:
2890 		fwprintf(sc, HBA_FLAGS_DBG_IOCTL_COMMANDS_B, "FSACTL_MINIPORT_REV_CHECK");
2891 		error = aac_rev_check(sc, arg);
2892 		break;
2893 	case FSACTL_QUERY_DISK:
2894 		arg = *(caddr_t*)arg;
2895 	case FSACTL_LNX_QUERY_DISK:
2896 		fwprintf(sc, HBA_FLAGS_DBG_IOCTL_COMMANDS_B, "FSACTL_QUERY_DISK");
2897 		error = aac_query_disk(sc, arg);
2898 		break;
2899 	case FSACTL_DELETE_DISK:
2900 	case FSACTL_LNX_DELETE_DISK:
2901 		/*
2902 		 * We don't trust the underland to tell us when to delete a
2903 		 * container, rather we rely on an AIF coming from the
2904 		 * controller
2905 		 */
2906 		error = 0;
2907 		break;
2908 	case FSACTL_GET_PCI_INFO:
2909 		arg = *(caddr_t*)arg;
2910 	case FSACTL_LNX_GET_PCI_INFO:
2911 		fwprintf(sc, HBA_FLAGS_DBG_IOCTL_COMMANDS_B, "FSACTL_GET_PCI_INFO");
2912 		error = aac_get_pci_info(sc, arg);
2913 		break;
2914 	case FSACTL_GET_FEATURES:
2915 		arg = *(caddr_t*)arg;
2916 	case FSACTL_LNX_GET_FEATURES:
2917 		fwprintf(sc, HBA_FLAGS_DBG_IOCTL_COMMANDS_B, "FSACTL_GET_FEATURES");
2918 		error = aac_supported_features(sc, arg);
2919 		break;
2920 	default:
2921 		fwprintf(sc, HBA_FLAGS_DBG_IOCTL_COMMANDS_B, "unsupported cmd 0x%lx\n", cmd);
2922 		error = EINVAL;
2923 		break;
2924 	}
2925 	return(error);
2926 }
2927 
2928 static struct filterops aac_filterops =
2929 	{ FILTEROP_ISFD|FILTEROP_MPSAFE, NULL, aac_filter_detach, aac_filter_read };
2930 
2931 static int
2932 aac_kqfilter(struct dev_kqfilter_args *ap)
2933 {
2934 	cdev_t dev = ap->a_head.a_dev;
2935 	struct aac_softc *sc = dev->si_drv1;
2936 	struct knote *kn = ap->a_kn;
2937 	struct klist *klist;
2938 
2939 	ap->a_result = 0;
2940 
2941 	switch (kn->kn_filter) {
2942 	case EVFILT_READ:
2943 		kn->kn_fop = &aac_filterops;
2944 		kn->kn_hook = (caddr_t)sc;
2945 		break;
2946 	default:
2947 		ap->a_result = EOPNOTSUPP;
2948 		return (0);
2949 	}
2950 
2951 	klist = &sc->rcv_kq.ki_note;
2952 	knote_insert(klist, kn);
2953 
2954 	return (0);
2955 }
2956 
2957 static void
2958 aac_filter_detach(struct knote *kn)
2959 {
2960 	struct aac_softc *sc = (struct aac_softc *)kn->kn_hook;
2961 	struct klist *klist;
2962 
2963 	klist = &sc->rcv_kq.ki_note;
2964 	knote_remove(klist, kn);
2965 }
2966 
2967 static int
2968 aac_filter_read(struct knote *kn, long hint)
2969 {
2970 	struct aac_softc *sc;
2971 	struct aac_fib_context *ctx;
2972 
2973 	sc = (struct aac_softc *)kn->kn_hook;
2974 
2975 	lockmgr(&sc->aac_aifq_lock, LK_EXCLUSIVE);
2976 	for (ctx = sc->fibctx; ctx; ctx = ctx->next)
2977 		if (ctx->ctx_idx != sc->aifq_idx || ctx->ctx_wrap)
2978 			return(1);
2979 	lockmgr(&sc->aac_aifq_lock, LK_RELEASE);
2980 
2981 	return (0);
2982 }
2983 
2984 static void
2985 aac_ioctl_event(struct aac_softc *sc, struct aac_event *event, void *arg)
2986 {
2987 
2988 	switch (event->ev_type) {
2989 	case AAC_EVENT_CMFREE:
2990 		KKASSERT(lockstatus(&sc->aac_io_lock, curthread) != 0);
2991 		if (aac_alloc_command(sc, (struct aac_command **)arg)) {
2992 			aac_add_event(sc, event);
2993 			return;
2994 		}
2995 		kfree(event, M_AACBUF);
2996 		wakeup(arg);
2997 		break;
2998 	default:
2999 		break;
3000 	}
3001 }
3002 
3003 /*
3004  * Send a FIB supplied from userspace
3005  */
3006 static int
3007 aac_ioctl_sendfib(struct aac_softc *sc, caddr_t ufib)
3008 {
3009 	struct aac_command *cm;
3010 	int size, error;
3011 
3012 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
3013 
3014 	cm = NULL;
3015 
3016 	/*
3017 	 * Get a command
3018 	 */
3019 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
3020 	if (aac_alloc_command(sc, &cm)) {
3021 		struct aac_event *event;
3022 
3023 		event = kmalloc(sizeof(struct aac_event), M_AACBUF,
3024 		    M_INTWAIT | M_ZERO);
3025 		event->ev_type = AAC_EVENT_CMFREE;
3026 		event->ev_callback = aac_ioctl_event;
3027 		event->ev_arg = &cm;
3028 		aac_add_event(sc, event);
3029 		lksleep(&cm, &sc->aac_io_lock, 0, "sendfib", 0);
3030 	}
3031 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
3032 
3033 	/*
3034 	 * Fetch the FIB header, then re-copy to get data as well.
3035 	 */
3036 	if ((error = copyin(ufib, cm->cm_fib,
3037 			    sizeof(struct aac_fib_header))) != 0)
3038 		goto out;
3039 	size = cm->cm_fib->Header.Size + sizeof(struct aac_fib_header);
3040 	if (size > sc->aac_max_fib_size) {
3041 		device_printf(sc->aac_dev, "incoming FIB oversized (%d > %d)\n",
3042 			      size, sc->aac_max_fib_size);
3043 		size = sc->aac_max_fib_size;
3044 	}
3045 	if ((error = copyin(ufib, cm->cm_fib, size)) != 0)
3046 		goto out;
3047 	cm->cm_fib->Header.Size = size;
3048 	cm->cm_timestamp = time_second;
3049 
3050 	/*
3051 	 * Pass the FIB to the controller, wait for it to complete.
3052 	 */
3053 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
3054 	error = aac_wait_command(cm);
3055 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
3056 	if (error != 0) {
3057 		device_printf(sc->aac_dev,
3058 			      "aac_wait_command return %d\n", error);
3059 		goto out;
3060 	}
3061 
3062 	/*
3063 	 * Copy the FIB and data back out to the caller.
3064 	 */
3065 	size = cm->cm_fib->Header.Size;
3066 	if (size > sc->aac_max_fib_size) {
3067 		device_printf(sc->aac_dev, "outbound FIB oversized (%d > %d)\n",
3068 			      size, sc->aac_max_fib_size);
3069 		size = sc->aac_max_fib_size;
3070 	}
3071 	error = copyout(cm->cm_fib, ufib, size);
3072 
3073 out:
3074 	if (cm != NULL) {
3075 		lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
3076 		aac_release_command(cm);
3077 		lockmgr(&sc->aac_io_lock, LK_RELEASE);
3078 	}
3079 	return(error);
3080 }
3081 
3082 /*
3083  * Send a passthrough FIB supplied from userspace
3084  */
3085 static int
3086 aac_ioctl_send_raw_srb(struct aac_softc *sc, caddr_t arg)
3087 {
3088 	struct aac_command *cm;
3089 	struct aac_event *event;
3090 	struct aac_fib *fib;
3091 	struct aac_srb *srbcmd, *user_srb;
3092 	struct aac_sg_entry *sge;
3093 	struct aac_sg_entry64 *sge64;
3094 	void *srb_sg_address, *ureply;
3095 	uint32_t fibsize, srb_sg_bytecount;
3096 	int error, transfer_data;
3097 
3098 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
3099 
3100 	cm = NULL;
3101 	transfer_data = 0;
3102 	fibsize = 0;
3103 	user_srb = (struct aac_srb *)arg;
3104 
3105 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
3106 	if (aac_alloc_command(sc, &cm)) {
3107 		 event = kmalloc(sizeof(struct aac_event), M_AACBUF,
3108 		    M_NOWAIT | M_ZERO);
3109 		if (event == NULL) {
3110 			error = EBUSY;
3111 			lockmgr(&sc->aac_io_lock, LK_RELEASE);
3112 			goto out;
3113 		}
3114 		event->ev_type = AAC_EVENT_CMFREE;
3115 		event->ev_callback = aac_ioctl_event;
3116 		event->ev_arg = &cm;
3117 		aac_add_event(sc, event);
3118 		lksleep(cm, &sc->aac_io_lock, 0, "aacraw", 0);
3119 	}
3120 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
3121 
3122 	cm->cm_data = NULL;
3123 	fib = cm->cm_fib;
3124 	srbcmd = (struct aac_srb *)fib->data;
3125 	error = copyin(&user_srb->data_len, &fibsize, sizeof(uint32_t));
3126 	if (error != 0)
3127 		goto out;
3128 	if (fibsize > (sc->aac_max_fib_size - sizeof(struct aac_fib_header))) {
3129 		error = EINVAL;
3130 		goto out;
3131 	}
3132 	error = copyin(user_srb, srbcmd, fibsize);
3133 	if (error != 0)
3134 		goto out;
3135 	srbcmd->function = 0;
3136 	srbcmd->retry_limit = 0;
3137 	if (srbcmd->sg_map.SgCount > 1) {
3138 		error = EINVAL;
3139 		goto out;
3140 	}
3141 
3142 	/* Retrieve correct SG entries. */
3143 	if (fibsize == (sizeof(struct aac_srb) +
3144 	    srbcmd->sg_map.SgCount * sizeof(struct aac_sg_entry))) {
3145 		sge = srbcmd->sg_map.SgEntry;
3146 		sge64 = NULL;
3147 		srb_sg_bytecount = sge->SgByteCount;
3148 		srb_sg_address = (void *)(uintptr_t)sge->SgAddress;
3149 	}
3150 #ifdef __amd64__
3151 	else if (fibsize == (sizeof(struct aac_srb) +
3152 	    srbcmd->sg_map.SgCount * sizeof(struct aac_sg_entry64))) {
3153 		sge = NULL;
3154 		sge64 = (struct aac_sg_entry64 *)srbcmd->sg_map.SgEntry;
3155 		srb_sg_bytecount = sge64->SgByteCount;
3156 		srb_sg_address = (void *)sge64->SgAddress;
3157 		if (sge64->SgAddress > 0xffffffffull &&
3158 		    (sc->flags & AAC_FLAGS_SG_64BIT) == 0) {
3159 			error = EINVAL;
3160 			goto out;
3161 		}
3162 	}
3163 #endif
3164 	else {
3165 		error = EINVAL;
3166 		goto out;
3167 	}
3168 	ureply = (char *)arg + fibsize;
3169 	srbcmd->data_len = srb_sg_bytecount;
3170 	if (srbcmd->sg_map.SgCount == 1)
3171 		transfer_data = 1;
3172 
3173 	cm->cm_sgtable = (struct aac_sg_table *)&srbcmd->sg_map;
3174 	if (transfer_data) {
3175 		cm->cm_datalen = srb_sg_bytecount;
3176 		cm->cm_data = kmalloc(cm->cm_datalen, M_AACBUF, M_NOWAIT);
3177 		if (cm->cm_data == NULL) {
3178 			error = ENOMEM;
3179 			goto out;
3180 		}
3181 		if (srbcmd->flags & AAC_SRB_FLAGS_DATA_IN)
3182 			cm->cm_flags |= AAC_CMD_DATAIN;
3183 		if (srbcmd->flags & AAC_SRB_FLAGS_DATA_OUT) {
3184 			cm->cm_flags |= AAC_CMD_DATAOUT;
3185 			error = copyin(srb_sg_address, cm->cm_data,
3186 			    cm->cm_datalen);
3187 			if (error != 0)
3188 				goto out;
3189 		}
3190 	}
3191 
3192 	fib->Header.Size = sizeof(struct aac_fib_header) +
3193 	    sizeof(struct aac_srb);
3194 	fib->Header.XferState =
3195 	    AAC_FIBSTATE_HOSTOWNED   |
3196 	    AAC_FIBSTATE_INITIALISED |
3197 	    AAC_FIBSTATE_EMPTY       |
3198 	    AAC_FIBSTATE_FROMHOST    |
3199 	    AAC_FIBSTATE_REXPECTED   |
3200 	    AAC_FIBSTATE_NORM        |
3201 	    AAC_FIBSTATE_ASYNC       |
3202 	    AAC_FIBSTATE_FAST_RESPONSE;
3203 	fib->Header.Command = (sc->flags & AAC_FLAGS_SG_64BIT) != 0 ?
3204 	    ScsiPortCommandU64 : ScsiPortCommand;
3205 
3206 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
3207 	aac_wait_command(cm);
3208 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
3209 
3210 	if (transfer_data && (srbcmd->flags & AAC_SRB_FLAGS_DATA_IN) != 0) {
3211 		error = copyout(cm->cm_data, srb_sg_address, cm->cm_datalen);
3212 		if (error != 0)
3213 			goto out;
3214 	}
3215 	error = copyout(fib->data, ureply, sizeof(struct aac_srb_response));
3216 out:
3217 	if (cm != NULL) {
3218 		if (cm->cm_data != NULL)
3219 			kfree(cm->cm_data, M_AACBUF);
3220 		lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
3221 		aac_release_command(cm);
3222 		lockmgr(&sc->aac_io_lock, LK_RELEASE);
3223 	}
3224 	return(error);
3225 }
3226 
3227 static int
3228 aac_close(struct dev_close_args *ap)
3229 {
3230 	cdev_t dev = ap->a_head.a_dev;
3231 	struct aac_softc *sc;
3232 
3233 	sc = dev->si_drv1;
3234 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
3235 	get_mplock();
3236 	device_unbusy(sc->aac_dev);
3237 	rel_mplock();
3238 
3239 	return 0;
3240 }
3241 
3242 /*
3243  * Handle an AIF sent to us by the controller; queue it for later reference.
3244  * If the queue fills up, then drop the older entries.
3245  */
3246 static void
3247 aac_handle_aif(struct aac_softc *sc, struct aac_fib *fib)
3248 {
3249 	struct aac_aif_command *aif;
3250 	struct aac_container *co, *co_next;
3251 	struct aac_fib_context *ctx;
3252 	struct aac_mntinforesp *mir;
3253 	int next, current, found;
3254 	int count = 0, added = 0, i = 0;
3255 	uint32_t channel;
3256 
3257 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
3258 
3259 	aif = (struct aac_aif_command*)&fib->data[0];
3260 	aac_print_aif(sc, aif);
3261 
3262 	/* Is it an event that we should care about? */
3263 	switch (aif->command) {
3264 	case AifCmdEventNotify:
3265 		switch (aif->data.EN.type) {
3266 		case AifEnAddContainer:
3267 		case AifEnDeleteContainer:
3268 			/*
3269 			 * A container was added or deleted, but the message
3270 			 * doesn't tell us anything else!  Re-enumerate the
3271 			 * containers and sort things out.
3272 			 */
3273 			aac_alloc_sync_fib(sc, &fib);
3274 			do {
3275 				/*
3276 				 * Ask the controller for its containers one at
3277 				 * a time.
3278 				 * XXX What if the controller's list changes
3279 				 * midway through this enumaration?
3280 				 * XXX This should be done async.
3281 				 */
3282 				if ((mir = aac_get_container_info(sc, fib, i)) == NULL)
3283 					continue;
3284 				if (i == 0)
3285 					count = mir->MntRespCount;
3286 				/*
3287 				 * Check the container against our list.
3288 				 * co->co_found was already set to 0 in a
3289 				 * previous run.
3290 				 */
3291 				if ((mir->Status == ST_OK) &&
3292 				    (mir->MntTable[0].VolType != CT_NONE)) {
3293 					found = 0;
3294 					TAILQ_FOREACH(co,
3295 						      &sc->aac_container_tqh,
3296 						      co_link) {
3297 						if (co->co_mntobj.ObjectId ==
3298 						    mir->MntTable[0].ObjectId) {
3299 							co->co_found = 1;
3300 							found = 1;
3301 							break;
3302 						}
3303 					}
3304 					/*
3305 					 * If the container matched, continue
3306 					 * in the list.
3307 					 */
3308 					if (found) {
3309 						i++;
3310 						continue;
3311 					}
3312 
3313 					/*
3314 					 * This is a new container.  Do all the
3315 					 * appropriate things to set it up.
3316 					 */
3317 					aac_add_container(sc, mir, 1);
3318 					added = 1;
3319 				}
3320 				i++;
3321 			} while ((i < count) && (i < AAC_MAX_CONTAINERS));
3322 			aac_release_sync_fib(sc);
3323 
3324 			/*
3325 			 * Go through our list of containers and see which ones
3326 			 * were not marked 'found'.  Since the controller didn't
3327 			 * list them they must have been deleted.  Do the
3328 			 * appropriate steps to destroy the device.  Also reset
3329 			 * the co->co_found field.
3330 			 */
3331 			co = TAILQ_FIRST(&sc->aac_container_tqh);
3332 			while (co != NULL) {
3333 				if (co->co_found == 0) {
3334 					lockmgr(&sc->aac_io_lock, LK_RELEASE);
3335 					get_mplock();
3336 					device_delete_child(sc->aac_dev,
3337 							    co->co_disk);
3338 					rel_mplock();
3339 					lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
3340 					co_next = TAILQ_NEXT(co, co_link);
3341 					lockmgr(&sc->aac_container_lock, LK_EXCLUSIVE);
3342 					TAILQ_REMOVE(&sc->aac_container_tqh, co,
3343 						     co_link);
3344 					lockmgr(&sc->aac_container_lock, LK_RELEASE);
3345 					kfree(co, M_AACBUF);
3346 					co = co_next;
3347 				} else {
3348 					co->co_found = 0;
3349 					co = TAILQ_NEXT(co, co_link);
3350 				}
3351 			}
3352 
3353 			/* Attach the newly created containers */
3354 			if (added) {
3355 				lockmgr(&sc->aac_io_lock, LK_RELEASE);
3356 				get_mplock();
3357 				bus_generic_attach(sc->aac_dev);
3358 				rel_mplock();
3359 				lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
3360 			}
3361 
3362 			break;
3363 
3364 		case AifEnEnclosureManagement:
3365 			switch (aif->data.EN.data.EEE.eventType) {
3366 			case AIF_EM_DRIVE_INSERTION:
3367 			case AIF_EM_DRIVE_REMOVAL:
3368 				channel = aif->data.EN.data.EEE.unitID;
3369 				if (sc->cam_rescan_cb != NULL)
3370 					sc->cam_rescan_cb(sc,
3371 					    (channel >> 24) & 0xF,
3372 					    (channel & 0xFFFF));
3373 				break;
3374 			}
3375 			break;
3376 
3377 		case AifEnAddJBOD:
3378 		case AifEnDeleteJBOD:
3379 			channel = aif->data.EN.data.ECE.container;
3380 			if (sc->cam_rescan_cb != NULL)
3381 				sc->cam_rescan_cb(sc, (channel >> 24) & 0xF,
3382 				    AAC_CAM_TARGET_WILDCARD);
3383 			break;
3384 
3385 		default:
3386 			break;
3387 		}
3388 
3389 	default:
3390 		break;
3391 	}
3392 
3393 	/* Copy the AIF data to the AIF queue for ioctl retrieval */
3394 	lockmgr(&sc->aac_aifq_lock, LK_EXCLUSIVE);
3395 	current = sc->aifq_idx;
3396 	next = (current + 1) % AAC_AIFQ_LENGTH;
3397 	if (next == 0)
3398 		sc->aifq_filled = 1;
3399 	bcopy(fib, &sc->aac_aifq[current], sizeof(struct aac_fib));
3400 	/* modify AIF contexts */
3401 	if (sc->aifq_filled) {
3402 		for (ctx = sc->fibctx; ctx; ctx = ctx->next) {
3403 			if (next == ctx->ctx_idx)
3404 				ctx->ctx_wrap = 1;
3405 			else if (current == ctx->ctx_idx && ctx->ctx_wrap)
3406 				ctx->ctx_idx = next;
3407 		}
3408 	}
3409 	sc->aifq_idx = next;
3410 	/* On the off chance that someone is sleeping for an aif... */
3411 	if (sc->aac_state & AAC_STATE_AIF_SLEEPER)
3412 		wakeup(sc->aac_aifq);
3413 	/* token may have been lost */
3414 	/* Wakeup any poll()ers */
3415 	KNOTE(&sc->rcv_kq.ki_note, 0);
3416 	/* token may have been lost */
3417 	lockmgr(&sc->aac_aifq_lock, LK_RELEASE);
3418 
3419 	return;
3420 }
3421 
3422 /*
3423  * Return the Revision of the driver to userspace and check to see if the
3424  * userspace app is possibly compatible.  This is extremely bogus since
3425  * our driver doesn't follow Adaptec's versioning system.  Cheat by just
3426  * returning what the card reported.
3427  */
3428 static int
3429 aac_rev_check(struct aac_softc *sc, caddr_t udata)
3430 {
3431 	struct aac_rev_check rev_check;
3432 	struct aac_rev_check_resp rev_check_resp;
3433 	int error = 0;
3434 
3435 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
3436 
3437 	/*
3438 	 * Copyin the revision struct from userspace
3439 	 */
3440 	if ((error = copyin(udata, (caddr_t)&rev_check,
3441 			sizeof(struct aac_rev_check))) != 0) {
3442 		return error;
3443 	}
3444 
3445 	fwprintf(sc, HBA_FLAGS_DBG_IOCTL_COMMANDS_B, "Userland revision= %d\n",
3446 	      rev_check.callingRevision.buildNumber);
3447 
3448 	/*
3449 	 * Doctor up the response struct.
3450 	 */
3451 	rev_check_resp.possiblyCompatible = 1;
3452 	rev_check_resp.adapterSWRevision.external.comp.major =
3453 	    AAC_DRIVER_MAJOR_VERSION;
3454 	rev_check_resp.adapterSWRevision.external.comp.minor =
3455 	    AAC_DRIVER_MINOR_VERSION;
3456 	rev_check_resp.adapterSWRevision.external.comp.type =
3457 	    AAC_DRIVER_TYPE;
3458 	rev_check_resp.adapterSWRevision.external.comp.dash =
3459 	    AAC_DRIVER_BUGFIX_LEVEL;
3460 	rev_check_resp.adapterSWRevision.buildNumber =
3461 	    AAC_DRIVER_BUILD;
3462 
3463 	return(copyout((caddr_t)&rev_check_resp, udata,
3464 			sizeof(struct aac_rev_check_resp)));
3465 }
3466 
3467 /*
3468  * Pass the fib context to the caller
3469  */
3470 static int
3471 aac_open_aif(struct aac_softc *sc, caddr_t arg)
3472 {
3473 	struct aac_fib_context *fibctx, *ctx;
3474 	int error = 0;
3475 
3476 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
3477 
3478 	fibctx = kmalloc(sizeof(struct aac_fib_context), M_AACBUF, M_NOWAIT|M_ZERO);
3479 	if (fibctx == NULL)
3480 		return (ENOMEM);
3481 
3482 	lockmgr(&sc->aac_aifq_lock, LK_EXCLUSIVE);
3483 	/* all elements are already 0, add to queue */
3484 	if (sc->fibctx == NULL)
3485 		sc->fibctx = fibctx;
3486 	else {
3487 		for (ctx = sc->fibctx; ctx->next; ctx = ctx->next)
3488 			;
3489 		ctx->next = fibctx;
3490 		fibctx->prev = ctx;
3491 	}
3492 
3493 	/* evaluate unique value */
3494 	fibctx->unique = (*(u_int32_t *)&fibctx & 0xffffffff);
3495 	ctx = sc->fibctx;
3496 	while (ctx != fibctx) {
3497 		if (ctx->unique == fibctx->unique) {
3498 			fibctx->unique++;
3499 			ctx = sc->fibctx;
3500 		} else {
3501 			ctx = ctx->next;
3502 		}
3503 	}
3504 	lockmgr(&sc->aac_aifq_lock, LK_RELEASE);
3505 
3506 	error = copyout(&fibctx->unique, (void *)arg, sizeof(u_int32_t));
3507 	if (error)
3508 		aac_close_aif(sc, (caddr_t)ctx);
3509 	return error;
3510 }
3511 
3512 /*
3513  * Close the caller's fib context
3514  */
3515 static int
3516 aac_close_aif(struct aac_softc *sc, caddr_t arg)
3517 {
3518 	struct aac_fib_context *ctx;
3519 
3520 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
3521 
3522 	lockmgr(&sc->aac_aifq_lock, LK_EXCLUSIVE);
3523 	for (ctx = sc->fibctx; ctx; ctx = ctx->next) {
3524 		if (ctx->unique == *(uint32_t *)&arg) {
3525 			if (ctx == sc->fibctx)
3526 				sc->fibctx = NULL;
3527 			else {
3528 				ctx->prev->next = ctx->next;
3529 				if (ctx->next)
3530 					ctx->next->prev = ctx->prev;
3531 			}
3532 			break;
3533 		}
3534 	}
3535 	lockmgr(&sc->aac_aifq_lock, LK_RELEASE);
3536 	if (ctx)
3537 		kfree(ctx, M_AACBUF);
3538 
3539 	return 0;
3540 }
3541 
3542 /*
3543  * Pass the caller the next AIF in their queue
3544  */
3545 static int
3546 aac_getnext_aif(struct aac_softc *sc, caddr_t arg)
3547 {
3548 	struct get_adapter_fib_ioctl agf;
3549 	struct aac_fib_context *ctx;
3550 	int error;
3551 
3552 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
3553 
3554 	if ((error = copyin(arg, &agf, sizeof(agf))) == 0) {
3555 		for (ctx = sc->fibctx; ctx; ctx = ctx->next) {
3556 			if (agf.AdapterFibContext == ctx->unique)
3557 				break;
3558 		}
3559 		if (!ctx)
3560 			return (EFAULT);
3561 
3562 		error = aac_return_aif(sc, ctx, agf.AifFib);
3563 		if (error == EAGAIN && agf.Wait) {
3564 			fwprintf(sc, HBA_FLAGS_DBG_AIF_B, "aac_getnext_aif(): waiting for AIF");
3565 			sc->aac_state |= AAC_STATE_AIF_SLEEPER;
3566 			while (error == EAGAIN) {
3567 				error = tsleep(sc->aac_aifq,
3568 					       PCATCH, "aacaif", 0);
3569 				if (error == 0)
3570 					error = aac_return_aif(sc, ctx, agf.AifFib);
3571 			}
3572 			sc->aac_state &= ~AAC_STATE_AIF_SLEEPER;
3573 		}
3574 	}
3575 	return(error);
3576 }
3577 
3578 /*
3579  * Hand the next AIF off the top of the queue out to userspace.
3580  */
3581 static int
3582 aac_return_aif(struct aac_softc *sc, struct aac_fib_context *ctx, caddr_t uptr)
3583 {
3584 	int current, error;
3585 
3586 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
3587 
3588 	lockmgr(&sc->aac_aifq_lock, LK_EXCLUSIVE);
3589 	current = ctx->ctx_idx;
3590 	if (current == sc->aifq_idx && !ctx->ctx_wrap) {
3591 		/* empty */
3592 		lockmgr(&sc->aac_aifq_lock, LK_RELEASE);
3593 		return (EAGAIN);
3594 	}
3595 	error =
3596 		copyout(&sc->aac_aifq[current], (void *)uptr, sizeof(struct aac_fib));
3597 	if (error)
3598 		device_printf(sc->aac_dev,
3599 		    "aac_return_aif: copyout returned %d\n", error);
3600 	else {
3601 		ctx->ctx_wrap = 0;
3602 		ctx->ctx_idx = (current + 1) % AAC_AIFQ_LENGTH;
3603 	}
3604 	lockmgr(&sc->aac_aifq_lock, LK_RELEASE);
3605 	return(error);
3606 }
3607 
3608 static int
3609 aac_get_pci_info(struct aac_softc *sc, caddr_t uptr)
3610 {
3611 	struct aac_pci_info {
3612 		u_int32_t bus;
3613 		u_int32_t slot;
3614 	} pciinf;
3615 	int error;
3616 
3617 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
3618 
3619 	pciinf.bus = pci_get_bus(sc->aac_dev);
3620 	pciinf.slot = pci_get_slot(sc->aac_dev);
3621 
3622 	error = copyout((caddr_t)&pciinf, uptr,
3623 			sizeof(struct aac_pci_info));
3624 
3625 	return (error);
3626 }
3627 
3628 static int
3629 aac_supported_features(struct aac_softc *sc, caddr_t uptr)
3630 {
3631 	struct aac_features f;
3632 	int error;
3633 
3634 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
3635 
3636 	if ((error = copyin(uptr, &f, sizeof (f))) != 0)
3637 		return (error);
3638 
3639 	/*
3640 	 * When the management driver receives FSACTL_GET_FEATURES ioctl with
3641 	 * ALL zero in the featuresState, the driver will return the current
3642 	 * state of all the supported features, the data field will not be
3643 	 * valid.
3644 	 * When the management driver receives FSACTL_GET_FEATURES ioctl with
3645 	 * a specific bit set in the featuresState, the driver will return the
3646 	 * current state of this specific feature and whatever data that are
3647 	 * associated with the feature in the data field or perform whatever
3648 	 * action needed indicates in the data field.
3649 	 */
3650 	if (f.feat.fValue == 0) {
3651 		f.feat.fBits.largeLBA =
3652 		    (sc->flags & AAC_FLAGS_LBA_64BIT) ? 1 : 0;
3653 		/* TODO: In the future, add other features state here as well */
3654 	} else {
3655 		if (f.feat.fBits.largeLBA)
3656 			f.feat.fBits.largeLBA =
3657 			    (sc->flags & AAC_FLAGS_LBA_64BIT) ? 1 : 0;
3658 		/* TODO: Add other features state and data in the future */
3659 	}
3660 
3661 	error = copyout(&f, uptr, sizeof (f));
3662 	return (error);
3663 }
3664 
3665 /*
3666  * Give the userland some information about the container.  The AAC arch
3667  * expects the driver to be a SCSI passthrough type driver, so it expects
3668  * the containers to have b:t:l numbers.  Fake it.
3669  */
3670 static int
3671 aac_query_disk(struct aac_softc *sc, caddr_t uptr)
3672 {
3673 	struct aac_query_disk query_disk;
3674 	struct aac_container *co;
3675 	struct aac_disk	*disk;
3676 	int error, id;
3677 
3678 	fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, "");
3679 
3680 	disk = NULL;
3681 
3682 	error = copyin(uptr, (caddr_t)&query_disk,
3683 		       sizeof(struct aac_query_disk));
3684 	if (error)
3685 		return (error);
3686 
3687 	id = query_disk.ContainerNumber;
3688 	if (id == -1)
3689 		return (EINVAL);
3690 
3691 	lockmgr(&sc->aac_container_lock, LK_EXCLUSIVE);
3692 	TAILQ_FOREACH(co, &sc->aac_container_tqh, co_link) {
3693 		if (co->co_mntobj.ObjectId == id)
3694 			break;
3695 		}
3696 
3697 	if (co == NULL) {
3698 			query_disk.Valid = 0;
3699 			query_disk.Locked = 0;
3700 			query_disk.Deleted = 1;		/* XXX is this right? */
3701 	} else {
3702 		disk = device_get_softc(co->co_disk);
3703 		query_disk.Valid = 1;
3704 		query_disk.Locked =
3705 		    (disk->ad_flags & AAC_DISK_OPEN) ? 1 : 0;
3706 		query_disk.Deleted = 0;
3707 		query_disk.Bus = device_get_unit(sc->aac_dev);
3708 		query_disk.Target = disk->unit;
3709 		query_disk.Lun = 0;
3710 		query_disk.UnMapped = 0;
3711 		bcopy(disk->ad_dev_t->si_name,
3712 		      &query_disk.diskDeviceName[0], 10);
3713 	}
3714 	lockmgr(&sc->aac_container_lock, LK_RELEASE);
3715 
3716 	error = copyout((caddr_t)&query_disk, uptr,
3717 			sizeof(struct aac_query_disk));
3718 
3719 	return (error);
3720 }
3721 
3722 static void
3723 aac_get_bus_info(struct aac_softc *sc)
3724 {
3725 	struct aac_fib *fib;
3726 	struct aac_ctcfg *c_cmd;
3727 	struct aac_ctcfg_resp *c_resp;
3728 	struct aac_vmioctl *vmi;
3729 	struct aac_vmi_businf_resp *vmi_resp;
3730 	struct aac_getbusinf businfo;
3731 	struct aac_sim *caminf;
3732 	device_t child;
3733 	int i, found, error;
3734 
3735 	lockmgr(&sc->aac_io_lock, LK_EXCLUSIVE);
3736 	aac_alloc_sync_fib(sc, &fib);
3737 	c_cmd = (struct aac_ctcfg *)&fib->data[0];
3738 	bzero(c_cmd, sizeof(struct aac_ctcfg));
3739 
3740 	c_cmd->Command = VM_ContainerConfig;
3741 	c_cmd->cmd = CT_GET_SCSI_METHOD;
3742 	c_cmd->param = 0;
3743 
3744 	error = aac_sync_fib(sc, ContainerCommand, 0, fib,
3745 	    sizeof(struct aac_ctcfg));
3746 	if (error) {
3747 		device_printf(sc->aac_dev, "Error %d sending "
3748 		    "VM_ContainerConfig command\n", error);
3749 		aac_release_sync_fib(sc);
3750 		lockmgr(&sc->aac_io_lock, LK_RELEASE);
3751 		return;
3752 	}
3753 
3754 	c_resp = (struct aac_ctcfg_resp *)&fib->data[0];
3755 	if (c_resp->Status != ST_OK) {
3756 		device_printf(sc->aac_dev, "VM_ContainerConfig returned 0x%x\n",
3757 		    c_resp->Status);
3758 		aac_release_sync_fib(sc);
3759 		lockmgr(&sc->aac_io_lock, LK_RELEASE);
3760 		return;
3761 	}
3762 
3763 	sc->scsi_method_id = c_resp->param;
3764 
3765 	vmi = (struct aac_vmioctl *)&fib->data[0];
3766 	bzero(vmi, sizeof(struct aac_vmioctl));
3767 
3768 	vmi->Command = VM_Ioctl;
3769 	vmi->ObjType = FT_DRIVE;
3770 	vmi->MethId = sc->scsi_method_id;
3771 	vmi->ObjId = 0;
3772 	vmi->IoctlCmd = GetBusInfo;
3773 
3774 	error = aac_sync_fib(sc, ContainerCommand, 0, fib,
3775 	    sizeof(struct aac_vmi_businf_resp));
3776 	if (error) {
3777 		device_printf(sc->aac_dev, "Error %d sending VMIoctl command\n",
3778 		    error);
3779 		aac_release_sync_fib(sc);
3780 		lockmgr(&sc->aac_io_lock, LK_RELEASE);
3781 		return;
3782 	}
3783 
3784 	vmi_resp = (struct aac_vmi_businf_resp *)&fib->data[0];
3785 	if (vmi_resp->Status != ST_OK) {
3786 		device_printf(sc->aac_dev, "VM_Ioctl returned %d\n",
3787 		    vmi_resp->Status);
3788 		aac_release_sync_fib(sc);
3789 		lockmgr(&sc->aac_io_lock, LK_RELEASE);
3790 		return;
3791 	}
3792 
3793 	bcopy(&vmi_resp->BusInf, &businfo, sizeof(struct aac_getbusinf));
3794 	aac_release_sync_fib(sc);
3795 	lockmgr(&sc->aac_io_lock, LK_RELEASE);
3796 
3797 	found = 0;
3798 	for (i = 0; i < businfo.BusCount; i++) {
3799 		if (businfo.BusValid[i] != AAC_BUS_VALID)
3800 			continue;
3801 
3802 		caminf = (struct aac_sim *)kmalloc(sizeof(struct aac_sim),
3803 		    M_AACBUF, M_INTWAIT | M_ZERO);
3804 
3805 		child = device_add_child(sc->aac_dev, "aacp", -1);
3806 		if (child == NULL) {
3807 			device_printf(sc->aac_dev,
3808 			    "device_add_child failed for passthrough bus %d\n",
3809 			    i);
3810 			kfree(caminf, M_AACBUF);
3811 			break;
3812 		}
3813 
3814 		caminf->TargetsPerBus = businfo.TargetsPerBus;
3815 		caminf->BusNumber = i;
3816 		caminf->InitiatorBusId = businfo.InitiatorBusId[i];
3817 		caminf->aac_sc = sc;
3818 		caminf->sim_dev = child;
3819 
3820 		device_set_ivars(child, caminf);
3821 		device_set_desc(child, "SCSI Passthrough Bus");
3822 		TAILQ_INSERT_TAIL(&sc->aac_sim_tqh, caminf, sim_link);
3823 
3824 		found = 1;
3825 	}
3826 
3827 	if (found)
3828 		bus_generic_attach(sc->aac_dev);
3829 
3830 	return;
3831 }
3832