npcm_otp.c 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512
  1. // SPDX-License-Identifier: GPL-2.0+
  2. /*
  3. * Copyright (c) 2021 Nuvoton Technology Corp.
  4. */
  5. #include <clk.h>
  6. #include <common.h>
  7. #include <dm.h>
  8. #include <errno.h>
  9. #include <fuse.h>
  10. #include <asm/io.h>
  11. #include <linux/delay.h>
  12. #include <asm/arch/otp.h>
  13. struct npcm_otp_priv {
  14. struct npcm_otp_regs *regs[2];
  15. };
  16. static struct npcm_otp_priv *otp_priv;
  17. /*----------------------------------------------------------------------------*/
  18. /* Function: npcm_otp_check_inputs */
  19. /* */
  20. /* Parameters: arr - fuse array number to check */
  21. /* word - fuse word (offset) to check */
  22. /* Returns: int */
  23. /* Side effects: */
  24. /* Description: Checks is arr and word are illegal and do not exceed */
  25. /* their range. Return 0 if they are legal, -1 if not */
  26. /*----------------------------------------------------------------------------*/
  27. static int npcm_otp_check_inputs(u32 arr, u32 word)
  28. {
  29. if (arr >= NPCM_NUM_OF_SA) {
  30. if (IS_ENABLED(CONFIG_ARCH_NPCM8XX))
  31. printf("\nError: npcm8XX otp includs only one bank: 0\n");
  32. if (IS_ENABLED(CONFIG_ARCH_NPCM7xx))
  33. printf("\nError: npcm7XX otp includs only two banks: 0 and 1\n");
  34. return -1;
  35. }
  36. if (word >= NPCM_OTP_ARR_BYTE_SIZE) {
  37. printf("\nError: npcm otp array comprises only %d bytes, numbered from 0 to %d\n",
  38. NPCM_OTP_ARR_BYTE_SIZE, NPCM_OTP_ARR_BYTE_SIZE - 1);
  39. return -1;
  40. }
  41. return 0;
  42. }
  43. /*----------------------------------------------------------------------------*/
  44. /* Function: npcm_otp_wait_for_otp_ready */
  45. /* */
  46. /* Parameters: array - fuse array to wait for */
  47. /* Returns: int */
  48. /* Side effects: */
  49. /* Description: Initialize the Fuse HW module. */
  50. /*----------------------------------------------------------------------------*/
  51. static int npcm_otp_wait_for_otp_ready(u32 arr, u32 timeout)
  52. {
  53. struct npcm_otp_regs *regs = otp_priv->regs[arr];
  54. u32 time = timeout;
  55. /*------------------------------------------------------------------------*/
  56. /* check parameters validity */
  57. /*------------------------------------------------------------------------*/
  58. if (arr > NPCM_FUSE_SA)
  59. return -EINVAL;
  60. while (--time > 1) {
  61. if (readl(&regs->fst) & FST_RDY) {
  62. /* fuse is ready, clear the status. */
  63. writel(readl(&regs->fst) | FST_RDST, &regs->fst);
  64. return 0;
  65. }
  66. }
  67. /* try to clear the status in case it was set */
  68. writel(readl(&regs->fst) | FST_RDST, &regs->fst);
  69. return -EINVAL;
  70. }
  71. /*----------------------------------------------------------------------------*/
  72. /* Function: npcm_otp_read_byte */
  73. /* */
  74. /* Parameters: arr - Storage Array type [input]. */
  75. /* addr - Byte-address to read from [input]. */
  76. /* data - Pointer to result [output]. */
  77. /* Returns: none */
  78. /* Side effects: */
  79. /* Description: Read 8-bit data from an OTP storage array. */
  80. /*----------------------------------------------------------------------------*/
  81. static void npcm_otp_read_byte(u32 arr, u32 addr, u8 *data)
  82. {
  83. struct npcm_otp_regs *regs = otp_priv->regs[arr];
  84. /* Wait for the Fuse Box Idle */
  85. npcm_otp_wait_for_otp_ready(arr, 0xDEADBEEF);
  86. /* Configure the byte address in the fuse array for read operation */
  87. writel(FADDR_VAL(addr, 0), &regs->faddr);
  88. /* Initiate a read cycle */
  89. writel(READ_INIT, &regs->fctl);
  90. /* Wait for read operation completion */
  91. npcm_otp_wait_for_otp_ready(arr, 0xDEADBEEF);
  92. /* Read the result */
  93. *data = readl(&regs->fdata) & FDATA_MASK;
  94. /* Clean FDATA contents to prevent unauthorized software from reading
  95. * sensitive information
  96. */
  97. writel(FDATA_CLEAN_VALUE, &regs->fdata);
  98. }
  99. /*----------------------------------------------------------------------------*/
  100. /* Function: npcm_otp_bit_is_programmed */
  101. /* */
  102. /* Parameters: arr - Storage Array type [input]. */
  103. /* byte_offset - Byte offset in array [input]. */
  104. /* bit_offset - Bit offset in byte [input]. */
  105. /* Returns: Nonzero if bit is programmed, zero otherwise. */
  106. /* Side effects: */
  107. /* Description: Check if a bit is programmed in an OTP storage array. */
  108. /*----------------------------------------------------------------------------*/
  109. static bool npcm_otp_bit_is_programmed(u32 arr,
  110. u32 byte_offset, u8 bit_offset)
  111. {
  112. u32 data = 0;
  113. /* Read the entire byte you wish to program */
  114. npcm_otp_read_byte(arr, byte_offset, (u8 *)&data);
  115. /* Check whether the bit is already programmed */
  116. if (data & (1 << bit_offset))
  117. return true;
  118. return false;
  119. }
  120. /*----------------------------------------------------------------------------*/
  121. /* Function: npcm_otp_program_bit */
  122. /* */
  123. /* Parameters: arr - Storage Array type [input]. */
  124. /* byte)offset - Byte offset in array [input]. */
  125. /* bit_offset - Bit offset in byte [input]. */
  126. /* Returns: int */
  127. /* Side effects: */
  128. /* Description: Program (set to 1) a bit in an OTP storage array. */
  129. /*----------------------------------------------------------------------------*/
  130. static int npcm_otp_program_bit(u32 arr, u32 byte_offset,
  131. u8 bit_offset)
  132. {
  133. struct npcm_otp_regs *regs = otp_priv->regs[arr];
  134. int count;
  135. u8 read_data;
  136. /* Wait for the Fuse Box Idle */
  137. npcm_otp_wait_for_otp_ready(arr, 0xDEADBEEF);
  138. /* Make sure the bit is not already programmed */
  139. if (npcm_otp_bit_is_programmed(arr, byte_offset, bit_offset))
  140. return 0;
  141. /* Configure the bit address in the fuse array for program operation */
  142. writel(FADDR_VAL(byte_offset, bit_offset), &regs->faddr);
  143. writel(readl(&regs->faddr) | FADDR_IN_PROG, &regs->faddr);
  144. // program up to MAX_PROGRAM_PULSES
  145. for (count = 1; count <= MAX_PROGRAM_PULSES; count++) {
  146. /* Initiate a program cycle */
  147. writel(PROGRAM_ARM, &regs->fctl);
  148. writel(PROGRAM_INIT, &regs->fctl);
  149. /* Wait for program operation completion */
  150. npcm_otp_wait_for_otp_ready(arr, 0xDEADBEEF);
  151. // after MIN_PROGRAM_PULSES start verifying the result
  152. if (count >= MIN_PROGRAM_PULSES) {
  153. /* Initiate a read cycle */
  154. writel(READ_INIT, &regs->fctl);
  155. /* Wait for read operation completion */
  156. npcm_otp_wait_for_otp_ready(arr, 0xDEADBEEF);
  157. /* Read the result */
  158. read_data = readl(&regs->fdata) & FDATA_MASK;
  159. /* If the bit is set the sequence ended correctly */
  160. if (read_data & (1 << bit_offset))
  161. break;
  162. }
  163. }
  164. // check if programmking failed
  165. if (count > MAX_PROGRAM_PULSES) {
  166. printf("program fail\n");
  167. return -EINVAL;
  168. }
  169. /*
  170. * Clean FDATA contents to prevent unauthorized software from reading
  171. * sensitive information
  172. */
  173. writel(FDATA_CLEAN_VALUE, &regs->fdata);
  174. return 0;
  175. }
  176. /*----------------------------------------------------------------------------*/
  177. /* Function: npcm_otp_program_byte */
  178. /* */
  179. /* Parameters: arr - Storage Array type [input]. */
  180. /* byte_offset - Byte offset in array [input]. */
  181. /* value - Byte to program [input]. */
  182. /* Returns: int */
  183. /* Side effects: */
  184. /* Description: Program (set to 1) a given byte's relevant bits in an */
  185. /* OTP storage array. */
  186. /*----------------------------------------------------------------------------*/
  187. static int npcm_otp_program_byte(u32 arr, u32 byte_offset,
  188. u8 value)
  189. {
  190. int status = 0;
  191. unsigned int i;
  192. u8 data = 0;
  193. int rc;
  194. rc = npcm_otp_check_inputs(arr, byte_offset);
  195. if (rc != 0)
  196. return rc;
  197. /* Wait for the Fuse Box Idle */
  198. npcm_otp_wait_for_otp_ready(arr, 0xDEADBEEF);
  199. /* Read the entire byte you wish to program */
  200. npcm_otp_read_byte(arr, byte_offset, &data);
  201. /* In case all relevant bits are already programmed - nothing to do */
  202. if ((~data & value) == 0)
  203. return status;
  204. /* Program unprogrammed bits. */
  205. for (i = 0; i < 8; i++) {
  206. if (value & (1 << i)) {
  207. /* Program (set to 1) the relevant bit */
  208. int last_status = npcm_otp_program_bit(arr, byte_offset, (u8)i);
  209. if (last_status != 0)
  210. status = last_status;
  211. }
  212. }
  213. return status;
  214. }
  215. /*----------------------------------------------------------------------------*/
  216. /* Function: npcm_otp_is_fuse_array_disabled */
  217. /* */
  218. /* Parameters: arr - Storage Array type [input]. */
  219. /* Returns: bool */
  220. /* Side effects: */
  221. /* Description: Return true if access to the first 2048 bits of the */
  222. /* specified fuse array is disabled, false if not */
  223. /*----------------------------------------------------------------------------*/
  224. bool npcm_otp_is_fuse_array_disabled(u32 arr)
  225. {
  226. struct npcm_otp_regs *regs = otp_priv->regs[arr];
  227. return (readl(&regs->fcfg) & FCFG_FDIS) != 0;
  228. }
  229. int npcm_otp_select_key(u8 key_index)
  230. {
  231. struct npcm_otp_regs *regs = otp_priv->regs[NPCM_KEY_SA];
  232. u32 idx = 0;
  233. u32 time = 0xDAEDBEEF;
  234. if (key_index >= 4)
  235. return -1;
  236. /* Do not destroy ECCDIS bit */
  237. idx = readl(&regs->fustrap_fkeyind);
  238. /* Configure the key size */
  239. idx &= ~FKEYIND_KSIZE_MASK;
  240. idx |= FKEYIND_KSIZE_256;
  241. /* Configure the key index (0 to 3) */
  242. idx &= ~FKEYIND_KIND_MASK;
  243. idx |= FKEYIND_KIND_KEY(key_index);
  244. writel(idx, &regs->fustrap_fkeyind);
  245. /* Wait for selection completetion */
  246. while (--time > 1) {
  247. if (readl(&regs->fustrap_fkeyind) & FKEYIND_KVAL)
  248. return 0;
  249. udelay(1);
  250. }
  251. return -1;
  252. }
  253. /*----------------------------------------------------------------------------*/
  254. /* Function: npcm_otp_nibble_parity_ecc_encode */
  255. /* */
  256. /* Parameters: datain - pointer to decoded data buffer */
  257. /* dataout - pointer to encoded data buffer (buffer size */
  258. /* should be 2 x dataout) */
  259. /* size - size of encoded data (decoded data x 2) */
  260. /* Returns: none */
  261. /* Side effects: */
  262. /* Description: Decodes the data according to nibble parity ECC scheme. */
  263. /* Size specifies the encoded data size. */
  264. /* Decodes whole bytes only */
  265. /*----------------------------------------------------------------------------*/
  266. void npcm_otp_nibble_parity_ecc_encode(u8 *datain, u8 *dataout, u32 size)
  267. {
  268. u32 i, idx;
  269. u8 E0, E1, E2, E3;
  270. for (i = 0; i < (size / 2); i++) {
  271. E0 = (datain[i] >> 0) & 0x01;
  272. E1 = (datain[i] >> 1) & 0x01;
  273. E2 = (datain[i] >> 2) & 0x01;
  274. E3 = (datain[i] >> 3) & 0x01;
  275. idx = i * 2;
  276. dataout[idx] = datain[i] & 0x0f;
  277. dataout[idx] |= (E0 ^ E1) << 4;
  278. dataout[idx] |= (E2 ^ E3) << 5;
  279. dataout[idx] |= (E0 ^ E2) << 6;
  280. dataout[idx] |= (E1 ^ E3) << 7;
  281. E0 = (datain[i] >> 4) & 0x01;
  282. E1 = (datain[i] >> 5) & 0x01;
  283. E2 = (datain[i] >> 6) & 0x01;
  284. E3 = (datain[i] >> 7) & 0x01;
  285. idx = i * 2 + 1;
  286. dataout[idx] = (datain[i] & 0xf0) >> 4;
  287. dataout[idx] |= (E0 ^ E1) << 4;
  288. dataout[idx] |= (E2 ^ E3) << 5;
  289. dataout[idx] |= (E0 ^ E2) << 6;
  290. dataout[idx] |= (E1 ^ E3) << 7;
  291. }
  292. }
  293. /*----------------------------------------------------------------------------*/
  294. /* Function: npcm_otp_majority_rule_ecc_encode */
  295. /* */
  296. /* Parameters: datain - pointer to decoded data buffer */
  297. /* dataout - pointer to encoded data buffer (buffer size */
  298. /* should be 3 x dataout) */
  299. /* size - size of encoded data (decoded data x 3) */
  300. /* Returns: none */
  301. /* Side effects: */
  302. /* Description: Decodes the data according to Major Rule ECC scheme. */
  303. /* Size specifies the encoded data size. */
  304. /* Decodes whole bytes only */
  305. /*----------------------------------------------------------------------------*/
  306. void npcm_otp_majority_rule_ecc_encode(u8 *datain, u8 *dataout, u32 size)
  307. {
  308. u32 byte;
  309. u32 bit;
  310. u8 bit_val;
  311. u32 decoded_size = size / 3;
  312. for (byte = 0; byte < decoded_size; byte++) {
  313. for (bit = 0; bit < 8; bit++) {
  314. bit_val = (datain[byte] >> bit) & 0x01;
  315. if (bit_val) {
  316. dataout[byte] |= (1 << bit);
  317. dataout[decoded_size + byte] |= (1 << bit);
  318. dataout[decoded_size * 2 + byte] |= (1 << bit);
  319. } else {
  320. dataout[byte] &= ~(1 << bit);
  321. dataout[decoded_size + byte] &= ~(1 << bit);
  322. dataout[decoded_size * 2 + byte] &= ~(1 << bit);
  323. }
  324. }
  325. }
  326. }
  327. /*----------------------------------------------------------------------------*/
  328. /* Function: fuse_program_data */
  329. /* */
  330. /* Parameters: bank - Storage Array type [input]. */
  331. /* word - Byte offset in array [input]. */
  332. /* data - Pointer to data buffer to program. */
  333. /* size - Number of bytes to program. */
  334. /* Returns: none */
  335. /* Side effects: */
  336. /* Description: Programs the given byte array (size bytes) to the given */
  337. /* OTP storage array, starting from offset word. */
  338. /*----------------------------------------------------------------------------*/
  339. int fuse_program_data(u32 bank, u32 word, u8 *data, u32 size)
  340. {
  341. u32 arr = (u32)bank;
  342. u32 byte;
  343. int rc;
  344. rc = npcm_otp_check_inputs(bank, word + size - 1);
  345. if (rc != 0)
  346. return rc;
  347. for (byte = 0; byte < size; byte++) {
  348. u8 val;
  349. val = data[byte];
  350. if (val == 0) // optimization
  351. continue;
  352. rc = npcm_otp_program_byte(arr, word + byte, data[byte]);
  353. if (rc != 0)
  354. return rc;
  355. // verify programming of every '1' bit
  356. val = 0;
  357. npcm_otp_read_byte((u32)bank, byte, &val);
  358. if ((data[byte] & ~val) != 0)
  359. return -1;
  360. }
  361. return 0;
  362. }
  363. int fuse_prog_image(u32 bank, uintptr_t address)
  364. {
  365. return fuse_program_data(bank, 0, (u8 *)address, NPCM_OTP_ARR_BYTE_SIZE);
  366. }
  367. int fuse_read(u32 bank, u32 word, u32 *val)
  368. {
  369. int rc = npcm_otp_check_inputs(bank, word);
  370. if (rc != 0)
  371. return rc;
  372. *val = 0;
  373. npcm_otp_read_byte((u32)bank, word, (u8 *)val);
  374. return 0;
  375. }
  376. int fuse_sense(u32 bank, u32 word, u32 *val)
  377. {
  378. /* We do not support overriding */
  379. return -EINVAL;
  380. }
  381. int fuse_prog(u32 bank, u32 word, u32 val)
  382. {
  383. int rc;
  384. rc = npcm_otp_check_inputs(bank, word);
  385. if (rc != 0)
  386. return rc;
  387. return npcm_otp_program_byte(bank, word, (u8)val);
  388. }
  389. int fuse_override(u32 bank, u32 word, u32 val)
  390. {
  391. /* We do not support overriding */
  392. return -EINVAL;
  393. }
  394. static int npcm_otp_bind(struct udevice *dev)
  395. {
  396. struct npcm_otp_regs *regs;
  397. otp_priv = calloc(1, sizeof(struct npcm_otp_priv));
  398. if (!otp_priv)
  399. return -ENOMEM;
  400. regs = dev_remap_addr_index(dev, 0);
  401. if (!regs) {
  402. printf("Cannot find reg address (arr #0), binding failed\n");
  403. return -EINVAL;
  404. }
  405. otp_priv->regs[0] = regs;
  406. if (IS_ENABLED(CONFIG_ARCH_NPCM7xx)) {
  407. regs = dev_remap_addr_index(dev, 1);
  408. if (!regs) {
  409. printf("Cannot find reg address (arr #1), binding failed\n");
  410. return -EINVAL;
  411. }
  412. otp_priv->regs[1] = regs;
  413. }
  414. printf("OTP: NPCM OTP module bind OK\n");
  415. return 0;
  416. }
  417. static const struct udevice_id npcm_otp_ids[] = {
  418. { .compatible = "nuvoton,npcm845-otp" },
  419. { .compatible = "nuvoton,npcm750-otp" },
  420. { }
  421. };
  422. U_BOOT_DRIVER(npcm_otp) = {
  423. .name = "npcm_otp",
  424. .id = UCLASS_MISC,
  425. .of_match = npcm_otp_ids,
  426. .priv_auto = sizeof(struct npcm_otp_priv),
  427. .bind = npcm_otp_bind,
  428. };