xen-devel.lists.xenproject.org archive mirror
 help / color / mirror / Atom feed
* [PATCH] linux/pcifront: fix freeing of device
@ 2010-10-04 11:09 Jan Beulich
  2010-10-04 11:46 ` Keir Fraser
  0 siblings, 1 reply; 4+ messages in thread
From: Jan Beulich @ 2010-10-04 11:09 UTC (permalink / raw)
  To: xen-devel@lists.xensource.com

[-- Attachment #1: Type: text/plain, Size: 2122 bytes --]

unbind_from_irqhandler() takes irq, not evtchn, as its first argument.

Once at it, improve error handling.

Signed-off-by: Jan Beulich <jbeulich@novell.com>
Reported-by: Rafal Wojtczuk <rafal@invisiblethingslab.com>

--- a/drivers/xen/pcifront/pcifront.h
+++ b/drivers/xen/pcifront/pcifront.h
@@ -30,6 +30,7 @@ struct pcifront_device {
 
 	int evtchn;
 	int gnt_ref;
+	int irq;
 
 	/* Lock this when doing any operations in sh_info */
 	spinlock_t sh_info_lock;
--- a/drivers/xen/pcifront/xenbus.c
+++ b/drivers/xen/pcifront/xenbus.c
@@ -48,6 +48,7 @@ static struct pcifront_device *alloc_pde
 
 	pdev->evtchn = INVALID_EVTCHN;
 	pdev->gnt_ref = INVALID_GRANT_REF;
+	pdev->irq = -1;
 
 	INIT_WORK(&pdev->op_work, pcifront_do_aer, pdev);
 
@@ -65,7 +66,9 @@ static void free_pdev(struct pcifront_de
 
 	/*For PCIE_AER error handling job*/
 	flush_scheduled_work();
-	unbind_from_irqhandler(pdev->evtchn, pdev);
+
+	if (pdev->irq > 0)
+		unbind_from_irqhandler(pdev->irq, pdev);
 
 	if (pdev->evtchn != INVALID_EVTCHN)
 		xenbus_free_evtchn(pdev->xdev, pdev->evtchn);
@@ -73,6 +76,8 @@ static void free_pdev(struct pcifront_de
 	if (pdev->gnt_ref != INVALID_GRANT_REF)
 		gnttab_end_foreign_access(pdev->gnt_ref,
 					  (unsigned long)pdev->sh_info);
+	else
+		free_page((unsigned long)pdev->sh_info);
 
 	pdev->xdev->dev.driver_data = NULL;
 
@@ -94,8 +99,16 @@ static int pcifront_publish_info(struct 
 	if (err)
 		goto out;
 
-	bind_caller_port_to_irqhandler(pdev->evtchn, pcifront_handler_aer, 
-		SA_SAMPLE_RANDOM, "pcifront", pdev); 
+	err = bind_caller_port_to_irqhandler(pdev->evtchn,
+					     pcifront_handler_aer,
+					     SA_SAMPLE_RANDOM,
+					     "pcifront", pdev);
+	if (err < 0) {
+		xenbus_dev_fatal(pdev->xdev, err,
+				 "Failed to bind event channel");
+		goto out;
+	}
+	pdev->irq = err;
 
       do_publish:
 	err = xenbus_transaction_start(&trans);
@@ -428,6 +441,8 @@ static int pcifront_xenbus_probe(struct 
 	}
 
 	err = pcifront_publish_info(pdev);
+	if (err)
+		free_pdev(pdev);
 
       out:
 	return err;




[-- Attachment #2: xen-pcifront-irq-not-evtchn.patch --]
[-- Type: text/plain, Size: 2160 bytes --]

Subject: pcifront: fix freeing of device

unbind_from_irqhandler() takes irq, not evtchn, as its first argument.

Once at it, improve error handling.

Signed-off-by: Jan Beulich <jbeulich@novell.com>
Reported-by: Rafal Wojtczuk <rafal@invisiblethingslab.com>

--- a/drivers/xen/pcifront/pcifront.h
+++ b/drivers/xen/pcifront/pcifront.h
@@ -30,6 +30,7 @@ struct pcifront_device {
 
 	int evtchn;
 	int gnt_ref;
+	int irq;
 
 	/* Lock this when doing any operations in sh_info */
 	spinlock_t sh_info_lock;
--- a/drivers/xen/pcifront/xenbus.c
+++ b/drivers/xen/pcifront/xenbus.c
@@ -48,6 +48,7 @@ static struct pcifront_device *alloc_pde
 
 	pdev->evtchn = INVALID_EVTCHN;
 	pdev->gnt_ref = INVALID_GRANT_REF;
+	pdev->irq = -1;
 
 	INIT_WORK(&pdev->op_work, pcifront_do_aer, pdev);
 
@@ -65,7 +66,9 @@ static void free_pdev(struct pcifront_de
 
 	/*For PCIE_AER error handling job*/
 	flush_scheduled_work();
-	unbind_from_irqhandler(pdev->evtchn, pdev);
+
+	if (pdev->irq > 0)
+		unbind_from_irqhandler(pdev->irq, pdev);
 
 	if (pdev->evtchn != INVALID_EVTCHN)
 		xenbus_free_evtchn(pdev->xdev, pdev->evtchn);
@@ -73,6 +76,8 @@ static void free_pdev(struct pcifront_de
 	if (pdev->gnt_ref != INVALID_GRANT_REF)
 		gnttab_end_foreign_access(pdev->gnt_ref,
 					  (unsigned long)pdev->sh_info);
+	else
+		free_page((unsigned long)pdev->sh_info);
 
 	pdev->xdev->dev.driver_data = NULL;
 
@@ -94,8 +99,16 @@ static int pcifront_publish_info(struct 
 	if (err)
 		goto out;
 
-	bind_caller_port_to_irqhandler(pdev->evtchn, pcifront_handler_aer, 
-		SA_SAMPLE_RANDOM, "pcifront", pdev); 
+	err = bind_caller_port_to_irqhandler(pdev->evtchn,
+					     pcifront_handler_aer,
+					     SA_SAMPLE_RANDOM,
+					     "pcifront", pdev);
+	if (err < 0) {
+		xenbus_dev_fatal(pdev->xdev, err,
+				 "Failed to bind event channel");
+		goto out;
+	}
+	pdev->irq = err;
 
       do_publish:
 	err = xenbus_transaction_start(&trans);
@@ -428,6 +441,8 @@ static int pcifront_xenbus_probe(struct 
 	}
 
 	err = pcifront_publish_info(pdev);
+	if (err)
+		free_pdev(pdev);
 
       out:
 	return err;

[-- Attachment #3: Type: text/plain, Size: 138 bytes --]

_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xensource.com
http://lists.xensource.com/xen-devel

^ permalink raw reply	[flat|nested] 4+ messages in thread

end of thread, other threads:[~2010-10-04 12:23 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2010-10-04 11:09 [PATCH] linux/pcifront: fix freeing of device Jan Beulich
2010-10-04 11:46 ` Keir Fraser
2010-10-04 12:22   ` Jan Beulich
2010-10-04 12:23     ` Keir Fraser

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).