1 /*- 2 * Written by: David Jeffery 3 * Copyright (c) 2002 Adaptec Inc. 4 * All rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 16 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 18 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 19 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 20 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 21 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 23 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 24 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 25 * SUCH DAMAGE. 26 */ 27 28 #include <sys/cdefs.h> 29 __FBSDID("$FreeBSD$"); 30 31 #include <dev/ips/ips.h> 32 #include <sys/stat.h> 33 #include <sys/time.h> 34 #include <machine/clock.h> 35 36 static d_open_t ips_open; 37 static d_close_t ips_close; 38 static d_ioctl_t ips_ioctl; 39 40 #define IPS_CDEV_MAJOR 175 41 static struct cdevsw ips_cdevsw = { 42 .d_open = ips_open, 43 .d_close = ips_close, 44 .d_ioctl = ips_ioctl, 45 .d_name = "ips", 46 .d_maj = IPS_CDEV_MAJOR, 47 }; 48 49 static const char* ips_adapter_name[] = { 50 "N/A", 51 "ServeRAID (copperhead)", 52 "ServeRAID II (copperhead refresh)", 53 "ServeRAID onboard (copperhead)", 54 "ServeRAID onboard (copperhead)", 55 "ServeRAID 3H (clarinet)", 56 "ServeRAID 3L (clarinet lite)", 57 "ServeRAID 4H (trombone)", 58 "ServeRAID 4M (morpheus)", 59 "ServeRAID 4L (morpheus lite)", 60 "ServeRAID 4Mx (neo)", 61 "ServeRAID 4Lx (neo lite)", 62 "ServeRAID 5i II (sarasota)", 63 "ServeRAID 5i (sarasota)", 64 "ServeRAID 6M (marco)", 65 "ServeRAID 6i (sebring)" 66 }; 67 68 69 static int ips_open(dev_t dev, int flags, int fmt, struct thread *td) 70 { 71 ips_softc_t *sc = dev->si_drv1; 72 sc->state |= IPS_DEV_OPEN; 73 return 0; 74 } 75 76 static int ips_close(dev_t dev, int flags, int fmt, struct thread *td) 77 { 78 ips_softc_t *sc = dev->si_drv1; 79 sc->state &= ~IPS_DEV_OPEN; 80 81 return 0; 82 } 83 84 static int ips_ioctl(dev_t dev, u_long command, caddr_t addr, int32_t flags, struct thread *td) 85 { 86 ips_softc_t *sc; 87 88 sc = dev->si_drv1; 89 return ips_ioctl_request(sc, command, addr, flags); 90 } 91 92 static void ips_cmd_dmaload(void *cmdptr, bus_dma_segment_t *segments,int segnum, int error) 93 { 94 ips_command_t *command = cmdptr; 95 PRINTF(10, "ips: in ips_cmd_dmaload\n"); 96 if(!error) 97 command->command_phys_addr = segments[0].ds_addr; 98 99 } 100 101 /* is locking needed? what locking guarentees are there on removal? */ 102 static __inline__ int ips_cmdqueue_free(ips_softc_t *sc) 103 { 104 int i, error = -1; 105 intrmask_t mask = splbio(); 106 if(!sc->used_commands){ 107 for(i = 0; i < sc->max_cmds; i++){ 108 if(!(sc->commandarray[i].command_phys_addr)) 109 continue; 110 bus_dmamap_unload(sc->command_dmatag, 111 sc->commandarray[i].command_dmamap); 112 bus_dmamem_free(sc->command_dmatag, 113 sc->commandarray[i].command_buffer, 114 sc->commandarray[i].command_dmamap); 115 } 116 error = 0; 117 sc->state |= IPS_OFFLINE; 118 } 119 splx(mask); 120 return error; 121 } 122 123 /* places all ips command structs on the free command queue. No locking as if someone else tries 124 * to access this during init, we have bigger problems */ 125 static __inline__ int ips_cmdqueue_init(ips_softc_t *sc) 126 { 127 int i; 128 ips_command_t *command; 129 SLIST_INIT(&sc->free_cmd_list); 130 STAILQ_INIT(&sc->cmd_wait_list); 131 for(i = 0; i < sc->max_cmds; i++){ 132 sc->commandarray[i].id = i; 133 sc->commandarray[i].sc = sc; 134 SLIST_INSERT_HEAD(&sc->free_cmd_list, &sc->commandarray[i], 135 next); 136 } 137 for(i = 0; i < sc->max_cmds; i++){ 138 command = &sc->commandarray[i]; 139 if(bus_dmamem_alloc(sc->command_dmatag,&command->command_buffer, 140 BUS_DMA_NOWAIT, &command->command_dmamap)) 141 goto error; 142 bus_dmamap_load(sc->command_dmatag, command->command_dmamap, 143 command->command_buffer,IPS_COMMAND_LEN, 144 ips_cmd_dmaload, command, BUS_DMA_NOWAIT); 145 if(!command->command_phys_addr){ 146 bus_dmamem_free(sc->command_dmatag, 147 command->command_buffer, command->command_dmamap); 148 goto error; 149 } 150 } 151 sc->state &= ~IPS_OFFLINE; 152 return 0; 153 error: 154 ips_cmdqueue_free(sc); 155 return ENOMEM; 156 } 157 158 static int ips_add_waiting_command(ips_softc_t *sc, int (*callback)(ips_command_t *), void *data, unsigned long flags) 159 { 160 intrmask_t mask; 161 ips_command_t *command; 162 ips_wait_list_t *waiter; 163 unsigned long memflags = 0; 164 if(IPS_NOWAIT_FLAG & flags) 165 memflags = M_NOWAIT; 166 waiter = malloc(sizeof(ips_wait_list_t), M_DEVBUF, memflags); 167 if(!waiter) 168 return ENOMEM; 169 mask = splbio(); 170 if(sc->state & IPS_OFFLINE){ 171 splx(mask); 172 return EIO; 173 } 174 command = SLIST_FIRST(&sc->free_cmd_list); 175 if(command && !(sc->state & IPS_TIMEOUT)){ 176 SLIST_REMOVE_HEAD(&sc->free_cmd_list, next); 177 (sc->used_commands)++; 178 splx(mask); 179 clear_ips_command(command); 180 bzero(command->command_buffer, IPS_COMMAND_LEN); 181 free(waiter, M_DEVBUF); 182 command->arg = data; 183 return callback(command); 184 } 185 DEVICE_PRINTF(1, sc->dev, "adding command to the wait queue\n"); 186 waiter->callback = callback; 187 waiter->data = data; 188 STAILQ_INSERT_TAIL(&sc->cmd_wait_list, waiter, next); 189 splx(mask); 190 return 0; 191 } 192 193 static void ips_run_waiting_command(ips_softc_t *sc) 194 { 195 ips_wait_list_t *waiter; 196 ips_command_t *command; 197 int (*callback)(ips_command_t*); 198 intrmask_t mask; 199 200 mask = splbio(); 201 waiter = STAILQ_FIRST(&sc->cmd_wait_list); 202 command = SLIST_FIRST(&sc->free_cmd_list); 203 if(!waiter || !command){ 204 splx(mask); 205 return; 206 } 207 DEVICE_PRINTF(1, sc->dev, "removing command from wait queue\n"); 208 SLIST_REMOVE_HEAD(&sc->free_cmd_list, next); 209 STAILQ_REMOVE_HEAD(&sc->cmd_wait_list, next); 210 (sc->used_commands)++; 211 splx(mask); 212 clear_ips_command(command); 213 bzero(command->command_buffer, IPS_COMMAND_LEN); 214 command->arg = waiter->data; 215 callback = waiter->callback; 216 free(waiter, M_DEVBUF); 217 callback(command); 218 return; 219 } 220 /* returns a free command struct if one is available. 221 * It also blanks out anything that may be a wild pointer/value. 222 * Also, command buffers are not freed. They are 223 * small so they are saved and kept dmamapped and loaded. 224 */ 225 int ips_get_free_cmd(ips_softc_t *sc, int (*callback)(ips_command_t *), void *data, unsigned long flags) 226 { 227 intrmask_t mask; 228 ips_command_t *command; 229 mask = splbio(); 230 231 if(sc->state & IPS_OFFLINE){ 232 splx(mask); 233 return EIO; 234 } 235 command = SLIST_FIRST(&sc->free_cmd_list); 236 if(!command || (sc->state & IPS_TIMEOUT)){ 237 splx(mask); 238 if(flags & IPS_NOWAIT_FLAG) 239 return EAGAIN; 240 return ips_add_waiting_command(sc, callback, data, flags); 241 } 242 SLIST_REMOVE_HEAD(&sc->free_cmd_list, next); 243 (sc->used_commands)++; 244 splx(mask); 245 clear_ips_command(command); 246 bzero(command->command_buffer, IPS_COMMAND_LEN); 247 command->arg = data; 248 return callback(command); 249 } 250 251 /* adds a command back to the free command queue */ 252 void ips_insert_free_cmd(ips_softc_t *sc, ips_command_t *command) 253 { 254 intrmask_t mask; 255 mask = splbio(); 256 SLIST_INSERT_HEAD(&sc->free_cmd_list, command, next); 257 (sc->used_commands)--; 258 splx(mask); 259 if(!(sc->state & IPS_TIMEOUT)) 260 ips_run_waiting_command(sc); 261 } 262 static const char* ips_diskdev_statename(u_int8_t state) 263 { 264 static char statebuf[20]; 265 switch(state){ 266 case IPS_LD_OFFLINE: 267 return("OFFLINE"); 268 break; 269 case IPS_LD_OKAY: 270 return("OK"); 271 break; 272 case IPS_LD_DEGRADED: 273 return("DEGRADED"); 274 break; 275 case IPS_LD_FREE: 276 return("FREE"); 277 break; 278 case IPS_LD_SYS: 279 return("SYS"); 280 break; 281 case IPS_LD_CRS: 282 return("CRS"); 283 break; 284 } 285 sprintf(statebuf,"UNKNOWN(0x%02x)", state); 286 return(statebuf); 287 } 288 289 static int ips_diskdev_init(ips_softc_t *sc) 290 { 291 int i; 292 for(i=0; i < IPS_MAX_NUM_DRIVES; i++){ 293 if(sc->drives[i].state == IPS_LD_FREE) continue; 294 device_printf(sc->dev, "Logical Drive %d: RAID%d sectors: %u, state %s\n", 295 i, sc->drives[i].raid_lvl, 296 sc->drives[i].sector_count, 297 ips_diskdev_statename(sc->drives[i].state)); 298 if(sc->drives[i].state == IPS_LD_OKAY || 299 sc->drives[i].state == IPS_LD_DEGRADED){ 300 sc->diskdev[i] = device_add_child(sc->dev, NULL, -1); 301 device_set_ivars(sc->diskdev[i],(void *)(uintptr_t) i); 302 } 303 } 304 if(bus_generic_attach(sc->dev)){ 305 device_printf(sc->dev, "Attaching bus failed\n"); 306 } 307 return 0; 308 } 309 310 static int ips_diskdev_free(ips_softc_t *sc) 311 { 312 int i; 313 int error = 0; 314 for(i = 0; i < IPS_MAX_NUM_DRIVES; i++){ 315 if(sc->diskdev[i]) 316 error = device_delete_child(sc->dev, sc->diskdev[i]); 317 if(error) 318 return error; 319 } 320 bus_generic_detach(sc->dev); 321 return 0; 322 } 323 324 /* ips_timeout is periodically called to make sure no commands sent 325 * to the card have become stuck. If it finds a stuck command, it 326 * sets a flag so the driver won't start any more commands and then 327 * is periodically called to see if all outstanding commands have 328 * either finished or timed out. Once timed out, an attempt to 329 * reinitialize the card is made. If that fails, the driver gives 330 * up and declares the card dead. */ 331 static void ips_timeout(void *arg) 332 { 333 intrmask_t mask; 334 ips_softc_t *sc = arg; 335 int i, state = 0; 336 ips_command_t *command; 337 command = &sc->commandarray[0]; 338 mask = splbio(); 339 for(i = 0; i < sc->max_cmds; i++){ 340 if(!command[i].timeout){ 341 continue; 342 } 343 command[i].timeout--; 344 if(!command[i].timeout){ 345 if(!(sc->state & IPS_TIMEOUT)){ 346 sc->state |= IPS_TIMEOUT; 347 device_printf(sc->dev, "WARNING: command timeout. Adapter is in toaster mode, resetting to known state\n"); 348 } 349 command[i].status.value = IPS_ERROR_STATUS; 350 command[i].callback(&command[i]); 351 /* hmm, this should be enough cleanup */ 352 } else 353 state = 1; 354 } 355 if(!state && (sc->state & IPS_TIMEOUT)){ 356 if(sc->ips_adapter_reinit(sc, 1)){ 357 device_printf(sc->dev, "AIEE! adapter reset failed, giving up and going home! Have a nice day.\n"); 358 sc->state |= IPS_OFFLINE; 359 sc->state &= ~IPS_TIMEOUT; 360 /* Grr, I hate this solution. I run waiting commands 361 one at a time and error them out just before they 362 would go to the card. This sucks. */ 363 } else 364 sc->state &= ~IPS_TIMEOUT; 365 ips_run_waiting_command(sc); 366 } 367 if (sc->state != IPS_OFFLINE) 368 sc->timer = timeout(ips_timeout, sc, 10*hz); 369 splx(mask); 370 } 371 372 /* check card and initialize it */ 373 int ips_adapter_init(ips_softc_t *sc) 374 { 375 int i; 376 DEVICE_PRINTF(1,sc->dev, "initializing\n"); 377 if (bus_dma_tag_create( /* parent */ sc->adapter_dmatag, 378 /* alignemnt */ 1, 379 /* boundary */ 0, 380 /* lowaddr */ BUS_SPACE_MAXADDR_32BIT, 381 /* highaddr */ BUS_SPACE_MAXADDR, 382 /* filter */ NULL, 383 /* filterarg */ NULL, 384 /* maxsize */ IPS_COMMAND_LEN + 385 IPS_MAX_SG_LEN, 386 /* numsegs */ 1, 387 /* maxsegsize*/ IPS_COMMAND_LEN + 388 IPS_MAX_SG_LEN, 389 /* flags */ 0, 390 /* lockfunc */ busdma_lock_mutex, 391 /* lockarg */ &Giant, 392 &sc->command_dmatag) != 0) { 393 device_printf(sc->dev, "can't alloc command dma tag\n"); 394 goto error; 395 } 396 if (bus_dma_tag_create( /* parent */ sc->adapter_dmatag, 397 /* alignemnt */ 1, 398 /* boundary */ 0, 399 /* lowaddr */ BUS_SPACE_MAXADDR_32BIT, 400 /* highaddr */ BUS_SPACE_MAXADDR, 401 /* filter */ NULL, 402 /* filterarg */ NULL, 403 /* maxsize */ IPS_MAX_IOBUF_SIZE, 404 /* numsegs */ IPS_MAX_SG_ELEMENTS, 405 /* maxsegsize*/ IPS_MAX_IOBUF_SIZE, 406 /* flags */ 0, 407 /* lockfunc */ busdma_lock_mutex, 408 /* lockarg */ &Giant, 409 &sc->sg_dmatag) != 0) { 410 device_printf(sc->dev, "can't alloc SG dma tag\n"); 411 goto error; 412 } 413 /* create one command buffer until we know how many commands this card 414 can handle */ 415 sc->max_cmds = 1; 416 ips_cmdqueue_init(sc); 417 callout_handle_init(&sc->timer); 418 419 if(sc->ips_adapter_reinit(sc, 0)) 420 goto error; 421 422 mtx_init(&sc->cmd_mtx, "ips command mutex", NULL, MTX_DEF); 423 424 /* initialize ffdc values */ 425 microtime(&sc->ffdc_resettime); 426 sc->ffdc_resetcount = 1; 427 if ((i = ips_ffdc_reset(sc)) != 0) { 428 device_printf(sc->dev, "failed to send ffdc reset to device (%d)\n", i); 429 goto error; 430 } 431 if ((i = ips_get_adapter_info(sc)) != 0) { 432 device_printf(sc->dev, "failed to get adapter configuration data from device (%d)\n", i); 433 goto error; 434 } 435 ips_update_nvram(sc); /* no error check as failure doesn't matter */ 436 if(sc->adapter_type > 0 && sc->adapter_type <= IPS_ADAPTER_MAX_T){ 437 device_printf(sc->dev, "adapter type: %s\n", ips_adapter_name[sc->adapter_type]); 438 } 439 if ((i = ips_get_drive_info(sc)) != 0) { 440 device_printf(sc->dev, "failed to get drive configuration data from device (%d)\n", i); 441 goto error; 442 } 443 444 ips_cmdqueue_free(sc); 445 if(sc->adapter_info.max_concurrent_cmds) 446 sc->max_cmds = min(128, sc->adapter_info.max_concurrent_cmds); 447 else 448 sc->max_cmds = 32; 449 if(ips_cmdqueue_init(sc)){ 450 device_printf(sc->dev, "failed to initialize command buffers\n"); 451 goto error; 452 } 453 sc->device_file = make_dev(&ips_cdevsw, device_get_unit(sc->dev), UID_ROOT, GID_OPERATOR, 454 S_IRUSR | S_IWUSR, "ips%d", device_get_unit(sc->dev)); 455 sc->device_file->si_drv1 = sc; 456 ips_diskdev_init(sc); 457 sc->timer = timeout(ips_timeout, sc, 10*hz); 458 return 0; 459 460 error: 461 ips_adapter_free(sc); 462 return ENXIO; 463 } 464 465 /* see if we should reinitialize the card and wait for it to timeout or complete initialization */ 466 int ips_morpheus_reinit(ips_softc_t *sc, int force) 467 { 468 u_int32_t tmp; 469 int i; 470 471 tmp = ips_read_4(sc, MORPHEUS_REG_OISR); 472 if(!force && (ips_read_4(sc, MORPHEUS_REG_OMR0) >= IPS_POST1_OK) && 473 (ips_read_4(sc, MORPHEUS_REG_OMR1) != 0xdeadbeef) && !tmp){ 474 ips_write_4(sc, MORPHEUS_REG_OIMR, 0); 475 return 0; 476 } 477 ips_write_4(sc, MORPHEUS_REG_OIMR, 0xff); 478 ips_read_4(sc, MORPHEUS_REG_OIMR); 479 480 device_printf(sc->dev, "resetting adapter, this may take up to 5 minutes\n"); 481 ips_write_4(sc, MORPHEUS_REG_IDR, 0x80000000); 482 DELAY(5000000); 483 pci_read_config(sc->dev, 0, 4); 484 485 tmp = ips_read_4(sc, MORPHEUS_REG_OISR); 486 for(i = 0; i < 45 && !(tmp & MORPHEUS_BIT_POST1); i++){ 487 DELAY(1000000); 488 DEVICE_PRINTF(2, sc->dev, "post1: %d\n", i); 489 tmp = ips_read_4(sc, MORPHEUS_REG_OISR); 490 } 491 if(tmp & MORPHEUS_BIT_POST1) 492 ips_write_4(sc, MORPHEUS_REG_OISR, MORPHEUS_BIT_POST1); 493 494 if( i == 45 || ips_read_4(sc, MORPHEUS_REG_OMR0) < IPS_POST1_OK){ 495 device_printf(sc->dev,"Adapter error during initialization.\n"); 496 return 1; 497 } 498 for(i = 0; i < 240 && !(tmp & MORPHEUS_BIT_POST2); i++){ 499 DELAY(1000000); 500 DEVICE_PRINTF(2, sc->dev, "post2: %d\n", i); 501 tmp = ips_read_4(sc, MORPHEUS_REG_OISR); 502 } 503 if(tmp & MORPHEUS_BIT_POST2) 504 ips_write_4(sc, MORPHEUS_REG_OISR, MORPHEUS_BIT_POST2); 505 506 if(i == 240 || !ips_read_4(sc, MORPHEUS_REG_OMR1)){ 507 device_printf(sc->dev, "adapter failed config check\n"); 508 return 1; 509 } 510 ips_write_4(sc, MORPHEUS_REG_OIMR, 0); 511 if(force && ips_clear_adapter(sc)){ 512 device_printf(sc->dev, "adapter clear failed\n"); 513 return 1; 514 } 515 return 0; 516 } 517 518 /* clean up so we can unload the driver. */ 519 int ips_adapter_free(ips_softc_t *sc) 520 { 521 int error = 0; 522 intrmask_t mask; 523 if(sc->state & IPS_DEV_OPEN) 524 return EBUSY; 525 if((error = ips_diskdev_free(sc))) 526 return error; 527 if(ips_cmdqueue_free(sc)){ 528 device_printf(sc->dev, 529 "trying to exit when command queue is not empty!\n"); 530 return EBUSY; 531 } 532 DEVICE_PRINTF(1, sc->dev, "free\n"); 533 mask = splbio(); 534 untimeout(ips_timeout, sc, sc->timer); 535 splx(mask); 536 if (mtx_initialized(&sc->cmd_mtx)) 537 mtx_destroy(&sc->cmd_mtx); 538 539 if(sc->sg_dmatag) 540 bus_dma_tag_destroy(sc->sg_dmatag); 541 if(sc->command_dmatag) 542 bus_dma_tag_destroy(sc->command_dmatag); 543 if(sc->device_file) 544 destroy_dev(sc->device_file); 545 return 0; 546 } 547 548 void ips_morpheus_intr(void *void_sc) 549 { 550 ips_softc_t *sc = (ips_softc_t *)void_sc; 551 u_int32_t oisr, iisr; 552 int cmdnumber; 553 ips_cmd_status_t status; 554 555 iisr =ips_read_4(sc, MORPHEUS_REG_IISR); 556 oisr =ips_read_4(sc, MORPHEUS_REG_OISR); 557 PRINTF(9,"interrupt registers in:%x out:%x\n",iisr, oisr); 558 if(!(oisr & MORPHEUS_BIT_CMD_IRQ)){ 559 DEVICE_PRINTF(2,sc->dev, "got a non-command irq\n"); 560 return; 561 } 562 while((status.value = ips_read_4(sc, MORPHEUS_REG_OQPR)) != 0xffffffff){ 563 cmdnumber = status.fields.command_id; 564 sc->commandarray[cmdnumber].status.value = status.value; 565 sc->commandarray[cmdnumber].timeout = 0; 566 sc->commandarray[cmdnumber].callback(&(sc->commandarray[cmdnumber])); 567 568 569 DEVICE_PRINTF(9,sc->dev, "got command %d\n", cmdnumber); 570 } 571 return; 572 } 573 574 void ips_issue_morpheus_cmd(ips_command_t *command) 575 { 576 intrmask_t mask = splbio(); 577 /* hmmm, is there a cleaner way to do this? */ 578 if(command->sc->state & IPS_OFFLINE){ 579 splx(mask); 580 command->status.value = IPS_ERROR_STATUS; 581 command->callback(command); 582 return; 583 } 584 command->timeout = 10; 585 ips_write_4(command->sc, MORPHEUS_REG_IQPR, command->command_phys_addr); 586 splx(mask); 587 } 588 589 static void ips_copperhead_queue_callback(void *queueptr, bus_dma_segment_t *segments,int segnum, int error) 590 { 591 ips_copper_queue_t *queue = queueptr; 592 if(error){ 593 return; 594 } 595 queue->base_phys_addr = segments[0].ds_addr; 596 } 597 598 static int ips_copperhead_queue_init(ips_softc_t *sc) 599 { 600 int error; 601 bus_dma_tag_t dmatag; 602 bus_dmamap_t dmamap; 603 if (bus_dma_tag_create( /* parent */ sc->adapter_dmatag, 604 /* alignemnt */ 1, 605 /* boundary */ 0, 606 /* lowaddr */ BUS_SPACE_MAXADDR_32BIT, 607 /* highaddr */ BUS_SPACE_MAXADDR, 608 /* filter */ NULL, 609 /* filterarg */ NULL, 610 /* maxsize */ sizeof(ips_copper_queue_t), 611 /* numsegs */ 1, 612 /* maxsegsize*/ sizeof(ips_copper_queue_t), 613 /* flags */ 0, 614 /* lockfunc */ busdma_lock_mutex, 615 /* lockarg */ &Giant, 616 &dmatag) != 0) { 617 device_printf(sc->dev, "can't alloc dma tag for statue queue\n"); 618 error = ENOMEM; 619 goto exit; 620 } 621 if(bus_dmamem_alloc(dmatag, (void *)&(sc->copper_queue), 622 BUS_DMA_NOWAIT, &dmamap)){ 623 error = ENOMEM; 624 goto exit; 625 } 626 bzero(sc->copper_queue, sizeof(ips_copper_queue_t)); 627 sc->copper_queue->dmatag = dmatag; 628 sc->copper_queue->dmamap = dmamap; 629 sc->copper_queue->nextstatus = 1; 630 bus_dmamap_load(dmatag, dmamap, 631 &(sc->copper_queue->status[0]), IPS_MAX_CMD_NUM * 4, 632 ips_copperhead_queue_callback, sc->copper_queue, 633 BUS_DMA_NOWAIT); 634 if(sc->copper_queue->base_phys_addr == 0){ 635 error = ENOMEM; 636 goto exit; 637 } 638 ips_write_4(sc, COPPER_REG_SQSR, sc->copper_queue->base_phys_addr); 639 ips_write_4(sc, COPPER_REG_SQER, sc->copper_queue->base_phys_addr + 640 IPS_MAX_CMD_NUM * 4); 641 ips_write_4(sc, COPPER_REG_SQHR, sc->copper_queue->base_phys_addr + 4); 642 ips_write_4(sc, COPPER_REG_SQTR, sc->copper_queue->base_phys_addr); 643 644 645 return 0; 646 exit: 647 bus_dmamem_free(dmatag, sc->copper_queue, dmamap); 648 bus_dma_tag_destroy(dmatag); 649 return error; 650 } 651 652 /* see if we should reinitialize the card and wait for it to timeout or complete initialization FIXME */ 653 int ips_copperhead_reinit(ips_softc_t *sc, int force) 654 { 655 int i, j; 656 u_int32_t postcode = 0, configstatus = 0; 657 ips_write_1(sc, COPPER_REG_SCPR, 0x80); 658 ips_write_1(sc, COPPER_REG_SCPR, 0); 659 device_printf(sc->dev, "reinitializing adapter, this could take several minutes.\n"); 660 for(j = 0; j < 2; j++){ 661 postcode <<= 8; 662 for(i = 0; i < 45; i++){ 663 if(ips_read_1(sc, COPPER_REG_HISR) & COPPER_GHI_BIT){ 664 postcode |= ips_read_1(sc, COPPER_REG_ISPR); 665 ips_write_1(sc, COPPER_REG_HISR, 666 COPPER_GHI_BIT); 667 break; 668 } else 669 DELAY(1000000); 670 } 671 if(i == 45) 672 return 1; 673 } 674 for(j = 0; j < 2; j++){ 675 configstatus <<= 8; 676 for(i = 0; i < 240; i++){ 677 if(ips_read_1(sc, COPPER_REG_HISR) & COPPER_GHI_BIT){ 678 configstatus |= ips_read_1(sc, COPPER_REG_ISPR); 679 ips_write_1(sc, COPPER_REG_HISR, 680 COPPER_GHI_BIT); 681 break; 682 } else 683 DELAY(1000000); 684 } 685 if(i == 240) 686 return 1; 687 } 688 for(i = 0; i < 240; i++){ 689 if(!(ips_read_1(sc, COPPER_REG_CBSP) & COPPER_OP_BIT)){ 690 break; 691 } else 692 DELAY(1000000); 693 } 694 if(i == 240) 695 return 1; 696 ips_write_2(sc, COPPER_REG_CCCR, 0x1000 | COPPER_ILE_BIT); 697 ips_write_1(sc, COPPER_REG_SCPR, COPPER_EBM_BIT); 698 ips_copperhead_queue_init(sc); 699 ips_write_1(sc, COPPER_REG_HISR, COPPER_GHI_BIT); 700 i = ips_read_1(sc, COPPER_REG_SCPR); 701 ips_write_1(sc, COPPER_REG_HISR, COPPER_EI_BIT); 702 if(!configstatus){ 703 device_printf(sc->dev, "adapter initialization failed\n"); 704 return 1; 705 } 706 if(force && ips_clear_adapter(sc)){ 707 device_printf(sc->dev, "adapter clear failed\n"); 708 return 1; 709 } 710 return 0; 711 } 712 static u_int32_t ips_copperhead_cmd_status(ips_softc_t *sc) 713 { 714 intrmask_t mask; 715 u_int32_t value; 716 int statnum = sc->copper_queue->nextstatus++; 717 if(sc->copper_queue->nextstatus == IPS_MAX_CMD_NUM) 718 sc->copper_queue->nextstatus = 0; 719 mask = splbio(); 720 value = sc->copper_queue->status[statnum]; 721 ips_write_4(sc, COPPER_REG_SQTR, sc->copper_queue->base_phys_addr + 722 4 * statnum); 723 splx(mask); 724 return value; 725 } 726 727 728 void ips_copperhead_intr(void *void_sc) 729 { 730 ips_softc_t *sc = (ips_softc_t *)void_sc; 731 int cmdnumber; 732 ips_cmd_status_t status; 733 734 while(ips_read_1(sc, COPPER_REG_HISR) & COPPER_SCE_BIT){ 735 status.value = ips_copperhead_cmd_status(sc); 736 cmdnumber = status.fields.command_id; 737 sc->commandarray[cmdnumber].status.value = status.value; 738 sc->commandarray[cmdnumber].timeout = 0; 739 sc->commandarray[cmdnumber].callback(&(sc->commandarray[cmdnumber])); 740 PRINTF(9, "ips: got command %d\n", cmdnumber); 741 } 742 return; 743 } 744 745 void ips_issue_copperhead_cmd(ips_command_t *command) 746 { 747 int i; 748 intrmask_t mask = splbio(); 749 /* hmmm, is there a cleaner way to do this? */ 750 if(command->sc->state & IPS_OFFLINE){ 751 splx(mask); 752 command->status.value = IPS_ERROR_STATUS; 753 command->callback(command); 754 return; 755 } 756 command->timeout = 10; 757 for(i = 0; ips_read_4(command->sc, COPPER_REG_CCCR) & COPPER_SEM_BIT; 758 i++ ){ 759 if( i == 20){ 760 printf("sem bit still set, can't send a command\n"); 761 splx(mask); 762 return; 763 } 764 DELAY(500);/* need to do a delay here */ 765 } 766 ips_write_4(command->sc, COPPER_REG_CCSAR, command->command_phys_addr); 767 ips_write_2(command->sc, COPPER_REG_CCCR, COPPER_CMD_START); 768 splx(mask); 769 } 770 771