Shop OBEX P1 Docs P2 Docs Learn Events
uSD Drivers FSRW and FAT32, both using same low level SPI drivers — Parallax Forums

uSD Drivers FSRW and FAT32, both using same low level SPI drivers

RaymanRayman Posts: 13,900
edited 2023-12-20 22:00 in Propeller 2

Here two uSD drivers that can both use your choice of three low level drivers.
One is inline assembly and doesn't need a cog, one uses a cog, and the other also uses a cog but adds audio output.

FSRW is a very minimalistic with only root directory access
FAT32 has more features and can access sub-directories

Tested with Propeller Tool 2.9.3

@Wuerfel_21 connected the low level driver from P2 version of FSRW to FAT32, also added the audio version..
FSRW was then modified a hair to also use the same low level drivers.

There's been a history of FSRW becoming broken by compiler changes, but I think it's OK now.
But, there's only been limited testing so far.

Attached are simple tests of both drivers.

Note: Small change made to FAT32 as suggested by @Wuerfel_21
Also made change suggested by @ke4pjw

Update: See post #23 for updated version of bashed with better release() so that can close one file and open another...

Comments

  • Thanks for putting this state of play summary and code together Rayman. I've always been a bit apprehensive as to finding out which P2 SD code currently works properly and what doesn't etc and have been wondering where to look to get something that actually does work. This post might be my go to resource now with any luck.

  • Quality.

  • Actually, you should probably change

    PUB readSkipBytes(count) : result
    
    '' ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    '' // Reads data from the file that is currently open and advances the file position by that amount of data.
    '' //
    '' // Returns the amount of data read from the disk. Reads nothing when at the end of a file.
    '' //
    '' // This method will do nothing if a file is not currently open for reading or writing.
    '' //
    '' // If an error occurs this method will abort and return a pointer to a string describing that error.
    '' //
    '' // Count - The amount of data to read from disk.
    '' ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    
      result~
      repeat while count >= 32768
        result := readData( $8000, 32768 )               ' read into hub ROM space          ???????????????????????????????????????
        count -= 32768
      result += readData ( $8000, count )                ' read into hub ROM space          ???????????????????????????????????????
    

    to

    PUB readSkipBytes(count) : result
    
    '' ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    '' // Reads data from the file that is currently open and advances the file position by that amount of data.
    '' //
    '' // Returns the amount of data read from the disk. Reads nothing when at the end of a file.
    '' //
    '' // This method will do nothing if a file is not currently open for reading or writing.
    '' //
    '' // If an error occurs this method will abort and return a pointer to a string describing that error.
    '' //
    '' // Count - The amount of data to read from disk.
    '' ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    
      result~
      repeat while count >= 32768
        result := readData( $80000, 32768 )               ' read into unmapped space          ???????????????????????????????????????
        count -= 32768
      result += readData ( $80000, count )                ' read into unmapped space          ???????????????????????????????????????
    

    There's a more correct fix for this but that'd take effort.

  • RaymanRayman Posts: 13,900

    Thanks @Wuerfel_21 , that does look dangerous!

  • RaymanRayman Posts: 13,900
    edited 2023-06-03 21:28

    Here's a test for both that adds a VGA driver.
    It reads BMP image from uSD card and displays using VGA.

    You must have the file, bitmap2.bmp, on your uSD card.

    Note: Updated these as well as described in top post.

  • Can I humbly suggest changing sdspi_with_audio to include mountCard() to the stop method? If it is not there, you will not be able to reboot the P2 Edge properly. You won't be able to reboot the Edge arbitrarily anyway, but if you are performing a software reboot, mountCard() sends the SD Card init, which will allow you to reboot.

    PUB Stop()
        if cog
           mountCard()
           cogstop(cog-1)
    
        cog := 0
    

    This is a software fix for the fact that the SD Card is not power cycled in a reset condition on the Edge.

    There is another bug in FAT32, where once you change out of the root directly, you can't change back to the root. (Can't remember if it was using ".." or changing back to "/" ) I fixed it in my code. I will need to diff it to find it.

  • RaymanRayman Posts: 13,900

    Thanks @ke4pjw , I know you looked at this a lot. Is it just the "with_audio" that needs this?

  • @rayman I would think they all need it, but that is the only one I have tested.

  • RaymanRayman Posts: 13,900

    @ke4pjw Ok, things still seem to work with that in all the drivers. I've updated all the zips.

  • RaymanRayman Posts: 13,900

    @Wuerfel_21 Do you have an example or notes on how one can play a 16-bit PCM stereo (or mono) .wav file using your version of the driver?

    I almost have my .wav player working again, but seems silly to use two cogs when you have it integrated into one...

  • Wuerfel_21Wuerfel_21 Posts: 4,509
    edited 2023-06-04 21:36

    It's pretty much a carbon copy of what tinySDDA does on P1 except less ridiculously crammed into one cog's cog RAM. Look up that: https://forums.parallax.com/discussion/171949/tinysdda-v1-0-sdcard-sector-r-w-stereo-music-sound-effects-in-one-cog-and-almost-no-hub-ram

    In short:
    - Can play both stereo 16bit and mono A-law at the same time with looping
    - Files need to be non-fragmented raw data (A WAV header may not cause too great a disturbance, but really, just use raw files)

    The reason why it is this way is because I wanted a non-stupid way to port Spin Hexagon, which uses TinySDDA on P1.

  • @Rayman said:
    Here two uSD drivers that can both use your choice of three low level drivers.
    One is inline assembly and doesn't need a cog, one uses a cog, and the other also uses a cog but adds audio output.

    FSRW is a very minimalistic with only root directory access
    FAT32 has more features and can access sub-directories

    Tested with Propeller Tool 2.9.3

    @Wuerfel_21 connected the low level driver from P2 version of FSRW to FAT32, also added the audio version..
    FSRW was then modified a hair to also use the same low level drivers.

    There's been a history of FSRW becoming broken by compiler changes, but I think it's OK now.
    But, there's only been limited testing so far.

    Attached are simple tests of both drivers.

    Note: Small change made to FAT32 as suggested by @Wuerfel_21
    Also made change suggested by @ke4pjw

    Thanks for the taking the time @Rayman ! When I get back home I'll play a bit with this and @ke4pjw files.

  • I've been struggling with FSRW on the P2. Reading from a simple text file sometimes works, sometimes it says the file can't be opened -- even though the file shows up in the directory listing.

    I've also noticed that with Ray's test code and mine (which is based on his), the file write never works -- it only ever creates an empty file.

    I have run the code in the Eval uSD, in a Parallax uSD adaptor, and in my own (which has a PFET for switching power to the uSD) -- the behavior is the same in all.

  • Try using the _with_audio SPI code. I definitely remember fixing an issue where writes would fail like that, maybe the regular one hasn't ever had that backported to it.

  • I'll try, but would prefer an atomic object -- I don't like the idea of putting audio into the SD object (even though there is a relationship).

  • Wuerfel_21Wuerfel_21 Posts: 4,509
    edited 2023-10-30 11:51

    It's just a normal SD driver with some extra features stuffed in (that do nothing by default) - point is I know that one works and I think the other guy with the light controller also started with it and it worked for him.

    (Though the reason it exists is because the SD driver is arguably the one correct place to put audio streaming if you want to keep other cogs free of having to babysit it - though on P2 the need for a dedicated SD/SPI cog is questionable. Could probably do a PSRAM+SD+Audio combined monster thing if I wanted)

  • RaymanRayman Posts: 13,900

    It's not entirely my code, but I guess I'll take blame as latest maintainer of it.
    I'm sure I checked it all out, but there are a lot of versions floating around and many are broke by compiler and other changes.
    I'll look into this right now.

  • RaymanRayman Posts: 13,900

    I just checked my first test file and it appears to be working. It creates speed.txt and seems to write and read from it.

    @JonnyMac Can you try this? The notes need updating, and I'm not sure it's the latest. But, seems to work at least.

  • RaymanRayman Posts: 13,900
    edited 2023-10-30 15:21

    This is, it appears, is the most recent version. Just hacked to do a write test and seems to work.

  • I just checked my first test file and it appears to be working. It creates speed.txt and seems to write and read from it.> @Rayman said:
    I just checked my first test file and it appears to be working. It creates speed.txt and seems to write and read from it.

    @JonnyMac Can you try this? The notes need updating, and I'm not sure it's the latest. But, seems to work at least.

    This version seems to work. Thank you.

  • RaymanRayman Posts: 13,900

    Think found the problem with "sdspi_bashed2.spin2" version of low level driver...
    The "release" function was not good enough to close a file so another could be opened.

    Copied the release code from "sdspi_with_audio.spin2" and seems all better now.

  • RaymanRayman Posts: 13,900

    Just tested all the versions with a slideshow program that reads from 4 different bmp files continuously.
    All the low level drivers work now. Also, commented out the debug statements in low level drivers so can use Prop Tool debug window as serial terminal...

  • RaymanRayman Posts: 13,900

    Ok, I was just testing another slideshow app, this one for PSRAM, and ran into an issue where it refused to open the second image in the slideshow.
    This was with the "bashed", coggless, version.

    Just figured out that, for some reason, have to try to open twice to make it work, like this:

        'Load bmp file
        ser.PrintLn(@"Opening BMP file...")
        ser.str(p)
        ser.crlf()
        repeat  2
          i:=sd.popen(p,"r")
          if i>=0
            quit
          waitms(100)
    

    The cogged version were also not working, but that was because I was overriding the cog it was using with the PSRAM driver :(.
    So, this issue may be limited to the Bashed version.

    Anyway, if anyone is having trouble with the bashed (like @JonnyMac seemed to have had), try the above open loop.
    Guess should add something like this to the driver itself to avoid this.
    Not sure why I haven't seen this issue before...

Sign In or Register to comment.