summaryrefslogtreecommitdiffstats
path: root/bsps/shared
diff options
context:
space:
mode:
authorKinsey Moore <kinsey.moore@oarcorp.com>2023-12-01 14:17:50 -0600
committerJoel Sherrill <joel@rtems.org>2023-12-14 13:40:03 -0600
commit7946cff0bc25544480033485d7271675e307984d (patch)
tree536656e0a7a01dbf8f33230bf232a7b42dddcf6a /bsps/shared
parentbsps/zynqmp/jffs2: Use BBT information directly (diff)
downloadrtems-7946cff0bc25544480033485d7271675e307984d.tar.bz2
bsps/xnandpsu: Fix BBT mapping functions
The xnandpsu driver includes functionality to map back and forth between the flash-based BBT and the memory-based BBT with the values in each being a bitwise inversion of each other. This resolves several bugs in this process and simplifies the inversion from operating on the block representation to operating on the entire BBT entry (4 blocks, 2 bits per block, one byte total). Bugs resolved in XNandPsu_ConvertBbt(): * The calculation of memory BBT entry offset was off by a factor of 4 * The entry offset into the flash BBT has been removed since each flash BBT directly describes the flash space it is contained within and has no reference to other devices in the chip Bugs resolved in XNandPsu_WriteBbt(): * The BBT length calculated was reduced to NumTargetBlocks from NumBlocks since only the relevant portion of the in-memory BBT should be written to the flash-based BBT space * An offset was applied to values retrieved from the in-memory BBT so that only the relevant portion was converted and written to the flash-based BBT
Diffstat (limited to 'bsps/shared')
-rw-r--r--bsps/shared/dev/nand/xnandpsu_bbm.c32
1 files changed, 32 insertions, 0 deletions
diff --git a/bsps/shared/dev/nand/xnandpsu_bbm.c b/bsps/shared/dev/nand/xnandpsu_bbm.c
index dd59148536..36ca62fd52 100644
--- a/bsps/shared/dev/nand/xnandpsu_bbm.c
+++ b/bsps/shared/dev/nand/xnandpsu_bbm.c
@@ -321,13 +321,23 @@ Out:
******************************************************************************/
static void XNandPsu_ConvertBbt(XNandPsu *InstancePtr, u8 *Buf, u32 Target)
{
+#ifndef __rtems__
u32 BlockOffset;
u8 BlockShift;
u32 Data;
u8 BlockType;
u32 BlockIndex;
+#endif
u32 BbtLen = InstancePtr->Geometry.NumTargetBlocks >>
XNANDPSU_BBT_BLOCK_SHIFT;
+#ifdef __rtems__
+ u32 BbtOffset = Target * InstancePtr->Geometry.NumTargetBlocks / XNANDPSU_BBT_ENTRY_NUM_BLOCKS;
+
+ for(u32 BbtIndex = 0; BbtIndex < BbtLen; BbtIndex++) {
+ /* Invert the byte to convert from in-flash BBT to in-memory BBT */
+ InstancePtr->Bbt[BbtIndex + BbtOffset] = ~Buf[BbtIndex];
+ }
+#else
u32 StartBlock = Target * InstancePtr->Geometry.NumTargetBlocks;
for(BlockOffset = StartBlock; BlockOffset < (StartBlock + BbtLen);
@@ -370,6 +380,7 @@ static void XNandPsu_ConvertBbt(XNandPsu *InstancePtr, u8 *Buf, u32 Target)
}
}
}
+#endif
}
/*****************************************************************************/
@@ -612,6 +623,7 @@ static s32 XNandPsu_WriteBbt(XNandPsu *InstancePtr, XNandPsu_BbtDesc *Desc,
u8 SpareBuf[XNANDPSU_MAX_SPARE_SIZE] __attribute__ ((aligned(64))) = {0U};
#endif
+#ifndef __rtems__
u8 Mask[4] = {0x00U, 0x01U, 0x02U, 0x03U};
u8 Data;
u32 BlockOffset;
@@ -621,11 +633,21 @@ static s32 XNandPsu_WriteBbt(XNandPsu *InstancePtr, XNandPsu_BbtDesc *Desc,
u32 Index;
u8 BlockType;
u32 BbtLen = InstancePtr->Geometry.NumBlocks >>
+#else
+ s32 Status;
+ u32 Index;
+ u32 BbtLen = InstancePtr->Geometry.NumTargetBlocks >>
+#endif
XNANDPSU_BBT_BLOCK_SHIFT;
/* Find a valid block to write the Bad Block Table(BBT) */
if ((!Desc->Valid) != 0U) {
for(Index = 0U; Index < Desc->MaxBlocks; Index++) {
Block = (EndBlock - Index);
+#ifdef __rtems__
+ if (XNandPsu_IsBlockBad(InstancePtr, Block) == XST_FAILURE) {
+ continue;
+ }
+#else
BlockOffset = Block >> XNANDPSU_BBT_BLOCK_SHIFT;
BlockShift = XNandPsu_BbtBlockShift(Block);
BlockType = (InstancePtr->Bbt[BlockOffset] >>
@@ -639,6 +661,7 @@ static s32 XNandPsu_WriteBbt(XNandPsu *InstancePtr, XNandPsu_BbtDesc *Desc,
/* Good Block */
break;
}
+#endif
Desc->PageOffset[Target] = Block *
InstancePtr->Geometry.PagesPerBlock;
if (Desc->PageOffset[Target] !=
@@ -666,6 +689,14 @@ static s32 XNandPsu_WriteBbt(XNandPsu *InstancePtr, XNandPsu_BbtDesc *Desc,
/* Convert the memory based BBT to flash based table */
(void)memset(Buf, 0xff, BbtLen);
+#ifdef __rtems__
+ u32 BbtTargetOffset = BbtLen * Target;
+ /* Loop through the BBT entries */
+ for(u32 BbtIndex = 0U; BbtIndex < BbtLen; BbtIndex++) {
+ /* Invert byte to convert from in-memory BBT to in-flash BBT */
+ Buf[BbtIndex] = ~InstancePtr->Bbt[BbtIndex + BbtTargetOffset];
+ }
+#else
/* Loop through the number of blocks */
for(BlockOffset = 0U; BlockOffset < BbtLen; BlockOffset++) {
Data = InstancePtr->Bbt[BlockOffset];
@@ -679,6 +710,7 @@ static s32 XNandPsu_WriteBbt(XNandPsu *InstancePtr, XNandPsu_BbtDesc *Desc,
Data >>= XNANDPSU_BBT_BLOCK_SHIFT;
}
}
+#endif
/* Write the Bad Block Table(BBT) to flash */
Status = XNandPsu_EraseBlock(InstancePtr, 0U, Block);
if (Status != XST_SUCCESS) {