summaryrefslogtreecommitdiff
path: root/include/linux/iio/adc/qcom-adc5-gen3-common.h
blob: 6303eaa6640be177e7c94ca54e7f87131abcd6ff (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
/* SPDX-License-Identifier: GPL-2.0 */
/*
 * Copyright (c) Qualcomm Technologies, Inc. and/or its subsidiaries.
 *
 * Code used in the main and auxiliary Qualcomm PMIC voltage ADCs
 * of type ADC5 Gen3.
 */

#ifndef QCOM_ADC5_GEN3_COMMON_H
#define QCOM_ADC5_GEN3_COMMON_H

#include <linux/auxiliary_bus.h>
#include <linux/bitfield.h>
#include <linux/bits.h>
#include <linux/device.h>
#include <linux/iio/adc/qcom-vadc-common.h>
#include <linux/regmap.h>
#include <linux/types.h>

#define ADC5_GEN3_HS				0x45
#define ADC5_GEN3_HS_BUSY			BIT(7)
#define ADC5_GEN3_HS_READY			BIT(0)

#define ADC5_GEN3_STATUS1			0x46
#define ADC5_GEN3_STATUS1_CONV_FAULT		BIT(7)
#define ADC5_GEN3_STATUS1_THR_CROSS		BIT(6)
#define ADC5_GEN3_STATUS1_EOC			BIT(0)

#define ADC5_GEN3_TM_EN_STS			0x47
#define ADC5_GEN3_TM_HIGH_STS			0x48
#define ADC5_GEN3_TM_LOW_STS			0x49

#define ADC5_GEN3_EOC_STS			0x4a
#define ADC5_GEN3_EOC_CHAN_0			BIT(0)

#define ADC5_GEN3_EOC_CLR			0x4b
#define ADC5_GEN3_TM_HIGH_STS_CLR		0x4c
#define ADC5_GEN3_TM_LOW_STS_CLR		0x4d
#define ADC5_GEN3_CONV_ERR_CLR			0x4e
#define ADC5_GEN3_CONV_ERR_CLR_REQ		BIT(0)

#define ADC5_GEN3_SID				0x4f
#define ADC5_GEN3_SID_MASK			GENMASK(3, 0)

#define ADC5_GEN3_PERPH_CH			0x50
#define ADC5_GEN3_CHAN_CONV_REQ			BIT(7)

#define ADC5_GEN3_TIMER_SEL			0x51
#define ADC5_GEN3_TIME_IMMEDIATE		0x1

#define ADC5_GEN3_DIG_PARAM			0x52
#define ADC5_GEN3_DIG_PARAM_CAL_SEL_MASK	GENMASK(5, 4)
#define ADC5_GEN3_DIG_PARAM_DEC_RATIO_SEL_MASK	GENMASK(3, 2)

#define ADC5_GEN3_FAST_AVG			0x53
#define ADC5_GEN3_FAST_AVG_CTL_EN		BIT(7)
#define ADC5_GEN3_FAST_AVG_CTL_SAMPLES_MASK	GENMASK(2, 0)

#define ADC5_GEN3_ADC_CH_SEL_CTL		0x54
#define ADC5_GEN3_DELAY_CTL			0x55
#define ADC5_GEN3_HW_SETTLE_DELAY_MASK		GENMASK(3, 0)

#define ADC5_GEN3_CH_EN				0x56
#define ADC5_GEN3_HIGH_THR_INT_EN		BIT(1)
#define ADC5_GEN3_LOW_THR_INT_EN		BIT(0)

#define ADC5_GEN3_LOW_THR0			0x57
#define ADC5_GEN3_LOW_THR1			0x58
#define ADC5_GEN3_HIGH_THR0			0x59
#define ADC5_GEN3_HIGH_THR1			0x5a

#define ADC5_GEN3_CH_DATA0(channel)	(0x5c + (channel) * 2)
#define ADC5_GEN3_CH_DATA1(channel)	(0x5d + (channel) * 2)

#define ADC5_GEN3_CONV_REQ			0xe5
#define ADC5_GEN3_CONV_REQ_REQ			BIT(0)

#define ADC5_GEN3_VIRTUAL_SID_MASK		GENMASK(15, 8)
#define ADC5_GEN3_CHANNEL_MASK			GENMASK(7, 0)
#define ADC5_GEN3_V_CHAN(x)		\
	(FIELD_PREP(ADC5_GEN3_VIRTUAL_SID_MASK, (x).sid) | (x).channel)

/* ADC channels for PMIC5 Gen3 */
#define ADC5_GEN3_REF_GND			0x00
#define ADC5_GEN3_1P25VREF			0x01
#define ADC5_GEN3_DIE_TEMP			0x03
#define ADC5_GEN3_USB_SNS_V_16			0x11
#define ADC5_GEN3_VIN_DIV16_MUX			0x12
#define ADC5_GEN3_VPH_PWR			0x8e
#define ADC5_GEN3_VBAT_SNS_QBG			0x8f
/* 100k pull-up channels */
#define ADC5_GEN3_AMUX1_THM_100K_PU		0x44
#define ADC5_GEN3_AMUX2_THM_100K_PU		0x45
#define ADC5_GEN3_AMUX3_THM_100K_PU		0x46
#define ADC5_GEN3_AMUX4_THM_100K_PU		0x47
#define ADC5_GEN3_AMUX5_THM_100K_PU		0x48
#define ADC5_GEN3_AMUX6_THM_100K_PU		0x49
#define ADC5_GEN3_AMUX1_GPIO_100K_PU		0x4a
#define ADC5_GEN3_AMUX2_GPIO_100K_PU		0x4b
#define ADC5_GEN3_AMUX3_GPIO_100K_PU		0x4c
#define ADC5_GEN3_AMUX4_GPIO_100K_PU		0x4d

#define ADC5_MAX_CHANNEL			0xc0

enum adc5_cal_method {
	ADC5_NO_CAL = 0,
	ADC5_RATIOMETRIC_CAL,
	ADC5_ABSOLUTE_CAL,
};

enum adc5_time_select {
	MEAS_INT_DISABLE = 0,
	MEAS_INT_IMMEDIATE,
	MEAS_INT_50MS,
	MEAS_INT_100MS,
	MEAS_INT_1S,
	MEAS_INT_NONE,
};

/**
 * struct adc5_sdam_data - data per SDAM allocated for adc usage
 * @base_addr: base address for the ADC SDAM peripheral.
 * @irq_name: ADC IRQ name.
 * @irq: ADC IRQ number.
 */
struct adc5_sdam_data {
	u16 base_addr;
	const char *irq_name;
	int irq;
};

/**
 * struct adc5_device_data - Top-level ADC device data
 * @regmap: ADC peripheral register map field.
 * @base: array of SDAM data.
 * @num_sdams: number of ADC SDAM peripherals.
 */
struct adc5_device_data {
	struct regmap *regmap;
	struct adc5_sdam_data *base;
	int num_sdams;
};

/**
 * struct adc5_channel_common_prop - ADC channel properties (common to ADC and TM).
 * @channel: channel number, refer to the channel list.
 * @cal_method: calibration method.
 * @decimation: sampling rate supported for the channel.
 * @sid: ID of PMIC owning the channel.
 * @label: Channel name used in device tree.
 * @prescale: channel scaling performed on the input signal.
 * @hw_settle_time_us: the time between AMUX being configured and the
 *	start of conversion in uS.
 * @avg_samples: ability to provide single result from the ADC
 *	that is an average of multiple measurements.
 * @scale_fn_type: Represents the scaling function to convert voltage
 *	physical units desired by the client for the channel.
 */
struct adc5_channel_common_prop {
	unsigned int channel;
	enum adc5_cal_method cal_method;
	unsigned int decimation;
	unsigned int sid;
	const char *label;
	unsigned int prescale;
	unsigned int hw_settle_time_us;
	unsigned int avg_samples;
	enum vadc_scale_fn_type scale_fn_type;
};

/**
 * struct tm5_aux_dev_wrapper - wrapper structure around TM auxiliary device
 * @aux_dev: TM auxiliary device structure.
 * @dev_data: Top-level ADC device data.
 * @tm_props: Array of common ADC channel properties for TM channels.
 * @n_tm_channels: number of TM channels.
 */
struct tm5_aux_dev_wrapper {
	struct auxiliary_device aux_dev;
	struct adc5_device_data *dev_data;
	struct adc5_channel_common_prop *tm_props;
	unsigned int n_tm_channels;
};

int adc5_gen3_read(struct adc5_device_data *adc, unsigned int sdam_index,
		   u16 offset, u8 *data, int len);

int adc5_gen3_write(struct adc5_device_data *adc, unsigned int sdam_index,
		    u16 offset, u8 *data, int len);

int adc5_gen3_poll_wait_hs(struct adc5_device_data *adc,
			   unsigned int sdam_index);

void adc5_gen3_update_dig_param(struct adc5_channel_common_prop *prop,
				u8 *data);

int adc5_gen3_status_clear(struct adc5_device_data *adc,
			   int sdam_index, u16 offset, u8 *val, int len);

void adc5_gen3_mutex_lock(struct device *dev);
void adc5_gen3_mutex_unlock(struct device *dev);
int adc5_gen3_get_scaled_reading(struct device *dev,
				 struct adc5_channel_common_prop *common_props,
				 int *val);
int adc5_gen3_therm_code_to_temp(struct device *dev,
				 struct adc5_channel_common_prop *common_props,
				 u16 code, int *val);
void adc5_gen3_register_tm_event_notifier(struct device *dev,
					  void (*handler)(struct auxiliary_device *));

#endif /* QCOM_ADC5_GEN3_COMMON_H */