aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/sym53c8xx_2/sym_glue.c
diff options
context:
space:
mode:
authorJames Bottomley <jejb@titanic.(none)>2005-06-17 19:42:23 -0400
committerJames Bottomley <jejb@titanic.(none)>2005-06-17 19:42:23 -0400
commit3237ee78fc00f786d5f5aec6f9310b0e39069f15 (patch)
tree4c94e70ab846ffcb8bb5715fb3c8d8473358a323 /drivers/scsi/sym53c8xx_2/sym_glue.c
parent9ee1c939d1cb936b1f98e8d81aeffab57bae46ab (diff)
parentdf0ae2497ddefd72a87f3a3b34ff32455d7d4ae0 (diff)
merge by hand (fix up qla_os.c merge error)
Diffstat (limited to 'drivers/scsi/sym53c8xx_2/sym_glue.c')
-rw-r--r--drivers/scsi/sym53c8xx_2/sym_glue.c152
1 files changed, 81 insertions, 71 deletions
diff --git a/drivers/scsi/sym53c8xx_2/sym_glue.c b/drivers/scsi/sym53c8xx_2/sym_glue.c
index 5b07c6ec3ecc..d76766c3ce16 100644
--- a/drivers/scsi/sym53c8xx_2/sym_glue.c
+++ b/drivers/scsi/sym53c8xx_2/sym_glue.c
@@ -155,10 +155,11 @@ pci_get_base_address(struct pci_dev *pdev, int index, unsigned long *basep)
155 base = tmp; 155 base = tmp;
156 if ((tmp & 0x7) == PCI_BASE_ADDRESS_MEM_TYPE_64) { 156 if ((tmp & 0x7) == PCI_BASE_ADDRESS_MEM_TYPE_64) {
157 pci_read_config_dword(pdev, PCI_BAR_OFFSET(index++), &tmp); 157 pci_read_config_dword(pdev, PCI_BAR_OFFSET(index++), &tmp);
158 if (tmp > 0) 158 if (tmp > 0) {
159 dev_err(&pdev->dev, 159 dev_err(&pdev->dev,
160 "BAR %d is 64-bit, disabling\n", index - 1); 160 "BAR %d is 64-bit, disabling\n", index - 1);
161 base = 0; 161 base = 0;
162 }
162 } 163 }
163 164
164 if ((base & PCI_BASE_ADDRESS_SPACE) == PCI_BASE_ADDRESS_SPACE_IO) { 165 if ((base & PCI_BASE_ADDRESS_SPACE) == PCI_BASE_ADDRESS_SPACE_IO) {
@@ -389,13 +390,20 @@ static int sym_scatter_no_sglist(struct sym_hcb *np, struct sym_ccb *cp, struct
389{ 390{
390 struct sym_tblmove *data = &cp->phys.data[SYM_CONF_MAX_SG-1]; 391 struct sym_tblmove *data = &cp->phys.data[SYM_CONF_MAX_SG-1];
391 int segment; 392 int segment;
393 unsigned int len = cmd->request_bufflen;
392 394
393 cp->data_len = cmd->request_bufflen; 395 if (len) {
394
395 if (cmd->request_bufflen) {
396 dma_addr_t baddr = map_scsi_single_data(np, cmd); 396 dma_addr_t baddr = map_scsi_single_data(np, cmd);
397 if (baddr) { 397 if (baddr) {
398 sym_build_sge(np, data, baddr, cmd->request_bufflen); 398 if (len & 1) {
399 struct sym_tcb *tp = &np->target[cp->target];
400 if (tp->head.wval & EWS) {
401 len++;
402 cp->odd_byte_adjustment++;
403 }
404 }
405 cp->data_len = len;
406 sym_build_sge(np, data, baddr, len);
399 segment = 1; 407 segment = 1;
400 } else { 408 } else {
401 segment = -2; 409 segment = -2;
@@ -418,6 +426,7 @@ static int sym_scatter(struct sym_hcb *np, struct sym_ccb *cp, struct scsi_cmnd
418 segment = sym_scatter_no_sglist(np, cp, cmd); 426 segment = sym_scatter_no_sglist(np, cp, cmd);
419 else if ((use_sg = map_scsi_sg_data(np, cmd)) > 0) { 427 else if ((use_sg = map_scsi_sg_data(np, cmd)) > 0) {
420 struct scatterlist *scatter = (struct scatterlist *)cmd->buffer; 428 struct scatterlist *scatter = (struct scatterlist *)cmd->buffer;
429 struct sym_tcb *tp = &np->target[cp->target];
421 struct sym_tblmove *data; 430 struct sym_tblmove *data;
422 431
423 if (use_sg > SYM_CONF_MAX_SG) { 432 if (use_sg > SYM_CONF_MAX_SG) {
@@ -431,6 +440,11 @@ static int sym_scatter(struct sym_hcb *np, struct sym_ccb *cp, struct scsi_cmnd
431 dma_addr_t baddr = sg_dma_address(&scatter[segment]); 440 dma_addr_t baddr = sg_dma_address(&scatter[segment]);
432 unsigned int len = sg_dma_len(&scatter[segment]); 441 unsigned int len = sg_dma_len(&scatter[segment]);
433 442
443 if ((len & 1) && (tp->head.wval & EWS)) {
444 len++;
445 cp->odd_byte_adjustment++;
446 }
447
434 sym_build_sge(np, &data[segment], baddr, len); 448 sym_build_sge(np, &data[segment], baddr, len);
435 cp->data_len += len; 449 cp->data_len += len;
436 } 450 }
@@ -456,10 +470,8 @@ static int sym_queue_command(struct sym_hcb *np, struct scsi_cmnd *cmd)
456 * Minimal checkings, so that we will not 470 * Minimal checkings, so that we will not
457 * go outside our tables. 471 * go outside our tables.
458 */ 472 */
459 if (sdev->id == np->myaddr || 473 if (sdev->id == np->myaddr) {
460 sdev->id >= SYM_CONF_MAX_TARGET || 474 sym_xpt_done2(np, cmd, DID_NO_CONNECT);
461 sdev->lun >= SYM_CONF_MAX_LUN) {
462 sym_xpt_done2(np, cmd, CAM_DEV_NOT_THERE);
463 return 0; 475 return 0;
464 } 476 }
465 477
@@ -469,28 +481,6 @@ static int sym_queue_command(struct sym_hcb *np, struct scsi_cmnd *cmd)
469 tp = &np->target[sdev->id]; 481 tp = &np->target[sdev->id];
470 482
471 /* 483 /*
472 * Complete the 1st INQUIRY command with error
473 * condition if the device is flagged NOSCAN
474 * at BOOT in the NVRAM. This may speed up
475 * the boot and maintain coherency with BIOS
476 * device numbering. Clearing the flag allows
477 * user to rescan skipped devices later.
478 * We also return error for devices not flagged
479 * for SCAN LUNS in the NVRAM since some mono-lun
480 * devices behave badly when asked for some non
481 * zero LUN. Btw, this is an absolute hack.:-)
482 */
483 if (cmd->cmnd[0] == 0x12 || cmd->cmnd[0] == 0x0) {
484 if ((tp->usrflags & SYM_SCAN_BOOT_DISABLED) ||
485 ((tp->usrflags & SYM_SCAN_LUNS_DISABLED) &&
486 sdev->lun != 0)) {
487 tp->usrflags &= ~SYM_SCAN_BOOT_DISABLED;
488 sym_xpt_done2(np, cmd, CAM_DEV_NOT_THERE);
489 return 0;
490 }
491 }
492
493 /*
494 * Select tagged/untagged. 484 * Select tagged/untagged.
495 */ 485 */
496 lp = sym_lp(tp, sdev->lun); 486 lp = sym_lp(tp, sdev->lun);
@@ -511,23 +501,10 @@ static int sym_queue_command(struct sym_hcb *np, struct scsi_cmnd *cmd)
511 */ 501 */
512static inline int sym_setup_cdb(struct sym_hcb *np, struct scsi_cmnd *cmd, struct sym_ccb *cp) 502static inline int sym_setup_cdb(struct sym_hcb *np, struct scsi_cmnd *cmd, struct sym_ccb *cp)
513{ 503{
514 u32 cmd_ba;
515 int cmd_len;
516
517 /*
518 * CDB is 16 bytes max.
519 */
520 if (cmd->cmd_len > sizeof(cp->cdb_buf)) {
521 sym_set_cam_status(cp->cmd, CAM_REQ_INVALID);
522 return -1;
523 }
524
525 memcpy(cp->cdb_buf, cmd->cmnd, cmd->cmd_len); 504 memcpy(cp->cdb_buf, cmd->cmnd, cmd->cmd_len);
526 cmd_ba = CCB_BA (cp, cdb_buf[0]);
527 cmd_len = cmd->cmd_len;
528 505
529 cp->phys.cmd.addr = cpu_to_scr(cmd_ba); 506 cp->phys.cmd.addr = CCB_BA(cp, cdb_buf[0]);
530 cp->phys.cmd.size = cpu_to_scr(cmd_len); 507 cp->phys.cmd.size = cpu_to_scr(cmd->cmd_len);
531 508
532 return 0; 509 return 0;
533} 510}
@@ -554,10 +531,7 @@ int sym_setup_data_and_start(struct sym_hcb *np, struct scsi_cmnd *cmd, struct s
554 if (dir != DMA_NONE) { 531 if (dir != DMA_NONE) {
555 cp->segments = sym_scatter(np, cp, cmd); 532 cp->segments = sym_scatter(np, cp, cmd);
556 if (cp->segments < 0) { 533 if (cp->segments < 0) {
557 if (cp->segments == -2) 534 sym_set_cam_status(cmd, DID_ERROR);
558 sym_set_cam_status(cmd, CAM_RESRC_UNAVAIL);
559 else
560 sym_set_cam_status(cmd, CAM_REQ_TOO_BIG);
561 goto out_abort; 535 goto out_abort;
562 } 536 }
563 } else { 537 } else {
@@ -855,7 +829,7 @@ prepare:
855 ep->to_do = to_do; 829 ep->to_do = to_do;
856 /* Complete the command with locks held as required by the driver */ 830 /* Complete the command with locks held as required by the driver */
857 if (to_do == SYM_EH_DO_COMPLETE) 831 if (to_do == SYM_EH_DO_COMPLETE)
858 sym_xpt_done2(np, cmd, CAM_REQ_ABORTED); 832 sym_xpt_done2(np, cmd, DID_ABORT);
859 833
860 /* Wait for completion with locks released, as required by kernel */ 834 /* Wait for completion with locks released, as required by kernel */
861 if (to_do == SYM_EH_DO_WAIT) { 835 if (to_do == SYM_EH_DO_WAIT) {
@@ -882,22 +856,46 @@ prepare:
882 */ 856 */
883static int sym53c8xx_eh_abort_handler(struct scsi_cmnd *cmd) 857static int sym53c8xx_eh_abort_handler(struct scsi_cmnd *cmd)
884{ 858{
885 return sym_eh_handler(SYM_EH_ABORT, "ABORT", cmd); 859 int rc;
860
861 spin_lock_irq(cmd->device->host->host_lock);
862 rc = sym_eh_handler(SYM_EH_ABORT, "ABORT", cmd);
863 spin_unlock_irq(cmd->device->host->host_lock);
864
865 return rc;
886} 866}
887 867
888static int sym53c8xx_eh_device_reset_handler(struct scsi_cmnd *cmd) 868static int sym53c8xx_eh_device_reset_handler(struct scsi_cmnd *cmd)
889{ 869{
890 return sym_eh_handler(SYM_EH_DEVICE_RESET, "DEVICE RESET", cmd); 870 int rc;
871
872 spin_lock_irq(cmd->device->host->host_lock);
873 rc = sym_eh_handler(SYM_EH_DEVICE_RESET, "DEVICE RESET", cmd);
874 spin_unlock_irq(cmd->device->host->host_lock);
875
876 return rc;
891} 877}
892 878
893static int sym53c8xx_eh_bus_reset_handler(struct scsi_cmnd *cmd) 879static int sym53c8xx_eh_bus_reset_handler(struct scsi_cmnd *cmd)
894{ 880{
895 return sym_eh_handler(SYM_EH_BUS_RESET, "BUS RESET", cmd); 881 int rc;
882
883 spin_lock_irq(cmd->device->host->host_lock);
884 rc = sym_eh_handler(SYM_EH_BUS_RESET, "BUS RESET", cmd);
885 spin_unlock_irq(cmd->device->host->host_lock);
886
887 return rc;
896} 888}
897 889
898static int sym53c8xx_eh_host_reset_handler(struct scsi_cmnd *cmd) 890static int sym53c8xx_eh_host_reset_handler(struct scsi_cmnd *cmd)
899{ 891{
900 return sym_eh_handler(SYM_EH_HOST_RESET, "HOST RESET", cmd); 892 int rc;
893
894 spin_lock_irq(cmd->device->host->host_lock);
895 rc = sym_eh_handler(SYM_EH_HOST_RESET, "HOST RESET", cmd);
896 spin_unlock_irq(cmd->device->host->host_lock);
897
898 return rc;
901} 899}
902 900
903/* 901/*
@@ -921,7 +919,7 @@ static void sym_tune_dev_queuing(struct sym_tcb *tp, int lun, u_short reqtags)
921 lp->s.reqtags = reqtags; 919 lp->s.reqtags = reqtags;
922 920
923 if (reqtags != oldtags) { 921 if (reqtags != oldtags) {
924 dev_info(&tp->sdev->sdev_target->dev, 922 dev_info(&tp->starget->dev,
925 "tagged command queuing %s, command queue depth %d.\n", 923 "tagged command queuing %s, command queue depth %d.\n",
926 lp->s.reqtags ? "enabled" : "disabled", 924 lp->s.reqtags ? "enabled" : "disabled",
927 lp->started_limit); 925 lp->started_limit);
@@ -981,22 +979,34 @@ static int device_queue_depth(struct sym_hcb *np, int target, int lun)
981 return DEF_DEPTH; 979 return DEF_DEPTH;
982} 980}
983 981
984static int sym53c8xx_slave_alloc(struct scsi_device *device) 982static int sym53c8xx_slave_alloc(struct scsi_device *sdev)
985{ 983{
986 struct sym_hcb *np = sym_get_hcb(device->host); 984 struct sym_hcb *np;
987 struct sym_tcb *tp = &np->target[device->id]; 985 struct sym_tcb *tp;
988 if (!tp->sdev)
989 tp->sdev = device;
990 986
991 return 0; 987 if (sdev->id >= SYM_CONF_MAX_TARGET || sdev->lun >= SYM_CONF_MAX_LUN)
992} 988 return -ENXIO;
993 989
994static void sym53c8xx_slave_destroy(struct scsi_device *device) 990 np = sym_get_hcb(sdev->host);
995{ 991 tp = &np->target[sdev->id];
996 struct sym_hcb *np = sym_get_hcb(device->host); 992
997 struct sym_tcb *tp = &np->target[device->id]; 993 /*
998 if (tp->sdev == device) 994 * Fail the device init if the device is flagged NOSCAN at BOOT in
999 tp->sdev = NULL; 995 * the NVRAM. This may speed up boot and maintain coherency with
996 * BIOS device numbering. Clearing the flag allows the user to
997 * rescan skipped devices later. We also return an error for
998 * devices not flagged for SCAN LUNS in the NVRAM since some single
999 * lun devices behave badly when asked for a non zero LUN.
1000 */
1001
1002 if ((tp->usrflags & SYM_SCAN_BOOT_DISABLED) ||
1003 ((tp->usrflags & SYM_SCAN_LUNS_DISABLED) && sdev->lun != 0)) {
1004 tp->usrflags &= ~SYM_SCAN_BOOT_DISABLED;
1005 return -ENXIO;
1006 }
1007
1008 tp->starget = sdev->sdev_target;
1009 return 0;
1000} 1010}
1001 1011
1002/* 1012/*
@@ -1897,6 +1907,7 @@ static int sym_detach(struct sym_hcb *np, struct pci_dev *pdev)
1897 */ 1907 */
1898 printk("%s: resetting chip\n", sym_name(np)); 1908 printk("%s: resetting chip\n", sym_name(np));
1899 OUTB(np, nc_istat, SRST); 1909 OUTB(np, nc_istat, SRST);
1910 INB(np, nc_mbox1);
1900 udelay(10); 1911 udelay(10);
1901 OUTB(np, nc_istat, 0); 1912 OUTB(np, nc_istat, 0);
1902 1913
@@ -1915,7 +1926,6 @@ static struct scsi_host_template sym2_template = {
1915 .queuecommand = sym53c8xx_queue_command, 1926 .queuecommand = sym53c8xx_queue_command,
1916 .slave_alloc = sym53c8xx_slave_alloc, 1927 .slave_alloc = sym53c8xx_slave_alloc,
1917 .slave_configure = sym53c8xx_slave_configure, 1928 .slave_configure = sym53c8xx_slave_configure,
1918 .slave_destroy = sym53c8xx_slave_destroy,
1919 .eh_abort_handler = sym53c8xx_eh_abort_handler, 1929 .eh_abort_handler = sym53c8xx_eh_abort_handler,
1920 .eh_device_reset_handler = sym53c8xx_eh_device_reset_handler, 1930 .eh_device_reset_handler = sym53c8xx_eh_device_reset_handler,
1921 .eh_bus_reset_handler = sym53c8xx_eh_bus_reset_handler, 1931 .eh_bus_reset_handler = sym53c8xx_eh_bus_reset_handler,