xref: /rk3399_rockchip-uboot/drivers/ufs/ufs-rockchip-usbplug.c (revision 3d58a3e83e9c707ced8b4cf0dcff35e39d1eedf8)
1 // SPDX-License-Identifier: GPL-2.0+
2 /*
3  * Rockchip UFS Host Controller driver
4  *
5  * Copyright (C) 2024 Rockchip Electronics Co.Ltd.
6  */
7 
8 #include <charset.h>
9 #include <common.h>
10 #include <dm.h>
11 #include <log.h>
12 #include <dm/lists.h>
13 #include <dm/device-internal.h>
14 #include <malloc.h>
15 #include <hexdump.h>
16 #include <scsi.h>
17 #include <asm/io.h>
18 #include <asm/dma-mapping.h>
19 #include <linux/bitops.h>
20 #include <linux/delay.h>
21 
22 #include "ufs-rockchip-usbplug.h"
23 #include "ufs.h"
24 /* Query request retries */
25 #define QUERY_REQ_RETRIES 3
26 /* Query request timeout */
27 #define QUERY_REQ_TIMEOUT 1500 /* 1.5 seconds */
28 
29 #if defined(CONFIG_SUPPORT_USBPLUG)
30 int _ufs_start(struct ufs_hba *hba);
31 
ufs_info_show_dev_desc(void * buf)32 static void ufs_info_show_dev_desc(void *buf)
33 {
34 	struct ufs_device_descriptor *dev = (struct ufs_device_descriptor *)buf;
35 
36 	printf("---------------------------\n");
37 	printf("---UFS Device Descriptor---\n");
38 	printf("---------------------------\n");
39 	printf("bLength: 0x%x\n", dev->b_length);
40 	printf("bDescriptorIDN: 0x%x\n", dev->b_descriptor_idn);
41 	printf("bDevice: 0x%x\n", dev->b_device);
42 	printf("bDeviceClass: 0x%x\n", dev->b_device_class);
43 	printf("bDeviceSubClass: 0x%x\n", dev->b_device_sub_class);
44 	printf("bProtocol: 0x%x\n", dev->b_protocol);
45 	printf("bNumberLU: 0x%x\n", dev->b_number_lu);
46 	printf("bNumberWLU: 0x%x\n", dev->b_number_wlu);
47 	printf("bBootEnable: 0x%x\n", dev->b_boot_enable);
48 	printf("bDescrAccessEn: 0x%x\n", dev->b_descr_access_en);
49 	printf("bInitPowerMode: 0x%x\n", dev->b_init_power_mode);
50 	printf("bHighPriorityLUN: 0x%x\n", dev->b_high_priority_lun);
51 	printf("bSecureRemovalType: 0x%x\n", dev->b_secure_removal_type);
52 	printf("bSecurityLU: 0x%x\n", dev->b_security_lu);
53 	printf("bBackgroundOpsTermLat: 0x%x\n", dev->b_background_ops_term_lat);
54 	printf("bInitActiveICCLevel: 0x%x\n", dev->b_init_active_icc_level);
55 	printf("wSpecVersion: 0x%x\n", to_bigendian16(dev->w_spec_version));
56 	printf("wManufactureDate: 0x%x\n", to_bigendian16(dev->w_manufacture_date));
57 	printf("iManufacturerName: 0x%x\n", dev->i_manufacturer_name);
58 	printf("iProductName: 0x%x\n", dev->i_product_name);
59 	printf("iSerialNumber: 0x%x\n", dev->i_serial_number);
60 	printf("iOemID: 0x%x\n", dev->i_oem_id);
61 	printf("wManufacturerID: 0x%x\n", to_bigendian16(dev->w_manufacturer_id));
62 	printf("bUD0BaseOffset: 0x%x\n", dev->b_ud_0base_offset);
63 	printf("bUDConfigPLength: 0x%x\n", dev->b_ud_config_plength);
64 	printf("bDeviceRTTCap: 0x%x\n", dev->b_device_rtt_cap);
65 	printf("wPeriodicRTCUpdate: 0x%x\n", to_bigendian16(dev->w_periodic_rtc_update));
66 	printf("bUFSFeatureSupport: 0x%x\n", dev->b_ufs_feature_support);
67 	printf("bFFUTimeout: 0x%x\n", dev->b_ffu_timeout);
68 	printf("bQueueDepth: 0x%x\n", dev->b_queue_depth);
69 	printf("wDeviceVersion: 0x%x\n", to_bigendian16(dev->w_device_version));
70 	printf("bNumSecureWPArea: 0x%x\n", dev->b_num_secure_wp_area);
71 	printf("dPSAMaxDataSize: 0x%x\n", to_bigendian32(dev->d_psa_max_data_size));
72 	printf("bPSAStateTimeout: 0x%x\n", dev->b_psa_state_timeout);
73 	printf("iProductRevisionLevel: 0x%x\n", dev->i_product_revision_level);
74 }
75 
ufs_info_show_conf_desc(void * buf)76 static void ufs_info_show_conf_desc(void *buf)
77 {
78 	struct ufs_configuration_descriptor *c_desc = (struct ufs_configuration_descriptor *)buf;
79 	struct ufs_dev_desc_configuration_param *dev;
80 	struct ufs_unit_desc_configuration_param *unit;
81 	int i;
82 
83 	dev = &c_desc->dev_desc_conf_param;
84 	printf("----------------------------------------\n");
85 	printf("---UFS Device Descriptor Config Param---\n");
86 	printf("----------------------------------------\n");
87 	printf("bLength: 0x%x\n", dev->b_length);
88 	printf("bDescriptorIDN: 0x%x\n", dev->b_descriptor_idn);
89 	printf("bConfDescContinue: 0x%x\n", dev->b_conf_desc_continue);
90 	printf("bBootEnable: 0x%x\n", dev->b_boot_enable);
91 	printf("bDescrAccessEn: 0x%x\n", dev->b_descr_access_en);
92 	printf("bInitPowerMode: 0x%x\n", dev->b_init_power_mode);
93 	printf("bHighPriorityLUN: 0x%x\n", dev->b_high_priority_lun);
94 	printf("bSecureRemovalType: 0x%x\n", dev->b_secure_removal_type);
95 	printf("bInitActiveICCLevel: 0x%x\n", dev->b_init_active_icc_level);
96 	printf("wPeriodicRTCUpdate: 0x%x\n", to_bigendian16(dev->w_periodic_rtc_update));
97 	printf("bSecureRemovalType: 0x%x\n", dev->b_secure_removal_type);
98 	printf("bInitActiveICCLevel: 0x%x\n", dev->b_init_active_icc_level);
99 	printf("wPeriodicRTCUpdate: 0x%x\n", to_bigendian16(dev->w_periodic_rtc_update));
100 	printf("bWB_EN: 0x%x\n", dev->b_write_booster_buffer_reserve_user_space_en);
101 	printf("WB_TYPE: 0x%x\n", dev->b_write_booster_buffer_type);
102 	printf("WB_alloc_units: 0x%x\n", to_bigendian32(dev->d_num_shared_write_booster_buffer_alloc_units));
103 
104 	for (i = 0; i < UNIT_DESCS_COUNT; i++) {
105 		unit = &c_desc->unit_desc_conf_param[i];
106 
107 		printf("-----------------------------------------\n");
108 		printf("---UFS Unit %d Descriptor Config Param---\n", i);
109 		printf("-----------------------------------------\n");
110 		printf("bLUEnable: 0x%x\n", unit->b_lu_enable);
111 		printf("bBootLunID: 0x%x\n", unit->b_boot_lun_id);
112 		printf("bLUWriteProtect: 0x%x\n", unit->b_lu_write_protect);
113 		printf("bMemoryType: 0x%x\n", unit->b_memory_type);
114 		printf("dNumAllocUnits: 0x%x\n", to_bigendian32(unit->d_num_alloc_units));
115 		printf("bDataReliability: 0x%x\n", unit->b_data_reliability);
116 		printf("bLogicalBlockSize: 0x%x\n", unit->b_logical_block_size);
117 		printf("bProvisioningType: 0x%x\n", unit->b_provisioning_type);
118 		printf("wContextCapabilities: 0x%x\n", to_bigendian16(unit->w_context_capabilities));
119 	}
120 }
121 
ufs_get_configuration_desc(struct ufs_hba * hba,struct ufs_configuration_descriptor * c_desc)122 static int ufs_get_configuration_desc(struct ufs_hba *hba, struct ufs_configuration_descriptor *c_desc)
123 {
124 	u8 desc_buf[CONFIGURATION_DESC_V31_LENGTH];
125 	u8 *buf = desc_buf;
126 	int length = hba->desc_size.conf_desc;
127 	int err;
128 
129 	if (CONFIGURATION_DESC_V31_LENGTH == hba->desc_size.conf_desc) {
130 		buf = (u8 *)c_desc;
131 	} else if(CONFIGURATION_DESC_V22_LENGTH != hba->desc_size.conf_desc &&
132 		  CONFIGURATION_DESC_V30_LENGTH != hba->desc_size.conf_desc) {
133 		return -EINVAL;
134 	}
135 
136 	err = ufshcd_read_desc_param(hba, QUERY_DESC_IDN_CONFIGURATION, 0, 0, buf, length);
137 	if (err) {
138 		dev_err(hba->dev, "%s: Failed reading configuration Desc. err = %d\n",
139 			__func__, err);
140 		return err;
141 	}
142 
143 	if (CONFIGURATION_DESC_V22_LENGTH == hba->desc_size.conf_desc) {
144 		memcpy(&c_desc->dev_desc_conf_param, buf, 0x10);
145 		buf += 0x10;
146 		for (int i = 0; i < UNIT_DESCS_COUNT; i++) {
147 			memcpy(&c_desc->unit_desc_conf_param[i], buf,  0x10);
148 			buf += 0x10;
149 		}
150 	}
151 
152 	if (CONFIGURATION_DESC_V30_LENGTH == hba->desc_size.conf_desc) {
153 		memcpy(&c_desc->dev_desc_conf_param, buf, 0x12);
154 		buf += 0x12;
155 		for (int i = 0; i < UNIT_DESCS_COUNT; i++) {
156 			memcpy(&c_desc->unit_desc_conf_param[i], buf,  0x1A);
157 			buf += 0x1A;
158 		}
159 	}
160 
161 	return err;
162 }
163 
ufshcd_write_desc_param(struct ufs_hba * hba,enum desc_idn desc_id,int desc_index,u8 param_offset,u8 * param_read_buf,u8 param_size)164 static int ufshcd_write_desc_param(struct ufs_hba *hba, enum desc_idn desc_id,
165 			   int desc_index, u8 param_offset, u8 *param_read_buf,
166 			   u8 param_size)
167 {
168 	int ret;
169 	u8 *desc_buf;
170 	int buff_len;
171 
172 	/* Safety check */
173 	if (desc_id >= QUERY_DESC_IDN_MAX || !param_size)
174 		return -EINVAL;
175 
176 	/* Get the max length of descriptor from structure filled up at probe
177 	 * time.
178 	 */
179 	ret = ufshcd_map_desc_id_to_length(hba, desc_id, &buff_len);
180 
181 	/* Sanity checks */
182 	if (ret || !buff_len) {
183 		dev_err(hba->dev, "%s: Failed to get full descriptor length\n",
184 			__func__);
185 		return ret;
186 	}
187 
188 	desc_buf = param_read_buf;
189 	/* Request for full descriptor */
190 	ret = ufshcd_query_descriptor_retry(hba, UPIU_QUERY_OPCODE_WRITE_DESC,
191 					    desc_id, desc_index, 0, desc_buf,
192 					    &buff_len);
193 
194 	if (ret)
195 		dev_err(hba->dev, "%s: Failed write descriptor. desc_id %d, desc_index %d, param_offset %d, ret %d\n",
196 			__func__, desc_id, desc_index, param_offset, ret);
197 
198 	return ret;
199 }
200 
ufs_write_configuration_desc(struct ufs_hba * hba,struct ufs_configuration_descriptor * c_desc)201 static int ufs_write_configuration_desc(struct ufs_hba *hba, struct ufs_configuration_descriptor *c_desc)
202 {
203 	u8 desc_buf[CONFIGURATION_DESC_V31_LENGTH];
204 	u8 *buf = desc_buf;
205 	int length = hba->desc_size.conf_desc;
206 	int err;
207 
208 	if (CONFIGURATION_DESC_V31_LENGTH == hba->desc_size.conf_desc) {
209 		buf = (u8 *)c_desc;
210 	} else if (CONFIGURATION_DESC_V22_LENGTH == hba->desc_size.conf_desc) {
211 		memcpy(buf, &c_desc->dev_desc_conf_param, 0x10);
212 		buf += 0x10;
213 		for (int i = 0; i < UNIT_DESCS_COUNT; i++) {
214 			memcpy(buf, &c_desc->unit_desc_conf_param[i], 0x10);
215 			buf += 0x10;
216 		}
217 		buf = desc_buf;
218 	} else if (CONFIGURATION_DESC_V30_LENGTH == hba->desc_size.conf_desc) {
219 		memcpy(buf, &c_desc->dev_desc_conf_param, 0x12);
220 		buf += 0x12;
221 		for (int i = 0; i < UNIT_DESCS_COUNT; i++) {
222 			memcpy(buf, &c_desc->unit_desc_conf_param[i], 0x1A);
223 			buf += 0x1A;
224 		}
225 		buf = desc_buf;
226 	} else {
227 		return -EINVAL;
228 	}
229 
230 	err = ufshcd_write_desc_param(hba, QUERY_DESC_IDN_CONFIGURATION, 0, 0, buf, length);
231 	if (err) {
232 		dev_err(hba->dev, "%s: Failed reading configuration Desc. err = %d\n",
233 			__func__, err);
234 		return err;
235 	}
236 
237 	return err;
238 }
239 
ufs_lu_configuration(struct ufs_hba * hba,struct ufs_configuration_descriptor * c_desc)240 static void ufs_lu_configuration(struct ufs_hba *hba, struct ufs_configuration_descriptor *c_desc)
241 {
242 	uint32_t denominator = hba->geo_desc->b_allocation_unit_size * to_bigendian32(hba->geo_desc->d_segment_size);
243 	struct ufs_dev_desc_configuration_param *dev;
244 	struct ufs_unit_desc_configuration_param *unit;
245 	uint32_t alloced_units = 0;
246 	int i, cap_adj_fac;
247 	uint64_t total_raw_device_capacity;
248 	uint32_t max_wb_alloc_units = cpu_to_be32(hba->geo_desc->d_write_booster_buffer_max_alloc_units);
249 	uint32_t wb_alloc_units;
250 
251 	cap_adj_fac = to_bigendian16(hba->geo_desc->w_enhanced1_cap_adj_fac) / 256;
252 	total_raw_device_capacity = cpu_to_be64(hba->geo_desc->q_total_raw_device_capacity);
253 
254 	dev = &c_desc->dev_desc_conf_param;
255 	dev->b_boot_enable = 0x1;
256 	dev->b_descr_access_en = 0x0;
257 	dev->b_init_power_mode = 0x1;
258 	dev->b_high_priority_lun = 0x7F;
259 	dev->b_secure_removal_type = 0x0;
260 	dev->b_init_active_icc_level = 0x0;
261 	dev->w_periodic_rtc_update = 0x0;
262 
263 	unit = &c_desc->unit_desc_conf_param[0];
264 	/* lu 1: boot lu A 4MB */
265 	unit[1].b_boot_lun_id = WELL_BOOT_LU_A; /* lu 0, boot a */
266 	unit[1].b_memory_type = 0x3;
267 	unit[1].d_num_alloc_units = (4 * 0x800 * cap_adj_fac + denominator - 1) / denominator;
268 	alloced_units += unit[1].d_num_alloc_units;
269 	/* lu 2: boot lu B 4MB */
270 	unit[2].b_boot_lun_id = WELL_BOOT_LU_B; /* lu 1, boot b */
271 	unit[2].b_memory_type = 0x3; /* lu 0, Enhanced Memory */
272 	unit[2].d_num_alloc_units = (4 * 0x800 * cap_adj_fac + denominator - 1) / denominator;
273 	alloced_units += unit[2].d_num_alloc_units;
274 	/* lu 3: data lu 8MB */
275 	unit[3].b_boot_lun_id = 0x0; /* lu 2 */
276 	unit[3].b_memory_type = 0x3; /* lu 2, Enhanced Memory */
277 	unit[3].d_num_alloc_units = (8 * 0x800 * cap_adj_fac + denominator - 1) / denominator;
278 	alloced_units += unit[3].d_num_alloc_units;
279 
280 	if (max_wb_alloc_units) {
281 		wb_alloc_units = max_wb_alloc_units;
282 		if (wb_alloc_units > max_wb_alloc_units)
283 			wb_alloc_units = max_wb_alloc_units;
284 		dev->b_write_booster_buffer_reserve_user_space_en = 1;
285 		dev->b_write_booster_buffer_type = 1;
286 		dev->d_num_shared_write_booster_buffer_alloc_units = to_bigendian32(wb_alloc_units);
287 	}
288 
289 	/* lu 0: data lu, max capacity*/
290 	unit[0].b_boot_lun_id = 0x0; /* lu 3 */
291 	unit[0].b_memory_type = 0x0; /* lu 3, Normal Memory */
292 	unit[0].d_num_alloc_units = lower_32_bits(total_raw_device_capacity) / denominator - alloced_units;
293 
294 	for (i = 0; i <= 3; i++) { /* lu 0 - 3 */
295 		unit[i].b_lu_enable = 0x1;
296 		unit[i].b_lu_write_protect = 0x0;
297 		unit[i].b_data_reliability = 0x1;
298 		unit[i].b_logical_block_size = 0x0c;
299 		unit[i].b_provisioning_type = 0x2;
300 		unit[i].w_context_capabilities = 0x0;
301 		unit[i].d_num_alloc_units = to_bigendian32(unit[i].d_num_alloc_units);
302 	}
303 }
304 
compair_conf_desp(struct ufs_configuration_descriptor * cda,struct ufs_configuration_descriptor * cdb)305 static int compair_conf_desp(struct ufs_configuration_descriptor *cda, struct ufs_configuration_descriptor *cdb)
306 {
307 	struct ufs_dev_desc_configuration_param *dev_a, *dev_b;
308 	struct ufs_unit_desc_configuration_param *unit_a, *unit_b;
309 	int i, ret;
310 
311 	dev_a = &cda->dev_desc_conf_param;
312 	dev_b = &cdb->dev_desc_conf_param;
313 
314 	if (dev_a->b_boot_enable != dev_b->b_boot_enable)
315 		return 0x3;
316 	if (dev_a->b_descr_access_en != dev_b->b_descr_access_en)
317 		return 0x4;
318 	if (dev_a->b_init_power_mode != dev_b->b_init_power_mode)
319 		return 0x5;
320 	if (dev_a->b_high_priority_lun != dev_b->b_high_priority_lun)
321 		return 0x6;
322 	if (dev_a->b_secure_removal_type != dev_b->b_secure_removal_type)
323 		return 0x7;
324 	if (dev_a->b_init_active_icc_level != dev_b->b_init_active_icc_level)
325 		return 0x8;
326 	if (dev_a->w_periodic_rtc_update != dev_b->w_periodic_rtc_update)
327 		return 0x9;
328 	if (dev_a->b_write_booster_buffer_reserve_user_space_en !=
329 	    dev_b->b_write_booster_buffer_reserve_user_space_en)
330 		return 0xA;
331 	if (dev_a->b_write_booster_buffer_type != dev_b->b_write_booster_buffer_type)
332 		return 0xB;
333 	if (dev_a->d_num_shared_write_booster_buffer_alloc_units !=
334 	    dev_b->d_num_shared_write_booster_buffer_alloc_units)
335 		return 0xC;
336 
337 	for (i = 0; i < UNIT_DESCS_COUNT; i++) {
338 		unit_a = &cda->unit_desc_conf_param[i];
339 		unit_b = &cdb->unit_desc_conf_param[i];
340 
341 		ret = 0x10 * (i + 1);
342 		if (unit_a->b_lu_enable != unit_b->b_lu_enable)
343 			return ret;
344 		if (unit_a->b_boot_lun_id != unit_b->b_boot_lun_id)
345 			return ret + 0x1;
346 		if (unit_a->b_lu_write_protect != unit_b->b_lu_write_protect)
347 			return ret + 0x2;
348 		if (unit_a->b_memory_type != unit_b->b_memory_type)
349 			return ret + 0x3;
350 		if (unit_a->d_num_alloc_units != unit_b->d_num_alloc_units)
351 			return ret + 0x4;
352 		if (unit_a->b_data_reliability != unit_b->b_data_reliability)
353 			return ret + 0x8;
354 		if (unit_a->b_logical_block_size != unit_b->b_logical_block_size)
355 			return ret + 0x9;
356 		if (unit_a->b_provisioning_type != unit_b->b_provisioning_type)
357 			return ret + 0xA;
358 		if (unit_a->w_context_capabilities != unit_b->w_context_capabilities)
359 			return ret + 0xB;
360 	}
361 	return 0;
362 }
363 
364 
365 /**
366  * ufshcd_init_query() - init the query response and request parameters
367  */
ufshcd_init_query(struct ufs_hba * hba,struct ufs_query_req ** request,struct ufs_query_res ** response,enum query_opcode opcode,u8 idn,u8 index,u8 selector)368 static inline void ufshcd_init_query(struct ufs_hba *hba,
369 				     struct ufs_query_req **request,
370 				     struct ufs_query_res **response,
371 				     enum query_opcode opcode,
372 				     u8 idn, u8 index, u8 selector)
373 {
374 	*request = &hba->dev_cmd.query.request;
375 	*response = &hba->dev_cmd.query.response;
376 	memset(*request, 0, sizeof(struct ufs_query_req));
377 	memset(*response, 0, sizeof(struct ufs_query_res));
378 	(*request)->upiu_req.opcode = opcode;
379 	(*request)->upiu_req.idn = idn;
380 	(*request)->upiu_req.index = index;
381 	(*request)->upiu_req.selector = selector;
382 }
383 
384 /**
385  * ufshcd_query_flag() - API function for sending flag query requests
386  */
ufshcd_query_attribute(struct ufs_hba * hba,enum query_opcode opcode,enum attr_id idn,u8 index,u8 selector,u32 * value)387 static int ufshcd_query_attribute(struct ufs_hba *hba,enum query_opcode opcode,
388 				  enum attr_id idn, u8 index, u8 selector, u32 *value)
389 {
390 	struct ufs_query_req *request = &hba->dev_cmd.query.request;
391 	struct ufs_query_res *response = &hba->dev_cmd.query.response;
392 	int err;
393 	int timeout = QUERY_REQ_TIMEOUT;
394 
395 	memset(request, 0, sizeof(struct ufs_query_req));
396 	memset(response, 0, sizeof(struct ufs_query_res));
397 	request->upiu_req.opcode = opcode;
398 	request->upiu_req.idn = idn;
399 	request->upiu_req.index = 0;
400 	request->upiu_req.selector = 0;
401 
402 	switch (opcode) {
403 	case UPIU_QUERY_OPCODE_WRITE_ATTR:
404 		request->query_func = UPIU_QUERY_FUNC_STANDARD_WRITE_REQUEST;
405 		request->upiu_req.value = be32_to_cpu(*value);
406 		break;
407 	case UPIU_QUERY_OPCODE_READ_ATTR:
408 		request->query_func = UPIU_QUERY_FUNC_STANDARD_READ_REQUEST;
409 		break;
410 	default:
411 		dev_err(hba->dev,
412 			"%s: Expected query flag opcode but got = %d\n",
413 			__func__, opcode);
414 		err = -EINVAL;
415 		goto out;
416 	}
417 
418 	err = ufshcd_exec_dev_cmd(hba, DEV_CMD_TYPE_QUERY, timeout);
419 
420 	if (err) {
421 		dev_err(hba->dev,
422 			"%s: Sending flag query for idn %d failed, err = %d\n",
423 			__func__, idn, err);
424 		goto out;
425 	}
426 
427 	if (value)
428 		*value = be32_to_cpu(response->upiu_res.value);
429 
430 out:
431 	return err;
432 }
433 
ufshcd_query_attribute_retry(struct ufs_hba * hba,enum query_opcode opcode,enum attr_id idn,u8 index,u8 selector,u32 * value)434 static int ufshcd_query_attribute_retry(struct ufs_hba *hba, enum query_opcode opcode,
435 					enum attr_id idn, u8 index, u8 selector, u32 *value)
436 {
437 	int ret;
438 	int retries;
439 
440 	for (retries = 0; retries < QUERY_REQ_RETRIES; retries++) {
441 		ret = ufshcd_query_attribute(hba, opcode, idn, index, selector, value);
442 		if (ret)
443 			dev_dbg(hba->dev,
444 				"%s: failed with error %d, retries %d\n",
445 				__func__, ret, retries);
446 		else
447 			break;
448 	}
449 
450 	if (ret)
451 		dev_err(hba->dev,
452 			"%s: query attribute, opcode %d, idn %d, failed with error %d after %d retires\n",
453 			__func__, opcode, idn, ret, retries);
454 	return ret;
455 }
456 
read_attribute(struct ufs_hba * hba,enum attr_id idn,u8 index,u8 selector,u32 * value)457 static int read_attribute(struct ufs_hba *hba, enum attr_id idn, u8 index, u8 selector, u32 *value)
458 {
459 	int ret;
460 
461 	ret = ufshcd_query_attribute_retry(hba, UPIU_QUERY_OPCODE_READ_ATTR,
462 					    idn, index, 0, value);
463 	return ret;
464 }
465 
write_attribute(struct ufs_hba * hba,enum attr_id idn,u8 index,u8 selector,u32 * value)466 static int write_attribute(struct ufs_hba *hba, enum attr_id idn, u8 index, u8 selector, u32 *value)
467 {
468 	int ret;
469 
470 	ret = ufshcd_query_attribute_retry(hba, UPIU_QUERY_OPCODE_WRITE_ATTR,
471 					    idn, index, 0, value);
472 	return ret;
473 }
474 
set_boot_lu_enable(struct ufs_hba * hba)475 static int set_boot_lu_enable(struct ufs_hba *hba)
476 {
477 	uint32_t value = 0;
478 	uint32_t target_value = DEFAULT_BOOT_LUN;
479 	int ret;
480 
481 	ret = read_attribute(hba, B_BOOT_LUNEN, 0, 0, &value);
482 	if (ret) {
483 		printf("read bBootLunEn fail. ret = %d\n", ret);
484 		return ret;
485 	}
486 
487 	if (value != 0)
488 		printf("UFS get boot W-LU-%c\n", (value == WELL_BOOT_LU_A) ? 'A' : 'B');
489 
490 	if (value == target_value)
491 		return 0;
492 
493 	/* set default boot from Boot LU A */
494 	value = target_value;
495 	ret = write_attribute(hba, B_BOOT_LUNEN, 0, 0, &value);
496 	if (ret) {
497 		printf("write bBootLunEn attribute fail. ret = %d\n", ret);
498 		return ret;
499 	}
500 
501 	ret = read_attribute(hba, B_BOOT_LUNEN, 0, 0, &value);
502 	if (ret) {
503 		printf("read bBootLunEn fail. ret = %d\n", ret);
504 		return ret;
505 	}
506 
507 	if (target_value == value)
508 		return 0;
509 
510 	printf("UFS set boot W-LU(%c) Fail value = %x\n", (value == WELL_BOOT_LU_A) ? 'A' : 'B', value);
511 	return 0;
512 }
513 
ufs_set_ref_clk(struct ufs_hba * hba)514 static int ufs_set_ref_clk(struct ufs_hba *hba)
515 {
516 	uint32_t value;
517 	int ret;
518 	uint32_t target_ref_clk;
519 
520 	target_ref_clk = 1; /* 26 MHz */
521 
522 	ret = read_attribute(hba, B_REFCLK_FREQ, 0, 0, &value);
523 	if (ret) {
524 		printf("read bRefClkFreq fail. ret = %d\n", ret);
525 		return ret;
526 	}
527 
528 	printf("UFS get ref clock %d Mhz\n", (value == 1) ? 26 : 19);
529 	if (target_ref_clk == value)
530 		return 0;
531 
532 	/* set default boot from Boot LU A */
533 	ret = write_attribute(hba, B_REFCLK_FREQ, 0, 0, &target_ref_clk);
534 	if (ret) {
535 		printf("write bRefClkFreq attribute fail. ret = %d\n", ret);
536 		return ret;
537 	}
538 
539 	ret = read_attribute(hba, B_REFCLK_FREQ, 0, 0, &value);
540 	if (ret) {
541 		printf("read bRefClkFreq fail. ret = %d\n", ret);
542 		return ret;
543 	}
544 
545 	if (target_ref_clk == value)
546 		return 0;
547 
548 	printf("UFS set bRefClkFreq  26Mhz Fail\n");
549 	return -EINVAL;
550 }
551 
ufs_create_partition_inventory(struct ufs_hba * hba)552 int ufs_create_partition_inventory(struct ufs_hba *hba)
553 {
554 	int err, length;
555 
556 	length = (int)sizeof(struct ufs_geometry_descriptor);
557 	if (length > hba->desc_size.geom_desc)
558 		length = hba->desc_size.geom_desc;
559 	err = ufshcd_read_desc_param(hba, QUERY_DESC_IDN_GEOMETRY, 0, 0, (u8 *)hba->geo_desc, length);
560 	if (err) {
561 		dev_err(hba->dev, "%s: Failed reading geometry Desc. err = %d\n", __func__, err);
562 		return err;
563 	}
564 
565 	dev_err(hba->dev, "%s: WB_max_alloc_units = %x\n", __func__,
566 		hba->geo_desc->d_write_booster_buffer_max_alloc_units);
567 
568 	err = ufs_get_configuration_desc(hba, hba->rc_desc);
569 	if (err) {
570 		dev_err(hba->dev, "%s: Failed getting conf info. err = %d\n", __func__, err);
571 		return err;
572 	}
573 	ufs_info_show_conf_desc(hba->rc_desc);
574 
575 	memset(hba->wc_desc, 0, sizeof(struct ufs_configuration_descriptor));
576 	hba->wc_desc->dev_desc_conf_param.b_length = hba->rc_desc->dev_desc_conf_param.b_length;
577 	hba->wc_desc->dev_desc_conf_param.b_descriptor_idn = hba->rc_desc->dev_desc_conf_param.b_descriptor_idn;
578 	ufs_lu_configuration(hba, hba->wc_desc);
579 	ufs_info_show_conf_desc(hba->wc_desc);
580 
581 	err = compair_conf_desp(hba->wc_desc, hba->rc_desc);
582 	printf("compair_conf_desp: 0x%x\n", err);
583 
584 	if (!err)
585 		goto out;
586 
587 	err = ufs_write_configuration_desc(hba, hba->wc_desc);
588 	if (err)
589 		dev_err(hba->dev, "%s: Failed write conf info. err = %d\n", __func__, err);
590 
591 	err =  _ufs_start(hba);
592         if (err)
593                 return err;
594 out:
595 	ufs_info_show_dev_desc(hba->dev_desc);
596 
597 	ufs_set_ref_clk(hba);
598 
599         return set_boot_lu_enable(hba);
600 }
601 #endif
602