Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 2230b76b authored by Bryan Wu's avatar Bryan Wu Committed by David Woodhouse
Browse files

[MTD] m25p80: add FAST_READ access support to M25Pxx

parent afc4bca6
Loading
Loading
Loading
Loading
+7 −0
Original line number Diff line number Diff line
@@ -77,6 +77,13 @@ config MTD_M25P80
	  if you want to specify device partitioning or to use a device which
	  doesn't support the JEDEC ID instruction.

config M25PXX_USE_FAST_READ
	bool "Use FAST_READ OPCode allowing SPI CLK <= 50MHz"
	depends on MTD_M25P80
	default y
	help
	  This option enables FAST_READ access supported by ST M25Pxx.

config MTD_SLRAM
	tristate "Uncached system RAM"
	help
+21 −10
Original line number Diff line number Diff line
@@ -33,7 +33,7 @@
/* Flash opcodes. */
#define	OPCODE_WREN		0x06	/* Write enable */
#define	OPCODE_RDSR		0x05	/* Read status register */
#define	OPCODE_READ		0x03	/* Read data bytes (low frequency) */
#define	OPCODE_NORM_READ	0x03	/* Read data bytes (low frequency) */
#define	OPCODE_FAST_READ	0x0b	/* Read data bytes (high frequency) */
#define	OPCODE_PP		0x02	/* Page program (up to 256 bytes) */
#define	OPCODE_BE_4K 		0x20	/* Erase 4KiB block */
@@ -52,7 +52,15 @@

/* Define max times to check status register before we give up. */
#define	MAX_READY_WAIT_COUNT	100000
#define	CMD_SIZE		4

#ifdef CONFIG_M25PXX_USE_FAST_READ
#define OPCODE_READ 	OPCODE_FAST_READ
#define FAST_READ_DUMMY_BYTE 1
#else
#define OPCODE_READ 	OPCODE_NORM_READ
#define FAST_READ_DUMMY_BYTE 0
#endif

#ifdef CONFIG_MTD_PARTITIONS
#define	mtd_has_partitions()	(1)
@@ -68,7 +76,7 @@ struct m25p {
	struct mtd_info		mtd;
	unsigned		partitioned:1;
	u8			erase_opcode;
	u8			command[4];
	u8			command[CMD_SIZE + FAST_READ_DUMMY_BYTE];
};

static inline struct m25p *mtd_to_m25p(struct mtd_info *mtd)
@@ -167,7 +175,7 @@ static int erase_sector(struct m25p *flash, u32 offset)
	flash->command[2] = offset >> 8;
	flash->command[3] = offset;

	spi_write(flash->spi, flash->command, sizeof(flash->command));
	spi_write(flash->spi, flash->command, CMD_SIZE);

	return 0;
}
@@ -253,8 +261,12 @@ static int m25p80_read(struct mtd_info *mtd, loff_t from, size_t len,
	spi_message_init(&m);
	memset(t, 0, (sizeof t));

	/* NOTE:
	 * OPCODE_FAST_READ (if available) is faster.
	 * Should add 1 byte DUMMY_BYTE.
	 */
	t[0].tx_buf = flash->command;
	t[0].len = sizeof(flash->command);
	t[0].len = CMD_SIZE + FAST_READ_DUMMY_BYTE;
	spi_message_add_tail(&t[0], &m);

	t[1].rx_buf = buf;
@@ -287,7 +299,7 @@ static int m25p80_read(struct mtd_info *mtd, loff_t from, size_t len,

	spi_sync(flash->spi, &m);

	*retlen = m.actual_length - sizeof(flash->command);
	*retlen = m.actual_length - CMD_SIZE - FAST_READ_DUMMY_BYTE;

	mutex_unlock(&flash->lock);

@@ -325,7 +337,7 @@ static int m25p80_write(struct mtd_info *mtd, loff_t to, size_t len,
	memset(t, 0, (sizeof t));

	t[0].tx_buf = flash->command;
	t[0].len = sizeof(flash->command);
	t[0].len = CMD_SIZE;
	spi_message_add_tail(&t[0], &m);

	t[1].tx_buf = buf;
@@ -354,7 +366,7 @@ static int m25p80_write(struct mtd_info *mtd, loff_t to, size_t len,

		spi_sync(flash->spi, &m);

		*retlen = m.actual_length - sizeof(flash->command);
		*retlen = m.actual_length - CMD_SIZE;
	} else {
		u32 i;

@@ -364,7 +376,7 @@ static int m25p80_write(struct mtd_info *mtd, loff_t to, size_t len,
		t[1].len = page_size;
		spi_sync(flash->spi, &m);

		*retlen = m.actual_length - sizeof(flash->command);
		*retlen = m.actual_length - CMD_SIZE;

		/* write everything in PAGESIZE chunks */
		for (i = page_size; i < len; i += page_size) {
@@ -387,8 +399,7 @@ static int m25p80_write(struct mtd_info *mtd, loff_t to, size_t len,
			spi_sync(flash->spi, &m);

			if (retlen)
				*retlen += m.actual_length
					- sizeof(flash->command);
				*retlen += m.actual_length - CMD_SIZE;
		}
	}