xref: /OK3568_Linux_fs/kernel/drivers/iio/common/ssp_sensors/ssp.h (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun /* SPDX-License-Identifier: GPL-2.0-or-later */
2*4882a593Smuzhiyun /*
3*4882a593Smuzhiyun  *  Copyright (C) 2014, Samsung Electronics Co. Ltd. All Rights Reserved.
4*4882a593Smuzhiyun  */
5*4882a593Smuzhiyun 
6*4882a593Smuzhiyun #ifndef __SSP_SENSORHUB_H__
7*4882a593Smuzhiyun #define __SSP_SENSORHUB_H__
8*4882a593Smuzhiyun 
9*4882a593Smuzhiyun #include <linux/delay.h>
10*4882a593Smuzhiyun #include <linux/gpio/consumer.h>
11*4882a593Smuzhiyun #include <linux/iio/common/ssp_sensors.h>
12*4882a593Smuzhiyun #include <linux/iio/iio.h>
13*4882a593Smuzhiyun #include <linux/spi/spi.h>
14*4882a593Smuzhiyun 
15*4882a593Smuzhiyun #define SSP_DEVICE_ID		0x55
16*4882a593Smuzhiyun 
17*4882a593Smuzhiyun #ifdef SSP_DBG
18*4882a593Smuzhiyun #define ssp_dbg(format, ...) pr_info("[SSP] "format, ##__VA_ARGS__)
19*4882a593Smuzhiyun #else
20*4882a593Smuzhiyun #define ssp_dbg(format, ...)
21*4882a593Smuzhiyun #endif
22*4882a593Smuzhiyun 
23*4882a593Smuzhiyun #define SSP_SW_RESET_TIME		3000
24*4882a593Smuzhiyun /* Sensor polling in ms */
25*4882a593Smuzhiyun #define SSP_DEFAULT_POLLING_DELAY	200
26*4882a593Smuzhiyun #define SSP_DEFAULT_RETRIES		3
27*4882a593Smuzhiyun #define SSP_DATA_PACKET_SIZE		960
28*4882a593Smuzhiyun #define SSP_HEADER_BUFFER_SIZE		4
29*4882a593Smuzhiyun 
30*4882a593Smuzhiyun enum {
31*4882a593Smuzhiyun 	SSP_KERNEL_BINARY = 0,
32*4882a593Smuzhiyun 	SSP_KERNEL_CRASHED_BINARY,
33*4882a593Smuzhiyun };
34*4882a593Smuzhiyun 
35*4882a593Smuzhiyun enum {
36*4882a593Smuzhiyun 	SSP_INITIALIZATION_STATE = 0,
37*4882a593Smuzhiyun 	SSP_NO_SENSOR_STATE,
38*4882a593Smuzhiyun 	SSP_ADD_SENSOR_STATE,
39*4882a593Smuzhiyun 	SSP_RUNNING_SENSOR_STATE,
40*4882a593Smuzhiyun };
41*4882a593Smuzhiyun 
42*4882a593Smuzhiyun /* Firmware download STATE */
43*4882a593Smuzhiyun enum {
44*4882a593Smuzhiyun 	SSP_FW_DL_STATE_FAIL = -1,
45*4882a593Smuzhiyun 	SSP_FW_DL_STATE_NONE = 0,
46*4882a593Smuzhiyun 	SSP_FW_DL_STATE_NEED_TO_SCHEDULE,
47*4882a593Smuzhiyun 	SSP_FW_DL_STATE_SCHEDULED,
48*4882a593Smuzhiyun 	SSP_FW_DL_STATE_DOWNLOADING,
49*4882a593Smuzhiyun 	SSP_FW_DL_STATE_SYNC,
50*4882a593Smuzhiyun 	SSP_FW_DL_STATE_DONE,
51*4882a593Smuzhiyun };
52*4882a593Smuzhiyun 
53*4882a593Smuzhiyun #define SSP_INVALID_REVISION			99999
54*4882a593Smuzhiyun #define SSP_INVALID_REVISION2			0xffffff
55*4882a593Smuzhiyun 
56*4882a593Smuzhiyun /* AP -> SSP Instruction */
57*4882a593Smuzhiyun #define SSP_MSG2SSP_INST_BYPASS_SENSOR_ADD	0xa1
58*4882a593Smuzhiyun #define SSP_MSG2SSP_INST_BYPASS_SENSOR_RM	0xa2
59*4882a593Smuzhiyun #define SSP_MSG2SSP_INST_REMOVE_ALL		0xa3
60*4882a593Smuzhiyun #define SSP_MSG2SSP_INST_CHANGE_DELAY		0xa4
61*4882a593Smuzhiyun #define SSP_MSG2SSP_INST_LIBRARY_ADD		0xb1
62*4882a593Smuzhiyun #define SSP_MSG2SSP_INST_LIBRARY_REMOVE		0xb2
63*4882a593Smuzhiyun #define SSP_MSG2SSP_INST_LIB_NOTI		0xb4
64*4882a593Smuzhiyun #define SSP_MSG2SSP_INST_LIB_DATA		0xc1
65*4882a593Smuzhiyun 
66*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_MCU_SET_GYRO_CAL		0xcd
67*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_MCU_SET_ACCEL_CAL	0xce
68*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_STATUS_SHUTDOWN		0xd0
69*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_STATUS_WAKEUP		0xd1
70*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_STATUS_SLEEP		0xd2
71*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_STATUS_RESUME		0xd3
72*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_STATUS_SUSPEND		0xd4
73*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_STATUS_RESET		0xd5
74*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_STATUS_POW_CONNECTED	0xd6
75*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_STATUS_POW_DISCONNECTED	0xd7
76*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_TEMPHUMIDITY_CAL_DONE	0xda
77*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_MCU_SET_DUMPMODE		0xdb
78*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_MCU_DUMP_CHECK		0xdc
79*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_MCU_BATCH_FLUSH		0xdd
80*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_MCU_BATCH_COUNT		0xdf
81*4882a593Smuzhiyun 
82*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_WHOAMI				0x0f
83*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_FIRMWARE_REV			0xf0
84*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_SENSOR_FORMATION			0xf1
85*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_SENSOR_PROXTHRESHOLD		0xf2
86*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_SENSOR_BARCODE_EMUL		0xf3
87*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_SENSOR_SCANNING			0xf4
88*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_SET_MAGNETIC_HWOFFSET		0xf5
89*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_GET_MAGNETIC_HWOFFSET		0xf6
90*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_SENSOR_GESTURE_CURRENT		0xf7
91*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_GET_THERM			0xf8
92*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_GET_BIG_DATA			0xf9
93*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_SET_BIG_DATA			0xfa
94*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_START_BIG_DATA			0xfb
95*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_SET_MAGNETIC_STATIC_MATRIX	0xfd
96*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_SENSOR_TILT			0xea
97*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_MCU_SET_TIME			0xfe
98*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_MCU_GET_TIME			0xff
99*4882a593Smuzhiyun 
100*4882a593Smuzhiyun #define SSP_MSG2SSP_AP_FUSEROM				0x01
101*4882a593Smuzhiyun 
102*4882a593Smuzhiyun /* voice data */
103*4882a593Smuzhiyun #define SSP_TYPE_WAKE_UP_VOICE_SERVICE			0x01
104*4882a593Smuzhiyun #define SSP_TYPE_WAKE_UP_VOICE_SOUND_SOURCE_AM		0x01
105*4882a593Smuzhiyun #define SSP_TYPE_WAKE_UP_VOICE_SOUND_SOURCE_GRAMMER	0x02
106*4882a593Smuzhiyun 
107*4882a593Smuzhiyun /* Factory Test */
108*4882a593Smuzhiyun #define SSP_ACCELEROMETER_FACTORY			0x80
109*4882a593Smuzhiyun #define SSP_GYROSCOPE_FACTORY				0x81
110*4882a593Smuzhiyun #define SSP_GEOMAGNETIC_FACTORY				0x82
111*4882a593Smuzhiyun #define SSP_PRESSURE_FACTORY				0x85
112*4882a593Smuzhiyun #define SSP_GESTURE_FACTORY				0x86
113*4882a593Smuzhiyun #define SSP_TEMPHUMIDITY_CRC_FACTORY			0x88
114*4882a593Smuzhiyun #define SSP_GYROSCOPE_TEMP_FACTORY			0x8a
115*4882a593Smuzhiyun #define SSP_GYROSCOPE_DPS_FACTORY			0x8b
116*4882a593Smuzhiyun #define SSP_MCU_FACTORY					0x8c
117*4882a593Smuzhiyun #define SSP_MCU_SLEEP_FACTORY				0x8d
118*4882a593Smuzhiyun 
119*4882a593Smuzhiyun /* SSP -> AP ACK about write CMD */
120*4882a593Smuzhiyun #define SSP_MSG_ACK		0x80	/* ACK from SSP to AP */
121*4882a593Smuzhiyun #define SSP_MSG_NAK		0x70	/* NAK from SSP to AP */
122*4882a593Smuzhiyun 
123*4882a593Smuzhiyun struct ssp_sensorhub_info {
124*4882a593Smuzhiyun 	char *fw_name;
125*4882a593Smuzhiyun 	char *fw_crashed_name;
126*4882a593Smuzhiyun 	unsigned int fw_rev;
127*4882a593Smuzhiyun 	const u8 * const mag_table;
128*4882a593Smuzhiyun 	const unsigned int mag_length;
129*4882a593Smuzhiyun };
130*4882a593Smuzhiyun 
131*4882a593Smuzhiyun /* ssp_msg options bit */
132*4882a593Smuzhiyun #define SSP_RW		0
133*4882a593Smuzhiyun #define SSP_INDEX	3
134*4882a593Smuzhiyun 
135*4882a593Smuzhiyun #define SSP_AP2HUB_READ		0
136*4882a593Smuzhiyun #define SSP_AP2HUB_WRITE	1
137*4882a593Smuzhiyun #define SSP_HUB2AP_WRITE	2
138*4882a593Smuzhiyun #define SSP_AP2HUB_READY	3
139*4882a593Smuzhiyun #define SSP_AP2HUB_RETURN	4
140*4882a593Smuzhiyun 
141*4882a593Smuzhiyun /**
142*4882a593Smuzhiyun  * struct ssp_data - ssp platformdata structure
143*4882a593Smuzhiyun  * @spi:		spi device
144*4882a593Smuzhiyun  * @sensorhub_info:	info about sensorhub board specific features
145*4882a593Smuzhiyun  * @wdt_timer:		watchdog timer
146*4882a593Smuzhiyun  * @work_wdt:		watchdog work
147*4882a593Smuzhiyun  * @work_firmware:	firmware upgrade work queue
148*4882a593Smuzhiyun  * @work_refresh:	refresh work queue for reset request from MCU
149*4882a593Smuzhiyun  * @shut_down:		shut down flag
150*4882a593Smuzhiyun  * @mcu_dump_mode:	mcu dump mode for debug
151*4882a593Smuzhiyun  * @time_syncing:	time syncing indication flag
152*4882a593Smuzhiyun  * @timestamp:		previous time in ns calculated for time syncing
153*4882a593Smuzhiyun  * @check_status:	status table for each sensor
154*4882a593Smuzhiyun  * @com_fail_cnt:	communication fail count
155*4882a593Smuzhiyun  * @reset_cnt:		reset count
156*4882a593Smuzhiyun  * @timeout_cnt:	timeout count
157*4882a593Smuzhiyun  * @available_sensors:	available sensors seen by sensorhub (bit array)
158*4882a593Smuzhiyun  * @cur_firm_rev:	cached current firmware revision
159*4882a593Smuzhiyun  * @last_resume_state:	last AP resume/suspend state used to handle the PM
160*4882a593Smuzhiyun  *                      state of ssp
161*4882a593Smuzhiyun  * @last_ap_state:	(obsolete) sleep notification for MCU
162*4882a593Smuzhiyun  * @sensor_enable:	sensor enable mask
163*4882a593Smuzhiyun  * @delay_buf:		data acquisition intervals table
164*4882a593Smuzhiyun  * @batch_latency_buf:	yet unknown but existing in communication protocol
165*4882a593Smuzhiyun  * @batch_opt_buf:	yet unknown but existing in communication protocol
166*4882a593Smuzhiyun  * @accel_position:	yet unknown but existing in communication protocol
167*4882a593Smuzhiyun  * @mag_position:	yet unknown but existing in communication protocol
168*4882a593Smuzhiyun  * @fw_dl_state:	firmware download state
169*4882a593Smuzhiyun  * @comm_lock:		lock protecting the handshake
170*4882a593Smuzhiyun  * @pending_lock:	lock protecting pending list and completion
171*4882a593Smuzhiyun  * @mcu_reset_gpiod:	mcu reset line
172*4882a593Smuzhiyun  * @ap_mcu_gpiod:	ap to mcu gpio line
173*4882a593Smuzhiyun  * @mcu_ap_gpiod:	mcu to ap gpio line
174*4882a593Smuzhiyun  * @pending_list:	pending list for messages queued to be sent/read
175*4882a593Smuzhiyun  * @sensor_devs:	registered IIO devices table
176*4882a593Smuzhiyun  * @enable_refcount:	enable reference count for wdt (watchdog timer)
177*4882a593Smuzhiyun  * @header_buffer:	cache aligned buffer for packet header
178*4882a593Smuzhiyun  */
179*4882a593Smuzhiyun struct ssp_data {
180*4882a593Smuzhiyun 	struct spi_device *spi;
181*4882a593Smuzhiyun 	const struct ssp_sensorhub_info *sensorhub_info;
182*4882a593Smuzhiyun 	struct timer_list wdt_timer;
183*4882a593Smuzhiyun 	struct work_struct work_wdt;
184*4882a593Smuzhiyun 	struct delayed_work work_refresh;
185*4882a593Smuzhiyun 
186*4882a593Smuzhiyun 	bool shut_down;
187*4882a593Smuzhiyun 	bool mcu_dump_mode;
188*4882a593Smuzhiyun 	bool time_syncing;
189*4882a593Smuzhiyun 	int64_t timestamp;
190*4882a593Smuzhiyun 
191*4882a593Smuzhiyun 	int check_status[SSP_SENSOR_MAX];
192*4882a593Smuzhiyun 
193*4882a593Smuzhiyun 	unsigned int com_fail_cnt;
194*4882a593Smuzhiyun 	unsigned int reset_cnt;
195*4882a593Smuzhiyun 	unsigned int timeout_cnt;
196*4882a593Smuzhiyun 
197*4882a593Smuzhiyun 	unsigned int available_sensors;
198*4882a593Smuzhiyun 	unsigned int cur_firm_rev;
199*4882a593Smuzhiyun 
200*4882a593Smuzhiyun 	char last_resume_state;
201*4882a593Smuzhiyun 	char last_ap_state;
202*4882a593Smuzhiyun 
203*4882a593Smuzhiyun 	unsigned int sensor_enable;
204*4882a593Smuzhiyun 	u32 delay_buf[SSP_SENSOR_MAX];
205*4882a593Smuzhiyun 	s32 batch_latency_buf[SSP_SENSOR_MAX];
206*4882a593Smuzhiyun 	s8 batch_opt_buf[SSP_SENSOR_MAX];
207*4882a593Smuzhiyun 
208*4882a593Smuzhiyun 	int accel_position;
209*4882a593Smuzhiyun 	int mag_position;
210*4882a593Smuzhiyun 	int fw_dl_state;
211*4882a593Smuzhiyun 
212*4882a593Smuzhiyun 	struct mutex comm_lock;
213*4882a593Smuzhiyun 	struct mutex pending_lock;
214*4882a593Smuzhiyun 
215*4882a593Smuzhiyun 	struct gpio_desc *mcu_reset_gpiod;
216*4882a593Smuzhiyun 	struct gpio_desc *ap_mcu_gpiod;
217*4882a593Smuzhiyun 	struct gpio_desc *mcu_ap_gpiod;
218*4882a593Smuzhiyun 
219*4882a593Smuzhiyun 	struct list_head pending_list;
220*4882a593Smuzhiyun 
221*4882a593Smuzhiyun 	struct iio_dev *sensor_devs[SSP_SENSOR_MAX];
222*4882a593Smuzhiyun 	atomic_t enable_refcount;
223*4882a593Smuzhiyun 
224*4882a593Smuzhiyun 	__le16 header_buffer[SSP_HEADER_BUFFER_SIZE / sizeof(__le16)]
225*4882a593Smuzhiyun 		____cacheline_aligned;
226*4882a593Smuzhiyun };
227*4882a593Smuzhiyun 
228*4882a593Smuzhiyun void ssp_clean_pending_list(struct ssp_data *data);
229*4882a593Smuzhiyun 
230*4882a593Smuzhiyun int ssp_command(struct ssp_data *data, char command, int arg);
231*4882a593Smuzhiyun 
232*4882a593Smuzhiyun int ssp_send_instruction(struct ssp_data *data, u8 inst, u8 sensor_type,
233*4882a593Smuzhiyun 			 u8 *send_buf, u8 length);
234*4882a593Smuzhiyun 
235*4882a593Smuzhiyun int ssp_irq_msg(struct ssp_data *data);
236*4882a593Smuzhiyun 
237*4882a593Smuzhiyun int ssp_get_chipid(struct ssp_data *data);
238*4882a593Smuzhiyun 
239*4882a593Smuzhiyun int ssp_set_magnetic_matrix(struct ssp_data *data);
240*4882a593Smuzhiyun 
241*4882a593Smuzhiyun unsigned int ssp_get_sensor_scanning_info(struct ssp_data *data);
242*4882a593Smuzhiyun 
243*4882a593Smuzhiyun unsigned int ssp_get_firmware_rev(struct ssp_data *data);
244*4882a593Smuzhiyun 
245*4882a593Smuzhiyun int ssp_queue_ssp_refresh_task(struct ssp_data *data, unsigned int delay);
246*4882a593Smuzhiyun 
247*4882a593Smuzhiyun #endif /* __SSP_SENSORHUB_H__ */
248