diff mbox series

[U-Boot,v1,26/26] board: colibri_imx6: check for and report ecc errors in fuses

Message ID 20190208174229.23562-27-marcel@ziswiler.com
State Accepted
Commit b87ca9907ca28d4472fff4bd8562f6f6ae000330
Delegated to: Stefano Babic
Headers show
Series colibri imx6 fixes, device tree enablement and driver model conversion | expand

Commit Message

Marcel Ziswiler Feb. 8, 2019, 5:42 p.m. UTC
From: Gerard Salvatella <gerard.salvatella@toradex.com>

The PMIC on the Colibri iMX6 may have ECC errors in fuses that will
prevent correct settings. Up to one bit error per fuse bank can be
reported and corrected by the ECC logic. Two bit errors can only be
reported.

Signed-off-by: Gerard Salvatella <gerard.salvatella@toradex.com>
Acked-by: Marcel Ziswiler <marcel.ziswiler@toradex.com>

---

 board/toradex/colibri_imx6/pf0100.c | 51 +++++++++++++++++++++++++
 board/toradex/colibri_imx6/pf0100.h | 59 ++++++++++++++++++++++++++++-
 2 files changed, 108 insertions(+), 2 deletions(-)

Comments

Marcel Ziswiler March 24, 2019, 9:42 p.m. UTC | #1
Hi Stefano

On Wed, 2019-03-13 at 09:38 +0000, sbabic@denx.de wrote:
> > From: Gerard Salvatella <gerard.salvatella@toradex.com>
> > The PMIC on the Colibri iMX6 may have ECC errors in fuses that will
> > prevent correct settings. Up to one bit error per fuse bank can be
> > reported and corrected by the ECC logic. Two bit errors can only be
> > reported.
> > Signed-off-by: Gerard Salvatella <gerard.salvatella@toradex.com>
> > Acked-by: Marcel Ziswiler <marcel.ziswiler@toradex.com>
> 
> Applied to u-boot-imx, -next, thanks !

Unfortunately, I can't find that one anywhere on u-boot-imx.git/next.

I will resend it as a separate patch for you to pick up, OK?

BTW: I will also send a V2 of the Colibri Vybrid stuff, plus the
Colibri iMX6ULL overhaul and the initial add of the Colibri iMX8QXP.

> Best regards,
> Stefano Babic

Cheers

Marcel
Stefano Babic March 25, 2019, 12:14 p.m. UTC | #2
On 24/03/19 22:42, Marcel Ziswiler wrote:
> Hi Stefano
> 
> On Wed, 2019-03-13 at 09:38 +0000, sbabic@denx.de wrote:
>>> From: Gerard Salvatella <gerard.salvatella@toradex.com>
>>> The PMIC on the Colibri iMX6 may have ECC errors in fuses that will
>>> prevent correct settings. Up to one bit error per fuse bank can be
>>> reported and corrected by the ECC logic. Two bit errors can only be
>>> reported.
>>> Signed-off-by: Gerard Salvatella <gerard.salvatella@toradex.com>
>>> Acked-by: Marcel Ziswiler <marcel.ziswiler@toradex.com>
>>
>> Applied to u-boot-imx, -next, thanks !
> 
> Unfortunately, I can't find that one anywhere on u-boot-imx.git/next.
> 
> I will resend it as a separate patch for you to pick up, OK?

mmhhh...I have applied them, I see in my local -next, I am sure I pushed
before. Let me see why they do not appear on git.denx.de, you do not
need to repush, they are alreay applied.

> 
> BTW: I will also send a V2 of the Colibri Vybrid stuff, plus the
> Colibri iMX6ULL overhaul and the initial add of the Colibri iMX8QXP.

Ok, thanks for info. I set V1 as obsolete in patchwork.

Regards,
Stefano

> 
>> Best regards,
>> Stefano Babic
> 
> Cheers
> 
> Marcel
>
diff mbox series

Patch

diff --git a/board/toradex/colibri_imx6/pf0100.c b/board/toradex/colibri_imx6/pf0100.c
index 09c3cc950a..e744243297 100644
--- a/board/toradex/colibri_imx6/pf0100.c
+++ b/board/toradex/colibri_imx6/pf0100.c
@@ -21,6 +21,8 @@ 
 /* define for PMIC register dump */
 /*#define DEBUG */
 
+#define WARNBAR "@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@\n"
+
 /* use GPIO: EXT_IO1 to switch on VPGM, ON: 1 */
 static __maybe_unused iomux_v3_cfg_t const pmic_prog_pads[] = {
 	MX6_PAD_NANDF_D3__GPIO2_IO03 | MUX_PAD_CTRL(NO_PAD_CTRL),
@@ -42,6 +44,55 @@  unsigned pmic_init(void)
 		       PFUZE100_I2C_ADDR);
 		return 0;
 	}
+
+	/* check for errors in PMIC fuses */
+	if (dm_i2c_read(dev, PFUZE100_INTSTAT3, &val, 1) < 0) {
+		puts("i2c pmic INTSTAT3 register read failed\n");
+		return 0;
+	}
+	if (val & PFUZE100_BIT_OTP_ECCI) {
+		puts("\n" WARNBAR);
+		puts("WARNING: ecc errors found in pmic fuse banks\n");
+		puts(WARNBAR);
+	}
+	if (dm_i2c_read(dev, PFUZE100_OTP_ECC_SE1, &val, 1) < 0) {
+		puts("i2c pmic ECC_SE1 register read failed\n");
+		return 0;
+	}
+	if (val & PFUZE100_BITS_ECC_SE1) {
+		puts(WARNBAR);
+		puts("WARNING: ecc has made bit corrections in banks 1 to 5\n");
+		puts(WARNBAR);
+	}
+	if (dm_i2c_read(dev, PFUZE100_OTP_ECC_SE2, &val, 1) < 0) {
+		puts("i2c pmic ECC_SE2 register read failed\n");
+		return 0;
+	}
+	if (val & PFUZE100_BITS_ECC_SE2) {
+		puts(WARNBAR);
+		puts("WARNING: ecc has made bit corrections in banks 6 to 10\n"
+		    );
+		puts(WARNBAR);
+	}
+	if (dm_i2c_read(dev, PFUZE100_OTP_ECC_DE1, &val, 1) < 0) {
+		puts("i2c pmic ECC_DE register read failed\n");
+		return 0;
+	}
+	if (val & PFUZE100_BITS_ECC_DE1) {
+		puts(WARNBAR);
+		puts("ERROR: banks 1 to 5 have uncorrectable bits\n");
+		puts(WARNBAR);
+	}
+	if (dm_i2c_read(dev, PFUZE100_OTP_ECC_DE2, &val, 1) < 0) {
+		puts("i2c pmic ECC_DE register read failed\n");
+		return 0;
+	}
+	if (val & PFUZE100_BITS_ECC_DE2) {
+		puts(WARNBAR);
+		puts("ERROR: banks 6 to 10 have uncorrectable bits\n");
+		puts(WARNBAR);
+	}
+
 	/* get device ident */
 	if (dm_i2c_read(dev, PFUZE100_DEVICEID, &devid, 1) < 0) {
 		puts("i2c pmic devid read failed\n");
diff --git a/board/toradex/colibri_imx6/pf0100.h b/board/toradex/colibri_imx6/pf0100.h
index c0efb79bbc..9257620511 100644
--- a/board/toradex/colibri_imx6/pf0100.h
+++ b/board/toradex/colibri_imx6/pf0100.h
@@ -1,6 +1,6 @@ 
 /* SPDX-License-Identifier: GPL-2.0+ */
 /*
- * Copyright (C) 2014-2016, Toradex AG
+ * Copyright (C) 2014-2019, Toradex AG
  */
 
 /*
@@ -10,11 +10,23 @@ 
 #ifndef PF0100_H_
 #define PF0100_H_
 
+/* bit definitions */
+#define PFUZE100_BIT_0			(0x01 << 0)
+#define PFUZE100_BIT_1			(0x01 << 1)
+#define PFUZE100_BIT_2			(0x01 << 2)
+#define PFUZE100_BIT_3			(0x01 << 3)
+#define PFUZE100_BIT_4			(0x01 << 4)
+#define PFUZE100_BIT_5			(0x01 << 5)
+#define PFUZE100_BIT_6			(0x01 << 6)
+#define PFUZE100_BIT_7			(0x01 << 7)
+
 /* 7-bit I2C bus slave address */
 #define PFUZE100_I2C_ADDR		(0x08)
 /* Register Addresses */
 #define PFUZE100_DEVICEID		(0x0)
 #define PFUZE100_REVID			(0x3)
+#define PFUZE100_INTSTAT3		(0xe)
+#define PFUZE100_BIT_OTP_ECCI		PFUZE100_BIT_7
 #define PFUZE100_SW1AMODE		(0x23)
 #define PFUZE100_SW1ACON		36
 #define PFUZE100_SW1ACON_SPEED_VAL	(0x1<<6)	/*default */
@@ -39,12 +51,55 @@ 
 #define PFUZE100_PAGE_REGISTER_PAGE2	(0x02 & PFUZE100_PAGE_REGISTER_PAGE_M)
 
 /* extended page 1 */
+#define PFUZE100_OTP_ECC_SE1		0x8a
+#define PFUZE100_BIT_ECC1_SE		PFUZE100_BIT_0
+#define PFUZE100_BIT_ECC2_SE		PFUZE100_BIT_1
+#define PFUZE100_BIT_ECC3_SE		PFUZE100_BIT_2
+#define PFUZE100_BIT_ECC4_SE		PFUZE100_BIT_3
+#define PFUZE100_BIT_ECC5_SE		PFUZE100_BIT_4
+#define PFUZE100_BITS_ECC_SE1		((PFUZE100_BIT_ECC1_SE) | \
+					(PFUZE100_BIT_ECC2_SE) | \
+					(PFUZE100_BIT_ECC3_SE) | \
+					(PFUZE100_BIT_ECC4_SE) | \
+					(PFUZE100_BIT_ECC5_SE))
+#define PFUZE100_OTP_ECC_SE2		0x8b
+#define PFUZE100_BIT_ECC6_SE		PFUZE100_BIT_0
+#define PFUZE100_BIT_ECC7_SE		PFUZE100_BIT_1
+#define PFUZE100_BIT_ECC8_SE		PFUZE100_BIT_2
+#define PFUZE100_BIT_ECC9_SE		PFUZE100_BIT_3
+#define PFUZE100_BIT_ECC10_SE		PFUZE100_BIT_4
+#define PFUZE100_BITS_ECC_SE2		((PFUZE100_BIT_ECC6_SE) | \
+					(PFUZE100_BIT_ECC7_SE) | \
+					(PFUZE100_BIT_ECC8_SE) | \
+					(PFUZE100_BIT_ECC9_SE) | \
+					(PFUZE100_BIT_ECC10_SE))
+#define PFUZE100_OTP_ECC_DE1		0x8c
+#define PFUZE100_BIT_ECC1_DE		PFUZE100_BIT_0
+#define PFUZE100_BIT_ECC2_DE		PFUZE100_BIT_1
+#define PFUZE100_BIT_ECC3_DE		PFUZE100_BIT_2
+#define PFUZE100_BIT_ECC4_DE		PFUZE100_BIT_3
+#define PFUZE100_BIT_ECC5_DE		PFUZE100_BIT_4
+#define PFUZE100_BITS_ECC_DE1		((PFUZE100_BIT_ECC1_DE) | \
+					(PFUZE100_BIT_ECC2_DE) | \
+					(PFUZE100_BIT_ECC3_DE) | \
+					(PFUZE100_BIT_ECC4_DE) | \
+					(PFUZE100_BIT_ECC5_DE))
+#define PFUZE100_OTP_ECC_DE2		0x8d
+#define PFUZE100_BIT_ECC6_DE		PFUZE100_BIT_0
+#define PFUZE100_BIT_ECC7_DE		PFUZE100_BIT_1
+#define PFUZE100_BIT_ECC8_DE		PFUZE100_BIT_2
+#define PFUZE100_BIT_ECC9_DE		PFUZE100_BIT_3
+#define PFUZE100_BIT_ECC10_DE		PFUZE100_BIT_4
+#define PFUZE100_BITS_ECC_DE2		((PFUZE100_BIT_ECC6_DE) | \
+					(PFUZE100_BIT_ECC7_DE) | \
+					(PFUZE100_BIT_ECC8_DE) | \
+					(PFUZE100_BIT_ECC9_DE) | \
+					(PFUZE100_BIT_ECC10_DE))
 #define PFUZE100_FUSE_POR1		0xe4
 #define PFUZE100_FUSE_POR2		0xe5
 #define PFUZE100_FUSE_POR3		0xe6
 #define PFUZE100_FUSE_POR_M		(0x1 << 1)
 
-
 /* output some informational messages, return the number FUSE_POR=1 */
 /* i.e. 0: unprogrammed, 3: programmed, other: undefined prog. state */
 unsigned pmic_init(void);