Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

[SCSI] qla2xxx: Avoid depending on SCSI host_lock in queuecommand function.

Signed-off-by: Giridhar Malavali <giridhar.malavali@qlogic.com>
Signed-off-by: Madhuranath Iyengar <Madhu.Iyengar@qlogic.com>
Signed-off-by: James Bottomley <James.Bottomley@suse.de>

authored by

Giridhar Malavali and committed by
James Bottomley
38170fa8 9dac0d9a

+11 -13
+4 -4
drivers/scsi/qla2xxx/qla_attr.c
··· 1538 1538 if (!fcport) 1539 1539 return; 1540 1540 1541 + /* Now that the rport has been deleted, set the fcport state to 1542 + FCS_DEVICE_DEAD */ 1543 + atomic_set(&fcport->state, FCS_DEVICE_DEAD); 1544 + 1541 1545 /* 1542 1546 * Transport has effectively 'deleted' the rport, clear 1543 1547 * all local references. ··· 1550 1546 fcport->rport = fcport->drport = NULL; 1551 1547 *((fc_port_t **)rport->dd_data) = NULL; 1552 1548 spin_unlock_irq(host->host_lock); 1553 - 1554 - /* Now that the rport has been deleted, set the fcport state to 1555 - FCS_DEVICE_DEAD */ 1556 - atomic_set(&fcport->state, FCS_DEVICE_DEAD); 1557 1549 1558 1550 if (test_bit(ABORT_ISP_ACTIVE, &fcport->vha->dpc_flags)) 1559 1551 return;
+1 -1
drivers/scsi/qla2xxx/qla_init.c
··· 2928 2928 fcport->flags &= ~(FCF_LOGIN_NEEDED | FCF_ASYNC_SENT); 2929 2929 2930 2930 qla2x00_iidma_fcport(vha, fcport); 2931 - atomic_set(&fcport->state, FCS_ONLINE); 2932 2931 qla2x00_reg_remote_port(vha, fcport); 2932 + atomic_set(&fcport->state, FCS_ONLINE); 2933 2933 } 2934 2934 2935 2935 /*
+6 -8
drivers/scsi/qla2xxx/qla_os.c
··· 545 545 srb_t *sp; 546 546 int rval; 547 547 548 + spin_unlock_irq(vha->host->host_lock); 548 549 if (ha->flags.eeh_busy) { 549 550 if (ha->flags.pci_channel_io_perm_failure) 550 551 cmd->result = DID_NO_CONNECT << 16; ··· 560 559 goto qc24_fail_command; 561 560 } 562 561 563 - /* Close window on fcport/rport state-transitioning. */ 564 - if (fcport->drport) 565 - goto qc24_target_busy; 566 - 567 562 if (!vha->flags.difdix_supported && 568 563 scsi_get_prot_op(cmd) != SCSI_PROT_NORMAL) { 569 564 DEBUG2(qla_printk(KERN_ERR, ha, ··· 570 573 } 571 574 if (atomic_read(&fcport->state) != FCS_ONLINE) { 572 575 if (atomic_read(&fcport->state) == FCS_DEVICE_DEAD || 573 - atomic_read(&base_vha->loop_state) == LOOP_DEAD) { 576 + atomic_read(&fcport->state) == FCS_DEVICE_LOST || 577 + atomic_read(&base_vha->loop_state) == LOOP_DEAD) { 574 578 cmd->result = DID_NO_CONNECT << 16; 575 579 goto qc24_fail_command; 576 580 } 577 581 goto qc24_target_busy; 578 582 } 579 - 580 - spin_unlock_irq(vha->host->host_lock); 581 583 582 584 sp = qla2x00_get_new_sp(base_vha, fcport, cmd, done); 583 585 if (!sp) ··· 599 603 return SCSI_MLQUEUE_HOST_BUSY; 600 604 601 605 qc24_target_busy: 606 + spin_lock_irq(vha->host->host_lock); 602 607 return SCSI_MLQUEUE_TARGET_BUSY; 603 608 604 609 qc24_fail_command: 610 + spin_lock_irq(vha->host->host_lock); 605 611 done(cmd); 606 612 607 613 return 0; ··· 2611 2613 if (atomic_read(&fcport->state) == FCS_DEVICE_DEAD) 2612 2614 continue; 2613 2615 if (atomic_read(&fcport->state) == FCS_ONLINE) { 2616 + atomic_set(&fcport->state, FCS_DEVICE_LOST); 2614 2617 if (defer) 2615 2618 qla2x00_schedule_rport_del(vha, fcport, defer); 2616 2619 else if (vha->vp_idx == fcport->vp_idx) 2617 2620 qla2x00_schedule_rport_del(vha, fcport, defer); 2618 2621 } 2619 - atomic_set(&fcport->state, FCS_DEVICE_LOST); 2620 2622 } 2621 2623 } 2622 2624