Running TCP/IP Stack in Linux Print

 

With uClinux running on the STM32F4, you get the full Linux TCP/IP stack (kernel version 2.6.33). Userspace POSIX APIs are provided by the uClibc library. Key user-space networking tools and utilities are available from the multi-call busybox. Additional tools and packages, such as for instance the SSH dropbear server, can be built specifically for uClinux. All in all, you have the powerful Linux TCP/IP stack at your disposal.

There is a full-functioning Ethernet device driver available in the kernel tree for the STM32F4. The device driver is linux/drivers/net/arm/stm32_eth.c configured in the kernel using the CONFIG_STM32_ETHER build time option in Device Drivers -> Network device support -> Etherner (10 or 100Mbit). You can also chose whether you want the Ethernet buffer descriptors and buffers to reside in the internal SRAM of the STM32F429 or in external RAM managed by the kernel:

Once you have enabled CONFIG_STM32_ETHER, go to System Type -> STM32 I/O interfaces and enable STM32 Ethernet port (CONFIG_STM32_MAC). This will register a platform device for the STM32F4 Ethernet controller with the Ethernet driver:

Emcraft provides a sample Linux project called networking that demonstrates TCP/IP over Ethernet on the STM32F4. In the Emcraft Linux distribution, the project can be found at projects/networking. The following provides detailed information on running that project on the STM32F429.

The bootable Linux image ready to be installed to the embedded Flash of the STM32F429 (networking.uImage) is about 1.6 MBytes in size. It fits into the on-chip Flash with some room to go.

With the Linux kernel running execute-in-place from the Flash, kernel performance is fast (167 BogoMIPS) and boot time to the shell is about 1 second from power-on / reset. In other words, in 1 second from power-on you have your unit running shell with the TCP/IP stack and Ethernet interface fully configured and connected to the network:

U-Boot 2010.03-00014-gb9aad35-dirty (Dec 25 2013 - 18:50:03)

CPU : STM32F4 (Cortex-M4)
Freqs: SYSCLK=180MHz,HCLK=180MHz,PCLK1=45MHz,PCLK2=90MHz
Board: STM32F429-DISCOVERY Rev 1.A
DRAM: 8 MB
...
Linux version 2.6.33-arm1 ( This e-mail address is being protected from spambots. You need JavaScript enabled to view it ) (gcc version 4.4.1 (Sourcery G++ Lite 2010q1-189) ) #366 Mon Jan 13 18:48:58 +0400 2014
CPU: ARMv7-M Processor [410fc241] revision 1 (ARMv7M)
CPU: NO data cache, NO instruction cache
Machine: STMicro STM32
...
Calibrating delay loop... 167.52 BogoMIPS (lpj=837632)
...
IP route cache hash table entries: 1024 (order: 0, 4096 bytes)
TCP established hash table entries: 512 (order: 0, 4096 bytes)
TCP bind hash table entries: 512 (order: -1, 2048 bytes)
TCP: Hash tables configured (established 512 bind 512)
TCP reno registered
RPC: Registered udp transport module.
RPC: Registered tcp transport module.
RPC: Registered tcp NFSv4.1 backchannel transport module.
...
blackfin-eth: Using SRAM for DMA buffers from 20001000
blackfin-eth: found MAC at 0x40028000, irq 61
blackfin_mii_bus: probed
found PHY id 0x20005c90 addr 1
eth0: using MII interface
eth0: attached PHY driver [Generic PHY] (mii_bus:phy_addr=00:01, irq=-1)
TCP cubic registered
NET: Registered protocol family 17
IP-Config: Guessing netmask 255.255.0.0
IP-Config: Complete:
device=eth0, addr=172.17.6.136, mask=255.255.0.0, gw=255.255.255.255,
host=stm32f4x9-som, domain=, nis-domain=(none),
bootserver=172.17.0.1, rootserver=172.17.0.1, rootpath=
...
init started: BusyBox v1.17.0 (2014-01-13 15:46:29 +0400)
~ # ifconfig eth0
eth0 Link encap:Ethernet HWaddr C0:B1:3D:88:88:89
inet addr:172.17.6.136 Bcast:172.17.255.255 Mask:255.255.0.0
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:55 errors:0 dropped:0 overruns:0 frame:0
TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:1000
RX bytes:6722 (6.5 KiB) TX bytes:0 (0.0 B)
~ #

Let's test the TCP/IP stack on the STM32F4.

From a development host validate that the STM32F4 is visible using ping:

-bash-3.2$ ping 172.17.6.136
PING 172.17.6.136 (172.17.6.136) 56(84) bytes of data.
64 bytes from 172.17.6.136: icmp_seq=1 ttl=64 time=1.80 ms
64 bytes from 172.17.6.136: icmp_seq=2 ttl=64 time=0.304 ms
64 bytes from 172.17.6.136: icmp_seq=3 ttl=64 time=0.301 ms
64 bytes from 172.17.6.136: icmp_seq=4 ttl=64 time=0.298 ms
64 bytes from 172.17.6.136: icmp_seq=5 ttl=64 time=0.299 ms
^C
--- 172.17.6.136 ping statistics ---
5 packets transmitted, 5 received, 0% packet loss, time 4646ms
rtt min/avg/max/mdev = 0.298/0.600/1.802/0.601 ms
-bash-3.2$

Ping the development host from the STM32F4:

~ # ping 172.17.0.1
PING 172.17.0.1 (172.17.0.1): 56 data bytes
64 bytes from 172.17.0.1: seq=0 ttl=64 time=0.691 ms
64 bytes from 172.17.0.1: seq=1 ttl=64 time=0.721 ms
64 bytes from 172.17.0.1: seq=2 ttl=64 time=0.724 ms
64 bytes from 172.17.0.1: seq=3 ttl=64 time=0.719 ms
^C
--- 172.17.0.1 ping statistics ---
4 packets transmitted, 4 packets received, 0% packet loss
round-trip min/avg/max = 0.691/0.713/0.724 ms
~ #

On the target, start the telnetd daemon to allow connections to the STM32F4:

~ # telnetd
~ # ps
PID USER VSZ STAT COMMAND
1 root 352 S init
2 root 0 SW [kthreadd]
3 root 0 SW [ksoftirqd/0]
4 root 0 SW [events/0]
5 root 0 SW [khelper]
6 root 0 SW [async/mgr]
7 root 0 SW [sync_supers]
8 root 0 SW [bdi-default]
9 root 0 SW [kblockd/0]
10 root 0 SW [rpciod/0]
11 root 0 SW [kswapd0]
12 root 0 SW [nfsiod]
18 root 367 S /bin/hush -i
25 root 332 S telnetd
26 root 348 R ps
~ #

Connect to the target from the development host using telnet. The target is configured to accept an empty password for root so just hit Enter when asked for password:

-bash-3.2$ telnet 172.17.6.136
Trying 172.17.6.136...
Connected to 172.17.6.136.
Escape character is '^]'.

stm32f4x9-som login: root
Password:
~ # ls
bin dev etc httpd init mnt proc root sys usr var
~ # exit
Connection closed by foreign host.
-bash-3.2$

Start the dropbear SSH daemon to allow secure connections to the target:

~ # dropbear
~ # ps
PID USER VSZ STAT COMMAND
1 root 352 S init
2 root 0 SW [kthreadd]
3 root 0 SW [ksoftirqd/0]
4 root 0 SW [events/0]
5 root 0 SW [khelper]
6 root 0 SW [async/mgr]
7 root 0 SW [sync_supers]
8 root 0 SW [bdi-default]
9 root 0 SW [kblockd/0]
10 root 0 SW [rpciod/0]
11 root 0 SW [kswapd0]
12 root 0 SW [nfsiod]
18 root 367 S /bin/hush -i
25 root 340 S telnetd
30 root 296 S dropbear
31 root 348 R ps
~ #

Connect to the target from the development host using ssh. The first connection takes several seconds to establish as the STM32F4 runs computation-extensive key calculations. Again, hit Enter on the password prompt:

-bash-3.2$ ssh root@ 172.17.6.136
root@ 172.17.6.136's password:
~ # ps
PID USER VSZ STAT COMMAND
1 root 352 S init
2 root 0 SW [kthreadd]
3 root 0 SW [ksoftirqd/0]
4 root 0 SW [events/0]
5 root 0 SW [khelper]
6 root 0 SW [async/mgr]
7 root 0 SW [sync_supers]
8 root 0 SW [bdi-default]
9 root 0 SW [kblockd/0]
10 root 0 SW [rpciod/0]
11 root 0 SW [kswapd0]
12 root 0 SW [nfsiod]
18 root 367 S /bin/hush -i
25 root 340 S telnetd
30 root 372 D dropbear
32 root 372 S dropbear
33 root 359 S -sh
34 root 348 R ps
~ # exit
Connection to 172.17.6.136 closed.
-bash-3.2$

On the target, configure a default gateway and a name resolver. Note how the sample configuration below makes use of the public name server provided by Google. Note also use of vi to edit target files on the target:

~ # route add default gw 172.17.0.1
~ # vi /etc/resolv.conf

nameserver 8.8.8.8
~

Use ntpd to synchronize the time on the target with the time provided by a public server:

~ # date
Thu Jan 1 00:40:53 UTC 1970
~ # ntpd -p 0.fedora.pool.ntp.org
~ # sleep 5
~ # date
Tue Jan 14 13:54:37 UTC 2014
~ #

Use wget to download a file from a remote server:

~ # wget ftp://ftp.gnu.org/README
Connecting to ftp.gnu.org (208.118.235.20:21)
README 100% |*******************************| 1962 --:--:-- ETA
~ # cat README
This is ftp.gnu.org, the FTP server of the the GNU project.
...

Mount a directory exported by a development host over NFS:

~ # mount -o nolock,rsize=1024 172.17.0.1:/home/vlad/test/linux-2.6.31-fl /mnt
~ # ls /mnt
LICENSE.TXT README linux-2.6.31-fl.patch
~ # umount /mnt
~ #

Start the HTTP daemon:

~ # httpd -h /httpd/html/
~ #

From a local host, open a Web browser to the STM32F4 and watch the demo web page provided by the target. The STM32F4 shows the current time and date as well as the list of the currently running processes: