[PATCH] usb: otg: notifier: switch to atomic notifiers

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



to be able to use notifiers from interrupt context
notifiers have been changed from blocking to atomic.

Signed-off-by: Arnaud Mandy <ext-arnaud.2.mandy@xxxxxxxxx>
---
 drivers/usb/otg/twl4030-usb.c |    8 +++-----
 include/linux/usb/otg.h       |   24 +++++++++++++++++++++---
 2 files changed, 24 insertions(+), 8 deletions(-)

diff --git a/drivers/usb/otg/twl4030-usb.c b/drivers/usb/otg/twl4030-usb.c
index 0bc9769..f69b502 100644
--- a/drivers/usb/otg/twl4030-usb.c
+++ b/drivers/usb/otg/twl4030-usb.c
@@ -507,8 +507,7 @@ static irqreturn_t twl4030_usb_irq(int irq, void *_twl)
 		else
 			twl4030_phy_resume(twl);
 
-		blocking_notifier_call_chain(&twl->otg.notifier, status,
-				twl->otg.gadget);
+		otg_notify_event(&twl->otg, status, twl->otg.gadget);
 	}
 	sysfs_notify(&twl->dev->kobj, NULL, "vbus");
 
@@ -529,8 +528,7 @@ static void twl4030_usb_phy_init(struct twl4030_usb *twl)
 			twl->asleep = 0;
 		}
 
-		blocking_notifier_call_chain(&twl->otg.notifier, status,
-				twl->otg.gadget);
+		otg_notify_event(&twl->otg, status, twl->otg.gadget);
 	}
 	sysfs_notify(&twl->dev->kobj, NULL, "vbus");
 }
@@ -618,7 +616,7 @@ static int __devinit twl4030_usb_probe(struct platform_device *pdev)
 	if (device_create_file(&pdev->dev, &dev_attr_vbus))
 		dev_warn(&pdev->dev, "could not create sysfs file\n");
 
-	BLOCKING_INIT_NOTIFIER_HEAD(&twl->otg.notifier);
+	ATOMIC_INIT_NOTIFIER_HEAD(&twl->otg.notifier);
 
 	/* Our job is to use irqs and status from the power module
 	 * to keep the transceiver disabled when nothing's connected.
diff --git a/include/linux/usb/otg.h b/include/linux/usb/otg.h
index 545cba7..026b89a 100644
--- a/include/linux/usb/otg.h
+++ b/include/linux/usb/otg.h
@@ -64,6 +64,8 @@ struct otg_transceiver {
 	const char		*label;
 	unsigned int		 flags;
 
+	void			*last_event_data;
+	u8			last_event;
 	u8			default_a;
 	enum usb_otg_state	state;
 
@@ -74,7 +76,7 @@ struct otg_transceiver {
 	void __iomem			*io_priv;
 
 	/* for notification of usb_xceiv_events */
-	struct blocking_notifier_head	notifier;
+	struct atomic_notifier_head	notifier;
 
 	/* to pass extra port status to the root hub */
 	u16			port_status;
@@ -223,13 +225,29 @@ otg_start_srp(struct otg_transceiver *otg)
 static inline int
 otg_register_notifier(struct otg_transceiver *otg, struct notifier_block *nb)
 {
-	return blocking_notifier_chain_register(&otg->notifier, nb);
+	return atomic_notifier_chain_register(&otg->notifier, nb);
+}
+
+static inline int
+otg_notify_event(struct otg_transceiver *otg, enum usb_xceiv_events event,
+		void *data)
+{
+	otg->last_event = event;
+	otg->last_event_data = data;
+
+	return atomic_notifier_call_chain(&otg->notifier, event, data);
+}
+
+static inline int
+otg_get_last_event(struct otg_transceiver *otg)
+{
+	return otg_notify_event(otg, otg->last_event, otg->last_event_data);
 }
 
 static inline void
 otg_unregister_notifier(struct otg_transceiver *otg, struct notifier_block *nb)
 {
-	blocking_notifier_chain_unregister(&otg->notifier, nb);
+	atomic_notifier_chain_unregister(&otg->notifier, nb);
 }
 
 /* for OTG controller drivers (and maybe other stuff) */
-- 
1.6.3.3

--
To unsubscribe from this list: send the line "unsubscribe linux-usb" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[Index of Archives]     [Linux Media]     [Linux Input]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]     [Old Linux USB Devel Archive]

  Powered by Linux