twe_freebsd.c (117126) | twe_freebsd.c (118508) |
---|---|
1/*- 2 * Copyright (c) 2000 Michael Smith 3 * Copyright (c) 2000 BSDi 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: --- 10 unchanged lines hidden (view full) --- 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 * | 1/*- 2 * Copyright (c) 2000 Michael Smith 3 * Copyright (c) 2000 BSDi 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: --- 10 unchanged lines hidden (view full) --- 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 * $FreeBSD: head/sys/dev/twe/twe_freebsd.c 117126 2003-07-01 15:52:06Z scottl $ | 27 * $FreeBSD: head/sys/dev/twe/twe_freebsd.c 118508 2003-08-05 19:55:21Z ps $ |
28 */ 29 30/* 31 * FreeBSD-specific code. 32 */ 33 34#include <sys/param.h> 35#include <sys/cons.h> --- 83 unchanged lines hidden (view full) --- 119 PCI device interface 120 ******************************************************************************** 121 ********************************************************************************/ 122 123static int twe_probe(device_t dev); 124static int twe_attach(device_t dev); 125static void twe_free(struct twe_softc *sc); 126static int twe_detach(device_t dev); | 28 */ 29 30/* 31 * FreeBSD-specific code. 32 */ 33 34#include <sys/param.h> 35#include <sys/cons.h> --- 83 unchanged lines hidden (view full) --- 119 PCI device interface 120 ******************************************************************************** 121 ********************************************************************************/ 122 123static int twe_probe(device_t dev); 124static int twe_attach(device_t dev); 125static void twe_free(struct twe_softc *sc); 126static int twe_detach(device_t dev); |
127static int twe_shutdown(device_t dev); | 127static void twe_shutdown(device_t dev); |
128static int twe_suspend(device_t dev); 129static int twe_resume(device_t dev); 130static void twe_pci_intr(void *arg); 131static void twe_intrhook(void *arg); 132 133static device_method_t twe_methods[] = { 134 /* Device interface */ 135 DEVMETHOD(device_probe, twe_probe), --- 55 unchanged lines hidden (view full) --- 191 debug_called(4); 192 193 /* 194 * Initialise the softc structure. 195 */ 196 sc = device_get_softc(dev); 197 sc->twe_dev = dev; 198 | 128static int twe_suspend(device_t dev); 129static int twe_resume(device_t dev); 130static void twe_pci_intr(void *arg); 131static void twe_intrhook(void *arg); 132 133static device_method_t twe_methods[] = { 134 /* Device interface */ 135 DEVMETHOD(device_probe, twe_probe), --- 55 unchanged lines hidden (view full) --- 191 debug_called(4); 192 193 /* 194 * Initialise the softc structure. 195 */ 196 sc = device_get_softc(dev); 197 sc->twe_dev = dev; 198 |
199 sysctl_ctx_init(&sc->sysctl_ctx); 200 sc->sysctl_tree = SYSCTL_ADD_NODE(&sc->sysctl_ctx, 201 SYSCTL_STATIC_CHILDREN(_hw), OID_AUTO, 202 device_get_nameunit(dev), CTLFLAG_RD, 0, ""); 203 if (sc->sysctl_tree == NULL) { 204 twe_printf(sc, "cannot add sysctl tree node\n"); 205 return (ENXIO); 206 } 207 SYSCTL_ADD_STRING(&sc->sysctl_ctx, SYSCTL_CHILDREN(sc->sysctl_tree), 208 OID_AUTO, "driver_version", CTLFLAG_RD, "$Revision$", 0, 209 "TWE driver version"); 210 |
|
199 /* 200 * Make sure we are going to be able to talk to this board. 201 */ 202 command = pci_read_config(dev, PCIR_COMMAND, 2); 203 if ((command & PCIM_CMD_PORTEN) == 0) { 204 twe_printf(sc, "register window not available\n"); 205 return(ENXIO); 206 } --- 134 unchanged lines hidden (view full) --- 341 342 /* release the register window mapping */ 343 if (sc->twe_io != NULL) 344 bus_release_resource(sc->twe_dev, SYS_RES_IOPORT, TWE_IO_CONFIG_REG, sc->twe_io); 345 346 /* destroy control device */ 347 if (sc->twe_dev_t != (dev_t)NULL) 348 destroy_dev(sc->twe_dev_t); | 211 /* 212 * Make sure we are going to be able to talk to this board. 213 */ 214 command = pci_read_config(dev, PCIR_COMMAND, 2); 215 if ((command & PCIM_CMD_PORTEN) == 0) { 216 twe_printf(sc, "register window not available\n"); 217 return(ENXIO); 218 } --- 134 unchanged lines hidden (view full) --- 353 354 /* release the register window mapping */ 355 if (sc->twe_io != NULL) 356 bus_release_resource(sc->twe_dev, SYS_RES_IOPORT, TWE_IO_CONFIG_REG, sc->twe_io); 357 358 /* destroy control device */ 359 if (sc->twe_dev_t != (dev_t)NULL) 360 destroy_dev(sc->twe_dev_t); |
361 362 sysctl_ctx_free(&sc->sysctl_ctx); |
|
349} 350 351/******************************************************************************** 352 * Disconnect from the controller completely, in preparation for unload. 353 */ 354static int 355twe_detach(device_t dev) 356{ --- 5 unchanged lines hidden (view full) --- 362 error = EBUSY; 363 s = splbio(); 364 if (sc->twe_state & TWE_STATE_OPEN) 365 goto out; 366 367 /* 368 * Shut the controller down. 369 */ | 363} 364 365/******************************************************************************** 366 * Disconnect from the controller completely, in preparation for unload. 367 */ 368static int 369twe_detach(device_t dev) 370{ --- 5 unchanged lines hidden (view full) --- 376 error = EBUSY; 377 s = splbio(); 378 if (sc->twe_state & TWE_STATE_OPEN) 379 goto out; 380 381 /* 382 * Shut the controller down. 383 */ |
370 if ((error = twe_shutdown(dev))) 371 goto out; | 384 twe_shutdown(dev); |
372 373 twe_free(sc); 374 375 error = 0; 376 out: 377 splx(s); 378 return(error); 379} 380 381/******************************************************************************** 382 * Bring the controller down to a dormant state and detach all child devices. 383 * 384 * Note that we can assume that the bioq on the controller is empty, as we won't 385 * allow shutdown if any device is open. 386 */ | 385 386 twe_free(sc); 387 388 error = 0; 389 out: 390 splx(s); 391 return(error); 392} 393 394/******************************************************************************** 395 * Bring the controller down to a dormant state and detach all child devices. 396 * 397 * Note that we can assume that the bioq on the controller is empty, as we won't 398 * allow shutdown if any device is open. 399 */ |
387static int | 400static void |
388twe_shutdown(device_t dev) 389{ 390 struct twe_softc *sc = device_get_softc(dev); | 401twe_shutdown(device_t dev) 402{ 403 struct twe_softc *sc = device_get_softc(dev); |
391 int i, s, error; | 404 int i, s; |
392 393 debug_called(4); 394 395 s = splbio(); | 405 406 debug_called(4); 407 408 s = splbio(); |
396 error = 0; | |
397 398 /* 399 * Delete all our child devices. 400 */ 401 for (i = 0; i < TWE_MAX_UNITS; i++) { | 409 410 /* 411 * Delete all our child devices. 412 */ 413 for (i = 0; i < TWE_MAX_UNITS; i++) { |
402 if (sc->twe_drive[i].td_disk != 0) { 403 if ((error = device_delete_child(sc->twe_dev, sc->twe_drive[i].td_disk)) != 0) 404 goto out; 405 sc->twe_drive[i].td_disk = 0; 406 } | 414 twe_detach_drive(sc, i); |
407 } 408 409 /* 410 * Bring the controller down. 411 */ 412 twe_deinit(sc); 413 | 415 } 416 417 /* 418 * Bring the controller down. 419 */ 420 twe_deinit(sc); 421 |
414 out: | |
415 splx(s); | 422 splx(s); |
416 return(error); | |
417} 418 419/******************************************************************************** 420 * Bring the controller to a quiescent state, ready for system suspend. 421 */ 422static int 423twe_suspend(device_t dev) 424{ --- 50 unchanged lines hidden (view full) --- 475 476 /* call core startup routine */ 477 twe_init(sc); 478} 479 480/******************************************************************************** 481 * Given a detected drive, attach it to the bio interface. 482 * | 423} 424 425/******************************************************************************** 426 * Bring the controller to a quiescent state, ready for system suspend. 427 */ 428static int 429twe_suspend(device_t dev) 430{ --- 50 unchanged lines hidden (view full) --- 481 482 /* call core startup routine */ 483 twe_init(sc); 484} 485 486/******************************************************************************** 487 * Given a detected drive, attach it to the bio interface. 488 * |
483 * This is called from twe_init. | 489 * This is called from twe_add_unit. |
484 */ 485void 486twe_attach_drive(struct twe_softc *sc, struct twe_drive *dr) 487{ 488 char buf[80]; 489 int error; 490 491 dr->td_disk = device_add_child(sc->twe_dev, NULL, -1); 492 if (dr->td_disk == NULL) { 493 twe_printf(sc, "device_add_child failed\n"); 494 return; 495 } 496 device_set_ivars(dr->td_disk, dr); 497 498 /* 499 * XXX It would make sense to test the online/initialising bits, but they seem to be 500 * always set... 501 */ | 490 */ 491void 492twe_attach_drive(struct twe_softc *sc, struct twe_drive *dr) 493{ 494 char buf[80]; 495 int error; 496 497 dr->td_disk = device_add_child(sc->twe_dev, NULL, -1); 498 if (dr->td_disk == NULL) { 499 twe_printf(sc, "device_add_child failed\n"); 500 return; 501 } 502 device_set_ivars(dr->td_disk, dr); 503 504 /* 505 * XXX It would make sense to test the online/initialising bits, but they seem to be 506 * always set... 507 */ |
502 sprintf(buf, "%s, %s", twe_describe_code(twe_table_unittype, dr->td_type), | 508 sprintf(buf, "Unit %d, %s, %s", 509 dr->td_unit, 510 twe_describe_code(twe_table_unittype, dr->td_type), |
503 twe_describe_code(twe_table_unitstate, dr->td_state & TWE_PARAM_UNITSTATUS_MASK)); 504 device_set_desc_copy(dr->td_disk, buf); 505 506 if ((error = bus_generic_attach(sc->twe_dev)) != 0) 507 twe_printf(sc, "bus_generic_attach returned %d\n", error); 508} 509 510/******************************************************************************** | 511 twe_describe_code(twe_table_unitstate, dr->td_state & TWE_PARAM_UNITSTATUS_MASK)); 512 device_set_desc_copy(dr->td_disk, buf); 513 514 if ((error = bus_generic_attach(sc->twe_dev)) != 0) 515 twe_printf(sc, "bus_generic_attach returned %d\n", error); 516} 517 518/******************************************************************************** |
519 * Detach the specified unit if it exsists 520 * 521 * This is called from twe_del_unit. 522 */ 523void 524twe_detach_drive(struct twe_softc *sc, int unit) 525{ 526 527 if (sc->twe_drive[unit].td_disk != 0) { 528 if (device_delete_child(sc->twe_dev, sc->twe_drive[unit].td_disk) != 0) 529 twe_printf(sc, "failed to delete unit %d\n", unit); 530 sc->twe_drive[unit].td_disk = 0; 531 } 532} 533 534/******************************************************************************** |
|
511 * Clear a PCI parity error. 512 */ 513void 514twe_clear_pci_parity_error(struct twe_softc *sc) 515{ 516 TWE_CONTROL(sc, TWE_CONTROL_CLEAR_PARITY_ERROR); 517 pci_write_config(sc->twe_dev, PCIR_STATUS, TWE_PCI_CLEAR_PARITY_ERROR, 2); 518} --- 289 unchanged lines hidden (view full) --- 808 * Map/unmap (tr)'s command and data in the controller's addressable space. 809 * 810 * These routines ensure that the data which the controller is going to try to 811 * access is actually visible to the controller, in a machine-independant 812 * fashion. Due to a hardware limitation, I/O buffers must be 512-byte aligned 813 * and we take care of that here as well. 814 */ 815static void | 535 * Clear a PCI parity error. 536 */ 537void 538twe_clear_pci_parity_error(struct twe_softc *sc) 539{ 540 TWE_CONTROL(sc, TWE_CONTROL_CLEAR_PARITY_ERROR); 541 pci_write_config(sc->twe_dev, PCIR_STATUS, TWE_PCI_CLEAR_PARITY_ERROR, 2); 542} --- 289 unchanged lines hidden (view full) --- 832 * Map/unmap (tr)'s command and data in the controller's addressable space. 833 * 834 * These routines ensure that the data which the controller is going to try to 835 * access is actually visible to the controller, in a machine-independant 836 * fashion. Due to a hardware limitation, I/O buffers must be 512-byte aligned 837 * and we take care of that here as well. 838 */ 839static void |
840twe_fillin_sgl(TWE_SG_Entry *sgl, bus_dma_segment_t *segs, int nsegments, int max_sgl) 841{ 842 int i; 843 844 for (i = 0; i < nsegments; i++) { 845 sgl[i].address = segs[i].ds_addr; 846 sgl[i].length = segs[i].ds_len; 847 } 848 for (; i < max_sgl; i++) { /* XXX necessary? */ 849 sgl[i].address = 0; 850 sgl[i].length = 0; 851 } 852} 853 854static void |
|
816twe_setup_data_dmamap(void *arg, bus_dma_segment_t *segs, int nsegments, int error) 817{ 818 struct twe_request *tr = (struct twe_request *)arg; 819 TWE_Command *cmd = &tr->tr_command; | 855twe_setup_data_dmamap(void *arg, bus_dma_segment_t *segs, int nsegments, int error) 856{ 857 struct twe_request *tr = (struct twe_request *)arg; 858 TWE_Command *cmd = &tr->tr_command; |
820 int i; | |
821 822 debug_called(4); 823 824 /* save base of first segment in command (applicable if there only one segment) */ 825 tr->tr_dataphys = segs[0].ds_addr; 826 827 /* correct command size for s/g list size */ 828 tr->tr_command.generic.size += 2 * nsegments; 829 830 /* 831 * Due to the fact that parameter and I/O commands have the scatter/gather list in 832 * different places, we need to determine which sort of command this actually is 833 * before we can populate it correctly. 834 */ 835 switch(cmd->generic.opcode) { 836 case TWE_OP_GET_PARAM: 837 case TWE_OP_SET_PARAM: 838 cmd->generic.sgl_offset = 2; | 859 860 debug_called(4); 861 862 /* save base of first segment in command (applicable if there only one segment) */ 863 tr->tr_dataphys = segs[0].ds_addr; 864 865 /* correct command size for s/g list size */ 866 tr->tr_command.generic.size += 2 * nsegments; 867 868 /* 869 * Due to the fact that parameter and I/O commands have the scatter/gather list in 870 * different places, we need to determine which sort of command this actually is 871 * before we can populate it correctly. 872 */ 873 switch(cmd->generic.opcode) { 874 case TWE_OP_GET_PARAM: 875 case TWE_OP_SET_PARAM: 876 cmd->generic.sgl_offset = 2; |
839 for (i = 0; i < nsegments; i++) { 840 cmd->param.sgl[i].address = segs[i].ds_addr; 841 cmd->param.sgl[i].length = segs[i].ds_len; 842 } 843 for (; i < TWE_MAX_SGL_LENGTH; i++) { /* XXX necessary? */ 844 cmd->param.sgl[i].address = 0; 845 cmd->param.sgl[i].length = 0; 846 } | 877 twe_fillin_sgl(&cmd->param.sgl[0], segs, nsegments, TWE_MAX_SGL_LENGTH); |
847 break; 848 case TWE_OP_READ: 849 case TWE_OP_WRITE: 850 cmd->generic.sgl_offset = 3; | 878 break; 879 case TWE_OP_READ: 880 case TWE_OP_WRITE: 881 cmd->generic.sgl_offset = 3; |
851 for (i = 0; i < nsegments; i++) { 852 cmd->io.sgl[i].address = segs[i].ds_addr; 853 cmd->io.sgl[i].length = segs[i].ds_len; 854 } 855 for (; i < TWE_MAX_SGL_LENGTH; i++) { /* XXX necessary? */ 856 cmd->io.sgl[i].address = 0; 857 cmd->io.sgl[i].length = 0; 858 } | 882 twe_fillin_sgl(&cmd->io.sgl[0], segs, nsegments, TWE_MAX_SGL_LENGTH); |
859 break; | 883 break; |
860 default: 861 /* no s/g list, nothing to do */ | 884 case TWE_OP_ATA_PASSTHROUGH: 885 cmd->generic.sgl_offset = 5; 886 twe_fillin_sgl(&cmd->ata.sgl[0], segs, nsegments, TWE_MAX_ATA_SGL_LENGTH); |
862 break; | 887 break; |
888 default: 889 /* 890 * Fall back to what the linux driver does. 891 * Do this because the API may send an opcode 892 * the driver knows nothing about and this will 893 * at least stop PCIABRT's from hosing us. 894 */ 895 switch (cmd->generic.sgl_offset) { 896 case 2: 897 twe_fillin_sgl(&cmd->param.sgl[0], segs, nsegments, TWE_MAX_SGL_LENGTH); 898 break; 899 case 3: 900 twe_fillin_sgl(&cmd->io.sgl[0], segs, nsegments, TWE_MAX_SGL_LENGTH); 901 break; 902 case 5: 903 twe_fillin_sgl(&cmd->ata.sgl[0], segs, nsegments, TWE_MAX_ATA_SGL_LENGTH); 904 break; 905 } |
|
863 } 864} 865 866static void 867twe_setup_request_dmamap(void *arg, bus_dma_segment_t *segs, int nsegments, int error) 868{ 869 struct twe_request *tr = (struct twe_request *)arg; 870 --- 105 unchanged lines hidden --- | 906 } 907} 908 909static void 910twe_setup_request_dmamap(void *arg, bus_dma_segment_t *segs, int nsegments, int error) 911{ 912 struct twe_request *tr = (struct twe_request *)arg; 913 --- 105 unchanged lines hidden --- |