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