123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106 |
- /*
- * linux/arch/arm/mach-omap2/gpmc-onenand.c
- *
- * Copyright (C) 2006 - 2009 Nokia Corporation
- * Contacts: Juha Yrjola
- * Tony Lindgren
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation.
- */
- #include <linux/string.h>
- #include <linux/kernel.h>
- #include <linux/platform_device.h>
- #include <linux/mtd/onenand_regs.h>
- #include <linux/io.h>
- #include <linux/platform_data/mtd-onenand-omap2.h>
- #include <linux/err.h>
- #include <asm/mach/flash.h>
- #include "gpmc.h"
- #include "soc.h"
- #include "gpmc-onenand.h"
- #define ONENAND_IO_SIZE SZ_128K
- #define ONENAND_FLAG_SYNCREAD (1 << 0)
- #define ONENAND_FLAG_SYNCWRITE (1 << 1)
- #define ONENAND_FLAG_HF (1 << 2)
- #define ONENAND_FLAG_VHF (1 << 3)
- static unsigned onenand_flags;
- static unsigned latency;
- static struct omap_onenand_platform_data *gpmc_onenand_data;
- static struct resource gpmc_onenand_resource = {
- .flags = IORESOURCE_MEM,
- };
- static struct platform_device gpmc_onenand_device = {
- .name = "omap2-onenand",
- .id = -1,
- .num_resources = 1,
- .resource = &gpmc_onenand_resource,
- };
- static struct gpmc_timings omap2_onenand_calc_async_timings(void)
- {
- struct gpmc_device_timings dev_t;
- struct gpmc_timings t;
- const int t_cer = 15;
- const int t_avdp = 12;
- const int t_aavdh = 7;
- const int t_ce = 76;
- const int t_aa = 76;
- const int t_oe = 20;
- const int t_cez = 20; /* max of t_cez, t_oez */
- const int t_wpl = 40;
- const int t_wph = 30;
- memset(&dev_t, 0, sizeof(dev_t));
- dev_t.mux = true;
- dev_t.t_avdp_r = max_t(int, t_avdp, t_cer) * 1000;
- dev_t.t_avdp_w = dev_t.t_avdp_r;
- dev_t.t_aavdh = t_aavdh * 1000;
- dev_t.t_aa = t_aa * 1000;
- dev_t.t_ce = t_ce * 1000;
- dev_t.t_oe = t_oe * 1000;
- dev_t.t_cez_r = t_cez * 1000;
- dev_t.t_cez_w = dev_t.t_cez_r;
- dev_t.t_wpl = t_wpl * 1000;
- dev_t.t_wph = t_wph * 1000;
- gpmc_calc_timings(&t, &dev_t);
- return t;
- }
- static int gpmc_set_async_mode(int cs, struct gpmc_timings *t)
- {
- /* Configure GPMC for asynchronous read */
- gpmc_cs_write_reg(cs, GPMC_CS_CONFIG1,
- GPMC_CONFIG1_DEVICESIZE_16 |
- GPMC_CONFIG1_MUXADDDATA);
- return gpmc_cs_set_timings(cs, t);
- }
- static void omap2_onenand_set_async_mode(void __iomem *onenand_base)
- {
- u32 reg;
- /* Ensure sync read and sync write are disabled */
- reg = readw(onenand_base + ONENAND_REG_SYS_CFG1);
- reg &= ~ONENAND_SYS_CFG1_SYNC_READ & ~ONENAND_SYS_CFG1_SYNC_WRITE;
- writew(reg, onenand_base + ONENAND_REG_SYS_CFG1);
- }
- static void set_onenand_cfg(void __iomem *onenand_base)
- {
- u32 reg;
|