void tegra_pd_remove_device(struct device *dev)
{
	struct generic_pm_domain *genpd = dev_to_genpd(dev);

	if (!IS_ERR_OR_NULL(genpd))
		pm_genpd_remove_device(genpd, dev);
}
static int exynos_pd_power_on(struct device *dev, const char * device_name)
{
	struct exynos_pm_domain *pd_index = NULL;
	int ret = 0;
	struct gpd_timing_data gpd_td = {
		.stop_latency_ns = 50000,
		.start_latency_ns = 50000,
		.save_state_latency_ns = 500000,
		.restore_state_latency_ns = 500000,
	};

#ifdef CONFIG_SOC_EXYNOS5260
	if(soc_is_exynos5260())
		pd_index = exynos5260_pm_domain();
#endif

#ifdef CONFIG_SOC_EXYNOS4415
	if (soc_is_exynos4415())
		pd_index = exynos4415_pm_domain();
#endif

	if (!pd_index) {
		pr_err(PM_DOMAIN_PREFIX "domain data is not found\n");
		return -EINVAL;
	}

	/* lookup master pd */
	for_each_power_domain(pd_index) {
		/* skip unmanaged power domains */
		if (!pd_index->enable)
			continue;

		if (strcmp(pd_index->name, device_name)) {
			continue;
		}

		if (pd_index->check_status(pd_index)) {
			pr_err("PM DOMAIN: %s is already on.\n", pd_index->name);
			break;
		}

		while (1) {
			ret = __pm_genpd_add_device(&pd_index->genpd, dev, &gpd_td);
			if (ret != -EAGAIN)
				break;
			cond_resched();
		}
		if (!ret) {
			pm_genpd_dev_need_restore(dev, true);
			pr_info("PM DOMAIN: %s, Device : %s Registered\n", pd_index->name, dev_name(dev));
		} else
			pr_err("PM DOMAIN: %s cannot add device %s\n", pd_index->name, dev_name(dev));

		pm_runtime_enable(dev);
		pm_runtime_get_sync(dev);
		pr_info("%s: power on.\n", pd_index->name);
	}

	return ret;

}

static int exynos_pd_power_off(struct device *dev, const char * device_name)
{
	struct exynos_pm_domain *pd_index = NULL;
	int ret = 0;

#ifdef CONFIG_SOC_EXYNOS5260
	if(soc_is_exynos5260())
		pd_index = exynos5260_pm_domain();
#endif

#ifdef CONFIG_SOC_EXYNOS4415
	if (soc_is_exynos4415())
		pd_index = exynos4415_pm_domain();
#endif

	if (!pd_index) {
		pr_err(PM_DOMAIN_PREFIX "domain data is not found\n");
		return -EINVAL;
	}

	/* lookup master pd */
	for_each_power_domain(pd_index) {
		/* skip unmanaged power domains */
		if (!pd_index->enable)
			continue;

		if (strcmp(pd_index->name, device_name)) {
			continue;
		}

		if (!pd_index->check_status(pd_index)) {
			pr_err("PM DOMAIN: %s is already off.\n", pd_index->name);
			break;
		}

		pm_runtime_put_sync(dev);
		pm_runtime_disable(dev);

		while (1) {
			ret = pm_genpd_remove_device(&pd_index->genpd, dev);
			if (ret != -EAGAIN)
				break;
			cond_resched();
		}
		if (ret)
			pr_err("PM DOMAIN: %s cannot remove device %s\n", pd_index->name, dev_name(dev));
		pr_info("%s: power off.\n", pd_index->name);
	}

	return ret;

}

static int exynos_pd_longrun_test(struct device *dev, const char * device_name)
{
	struct exynos_pm_domain *pd_index = NULL;
	int i, ret = 0;
	struct gpd_timing_data gpd_td = {
		.stop_latency_ns = 50000,
		.start_latency_ns = 50000,
		.save_state_latency_ns = 500000,
		.restore_state_latency_ns = 500000,
	};

#ifdef CONFIG_SOC_EXYNOS5260
	if(soc_is_exynos5260())
		pd_index = exynos5260_pm_domain();
#endif

#ifdef CONFIG_SOC_EXYNOS4415
	if (soc_is_exynos4415())
		pd_index = exynos4415_pm_domain();
#endif

	if (!pd_index) {
		pr_err(PM_DOMAIN_PREFIX "domain data is not found\n");
		return -EINVAL;
	}

	/* lookup master pd */
	for_each_power_domain(pd_index) {
		/* skip unmanaged power domains */
		if (!pd_index->enable)
			continue;

		if (strcmp(pd_index->name, device_name)) {
			continue;
		}

		if (pd_index->check_status(pd_index)) {
			pr_err("PM DOMAIN: %s is working. Stop testing\n", pd_index->genpd.name);
			break;
		}

		while (1) {
			ret = __pm_genpd_add_device(&pd_index->genpd, dev, &gpd_td);
			if (ret != -EAGAIN)
				break;
			cond_resched();
		}
		if (!ret) {
			pm_genpd_dev_need_restore(dev, true);
			pr_info("PM DOMAIN: %s, Device : %s Registered\n", pd_index->genpd.name, dev_name(dev));
		} else
			pr_err("PM DOMAIN: %s cannot add device %s\n", pd_index->genpd.name, dev_name(dev));

		pr_info("%s: test start.\n", pd_index->genpd.name);
		pm_runtime_enable(dev);
		for (i=0; i<100; i++) {
			pm_runtime_get_sync(dev);
			mdelay(50);
			pm_runtime_put_sync(dev);
			mdelay(50);
		}
		pr_info("%s: test done.\n", pd_index->genpd.name);
		pm_runtime_disable(dev);

		while (1) {
			ret = pm_genpd_remove_device(&pd_index->genpd, dev);
			if (ret != -EAGAIN)
				break;
			cond_resched();
		}
		if (ret)
			pr_err("PM DOMAIN: %s cannot remove device %s\n", pd_index->name, dev_name(dev));
	}

	return ret;
}

static ssize_t store_power_domain_test(struct device *dev, struct device_attribute *attr, const char *buf, size_t count)
{
	char device_name[32], test_name[32];

	sscanf(buf, "%s %s", device_name, test_name);

	switch (test_name[0]) {
	case '1':
		exynos_pd_power_on(dev, device_name);
		break;

	case '0':
		exynos_pd_power_off(dev, device_name);
		break;

	case 't':
		exynos_pd_longrun_test(dev, device_name);
		break;

	default:
		printk("echo \"device\" \"test\" > control\n");
	}

	return count;
}

static DEVICE_ATTR(control, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH, show_power_domain, store_power_domain_test);

static struct attribute *control_device_attrs[] = {
	&dev_attr_control.attr,
	NULL,
};

static const struct attribute_group control_device_attr_group = {
	.attrs = control_device_attrs,
};

static int runtime_pm_test_probe(struct platform_device *pdev)
{
	struct class *runtime_pm_class;
	struct device *runtime_pm_dev;
	int ret;

	runtime_pm_class = class_create(THIS_MODULE, "runtime_pm");
	runtime_pm_dev = device_create(runtime_pm_class, NULL, 0, NULL, "test");
	ret = sysfs_create_group(&runtime_pm_dev->kobj, &control_device_attr_group);
	if (ret) {
		pr_err("Runtime PM Test : error to create sysfs\n");
		return -EINVAL;
	}

	pm_runtime_enable(&pdev->dev);

	return 0;
}

static int runtime_pm_test_runtime_suspend(struct device *dev)
{
	pr_info("Runtime PM Test : Runtime_Suspend\n");
	return 0;
}