// SPDX-License-Identifier: GPL-2.0
/*
 * Miscellaneous character driver for ChromeOS Embedded Controller
 *
 * Copyright 2014 Google, Inc.
 * Copyright 2019 Google LLC
 *
 * This file is a rework and part of the code is ported from
 * drivers/mfd/cros_ec_dev.c that was originally written by
 * Bill Richardson.
 */

#include <linux/init.h>
#include <linux/device.h>
#include <linux/fs.h>
#include <linux/miscdevice.h>
#include <linux/module.h>
#include <linux/notifier.h>
#include <linux/platform_data/cros_ec_chardev.h>
#include <linux/platform_data/cros_ec_commands.h>
#include <linux/platform_data/cros_ec_proto.h>
#include <linux/platform_device.h>
#include <linux/poll.h>
#include <linux/slab.h>
#include <linux/types.h>
#include <linux/uaccess.h>

#define DRV_NAME		"cros-ec-chardev"

/* Arbitrary bounded size for the event queue */
#define CROS_MAX_EVENT_LEN	PAGE_SIZE

struct chardev_data {
	struct cros_ec_dev *ec_dev;
	struct miscdevice misc;
};

struct chardev_priv {
	struct cros_ec_dev *ec_dev;
	struct notifier_block notifier;
	wait_queue_head_t wait_event;
	unsigned long event_mask;
	struct list_head events;
	size_t event_len;
};

struct ec_event {
	struct list_head node;
	size_t size;
	u8 event_type;
	u8 data[0];
};

static int ec_get_version(struct cros_ec_dev *ec, char *str, int maxlen)
{
	static const char * const current_image_name[] = {
		"unknown", "read-only", "read-write", "invalid",
	};
	struct ec_response_get_version *resp;
	struct cros_ec_command *msg;
	int ret;

	msg = kzalloc(sizeof(*msg) + sizeof(*resp), GFP_KERNEL);
	if (!msg)
		return -ENOMEM;

	msg->command = EC_CMD_GET_VERSION + ec->cmd_offset;
	msg->insize = sizeof(*resp);

	ret = cros_ec_cmd_xfer_status(ec->ec_dev, msg);
	if (ret < 0) {
		snprintf(str, maxlen,
			 "Unknown EC version, returned error: %d\n",
			 msg->result);
		goto exit;
	}

	resp = (struct ec_response_get_version *)msg->data;
	if (resp->current_image >= ARRAY_SIZE(current_image_name))
		resp->current_image = 3; /* invalid */

	snprintf(str, maxlen, "%s\n%s\n%s\n%s\n", CROS_EC_DEV_VERSION,
		 resp->version_string_ro, resp->version_string_rw,
		 current_image_name[resp->current_image]);

	ret = 0;
exit:
	kfree(msg);
	return ret;
}

static int cros_ec_chardev_mkbp_event(struct notifier_block *nb,
				      unsigned long queued_during_suspend,
				      void *_notify)
{
	struct chardev_priv *priv = container_of(nb, struct chardev_priv,
						 notifier);
	struct cros_ec_device *ec_dev = priv->ec_dev->ec_dev;
	struct ec_event *event;
	unsigned long event_bit = 1 << ec_dev->event_data.event_type;
	int total_size = sizeof(*event) + ec_dev->event_size;

	if (!(event_bit & priv->event_mask) ||
	    (priv->event_len + total_size) > CROS_MAX_EVENT_LEN)
		return NOTIFY_DONE;

	event = kzalloc(total_size, GFP_KERNEL);
	if (!event)
		return NOTIFY_DONE;

	event->size = ec_dev->event_size;
	event->event_type = ec_dev->event_data.event_type;
	memcpy(event->data, &ec_dev->event_data.data, ec_dev->event_size);

	spin_lock(&priv->wait_event.lock);
	list_add_tail(&event->node, &priv->events);
	priv->event_len += total_size;
	wake_up_locked(&priv->wait_event);
	spin_unlock(&priv->wait_event.lock);

	return NOTIFY_OK;
}

static struct ec_event *cros_ec_chardev_fetch_event(struct chardev_priv *priv,
						    bool fetch, bool block)
{
	struct ec_event *event;
	int err;

	spin_lock(&priv->wait_event.lock);
	if (!block && list_empty(&priv->events)) {
		event = ERR_PTR(-EWOULDBLOCK);
		goto out;
	}

	if (!fetch) {
		event = NULL;
		goto out;
	}

	err = wait_event_interruptible_locked(priv->wait_event,
					      !list_empty(&priv->events));
	if (err) {
		event = ERR_PTR(err);
		goto out;
	}

	event = list_first_entry(&priv->events, struct ec_event, node);
	list_del(&event->node);
	priv->event_len -= sizeof(*event) + event->size;

out:
	spin_unlock(&priv->wait_event.lock);
	return event;
}

/*
 * Device file ops
 */
static int cros_ec_chardev_open(struct inode *inode, struct file *filp)
{
	struct miscdevice *mdev = filp->private_data;
	struct cros_ec_dev *ec_dev = dev_get_drvdata(mdev->parent);
	struct chardev_priv *priv;
	int ret;

	priv = kzalloc(sizeof(*priv), GFP_KERNEL);
	if (!priv)
		return -ENOMEM;

	priv->ec_dev = ec_dev;
	filp->private_data = priv;
	INIT_LIST_HEAD(&priv->events);
	init_waitqueue_head(&priv->wait_event);
	nonseekable_open(inode, filp);

	priv->notifier.notifier_call = cros_ec_chardev_mkbp_event;
	ret = blocking_notifier_chain_register(&ec_dev->ec_dev->event_notifier,
					       &priv->notifier);
	if (ret) {
		dev_err(ec_dev->dev, "failed to register event notifier\n");
		kfree(priv);
	}

	return ret;
}

static __poll_t cros_ec_chardev_poll(struct file *filp, poll_table *wait)
{
	struct chardev_priv *priv = filp->private_data;

	poll_wait(filp, &priv->wait_event, wait);

	if (list_empty(&priv->events))
		return 0;

	return EPOLLIN | EPOLLRDNORM;
}

static ssize_t cros_ec_chardev_read(struct file *filp, char __user *buffer,
				     size_t length, loff_t *offset)
{
	char msg[sizeof(struct ec_response_get_version) +
		 sizeof(CROS_EC_DEV_VERSION)];
	struct chardev_priv *priv = filp->private_data;
	struct cros_ec_dev *ec_dev = priv->ec_dev;
	size_t count;
	int ret;

	if (priv->event_mask) { /* queued MKBP event */
		struct ec_event *event;

		event = cros_ec_chardev_fetch_event(priv, length != 0,
						!(filp->f_flags & O_NONBLOCK));
		if (IS_ERR(event))
			return PTR_ERR(event);
		/*
		 * length == 0 is special - no IO is done but we check
		 * for error conditions.
		 */
		if (length == 0)
			return 0;

		/* The event is 1 byte of type plus the payload */
		count = min(length, event->size + 1);
		ret = copy_to_user(buffer, &event->event_type, count);
		kfree(event);
		if (ret) /* the copy failed */
			return -EFAULT;
		*offset = count;
		return count;
	}

	/*
	 * Legacy behavior if no event mask is defined
	 */
	if (*offset != 0)
		return 0;

	ret = ec_get_version(ec_dev, msg, sizeof(msg));
	if (ret)
		return ret;

	count = min(length, strlen(msg));

	if (copy_to_user(buffer, msg, count))
		return -EFAULT;

	*offset = count;
	return count;
}

static int cros_ec_chardev_release(struct inode *inode, struct file *filp)
{
	struct chardev_priv *priv = filp->private_data;
	struct cros_ec_dev *ec_dev = priv->ec_dev;
	struct ec_event *event, *e;

	blocking_notifier_chain_unregister(&ec_dev->ec_dev->event_notifier,
					   &priv->notifier);

	list_for_each_entry_safe(event, e, &priv->events, node) {
		list_del(&event->node);
		kfree(event);
	}
	kfree(priv);

	return 0;
}

/*
 * Ioctls
 */
static long cros_ec_chardev_ioctl_xcmd(struct cros_ec_dev *ec, void __user *arg)
{
	struct cros_ec_command *s_cmd;
	struct cros_ec_command u_cmd;
	long ret;

	if (copy_from_user(&u_cmd, arg, sizeof(u_cmd)))
		return -EFAULT;

	if (u_cmd.outsize > EC_MAX_MSG_BYTES ||
	    u_cmd.insize > EC_MAX_MSG_BYTES)
		return -EINVAL;

	s_cmd = kmalloc(sizeof(*s_cmd) + max(u_cmd.outsize, u_cmd.insize),
			GFP_KERNEL);
	if (!s_cmd)
		return -ENOMEM;

	if (copy_from_user(s_cmd, arg, sizeof(*s_cmd) + u_cmd.outsize)) {
		ret = -EFAULT;
		goto exit;
	}

	if (u_cmd.outsize != s_cmd->outsize ||
	    u_cmd.insize != s_cmd->insize) {
		ret = -EINVAL;
		goto exit;
	}

	s_cmd->command += ec->cmd_offset;
	ret = cros_ec_cmd_xfer(ec->ec_dev, s_cmd);
	/* Only copy data to userland if data was received. */
	if (ret < 0)
		goto exit;

	if (copy_to_user(arg, s_cmd, sizeof(*s_cmd) + s_cmd->insize))
		ret = -EFAULT;
exit:
	kfree(s_cmd);
	return ret;
}

static long cros_ec_chardev_ioctl_readmem(struct cros_ec_dev *ec,
					   void __user *arg)
{
	struct cros_ec_device *ec_dev = ec->ec_dev;
	struct cros_ec_readmem s_mem = { };
	long num;

	/* Not every platform supports direct reads */
	if (!ec_dev->cmd_readmem)
		return -ENOTTY;

	if (copy_from_user(&s_mem, arg, sizeof(s_mem)))
		return -EFAULT;

	num = ec_dev->cmd_readmem(ec_dev, s_mem.offset, s_mem.bytes,
				  s_mem.buffer);
	if (num <= 0)
		return num;

	if (copy_to_user((void __user *)arg, &s_mem, sizeof(s_mem)))
		return -EFAULT;

	return num;
}

static long cros_ec_chardev_ioctl(struct file *filp, unsigned int cmd,
				   unsigned long arg)
{
	struct chardev_priv *priv = filp->private_data;
	struct cros_ec_dev *ec = priv->ec_dev;

	if (_IOC_TYPE(cmd) != CROS_EC_DEV_IOC)
		return -ENOTTY;

	switch (cmd) {
	case CROS_EC_DEV_IOCXCMD:
		return cros_ec_chardev_ioctl_xcmd(ec, (void __user *)arg);
	case CROS_EC_DEV_IOCRDMEM:
		return cros_ec_chardev_ioctl_readmem(ec, (void __user *)arg);
	case CROS_EC_DEV_IOCEVENTMASK:
		priv->event_mask = arg;
		return 0;
	}

	return -ENOTTY;
}

static const struct file_operations chardev_fops = {
	.open		= cros_ec_chardev_open,
	.poll		= cros_ec_chardev_poll,
	.read		= cros_ec_chardev_read,
	.release	= cros_ec_chardev_release,
	.unlocked_ioctl	= cros_ec_chardev_ioctl,
#ifdef CONFIG_COMPAT
	.compat_ioctl	= cros_ec_chardev_ioctl,
#endif
};

static int cros_ec_chardev_probe(struct platform_device *pdev)
{
	struct cros_ec_dev *ec_dev = dev_get_drvdata(pdev->dev.parent);
	struct cros_ec_platform *ec_platform = dev_get_platdata(ec_dev->dev);
	struct chardev_data *data;

	/* Create a char device: we want to create it anew */
	data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL);
	if (!data)
		return -ENOMEM;

	data->ec_dev = ec_dev;
	data->misc.minor = MISC_DYNAMIC_MINOR;
	data->misc.fops = &chardev_fops;
	data->misc.name = ec_platform->ec_name;
	data->misc.parent = pdev->dev.parent;

	dev_set_drvdata(&pdev->dev, data);

	return misc_register(&data->misc);
}

static int cros_ec_chardev_remove(struct platform_device *pdev)
{
	struct chardev_data *data = dev_get_drvdata(&pdev->dev);

	misc_deregister(&data->misc);

	return 0;
}

static struct platform_driver cros_ec_chardev_driver = {
	.driver = {
		.name = DRV_NAME,
	},
	.probe = cros_ec_chardev_probe,
	.remove = cros_ec_chardev_remove,
};

module_platform_driver(cros_ec_chardev_driver);

MODULE_ALIAS("platform:" DRV_NAME);
MODULE_AUTHOR("Enric Balletbo i Serra <enric.balletbo@collabora.com>");
MODULE_DESCRIPTION("ChromeOS EC Miscellaneous Character Driver");
MODULE_LICENSE("GPL");
