This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

How to use SPI1 and SPI2 on DM365 (Davinci)?

Other Parts Discussed in Thread: DA8XX, THS7303, TVP5146, OMAP-L138

How to use SPI1 and SPI2 on DM365 (Davinci)?

I am trying to use two SPIs: SPI1 and SPI2 on user space mode using spidev

but I couldn't enable two SPIs at the same time.

The only one SPI is enabled.

Followings are my modifined code.

Please advice me to enable two SPIs.

Am I missing something?

Thank you

====================================================
Version:
dvsdk_3_10_00_19
Linux dm365-evm 2.6.32-rc2-davinci1
====================================================
menuconfig
- SPI support
[*]   Debug support for SPI drivers
      *** SPI Master Controller Drivers ***
<*>   SPI controller driver for DaVinci/DA8xx SoC's
-*-   Utilities for Bitbanging SPI masters
<*>   GPIO-based bitbanging SPI Master
      *** SPI Protocol Masters ***
<*>   User mode SPI device driver support
< >   Infineon TLE62X0 (for power switching)

====================================================
Boot log: only spi1( /dev/spidev1.0) is enabled

....
at24 1-0050: 32768 byte 24c256 EEPROM (writable)
Error: Driver 'at25' is already registered, aborting...
NAND device: Manufacturer ID: 0x2c, Chip ID: 0xda (Micron NAND 256MiB 3,3V 8-bit)
2 NAND chips detected
Creating 5 MTD partitions on "davinci_nand.0":
0x000000000000-0x000000f00000 : "bootloader"
0x000000f00000-0x000001000000 : "params"
0x000001000000-0x000001400000 : "kernel"
0x000001400000-0x000021400000 : "filesystem1"
mtd: partition "filesystem1" extends beyond the end of device "davinci_nand.0" -- size truncated to 0x1ec00000
0x000020000000-0x000020000000 : "filesystem2"
mtd: partition "filesystem2" is out of reach -- disabled
davinci_nand davinci_nand.0: controller rev. 2.3
setup mode -1069853597, <NULL>
spi_davinci spi_davinci.1: Controller at 0xfec66800
console [netcon0] enabled
netconsole: network logging started
mice: PS/2 mouse device common for all mice
input: DM365 EVM Controls as /devices/platform/i2c_davinci.1/i2c-1/1-0025/input/input0
i2c /dev entries driver
Linux video capture interface: v2.00
ths7303 1-002c: chip found @ 0x58 (DaVinci I2C adapter)
ths7303 1-002c: ths7303 write failed
ths7303: probe of 1-002c failed with error -121
vpfe_init
vpfe-capture: vpss clock vpss_master enabled
vpfe-capture vpfe-capture: v4l2 device registered
vpfe-capture vpfe-capture: video device registered
EVM: switch to tvp5146 SD video input
.....

====================================================
board-dm365-evm.c

static struct spi_board_info dm365_evm_spi1_info[] __initconst = {
 {
  .modalias     = "spidev",
  .max_speed_hz = 25 * 1000 * 1000,
  .bus_num     = 1,
  .chip_select = 0,
  .mode      = SPI_MODE_0,
 },
 {
  .modalias     = "spidev",
  .max_speed_hz = 25 * 1000 * 1000,
  .bus_num     = 2,
  .chip_select = 0,
  .mode      = SPI_MODE_0,
 },
 
};

static struct spi_board_info dm365_evm_spi2_info[] __initconst = {
 {
  .modalias     = "spidev",
  .max_speed_hz = 25 * 1000 * 1000, /* at 3v3 */
  .bus_num     = 2,
  .chip_select = 0,
  .mode      = SPI_MODE_0,
 },
};

 

static __init void dm365_evm_init(void)
{
 evm_init_i2c();
 davinci_serial_init(&uart_config);

 dm365evm_emac_configure();
 dm365evm_mmc_configure();
 dm365evm_usb_configure();

 davinci_setup_mmc(0, &dm365evm_mmc_config);

 /* maybe setup mmc1/etc ... _after_ mmc0 */
 evm_init_cpld();

 dm365_init_asp(&dm365_evm_snd_data);
 dm365_init_rtc();
 dm365_init_ks(&dm365evm_ks_data);

 dm365_init_spi1(BIT(0), dm365_evm_spi1_info,
   ARRAY_SIZE(dm365_evm_spi1_info));
   
}

====================================================
dm365.c

static u64 dm365_spi1_dma_mask = DMA_BIT_MASK(32);

static struct davinci_spi_platform_data dm365_spi1_pdata = {
 .version  = SPI_VERSION_1,
 .num_chipselect = 2,
 .clk_internal = 1,
 .cs_hold = 1,
 .intr_level = 0,
 .poll_mode = 1, /* 0 -> interrupt mode 1-> polling mode */
 .use_dma = 1, /* when 1, value in poll_mode is ignored */
 .c2tdelay = 0,
 .t2cdelay = 0,
};

static struct resource dm365_spi1_resources[] = {
 {
  .start = 0x01c66800,
  .end   = 0x01c66fff,
  .flags = IORESOURCE_MEM,
 },
 {
  .start = IRQ_DM365_SPIINT0_0,
  .flags = IORESOURCE_IRQ,
 },
 {
  .start = EDMA_CHANNEL_ANY,
  .flags = IORESOURCE_DMA | IORESOURCE_DMA_RX_CHAN,
 },
 {
  .start = EDMA_CHANNEL_ANY,
  .flags = IORESOURCE_DMA | IORESOURCE_DMA_TX_CHAN,
 },
 {
  .start = EVENTQ_3,
  .flags = IORESOURCE_DMA | IORESOURCE_DMA_EVENT_Q,
 },
};

static struct platform_device dm365_spi1_device = {
 .name = "spi_davinci",
 .id = 1,
 .dev = {
  .dma_mask = &dm365_spi1_dma_mask,
  .coherent_dma_mask = DMA_BIT_MASK(32),
  .platform_data = &dm365_spi1_pdata,
 },
 .num_resources = ARRAY_SIZE(dm365_spi1_resources),
 .resource = dm365_spi1_resources,
};

 

// SPI 2 : 22222222222222
static u64 dm365_spi2_dma_mask = DMA_BIT_MASK(32);

static struct davinci_spi_platform_data dm365_spi2_pdata = {
 .version  = SPI_VERSION_1,
 .num_chipselect = 2,
 .clk_internal = 1,
 .cs_hold = 1,
 .intr_level = 0,
 .poll_mode = 1, /* 0 -> interrupt mode 1-> polling mode */
 .use_dma = 0, /* when 1, value in poll_mode is ignored */
 .c2tdelay = 0,
 .t2cdelay = 0,
};

static struct resource dm365_spi2_resources[] = {
 {
  .start = 0x01c67800,
  .end   = 0x01c67fff,
  .flags = IORESOURCE_MEM,
 },
 {
  .start = IRQ_DM365_SPIINT0_0,
  .flags = IORESOURCE_IRQ,
 },
 {
  .start = EDMA_CHANNEL_ANY,
  .flags = IORESOURCE_DMA | IORESOURCE_DMA_RX_CHAN,
 },
 {
  .start = EDMA_CHANNEL_ANY,
  .flags = IORESOURCE_DMA | IORESOURCE_DMA_TX_CHAN,
 },
 {
  .start = EVENTQ_3,
  .flags = IORESOURCE_DMA | IORESOURCE_DMA_EVENT_Q,
 },
};

static struct platform_device dm365_spi2_device = {
 .name = "spi_davinci_Zslave",
 .id = 2,
 .dev = {
  .dma_mask = &dm365_spi2_dma_mask,
  .coherent_dma_mask = DMA_BIT_MASK(32),
  .platform_data = &dm365_spi2_pdata,
 },
 .num_resources = ARRAY_SIZE(dm365_spi2_resources),
 .resource = dm365_spi2_resources,
};

 

void __init dm365_init_spi1(unsigned chipselect_mask,
  struct spi_board_info *info, unsigned len)
{
 davinci_cfg_reg(DM365_SPI1_SCLK);
 davinci_cfg_reg(DM365_SPI1_SDI);
 davinci_cfg_reg(DM365_SPI1_SDO);

 /* not all slaves will be wired up */
 if (chipselect_mask & BIT(0))
  davinci_cfg_reg(DM365_SPI1_SDENA0);
 if (chipselect_mask & BIT(1))
  davinci_cfg_reg(DM365_SPI1_SDENA1);


 davinci_cfg_reg(DM365_SPI2_SCLK);
 davinci_cfg_reg(DM365_SPI2_SDI);
 davinci_cfg_reg(DM365_SPI2_SDO);

 /* not all slaves will be wired up */
 if (chipselect_mask & BIT(0))
   davinci_cfg_reg(DM365_SPI2_SDENA0);
 if (chipselect_mask & BIT(1))
  davinci_cfg_reg(DM365_SPI2_SDENA1);


 platform_device_register(&dm365_spi1_device);
 platform_device_register(&dm365_spi2_device);

 spi_register_board_info(info, len);
}

====================================================

 

  • Hi,

    I think the problem is with the value of the 'name ' field of the 'dm365_spi2_device' structure.

    It should be "spi_davinci" and not "spi_davinci_Zslave".  Just a typo perhaps?

  • Thank you for pointing out.

    I was trying to do many different kinds and it was left as "spi_davinci_Zslave".

    Even if i correct it to "spi_davinci", it doesn't show up two SPIs.

     

    Thank you

  • Hi,

    I am attempting to do a similar thing but am currently working with SPI0 and SPI1.  At first only SPI0 would show up, but then I was able to get them both working simultaneously by specifying different IRQs - I believe that could be your problem here.  In the code you pasted SPIINT0_0 is given as the IRQ for both SPI1 and SPI2 - maybe try using SPIINT0_1 (43) in dm365_spi2_resources[] and see if that helps?

    In fact, I would think that for SPI1 and SPI2 we should be using SPIINT1_0, SPIINT1_1, SPIINT2_0 and SPIINT2_1, but the first 3 of those overlap with EDMA IRQs... does that mean we can't use SPI1 in interrupt mode if EDMA is in use?

    Kind regards

    Ian

  • Hi,

    I'm developing IP camera(DM365) with VA(Video Analytics) module(DM6435).

    The communication between DM365 and DM6435 is performed using SPI.

    After enabling DM365 SPI in kernel compile option(make menuconfig), after booting that kernel, there is no /dev/spidev* device file. Why?

    My kernel version is 2.6.18 and DVSDK version is 2.10.01.18.

    Booting logs are the followings.

     

    04000000-0x07000000 : "area"
    nand_davinci nand_davinci.0: hardware revision: 2.3
    MUX: initialized SPI0_SCLK
    MUX: initialized SPI0_SDO)
    MUX: initialized SPI0_SDI
    MUX: initialized SPI0_SDENA0
    dm_spi.0: davinci SPI Controller driver at 0xc5066000 (irq = 42) use_dma=0

  • Hello Ian,

    I also happen with the SPI1 IRQ issue for SPIINT1_0 and SPIINT1_1 overlap with EDMA IRQs.

    Can your SPI1 work with SPI0's IRQ SPIINT0_1?  It's appoint to process SPI0.

    Thanks

    Peter

  • The spi will be dev/mtd5 (See the LSP 2.0 Manual).

    Thanks and regards

    Nikhil

  • Hello SooYoung,

    I am encountering the same problems on OMAP-L138.
    Did you succeed in working with both SPI ? If so, do you mind sending the relevant code ?

    Many Thanks!

    Ran

  • Hello Ran

    I couldn't use two SPI simultaneously.
    There were dead line to finish project up,
    So I used SPI1 with kernel module and made device driver for SPI2 from the source in the internet. 
    You can google it, 
    or... 
    Oh, I saved link.
    they are look different, but when you cafully see whole code, they are same.

  • Peter Jiao said:
    Can your SPI1 work with SPI0's IRQ SPIINT0_1?

    Hi Peter,

    What I ended up doing is just running all my SPIs in polled mode and haven't actually tried using interrupt or DMA since it is working adequately for me.  My resources are as follows:

     

    static struct resource dm365_spi1_resources[] = {

            {

                    .start = 0x01c66800,   // sprufg5a, Table 7.

                    .end   = 0x01c66fff,

                    .flags = IORESOURCE_MEM,

            },

            {

                    .start = IRQ_DM365_SPIINT3_0,//IRQ_CCERRINT,   // CCERRINT and DM365_SPIINT1_0 are the same. sprufg5a, Table 54

                    .flags = IORESOURCE_IRQ,

            },

            {

                    .start = 15,   // sprufi0, Table 2-5

                    .flags = IORESOURCE_DMA | IORESOURCE_DMA_RX_CHAN,

            },

            {

                    .start = 14,

                    .flags = IORESOURCE_DMA | IORESOURCE_DMA_TX_CHAN,

            },

            {

                    .start = EVENTQ_3,

                    .flags = IORESOURCE_DMA | IORESOURCE_DMA_EVENT_Q,

            },

    };

    static struct resource dm365_spi2_resources[] = {

            {

                    .start = 0x01c67800,   // sprufg5a, Table 7.

                    .end   = 0x01c67fff,

                    .flags = IORESOURCE_MEM,

            },

            {

                    .start = IRQ_DM365_SPINT2_1,    // sprufg5a, Table 54

                    .flags = IORESOURCE_IRQ,

            },

            {

                    .start = 11,   // sprufi0, Table 2-5

                    .flags = IORESOURCE_DMA | IORESOURCE_DMA_RX_CHAN,

            },

            {

                    .start = 10,

                    .flags = IORESOURCE_DMA | IORESOURCE_DMA_TX_CHAN,

            },

            {

                    .start = EVENTQ_3,

                    .flags = IORESOURCE_DMA | IORESOURCE_DMA_EVENT_Q,

            },

    };

    Looking back, I actually have no idea why I specified SPIINT3_0 for SPI1, but I suppose it's working because I'm not actually using interrupt mode.

    sylee@probedigital.com said:
    After enabling DM365 SPI in kernel compile option(make menuconfig), after booting that kernel, there is no /dev/spidev* device file. Why?

    Hi Sylee,

    spidev is a separate kernel config option.  You need to enable "User mode SPI device driver support" in menuconfig and then you should get spidev device files for your SPI devices.  I can't remember if there were any other complications - I only used spidev briefly a long time ago.