Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-only
0002 /*
0003  * DM355 leopard board support
0004  *
0005  * Based on board-dm355-evm.c
0006  */
0007 #include <linux/kernel.h>
0008 #include <linux/init.h>
0009 #include <linux/err.h>
0010 #include <linux/platform_device.h>
0011 #include <linux/mtd/mtd.h>
0012 #include <linux/mtd/partitions.h>
0013 #include <linux/mtd/rawnand.h>
0014 #include <linux/i2c.h>
0015 #include <linux/gpio.h>
0016 #include <linux/clk.h>
0017 #include <linux/spi/spi.h>
0018 #include <linux/spi/eeprom.h>
0019 #include <linux/platform_data/i2c-davinci.h>
0020 #include <linux/platform_data/mmc-davinci.h>
0021 #include <linux/platform_data/mtd-davinci.h>
0022 #include <linux/platform_data/usb-davinci.h>
0023 
0024 #include <asm/mach-types.h>
0025 #include <asm/mach/arch.h>
0026 
0027 #include "common.h"
0028 #include "serial.h"
0029 #include "davinci.h"
0030 
0031 /* NOTE:  this is geared for the standard config, with a socketed
0032  * 2 GByte Micron NAND (MT29F16G08FAA) using 128KB sectors.  If you
0033  * swap chips, maybe with a different block size, partitioning may
0034  * need to be changed.
0035  */
0036 #define NAND_BLOCK_SIZE     SZ_128K
0037 
0038 static struct mtd_partition davinci_nand_partitions[] = {
0039     {
0040         /* UBL (a few copies) plus U-Boot */
0041         .name       = "bootloader",
0042         .offset     = 0,
0043         .size       = 15 * NAND_BLOCK_SIZE,
0044         .mask_flags = MTD_WRITEABLE, /* force read-only */
0045     }, {
0046         /* U-Boot environment */
0047         .name       = "params",
0048         .offset     = MTDPART_OFS_APPEND,
0049         .size       = 1 * NAND_BLOCK_SIZE,
0050         .mask_flags = 0,
0051     }, {
0052         .name       = "kernel",
0053         .offset     = MTDPART_OFS_APPEND,
0054         .size       = SZ_4M,
0055         .mask_flags = 0,
0056     }, {
0057         .name       = "filesystem1",
0058         .offset     = MTDPART_OFS_APPEND,
0059         .size       = SZ_512M,
0060         .mask_flags = 0,
0061     }, {
0062         .name       = "filesystem2",
0063         .offset     = MTDPART_OFS_APPEND,
0064         .size       = MTDPART_SIZ_FULL,
0065         .mask_flags = 0,
0066     }
0067     /* two blocks with bad block table (and mirror) at the end */
0068 };
0069 
0070 static struct davinci_nand_pdata davinci_nand_data = {
0071     .core_chipsel       = 0,
0072     .mask_chipsel       = BIT(14),
0073     .parts          = davinci_nand_partitions,
0074     .nr_parts       = ARRAY_SIZE(davinci_nand_partitions),
0075     .engine_type        = NAND_ECC_ENGINE_TYPE_ON_HOST,
0076     .ecc_placement      = NAND_ECC_PLACEMENT_INTERLEAVED,
0077     .ecc_bits       = 4,
0078     .bbt_options        = NAND_BBT_USE_FLASH,
0079 };
0080 
0081 static struct resource davinci_nand_resources[] = {
0082     {
0083         .start      = DM355_ASYNC_EMIF_DATA_CE0_BASE,
0084         .end        = DM355_ASYNC_EMIF_DATA_CE0_BASE + SZ_32M - 1,
0085         .flags      = IORESOURCE_MEM,
0086     }, {
0087         .start      = DM355_ASYNC_EMIF_CONTROL_BASE,
0088         .end        = DM355_ASYNC_EMIF_CONTROL_BASE + SZ_4K - 1,
0089         .flags      = IORESOURCE_MEM,
0090     },
0091 };
0092 
0093 static struct platform_device davinci_nand_device = {
0094     .name           = "davinci_nand",
0095     .id         = 0,
0096 
0097     .num_resources      = ARRAY_SIZE(davinci_nand_resources),
0098     .resource       = davinci_nand_resources,
0099 
0100     .dev            = {
0101         .platform_data  = &davinci_nand_data,
0102     },
0103 };
0104 
0105 static struct davinci_i2c_platform_data i2c_pdata = {
0106     .bus_freq   = 400   /* kHz */,
0107     .bus_delay  = 0 /* usec */,
0108 };
0109 
0110 static int leopard_mmc_gpio = -EINVAL;
0111 
0112 static void dm355leopard_mmcsd_gpios(unsigned gpio)
0113 {
0114     gpio_request(gpio + 0, "mmc0_ro");
0115     gpio_request(gpio + 1, "mmc0_cd");
0116     gpio_request(gpio + 2, "mmc1_ro");
0117     gpio_request(gpio + 3, "mmc1_cd");
0118 
0119     /* we "know" these are input-only so we don't
0120      * need to call gpio_direction_input()
0121      */
0122 
0123     leopard_mmc_gpio = gpio;
0124 }
0125 
0126 static struct i2c_board_info dm355leopard_i2c_info[] = {
0127     { I2C_BOARD_INFO("dm355leopard_msp", 0x25),
0128         .platform_data = dm355leopard_mmcsd_gpios,
0129         /* plus irq */ },
0130     /* { I2C_BOARD_INFO("tlv320aic3x", 0x1b), }, */
0131     /* { I2C_BOARD_INFO("tvp5146", 0x5d), }, */
0132 };
0133 
0134 static void __init leopard_init_i2c(void)
0135 {
0136     davinci_init_i2c(&i2c_pdata);
0137 
0138     gpio_request(5, "dm355leopard_msp");
0139     gpio_direction_input(5);
0140     dm355leopard_i2c_info[0].irq = gpio_to_irq(5);
0141 
0142     i2c_register_board_info(1, dm355leopard_i2c_info,
0143             ARRAY_SIZE(dm355leopard_i2c_info));
0144 }
0145 
0146 static struct resource dm355leopard_dm9000_rsrc[] = {
0147     {
0148         /* addr */
0149         .start  = 0x04000000,
0150         .end    = 0x04000001,
0151         .flags  = IORESOURCE_MEM,
0152     }, {
0153         /* data */
0154         .start  = 0x04000016,
0155         .end    = 0x04000017,
0156         .flags  = IORESOURCE_MEM,
0157     }, {
0158         .flags  = IORESOURCE_IRQ
0159             | IORESOURCE_IRQ_HIGHEDGE /* rising (active high) */,
0160     },
0161 };
0162 
0163 static struct platform_device dm355leopard_dm9000 = {
0164     .name       = "dm9000",
0165     .id     = -1,
0166     .resource   = dm355leopard_dm9000_rsrc,
0167     .num_resources  = ARRAY_SIZE(dm355leopard_dm9000_rsrc),
0168 };
0169 
0170 static struct platform_device *davinci_leopard_devices[] __initdata = {
0171     &dm355leopard_dm9000,
0172     &davinci_nand_device,
0173 };
0174 
0175 static void __init dm355_leopard_map_io(void)
0176 {
0177     dm355_init();
0178 }
0179 
0180 static int dm355leopard_mmc_get_cd(int module)
0181 {
0182     if (!gpio_is_valid(leopard_mmc_gpio))
0183         return -ENXIO;
0184     /* low == card present */
0185     return !gpio_get_value_cansleep(leopard_mmc_gpio + 2 * module + 1);
0186 }
0187 
0188 static int dm355leopard_mmc_get_ro(int module)
0189 {
0190     if (!gpio_is_valid(leopard_mmc_gpio))
0191         return -ENXIO;
0192     /* high == card's write protect switch active */
0193     return gpio_get_value_cansleep(leopard_mmc_gpio + 2 * module + 0);
0194 }
0195 
0196 static struct davinci_mmc_config dm355leopard_mmc_config = {
0197     .get_cd     = dm355leopard_mmc_get_cd,
0198     .get_ro     = dm355leopard_mmc_get_ro,
0199     .wires      = 4,
0200     .max_freq       = 50000000,
0201     .caps           = MMC_CAP_MMC_HIGHSPEED | MMC_CAP_SD_HIGHSPEED,
0202 };
0203 
0204 /* Don't connect anything to J10 unless you're only using USB host
0205  * mode *and* have to do so with some kind of gender-bender.  If
0206  * you have proper Mini-B or Mini-A cables (or Mini-A adapters)
0207  * the ID pin won't need any help.
0208  */
0209 #define USB_ID_VALUE    1   /* ID pulled low */
0210 
0211 static struct spi_eeprom at25640a = {
0212     .byte_len   = SZ_64K / 8,
0213     .name       = "at25640a",
0214     .page_size  = 32,
0215     .flags      = EE_ADDR2,
0216 };
0217 
0218 static const struct spi_board_info dm355_leopard_spi_info[] __initconst = {
0219     {
0220         .modalias   = "at25",
0221         .platform_data  = &at25640a,
0222         .max_speed_hz   = 10 * 1000 * 1000, /* at 3v3 */
0223         .bus_num    = 0,
0224         .chip_select    = 0,
0225         .mode       = SPI_MODE_0,
0226     },
0227 };
0228 
0229 static __init void dm355_leopard_init(void)
0230 {
0231     struct clk *aemif;
0232     int ret;
0233 
0234     dm355_register_clocks();
0235 
0236     ret = dm355_gpio_register();
0237     if (ret)
0238         pr_warn("%s: GPIO init failed: %d\n", __func__, ret);
0239 
0240     gpio_request(9, "dm9000");
0241     gpio_direction_input(9);
0242     dm355leopard_dm9000_rsrc[2].start = gpio_to_irq(9);
0243 
0244     aemif = clk_get(&dm355leopard_dm9000.dev, "aemif");
0245     if (!WARN(IS_ERR(aemif), "unable to get AEMIF clock\n"))
0246         clk_prepare_enable(aemif);
0247 
0248     platform_add_devices(davinci_leopard_devices,
0249                  ARRAY_SIZE(davinci_leopard_devices));
0250     leopard_init_i2c();
0251     davinci_serial_init(dm355_serial_device);
0252 
0253     /* NOTE:  NAND flash timings set by the UBL are slower than
0254      * needed by MT29F16G08FAA chips ... EMIF.A1CR is 0x40400204
0255      * but could be 0x0400008c for about 25% faster page reads.
0256      */
0257 
0258     gpio_request(2, "usb_id_toggle");
0259     gpio_direction_output(2, USB_ID_VALUE);
0260     /* irlml6401 switches over 1A in under 8 msec */
0261     davinci_setup_usb(1000, 8);
0262 
0263     davinci_setup_mmc(0, &dm355leopard_mmc_config);
0264     davinci_setup_mmc(1, &dm355leopard_mmc_config);
0265 
0266     dm355_init_spi0(BIT(0), dm355_leopard_spi_info,
0267             ARRAY_SIZE(dm355_leopard_spi_info));
0268 }
0269 
0270 MACHINE_START(DM355_LEOPARD, "DaVinci DM355 leopard")
0271     .atag_offset  = 0x100,
0272     .map_io       = dm355_leopard_map_io,
0273     .init_irq     = dm355_init_irq,
0274     .init_time  = dm355_init_time,
0275     .init_machine = dm355_leopard_init,
0276     .init_late  = davinci_init_late,
0277     .dma_zone_size  = SZ_128M,
0278 MACHINE_END