// SPDX-License-Identifier: GPL-2.0+
/*
 * Copyright (c) 2023 Neil Armstrong <neil.armstrong@linaro.org>
 */
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/of.h>
#include <linux/platform_device.h>
#include <linux/mfd/rk808.h>
#include <linux/regmap.h>
#include <linux/module.h>
#include <linux/reboot.h>
#include <linux/i2c.h>

/*
 * The Odroid Go Ultra has 2 PMICs:
 * - RK818 (manages the battery and USB-C power supply)
 * - RK817
 * Both PMICs feeds power to the S922X SoC, so they must be powered-off in sequence.
 * Vendor does power-off the RK817 first, then the RK818 so here we follow this sequence.
 */

struct odroid_go_ultra_poweroff_data {
	struct device *dev;
	struct device *rk817;
	struct device *rk818;
};

static int odroid_go_ultra_poweroff_prepare(struct sys_off_data *data)
{
	struct odroid_go_ultra_poweroff_data *poweroff_data = data->cb_data;
	struct regmap *rk817, *rk818;
	int ret;

	/* RK817 Regmap */
	rk817 = dev_get_regmap(poweroff_data->rk817, NULL);
	if (!rk817) {
		dev_err(poweroff_data->dev, "failed to get rk817 regmap\n");
		return notifier_from_errno(-EINVAL);
	}

	/* RK818 Regmap */
	rk818 = dev_get_regmap(poweroff_data->rk818, NULL);
	if (!rk818) {
		dev_err(poweroff_data->dev, "failed to get rk818 regmap\n");
		return notifier_from_errno(-EINVAL);
	}

	dev_info(poweroff_data->dev, "Setting PMICs for power off");

	/* RK817 */
	ret = regmap_update_bits(rk817, RK817_SYS_CFG(3), DEV_OFF, DEV_OFF);
	if (ret) {
		dev_err(poweroff_data->dev, "failed to poweroff rk817\n");
		return notifier_from_errno(ret);
	}

	/* RK818 */
	ret = regmap_update_bits(rk818, RK818_DEVCTRL_REG, DEV_OFF, DEV_OFF);
	if (ret) {
		dev_err(poweroff_data->dev, "failed to poweroff rk818\n");
		return notifier_from_errno(ret);
	}

	return NOTIFY_OK;
}

static void odroid_go_ultra_poweroff_put_pmic_device(void *data)
{
	struct device *dev = data;

	put_device(dev);
}

static int odroid_go_ultra_poweroff_get_pmic_device(struct device *dev, const char *compatible,
						    struct device **pmic)
{
	struct device_node *pmic_node;
	struct i2c_client *pmic_client;

	pmic_node = of_find_compatible_node(NULL, NULL, compatible);
	if (!pmic_node)
		return -ENODEV;

	pmic_client = of_find_i2c_device_by_node(pmic_node);
	of_node_put(pmic_node);
	if (!pmic_client)
		return -EPROBE_DEFER;

	*pmic = &pmic_client->dev;

	return devm_add_action_or_reset(dev, odroid_go_ultra_poweroff_put_pmic_device, *pmic);
}

static int odroid_go_ultra_poweroff_probe(struct platform_device *pdev)
{
	struct odroid_go_ultra_poweroff_data *poweroff_data;
	int ret;

	poweroff_data = devm_kzalloc(&pdev->dev, sizeof(*poweroff_data), GFP_KERNEL);
	if (!poweroff_data)
		return -ENOMEM;

	dev_set_drvdata(&pdev->dev, poweroff_data);

	/* RK818 PMIC Device */
	ret = odroid_go_ultra_poweroff_get_pmic_device(&pdev->dev, "rockchip,rk818",
						       &poweroff_data->rk818);
	if (ret)
		return dev_err_probe(&pdev->dev, ret, "failed to get rk818 mfd data\n");

	/* RK817 PMIC Device */
	ret = odroid_go_ultra_poweroff_get_pmic_device(&pdev->dev, "rockchip,rk817",
						       &poweroff_data->rk817);
	if (ret)
		return dev_err_probe(&pdev->dev, ret, "failed to get rk817 mfd data\n");

	/* Register as SYS_OFF_MODE_POWER_OFF_PREPARE because regmap_update_bits may sleep */
	ret = devm_register_sys_off_handler(&pdev->dev,
					    SYS_OFF_MODE_POWER_OFF_PREPARE,
					    SYS_OFF_PRIO_DEFAULT,
					    odroid_go_ultra_poweroff_prepare,
					    poweroff_data);
	if (ret)
		return dev_err_probe(&pdev->dev, ret, "failed to register sys-off handler\n");

	dev_info(&pdev->dev, "Registered Power-Off handler\n");

	return 0;
}
static struct platform_device *pdev;

static struct platform_driver odroid_go_ultra_poweroff_driver = {
	.driver = {
		.name	= "odroid-go-ultra-poweroff",
	},
	.probe = odroid_go_ultra_poweroff_probe,
};

static int __init odroid_go_ultra_poweroff_init(void)
{
	int ret;

	/* Only create when running on the Odroid Go Ultra device */
	if (!of_device_is_compatible(of_root, "hardkernel,odroid-go-ultra"))
		return -ENODEV;

	ret = platform_driver_register(&odroid_go_ultra_poweroff_driver);
	if (ret)
		return ret;

	pdev = platform_device_register_resndata(NULL, "odroid-go-ultra-poweroff", -1,
						 NULL, 0, NULL, 0);

	if (IS_ERR(pdev)) {
		platform_driver_unregister(&odroid_go_ultra_poweroff_driver);
		return PTR_ERR(pdev);
	}

	return 0;
}

static void __exit odroid_go_ultra_poweroff_exit(void)
{
	/* Only delete when running on the Odroid Go Ultra device */
	if (!of_device_is_compatible(of_root, "hardkernel,odroid-go-ultra"))
		return;

	platform_device_unregister(pdev);
	platform_driver_unregister(&odroid_go_ultra_poweroff_driver);
}

module_init(odroid_go_ultra_poweroff_init);
module_exit(odroid_go_ultra_poweroff_exit);

MODULE_AUTHOR("Neil Armstrong <neil.armstrong@linaro.org>");
MODULE_DESCRIPTION("Odroid Go Ultra poweroff driver");
MODULE_LICENSE("GPL");
