OpenWrt Forum Archive

Topic: WRT54G optimized SD card driver for kernel 2.6 (brcm47xx)

The content of this topic has been archived on 30 Apr 2018. There are no obvious gaps in this topic, but there may still be some posts missing at the end.

I've ported the broadcom-sdhc driver (which was based on the old "optimized mmc" driver) to kernel 2.6 and improved the startup scripts. You should get significantly more reliable SD card support and performance compared to the mmc_over_gpio driver.

In theory, this should work with any WRT54G/GL with the sd card mod. I have no idea if this works on any other Broadcom platform, if you're feeling adventurous, try it out and let me know here!

This works on my WRT54GL with the SD card mod with:
data in on gpio 2
data out on gpio 4
clock on gpio 3
chip select on gpio 7

I'm not responsible if this bricks your router etc. smile

This should work on any relatively recent trunk/snapshot, and maybe even 10.04-rc4. Make sure you do not have mmc_over_gpio installed.

Download package or you can run:

opkg install http://dev.xephris.net/openwrt/broadcom-sdhc26/files/kmod-broadcom-sdhc26_2.6.37.6-1_brcm47xx.ipk

And if you want to build it yourself, you can always download the source.

If you want to use wireless (e.g. b43), make sure you mask off the GPIOs appropriately first.

/etc/modules.d/30-b43

b43 gpiomask=0x1

A safe value is 0 (b43 will not touch GPIOs). If you use the same GPIOs and hardware as I do, 0x1 is safe (this enables the wifi LED).
This gpiomask is the GPIOs to ALLOW b43 to use. (This is opposite to the gpiomask for diag, which is the GPIOs to not allow it to use.)

You will need to update /etc/config/broadcom_sdhc26 before it will work, especially if you use different GPIOs than I do. The file should be pretty self-explanatory.

If you just want some extra storage:

 option 'enabled' '1'

Then run:

/etc/init.d/broadcom_sdhc26 start

If the above command didn't kill your router, and you also want it to run on boot, also do:

/etc/init.d/broadcom_sdhc26 enable

This will also work with extroot, see the extroot howto
You'll need to have block-mount installed and configured like the howto.

In /etc/config/broadcom_sdhc26:

 option 'enabled' '1'
 option 'preinit' '1'

Then run:

/etc/init.d/broadcom_sdhc26 disable

Yes, that does say "disable". The script will get run in the preinit phase so you shouldn't run it twice.


Post here to report your success, or if you have any problems.
If someone is interested in making this an official package, please let me know.

Just jumping in here to say that I had been struggling trying to get SD card support working under 2.6 for a couple days.  I could get the GPIOs to toggle from the diag driver but the mmc_over_gpio just would not do anything.  I couldn't even get it to work with no other kernel modules loaded. 

I built a firmware with your driver installed and it worked like a charm for one of the other Wrt users. My micro SD card doesn't work but I can see the lines wiggling.  I might just have it soldered incorrectly, but I wanted to report that it does work for someone who knows how to solder.  I wanted to make sure someone have you some kudos for your work!

The configuration file might be a little wordy though, perhaps something that would be better off in a README that isn't deployed with the package?  I can't believe I'm raising an objection for having too much documentation smile

If your card works with the broadcom-sdhc driver on brcm-2.4, it should work with my release. Some older cards (<128MB) and some microSD seem to have issues, they might not support SPI mode.

Thanks for the feedback!

Hello,

I would like to compile it within a firmware.

I downloaded the latest trunk with

svn co .../trunk

then I put your package within the folder trunk/package/broadcom-sdhc

but when i do a make menuconfig, I don't see it appear in the list of "other kernel modules"....

I also don't understand what you mean in the readme file with "Copy in 'Makefile.x.y' as 'Makefile' where 'x.y' is your openwrt version.  (7.09 or 8.09)"

Can you help ?

Thanks,

Whoops, the README is actually wrong. I hadn't updated from the package this port was based on.
You should find the module under Kernel Modules -> Block Devices. If you don't see it, try doing 'make package/index' before make menuconfig.

Indeed.... I could build a firmware for it.

It seems to be willing to start the sd card... but something goes wrong...

root@OpenWrt:/# dmesg
[INF] bcm_sdhc: Version: 1.0.0  Params: major=0 din=2 dout=4 clk=3 cs=7 maxsec=32 dbg=0001
[DBG] bcm_sdhc: init: power on/insertion initialization...
[DBG] bcm_sdhc: init: CMD0 - reset...
[DBG] bcm_sdhc: init SD: CMD8 - CIC voltage range check...
[DBG] bcm_sdhc: init SD: CMD58 - OCR voltage range check...
[DBG] bcm_sdhc: init SD: ACMD41 - card initialization...
[DBG] bcm_sdhc: init SD: CMD58 - Card Capacity Status check...
[DBG] bcm_sdhc: init SD: CMD10 - Card Identification Register read...
[DBG] bcm_sdhc: init SD: CMD9 - Card Specific Data read...
[DBG] bcm_sdhc: init SD: ACMD51 - SD Config Register read...
[INF] bcm_sdhc: SD Card detected & initialized
[DBG] bcm_sdhc: init - CMD16 - set 512 byte blocksize...
[INF] bcm_sdhc: Assigned dynamic major number 254
 bcmsdhc: bcmsdhc1 bcmsdhc2 bcmsdhc3
[INF] bcm_sdhc: Module loaded
root@OpenWrt:/# ls /dev/
bcmsdhc             log                 mtd2                mtdblock0           network_latency     pts                 ttyS1
bcmsdhc1            mem                 mtd2ro              mtdblock1           network_throughput  random              tun
console             mtd0                mtd3                mtdblock2           null                root                urandom
cpu_dma_latency     mtd0ro              mtd3ro              mtdblock3           port                shm                 watchdog
full                mtd1                mtd4                mtdblock4           ppp                 tty                 zero
kmsg                mtd1ro              mtd4ro              net                 ptmx                ttyS0
root@OpenWrt:/#

It detects the 3 partitions on the SD card (dmesg output), but it only lists one in /dev.
Once loaded, the orange led stays bright lit and I cannot do anything on the card...

The router was previously set up with a 2.4 kernel and the "optimized" mmc driver and was working fine....

I will try to rebuild another image with full standard settings sees what it gives.... But so far, no luck sad


Edit : I tried a new build, with complete standard settings (with the exception of the requirements for this module), still no luck...
As I can't put my hand on a wrt with kernel 2.6.37.2, I cannot test the pre-compiled package...

(Last edited by Tsunulukai on 29 Jul 2011, 09:27)

That's very strange. What SD card (size/make/model) are you using?

So you can't access /dev/bcmsdhc1, and the orange light stays solid? If you do /etc/init.d/broadcom_sdhc26 stop ; /etc/init.d/broadcom_sdhc26 start does that do anything or help?

What source revision and branch are you building off of?

Did you build the wifi module? If so, did you edit the b43 module to mask off the gpio (as in the top post)?

What are the contents of /proc/diag/gpiomask?

It's a 4Gb transcend card.

I'm building from the latest trunk (27833)

I enabled following modules during compilation
- bloc-mount
- kmod-broadcom-sdhc26 (default config)
- kmod-fs-ext4
- e2fsprogs
- fdisk
those are the only changes I made within make menuconfig

root@OpenWrt:/# /etc/init.d/broadcom_sdhc26 stop
rmmod: can't unload 'bcm_sdhc': Resource temporarily unavailable

I cannot stop the module...

Before starting the module,

root@OpenWrt:/# cat /proc/diag/gpiomask
0x0000

And after...

root@OpenWrt:/# cat /proc/diag/gpiomask
0x009c

Wifi driver has been compiled, but wifi is not enabled. I did adapt the file /etc/modules.d/30-b43 as mentionned...

When the module starts, the orange light lits, the white shortly blinks, and the the orange stays lit....
And can't access /dev/bcmsdhc1, nor do a fdisk on /dev/bcmsdhc...

It worked fine with that driver under a 2.4 kernel...

I just tried with  other SD cards, one  4Gb iSmart card & one 2Gb Optima... without success.
I'll try to downgrade to the 2.4 firmware, just to be sure it still works.

Thanks for the feedback. I'll look into it over the weekend. I haven't upgraded my router since I built the package, so something might have changed or broke it.

For info, I just tried back with the 2.4 kernel, here is what I get :

[INFO] mmc_hardware_init: initializing GPIOs
[INFO] mmc_card_init: the period of a 380KHz frequency lasts 524 CPU cycles
[INFO] mmc_card_init: powering card on. sending 80 CLK
[INFO] mmc_card_init: 80 CLK sent in 43646 CPU cycles
[INFO] mmc_card_init: resetting card (CMD0)
[INFO] mmc_card_init: doing initialization loop
[INFO] mmc_card_init: card inited successfully in 324 tries (9995283 CPU cycles).
[INFO] mmc_init: MMC/SD Card ID:
1c 53 56 53 44 43 20 20 10 00 00 2d cc 00 89 2d [INFO] Manufacturer ID   : 1c
[INFO] OEM/Application ID: SV
[INFO] Product name      : SDC
[INFO] Product revision  : 1.0
[INFO] Product SN        : 00002dcc
[INFO] Product Date      : 2008-9
[INFO] mmc_card_config: size = 3905536, hardsectsize = 2048, sectors = 1952768
[WARN] mmc_init: hd_sizes=3905536, hd[0].nr_sects=7811072
[INFO] mmc_card_init: set_blocklen (CMD16) succeeded !
Partition check:
 mmca: p1 p2 p3
root@OpenWrt:~# fdisk /dev/mmc/disc0/
/dev/mmc/disc0/disc   /dev/mmc/disc0/part1  /dev/mmc/disc0/part2  /dev/mmc/disc0/part3
root@OpenWrt:~# fdisk /dev/mmc/disc0/disc

The number of cylinders for this disk is set to 2415.
There is nothing wrong with that, but this is larger than 1024,
and could in certain setups cause problems with:
1) software that runs at boot time (e.g., old versions of LILO)
2) booting and partitioning software from other OSs
   (e.g., DOS FDISK, OS/2 FDISK)

Command (m for help): p

Disk /dev/mmc/disc0/disc: 3999 MB, 3999268864 bytes
98 heads, 33 sectors/track, 2415 cylinders
Units = cylinders of 3234 * 512 = 1655808 bytes

              Device Boot      Start         End      Blocks   Id  System
/dev/mmc/disc0/part1               1         310      501253+  83  Linux
/dev/mmc/disc0/part2             311         466      252252   82  Linux swap / Solaris
/dev/mmc/disc0/part3             467        2415     3151533   83  Linux

The  2.4 driver I use is the v 1.3.4 GPIO2 on that page : https://forum.openwrt.org/viewtopic.php?pid=43894 
There it works just fine

Sorry for the delay. I haven't had as much time to look into this as I thought I would have. I just wanted to let you know that I've managed to reproduce the issue and I'm looking into it.

That's great ! Thank you very much for your help smile
Looking forward to see your next post !

I've tested the driver with latest trunk from 20 Aug, 2011. In the log files it says the SD card (2GB Kingston) is recognized and there are no errors. I see the device and the partition added to the "/dev". However the "mount" command hangs forever. I'm having "ext2" file system on the card, so I had  "ext4" driver, which should work with ext2 as well. My schematic is the same:
data in on gpio 2
data out on gpio 4
clock on gpio 3
chip select on gpio 7
I'm using the opensource broadcom driver and I have changed "/etc/modules.d/30-b43" accordingly. I rebooted the router and then the "broadcom_sdhc26 start" script did not work anymore: it was giving me some error that the file is already there and the stop script failed as well with the same error as reported by others: "rmmod: can't unload 'bcm_sdhc': Resource temporarily unavailable"
I tested with Backfire RC5 2.4 kernel with the old "optimized mmc" driver - the card mounted fine and the speed was great. However I'd like to use the latest kernel (the trunk is on 3.0.3).
I was able to mount the card on 2.6 kernel with the "mmc_over_gpio" driver, but I get a terribly slow transfer speed and the systems hangs shortly afterward.
Zinc, thank you very much for working on this. Please let me know if there is a new version that I can test.

Sorry for the delay again guys, I hadn't had as much time as I wanted this past month to work on this. I found some quirks with how I was handling spinlocking and scheduling. For now, you guys can try this one.

Source: http://dev.xephris.net/openwrt/broadcom … rc.tar.bz2

If it works well, I'll look into doing a kthreads version instead. A known issue is that the router will be slow and might appear to lock up (depending on how fast your SD card is) if it's transferring lots of data quickly, but the performance should be around 400-600 KB/s depending on SD card speed and router CPU clock speed.

README has also been updated smile

I'll take a look and keep you posted ASAP !
Greetz!

zinc wrote:

Sorry for the delay again guys, I hadn't had as much time as I wanted this past month to work on this. I found some quirks with how I was handling spinlocking and scheduling. For now, you guys can try this one.

Source: http://dev.xephris.net/openwrt/broadcom … rc.tar.bz2

Huzzah! You are the man again. I thought I had broken my SD card a few months ago when it stopped working and the mount process kept hanging so I disabled it, and this works perfectly. On a WRT54GL ext2:
10MB read = 26s real, 10s sys or about 384KB/s
10MB write = 20s real, 2.5s sys or about 500KB/s

Write was /dev/zero to /mnt/xxx
Read was /mnt/xxx to /dev/null

Thanks again, this is fan-friggin-tastic.

Nice to read !
I can't wait for kernel.org to come back online to try and test it by myself smile

zinc: FYI there's a minor error raised during the build (in the part where it installs the package to the firmware image root)
./etc/init.d/broadcom_sdhc26: line 5: /lib/functions/broadcom_sdhc26.sh: No such file or directory

I think the build process calls `/etc/init.d/broadcom_sdhc26 enable` or something.

Hello !

I count mount an existing ext2 partition without problem. I can also list my complete partition table, which I couldn't before...
Nevertheless, I'm unable to format a partition in ext2. It always ends up closing my telnet/ssh remote session without even finishing the job...
I might be because the CPU is too busy and can't answer the SSH/telnet session fast enough...

Therefore, I coulnd't try the extroot as I'm unable to format the partition to do so sad

Anyway, that's a good step forward ! Keep up the good work smile
See you !

FYI: kernel.org is back smile

@CapnBry -- I'll look into it

@Tsunulukai -- How big of an sdcard are you using? If you telnet in, and background the mkfs command, does it eventually start responding again? Alternatively, you can mkfs it on your desktop then just stick the card in.

It probably is the CPU being too busy, I took out the interrupt code because of some issues with it -- so I guess your use case is a good reason to do the kthreads version.

Hi zinc,
the driver works fine on my WRT54GL v1.1 using a 2GB SanDisk microSD card. The speed is about 600kB/s, which is great!
However, as soon as I use it with extroot pivot overlay (setting the 'preinit' option in /etc/config/broadcom_sdhc26 to 1) the SD card gets very slow with a r/w speed of only about 25 kB/s.


I compiled the broadcom-sdhc26-2 sources to a package for Backfire 10.03.1. (Kernel 2.6.32.27)
The filesystem on my SD card is ext2.

The card is mounted correctly to /overlay (see below) and everything works but very slowly sad

Filesystem                Size      Used Available Use% Mounted on
/dev/root                 1.9M      1.9M         0 100% /rom
tmpfs                     6.5M      1.2M      5.3M  18% /tmp
tmpfs                   512.0K         0    512.0K   0% /dev
/dev/bcmsdhc1             1.8G      2.8M      1.7G   0% /overlay
mini_fo:/overlay          1.9M      1.9M         0 100% /


dmesg tells me the following about the SD card, which seems alright:

[INF] bcm_sdhc: Version: 1.0.0  Params: major=0 din=2 dout=4 clk=3 cs=7 maxsec=32 dbg=0000
[INF] bcm_sdhc: SD Card detected & initialized
[INF] bcm_sdhc: Assigned dynamic major number 254
bcmsdhc: bcmsdhc1
[INF] bcm_sdhc: Module loaded
EXT2-fs warning: mounting unchecked fs, running e2fsck is recommended


Any idea why it's so slow with extroot?

i  am sorry, but i have not found clear photos and there is not a description ho to connect

data in on gpio 2
data out on gpio 4
clock on gpio 3
chip select on gpio 7

by the other side.

i got a linksys wrt 54gl ver 1.1 and i would to put a SD card !

i'll be happy to do this hack :-)

possibly i would not to use the port RS-232 9 pins, i would to left it empty, because if necessary i would to use to connect a RS-232 or any other circuit in the limits offered by linksys wrt 54gl ver 1.1

i would to use on the serial port with the stripsets for the sd or mmc cards.

anyway i would understand how you etablished which are gpio 2, 4, 3, 7 and who told you that they works for in & out data, for the clock i suppose in mhz, and for chip select that i don't know what is.

for in & out data refer to tx and rx data ? or else ?

is it possible to see any picture about the cables weldered on gpio 2, 4, 3, 7 and how are connected on the mmc card or sd card or on the socket which hosts sd or mmc card ?
 
awaiting your reply,

paolo

Palvz,

I know this is a couple months late but in case you still need help here is an image I created to help with wiring an SDCard for the wrt54gl v1.1.  It follows the same GPIO map as discussed above

http://www.jedge.com/cpg15x/albums/link … iption.jpg

I guess you could find the whole gallery helpful:  http://www.jedge.com/cpg15x/thumbnails.php?album=1

I found this forum post as I'm dusting off the WRT to install the 2.6 kernel and I need a new driver for my sdcard.

Hello everybody,

I'm a newbee on openwrt.
I'm using the Backfire 10.03.1 brcm47xx version of openwrt on a WRT54GL.
I would like to use SDHC card on it. But I can't build this package for this version of kernel...
Someone could help me ? Someone have already build it for this kernel ?

I have downloaded the SDK from this URL : http://downloads.openwrt.org/backfire/1 … .1.tar.bz2

I have placed the folder broadcom-sdhc26 into the folder package.

I execute the commande : make package/broadcom-sdhc26/compile V=99
and I obtain this error :

#
# using defaults found in .config
#


*** End of OpenWrt configuration.
*** Execute 'make' to build the OpenWrt or try 'make help'.

make[4]: Entering directory `/home/julien/openwrt/OpenWrt-SDK-brcm47xx-for-Linux-i686-gcc-4.3.3+cs_uClibc-0.9.30.1/package/broadcom-sdhc26'
make[4]: Leaving directory `/home/julien/openwrt/OpenWrt-SDK-brcm47xx-for-Linux-i686-gcc-4.3.3+cs_uClibc-0.9.30.1/package/broadcom-sdhc26'
make[1]: Entering directory `/home/julien/openwrt/OpenWrt-SDK-brcm47xx-for-Linux-i686-gcc-4.3.3+cs_uClibc-0.9.30.1'
make[2]: Entering directory `/home/julien/openwrt/OpenWrt-SDK-brcm47xx-for-Linux-i686-gcc-4.3.3+cs_uClibc-0.9.30.1/package/broadcom-sdhc26'
make[2]: *** No rule to make target `/home/julien/openwrt/OpenWrt-SDK-brcm47xx-for-Linux-i686-gcc-4.3.3+cs_uClibc-0.9.30.1/build_dir/linux-brcm47xx/linux-2.6.32.27/.config', needed by `/home/julien/openwrt/OpenWrt-SDK-brcm47xx-for-Linux-i686-gcc-4.3.3+cs_uClibc-0.9.30.1/build_dir/linux-brcm47xx/broadcom-sdhc26/.built'.  Stop.
make[2]: Leaving directory `/home/julien/openwrt/OpenWrt-SDK-brcm47xx-for-Linux-i686-gcc-4.3.3+cs_uClibc-0.9.30.1/package/broadcom-sdhc26'
make[1]: *** [package/broadcom-sdhc26/compile] Error 2
make[1]: Leaving directory `/home/julien/openwrt/OpenWrt-SDK-brcm47xx-for-Linux-i686-gcc-4.3.3+cs_uClibc-0.9.30.1'
make: *** [package/broadcom-sdhc26/compile] Erreur 2

I have checked, I don't have any files .config.
I have executed make menuconfig, but nothing change.
I search on the SDK folder and I don't found any .config file...

Someone can help me ?

Thanks

Julien

The discussion might have continued from here.