mtd: rawnand: arasan: Workaround a misbehaving prog type with NV-DDR
As explained in the comment introduced above the fix, the Arasan controller driver starts an operation when the prog register is being written with a "type" specific to the action to perform. The prog type used until now to perform a CHANGE READ COLUMN with an SDR interface was the PAGE READ type (CMD + ADDR + CMD + DATA). Unfortunately, for an unknown reason (let's call this a silicon bug) any CHANGE READ COLUMN performed this way in NV-DDR mode will fail: the data ready flag will never be triggered, nor will be the transfer complete flag. Forcefully, this leads to a timeout situation which is not easy to handle. Fortunately, it was spotted that sending the same commands through a different prog register "type", CHANGE READ COLUMN ENHANCED, would work all the time (even though this particular command is not supported by the core and is only available in a limited set of devices - we only care about the controller configuration and not the actual command which is sent to the device). So let's use this type instead when a CHANGE READ COLUMN is requested. Signed-off-by: Miquel Raynal <miquel.raynal@bootlin.com> Link: https://lore.kernel.org/linux-mtd/20210505213750.257417-22-miquel.raynal@bootlin.com
This commit is contained in:
parent
698ddeb89e
commit
10938a08fc
@ -53,6 +53,7 @@
|
||||
#define PROG_RST BIT(8)
|
||||
#define PROG_GET_FEATURE BIT(9)
|
||||
#define PROG_SET_FEATURE BIT(10)
|
||||
#define PROG_CHG_RD_COL_ENH BIT(14)
|
||||
|
||||
#define INTR_STS_EN_REG 0x14
|
||||
#define INTR_SIG_EN_REG 0x18
|
||||
@ -622,7 +623,23 @@ static int anfc_param_read_type_exec(struct nand_chip *chip,
|
||||
static int anfc_data_read_type_exec(struct nand_chip *chip,
|
||||
const struct nand_subop *subop)
|
||||
{
|
||||
return anfc_misc_data_type_exec(chip, subop, PROG_PGRD);
|
||||
u32 prog_reg = PROG_PGRD;
|
||||
|
||||
/*
|
||||
* Experience shows that while in SDR mode sending a CHANGE READ COLUMN
|
||||
* command through the READ PAGE "type" always works fine, when in
|
||||
* NV-DDR mode the same command simply fails. However, it was also
|
||||
* spotted that any CHANGE READ COLUMN command sent through the CHANGE
|
||||
* READ COLUMN ENHANCED "type" would correctly work in both cases (SDR
|
||||
* and NV-DDR). So, for simplicity, let's program the controller with
|
||||
* the CHANGE READ COLUMN ENHANCED "type" whenever we are requested to
|
||||
* perform a CHANGE READ COLUMN operation.
|
||||
*/
|
||||
if (subop->instrs[0].ctx.cmd.opcode == NAND_CMD_RNDOUT &&
|
||||
subop->instrs[2].ctx.cmd.opcode == NAND_CMD_RNDOUTSTART)
|
||||
prog_reg = PROG_CHG_RD_COL_ENH;
|
||||
|
||||
return anfc_misc_data_type_exec(chip, subop, prog_reg);
|
||||
}
|
||||
|
||||
static int anfc_param_write_type_exec(struct nand_chip *chip,
|
||||
|
Loading…
x
Reference in New Issue
Block a user