not_suspended = 0;
        list_for_each_entry(pdd, &genpd->dev_list, list_node)
                if (pdd->dev->driver && (!pm_runtime_suspended(pdd->dev)
-                   || pdd->dev->power.irq_safe))
+                   || pdd->dev->power.irq_safe || to_gpd_data(pdd)->always_on))
                        not_suspended++;
 
        if (not_suspended > genpd->in_progress)
 
        might_sleep_if(!genpd->dev_irq_safe);
 
+       if (dev_gpd_data(dev)->always_on)
+               return -EBUSY;
+
        stop_ok = genpd->gov ? genpd->gov->stop_ok : NULL;
        if (stop_ok && !stop_ok(dev))
                return -EBUSY;
        if (IS_ERR(genpd))
                return -EINVAL;
 
-       if (genpd->suspend_power_off
+       if (genpd->suspend_power_off || dev_gpd_data(dev)->always_on
            || (dev->power.wakeup_path && genpd_dev_active_wakeup(genpd, dev)))
                return 0;
 
        if (IS_ERR(genpd))
                return -EINVAL;
 
-       if (genpd->suspend_power_off
+       if (genpd->suspend_power_off || dev_gpd_data(dev)->always_on
            || (dev->power.wakeup_path && genpd_dev_active_wakeup(genpd, dev)))
                return 0;
 
        if (IS_ERR(genpd))
                return -EINVAL;
 
-       return genpd->suspend_power_off ? 0 : genpd_stop_dev(genpd, dev);
+       return genpd->suspend_power_off || dev_gpd_data(dev)->always_on ?
+               0 : genpd_stop_dev(genpd, dev);
 }
 
 /**
        if (IS_ERR(genpd))
                return -EINVAL;
 
-       return genpd->suspend_power_off ? 0 : genpd_start_dev(genpd, dev);
+       return genpd->suspend_power_off || dev_gpd_data(dev)->always_on ?
+               0 : genpd_start_dev(genpd, dev);
 }
 
 /**
 
        pm_genpd_poweron(genpd);
 
-       return genpd_start_dev(genpd, dev);
+       return dev_gpd_data(dev)->always_on ? 0 : genpd_start_dev(genpd, dev);
 }
 
 /**
        return ret;
 }
 
+/**
+ * pm_genpd_dev_always_on - Set/unset the "always on" flag for a given device.
+ * @dev: Device to set/unset the flag for.
+ * @val: The new value of the device's "always on" flag.
+ */
+void pm_genpd_dev_always_on(struct device *dev, bool val)
+{
+       struct pm_subsys_data *psd;
+       unsigned long flags;
+
+       spin_lock_irqsave(&dev->power.lock, flags);
+
+       psd = dev_to_psd(dev);
+       if (psd && psd->domain_data)
+               to_gpd_data(psd->domain_data)->always_on = val;
+
+       spin_unlock_irqrestore(&dev->power.lock, flags);
+}
+EXPORT_SYMBOL_GPL(pm_genpd_dev_always_on);
+
 /**
  * pm_genpd_add_subdomain - Add a subdomain to an I/O PM domain.
  * @genpd: Master PM domain to add the subdomain to.
 
        struct gpd_dev_ops ops;
        struct gpd_timing_data td;
        bool need_restore;
+       bool always_on;
 };
 
 #ifdef CONFIG_PM_GENERIC_DOMAINS
 
 extern int pm_genpd_remove_device(struct generic_pm_domain *genpd,
                                  struct device *dev);
+extern void pm_genpd_dev_always_on(struct device *dev, bool val);
 extern int pm_genpd_add_subdomain(struct generic_pm_domain *genpd,
                                  struct generic_pm_domain *new_subdomain);
 extern int pm_genpd_remove_subdomain(struct generic_pm_domain *genpd,
 {
        return -ENOSYS;
 }
+static inline void pm_genpd_dev_always_on(struct device *dev, bool val) {}
 static inline int pm_genpd_add_subdomain(struct generic_pm_domain *genpd,
                                         struct generic_pm_domain *new_sd)
 {