// SPDX-License-Identifier: GPL-2.0-or-later
/*
 * tc654.c - Linux kernel modules for fan speed controller
 *
 * Copyright (C) 2016 Allied Telesis Labs NZ
 */

#include <linux/bitops.h>
#include <linux/err.h>
#include <linux/hwmon.h>
#include <linux/hwmon-sysfs.h>
#include <linux/i2c.h>
#include <linux/init.h>
#include <linux/jiffies.h>
#include <linux/module.h>
#include <linux/mutex.h>
#include <linux/slab.h>
#include <linux/thermal.h>
#include <linux/util_macros.h>

enum tc654_regs {
	TC654_REG_RPM1 = 0x00,	/* RPM Output 1 */
	TC654_REG_RPM2 = 0x01,	/* RPM Output 2 */
	TC654_REG_FAN_FAULT1 = 0x02,	/* Fan Fault 1 Threshold */
	TC654_REG_FAN_FAULT2 = 0x03,	/* Fan Fault 2 Threshold */
	TC654_REG_CONFIG = 0x04,	/* Configuration */
	TC654_REG_STATUS = 0x05,	/* Status */
	TC654_REG_DUTY_CYCLE = 0x06,	/* Fan Speed Duty Cycle */
	TC654_REG_MFR_ID = 0x07,	/* Manufacturer Identification */
	TC654_REG_VER_ID = 0x08,	/* Version Identification */
};

/* Macros to easily index the registers */
#define TC654_REG_RPM(idx)		(TC654_REG_RPM1 + (idx))
#define TC654_REG_FAN_FAULT(idx)	(TC654_REG_FAN_FAULT1 + (idx))

/* Config register bits */
#define TC654_REG_CONFIG_RES		BIT(6)	/* Resolution Selection */
#define TC654_REG_CONFIG_DUTYC		BIT(5)	/* Duty Cycle Control */
#define TC654_REG_CONFIG_SDM		BIT(0)	/* Shutdown Mode */

/* Status register bits */
#define TC654_REG_STATUS_F2F		BIT(1)	/* Fan 2 Fault */
#define TC654_REG_STATUS_F1F		BIT(0)	/* Fan 1 Fault */

/* RPM resolution for RPM Output registers */
#define TC654_HIGH_RPM_RESOLUTION	25	/* 25 RPM resolution */
#define TC654_LOW_RPM_RESOLUTION	50	/* 50 RPM resolution */

/* Convert to the fan fault RPM threshold from register value */
#define TC654_FAN_FAULT_FROM_REG(val)	((val) * 50)	/* 50 RPM resolution */

/* Convert to register value from the fan fault RPM threshold */
#define TC654_FAN_FAULT_TO_REG(val)	(((val) / 50) & 0xff)

/* Register data is read (and cached) at most once per second. */
#define TC654_UPDATE_INTERVAL		HZ

struct tc654_data {
	struct i2c_client *client;

	/* update mutex */
	struct mutex update_lock;

	/* tc654 register cache */
	bool valid;
	unsigned long last_updated;	/* in jiffies */

	u8 rpm_output[2];	/* The fan RPM data for fans 1 and 2 is then
				 * written to registers RPM1 and RPM2
				 */
	u8 fan_fault[2];	/* The Fan Fault Threshold Registers are used to
				 * set the fan fault threshold levels for fan 1
				 * and fan 2
				 */
	u8 config;	/* The Configuration Register is an 8-bit read/
			 * writable multi-function control register
			 *   7: Fan Fault Clear
			 *      1 = Clear Fan Fault
			 *      0 = Normal Operation (default)
			 *   6: Resolution Selection for RPM Output Registers
			 *      RPM Output Registers (RPM1 and RPM2) will be
			 *      set for
			 *      1 = 25 RPM (9-bit) resolution
			 *      0 = 50 RPM (8-bit) resolution (default)
			 *   5: Duty Cycle Control Method
			 *      The V OUT duty cycle will be controlled via
			 *      1 = the SMBus interface.
			 *      0 = via the V IN analog input pin. (default)
			 * 4,3: Fan 2 Pulses Per Rotation
			 *      00 = 1
			 *      01 = 2 (default)
			 *      10 = 4
			 *      11 = 8
			 * 2,1: Fan 1 Pulses Per Rotation
			 *      00 = 1
			 *      01 = 2 (default)
			 *      10 = 4
			 *      11 = 8
			 *   0: Shutdown Mode
			 *      1 = Shutdown mode.
			 *      0 = Normal operation. (default)
			 */
	u8 status;	/* The Status register provides all the information
			 * about what is going on within the TC654/TC655
			 * devices.
			 * 7,6: Unimplemented, Read as '0'
			 *   5: Over-Temperature Fault Condition
			 *      1 = Over-Temperature condition has occurred
			 *      0 = Normal operation. V IN is less than 2.6V
			 *   4: RPM2 Counter Overflow
			 *      1 = Fault condition
			 *      0 = Normal operation
			 *   3: RPM1 Counter Overflow
			 *      1 = Fault condition
			 *      0 = Normal operation
			 *   2: V IN Input Status
			 *      1 = V IN is open
			 *      0 = Normal operation. voltage present at V IN
			 *   1: Fan 2 Fault
			 *      1 = Fault condition
			 *      0 = Normal operation
			 *   0: Fan 1 Fault
			 *      1 = Fault condition
			 *      0 = Normal operation
			 */
	u8 duty_cycle;	/* The DUTY_CYCLE register is a 4-bit read/
			 * writable register used to control the duty
			 * cycle of the V OUT output.
			 */
};

/* helper to grab and cache data, at most one time per second */
static struct tc654_data *tc654_update_client(struct device *dev)
{
	struct tc654_data *data = dev_get_drvdata(dev);
	struct i2c_client *client = data->client;
	int ret = 0;

	mutex_lock(&data->update_lock);
	if (time_before(jiffies, data->last_updated + TC654_UPDATE_INTERVAL) &&
	    likely(data->valid))
		goto out;

	ret = i2c_smbus_read_byte_data(client, TC654_REG_RPM(0));
	if (ret < 0)
		goto out;
	data->rpm_output[0] = ret;

	ret = i2c_smbus_read_byte_data(client, TC654_REG_RPM(1));
	if (ret < 0)
		goto out;
	data->rpm_output[1] = ret;

	ret = i2c_smbus_read_byte_data(client, TC654_REG_FAN_FAULT(0));
	if (ret < 0)
		goto out;
	data->fan_fault[0] = ret;

	ret = i2c_smbus_read_byte_data(client, TC654_REG_FAN_FAULT(1));
	if (ret < 0)
		goto out;
	data->fan_fault[1] = ret;

	ret = i2c_smbus_read_byte_data(client, TC654_REG_CONFIG);
	if (ret < 0)
		goto out;
	data->config = ret;

	ret = i2c_smbus_read_byte_data(client, TC654_REG_STATUS);
	if (ret < 0)
		goto out;
	data->status = ret;

	ret = i2c_smbus_read_byte_data(client, TC654_REG_DUTY_CYCLE);
	if (ret < 0)
		goto out;
	data->duty_cycle = ret & 0x0f;

	data->last_updated = jiffies;
	data->valid = true;
out:
	mutex_unlock(&data->update_lock);

	if (ret < 0)		/* upon error, encode it in return value */
		data = ERR_PTR(ret);

	return data;
}

/*
 * sysfs attributes
 */

static ssize_t fan_show(struct device *dev, struct device_attribute *da,
			char *buf)
{
	int nr = to_sensor_dev_attr(da)->index;
	struct tc654_data *data = tc654_update_client(dev);
	int val;

	if (IS_ERR(data))
		return PTR_ERR(data);

	if (data->config & TC654_REG_CONFIG_RES)
		val = data->rpm_output[nr] * TC654_HIGH_RPM_RESOLUTION;
	else
		val = data->rpm_output[nr] * TC654_LOW_RPM_RESOLUTION;

	return sprintf(buf, "%d\n", val);
}

static ssize_t fan_min_show(struct device *dev, struct device_attribute *da,
			    char *buf)
{
	int nr = to_sensor_dev_attr(da)->index;
	struct tc654_data *data = tc654_update_client(dev);

	if (IS_ERR(data))
		return PTR_ERR(data);

	return sprintf(buf, "%d\n",
		       TC654_FAN_FAULT_FROM_REG(data->fan_fault[nr]));
}

static ssize_t fan_min_store(struct device *dev, struct device_attribute *da,
			     const char *buf, size_t count)
{
	int nr = to_sensor_dev_attr(da)->index;
	struct tc654_data *data = dev_get_drvdata(dev);
	struct i2c_client *client = data->client;
	unsigned long val;
	int ret;

	if (kstrtoul(buf, 10, &val))
		return -EINVAL;

	val = clamp_val(val, 0, 12750);

	mutex_lock(&data->update_lock);

	data->fan_fault[nr] = TC654_FAN_FAULT_TO_REG(val);
	ret = i2c_smbus_write_byte_data(client, TC654_REG_FAN_FAULT(nr),
					data->fan_fault[nr]);

	mutex_unlock(&data->update_lock);
	return ret < 0 ? ret : count;
}

static ssize_t fan_alarm_show(struct device *dev, struct device_attribute *da,
			      char *buf)
{
	int nr = to_sensor_dev_attr(da)->index;
	struct tc654_data *data = tc654_update_client(dev);
	int val;

	if (IS_ERR(data))
		return PTR_ERR(data);

	if (nr == 0)
		val = !!(data->status & TC654_REG_STATUS_F1F);
	else
		val = !!(data->status & TC654_REG_STATUS_F2F);

	return sprintf(buf, "%d\n", val);
}

static const u8 TC654_FAN_PULSE_SHIFT[] = { 1, 3 };

static ssize_t fan_pulses_show(struct device *dev,
			       struct device_attribute *da, char *buf)
{
	int nr = to_sensor_dev_attr(da)->index;
	struct tc654_data *data = tc654_update_client(dev);
	u8 val;

	if (IS_ERR(data))
		return PTR_ERR(data);

	val = BIT((data->config >> TC654_FAN_PULSE_SHIFT[nr]) & 0x03);
	return sprintf(buf, "%d\n", val);
}

static ssize_t fan_pulses_store(struct device *dev,
				struct device_attribute *da, const char *buf,
				size_t count)
{
	int nr = to_sensor_dev_attr(da)->index;
	struct tc654_data *data = dev_get_drvdata(dev);
	struct i2c_client *client = data->client;
	u8 config;
	unsigned long val;
	int ret;

	if (kstrtoul(buf, 10, &val))
		return -EINVAL;

	switch (val) {
	case 1:
		config = 0;
		break;
	case 2:
		config = 1;
		break;
	case 4:
		config = 2;
		break;
	case 8:
		config = 3;
		break;
	default:
		return -EINVAL;
	}

	mutex_lock(&data->update_lock);

	data->config &= ~(0x03 << TC654_FAN_PULSE_SHIFT[nr]);
	data->config |= (config << TC654_FAN_PULSE_SHIFT[nr]);
	ret = i2c_smbus_write_byte_data(client, TC654_REG_CONFIG, data->config);

	mutex_unlock(&data->update_lock);
	return ret < 0 ? ret : count;
}

static ssize_t pwm_mode_show(struct device *dev, struct device_attribute *da,
			     char *buf)
{
	struct tc654_data *data = tc654_update_client(dev);

	if (IS_ERR(data))
		return PTR_ERR(data);

	return sprintf(buf, "%d\n", !!(data->config & TC654_REG_CONFIG_DUTYC));
}

static ssize_t pwm_mode_store(struct device *dev, struct device_attribute *da,
			      const char *buf, size_t count)
{
	struct tc654_data *data = dev_get_drvdata(dev);
	struct i2c_client *client = data->client;
	unsigned long val;
	int ret;

	if (kstrtoul(buf, 10, &val))
		return -EINVAL;

	if (val != 0 && val != 1)
		return -EINVAL;

	mutex_lock(&data->update_lock);

	if (val)
		data->config |= TC654_REG_CONFIG_DUTYC;
	else
		data->config &= ~TC654_REG_CONFIG_DUTYC;

	ret = i2c_smbus_write_byte_data(client, TC654_REG_CONFIG, data->config);

	mutex_unlock(&data->update_lock);
	return ret < 0 ? ret : count;
}

static const int tc654_pwm_map[16] = { 77,  88, 102, 112, 124, 136, 148, 160,
				      172, 184, 196, 207, 219, 231, 243, 255};

static ssize_t pwm_show(struct device *dev, struct device_attribute *da,
			char *buf)
{
	struct tc654_data *data = tc654_update_client(dev);
	int pwm;

	if (IS_ERR(data))
		return PTR_ERR(data);

	if (data->config & TC654_REG_CONFIG_SDM)
		pwm = 0;
	else
		pwm = tc654_pwm_map[data->duty_cycle];

	return sprintf(buf, "%d\n", pwm);
}

static int _set_pwm(struct tc654_data *data, unsigned long val)
{
	struct i2c_client *client = data->client;
	int ret;

	mutex_lock(&data->update_lock);

	if (val == 0) {
		data->config |= TC654_REG_CONFIG_SDM;
		data->duty_cycle = 0;
	} else {
		data->config &= ~TC654_REG_CONFIG_SDM;
		data->duty_cycle = val - 1;
	}

	ret = i2c_smbus_write_byte_data(client, TC654_REG_CONFIG, data->config);
	if (ret < 0)
		goto out;

	ret = i2c_smbus_write_byte_data(client, TC654_REG_DUTY_CYCLE,
					data->duty_cycle);

out:
	mutex_unlock(&data->update_lock);
	return ret;
}

static ssize_t pwm_store(struct device *dev, struct device_attribute *da,
			 const char *buf, size_t count)
{
	struct tc654_data *data = dev_get_drvdata(dev);
	unsigned long val;
	int ret;

	if (kstrtoul(buf, 10, &val))
		return -EINVAL;
	if (val > 255)
		return -EINVAL;
	if (val > 0)
		val = find_closest(val, tc654_pwm_map, ARRAY_SIZE(tc654_pwm_map)) + 1;

	ret = _set_pwm(data, val);
	return ret < 0 ? ret : count;
}

static SENSOR_DEVICE_ATTR_RO(fan1_input, fan, 0);
static SENSOR_DEVICE_ATTR_RO(fan2_input, fan, 1);
static SENSOR_DEVICE_ATTR_RW(fan1_min, fan_min, 0);
static SENSOR_DEVICE_ATTR_RW(fan2_min, fan_min, 1);
static SENSOR_DEVICE_ATTR_RO(fan1_alarm, fan_alarm, 0);
static SENSOR_DEVICE_ATTR_RO(fan2_alarm, fan_alarm, 1);
static SENSOR_DEVICE_ATTR_RW(fan1_pulses, fan_pulses, 0);
static SENSOR_DEVICE_ATTR_RW(fan2_pulses, fan_pulses, 1);
static SENSOR_DEVICE_ATTR_RW(pwm1_mode, pwm_mode, 0);
static SENSOR_DEVICE_ATTR_RW(pwm1, pwm, 0);

/* Driver data */
static struct attribute *tc654_attrs[] = {
	&sensor_dev_attr_fan1_input.dev_attr.attr,
	&sensor_dev_attr_fan2_input.dev_attr.attr,
	&sensor_dev_attr_fan1_min.dev_attr.attr,
	&sensor_dev_attr_fan2_min.dev_attr.attr,
	&sensor_dev_attr_fan1_alarm.dev_attr.attr,
	&sensor_dev_attr_fan2_alarm.dev_attr.attr,
	&sensor_dev_attr_fan1_pulses.dev_attr.attr,
	&sensor_dev_attr_fan2_pulses.dev_attr.attr,
	&sensor_dev_attr_pwm1_mode.dev_attr.attr,
	&sensor_dev_attr_pwm1.dev_attr.attr,
	NULL
};

ATTRIBUTE_GROUPS(tc654);

/*
 * thermal cooling device functions
 *
 * Account for the "ShutDown Mode (SDM)" state by offsetting
 * the 16 PWM duty cycle states by 1.
 *
 * State  0 =   0% PWM | Shutdown - Fan(s) are off
 * State  1 =  30% PWM | duty_cycle =  0
 * State  2 = ~35% PWM | duty_cycle =  1
 * [...]
 * State 15 = ~95% PWM | duty_cycle = 14
 * State 16 = 100% PWM | duty_cycle = 15
 */
#define TC654_MAX_COOLING_STATE	16

static int tc654_get_max_state(struct thermal_cooling_device *cdev, unsigned long *state)
{
	*state = TC654_MAX_COOLING_STATE;
	return 0;
}

static int tc654_get_cur_state(struct thermal_cooling_device *cdev, unsigned long *state)
{
	struct tc654_data *data = tc654_update_client(cdev->devdata);

	if (IS_ERR(data))
		return PTR_ERR(data);

	if (data->config & TC654_REG_CONFIG_SDM)
		*state = 0;	/* FAN is off */
	else
		*state = data->duty_cycle + 1;	/* offset PWM States by 1 */

	return 0;
}

static int tc654_set_cur_state(struct thermal_cooling_device *cdev, unsigned long state)
{
	struct tc654_data *data = tc654_update_client(cdev->devdata);

	if (IS_ERR(data))
		return PTR_ERR(data);

	return _set_pwm(data, clamp_val(state, 0, TC654_MAX_COOLING_STATE));
}

static const struct thermal_cooling_device_ops tc654_fan_cool_ops = {
	.get_max_state = tc654_get_max_state,
	.get_cur_state = tc654_get_cur_state,
	.set_cur_state = tc654_set_cur_state,
};

/*
 * device probe and removal
 */

static int tc654_probe(struct i2c_client *client)
{
	struct device *dev = &client->dev;
	struct tc654_data *data;
	struct device *hwmon_dev;
	int ret;

	if (!i2c_check_functionality(client->adapter, I2C_FUNC_SMBUS_BYTE_DATA))
		return -ENODEV;

	data = devm_kzalloc(dev, sizeof(struct tc654_data), GFP_KERNEL);
	if (!data)
		return -ENOMEM;

	data->client = client;
	mutex_init(&data->update_lock);

	ret = i2c_smbus_read_byte_data(client, TC654_REG_CONFIG);
	if (ret < 0)
		return ret;

	data->config = ret;

	hwmon_dev =
	    devm_hwmon_device_register_with_groups(dev, client->name, data,
						   tc654_groups);
	if (IS_ERR(hwmon_dev))
		return PTR_ERR(hwmon_dev);

	if (IS_ENABLED(CONFIG_THERMAL)) {
		struct thermal_cooling_device *cdev;

		cdev = devm_thermal_of_cooling_device_register(dev, dev->of_node, client->name,
							       hwmon_dev, &tc654_fan_cool_ops);
		return PTR_ERR_OR_ZERO(cdev);
	}

	return 0;
}

static const struct i2c_device_id tc654_id[] = {
	{"tc654", 0},
	{"tc655", 0},
	{}
};

MODULE_DEVICE_TABLE(i2c, tc654_id);

static struct i2c_driver tc654_driver = {
	.driver = {
		   .name = "tc654",
		   },
	.probe_new = tc654_probe,
	.id_table = tc654_id,
};

module_i2c_driver(tc654_driver);

MODULE_AUTHOR("Allied Telesis Labs");
MODULE_DESCRIPTION("Microchip TC654/TC655 driver");
MODULE_LICENSE("GPL");
