// SPDX-License-Identifier: GPL-2.0-only
/*
 * These are the two Sharp GP2AP002 variants supported by this driver:
 * GP2AP002A00F Ambient Light and Proximity Sensor
 * GP2AP002S00F Proximity Sensor
 *
 * Copyright (C) 2020 Linaro Ltd.
 * Author: Linus Walleij <linus.walleij@linaro.org>
 *
 * Based partly on the code in Sony Ericssons GP2AP00200F driver by
 * Courtney Cavin and Oskar Andero in drivers/input/misc/gp2ap002a00f.c
 * Based partly on a Samsung misc driver submitted by
 * Donggeun Kim & Minkyu Kang in 2011:
 * https://lore.kernel.org/lkml/1315556546-7445-1-git-send-email-dg77.kim@samsung.com/
 * Based partly on a submission by
 * Jonathan Bakker and Paweł Chmiel in january 2019:
 * https://lore.kernel.org/linux-input/20190125175045.22576-1-pawel.mikolaj.chmiel@gmail.com/
 * Based partly on code from the Samsung GT-S7710 by <mjchen@sta.samsung.com>
 * Based partly on the code in LG Electronics GP2AP00200F driver by
 * Kenobi Lee <sungyoung.lee@lge.com> and EunYoung Cho <ey.cho@lge.com>
 */
#include <linux/module.h>
#include <linux/i2c.h>
#include <linux/regmap.h>
#include <linux/iio/iio.h>
#include <linux/iio/sysfs.h>
#include <linux/iio/events.h>
#include <linux/iio/consumer.h> /* To get our ADC channel */
#include <linux/iio/types.h> /* To deal with our ADC channel */
#include <linux/init.h>
#include <linux/delay.h>
#include <linux/regulator/consumer.h>
#include <linux/pm_runtime.h>
#include <linux/interrupt.h>
#include <linux/bits.h>
#include <linux/math64.h>
#include <linux/pm.h>

#define GP2AP002_PROX_CHANNEL 0
#define GP2AP002_ALS_CHANNEL 1

/* ------------------------------------------------------------------------ */
/* ADDRESS SYMBOL             DATA                                 Init R/W */
/*                   D7    D6    D5    D4    D3    D2    D1    D0           */
/* ------------------------------------------------------------------------ */
/*    0      PROX     X     X     X     X     X     X     X    VO  H'00   R */
/*    1      GAIN     X     X     X     X  LED0     X     X     X  H'00   W */
/*    2       HYS  HYSD HYSC1 HYSC0     X HYSF3 HYSF2 HYSF1 HYSF0  H'00   W */
/*    3     CYCLE     X     X CYCL2 CYCL1 CYCL0  OSC2     X     X  H'00   W */
/*    4     OPMOD     X     X     X   ASD     X     X  VCON   SSD  H'00   W */
/*    6       CON     X     X     X OCON1 OCON0     X     X     X  H'00   W */
/* ------------------------------------------------------------------------ */
/* VO   :Proximity sensing result(0: no detection, 1: detection)            */
/* LED0 :Select switch for LED driver's On-registence(0:2x higher, 1:normal)*/
/* HYSD/HYSF :Adjusts the receiver sensitivity                              */
/* OSC  :Select switch internal clocl frequency hoppling(0:effective)       */
/* CYCL :Determine the detection cycle(typically 8ms, up to 128x)           */
/* SSD  :Software Shutdown function(0:shutdown, 1:operating)                */
/* VCON :VOUT output method control(0:normal, 1:interrupt)                  */
/* ASD  :Select switch for analog sleep function(0:ineffective, 1:effective)*/
/* OCON :Select switch for enabling/disabling VOUT (00:enable, 11:disable)  */

#define GP2AP002_PROX				0x00
#define GP2AP002_GAIN				0x01
#define GP2AP002_HYS				0x02
#define GP2AP002_CYCLE				0x03
#define GP2AP002_OPMOD				0x04
#define GP2AP002_CON				0x06

#define GP2AP002_PROX_VO_DETECT			BIT(0)

/* Setting this bit to 0 means 2x higher LED resistance */
#define GP2AP002_GAIN_LED_NORMAL		BIT(3)

/*
 * These bits adjusts the proximity sensitivity, determining characteristics
 * of the detection distance and its hysteresis.
 */
#define GP2AP002_HYS_HYSD_SHIFT		7
#define GP2AP002_HYS_HYSD_MASK		BIT(7)
#define GP2AP002_HYS_HYSC_SHIFT		5
#define GP2AP002_HYS_HYSC_MASK		GENMASK(6, 5)
#define GP2AP002_HYS_HYSF_SHIFT		0
#define GP2AP002_HYS_HYSF_MASK		GENMASK(3, 0)
#define GP2AP002_HYS_MASK		(GP2AP002_HYS_HYSD_MASK | \
					 GP2AP002_HYS_HYSC_MASK | \
					 GP2AP002_HYS_HYSF_MASK)

/*
 * These values determine the detection cycle response time
 * 0: 8ms, 1: 16ms, 2: 32ms, 3: 64ms, 4: 128ms,
 * 5: 256ms, 6: 512ms, 7: 1024ms
 */
#define GP2AP002_CYCLE_CYCL_SHIFT	3
#define GP2AP002_CYCLE_CYCL_MASK	GENMASK(5, 3)

/*
 * Select switch for internal clock frequency hopping
 *	0: effective,
 *	1: ineffective
 */
#define GP2AP002_CYCLE_OSC_EFFECTIVE	0
#define GP2AP002_CYCLE_OSC_INEFFECTIVE	BIT(2)
#define GP2AP002_CYCLE_OSC_MASK		BIT(2)

/* Analog sleep effective */
#define GP2AP002_OPMOD_ASD		BIT(4)
/* Enable chip */
#define GP2AP002_OPMOD_SSD_OPERATING	BIT(0)
/* IRQ mode */
#define GP2AP002_OPMOD_VCON_IRQ		BIT(1)
#define GP2AP002_OPMOD_MASK		(BIT(0) | BIT(1) | BIT(4))

/*
 * Select switch for enabling/disabling Vout pin
 * 0: enable
 * 2: force to go Low
 * 3: force to go High
 */
#define GP2AP002_CON_OCON_SHIFT		3
#define GP2AP002_CON_OCON_ENABLE	(0x0 << GP2AP002_CON_OCON_SHIFT)
#define GP2AP002_CON_OCON_LOW		(0x2 << GP2AP002_CON_OCON_SHIFT)
#define GP2AP002_CON_OCON_HIGH		(0x3 << GP2AP002_CON_OCON_SHIFT)
#define GP2AP002_CON_OCON_MASK		(0x3 << GP2AP002_CON_OCON_SHIFT)

/**
 * struct gp2ap002 - GP2AP002 state
 * @map: regmap pointer for the i2c regmap
 * @dev: pointer to parent device
 * @vdd: regulator controlling VDD
 * @vio: regulator controlling VIO
 * @alsout: IIO ADC channel to convert the ALSOUT signal
 * @hys_far: hysteresis control from device tree
 * @hys_close: hysteresis control from device tree
 * @is_gp2ap002s00f: this is the GP2AP002F variant of the chip
 * @irq: the IRQ line used by this device
 * @enabled: we cannot read the status of the hardware so we need to
 * keep track of whether the event is enabled using this state variable
 */
struct gp2ap002 {
	struct regmap *map;
	struct device *dev;
	struct regulator *vdd;
	struct regulator *vio;
	struct iio_channel *alsout;
	u8 hys_far;
	u8 hys_close;
	bool is_gp2ap002s00f;
	int irq;
	bool enabled;
};

static irqreturn_t gp2ap002_prox_irq(int irq, void *d)
{
	struct iio_dev *indio_dev = d;
	struct gp2ap002 *gp2ap002 = iio_priv(indio_dev);
	u64 ev;
	int val;
	int ret;

	if (!gp2ap002->enabled)
		goto err_retrig;

	ret = regmap_read(gp2ap002->map, GP2AP002_PROX, &val);
	if (ret) {
		dev_err(gp2ap002->dev, "error reading proximity\n");
		goto err_retrig;
	}

	if (val & GP2AP002_PROX_VO_DETECT) {
		/* Close */
		dev_dbg(gp2ap002->dev, "close\n");
		ret = regmap_write(gp2ap002->map, GP2AP002_HYS,
				   gp2ap002->hys_far);
		if (ret)
			dev_err(gp2ap002->dev,
				"error setting up proximity hysteresis\n");
		ev = IIO_UNMOD_EVENT_CODE(IIO_PROXIMITY, GP2AP002_PROX_CHANNEL,
					IIO_EV_TYPE_THRESH, IIO_EV_DIR_RISING);
	} else {
		/* Far */
		dev_dbg(gp2ap002->dev, "far\n");
		ret = regmap_write(gp2ap002->map, GP2AP002_HYS,
				   gp2ap002->hys_close);
		if (ret)
			dev_err(gp2ap002->dev,
				"error setting up proximity hysteresis\n");
		ev = IIO_UNMOD_EVENT_CODE(IIO_PROXIMITY, GP2AP002_PROX_CHANNEL,
					IIO_EV_TYPE_THRESH, IIO_EV_DIR_FALLING);
	}
	iio_push_event(indio_dev, ev, iio_get_time_ns(indio_dev));

	/*
	 * After changing hysteresis, we need to wait for one detection
	 * cycle to see if anything changed, or we will just trigger the
	 * previous interrupt again. A detection cycle depends on the CYCLE
	 * register, we are hard-coding ~8 ms in probe() so wait some more
	 * than this, 20-30 ms.
	 */
	usleep_range(20000, 30000);

err_retrig:
	ret = regmap_write(gp2ap002->map, GP2AP002_CON,
			   GP2AP002_CON_OCON_ENABLE);
	if (ret)
		dev_err(gp2ap002->dev, "error setting up VOUT control\n");

	return IRQ_HANDLED;
}

/*
 * This array maps current and lux.
 *
 * Ambient light sensing range is 3 to 55000 lux.
 *
 * This mapping is based on the following formula.
 * illuminance = 10 ^ (current[mA] / 10)
 *
 * When the ADC measures 0, return 0 lux.
 */
static const u16 gp2ap002_illuminance_table[] = {
	0, 1, 1, 2, 2, 3, 4, 5, 6, 8, 10, 12, 16, 20, 25, 32, 40, 50, 63, 79,
	100, 126, 158, 200, 251, 316, 398, 501, 631, 794, 1000, 1259, 1585,
	1995, 2512, 3162, 3981, 5012, 6310, 7943, 10000, 12589, 15849, 19953,
	25119, 31623, 39811, 50119,
};

static int gp2ap002_get_lux(struct gp2ap002 *gp2ap002)
{
	int ret, res;
	u16 lux;

	ret = iio_read_channel_processed(gp2ap002->alsout, &res);
	if (ret < 0)
		return ret;

	dev_dbg(gp2ap002->dev, "read %d mA from ADC\n", res);

	/* ensure we don't under/overflow */
	res = clamp(res, 0, (int)ARRAY_SIZE(gp2ap002_illuminance_table) - 1);
	lux = gp2ap002_illuminance_table[res];

	return (int)lux;
}

static int gp2ap002_read_raw(struct iio_dev *indio_dev,
			   struct iio_chan_spec const *chan,
			   int *val, int *val2, long mask)
{
	struct gp2ap002 *gp2ap002 = iio_priv(indio_dev);
	int ret;

	pm_runtime_get_sync(gp2ap002->dev);

	switch (mask) {
	case IIO_CHAN_INFO_RAW:
		switch (chan->type) {
		case IIO_LIGHT:
			ret = gp2ap002_get_lux(gp2ap002);
			if (ret < 0)
				return ret;
			*val = ret;
			ret = IIO_VAL_INT;
			goto out;
		default:
			ret = -EINVAL;
			goto out;
		}
	default:
		ret = -EINVAL;
	}

out:
	pm_runtime_mark_last_busy(gp2ap002->dev);
	pm_runtime_put_autosuspend(gp2ap002->dev);

	return ret;
}

static int gp2ap002_init(struct gp2ap002 *gp2ap002)
{
	int ret;

	/* Set up the IR LED resistance */
	ret = regmap_write(gp2ap002->map, GP2AP002_GAIN,
			   GP2AP002_GAIN_LED_NORMAL);
	if (ret) {
		dev_err(gp2ap002->dev, "error setting up LED gain\n");
		return ret;
	}
	ret = regmap_write(gp2ap002->map, GP2AP002_HYS, gp2ap002->hys_far);
	if (ret) {
		dev_err(gp2ap002->dev,
			"error setting up proximity hysteresis\n");
		return ret;
	}

	/* Disable internal frequency hopping */
	ret = regmap_write(gp2ap002->map, GP2AP002_CYCLE,
			   GP2AP002_CYCLE_OSC_INEFFECTIVE);
	if (ret) {
		dev_err(gp2ap002->dev,
			"error setting up internal frequency hopping\n");
		return ret;
	}

	/* Enable chip and IRQ, disable analog sleep */
	ret = regmap_write(gp2ap002->map, GP2AP002_OPMOD,
			   GP2AP002_OPMOD_SSD_OPERATING |
			   GP2AP002_OPMOD_VCON_IRQ);
	if (ret) {
		dev_err(gp2ap002->dev, "error setting up operation mode\n");
		return ret;
	}

	/* Interrupt on VOUT enabled */
	ret = regmap_write(gp2ap002->map, GP2AP002_CON,
			   GP2AP002_CON_OCON_ENABLE);
	if (ret)
		dev_err(gp2ap002->dev, "error setting up VOUT control\n");

	return ret;
}

static int gp2ap002_read_event_config(struct iio_dev *indio_dev,
				      const struct iio_chan_spec *chan,
				      enum iio_event_type type,
				      enum iio_event_direction dir)
{
	struct gp2ap002 *gp2ap002 = iio_priv(indio_dev);

	/*
	 * We just keep track of this internally, as it is not possible to
	 * query the hardware.
	 */
	return gp2ap002->enabled;
}

static int gp2ap002_write_event_config(struct iio_dev *indio_dev,
				       const struct iio_chan_spec *chan,
				       enum iio_event_type type,
				       enum iio_event_direction dir,
				       int state)
{
	struct gp2ap002 *gp2ap002 = iio_priv(indio_dev);

	if (state) {
		/*
		 * This will bring the regulators up (unless they are on
		 * already) and reintialize the sensor by using runtime_pm
		 * callbacks.
		 */
		pm_runtime_get_sync(gp2ap002->dev);
		gp2ap002->enabled = true;
	} else {
		pm_runtime_mark_last_busy(gp2ap002->dev);
		pm_runtime_put_autosuspend(gp2ap002->dev);
		gp2ap002->enabled = false;
	}

	return 0;
}

static const struct iio_info gp2ap002_info = {
	.read_raw = gp2ap002_read_raw,
	.read_event_config = gp2ap002_read_event_config,
	.write_event_config = gp2ap002_write_event_config,
};

static const struct iio_event_spec gp2ap002_events[] = {
	{
		.type = IIO_EV_TYPE_THRESH,
		.dir = IIO_EV_DIR_EITHER,
		.mask_separate = BIT(IIO_EV_INFO_ENABLE),
	},
};

static const struct iio_chan_spec gp2ap002_channels[] = {
	{
		.type = IIO_PROXIMITY,
		.event_spec = gp2ap002_events,
		.num_event_specs = ARRAY_SIZE(gp2ap002_events),
	},
	{
		.type = IIO_LIGHT,
		.info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
		.channel = GP2AP002_ALS_CHANNEL,
	},
};

/*
 * We need a special regmap because this hardware expects to
 * write single bytes to registers but read a 16bit word on some
 * variants and discard the lower 8 bits so combine
 * i2c_smbus_read_word_data() with i2c_smbus_write_byte_data()
 * selectively like this.
 */
static int gp2ap002_regmap_i2c_read(void *context, unsigned int reg,
				    unsigned int *val)
{
	struct device *dev = context;
	struct i2c_client *i2c = to_i2c_client(dev);
	int ret;

	ret = i2c_smbus_read_word_data(i2c, reg);
	if (ret < 0)
		return ret;

	*val = (ret >> 8) & 0xFF;

	return 0;
}

static int gp2ap002_regmap_i2c_write(void *context, unsigned int reg,
				     unsigned int val)
{
	struct device *dev = context;
	struct i2c_client *i2c = to_i2c_client(dev);

	return i2c_smbus_write_byte_data(i2c, reg, val);
}

static struct regmap_bus gp2ap002_regmap_bus = {
	.reg_read = gp2ap002_regmap_i2c_read,
	.reg_write = gp2ap002_regmap_i2c_write,
};

static int gp2ap002_probe(struct i2c_client *client,
			  const struct i2c_device_id *id)
{
	struct gp2ap002 *gp2ap002;
	struct iio_dev *indio_dev;
	struct device *dev = &client->dev;
	enum iio_chan_type ch_type;
	static const struct regmap_config config = {
		.reg_bits = 8,
		.val_bits = 8,
		.max_register = GP2AP002_CON,
	};
	struct regmap *regmap;
	int num_chan;
	const char *compat;
	u8 val;
	int ret;

	indio_dev = devm_iio_device_alloc(dev, sizeof(*gp2ap002));
	if (!indio_dev)
		return -ENOMEM;
	i2c_set_clientdata(client, indio_dev);

	gp2ap002 = iio_priv(indio_dev);
	gp2ap002->dev = dev;

	/*
	 * Check the device compatible like this makes it possible to use
	 * ACPI PRP0001 for registering the sensor using device tree
	 * properties.
	 */
	ret = device_property_read_string(dev, "compatible", &compat);
	if (ret) {
		dev_err(dev, "cannot check compatible\n");
		return ret;
	}
	gp2ap002->is_gp2ap002s00f = !strcmp(compat, "sharp,gp2ap002s00f");

	regmap = devm_regmap_init(dev, &gp2ap002_regmap_bus, dev, &config);
	if (IS_ERR(regmap)) {
		dev_err(dev, "Failed to register i2c regmap %ld\n", PTR_ERR(regmap));
		return PTR_ERR(regmap);
	}
	gp2ap002->map = regmap;

	/*
	 * The hysteresis settings are coded into the device tree as values
	 * to be written into the hysteresis register. The datasheet defines
	 * modes "A", "B1" and "B2" with fixed values to be use but vendor
	 * code trees for actual devices are tweaking these values and refer to
	 * modes named things like "B1.5". To be able to support any devices,
	 * we allow passing an arbitrary hysteresis setting for "near" and
	 * "far".
	 */

	/* Check the device tree for the IR LED hysteresis */
	ret = device_property_read_u8(dev, "sharp,proximity-far-hysteresis",
				      &val);
	if (ret) {
		dev_err(dev, "failed to obtain proximity far setting\n");
		return ret;
	}
	dev_dbg(dev, "proximity far setting %02x\n", val);
	gp2ap002->hys_far = val;

	ret = device_property_read_u8(dev, "sharp,proximity-close-hysteresis",
				      &val);
	if (ret) {
		dev_err(dev, "failed to obtain proximity close setting\n");
		return ret;
	}
	dev_dbg(dev, "proximity close setting %02x\n", val);
	gp2ap002->hys_close = val;

	/* The GP2AP002A00F has a light sensor too */
	if (!gp2ap002->is_gp2ap002s00f) {
		gp2ap002->alsout = devm_iio_channel_get(dev, "alsout");
		if (IS_ERR(gp2ap002->alsout)) {
			ret = PTR_ERR(gp2ap002->alsout);
			ret = (ret == -ENODEV) ? -EPROBE_DEFER : ret;
			return dev_err_probe(dev, ret, "failed to get ALSOUT ADC channel\n");
		}
		ret = iio_get_channel_type(gp2ap002->alsout, &ch_type);
		if (ret < 0)
			return ret;
		if (ch_type != IIO_CURRENT) {
			dev_err(dev,
				"wrong type of IIO channel specified for ALSOUT\n");
			return -EINVAL;
		}
	}

	gp2ap002->vdd = devm_regulator_get(dev, "vdd");
	if (IS_ERR(gp2ap002->vdd))
		return dev_err_probe(dev, PTR_ERR(gp2ap002->vdd),
				     "failed to get VDD regulator\n");

	gp2ap002->vio = devm_regulator_get(dev, "vio");
	if (IS_ERR(gp2ap002->vio))
		return dev_err_probe(dev, PTR_ERR(gp2ap002->vio),
				     "failed to get VIO regulator\n");

	/* Operating voltage 2.4V .. 3.6V according to datasheet */
	ret = regulator_set_voltage(gp2ap002->vdd, 2400000, 3600000);
	if (ret) {
		dev_err(dev, "failed to sett VDD voltage\n");
		return ret;
	}

	/* VIO should be between 1.65V and VDD */
	ret = regulator_get_voltage(gp2ap002->vdd);
	if (ret < 0) {
		dev_err(dev, "failed to get VDD voltage\n");
		return ret;
	}
	ret = regulator_set_voltage(gp2ap002->vio, 1650000, ret);
	if (ret) {
		dev_err(dev, "failed to set VIO voltage\n");
		return ret;
	}

	ret = regulator_enable(gp2ap002->vdd);
	if (ret) {
		dev_err(dev, "failed to enable VDD regulator\n");
		return ret;
	}
	ret = regulator_enable(gp2ap002->vio);
	if (ret) {
		dev_err(dev, "failed to enable VIO regulator\n");
		goto out_disable_vdd;
	}

	msleep(20);

	/*
	 * Initialize the device and signal to runtime PM that now we are
	 * definitely up and using power.
	 */
	ret = gp2ap002_init(gp2ap002);
	if (ret) {
		dev_err(dev, "initialization failed\n");
		goto out_disable_vio;
	}
	pm_runtime_get_noresume(dev);
	pm_runtime_set_active(dev);
	pm_runtime_enable(dev);
	gp2ap002->enabled = false;

	ret = devm_request_threaded_irq(dev, client->irq, NULL,
					gp2ap002_prox_irq, IRQF_ONESHOT,
					"gp2ap002", indio_dev);
	if (ret) {
		dev_err(dev, "unable to request IRQ\n");
		goto out_put_pm;
	}
	gp2ap002->irq = client->irq;

	/*
	 * As the device takes 20 ms + regulator delay to come up with a fresh
	 * measurement after power-on, do not shut it down unnecessarily.
	 * Set autosuspend to a one second.
	 */
	pm_runtime_set_autosuspend_delay(dev, 1000);
	pm_runtime_use_autosuspend(dev);
	pm_runtime_put(dev);

	indio_dev->info = &gp2ap002_info;
	indio_dev->name = "gp2ap002";
	indio_dev->channels = gp2ap002_channels;
	/* Skip light channel for the proximity-only sensor */
	num_chan = ARRAY_SIZE(gp2ap002_channels);
	if (gp2ap002->is_gp2ap002s00f)
		num_chan--;
	indio_dev->num_channels = num_chan;
	indio_dev->modes = INDIO_DIRECT_MODE;

	ret = iio_device_register(indio_dev);
	if (ret)
		goto out_disable_pm;
	dev_dbg(dev, "Sharp GP2AP002 probed successfully\n");

	return 0;

out_put_pm:
	pm_runtime_put_noidle(dev);
out_disable_pm:
	pm_runtime_disable(dev);
out_disable_vio:
	regulator_disable(gp2ap002->vio);
out_disable_vdd:
	regulator_disable(gp2ap002->vdd);
	return ret;
}

static int gp2ap002_remove(struct i2c_client *client)
{
	struct iio_dev *indio_dev = i2c_get_clientdata(client);
	struct gp2ap002 *gp2ap002 = iio_priv(indio_dev);
	struct device *dev = &client->dev;

	pm_runtime_get_sync(dev);
	pm_runtime_put_noidle(dev);
	pm_runtime_disable(dev);
	iio_device_unregister(indio_dev);
	regulator_disable(gp2ap002->vio);
	regulator_disable(gp2ap002->vdd);

	return 0;
}

static int __maybe_unused gp2ap002_runtime_suspend(struct device *dev)
{
	struct iio_dev *indio_dev = dev_get_drvdata(dev);
	struct gp2ap002 *gp2ap002 = iio_priv(indio_dev);
	int ret;

	/* Deactivate the IRQ */
	disable_irq(gp2ap002->irq);

	/* Disable chip and IRQ, everything off */
	ret = regmap_write(gp2ap002->map, GP2AP002_OPMOD, 0x00);
	if (ret) {
		dev_err(gp2ap002->dev, "error setting up operation mode\n");
		return ret;
	}
	/*
	 * As these regulators may be shared, at least we are now in
	 * sleep even if the regulators aren't really turned off.
	 */
	regulator_disable(gp2ap002->vio);
	regulator_disable(gp2ap002->vdd);

	return 0;
}

static int __maybe_unused gp2ap002_runtime_resume(struct device *dev)
{
	struct iio_dev *indio_dev = dev_get_drvdata(dev);
	struct gp2ap002 *gp2ap002 = iio_priv(indio_dev);
	int ret;

	ret = regulator_enable(gp2ap002->vdd);
	if (ret) {
		dev_err(dev, "failed to enable VDD regulator in resume path\n");
		return ret;
	}
	ret = regulator_enable(gp2ap002->vio);
	if (ret) {
		dev_err(dev, "failed to enable VIO regulator in resume path\n");
		return ret;
	}

	msleep(20);

	ret = gp2ap002_init(gp2ap002);
	if (ret) {
		dev_err(dev, "re-initialization failed\n");
		return ret;
	}

	/* Re-activate the IRQ */
	enable_irq(gp2ap002->irq);

	return 0;
}

static const struct dev_pm_ops gp2ap002_dev_pm_ops = {
	SET_SYSTEM_SLEEP_PM_OPS(pm_runtime_force_suspend,
				pm_runtime_force_resume)
	SET_RUNTIME_PM_OPS(gp2ap002_runtime_suspend,
			   gp2ap002_runtime_resume, NULL)
};

static const struct i2c_device_id gp2ap002_id_table[] = {
	{ "gp2ap002", 0 },
	{ },
};
MODULE_DEVICE_TABLE(i2c, gp2ap002_id_table);

static const struct of_device_id gp2ap002_of_match[] = {
	{ .compatible = "sharp,gp2ap002a00f" },
	{ .compatible = "sharp,gp2ap002s00f" },
	{ },
};
MODULE_DEVICE_TABLE(of, gp2ap002_of_match);

static struct i2c_driver gp2ap002_driver = {
	.driver = {
		.name = "gp2ap002",
		.of_match_table = gp2ap002_of_match,
		.pm = &gp2ap002_dev_pm_ops,
	},
	.probe = gp2ap002_probe,
	.remove = gp2ap002_remove,
	.id_table = gp2ap002_id_table,
};
module_i2c_driver(gp2ap002_driver);

MODULE_AUTHOR("Linus Walleij <linus.walleij@linaro.org>");
MODULE_DESCRIPTION("GP2AP002 ambient light and proximity sensor driver");
MODULE_LICENSE("GPL v2");
