aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorNicolas Ferre <nicolas.ferre@atmel.com>2011-07-04 10:17:53 -0400
committerArtem Bityutskiy <artem.bityutskiy@intel.com>2011-09-11 08:02:15 -0400
commitfb5427508abbd635e877fabdf55795488119c2d6 (patch)
treefc37be0505a74d27df25111f851843ea271c9eb2
parent57b078a09bf0ab3f0babcfe6ecb2ac226d9178be (diff)
mtd: atmel_nand: optimize read/write buffer functions
For PIO NAND access functions, we use the features of the SMC: - no need to take into account the NAND bus width: SMC will deal with this - use of an IO memcpy on the NAND chip-select space is able to generate proper SMC behavior. Signed-off-by: Nicolas Ferre <nicolas.ferre@atmel.com> Signed-off-by: Artem Bityutskiy <dedekind1@gmail.com>
-rw-r--r--drivers/mtd/nand/atmel_nand.c45
1 files changed, 4 insertions, 41 deletions
diff --git a/drivers/mtd/nand/atmel_nand.c b/drivers/mtd/nand/atmel_nand.c
index ee6e26e78a1a..23e5d77c39fc 100644
--- a/drivers/mtd/nand/atmel_nand.c
+++ b/drivers/mtd/nand/atmel_nand.c
@@ -161,37 +161,6 @@ static int atmel_nand_device_ready(struct mtd_info *mtd)
161 !!host->board->rdy_pin_active_low; 161 !!host->board->rdy_pin_active_low;
162} 162}
163 163
164/*
165 * Minimal-overhead PIO for data access.
166 */
167static void atmel_read_buf8(struct mtd_info *mtd, u8 *buf, int len)
168{
169 struct nand_chip *nand_chip = mtd->priv;
170
171 __raw_readsb(nand_chip->IO_ADDR_R, buf, len);
172}
173
174static void atmel_read_buf16(struct mtd_info *mtd, u8 *buf, int len)
175{
176 struct nand_chip *nand_chip = mtd->priv;
177
178 __raw_readsw(nand_chip->IO_ADDR_R, buf, len / 2);
179}
180
181static void atmel_write_buf8(struct mtd_info *mtd, const u8 *buf, int len)
182{
183 struct nand_chip *nand_chip = mtd->priv;
184
185 __raw_writesb(nand_chip->IO_ADDR_W, buf, len);
186}
187
188static void atmel_write_buf16(struct mtd_info *mtd, const u8 *buf, int len)
189{
190 struct nand_chip *nand_chip = mtd->priv;
191
192 __raw_writesw(nand_chip->IO_ADDR_W, buf, len / 2);
193}
194
195static void dma_complete_func(void *completion) 164static void dma_complete_func(void *completion)
196{ 165{
197 complete(completion); 166 complete(completion);
@@ -266,33 +235,27 @@ err_buf:
266static void atmel_read_buf(struct mtd_info *mtd, u8 *buf, int len) 235static void atmel_read_buf(struct mtd_info *mtd, u8 *buf, int len)
267{ 236{
268 struct nand_chip *chip = mtd->priv; 237 struct nand_chip *chip = mtd->priv;
269 struct atmel_nand_host *host = chip->priv;
270 238
271 if (use_dma && len > mtd->oobsize) 239 if (use_dma && len > mtd->oobsize)
272 /* only use DMA for bigger than oob size: better performances */ 240 /* only use DMA for bigger than oob size: better performances */
273 if (atmel_nand_dma_op(mtd, buf, len, 1) == 0) 241 if (atmel_nand_dma_op(mtd, buf, len, 1) == 0)
274 return; 242 return;
275 243
276 if (host->board->bus_width_16) 244 /* if no DMA operation possible, use PIO */
277 atmel_read_buf16(mtd, buf, len); 245 memcpy_fromio(buf, chip->IO_ADDR_R, len);
278 else
279 atmel_read_buf8(mtd, buf, len);
280} 246}
281 247
282static void atmel_write_buf(struct mtd_info *mtd, const u8 *buf, int len) 248static void atmel_write_buf(struct mtd_info *mtd, const u8 *buf, int len)
283{ 249{
284 struct nand_chip *chip = mtd->priv; 250 struct nand_chip *chip = mtd->priv;
285 struct atmel_nand_host *host = chip->priv;
286 251
287 if (use_dma && len > mtd->oobsize) 252 if (use_dma && len > mtd->oobsize)
288 /* only use DMA for bigger than oob size: better performances */ 253 /* only use DMA for bigger than oob size: better performances */
289 if (atmel_nand_dma_op(mtd, (void *)buf, len, 0) == 0) 254 if (atmel_nand_dma_op(mtd, (void *)buf, len, 0) == 0)
290 return; 255 return;
291 256
292 if (host->board->bus_width_16) 257 /* if no DMA operation possible, use PIO */
293 atmel_write_buf16(mtd, buf, len); 258 memcpy_toio(chip->IO_ADDR_W, buf, len);
294 else
295 atmel_write_buf8(mtd, buf, len);
296} 259}
297 260
298/* 261/*