// SPDX-License-Identifier: GPL-2.0-only
/*
 * devfreq-event: a framework to provide raw data and events of devfreq devices
 *
 * Copyright (C) 2015 Samsung Electronics
 * Author: Chanwoo Choi <cw00.choi@samsung.com>
 *
 * This driver is based on drivers/devfreq/devfreq.c.
 */

#include <linux/devfreq-event.h>
#include <linux/kernel.h>
#include <linux/err.h>
#include <linux/init.h>
#include <linux/export.h>
#include <linux/slab.h>
#include <linux/list.h>
#include <linux/of.h>

static struct class *devfreq_event_class;

/* The list of all devfreq event list */
static LIST_HEAD(devfreq_event_list);
static DEFINE_MUTEX(devfreq_event_list_lock);

#define to_devfreq_event(DEV) container_of(DEV, struct devfreq_event_dev, dev)

/**
 * devfreq_event_enable_edev() - Enable the devfreq-event dev and increase
 *				 the enable_count of devfreq-event dev.
 * @edev	: the devfreq-event device
 *
 * Note that this function increase the enable_count and enable the
 * devfreq-event device. The devfreq-event device should be enabled before
 * using it by devfreq device.
 */
int devfreq_event_enable_edev(struct devfreq_event_dev *edev)
{
	int ret = 0;

	if (!edev || !edev->desc)
		return -EINVAL;

	mutex_lock(&edev->lock);
	if (edev->desc->ops && edev->desc->ops->enable
			&& edev->enable_count == 0) {
		ret = edev->desc->ops->enable(edev);
		if (ret < 0)
			goto err;
	}
	edev->enable_count++;
err:
	mutex_unlock(&edev->lock);

	return ret;
}
EXPORT_SYMBOL_GPL(devfreq_event_enable_edev);

/**
 * devfreq_event_disable_edev() - Disable the devfreq-event dev and decrease
 *				  the enable_count of the devfreq-event dev.
 * @edev	: the devfreq-event device
 *
 * Note that this function decrease the enable_count and disable the
 * devfreq-event device. After the devfreq-event device is disabled,
 * devfreq device can't use the devfreq-event device for get/set/reset
 * operations.
 */
int devfreq_event_disable_edev(struct devfreq_event_dev *edev)
{
	int ret = 0;

	if (!edev || !edev->desc)
		return -EINVAL;

	mutex_lock(&edev->lock);
	if (edev->enable_count <= 0) {
		dev_warn(&edev->dev, "unbalanced enable_count\n");
		ret = -EIO;
		goto err;
	}

	if (edev->desc->ops && edev->desc->ops->disable
			&& edev->enable_count == 1) {
		ret = edev->desc->ops->disable(edev);
		if (ret < 0)
			goto err;
	}
	edev->enable_count--;
err:
	mutex_unlock(&edev->lock);

	return ret;
}
EXPORT_SYMBOL_GPL(devfreq_event_disable_edev);

/**
 * devfreq_event_is_enabled() - Check whether devfreq-event dev is enabled or
 *				not.
 * @edev	: the devfreq-event device
 *
 * Note that this function check whether devfreq-event dev is enabled or not.
 * If return true, the devfreq-event dev is enabeld. If return false, the
 * devfreq-event dev is disabled.
 */
bool devfreq_event_is_enabled(struct devfreq_event_dev *edev)
{
	bool enabled = false;

	if (!edev || !edev->desc)
		return enabled;

	mutex_lock(&edev->lock);

	if (edev->enable_count > 0)
		enabled = true;

	mutex_unlock(&edev->lock);

	return enabled;
}
EXPORT_SYMBOL_GPL(devfreq_event_is_enabled);

/**
 * devfreq_event_set_event() - Set event to devfreq-event dev to start.
 * @edev	: the devfreq-event device
 *
 * Note that this function set the event to the devfreq-event device to start
 * for getting the event data which could be various event type.
 */
int devfreq_event_set_event(struct devfreq_event_dev *edev)
{
	int ret;

	if (!edev || !edev->desc)
		return -EINVAL;

	if (!edev->desc->ops || !edev->desc->ops->set_event)
		return -EINVAL;

	if (!devfreq_event_is_enabled(edev))
		return -EPERM;

	mutex_lock(&edev->lock);
	ret = edev->desc->ops->set_event(edev);
	mutex_unlock(&edev->lock);

	return ret;
}
EXPORT_SYMBOL_GPL(devfreq_event_set_event);

/**
 * devfreq_event_get_event() - Get {load|total}_count from devfreq-event dev.
 * @edev	: the devfreq-event device
 * @edata	: the calculated data of devfreq-event device
 *
 * Note that this function get the calculated event data from devfreq-event dev
 * after stoping the progress of whole sequence of devfreq-event dev.
 */
int devfreq_event_get_event(struct devfreq_event_dev *edev,
			    struct devfreq_event_data *edata)
{
	int ret;

	if (!edev || !edev->desc)
		return -EINVAL;

	if (!edev->desc->ops || !edev->desc->ops->get_event)
		return -EINVAL;

	if (!devfreq_event_is_enabled(edev))
		return -EINVAL;

	edata->total_count = edata->load_count = 0;

	mutex_lock(&edev->lock);
	ret = edev->desc->ops->get_event(edev, edata);
	if (ret < 0)
		edata->total_count = edata->load_count = 0;
	mutex_unlock(&edev->lock);

	return ret;
}
EXPORT_SYMBOL_GPL(devfreq_event_get_event);

/**
 * devfreq_event_reset_event() - Reset all opeations of devfreq-event dev.
 * @edev	: the devfreq-event device
 *
 * Note that this function stop all operations of devfreq-event dev and reset
 * the current event data to make the devfreq-event device into initial state.
 */
int devfreq_event_reset_event(struct devfreq_event_dev *edev)
{
	int ret = 0;

	if (!edev || !edev->desc)
		return -EINVAL;

	if (!devfreq_event_is_enabled(edev))
		return -EPERM;

	mutex_lock(&edev->lock);
	if (edev->desc->ops && edev->desc->ops->reset)
		ret = edev->desc->ops->reset(edev);
	mutex_unlock(&edev->lock);

	return ret;
}
EXPORT_SYMBOL_GPL(devfreq_event_reset_event);

/**
 * devfreq_event_get_edev_by_phandle() - Get the devfreq-event dev from
 *					 devicetree.
 * @dev		: the pointer to the given device
 * @index	: the index into list of devfreq-event device
 *
 * Note that this function return the pointer of devfreq-event device.
 */
struct devfreq_event_dev *devfreq_event_get_edev_by_phandle(struct device *dev,
						      int index)
{
	struct device_node *node;
	struct devfreq_event_dev *edev;

	if (!dev->of_node)
		return ERR_PTR(-EINVAL);

	node = of_parse_phandle(dev->of_node, "devfreq-events", index);
	if (!node)
		return ERR_PTR(-ENODEV);

	mutex_lock(&devfreq_event_list_lock);
	list_for_each_entry(edev, &devfreq_event_list, node) {
		if (edev->dev.parent && edev->dev.parent->of_node == node)
			goto out;
	}

	list_for_each_entry(edev, &devfreq_event_list, node) {
		if (of_node_name_eq(node, edev->desc->name))
			goto out;
	}
	edev = NULL;
out:
	mutex_unlock(&devfreq_event_list_lock);

	if (!edev) {
		of_node_put(node);
		return ERR_PTR(-ENODEV);
	}

	of_node_put(node);

	return edev;
}
EXPORT_SYMBOL_GPL(devfreq_event_get_edev_by_phandle);

/**
 * devfreq_event_get_edev_count() - Get the count of devfreq-event dev
 * @dev		: the pointer to the given device
 *
 * Note that this function return the count of devfreq-event devices.
 */
int devfreq_event_get_edev_count(struct device *dev)
{
	int count;

	if (!dev->of_node) {
		dev_err(dev, "device does not have a device node entry\n");
		return -EINVAL;
	}

	count = of_property_count_elems_of_size(dev->of_node, "devfreq-events",
						sizeof(u32));
	if (count < 0) {
		dev_err(dev,
			"failed to get the count of devfreq-event in %pOF node\n",
			dev->of_node);
		return count;
	}

	return count;
}
EXPORT_SYMBOL_GPL(devfreq_event_get_edev_count);

static void devfreq_event_release_edev(struct device *dev)
{
	struct devfreq_event_dev *edev = to_devfreq_event(dev);

	kfree(edev);
}

/**
 * devfreq_event_add_edev() - Add new devfreq-event device.
 * @dev		: the device owning the devfreq-event device being created
 * @desc	: the devfreq-event device's decriptor which include essential
 *		  data for devfreq-event device.
 *
 * Note that this function add new devfreq-event device to devfreq-event class
 * list and register the device of the devfreq-event device.
 */
struct devfreq_event_dev *devfreq_event_add_edev(struct device *dev,
						struct devfreq_event_desc *desc)
{
	struct devfreq_event_dev *edev;
	static atomic_t event_no = ATOMIC_INIT(-1);
	int ret;

	if (!dev || !desc)
		return ERR_PTR(-EINVAL);

	if (!desc->name || !desc->ops)
		return ERR_PTR(-EINVAL);

	if (!desc->ops->set_event || !desc->ops->get_event)
		return ERR_PTR(-EINVAL);

	edev = kzalloc(sizeof(struct devfreq_event_dev), GFP_KERNEL);
	if (!edev)
		return ERR_PTR(-ENOMEM);

	mutex_init(&edev->lock);
	edev->desc = desc;
	edev->enable_count = 0;
	edev->dev.parent = dev;
	edev->dev.class = devfreq_event_class;
	edev->dev.release = devfreq_event_release_edev;

	dev_set_name(&edev->dev, "event%d", atomic_inc_return(&event_no));
	ret = device_register(&edev->dev);
	if (ret < 0) {
		put_device(&edev->dev);
		return ERR_PTR(ret);
	}
	dev_set_drvdata(&edev->dev, edev);

	INIT_LIST_HEAD(&edev->node);

	mutex_lock(&devfreq_event_list_lock);
	list_add(&edev->node, &devfreq_event_list);
	mutex_unlock(&devfreq_event_list_lock);

	return edev;
}
EXPORT_SYMBOL_GPL(devfreq_event_add_edev);

/**
 * devfreq_event_remove_edev() - Remove the devfreq-event device registered.
 * @dev		: the devfreq-event device
 *
 * Note that this function remove the registered devfreq-event device.
 */
int devfreq_event_remove_edev(struct devfreq_event_dev *edev)
{
	if (!edev)
		return -EINVAL;

	WARN_ON(edev->enable_count);

	mutex_lock(&devfreq_event_list_lock);
	list_del(&edev->node);
	mutex_unlock(&devfreq_event_list_lock);

	device_unregister(&edev->dev);

	return 0;
}
EXPORT_SYMBOL_GPL(devfreq_event_remove_edev);

static int devm_devfreq_event_match(struct device *dev, void *res, void *data)
{
	struct devfreq_event_dev **r = res;

	if (WARN_ON(!r || !*r))
		return 0;

	return *r == data;
}

static void devm_devfreq_event_release(struct device *dev, void *res)
{
	devfreq_event_remove_edev(*(struct devfreq_event_dev **)res);
}

/**
 * devm_devfreq_event_add_edev() - Resource-managed devfreq_event_add_edev()
 * @dev		: the device owning the devfreq-event device being created
 * @desc	: the devfreq-event device's decriptor which include essential
 *		  data for devfreq-event device.
 *
 * Note that this function manages automatically the memory of devfreq-event
 * device using device resource management and simplify the free operation
 * for memory of devfreq-event device.
 */
struct devfreq_event_dev *devm_devfreq_event_add_edev(struct device *dev,
						struct devfreq_event_desc *desc)
{
	struct devfreq_event_dev **ptr, *edev;

	ptr = devres_alloc(devm_devfreq_event_release, sizeof(*ptr),
				GFP_KERNEL);
	if (!ptr)
		return ERR_PTR(-ENOMEM);

	edev = devfreq_event_add_edev(dev, desc);
	if (IS_ERR(edev)) {
		devres_free(ptr);
		return ERR_PTR(-ENOMEM);
	}

	*ptr = edev;
	devres_add(dev, ptr);

	return edev;
}
EXPORT_SYMBOL_GPL(devm_devfreq_event_add_edev);

/**
 * devm_devfreq_event_remove_edev()- Resource-managed devfreq_event_remove_edev()
 * @dev		: the device owning the devfreq-event device being created
 * @edev	: the devfreq-event device
 *
 * Note that this function manages automatically the memory of devfreq-event
 * device using device resource management.
 */
void devm_devfreq_event_remove_edev(struct device *dev,
				struct devfreq_event_dev *edev)
{
	WARN_ON(devres_release(dev, devm_devfreq_event_release,
			       devm_devfreq_event_match, edev));
}
EXPORT_SYMBOL_GPL(devm_devfreq_event_remove_edev);

/*
 * Device attributes for devfreq-event class.
 */
static ssize_t name_show(struct device *dev, struct device_attribute *attr,
			 char *buf)
{
	struct devfreq_event_dev *edev = to_devfreq_event(dev);

	if (!edev || !edev->desc)
		return -EINVAL;

	return sprintf(buf, "%s\n", edev->desc->name);
}
static DEVICE_ATTR_RO(name);

static ssize_t enable_count_show(struct device *dev,
				  struct device_attribute *attr, char *buf)
{
	struct devfreq_event_dev *edev = to_devfreq_event(dev);

	if (!edev || !edev->desc)
		return -EINVAL;

	return sprintf(buf, "%d\n", edev->enable_count);
}
static DEVICE_ATTR_RO(enable_count);

static struct attribute *devfreq_event_attrs[] = {
	&dev_attr_name.attr,
	&dev_attr_enable_count.attr,
	NULL,
};
ATTRIBUTE_GROUPS(devfreq_event);

static int __init devfreq_event_init(void)
{
	devfreq_event_class = class_create(THIS_MODULE, "devfreq-event");
	if (IS_ERR(devfreq_event_class)) {
		pr_err("%s: couldn't create class\n", __FILE__);
		return PTR_ERR(devfreq_event_class);
	}

	devfreq_event_class->dev_groups = devfreq_event_groups;

	return 0;
}
subsys_initcall(devfreq_event_init);
