/* Copyright (c) 2012-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.
 *
 */

#include <linux/module.h>
#include <linux/platform_device.h>
#include <linux/slab.h>
#include <linux/err.h>
#include <linux/of.h>
#include <linux/vmalloc.h>
#include "tsens.h"
#include "thermal_core.h"

#define TSENS_DRIVER_NAME			"msm-tsens"

#define TSENS_TM_INT_EN(n)			((n) + 0x4)
#define TSENS_TM_CRITICAL_INT_STATUS(n)		((n) + 0x14)
#define TSENS_TM_CRITICAL_INT_CLEAR(n)		((n) + 0x18)
#define TSENS_TM_CRITICAL_INT_MASK(n)		((n) + 0x1c)
#define TSENS_TM_CRITICAL_WD_BARK		BIT(31)
#define TSENS_TM_CRITICAL_CYCLE_MONITOR		BIT(30)
#define TSENS_TM_CRITICAL_INT_EN		BIT(2)
#define TSENS_TM_UPPER_INT_EN			BIT(1)
#define TSENS_TM_LOWER_INT_EN			BIT(0)
#define TSENS_TM_SN_UPPER_LOWER_THRESHOLD(n)	((n) + 0x20)
#define TSENS_TM_SN_ADDR_OFFSET			0x4
#define TSENS_TM_UPPER_THRESHOLD_SET(n)		((n) << 12)
#define TSENS_TM_UPPER_THRESHOLD_VALUE_SHIFT(n)	((n) >> 12)
#define TSENS_TM_LOWER_THRESHOLD_VALUE(n)	((n) & 0xfff)
#define TSENS_TM_UPPER_THRESHOLD_VALUE(n)	(((n) & 0xfff000) >> 12)
#define TSENS_TM_UPPER_THRESHOLD_MASK		0xfff000
#define TSENS_TM_LOWER_THRESHOLD_MASK		0xfff
#define TSENS_TM_UPPER_THRESHOLD_SHIFT		12
#define TSENS_TM_SN_CRITICAL_THRESHOLD(n)	((n) + 0x60)
#define TSENS_STATUS_ADDR_OFFSET		2
#define TSENS_TM_UPPER_INT_MASK(n)		(((n) & 0xffff0000) >> 16)
#define TSENS_TM_LOWER_INT_MASK(n)		((n) & 0xffff)
#define TSENS_TM_UPPER_LOWER_INT_STATUS(n)	((n) + 0x8)
#define TSENS_TM_UPPER_LOWER_INT_CLEAR(n)	((n) + 0xc)
#define TSENS_TM_UPPER_LOWER_INT_MASK(n)	((n) + 0x10)
#define TSENS_TM_UPPER_INT_SET(n)		(1 << (n + 16))
#define TSENS_TM_SN_CRITICAL_THRESHOLD_MASK	0xfff
#define TSENS_TM_SN_STATUS_VALID_BIT		BIT(21)
#define TSENS_TM_SN_STATUS_CRITICAL_STATUS	BIT(19)
#define TSENS_TM_SN_STATUS_UPPER_STATUS		BIT(18)
#define TSENS_TM_SN_STATUS_LOWER_STATUS		BIT(17)
#define TSENS_TM_SN_LAST_TEMP_MASK		0xfff
#define TSENS_TM_CODE_BIT_MASK			0xfff
#define TSENS_TM_CODE_SIGN_BIT			0x800
#define TSENS_TM_SCALE_DECI_MILLIDEG		100
#define TSENS_DEBUG_WDOG_TRIGGER_COUNT		5
#define TSENS_TM_WATCHDOG_LOG(n)		((n) + 0x13c)

#define TSENS_EN				BIT(0)
#define TSENS_CTRL_SENSOR_EN_MASK(n)		((n >> 3) & 0xffff)

static void msm_tsens_convert_temp(int last_temp, int *temp)
{
	int code_mask = ~TSENS_TM_CODE_BIT_MASK;

	if (last_temp & TSENS_TM_CODE_SIGN_BIT) {
		/* Sign extension for negative value */
		last_temp |= code_mask;
	}

	*temp = last_temp * TSENS_TM_SCALE_DECI_MILLIDEG;
}

static int tsens2xxx_get_temp(struct tsens_sensor *sensor, int *temp)
{
	struct tsens_device *tmdev = NULL;
	unsigned int code;
	void __iomem *sensor_addr;
	int last_temp = 0, last_temp2 = 0, last_temp3 = 0;

	if (!sensor)
		return -EINVAL;

	tmdev = sensor->tmdev;
	sensor_addr = TSENS_TM_SN_STATUS(tmdev->tsens_tm_addr);

	code = readl_relaxed_no_log(sensor_addr +
			(sensor->hw_id << TSENS_STATUS_ADDR_OFFSET));
	last_temp = code & TSENS_TM_SN_LAST_TEMP_MASK;

	if (code & TSENS_TM_SN_STATUS_VALID_BIT) {
		msm_tsens_convert_temp(last_temp, temp);
		return 0;
	}

	code = readl_relaxed_no_log(sensor_addr +
		(sensor->hw_id << TSENS_STATUS_ADDR_OFFSET));
	last_temp2 = code & TSENS_TM_SN_LAST_TEMP_MASK;
	if (code & TSENS_TM_SN_STATUS_VALID_BIT) {
		last_temp = last_temp2;
		msm_tsens_convert_temp(last_temp, temp);
		return 0;
	}

	code = readl_relaxed_no_log(sensor_addr +
			(sensor->hw_id <<
			TSENS_STATUS_ADDR_OFFSET));
	last_temp3 = code & TSENS_TM_SN_LAST_TEMP_MASK;
	if (code & TSENS_TM_SN_STATUS_VALID_BIT) {
		last_temp = last_temp3;
		msm_tsens_convert_temp(last_temp, temp);
		return 0;
	}

	if (last_temp == last_temp2)
		last_temp = last_temp2;
	else if (last_temp2 == last_temp3)
		last_temp = last_temp3;

	msm_tsens_convert_temp(last_temp, temp);

	if (tmdev->ops->dbg)
		tmdev->ops->dbg(tmdev, (u32) sensor->hw_id,
					TSENS_DBG_LOG_TEMP_READS, temp);

	return 0;
}

static int tsens_tm_activate_trip_type(struct tsens_sensor *tm_sensor,
			int trip, enum thermal_trip_activation_mode mode)
{
	struct tsens_device *tmdev = NULL;
	unsigned int reg_cntl, mask;
	int rc = 0;

	/* clear the interrupt and unmask */
	if (!tm_sensor || trip < 0)
		return -EINVAL;

	tmdev = tm_sensor->tmdev;
	if (!tmdev)
		return -EINVAL;


	mask = (tm_sensor->hw_id);
	switch (trip) {
	case THERMAL_TRIP_CRITICAL:
		tmdev->sensor[tm_sensor->hw_id].
			thr_state.crit_th_state = mode;
		reg_cntl = readl_relaxed(TSENS_TM_CRITICAL_INT_MASK
						(tmdev->tsens_tm_addr));
		if (mode == THERMAL_TRIP_ACTIVATION_DISABLED)
			writel_relaxed(reg_cntl | (1 << mask),
				(TSENS_TM_CRITICAL_INT_MASK
				(tmdev->tsens_tm_addr)));
		else
			writel_relaxed(reg_cntl & ~(1 << mask),
				(TSENS_TM_CRITICAL_INT_MASK
				(tmdev->tsens_tm_addr)));
		break;
	case THERMAL_TRIP_CONFIGURABLE_HI:
		tmdev->sensor[tm_sensor->hw_id].
			thr_state.high_th_state = mode;
		reg_cntl = readl_relaxed(TSENS_TM_UPPER_LOWER_INT_MASK
						(tmdev->tsens_tm_addr));
		if (mode == THERMAL_TRIP_ACTIVATION_DISABLED)
			writel_relaxed(reg_cntl |
				(TSENS_TM_UPPER_INT_SET(mask)),
				(TSENS_TM_UPPER_LOWER_INT_MASK
				(tmdev->tsens_tm_addr)));
		else
			writel_relaxed(reg_cntl &
				~(TSENS_TM_UPPER_INT_SET(mask)),
				(TSENS_TM_UPPER_LOWER_INT_MASK
				(tmdev->tsens_tm_addr)));
		break;
	case THERMAL_TRIP_CONFIGURABLE_LOW:
		tmdev->sensor[tm_sensor->hw_id].
			thr_state.low_th_state = mode;
		reg_cntl = readl_relaxed(TSENS_TM_UPPER_LOWER_INT_MASK
						(tmdev->tsens_tm_addr));
		if (mode == THERMAL_TRIP_ACTIVATION_DISABLED)
			writel_relaxed(reg_cntl | (1 << mask),
			(TSENS_TM_UPPER_LOWER_INT_MASK
						(tmdev->tsens_tm_addr)));
		else
			writel_relaxed(reg_cntl & ~(1 << mask),
			(TSENS_TM_UPPER_LOWER_INT_MASK
						(tmdev->tsens_tm_addr)));
		break;
	default:
		rc = -EINVAL;
	}

	/* Activate and enable the respective trip threshold setting */
	mb();

	return rc;
}

static int tsens2xxx_set_trip_temp(struct tsens_sensor *tm_sensor,
						int low_temp, int high_temp)
{
	unsigned int reg_cntl;
	unsigned long flags;
	struct tsens_device *tmdev = NULL;
	int rc = 0;

	if (!tm_sensor)
		return -EINVAL;

	tmdev = tm_sensor->tmdev;
	if (!tmdev)
		return -EINVAL;

	spin_lock_irqsave(&tmdev->tsens_upp_low_lock, flags);

	if (high_temp != INT_MAX) {
		tmdev->sensor[tm_sensor->hw_id].
				thr_state.high_temp = high_temp;
		reg_cntl = readl_relaxed((TSENS_TM_SN_UPPER_LOWER_THRESHOLD
				(tmdev->tsens_tm_addr)) +
				(tm_sensor->hw_id *
				TSENS_TM_SN_ADDR_OFFSET));
		high_temp /= TSENS_TM_SCALE_DECI_MILLIDEG;
		high_temp = TSENS_TM_UPPER_THRESHOLD_SET(high_temp);
		high_temp &= TSENS_TM_UPPER_THRESHOLD_MASK;
		reg_cntl &= ~TSENS_TM_UPPER_THRESHOLD_MASK;
		writel_relaxed(reg_cntl | high_temp,
			(TSENS_TM_SN_UPPER_LOWER_THRESHOLD
				(tmdev->tsens_tm_addr) +
			(tm_sensor->hw_id * TSENS_TM_SN_ADDR_OFFSET)));
	}

	if (low_temp != INT_MIN) {
		tmdev->sensor[tm_sensor->hw_id].
				thr_state.low_temp = low_temp;
		reg_cntl = readl_relaxed((TSENS_TM_SN_UPPER_LOWER_THRESHOLD
				(tmdev->tsens_tm_addr)) +
				(tm_sensor->hw_id *
				TSENS_TM_SN_ADDR_OFFSET));
		low_temp /= TSENS_TM_SCALE_DECI_MILLIDEG;
		low_temp &= TSENS_TM_LOWER_THRESHOLD_MASK;
		reg_cntl &= ~TSENS_TM_LOWER_THRESHOLD_MASK;
		writel_relaxed(reg_cntl | low_temp,
			(TSENS_TM_SN_UPPER_LOWER_THRESHOLD
				(tmdev->tsens_tm_addr) +
			(tm_sensor->hw_id * TSENS_TM_SN_ADDR_OFFSET)));
	}

	/* Set trip temperature thresholds */
	mb();

	if (high_temp != INT_MAX) {
		rc = tsens_tm_activate_trip_type(tm_sensor,
				THERMAL_TRIP_CONFIGURABLE_HI,
				THERMAL_TRIP_ACTIVATION_ENABLED);
		if (rc) {
			pr_err("trip high enable error :%d\n", rc);
			goto fail;
		}
	} else {
		rc = tsens_tm_activate_trip_type(tm_sensor,
				THERMAL_TRIP_CONFIGURABLE_HI,
				THERMAL_TRIP_ACTIVATION_DISABLED);
		if (rc) {
			pr_err("trip high disable error :%d\n", rc);
			goto fail;
		}
	}

	if (low_temp != INT_MIN) {
		rc = tsens_tm_activate_trip_type(tm_sensor,
				THERMAL_TRIP_CONFIGURABLE_LOW,
				THERMAL_TRIP_ACTIVATION_ENABLED);
		if (rc) {
			pr_err("trip low enable activation error :%d\n", rc);
			goto fail;
		}
	} else {
		rc = tsens_tm_activate_trip_type(tm_sensor,
				THERMAL_TRIP_CONFIGURABLE_LOW,
				THERMAL_TRIP_ACTIVATION_DISABLED);
		if (rc) {
			pr_err("trip low disable error :%d\n", rc);
			goto fail;
		}
	}

fail:
	spin_unlock_irqrestore(&tmdev->tsens_upp_low_lock, flags);
	return rc;
}

static irqreturn_t tsens_tm_critical_irq_thread(int irq, void *data)
{
	struct tsens_device *tm = data;
	unsigned int i, status, wd_log, wd_mask;
	unsigned long flags;
	void __iomem *sensor_status_addr, *sensor_int_mask_addr;
	void __iomem *sensor_critical_addr;
	void __iomem *wd_critical_addr, *wd_log_addr;

	sensor_status_addr = TSENS_TM_SN_STATUS(tm->tsens_tm_addr);
	sensor_int_mask_addr =
		TSENS_TM_CRITICAL_INT_MASK(tm->tsens_tm_addr);
	sensor_critical_addr =
		TSENS_TM_SN_CRITICAL_THRESHOLD(tm->tsens_tm_addr);
	wd_critical_addr =
		TSENS_TM_CRITICAL_INT_STATUS(tm->tsens_tm_addr);
	wd_log_addr = TSENS_TM_WATCHDOG_LOG(tm->tsens_tm_addr);

	if (tm->ctrl_data->wd_bark) {
		wd_mask = readl_relaxed(wd_critical_addr);
		if (wd_mask & TSENS_TM_CRITICAL_WD_BARK) {
			/*
			 * Clear watchdog interrupt and
			 * increment global wd count
			 */
			writel_relaxed(wd_mask | TSENS_TM_CRITICAL_WD_BARK,
				(TSENS_TM_CRITICAL_INT_CLEAR
				(tm->tsens_tm_addr)));
			writel_relaxed(wd_mask & ~(TSENS_TM_CRITICAL_WD_BARK),
				(TSENS_TM_CRITICAL_INT_CLEAR
				(tm->tsens_tm_addr)));
			wd_log = readl_relaxed(wd_log_addr);
			if (wd_log >= TSENS_DEBUG_WDOG_TRIGGER_COUNT) {
				pr_err("Watchdog count:%d\n", wd_log);
				if (tm->ops->dbg)
					tm->ops->dbg(tm, 0,
					TSENS_DBG_LOG_BUS_ID_DATA, NULL);
				BUG();
			}

			return IRQ_HANDLED;
		}
	}

	for (i = 0; i < TSENS_MAX_SENSORS; i++) {
		int int_mask, int_mask_val;
		u32 addr_offset;

		if (IS_ERR(tm->sensor[i].tzd))
			continue;

		spin_lock_irqsave(&tm->tsens_crit_lock, flags);
		addr_offset = tm->sensor[i].hw_id *
						TSENS_TM_SN_ADDR_OFFSET;
		status = readl_relaxed(sensor_status_addr + addr_offset);
		int_mask = readl_relaxed(sensor_int_mask_addr);

		if ((status & TSENS_TM_SN_STATUS_CRITICAL_STATUS) &&
			!(int_mask & (1 << tm->sensor[i].hw_id))) {
			int_mask = readl_relaxed(sensor_int_mask_addr);
			int_mask_val = (1 << tm->sensor[i].hw_id);
			/* Mask the corresponding interrupt for the sensors */
			writel_relaxed(int_mask | int_mask_val,
				TSENS_TM_CRITICAL_INT_MASK(
					tm->tsens_tm_addr));
			/* Clear the corresponding sensors interrupt */
			writel_relaxed(int_mask_val,
				TSENS_TM_CRITICAL_INT_CLEAR
					(tm->tsens_tm_addr));
			writel_relaxed(0,
				TSENS_TM_CRITICAL_INT_CLEAR(
					tm->tsens_tm_addr));
			tm->sensor[i].thr_state.
					crit_th_state = THERMAL_DEVICE_DISABLED;
		}
		spin_unlock_irqrestore(&tm->tsens_crit_lock, flags);
	}

	/* Mask critical interrupt */
	mb();

	return IRQ_HANDLED;
}

static irqreturn_t tsens_tm_irq_thread(int irq, void *data)
{
	struct tsens_device *tm = data;
	unsigned int i, status, threshold, temp;
	unsigned long flags;
	void __iomem *sensor_status_addr;
	void __iomem *sensor_int_mask_addr;
	void __iomem *sensor_upper_lower_addr;
	u32 addr_offset = 0;

	sensor_status_addr = TSENS_TM_SN_STATUS(tm->tsens_tm_addr);
	sensor_int_mask_addr =
		TSENS_TM_UPPER_LOWER_INT_MASK(tm->tsens_tm_addr);
	sensor_upper_lower_addr =
		TSENS_TM_SN_UPPER_LOWER_THRESHOLD(tm->tsens_tm_addr);

	for (i = 0; i < TSENS_MAX_SENSORS; i++) {
		bool upper_thr = false, lower_thr = false;
		int int_mask, int_mask_val = 0, rc;

		if (IS_ERR(tm->sensor[i].tzd))
			continue;

		rc = tsens2xxx_get_temp(&tm->sensor[i], &temp);
		if (rc) {
			pr_debug("Error:%d reading temp sensor:%d\n", rc, i);
			continue;
		}

		spin_lock_irqsave(&tm->tsens_upp_low_lock, flags);
		addr_offset = tm->sensor[i].hw_id *
						TSENS_TM_SN_ADDR_OFFSET;
		status = readl_relaxed(sensor_status_addr + addr_offset);
		threshold = readl_relaxed(sensor_upper_lower_addr +
								addr_offset);
		int_mask = readl_relaxed(sensor_int_mask_addr);

		if ((status & TSENS_TM_SN_STATUS_UPPER_STATUS) &&
			!(int_mask &
				(1 << (tm->sensor[i].hw_id + 16)))) {
			int_mask = readl_relaxed(sensor_int_mask_addr);
			int_mask_val = TSENS_TM_UPPER_INT_SET(
					tm->sensor[i].hw_id);
			/* Mask the corresponding interrupt for the sensors */
			writel_relaxed(int_mask | int_mask_val,
				TSENS_TM_UPPER_LOWER_INT_MASK(
					tm->tsens_tm_addr));
			/* Clear the corresponding sensors interrupt */
			writel_relaxed(int_mask_val,
				TSENS_TM_UPPER_LOWER_INT_CLEAR(
					tm->tsens_tm_addr));
			writel_relaxed(0,
				TSENS_TM_UPPER_LOWER_INT_CLEAR(
					tm->tsens_tm_addr));
			if (TSENS_TM_UPPER_THRESHOLD_VALUE(threshold) >
				(temp/TSENS_TM_SCALE_DECI_MILLIDEG)) {
				pr_debug("Re-arm high threshold\n");
				rc = tsens_tm_activate_trip_type(
					&tm->sensor[i],
					THERMAL_TRIP_CONFIGURABLE_HI,
					THERMAL_TRIP_ACTIVATION_ENABLED);
				if (rc)
					pr_err("high rearm failed:%d\n", rc);
			} else {
				upper_thr = true;
				tm->sensor[i].thr_state.
					high_th_state = THERMAL_DEVICE_DISABLED;
			}
		}

		if ((status & TSENS_TM_SN_STATUS_LOWER_STATUS) &&
			!(int_mask &
				(1 << tm->sensor[i].hw_id))) {
			int_mask = readl_relaxed(sensor_int_mask_addr);
			int_mask_val = (1 << tm->sensor[i].hw_id);
			/* Mask the corresponding interrupt for the sensors */
			writel_relaxed(int_mask | int_mask_val,
				TSENS_TM_UPPER_LOWER_INT_MASK(
					tm->tsens_tm_addr));
			/* Clear the corresponding sensors interrupt */
			writel_relaxed(int_mask_val,
				TSENS_TM_UPPER_LOWER_INT_CLEAR(
					tm->tsens_tm_addr));
			writel_relaxed(0,
				TSENS_TM_UPPER_LOWER_INT_CLEAR(
					tm->tsens_tm_addr));
			if (TSENS_TM_LOWER_THRESHOLD_VALUE(threshold)
				< (temp/TSENS_TM_SCALE_DECI_MILLIDEG)) {
				pr_debug("Re-arm low threshold\n");
				rc = tsens_tm_activate_trip_type(
					&tm->sensor[i],
					THERMAL_TRIP_CONFIGURABLE_LOW,
					THERMAL_TRIP_ACTIVATION_ENABLED);
				if (rc)
					pr_err("low rearm failed:%d\n", rc);
			} else {
				lower_thr = true;
				tm->sensor[i].thr_state.
					low_th_state = THERMAL_DEVICE_DISABLED;
			}
		}
		spin_unlock_irqrestore(&tm->tsens_upp_low_lock, flags);

		if (upper_thr || lower_thr) {
			/* Use id for multiple controllers */
			pr_debug("sensor:%d trigger temp (%d degC)\n",
				tm->sensor[i].hw_id, temp);
			of_thermal_handle_trip(tm->sensor[i].tzd);
		}
	}

	/* Disable monitoring sensor trip threshold for triggered sensor */
	mb();

	if (tm->ops->dbg)
		tm->ops->dbg(tm, 0, TSENS_DBG_LOG_INTERRUPT_TIMESTAMP, NULL);

	return IRQ_HANDLED;
}

static int tsens2xxx_hw_sensor_en(struct tsens_device *tmdev,
					u32 sensor_id)
{
	void __iomem *srot_addr;
	unsigned int srot_val, sensor_en;

	srot_addr = TSENS_CTRL_ADDR(tmdev->tsens_srot_addr + 0x4);
	srot_val = readl_relaxed(srot_addr);
	srot_val = TSENS_CTRL_SENSOR_EN_MASK(srot_val);

	sensor_en = ((1 << sensor_id) & srot_val);

	return sensor_en;
}

static int tsens2xxx_hw_init(struct tsens_device *tmdev)
{
	void __iomem *srot_addr;
	void __iomem *sensor_int_mask_addr;
	unsigned int srot_val, crit_mask, crit_val;

	srot_addr = TSENS_CTRL_ADDR(tmdev->tsens_srot_addr + 0x4);
	srot_val = readl_relaxed(srot_addr);
	if (!(srot_val & TSENS_EN)) {
		pr_err("TSENS device is not enabled\n");
		return -ENODEV;
	}

	if (tmdev->ctrl_data->cycle_monitor) {
		sensor_int_mask_addr =
			TSENS_TM_CRITICAL_INT_MASK(tmdev->tsens_tm_addr);
		crit_mask = readl_relaxed(sensor_int_mask_addr);
		crit_val = TSENS_TM_CRITICAL_CYCLE_MONITOR;
		if (tmdev->ctrl_data->cycle_compltn_monitor_mask)
			writel_relaxed((crit_mask | crit_val),
				(TSENS_TM_CRITICAL_INT_MASK
				(tmdev->tsens_tm_addr)));
		else
			writel_relaxed((crit_mask & ~crit_val),
				(TSENS_TM_CRITICAL_INT_MASK
				(tmdev->tsens_tm_addr)));
		/*Update critical cycle monitoring*/
		mb();
	}

	if (tmdev->ctrl_data->wd_bark) {
		sensor_int_mask_addr =
			TSENS_TM_CRITICAL_INT_MASK(tmdev->tsens_tm_addr);
		crit_mask = readl_relaxed(sensor_int_mask_addr);
		crit_val = TSENS_TM_CRITICAL_WD_BARK;
		if (tmdev->ctrl_data->wd_bark_mask)
			writel_relaxed((crit_mask | crit_val),
			(TSENS_TM_CRITICAL_INT_MASK
			(tmdev->tsens_tm_addr)));
		else
			writel_relaxed((crit_mask & ~crit_val),
			(TSENS_TM_CRITICAL_INT_MASK
			(tmdev->tsens_tm_addr)));
		/*Update watchdog monitoring*/
		mb();
	}

	writel_relaxed(TSENS_TM_CRITICAL_INT_EN |
		TSENS_TM_UPPER_INT_EN | TSENS_TM_LOWER_INT_EN,
		TSENS_TM_INT_EN(tmdev->tsens_tm_addr));

	spin_lock_init(&tmdev->tsens_crit_lock);
	spin_lock_init(&tmdev->tsens_upp_low_lock);

	return 0;
}

static const struct tsens_irqs tsens2xxx_irqs[] = {
	{ "tsens-upper-lower", tsens_tm_irq_thread},
	{ "tsens-critical", tsens_tm_critical_irq_thread},
};

static int tsens2xxx_register_interrupts(struct tsens_device *tmdev)
{
	struct platform_device *pdev;
	int i, rc;

	if (!tmdev)
		return -EINVAL;

	pdev = tmdev->pdev;

	for (i = 0; i < ARRAY_SIZE(tsens2xxx_irqs); i++) {
		int irq;

		irq = platform_get_irq_byname(pdev, tsens2xxx_irqs[i].name);
		if (irq < 0) {
			dev_err(&pdev->dev, "failed to get irq %s\n",
					tsens2xxx_irqs[i].name);
			return irq;
		}

		rc = devm_request_threaded_irq(&pdev->dev, irq, NULL,
				tsens2xxx_irqs[i].handler,
				IRQF_TRIGGER_HIGH | IRQF_ONESHOT,
				tsens2xxx_irqs[i].name, tmdev);
		if (rc) {
			dev_err(&pdev->dev, "failed to get irq %s\n",
					tsens2xxx_irqs[i].name);
			return rc;
		}
		enable_irq_wake(irq);
	}

	return 0;
}

static const struct tsens_ops ops_tsens2xxx = {
	.hw_init	= tsens2xxx_hw_init,
	.get_temp	= tsens2xxx_get_temp,
	.set_trips	= tsens2xxx_set_trip_temp,
	.interrupts_reg	= tsens2xxx_register_interrupts,
	.dbg		= tsens2xxx_dbg,
	.sensor_en	= tsens2xxx_hw_sensor_en,
};

const struct tsens_data data_tsens2xxx = {
	.cycle_monitor			= false,
	.cycle_compltn_monitor_mask	= 1,
	.wd_bark			= false,
	.wd_bark_mask			= 1,
	.ops				= &ops_tsens2xxx,
};

const struct tsens_data data_tsens23xx = {
	.cycle_monitor			= true,
	.cycle_compltn_monitor_mask	= 1,
	.wd_bark			= true,
	.wd_bark_mask			= 1,
	.ops				= &ops_tsens2xxx,
};

const struct tsens_data data_tsens24xx = {
	.cycle_monitor			= true,
	.cycle_compltn_monitor_mask	= 1,
	.wd_bark			= true,
	/* Enable Watchdog monitoring by unmasking */
	.wd_bark_mask			= 0,
	.ops				= &ops_tsens2xxx,
};
