/* lsm6ds0.c - Driver for LSM6DS0 accelerometer, gyroscope and
 * temperature sensor
 */

/*
 * Copyright (c) 2016 Intel Corporation
 *
 * SPDX-License-Identifier: Apache-2.0
 */

#include <sensor.h>
#include <kernel.h>
#include <device.h>
#include <init.h>
#include <misc/byteorder.h>
#include <misc/__assert.h>
#include <logging/log.h>

#include "lsm6ds0.h"

#define LOG_LEVEL CONFIG_SENSOR_LOG_LEVEL
LOG_MODULE_REGISTER(LSM6DS0);

static inline int lsm6ds0_reboot(struct device *dev)
{
	struct lsm6ds0_data *data = dev->driver_data;
	const struct lsm6ds0_config *config = dev->config->config_info;

	if (i2c_reg_update_byte(data->i2c_master, config->i2c_slave_addr,
				LSM6DS0_REG_CTRL_REG8,
				LSM6DS0_MASK_CTRL_REG8_BOOT,
				1 << LSM6DS0_SHIFT_CTRL_REG8_BOOT) < 0) {
		return -EIO;
	}

	k_busy_wait(50 * USEC_PER_MSEC);

	return 0;
}

static inline int lsm6ds0_accel_axis_ctrl(struct device *dev, int x_en,
					  int y_en, int z_en)
{
	struct lsm6ds0_data *data = dev->driver_data;
	const struct lsm6ds0_config *config = dev->config->config_info;
	u8_t state = (x_en << LSM6DS0_SHIFT_CTRL_REG5_XL_XEN_XL) |
			(y_en << LSM6DS0_SHIFT_CTRL_REG5_XL_YEN_XL) |
			(z_en << LSM6DS0_SHIFT_CTRL_REG5_XL_ZEN_XL);

	return i2c_reg_update_byte(data->i2c_master, config->i2c_slave_addr,
				   LSM6DS0_REG_CTRL_REG5_XL,
				   LSM6DS0_MASK_CTRL_REG5_XL_XEN_XL |
				   LSM6DS0_MASK_CTRL_REG5_XL_YEN_XL |
				   LSM6DS0_MASK_CTRL_REG5_XL_ZEN_XL,
				   state);
}

static int lsm6ds0_accel_set_fs_raw(struct device *dev, u8_t fs)
{
	struct lsm6ds0_data *data = dev->driver_data;
	const struct lsm6ds0_config *config = dev->config->config_info;

	if (i2c_reg_update_byte(data->i2c_master, config->i2c_slave_addr,
				LSM6DS0_REG_CTRL_REG6_XL,
				LSM6DS0_MASK_CTRL_REG6_XL_FS_XL,
				fs << LSM6DS0_SHIFT_CTRL_REG6_XL_FS_XL) < 0) {
		return -EIO;
	}

	return 0;
}

static int lsm6ds0_accel_set_odr_raw(struct device *dev, u8_t odr)
{
	struct lsm6ds0_data *data = dev->driver_data;
	const struct lsm6ds0_config *config = dev->config->config_info;

	if (i2c_reg_update_byte(data->i2c_master, config->i2c_slave_addr,
				LSM6DS0_REG_CTRL_REG6_XL,
				LSM6DS0_MASK_CTRL_REG6_XL_ODR_XL,
				odr << LSM6DS0_SHIFT_CTRL_REG6_XL_ODR_XL) < 0) {
		return -EIO;
	}

	return 0;
}

static inline int lsm6ds0_gyro_axis_ctrl(struct device *dev, int x_en, int y_en,
					 int z_en)
{
	struct lsm6ds0_data *data = dev->driver_data;
	const struct lsm6ds0_config *config = dev->config->config_info;
	u8_t state = (x_en << LSM6DS0_SHIFT_CTRL_REG4_XEN_G) |
			(y_en << LSM6DS0_SHIFT_CTRL_REG4_YEN_G) |
			(z_en << LSM6DS0_SHIFT_CTRL_REG4_ZEN_G);

	return i2c_reg_update_byte(data->i2c_master, config->i2c_slave_addr,
				   LSM6DS0_REG_CTRL_REG4,
				   LSM6DS0_MASK_CTRL_REG4_XEN_G |
				   LSM6DS0_MASK_CTRL_REG4_YEN_G |
				   LSM6DS0_MASK_CTRL_REG4_ZEN_G,
				   state);
}

static int lsm6ds0_gyro_set_fs_raw(struct device *dev, u8_t fs)
{
	struct lsm6ds0_data *data = dev->driver_data;
	const struct lsm6ds0_config *config = dev->config->config_info;

	if (i2c_reg_update_byte(data->i2c_master, config->i2c_slave_addr,
				LSM6DS0_REG_CTRL_REG1_G,
				LSM6DS0_MASK_CTRL_REG1_G_FS_G,
				fs << LSM6DS0_SHIFT_CTRL_REG1_G_FS_G) < 0) {
		return -EIO;
	}

	return 0;
}

static int lsm6ds0_gyro_set_odr_raw(struct device *dev, u8_t odr)
{
	struct lsm6ds0_data *data = dev->driver_data;
	const struct lsm6ds0_config *config = dev->config->config_info;

	if (i2c_reg_update_byte(data->i2c_master, config->i2c_slave_addr,
				LSM6DS0_REG_CTRL_REG1_G,
				LSM6DS0_MASK_CTRL_REG1_G_ODR_G,
				odr << LSM6DS0_SHIFT_CTRL_REG1_G_ODR_G) < 0) {
		return -EIO;
	}

	return 0;
}

static int lsm6ds0_sample_fetch_accel(struct device *dev)
{
	struct lsm6ds0_data *data = dev->driver_data;
	const struct lsm6ds0_config *config = dev->config->config_info;
	u8_t buf[6];

	if (i2c_burst_read(data->i2c_master, config->i2c_slave_addr,
			   LSM6DS0_REG_OUT_X_L_XL, buf, sizeof(buf)) < 0) {
		LOG_DBG("failed to read sample");
		return -EIO;
	}

#if defined(CONFIG_LSM6DS0_ACCEL_ENABLE_X_AXIS)
	data->accel_sample_x = (s16_t)((u16_t)(buf[0]) |
				((u16_t)(buf[1]) << 8));
#endif
#if defined(CONFIG_LSM6DS0_ACCEL_ENABLE_Y_AXIS)
	data->accel_sample_y = (s16_t)((u16_t)(buf[2]) |
				((u16_t)(buf[3]) << 8));
#endif
#if defined(CONFIG_LSM6DS0_ACCEL_ENABLE_Z_AXIS)
	data->accel_sample_z = (s16_t)((u16_t)(buf[4]) |
				((u16_t)(buf[5]) << 8));
#endif

	return 0;
}

static int lsm6ds0_sample_fetch_gyro(struct device *dev)
{
	struct lsm6ds0_data *data = dev->driver_data;
	const struct lsm6ds0_config *config = dev->config->config_info;
	u8_t buf[6];

	if (i2c_burst_read(data->i2c_master, config->i2c_slave_addr,
			   LSM6DS0_REG_OUT_X_L_G, buf, sizeof(buf)) < 0) {
		LOG_DBG("failed to read sample");
		return -EIO;
	}

#if defined(CONFIG_LSM6DS0_GYRO_ENABLE_X_AXIS)
	data->gyro_sample_x = (s16_t)((u16_t)(buf[0]) |
				((u16_t)(buf[1]) << 8));
#endif
#if defined(CONFIG_LSM6DS0_GYRO_ENABLE_Y_AXIS)
	data->gyro_sample_y = (s16_t)((u16_t)(buf[2]) |
				((u16_t)(buf[3]) << 8));
#endif
#if defined(CONFIG_LSM6DS0_GYRO_ENABLE_Z_AXIS)
	data->gyro_sample_z = (s16_t)((u16_t)(buf[4]) |
				((u16_t)(buf[5]) << 8));
#endif

	return 0;
}

#if defined(CONFIG_LSM6DS0_ENABLE_TEMP)
static int lsm6ds0_sample_fetch_temp(struct device *dev)
{
	struct lsm6ds0_data *data = dev->driver_data;
	const struct lsm6ds0_config *config = dev->config->config_info;
	u8_t buf[2];

	if (i2c_burst_read(data->i2c_master, config->i2c_slave_addr,
			   LSM6DS0_REG_OUT_TEMP_L, buf, sizeof(buf)) < 0) {
		LOG_DBG("failed to read sample");
		return -EIO;
	}

	data->temp_sample = (s16_t)((u16_t)(buf[0]) |
				((u16_t)(buf[1]) << 8));

	return 0;
}
#endif

static int lsm6ds0_sample_fetch(struct device *dev, enum sensor_channel chan)
{
	__ASSERT_NO_MSG(chan == SENSOR_CHAN_ALL ||
			chan == SENSOR_CHAN_ACCEL_XYZ ||
#if defined(CONFIG_LSM6DS0_ENABLE_TEMP)
			chan == SENSOR_CHAN_DIE_TEMP ||
#endif
			chan == SENSOR_CHAN_GYRO_XYZ);

	switch (chan) {
	case SENSOR_CHAN_ACCEL_XYZ:
		lsm6ds0_sample_fetch_accel(dev);
		break;
	case SENSOR_CHAN_GYRO_XYZ:
		lsm6ds0_sample_fetch_gyro(dev);
		break;
#if defined(CONFIG_LSM6DS0_ENABLE_TEMP)
	case SENSOR_CHAN_DIE_TEMP:
		lsm6ds0_sample_fetch_temp(dev);
		break;
#endif
	case SENSOR_CHAN_ALL:
		lsm6ds0_sample_fetch_accel(dev);
		lsm6ds0_sample_fetch_gyro(dev);
#if defined(CONFIG_LSM6DS0_ENABLE_TEMP)
		lsm6ds0_sample_fetch_temp(dev);
#endif
		break;
	default:
		return -ENOTSUP;
	}

	return 0;
}

static inline void lsm6ds0_accel_convert(struct sensor_value *val, int raw_val,
					 float scale)
{
	double dval;

	dval = (double)(raw_val) * scale / 32767.0;
	val->val1 = (s32_t)dval;
	val->val2 = ((s32_t)(dval * 1000000)) % 1000000;
}

static inline int lsm6ds0_accel_get_channel(enum sensor_channel chan,
					    struct sensor_value *val,
					    struct lsm6ds0_data *data,
					    float scale)
{
	switch (chan) {
#if defined(CONFIG_LSM6DS0_ACCEL_ENABLE_X_AXIS)
	case SENSOR_CHAN_ACCEL_X:
		lsm6ds0_accel_convert(val, data->accel_sample_x, scale);
		break;
#endif
#if defined(CONFIG_LSM6DS0_ACCEL_ENABLE_Y_AXIS)
	case SENSOR_CHAN_ACCEL_Y:
		lsm6ds0_accel_convert(val, data->accel_sample_y, scale);
		break;
#endif
#if defined(CONFIG_LSM6DS0_ACCEL_ENABLE_Z_AXIS)
	case SENSOR_CHAN_ACCEL_Z:
		lsm6ds0_accel_convert(val, data->accel_sample_z, scale);
		break;
#endif
	case SENSOR_CHAN_ACCEL_XYZ:
#if defined(CONFIG_LSM6DS0_ACCEL_ENABLE_X_AXIS)
		lsm6ds0_accel_convert(val, data->accel_sample_x, scale);
#endif
#if defined(CONFIG_LSM6DS0_ACCEL_ENABLE_Y_AXIS)
		lsm6ds0_accel_convert(val + 1, data->accel_sample_y, scale);
#endif
#if defined(CONFIG_LSM6DS0_ACCEL_ENABLE_Z_AXIS)
		lsm6ds0_accel_convert(val + 2, data->accel_sample_z, scale);
#endif
		break;
	default:
		return -ENOTSUP;
	}

	return 0;
}

static int lsm6ds0_accel_channel_get(enum sensor_channel chan,
				     struct sensor_value *val,
				     struct lsm6ds0_data *data)
{
	return lsm6ds0_accel_get_channel(chan, val, data,
					LSM6DS0_DEFAULT_ACCEL_FULLSCALE_FACTOR);
}

static inline void lsm6ds0_gyro_convert(struct sensor_value *val, int raw_val,
					float numerator)
{
	double dval;

	dval = (double)(raw_val) * numerator / 1000.0 * SENSOR_DEG2RAD_DOUBLE;
	val->val1 = (s32_t)dval;
	val->val2 = ((s32_t)(dval * 1000000)) % 1000000;
}

static inline int lsm6ds0_gyro_get_channel(enum sensor_channel chan,
					   struct sensor_value *val,
					   struct lsm6ds0_data *data,
					   float numerator)
{
	switch (chan) {
#if defined(CONFIG_LSM6DS0_GYRO_ENABLE_X_AXIS)
	case SENSOR_CHAN_GYRO_X:
		lsm6ds0_gyro_convert(val, data->gyro_sample_x, numerator);
		break;
#endif
#if defined(CONFIG_LSM6DS0_GYRO_ENABLE_Y_AXIS)
	case SENSOR_CHAN_GYRO_Y:
		lsm6ds0_gyro_convert(val, data->gyro_sample_y, numerator);
		break;
#endif
#if defined(CONFIG_LSM6DS0_GYRO_ENABLE_Z_AXIS)
	case SENSOR_CHAN_GYRO_Z:
		lsm6ds0_gyro_convert(val, data->gyro_sample_z, numerator);
		break;
#endif
	case SENSOR_CHAN_GYRO_XYZ:
#if defined(CONFIG_LSM6DS0_GYRO_ENABLE_X_AXIS)
		lsm6ds0_gyro_convert(val, data->gyro_sample_x, numerator);
#endif
#if defined(CONFIG_LSM6DS0_GYRO_ENABLE_Y_AXIS)
		lsm6ds0_gyro_convert(val + 1, data->gyro_sample_y, numerator);
#endif
#if defined(CONFIG_LSM6DS0_GYRO_ENABLE_Z_AXIS)
		lsm6ds0_gyro_convert(val + 2, data->gyro_sample_z, numerator);
#endif
		break;
	default:
		return -ENOTSUP;
	}

	return 0;
}

static int lsm6ds0_gyro_channel_get(enum sensor_channel chan,
				    struct sensor_value *val,
				    struct lsm6ds0_data *data)
{
	return lsm6ds0_gyro_get_channel(chan, val, data,
					LSM6DS0_DEFAULT_GYRO_FULLSCALE_FACTOR);
}

#if defined(CONFIG_LSM6DS0_ENABLE_TEMP)
static void lsm6ds0_gyro_channel_get_temp(struct sensor_value *val,
					  struct lsm6ds0_data *data)
{
	/* val = temp_sample / 16 + 25 */
	val->val1 = data->temp_sample / 16 + 25;
	val->val2 = (data->temp_sample % 16) * (1000000 / 16);
}
#endif

static int lsm6ds0_channel_get(struct device *dev,
			       enum sensor_channel chan,
			       struct sensor_value *val)
{
	struct lsm6ds0_data *data = dev->driver_data;

	switch (chan) {
	case SENSOR_CHAN_ACCEL_X:
	case SENSOR_CHAN_ACCEL_Y:
	case SENSOR_CHAN_ACCEL_Z:
	case SENSOR_CHAN_ACCEL_XYZ:
		lsm6ds0_accel_channel_get(chan, val, data);
		break;
	case SENSOR_CHAN_GYRO_X:
	case SENSOR_CHAN_GYRO_Y:
	case SENSOR_CHAN_GYRO_Z:
	case SENSOR_CHAN_GYRO_XYZ:
		lsm6ds0_gyro_channel_get(chan, val, data);
		break;
#if defined(CONFIG_LSM6DS0_ENABLE_TEMP)
	case SENSOR_CHAN_DIE_TEMP:
		lsm6ds0_gyro_channel_get_temp(val, data);
		break;
#endif
	default:
		return -ENOTSUP;
	}

	return 0;
}

static const struct sensor_driver_api lsm6ds0_api_funcs = {
	.sample_fetch = lsm6ds0_sample_fetch,
	.channel_get = lsm6ds0_channel_get,
};

static int lsm6ds0_init_chip(struct device *dev)
{
	struct lsm6ds0_data *data = dev->driver_data;
	const struct lsm6ds0_config *config = dev->config->config_info;
	u8_t chip_id;

	if (lsm6ds0_reboot(dev) < 0) {
		LOG_DBG("failed to reboot device");
		return -EIO;
	}

	if (i2c_reg_read_byte(data->i2c_master, config->i2c_slave_addr,
			      LSM6DS0_REG_WHO_AM_I, &chip_id) < 0) {
		LOG_DBG("failed reading chip id");
		return -EIO;
	}
	if (chip_id != LSM6DS0_VAL_WHO_AM_I) {
		LOG_DBG("invalid chip id 0x%x", chip_id);
		return -EIO;
	}
	LOG_DBG("chip id 0x%x", chip_id);

	if (lsm6ds0_accel_axis_ctrl(dev, LSM6DS0_ACCEL_ENABLE_X_AXIS,
				    LSM6DS0_ACCEL_ENABLE_Y_AXIS,
				    LSM6DS0_ACCEL_ENABLE_Z_AXIS) < 0) {
		LOG_DBG("failed to set accelerometer axis");
		return -EIO;
	}

	if (lsm6ds0_accel_set_fs_raw(dev, LSM6DS0_DEFAULT_ACCEL_FULLSCALE)
				     < 0) {
		LOG_DBG("failed to set accelerometer full-scale");
		return -EIO;
	}

	if (lsm6ds0_accel_set_odr_raw(dev, LSM6DS0_DEFAULT_ACCEL_SAMPLING_RATE)
				      < 0) {
		LOG_DBG("failed to set accelerometer sampling rate");
		return -EIO;
	}

	if (lsm6ds0_gyro_axis_ctrl(dev, LSM6DS0_GYRO_ENABLE_X_AXIS,
				   LSM6DS0_GYRO_ENABLE_Y_AXIS,
				   LSM6DS0_GYRO_ENABLE_Z_AXIS) < 0) {
		LOG_DBG("failed to set gyroscope axis");
		return -EIO;
	}

	if (lsm6ds0_gyro_set_fs_raw(dev, LSM6DS0_DEFAULT_GYRO_FULLSCALE)
				    < 0) {
		LOG_DBG("failed to set gyroscope full-scale");
		return -EIO;
	}

	if (lsm6ds0_gyro_set_odr_raw(dev, LSM6DS0_DEFAULT_GYRO_SAMPLING_RATE)
				     < 0) {
		LOG_DBG("failed to set gyroscope sampling rate");
		return -EIO;
	}

	if (i2c_reg_update_byte(data->i2c_master, config->i2c_slave_addr,
				LSM6DS0_REG_CTRL_REG8,
				LSM6DS0_MASK_CTRL_REG8_BDU |
				LSM6DS0_MASK_CTRL_REG8_BLE |
				LSM6DS0_MASK_CTRL_REG8_IF_ADD_INC,
				(1 << LSM6DS0_SHIFT_CTRL_REG8_BDU) |
				(0 << LSM6DS0_SHIFT_CTRL_REG8_BLE) |
				(1 << LSM6DS0_SHIFT_CTRL_REG8_IF_ADD_INC))
				< 0) {
		LOG_DBG("failed to set BDU, BLE and burst");
		return -EIO;
	}

	return 0;
}

static int lsm6ds0_init(struct device *dev)
{
	const struct lsm6ds0_config * const config = dev->config->config_info;
	struct lsm6ds0_data *data = dev->driver_data;

	data->i2c_master = device_get_binding(config->i2c_master_dev_name);
	if (!data->i2c_master) {
		LOG_DBG("i2c master not found: %s",
			    config->i2c_master_dev_name);
		return -EINVAL;
	}

	if (lsm6ds0_init_chip(dev) < 0) {
		LOG_DBG("failed to initialize chip");
		return -EIO;
	}

	return 0;
}

static const struct lsm6ds0_config lsm6ds0_config = {
	.i2c_master_dev_name = DT_ST_LSM6DS0_0_BUS_NAME,
	.i2c_slave_addr = DT_ST_LSM6DS0_0_BASE_ADDRESS,
};

static struct lsm6ds0_data lsm6ds0_data;

DEVICE_AND_API_INIT(lsm6ds0, DT_ST_LSM6DS0_0_LABEL, lsm6ds0_init,
		    &lsm6ds0_data, &lsm6ds0_config, POST_KERNEL,
		    CONFIG_SENSOR_INIT_PRIORITY, &lsm6ds0_api_funcs);
