1 // SPDX-License-Identifier: GPL-2.0
2 /* Copyright(c) 2009-2012  Realtek Corporation.*/
3 
4 #include "wifi.h"
5 #include "efuse.h"
6 #include "pci.h"
7 #include <linux/export.h>
8 
9 static const u8 PGPKT_DATA_SIZE = 8;
10 static const int EFUSE_MAX_SIZE = 512;
11 
12 #define START_ADDRESS		0x1000
13 #define REG_MCUFWDL		0x0080
14 
15 static const struct rtl_efuse_ops efuse_ops = {
16 	.efuse_onebyte_read = efuse_one_byte_read,
17 	.efuse_logical_map_read = efuse_shadow_read,
18 };
19 
20 static void efuse_shadow_read_1byte(struct ieee80211_hw *hw, u16 offset,
21 				    u8 *value);
22 static void efuse_shadow_read_2byte(struct ieee80211_hw *hw, u16 offset,
23 				    u16 *value);
24 static void efuse_shadow_read_4byte(struct ieee80211_hw *hw, u16 offset,
25 				    u32 *value);
26 static void efuse_shadow_write_1byte(struct ieee80211_hw *hw, u16 offset,
27 				     u8 value);
28 static void efuse_shadow_write_2byte(struct ieee80211_hw *hw, u16 offset,
29 				     u16 value);
30 static void efuse_shadow_write_4byte(struct ieee80211_hw *hw, u16 offset,
31 				     u32 value);
32 static int efuse_one_byte_write(struct ieee80211_hw *hw, u16 addr,
33 				u8 data);
34 static void efuse_read_all_map(struct ieee80211_hw *hw, u8 *efuse);
35 static int efuse_pg_packet_read(struct ieee80211_hw *hw, u8 offset,
36 				u8 *data);
37 static int efuse_pg_packet_write(struct ieee80211_hw *hw, u8 offset,
38 				 u8 word_en, u8 *data);
39 static void efuse_word_enable_data_read(u8 word_en, u8 *sourdata,
40 					u8 *targetdata);
41 static u8 enable_efuse_data_write(struct ieee80211_hw *hw,
42 				  u16 efuse_addr, u8 word_en, u8 *data);
43 static u16 efuse_get_current_size(struct ieee80211_hw *hw);
44 static u8 efuse_calculate_word_cnts(u8 word_en);
45 
efuse_initialize(struct ieee80211_hw * hw)46 void efuse_initialize(struct ieee80211_hw *hw)
47 {
48 	struct rtl_priv *rtlpriv = rtl_priv(hw);
49 	u8 bytetemp;
50 	u8 temp;
51 
52 	bytetemp = rtl_read_byte(rtlpriv, rtlpriv->cfg->maps[SYS_FUNC_EN] + 1);
53 	temp = bytetemp | 0x20;
54 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[SYS_FUNC_EN] + 1, temp);
55 
56 	bytetemp = rtl_read_byte(rtlpriv, rtlpriv->cfg->maps[SYS_ISO_CTRL] + 1);
57 	temp = bytetemp & 0xFE;
58 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[SYS_ISO_CTRL] + 1, temp);
59 
60 	bytetemp = rtl_read_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_TEST] + 3);
61 	temp = bytetemp | 0x80;
62 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_TEST] + 3, temp);
63 
64 	rtl_write_byte(rtlpriv, 0x2F8, 0x3);
65 
66 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 3, 0x72);
67 
68 }
69 
efuse_read_1byte(struct ieee80211_hw * hw,u16 address)70 u8 efuse_read_1byte(struct ieee80211_hw *hw, u16 address)
71 {
72 	struct rtl_priv *rtlpriv = rtl_priv(hw);
73 	u8 data;
74 	u8 bytetemp;
75 	u8 temp;
76 	u32 k = 0;
77 	const u32 efuse_len =
78 		rtlpriv->cfg->maps[EFUSE_REAL_CONTENT_SIZE];
79 
80 	if (address < efuse_len) {
81 		temp = address & 0xFF;
82 		rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 1,
83 			       temp);
84 		bytetemp = rtl_read_byte(rtlpriv,
85 					 rtlpriv->cfg->maps[EFUSE_CTRL] + 2);
86 		temp = ((address >> 8) & 0x03) | (bytetemp & 0xFC);
87 		rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 2,
88 			       temp);
89 
90 		bytetemp = rtl_read_byte(rtlpriv,
91 					 rtlpriv->cfg->maps[EFUSE_CTRL] + 3);
92 		temp = bytetemp & 0x7F;
93 		rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 3,
94 			       temp);
95 
96 		bytetemp = rtl_read_byte(rtlpriv,
97 					 rtlpriv->cfg->maps[EFUSE_CTRL] + 3);
98 		while (!(bytetemp & 0x80)) {
99 			bytetemp = rtl_read_byte(rtlpriv,
100 						 rtlpriv->cfg->
101 						 maps[EFUSE_CTRL] + 3);
102 			k++;
103 			if (k == 1000)
104 				break;
105 		}
106 		data = rtl_read_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL]);
107 		return data;
108 	} else
109 		return 0xFF;
110 
111 }
112 EXPORT_SYMBOL(efuse_read_1byte);
113 
efuse_write_1byte(struct ieee80211_hw * hw,u16 address,u8 value)114 void efuse_write_1byte(struct ieee80211_hw *hw, u16 address, u8 value)
115 {
116 	struct rtl_priv *rtlpriv = rtl_priv(hw);
117 	u8 bytetemp;
118 	u8 temp;
119 	u32 k = 0;
120 	const u32 efuse_len =
121 		rtlpriv->cfg->maps[EFUSE_REAL_CONTENT_SIZE];
122 
123 	rtl_dbg(rtlpriv, COMP_EFUSE, DBG_LOUD, "Addr=%x Data =%x\n",
124 		address, value);
125 
126 	if (address < efuse_len) {
127 		rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL], value);
128 
129 		temp = address & 0xFF;
130 		rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 1,
131 			       temp);
132 		bytetemp = rtl_read_byte(rtlpriv,
133 					 rtlpriv->cfg->maps[EFUSE_CTRL] + 2);
134 
135 		temp = ((address >> 8) & 0x03) | (bytetemp & 0xFC);
136 		rtl_write_byte(rtlpriv,
137 			       rtlpriv->cfg->maps[EFUSE_CTRL] + 2, temp);
138 
139 		bytetemp = rtl_read_byte(rtlpriv,
140 					 rtlpriv->cfg->maps[EFUSE_CTRL] + 3);
141 		temp = bytetemp | 0x80;
142 		rtl_write_byte(rtlpriv,
143 			       rtlpriv->cfg->maps[EFUSE_CTRL] + 3, temp);
144 
145 		bytetemp = rtl_read_byte(rtlpriv,
146 					 rtlpriv->cfg->maps[EFUSE_CTRL] + 3);
147 
148 		while (bytetemp & 0x80) {
149 			bytetemp = rtl_read_byte(rtlpriv,
150 						 rtlpriv->cfg->
151 						 maps[EFUSE_CTRL] + 3);
152 			k++;
153 			if (k == 100) {
154 				k = 0;
155 				break;
156 			}
157 		}
158 	}
159 
160 }
161 
read_efuse_byte(struct ieee80211_hw * hw,u16 _offset,u8 * pbuf)162 void read_efuse_byte(struct ieee80211_hw *hw, u16 _offset, u8 *pbuf)
163 {
164 	struct rtl_priv *rtlpriv = rtl_priv(hw);
165 	u32 value32;
166 	u8 readbyte;
167 	u16 retry;
168 
169 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 1,
170 		       (_offset & 0xff));
171 	readbyte = rtl_read_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 2);
172 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 2,
173 		       ((_offset >> 8) & 0x03) | (readbyte & 0xfc));
174 
175 	readbyte = rtl_read_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 3);
176 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 3,
177 		       (readbyte & 0x7f));
178 
179 	retry = 0;
180 	value32 = rtl_read_dword(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL]);
181 	while (!(((value32 >> 24) & 0xff) & 0x80) && (retry < 10000)) {
182 		value32 = rtl_read_dword(rtlpriv,
183 					 rtlpriv->cfg->maps[EFUSE_CTRL]);
184 		retry++;
185 	}
186 
187 	udelay(50);
188 	value32 = rtl_read_dword(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL]);
189 
190 	*pbuf = (u8) (value32 & 0xff);
191 }
192 EXPORT_SYMBOL_GPL(read_efuse_byte);
193 
read_efuse(struct ieee80211_hw * hw,u16 _offset,u16 _size_byte,u8 * pbuf)194 void read_efuse(struct ieee80211_hw *hw, u16 _offset, u16 _size_byte, u8 *pbuf)
195 {
196 	struct rtl_priv *rtlpriv = rtl_priv(hw);
197 	struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
198 	u8 *efuse_tbl;
199 	u8 rtemp8[1];
200 	u16 efuse_addr = 0;
201 	u8 offset, wren;
202 	u8 u1temp = 0;
203 	u16 i;
204 	u16 j;
205 	const u16 efuse_max_section =
206 		rtlpriv->cfg->maps[EFUSE_MAX_SECTION_MAP];
207 	const u32 efuse_len =
208 		rtlpriv->cfg->maps[EFUSE_REAL_CONTENT_SIZE];
209 	u16 **efuse_word;
210 	u16 efuse_utilized = 0;
211 	u8 efuse_usage;
212 
213 	if ((_offset + _size_byte) > rtlpriv->cfg->maps[EFUSE_HWSET_MAX_SIZE]) {
214 		rtl_dbg(rtlpriv, COMP_EFUSE, DBG_LOUD,
215 			"%s: Invalid offset(%#x) with read bytes(%#x)!!\n",
216 			__func__, _offset, _size_byte);
217 		return;
218 	}
219 
220 	/* allocate memory for efuse_tbl and efuse_word */
221 	efuse_tbl = kzalloc(rtlpriv->cfg->maps[EFUSE_HWSET_MAX_SIZE],
222 			    GFP_ATOMIC);
223 	if (!efuse_tbl)
224 		return;
225 	efuse_word = kcalloc(EFUSE_MAX_WORD_UNIT, sizeof(u16 *), GFP_ATOMIC);
226 	if (!efuse_word)
227 		goto out;
228 	for (i = 0; i < EFUSE_MAX_WORD_UNIT; i++) {
229 		efuse_word[i] = kcalloc(efuse_max_section, sizeof(u16),
230 					GFP_ATOMIC);
231 		if (!efuse_word[i])
232 			goto done;
233 	}
234 
235 	for (i = 0; i < efuse_max_section; i++)
236 		for (j = 0; j < EFUSE_MAX_WORD_UNIT; j++)
237 			efuse_word[j][i] = 0xFFFF;
238 
239 	read_efuse_byte(hw, efuse_addr, rtemp8);
240 	if (*rtemp8 != 0xFF) {
241 		efuse_utilized++;
242 		RTPRINT(rtlpriv, FEEPROM, EFUSE_READ_ALL,
243 			"Addr=%d\n", efuse_addr);
244 		efuse_addr++;
245 	}
246 
247 	while ((*rtemp8 != 0xFF) && (efuse_addr < efuse_len)) {
248 		/*  Check PG header for section num.  */
249 		if ((*rtemp8 & 0x1F) == 0x0F) {/* extended header */
250 			u1temp = ((*rtemp8 & 0xE0) >> 5);
251 			read_efuse_byte(hw, efuse_addr, rtemp8);
252 
253 			if ((*rtemp8 & 0x0F) == 0x0F) {
254 				efuse_addr++;
255 				read_efuse_byte(hw, efuse_addr, rtemp8);
256 
257 				if (*rtemp8 != 0xFF &&
258 				    (efuse_addr < efuse_len)) {
259 					efuse_addr++;
260 				}
261 				continue;
262 			} else {
263 				offset = ((*rtemp8 & 0xF0) >> 1) | u1temp;
264 				wren = (*rtemp8 & 0x0F);
265 				efuse_addr++;
266 			}
267 		} else {
268 			offset = ((*rtemp8 >> 4) & 0x0f);
269 			wren = (*rtemp8 & 0x0f);
270 		}
271 
272 		if (offset < efuse_max_section) {
273 			RTPRINT(rtlpriv, FEEPROM, EFUSE_READ_ALL,
274 				"offset-%d Worden=%x\n", offset, wren);
275 
276 			for (i = 0; i < EFUSE_MAX_WORD_UNIT; i++) {
277 				if (!(wren & 0x01)) {
278 					RTPRINT(rtlpriv, FEEPROM,
279 						EFUSE_READ_ALL,
280 						"Addr=%d\n", efuse_addr);
281 
282 					read_efuse_byte(hw, efuse_addr, rtemp8);
283 					efuse_addr++;
284 					efuse_utilized++;
285 					efuse_word[i][offset] =
286 							 (*rtemp8 & 0xff);
287 
288 					if (efuse_addr >= efuse_len)
289 						break;
290 
291 					RTPRINT(rtlpriv, FEEPROM,
292 						EFUSE_READ_ALL,
293 						"Addr=%d\n", efuse_addr);
294 
295 					read_efuse_byte(hw, efuse_addr, rtemp8);
296 					efuse_addr++;
297 					efuse_utilized++;
298 					efuse_word[i][offset] |=
299 					    (((u16)*rtemp8 << 8) & 0xff00);
300 
301 					if (efuse_addr >= efuse_len)
302 						break;
303 				}
304 
305 				wren >>= 1;
306 			}
307 		}
308 
309 		RTPRINT(rtlpriv, FEEPROM, EFUSE_READ_ALL,
310 			"Addr=%d\n", efuse_addr);
311 		read_efuse_byte(hw, efuse_addr, rtemp8);
312 		if (*rtemp8 != 0xFF && (efuse_addr < efuse_len)) {
313 			efuse_utilized++;
314 			efuse_addr++;
315 		}
316 	}
317 
318 	for (i = 0; i < efuse_max_section; i++) {
319 		for (j = 0; j < EFUSE_MAX_WORD_UNIT; j++) {
320 			efuse_tbl[(i * 8) + (j * 2)] =
321 			    (efuse_word[j][i] & 0xff);
322 			efuse_tbl[(i * 8) + ((j * 2) + 1)] =
323 			    ((efuse_word[j][i] >> 8) & 0xff);
324 		}
325 	}
326 
327 	for (i = 0; i < _size_byte; i++)
328 		pbuf[i] = efuse_tbl[_offset + i];
329 
330 	rtlefuse->efuse_usedbytes = efuse_utilized;
331 	efuse_usage = (u8) ((efuse_utilized * 100) / efuse_len);
332 	rtlefuse->efuse_usedpercentage = efuse_usage;
333 	rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_EFUSE_BYTES,
334 				      (u8 *)&efuse_utilized);
335 	rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_EFUSE_USAGE,
336 				      &efuse_usage);
337 done:
338 	for (i = 0; i < EFUSE_MAX_WORD_UNIT; i++)
339 		kfree(efuse_word[i]);
340 	kfree(efuse_word);
341 out:
342 	kfree(efuse_tbl);
343 }
344 
efuse_shadow_update_chk(struct ieee80211_hw * hw)345 bool efuse_shadow_update_chk(struct ieee80211_hw *hw)
346 {
347 	struct rtl_priv *rtlpriv = rtl_priv(hw);
348 	struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
349 	u8 section_idx, i, base;
350 	u16 words_need = 0, hdr_num = 0, totalbytes, efuse_used;
351 	bool wordchanged, result = true;
352 
353 	for (section_idx = 0; section_idx < 16; section_idx++) {
354 		base = section_idx * 8;
355 		wordchanged = false;
356 
357 		for (i = 0; i < 8; i = i + 2) {
358 			if (rtlefuse->efuse_map[EFUSE_INIT_MAP][base + i] !=
359 			    rtlefuse->efuse_map[EFUSE_MODIFY_MAP][base + i] ||
360 			    rtlefuse->efuse_map[EFUSE_INIT_MAP][base + i + 1] !=
361 			    rtlefuse->efuse_map[EFUSE_MODIFY_MAP][base + i +
362 								   1]) {
363 				words_need++;
364 				wordchanged = true;
365 			}
366 		}
367 
368 		if (wordchanged)
369 			hdr_num++;
370 	}
371 
372 	totalbytes = hdr_num + words_need * 2;
373 	efuse_used = rtlefuse->efuse_usedbytes;
374 
375 	if ((totalbytes + efuse_used) >=
376 	    (EFUSE_MAX_SIZE - rtlpriv->cfg->maps[EFUSE_OOB_PROTECT_BYTES_LEN]))
377 		result = false;
378 
379 	rtl_dbg(rtlpriv, COMP_EFUSE, DBG_LOUD,
380 		"%s: totalbytes(%#x), hdr_num(%#x), words_need(%#x), efuse_used(%d)\n",
381 		__func__, totalbytes, hdr_num, words_need, efuse_used);
382 
383 	return result;
384 }
385 
efuse_shadow_read(struct ieee80211_hw * hw,u8 type,u16 offset,u32 * value)386 void efuse_shadow_read(struct ieee80211_hw *hw, u8 type,
387 		       u16 offset, u32 *value)
388 {
389 	if (type == 1)
390 		efuse_shadow_read_1byte(hw, offset, (u8 *)value);
391 	else if (type == 2)
392 		efuse_shadow_read_2byte(hw, offset, (u16 *)value);
393 	else if (type == 4)
394 		efuse_shadow_read_4byte(hw, offset, value);
395 
396 }
397 EXPORT_SYMBOL(efuse_shadow_read);
398 
efuse_shadow_write(struct ieee80211_hw * hw,u8 type,u16 offset,u32 value)399 void efuse_shadow_write(struct ieee80211_hw *hw, u8 type, u16 offset,
400 				u32 value)
401 {
402 	if (type == 1)
403 		efuse_shadow_write_1byte(hw, offset, (u8) value);
404 	else if (type == 2)
405 		efuse_shadow_write_2byte(hw, offset, (u16) value);
406 	else if (type == 4)
407 		efuse_shadow_write_4byte(hw, offset, value);
408 
409 }
410 
efuse_shadow_update(struct ieee80211_hw * hw)411 bool efuse_shadow_update(struct ieee80211_hw *hw)
412 {
413 	struct rtl_priv *rtlpriv = rtl_priv(hw);
414 	struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
415 	u16 i, offset, base;
416 	u8 word_en = 0x0F;
417 	u8 first_pg = false;
418 
419 	rtl_dbg(rtlpriv, COMP_EFUSE, DBG_LOUD, "\n");
420 
421 	if (!efuse_shadow_update_chk(hw)) {
422 		efuse_read_all_map(hw, &rtlefuse->efuse_map[EFUSE_INIT_MAP][0]);
423 		memcpy(&rtlefuse->efuse_map[EFUSE_MODIFY_MAP][0],
424 		       &rtlefuse->efuse_map[EFUSE_INIT_MAP][0],
425 		       rtlpriv->cfg->maps[EFUSE_HWSET_MAX_SIZE]);
426 
427 		rtl_dbg(rtlpriv, COMP_EFUSE, DBG_LOUD,
428 			"efuse out of capacity!!\n");
429 		return false;
430 	}
431 	efuse_power_switch(hw, true, true);
432 
433 	for (offset = 0; offset < 16; offset++) {
434 
435 		word_en = 0x0F;
436 		base = offset * 8;
437 
438 		for (i = 0; i < 8; i++) {
439 			if (first_pg) {
440 				word_en &= ~(BIT(i / 2));
441 
442 				rtlefuse->efuse_map[EFUSE_INIT_MAP][base + i] =
443 				    rtlefuse->efuse_map[EFUSE_MODIFY_MAP][base + i];
444 			} else {
445 
446 				if (rtlefuse->efuse_map[EFUSE_INIT_MAP][base + i] !=
447 				    rtlefuse->efuse_map[EFUSE_MODIFY_MAP][base + i]) {
448 					word_en &= ~(BIT(i / 2));
449 
450 					rtlefuse->efuse_map[EFUSE_INIT_MAP][base + i] =
451 					    rtlefuse->efuse_map[EFUSE_MODIFY_MAP][base + i];
452 				}
453 			}
454 		}
455 
456 		if (word_en != 0x0F) {
457 			u8 tmpdata[8];
458 
459 			memcpy(tmpdata,
460 			       &rtlefuse->efuse_map[EFUSE_MODIFY_MAP][base],
461 			       8);
462 			RT_PRINT_DATA(rtlpriv, COMP_INIT, DBG_LOUD,
463 				      "U-efuse\n", tmpdata, 8);
464 
465 			if (!efuse_pg_packet_write(hw, (u8) offset, word_en,
466 						   tmpdata)) {
467 				rtl_dbg(rtlpriv, COMP_ERR, DBG_WARNING,
468 					"PG section(%#x) fail!!\n", offset);
469 				break;
470 			}
471 		}
472 	}
473 
474 	efuse_power_switch(hw, true, false);
475 	efuse_read_all_map(hw, &rtlefuse->efuse_map[EFUSE_INIT_MAP][0]);
476 
477 	memcpy(&rtlefuse->efuse_map[EFUSE_MODIFY_MAP][0],
478 	       &rtlefuse->efuse_map[EFUSE_INIT_MAP][0],
479 	       rtlpriv->cfg->maps[EFUSE_HWSET_MAX_SIZE]);
480 
481 	rtl_dbg(rtlpriv, COMP_EFUSE, DBG_LOUD, "\n");
482 	return true;
483 }
484 
rtl_efuse_shadow_map_update(struct ieee80211_hw * hw)485 void rtl_efuse_shadow_map_update(struct ieee80211_hw *hw)
486 {
487 	struct rtl_priv *rtlpriv = rtl_priv(hw);
488 	struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
489 
490 	if (rtlefuse->autoload_failflag)
491 		memset((&rtlefuse->efuse_map[EFUSE_INIT_MAP][0]),
492 		       0xFF, rtlpriv->cfg->maps[EFUSE_HWSET_MAX_SIZE]);
493 	else
494 		efuse_read_all_map(hw, &rtlefuse->efuse_map[EFUSE_INIT_MAP][0]);
495 
496 	memcpy(&rtlefuse->efuse_map[EFUSE_MODIFY_MAP][0],
497 			&rtlefuse->efuse_map[EFUSE_INIT_MAP][0],
498 			rtlpriv->cfg->maps[EFUSE_HWSET_MAX_SIZE]);
499 
500 }
501 EXPORT_SYMBOL(rtl_efuse_shadow_map_update);
502 
efuse_force_write_vendor_id(struct ieee80211_hw * hw)503 void efuse_force_write_vendor_id(struct ieee80211_hw *hw)
504 {
505 	u8 tmpdata[8] = { 0xFF, 0xFF, 0xEC, 0x10, 0xFF, 0xFF, 0xFF, 0xFF };
506 
507 	efuse_power_switch(hw, true, true);
508 
509 	efuse_pg_packet_write(hw, 1, 0xD, tmpdata);
510 
511 	efuse_power_switch(hw, true, false);
512 
513 }
514 
efuse_re_pg_section(struct ieee80211_hw * hw,u8 section_idx)515 void efuse_re_pg_section(struct ieee80211_hw *hw, u8 section_idx)
516 {
517 }
518 
efuse_shadow_read_1byte(struct ieee80211_hw * hw,u16 offset,u8 * value)519 static void efuse_shadow_read_1byte(struct ieee80211_hw *hw,
520 				    u16 offset, u8 *value)
521 {
522 	struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
523 	*value = rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset];
524 }
525 
efuse_shadow_read_2byte(struct ieee80211_hw * hw,u16 offset,u16 * value)526 static void efuse_shadow_read_2byte(struct ieee80211_hw *hw,
527 				    u16 offset, u16 *value)
528 {
529 	struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
530 
531 	*value = rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset];
532 	*value |= rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset + 1] << 8;
533 
534 }
535 
efuse_shadow_read_4byte(struct ieee80211_hw * hw,u16 offset,u32 * value)536 static void efuse_shadow_read_4byte(struct ieee80211_hw *hw,
537 				    u16 offset, u32 *value)
538 {
539 	struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
540 
541 	*value = rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset];
542 	*value |= rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset + 1] << 8;
543 	*value |= rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset + 2] << 16;
544 	*value |= rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset + 3] << 24;
545 }
546 
efuse_shadow_write_1byte(struct ieee80211_hw * hw,u16 offset,u8 value)547 static void efuse_shadow_write_1byte(struct ieee80211_hw *hw,
548 				     u16 offset, u8 value)
549 {
550 	struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
551 
552 	rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset] = value;
553 }
554 
efuse_shadow_write_2byte(struct ieee80211_hw * hw,u16 offset,u16 value)555 static void efuse_shadow_write_2byte(struct ieee80211_hw *hw,
556 				     u16 offset, u16 value)
557 {
558 	struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
559 
560 	rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset] = value & 0x00FF;
561 	rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset + 1] = value >> 8;
562 
563 }
564 
efuse_shadow_write_4byte(struct ieee80211_hw * hw,u16 offset,u32 value)565 static void efuse_shadow_write_4byte(struct ieee80211_hw *hw,
566 				     u16 offset, u32 value)
567 {
568 	struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
569 
570 	rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset] =
571 	    (u8) (value & 0x000000FF);
572 	rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset + 1] =
573 	    (u8) ((value >> 8) & 0x0000FF);
574 	rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset + 2] =
575 	    (u8) ((value >> 16) & 0x00FF);
576 	rtlefuse->efuse_map[EFUSE_MODIFY_MAP][offset + 3] =
577 	    (u8) ((value >> 24) & 0xFF);
578 
579 }
580 
efuse_one_byte_read(struct ieee80211_hw * hw,u16 addr,u8 * data)581 int efuse_one_byte_read(struct ieee80211_hw *hw, u16 addr, u8 *data)
582 {
583 	struct rtl_priv *rtlpriv = rtl_priv(hw);
584 	u8 tmpidx = 0;
585 	int result;
586 
587 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 1,
588 		       (u8) (addr & 0xff));
589 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 2,
590 		       ((u8) ((addr >> 8) & 0x03)) |
591 		       (rtl_read_byte(rtlpriv,
592 				      rtlpriv->cfg->maps[EFUSE_CTRL] + 2) &
593 			0xFC));
594 
595 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 3, 0x72);
596 
597 	while (!(0x80 & rtl_read_byte(rtlpriv,
598 				      rtlpriv->cfg->maps[EFUSE_CTRL] + 3))
599 	       && (tmpidx < 100)) {
600 		tmpidx++;
601 	}
602 
603 	if (tmpidx < 100) {
604 		*data = rtl_read_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL]);
605 		result = true;
606 	} else {
607 		*data = 0xff;
608 		result = false;
609 	}
610 	return result;
611 }
612 EXPORT_SYMBOL(efuse_one_byte_read);
613 
efuse_one_byte_write(struct ieee80211_hw * hw,u16 addr,u8 data)614 static int efuse_one_byte_write(struct ieee80211_hw *hw, u16 addr, u8 data)
615 {
616 	struct rtl_priv *rtlpriv = rtl_priv(hw);
617 	u8 tmpidx = 0;
618 
619 	rtl_dbg(rtlpriv, COMP_EFUSE, DBG_LOUD,
620 		"Addr = %x Data=%x\n", addr, data);
621 
622 	rtl_write_byte(rtlpriv,
623 		       rtlpriv->cfg->maps[EFUSE_CTRL] + 1, (u8) (addr & 0xff));
624 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 2,
625 		       (rtl_read_byte(rtlpriv,
626 			 rtlpriv->cfg->maps[EFUSE_CTRL] +
627 			 2) & 0xFC) | (u8) ((addr >> 8) & 0x03));
628 
629 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL], data);
630 	rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL] + 3, 0xF2);
631 
632 	while ((0x80 & rtl_read_byte(rtlpriv,
633 				     rtlpriv->cfg->maps[EFUSE_CTRL] + 3))
634 	       && (tmpidx < 100)) {
635 		tmpidx++;
636 	}
637 
638 	if (tmpidx < 100)
639 		return true;
640 	return false;
641 }
642 
efuse_read_all_map(struct ieee80211_hw * hw,u8 * efuse)643 static void efuse_read_all_map(struct ieee80211_hw *hw, u8 *efuse)
644 {
645 	struct rtl_priv *rtlpriv = rtl_priv(hw);
646 
647 	efuse_power_switch(hw, false, true);
648 	read_efuse(hw, 0, rtlpriv->cfg->maps[EFUSE_HWSET_MAX_SIZE], efuse);
649 	efuse_power_switch(hw, false, false);
650 }
651 
efuse_read_data_case1(struct ieee80211_hw * hw,u16 * efuse_addr,u8 efuse_data,u8 offset,u8 * tmpdata,u8 * readstate)652 static void efuse_read_data_case1(struct ieee80211_hw *hw, u16 *efuse_addr,
653 				u8 efuse_data, u8 offset, u8 *tmpdata,
654 				u8 *readstate)
655 {
656 	bool dataempty = true;
657 	u8 hoffset;
658 	u8 tmpidx;
659 	u8 hworden;
660 	u8 word_cnts;
661 
662 	hoffset = (efuse_data >> 4) & 0x0F;
663 	hworden = efuse_data & 0x0F;
664 	word_cnts = efuse_calculate_word_cnts(hworden);
665 
666 	if (hoffset == offset) {
667 		for (tmpidx = 0; tmpidx < word_cnts * 2; tmpidx++) {
668 			if (efuse_one_byte_read(hw, *efuse_addr + 1 + tmpidx,
669 						&efuse_data)) {
670 				tmpdata[tmpidx] = efuse_data;
671 				if (efuse_data != 0xff)
672 					dataempty = false;
673 			}
674 		}
675 
676 		if (!dataempty) {
677 			*readstate = PG_STATE_DATA;
678 		} else {
679 			*efuse_addr = *efuse_addr + (word_cnts * 2) + 1;
680 			*readstate = PG_STATE_HEADER;
681 		}
682 
683 	} else {
684 		*efuse_addr = *efuse_addr + (word_cnts * 2) + 1;
685 		*readstate = PG_STATE_HEADER;
686 	}
687 }
688 
efuse_pg_packet_read(struct ieee80211_hw * hw,u8 offset,u8 * data)689 static int efuse_pg_packet_read(struct ieee80211_hw *hw, u8 offset, u8 *data)
690 {
691 	u8 readstate = PG_STATE_HEADER;
692 
693 	bool continual = true;
694 
695 	u8 efuse_data, word_cnts = 0;
696 	u16 efuse_addr = 0;
697 	u8 tmpdata[8];
698 
699 	if (data == NULL)
700 		return false;
701 	if (offset > 15)
702 		return false;
703 
704 	memset(data, 0xff, PGPKT_DATA_SIZE * sizeof(u8));
705 	memset(tmpdata, 0xff, PGPKT_DATA_SIZE * sizeof(u8));
706 
707 	while (continual && (efuse_addr < EFUSE_MAX_SIZE)) {
708 		if (readstate & PG_STATE_HEADER) {
709 			if (efuse_one_byte_read(hw, efuse_addr, &efuse_data)
710 			    && (efuse_data != 0xFF))
711 				efuse_read_data_case1(hw, &efuse_addr,
712 						      efuse_data, offset,
713 						      tmpdata, &readstate);
714 			else
715 				continual = false;
716 		} else if (readstate & PG_STATE_DATA) {
717 			efuse_word_enable_data_read(0, tmpdata, data);
718 			efuse_addr = efuse_addr + (word_cnts * 2) + 1;
719 			readstate = PG_STATE_HEADER;
720 		}
721 
722 	}
723 
724 	if ((data[0] == 0xff) && (data[1] == 0xff) &&
725 	    (data[2] == 0xff) && (data[3] == 0xff) &&
726 	    (data[4] == 0xff) && (data[5] == 0xff) &&
727 	    (data[6] == 0xff) && (data[7] == 0xff))
728 		return false;
729 	else
730 		return true;
731 
732 }
733 
efuse_write_data_case1(struct ieee80211_hw * hw,u16 * efuse_addr,u8 efuse_data,u8 offset,int * continual,u8 * write_state,struct pgpkt_struct * target_pkt,int * repeat_times,int * result,u8 word_en)734 static void efuse_write_data_case1(struct ieee80211_hw *hw, u16 *efuse_addr,
735 				   u8 efuse_data, u8 offset,
736 				   int *continual, u8 *write_state,
737 				   struct pgpkt_struct *target_pkt,
738 				   int *repeat_times, int *result, u8 word_en)
739 {
740 	struct rtl_priv *rtlpriv = rtl_priv(hw);
741 	struct pgpkt_struct tmp_pkt;
742 	int dataempty = true;
743 	u8 originaldata[8 * sizeof(u8)];
744 	u8 badworden = 0x0F;
745 	u8 match_word_en, tmp_word_en;
746 	u8 tmpindex;
747 	u8 tmp_header = efuse_data;
748 	u8 tmp_word_cnts;
749 
750 	tmp_pkt.offset = (tmp_header >> 4) & 0x0F;
751 	tmp_pkt.word_en = tmp_header & 0x0F;
752 	tmp_word_cnts = efuse_calculate_word_cnts(tmp_pkt.word_en);
753 
754 	if (tmp_pkt.offset != target_pkt->offset) {
755 		*efuse_addr = *efuse_addr + (tmp_word_cnts * 2) + 1;
756 		*write_state = PG_STATE_HEADER;
757 	} else {
758 		for (tmpindex = 0; tmpindex < (tmp_word_cnts * 2); tmpindex++) {
759 			if (efuse_one_byte_read(hw,
760 						(*efuse_addr + 1 + tmpindex),
761 						&efuse_data) &&
762 			    (efuse_data != 0xFF))
763 				dataempty = false;
764 		}
765 
766 		if (!dataempty) {
767 			*efuse_addr = *efuse_addr + (tmp_word_cnts * 2) + 1;
768 			*write_state = PG_STATE_HEADER;
769 		} else {
770 			match_word_en = 0x0F;
771 			if (!((target_pkt->word_en & BIT(0)) |
772 			    (tmp_pkt.word_en & BIT(0))))
773 				match_word_en &= (~BIT(0));
774 
775 			if (!((target_pkt->word_en & BIT(1)) |
776 			    (tmp_pkt.word_en & BIT(1))))
777 				match_word_en &= (~BIT(1));
778 
779 			if (!((target_pkt->word_en & BIT(2)) |
780 			    (tmp_pkt.word_en & BIT(2))))
781 				match_word_en &= (~BIT(2));
782 
783 			if (!((target_pkt->word_en & BIT(3)) |
784 			    (tmp_pkt.word_en & BIT(3))))
785 				match_word_en &= (~BIT(3));
786 
787 			if ((match_word_en & 0x0F) != 0x0F) {
788 				badworden =
789 				  enable_efuse_data_write(hw,
790 							  *efuse_addr + 1,
791 							  tmp_pkt.word_en,
792 							  target_pkt->data);
793 
794 				if (0x0F != (badworden & 0x0F))	{
795 					u8 reorg_offset = offset;
796 					u8 reorg_worden = badworden;
797 
798 					efuse_pg_packet_write(hw, reorg_offset,
799 							      reorg_worden,
800 							      originaldata);
801 				}
802 
803 				tmp_word_en = 0x0F;
804 				if ((target_pkt->word_en & BIT(0)) ^
805 				    (match_word_en & BIT(0)))
806 					tmp_word_en &= (~BIT(0));
807 
808 				if ((target_pkt->word_en & BIT(1)) ^
809 				    (match_word_en & BIT(1)))
810 					tmp_word_en &= (~BIT(1));
811 
812 				if ((target_pkt->word_en & BIT(2)) ^
813 				    (match_word_en & BIT(2)))
814 					tmp_word_en &= (~BIT(2));
815 
816 				if ((target_pkt->word_en & BIT(3)) ^
817 				    (match_word_en & BIT(3)))
818 					tmp_word_en &= (~BIT(3));
819 
820 				if ((tmp_word_en & 0x0F) != 0x0F) {
821 					*efuse_addr = efuse_get_current_size(hw);
822 					target_pkt->offset = offset;
823 					target_pkt->word_en = tmp_word_en;
824 				} else {
825 					*continual = false;
826 				}
827 				*write_state = PG_STATE_HEADER;
828 				*repeat_times += 1;
829 				if (*repeat_times > EFUSE_REPEAT_THRESHOLD_) {
830 					*continual = false;
831 					*result = false;
832 				}
833 			} else {
834 				*efuse_addr += (2 * tmp_word_cnts) + 1;
835 				target_pkt->offset = offset;
836 				target_pkt->word_en = word_en;
837 				*write_state = PG_STATE_HEADER;
838 			}
839 		}
840 	}
841 	RTPRINT(rtlpriv, FEEPROM, EFUSE_PG, "efuse PG_STATE_HEADER-1\n");
842 }
843 
efuse_write_data_case2(struct ieee80211_hw * hw,u16 * efuse_addr,int * continual,u8 * write_state,struct pgpkt_struct target_pkt,int * repeat_times,int * result)844 static void efuse_write_data_case2(struct ieee80211_hw *hw, u16 *efuse_addr,
845 				   int *continual, u8 *write_state,
846 				   struct pgpkt_struct target_pkt,
847 				   int *repeat_times, int *result)
848 {
849 	struct rtl_priv *rtlpriv = rtl_priv(hw);
850 	struct pgpkt_struct tmp_pkt;
851 	u8 pg_header;
852 	u8 tmp_header;
853 	u8 originaldata[8 * sizeof(u8)];
854 	u8 tmp_word_cnts;
855 	u8 badworden = 0x0F;
856 
857 	pg_header = ((target_pkt.offset << 4) & 0xf0) | target_pkt.word_en;
858 	efuse_one_byte_write(hw, *efuse_addr, pg_header);
859 	efuse_one_byte_read(hw, *efuse_addr, &tmp_header);
860 
861 	if (tmp_header == pg_header) {
862 		*write_state = PG_STATE_DATA;
863 	} else if (tmp_header == 0xFF) {
864 		*write_state = PG_STATE_HEADER;
865 		*repeat_times += 1;
866 		if (*repeat_times > EFUSE_REPEAT_THRESHOLD_) {
867 			*continual = false;
868 			*result = false;
869 		}
870 	} else {
871 		tmp_pkt.offset = (tmp_header >> 4) & 0x0F;
872 		tmp_pkt.word_en = tmp_header & 0x0F;
873 
874 		tmp_word_cnts = efuse_calculate_word_cnts(tmp_pkt.word_en);
875 
876 		memset(originaldata, 0xff,  8 * sizeof(u8));
877 
878 		if (efuse_pg_packet_read(hw, tmp_pkt.offset, originaldata)) {
879 			badworden = enable_efuse_data_write(hw,
880 							    *efuse_addr + 1,
881 							    tmp_pkt.word_en,
882 							    originaldata);
883 
884 			if (0x0F != (badworden & 0x0F)) {
885 				u8 reorg_offset = tmp_pkt.offset;
886 				u8 reorg_worden = badworden;
887 
888 				efuse_pg_packet_write(hw, reorg_offset,
889 						      reorg_worden,
890 						      originaldata);
891 				*efuse_addr = efuse_get_current_size(hw);
892 			} else {
893 				*efuse_addr = *efuse_addr +
894 					      (tmp_word_cnts * 2) + 1;
895 			}
896 		} else {
897 			*efuse_addr = *efuse_addr + (tmp_word_cnts * 2) + 1;
898 		}
899 
900 		*write_state = PG_STATE_HEADER;
901 		*repeat_times += 1;
902 		if (*repeat_times > EFUSE_REPEAT_THRESHOLD_) {
903 			*continual = false;
904 			*result = false;
905 		}
906 
907 		RTPRINT(rtlpriv, FEEPROM, EFUSE_PG,
908 			"efuse PG_STATE_HEADER-2\n");
909 	}
910 }
911 
efuse_pg_packet_write(struct ieee80211_hw * hw,u8 offset,u8 word_en,u8 * data)912 static int efuse_pg_packet_write(struct ieee80211_hw *hw,
913 				 u8 offset, u8 word_en, u8 *data)
914 {
915 	struct rtl_priv *rtlpriv = rtl_priv(hw);
916 	struct pgpkt_struct target_pkt;
917 	u8 write_state = PG_STATE_HEADER;
918 	int continual = true, result = true;
919 	u16 efuse_addr = 0;
920 	u8 efuse_data;
921 	u8 target_word_cnts = 0;
922 	u8 badworden = 0x0F;
923 	static int repeat_times;
924 
925 	if (efuse_get_current_size(hw) >= (EFUSE_MAX_SIZE -
926 		rtlpriv->cfg->maps[EFUSE_OOB_PROTECT_BYTES_LEN])) {
927 		RTPRINT(rtlpriv, FEEPROM, EFUSE_PG,
928 			"efuse_pg_packet_write error\n");
929 		return false;
930 	}
931 
932 	target_pkt.offset = offset;
933 	target_pkt.word_en = word_en;
934 
935 	memset(target_pkt.data, 0xFF,  8 * sizeof(u8));
936 
937 	efuse_word_enable_data_read(word_en, data, target_pkt.data);
938 	target_word_cnts = efuse_calculate_word_cnts(target_pkt.word_en);
939 
940 	RTPRINT(rtlpriv, FEEPROM, EFUSE_PG, "efuse Power ON\n");
941 
942 	while (continual && (efuse_addr < (EFUSE_MAX_SIZE -
943 		rtlpriv->cfg->maps[EFUSE_OOB_PROTECT_BYTES_LEN]))) {
944 		if (write_state == PG_STATE_HEADER) {
945 			badworden = 0x0F;
946 			RTPRINT(rtlpriv, FEEPROM, EFUSE_PG,
947 				"efuse PG_STATE_HEADER\n");
948 
949 			if (efuse_one_byte_read(hw, efuse_addr, &efuse_data) &&
950 			    (efuse_data != 0xFF))
951 				efuse_write_data_case1(hw, &efuse_addr,
952 						       efuse_data, offset,
953 						       &continual,
954 						       &write_state,
955 						       &target_pkt,
956 						       &repeat_times, &result,
957 						       word_en);
958 			else
959 				efuse_write_data_case2(hw, &efuse_addr,
960 						       &continual,
961 						       &write_state,
962 						       target_pkt,
963 						       &repeat_times,
964 						       &result);
965 
966 		} else if (write_state == PG_STATE_DATA) {
967 			RTPRINT(rtlpriv, FEEPROM, EFUSE_PG,
968 				"efuse PG_STATE_DATA\n");
969 			badworden =
970 			    enable_efuse_data_write(hw, efuse_addr + 1,
971 						    target_pkt.word_en,
972 						    target_pkt.data);
973 
974 			if ((badworden & 0x0F) == 0x0F) {
975 				continual = false;
976 			} else {
977 				efuse_addr =
978 				    efuse_addr + (2 * target_word_cnts) + 1;
979 
980 				target_pkt.offset = offset;
981 				target_pkt.word_en = badworden;
982 				target_word_cnts =
983 				    efuse_calculate_word_cnts(target_pkt.
984 							      word_en);
985 				write_state = PG_STATE_HEADER;
986 				repeat_times++;
987 				if (repeat_times > EFUSE_REPEAT_THRESHOLD_) {
988 					continual = false;
989 					result = false;
990 				}
991 				RTPRINT(rtlpriv, FEEPROM, EFUSE_PG,
992 					"efuse PG_STATE_HEADER-3\n");
993 			}
994 		}
995 	}
996 
997 	if (efuse_addr >= (EFUSE_MAX_SIZE -
998 		rtlpriv->cfg->maps[EFUSE_OOB_PROTECT_BYTES_LEN])) {
999 		rtl_dbg(rtlpriv, COMP_EFUSE, DBG_LOUD,
1000 			"efuse_addr(%#x) Out of size!!\n", efuse_addr);
1001 	}
1002 
1003 	return true;
1004 }
1005 
efuse_word_enable_data_read(u8 word_en,u8 * sourdata,u8 * targetdata)1006 static void efuse_word_enable_data_read(u8 word_en, u8 *sourdata,
1007 					u8 *targetdata)
1008 {
1009 	if (!(word_en & BIT(0))) {
1010 		targetdata[0] = sourdata[0];
1011 		targetdata[1] = sourdata[1];
1012 	}
1013 
1014 	if (!(word_en & BIT(1))) {
1015 		targetdata[2] = sourdata[2];
1016 		targetdata[3] = sourdata[3];
1017 	}
1018 
1019 	if (!(word_en & BIT(2))) {
1020 		targetdata[4] = sourdata[4];
1021 		targetdata[5] = sourdata[5];
1022 	}
1023 
1024 	if (!(word_en & BIT(3))) {
1025 		targetdata[6] = sourdata[6];
1026 		targetdata[7] = sourdata[7];
1027 	}
1028 }
1029 
enable_efuse_data_write(struct ieee80211_hw * hw,u16 efuse_addr,u8 word_en,u8 * data)1030 static u8 enable_efuse_data_write(struct ieee80211_hw *hw,
1031 				  u16 efuse_addr, u8 word_en, u8 *data)
1032 {
1033 	struct rtl_priv *rtlpriv = rtl_priv(hw);
1034 	u16 tmpaddr;
1035 	u16 start_addr = efuse_addr;
1036 	u8 badworden = 0x0F;
1037 	u8 tmpdata[8];
1038 
1039 	memset(tmpdata, 0xff, PGPKT_DATA_SIZE);
1040 	rtl_dbg(rtlpriv, COMP_EFUSE, DBG_LOUD,
1041 		"word_en = %x efuse_addr=%x\n", word_en, efuse_addr);
1042 
1043 	if (!(word_en & BIT(0))) {
1044 		tmpaddr = start_addr;
1045 		efuse_one_byte_write(hw, start_addr++, data[0]);
1046 		efuse_one_byte_write(hw, start_addr++, data[1]);
1047 
1048 		efuse_one_byte_read(hw, tmpaddr, &tmpdata[0]);
1049 		efuse_one_byte_read(hw, tmpaddr + 1, &tmpdata[1]);
1050 		if ((data[0] != tmpdata[0]) || (data[1] != tmpdata[1]))
1051 			badworden &= (~BIT(0));
1052 	}
1053 
1054 	if (!(word_en & BIT(1))) {
1055 		tmpaddr = start_addr;
1056 		efuse_one_byte_write(hw, start_addr++, data[2]);
1057 		efuse_one_byte_write(hw, start_addr++, data[3]);
1058 
1059 		efuse_one_byte_read(hw, tmpaddr, &tmpdata[2]);
1060 		efuse_one_byte_read(hw, tmpaddr + 1, &tmpdata[3]);
1061 		if ((data[2] != tmpdata[2]) || (data[3] != tmpdata[3]))
1062 			badworden &= (~BIT(1));
1063 	}
1064 
1065 	if (!(word_en & BIT(2))) {
1066 		tmpaddr = start_addr;
1067 		efuse_one_byte_write(hw, start_addr++, data[4]);
1068 		efuse_one_byte_write(hw, start_addr++, data[5]);
1069 
1070 		efuse_one_byte_read(hw, tmpaddr, &tmpdata[4]);
1071 		efuse_one_byte_read(hw, tmpaddr + 1, &tmpdata[5]);
1072 		if ((data[4] != tmpdata[4]) || (data[5] != tmpdata[5]))
1073 			badworden &= (~BIT(2));
1074 	}
1075 
1076 	if (!(word_en & BIT(3))) {
1077 		tmpaddr = start_addr;
1078 		efuse_one_byte_write(hw, start_addr++, data[6]);
1079 		efuse_one_byte_write(hw, start_addr++, data[7]);
1080 
1081 		efuse_one_byte_read(hw, tmpaddr, &tmpdata[6]);
1082 		efuse_one_byte_read(hw, tmpaddr + 1, &tmpdata[7]);
1083 		if ((data[6] != tmpdata[6]) || (data[7] != tmpdata[7]))
1084 			badworden &= (~BIT(3));
1085 	}
1086 
1087 	return badworden;
1088 }
1089 
efuse_power_switch(struct ieee80211_hw * hw,u8 write,u8 pwrstate)1090 void efuse_power_switch(struct ieee80211_hw *hw, u8 write, u8 pwrstate)
1091 {
1092 	struct rtl_priv *rtlpriv = rtl_priv(hw);
1093 	struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
1094 	u8 tempval;
1095 	u16 tmpv16;
1096 
1097 	if (pwrstate && (rtlhal->hw_type != HARDWARE_TYPE_RTL8192SE)) {
1098 		if (rtlhal->hw_type != HARDWARE_TYPE_RTL8192CE &&
1099 		    rtlhal->hw_type != HARDWARE_TYPE_RTL8192DE) {
1100 			rtl_write_byte(rtlpriv,
1101 				       rtlpriv->cfg->maps[EFUSE_ACCESS], 0x69);
1102 		} else {
1103 			tmpv16 =
1104 			  rtl_read_word(rtlpriv,
1105 					rtlpriv->cfg->maps[SYS_ISO_CTRL]);
1106 			if (!(tmpv16 & rtlpriv->cfg->maps[EFUSE_PWC_EV12V])) {
1107 				tmpv16 |= rtlpriv->cfg->maps[EFUSE_PWC_EV12V];
1108 				rtl_write_word(rtlpriv,
1109 					       rtlpriv->cfg->maps[SYS_ISO_CTRL],
1110 					       tmpv16);
1111 			}
1112 		}
1113 		tmpv16 = rtl_read_word(rtlpriv,
1114 				       rtlpriv->cfg->maps[SYS_FUNC_EN]);
1115 		if (!(tmpv16 & rtlpriv->cfg->maps[EFUSE_FEN_ELDR])) {
1116 			tmpv16 |= rtlpriv->cfg->maps[EFUSE_FEN_ELDR];
1117 			rtl_write_word(rtlpriv,
1118 				       rtlpriv->cfg->maps[SYS_FUNC_EN], tmpv16);
1119 		}
1120 
1121 		tmpv16 = rtl_read_word(rtlpriv, rtlpriv->cfg->maps[SYS_CLK]);
1122 		if ((!(tmpv16 & rtlpriv->cfg->maps[EFUSE_LOADER_CLK_EN])) ||
1123 		    (!(tmpv16 & rtlpriv->cfg->maps[EFUSE_ANA8M]))) {
1124 			tmpv16 |= (rtlpriv->cfg->maps[EFUSE_LOADER_CLK_EN] |
1125 				   rtlpriv->cfg->maps[EFUSE_ANA8M]);
1126 			rtl_write_word(rtlpriv,
1127 				       rtlpriv->cfg->maps[SYS_CLK], tmpv16);
1128 		}
1129 	}
1130 
1131 	if (pwrstate) {
1132 		if (write) {
1133 			tempval = rtl_read_byte(rtlpriv,
1134 						rtlpriv->cfg->maps[EFUSE_TEST] +
1135 						3);
1136 
1137 			if (rtlhal->hw_type == HARDWARE_TYPE_RTL8812AE) {
1138 				tempval &= ~(BIT(3) | BIT(4) | BIT(5) | BIT(6));
1139 				tempval |= (VOLTAGE_V25 << 3);
1140 			} else if (rtlhal->hw_type != HARDWARE_TYPE_RTL8192SE) {
1141 				tempval &= 0x0F;
1142 				tempval |= (VOLTAGE_V25 << 4);
1143 			}
1144 
1145 			rtl_write_byte(rtlpriv,
1146 				       rtlpriv->cfg->maps[EFUSE_TEST] + 3,
1147 				       (tempval | 0x80));
1148 		}
1149 
1150 		if (rtlhal->hw_type == HARDWARE_TYPE_RTL8192SE) {
1151 			rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CLK],
1152 				       0x03);
1153 		}
1154 	} else {
1155 		if (rtlhal->hw_type != HARDWARE_TYPE_RTL8192CE &&
1156 		    rtlhal->hw_type != HARDWARE_TYPE_RTL8192DE)
1157 			rtl_write_byte(rtlpriv,
1158 				       rtlpriv->cfg->maps[EFUSE_ACCESS], 0);
1159 
1160 		if (write) {
1161 			tempval = rtl_read_byte(rtlpriv,
1162 						rtlpriv->cfg->maps[EFUSE_TEST] +
1163 						3);
1164 			rtl_write_byte(rtlpriv,
1165 				       rtlpriv->cfg->maps[EFUSE_TEST] + 3,
1166 				       (tempval & 0x7F));
1167 		}
1168 
1169 		if (rtlhal->hw_type == HARDWARE_TYPE_RTL8192SE) {
1170 			rtl_write_byte(rtlpriv, rtlpriv->cfg->maps[EFUSE_CLK],
1171 				       0x02);
1172 		}
1173 	}
1174 }
1175 EXPORT_SYMBOL(efuse_power_switch);
1176 
efuse_get_current_size(struct ieee80211_hw * hw)1177 static u16 efuse_get_current_size(struct ieee80211_hw *hw)
1178 {
1179 	int continual = true;
1180 	u16 efuse_addr = 0;
1181 	u8 hworden;
1182 	u8 efuse_data, word_cnts;
1183 
1184 	while (continual && efuse_one_byte_read(hw, efuse_addr, &efuse_data) &&
1185 	       (efuse_addr < EFUSE_MAX_SIZE)) {
1186 		if (efuse_data != 0xFF) {
1187 			hworden = efuse_data & 0x0F;
1188 			word_cnts = efuse_calculate_word_cnts(hworden);
1189 			efuse_addr = efuse_addr + (word_cnts * 2) + 1;
1190 		} else {
1191 			continual = false;
1192 		}
1193 	}
1194 
1195 	return efuse_addr;
1196 }
1197 
efuse_calculate_word_cnts(u8 word_en)1198 static u8 efuse_calculate_word_cnts(u8 word_en)
1199 {
1200 	u8 word_cnts = 0;
1201 
1202 	if (!(word_en & BIT(0)))
1203 		word_cnts++;
1204 	if (!(word_en & BIT(1)))
1205 		word_cnts++;
1206 	if (!(word_en & BIT(2)))
1207 		word_cnts++;
1208 	if (!(word_en & BIT(3)))
1209 		word_cnts++;
1210 	return word_cnts;
1211 }
1212 
rtl_get_hwinfo(struct ieee80211_hw * hw,struct rtl_priv * rtlpriv,int max_size,u8 * hwinfo,const int * params)1213 int rtl_get_hwinfo(struct ieee80211_hw *hw, struct rtl_priv *rtlpriv,
1214 		   int max_size, u8 *hwinfo, const int *params)
1215 {
1216 	struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
1217 	struct rtl_pci_priv *rtlpcipriv = rtl_pcipriv(hw);
1218 	struct device *dev = &rtlpcipriv->dev.pdev->dev;
1219 	u16 eeprom_id;
1220 	u16 i, usvalue;
1221 
1222 	switch (rtlefuse->epromtype) {
1223 	case EEPROM_BOOT_EFUSE:
1224 		rtl_efuse_shadow_map_update(hw);
1225 		break;
1226 
1227 	case EEPROM_93C46:
1228 		pr_err("RTL8XXX did not boot from eeprom, check it !!\n");
1229 		return 1;
1230 
1231 	default:
1232 		dev_warn(dev, "no efuse data\n");
1233 		return 1;
1234 	}
1235 
1236 	memcpy(hwinfo, &rtlefuse->efuse_map[EFUSE_INIT_MAP][0], max_size);
1237 
1238 	RT_PRINT_DATA(rtlpriv, COMP_INIT, DBG_DMESG, "MAP",
1239 		      hwinfo, max_size);
1240 
1241 	eeprom_id = *((u16 *)&hwinfo[0]);
1242 	if (eeprom_id != params[0]) {
1243 		rtl_dbg(rtlpriv, COMP_ERR, DBG_WARNING,
1244 			"EEPROM ID(%#x) is invalid!!\n", eeprom_id);
1245 		rtlefuse->autoload_failflag = true;
1246 	} else {
1247 		rtl_dbg(rtlpriv, COMP_INIT, DBG_LOUD, "Autoload OK\n");
1248 		rtlefuse->autoload_failflag = false;
1249 	}
1250 
1251 	if (rtlefuse->autoload_failflag)
1252 		return 1;
1253 
1254 	rtlefuse->eeprom_vid = *(u16 *)&hwinfo[params[1]];
1255 	rtlefuse->eeprom_did = *(u16 *)&hwinfo[params[2]];
1256 	rtlefuse->eeprom_svid = *(u16 *)&hwinfo[params[3]];
1257 	rtlefuse->eeprom_smid = *(u16 *)&hwinfo[params[4]];
1258 	rtl_dbg(rtlpriv, COMP_INIT, DBG_LOUD,
1259 		"EEPROMId = 0x%4x\n", eeprom_id);
1260 	rtl_dbg(rtlpriv, COMP_INIT, DBG_LOUD,
1261 		"EEPROM VID = 0x%4x\n", rtlefuse->eeprom_vid);
1262 	rtl_dbg(rtlpriv, COMP_INIT, DBG_LOUD,
1263 		"EEPROM DID = 0x%4x\n", rtlefuse->eeprom_did);
1264 	rtl_dbg(rtlpriv, COMP_INIT, DBG_LOUD,
1265 		"EEPROM SVID = 0x%4x\n", rtlefuse->eeprom_svid);
1266 	rtl_dbg(rtlpriv, COMP_INIT, DBG_LOUD,
1267 		"EEPROM SMID = 0x%4x\n", rtlefuse->eeprom_smid);
1268 
1269 	for (i = 0; i < 6; i += 2) {
1270 		usvalue = *(u16 *)&hwinfo[params[5] + i];
1271 		*((u16 *)(&rtlefuse->dev_addr[i])) = usvalue;
1272 	}
1273 	rtl_dbg(rtlpriv, COMP_INIT, DBG_DMESG, "%pM\n", rtlefuse->dev_addr);
1274 
1275 	rtlefuse->eeprom_channelplan = *&hwinfo[params[6]];
1276 	rtlefuse->eeprom_version = *(u16 *)&hwinfo[params[7]];
1277 	rtlefuse->txpwr_fromeprom = true;
1278 	rtlefuse->eeprom_oemid = *&hwinfo[params[8]];
1279 
1280 	rtl_dbg(rtlpriv, COMP_INIT, DBG_LOUD,
1281 		"EEPROM Customer ID: 0x%2x\n", rtlefuse->eeprom_oemid);
1282 
1283 	/* set channel plan to world wide 13 */
1284 	rtlefuse->channel_plan = params[9];
1285 
1286 	return 0;
1287 }
1288 EXPORT_SYMBOL_GPL(rtl_get_hwinfo);
1289 
_rtl_fw_block_write_usb(struct ieee80211_hw * hw,u8 * buffer,u32 size)1290 static void _rtl_fw_block_write_usb(struct ieee80211_hw *hw, u8 *buffer, u32 size)
1291 {
1292 	struct rtl_priv *rtlpriv = rtl_priv(hw);
1293 	u32 start = START_ADDRESS;
1294 	u32 n;
1295 
1296 	while (size > 0) {
1297 		if (size >= 64)
1298 			n = 64;
1299 		else if (size >= 8)
1300 			n = 8;
1301 		else
1302 			n = 1;
1303 
1304 		rtl_write_chunk(rtlpriv, start, n, buffer);
1305 
1306 		start += n;
1307 		buffer += n;
1308 		size -= n;
1309 	}
1310 }
1311 
rtl_fw_block_write(struct ieee80211_hw * hw,u8 * buffer,u32 size)1312 void rtl_fw_block_write(struct ieee80211_hw *hw, u8 *buffer, u32 size)
1313 {
1314 	struct rtl_priv *rtlpriv = rtl_priv(hw);
1315 	u32 i;
1316 
1317 	if (rtlpriv->rtlhal.interface == INTF_PCI) {
1318 		for (i = 0; i < size; i++)
1319 			rtl_write_byte(rtlpriv, (START_ADDRESS + i),
1320 				       *(buffer + i));
1321 	} else if (rtlpriv->rtlhal.interface == INTF_USB) {
1322 		_rtl_fw_block_write_usb(hw, buffer, size);
1323 	}
1324 }
1325 EXPORT_SYMBOL_GPL(rtl_fw_block_write);
1326 
rtl_fw_page_write(struct ieee80211_hw * hw,u32 page,u8 * buffer,u32 size)1327 void rtl_fw_page_write(struct ieee80211_hw *hw, u32 page, u8 *buffer,
1328 		       u32 size)
1329 {
1330 	struct rtl_priv *rtlpriv = rtl_priv(hw);
1331 	u8 value8;
1332 	u8 u8page = (u8)(page & 0x07);
1333 
1334 	value8 = (rtl_read_byte(rtlpriv, REG_MCUFWDL + 2) & 0xF8) | u8page;
1335 
1336 	rtl_write_byte(rtlpriv, (REG_MCUFWDL + 2), value8);
1337 	rtl_fw_block_write(hw, buffer, size);
1338 }
1339 EXPORT_SYMBOL_GPL(rtl_fw_page_write);
1340 
rtl_fill_dummy(u8 * pfwbuf,u32 * pfwlen)1341 void rtl_fill_dummy(u8 *pfwbuf, u32 *pfwlen)
1342 {
1343 	u32 fwlen = *pfwlen;
1344 	u8 remain = (u8)(fwlen % 4);
1345 
1346 	remain = (remain == 0) ? 0 : (4 - remain);
1347 
1348 	while (remain > 0) {
1349 		pfwbuf[fwlen] = 0;
1350 		fwlen++;
1351 		remain--;
1352 	}
1353 
1354 	*pfwlen = fwlen;
1355 }
1356 EXPORT_SYMBOL_GPL(rtl_fill_dummy);
1357 
rtl_efuse_ops_init(struct ieee80211_hw * hw)1358 void rtl_efuse_ops_init(struct ieee80211_hw *hw)
1359 {
1360 	struct rtl_priv *rtlpriv = rtl_priv(hw);
1361 
1362 	rtlpriv->efuse.efuse_ops = &efuse_ops;
1363 }
1364 EXPORT_SYMBOL_GPL(rtl_efuse_ops_init);
1365