From 013068fa6f65f7037adedc141fbd27afc99ab1bb Mon Sep 17 00:00:00 2001 From: Bhanu Prakash Gollapudi Date: Tue, 30 Aug 2011 15:54:52 -0700 Subject: [SCSI] bnx2fc: Fix panic caused because of incorrect errror handling in create(). Driver incorrectly calls bnx2fc_interface_cleanup() when bnx2fc_if_create fails which accesses bad pointer. Handle bnx2fc_if_create failure by directly calling bnx2fc_net_cleanup. Signed-off-by: Bhanu Prakash Gollapudi Signed-off-by: James Bottomley --- drivers/scsi/bnx2fc/bnx2fc_fcoe.c | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) (limited to 'drivers') diff --git a/drivers/scsi/bnx2fc/bnx2fc_fcoe.c b/drivers/scsi/bnx2fc/bnx2fc_fcoe.c index a5111f3..330f9f0 100644 --- a/drivers/scsi/bnx2fc/bnx2fc_fcoe.c +++ b/drivers/scsi/bnx2fc/bnx2fc_fcoe.c @@ -1441,6 +1441,14 @@ free_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 fc_lport *lport = interface->ctlr.lp; @@ -1453,10 +1461,7 @@ static void bnx2fc_interface_cleanup(struct bnx2fc_interface *interface) /* Free existing transmit skbs */ fcoe_clean_pending_queue(lport); - /* Dont listen for Ethernet packets anymore */ - __dev_remove_pack(&interface->fcoe_packet_type); - __dev_remove_pack(&interface->fip_packet_type); - synchronize_net(); + bnx2fc_net_cleanup(interface); bnx2fc_free_vport(hba, lport); } @@ -1991,7 +1996,6 @@ static int bnx2fc_create(struct net_device *netdev, enum fip_state fip_mode) if (!lport) { printk(KERN_ERR PFX "Failed to create interface (%s)\n", netdev->name); - bnx2fc_interface_cleanup(interface); rc = -EINVAL; goto if_create_err; } @@ -2026,6 +2030,7 @@ static int bnx2fc_create(struct net_device *netdev, enum fip_state fip_mode) if_create_err: destroy_workqueue(interface->timer_work_queue); ifput_err: + bnx2fc_net_cleanup(interface); bnx2fc_interface_put(interface); netdev_err: module_put(THIS_MODULE); -- cgit v1.1