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.

SPI read timeout

Other Parts Discussed in Thread: AM3352

Hello,

We've a custom board that has an AM3352 together with an SPI flash M25P32 (from STmicro). We managed to get the bootloader working, with the SPI flash being correctly detected:

SF: Detected M25P32 with page size 256 Bytes, erase size 64 KiB, total 4 MiB

However, whenever I want to read data from the SPI flash, we get an error stating that a timeout has occured:

SPI RXS timed out, status=0x00000002

Looking in the code, we found that this simply means that the RXS flash in the mcspi channel 0 status register is not set, so no data has "entered" the buffer. The status simply means that the transmit has completed.

I've measured the SPI clock, and the system works as expected, data is being transmitted on the MISO line. The line integrity is very good. I've tried lowering the frequency from 24MHz to 100KHz, but that didn't seem to solve the problem either.

Kind regards,

Arend

  • Hi Arend,

    Check if you have receiver enabled in the AM335X SPI_SCK pinmux. This is necessary for SPI read operations to function properly.

  • Hi Biser,

    Thank you for your quick reply. This is my pinmux for SPI:

    static struct module_pin_mux spi0_pin_mux[] = {
    	{OFFSET(spi0_sclk), (MODE(0) | RXACTIVE | PULLUDEN)},	/* SPI0_SCLK */
    	{OFFSET(spi0_d0), (MODE(0) | RXACTIVE |
    			PULLUDEN | PULLUP_EN)},			/* SPI0_D0 */
    	{OFFSET(spi0_d1), (MODE(0) | RXACTIVE | PULLUDEN)},	/* SPI0_D1 */
    	{OFFSET(spi0_cs0), (MODE(0) | RXACTIVE |
    			PULLUDEN | PULLUP_EN)},			/* SPI0_CS0 */
    	{OFFSET(spi0_cs1), (MODE(0) | RXACTIVE |
    			PULLUDEN | PULLUP_EN)},			/* SPI0_CS1 */
    	{-1},
    };

    So, RXACTIVE is already used. I was wondering, do I have to init SPI somewhere, just like I have to init I2C?
    e.g. i2c_init(CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);

    Kind regards,

    Arend

  • What is the software you are using?

  • Hello,

    What do you mean with "what software do you use"? I'm trying to build the bootloader, so I'm not trying to get my kernel to work yet. The mux that I send you, was in the file mux.c in the u-boot board folder.

    I'm building my bootloader on a linux platform. This codebase is provided in the 7.00 ezsdk package.

    I hope this answers your question?:-)

    Kind regards,

    Arend

  • Yes it does. I was asking because there are several different SW environments for the AM335X.

  • Hello Biser,

    The wiki you've send me is about the kernel, since I'm still on the bootloader I can't really use it right now. I read it though, hoping that it would give me some pointers. I've also read the reference manual, more specifically: the part talking about the RXS flag, but couldn't really come up with a good reason why it's not set.

    Kind regards,

    Arend

  • One more thing... when I try the SPI flash with my older bootloader, one I used for a previous project, I can read the flash  . So this tells me the hardware is working perfectly. So it must have something to do with my configuration I suspect....

  • Ok, stranger things are happening now. I CAN read the SPI flash, but only from the u-boot console. At startup I still get a timeout message: 

    CCCCxyzModem - CRC mode, 0(SOH)/368(STX)/0(CAN) packets, 6 retries
    Loaded 375004 bytes


    U-Boot 2013.10 (Sep 03 2014 - 17:50:02)

    I2C: ready
    DRAM: 128 MiB
    NAND: 512 MiB
    MMC: OMAP SD/MMC: 0, OMAP SD/MMC: 1
    SF: Detected M25P32 with page size 256 Bytes, erase size 64 KiB, total 4 MiB
    SPI RXS timed out, status=0x00000002
    *** Warning - spi_flash_read() failed, using default environment

    Net: cpsw
    Hit any key to stop autoboot: 0
    Booting from nand ...

    NAND read: device 0 offset 0x80000, size 0x40000
    262144 bytes read: OK

    NAND read: device 0 offset 0x200000, size 0x800000
    8388608 bytes read: OK
    Bad Linux ARM zImage magic!
    U-Boot#

    The default environment is effectively used in stead of my new environment ( I wrote a test variable ).

     I can however read and write perfectly from the u-boot terminal. Now I strongly believe that I missed an init somewherre, wouldn't you think?

  • Allright,

    I found something here, if I increase the SPI_WAIT_TIMEOUT in drivers/spi/omap3_spi.c from 3000000 to 30000000, it seems to work.

    I'm now struggling with erase problems during saveenv ( and again, not when I manually perform the function...although the functions used are exactly the same ... )

    edit:

    I've turned on debug messages and got the following output:

    U-Boot# saveenv
    Saving Environment to SPI Flash...
    SF: Got idcodes
    00000000: 20 20 16 10 00                                       ...
    SF: Detected M25P32 with page size 256 Bytes, erase size 64 KiB, total 4 MiB
    EXPORT  table = 877a16e4, htab.size = 277, htab.filled = 42, size = 131067
    Unsorted: n=42
              0: 8736afe8 ==> rdaddr     => 0x81000000
              1: 8736b024 ==> nandboot   => echo Booting from nand ...; run nandargs; nand read ${fdtaddr} NAND.golden.kernel.dt; nand read ${loadaddr} NAND.golden.kernel; bootz ${loadaddr} - ${fdtaddr}
              2: 8736b128 ==> ethaddr    => 7c:66:9d:06:1e:79
              3: 8736b178 ==> partitions => uuid_disk=${uuid_gpt_disk};name=rootfs,start=2MiB,size=-,uuid=${uuid_gpt_rootfs}
              4: 8736b1c8 ==> mtdids     => nand0=nand.0
              5: 8736b380 ==> board_rev  => 1
              6: 8736b3bc ==> mtddevname => NAND.golden.kernel
              7: 8736b40c ==> baudrate   => 115200
              8: 8736b4ac ==> fdt_high   => 0xa0000000
              9: 8736b4c0 ==> script_boot => if load ${devtype} ${devnum}:${rootpart} ${loadaddr} ${bootdir}/${bootfile}; then run findfdt; load ${devtype} ${devnum}:${rootpart} ${fdtaddr} ${bootdir}/${fdtfile};fi;
             10: 8736b4d4 ==> fdtaddr    => 0x80F80000
             11: 8736b4fc ==> nandargs   => setenv bootargs console=${console} ${optargs} root=${nandroot} rootfstype=${nandrootfstype}
             12: 8736b59c ==> cpu        => armv7
             13: 8736b5ec ==> dfu_alt_info_nand => NAND.SPL part 0 1;NAND.SPL.backup1 part 0 2;NAND.SPL.backup2 part 0 3;NAND.SPL.backup3 part 0 4;NAND.u-boot-spl-os part 0 5;NAND.u-boot part 0 6;NAND.u-boot-env part 0 7;NAND.u-boot-env.backup1 part 0 8;NAND.kernel part 0 9;NAND.rootfs part 0 10
             14: 8736b740 ==> ethact     => cpsw
             15: 8736b7b8 ==> bootcmd_nand => run nandboot;
             16: 8736b7e0 ==> stdout     => serial
             17: 8736b894 ==> console    => ttyO0,115200n8
             18: 8736b998 ==> static_ip  => ${ipaddr}:${serverip}:${gatewayip}:${netmask}:${hostname}::off
             19: 8736b9ac ==> mtddevnum  => 0
             20: 8736ba60 ==> nandroot   => ubi0:rootfs rw ubi.mtd=NAND.golden.rootfs,2048
             21: 8736bb14 ==> bootargs   => console=ttyO0,115200n8 root=ubi0:rootfs rw ubi.mtd=NAND.golden.rootfs,2048 rootfstype=ubifs rootwait=1
             22: 8736bb8c ==> fdtfile    => venus.dtb
             23: 8736bcb8 ==> arch       => arm
             24: 8736bce0 ==> vendor     => televic
             25: 8736bd08 ==> stdin      => serial
             26: 8736bd6c ==> board_name => Venus
             27: 8736bd80 ==> soc        => am33xx
             28: 8736bd94 ==> loadaddr   => 0x80200000
             29: 8736bde4 ==> board      => Venus
             30: 8736be20 ==> eth1addr   => 7c:66:9d:06:1e:7b
             31: 8736bf74 ==> rootpart   => 2
             32: 8736bfc4 ==> scan_boot  => echo Scanning ${devtype} ${devnum}...; for prefix in ${bootdir}; do for script in ${bootfile}; do run script_boot; done; done;
             33: 8736c0b4 ==> stderr     => serial
             34: 8736c168 ==> boot_targets =>   nand
             35: 8736c17c ==> partition  => nand0,0
             36: 8736c21c ==> bootdelay  => 3
             37: 8736c280 ==> nandrootfstype => ubifs rootwait=1
             38: 8736c35c ==> mtdparts   => mtdparts=nand.0:8M(NAND.golden.kernel),256K(NAND.golden.kernel.dt),8M(NAND.kernel),256K(NAND.kernel.dt),150M(NAND.golden.rootfs),150M(NAND.application.a.rootfs),150M(NAND.application.b.rootfs)
             39: 8736c398 ==> bootcmd    => for target in ${boot_targets}; do run bootcmd_${target}; done
             40: 8736c3e8 ==> ver        => U-Boot 2013.10 (Sep 09 2014 - 15:50:55)
             41: 8736c44c ==> bootfile   => zImage
    Erasing SPI flash...@1966080 131072 bytes in 2 sectors(65536B/sector)
    SF: erase d8 1e  0  0 (1e0000)
    SF: time out!
    SF: write page erase timed out
    SF: erase failed
    SF: 131072 bytes @1e0000 Erased: ERROR [-1]
    Command failed, result=1

    When doing a "manual" erase I get the following:

    U-Boot# sf erase 1E0000 20000
    SF: erase d8 1e  0  0 (1e0000)
    SF: erase d8 1f  0  0 (1f0000)
    SF: 131072 bytes @ 0x1e0000 Erased: OK
    U-Boot#

    AS you can see...the same...and yet not! If somebody could explain this to me...

    When I resolve the problem, I'll post it here for others to learn from.

    Kind regards,

    Arend

  • Allright...found it! finally!

    The fix is rather easy, once you know what to do. Just confirm that these lines are in your config:

    #define CONFIG_SF_DEFAULT_SPEED 24000000
    #define CONFIG_ENV_SPI_MAX_HZ CONFIG_SF_DEFAULT_SPEED

    and leave SPI_WAIT_TIMEOUT at its original value. This is one fix I did not see coming...

    Kind regards,

    Arend Lapere

  • Arend Lapere said:

    The fix is rather easy, once you know what to do. Just confirm that these lines are in your config:

    #define CONFIG_SF_DEFAULT_SPEED 24000000
    #define CONFIG_ENV_SPI_MAX_HZ CONFIG_SF_DEFAULT_SPEED

    I am trying to do some development work with SPI NOR flash on the TI Starter Kit reference board and am seeing a similar issue (RXS timed out with status 0x00000007).

    I have verified that the options you mentioned are set and they are but I still see the issue.  Are there any other changes you made when debugging this issue that you have left in your code that may be part of the fix?

    Thanks,

    Andy.

  • Hello Andy,

    When do you receive this error? When booting u-boot, like me? Or when you use something like sf read 80200000 0 10?

    In the TRM this state means that the EOT bit is set, as the RXS and TXS. So it seems as if all went well.

    If you see it at boot-time, try the following commands in the console:

    sf probe 0;
    sf read 80200000 0 10;

    If this works without problems, I guess it either has something to do with the speed being to high? instead of 24000000 MHz, check the datasheet of the used SPI flash.

    Also, don't forget to adjust your board settings to the correct flash settings. If your device is smaller then 1E0000h + 20000h, then I suspect strange things will happen too.

    The above is just speculation and some trial and error, for now, to see if the problem resembles ours :-)

    Kind regards,

    Arend

  • Hello Arend,

    The board boots U-Boot-SPL and U-Boot to the command prompt without reporting any errors.  I only see issues when I issue:

    sf probe 0;
    sf read 80200000 0xE0000 <num_bytes>

    If <num_bytes> is 0x16E350 or less then the read is OK, if <num_bytes> is greater than that value then it gives the timeout error.

    The two flash devices I have tried (one from Spansion one from Atmel) are both 8MiB devices.

    Andy.

  • Hello,

    The size then looks OK to me :-) you could try the first fix that I suggested:
     increase the SPI_WAIT_TIMEOUT in drivers/spi/omap3_spi.c from 3000000 to 30000000


    That helped me with timeouts due to size.

    Kind regards,

    Arend

  • Hi Arend,

    Did you have this problem, can not erase the sectors  except this first one? And even in the first sector, it can not be written correctly?

    Best Regards

    xixiguo

  • Hi Xixiguo,

    It looks like a timing issue. There are a few things to consider:

    - Wait longer before accessing the flash: some flashes require a "long timeout" before you can write/erase. This timeout can be found in the datasheet

    - Bus-integrity faults: you can verify this by simply measuring with a scope ( not a signal analyzer ) and check if the flanks are straight or bend. If they are bend you best slow down your frequency (easy fix) or increase your drive strength (not so easy)

    - A wrong driver, did you use a standard driver? if so, is it the correct one? If not, did you check that you did the correct order of execution. First you wait untill the write busy is low, send write enable followed by a sector erase. Again, you wait untill the write busy is low. You do another write enable, and now you write your data. note that some flashes will limit the amount of sequential data written to it. In my experience this is mostly the page length. Between each page write you'll have to re-enable the write enable latch again and again untill all data is written.

    I hope this can help you identify the problem :-)

    Kind regards,

    Arend

  • Hi Arend,

    First, thank you very much for your answer.

    For the driver :   We use micron N25Q32, and I add it's probe in stmicro.c as follow : 

    static const struct stmicro_spi_flash_params stmicro_spi_flash_table[] = {

    ...

    + {
    + .id = 0xba16,
    + .pages_per_sector = 256,
    + .nr_sectors = 64,
    + .name = "N25Q32",
    + },

    ...

    struct spi_flash *spi_flash_probe_stmicro(struct spi_slave *spi, u8 * idcode) {

    ...

    /* clear BP# bit for locked flash */ 
    spi_flash_cmd_write_status(flash, 0);

    ...

    Then I add the macro definition of CONFIG_SPI_FLASH_STMICRO. I got the flash was detected : 

    U-Boot# sf probe
    SF:: Got idcodes
    00000000: 20 ba 16 10 00 ....
    SF: Detected N25Q32 with page size 64 KiB, total 4 MiB

     Can it prove the drvier is correct?

    And when I erase the flash, it never come out error, it seemed erase correctly :

    SF: erase d8 1 0 0 (20000)
    status=0x0
    SF: erase d8 2 0 0 (30000)
    status=0x0
    SF: erase d8 3 0 0 (40000)
    status=0x0
    SF: erase d8 4 0 0 (50000)
    status=0x0
    SF: erase d8 5 0 0 (60000)
    status=0x0
    SF: erase d8 6 0 0 (70000)
    status=0x0
    SF: erase d8 7 0 0 (80000)
    status=0x0
    SF: erase d8 8 0 0 (90000)
    status=0x0
    SF: erase d8 9 0 0 (a0000)
    status=0x0
    SF: erase d8 a 0 0 (b0000)
    status=0x0
    SF: erase d8 b 0 0 (c0000)
    status=0x0
    SF: erase d8 c 0 0 (d0000)
    status=0x0
    SF: erase d8 d 0 0 (e0000)
    status=0x0
    SF: erase d8 e 0 0 (f0000)
    status=0x0
    SF: erase d8 f 0 0 (100000)
    status=0x0
    SF: erase d8 10 0 0 (110000)
    status=0x0
    SF: erase d8 11 0 0 (120000)
    status=0x0
    SF: erase d8 12 0 0 (130000)
    status=0x0
    SF: erase d8 13 0 0 (140000)
    status=0x0
    SF: erase d8 14 0 0 (150000)
    status=0x0
    SF: erase d8 15 0 0 (160000)
    status=0x0
    SF: erase d8 16 0 0 (170000)
    status=0x0
    SF: erase d8 17 0 0 (180000)
    status=0x0
    SF: erase d8 18 0 0 (190000)
    status=0x0
    SF: erase d8 19 0 0 (1a0000)
    status=0x0
    SF: erase d8 1a 0 0 (1b0000)
    status=0x0
    SF: erase d8 1b 0 0 (1c0000)
    status=0x0
    SF: erase d8 1c 0 0 (1d0000)
    status=0x0
    SF: erase d8 1d 0 0 (1e0000)
    status=0x0
    SF: erase d8 1e 0 0 (1f0000)
    status=0x0
    SF: erase d8 1f 0 0 (200000)
    status=0x0
    SF: erase d8 20 0 0 (210000)
    status=0x0
    SF: erase d8 21 0 0 (220000)
    status=0x0
    SF: Successfully erased 2228224 bytes @ 0x0

    But I read out the data, it is not 0xff. 

    Best Regards

    xixiguo

  • Hi Arend,

    I find something strange. It can be erased by only one sector at a time. Like use : 

    sf erase 0x10000 0x10000

    It will erase the second sector correctly. But the erase function int spi_flash_cmd_erase(struct spi_flash *flash, u32 offset, size_t len) use a while loop to erase N sector. I tried to wait longer before erase next sector, but it did not work.

    Best regards

    xixiguo