// SPDX-License-Identifier: GPL-2.0
// Copyright (C) 2020 ROHM Semiconductors

#include <linux/errno.h>
#include <linux/mfd/rohm-generic.h>
#include <linux/module.h>
#include <linux/of.h>
#include <linux/regmap.h>
#include <linux/regulator/driver.h>

static int set_dvs_level(const struct regulator_desc *desc,
			 struct device_node *np, struct regmap *regmap,
			 char *prop, unsigned int reg, unsigned int mask,
			 unsigned int omask, unsigned int oreg)
{
	int ret, i;
	uint32_t uv;

	ret = of_property_read_u32(np, prop, &uv);
	if (ret) {
		if (ret != -EINVAL)
			return ret;
		return 0;
	}
	/* If voltage is set to 0 => disable */
	if (uv == 0) {
		if (omask)
			return regmap_update_bits(regmap, oreg, omask, 0);
	}
	/* Some setups don't allow setting own voltage but do allow enabling */
	if (!mask) {
		if (omask)
			return regmap_update_bits(regmap, oreg, omask, omask);

		return -EINVAL;
	}
	for (i = 0; i < desc->n_voltages; i++) {
		/* NOTE to next hacker - Does not support pickable ranges */
		if (desc->linear_range_selectors_bitfield)
			return -EINVAL;
		if (desc->n_linear_ranges)
			ret = regulator_desc_list_voltage_linear_range(desc, i);
		else
			ret = regulator_desc_list_voltage_linear(desc, i);
		if (ret < 0)
			continue;
		if (ret == uv) {
			i <<= ffs(desc->vsel_mask) - 1;

			ret = regmap_update_bits(regmap, reg, mask, i);
			if (omask && !ret)
				ret = regmap_update_bits(regmap, oreg, omask,
							 omask);
			break;
		}
	}
	if (i == desc->n_voltages)
		pr_warn("Unsupported %s voltage %u\n", prop, uv);

	return ret;
}

int rohm_regulator_set_dvs_levels(const struct rohm_dvs_config *dvs,
			  struct device_node *np,
			  const struct regulator_desc *desc,
			  struct regmap *regmap)
{
	int i, ret = 0;
	char *prop;
	unsigned int reg, mask, omask, oreg = desc->enable_reg;

	for (i = 0; i < ROHM_DVS_LEVEL_VALID_AMOUNT && !ret; i++) {
		int bit;

		bit = BIT(i);
		if (dvs->level_map & bit) {
			switch (bit) {
			case ROHM_DVS_LEVEL_RUN:
				prop = "rohm,dvs-run-voltage";
				reg = dvs->run_reg;
				mask = dvs->run_mask;
				omask = dvs->run_on_mask;
				break;
			case ROHM_DVS_LEVEL_IDLE:
				prop = "rohm,dvs-idle-voltage";
				reg = dvs->idle_reg;
				mask = dvs->idle_mask;
				omask = dvs->idle_on_mask;
				break;
			case ROHM_DVS_LEVEL_SUSPEND:
				prop = "rohm,dvs-suspend-voltage";
				reg = dvs->suspend_reg;
				mask = dvs->suspend_mask;
				omask = dvs->suspend_on_mask;
				break;
			case ROHM_DVS_LEVEL_LPSR:
				prop = "rohm,dvs-lpsr-voltage";
				reg = dvs->lpsr_reg;
				mask = dvs->lpsr_mask;
				omask = dvs->lpsr_on_mask;
				break;
			case ROHM_DVS_LEVEL_SNVS:
				prop = "rohm,dvs-snvs-voltage";
				reg = dvs->snvs_reg;
				mask = dvs->snvs_mask;
				omask = dvs->snvs_on_mask;
				break;
			default:
				return -EINVAL;
			}
			ret = set_dvs_level(desc, np, regmap, prop, reg, mask,
					    omask, oreg);
		}
	}
	return ret;
}
EXPORT_SYMBOL(rohm_regulator_set_dvs_levels);

/*
 * Few ROHM PMIC ICs have constrains on voltage changing:
 * BD71837 - only buck 1-4 voltages can be changed when they are enabled.
 * Other bucks and all LDOs must be disabled when voltage is changed.
 * BD96801 - LDO voltage levels can be changed when LDOs are disabled.
 */
int rohm_regulator_set_voltage_sel_restricted(struct regulator_dev *rdev,
					      unsigned int sel)
{
	if (rdev->desc->ops->is_enabled(rdev))
		return -EBUSY;

	return regulator_set_voltage_sel_regmap(rdev, sel);
}
EXPORT_SYMBOL_GPL(rohm_regulator_set_voltage_sel_restricted);

MODULE_LICENSE("GPL v2");
MODULE_AUTHOR("Matti Vaittinen <matti.vaittinen@fi.rohmeurope.com>");
MODULE_DESCRIPTION("Generic helpers for ROHM PMIC regulator drivers");
