/* bnx2fc_fcoe.c: QLogic Linux FCoE offload driver.
 * This file contains the code that interacts with libfc, libfcoe,
 * cnic modules to create FCoE instances, send/receive non-offloaded
 * FIP/FCoE packets, listen to link events etc.
 *
 * Copyright (c) 2008-2013 Broadcom Corporation
 * Copyright (c) 2014-2016 QLogic Corporation
 * Copyright (c) 2016-2017 Cavium Inc.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation.
 *
 * Written by: Bhanu Prakash Gollapudi (bprakash@broadcom.com)
 */

#include "bnx2fc.h"

static struct list_head adapter_list;
static struct list_head if_list;
static u32 adapter_count;
static DEFINE_MUTEX(bnx2fc_dev_lock);
DEFINE_PER_CPU(struct bnx2fc_percpu_s, bnx2fc_percpu);

#define DRV_MODULE_NAME		"bnx2fc"
#define DRV_MODULE_VERSION	BNX2FC_VERSION
#define DRV_MODULE_RELDATE	"October 15, 2015"


static char version[] =
		"QLogic FCoE Driver " DRV_MODULE_NAME \
		" v" DRV_MODULE_VERSION " (" DRV_MODULE_RELDATE ")\n";


MODULE_AUTHOR("Bhanu Prakash Gollapudi <bprakash@broadcom.com>");
MODULE_DESCRIPTION("QLogic FCoE Driver");
MODULE_LICENSE("GPL");
MODULE_VERSION(DRV_MODULE_VERSION);

#define BNX2FC_MAX_QUEUE_DEPTH	256
#define BNX2FC_MIN_QUEUE_DEPTH	32
#define FCOE_WORD_TO_BYTE  4

static struct scsi_transport_template	*bnx2fc_transport_template;
static struct scsi_transport_template	*bnx2fc_vport_xport_template;

struct workqueue_struct *bnx2fc_wq;

/* bnx2fc structure needs only one instance of the fcoe_percpu_s structure.
 * Here the io threads are per cpu but the l2 thread is just one
 */
struct fcoe_percpu_s bnx2fc_global;
DEFINE_SPINLOCK(bnx2fc_global_lock);

static struct cnic_ulp_ops bnx2fc_cnic_cb;
static struct libfc_function_template bnx2fc_libfc_fcn_templ;
static struct scsi_host_template bnx2fc_shost_template;
static struct fc_function_template bnx2fc_transport_function;
static struct fcoe_sysfs_function_template bnx2fc_fcoe_sysfs_templ;
static struct fc_function_template bnx2fc_vport_xport_function;
static int bnx2fc_create(struct net_device *netdev, enum fip_mode fip_mode);
static void __bnx2fc_destroy(struct bnx2fc_interface *interface);
static int bnx2fc_destroy(struct net_device *net_device);
static int bnx2fc_enable(struct net_device *netdev);
static int bnx2fc_disable(struct net_device *netdev);

/* fcoe_syfs control interface handlers */
static int bnx2fc_ctlr_alloc(struct net_device *netdev);
static int bnx2fc_ctlr_enabled(struct fcoe_ctlr_device *cdev);

static void bnx2fc_recv_frame(struct sk_buff *skb);

static void bnx2fc_start_disc(struct bnx2fc_interface *interface);
static int bnx2fc_shost_config(struct fc_lport *lport, struct device *dev);
static int bnx2fc_lport_config(struct fc_lport *lport);
static int bnx2fc_em_config(struct fc_lport *lport, struct bnx2fc_hba *hba);
static int bnx2fc_bind_adapter_devices(struct bnx2fc_hba *hba);
static void bnx2fc_unbind_adapter_devices(struct bnx2fc_hba *hba);
static int bnx2fc_bind_pcidev(struct bnx2fc_hba *hba);
static void bnx2fc_unbind_pcidev(struct bnx2fc_hba *hba);
static struct fc_lport *bnx2fc_if_create(struct bnx2fc_interface *interface,
				  struct device *parent, int npiv);
static void bnx2fc_destroy_work(struct work_struct *work);

static struct bnx2fc_hba *bnx2fc_hba_lookup(struct net_device *phys_dev);
static struct bnx2fc_interface *bnx2fc_interface_lookup(struct net_device
							*phys_dev);
static inline void bnx2fc_interface_put(struct bnx2fc_interface *interface);
static struct bnx2fc_hba *bnx2fc_find_hba_for_cnic(struct cnic_dev *cnic);

static int bnx2fc_fw_init(struct bnx2fc_hba *hba);
static void bnx2fc_fw_destroy(struct bnx2fc_hba *hba);

static void bnx2fc_port_shutdown(struct fc_lport *lport);
static void bnx2fc_stop(struct bnx2fc_interface *interface);
static int __init bnx2fc_mod_init(void);
static void __exit bnx2fc_mod_exit(void);

unsigned int bnx2fc_debug_level;
module_param_named(debug_logging, bnx2fc_debug_level, int, S_IRUGO|S_IWUSR);
MODULE_PARM_DESC(debug_logging,
		"Option to enable extended logging,\n"
		"\t\tDefault is 0 - no logging.\n"
		"\t\t0x01 - SCSI cmd error, cleanup.\n"
		"\t\t0x02 - Session setup, cleanup, etc.\n"
		"\t\t0x04 - lport events, link, mtu, etc.\n"
		"\t\t0x08 - ELS logs.\n"
		"\t\t0x10 - fcoe L2 fame related logs.\n"
		"\t\t0xff - LOG all messages.");

uint bnx2fc_devloss_tmo;
module_param_named(devloss_tmo, bnx2fc_devloss_tmo, uint, S_IRUGO);
MODULE_PARM_DESC(devloss_tmo, " Change devloss_tmo for the remote ports "
	"attached via bnx2fc.");

uint bnx2fc_max_luns = BNX2FC_MAX_LUN;
module_param_named(max_luns, bnx2fc_max_luns, uint, S_IRUGO);
MODULE_PARM_DESC(max_luns, " Change the default max_lun per SCSI host. Default "
	"0xffff.");

uint bnx2fc_queue_depth;
module_param_named(queue_depth, bnx2fc_queue_depth, uint, S_IRUGO);
MODULE_PARM_DESC(queue_depth, " Change the default queue depth of SCSI devices "
	"attached via bnx2fc.");

uint bnx2fc_log_fka;
module_param_named(log_fka, bnx2fc_log_fka, uint, S_IRUGO|S_IWUSR);
MODULE_PARM_DESC(log_fka, " Print message to kernel log when fcoe is "
	"initiating a FIP keep alive when debug logging is enabled.");

static inline struct net_device *bnx2fc_netdev(const struct fc_lport *lport)
{
	return ((struct bnx2fc_interface *)
		((struct fcoe_port *)lport_priv(lport))->priv)->netdev;
}

static void bnx2fc_fcf_get_vlan_id(struct fcoe_fcf_device *fcf_dev)
{
	struct fcoe_ctlr_device *ctlr_dev =
		fcoe_fcf_dev_to_ctlr_dev(fcf_dev);
	struct fcoe_ctlr *ctlr = fcoe_ctlr_device_priv(ctlr_dev);
	struct bnx2fc_interface *fcoe = fcoe_ctlr_priv(ctlr);

	fcf_dev->vlan_id = fcoe->vlan_id;
}

static void bnx2fc_clean_rx_queue(struct fc_lport *lp)
{
	struct fcoe_percpu_s *bg;
	struct fcoe_rcv_info *fr;
	struct sk_buff_head *list;
	struct sk_buff *skb, *next;

	bg = &bnx2fc_global;
	spin_lock_bh(&bg->fcoe_rx_list.lock);
	list = &bg->fcoe_rx_list;
	skb_queue_walk_safe(list, skb, next) {
		fr = fcoe_dev_from_skb(skb);
		if (fr->fr_dev == lp) {
			__skb_unlink(skb, list);
			kfree_skb(skb);
		}
	}
	spin_unlock_bh(&bg->fcoe_rx_list.lock);
}

int bnx2fc_get_paged_crc_eof(struct sk_buff *skb, int tlen)
{
	int rc;
	spin_lock(&bnx2fc_global_lock);
	rc = fcoe_get_paged_crc_eof(skb, tlen, &bnx2fc_global);
	spin_unlock(&bnx2fc_global_lock);

	return rc;
}

static void bnx2fc_abort_io(struct fc_lport *lport)
{
	/*
	 * This function is no-op for bnx2fc, but we do
	 * not want to leave it as NULL either, as libfc
	 * can call the default function which is
	 * fc_fcp_abort_io.
	 */
}

static void bnx2fc_cleanup(struct fc_lport *lport)
{
	struct fcoe_port *port = lport_priv(lport);
	struct bnx2fc_interface *interface = port->priv;
	struct bnx2fc_hba *hba = interface->hba;
	struct bnx2fc_rport *tgt;
	int i;

	BNX2FC_MISC_DBG("Entered %s\n", __func__);
	mutex_lock(&hba->hba_mutex);
	spin_lock_bh(&hba->hba_lock);
	for (i = 0; i < BNX2FC_NUM_MAX_SESS; i++) {
		tgt = hba->tgt_ofld_list[i];
		if (tgt) {
			/* Cleanup IOs belonging to requested vport */
			if (tgt->port == port) {
				spin_unlock_bh(&hba->hba_lock);
				BNX2FC_TGT_DBG(tgt, "flush/cleanup\n");
				bnx2fc_flush_active_ios(tgt);
				spin_lock_bh(&hba->hba_lock);
			}
		}
	}
	spin_unlock_bh(&hba->hba_lock);
	mutex_unlock(&hba->hba_mutex);
}

static int bnx2fc_xmit_l2_frame(struct bnx2fc_rport *tgt,
			     struct fc_frame *fp)
{
	struct fc_rport_priv *rdata = tgt->rdata;
	struct fc_frame_header *fh;
	int rc = 0;

	fh = fc_frame_header_get(fp);
	BNX2FC_TGT_DBG(tgt, "Xmit L2 frame rport = 0x%x, oxid = 0x%x, "
			"r_ctl = 0x%x\n", rdata->ids.port_id,
			ntohs(fh->fh_ox_id), fh->fh_r_ctl);
	if ((fh->fh_type == FC_TYPE_ELS) &&
	    (fh->fh_r_ctl == FC_RCTL_ELS_REQ)) {

		switch (fc_frame_payload_op(fp)) {
		case ELS_ADISC:
			rc = bnx2fc_send_adisc(tgt, fp);
			break;
		case ELS_LOGO:
			rc = bnx2fc_send_logo(tgt, fp);
			break;
		case ELS_RLS:
			rc = bnx2fc_send_rls(tgt, fp);
			break;
		default:
			break;
		}
	} else if ((fh->fh_type ==  FC_TYPE_BLS) &&
	    (fh->fh_r_ctl == FC_RCTL_BA_ABTS))
		BNX2FC_TGT_DBG(tgt, "ABTS frame\n");
	else {
		BNX2FC_TGT_DBG(tgt, "Send L2 frame type 0x%x "
				"rctl 0x%x thru non-offload path\n",
				fh->fh_type, fh->fh_r_ctl);
		return -ENODEV;
	}
	if (rc)
		return -ENOMEM;
	else
		return 0;
}

/**
 * bnx2fc_xmit - bnx2fc's FCoE frame transmit function
 *
 * @lport:	the associated local port
 * @fp:	the fc_frame to be transmitted
 */
static int bnx2fc_xmit(struct fc_lport *lport, struct fc_frame *fp)
{
	struct ethhdr		*eh;
	struct fcoe_crc_eof	*cp;
	struct sk_buff		*skb;
	struct fc_frame_header	*fh;
	struct bnx2fc_interface	*interface;
	struct fcoe_ctlr        *ctlr;
	struct bnx2fc_hba *hba;
	struct fcoe_port	*port;
	struct fcoe_hdr		*hp;
	struct bnx2fc_rport	*tgt;
	struct fc_stats		*stats;
	u8			sof, eof;
	u32			crc;
	unsigned int		hlen, tlen, elen;
	int			wlen, rc = 0;

	port = (struct fcoe_port *)lport_priv(lport);
	interface = port->priv;
	ctlr = bnx2fc_to_ctlr(interface);
	hba = interface->hba;

	fh = fc_frame_header_get(fp);

	skb = fp_skb(fp);
	if (!lport->link_up) {
		BNX2FC_HBA_DBG(lport, "bnx2fc_xmit link down\n");
		kfree_skb(skb);
		return 0;
	}

	if (unlikely(fh->fh_r_ctl == FC_RCTL_ELS_REQ)) {
		if (!ctlr->sel_fcf) {
			BNX2FC_HBA_DBG(lport, "FCF not selected yet!\n");
			kfree_skb(skb);
			return -EINVAL;
		}
		if (fcoe_ctlr_els_send(ctlr, lport, skb))
			return 0;
	}

	sof = fr_sof(fp);
	eof = fr_eof(fp);

	/*
	 * Snoop the frame header to check if the frame is for
	 * an offloaded session
	 */
	/*
	 * tgt_ofld_list access is synchronized using
	 * both hba mutex and hba lock. Atleast hba mutex or
	 * hba lock needs to be held for read access.
	 */

	spin_lock_bh(&hba->hba_lock);
	tgt = bnx2fc_tgt_lookup(port, ntoh24(fh->fh_d_id));
	if (tgt && (test_bit(BNX2FC_FLAG_SESSION_READY, &tgt->flags))) {
		/* This frame is for offloaded session */
		BNX2FC_HBA_DBG(lport, "xmit: Frame is for offloaded session "
				"port_id = 0x%x\n", ntoh24(fh->fh_d_id));
		spin_unlock_bh(&hba->hba_lock);
		rc = bnx2fc_xmit_l2_frame(tgt, fp);
		if (rc != -ENODEV) {
			kfree_skb(skb);
			return rc;
		}
	} else {
		spin_unlock_bh(&hba->hba_lock);
	}

	elen = sizeof(struct ethhdr);
	hlen = sizeof(struct fcoe_hdr);
	tlen = sizeof(struct fcoe_crc_eof);
	wlen = (skb->len - tlen + sizeof(crc)) / FCOE_WORD_TO_BYTE;

	skb->ip_summed = CHECKSUM_NONE;
	crc = fcoe_fc_crc(fp);

	/* copy port crc and eof to the skb buff */
	if (skb_is_nonlinear(skb)) {
		skb_frag_t *frag;
		if (bnx2fc_get_paged_crc_eof(skb, tlen)) {
			kfree_skb(skb);
			return -ENOMEM;
		}
		frag = &skb_shinfo(skb)->frags[skb_shinfo(skb)->nr_frags - 1];
		cp = kmap_atomic(skb_frag_page(frag)) + skb_frag_off(frag);
	} else {
		cp = skb_put(skb, tlen);
	}

	memset(cp, 0, sizeof(*cp));
	cp->fcoe_eof = eof;
	cp->fcoe_crc32 = cpu_to_le32(~crc);
	if (skb_is_nonlinear(skb)) {
		kunmap_atomic(cp);
		cp = NULL;
	}

	/* adjust skb network/transport offsets to match mac/fcoe/port */
	skb_push(skb, elen + hlen);
	skb_reset_mac_header(skb);
	skb_reset_network_header(skb);
	skb->mac_len = elen;
	skb->protocol = htons(ETH_P_FCOE);
	skb->dev = interface->netdev;

	/* fill up mac and fcoe headers */
	eh = eth_hdr(skb);
	eh->h_proto = htons(ETH_P_FCOE);
	if (ctlr->map_dest)
		fc_fcoe_set_mac(eh->h_dest, fh->fh_d_id);
	else
		/* insert GW address */
		memcpy(eh->h_dest, ctlr->dest_addr, ETH_ALEN);

	if (unlikely(ctlr->flogi_oxid != FC_XID_UNKNOWN))
		memcpy(eh->h_source, ctlr->ctl_src_addr, ETH_ALEN);
	else
		memcpy(eh->h_source, port->data_src_addr, ETH_ALEN);

	hp = (struct fcoe_hdr *)(eh + 1);
	memset(hp, 0, sizeof(*hp));
	if (FC_FCOE_VER)
		FC_FCOE_ENCAPS_VER(hp, FC_FCOE_VER);
	hp->fcoe_sof = sof;

	/* fcoe lso, mss is in max_payload which is non-zero for FCP data */
	if (lport->seq_offload && fr_max_payload(fp)) {
		skb_shinfo(skb)->gso_type = SKB_GSO_FCOE;
		skb_shinfo(skb)->gso_size = fr_max_payload(fp);
	} else {
		skb_shinfo(skb)->gso_type = 0;
		skb_shinfo(skb)->gso_size = 0;
	}

	/*update tx stats */
	stats = per_cpu_ptr(lport->stats, get_cpu());
	stats->TxFrames++;
	stats->TxWords += wlen;
	put_cpu();

	/* send down to lld */
	fr_dev(fp) = lport;
	if (port->fcoe_pending_queue.qlen)
		fcoe_check_wait_queue(lport, skb);
	else if (fcoe_start_io(skb))
		fcoe_check_wait_queue(lport, skb);

	return 0;
}

/**
 * bnx2fc_rcv - This is bnx2fc's receive function called by NET_RX_SOFTIRQ
 *
 * @skb:	the receive socket buffer
 * @dev:	associated net device
 * @ptype:	context
 * @olddev:	last device
 *
 * This function receives the packet and builds FC frame and passes it up
 */
static int bnx2fc_rcv(struct sk_buff *skb, struct net_device *dev,
		struct packet_type *ptype, struct net_device *olddev)
{
	struct fc_lport *lport;
	struct bnx2fc_interface *interface;
	struct fcoe_ctlr *ctlr;
	struct fcoe_rcv_info *fr;
	struct fcoe_percpu_s *bg;
	struct sk_buff *tmp_skb;

	interface = container_of(ptype, struct bnx2fc_interface,
				 fcoe_packet_type);
	ctlr = bnx2fc_to_ctlr(interface);
	lport = ctlr->lp;

	if (unlikely(lport == NULL)) {
		printk(KERN_ERR PFX "bnx2fc_rcv: lport is NULL\n");
		goto err;
	}

	tmp_skb = skb_share_check(skb, GFP_ATOMIC);
	if (!tmp_skb)
		goto err;

	skb = tmp_skb;

	if (unlikely(eth_hdr(skb)->h_proto != htons(ETH_P_FCOE))) {
		printk(KERN_ERR PFX "bnx2fc_rcv: Wrong FC type frame\n");
		goto err;
	}

	/*
	 * Check for minimum frame length, and make sure required FCoE
	 * and FC headers are pulled into the linear data area.
	 */
	if (unlikely((skb->len < FCOE_MIN_FRAME) ||
	    !pskb_may_pull(skb, FCOE_HEADER_LEN)))
		goto err;

	skb_set_transport_header(skb, sizeof(struct fcoe_hdr));

	fr = fcoe_dev_from_skb(skb);
	fr->fr_dev = lport;

	bg = &bnx2fc_global;
	spin_lock(&bg->fcoe_rx_list.lock);

	__skb_queue_tail(&bg->fcoe_rx_list, skb);
	if (bg->fcoe_rx_list.qlen == 1)
		wake_up_process(bg->kthread);

	spin_unlock(&bg->fcoe_rx_list.lock);

	return 0;
err:
	kfree_skb(skb);
	return -1;
}

static int bnx2fc_l2_rcv_thread(void *arg)
{
	struct fcoe_percpu_s *bg = arg;
	struct sk_buff *skb;

	set_user_nice(current, MIN_NICE);
	set_current_state(TASK_INTERRUPTIBLE);
	while (!kthread_should_stop()) {
		schedule();
		spin_lock_bh(&bg->fcoe_rx_list.lock);
		while ((skb = __skb_dequeue(&bg->fcoe_rx_list)) != NULL) {
			spin_unlock_bh(&bg->fcoe_rx_list.lock);
			bnx2fc_recv_frame(skb);
			spin_lock_bh(&bg->fcoe_rx_list.lock);
		}
		__set_current_state(TASK_INTERRUPTIBLE);
		spin_unlock_bh(&bg->fcoe_rx_list.lock);
	}
	__set_current_state(TASK_RUNNING);
	return 0;
}


static void bnx2fc_recv_frame(struct sk_buff *skb)
{
	u32 fr_len;
	struct fc_lport *lport;
	struct fcoe_rcv_info *fr;
	struct fc_stats *stats;
	struct fc_frame_header *fh;
	struct fcoe_crc_eof crc_eof;
	struct fc_frame *fp;
	struct fc_lport *vn_port;
	struct fcoe_port *port, *phys_port;
	u8 *mac = NULL;
	u8 *dest_mac = NULL;
	struct fcoe_hdr *hp;
	struct bnx2fc_interface *interface;
	struct fcoe_ctlr *ctlr;

	fr = fcoe_dev_from_skb(skb);
	lport = fr->fr_dev;
	if (unlikely(lport == NULL)) {
		printk(KERN_ERR PFX "Invalid lport struct\n");
		kfree_skb(skb);
		return;
	}

	if (skb_is_nonlinear(skb))
		skb_linearize(skb);
	mac = eth_hdr(skb)->h_source;
	dest_mac = eth_hdr(skb)->h_dest;

	/* Pull the header */
	hp = (struct fcoe_hdr *) skb_network_header(skb);
	fh = (struct fc_frame_header *) skb_transport_header(skb);
	skb_pull(skb, sizeof(struct fcoe_hdr));
	fr_len = skb->len - sizeof(struct fcoe_crc_eof);

	fp = (struct fc_frame *)skb;
	fc_frame_init(fp);
	fr_dev(fp) = lport;
	fr_sof(fp) = hp->fcoe_sof;
	if (skb_copy_bits(skb, fr_len, &crc_eof, sizeof(crc_eof))) {
		kfree_skb(skb);
		return;
	}
	fr_eof(fp) = crc_eof.fcoe_eof;
	fr_crc(fp) = crc_eof.fcoe_crc32;
	if (pskb_trim(skb, fr_len)) {
		kfree_skb(skb);
		return;
	}

	phys_port = lport_priv(lport);
	interface = phys_port->priv;
	ctlr = bnx2fc_to_ctlr(interface);

	fh = fc_frame_header_get(fp);

	if (ntoh24(&dest_mac[3]) != ntoh24(fh->fh_d_id)) {
		BNX2FC_HBA_DBG(lport, "FC frame d_id mismatch with MAC %pM.\n",
		    dest_mac);
		kfree_skb(skb);
		return;
	}

	vn_port = fc_vport_id_lookup(lport, ntoh24(fh->fh_d_id));
	if (vn_port) {
		port = lport_priv(vn_port);
		if (!ether_addr_equal(port->data_src_addr, dest_mac)) {
			BNX2FC_HBA_DBG(lport, "fpma mismatch\n");
			kfree_skb(skb);
			return;
		}
	}
	if (ctlr->state) {
		if (!ether_addr_equal(mac, ctlr->dest_addr)) {
			BNX2FC_HBA_DBG(lport, "Wrong source address: mac:%pM dest_addr:%pM.\n",
			    mac, ctlr->dest_addr);
			kfree_skb(skb);
			return;
		}
	}
	if (fh->fh_r_ctl == FC_RCTL_DD_SOL_DATA &&
	    fh->fh_type == FC_TYPE_FCP) {
		/* Drop FCP data. We dont this in L2 path */
		kfree_skb(skb);
		return;
	}
	if (fh->fh_r_ctl == FC_RCTL_ELS_REQ &&
	    fh->fh_type == FC_TYPE_ELS) {
		switch (fc_frame_payload_op(fp)) {
		case ELS_LOGO:
			if (ntoh24(fh->fh_s_id) == FC_FID_FLOGI) {
				/* drop non-FIP LOGO */
				kfree_skb(skb);
				return;
			}
			break;
		}
	}

	if (fh->fh_r_ctl == FC_RCTL_BA_ABTS) {
		/* Drop incoming ABTS */
		kfree_skb(skb);
		return;
	}

	/*
	 * If the destination ID from the frame header does not match what we
	 * have on record for lport and the search for a NPIV port came up
	 * empty then this is not addressed to our port so simply drop it.
	 */
	if (lport->port_id != ntoh24(fh->fh_d_id) && !vn_port) {
		BNX2FC_HBA_DBG(lport, "Dropping frame due to destination mismatch: lport->port_id=%x fh->d_id=%x.\n",
		    lport->port_id, ntoh24(fh->fh_d_id));
		kfree_skb(skb);
		return;
	}

	stats = per_cpu_ptr(lport->stats, smp_processor_id());
	stats->RxFrames++;
	stats->RxWords += fr_len / FCOE_WORD_TO_BYTE;

	if (le32_to_cpu(fr_crc(fp)) !=
			~crc32(~0, skb->data, fr_len)) {
		if (stats->InvalidCRCCount < 5)
			printk(KERN_WARNING PFX "dropping frame with "
			       "CRC error\n");
		stats->InvalidCRCCount++;
		kfree_skb(skb);
		return;
	}
	fc_exch_recv(lport, fp);
}

/**
 * bnx2fc_percpu_io_thread - thread per cpu for ios
 *
 * @arg:	ptr to bnx2fc_percpu_info structure
 */
static int bnx2fc_percpu_io_thread(void *arg)
{
	struct bnx2fc_percpu_s *p = arg;
	struct bnx2fc_work *work, *tmp;
	LIST_HEAD(work_list);

	set_user_nice(current, MIN_NICE);
	set_current_state(TASK_INTERRUPTIBLE);
	while (!kthread_should_stop()) {
		schedule();
		spin_lock_bh(&p->fp_work_lock);
		while (!list_empty(&p->work_list)) {
			list_splice_init(&p->work_list, &work_list);
			spin_unlock_bh(&p->fp_work_lock);

			list_for_each_entry_safe(work, tmp, &work_list, list) {
				list_del_init(&work->list);
				bnx2fc_process_cq_compl(work->tgt, work->wqe);
				kfree(work);
			}

			spin_lock_bh(&p->fp_work_lock);
		}
		__set_current_state(TASK_INTERRUPTIBLE);
		spin_unlock_bh(&p->fp_work_lock);
	}
	__set_current_state(TASK_RUNNING);

	return 0;
}

static struct fc_host_statistics *bnx2fc_get_host_stats(struct Scsi_Host *shost)
{
	struct fc_host_statistics *bnx2fc_stats;
	struct fc_lport *lport = shost_priv(shost);
	struct fcoe_port *port = lport_priv(lport);
	struct bnx2fc_interface *interface = port->priv;
	struct bnx2fc_hba *hba = interface->hba;
	struct fcoe_statistics_params *fw_stats;
	int rc = 0;

	fw_stats = (struct fcoe_statistics_params *)hba->stats_buffer;
	if (!fw_stats)
		return NULL;

	mutex_lock(&hba->hba_stats_mutex);

	bnx2fc_stats = fc_get_host_stats(shost);

	init_completion(&hba->stat_req_done);
	if (bnx2fc_send_stat_req(hba))
		goto unlock_stats_mutex;
	rc = wait_for_completion_timeout(&hba->stat_req_done, (2 * HZ));
	if (!rc) {
		BNX2FC_HBA_DBG(lport, "FW stat req timed out\n");
		goto unlock_stats_mutex;
	}
	BNX2FC_STATS(hba, rx_stat2, fc_crc_cnt);
	bnx2fc_stats->invalid_crc_count += hba->bfw_stats.fc_crc_cnt;
	BNX2FC_STATS(hba, tx_stat, fcoe_tx_pkt_cnt);
	bnx2fc_stats->tx_frames += hba->bfw_stats.fcoe_tx_pkt_cnt;
	BNX2FC_STATS(hba, tx_stat, fcoe_tx_byte_cnt);
	bnx2fc_stats->tx_words += ((hba->bfw_stats.fcoe_tx_byte_cnt) / 4);
	BNX2FC_STATS(hba, rx_stat0, fcoe_rx_pkt_cnt);
	bnx2fc_stats->rx_frames += hba->bfw_stats.fcoe_rx_pkt_cnt;
	BNX2FC_STATS(hba, rx_stat0, fcoe_rx_byte_cnt);
	bnx2fc_stats->rx_words += ((hba->bfw_stats.fcoe_rx_byte_cnt) / 4);

	bnx2fc_stats->dumped_frames = 0;
	bnx2fc_stats->lip_count = 0;
	bnx2fc_stats->nos_count = 0;
	bnx2fc_stats->loss_of_sync_count = 0;
	bnx2fc_stats->loss_of_signal_count = 0;
	bnx2fc_stats->prim_seq_protocol_err_count = 0;

	memcpy(&hba->prev_stats, hba->stats_buffer,
	       sizeof(struct fcoe_statistics_params));

unlock_stats_mutex:
	mutex_unlock(&hba->hba_stats_mutex);
	return bnx2fc_stats;
}

static int bnx2fc_shost_config(struct fc_lport *lport, struct device *dev)
{
	struct fcoe_port *port = lport_priv(lport);
	struct bnx2fc_interface *interface = port->priv;
	struct bnx2fc_hba *hba = interface->hba;
	struct Scsi_Host *shost = lport->host;
	int rc = 0;

	shost->max_cmd_len = BNX2FC_MAX_CMD_LEN;
	shost->max_lun = bnx2fc_max_luns;
	shost->max_id = BNX2FC_MAX_FCP_TGT;
	shost->max_channel = 0;
	if (lport->vport)
		shost->transportt = bnx2fc_vport_xport_template;
	else
		shost->transportt = bnx2fc_transport_template;

	/* Add the new host to SCSI-ml */
	rc = scsi_add_host(lport->host, dev);
	if (rc) {
		printk(KERN_ERR PFX "Error on scsi_add_host\n");
		return rc;
	}
	if (!lport->vport)
		fc_host_max_npiv_vports(lport->host) = USHRT_MAX;
	snprintf(fc_host_symbolic_name(lport->host), 256,
		 "%s (QLogic %s) v%s over %s",
		BNX2FC_NAME, hba->chip_num, BNX2FC_VERSION,
		interface->netdev->name);

	return 0;
}

static int bnx2fc_link_ok(struct fc_lport *lport)
{
	struct fcoe_port *port = lport_priv(lport);
	struct bnx2fc_interface *interface = port->priv;
	struct bnx2fc_hba *hba = interface->hba;
	struct net_device *dev = hba->phys_dev;
	int rc = 0;

	if ((dev->flags & IFF_UP) && netif_carrier_ok(dev))
		clear_bit(ADAPTER_STATE_LINK_DOWN, &hba->adapter_state);
	else {
		set_bit(ADAPTER_STATE_LINK_DOWN, &hba->adapter_state);
		rc = -1;
	}
	return rc;
}

/**
 * bnx2fc_get_link_state - get network link state
 *
 * @hba:	adapter instance pointer
 *
 * updates adapter structure flag based on netdev state
 */
void bnx2fc_get_link_state(struct bnx2fc_hba *hba)
{
	if (test_bit(__LINK_STATE_NOCARRIER, &hba->phys_dev->state))
		set_bit(ADAPTER_STATE_LINK_DOWN, &hba->adapter_state);
	else
		clear_bit(ADAPTER_STATE_LINK_DOWN, &hba->adapter_state);
}

static int bnx2fc_net_config(struct fc_lport *lport, struct net_device *netdev)
{
	struct bnx2fc_hba *hba;
	struct bnx2fc_interface *interface;
	struct fcoe_ctlr *ctlr;
	struct fcoe_port *port;
	u64 wwnn, wwpn;

	port = lport_priv(lport);
	interface = port->priv;
	ctlr = bnx2fc_to_ctlr(interface);
	hba = interface->hba;

	/* require support for get_pauseparam ethtool op. */
	if (!hba->phys_dev->ethtool_ops ||
	    !hba->phys_dev->ethtool_ops->get_pauseparam)
		return -EOPNOTSUPP;

	if (fc_set_mfs(lport, BNX2FC_MFS))
		return -EINVAL;

	skb_queue_head_init(&port->fcoe_pending_queue);
	port->fcoe_pending_queue_active = 0;
	timer_setup(&port->timer, fcoe_queue_timer, 0);

	fcoe_link_speed_update(lport);

	if (!lport->vport) {
		if (fcoe_get_wwn(netdev, &wwnn, NETDEV_FCOE_WWNN))
			wwnn = fcoe_wwn_from_mac(ctlr->ctl_src_addr,
						 1, 0);
		BNX2FC_HBA_DBG(lport, "WWNN = 0x%llx\n", wwnn);
		fc_set_wwnn(lport, wwnn);

		if (fcoe_get_wwn(netdev, &wwpn, NETDEV_FCOE_WWPN))
			wwpn = fcoe_wwn_from_mac(ctlr->ctl_src_addr,
						 2, 0);

		BNX2FC_HBA_DBG(lport, "WWPN = 0x%llx\n", wwpn);
		fc_set_wwpn(lport, wwpn);
	}

	return 0;
}

static void bnx2fc_destroy_timer(struct timer_list *t)
{
	struct bnx2fc_hba *hba = from_timer(hba, t, destroy_timer);

	printk(KERN_ERR PFX "ERROR:bnx2fc_destroy_timer - "
	       "Destroy compl not received!!\n");
	set_bit(BNX2FC_FLAG_DESTROY_CMPL, &hba->flags);
	wake_up_interruptible(&hba->destroy_wait);
}

/**
 * bnx2fc_indicate_netevent - Generic netdev event handler
 *
 * @context:	adapter structure pointer
 * @event:	event type
 * @vlan_id:	vlan id - associated vlan id with this event
 *
 * Handles NETDEV_UP, NETDEV_DOWN, NETDEV_GOING_DOWN,NETDEV_CHANGE and
 * NETDEV_CHANGE_MTU events. Handle NETDEV_UNREGISTER only for vlans.
 */
static void bnx2fc_indicate_netevent(void *context, unsigned long event,
				     u16 vlan_id)
{
	struct bnx2fc_hba *hba = (struct bnx2fc_hba *)context;
	struct fcoe_ctlr_device *cdev;
	struct fc_lport *lport;
	struct fc_lport *vport;
	struct bnx2fc_interface *interface, *tmp;
	struct fcoe_ctlr *ctlr;
	int wait_for_upload = 0;
	u32 link_possible = 1;

	if (vlan_id != 0 && event != NETDEV_UNREGISTER)
		return;

	switch (event) {
	case NETDEV_UP:
		if (!test_bit(ADAPTER_STATE_UP, &hba->adapter_state))
			printk(KERN_ERR "indicate_netevent: "\
					"hba is not UP!!\n");
		break;

	case NETDEV_DOWN:
		clear_bit(ADAPTER_STATE_GOING_DOWN, &hba->adapter_state);
		clear_bit(ADAPTER_STATE_UP, &hba->adapter_state);
		link_possible = 0;
		break;

	case NETDEV_GOING_DOWN:
		set_bit(ADAPTER_STATE_GOING_DOWN, &hba->adapter_state);
		link_possible = 0;
		break;

	case NETDEV_CHANGE:
		break;

	case NETDEV_UNREGISTER:
		if (!vlan_id)
			return;
		mutex_lock(&bnx2fc_dev_lock);
		list_for_each_entry_safe(interface, tmp, &if_list, list) {
			if (interface->hba == hba &&
			    interface->vlan_id == (vlan_id & VLAN_VID_MASK))
				__bnx2fc_destroy(interface);
		}
		mutex_unlock(&bnx2fc_dev_lock);

		/* Ensure ALL destroy work has been completed before return */
		flush_workqueue(bnx2fc_wq);
		return;

	default:
		return;
	}

	mutex_lock(&bnx2fc_dev_lock);
	list_for_each_entry(interface, &if_list, list) {

		if (interface->hba != hba)
			continue;

		ctlr = bnx2fc_to_ctlr(interface);
		lport = ctlr->lp;
		BNX2FC_HBA_DBG(lport, "netevent handler - event=%s %ld\n",
				interface->netdev->name, event);

		fcoe_link_speed_update(lport);

		cdev = fcoe_ctlr_to_ctlr_dev(ctlr);

		if (link_possible && !bnx2fc_link_ok(lport)) {
			switch (cdev->enabled) {
			case FCOE_CTLR_DISABLED:
				pr_info("Link up while interface is disabled.\n");
				break;
			case FCOE_CTLR_ENABLED:
			case FCOE_CTLR_UNUSED:
				/* Reset max recv frame size to default */
				fc_set_mfs(lport, BNX2FC_MFS);
				/*
				 * ctlr link up will only be handled during
				 * enable to avoid sending discovery
				 * solicitation on a stale vlan
				 */
				if (interface->enabled)
					fcoe_ctlr_link_up(ctlr);
			};
		} else if (fcoe_ctlr_link_down(ctlr)) {
			switch (cdev->enabled) {
			case FCOE_CTLR_DISABLED:
				pr_info("Link down while interface is disabled.\n");
				break;
			case FCOE_CTLR_ENABLED:
			case FCOE_CTLR_UNUSED:
				mutex_lock(&lport->lp_mutex);
				list_for_each_entry(vport, &lport->vports, list)
					fc_host_port_type(vport->host) =
					FC_PORTTYPE_UNKNOWN;
				mutex_unlock(&lport->lp_mutex);
				fc_host_port_type(lport->host) =
					FC_PORTTYPE_UNKNOWN;
				per_cpu_ptr(lport->stats,
					    get_cpu())->LinkFailureCount++;
				put_cpu();
				fcoe_clean_pending_queue(lport);
				wait_for_upload = 1;
			};
		}
	}
	mutex_unlock(&bnx2fc_dev_lock);

	if (wait_for_upload) {
		clear_bit(ADAPTER_STATE_READY, &hba->adapter_state);
		init_waitqueue_head(&hba->shutdown_wait);
		BNX2FC_MISC_DBG("indicate_netevent "
				"num_ofld_sess = %d\n",
				hba->num_ofld_sess);
		hba->wait_for_link_down = 1;
		wait_event_interruptible(hba->shutdown_wait,
					 (hba->num_ofld_sess == 0));
		BNX2FC_MISC_DBG("wakeup - num_ofld_sess = %d\n",
				hba->num_ofld_sess);
		hba->wait_for_link_down = 0;

		if (signal_pending(current))
			flush_signals(current);
	}
}

static int bnx2fc_libfc_config(struct fc_lport *lport)
{

	/* Set the function pointers set by bnx2fc driver */
	memcpy(&lport->tt, &bnx2fc_libfc_fcn_templ,
		sizeof(struct libfc_function_template));
	fc_elsct_init(lport);
	fc_exch_init(lport);
	fc_disc_init(lport);
	fc_disc_config(lport, lport);
	return 0;
}

static int bnx2fc_em_config(struct fc_lport *lport, struct bnx2fc_hba *hba)
{
	int fcoe_min_xid, fcoe_max_xid;

	fcoe_min_xid = hba->max_xid + 1;
	if (nr_cpu_ids <= 2)
		fcoe_max_xid = hba->max_xid + FCOE_XIDS_PER_CPU_OFFSET;
	else
		fcoe_max_xid = hba->max_xid + FCOE_MAX_XID_OFFSET;
	if (!fc_exch_mgr_alloc(lport, FC_CLASS_3, fcoe_min_xid,
			       fcoe_max_xid, NULL)) {
		printk(KERN_ERR PFX "em_config:fc_exch_mgr_alloc failed\n");
		return -ENOMEM;
	}

	return 0;
}

static int bnx2fc_lport_config(struct fc_lport *lport)
{
	lport->link_up = 0;
	lport->qfull = 0;
	lport->max_retry_count = BNX2FC_MAX_RETRY_CNT;
	lport->max_rport_retry_count = BNX2FC_MAX_RPORT_RETRY_CNT;
	lport->e_d_tov = 2 * 1000;
	lport->r_a_tov = 10 * 1000;

	lport->service_params = (FCP_SPPF_INIT_FCN | FCP_SPPF_RD_XRDY_DIS |
				FCP_SPPF_RETRY | FCP_SPPF_CONF_COMPL);
	lport->does_npiv = 1;

	memset(&lport->rnid_gen, 0, sizeof(struct fc_els_rnid_gen));
	lport->rnid_gen.rnid_atype = BNX2FC_RNID_HBA;

	/* alloc stats structure */
	if (fc_lport_init_stats(lport))
		return -ENOMEM;

	/* Finish fc_lport configuration */
	fc_lport_config(lport);

	return 0;
}

/**
 * bnx2fc_fip_recv - handle a received FIP frame.
 *
 * @skb: the received skb
 * @dev: associated &net_device
 * @ptype: the &packet_type structure which was used to register this handler.
 * @orig_dev: original receive &net_device, in case @ dev is a bond.
 *
 * Returns: 0 for success
 */
static int bnx2fc_fip_recv(struct sk_buff *skb, struct net_device *dev,
			   struct packet_type *ptype,
			   struct net_device *orig_dev)
{
	struct bnx2fc_interface *interface;
	struct fcoe_ctlr *ctlr;
	interface = container_of(ptype, struct bnx2fc_interface,
				 fip_packet_type);
	ctlr = bnx2fc_to_ctlr(interface);
	fcoe_ctlr_recv(ctlr, skb);
	return 0;
}

/**
 * bnx2fc_update_src_mac - Update Ethernet MAC filters.
 *
 * @fip: FCoE controller.
 * @old: Unicast MAC address to delete if the MAC is non-zero.
 * @new: Unicast MAC address to add.
 *
 * Remove any previously-set unicast MAC filter.
 * Add secondary FCoE MAC address filter for our OUI.
 */
static void bnx2fc_update_src_mac(struct fc_lport *lport, u8 *addr)
{
	struct fcoe_port *port = lport_priv(lport);

	memcpy(port->data_src_addr, addr, ETH_ALEN);
}

/**
 * bnx2fc_get_src_mac - return the ethernet source address for an lport
 *
 * @lport: libfc port
 */
static u8 *bnx2fc_get_src_mac(struct fc_lport *lport)
{
	struct fcoe_port *port;

	port = (struct fcoe_port *)lport_priv(lport);
	return port->data_src_addr;
}

/**
 * bnx2fc_fip_send - send an Ethernet-encapsulated FIP frame.
 *
 * @fip: FCoE controller.
 * @skb: FIP Packet.
 */
static void bnx2fc_fip_send(struct fcoe_ctlr *fip, struct sk_buff *skb)
{
	struct fip_header *fiph;
	struct ethhdr *eth_hdr;
	u16 op;
	u8 sub;

	fiph = (struct fip_header *) ((void *)skb->data + 2 * ETH_ALEN + 2);
	eth_hdr = (struct ethhdr *)skb_mac_header(skb);
	op = ntohs(fiph->fip_op);
	sub = fiph->fip_subcode;

	if (op == FIP_OP_CTRL && sub == FIP_SC_SOL && bnx2fc_log_fka)
		BNX2FC_MISC_DBG("Sending FKA from %pM to %pM.\n",
		    eth_hdr->h_source, eth_hdr->h_dest);

	skb->dev = bnx2fc_from_ctlr(fip)->netdev;
	dev_queue_xmit(skb);
}

static int bnx2fc_vport_create(struct fc_vport *vport, bool disabled)
{
	struct Scsi_Host *shost = vport_to_shost(vport);
	struct fc_lport *n_port = shost_priv(shost);
	struct fcoe_port *port = lport_priv(n_port);
	struct bnx2fc_interface *interface = port->priv;
	struct net_device *netdev = interface->netdev;
	struct fc_lport *vn_port;
	int rc;
	char buf[32];

	rc = fcoe_validate_vport_create(vport);
	if (rc) {
		fcoe_wwn_to_str(vport->port_name, buf, sizeof(buf));
		printk(KERN_ERR PFX "Failed to create vport, "
		       "WWPN (0x%s) already exists\n",
		       buf);
		return rc;
	}

	if (!test_bit(BNX2FC_FLAG_FW_INIT_DONE, &interface->hba->flags)) {
		printk(KERN_ERR PFX "vn ports cannot be created on"
			"this interface\n");
		return -EIO;
	}
	rtnl_lock();
	mutex_lock(&bnx2fc_dev_lock);
	vn_port = bnx2fc_if_create(interface, &vport->dev, 1);
	mutex_unlock(&bnx2fc_dev_lock);
	rtnl_unlock();

	if (!vn_port) {
		printk(KERN_ERR PFX "bnx2fc_vport_create (%s) failed\n",
			netdev->name);
		return -EIO;
	}

	if (bnx2fc_devloss_tmo)
		fc_host_dev_loss_tmo(vn_port->host) = bnx2fc_devloss_tmo;

	if (disabled) {
		fc_vport_set_state(vport, FC_VPORT_DISABLED);
	} else {
		vn_port->boot_time = jiffies;
		fc_lport_init(vn_port);
		fc_fabric_login(vn_port);
		fc_vport_setlink(vn_port);
	}
	return 0;
}

static void bnx2fc_free_vport(struct bnx2fc_hba *hba, struct fc_lport *lport)
{
	struct bnx2fc_lport *blport, *tmp;

	spin_lock_bh(&hba->hba_lock);
	list_for_each_entry_safe(blport, tmp, &hba->vports, list) {
		if (blport->lport == lport) {
			list_del(&blport->list);
			kfree(blport);
		}
	}
	spin_unlock_bh(&hba->hba_lock);
}

static int bnx2fc_vport_destroy(struct fc_vport *vport)
{
	struct Scsi_Host *shost = vport_to_shost(vport);
	struct fc_lport *n_port = shost_priv(shost);
	struct fc_lport *vn_port = vport->dd_data;
	struct fcoe_port *port = lport_priv(vn_port);
	struct bnx2fc_interface *interface = port->priv;
	struct fc_lport *v_port;
	bool found = false;

	mutex_lock(&n_port->lp_mutex);
	list_for_each_entry(v_port, &n_port->vports, list)
		if (v_port->vport == vport) {
			found = true;
			break;
		}

	if (!found) {
		mutex_unlock(&n_port->lp_mutex);
		return -ENOENT;
	}
	list_del(&vn_port->list);
	mutex_unlock(&n_port->lp_mutex);
	bnx2fc_free_vport(interface->hba, port->lport);
	bnx2fc_port_shutdown(port->lport);
	bnx2fc_interface_put(interface);
	queue_work(bnx2fc_wq, &port->destroy_work);
	return 0;
}

static int bnx2fc_vport_disable(struct fc_vport *vport, bool disable)
{
	struct fc_lport *lport = vport->dd_data;

	if (disable) {
		fc_vport_set_state(vport, FC_VPORT_DISABLED);
		fc_fabric_logoff(lport);
	} else {
		lport->boot_time = jiffies;
		fc_fabric_login(lport);
		fc_vport_setlink(lport);
	}
	return 0;
}


static int bnx2fc_interface_setup(struct bnx2fc_interface *interface)
{
	struct net_device *netdev = interface->netdev;
	struct net_device *physdev = interface->hba->phys_dev;
	struct fcoe_ctlr *ctlr = bnx2fc_to_ctlr(interface);
	struct netdev_hw_addr *ha;
	int sel_san_mac = 0;

	/* setup Source MAC Address */
	rcu_read_lock();
	for_each_dev_addr(physdev, ha) {
		BNX2FC_MISC_DBG("net_config: ha->type = %d, fip_mac = ",
				ha->type);
		printk(KERN_INFO "%2x:%2x:%2x:%2x:%2x:%2x\n", ha->addr[0],
				ha->addr[1], ha->addr[2], ha->addr[3],
				ha->addr[4], ha->addr[5]);

		if ((ha->type == NETDEV_HW_ADDR_T_SAN) &&
		    (is_valid_ether_addr(ha->addr))) {
			memcpy(ctlr->ctl_src_addr, ha->addr,
			       ETH_ALEN);
			sel_san_mac = 1;
			BNX2FC_MISC_DBG("Found SAN MAC\n");
		}
	}
	rcu_read_unlock();

	if (!sel_san_mac)
		return -ENODEV;

	interface->fip_packet_type.func = bnx2fc_fip_recv;
	interface->fip_packet_type.type = htons(ETH_P_FIP);
	interface->fip_packet_type.dev = netdev;
	dev_add_pack(&interface->fip_packet_type);

	interface->fcoe_packet_type.func = bnx2fc_rcv;
	interface->fcoe_packet_type.type = __constant_htons(ETH_P_FCOE);
	interface->fcoe_packet_type.dev = netdev;
	dev_add_pack(&interface->fcoe_packet_type);

	return 0;
}

static int bnx2fc_attach_transport(void)
{
	bnx2fc_transport_template =
		fc_attach_transport(&bnx2fc_transport_function);

	if (bnx2fc_transport_template == NULL) {
		printk(KERN_ERR PFX "Failed to attach FC transport\n");
		return -ENODEV;
	}

	bnx2fc_vport_xport_template =
		fc_attach_transport(&bnx2fc_vport_xport_function);
	if (bnx2fc_vport_xport_template == NULL) {
		printk(KERN_ERR PFX
		       "Failed to attach FC transport for vport\n");
		fc_release_transport(bnx2fc_transport_template);
		bnx2fc_transport_template = NULL;
		return -ENODEV;
	}
	return 0;
}
static void bnx2fc_release_transport(void)
{
	fc_release_transport(bnx2fc_transport_template);
	fc_release_transport(bnx2fc_vport_xport_template);
	bnx2fc_transport_template = NULL;
	bnx2fc_vport_xport_template = NULL;
}

static void bnx2fc_interface_release(struct kref *kref)
{
	struct fcoe_ctlr_device *ctlr_dev;
	struct bnx2fc_interface *interface;
	struct fcoe_ctlr *ctlr;
	struct net_device *netdev;

	interface = container_of(kref, struct bnx2fc_interface, kref);
	BNX2FC_MISC_DBG("Interface is being released\n");

	ctlr = bnx2fc_to_ctlr(interface);
	ctlr_dev = fcoe_ctlr_to_ctlr_dev(ctlr);
	netdev = interface->netdev;

	/* tear-down FIP controller */
	if (test_and_clear_bit(BNX2FC_CTLR_INIT_DONE, &interface->if_flags))
		fcoe_ctlr_destroy(ctlr);

	fcoe_ctlr_device_delete(ctlr_dev);

	dev_put(netdev);
	module_put(THIS_MODULE);
}

static inline void bnx2fc_interface_get(struct bnx2fc_interface *interface)
{
	kref_get(&interface->kref);
}

static inline void bnx2fc_interface_put(struct bnx2fc_interface *interface)
{
	kref_put(&interface->kref, bnx2fc_interface_release);
}
static void bnx2fc_hba_destroy(struct bnx2fc_hba *hba)
{
	/* Free the command manager */
	if (hba->cmd_mgr) {
		bnx2fc_cmd_mgr_free(hba->cmd_mgr);
		hba->cmd_mgr = NULL;
	}
	kfree(hba->tgt_ofld_list);
	bnx2fc_unbind_pcidev(hba);
	kfree(hba);
}

/**
 * bnx2fc_hba_create - create a new bnx2fc hba
 *
 * @cnic:	pointer to cnic device
 *
 * Creates a new FCoE hba on the given device.
 *
 */
static struct bnx2fc_hba *bnx2fc_hba_create(struct cnic_dev *cnic)
{
	struct bnx2fc_hba *hba;
	struct fcoe_capabilities *fcoe_cap;
	int rc;

	hba = kzalloc(sizeof(*hba), GFP_KERNEL);
	if (!hba) {
		printk(KERN_ERR PFX "Unable to allocate hba structure\n");
		return NULL;
	}
	spin_lock_init(&hba->hba_lock);
	mutex_init(&hba->hba_mutex);
	mutex_init(&hba->hba_stats_mutex);

	hba->cnic = cnic;

	hba->max_tasks = cnic->max_fcoe_exchanges;
	hba->elstm_xids = (hba->max_tasks / 2);
	hba->max_outstanding_cmds = hba->elstm_xids;
	hba->max_xid = (hba->max_tasks - 1);

	rc = bnx2fc_bind_pcidev(hba);
	if (rc) {
		printk(KERN_ERR PFX "create_adapter:  bind error\n");
		goto bind_err;
	}
	hba->phys_dev = cnic->netdev;
	hba->next_conn_id = 0;

	hba->tgt_ofld_list =
		kcalloc(BNX2FC_NUM_MAX_SESS, sizeof(struct bnx2fc_rport *),
			GFP_KERNEL);
	if (!hba->tgt_ofld_list) {
		printk(KERN_ERR PFX "Unable to allocate tgt offload list\n");
		goto tgtofld_err;
	}

	hba->num_ofld_sess = 0;

	hba->cmd_mgr = bnx2fc_cmd_mgr_alloc(hba);
	if (!hba->cmd_mgr) {
		printk(KERN_ERR PFX "em_config:bnx2fc_cmd_mgr_alloc failed\n");
		goto cmgr_err;
	}
	fcoe_cap = &hba->fcoe_cap;

	fcoe_cap->capability1 = BNX2FC_TM_MAX_SQES <<
					FCOE_IOS_PER_CONNECTION_SHIFT;
	fcoe_cap->capability1 |= BNX2FC_NUM_MAX_SESS <<
					FCOE_LOGINS_PER_PORT_SHIFT;
	fcoe_cap->capability2 = hba->max_outstanding_cmds <<
					FCOE_NUMBER_OF_EXCHANGES_SHIFT;
	fcoe_cap->capability2 |= BNX2FC_MAX_NPIV <<
					FCOE_NPIV_WWN_PER_PORT_SHIFT;
	fcoe_cap->capability3 = BNX2FC_NUM_MAX_SESS <<
					FCOE_TARGETS_SUPPORTED_SHIFT;
	fcoe_cap->capability3 |= hba->max_outstanding_cmds <<
					FCOE_OUTSTANDING_COMMANDS_SHIFT;
	fcoe_cap->capability4 = FCOE_CAPABILITY4_STATEFUL;

	init_waitqueue_head(&hba->shutdown_wait);
	init_waitqueue_head(&hba->destroy_wait);
	INIT_LIST_HEAD(&hba->vports);

	return hba;

cmgr_err:
	kfree(hba->tgt_ofld_list);
tgtofld_err:
	bnx2fc_unbind_pcidev(hba);
bind_err:
	kfree(hba);
	return NULL;
}

static struct bnx2fc_interface *
bnx2fc_interface_create(struct bnx2fc_hba *hba,
			struct net_device *netdev,
			enum fip_mode fip_mode)
{
	struct fcoe_ctlr_device *ctlr_dev;
	struct bnx2fc_interface *interface;
	struct fcoe_ctlr *ctlr;
	int size;
	int rc = 0;

	size = (sizeof(*interface) + sizeof(struct fcoe_ctlr));
	ctlr_dev = fcoe_ctlr_device_add(&netdev->dev, &bnx2fc_fcoe_sysfs_templ,
					 size);
	if (!ctlr_dev) {
		printk(KERN_ERR PFX "Unable to allocate interface structure\n");
		return NULL;
	}
	ctlr = fcoe_ctlr_device_priv(ctlr_dev);
	ctlr->cdev = ctlr_dev;
	interface = fcoe_ctlr_priv(ctlr);
	dev_hold(netdev);
	kref_init(&interface->kref);
	interface->hba = hba;
	interface->netdev = netdev;

	/* Initialize FIP */
	fcoe_ctlr_init(ctlr, fip_mode);
	ctlr->send = bnx2fc_fip_send;
	ctlr->update_mac = bnx2fc_update_src_mac;
	ctlr->get_src_addr = bnx2fc_get_src_mac;
	set_bit(BNX2FC_CTLR_INIT_DONE, &interface->if_flags);

	rc = bnx2fc_interface_setup(interface);
	if (!rc)
		return interface;

	fcoe_ctlr_destroy(ctlr);
	dev_put(netdev);
	fcoe_ctlr_device_delete(ctlr_dev);
	return NULL;
}

/**
 * bnx2fc_if_create - Create FCoE instance on a given interface
 *
 * @interface:	FCoE interface to create a local port on
 * @parent:	Device pointer to be the parent in sysfs for the SCSI host
 * @npiv:	Indicates if the port is vport or not
 *
 * Creates a fc_lport instance and a Scsi_Host instance and configure them.
 *
 * Returns:	Allocated fc_lport or an error pointer
 */
static struct fc_lport *bnx2fc_if_create(struct bnx2fc_interface *interface,
				  struct device *parent, int npiv)
{
	struct fcoe_ctlr        *ctlr = bnx2fc_to_ctlr(interface);
	struct fc_lport		*lport, *n_port;
	struct fcoe_port	*port;
	struct Scsi_Host	*shost;
	struct fc_vport		*vport = dev_to_vport(parent);
	struct bnx2fc_lport	*blport;
	struct bnx2fc_hba	*hba = interface->hba;
	int			rc = 0;

	blport = kzalloc(sizeof(struct bnx2fc_lport), GFP_KERNEL);
	if (!blport) {
		BNX2FC_HBA_DBG(ctlr->lp, "Unable to alloc blport\n");
		return NULL;
	}

	/* Allocate Scsi_Host structure */
	bnx2fc_shost_template.can_queue = hba->max_outstanding_cmds;
	if (!npiv)
		lport = libfc_host_alloc(&bnx2fc_shost_template, sizeof(*port));
	else
		lport = libfc_vport_create(vport, sizeof(*port));

	if (!lport) {
		printk(KERN_ERR PFX "could not allocate scsi host structure\n");
		goto free_blport;
	}
	shost = lport->host;
	port = lport_priv(lport);
	port->lport = lport;
	port->priv = interface;
	port->get_netdev = bnx2fc_netdev;
	INIT_WORK(&port->destroy_work, bnx2fc_destroy_work);

	/* Configure fcoe_port */
	rc = bnx2fc_lport_config(lport);
	if (rc)
		goto lp_config_err;

	if (npiv) {
		printk(KERN_ERR PFX "Setting vport names, 0x%llX 0x%llX\n",
			vport->node_name, vport->port_name);
		fc_set_wwnn(lport, vport->node_name);
		fc_set_wwpn(lport, vport->port_name);
	}
	/* Configure netdev and networking properties of the lport */
	rc = bnx2fc_net_config(lport, interface->netdev);
	if (rc) {
		printk(KERN_ERR PFX "Error on bnx2fc_net_config\n");
		goto lp_config_err;
	}

	rc = bnx2fc_shost_config(lport, parent);
	if (rc) {
		printk(KERN_ERR PFX "Couldn't configure shost for %s\n",
			interface->netdev->name);
		goto lp_config_err;
	}

	/* Initialize the libfc library */
	rc = bnx2fc_libfc_config(lport);
	if (rc) {
		printk(KERN_ERR PFX "Couldn't configure libfc\n");
		goto shost_err;
	}
	fc_host_port_type(lport->host) = FC_PORTTYPE_UNKNOWN;

	if (bnx2fc_devloss_tmo)
		fc_host_dev_loss_tmo(shost) = bnx2fc_devloss_tmo;

	/* Allocate exchange manager */
	if (!npiv)
		rc = bnx2fc_em_config(lport, hba);
	else {
		shost = vport_to_shost(vport);
		n_port = shost_priv(shost);
		rc = fc_exch_mgr_list_clone(n_port, lport);
	}

	if (rc) {
		printk(KERN_ERR PFX "Error on bnx2fc_em_config\n");
		goto shost_err;
	}

	bnx2fc_interface_get(interface);

	spin_lock_bh(&hba->hba_lock);
	blport->lport = lport;
	list_add_tail(&blport->list, &hba->vports);
	spin_unlock_bh(&hba->hba_lock);

	return lport;

shost_err:
	scsi_remove_host(shost);
lp_config_err:
	scsi_host_put(lport->host);
free_blport:
	kfree(blport);
	return NULL;
}

static void bnx2fc_net_cleanup(struct bnx2fc_interface *interface)
{
	/* Dont listen for Ethernet packets anymore */
	__dev_remove_pack(&interface->fcoe_packet_type);
	__dev_remove_pack(&interface->fip_packet_type);
	synchronize_net();
}

static void bnx2fc_interface_cleanup(struct bnx2fc_interface *interface)
{
	struct fcoe_ctlr *ctlr = bnx2fc_to_ctlr(interface);
	struct fc_lport *lport = ctlr->lp;
	struct fcoe_port *port = lport_priv(lport);
	struct bnx2fc_hba *hba = interface->hba;

	/* Stop the transmit retry timer */
	del_timer_sync(&port->timer);

	/* Free existing transmit skbs */
	fcoe_clean_pending_queue(lport);

	bnx2fc_net_cleanup(interface);

	bnx2fc_free_vport(hba, lport);
}

static void bnx2fc_if_destroy(struct fc_lport *lport)
{

	/* Free queued packets for the receive thread */
	bnx2fc_clean_rx_queue(lport);

	/* Detach from scsi-ml */
	fc_remove_host(lport->host);
	scsi_remove_host(lport->host);

	/*
	 * Note that only the physical lport will have the exchange manager.
	 * for vports, this function is NOP
	 */
	fc_exch_mgr_free(lport);

	/* Free memory used by statistical counters */
	fc_lport_free_stats(lport);

	/* Release Scsi_Host */
	scsi_host_put(lport->host);
}

static void __bnx2fc_destroy(struct bnx2fc_interface *interface)
{
	struct fcoe_ctlr *ctlr = bnx2fc_to_ctlr(interface);
	struct fc_lport *lport = ctlr->lp;
	struct fcoe_port *port = lport_priv(lport);

	bnx2fc_interface_cleanup(interface);
	bnx2fc_stop(interface);
	list_del(&interface->list);
	bnx2fc_interface_put(interface);
	queue_work(bnx2fc_wq, &port->destroy_work);
}

/**
 * bnx2fc_destroy - Destroy a bnx2fc FCoE interface
 *
 * @buffer: The name of the Ethernet interface to be destroyed
 * @kp:     The associated kernel parameter
 *
 * Called from sysfs.
 *
 * Returns: 0 for success
 */
static int bnx2fc_destroy(struct net_device *netdev)
{
	struct bnx2fc_interface *interface = NULL;
	struct workqueue_struct *timer_work_queue;
	struct fcoe_ctlr *ctlr;
	int rc = 0;

	rtnl_lock();
	mutex_lock(&bnx2fc_dev_lock);

	interface = bnx2fc_interface_lookup(netdev);
	ctlr = bnx2fc_to_ctlr(interface);
	if (!interface || !ctlr->lp) {
		rc = -ENODEV;
		printk(KERN_ERR PFX "bnx2fc_destroy: interface or lport not found\n");
		goto netdev_err;
	}

	timer_work_queue = interface->timer_work_queue;
	__bnx2fc_destroy(interface);
	destroy_workqueue(timer_work_queue);

netdev_err:
	mutex_unlock(&bnx2fc_dev_lock);
	rtnl_unlock();
	return rc;
}

static void bnx2fc_destroy_work(struct work_struct *work)
{
	struct fcoe_port *port;
	struct fc_lport *lport;

	port = container_of(work, struct fcoe_port, destroy_work);
	lport = port->lport;

	BNX2FC_HBA_DBG(lport, "Entered bnx2fc_destroy_work\n");

	bnx2fc_if_destroy(lport);
}

static void bnx2fc_unbind_adapter_devices(struct bnx2fc_hba *hba)
{
	bnx2fc_free_fw_resc(hba);
	bnx2fc_free_task_ctx(hba);
}

/**
 * bnx2fc_bind_adapter_devices - binds bnx2fc adapter with the associated
 *			pci structure
 *
 * @hba:		Adapter instance
 */
static int bnx2fc_bind_adapter_devices(struct bnx2fc_hba *hba)
{
	if (bnx2fc_setup_task_ctx(hba))
		goto mem_err;

	if (bnx2fc_setup_fw_resc(hba))
		goto mem_err;

	return 0;
mem_err:
	bnx2fc_unbind_adapter_devices(hba);
	return -ENOMEM;
}

static int bnx2fc_bind_pcidev(struct bnx2fc_hba *hba)
{
	struct cnic_dev *cnic;
	struct pci_dev *pdev;

	if (!hba->cnic) {
		printk(KERN_ERR PFX "cnic is NULL\n");
		return -ENODEV;
	}
	cnic = hba->cnic;
	pdev = hba->pcidev = cnic->pcidev;
	if (!hba->pcidev)
		return -ENODEV;

	switch (pdev->device) {
	case PCI_DEVICE_ID_NX2_57710:
		strncpy(hba->chip_num, "BCM57710", BCM_CHIP_LEN);
		break;
	case PCI_DEVICE_ID_NX2_57711:
		strncpy(hba->chip_num, "BCM57711", BCM_CHIP_LEN);
		break;
	case PCI_DEVICE_ID_NX2_57712:
	case PCI_DEVICE_ID_NX2_57712_MF:
	case PCI_DEVICE_ID_NX2_57712_VF:
		strncpy(hba->chip_num, "BCM57712", BCM_CHIP_LEN);
		break;
	case PCI_DEVICE_ID_NX2_57800:
	case PCI_DEVICE_ID_NX2_57800_MF:
	case PCI_DEVICE_ID_NX2_57800_VF:
		strncpy(hba->chip_num, "BCM57800", BCM_CHIP_LEN);
		break;
	case PCI_DEVICE_ID_NX2_57810:
	case PCI_DEVICE_ID_NX2_57810_MF:
	case PCI_DEVICE_ID_NX2_57810_VF:
		strncpy(hba->chip_num, "BCM57810", BCM_CHIP_LEN);
		break;
	case PCI_DEVICE_ID_NX2_57840:
	case PCI_DEVICE_ID_NX2_57840_MF:
	case PCI_DEVICE_ID_NX2_57840_VF:
	case PCI_DEVICE_ID_NX2_57840_2_20:
	case PCI_DEVICE_ID_NX2_57840_4_10:
		strncpy(hba->chip_num, "BCM57840", BCM_CHIP_LEN);
		break;
	default:
		pr_err(PFX "Unknown device id 0x%x\n", pdev->device);
		break;
	}
	pci_dev_get(hba->pcidev);
	return 0;
}

static void bnx2fc_unbind_pcidev(struct bnx2fc_hba *hba)
{
	if (hba->pcidev) {
		hba->chip_num[0] = '\0';
		pci_dev_put(hba->pcidev);
	}
	hba->pcidev = NULL;
}

/**
 * bnx2fc_ulp_get_stats - cnic callback to populate FCoE stats
 *
 * @handle:    transport handle pointing to adapter struture
 */
static int bnx2fc_ulp_get_stats(void *handle)
{
	struct bnx2fc_hba *hba = handle;
	struct cnic_dev *cnic;
	struct fcoe_stats_info *stats_addr;

	if (!hba)
		return -EINVAL;

	cnic = hba->cnic;
	stats_addr = &cnic->stats_addr->fcoe_stat;
	if (!stats_addr)
		return -EINVAL;

	strncpy(stats_addr->version, BNX2FC_VERSION,
		sizeof(stats_addr->version));
	stats_addr->txq_size = BNX2FC_SQ_WQES_MAX;
	stats_addr->rxq_size = BNX2FC_CQ_WQES_MAX;

	return 0;
}


/**
 * bnx2fc_ulp_start - cnic callback to initialize & start adapter instance
 *
 * @handle:	transport handle pointing to adapter structure
 *
 * This function maps adapter structure to pcidev structure and initiates
 *	firmware handshake to enable/initialize on-chip FCoE components.
 *	This bnx2fc - cnic interface api callback is used after following
 *	conditions are met -
 *	a) underlying network interface is up (marked by event NETDEV_UP
 *		from netdev
 *	b) bnx2fc adatper structure is registered.
 */
static void bnx2fc_ulp_start(void *handle)
{
	struct bnx2fc_hba *hba = handle;
	struct bnx2fc_interface *interface;
	struct fcoe_ctlr *ctlr;
	struct fc_lport *lport;

	mutex_lock(&bnx2fc_dev_lock);

	if (!test_bit(BNX2FC_FLAG_FW_INIT_DONE, &hba->flags))
		bnx2fc_fw_init(hba);

	BNX2FC_MISC_DBG("bnx2fc started.\n");

	list_for_each_entry(interface, &if_list, list) {
		if (interface->hba == hba) {
			ctlr = bnx2fc_to_ctlr(interface);
			lport = ctlr->lp;
			/* Kick off Fabric discovery*/
			printk(KERN_ERR PFX "ulp_init: start discovery\n");
			lport->tt.frame_send = bnx2fc_xmit;
			bnx2fc_start_disc(interface);
		}
	}

	mutex_unlock(&bnx2fc_dev_lock);
}

static void bnx2fc_port_shutdown(struct fc_lport *lport)
{
	BNX2FC_MISC_DBG("Entered %s\n", __func__);
	fc_fabric_logoff(lport);
	fc_lport_destroy(lport);
}

static void bnx2fc_stop(struct bnx2fc_interface *interface)
{
	struct fcoe_ctlr *ctlr = bnx2fc_to_ctlr(interface);
	struct fc_lport *lport;
	struct fc_lport *vport;

	if (!test_bit(BNX2FC_FLAG_FW_INIT_DONE, &interface->hba->flags))
		return;

	lport = ctlr->lp;
	bnx2fc_port_shutdown(lport);

	mutex_lock(&lport->lp_mutex);
	list_for_each_entry(vport, &lport->vports, list)
		fc_host_port_type(vport->host) =
					FC_PORTTYPE_UNKNOWN;
	mutex_unlock(&lport->lp_mutex);
	fc_host_port_type(lport->host) = FC_PORTTYPE_UNKNOWN;
	fcoe_ctlr_link_down(ctlr);
	fcoe_clean_pending_queue(lport);
}

static int bnx2fc_fw_init(struct bnx2fc_hba *hba)
{
#define BNX2FC_INIT_POLL_TIME		(1000 / HZ)
	int rc = -1;
	int i = HZ;

	rc = bnx2fc_bind_adapter_devices(hba);
	if (rc) {
		printk(KERN_ALERT PFX
			"bnx2fc_bind_adapter_devices failed - rc = %d\n", rc);
		goto err_out;
	}

	rc = bnx2fc_send_fw_fcoe_init_msg(hba);
	if (rc) {
		printk(KERN_ALERT PFX
			"bnx2fc_send_fw_fcoe_init_msg failed - rc = %d\n", rc);
		goto err_unbind;
	}

	/*
	 * Wait until the adapter init message is complete, and adapter
	 * state is UP.
	 */
	while (!test_bit(ADAPTER_STATE_UP, &hba->adapter_state) && i--)
		msleep(BNX2FC_INIT_POLL_TIME);

	if (!test_bit(ADAPTER_STATE_UP, &hba->adapter_state)) {
		printk(KERN_ERR PFX "bnx2fc_start: %s failed to initialize.  "
				"Ignoring...\n",
				hba->cnic->netdev->name);
		rc = -1;
		goto err_unbind;
	}


	set_bit(BNX2FC_FLAG_FW_INIT_DONE, &hba->flags);
	return 0;

err_unbind:
	bnx2fc_unbind_adapter_devices(hba);
err_out:
	return rc;
}

static void bnx2fc_fw_destroy(struct bnx2fc_hba *hba)
{
	if (test_and_clear_bit(BNX2FC_FLAG_FW_INIT_DONE, &hba->flags)) {
		if (bnx2fc_send_fw_fcoe_destroy_msg(hba) == 0) {
			timer_setup(&hba->destroy_timer, bnx2fc_destroy_timer,
				    0);
			hba->destroy_timer.expires = BNX2FC_FW_TIMEOUT +
								jiffies;
			add_timer(&hba->destroy_timer);
			wait_event_interruptible(hba->destroy_wait,
					test_bit(BNX2FC_FLAG_DESTROY_CMPL,
						 &hba->flags));
			clear_bit(BNX2FC_FLAG_DESTROY_CMPL, &hba->flags);
			/* This should never happen */
			if (signal_pending(current))
				flush_signals(current);

			del_timer_sync(&hba->destroy_timer);
		}
		bnx2fc_unbind_adapter_devices(hba);
	}
}

/**
 * bnx2fc_ulp_stop - cnic callback to shutdown adapter instance
 *
 * @handle:	transport handle pointing to adapter structure
 *
 * Driver checks if adapter is already in shutdown mode, if not start
 *	the shutdown process.
 */
static void bnx2fc_ulp_stop(void *handle)
{
	struct bnx2fc_hba *hba = handle;
	struct bnx2fc_interface *interface;

	printk(KERN_ERR "ULP_STOP\n");

	mutex_lock(&bnx2fc_dev_lock);
	if (!test_bit(BNX2FC_FLAG_FW_INIT_DONE, &hba->flags))
		goto exit;
	list_for_each_entry(interface, &if_list, list) {
		if (interface->hba == hba)
			bnx2fc_stop(interface);
	}
	BUG_ON(hba->num_ofld_sess != 0);

	mutex_lock(&hba->hba_mutex);
	clear_bit(ADAPTER_STATE_UP, &hba->adapter_state);
	clear_bit(ADAPTER_STATE_GOING_DOWN,
		  &hba->adapter_state);

	clear_bit(ADAPTER_STATE_READY, &hba->adapter_state);
	mutex_unlock(&hba->hba_mutex);

	bnx2fc_fw_destroy(hba);
exit:
	mutex_unlock(&bnx2fc_dev_lock);
}

static void bnx2fc_start_disc(struct bnx2fc_interface *interface)
{
	struct fcoe_ctlr *ctlr = bnx2fc_to_ctlr(interface);
	struct fc_lport *lport;
	int wait_cnt = 0;

	BNX2FC_MISC_DBG("Entered %s\n", __func__);
	/* Kick off FIP/FLOGI */
	if (!test_bit(BNX2FC_FLAG_FW_INIT_DONE, &interface->hba->flags)) {
		printk(KERN_ERR PFX "Init not done yet\n");
		return;
	}

	lport = ctlr->lp;
	BNX2FC_HBA_DBG(lport, "calling fc_fabric_login\n");

	if (!bnx2fc_link_ok(lport) && interface->enabled) {
		BNX2FC_HBA_DBG(lport, "ctlr_link_up\n");
		fcoe_ctlr_link_up(ctlr);
		fc_host_port_type(lport->host) = FC_PORTTYPE_NPORT;
		set_bit(ADAPTER_STATE_READY, &interface->hba->adapter_state);
	}

	/* wait for the FCF to be selected before issuing FLOGI */
	while (!ctlr->sel_fcf) {
		msleep(250);
		/* give up after 3 secs */
		if (++wait_cnt > 12)
			break;
	}

	/* Reset max receive frame size to default */
	if (fc_set_mfs(lport, BNX2FC_MFS))
		return;

	fc_lport_init(lport);
	fc_fabric_login(lport);
}


/**
 * bnx2fc_ulp_init - Initialize an adapter instance
 *
 * @dev :	cnic device handle
 * Called from cnic_register_driver() context to initialize all
 *	enumerated cnic devices. This routine allocates adapter structure
 *	and other device specific resources.
 */
static void bnx2fc_ulp_init(struct cnic_dev *dev)
{
	struct bnx2fc_hba *hba;
	int rc = 0;

	BNX2FC_MISC_DBG("Entered %s\n", __func__);
	/* bnx2fc works only when bnx2x is loaded */
	if (!test_bit(CNIC_F_BNX2X_CLASS, &dev->flags) ||
	    (dev->max_fcoe_conn == 0)) {
		printk(KERN_ERR PFX "bnx2fc FCoE not supported on %s,"
				    " flags: %lx fcoe_conn: %d\n",
			dev->netdev->name, dev->flags, dev->max_fcoe_conn);
		return;
	}

	hba = bnx2fc_hba_create(dev);
	if (!hba) {
		printk(KERN_ERR PFX "hba initialization failed\n");
		return;
	}

	pr_info(PFX "FCoE initialized for %s.\n", dev->netdev->name);

	/* Add HBA to the adapter list */
	mutex_lock(&bnx2fc_dev_lock);
	list_add_tail(&hba->list, &adapter_list);
	adapter_count++;
	mutex_unlock(&bnx2fc_dev_lock);

	dev->fcoe_cap = &hba->fcoe_cap;
	clear_bit(BNX2FC_CNIC_REGISTERED, &hba->reg_with_cnic);
	rc = dev->register_device(dev, CNIC_ULP_FCOE,
						(void *) hba);
	if (rc)
		printk(KERN_ERR PFX "register_device failed, rc = %d\n", rc);
	else
		set_bit(BNX2FC_CNIC_REGISTERED, &hba->reg_with_cnic);
}

/* Assumes rtnl_lock and the bnx2fc_dev_lock are already taken */
static int __bnx2fc_disable(struct fcoe_ctlr *ctlr)
{
	struct bnx2fc_interface *interface = fcoe_ctlr_priv(ctlr);

	if (interface->enabled == true) {
		if (!ctlr->lp) {
			pr_err(PFX "__bnx2fc_disable: lport not found\n");
			return -ENODEV;
		} else {
			interface->enabled = false;
			fcoe_ctlr_link_down(ctlr);
			fcoe_clean_pending_queue(ctlr->lp);
		}
	}
	return 0;
}

/**
 * Deperecated: Use bnx2fc_enabled()
 */
static int bnx2fc_disable(struct net_device *netdev)
{
	struct bnx2fc_interface *interface;
	struct fcoe_ctlr *ctlr;
	int rc = 0;

	rtnl_lock();
	mutex_lock(&bnx2fc_dev_lock);

	interface = bnx2fc_interface_lookup(netdev);
	ctlr = bnx2fc_to_ctlr(interface);

	if (!interface) {
		rc = -ENODEV;
		pr_err(PFX "bnx2fc_disable: interface not found\n");
	} else {
		rc = __bnx2fc_disable(ctlr);
	}
	mutex_unlock(&bnx2fc_dev_lock);
	rtnl_unlock();
	return rc;
}

static uint bnx2fc_npiv_create_vports(struct fc_lport *lport,
				      struct cnic_fc_npiv_tbl *npiv_tbl)
{
	struct fc_vport_identifiers vpid;
	uint i, created = 0;
	u64 wwnn = 0;
	char wwpn_str[32];
	char wwnn_str[32];

	if (npiv_tbl->count > MAX_NPIV_ENTRIES) {
		BNX2FC_HBA_DBG(lport, "Exceeded count max of npiv table\n");
		goto done;
	}

	/* Sanity check the first entry to make sure it's not 0 */
	if (wwn_to_u64(npiv_tbl->wwnn[0]) == 0 &&
	    wwn_to_u64(npiv_tbl->wwpn[0]) == 0) {
		BNX2FC_HBA_DBG(lport, "First NPIV table entries invalid.\n");
		goto done;
	}

	vpid.roles = FC_PORT_ROLE_FCP_INITIATOR;
	vpid.vport_type = FC_PORTTYPE_NPIV;
	vpid.disable = false;

	for (i = 0; i < npiv_tbl->count; i++) {
		wwnn = wwn_to_u64(npiv_tbl->wwnn[i]);
		if (wwnn == 0) {
			/*
			 * If we get a 0 element from for the WWNN then assume
			 * the WWNN should be the same as the physical port.
			 */
			wwnn = lport->wwnn;
		}
		vpid.node_name = wwnn;
		vpid.port_name = wwn_to_u64(npiv_tbl->wwpn[i]);
		scnprintf(vpid.symbolic_name, sizeof(vpid.symbolic_name),
		    "NPIV[%u]:%016llx-%016llx",
		    created, vpid.port_name, vpid.node_name);
		fcoe_wwn_to_str(vpid.node_name, wwnn_str, sizeof(wwnn_str));
		fcoe_wwn_to_str(vpid.port_name, wwpn_str, sizeof(wwpn_str));
		BNX2FC_HBA_DBG(lport, "Creating vport %s:%s.\n", wwnn_str,
		    wwpn_str);
		if (fc_vport_create(lport->host, 0, &vpid))
			created++;
		else
			BNX2FC_HBA_DBG(lport, "Failed to create vport\n");
	}
done:
	return created;
}

static int __bnx2fc_enable(struct fcoe_ctlr *ctlr)
{
	struct bnx2fc_interface *interface = fcoe_ctlr_priv(ctlr);
	struct bnx2fc_hba *hba;
	struct cnic_fc_npiv_tbl *npiv_tbl;
	struct fc_lport *lport;

	if (interface->enabled == false) {
		if (!ctlr->lp) {
			pr_err(PFX "__bnx2fc_enable: lport not found\n");
			return -ENODEV;
		} else if (!bnx2fc_link_ok(ctlr->lp)) {
			fcoe_ctlr_link_up(ctlr);
			interface->enabled = true;
		}
	}

	/* Create static NPIV ports if any are contained in NVRAM */
	hba = interface->hba;
	lport = ctlr->lp;

	if (!hba)
		goto done;

	if (!hba->cnic)
		goto done;

	if (!lport)
		goto done;

	if (!lport->host)
		goto done;

	if (!hba->cnic->get_fc_npiv_tbl)
		goto done;

	npiv_tbl = kzalloc(sizeof(struct cnic_fc_npiv_tbl), GFP_KERNEL);
	if (!npiv_tbl)
		goto done;

	if (hba->cnic->get_fc_npiv_tbl(hba->cnic, npiv_tbl))
		goto done_free;

	bnx2fc_npiv_create_vports(lport, npiv_tbl);
done_free:
	kfree(npiv_tbl);
done:
	return 0;
}

/**
 * Deprecated: Use bnx2fc_enabled()
 */
static int bnx2fc_enable(struct net_device *netdev)
{
	struct bnx2fc_interface *interface;
	struct fcoe_ctlr *ctlr;
	int rc = 0;

	rtnl_lock();
	mutex_lock(&bnx2fc_dev_lock);

	interface = bnx2fc_interface_lookup(netdev);
	ctlr = bnx2fc_to_ctlr(interface);
	if (!interface) {
		rc = -ENODEV;
		pr_err(PFX "bnx2fc_enable: interface not found\n");
	} else {
		rc = __bnx2fc_enable(ctlr);
	}

	mutex_unlock(&bnx2fc_dev_lock);
	rtnl_unlock();
	return rc;
}

/**
 * bnx2fc_ctlr_enabled() - Enable or disable an FCoE Controller
 * @cdev: The FCoE Controller that is being enabled or disabled
 *
 * fcoe_sysfs will ensure that the state of 'enabled' has
 * changed, so no checking is necessary here. This routine simply
 * calls fcoe_enable or fcoe_disable, both of which are deprecated.
 * When those routines are removed the functionality can be merged
 * here.
 */
static int bnx2fc_ctlr_enabled(struct fcoe_ctlr_device *cdev)
{
	struct fcoe_ctlr *ctlr = fcoe_ctlr_device_priv(cdev);

	switch (cdev->enabled) {
	case FCOE_CTLR_ENABLED:
		return __bnx2fc_enable(ctlr);
	case FCOE_CTLR_DISABLED:
		return __bnx2fc_disable(ctlr);
	case FCOE_CTLR_UNUSED:
	default:
		return -ENOTSUPP;
	};
}

enum bnx2fc_create_link_state {
	BNX2FC_CREATE_LINK_DOWN,
	BNX2FC_CREATE_LINK_UP,
};

/**
 * _bnx2fc_create() - Create bnx2fc FCoE interface
 * @netdev  :   The net_device object the Ethernet interface to create on
 * @fip_mode:   The FIP mode for this creation
 * @link_state: The ctlr link state on creation
 *
 * Called from either the libfcoe 'create' module parameter
 * via fcoe_create or from fcoe_syfs's ctlr_create file.
 *
 * libfcoe's 'create' module parameter is deprecated so some
 * consolidation of code can be done when that interface is
 * removed.
 *
 * Returns: 0 for success
 */
static int _bnx2fc_create(struct net_device *netdev,
			  enum fip_mode fip_mode,
			  enum bnx2fc_create_link_state link_state)
{
	struct fcoe_ctlr_device *cdev;
	struct fcoe_ctlr *ctlr;
	struct bnx2fc_interface *interface;
	struct bnx2fc_hba *hba;
	struct net_device *phys_dev = netdev;
	struct fc_lport *lport;
	struct ethtool_drvinfo drvinfo;
	int rc = 0;
	int vlan_id = 0;

	BNX2FC_MISC_DBG("Entered bnx2fc_create\n");
	if (fip_mode != FIP_MODE_FABRIC) {
		printk(KERN_ERR "fip mode not FABRIC\n");
		return -EIO;
	}

	rtnl_lock();

	mutex_lock(&bnx2fc_dev_lock);

	if (!try_module_get(THIS_MODULE)) {
		rc = -EINVAL;
		goto mod_err;
	}

	/* obtain physical netdev */
	if (is_vlan_dev(netdev))
		phys_dev = vlan_dev_real_dev(netdev);

	/* verify if the physical device is a netxtreme2 device */
	if (phys_dev->ethtool_ops && phys_dev->ethtool_ops->get_drvinfo) {
		memset(&drvinfo, 0, sizeof(drvinfo));
		phys_dev->ethtool_ops->get_drvinfo(phys_dev, &drvinfo);
		if (strncmp(drvinfo.driver, "bnx2x", strlen("bnx2x"))) {
			printk(KERN_ERR PFX "Not a netxtreme2 device\n");
			rc = -EINVAL;
			goto netdev_err;
		}
	} else {
		printk(KERN_ERR PFX "unable to obtain drv_info\n");
		rc = -EINVAL;
		goto netdev_err;
	}

	/* obtain interface and initialize rest of the structure */
	hba = bnx2fc_hba_lookup(phys_dev);
	if (!hba) {
		rc = -ENODEV;
		printk(KERN_ERR PFX "bnx2fc_create: hba not found\n");
		goto netdev_err;
	}

	if (bnx2fc_interface_lookup(netdev)) {
		rc = -EEXIST;
		goto netdev_err;
	}

	interface = bnx2fc_interface_create(hba, netdev, fip_mode);
	if (!interface) {
		printk(KERN_ERR PFX "bnx2fc_interface_create failed\n");
		rc = -ENOMEM;
		goto netdev_err;
	}

	if (is_vlan_dev(netdev)) {
		vlan_id = vlan_dev_vlan_id(netdev);
		interface->vlan_enabled = 1;
	}

	ctlr = bnx2fc_to_ctlr(interface);
	cdev = fcoe_ctlr_to_ctlr_dev(ctlr);
	interface->vlan_id = vlan_id;
	interface->tm_timeout = BNX2FC_TM_TIMEOUT;

	interface->timer_work_queue =
			create_singlethread_workqueue("bnx2fc_timer_wq");
	if (!interface->timer_work_queue) {
		printk(KERN_ERR PFX "ulp_init could not create timer_wq\n");
		rc = -EINVAL;
		goto ifput_err;
	}

	lport = bnx2fc_if_create(interface, &cdev->dev, 0);
	if (!lport) {
		printk(KERN_ERR PFX "Failed to create interface (%s)\n",
			netdev->name);
		rc = -EINVAL;
		goto if_create_err;
	}

	/* Add interface to if_list */
	list_add_tail(&interface->list, &if_list);

	lport->boot_time = jiffies;

	/* Make this master N_port */
	ctlr->lp = lport;

	if (link_state == BNX2FC_CREATE_LINK_UP)
		cdev->enabled = FCOE_CTLR_ENABLED;
	else
		cdev->enabled = FCOE_CTLR_DISABLED;

	if (link_state == BNX2FC_CREATE_LINK_UP &&
	    !bnx2fc_link_ok(lport)) {
		fcoe_ctlr_link_up(ctlr);
		fc_host_port_type(lport->host) = FC_PORTTYPE_NPORT;
		set_bit(ADAPTER_STATE_READY, &interface->hba->adapter_state);
	}

	BNX2FC_HBA_DBG(lport, "create: START DISC\n");
	bnx2fc_start_disc(interface);

	if (link_state == BNX2FC_CREATE_LINK_UP)
		interface->enabled = true;

	/*
	 * Release from kref_init in bnx2fc_interface_setup, on success
	 * lport should be holding a reference taken in bnx2fc_if_create
	 */
	bnx2fc_interface_put(interface);
	/* put netdev that was held while calling dev_get_by_name */
	mutex_unlock(&bnx2fc_dev_lock);
	rtnl_unlock();
	return 0;

if_create_err:
	destroy_workqueue(interface->timer_work_queue);
ifput_err:
	bnx2fc_net_cleanup(interface);
	bnx2fc_interface_put(interface);
	goto mod_err;
netdev_err:
	module_put(THIS_MODULE);
mod_err:
	mutex_unlock(&bnx2fc_dev_lock);
	rtnl_unlock();
	return rc;
}

/**
 * bnx2fc_create() - Create a bnx2fc interface
 * @netdev  : The net_device object the Ethernet interface to create on
 * @fip_mode: The FIP mode for this creation
 *
 * Called from fcoe transport
 *
 * Returns: 0 for success
 */
static int bnx2fc_create(struct net_device *netdev, enum fip_mode fip_mode)
{
	return _bnx2fc_create(netdev, fip_mode, BNX2FC_CREATE_LINK_UP);
}

/**
 * bnx2fc_ctlr_alloc() - Allocate a bnx2fc interface from fcoe_sysfs
 * @netdev: The net_device to be used by the allocated FCoE Controller
 *
 * This routine is called from fcoe_sysfs. It will start the fcoe_ctlr
 * in a link_down state. The allows the user an opportunity to configure
 * the FCoE Controller from sysfs before enabling the FCoE Controller.
 *
 * Creating in with this routine starts the FCoE Controller in Fabric
 * mode. The user can change to VN2VN or another mode before enabling.
 */
static int bnx2fc_ctlr_alloc(struct net_device *netdev)
{
	return _bnx2fc_create(netdev, FIP_MODE_FABRIC,
			      BNX2FC_CREATE_LINK_DOWN);
}

/**
 * bnx2fc_find_hba_for_cnic - maps cnic instance to bnx2fc hba instance
 *
 * @cnic:	Pointer to cnic device instance
 *
 **/
static struct bnx2fc_hba *bnx2fc_find_hba_for_cnic(struct cnic_dev *cnic)
{
	struct bnx2fc_hba *hba;

	/* Called with bnx2fc_dev_lock held */
	list_for_each_entry(hba, &adapter_list, list) {
		if (hba->cnic == cnic)
			return hba;
	}
	return NULL;
}

static struct bnx2fc_interface *bnx2fc_interface_lookup(struct net_device
							*netdev)
{
	struct bnx2fc_interface *interface;

	/* Called with bnx2fc_dev_lock held */
	list_for_each_entry(interface, &if_list, list) {
		if (interface->netdev == netdev)
			return interface;
	}
	return NULL;
}

static struct bnx2fc_hba *bnx2fc_hba_lookup(struct net_device
						      *phys_dev)
{
	struct bnx2fc_hba *hba;

	/* Called with bnx2fc_dev_lock held */
	list_for_each_entry(hba, &adapter_list, list) {
		if (hba->phys_dev == phys_dev)
			return hba;
	}
	printk(KERN_ERR PFX "adapter_lookup: hba NULL\n");
	return NULL;
}

/**
 * bnx2fc_ulp_exit - shuts down adapter instance and frees all resources
 *
 * @dev		cnic device handle
 */
static void bnx2fc_ulp_exit(struct cnic_dev *dev)
{
	struct bnx2fc_hba *hba;
	struct bnx2fc_interface *interface, *tmp;

	BNX2FC_MISC_DBG("Entered bnx2fc_ulp_exit\n");

	if (!test_bit(CNIC_F_BNX2X_CLASS, &dev->flags)) {
		printk(KERN_ERR PFX "bnx2fc port check: %s, flags: %lx\n",
			dev->netdev->name, dev->flags);
		return;
	}

	mutex_lock(&bnx2fc_dev_lock);
	hba = bnx2fc_find_hba_for_cnic(dev);
	if (!hba) {
		printk(KERN_ERR PFX "bnx2fc_ulp_exit: hba not found, dev 0%p\n",
		       dev);
		mutex_unlock(&bnx2fc_dev_lock);
		return;
	}

	list_del_init(&hba->list);
	adapter_count--;

	list_for_each_entry_safe(interface, tmp, &if_list, list)
		/* destroy not called yet, move to quiesced list */
		if (interface->hba == hba)
			__bnx2fc_destroy(interface);
	mutex_unlock(&bnx2fc_dev_lock);

	/* Ensure ALL destroy work has been completed before return */
	flush_workqueue(bnx2fc_wq);

	bnx2fc_ulp_stop(hba);
	/* unregister cnic device */
	if (test_and_clear_bit(BNX2FC_CNIC_REGISTERED, &hba->reg_with_cnic))
		hba->cnic->unregister_device(hba->cnic, CNIC_ULP_FCOE);
	bnx2fc_hba_destroy(hba);
}

static void bnx2fc_rport_terminate_io(struct fc_rport *rport)
{
	/* This is a no-op */
}

/**
 * bnx2fc_fcoe_reset - Resets the fcoe
 *
 * @shost: shost the reset is from
 *
 * Returns: always 0
 */
static int bnx2fc_fcoe_reset(struct Scsi_Host *shost)
{
	struct fc_lport *lport = shost_priv(shost);
	fc_lport_reset(lport);
	return 0;
}


static bool bnx2fc_match(struct net_device *netdev)
{
	struct net_device *phys_dev = netdev;

	mutex_lock(&bnx2fc_dev_lock);
	if (is_vlan_dev(netdev))
		phys_dev = vlan_dev_real_dev(netdev);

	if (bnx2fc_hba_lookup(phys_dev)) {
		mutex_unlock(&bnx2fc_dev_lock);
		return true;
	}

	mutex_unlock(&bnx2fc_dev_lock);
	return false;
}


static struct fcoe_transport bnx2fc_transport = {
	.name = {"bnx2fc"},
	.attached = false,
	.list = LIST_HEAD_INIT(bnx2fc_transport.list),
	.alloc = bnx2fc_ctlr_alloc,
	.match = bnx2fc_match,
	.create = bnx2fc_create,
	.destroy = bnx2fc_destroy,
	.enable = bnx2fc_enable,
	.disable = bnx2fc_disable,
};

/**
 * bnx2fc_cpu_online - Create a receive thread for an  online CPU
 *
 * @cpu: cpu index for the online cpu
 */
static int bnx2fc_cpu_online(unsigned int cpu)
{
	struct bnx2fc_percpu_s *p;
	struct task_struct *thread;

	p = &per_cpu(bnx2fc_percpu, cpu);

	thread = kthread_create_on_node(bnx2fc_percpu_io_thread,
					(void *)p, cpu_to_node(cpu),
					"bnx2fc_thread/%d", cpu);
	if (IS_ERR(thread))
		return PTR_ERR(thread);

	/* bind thread to the cpu */
	kthread_bind(thread, cpu);
	p->iothread = thread;
	wake_up_process(thread);
	return 0;
}

static int bnx2fc_cpu_offline(unsigned int cpu)
{
	struct bnx2fc_percpu_s *p;
	struct task_struct *thread;
	struct bnx2fc_work *work, *tmp;

	BNX2FC_MISC_DBG("destroying io thread for CPU %d\n", cpu);

	/* Prevent any new work from being queued for this CPU */
	p = &per_cpu(bnx2fc_percpu, cpu);
	spin_lock_bh(&p->fp_work_lock);
	thread = p->iothread;
	p->iothread = NULL;

	/* Free all work in the list */
	list_for_each_entry_safe(work, tmp, &p->work_list, list) {
		list_del_init(&work->list);
		bnx2fc_process_cq_compl(work->tgt, work->wqe);
		kfree(work);
	}

	spin_unlock_bh(&p->fp_work_lock);

	if (thread)
		kthread_stop(thread);
	return 0;
}

static int bnx2fc_slave_configure(struct scsi_device *sdev)
{
	if (!bnx2fc_queue_depth)
		return 0;

	scsi_change_queue_depth(sdev, bnx2fc_queue_depth);
	return 0;
}

static enum cpuhp_state bnx2fc_online_state;

/**
 * bnx2fc_mod_init - module init entry point
 *
 * Initialize driver wide global data structures, and register
 * with cnic module
 **/
static int __init bnx2fc_mod_init(void)
{
	struct fcoe_percpu_s *bg;
	struct task_struct *l2_thread;
	int rc = 0;
	unsigned int cpu = 0;
	struct bnx2fc_percpu_s *p;

	printk(KERN_INFO PFX "%s", version);

	/* register as a fcoe transport */
	rc = fcoe_transport_attach(&bnx2fc_transport);
	if (rc) {
		printk(KERN_ERR "failed to register an fcoe transport, check "
			"if libfcoe is loaded\n");
		goto out;
	}

	INIT_LIST_HEAD(&adapter_list);
	INIT_LIST_HEAD(&if_list);
	mutex_init(&bnx2fc_dev_lock);
	adapter_count = 0;

	/* Attach FC transport template */
	rc = bnx2fc_attach_transport();
	if (rc)
		goto detach_ft;

	bnx2fc_wq = alloc_workqueue("bnx2fc", 0, 0);
	if (!bnx2fc_wq) {
		rc = -ENOMEM;
		goto release_bt;
	}

	bg = &bnx2fc_global;
	skb_queue_head_init(&bg->fcoe_rx_list);
	l2_thread = kthread_create(bnx2fc_l2_rcv_thread,
				   (void *)bg,
				   "bnx2fc_l2_thread");
	if (IS_ERR(l2_thread)) {
		rc = PTR_ERR(l2_thread);
		goto free_wq;
	}
	wake_up_process(l2_thread);
	spin_lock_bh(&bg->fcoe_rx_list.lock);
	bg->kthread = l2_thread;
	spin_unlock_bh(&bg->fcoe_rx_list.lock);

	for_each_possible_cpu(cpu) {
		p = &per_cpu(bnx2fc_percpu, cpu);
		INIT_LIST_HEAD(&p->work_list);
		spin_lock_init(&p->fp_work_lock);
	}

	rc = cpuhp_setup_state(CPUHP_AP_ONLINE_DYN, "scsi/bnx2fc:online",
			       bnx2fc_cpu_online, bnx2fc_cpu_offline);
	if (rc < 0)
		goto stop_thread;
	bnx2fc_online_state = rc;

	cnic_register_driver(CNIC_ULP_FCOE, &bnx2fc_cnic_cb);
	return 0;

stop_thread:
	kthread_stop(l2_thread);
free_wq:
	destroy_workqueue(bnx2fc_wq);
release_bt:
	bnx2fc_release_transport();
detach_ft:
	fcoe_transport_detach(&bnx2fc_transport);
out:
	return rc;
}

static void __exit bnx2fc_mod_exit(void)
{
	LIST_HEAD(to_be_deleted);
	struct bnx2fc_hba *hba, *next;
	struct fcoe_percpu_s *bg;
	struct task_struct *l2_thread;
	struct sk_buff *skb;

	/*
	 * NOTE: Since cnic calls register_driver routine rtnl_lock,
	 * it will have higher precedence than bnx2fc_dev_lock.
	 * unregister_device() cannot be called with bnx2fc_dev_lock
	 * held.
	 */
	mutex_lock(&bnx2fc_dev_lock);
	list_splice_init(&adapter_list, &to_be_deleted);
	adapter_count = 0;
	mutex_unlock(&bnx2fc_dev_lock);

	/* Unregister with cnic */
	list_for_each_entry_safe(hba, next, &to_be_deleted, list) {
		list_del_init(&hba->list);
		printk(KERN_ERR PFX "MOD_EXIT:destroy hba = 0x%p\n",
		       hba);
		bnx2fc_ulp_stop(hba);
		/* unregister cnic device */
		if (test_and_clear_bit(BNX2FC_CNIC_REGISTERED,
				       &hba->reg_with_cnic))
			hba->cnic->unregister_device(hba->cnic,
							 CNIC_ULP_FCOE);
		bnx2fc_hba_destroy(hba);
	}
	cnic_unregister_driver(CNIC_ULP_FCOE);

	/* Destroy global thread */
	bg = &bnx2fc_global;
	spin_lock_bh(&bg->fcoe_rx_list.lock);
	l2_thread = bg->kthread;
	bg->kthread = NULL;
	while ((skb = __skb_dequeue(&bg->fcoe_rx_list)) != NULL)
		kfree_skb(skb);

	spin_unlock_bh(&bg->fcoe_rx_list.lock);

	if (l2_thread)
		kthread_stop(l2_thread);

	cpuhp_remove_state(bnx2fc_online_state);

	destroy_workqueue(bnx2fc_wq);
	/*
	 * detach from scsi transport
	 * must happen after all destroys are done
	 */
	bnx2fc_release_transport();

	/* detach from fcoe transport */
	fcoe_transport_detach(&bnx2fc_transport);
}

module_init(bnx2fc_mod_init);
module_exit(bnx2fc_mod_exit);

static struct fcoe_sysfs_function_template bnx2fc_fcoe_sysfs_templ = {
	.set_fcoe_ctlr_enabled = bnx2fc_ctlr_enabled,
	.get_fcoe_ctlr_link_fail = fcoe_ctlr_get_lesb,
	.get_fcoe_ctlr_vlink_fail = fcoe_ctlr_get_lesb,
	.get_fcoe_ctlr_miss_fka = fcoe_ctlr_get_lesb,
	.get_fcoe_ctlr_symb_err = fcoe_ctlr_get_lesb,
	.get_fcoe_ctlr_err_block = fcoe_ctlr_get_lesb,
	.get_fcoe_ctlr_fcs_error = fcoe_ctlr_get_lesb,

	.get_fcoe_fcf_selected = fcoe_fcf_get_selected,
	.get_fcoe_fcf_vlan_id = bnx2fc_fcf_get_vlan_id,
};

static struct fc_function_template bnx2fc_transport_function = {
	.show_host_node_name = 1,
	.show_host_port_name = 1,
	.show_host_supported_classes = 1,
	.show_host_supported_fc4s = 1,
	.show_host_active_fc4s = 1,
	.show_host_maxframe_size = 1,

	.show_host_port_id = 1,
	.show_host_supported_speeds = 1,
	.get_host_speed = fc_get_host_speed,
	.show_host_speed = 1,
	.show_host_port_type = 1,
	.get_host_port_state = fc_get_host_port_state,
	.show_host_port_state = 1,
	.show_host_symbolic_name = 1,

	.dd_fcrport_size = (sizeof(struct fc_rport_libfc_priv) +
				sizeof(struct bnx2fc_rport)),
	.show_rport_maxframe_size = 1,
	.show_rport_supported_classes = 1,

	.show_host_fabric_name = 1,
	.show_starget_node_name = 1,
	.show_starget_port_name = 1,
	.show_starget_port_id = 1,
	.set_rport_dev_loss_tmo = fc_set_rport_loss_tmo,
	.show_rport_dev_loss_tmo = 1,
	.get_fc_host_stats = bnx2fc_get_host_stats,

	.issue_fc_host_lip = bnx2fc_fcoe_reset,

	.terminate_rport_io = bnx2fc_rport_terminate_io,

	.vport_create = bnx2fc_vport_create,
	.vport_delete = bnx2fc_vport_destroy,
	.vport_disable = bnx2fc_vport_disable,
	.bsg_request = fc_lport_bsg_request,
};

static struct fc_function_template bnx2fc_vport_xport_function = {
	.show_host_node_name = 1,
	.show_host_port_name = 1,
	.show_host_supported_classes = 1,
	.show_host_supported_fc4s = 1,
	.show_host_active_fc4s = 1,
	.show_host_maxframe_size = 1,

	.show_host_port_id = 1,
	.show_host_supported_speeds = 1,
	.get_host_speed = fc_get_host_speed,
	.show_host_speed = 1,
	.show_host_port_type = 1,
	.get_host_port_state = fc_get_host_port_state,
	.show_host_port_state = 1,
	.show_host_symbolic_name = 1,

	.dd_fcrport_size = (sizeof(struct fc_rport_libfc_priv) +
				sizeof(struct bnx2fc_rport)),
	.show_rport_maxframe_size = 1,
	.show_rport_supported_classes = 1,

	.show_host_fabric_name = 1,
	.show_starget_node_name = 1,
	.show_starget_port_name = 1,
	.show_starget_port_id = 1,
	.set_rport_dev_loss_tmo = fc_set_rport_loss_tmo,
	.show_rport_dev_loss_tmo = 1,
	.get_fc_host_stats = fc_get_host_stats,
	.issue_fc_host_lip = bnx2fc_fcoe_reset,
	.terminate_rport_io = fc_rport_terminate_io,
	.bsg_request = fc_lport_bsg_request,
};

/*
 * Additional scsi_host attributes.
 */
static ssize_t
bnx2fc_tm_timeout_show(struct device *dev, struct device_attribute *attr,
	char *buf)
{
	struct Scsi_Host *shost = class_to_shost(dev);
	struct fc_lport *lport = shost_priv(shost);
	struct fcoe_port *port = lport_priv(lport);
	struct bnx2fc_interface *interface = port->priv;

	sprintf(buf, "%u\n", interface->tm_timeout);
	return strlen(buf);
}

static ssize_t
bnx2fc_tm_timeout_store(struct device *dev,
	struct device_attribute *attr, const char *buf, size_t count)
{
	struct Scsi_Host *shost = class_to_shost(dev);
	struct fc_lport *lport = shost_priv(shost);
	struct fcoe_port *port = lport_priv(lport);
	struct bnx2fc_interface *interface = port->priv;
	int rval, val;

	rval = kstrtouint(buf, 10, &val);
	if (rval)
		return rval;
	if (val > 255)
		return -ERANGE;

	interface->tm_timeout = (u8)val;
	return strlen(buf);
}

static DEVICE_ATTR(tm_timeout, S_IRUGO|S_IWUSR, bnx2fc_tm_timeout_show,
	bnx2fc_tm_timeout_store);

static struct device_attribute *bnx2fc_host_attrs[] = {
	&dev_attr_tm_timeout,
	NULL,
};

/**
 * scsi_host_template structure used while registering with SCSI-ml
 */
static struct scsi_host_template bnx2fc_shost_template = {
	.module			= THIS_MODULE,
	.name			= "QLogic Offload FCoE Initiator",
	.queuecommand		= bnx2fc_queuecommand,
	.eh_timed_out		= fc_eh_timed_out,
	.eh_abort_handler	= bnx2fc_eh_abort,	  /* abts */
	.eh_device_reset_handler = bnx2fc_eh_device_reset, /* lun reset */
	.eh_target_reset_handler = bnx2fc_eh_target_reset, /* tgt reset */
	.eh_host_reset_handler	= fc_eh_host_reset,
	.slave_alloc		= fc_slave_alloc,
	.change_queue_depth	= scsi_change_queue_depth,
	.this_id		= -1,
	.cmd_per_lun		= 3,
	.sg_tablesize		= BNX2FC_MAX_BDS_PER_CMD,
	.dma_boundary           = 0x7fff,
	.max_sectors		= 0x3fbf,
	.track_queue_depth	= 1,
	.slave_configure	= bnx2fc_slave_configure,
	.shost_attrs		= bnx2fc_host_attrs,
};

static struct libfc_function_template bnx2fc_libfc_fcn_templ = {
	.frame_send		= bnx2fc_xmit,
	.elsct_send		= bnx2fc_elsct_send,
	.fcp_abort_io		= bnx2fc_abort_io,
	.fcp_cleanup		= bnx2fc_cleanup,
	.get_lesb		= fcoe_get_lesb,
	.rport_event_callback	= bnx2fc_rport_event_handler,
};

/**
 * bnx2fc_cnic_cb - global template of bnx2fc - cnic driver interface
 *			structure carrying callback function pointers
 */
static struct cnic_ulp_ops bnx2fc_cnic_cb = {
	.owner			= THIS_MODULE,
	.cnic_init		= bnx2fc_ulp_init,
	.cnic_exit		= bnx2fc_ulp_exit,
	.cnic_start		= bnx2fc_ulp_start,
	.cnic_stop		= bnx2fc_ulp_stop,
	.indicate_kcqes		= bnx2fc_indicate_kcqe,
	.indicate_netevent	= bnx2fc_indicate_netevent,
	.cnic_get_stats		= bnx2fc_ulp_get_stats,
};
