1 /* SPDX-License-Identifier: GPL-2.0-only */
2 /*
3  * Copyright (c) 2007-2016, Synaptics Incorporated
4  * Copyright (C) 2016 Zodiac Inflight Innovations
5  */
6 
7 #ifndef _RMI_F34_H
8 #define _RMI_F34_H
9 
10 /* F34 image file offsets. */
11 #define F34_FW_IMAGE_OFFSET	0x100
12 
13 /* F34 register offsets. */
14 #define F34_BLOCK_DATA_OFFSET	2
15 
16 /* F34 commands */
17 #define F34_WRITE_FW_BLOCK	0x2
18 #define F34_ERASE_ALL		0x3
19 #define F34_READ_CONFIG_BLOCK	0x5
20 #define F34_WRITE_CONFIG_BLOCK	0x6
21 #define F34_ERASE_CONFIG	0x7
22 #define F34_ENABLE_FLASH_PROG	0xf
23 
24 #define F34_STATUS_IN_PROGRESS	0xff
25 #define F34_STATUS_IDLE		0x80
26 
27 #define F34_IDLE_WAIT_MS	500
28 #define F34_ENABLE_WAIT_MS	300
29 #define F34_ERASE_WAIT_MS	5000
30 #define F34_WRITE_WAIT_MS	3000
31 
32 #define F34_BOOTLOADER_ID_LEN	2
33 
34 /* F34 V7 defines */
35 #define V7_FLASH_STATUS_OFFSET		0
36 #define V7_PARTITION_ID_OFFSET		1
37 #define V7_BLOCK_NUMBER_OFFSET		2
38 #define V7_TRANSFER_LENGTH_OFFSET	3
39 #define V7_COMMAND_OFFSET		4
40 #define V7_PAYLOAD_OFFSET		5
41 #define V7_BOOTLOADER_ID_OFFSET		1
42 
43 #define IMAGE_HEADER_VERSION_10		0x10
44 
45 #define CONFIG_ID_SIZE			32
46 #define PRODUCT_ID_SIZE			10
47 
48 
49 #define HAS_BSR				BIT(5)
50 #define HAS_CONFIG_ID			BIT(3)
51 #define HAS_GUEST_CODE			BIT(6)
52 #define HAS_DISP_CFG			BIT(5)
53 
54 /* F34 V7 commands */
55 #define CMD_V7_IDLE			0
56 #define CMD_V7_ENTER_BL			1
57 #define CMD_V7_READ			2
58 #define CMD_V7_WRITE			3
59 #define CMD_V7_ERASE			4
60 #define CMD_V7_ERASE_AP			5
61 #define CMD_V7_SENSOR_ID		6
62 
63 #define v7_CMD_IDLE			0
64 #define v7_CMD_WRITE_FW			1
65 #define v7_CMD_WRITE_CONFIG		2
66 #define v7_CMD_WRITE_LOCKDOWN		3
67 #define v7_CMD_WRITE_GUEST_CODE		4
68 #define v7_CMD_READ_CONFIG		5
69 #define v7_CMD_ERASE_ALL		6
70 #define v7_CMD_ERASE_UI_FIRMWARE	7
71 #define v7_CMD_ERASE_UI_CONFIG		8
72 #define v7_CMD_ERASE_BL_CONFIG		9
73 #define v7_CMD_ERASE_DISP_CONFIG	10
74 #define v7_CMD_ERASE_FLASH_CONFIG	11
75 #define v7_CMD_ERASE_GUEST_CODE		12
76 #define v7_CMD_ENABLE_FLASH_PROG	13
77 
78 #define v7_UI_CONFIG_AREA		0
79 #define v7_PM_CONFIG_AREA		1
80 #define v7_BL_CONFIG_AREA		2
81 #define v7_DP_CONFIG_AREA		3
82 #define v7_FLASH_CONFIG_AREA		4
83 
84 /* F34 V7 partition IDs */
85 #define BOOTLOADER_PARTITION		1
86 #define DEVICE_CONFIG_PARTITION		2
87 #define FLASH_CONFIG_PARTITION		3
88 #define MANUFACTURING_BLOCK_PARTITION	4
89 #define GUEST_SERIALIZATION_PARTITION	5
90 #define GLOBAL_PARAMETERS_PARTITION	6
91 #define CORE_CODE_PARTITION		7
92 #define CORE_CONFIG_PARTITION		8
93 #define GUEST_CODE_PARTITION		9
94 #define DISPLAY_CONFIG_PARTITION	10
95 
96 /* F34 V7 container IDs */
97 #define TOP_LEVEL_CONTAINER			0
98 #define UI_CONTAINER				1
99 #define UI_CONFIG_CONTAINER			2
100 #define BL_CONTAINER				3
101 #define BL_IMAGE_CONTAINER			4
102 #define BL_CONFIG_CONTAINER			5
103 #define BL_LOCKDOWN_INFO_CONTAINER		6
104 #define PERMANENT_CONFIG_CONTAINER		7
105 #define GUEST_CODE_CONTAINER			8
106 #define BL_PROTOCOL_DESCRIPTOR_CONTAINER	9
107 #define UI_PROTOCOL_DESCRIPTOR_CONTAINER	10
108 #define RMI_SELF_DISCOVERY_CONTAINER		11
109 #define RMI_PAGE_CONTENT_CONTAINER		12
110 #define GENERAL_INFORMATION_CONTAINER		13
111 #define DEVICE_CONFIG_CONTAINER			14
112 #define FLASH_CONFIG_CONTAINER			15
113 #define GUEST_SERIALIZATION_CONTAINER		16
114 #define GLOBAL_PARAMETERS_CONTAINER		17
115 #define CORE_CODE_CONTAINER			18
116 #define CORE_CONFIG_CONTAINER			19
117 #define DISPLAY_CONFIG_CONTAINER		20
118 
119 struct f34v7_query_1_7 {
120 	u8 bl_minor_revision;			/* query 1 */
121 	u8 bl_major_revision;
122 	__le32 bl_fw_id;			/* query 2 */
123 	u8 minimum_write_size;			/* query 3 */
124 	__le16 block_size;
125 	__le16 flash_page_size;
126 	__le16 adjustable_partition_area_size;	/* query 4 */
127 	__le16 flash_config_length;		/* query 5 */
128 	__le16 payload_length;			/* query 6 */
129 	u8 partition_support[4];		/* query 7 */
130 } __packed;
131 
132 struct f34v7_data_1_5 {
133 	u8 partition_id;
134 	__le16 block_offset;
135 	__le16 transfer_length;
136 	u8 command;
137 	u8 payload[2];
138 } __packed;
139 
140 struct block_data {
141 	const void *data;
142 	int size;
143 };
144 
145 struct partition_table {
146 	u8 partition_id;
147 	u8 byte_1_reserved;
148 	__le16 partition_length;
149 	__le16 start_physical_address;
150 	__le16 partition_properties;
151 } __packed;
152 
153 struct physical_address {
154 	u16 ui_firmware;
155 	u16 ui_config;
156 	u16 dp_config;
157 	u16 guest_code;
158 };
159 
160 struct container_descriptor {
161 	__le32 content_checksum;
162 	__le16 container_id;
163 	u8 minor_version;
164 	u8 major_version;
165 	u8 reserved_08;
166 	u8 reserved_09;
167 	u8 reserved_0a;
168 	u8 reserved_0b;
169 	u8 container_option_flags[4];
170 	__le32 content_options_length;
171 	__le32 content_options_address;
172 	__le32 content_length;
173 	__le32 content_address;
174 } __packed;
175 
176 struct block_count {
177 	u16 ui_firmware;
178 	u16 ui_config;
179 	u16 dp_config;
180 	u16 fl_config;
181 	u16 pm_config;
182 	u16 bl_config;
183 	u16 lockdown;
184 	u16 guest_code;
185 };
186 
187 struct image_header_10 {
188 	__le32 checksum;
189 	u8 reserved_04;
190 	u8 reserved_05;
191 	u8 minor_header_version;
192 	u8 major_header_version;
193 	u8 reserved_08;
194 	u8 reserved_09;
195 	u8 reserved_0a;
196 	u8 reserved_0b;
197 	__le32 top_level_container_start_addr;
198 };
199 
200 struct image_metadata {
201 	bool contains_firmware_id;
202 	bool contains_bootloader;
203 	bool contains_display_cfg;
204 	bool contains_guest_code;
205 	bool contains_flash_config;
206 	unsigned int firmware_id;
207 	unsigned int checksum;
208 	unsigned int bootloader_size;
209 	unsigned int display_cfg_offset;
210 	unsigned char bl_version;
211 	unsigned char product_id[PRODUCT_ID_SIZE + 1];
212 	unsigned char cstmr_product_id[PRODUCT_ID_SIZE + 1];
213 	struct block_data bootloader;
214 	struct block_data ui_firmware;
215 	struct block_data ui_config;
216 	struct block_data dp_config;
217 	struct block_data fl_config;
218 	struct block_data bl_config;
219 	struct block_data guest_code;
220 	struct block_data lockdown;
221 	struct block_count blkcount;
222 	struct physical_address phyaddr;
223 };
224 
225 struct register_offset {
226 	u8 properties;
227 	u8 properties_2;
228 	u8 block_size;
229 	u8 block_count;
230 	u8 gc_block_count;
231 	u8 flash_status;
232 	u8 partition_id;
233 	u8 block_number;
234 	u8 transfer_length;
235 	u8 flash_cmd;
236 	u8 payload;
237 };
238 
239 struct rmi_f34_firmware {
240 	__le32 checksum;
241 	u8 pad1[3];
242 	u8 bootloader_version;
243 	__le32 image_size;
244 	__le32 config_size;
245 	u8 product_id[10];
246 	u8 product_info[2];
247 	u8 pad2[228];
248 	u8 data[];
249 };
250 
251 struct f34v5_data {
252 	u16 block_size;
253 	u16 fw_blocks;
254 	u16 config_blocks;
255 	u16 ctrl_address;
256 	u8 status;
257 
258 	struct completion cmd_done;
259 	struct mutex flash_mutex;
260 };
261 
262 struct f34v7_data {
263 	bool has_display_cfg;
264 	bool has_guest_code;
265 	bool force_update;
266 	bool in_bl_mode;
267 	u8 *read_config_buf;
268 	size_t read_config_buf_size;
269 	u8 command;
270 	u8 flash_status;
271 	u16 block_size;
272 	u16 config_block_count;
273 	u16 config_size;
274 	u16 config_area;
275 	u16 flash_config_length;
276 	u16 payload_length;
277 	u8 partitions;
278 	u16 partition_table_bytes;
279 	bool new_partition_table;
280 
281 	struct register_offset off;
282 	struct block_count blkcount;
283 	struct physical_address phyaddr;
284 	struct image_metadata img;
285 
286 	const void *config_data;
287 	const void *image;
288 	struct completion cmd_done;
289 };
290 
291 struct f34_data {
292 	struct rmi_function *fn;
293 
294 	u8 bl_version;
295 	unsigned char bootloader_id[5];
296 	unsigned char configuration_id[CONFIG_ID_SIZE*2 + 1];
297 
298 	int update_status;
299 	int update_progress;
300 	int update_size;
301 
302 	union {
303 		struct f34v5_data v5;
304 		struct f34v7_data v7;
305 	};
306 };
307 
308 int rmi_f34v7_start_reflash(struct f34_data *f34, const struct firmware *fw);
309 int rmi_f34v7_do_reflash(struct f34_data *f34, const struct firmware *fw);
310 int rmi_f34v7_probe(struct f34_data *f34);
311 
312 #endif /* _RMI_F34_H */
313