#include <linux/platform_device.h>
 #include <linux/types.h>
+#include <linux/notifier.h>
 #include <linux/workqueue.h>
 #include <linux/interrupt.h>
 #include <linux/kernel.h>
 void snd_soc_jack_report(struct snd_soc_jack *jack, int status, int mask);
 int snd_soc_jack_add_pins(struct snd_soc_jack *jack, int count,
                          struct snd_soc_jack_pin *pins);
+void snd_soc_jack_notifier_register(struct snd_soc_jack *jack,
+                                   struct notifier_block *nb);
+void snd_soc_jack_notifier_unregister(struct snd_soc_jack *jack,
+                                     struct notifier_block *nb);
 #ifdef CONFIG_GPIOLIB
 int snd_soc_jack_add_gpios(struct snd_soc_jack *jack, int count,
                        struct snd_soc_jack_gpio *gpios);
        struct snd_soc_card *card;
        struct list_head pins;
        int status;
+       struct blocking_notifier_head notifier;
 };
 
 /* SoC PCM stream information */
 
 {
        jack->card = card;
        INIT_LIST_HEAD(&jack->pins);
+       BLOCKING_INIT_NOTIFIER_HEAD(&jack->notifier);
 
        return snd_jack_new(card->codec->card, id, type, &jack->jack);
 }
                        snd_soc_dapm_disable_pin(codec, pin->pin);
        }
 
+       /* Report before the DAPM sync to help users updating micbias status */
+       blocking_notifier_call_chain(&jack->notifier, status, NULL);
+
        snd_soc_dapm_sync(codec);
 
        snd_jack_report(jack->jack, status);
 }
 EXPORT_SYMBOL_GPL(snd_soc_jack_add_pins);
 
+/**
+ * snd_soc_jack_notifier_register - Register a notifier for jack status
+ *
+ * @jack:  ASoC jack
+ * @nb:    Notifier block to register
+ *
+ * Register for notification of the current status of the jack.  Note
+ * that it is not possible to report additional jack events in the
+ * callback from the notifier, this is intended to support
+ * applications such as enabling electrical detection only when a
+ * mechanical detection event has occurred.
+ */
+void snd_soc_jack_notifier_register(struct snd_soc_jack *jack,
+                                   struct notifier_block *nb)
+{
+       blocking_notifier_chain_register(&jack->notifier, nb);
+}
+EXPORT_SYMBOL_GPL(snd_soc_jack_notifier_register);
+
+/**
+ * snd_soc_jack_notifier_unregister - Unregister a notifier for jack status
+ *
+ * @jack:  ASoC jack
+ * @nb:    Notifier block to unregister
+ *
+ * Stop notifying for status changes.
+ */
+void snd_soc_jack_notifier_unregister(struct snd_soc_jack *jack,
+                                     struct notifier_block *nb)
+{
+       blocking_notifier_chain_unregister(&jack->notifier, nb);
+}
+EXPORT_SYMBOL_GPL(snd_soc_jack_notifier_unregister);
+
 #ifdef CONFIG_GPIOLIB
 /* gpio detect */
 static void snd_soc_jack_gpio_detect(struct snd_soc_jack_gpio *gpio)