/*
 * Copyright (c) 2022 Nordic Semiconductor ASA
 * SPDX-License-Identifier: Apache-2.0
 */

#define DT_DRV_COMPAT nordic_npm6001_regulator

#include <errno.h>

#include <zephyr/drivers/i2c.h>
#include <zephyr/drivers/regulator.h>
#include <zephyr/dt-bindings/regulator/npm6001.h>
#include <zephyr/sys/__assert.h>
#include <zephyr/sys/linear_range.h>
#include <zephyr/sys/util.h>

/* nPM6001 voltage sources */
enum npm6001_sources {
	NPM6001_SOURCE_BUCK0,
	NPM6001_SOURCE_BUCK1,
	NPM6001_SOURCE_BUCK2,
	NPM6001_SOURCE_BUCK3,
	NPM6001_SOURCE_LDO0,
	NPM6001_SOURCE_LDO1,
};

/* nPM6001 regulator related registers */
#define NPM6001_TASKS_START_BUCK3    0x02U
#define NPM6001_TASKS_START_LDO0     0x03U
#define NPM6001_TASKS_START_LDO1     0x04U
#define NPM6001_TASKS_STOP_BUCK3     0x08U
#define NPM6001_TASKS_STOP_LDO0	     0x09U
#define NPM6001_TASKS_STOP_LDO1	     0x0AU
#define NPM6001_TASKS_UPDATE_VOUTPWM 0x0EU
#define NPM6001_EVENTS_THWARN	     0x1EU
#define NPM6001_EVENTS_BUCK0OC	     0x1FU
#define NPM6001_EVENTS_BUCK1OC	     0x20U
#define NPM6001_EVENTS_BUCK2OC	     0x21U
#define NPM6001_EVENTS_BUCK3OC	     0x22U
#define NPM6001_BUCK0VOUTULP	     0x3AU
#define NPM6001_BUCK1VOUTULP	     0x3CU
#define NPM6001_BUCK2VOUTULP	     0x40U
#define NPM6001_BUCK3SELDAC	     0x44U
#define NPM6001_BUCK3VOUT	     0x45U
#define NPM6001_LDO0VOUT	     0x46U
#define NPM6001_BUCK0CONFPWMMODE     0x4AU
#define NPM6001_BUCK1CONFPWMMODE     0x4BU
#define NPM6001_BUCK2CONFPWMMODE     0x4CU
#define NPM6001_BUCK3CONFPWMMODE     0x4DU
#define NPM6001_BUCKMODEPADCONF	     0x4EU
#define NPM6001_PADDRIVESTRENGTH     0x53U
#define NPM6001_OVERRIDEPWRUPBUCK    0xABU

/* nPM6001 LDO0VOUT values */
#define NPM6001_LDO0VOUT_SET1V8	 0x06U
#define NPM6001_LDO0VOUT_SET2V1	 0x0BU
#define NPM6001_LDO0VOUT_SET2V41 0x10U
#define NPM6001_LDO0VOUT_SET2V7	 0x15U
#define NPM6001_LDO0VOUT_SET3V0	 0x1AU
#define NPM6001_LDO0VOUT_SET3V3	 0x1EU

/* nPM6001 BUCKXCONFPWMMODE fields */
#define NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM_MSK 0x8U
#define NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM_POS 3
#define NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM                                   \
	BIT(NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM_POS)

#define NPM6001_BUCKMODEPADCONF_BUCKMODE0PADTYPE_CMOS  BIT(0)
#define NPM6001_BUCKMODEPADCONF_BUCKMODE1PADTYPE_CMOS  BIT(1)
#define NPM6001_BUCKMODEPADCONF_BUCKMODE2PADTYPE_CMOS  BIT(2)
#define NPM6001_BUCKMODEPADCONF_BUCKMODE0PULLD_ENABLED BIT(4)
#define NPM6001_BUCKMODEPADCONF_BUCKMODE1PULLD_ENABLED BIT(5)
#define NPM6001_BUCKMODEPADCONF_BUCKMODE2PULLD_ENABLED BIT(6)

/* nPM6001 PADDRIVESTRENGTH fields */
#define NPM6001_PADDRIVESTRENGTH_READY_HIGH BIT(2)
#define NPM6001_PADDRIVESTRENGTH_NINT_HIGH  BIT(3)
#define NPM6001_PADDRIVESTRENGTH_SDA_HIGH   BIT(5)

/* nPM6001 OVERRIDEPWRUPBUCK fields */
#define NPM6001_OVERRIDEPWRUPBUCK_BUCK1DISABLE_MSK 0x22U
#define NPM6001_OVERRIDEPWRUPBUCK_BUCK2DISABLE_MSK 0x44U
#define NPM6001_OVERRIDEPWRUPBUCK_BUCK1DISABLE     BIT(1)
#define NPM6001_OVERRIDEPWRUPBUCK_BUCK2DISABLE     BIT(2)

struct regulator_npm6001_pconfig {
	struct i2c_dt_spec i2c;
	uint8_t buck_pad_val;
	uint8_t pad_val;
};

struct regulator_npm6001_config {
	struct regulator_common_config common;
	const struct device *p;
	uint8_t source;
};

struct regulator_npm6001_data {
	struct regulator_common_data data;
};

struct regulator_npm6001_vmap {
	uint8_t reg_val;
	int32_t volt_uv;
};

static const struct linear_range buck0_range =
	LINEAR_RANGE_INIT(1800000, 100000U, 0x0U, 0xFU);

static const struct linear_range buck1_range =
	LINEAR_RANGE_INIT(700000, 50000U, 0x0U, 0xEU);

static const struct linear_range buck2_range =
	LINEAR_RANGE_INIT(1200000, 50000U, 0xAU, 0xEU);

static const struct linear_range buck3_range =
	LINEAR_RANGE_INIT(500000, 25000U, 0x0U, 0x70U);

static const struct regulator_npm6001_vmap ldo0_voltages[] = {
	{ NPM6001_LDO0VOUT_SET1V8, 1800000 },
	{ NPM6001_LDO0VOUT_SET2V1, 2100000 },
	{ NPM6001_LDO0VOUT_SET2V41, 2410000 },
	{ NPM6001_LDO0VOUT_SET2V7, 2700000 },
	{ NPM6001_LDO0VOUT_SET3V0, 3000000 },
	{ NPM6001_LDO0VOUT_SET3V3, 3300000 },
};

static int regulator_npm6001_ldo0_list_voltage(const struct device *dev,
					       unsigned int idx,
					       int32_t *volt_uv)
{
	if (idx >= ARRAY_SIZE(ldo0_voltages)) {
		return -EINVAL;
	}

	*volt_uv = ldo0_voltages[idx].volt_uv;

	return 0;
}

static int regulator_npm6001_buck012_set_voltage(
	const struct device *dev, int32_t min_uv, int32_t max_uv,
	const struct linear_range *range, uint8_t vout_reg, uint8_t conf_reg)
{
	const struct regulator_npm6001_config *config = dev->config;
	const struct regulator_npm6001_pconfig *pconfig = config->p->config;
	uint8_t conf, buf[3];
	uint16_t idx;
	int ret;

	ret = linear_range_get_win_index(range, min_uv, max_uv, &idx);
	if (ret == -EINVAL) {
		return ret;
	}

	/* force PWM mode when updating voltage */
	ret = i2c_reg_read_byte_dt(&pconfig->i2c, conf_reg, &conf);
	if (ret < 0) {
		return ret;
	}

	if ((conf & NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM) == 0U) {
		ret = i2c_reg_write_byte_dt(
			&pconfig->i2c, conf_reg,
			conf | NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM);
		if (ret < 0) {
			return ret;
		}
	}

	/* write voltage in both ULP/PWM registers */
	buf[0] = vout_reg;
	buf[1] = (uint8_t)idx;
	buf[2] = (uint8_t)idx;

	ret = i2c_write_dt(&pconfig->i2c, buf, sizeof(buf));
	if (ret < 0) {
		return ret;
	}

	ret = i2c_reg_write_byte_dt(&pconfig->i2c, NPM6001_TASKS_UPDATE_VOUTPWM,
				    1U);
	if (ret < 0) {
		return ret;
	}

	/* restore HYS mode if enabled before */
	if ((conf & NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM) == 0U) {
		ret = i2c_reg_write_byte_dt(&pconfig->i2c, conf_reg, conf);
		if (ret < 0) {
			return ret;
		}
	}

	return 0;
}

static int regulator_npm6001_buck3_set_voltage(const struct device *dev,
					       int32_t min_uv, int32_t max_uv)
{
	const struct regulator_npm6001_config *config = dev->config;
	const struct regulator_npm6001_pconfig *pconfig = config->p->config;
	uint16_t idx;
	uint8_t conf;
	int ret;

	ret = linear_range_get_win_index(&buck3_range, min_uv, max_uv, &idx);
	if (ret == -EINVAL) {
		return ret;
	}

	/* force PWM mode when updating voltage */
	ret = i2c_reg_read_byte_dt(&pconfig->i2c, NPM6001_BUCK3CONFPWMMODE,
				   &conf);
	if (ret < 0) {
		return ret;
	}

	if ((conf & NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM) == 0U) {
		ret = i2c_reg_write_byte_dt(
			&pconfig->i2c, NPM6001_BUCK3CONFPWMMODE,
			conf | NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM);
		if (ret < 0) {
			return ret;
		}
	}

	ret = i2c_reg_write_byte_dt(&pconfig->i2c, NPM6001_BUCK3VOUT,
				    (uint8_t)idx);
	if (ret < 0) {
		return ret;
	}

	/* restore HYS mode if enabled before */
	if ((conf & NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM) == 0U) {
		ret = i2c_reg_write_byte_dt(&pconfig->i2c,
					    NPM6001_BUCK3CONFPWMMODE, conf);
		if (ret < 0) {
			return ret;
		}
	}

	return 0;
}

static int regulator_npm6001_ldo0_set_voltage(const struct device *dev,
					      int32_t min_uv, int32_t max_uv)
{
	const struct regulator_npm6001_config *config = dev->config;
	const struct regulator_npm6001_pconfig *pconfig = config->p->config;
	uint8_t val;
	size_t i;

	for (i = 0U; i < ARRAY_SIZE(ldo0_voltages); i++) {
		if ((min_uv <= ldo0_voltages[i].volt_uv) &&
		    (max_uv >= ldo0_voltages[i].volt_uv)) {
			val = ldo0_voltages[i].reg_val;
			break;
		}
	}

	if (i == ARRAY_SIZE(ldo0_voltages)) {
		return -EINVAL;
	}

	return i2c_reg_write_byte_dt(&pconfig->i2c, NPM6001_LDO0VOUT, val);
}

static int
regulator_npm6001_buck0123_get_voltage(const struct device *dev,
				       const struct linear_range *range,
				       uint8_t vout_reg, int32_t *volt_uv)
{
	const struct regulator_npm6001_config *config = dev->config;
	const struct regulator_npm6001_pconfig *pconfig = config->p->config;
	uint8_t idx;
	int ret;

	ret = i2c_reg_read_byte_dt(&pconfig->i2c, vout_reg, &idx);
	if (ret < 0) {
		return ret;
	}

	return linear_range_get_value(range, idx, volt_uv);
}

static int regulator_npm6001_ldo0_get_voltage(const struct device *dev,
					      int32_t *volt_uv)
{
	const struct regulator_npm6001_config *config = dev->config;
	const struct regulator_npm6001_pconfig *pconfig = config->p->config;
	uint8_t val;
	int ret;

	ret = i2c_reg_read_byte_dt(&pconfig->i2c, NPM6001_LDO0VOUT, &val);
	if (ret < 0) {
		return ret;
	}

	for (size_t i = 0U; i < ARRAY_SIZE(ldo0_voltages); i++) {
		if (val == ldo0_voltages[i].reg_val) {
			*volt_uv = ldo0_voltages[i].volt_uv;
			return 0;
		}
	}

	__ASSERT(NULL, "Unexpected voltage");

	return -EINVAL;
}

static unsigned int regulator_npm6001_count_voltages(const struct device *dev)
{
	const struct regulator_npm6001_config *config = dev->config;

	switch (config->source) {
	case NPM6001_SOURCE_BUCK0:
		return linear_range_values_count(&buck0_range);
	case NPM6001_SOURCE_BUCK1:
		return linear_range_values_count(&buck1_range);
	case NPM6001_SOURCE_BUCK2:
		return linear_range_values_count(&buck2_range);
	case NPM6001_SOURCE_BUCK3:
		return linear_range_values_count(&buck3_range);
	case NPM6001_SOURCE_LDO0:
		return 6U;
	case NPM6001_SOURCE_LDO1:
		return 1U;
	default:
		__ASSERT(NULL, "Unexpected source");
	}

	return 0;
}

static int regulator_npm6001_list_voltage(const struct device *dev,
					  unsigned int idx, int32_t *volt_uv)
{
	const struct regulator_npm6001_config *config = dev->config;

	switch (config->source) {
	case NPM6001_SOURCE_BUCK0:
		return linear_range_get_value(&buck0_range, idx, volt_uv);
	case NPM6001_SOURCE_BUCK1:
		return linear_range_get_value(&buck1_range, idx, volt_uv);
	case NPM6001_SOURCE_BUCK2:
		return linear_range_get_value(
			&buck2_range, idx + buck2_range.min_idx, volt_uv);
	case NPM6001_SOURCE_BUCK3:
		return linear_range_get_value(&buck3_range, idx, volt_uv);
	case NPM6001_SOURCE_LDO0:
		return regulator_npm6001_ldo0_list_voltage(dev, idx, volt_uv);
	case NPM6001_SOURCE_LDO1:
		*volt_uv = 1800000;
		break;
	default:
		__ASSERT(NULL, "Unexpected source");
	}

	return 0;
}

static int regulator_npm6001_set_voltage(const struct device *dev,
					 int32_t min_uv, int32_t max_uv)
{
	const struct regulator_npm6001_config *config = dev->config;

	switch (config->source) {
	case NPM6001_SOURCE_BUCK0:
		return regulator_npm6001_buck012_set_voltage(
			dev, min_uv, max_uv, &buck0_range, NPM6001_BUCK0VOUTULP,
			NPM6001_BUCK0CONFPWMMODE);
	case NPM6001_SOURCE_BUCK1:
		return regulator_npm6001_buck012_set_voltage(
			dev, min_uv, max_uv, &buck1_range, NPM6001_BUCK1VOUTULP,
			NPM6001_BUCK1CONFPWMMODE);
	case NPM6001_SOURCE_BUCK2:
		return regulator_npm6001_buck012_set_voltage(
			dev, min_uv, max_uv, &buck2_range, NPM6001_BUCK2VOUTULP,
			NPM6001_BUCK2CONFPWMMODE);
	case NPM6001_SOURCE_BUCK3:
		return regulator_npm6001_buck3_set_voltage(dev, min_uv, max_uv);
	case NPM6001_SOURCE_LDO0:
		return regulator_npm6001_ldo0_set_voltage(dev, min_uv, max_uv);
	case NPM6001_SOURCE_LDO1:
		if ((min_uv != 1800000) && (max_uv != 1800000)) {
			return -EINVAL;
		}
		break;
	default:
		__ASSERT(NULL, "Unexpected source");
	}

	return 0;
}

static int regulator_npm6001_get_voltage(const struct device *dev,
					 int32_t *volt_uv)
{
	const struct regulator_npm6001_config *config = dev->config;

	switch (config->source) {
	case NPM6001_SOURCE_BUCK0:
		return regulator_npm6001_buck0123_get_voltage(
			dev, &buck0_range, NPM6001_BUCK0VOUTULP, volt_uv);
	case NPM6001_SOURCE_BUCK1:
		return regulator_npm6001_buck0123_get_voltage(
			dev, &buck1_range, NPM6001_BUCK1VOUTULP, volt_uv);
	case NPM6001_SOURCE_BUCK2:
		return regulator_npm6001_buck0123_get_voltage(
			dev, &buck2_range, NPM6001_BUCK2VOUTULP, volt_uv);
	case NPM6001_SOURCE_BUCK3:
		return regulator_npm6001_buck0123_get_voltage(
			dev, &buck3_range, NPM6001_BUCK3VOUT, volt_uv);
	case NPM6001_SOURCE_LDO0:
		return regulator_npm6001_ldo0_get_voltage(dev, volt_uv);
	case NPM6001_SOURCE_LDO1:
		*volt_uv = 1800000U;
		break;
	default:
		__ASSERT(NULL, "Unexpected source");
	}

	return 0;
}

static int regulator_npm6001_set_mode(const struct device *dev,
				      regulator_mode_t mode)
{
	const struct regulator_npm6001_config *config = dev->config;
	const struct regulator_npm6001_pconfig *pconfig = config->p->config;
	uint8_t conf_reg;

	if (mode > NPM6001_MODE_PWM) {
		return -ENOTSUP;
	}

	switch (config->source) {
	case NPM6001_SOURCE_BUCK0:
		conf_reg = NPM6001_BUCK0CONFPWMMODE;
		break;
	case NPM6001_SOURCE_BUCK1:
		conf_reg = NPM6001_BUCK1CONFPWMMODE;
		break;
	case NPM6001_SOURCE_BUCK2:
		conf_reg = NPM6001_BUCK2CONFPWMMODE;
		break;
	case NPM6001_SOURCE_BUCK3:
		conf_reg = NPM6001_BUCK3CONFPWMMODE;
		break;
	default:
		return -ENOTSUP;
	}

	return i2c_reg_update_byte_dt(
		&pconfig->i2c, conf_reg,
		NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM_MSK,
		mode << NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM_POS);
}

static int regulator_npm6001_get_mode(const struct device *dev,
				      regulator_mode_t *mode)
{
	const struct regulator_npm6001_config *config = dev->config;
	const struct regulator_npm6001_pconfig *pconfig = config->p->config;
	uint8_t conf_reg, conf;
	int ret;

	switch (config->source) {
	case NPM6001_SOURCE_BUCK0:
		conf_reg = NPM6001_BUCK0CONFPWMMODE;
		break;
	case NPM6001_SOURCE_BUCK1:
		conf_reg = NPM6001_BUCK1CONFPWMMODE;
		break;
	case NPM6001_SOURCE_BUCK2:
		conf_reg = NPM6001_BUCK2CONFPWMMODE;
		break;
	case NPM6001_SOURCE_BUCK3:
		conf_reg = NPM6001_BUCK3CONFPWMMODE;
		break;
	default:
		return -ENOTSUP;
	}

	ret = i2c_reg_read_byte_dt(&pconfig->i2c, conf_reg, &conf);
	if (ret < 0) {
		return ret;
	}

	*mode = (conf & NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM_MSK) >>
		NPM6001_BUCKXCONFPWMMODE_SETFORCEPWM_POS;

	return 0;
}

static int regulator_npm6001_enable(const struct device *dev)
{
	const struct regulator_npm6001_config *config = dev->config;
	const struct regulator_npm6001_pconfig *pconfig = config->p->config;

	switch (config->source) {
	case NPM6001_SOURCE_BUCK1:
		return i2c_reg_update_byte_dt(
			&pconfig->i2c, NPM6001_OVERRIDEPWRUPBUCK,
			NPM6001_OVERRIDEPWRUPBUCK_BUCK1DISABLE_MSK, 0U);
	case NPM6001_SOURCE_BUCK2:
		return i2c_reg_update_byte_dt(
			&pconfig->i2c, NPM6001_OVERRIDEPWRUPBUCK,
			NPM6001_OVERRIDEPWRUPBUCK_BUCK2DISABLE_MSK, 0U);
	case NPM6001_SOURCE_BUCK3:
		return i2c_reg_write_byte_dt(&pconfig->i2c,
					     NPM6001_TASKS_START_BUCK3, 1U);
	case NPM6001_SOURCE_LDO0:
		return i2c_reg_write_byte_dt(&pconfig->i2c,
					     NPM6001_TASKS_START_LDO0, 1U);
	case NPM6001_SOURCE_LDO1:
		return i2c_reg_write_byte_dt(&pconfig->i2c,
					     NPM6001_TASKS_START_LDO1, 1U);
	default:
		return 0;
	}
}

static int regulator_npm6001_disable(const struct device *dev)
{
	const struct regulator_npm6001_config *config = dev->config;
	const struct regulator_npm6001_pconfig *pconfig = config->p->config;

	switch (config->source) {
	case NPM6001_SOURCE_BUCK1:
		return i2c_reg_update_byte_dt(
			&pconfig->i2c, NPM6001_OVERRIDEPWRUPBUCK,
			NPM6001_OVERRIDEPWRUPBUCK_BUCK1DISABLE_MSK,
			NPM6001_OVERRIDEPWRUPBUCK_BUCK1DISABLE);
	case NPM6001_SOURCE_BUCK2:
		return i2c_reg_update_byte_dt(
			&pconfig->i2c, NPM6001_OVERRIDEPWRUPBUCK,
			NPM6001_OVERRIDEPWRUPBUCK_BUCK2DISABLE_MSK,
			NPM6001_OVERRIDEPWRUPBUCK_BUCK2DISABLE);
	case NPM6001_SOURCE_BUCK3:
		return i2c_reg_write_byte_dt(&pconfig->i2c,
					     NPM6001_TASKS_STOP_BUCK3, 1U);
	case NPM6001_SOURCE_LDO0:
		return i2c_reg_write_byte_dt(&pconfig->i2c,
					     NPM6001_TASKS_STOP_LDO0, 1U);
	case NPM6001_SOURCE_LDO1:
		return i2c_reg_write_byte_dt(&pconfig->i2c,
					     NPM6001_TASKS_STOP_LDO1, 1U);
	default:
		return 0;
	}
}

static int regulator_npm6001_get_error_flags(const struct device *dev,
					     regulator_error_flags_t *flags)
{
	const struct regulator_npm6001_config *config = dev->config;
	const struct regulator_npm6001_pconfig *pconfig = config->p->config;
	uint8_t oc_reg, val;
	int ret;

	*flags = 0U;

	/* read thermal warning */
	ret = i2c_reg_read_byte_dt(&pconfig->i2c, NPM6001_EVENTS_THWARN, &val);
	if (ret < 0) {
		return ret;
	}

	if (val != 0U) {
		/* clear thermal warning */
		ret = i2c_reg_write_byte_dt(&pconfig->i2c,
					    NPM6001_EVENTS_THWARN, 0U);
		if (ret < 0) {
			return ret;
		}

		*flags |= REGULATOR_ERROR_OVER_TEMP;
	}

	/* read overcurrent event */
	switch (config->source) {
	case NPM6001_SOURCE_BUCK0:
		oc_reg = NPM6001_EVENTS_BUCK0OC;
		break;
	case NPM6001_SOURCE_BUCK1:
		oc_reg = NPM6001_EVENTS_BUCK1OC;
		break;
	case NPM6001_SOURCE_BUCK2:
		oc_reg = NPM6001_EVENTS_BUCK2OC;
		break;
	case NPM6001_SOURCE_BUCK3:
		oc_reg = NPM6001_EVENTS_BUCK3OC;
		break;
	default:
		return 0;
	}

	ret = i2c_reg_read_byte_dt(&pconfig->i2c, oc_reg, &val);
	if (ret < 0) {
		return ret;
	}

	if (val != 0U) {
		/* clear overcurrent event */
		ret = i2c_reg_write_byte_dt(&pconfig->i2c, oc_reg, 0U);
		if (ret < 0) {
			return ret;
		}

		*flags |= REGULATOR_ERROR_OVER_CURRENT;
	}

	return 0;
}

static int regulator_npm6001_init(const struct device *dev)
{
	const struct regulator_npm6001_config *config = dev->config;
	bool is_enabled;

	regulator_common_data_init(dev);

	if (!device_is_ready(config->p)) {
		return -ENODEV;
	}

	/* BUCK1/2 are ON by default */
	is_enabled = (config->source == NPM6001_SOURCE_BUCK1) ||
		     (config->source == NPM6001_SOURCE_BUCK2);

	return regulator_common_init(dev, is_enabled);
}

static int regulator_npm6001_common_init(const struct device *dev)
{
	const struct regulator_npm6001_pconfig *config = dev->config;
	int ret;

	if (!device_is_ready(config->i2c.bus)) {
		return -ENODEV;
	}

	/* always select BUCK3 DAC (does not increase power consumption) */
	ret = i2c_reg_write_byte_dt(&config->i2c, NPM6001_BUCK3SELDAC, 1U);
	if (ret < 0) {
		return ret;
	}

	/* configure pad properties */
	ret = i2c_reg_write_byte_dt(&config->i2c, NPM6001_BUCKMODEPADCONF,
				    config->buck_pad_val);
	if (ret < 0) {
		return ret;
	}

	ret = i2c_reg_write_byte_dt(&config->i2c, NPM6001_PADDRIVESTRENGTH,
				    config->pad_val);
	if (ret < 0) {
		return ret;
	}

	return 0;
}

static const struct regulator_driver_api api = {
	.enable = regulator_npm6001_enable,
	.disable = regulator_npm6001_disable,
	.count_voltages = regulator_npm6001_count_voltages,
	.list_voltage = regulator_npm6001_list_voltage,
	.set_voltage = regulator_npm6001_set_voltage,
	.get_voltage = regulator_npm6001_get_voltage,
	.set_mode = regulator_npm6001_set_mode,
	.get_mode = regulator_npm6001_get_mode,
	.get_error_flags = regulator_npm6001_get_error_flags,
};

#define REGULATOR_NPM6001_DEFINE(node_id, id, _source, parent)                 \
	static struct regulator_npm6001_data data_##id;                        \
                                                                               \
	static const struct regulator_npm6001_config config_##id = {           \
		.common = REGULATOR_DT_COMMON_CONFIG_INIT(node_id),            \
		.p = parent,                                                   \
		.source = _source,                                             \
	};                                                                     \
                                                                               \
	DEVICE_DT_DEFINE(node_id, regulator_npm6001_init, NULL, &data_##id,    \
			 &config_##id, POST_KERNEL,                            \
			 CONFIG_REGULATOR_NPM6001_INIT_PRIORITY, &api);

#define REGULATOR_NPM6001_DEFINE_COND(inst, child, source, parent)             \
	COND_CODE_1(DT_NODE_EXISTS(DT_INST_CHILD(inst, child)),                \
		    (REGULATOR_NPM6001_DEFINE(DT_INST_CHILD(inst, child),      \
					      child##inst, source, parent)),   \
		    ())

#define REGULATOR_NPM6001_DEFINE_ALL(inst)                                     \
	static const struct regulator_npm6001_pconfig config_##inst = {        \
		.i2c = I2C_DT_SPEC_GET(DT_INST_PARENT(inst)),                  \
		.buck_pad_val =                                                \
			((DT_INST_ENUM_IDX(inst,                               \
					   nordic_buck_mode0_input_type) *     \
			  NPM6001_BUCKMODEPADCONF_BUCKMODE0PADTYPE_CMOS) |     \
			 (DT_INST_ENUM_IDX(inst,                               \
					   nordic_buck_mode1_input_type) *     \
			  NPM6001_BUCKMODEPADCONF_BUCKMODE1PADTYPE_CMOS) |     \
			 (DT_INST_ENUM_IDX(inst,                               \
					   nordic_buck_mode2_input_type) *     \
			  NPM6001_BUCKMODEPADCONF_BUCKMODE2PADTYPE_CMOS) |     \
			 (DT_INST_PROP(inst, nordic_buck_mode0_pull_down) *    \
			  NPM6001_BUCKMODEPADCONF_BUCKMODE0PULLD_ENABLED) |    \
			 (DT_INST_PROP(inst, nordic_buck_mode1_pull_down) *    \
			  NPM6001_BUCKMODEPADCONF_BUCKMODE1PULLD_ENABLED) |    \
			 (DT_INST_PROP(inst, nordic_buck_mode2_pull_down) *    \
			  NPM6001_BUCKMODEPADCONF_BUCKMODE2PULLD_ENABLED)),    \
		.pad_val = ((DT_INST_PROP(inst, nordic_ready_high_drive) *     \
			     NPM6001_PADDRIVESTRENGTH_READY_HIGH) |            \
			    (DT_INST_PROP(inst, nordic_nint_high_drive) *      \
			     NPM6001_PADDRIVESTRENGTH_NINT_HIGH) |             \
			    (DT_INST_PROP(inst, nordic_sda_high_drive) *       \
			     NPM6001_PADDRIVESTRENGTH_SDA_HIGH)),              \
	};                                                                     \
                                                                               \
	DEVICE_DT_INST_DEFINE(inst, regulator_npm6001_common_init, NULL, NULL, \
			      &config_##inst, POST_KERNEL,                     \
			      CONFIG_REGULATOR_NPM6001_COMMON_INIT_PRIORITY,   \
			      NULL);                                           \
                                                                               \
	REGULATOR_NPM6001_DEFINE_COND(inst, buck0, NPM6001_SOURCE_BUCK0,       \
				      DEVICE_DT_INST_GET(inst))                \
	REGULATOR_NPM6001_DEFINE_COND(inst, buck1, NPM6001_SOURCE_BUCK1,       \
				      DEVICE_DT_INST_GET(inst))                \
	REGULATOR_NPM6001_DEFINE_COND(inst, buck2, NPM6001_SOURCE_BUCK2,       \
				      DEVICE_DT_INST_GET(inst))                \
	REGULATOR_NPM6001_DEFINE_COND(inst, buck3, NPM6001_SOURCE_BUCK3,       \
				      DEVICE_DT_INST_GET(inst))                \
	REGULATOR_NPM6001_DEFINE_COND(inst, ldo0, NPM6001_SOURCE_LDO0,         \
				      DEVICE_DT_INST_GET(inst))                \
	REGULATOR_NPM6001_DEFINE_COND(inst, ldo1, NPM6001_SOURCE_LDO1,         \
				      DEVICE_DT_INST_GET(inst))

DT_INST_FOREACH_STATUS_OKAY(REGULATOR_NPM6001_DEFINE_ALL)
