/*
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 as
 * published by the Free Software Foundation.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * Copyright (C) 2012 ARM Limited
 */

#include <linux/delay.h>
#include <linux/of.h>
#include <linux/of_device.h>
#include <linux/platform_device.h>
#include <linux/stat.h>
#include <linux/vexpress.h>

#include <asm/system_misc.h>

static void vexpress_reset_do(struct device *dev, const char *what)
{
	int err = -ENOENT;
	struct vexpress_config_func *func = dev_get_drvdata(dev);

	if (func) {
		err = vexpress_config_write(func, 0, 0);
		if (!err)
			mdelay(1000);
	}

	dev_emerg(dev, "Unable to %s (%d)\n", what, err);
}

static struct device *vexpress_power_off_device;

static void vexpress_power_off(void)
{
	vexpress_reset_do(vexpress_power_off_device, "power off");
}

static struct device *vexpress_restart_device;

static void vexpress_restart(enum reboot_mode reboot_mode, const char *cmd)
{
	vexpress_reset_do(vexpress_restart_device, "restart");
}

static ssize_t vexpress_reset_active_show(struct device *dev,
		struct device_attribute *attr, char *buf)
{
	return sprintf(buf, "%d\n", vexpress_restart_device == dev);
}

static ssize_t vexpress_reset_active_store(struct device *dev,
		struct device_attribute *attr, const char *buf, size_t count)
{
	long value;
	int err = kstrtol(buf, 0, &value);

	if (!err && value)
		vexpress_restart_device = dev;

	return err ? err : count;
}

DEVICE_ATTR(active, S_IRUGO | S_IWUSR, vexpress_reset_active_show,
		vexpress_reset_active_store);


enum vexpress_reset_func { FUNC_RESET, FUNC_SHUTDOWN, FUNC_REBOOT };

static struct of_device_id vexpress_reset_of_match[] = {
	{
		.compatible = "arm,vexpress-reset",
		.data = (void *)FUNC_RESET,
	}, {
		.compatible = "arm,vexpress-shutdown",
		.data = (void *)FUNC_SHUTDOWN
	}, {
		.compatible = "arm,vexpress-reboot",
		.data = (void *)FUNC_REBOOT
	},
	{}
};

static int vexpress_reset_probe(struct platform_device *pdev)
{
	enum vexpress_reset_func func;
	const struct of_device_id *match =
			of_match_device(vexpress_reset_of_match, &pdev->dev);
	struct vexpress_config_func *config_func;

	if (match)
		func = (enum vexpress_reset_func)match->data;
	else
		func = pdev->id_entry->driver_data;

	config_func = vexpress_config_func_get_by_dev(&pdev->dev);
	if (!config_func)
		return -EINVAL;
	dev_set_drvdata(&pdev->dev, config_func);

	switch (func) {
	case FUNC_SHUTDOWN:
		vexpress_power_off_device = &pdev->dev;
		pm_power_off = vexpress_power_off;
		break;
	case FUNC_RESET:
		if (!vexpress_restart_device)
			vexpress_restart_device = &pdev->dev;
		arm_pm_restart = vexpress_restart;
		device_create_file(&pdev->dev, &dev_attr_active);
		break;
	case FUNC_REBOOT:
		vexpress_restart_device = &pdev->dev;
		arm_pm_restart = vexpress_restart;
		device_create_file(&pdev->dev, &dev_attr_active);
		break;
	};

	return 0;
}

static const struct platform_device_id vexpress_reset_id_table[] = {
	{ .name = "vexpress-reset", .driver_data = FUNC_RESET, },
	{ .name = "vexpress-shutdown", .driver_data = FUNC_SHUTDOWN, },
	{ .name = "vexpress-reboot", .driver_data = FUNC_REBOOT, },
	{}
};

static struct platform_driver vexpress_reset_driver = {
	.probe = vexpress_reset_probe,
	.driver = {
		.name = "vexpress-reset",
		.of_match_table = vexpress_reset_of_match,
	},
	.id_table = vexpress_reset_id_table,
};

static int __init vexpress_reset_init(void)
{
	return platform_driver_register(&vexpress_reset_driver);
}
device_initcall(vexpress_reset_init);
