@Rayman said:
Just thinking about the pull-up situation …
Can we not turn off p2 internal pull-ups during power cycle and then turn on after?
Not a big deal just curious…
Probably better to drive them low for a while to help discharge anything. They're not real pullups as such so driving them high when you want logic 1's is not the same as driving a logic high with a real pullup attached.
@Rayman said:
Just thinking about the pull-up situation …
Can we not turn off p2 internal pull-ups during power cycle and then turn on after?
Not a big deal just curious…
If you mean could we be using the Prop2's ability for pull-up/down in place of the real resistors? And just enable/disable where appropriate ...?
Short answer is no. Long answer is the fast/complete discharge at power down depends on that particular wiring that Roger did. The pull-up resistors discharge the capacitors because they are on that side of the power switch. The Prop2 can't offer such a current path.
Extended answer: CMOS circuits are very good at not using power when the clock stops. And this gets amplified when the power rail droops low. The Flash memory chip will stop ticking below a certain voltage. Meanwhile the volts stay above the specified power down threshold. By driving the Prop2 pins low, those pull-up resistors draw away that last bit of charge that the Flash chip wasn't consuming.
If you look at my wiring in post 1 you'll see that the very useful power LED does double duty and helps discharge the power rail after the pFET. If you pull SD pins down it'd also help a bit as all six 22k pulldowns in parallel is 3.6k to ground too.
_pinh(PIN_POW); // power off the SD card by overpowering the 1800 ohm Card Detect
_pinl(PIN_DAT); // drive DAT pin group low to discharge the now unpowered capacitors
_pinl(PIN_CMD); // ditto CMD
And further down:
_pinf(PIN_DAT);
_pinf(PIN_CMD);
_pinf(PIN_POW); // and power back on, released back to Card Detect function
??? why does it flush the file before writing? That makes no sense and seems like it would destroy performance when doing small-sized writes. It does the same thing in fread. Why?
To handle transitions between fputc() and fwrite() (and between reading and writing). If the user was using fputc() then the internal buffer in the FILE has a partial set of data, which needs to be flushed to disk before the write.
@ersmith said:
To handle transitions between fputc() and fwrite() (and between reading and writing). If the user was using fputc() then the internal buffer in the FILE has a partial set of data, which needs to be flushed to disk before the write.
But why? The FS has perfectly fine buffering of its own. I smell some hot bloatware to get rid of~
Was copying some code from @ersmith where he checks the result of mount() for error...
Seems that the SPI version returns -1 unless you call unmount() first.
But, seems SDIO version will return 0 without calling unmount() first.
Is this right?
@ersmith said:
To handle transitions between fputc() and fwrite() (and between reading and writing). If the user was using fputc() then the internal buffer in the FILE has a partial set of data, which needs to be flushed to disk before the write.
But why? The FS has perfectly fine buffering of its own. I smell some hot bloatware to get rid of~
fwrite() is a general library function, not FS specific, so it has to work with all file systems, including those that do not have good buffering. If FatFS already handles buffering well then we can probably simplify the VFS layer for it to bypass the standard fputc() and fgetc() calls, but many file systems do not do well with 1 byte writes.
@ersmith said:
fwrite() is a general library function, not FS specific, so it has to work with all file systems, including those that do not have good buffering. If FatFS already handles buffering well then we can probably simplify the VFS layer for it to bypass the standard fputc() and fgetc() calls, but many file systems do not do well with 1 byte writes.
Of the 3 available ones, the only one I would imagine to have no internal buffer is the 9P client. That should possibly be handled by adding sufficient buffers in there (unsubstantiated guess: 9P is probably the leanest of the bunch, anyways). Only having buffering on fputc is dumb anyways, since that doesn't work (and causes excessive drive writes from these flushes) if you're, e.g. writing small 16 byte structures with fwrite.
Just made this program to test loading in VGA image from uSD to hub ram.
Similar to the @evanh test code, but with ability to see result on monitor and directly compare SPI and SDIO speeds.
Seems SPI mode gets around 2,800 kB/s whereas SDIO gets 21,000 kB/s
So, 7.5 X faster...
Did just notice a SDIO glitch though in 1 of about 10 tests.
After about 10 reads of the bmp, the speed dropped to ~7,000 kB/s for about 10 bmp reads and then jumped back up to 21,000 kB/s.
Going to try a few more times to see if it ever comes back...
Looking back on what was able to do years ago in terms of video, things would be much nicer with this read speed.
Thinking could easily do 640x480x8bpp with 256 color palette. Or, QVGA in 16bit color.
Would be a vast improvement...
Yes, it is much happier reading from one giant file than the same file over and over, good news!
I switched it to only printing the speed when it dropped below 19,000 kB/s and it just did a >1 GB file with only one frame and that was ~17,000 kB/s.
@Rayman said:
Looking back on what was able to do years ago in terms of video, things would be much nicer with this read speed.
Thinking could easily do 640x480x8bpp with 256 color palette. Or, QVGA in 16bit color.
Would be a vast improvement...
For sure. This sort of throughput and the SD capacity makes it a good candidate for video storage/playback. The trick will be maintaining the performance and somehow avoiding or mitigating temporary drop outs in speed that could occur now and again from seek activity and internal SD housekeeping. I'm thinking/hoping PSRAM could help a bit there with a large multi-frame buffer area.
Ideally want to have Flexspin libraries, namely the FAT FS stack, be capable of seeing such a RAM expansion as part of its address space. Then it could fill said PSRAM buffer in a single fread() call. Even more important for writing to the SD card. That cleans up a lot of the hassle of filesystem housekeeping that does lots of little single block writes for each fwrite().
It could be a decent design exercise though. At the moment the passed address can be directly used with the one streamer for reading or writing the SD card. But a single streamer can't do both SD I/O and external RAM I/O in the one op. I guess it'd have to become two ops via a small buffer. Block by block is not unreasonable. The shuffle would definitely slow things down.
@Rayman said:
Was copying some code from @ersmith where he checks the result of mount() for error...
Seems that the SPI version returns -1 unless you call unmount() first.
But, seems SDIO version will return 0 without calling unmount() first.
Is this right?
More detail please. Links/code samples.
EDIT: Found it in your SimpleVGA.c I think:
void MountSD()
{
int r = 0;
_umount("/sd"); //have to unmount to get 0 from mount
#ifndef USE_SDIO
r = mount("/sd", _vfs_open_sdcardx(PIN_CLK, PIN_SS, PIN_MOSI, PIN_MISO));
#else
r = mount("/sd", _vfs_open_sdsdcard(CLK_DIV, PIN_CLK, PIN_CMD, PIN_DAT0, PIN_CD, PIN_RED));
#endif // !USE_SDIO
if (r != 0) {
printf("ERROR: got error %d during mount\n", r);
for (;;) {}
}
}
Don't know why that happen. Nor why unmounting helps. The driver's DSTATUS return code should be zero in both cases.
Oh, it'll be the disk_setpins() return code. The SPI driver doesn't produce a return code. I presume it never has.
@Rayman said:
Wondering about dedicating a cog to SDIO...
Would that make it even faster?
Or, let you do other things while loading in a large file to memory?
You can do that explicitly yourself. You'd launch a fresh cog for managing the SD card with the same C file API it uses right now. But then add your own custom buffer swapping in hubRAM for talking with the other cogs. Those other cogs then make requests of your file manager via that buffer, or buffers.
No it wouldn't make it faster. The filesystem layer hasn't changed.
Yes, other tasks can be operating concurrently.
I'm not liking the idea of giving up a pin to power cycle the uSD.
Thinking about using I2C instead with 4 bit i/o expander like this: https://www.ti.com/lit/ds/symlink/tca9536.pdf
@Rayman said:
I'm not liking the idea of giving up a pin to power cycle the uSD.
Thinking about using I2C instead with 4 bit i/o expander like this: https://www.ti.com/lit/ds/symlink/tca9536.pdf
That's perfectly okay to use for LED and power switch control. But also requires a digital input for Card Detect solution. The power switch pin does double duty on that currently.
Or, is tying it power cycle to reset good enough?
Short answer is not really. In theory, it should be fine without the power-cycling ability as there isn't anything in normal ops that should ever confuse the SD card. But there is documented modes that only a power cycle can recover from should such be inadvertently entered, and the spec does say that power-cycling is the first step in initialising any SD card.
BTW: calling this SDIO mode is correct, right?
I had avoided the label because, in the spec it describes SD Memory Cards and SD I/O Cards as two distinct types. Both of which can be commanded via both the SD interface and the SPI interface.
Looking up the specs again, section 3.6, I see they're naming the two interfaces as SD Bus Protocol and SPI Bus Protocol. Not a great help, can't really abbreviate them.
Being a little more pragmatic ... In the development environment the Eval Board's use of Prop2 reset doubling up as SD power cycle has proven beneficial - Since it fires upon every fresh download. I remember someone was complaining about the Edge Card missing this ability.
For production scenarios, making the reset a feature of user input then it would probably be fine like that. But if reset only happens on power up then I would expect the SD Card would be best with a separate power control.
Manual power on/off control of SD power after either software init/rebooting ensures a stable system always beginning from a consistent state. You risk requiring manual card re-insertions and potential hangs otherwise.
I do like the 8-pin group approach. It's simple, clean, direct and nothing is left wanting. And I rather like the red LED too, it glimmers beautifully according to the throughput of the SD card.
Comments
Probably better to drive them low for a while to help discharge anything. They're not real pullups as such so driving them high when you want logic 1's is not the same as driving a logic high with a real pullup attached.
If you mean could we be using the Prop2's ability for pull-up/down in place of the real resistors? And just enable/disable where appropriate ...?
Short answer is no. Long answer is the fast/complete discharge at power down depends on that particular wiring that Roger did. The pull-up resistors discharge the capacitors because they are on that side of the power switch. The Prop2 can't offer such a current path.
Extended answer: CMOS circuits are very good at not using power when the clock stops. And this gets amplified when the power rail droops low. The Flash memory chip will stop ticking below a certain voltage. Meanwhile the volts stay above the specified power down threshold. By driving the Prop2 pins low, those pull-up resistors draw away that last bit of charge that the Flash chip wasn't consuming.
If you look at my wiring in post 1 you'll see that the very useful power LED does double duty and helps discharge the power rail after the pFET. If you pull SD pins down it'd also help a bit as all six 22k pulldowns in parallel is 3.6k to ground too.
Here's the relevant source code:
And further down:
To handle transitions between fputc() and fwrite() (and between reading and writing). If the user was using fputc() then the internal buffer in the FILE has a partial set of data, which needs to be flushed to disk before the write.
Oh well, removing the flush didn't improve SD performance anyway.
But why? The FS has perfectly fine buffering of its own. I smell some hot bloatware to get rid of~
Write buffering should be disabled or at least optional on microcontroller right?
Power cycling happens a lot in many cases…
Was copying some code from @ersmith where he checks the result of mount() for error...
Seems that the SPI version returns -1 unless you call unmount() first.
But, seems SDIO version will return 0 without calling unmount() first.
Is this right?
Wondering about dedicating a cog to SDIO...
Would that make it even faster?
Or, let you do other things while loading in a large file to memory?
fwrite() is a general library function, not FS specific, so it has to work with all file systems, including those that do not have good buffering. If FatFS already handles buffering well then we can probably simplify the VFS layer for it to bypass the standard fputc() and fgetc() calls, but many file systems do not do well with 1 byte writes.
Of the 3 available ones, the only one I would imagine to have no internal buffer is the 9P client. That should possibly be handled by adding sufficient buffers in there (unsubstantiated guess: 9P is probably the leanest of the bunch, anyways). Only having buffering on fputc is dumb anyways, since that doesn't work (and causes excessive drive writes from these flushes) if you're, e.g. writing small 16 byte structures with fwrite.
Just made this program to test loading in VGA image from uSD to hub ram.
Similar to the @evanh test code, but with ability to see result on monitor and directly compare SPI and SDIO speeds.
Seems SPI mode gets around 2,800 kB/s whereas SDIO gets 21,000 kB/s
So, 7.5 X faster...
Did just notice a SDIO glitch though in 1 of about 10 tests.
After about 10 reads of the bmp, the speed dropped to ~7,000 kB/s for about 10 bmp reads and then jumped back up to 21,000 kB/s.
Going to try a few more times to see if it ever comes back...
Seems the speed glitch mentioned above is reproduceable.
Happens about every minute or so it seems.
Caught this one (and other in the act):
Maybe it gets sick of opening the same file over and over and protests occassionally?
I should try this with a big movie file instead...
Looking back on what was able to do years ago in terms of video, things would be much nicer with this read speed.
Thinking could easily do 640x480x8bpp with 256 color palette. Or, QVGA in 16bit color.
Would be a vast improvement...
Yes, it is much happier reading from one giant file than the same file over and over, good news!
I switched it to only printing the speed when it dropped below 19,000 kB/s and it just did a >1 GB file with only one frame and that was ~17,000 kB/s.
So video potential is looking good.
For sure. This sort of throughput and the SD capacity makes it a good candidate for video storage/playback. The trick will be maintaining the performance and somehow avoiding or mitigating temporary drop outs in speed that could occur now and again from seek activity and internal SD housekeeping. I'm thinking/hoping PSRAM could help a bit there with a large multi-frame buffer area.
Interesting idea to use psram as buffer..
Ideally want to have Flexspin libraries, namely the FAT FS stack, be capable of seeing such a RAM expansion as part of its address space. Then it could fill said PSRAM buffer in a single fread() call. Even more important for writing to the SD card. That cleans up a lot of the hassle of filesystem housekeeping that does lots of little single block writes for each fwrite().
It could be a decent design exercise though. At the moment the passed address can be directly used with the one streamer for reading or writing the SD card. But a single streamer can't do both SD I/O and external RAM I/O in the one op. I guess it'd have to become two ops via a small buffer. Block by block is not unreasonable. The shuffle would definitely slow things down.
More detail please. Links/code samples.
EDIT: Found it in your SimpleVGA.c I think:
Don't know why that happen. Nor why unmounting helps. The driver's DSTATUS return code should be zero in both cases.
Oh, it'll be the disk_setpins() return code. The SPI driver doesn't produce a return code. I presume it never has.
You can do that explicitly yourself. You'd launch a fresh cog for managing the SD card with the same C file API it uses right now. But then add your own custom buffer swapping in hubRAM for talking with the other cogs. Those other cogs then make requests of your file manager via that buffer, or buffers.
No it wouldn't make it faster. The filesystem layer hasn't changed.
Yes, other tasks can be operating concurrently.
Looks like could do 1080p @ 30 Hz video with color cell compression. It'd be interesting to see what that looks like...
I'm not liking the idea of giving up a pin to power cycle the uSD.
Thinking about using I2C instead with 4 bit i/o expander like this:
https://www.ti.com/lit/ds/symlink/tca9536.pdf
Or, is tying it power cycle to reset good enough?
Wish there was a way to use free FTDI I/O pin from P2 side, but don't think there is...
Never mind... Think have to go all in with LEDs and all...
BTW: calling this SDIO mode is correct, right?
That's perfectly okay to use for LED and power switch control. But also requires a digital input for Card Detect solution. The power switch pin does double duty on that currently.
Short answer is not really. In theory, it should be fine without the power-cycling ability as there isn't anything in normal ops that should ever confuse the SD card. But there is documented modes that only a power cycle can recover from should such be inadvertently entered, and the spec does say that power-cycling is the first step in initialising any SD card.
I had avoided the label because, in the spec it describes SD Memory Cards and SD I/O Cards as two distinct types. Both of which can be commanded via both the SD interface and the SPI interface.
Looking up the specs again, section 3.6, I see they're naming the two interfaces as SD Bus Protocol and SPI Bus Protocol. Not a great help, can't really abbreviate them.
Being a little more pragmatic ... In the development environment the Eval Board's use of Prop2 reset doubling up as SD power cycle has proven beneficial - Since it fires upon every fresh download. I remember someone was complaining about the Edge Card missing this ability.
For production scenarios, making the reset a feature of user input then it would probably be fine like that. But if reset only happens on power up then I would expect the SD Card would be best with a separate power control.
Manual power on/off control of SD power after either software init/rebooting ensures a stable system always beginning from a consistent state. You risk requiring manual card re-insertions and potential hangs otherwise.
I do like the 8-pin group approach. It's simple, clean, direct and nothing is left wanting. And I rather like the red LED too, it glimmers beautifully according to the throughput of the SD card.