aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/fnic/fnic_scsi.c
diff options
context:
space:
mode:
authorAndrea Bastoni <bastoni@cs.unc.edu>2010-05-30 19:16:45 -0400
committerAndrea Bastoni <bastoni@cs.unc.edu>2010-05-30 19:16:45 -0400
commitada47b5fe13d89735805b566185f4885f5a3f750 (patch)
tree644b88f8a71896307d71438e9b3af49126ffb22b /drivers/scsi/fnic/fnic_scsi.c
parent43e98717ad40a4ae64545b5ba047c7b86aa44f4f (diff)
parent3280f21d43ee541f97f8cda5792150d2dbec20d5 (diff)
Merge branch 'wip-2.6.34' into old-private-masterarchived-private-master
Diffstat (limited to 'drivers/scsi/fnic/fnic_scsi.c')
-rw-r--r--drivers/scsi/fnic/fnic_scsi.c97
1 files changed, 39 insertions, 58 deletions
diff --git a/drivers/scsi/fnic/fnic_scsi.c b/drivers/scsi/fnic/fnic_scsi.c
index bfc996971b81..3cc47c6e1ada 100644
--- a/drivers/scsi/fnic/fnic_scsi.c
+++ b/drivers/scsi/fnic/fnic_scsi.c
@@ -26,6 +26,7 @@
26#include <linux/if_ether.h> 26#include <linux/if_ether.h>
27#include <linux/if_vlan.h> 27#include <linux/if_vlan.h>
28#include <linux/delay.h> 28#include <linux/delay.h>
29#include <linux/gfp.h>
29#include <scsi/scsi.h> 30#include <scsi/scsi.h>
30#include <scsi/scsi_host.h> 31#include <scsi/scsi_host.h>
31#include <scsi/scsi_device.h> 32#include <scsi/scsi_device.h>
@@ -174,6 +175,9 @@ int fnic_fw_reset_handler(struct fnic *fnic)
174 int ret = 0; 175 int ret = 0;
175 unsigned long flags; 176 unsigned long flags;
176 177
178 skb_queue_purge(&fnic->frame_queue);
179 skb_queue_purge(&fnic->tx_queue);
180
177 spin_lock_irqsave(&fnic->wq_copy_lock[0], flags); 181 spin_lock_irqsave(&fnic->wq_copy_lock[0], flags);
178 182
179 if (vnic_wq_copy_desc_avail(wq) <= fnic->wq_copy_desc_low[0]) 183 if (vnic_wq_copy_desc_avail(wq) <= fnic->wq_copy_desc_low[0])
@@ -200,9 +204,11 @@ int fnic_fw_reset_handler(struct fnic *fnic)
200 * fnic_flogi_reg_handler 204 * fnic_flogi_reg_handler
201 * Routine to send flogi register msg to fw 205 * Routine to send flogi register msg to fw
202 */ 206 */
203int fnic_flogi_reg_handler(struct fnic *fnic) 207int fnic_flogi_reg_handler(struct fnic *fnic, u32 fc_id)
204{ 208{
205 struct vnic_wq_copy *wq = &fnic->wq_copy[0]; 209 struct vnic_wq_copy *wq = &fnic->wq_copy[0];
210 enum fcpio_flogi_reg_format_type format;
211 struct fc_lport *lp = fnic->lport;
206 u8 gw_mac[ETH_ALEN]; 212 u8 gw_mac[ETH_ALEN];
207 int ret = 0; 213 int ret = 0;
208 unsigned long flags; 214 unsigned long flags;
@@ -217,23 +223,32 @@ int fnic_flogi_reg_handler(struct fnic *fnic)
217 goto flogi_reg_ioreq_end; 223 goto flogi_reg_ioreq_end;
218 } 224 }
219 225
220 if (fnic->fcoui_mode) 226 if (fnic->ctlr.map_dest) {
221 memset(gw_mac, 0xff, ETH_ALEN); 227 memset(gw_mac, 0xff, ETH_ALEN);
222 else 228 format = FCPIO_FLOGI_REG_DEF_DEST;
223 memcpy(gw_mac, fnic->dest_addr, ETH_ALEN); 229 } else {
230 memcpy(gw_mac, fnic->ctlr.dest_addr, ETH_ALEN);
231 format = FCPIO_FLOGI_REG_GW_DEST;
232 }
224 233
225 fnic_queue_wq_copy_desc_flogi_reg(wq, SCSI_NO_TAG, 234 if ((fnic->config.flags & VFCF_FIP_CAPABLE) && !fnic->ctlr.map_dest) {
226 FCPIO_FLOGI_REG_GW_DEST, 235 fnic_queue_wq_copy_desc_fip_reg(wq, SCSI_NO_TAG,
227 fnic->s_id, 236 fc_id, gw_mac,
228 gw_mac); 237 fnic->data_src_addr,
238 lp->r_a_tov, lp->e_d_tov);
239 FNIC_SCSI_DBG(KERN_DEBUG, fnic->lport->host,
240 "FLOGI FIP reg issued fcid %x src %pM dest %pM\n",
241 fc_id, fnic->data_src_addr, gw_mac);
242 } else {
243 fnic_queue_wq_copy_desc_flogi_reg(wq, SCSI_NO_TAG,
244 format, fc_id, gw_mac);
245 FNIC_SCSI_DBG(KERN_DEBUG, fnic->lport->host,
246 "FLOGI reg issued fcid %x map %d dest %pM\n",
247 fc_id, fnic->ctlr.map_dest, gw_mac);
248 }
229 249
230flogi_reg_ioreq_end: 250flogi_reg_ioreq_end:
231 spin_unlock_irqrestore(&fnic->wq_copy_lock[0], flags); 251 spin_unlock_irqrestore(&fnic->wq_copy_lock[0], flags);
232
233 if (!ret)
234 FNIC_SCSI_DBG(KERN_DEBUG, fnic->lport->host,
235 "flog reg issued\n");
236
237 return ret; 252 return ret;
238} 253}
239 254
@@ -319,7 +334,8 @@ static inline int fnic_queue_wq_copy_desc(struct fnic *fnic,
319 0, /* scsi cmd ref, always 0 */ 334 0, /* scsi cmd ref, always 0 */
320 pri_tag, /* scsi pri and tag */ 335 pri_tag, /* scsi pri and tag */
321 flags, /* command flags */ 336 flags, /* command flags */
322 sc->cmnd, scsi_bufflen(sc), 337 sc->cmnd, sc->cmd_len,
338 scsi_bufflen(sc),
323 fc_lun.scsi_lun, io_req->port_id, 339 fc_lun.scsi_lun, io_req->port_id,
324 rport->maxframe_size, rp->r_a_tov, 340 rport->maxframe_size, rp->r_a_tov,
325 rp->e_d_tov); 341 rp->e_d_tov);
@@ -452,7 +468,6 @@ static int fnic_fcpio_fw_reset_cmpl_handler(struct fnic *fnic,
452 u8 hdr_status; 468 u8 hdr_status;
453 struct fcpio_tag tag; 469 struct fcpio_tag tag;
454 int ret = 0; 470 int ret = 0;
455 struct fc_frame *flogi;
456 unsigned long flags; 471 unsigned long flags;
457 472
458 fcpio_header_dec(&desc->hdr, &type, &hdr_status, &tag); 473 fcpio_header_dec(&desc->hdr, &type, &hdr_status, &tag);
@@ -462,9 +477,6 @@ static int fnic_fcpio_fw_reset_cmpl_handler(struct fnic *fnic,
462 477
463 spin_lock_irqsave(&fnic->fnic_lock, flags); 478 spin_lock_irqsave(&fnic->fnic_lock, flags);
464 479
465 flogi = fnic->flogi;
466 fnic->flogi = NULL;
467
468 /* fnic should be in FC_TRANS_ETH_MODE */ 480 /* fnic should be in FC_TRANS_ETH_MODE */
469 if (fnic->state == FNIC_IN_FC_TRANS_ETH_MODE) { 481 if (fnic->state == FNIC_IN_FC_TRANS_ETH_MODE) {
470 /* Check status of reset completion */ 482 /* Check status of reset completion */
@@ -505,17 +517,14 @@ static int fnic_fcpio_fw_reset_cmpl_handler(struct fnic *fnic,
505 * free the flogi frame. Else, send it out 517 * free the flogi frame. Else, send it out
506 */ 518 */
507 if (fnic->remove_wait || ret) { 519 if (fnic->remove_wait || ret) {
508 fnic->flogi_oxid = FC_XID_UNKNOWN;
509 spin_unlock_irqrestore(&fnic->fnic_lock, flags); 520 spin_unlock_irqrestore(&fnic->fnic_lock, flags);
510 if (flogi) 521 skb_queue_purge(&fnic->tx_queue);
511 dev_kfree_skb_irq(fp_skb(flogi));
512 goto reset_cmpl_handler_end; 522 goto reset_cmpl_handler_end;
513 } 523 }
514 524
515 spin_unlock_irqrestore(&fnic->fnic_lock, flags); 525 spin_unlock_irqrestore(&fnic->fnic_lock, flags);
516 526
517 if (flogi) 527 fnic_flush_tx(fnic);
518 ret = fnic_send_frame(fnic, flogi);
519 528
520 reset_cmpl_handler_end: 529 reset_cmpl_handler_end:
521 return ret; 530 return ret;
@@ -532,18 +541,13 @@ static int fnic_fcpio_flogi_reg_cmpl_handler(struct fnic *fnic,
532 u8 hdr_status; 541 u8 hdr_status;
533 struct fcpio_tag tag; 542 struct fcpio_tag tag;
534 int ret = 0; 543 int ret = 0;
535 struct fc_frame *flogi_resp = NULL;
536 unsigned long flags; 544 unsigned long flags;
537 struct sk_buff *skb;
538 545
539 fcpio_header_dec(&desc->hdr, &type, &hdr_status, &tag); 546 fcpio_header_dec(&desc->hdr, &type, &hdr_status, &tag);
540 547
541 /* Update fnic state based on status of flogi reg completion */ 548 /* Update fnic state based on status of flogi reg completion */
542 spin_lock_irqsave(&fnic->fnic_lock, flags); 549 spin_lock_irqsave(&fnic->fnic_lock, flags);
543 550
544 flogi_resp = fnic->flogi_resp;
545 fnic->flogi_resp = NULL;
546
547 if (fnic->state == FNIC_IN_ETH_TRANS_FC_MODE) { 551 if (fnic->state == FNIC_IN_ETH_TRANS_FC_MODE) {
548 552
549 /* Check flogi registration completion status */ 553 /* Check flogi registration completion status */
@@ -567,25 +571,17 @@ static int fnic_fcpio_flogi_reg_cmpl_handler(struct fnic *fnic,
567 ret = -1; 571 ret = -1;
568 } 572 }
569 573
570 /* Successful flogi reg cmpl, pass frame to LibFC */ 574 if (!ret) {
571 if (!ret && flogi_resp) {
572 if (fnic->stop_rx_link_events) { 575 if (fnic->stop_rx_link_events) {
573 spin_unlock_irqrestore(&fnic->fnic_lock, flags); 576 spin_unlock_irqrestore(&fnic->fnic_lock, flags);
574 goto reg_cmpl_handler_end; 577 goto reg_cmpl_handler_end;
575 } 578 }
576 skb = (struct sk_buff *)flogi_resp;
577 /* Use fr_flags to indicate whether flogi resp or not */
578 fr_flags(flogi_resp) = 1;
579 fr_dev(flogi_resp) = fnic->lport;
580 spin_unlock_irqrestore(&fnic->fnic_lock, flags); 579 spin_unlock_irqrestore(&fnic->fnic_lock, flags);
581 580
582 skb_queue_tail(&fnic->frame_queue, skb); 581 fnic_flush_tx(fnic);
583 queue_work(fnic_event_queue, &fnic->frame_work); 582 queue_work(fnic_event_queue, &fnic->frame_work);
584
585 } else { 583 } else {
586 spin_unlock_irqrestore(&fnic->fnic_lock, flags); 584 spin_unlock_irqrestore(&fnic->fnic_lock, flags);
587 if (flogi_resp)
588 dev_kfree_skb_irq(fp_skb(flogi_resp));
589 } 585 }
590 586
591reg_cmpl_handler_end: 587reg_cmpl_handler_end:
@@ -907,6 +903,7 @@ static int fnic_fcpio_cmpl_handler(struct vnic_dev *vdev,
907 break; 903 break;
908 904
909 case FCPIO_FLOGI_REG_CMPL: /* fw completed flogi_reg */ 905 case FCPIO_FLOGI_REG_CMPL: /* fw completed flogi_reg */
906 case FCPIO_FLOGI_FIP_REG_CMPL: /* fw completed flogi_fip_reg */
910 ret = fnic_fcpio_flogi_reg_cmpl_handler(fnic, desc); 907 ret = fnic_fcpio_flogi_reg_cmpl_handler(fnic, desc);
911 break; 908 break;
912 909
@@ -1224,22 +1221,6 @@ void fnic_terminate_rport_io(struct fc_rport *rport)
1224 1221
1225} 1222}
1226 1223
1227static void fnic_block_error_handler(struct scsi_cmnd *sc)
1228{
1229 struct Scsi_Host *shost = sc->device->host;
1230 struct fc_rport *rport = starget_to_rport(scsi_target(sc->device));
1231 unsigned long flags;
1232
1233 spin_lock_irqsave(shost->host_lock, flags);
1234 while (rport->port_state == FC_PORTSTATE_BLOCKED) {
1235 spin_unlock_irqrestore(shost->host_lock, flags);
1236 msleep(1000);
1237 spin_lock_irqsave(shost->host_lock, flags);
1238 }
1239 spin_unlock_irqrestore(shost->host_lock, flags);
1240
1241}
1242
1243/* 1224/*
1244 * This function is exported to SCSI for sending abort cmnds. 1225 * This function is exported to SCSI for sending abort cmnds.
1245 * A SCSI IO is represented by a io_req in the driver. 1226 * A SCSI IO is represented by a io_req in the driver.
@@ -1259,7 +1240,7 @@ int fnic_abort_cmd(struct scsi_cmnd *sc)
1259 DECLARE_COMPLETION_ONSTACK(tm_done); 1240 DECLARE_COMPLETION_ONSTACK(tm_done);
1260 1241
1261 /* Wait for rport to unblock */ 1242 /* Wait for rport to unblock */
1262 fnic_block_error_handler(sc); 1243 fc_block_scsi_eh(sc);
1263 1244
1264 /* Get local-port, check ready and link up */ 1245 /* Get local-port, check ready and link up */
1265 lp = shost_priv(sc->device->host); 1246 lp = shost_priv(sc->device->host);
@@ -1541,7 +1522,7 @@ int fnic_device_reset(struct scsi_cmnd *sc)
1541 DECLARE_COMPLETION_ONSTACK(tm_done); 1522 DECLARE_COMPLETION_ONSTACK(tm_done);
1542 1523
1543 /* Wait for rport to unblock */ 1524 /* Wait for rport to unblock */
1544 fnic_block_error_handler(sc); 1525 fc_block_scsi_eh(sc);
1545 1526
1546 /* Get local-port, check ready and link up */ 1527 /* Get local-port, check ready and link up */
1547 lp = shost_priv(sc->device->host); 1528 lp = shost_priv(sc->device->host);
@@ -1762,7 +1743,7 @@ void fnic_scsi_abort_io(struct fc_lport *lp)
1762 fnic->remove_wait = &remove_wait; 1743 fnic->remove_wait = &remove_wait;
1763 old_state = fnic->state; 1744 old_state = fnic->state;
1764 fnic->state = FNIC_IN_FC_TRANS_ETH_MODE; 1745 fnic->state = FNIC_IN_FC_TRANS_ETH_MODE;
1765 vnic_dev_del_addr(fnic->vdev, fnic->data_src_addr); 1746 fnic_update_mac_locked(fnic, fnic->ctlr.ctl_src_addr);
1766 spin_unlock_irqrestore(&fnic->fnic_lock, flags); 1747 spin_unlock_irqrestore(&fnic->fnic_lock, flags);
1767 1748
1768 err = fnic_fw_reset_handler(fnic); 1749 err = fnic_fw_reset_handler(fnic);
@@ -1802,7 +1783,7 @@ void fnic_scsi_cleanup(struct fc_lport *lp)
1802 spin_lock_irqsave(&fnic->fnic_lock, flags); 1783 spin_lock_irqsave(&fnic->fnic_lock, flags);
1803 old_state = fnic->state; 1784 old_state = fnic->state;
1804 fnic->state = FNIC_IN_FC_TRANS_ETH_MODE; 1785 fnic->state = FNIC_IN_FC_TRANS_ETH_MODE;
1805 vnic_dev_del_addr(fnic->vdev, fnic->data_src_addr); 1786 fnic_update_mac_locked(fnic, fnic->ctlr.ctl_src_addr);
1806 spin_unlock_irqrestore(&fnic->fnic_lock, flags); 1787 spin_unlock_irqrestore(&fnic->fnic_lock, flags);
1807 1788
1808 if (fnic_fw_reset_handler(fnic)) { 1789 if (fnic_fw_reset_handler(fnic)) {