/*
 * Copyright (c) 2015-2017, The Linux Foundation. All rights reserved.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 and
 * only 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.
 */

/*
 * This file contains utility functions to be used by platform specific CPR3
 * regulator drivers.
 */

#define pr_fmt(fmt) "%s: " fmt, __func__

#include <linux/cpumask.h>
#include <linux/device.h>
#include <linux/io.h>
#include <linux/kernel.h>
#include <linux/of.h>
#include <linux/platform_device.h>
#include <linux/slab.h>
#include <linux/types.h>

#include "cpr3-regulator.h"

#define BYTES_PER_FUSE_ROW		8
#define MAX_FUSE_ROW_BIT		63

#define CPR3_CONSECUTIVE_UP_DOWN_MIN	0
#define CPR3_CONSECUTIVE_UP_DOWN_MAX	15
#define CPR3_UP_DOWN_THRESHOLD_MIN	0
#define CPR3_UP_DOWN_THRESHOLD_MAX	31
#define CPR3_STEP_QUOT_MIN		0
#define CPR3_STEP_QUOT_MAX		63
#define CPR3_IDLE_CLOCKS_MIN		0
#define CPR3_IDLE_CLOCKS_MAX		31

/* This constant has units of uV/mV so 1000 corresponds to 100%. */
#define CPR3_AGING_DERATE_UNITY		1000

/**
 * cpr3_allocate_regulators() - allocate and initialize CPR3 regulators for a
 *		given thread based upon device tree data
 * @thread:		Pointer to the CPR3 thread
 *
 * This function allocates the thread->vreg array based upon the number of
 * device tree regulator subnodes.  It also initializes generic elements of each
 * regulator struct such as name, of_node, and thread.
 *
 * Return: 0 on success, errno on failure
 */
static int cpr3_allocate_regulators(struct cpr3_thread *thread)
{
	struct device_node *node;
	int i, rc;

	thread->vreg_count = 0;

	for_each_available_child_of_node(thread->of_node, node) {
		thread->vreg_count++;
	}

	thread->vreg = devm_kcalloc(thread->ctrl->dev, thread->vreg_count,
			sizeof(*thread->vreg), GFP_KERNEL);
	if (!thread->vreg)
		return -ENOMEM;

	i = 0;
	for_each_available_child_of_node(thread->of_node, node) {
		thread->vreg[i].of_node = node;
		thread->vreg[i].thread = thread;

		rc = of_property_read_string(node, "regulator-name",
						&thread->vreg[i].name);
		if (rc) {
			dev_err(thread->ctrl->dev, "could not find regulator name, rc=%d\n",
				rc);
			return rc;
		}

		i++;
	}

	return 0;
}

/**
 * cpr3_allocate_threads() - allocate and initialize CPR3 threads for a given
 *			     controller based upon device tree data
 * @ctrl:		Pointer to the CPR3 controller
 * @min_thread_id:	Minimum allowed hardware thread ID for this controller
 * @max_thread_id:	Maximum allowed hardware thread ID for this controller
 *
 * This function allocates the ctrl->thread array based upon the number of
 * device tree thread subnodes.  It also initializes generic elements of each
 * thread struct such as thread_id, of_node, ctrl, and vreg array.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_allocate_threads(struct cpr3_controller *ctrl, u32 min_thread_id,
			u32 max_thread_id)
{
	struct device *dev = ctrl->dev;
	struct device_node *thread_node;
	int i, j, rc;

	ctrl->thread_count = 0;

	for_each_available_child_of_node(dev->of_node, thread_node) {
		ctrl->thread_count++;
	}

	ctrl->thread = devm_kcalloc(dev, ctrl->thread_count,
			sizeof(*ctrl->thread), GFP_KERNEL);
	if (!ctrl->thread)
		return -ENOMEM;

	i = 0;
	for_each_available_child_of_node(dev->of_node, thread_node) {
		ctrl->thread[i].of_node = thread_node;
		ctrl->thread[i].ctrl = ctrl;

		rc = of_property_read_u32(thread_node, "qcom,cpr-thread-id",
					  &ctrl->thread[i].thread_id);
		if (rc) {
			dev_err(dev, "could not read DT property qcom,cpr-thread-id, rc=%d\n",
				rc);
			return rc;
		}

		if (ctrl->thread[i].thread_id < min_thread_id ||
				ctrl->thread[i].thread_id > max_thread_id) {
			dev_err(dev, "invalid thread id = %u; not within [%u, %u]\n",
				ctrl->thread[i].thread_id, min_thread_id,
				max_thread_id);
			return -EINVAL;
		}

		/* Verify that the thread ID is unique for all child nodes. */
		for (j = 0; j < i; j++) {
			if (ctrl->thread[j].thread_id
					== ctrl->thread[i].thread_id) {
				dev_err(dev, "duplicate thread id = %u found\n",
					ctrl->thread[i].thread_id);
				return -EINVAL;
			}
		}

		rc = cpr3_allocate_regulators(&ctrl->thread[i]);
		if (rc)
			return rc;

		i++;
	}

	return 0;
}

/**
 * cpr3_map_fuse_base() - ioremap the base address of the fuse region
 * @ctrl:	Pointer to the CPR3 controller
 * @pdev:	Platform device pointer for the CPR3 controller
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_map_fuse_base(struct cpr3_controller *ctrl,
			struct platform_device *pdev)
{
	struct resource *res;

	res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "fuse_base");
	if (!res || !res->start) {
		dev_err(&pdev->dev, "fuse base address is missing\n");
		return -ENXIO;
	}

	ctrl->fuse_base = devm_ioremap(&pdev->dev, res->start,
						resource_size(res));

	return 0;
}

/**
 * cpr3_read_fuse_param() - reads a CPR3 fuse parameter out of eFuses
 * @fuse_base_addr:	Virtual memory address of the eFuse base address
 * @param:		Null terminated array of fuse param segments to read
 *			from
 * @param_value:	Output with value read from the eFuses
 *
 * This function reads from each of the parameter segments listed in the param
 * array and concatenates their values together.  Reading stops when an element
 * is reached which has all 0 struct values.  The total number of bits specified
 * for the fuse parameter across all segments must be less than or equal to 64.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_read_fuse_param(void __iomem *fuse_base_addr,
		const struct cpr3_fuse_param *param, u64 *param_value)
{
	u64 fuse_val, val;
	int bits;
	int bits_total = 0;

	*param_value = 0;

	while (param->row || param->bit_start || param->bit_end) {
		if (param->bit_start > param->bit_end
		    || param->bit_end > MAX_FUSE_ROW_BIT) {
			pr_err("Invalid fuse parameter segment: row=%u, start=%u, end=%u\n",
				param->row, param->bit_start, param->bit_end);
			return -EINVAL;
		}

		bits = param->bit_end - param->bit_start + 1;
		if (bits_total + bits > 64) {
			pr_err("Invalid fuse parameter segments; total bits = %d\n",
				bits_total + bits);
			return -EINVAL;
		}

		fuse_val = readq_relaxed(fuse_base_addr
					 + param->row * BYTES_PER_FUSE_ROW);
		val = (fuse_val >> param->bit_start) & ((1ULL << bits) - 1);
		*param_value |= val << bits_total;
		bits_total += bits;

		param++;
	}

	return 0;
}

/**
 * cpr3_convert_open_loop_voltage_fuse() - converts an open loop voltage fuse
 *		value into an absolute voltage with units of microvolts
 * @ref_volt:		Reference voltage in microvolts
 * @step_volt:		The step size in microvolts of the fuse LSB
 * @fuse:		Open loop voltage fuse value
 * @fuse_len:		The bit length of the fuse value
 *
 * The MSB of the fuse parameter corresponds to a sign bit.  If it is set, then
 * the lower bits correspond to the number of steps to go down from the
 * reference voltage.  If it is not set, then the lower bits correspond to the
 * number of steps to go up from the reference voltage.
 */
int cpr3_convert_open_loop_voltage_fuse(int ref_volt, int step_volt, u32 fuse,
					int fuse_len)
{
	int sign, steps;

	sign = (fuse & (1 << (fuse_len - 1))) ? -1 : 1;
	steps = fuse & ((1 << (fuse_len - 1)) - 1);

	return ref_volt + sign * steps * step_volt;
}

/**
 * cpr3_interpolate() - performs linear interpolation
 * @x1		Lower known x value
 * @y1		Lower known y value
 * @x2		Upper known x value
 * @y2		Upper known y value
 * @x		Intermediate x value
 *
 * Returns y where (x, y) falls on the line between (x1, y1) and (x2, y2).
 * It is required that x1 < x2, y1 <= y2, and x1 <= x <= x2.  If these
 * conditions are not met, then y2 will be returned.
 */
u64 cpr3_interpolate(u64 x1, u64 y1, u64 x2, u64 y2, u64 x)
{
	u64 temp;

	if (x1 >= x2 || y1 > y2 || x1 > x || x > x2)
		return y2;

	temp = (x2 - x) * (y2 - y1);
	do_div(temp, (u32)(x2 - x1));

	return y2 - temp;
}

/**
 * cpr3_parse_array_property() - fill an array from a portion of the values
 *		specified for a device tree property
 * @vreg:		Pointer to the CPR3 regulator
 * @prop_name:		The name of the device tree property to read from
 * @tuple_size:		The number of elements in each tuple
 * @out:		Output data array which must be of size tuple_size
 *
 * cpr3_parse_common_corner_data() must be called for vreg before this function
 * is called so that fuse combo and speed bin size elements are initialized.
 *
 * Three formats are supported for the device tree property:
 * 1. Length == tuple_size
 *	(reading begins at index 0)
 * 2. Length == tuple_size * vreg->fuse_combos_supported
 *	(reading begins at index tuple_size * vreg->fuse_combo)
 * 3. Length == tuple_size * vreg->speed_bins_supported
 *	(reading begins at index tuple_size * vreg->speed_bin_fuse)
 *
 * All other property lengths are treated as errors.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_parse_array_property(struct cpr3_regulator *vreg,
		const char *prop_name, int tuple_size, u32 *out)
{
	struct device_node *node = vreg->of_node;
	int len = 0;
	int i, offset, rc;

	if (!of_find_property(node, prop_name, &len)) {
		cpr3_err(vreg, "property %s is missing\n", prop_name);
		return -EINVAL;
	}

	if (len == tuple_size * sizeof(u32)) {
		offset = 0;
	} else if (len == tuple_size * vreg->fuse_combos_supported
				     * sizeof(u32)) {
		offset = tuple_size * vreg->fuse_combo;
	} else if (vreg->speed_bins_supported > 0 &&
		 len == tuple_size * vreg->speed_bins_supported * sizeof(u32)) {
		offset = tuple_size * vreg->speed_bin_fuse;
	} else {
		if (vreg->speed_bins_supported > 0)
			cpr3_err(vreg, "property %s has invalid length=%d, should be %zu, %zu, or %zu\n",
				prop_name, len,
				tuple_size * sizeof(u32),
				tuple_size * vreg->speed_bins_supported
					   * sizeof(u32),
				tuple_size * vreg->fuse_combos_supported
					   * sizeof(u32));
		else
			cpr3_err(vreg, "property %s has invalid length=%d, should be %zu or %zu\n",
				prop_name, len,
				tuple_size * sizeof(u32),
				tuple_size * vreg->fuse_combos_supported
					   * sizeof(u32));
		return -EINVAL;
	}

	for (i = 0; i < tuple_size; i++) {
		rc = of_property_read_u32_index(node, prop_name, offset + i,
						&out[i]);
		if (rc) {
			cpr3_err(vreg, "error reading property %s, rc=%d\n",
				prop_name, rc);
			return rc;
		}
	}

	return 0;
}

/**
 * cpr3_parse_corner_array_property() - fill a per-corner array from a portion
 *		of the values specified for a device tree property
 * @vreg:		Pointer to the CPR3 regulator
 * @prop_name:		The name of the device tree property to read from
 * @tuple_size:		The number of elements in each per-corner tuple
 * @out:		Output data array which must be of size:
 *			tuple_size * vreg->corner_count
 *
 * cpr3_parse_common_corner_data() must be called for vreg before this function
 * is called so that fuse combo and speed bin size elements are initialized.
 *
 * Three formats are supported for the device tree property:
 * 1. Length == tuple_size * vreg->corner_count
 *	(reading begins at index 0)
 * 2. Length == tuple_size * vreg->fuse_combo_corner_sum
 *	(reading begins at index tuple_size * vreg->fuse_combo_offset)
 * 3. Length == tuple_size * vreg->speed_bin_corner_sum
 *	(reading begins at index tuple_size * vreg->speed_bin_offset)
 *
 * All other property lengths are treated as errors.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_parse_corner_array_property(struct cpr3_regulator *vreg,
		const char *prop_name, int tuple_size, u32 *out)
{
	struct device_node *node = vreg->of_node;
	int len = 0;
	int i, offset, rc;

	if (!of_find_property(node, prop_name, &len)) {
		cpr3_err(vreg, "property %s is missing\n", prop_name);
		return -EINVAL;
	}

	if (len == tuple_size * vreg->corner_count * sizeof(u32)) {
		offset = 0;
	} else if (len == tuple_size * vreg->fuse_combo_corner_sum
				     * sizeof(u32)) {
		offset = tuple_size * vreg->fuse_combo_offset;
	} else if (vreg->speed_bin_corner_sum > 0 &&
		 len == tuple_size * vreg->speed_bin_corner_sum * sizeof(u32)) {
		offset = tuple_size * vreg->speed_bin_offset;
	} else {
		if (vreg->speed_bin_corner_sum > 0)
			cpr3_err(vreg, "property %s has invalid length=%d, should be %zu, %zu, or %zu\n",
				prop_name, len,
				tuple_size * vreg->corner_count * sizeof(u32),
				tuple_size * vreg->speed_bin_corner_sum
					   * sizeof(u32),
				tuple_size * vreg->fuse_combo_corner_sum
					   * sizeof(u32));
		else
			cpr3_err(vreg, "property %s has invalid length=%d, should be %zu or %zu\n",
				prop_name, len,
				tuple_size * vreg->corner_count * sizeof(u32),
				tuple_size * vreg->fuse_combo_corner_sum
					   * sizeof(u32));
		return -EINVAL;
	}

	for (i = 0; i < tuple_size * vreg->corner_count; i++) {
		rc = of_property_read_u32_index(node, prop_name, offset + i,
						&out[i]);
		if (rc) {
			cpr3_err(vreg, "error reading property %s, rc=%d\n",
				prop_name, rc);
			return rc;
		}
	}

	return 0;
}

/**
 * cpr3_parse_corner_band_array_property() - fill a per-corner band array
 *		from a portion of the values specified for a device tree
 *		property
 * @vreg:		Pointer to the CPR3 regulator
 * @prop_name:		The name of the device tree property to read from
 * @tuple_size:		The number of elements in each per-corner band tuple
 * @out:		Output data array which must be of size:
 *			tuple_size * vreg->corner_band_count
 *
 * cpr3_parse_common_corner_data() must be called for vreg before this function
 * is called so that fuse combo and speed bin size elements are initialized.
 * In addition, corner band fuse combo and speed bin sum and offset elements
 * must be initialized prior to executing this function.
 *
 * Three formats are supported for the device tree property:
 * 1. Length == tuple_size * vreg->corner_band_count
 *	(reading begins at index 0)
 * 2. Length == tuple_size * vreg->fuse_combo_corner_band_sum
 *	(reading begins at index tuple_size *
 *		vreg->fuse_combo_corner_band_offset)
 * 3. Length == tuple_size * vreg->speed_bin_corner_band_sum
 *	(reading begins at index tuple_size *
 *		vreg->speed_bin_corner_band_offset)
 *
 * All other property lengths are treated as errors.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_parse_corner_band_array_property(struct cpr3_regulator *vreg,
		const char *prop_name, int tuple_size, u32 *out)
{
	struct device_node *node = vreg->of_node;
	int len = 0;
	int i, offset, rc;

	if (!of_find_property(node, prop_name, &len)) {
		cpr3_err(vreg, "property %s is missing\n", prop_name);
		return -EINVAL;
	}

	if (len == tuple_size * vreg->corner_band_count * sizeof(u32)) {
		offset = 0;
	} else if (len == tuple_size * vreg->fuse_combo_corner_band_sum
				     * sizeof(u32)) {
		offset = tuple_size * vreg->fuse_combo_corner_band_offset;
	} else if (vreg->speed_bin_corner_band_sum > 0 &&
		 len == tuple_size * vreg->speed_bin_corner_band_sum *
		   sizeof(u32)) {
		offset = tuple_size * vreg->speed_bin_corner_band_offset;
	} else {
		if (vreg->speed_bin_corner_band_sum > 0)
			cpr3_err(vreg, "property %s has invalid length=%d, should be %zu, %zu, or %zu\n",
				prop_name, len,
				tuple_size * vreg->corner_band_count *
				 sizeof(u32),
				tuple_size * vreg->speed_bin_corner_band_sum
					   * sizeof(u32),
				tuple_size * vreg->fuse_combo_corner_band_sum
					   * sizeof(u32));
		else
			cpr3_err(vreg, "property %s has invalid length=%d, should be %zu or %zu\n",
				prop_name, len,
				tuple_size * vreg->corner_band_count *
				 sizeof(u32),
				tuple_size * vreg->fuse_combo_corner_band_sum
					   * sizeof(u32));
		return -EINVAL;
	}

	for (i = 0; i < tuple_size * vreg->corner_band_count; i++) {
		rc = of_property_read_u32_index(node, prop_name, offset + i,
						&out[i]);
		if (rc) {
			cpr3_err(vreg, "error reading property %s, rc=%d\n",
				prop_name, rc);
			return rc;
		}
	}

	return 0;
}

/**
 * cpr3_parse_common_corner_data() - parse common CPR3 properties relating to
 *		the corners supported by a CPR3 regulator from device tree
 * @vreg:		Pointer to the CPR3 regulator
 *
 * This function reads, validates, and utilizes the following device tree
 * properties: qcom,cpr-fuse-corners, qcom,cpr-fuse-combos, qcom,cpr-speed-bins,
 * qcom,cpr-speed-bin-corners, qcom,cpr-corners, qcom,cpr-voltage-ceiling,
 * qcom,cpr-voltage-floor, qcom,corner-frequencies,
 * and qcom,cpr-corner-fmax-map.
 *
 * It initializes these CPR3 regulator elements: corner, corner_count,
 * fuse_combos_supported, fuse_corner_map, and speed_bins_supported.  It
 * initializes these elements for each corner: ceiling_volt, floor_volt,
 * proc_freq, and cpr_fuse_corner.
 *
 * It requires that the following CPR3 regulator elements be initialized before
 * being called: fuse_corner_count, fuse_combo, and speed_bin_fuse.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_parse_common_corner_data(struct cpr3_regulator *vreg)
{
	struct device_node *node = vreg->of_node;
	struct cpr3_controller *ctrl = vreg->thread->ctrl;
	u32 max_fuse_combos, fuse_corners, aging_allowed = 0;
	u32 max_speed_bins = 0;
	u32 *combo_corners;
	u32 *speed_bin_corners;
	u32 *temp;
	int i, j, rc;

	rc = of_property_read_u32(node, "qcom,cpr-fuse-corners", &fuse_corners);
	if (rc) {
		cpr3_err(vreg, "error reading property qcom,cpr-fuse-corners, rc=%d\n",
			rc);
		return rc;
	}

	if (vreg->fuse_corner_count != fuse_corners) {
		cpr3_err(vreg, "device tree config supports %d fuse corners but the hardware has %d fuse corners\n",
			fuse_corners, vreg->fuse_corner_count);
		return -EINVAL;
	}

	/*
	 * Check if CPR3 regulator's fuse_combos_supported element is already
	 * populated by fuse-combo-map logic. If not populated, then parse the
	 * qcom,cpr-fuse-combos property.
	 */
	if (vreg->fuse_combos_supported)
		max_fuse_combos = vreg->fuse_combos_supported;
	else {
		rc = of_property_read_u32(node, "qcom,cpr-fuse-combos",
					&max_fuse_combos);
		if (rc) {
			cpr3_err(vreg, "error reading property qcom,cpr-fuse-combos, rc=%d\n",
				rc);
			return rc;
		}

		/*
		 * Sanity check against arbitrarily large value to avoid
		 * excessive memory allocation.
		 */
		if (max_fuse_combos > 100 || max_fuse_combos == 0) {
			cpr3_err(vreg, "qcom,cpr-fuse-combos is invalid: %u\n",
				max_fuse_combos);
			return -EINVAL;
		}

		if (vreg->fuse_combo >= max_fuse_combos) {
			cpr3_err(vreg, "device tree config supports fuse combos 0-%u but the hardware has combo %d\n",
				max_fuse_combos - 1, vreg->fuse_combo);
			WARN_ON(1);
			return -EINVAL;
		}

		vreg->fuse_combos_supported = max_fuse_combos;
	}

	of_property_read_u32(node, "qcom,cpr-speed-bins", &max_speed_bins);

	/*
	 * Sanity check against arbitrarily large value to avoid excessive
	 * memory allocation.
	 */
	if (max_speed_bins > 100) {
		cpr3_err(vreg, "qcom,cpr-speed-bins is invalid: %u\n",
			max_speed_bins);
		return -EINVAL;
	}

	if (max_speed_bins && vreg->speed_bin_fuse >= max_speed_bins) {
		cpr3_err(vreg, "device tree config supports speed bins 0-%u but the hardware has speed bin %d\n",
			max_speed_bins - 1, vreg->speed_bin_fuse);
		BUG();
		return -EINVAL;
	}

	vreg->speed_bins_supported = max_speed_bins;

	combo_corners = kcalloc(vreg->fuse_combos_supported,
				sizeof(*combo_corners), GFP_KERNEL);
	if (!combo_corners)
		return -ENOMEM;

	rc = of_property_read_u32_array(node, "qcom,cpr-corners", combo_corners,
					vreg->fuse_combos_supported);
	if (rc == -EOVERFLOW) {
		/* Single value case */
		rc = of_property_read_u32(node, "qcom,cpr-corners",
					combo_corners);
		for (i = 1; i < vreg->fuse_combos_supported; i++)
			combo_corners[i] = combo_corners[0];
	}
	if (rc) {
		cpr3_err(vreg, "error reading property qcom,cpr-corners, rc=%d\n",
			rc);
		kfree(combo_corners);
		return rc;
	}

	vreg->fuse_combo_offset = 0;
	vreg->fuse_combo_corner_sum = 0;
	for (i = 0; i < vreg->fuse_combos_supported; i++) {
		vreg->fuse_combo_corner_sum += combo_corners[i];
		if (i < vreg->fuse_combo)
			vreg->fuse_combo_offset += combo_corners[i];
	}

	vreg->corner_count = combo_corners[vreg->fuse_combo];

	kfree(combo_corners);

	vreg->speed_bin_offset = 0;
	vreg->speed_bin_corner_sum = 0;
	if (vreg->speed_bins_supported > 0) {
		speed_bin_corners = kcalloc(vreg->speed_bins_supported,
					sizeof(*speed_bin_corners), GFP_KERNEL);
		if (!speed_bin_corners)
			return -ENOMEM;

		rc = of_property_read_u32_array(node,
				"qcom,cpr-speed-bin-corners", speed_bin_corners,
				vreg->speed_bins_supported);
		if (rc) {
			cpr3_err(vreg, "error reading property qcom,cpr-speed-bin-corners, rc=%d\n",
				rc);
			kfree(speed_bin_corners);
			return rc;
		}

		for (i = 0; i < vreg->speed_bins_supported; i++) {
			vreg->speed_bin_corner_sum += speed_bin_corners[i];
			if (i < vreg->speed_bin_fuse)
				vreg->speed_bin_offset += speed_bin_corners[i];
		}

		if (speed_bin_corners[vreg->speed_bin_fuse]
		    != vreg->corner_count) {
			cpr3_err(vreg, "qcom,cpr-corners and qcom,cpr-speed-bin-corners conflict on number of corners: %d vs %u\n",
				vreg->corner_count,
				speed_bin_corners[vreg->speed_bin_fuse]);
			kfree(speed_bin_corners);
			return -EINVAL;
		}

		kfree(speed_bin_corners);
	}

	/*
	 * For CPRh compliant controllers two additional corners are
	 * allocated to correspond to the APM crossover voltage and the MEM ACC
	 * crossover voltage.
	 */
	vreg->corner = devm_kcalloc(ctrl->dev, ctrl->ctrl_type ==
				    CPR_CTRL_TYPE_CPRH ?
				    vreg->corner_count + 2 :
				    vreg->corner_count,
				    sizeof(*vreg->corner), GFP_KERNEL);
	temp = kcalloc(vreg->corner_count, sizeof(*temp), GFP_KERNEL);
	if (!vreg->corner || !temp)
		return -ENOMEM;

	rc = cpr3_parse_corner_array_property(vreg, "qcom,cpr-voltage-ceiling",
			1, temp);
	if (rc)
		goto free_temp;
	for (i = 0; i < vreg->corner_count; i++) {
		vreg->corner[i].ceiling_volt
			= CPR3_ROUND(temp[i], ctrl->step_volt);
		vreg->corner[i].abs_ceiling_volt = vreg->corner[i].ceiling_volt;
	}

	rc = cpr3_parse_corner_array_property(vreg, "qcom,cpr-voltage-floor",
			1, temp);
	if (rc)
		goto free_temp;
	for (i = 0; i < vreg->corner_count; i++)
		vreg->corner[i].floor_volt
			= CPR3_ROUND(temp[i], ctrl->step_volt);

	/* Validate ceiling and floor values */
	for (i = 0; i < vreg->corner_count; i++) {
		if (vreg->corner[i].floor_volt
		    > vreg->corner[i].ceiling_volt) {
			cpr3_err(vreg, "CPR floor[%d]=%d > ceiling[%d]=%d uV\n",
				i, vreg->corner[i].floor_volt,
				i, vreg->corner[i].ceiling_volt);
			rc = -EINVAL;
			goto free_temp;
		}
	}

	/* Load optional system-supply voltages */
	if (of_find_property(vreg->of_node, "qcom,system-voltage", NULL)) {
		rc = cpr3_parse_corner_array_property(vreg,
			"qcom,system-voltage", 1, temp);
		if (rc)
			goto free_temp;
		for (i = 0; i < vreg->corner_count; i++)
			vreg->corner[i].system_volt = temp[i];
	}

	rc = cpr3_parse_corner_array_property(vreg, "qcom,corner-frequencies",
			1, temp);
	if (rc)
		goto free_temp;
	for (i = 0; i < vreg->corner_count; i++)
		vreg->corner[i].proc_freq = temp[i];

	/* Validate frequencies */
	for (i = 1; i < vreg->corner_count; i++) {
		if (vreg->corner[i].proc_freq
		    < vreg->corner[i - 1].proc_freq) {
			cpr3_err(vreg, "invalid frequency: freq[%d]=%u < freq[%d]=%u\n",
				i, vreg->corner[i].proc_freq, i - 1,
				vreg->corner[i - 1].proc_freq);
			rc = -EINVAL;
			goto free_temp;
		}
	}

	vreg->fuse_corner_map = devm_kcalloc(ctrl->dev, vreg->fuse_corner_count,
				    sizeof(*vreg->fuse_corner_map), GFP_KERNEL);
	if (!vreg->fuse_corner_map) {
		rc = -ENOMEM;
		goto free_temp;
	}

	rc = cpr3_parse_array_property(vreg, "qcom,cpr-corner-fmax-map",
		vreg->fuse_corner_count, temp);
	if (rc)
		goto free_temp;
	for (i = 0; i < vreg->fuse_corner_count; i++) {
		vreg->fuse_corner_map[i] = temp[i] - CPR3_CORNER_OFFSET;
		if (temp[i] < CPR3_CORNER_OFFSET
		    || temp[i] > vreg->corner_count + CPR3_CORNER_OFFSET) {
			cpr3_err(vreg, "invalid corner value specified in qcom,cpr-corner-fmax-map: %u\n",
				temp[i]);
			rc = -EINVAL;
			goto free_temp;
		} else if (i > 0 && temp[i - 1] >= temp[i]) {
			cpr3_err(vreg, "invalid corner %u less than or equal to previous corner %u\n",
				temp[i], temp[i - 1]);
			rc = -EINVAL;
			goto free_temp;
		}
	}
	if (temp[vreg->fuse_corner_count - 1] != vreg->corner_count)
		cpr3_debug(vreg, "Note: highest Fmax corner %u in qcom,cpr-corner-fmax-map does not match highest supported corner %d\n",
			temp[vreg->fuse_corner_count - 1],
			vreg->corner_count);

	for (i = 0; i < vreg->corner_count; i++) {
		for (j = 0; j < vreg->fuse_corner_count; j++) {
			if (i + CPR3_CORNER_OFFSET <= temp[j]) {
				vreg->corner[i].cpr_fuse_corner = j;
				break;
			}
		}
		if (j == vreg->fuse_corner_count) {
			/*
			 * Handle the case where the highest fuse corner maps
			 * to a corner below the highest corner.
			 */
			vreg->corner[i].cpr_fuse_corner
				= vreg->fuse_corner_count - 1;
		}
	}

	if (of_find_property(vreg->of_node,
				"qcom,allow-aging-voltage-adjustment", NULL)) {
		rc = cpr3_parse_array_property(vreg,
			"qcom,allow-aging-voltage-adjustment",
			1, &aging_allowed);
		if (rc)
			goto free_temp;

		vreg->aging_allowed = aging_allowed;
	}

	if (of_find_property(vreg->of_node,
		       "qcom,allow-aging-open-loop-voltage-adjustment", NULL)) {
		rc = cpr3_parse_array_property(vreg,
			"qcom,allow-aging-open-loop-voltage-adjustment",
			1, &aging_allowed);
		if (rc)
			goto free_temp;

		vreg->aging_allow_open_loop_adj = aging_allowed;
	}

	if (vreg->aging_allowed) {
		if (ctrl->aging_ref_volt <= 0) {
			cpr3_err(ctrl, "qcom,cpr-aging-ref-voltage must be specified\n");
			rc = -EINVAL;
			goto free_temp;
		}

		rc = cpr3_parse_array_property(vreg,
			"qcom,cpr-aging-max-voltage-adjustment",
			1, &vreg->aging_max_adjust_volt);
		if (rc)
			goto free_temp;

		rc = cpr3_parse_array_property(vreg,
			"qcom,cpr-aging-ref-corner", 1, &vreg->aging_corner);
		if (rc) {
			goto free_temp;
		} else if (vreg->aging_corner < CPR3_CORNER_OFFSET
			   || vreg->aging_corner > vreg->corner_count - 1
							+ CPR3_CORNER_OFFSET) {
			cpr3_err(vreg, "aging reference corner=%d not in range [%d, %d]\n",
				vreg->aging_corner, CPR3_CORNER_OFFSET,
				vreg->corner_count - 1 + CPR3_CORNER_OFFSET);
			rc = -EINVAL;
			goto free_temp;
		}
		vreg->aging_corner -= CPR3_CORNER_OFFSET;

		if (of_find_property(vreg->of_node, "qcom,cpr-aging-derate",
					NULL)) {
			rc = cpr3_parse_corner_array_property(vreg,
				"qcom,cpr-aging-derate", 1, temp);
			if (rc)
				goto free_temp;

			for (i = 0; i < vreg->corner_count; i++)
				vreg->corner[i].aging_derate = temp[i];
		} else {
			for (i = 0; i < vreg->corner_count; i++)
				vreg->corner[i].aging_derate
					= CPR3_AGING_DERATE_UNITY;
		}
	}

free_temp:
	kfree(temp);
	return rc;
}

/**
 * cpr3_parse_thread_u32() - parse the specified property from the CPR3 thread's
 *		device tree node and verify that it is within the allowed limits
 * @thread:		Pointer to the CPR3 thread
 * @propname:		The name of the device tree property to read
 * @out_value:		The output pointer to fill with the value read
 * @value_min:		The minimum allowed property value
 * @value_max:		The maximum allowed property value
 *
 * This function prints a verbose error message if the property is missing or
 * has a value which is not within the specified range.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_parse_thread_u32(struct cpr3_thread *thread, const char *propname,
		       u32 *out_value, u32 value_min, u32 value_max)
{
	int rc;

	rc = of_property_read_u32(thread->of_node, propname, out_value);
	if (rc) {
		cpr3_err(thread->ctrl, "thread %u error reading property %s, rc=%d\n",
			thread->thread_id, propname, rc);
		return rc;
	}

	if (*out_value < value_min || *out_value > value_max) {
		cpr3_err(thread->ctrl, "thread %u %s=%u is invalid; allowed range: [%u, %u]\n",
			thread->thread_id, propname, *out_value, value_min,
			value_max);
		return -EINVAL;
	}

	return 0;
}

/**
 * cpr3_parse_ctrl_u32() - parse the specified property from the CPR3
 *		controller's device tree node and verify that it is within the
 *		allowed limits
 * @ctrl:		Pointer to the CPR3 controller
 * @propname:		The name of the device tree property to read
 * @out_value:		The output pointer to fill with the value read
 * @value_min:		The minimum allowed property value
 * @value_max:		The maximum allowed property value
 *
 * This function prints a verbose error message if the property is missing or
 * has a value which is not within the specified range.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_parse_ctrl_u32(struct cpr3_controller *ctrl, const char *propname,
		       u32 *out_value, u32 value_min, u32 value_max)
{
	int rc;

	rc = of_property_read_u32(ctrl->dev->of_node, propname, out_value);
	if (rc) {
		cpr3_err(ctrl, "error reading property %s, rc=%d\n",
			propname, rc);
		return rc;
	}

	if (*out_value < value_min || *out_value > value_max) {
		cpr3_err(ctrl, "%s=%u is invalid; allowed range: [%u, %u]\n",
			propname, *out_value, value_min, value_max);
		return -EINVAL;
	}

	return 0;
}

/**
 * cpr3_parse_common_thread_data() - parse common CPR3 thread properties from
 *		device tree
 * @thread:		Pointer to the CPR3 thread
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_parse_common_thread_data(struct cpr3_thread *thread)
{
	int rc;

	rc = cpr3_parse_thread_u32(thread, "qcom,cpr-consecutive-up",
			&thread->consecutive_up, CPR3_CONSECUTIVE_UP_DOWN_MIN,
			CPR3_CONSECUTIVE_UP_DOWN_MAX);
	if (rc)
		return rc;

	rc = cpr3_parse_thread_u32(thread, "qcom,cpr-consecutive-down",
			&thread->consecutive_down, CPR3_CONSECUTIVE_UP_DOWN_MIN,
			CPR3_CONSECUTIVE_UP_DOWN_MAX);
	if (rc)
		return rc;

	rc = cpr3_parse_thread_u32(thread, "qcom,cpr-up-threshold",
			&thread->up_threshold, CPR3_UP_DOWN_THRESHOLD_MIN,
			CPR3_UP_DOWN_THRESHOLD_MAX);
	if (rc)
		return rc;

	rc = cpr3_parse_thread_u32(thread, "qcom,cpr-down-threshold",
			&thread->down_threshold, CPR3_UP_DOWN_THRESHOLD_MIN,
			CPR3_UP_DOWN_THRESHOLD_MAX);
	if (rc)
		return rc;

	return rc;
}

/**
 * cpr3_parse_irq_affinity() - parse CPR IRQ affinity information
 * @ctrl:		Pointer to the CPR3 controller
 *
 * Return: 0 on success, errno on failure
 */
static int cpr3_parse_irq_affinity(struct cpr3_controller *ctrl)
{
	struct device_node *cpu_node;
	int i, cpu;
	int len = 0;

	if (!of_find_property(ctrl->dev->of_node, "qcom,cpr-interrupt-affinity",
				&len)) {
		/* No IRQ affinity required */
		return 0;
	}

	len /= sizeof(u32);

	for (i = 0; i < len; i++) {
		cpu_node = of_parse_phandle(ctrl->dev->of_node,
					    "qcom,cpr-interrupt-affinity", i);
		if (!cpu_node) {
			cpr3_err(ctrl, "could not find CPU node %d\n", i);
			return -EINVAL;
		}

		for_each_possible_cpu(cpu) {
			if (of_get_cpu_node(cpu, NULL) == cpu_node) {
				cpumask_set_cpu(cpu, &ctrl->irq_affinity_mask);
				break;
			}
		}
		of_node_put(cpu_node);
	}

	return 0;
}

static int cpr3_panic_notifier_init(struct cpr3_controller *ctrl)
{
	struct device_node *node = ctrl->dev->of_node;
	struct cpr3_panic_regs_info *panic_regs_info;
	struct cpr3_reg_info *regs;
	int i, reg_count, len, rc = 0;

	if (!of_find_property(node, "qcom,cpr-panic-reg-addr-list", &len)) {
		/* panic register address list not specified */
		return rc;
	}

	reg_count = len / sizeof(u32);
	if (!reg_count) {
		cpr3_err(ctrl, "qcom,cpr-panic-reg-addr-list has invalid len = %d\n",
			len);
		return -EINVAL;
	}

	if (!of_find_property(node, "qcom,cpr-panic-reg-name-list", NULL)) {
		cpr3_err(ctrl, "property qcom,cpr-panic-reg-name-list not specified\n");
		return -EINVAL;
	}

	len = of_property_count_strings(node, "qcom,cpr-panic-reg-name-list");
	if (reg_count != len) {
		cpr3_err(ctrl, "qcom,cpr-panic-reg-name-list should have %d strings\n",
			reg_count);
		return -EINVAL;
	}

	panic_regs_info = devm_kzalloc(ctrl->dev, sizeof(*panic_regs_info),
					GFP_KERNEL);
	if (!panic_regs_info)
		return -ENOMEM;

	regs = devm_kcalloc(ctrl->dev, reg_count, sizeof(*regs), GFP_KERNEL);
	if (!regs)
		return -ENOMEM;

	for (i = 0; i < reg_count; i++) {
		rc = of_property_read_string_index(node,
				"qcom,cpr-panic-reg-name-list", i,
				&(regs[i].name));
		if (rc) {
			cpr3_err(ctrl, "error reading property qcom,cpr-panic-reg-name-list, rc=%d\n",
				rc);
			return rc;
		}

		rc = of_property_read_u32_index(node,
				"qcom,cpr-panic-reg-addr-list", i,
				&(regs[i].addr));
		if (rc) {
			cpr3_err(ctrl, "error reading property qcom,cpr-panic-reg-addr-list, rc=%d\n",
				rc);
			return rc;
		}
		regs[i].virt_addr = devm_ioremap(ctrl->dev, regs[i].addr, 0x4);
		if (!regs[i].virt_addr) {
			pr_err("Unable to map panic register addr 0x%08x\n",
				regs[i].addr);
			return -EINVAL;
		}
		regs[i].value = 0xFFFFFFFF;
	}

	panic_regs_info->reg_count = reg_count;
	panic_regs_info->regs = regs;
	ctrl->panic_regs_info = panic_regs_info;

	return rc;
}

/**
 * cpr3_parse_common_ctrl_data() - parse common CPR3 controller properties from
 *		device tree
 * @ctrl:		Pointer to the CPR3 controller
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_parse_common_ctrl_data(struct cpr3_controller *ctrl)
{
	int rc;

	rc = cpr3_parse_ctrl_u32(ctrl, "qcom,cpr-sensor-time",
			&ctrl->sensor_time, 0, UINT_MAX);
	if (rc)
		return rc;

	rc = cpr3_parse_ctrl_u32(ctrl, "qcom,cpr-loop-time",
			&ctrl->loop_time, 0, UINT_MAX);
	if (rc)
		return rc;

	rc = cpr3_parse_ctrl_u32(ctrl, "qcom,cpr-idle-cycles",
			&ctrl->idle_clocks, CPR3_IDLE_CLOCKS_MIN,
			CPR3_IDLE_CLOCKS_MAX);
	if (rc)
		return rc;

	rc = cpr3_parse_ctrl_u32(ctrl, "qcom,cpr-step-quot-init-min",
			&ctrl->step_quot_init_min, CPR3_STEP_QUOT_MIN,
			CPR3_STEP_QUOT_MAX);
	if (rc)
		return rc;

	rc = cpr3_parse_ctrl_u32(ctrl, "qcom,cpr-step-quot-init-max",
			&ctrl->step_quot_init_max, CPR3_STEP_QUOT_MIN,
			CPR3_STEP_QUOT_MAX);
	if (rc)
		return rc;

	rc = of_property_read_u32(ctrl->dev->of_node, "qcom,voltage-step",
				&ctrl->step_volt);
	if (rc) {
		cpr3_err(ctrl, "error reading property qcom,voltage-step, rc=%d\n",
			rc);
		return rc;
	}
	if (ctrl->step_volt <= 0) {
		cpr3_err(ctrl, "qcom,voltage-step=%d is invalid\n",
			ctrl->step_volt);
		return -EINVAL;
	}

	rc = cpr3_parse_ctrl_u32(ctrl, "qcom,cpr-count-mode",
			&ctrl->count_mode, CPR3_COUNT_MODE_ALL_AT_ONCE_MIN,
			CPR3_COUNT_MODE_STAGGERED);
	if (rc)
		return rc;

	/* Count repeat is optional */
	ctrl->count_repeat = 0;
	of_property_read_u32(ctrl->dev->of_node, "qcom,cpr-count-repeat",
			&ctrl->count_repeat);

	ctrl->cpr_allowed_sw = of_property_read_bool(ctrl->dev->of_node,
			"qcom,cpr-enable");

	rc = cpr3_parse_irq_affinity(ctrl);
	if (rc)
		return rc;

	ctrl->ignore_invalid_fuses = of_property_read_bool(ctrl->dev->of_node,
				"qcom,cpr-ignore-invalid-fuses");

	/* Aging reference voltage is optional */
	ctrl->aging_ref_volt = 0;
	of_property_read_u32(ctrl->dev->of_node, "qcom,cpr-aging-ref-voltage",
			&ctrl->aging_ref_volt);

	/* Aging possible bitmask is optional */
	ctrl->aging_possible_mask = 0;
	of_property_read_u32(ctrl->dev->of_node,
			"qcom,cpr-aging-allowed-reg-mask",
			&ctrl->aging_possible_mask);

	if (ctrl->aging_possible_mask) {
		/*
		 * Aging possible register value required if bitmask is
		 * specified
		 */
		rc = cpr3_parse_ctrl_u32(ctrl,
				"qcom,cpr-aging-allowed-reg-value",
				&ctrl->aging_possible_val, 0, UINT_MAX);
		if (rc)
			return rc;
	}

	if (of_find_property(ctrl->dev->of_node, "clock-names", NULL)) {
		ctrl->core_clk = devm_clk_get(ctrl->dev, "core_clk");
		if (IS_ERR(ctrl->core_clk)) {
			rc = PTR_ERR(ctrl->core_clk);
			if (rc != -EPROBE_DEFER)
				cpr3_err(ctrl, "unable request core clock, rc=%d\n",
				rc);
			return rc;
		}
	}

	rc = cpr3_panic_notifier_init(ctrl);
	if (rc)
		return rc;

	if (of_find_property(ctrl->dev->of_node, "vdd-supply", NULL)) {
		ctrl->vdd_regulator = devm_regulator_get(ctrl->dev, "vdd");
		if (IS_ERR(ctrl->vdd_regulator)) {
			rc = PTR_ERR(ctrl->vdd_regulator);
			if (rc != -EPROBE_DEFER)
				cpr3_err(ctrl, "unable to request vdd regulator, rc=%d\n",
					 rc);
			return rc;
		}
	} else if (ctrl->ctrl_type == CPR_CTRL_TYPE_CPRH) {
		/* vdd-supply is optional for CPRh controllers. */
		ctrl->vdd_regulator = NULL;
	} else {
		cpr3_err(ctrl, "vdd supply is not defined\n");
		return -ENODEV;
	}

	/*
	 * Reset step_quot to default on each loop_en = 0 transition is
	 * optional.
	 */
	ctrl->reset_step_quot_loop_en
		= of_property_read_bool(ctrl->dev->of_node,
					"qcom,cpr-reset-step-quot-loop-en");

	/*
	 * Regulator device handles are not necessary for CPRh controllers
	 * since communication with the regulators is completely managed
	 * in hardware.
	 */
	if (ctrl->ctrl_type == CPR_CTRL_TYPE_CPRH)
		return rc;

	ctrl->system_regulator = devm_regulator_get_optional(ctrl->dev,
								"system");
	if (IS_ERR(ctrl->system_regulator)) {
		rc = PTR_ERR(ctrl->system_regulator);
		if (rc != -EPROBE_DEFER) {
			rc = 0;
			ctrl->system_regulator = NULL;
		} else {
			return rc;
		}
	}

	ctrl->mem_acc_regulator = devm_regulator_get_optional(ctrl->dev,
							      "mem-acc");
	if (IS_ERR(ctrl->mem_acc_regulator)) {
		rc = PTR_ERR(ctrl->mem_acc_regulator);
		if (rc != -EPROBE_DEFER) {
			rc = 0;
			ctrl->mem_acc_regulator = NULL;
		} else {
			return rc;
		}
	}

	return rc;
}

/**
 * cpr3_limit_open_loop_voltages() - modify the open-loop voltage of each corner
 *				so that it fits within the floor to ceiling
 *				voltage range of the corner
 * @vreg:		Pointer to the CPR3 regulator
 *
 * This function clips the open-loop voltage for each corner so that it is
 * limited to the floor to ceiling range.  It also rounds each open-loop voltage
 * so that it corresponds to a set point available to the underlying regulator.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_limit_open_loop_voltages(struct cpr3_regulator *vreg)
{
	int i, volt;

	cpr3_debug(vreg, "open-loop voltages after trimming and rounding:\n");
	for (i = 0; i < vreg->corner_count; i++) {
		volt = CPR3_ROUND(vreg->corner[i].open_loop_volt,
					vreg->thread->ctrl->step_volt);
		if (volt < vreg->corner[i].floor_volt)
			volt = vreg->corner[i].floor_volt;
		else if (volt > vreg->corner[i].ceiling_volt)
			volt = vreg->corner[i].ceiling_volt;
		vreg->corner[i].open_loop_volt = volt;
		cpr3_debug(vreg, "corner[%2d]: open-loop=%d uV\n", i, volt);
	}

	return 0;
}

/**
 * cpr3_open_loop_voltage_as_ceiling() - configures the ceiling voltage for each
 *		corner to equal the open-loop voltage if the relevant device
 *		tree property is found for the CPR3 regulator
 * @vreg:		Pointer to the CPR3 regulator
 *
 * This function assumes that the the open-loop voltage for each corner has
 * already been rounded to the nearest allowed set point and that it falls
 * within the floor to ceiling range.
 *
 * Return: none
 */
void cpr3_open_loop_voltage_as_ceiling(struct cpr3_regulator *vreg)
{
	int i;

	if (!of_property_read_bool(vreg->of_node,
				"qcom,cpr-scaled-open-loop-voltage-as-ceiling"))
		return;

	for (i = 0; i < vreg->corner_count; i++)
		vreg->corner[i].ceiling_volt
			= vreg->corner[i].open_loop_volt;
}

/**
 * cpr3_limit_floor_voltages() - raise the floor voltage of each corner so that
 *		the optional maximum floor to ceiling voltage range specified in
 *		device tree is satisfied
 * @vreg:		Pointer to the CPR3 regulator
 *
 * This function also ensures that the open-loop voltage for each corner falls
 * within the final floor to ceiling voltage range and that floor voltages
 * increase monotonically.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_limit_floor_voltages(struct cpr3_regulator *vreg)
{
	char *prop = "qcom,cpr-floor-to-ceiling-max-range";
	int i, floor_new;
	u32 *floor_range;
	int rc = 0;

	if (!of_find_property(vreg->of_node, prop, NULL))
		goto enforce_monotonicity;

	floor_range = kcalloc(vreg->corner_count, sizeof(*floor_range),
				GFP_KERNEL);
	if (!floor_range)
		return -ENOMEM;

	rc = cpr3_parse_corner_array_property(vreg, prop, 1, floor_range);
	if (rc)
		goto free_floor_adjust;

	for (i = 0; i < vreg->corner_count; i++) {
		if ((s32)floor_range[i] >= 0) {
			floor_new = CPR3_ROUND(vreg->corner[i].ceiling_volt
							- floor_range[i],
						vreg->thread->ctrl->step_volt);

			vreg->corner[i].floor_volt = max(floor_new,
						vreg->corner[i].floor_volt);
			if (vreg->corner[i].open_loop_volt
			    < vreg->corner[i].floor_volt)
				vreg->corner[i].open_loop_volt
					= vreg->corner[i].floor_volt;
		}
	}

free_floor_adjust:
	kfree(floor_range);

enforce_monotonicity:
	/* Ensure that floor voltages increase monotonically. */
	for (i = 1; i < vreg->corner_count; i++) {
		if (vreg->corner[i].floor_volt
		    < vreg->corner[i - 1].floor_volt) {
			cpr3_debug(vreg, "corner %d floor voltage=%d uV < corner %d voltage=%d uV; overriding: corner %d voltage=%d\n",
				i, vreg->corner[i].floor_volt,
				i - 1, vreg->corner[i - 1].floor_volt,
				i, vreg->corner[i - 1].floor_volt);
			vreg->corner[i].floor_volt
				= vreg->corner[i - 1].floor_volt;

			if (vreg->corner[i].open_loop_volt
			    < vreg->corner[i].floor_volt)
				vreg->corner[i].open_loop_volt
					= vreg->corner[i].floor_volt;
			if (vreg->corner[i].ceiling_volt
			    < vreg->corner[i].floor_volt)
				vreg->corner[i].ceiling_volt
					= vreg->corner[i].floor_volt;
		}
	}

	return rc;
}

/**
 * cpr3_print_quots() - print CPR target quotients into the kernel log for
 *		debugging purposes
 * @vreg:		Pointer to the CPR3 regulator
 *
 * Return: none
 */
void cpr3_print_quots(struct cpr3_regulator *vreg)
{
	int i, j, pos;
	size_t buflen;
	char *buf;

	buflen = sizeof(*buf) * CPR3_RO_COUNT * (MAX_CHARS_PER_INT + 2);
	buf = kzalloc(buflen, GFP_KERNEL);
	if (!buf)
		return;

	for (i = 0; i < vreg->corner_count; i++) {
		for (j = 0, pos = 0; j < CPR3_RO_COUNT; j++)
			pos += scnprintf(buf + pos, buflen - pos, " %u",
				vreg->corner[i].target_quot[j]);
		cpr3_debug(vreg, "target quots[%2d]:%s\n", i, buf);
	}

	kfree(buf);
}

/**
 * cpr3_adjust_fused_open_loop_voltages() - adjust the fused open-loop voltages
 *		for each fuse corner according to device tree values
 * @vreg:		Pointer to the CPR3 regulator
 * @fuse_volt:		Pointer to an array of the fused open-loop voltage
 *			values
 *
 * Voltage values in fuse_volt are modified in place.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_adjust_fused_open_loop_voltages(struct cpr3_regulator *vreg,
		int *fuse_volt)
{
	int i, rc, prev_volt;
	int *volt_adjust;

	if (!of_find_property(vreg->of_node,
			"qcom,cpr-open-loop-voltage-fuse-adjustment", NULL)) {
		/* No adjustment required. */
		return 0;
	}

	volt_adjust = kcalloc(vreg->fuse_corner_count, sizeof(*volt_adjust),
				GFP_KERNEL);
	if (!volt_adjust)
		return -ENOMEM;

	rc = cpr3_parse_array_property(vreg,
		"qcom,cpr-open-loop-voltage-fuse-adjustment",
		vreg->fuse_corner_count, volt_adjust);
	if (rc) {
		cpr3_err(vreg, "could not load open-loop fused voltage adjustments, rc=%d\n",
			rc);
		goto done;
	}

	for (i = 0; i < vreg->fuse_corner_count; i++) {
		if (volt_adjust[i]) {
			prev_volt = fuse_volt[i];
			fuse_volt[i] += volt_adjust[i];
			cpr3_debug(vreg, "adjusted fuse corner %d open-loop voltage: %d --> %d uV\n",
				i, prev_volt, fuse_volt[i]);
		}
	}

done:
	kfree(volt_adjust);
	return rc;
}

/**
 * cpr3_adjust_open_loop_voltages() - adjust the open-loop voltages for each
 *		corner according to device tree values
 * @vreg:		Pointer to the CPR3 regulator
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_adjust_open_loop_voltages(struct cpr3_regulator *vreg)
{
	int i, rc, prev_volt, min_volt;
	int *volt_adjust, *volt_diff;

	if (!of_find_property(vreg->of_node,
			"qcom,cpr-open-loop-voltage-adjustment", NULL)) {
		/* No adjustment required. */
		return 0;
	}

	volt_adjust = kcalloc(vreg->corner_count, sizeof(*volt_adjust),
				GFP_KERNEL);
	volt_diff = kcalloc(vreg->corner_count, sizeof(*volt_diff), GFP_KERNEL);
	if (!volt_adjust || !volt_diff) {
		rc = -ENOMEM;
		goto done;
	}

	rc = cpr3_parse_corner_array_property(vreg,
		"qcom,cpr-open-loop-voltage-adjustment", 1, volt_adjust);
	if (rc) {
		cpr3_err(vreg, "could not load open-loop voltage adjustments, rc=%d\n",
			rc);
		goto done;
	}

	for (i = 0; i < vreg->corner_count; i++) {
		if (volt_adjust[i]) {
			prev_volt = vreg->corner[i].open_loop_volt;
			vreg->corner[i].open_loop_volt += volt_adjust[i];
			cpr3_debug(vreg, "adjusted corner %d open-loop voltage: %d --> %d uV\n",
				i, prev_volt, vreg->corner[i].open_loop_volt);
		}
	}

	if (of_find_property(vreg->of_node,
			"qcom,cpr-open-loop-voltage-min-diff", NULL)) {
		rc = cpr3_parse_corner_array_property(vreg,
			"qcom,cpr-open-loop-voltage-min-diff", 1, volt_diff);
		if (rc) {
			cpr3_err(vreg, "could not load minimum open-loop voltage differences, rc=%d\n",
				rc);
			goto done;
		}
	}

	/*
	 * Ensure that open-loop voltages increase monotonically with respect
	 * to configurable minimum allowed differences.
	 */
	for (i = 1; i < vreg->corner_count; i++) {
		min_volt = vreg->corner[i - 1].open_loop_volt + volt_diff[i];
		if (vreg->corner[i].open_loop_volt < min_volt) {
			cpr3_debug(vreg, "adjusted corner %d open-loop voltage=%d uV < corner %d voltage=%d uV + min diff=%d uV; overriding: corner %d voltage=%d\n",
				i, vreg->corner[i].open_loop_volt,
				i - 1, vreg->corner[i - 1].open_loop_volt,
				volt_diff[i], i, min_volt);
			vreg->corner[i].open_loop_volt = min_volt;
		}
	}

done:
	kfree(volt_diff);
	kfree(volt_adjust);
	return rc;
}

/**
 * cpr3_quot_adjustment() - returns the quotient adjustment value resulting from
 *		the specified voltage adjustment and RO scaling factor
 * @ro_scale:		The CPR ring oscillator (RO) scaling factor with units
 *			of QUOT/V
 * @volt_adjust:	The amount to adjust the voltage by in units of
 *			microvolts.  This value may be positive or negative.
 */
int cpr3_quot_adjustment(int ro_scale, int volt_adjust)
{
	unsigned long long temp;
	int quot_adjust;
	int sign = 1;

	if (ro_scale < 0) {
		sign = -sign;
		ro_scale = -ro_scale;
	}

	if (volt_adjust < 0) {
		sign = -sign;
		volt_adjust = -volt_adjust;
	}

	temp = (unsigned long long)ro_scale * (unsigned long long)volt_adjust;
	do_div(temp, 1000000);

	quot_adjust = temp;
	quot_adjust *= sign;

	return quot_adjust;
}

/**
 * cpr3_voltage_adjustment() - returns the voltage adjustment value resulting
 *		from the specified quotient adjustment and RO scaling factor
 * @ro_scale:		The CPR ring oscillator (RO) scaling factor with units
 *			of QUOT/V
 * @quot_adjust:	The amount to adjust the quotient by in units of
 *			QUOT.  This value may be positive or negative.
 */
int cpr3_voltage_adjustment(int ro_scale, int quot_adjust)
{
	unsigned long long temp;
	int volt_adjust;
	int sign = 1;

	if (ro_scale < 0) {
		sign = -sign;
		ro_scale = -ro_scale;
	}

	if (quot_adjust < 0) {
		sign = -sign;
		quot_adjust = -quot_adjust;
	}

	if (ro_scale == 0)
		return 0;

	temp = (unsigned long long)quot_adjust * 1000000;
	do_div(temp, ro_scale);

	volt_adjust = temp;
	volt_adjust *= sign;

	return volt_adjust;
}

/**
 * cpr3_parse_closed_loop_voltage_adjustments() - load per-fuse-corner and
 *		per-corner closed-loop adjustment values from device tree
 * @vreg:		Pointer to the CPR3 regulator
 * @ro_sel:		Array of ring oscillator values selected for each
 *			fuse corner
 * @volt_adjust:	Pointer to array which will be filled with the
 *			per-corner closed-loop adjustment voltages
 * @volt_adjust_fuse:	Pointer to array which will be filled with the
 *			per-fuse-corner closed-loop adjustment voltages
 * @ro_scale:		Pointer to array which will be filled with the
 *			per-fuse-corner RO scaling factor values with units of
 *			QUOT/V
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_parse_closed_loop_voltage_adjustments(
			struct cpr3_regulator *vreg, u64 *ro_sel,
			int *volt_adjust, int *volt_adjust_fuse, int *ro_scale)
{
	int i, rc;
	u32 *ro_all_scale;

	if (!of_find_property(vreg->of_node,
			"qcom,cpr-closed-loop-voltage-adjustment", NULL)
	    && !of_find_property(vreg->of_node,
			"qcom,cpr-closed-loop-voltage-fuse-adjustment", NULL)
	    && !vreg->aging_allowed) {
		/* No adjustment required. */
		return 0;
	} else if (!of_find_property(vreg->of_node,
			"qcom,cpr-ro-scaling-factor", NULL)) {
		cpr3_err(vreg, "qcom,cpr-ro-scaling-factor is required for closed-loop voltage adjustment, but is missing\n");
		return -EINVAL;
	}

	ro_all_scale = kcalloc(vreg->fuse_corner_count * CPR3_RO_COUNT,
				sizeof(*ro_all_scale), GFP_KERNEL);
	if (!ro_all_scale)
		return -ENOMEM;

	rc = cpr3_parse_array_property(vreg, "qcom,cpr-ro-scaling-factor",
		vreg->fuse_corner_count * CPR3_RO_COUNT, ro_all_scale);
	if (rc) {
		cpr3_err(vreg, "could not load RO scaling factors, rc=%d\n",
			rc);
		goto done;
	}

	for (i = 0; i < vreg->fuse_corner_count; i++)
		ro_scale[i] = ro_all_scale[i * CPR3_RO_COUNT + ro_sel[i]];

	for (i = 0; i < vreg->corner_count; i++)
		memcpy(vreg->corner[i].ro_scale,
		 &ro_all_scale[vreg->corner[i].cpr_fuse_corner * CPR3_RO_COUNT],
		 sizeof(*ro_all_scale) * CPR3_RO_COUNT);

	if (of_find_property(vreg->of_node,
			"qcom,cpr-closed-loop-voltage-fuse-adjustment", NULL)) {
		rc = cpr3_parse_array_property(vreg,
			"qcom,cpr-closed-loop-voltage-fuse-adjustment",
			vreg->fuse_corner_count, volt_adjust_fuse);
		if (rc) {
			cpr3_err(vreg, "could not load closed-loop fused voltage adjustments, rc=%d\n",
				rc);
			goto done;
		}
	}

	if (of_find_property(vreg->of_node,
			"qcom,cpr-closed-loop-voltage-adjustment", NULL)) {
		rc = cpr3_parse_corner_array_property(vreg,
			"qcom,cpr-closed-loop-voltage-adjustment",
			1, volt_adjust);
		if (rc) {
			cpr3_err(vreg, "could not load closed-loop voltage adjustments, rc=%d\n",
				rc);
			goto done;
		}
	}

done:
	kfree(ro_all_scale);
	return rc;
}

/**
 * cpr3_apm_init() - initialize APM data for a CPR3 controller
 * @ctrl:		Pointer to the CPR3 controller
 *
 * This function loads memory array power mux (APM) data from device tree
 * if it is present and requests a handle to the appropriate APM controller
 * device.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_apm_init(struct cpr3_controller *ctrl)
{
	struct device_node *node = ctrl->dev->of_node;
	int rc;

	if (!of_find_property(node, "qcom,apm-ctrl", NULL)) {
		/* No APM used */
		return 0;
	}

	ctrl->apm = msm_apm_ctrl_dev_get(ctrl->dev);
	if (IS_ERR(ctrl->apm)) {
		rc = PTR_ERR(ctrl->apm);
		if (rc != -EPROBE_DEFER)
			cpr3_err(ctrl, "APM get failed, rc=%d\n", rc);
		return rc;
	}

	rc = of_property_read_u32(node, "qcom,apm-threshold-voltage",
				&ctrl->apm_threshold_volt);
	if (rc) {
		cpr3_err(ctrl, "error reading qcom,apm-threshold-voltage, rc=%d\n",
			rc);
		return rc;
	}
	ctrl->apm_threshold_volt
		= CPR3_ROUND(ctrl->apm_threshold_volt, ctrl->step_volt);

	/* No error check since this is an optional property. */
	of_property_read_u32(node, "qcom,apm-hysteresis-voltage",
				&ctrl->apm_adj_volt);
	ctrl->apm_adj_volt = CPR3_ROUND(ctrl->apm_adj_volt, ctrl->step_volt);

	ctrl->apm_high_supply = MSM_APM_SUPPLY_APCC;
	ctrl->apm_low_supply = MSM_APM_SUPPLY_MX;

	return 0;
}

/**
 * cpr3_mem_acc_init() - initialize mem-acc regulator data for
 *		a CPR3 regulator
 * @ctrl:		Pointer to the CPR3 controller
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_mem_acc_init(struct cpr3_regulator *vreg)
{
	struct cpr3_controller *ctrl = vreg->thread->ctrl;
	u32 *temp;
	int i, rc;

	if (!ctrl->mem_acc_regulator) {
		cpr3_info(ctrl, "not using memory accelerator regulator\n");
		return 0;
	}

	temp = kcalloc(vreg->corner_count, sizeof(*temp), GFP_KERNEL);
	if (!temp)
		return -ENOMEM;

	rc = cpr3_parse_corner_array_property(vreg, "qcom,mem-acc-voltage",
					      1, temp);
	if (rc) {
		cpr3_err(ctrl, "could not load mem-acc corners, rc=%d\n", rc);
	} else {
		for (i = 0; i < vreg->corner_count; i++)
			vreg->corner[i].mem_acc_volt = temp[i];
	}

	kfree(temp);
	return rc;
}

/**
 * cpr4_load_core_and_temp_adj() - parse amount of voltage adjustment for
 *		per-online-core and per-temperature voltage adjustment for a
 *		given corner or corner band from device tree.
 * @vreg:	Pointer to the CPR3 regulator
 * @num:	Corner number or corner band number
 * @use_corner_band:	Boolean indicating if the CPR3 regulator supports
 *			adjustments per corner band
 *
 * Return: 0 on success, errno on failure
 */
static int cpr4_load_core_and_temp_adj(struct cpr3_regulator *vreg,
					int num, bool use_corner_band)
{
	struct cpr3_controller *ctrl = vreg->thread->ctrl;
	struct cpr4_sdelta *sdelta;
	int sdelta_size, i, j, pos, rc = 0;
	char str[75];
	size_t buflen;
	char *buf;

	sdelta = use_corner_band ? vreg->corner_band[num].sdelta :
		vreg->corner[num].sdelta;

	if (!sdelta->allow_core_count_adj && !sdelta->allow_temp_adj) {
		/* corner doesn't need sdelta table */
		sdelta->max_core_count = 0;
		sdelta->temp_band_count = 0;
		return rc;
	}

	sdelta_size = sdelta->max_core_count * sdelta->temp_band_count;
	snprintf(str, sizeof(str), use_corner_band ?
	 "corner_band=%d core_config_count=%d temp_band_count=%d sdelta_size=%d\n"
	 : "corner=%d core_config_count=%d temp_band_count=%d sdelta_size=%d\n",
		 num, sdelta->max_core_count,
		 sdelta->temp_band_count, sdelta_size);

	cpr3_debug(vreg, "%s", str);

	sdelta->table = devm_kcalloc(ctrl->dev, sdelta_size,
				sizeof(*sdelta->table), GFP_KERNEL);
	if (!sdelta->table)
		return -ENOMEM;

	snprintf(str, sizeof(str), use_corner_band ?
		 "qcom,cpr-corner-band%d-temp-core-voltage-adjustment" :
		 "qcom,cpr-corner%d-temp-core-voltage-adjustment",
		 num + CPR3_CORNER_OFFSET);

	rc = cpr3_parse_array_property(vreg, str, sdelta_size,
				sdelta->table);
	if (rc) {
		cpr3_err(vreg, "could not load %s, rc=%d\n", str, rc);
		return rc;
	}

	/*
	 * Convert sdelta margins from uV to PMIC steps and apply negation to
	 * follow the SDELTA register semantics.
	 */
	for (i = 0; i < sdelta_size; i++)
		sdelta->table[i] = -(sdelta->table[i] / ctrl->step_volt);

	buflen = sizeof(*buf) * sdelta_size * (MAX_CHARS_PER_INT + 2);
	buf = kzalloc(buflen, GFP_KERNEL);
	if (!buf)
		return rc;

	for (i = 0; i < sdelta->max_core_count; i++) {
		for (j = 0, pos = 0; j < sdelta->temp_band_count; j++)
			pos += scnprintf(buf + pos, buflen - pos, " %u",
			 sdelta->table[i * sdelta->temp_band_count + j]);
		cpr3_debug(vreg, "sdelta[%d]:%s\n", i, buf);
	}

	kfree(buf);
	return rc;
}

/**
 * cpr4_parse_core_count_temp_voltage_adj() - parse configuration data for
 *		per-online-core and per-temperature voltage adjustment for
 *		a CPR3 regulator from device tree.
 * @vreg:	Pointer to the CPR3 regulator
 * @use_corner_band:	Boolean indicating if the CPR3 regulator supports
 *			adjustments per corner band
 *
 * This function supports parsing of per-online-core and per-temperature
 * adjustments per corner or per corner band. CPR controllers which support
 * corner bands apply the same adjustments to all corners within a corner band.
 *
 * Return: 0 on success, errno on failure
 */
int cpr4_parse_core_count_temp_voltage_adj(
			struct cpr3_regulator *vreg, bool use_corner_band)
{
	struct cpr3_controller *ctrl = vreg->thread->ctrl;
	struct device_node *node = vreg->of_node;
	struct cpr3_corner *corner;
	struct cpr4_sdelta *sdelta;
	int i, sdelta_table_count, rc = 0;
	int *allow_core_count_adj = NULL, *allow_temp_adj = NULL;
	char prop_str[75];

	if (of_find_property(node, use_corner_band ?
			     "qcom,corner-band-allow-temp-adjustment"
			     : "qcom,corner-allow-temp-adjustment", NULL)) {
		if (!ctrl->allow_temp_adj) {
			cpr3_err(ctrl, "Temperature adjustment configurations missing\n");
			return -EINVAL;
		}

		vreg->allow_temp_adj = true;
	}

	if (of_find_property(node, use_corner_band ?
			     "qcom,corner-band-allow-core-count-adjustment"
			     : "qcom,corner-allow-core-count-adjustment",
			     NULL)) {
		rc = of_property_read_u32(node, "qcom,max-core-count",
				&vreg->max_core_count);
		if (rc) {
			cpr3_err(vreg, "error reading qcom,max-core-count, rc=%d\n",
				rc);
			return -EINVAL;
		}

		vreg->allow_core_count_adj = true;
		ctrl->allow_core_count_adj = true;
	}

	if (!vreg->allow_temp_adj && !vreg->allow_core_count_adj) {
		/*
		 * Both per-online-core and temperature based adjustments are
		 * disabled for this regulator.
		 */
		return 0;
	} else if (!vreg->allow_core_count_adj) {
		/*
		 * Only per-temperature voltage adjusments are allowed.
		 * Keep max core count value as 1 to allocate SDELTA.
		 */
		vreg->max_core_count = 1;
	}

	if (vreg->allow_core_count_adj) {
		allow_core_count_adj = kcalloc(vreg->corner_count,
					sizeof(*allow_core_count_adj),
					GFP_KERNEL);
		if (!allow_core_count_adj)
			return -ENOMEM;

		snprintf(prop_str, sizeof(prop_str), use_corner_band ?
			 "qcom,corner-band-allow-core-count-adjustment" :
			 "qcom,corner-allow-core-count-adjustment");

		rc = use_corner_band ?
			cpr3_parse_corner_band_array_property(vreg, prop_str,
					      1, allow_core_count_adj) :
			cpr3_parse_corner_array_property(vreg, prop_str,
						 1, allow_core_count_adj);
		if (rc) {
			cpr3_err(vreg, "error reading %s, rc=%d\n", prop_str,
				 rc);
			goto done;
		}
	}

	if (vreg->allow_temp_adj) {
		allow_temp_adj = kcalloc(vreg->corner_count,
					sizeof(*allow_temp_adj), GFP_KERNEL);
		if (!allow_temp_adj) {
			rc = -ENOMEM;
			goto done;
		}

		snprintf(prop_str, sizeof(prop_str), use_corner_band ?
			 "qcom,corner-band-allow-temp-adjustment" :
			 "qcom,corner-allow-temp-adjustment");

		rc = use_corner_band ?
			cpr3_parse_corner_band_array_property(vreg, prop_str,
						      1, allow_temp_adj) :
			cpr3_parse_corner_array_property(vreg, prop_str,
						 1, allow_temp_adj);
		if (rc) {
			cpr3_err(vreg, "error reading %s, rc=%d\n", prop_str,
				 rc);
			goto done;
		}
	}

	sdelta_table_count = use_corner_band ? vreg->corner_band_count :
		vreg->corner_count;

	for (i = 0; i < sdelta_table_count; i++) {
		sdelta = devm_kzalloc(ctrl->dev, sizeof(*corner->sdelta),
				      GFP_KERNEL);
		if (!sdelta) {
			rc = -ENOMEM;
			goto done;
		}

		if (allow_core_count_adj)
			sdelta->allow_core_count_adj = allow_core_count_adj[i];
		if (allow_temp_adj)
			sdelta->allow_temp_adj = allow_temp_adj[i];
		sdelta->max_core_count = vreg->max_core_count;
		sdelta->temp_band_count = ctrl->temp_band_count;

		if (use_corner_band)
			vreg->corner_band[i].sdelta = sdelta;
		else
			vreg->corner[i].sdelta = sdelta;

		rc = cpr4_load_core_and_temp_adj(vreg, i, use_corner_band);
		if (rc) {
			cpr3_err(vreg, "corner/band %d core and temp adjustment loading failed, rc=%d\n",
				 i, rc);
			goto done;
		}
	}

done:
	kfree(allow_core_count_adj);
	kfree(allow_temp_adj);

	return rc;
}

/**
 * cprh_adjust_voltages_for_apm() - adjust per-corner floor and ceiling voltages
 *		so that they do not overlap the APM threshold voltage.
 * @vreg:		Pointer to the CPR3 regulator
 *
 * The memory array power mux (APM) must be configured for a specific supply
 * based upon where the VDD voltage lies with respect to the APM threshold
 * voltage.  When using CPR hardware closed-loop, the voltage may vary anywhere
 * between the floor and ceiling voltage without software notification.
 * Therefore, it is required that the floor to ceiling range for every corner
 * not intersect the APM threshold voltage.  This function adjusts the floor to
 * ceiling range for each corner which violates this requirement.
 *
 * The following algorithm is applied:
 *	if floor < threshold <= ceiling:
 *		if open_loop >= threshold, then floor = threshold - adj
 *		else ceiling = threshold - step
 * where:
 *	adj = APM hysteresis voltage established to minimize the number of
 *	      corners with artificially increased floor voltages
 *	step = voltage in microvolts of a single step of the VDD supply
 *
 * The open-loop voltage is also bounded by the new floor or ceiling value as
 * needed.
 *
 * Return: none
 */
void cprh_adjust_voltages_for_apm(struct cpr3_regulator *vreg)
{
	struct cpr3_controller *ctrl = vreg->thread->ctrl;
	struct cpr3_corner *corner;
	int i, adj, threshold, prev_ceiling, prev_floor, prev_open_loop;

	if (!ctrl->apm_threshold_volt) {
		/* APM not being used. */
		return;
	}

	ctrl->apm_threshold_volt = CPR3_ROUND(ctrl->apm_threshold_volt,
						ctrl->step_volt);
	ctrl->apm_adj_volt = CPR3_ROUND(ctrl->apm_adj_volt, ctrl->step_volt);

	threshold = ctrl->apm_threshold_volt;
	adj = ctrl->apm_adj_volt;

	for (i = 0; i < vreg->corner_count; i++) {
		corner = &vreg->corner[i];

		if (threshold <= corner->floor_volt
		    || threshold > corner->ceiling_volt)
			continue;

		prev_floor = corner->floor_volt;
		prev_ceiling = corner->ceiling_volt;
		prev_open_loop = corner->open_loop_volt;

		if (corner->open_loop_volt >= threshold) {
			corner->floor_volt = max(corner->floor_volt,
						 threshold - adj);
			if (corner->open_loop_volt < corner->floor_volt)
				corner->open_loop_volt = corner->floor_volt;
		} else {
			corner->ceiling_volt = threshold - ctrl->step_volt;
		}

		if (corner->floor_volt != prev_floor
		    || corner->ceiling_volt != prev_ceiling
		    || corner->open_loop_volt != prev_open_loop)
			cpr3_debug(vreg, "APM threshold=%d, APM adj=%d changed corner %d voltages; prev: floor=%d, ceiling=%d, open-loop=%d; new: floor=%d, ceiling=%d, open-loop=%d\n",
				threshold, adj, i, prev_floor, prev_ceiling,
				prev_open_loop, corner->floor_volt,
				corner->ceiling_volt, corner->open_loop_volt);
	}
}

/**
 * cprh_adjust_voltages_for_mem_acc() - adjust per-corner floor and ceiling
 *		voltages so that they do not intersect the MEM ACC threshold
 *		voltage
 * @vreg:		Pointer to the CPR3 regulator
 *
 * The following algorithm is applied:
 *	if floor < threshold <= ceiling:
 *		if open_loop >= threshold, then floor = threshold
 *		else ceiling = threshold - step
 * where:
 *	step = voltage in microvolts of a single step of the VDD supply
 *
 * The open-loop voltage is also bounded by the new floor or ceiling value as
 * needed.
 *
 * Return: none
 */
void cprh_adjust_voltages_for_mem_acc(struct cpr3_regulator *vreg)
{
	struct cpr3_controller *ctrl = vreg->thread->ctrl;
	struct cpr3_corner *corner;
	int i, threshold, prev_ceiling, prev_floor, prev_open_loop;

	if (!ctrl->mem_acc_threshold_volt) {
		/* MEM ACC not being used. */
		return;
	}

	ctrl->mem_acc_threshold_volt = CPR3_ROUND(ctrl->mem_acc_threshold_volt,
						ctrl->step_volt);

	threshold = ctrl->mem_acc_threshold_volt;

	for (i = 0; i < vreg->corner_count; i++) {
		corner = &vreg->corner[i];

		if (threshold <= corner->floor_volt
		    || threshold > corner->ceiling_volt)
			continue;

		prev_floor = corner->floor_volt;
		prev_ceiling = corner->ceiling_volt;
		prev_open_loop = corner->open_loop_volt;

		if (corner->open_loop_volt >= threshold) {
			corner->floor_volt = max(corner->floor_volt, threshold);
			if (corner->open_loop_volt < corner->floor_volt)
				corner->open_loop_volt = corner->floor_volt;
		} else {
			corner->ceiling_volt = threshold - ctrl->step_volt;
		}

		if (corner->floor_volt != prev_floor
		    || corner->ceiling_volt != prev_ceiling
		    || corner->open_loop_volt != prev_open_loop)
			cpr3_debug(vreg, "MEM ACC threshold=%d changed corner %d voltages; prev: floor=%d, ceiling=%d, open-loop=%d; new: floor=%d, ceiling=%d, open-loop=%d\n",
				threshold, i, prev_floor, prev_ceiling,
				prev_open_loop, corner->floor_volt,
				corner->ceiling_volt, corner->open_loop_volt);
	}
}

/**
 * cpr3_apply_closed_loop_offset_voltages() - modify the closed-loop voltage
 *		adjustments by the amounts that are needed for this
 *		fuse combo
 * @vreg:		Pointer to the CPR3 regulator
 * @volt_adjust:	Array of closed-loop voltage adjustment values of length
 *			vreg->corner_count which is further adjusted based upon
 *			offset voltage fuse values.
 * @fuse_volt_adjust:	Fused closed-loop voltage adjustment values of length
 *			vreg->fuse_corner_count.
 *
 * Return: 0 on success, errno on failure
 */
static int cpr3_apply_closed_loop_offset_voltages(struct cpr3_regulator *vreg,
			int *volt_adjust, int *fuse_volt_adjust)
{
	u32 *corner_map;
	int rc = 0, i;

	if (!of_find_property(vreg->of_node,
		"qcom,cpr-fused-closed-loop-voltage-adjustment-map", NULL)) {
		/* No closed-loop offset required. */
		return 0;
	}

	corner_map = kcalloc(vreg->corner_count, sizeof(*corner_map),
				GFP_KERNEL);
	if (!corner_map)
		return -ENOMEM;

	rc = cpr3_parse_corner_array_property(vreg,
		"qcom,cpr-fused-closed-loop-voltage-adjustment-map",
		1, corner_map);
	if (rc)
		goto done;

	for (i = 0; i < vreg->corner_count; i++) {
		if (corner_map[i] == 0) {
			continue;
		} else if (corner_map[i] > vreg->fuse_corner_count) {
			cpr3_err(vreg, "corner %d mapped to invalid fuse corner: %u\n",
				i, corner_map[i]);
			rc = -EINVAL;
			goto done;
		}

		volt_adjust[i] += fuse_volt_adjust[corner_map[i] - 1];
	}

done:
	kfree(corner_map);
	return rc;
}

/**
 * cpr3_enforce_inc_quotient_monotonicity() - Ensure that target quotients
 *		increase monotonically from lower to higher corners
 * @vreg:		Pointer to the CPR3 regulator
 *
 * Return: 0 on success, errno on failure
 */
static void cpr3_enforce_inc_quotient_monotonicity(struct cpr3_regulator *vreg)
{
	int i, j;

	for (i = 1; i < vreg->corner_count; i++) {
		for (j = 0; j < CPR3_RO_COUNT; j++) {
			if (vreg->corner[i].target_quot[j]
			    && vreg->corner[i].target_quot[j]
					< vreg->corner[i - 1].target_quot[j]) {
				cpr3_debug(vreg, "corner %d RO%u target quot=%u < corner %d RO%u target quot=%u; overriding: corner %d RO%u target quot=%u\n",
					i, j,
					vreg->corner[i].target_quot[j],
					i - 1, j,
					vreg->corner[i - 1].target_quot[j],
					i, j,
					vreg->corner[i - 1].target_quot[j]);
				vreg->corner[i].target_quot[j]
					= vreg->corner[i - 1].target_quot[j];
			}
		}
	}
}

/**
 * cpr3_enforce_dec_quotient_monotonicity() - Ensure that target quotients
 *		decrease monotonically from higher to lower corners
 * @vreg:		Pointer to the CPR3 regulator
 *
 * Return: 0 on success, errno on failure
 */
static void cpr3_enforce_dec_quotient_monotonicity(struct cpr3_regulator *vreg)
{
	int i, j;

	for (i = vreg->corner_count - 2; i >= 0; i--) {
		for (j = 0; j < CPR3_RO_COUNT; j++) {
			if (vreg->corner[i + 1].target_quot[j]
			    && vreg->corner[i].target_quot[j]
					> vreg->corner[i + 1].target_quot[j]) {
				cpr3_debug(vreg, "corner %d RO%u target quot=%u > corner %d RO%u target quot=%u; overriding: corner %d RO%u target quot=%u\n",
					i, j,
					vreg->corner[i].target_quot[j],
					i + 1, j,
					vreg->corner[i + 1].target_quot[j],
					i, j,
					vreg->corner[i + 1].target_quot[j]);
				vreg->corner[i].target_quot[j]
					= vreg->corner[i + 1].target_quot[j];
			}
		}
	}
}

/**
 * _cpr3_adjust_target_quotients() - adjust the target quotients for each
 *		corner of the regulator according to input adjustment and
 *		scaling arrays
 * @vreg:		Pointer to the CPR3 regulator
 * @volt_adjust:	Pointer to an array of closed-loop voltage adjustments
 *			with units of microvolts.  The array must have
 *			vreg->corner_count number of elements.
 * @ro_scale:		Pointer to a flattened 2D array of RO scaling factors.
 *			The array must have an inner dimension of CPR3_RO_COUNT
 *			and an outer dimension of vreg->corner_count
 * @label:		Null terminated string providing a label for the type
 *			of adjustment.
 *
 * Return: true if any corners received a positive voltage adjustment (> 0),
 *	   else false
 */
static bool _cpr3_adjust_target_quotients(struct cpr3_regulator *vreg,
		const int *volt_adjust, const int *ro_scale, const char *label)
{
	int i, j, quot_adjust;
	bool is_increasing = false;
	u32 prev_quot;

	for (i = 0; i < vreg->corner_count; i++) {
		for (j = 0; j < CPR3_RO_COUNT; j++) {
			if (vreg->corner[i].target_quot[j]) {
				quot_adjust = cpr3_quot_adjustment(
					ro_scale[i * CPR3_RO_COUNT + j],
					volt_adjust[i]);
				if (quot_adjust) {
					prev_quot = vreg->corner[i].
							target_quot[j];
					vreg->corner[i].target_quot[j]
						+= quot_adjust;
					cpr3_debug(vreg, "adjusted corner %d RO%d target quot %s: %u --> %u (%d uV)\n",
						i, j, label, prev_quot,
						vreg->corner[i].target_quot[j],
						volt_adjust[i]);
				}
			}
		}
		if (volt_adjust[i] > 0)
			is_increasing = true;
	}

	return is_increasing;
}

/**
 * cpr3_adjust_target_quotients() - adjust the target quotients for each
 *			corner according to device tree values and fuse values
 * @vreg:		Pointer to the CPR3 regulator
 * @fuse_volt_adjust:	Fused closed-loop voltage adjustment values of length
 *			vreg->fuse_corner_count. This parameter could be null
 *			pointer when no fused adjustments are needed.
 *
 * Return: 0 on success, errno on failure
 */
int cpr3_adjust_target_quotients(struct cpr3_regulator *vreg,
			int *fuse_volt_adjust)
{
	int i, rc;
	int *volt_adjust, *ro_scale;
	bool explicit_adjustment, fused_adjustment, is_increasing;

	explicit_adjustment = of_find_property(vreg->of_node,
		"qcom,cpr-closed-loop-voltage-adjustment", NULL);
	fused_adjustment = of_find_property(vreg->of_node,
		"qcom,cpr-fused-closed-loop-voltage-adjustment-map", NULL);

	if (!explicit_adjustment && !fused_adjustment && !vreg->aging_allowed) {
		/* No adjustment required. */
		return 0;
	} else if (!of_find_property(vreg->of_node,
			"qcom,cpr-ro-scaling-factor", NULL)) {
		cpr3_err(vreg, "qcom,cpr-ro-scaling-factor is required for closed-loop voltage adjustment, but is missing\n");
		return -EINVAL;
	}

	volt_adjust = kcalloc(vreg->corner_count, sizeof(*volt_adjust),
				GFP_KERNEL);
	ro_scale = kcalloc(vreg->corner_count * CPR3_RO_COUNT,
				sizeof(*ro_scale), GFP_KERNEL);
	if (!volt_adjust || !ro_scale) {
		rc = -ENOMEM;
		goto done;
	}

	rc = cpr3_parse_corner_array_property(vreg,
			"qcom,cpr-ro-scaling-factor", CPR3_RO_COUNT, ro_scale);
	if (rc) {
		cpr3_err(vreg, "could not load RO scaling factors, rc=%d\n",
			rc);
		goto done;
	}

	for (i = 0; i < vreg->corner_count; i++)
		memcpy(vreg->corner[i].ro_scale, &ro_scale[i * CPR3_RO_COUNT],
			sizeof(*ro_scale) * CPR3_RO_COUNT);

	if (explicit_adjustment) {
		rc = cpr3_parse_corner_array_property(vreg,
			"qcom,cpr-closed-loop-voltage-adjustment",
			1, volt_adjust);
		if (rc) {
			cpr3_err(vreg, "could not load closed-loop voltage adjustments, rc=%d\n",
				rc);
			goto done;
		}

		_cpr3_adjust_target_quotients(vreg, volt_adjust, ro_scale,
			"from DT");
		cpr3_enforce_inc_quotient_monotonicity(vreg);
	}

	if (fused_adjustment && fuse_volt_adjust) {
		memset(volt_adjust, 0,
			sizeof(*volt_adjust) * vreg->corner_count);

		rc = cpr3_apply_closed_loop_offset_voltages(vreg, volt_adjust,
				fuse_volt_adjust);
		if (rc) {
			cpr3_err(vreg, "could not apply fused closed-loop voltage reductions, rc=%d\n",
				rc);
			goto done;
		}

		is_increasing = _cpr3_adjust_target_quotients(vreg, volt_adjust,
					ro_scale, "from fuse");
		if (is_increasing)
			cpr3_enforce_inc_quotient_monotonicity(vreg);
		else
			cpr3_enforce_dec_quotient_monotonicity(vreg);
	}

done:
	kfree(volt_adjust);
	kfree(ro_scale);
	return rc;
}

/**
 * cpr3_parse_fuse_combo_map() - parse fuse combo map data for a CPR3 regulator
 *		from device tree.
 * @vreg:		Pointer to the CPR3 regulator
 * @fuse_val:		Array of selection fuse parameter values
 * @fuse_count:		Number of selection fuse parameters used in fuse combo
 *			map
 *
 * This function reads the qcom,cpr-fuse-combo-map device tree property and
 * populates the fuse_combo element of CPR3 regulator with the row number of
 * fuse combo map data that matches with the data in fuse_val input array.
 *
 * Return: 0 on success, -ENODEV if qcom,cpr-fuse-combo-map property is not
 *		specified in device node, other errno on failure
 */
int cpr3_parse_fuse_combo_map(struct cpr3_regulator *vreg, u64 *fuse_val,
			int fuse_count)
{
	struct device_node *node = vreg->of_node;
	int i, j, len, num_fuse_combos, row_size, rc = 0;
	u32 *tmp;

	if (!of_find_property(node, "qcom,cpr-fuse-combo-map", &len)) {
		/* property not specified */
		return -ENODEV;
	}

	row_size = fuse_count * 2;
	if (len == 0 || len % (sizeof(u32) * row_size)) {
		cpr3_err(vreg, "qcom,cpr-fuse-combo-map length=%d is invalid\n",
			len);
		return -EINVAL;
	}

	num_fuse_combos = len / (sizeof(u32) * row_size);
	vreg->fuse_combos_supported = num_fuse_combos;

	tmp = kzalloc(len, GFP_KERNEL);
	if (!tmp)
		return -ENOMEM;

	rc = of_property_read_u32_array(node, "qcom,cpr-fuse-combo-map",
			tmp, num_fuse_combos * row_size);
	if (rc) {
		cpr3_err(vreg, "could not read qcom,cpr-fuse-combo-map, rc=%d\n",
			rc);
		goto done;
	}

	for (i = 0; i < num_fuse_combos; i++) {
		for (j = 0; j < fuse_count; j++) {
			if (tmp[i * row_size + j * 2] > fuse_val[j]
			      || tmp[i * row_size + j * 2 + 1] < fuse_val[j])
				break;
		}
		if (j == fuse_count) {
			vreg->fuse_combo = i;
			break;
		}
	}

	if (i >= num_fuse_combos) {
		cpr3_err(vreg, "No matching CPR fuse combo found!\n");
		WARN_ON(1);
		rc = -EINVAL;
		goto done;
	}

done:
	kfree(tmp);
	return rc;
}
