Asterisk on an Atcom IP01
Introduction
Oct 2012: I would recommend a SheevaPlug/RaspberryPi + Obi110 instead of
the Atcom IP01 for the following reasons:
- Due to its lack of an MMU, the Atcom requires a specific Linux distro
(uClinux)
- There's only one project still supported (Switchfin), and even then,
only by a couple of programmers. So if there's a bug, you're basically on
your own (and the Blackfin uClinux forum won't help much since they only
provide the CPU)
- Switchfin/AstFin don't provide a packaging system, so you must recompile
a whole new image to add/remove applications
- Applications must be recompiled, and possibly rewritten to run on uClinux
- The appliance only provides 64MB of RAM, and even less if RAM is used
to host the root filesystem instead of reading it off the NAND memory
- Asterisk is the only IP PBX available, and only in old releases (1.4
or 1.6)
- Zaptel isn't as good a solution as a dedicate appliance to connect to
the PSTN
This article contains information on how to work with the Atcom
IP01 Asterisk appliance based on a project by David
Rowe. The unit I ordered came with a single FXO module so as to connect it to
an analog phone line, and used David's modular BAPS packaging system (ŕ la OpenWrt)
which is different
from the Astfin/Switchfin solution that includes everything into a single binary
image.
As of June 2009, this device uses the BlackfinOne
BF532 board using a Blackfin ADSP-BF532
CPU, 64MB RAM+ 256MB NAND flash RAM + 2MB SPI Flash, and runs uCLinux
(short for "Micro Controller Linux") instead of the standard Linux
because the Blackfin has no Memory Management Unit
(MMU). You can learn more about what the lack of MMU means and the differences
between run-of-the-mill Linux and uClinux in the following articles: Differences
between µClinux and Linux, Blackfin,
uClinux for Linux Programmers,
and Why is Malloc
Different Under uClinux?.
When an application running under uClinux crashes, it might leave RAM in
a poor state and it is recommended to reboot the appliance.
As the Blackfin boot ROM can't read the Linux kernel directly off the NAND,
the Atcom uses a 256KB SPI flash chip (Serial Peripheral Interface) to hold the Uboot bootloader, which is
able to read the NAND to copy the Linux kernel to RAM. When using "root=/dev/mtdblock0",
this is a RAM-based root filesystem, while "root=/dev/mtdblock2" is
the second partition in the NAND.
Note that the label of /dev/mtd0 is "ROMfs", but it's actually
a device in RAM that uses the romfs
filesystem as the initial ram disk, ie. this tiny RAM-based filesystem is
concatenated
to the kernel, so that you can safely erase and rewrite the NAND with a
real, full filesystem.
FYI, "µClinux a.k.a. uClinux-dist, is a Linux distribution
like any other Linux distribution, built from the Linux kernel from kernel.org
and assorted other packages, and software from the GNU project. Since µClinux
is optimised for size, it uses more compact alternatives (busybox, uclibc,
etc) than a non-embedded distribution."
Since Blackfin uClinux-dist
is meant to be used with any Blackfin-based appliance, uClinux-dist-based alternatives
AstFin and Switchfin had to include telephony applications such as Asterisk + Zaptel/Dahdi.
"Buildroot is a set of Makefiles
and patches that allows you to easily generate a cross-compilation toolchain,
a root filesystem and a Linux kernel image for your target. Buildroot can be
used for one, two or all of these options, independently.
Buildroot is useful
mainly for people working with embedded systems. Embedded systems often use
processors that are not the regular x86 processors everyone is used to having
in his PC. They can be PowerPC processors, MIPS processors, ARM processors,
etc.
A compilation toolchain is the set of tools that allows you to compile
code for your system. It consists of a compiler (in our case, gcc), binary utils
like assembler and linker (in our case, binutils) and a C standard library (for
example GNU Libc, uClibc or dietlibc)."
Note that if you use the Atcom exclusively
with digital devices and make sure all SIP devices use the same codec (ie. with
no need to perform translation), the
Blackfin is a questionable choice since its being a DSP offers no added-value compared
to more standard CPUs with an MMU, which have the advantage of requiring less or no application
rewrites. In this case, consider other compact, embedded devices like Alix
boards, the SheevaPlug, Buffalo (eg. WZR-HP-G300NH)
or Linksys (eg. WRT54GS)
routers, the Seagate
FreeAgent Dockstar NAS, or even some thin clients like HP's 55xx series.
Note that Freeswitch, the alternative to Asterisk, doesn't
(yet?) support Blackfin processors, although someone was able to compile and
run FS on a Planex router
and the uClinux-based OpenWrt firmware.
Finally, when it comes to getting help, you should know that...
- Atcom doesn't provide a forum where you could ask questions, and as
of January 2011, its wiki is gone
- The two
forums for the BAPS software has very little traffic; The Freetel
mailing list is a bit more responsive but not by much
- the AstFin and the Switchfin
forums are a bit more active, but not by much either
- The Blackfin
uClinux-dist forum doesn't know anything about the Atcom appliance,
since this product simply happens to use a Blackfin CPU but has otherwise
no connection with Blackfin, and the Atcom appliance is not part of the
official uClinux-dist software
- Applications that are part of uClinux-dist don't all work. You'll have
to include and test them to check
- Therefore, since the Atcom uses Uboot, uClinux-dist, the uClibc library,
and (for the BAPS software) the (now obsolete and replaced by opkg)
ipkg packaging tool, you
should also try to ask in sites dealing with those applications, such as
the OpenWrt community
MTD
Note: The MTD utilities can be installed on the workstation with "# apt-get install mtd-utils".
NAND
www.linux-mtd.infradead.org
"The memory is arranged as an array of pages. A page consists of 256
/ 512 Byte data and 8 / 16 Byte spare (out of band) area. Newer chips have 2048
Bytes data and and 64 Bytes spare area sizes. The spare area is used to store
ECC (error correction code), bad block information and filesystem-dependent
data. n pages build one block. The read / write access to data is on a per page
basis. Erase is done on a per block basis. The commands to read / write / erase
the chip is given by writing to the chip with the Command Latch Enable pin high.
Address is given by writing with the Address Latch Enable pin high.
[...] UBI stores 2 small 64-byte headers at the beginning of each non-bad
physical eraseblock:
- erase counter header (or EC header) which contains the erase counter
of the physical eraseblock (PEB) plus some other not so important information;
- volume identifier header (or VID header) which stores volume ID and
logical eraseblock (LEB) number this PEB belongs to (plus some other not
so important information).
This is why logical eraseblocks are smaller than physical eraseblock - the
headers take some flash space.
[...] Flash reads and writes may only be done in portions of minimum input/output
unit size, which depends on flash type: NAND flashes usually have 512, 2048
or 4096 byte min. I/O. unit size, which corresponds to NAND page size. NAND
flashes store per-NAND page ECC codes in the OOB area, which means that whole
NAND page has to be written at once to calculate the ECC code, and whole NAND
page has to be read at once to check the ECC code.
[...] When working with UBI, it is important to realize that UBI stores erase
counters on the flash media. Namely, each physical eraseblock has so-called
erase counter header which stores the amount of times this physical eraseblock
has been erased (see here). And of course, it is important not to lose the erase
counters, which means that the tools you use to erase the flash and to write
UBI images have to be UBI-aware. The mtd-utils repository contains the ubiformat
utility which takes things right, instead of using flash_erase, dd, or nandwrite.
[...] UBIFS works on top of UBI volumes and cannot operate on top of MTD
devices
Avoid formating an empty flash before running UBI on top of it, as you lose
erase counters (wearing information) every time you erase the flash. Try to
use UBI-aware utilities and flashing programs, eg. ubiformat /dev/mtd0
The ubinize utility uses a configuration file that describres all UBI volume(s)
which the image has to contain".
Find NAND hardware information
Before flashing the NAND with a root filesystem, you'll need the following
informations that are provided by the mtdinfo utility:
- Physical erase block (PEB) (cat /proc/mtd)
- Minimum I/O unit size
- Sub-page size
From those, you can compute the Logical
erase block (LEB) used by Ubi(fs).
Resources
Ubi(fs)
Ubi works with raw devices such as NAND, ie. those that don't have firmware
to provide block-based access through FTL. UBI maps logical eraseblocks to physical
eraseblocks, and provides wear-leveling and transparent I/O errors handling.
A UBI volume is a set of consecutive logical eraseblocks (LEBs). Each logical
eraseblock may be mapped to any physical eraseblock (PEB). UBI volume size is
specified when the volume is created and may later be changed.
UBI volumes can be static or dynamic, ie. they may be created, removed or
re-sized dynamically, while MTD partitions are static.
Important UBI applications:
- mtdinfo - reports information about MTD devices found in the system.
- ubinfo - provides information about UBI devices and volumes found in
the system
- ubiattach/ubidetach- attaches/detaches MTD devices (which describe raw
flash) to UBI and creates corresponding UBI devices
- ubimkvol/ubirmvol - creates/removes UBI volumes on UBI devices
- ubiupdatevol - updates UBI volumes; this tool uses the UBI volume update
feature which leaves the volume in "corrupted" state if the update
was interrupted; additionally, this tool may be used to wipe out UBI volumes
- ubinize - generates UBI images
- ubiformat - formats empty flash, erases flash and preserves erase counters,
flashes UBI images to MTD devices
Adding Ubi to menuconfig
Memory Technology Device (MTD) support > UBI - Unsorted block images >
<*> Enable UBI
Add support for Ubifs filesystem.
Device nodes
For Ubi(fs), it is recommended to run "mdev" and let it create
device nodes dynamically instead of listing device nodes statically in device_table.txt.
- make config_menuconfig
Miscellaneous Configuration > Device
Nodes (Dynamic)
BusyBox > Linux System Utilities
[*] mdev
[*] Support /etc/mdev.conf
[
] Support subdirs/symlinks (NEW)
[ ] Support
command execution at device addition/removal (NEW)
[ ] Support
loading of firmwares (NEW)
- vi /usr/src/uClinux-dist-2010R1-RC5/vendors/Rowetel/IP04/mdev
#!/bin/sh
#
Start up file for mdev
case $1 in
start)
echo "Starting mdev...";
echo
/sbin/mdev > /proc/sys/kernel/hotplug;
/sbin/mdev
-s;
;;
stop)
killall -9 mdev;;
enable)
rm -f /etc/rc.d/S20mdev;
ln
-s /etc/init.d/mdev /etc/rc.d/S20mdev;;
disable)
rm -f /etc/rc.d/S20mdev;;
*)
cat <<EOF;;
Syntax: /etc/init.d/mdev [command]
Available
commands:
start Start
the service
stop Stop
the service
enable Enable
service autostart
disable
Disable service autostart
EOF
esac
- vi /usr/src/uClinux-dist-2010R1-RC5/vendors/Rowetel/IP04/Makefile
#Added
$(ROMFSINST)
/etc/init.d/mdev
$(ROMFSINST) -s /etc/init.d/mdev /etc/rc.d/S20mdev
Alternatively, here's how to create nodes manually:
- mknod /dev/ubi_ctrl c 10 63
- mknod /dev/ubi0 c 253 0
Upgrading just the kernel
Couldn't figure out how to get a running kernel without
attached ext2 root filesystem.
First, boot up and run mtdinfo -a to check the size of the mtd1 partition
- ip04> set autostart
- ip04> tftp 0x1000000 uImage
Note the size of the image in
hexa, eg. "Bytes transferred = 3670016 (380000 hex)"
- ip04> nand erase clean 0x0 <size of mtd1>
- ip04> nand erase 0x0 <size of mtd1>
- ip04> nand write 0x1000000 0x0 0x380000
Important: "nand" expects numbers to be in hexa.
Creating Ubifs root filesystem
On the workstation
Compile uClinux mtdinfo
On the Atcom
- Download and run mtdinfo /dev/mtd2 -u
- Write down "Default UBI LEB size" (UBIFS_LEB_SIZE) + "Amount
of eraseblocks" (UBIFS_MAX_LEB_CNT) + "Minimum I/O unit size"
(UBIFS_MIN_IO_SIZE), where the total size of the partition is Eraseblock
size * Amount of eraseblocks
On the workstation
- vi vendors/AnalogDevices/vendor.mak
UBIFS_MIN_IO_SIZE ?= 2048
UBIFS_LEB_SIZE
?= 129024
UBIFS_MAX_LEB_CNT ?= 1984
- vi ubi.cfg
[ubifs]
mode=ubi
image=./images/rootfs.ubifs
vol_id=0
vol_size=230MiB
vol_type=dynamic
vol_name=rootfs
vol_flags=autoresize
- ubinize -o rootfs.ubi.img -m 2048 -p 128KiB -s 512 ./ubi.cfg
- mv rootfs.ubi.img /var/www
On the Atcom
- Boot with a RAM-based root filesystem
- wget -c http://192.168.0.3/rootfs.ubi.img
- ubiformat /dev/mtd2 -s 512 -f rootfs.ubi.img
- ubiattach /dev/ubi_ctrl -m 2
- mount -t ubifs ubi0:rootfs /mnt
Note: "rootfs" is set
in ubi.cfg
If mounted OK:
- umount /mnt
- ubidetach /dev/ubi_ctrl -m 2
- reboot
- uboot> set bootargs ubi.mtd=2
root=ubi0:rootfs rw rootfstype=ubifs
Mounting a Ubifs partition
- First, attach the MTD partition to Ubi: ubiattach /dev/ubi_ctrl -m 2 (2 = mtdblock2)
- To create /dev/ubi0: mdev -s
- Check Ubi infos: ubinfo /dev/ubi0 -a
- NOT NEEDED AFTER FIRST TIME? ubimkvol /dev/ubi0 -m -N ubifs0
- mount -t ubifs ubi0:rootfs /mnt
- umount /mnt
- ubidetach /dev/ubi_ctrl -m 2
- reboot
Do not worry about "UBIFS: recovery needed" after rebooting: /bin/reboot
takes care of calling sync() before rebooting, so the Ubifs partition should
be left in a stable state.
If you'd rather that uClinux unmount the Ubifs partition before rebooting,
replace the default simpleinit with Busybox's init and include the "poweroff,
halt, and reboot" option, More information here.
Resources
Updating to a new firmware
Tips for newbies
- On the workstation where you'll build new images, use a standard Linux distro, and not too recent, so as to increases
chances of having the expected version of dependencies. Ubuntu seems like
the most common distro
- On Ubuntu, install a TFTP server thusly: apt-get update ; apt-get install
tftpd-hpa ; vi /etc/default/tftpd-hpa: RUN_DAEMON="yes";
service tftpd-hpa start; Copy bootable image in /var/lib/tftpboot/
- uClinux provides "make single" to force GCC to only use one
core on CPU: Makes for easier debugging
- If requested for investigation, you can create a small bugreport by
running "make bugreport" in uClinux-dist. The tarball contains
information about the toolchain and configuration files
- Astfin/Switchfin require compiling Asterisk to get a web GUI to the
Atcom, even if it's just to update the firmware. Compiling Lighttpd isn't
enough (or even needed: The web GUI might use another web server).
- Tips on debugging
applications. Also use the "LD_DEBUG" environment variable
to investigate library issues
- Read how
to build applications/libraries either in FLAT or FDPIC ELF formats
- "the -l option is a linker option, and thus needs to be placed
AFTER the name of the file to be compiled. This is quite different from
the normal option syntax. If you place the -l option before the filename,
it may fail to link at all, and you can end up with mysterious errors."
(source)
Pay particular attention to linking options, such as for instance "-Wl,-E"
which is required to compile the Lua interpreter
- If the image doesn't include "ldd" to check which libraries
an application needs, you can find it in recent releases of uClinux
(in uClibc/utils/). If it doesn't compile, try "scanefl -an" from pax-utils
or "readelf"
- bin-elf is only needed if you wish to compile code as bare-metal, ie.
stand-alone apps that don't use any OS to run. Since we'll use uClinux, ignore
stuff that mention bin-elf
- To figure how to build and install the files that make an application,
you'll have to go through its config/Makefile(s) line by line. It's easier
to start from the deepest Makefile and work your way up
- If an application is part of uClinux-dist and you would like to compile
it indepently into an ipkg package but there are errors you can't solve,
a work around is to simply run "make menuconfig" to include it
in uClinux, build an image, and simply copy the binaries from its staging
directory and build an ipkg package
- Do not bother adding -fpic/-fPIC switches: The Blackfin toolchain takes
care of this
- Don't mix different versions of the toolchain, the uClinux-dist, and
the kernel + libraries running on the Atcom
- To add files to ./romfs during the build process, edit vendors/Rowetel/IP04/Makefile
- If you added files manually in ./romfs, you can build a new image with
"make image"
- To find out which version of uClibc is included in uClinux-dist:
printf
'#include <features.h>\n__UCLIBC_MAJOR__ __UCLIBC_MINOR__ __UCLIBC_SUBLEVEL__\n'
| bfin-uclinux-gcc -E - | tail -1
- To remove unneeded libraries, in uClinux-dist, run "make config_menuconfig",
go to Blackfin build options, and enable "Cull unused ELF shared libraries".
Make sure no application requires those libraries, though: For instance,
dropbear requires libutil.so.0, which is removed by that option...
- In uClinux-dist in the ./vendor section, if a Makefile.local exists,
it gets included along with the Makefile. An easy way to add commands without
changing the standard Makefile
Here are standard variables that you can use in Makefiles to compile files
as ELF FDPIC (instead of FLAT):
- #Assuming the Blackfin toolchain is untarred there
- export PATH:=$(PATH):/opt/uClinux/bfin-linux-uclibc/bin
-
- TARGET_CROSS=bfin-linux-uclibc-
-
- export CC=$(TARGET_CROSS)gcc
- export STRIP=$(TARGET_CROSS)strip
- export AR=$(TARGET_CROSS)ar rcu
- export RANLIB=$(TARGET_CROSS)ranlib
-
- #Download and untar uClinux-dist for apps that need it
#Compile uClinux
to get binaries
export STAGING_DIR=/usr/src/uClinux-dist/staging
- export UCLINUX_LIB=/usr/src/uClinux-dist/lib
- export UCLINUX_ROOT_LIB=/usr/src/uClinux-dist/root/lib
-
- export CFLAGS=-O2 -Wall -pedantic -I$(STAGING_DIR)/usr/include
- export LDFLAGS=-L$(STAGING_DIR)/usr/lib -L$(UCLINUX_LIB) -L$(UCLINUX_ROOT_LIB)
add_required_libraries_here
To compile a static library:
- $(AR) rcu -static -o libmylib.a mylib.o mylib2.o
- #ranlib not always needed, but it doesn't hurt
- $(RANLIB) libmylib.a
To compile a shared library:
- $(CC) $(CFLAGS) -shared -Wl,-E,-soname,libmylib.so -o libmylib.so
mylib.c
To call AutoTool's configure to compile a C application:
- export PATH=$PATH:/usr/src/baps/opt/uClinux/bfin-linux-uclibc/bin
-
- ./configure --host=bfin-linux-uclibc CC=bfin-linux-uclibc-gcc AS=bfin-linux-uclibc-as
CFLAGS="-O2 -Wall -ansi -pedantic -I/usr/src/uClinux-dist/linux-2.6.x
-I/usr/src/uClinux-dist/staging/usr/include " LDFLAGS="$LDFLAGS
-L/usr/src/uClinux-dist/staging/usr/lib" AR="bfin-linux-uclibc-ar
rcu" RANLIB=bfin-linux-uclibc-ranlib
The same, to compile a C++ application:
./configure --host=bfin-linux-uclibc CPP=bfin-linux-uclibc-cpp CXX=bfin-linux-uclibc-g++
CC=bfin-linux-uclibc-gcc
Testing an image
You don't have to burn a new image just to try it and see if it works. Here's
how to set things up:
- Now is the time to save any data out of the Atcom, in case they get
removed/overwritten...
- On a workstation, run a TFTP server and put the image in its data directory
(for Windows, you can try the open-source Tftpd32
)
- Connect a serial cable to the Atcom and reboot
- Hit any key to prevent Uboot from loading Linux, and type the following
commands:
#Disable autoloading of kernel
set autostart
set
serverip tftpd.server.address
set bootargs ethaddr=atcom.MAC.address
root=/dev/mtdblock0 rw
#Save params to EEPROM
save
tftp 0x1000000
myimage
bootm 0x1000000
Important: Astfin-based images from Atcom are hard-coded to use mtd2 to save
persistent data, even if you just wanted to test an image...
If the image works OK, reboot the Atcom, enter Uboot, and type the following
commands to burn the image in the NAND:
- nand erase clean
- nand erase
set autostart
tftp 0x1000000 uImage
;tftp gives image size in "Bytes transferred": Use this
info as the last parameter below, using the next 20.000 increment to make
sure it fits:
nand write 0x1000000 0x0 0x300000
;alternatively, use
the "filesize" variable
- nand write 0x1000000 0x0 ${filesize}
set autostart yes
- save
- reset
Switchfin
Switchfin is a fork of the AstFin2
project by the SwitchVoice people that
compiles a full binary image of the uClinux OS, and optionally Asterisk, Dahdi
and some other
software (ls /usr/src/switchfin/package/).
Its makefile will take care of downloading
the Blackfin toolchain, uClinux, and uClibc, and by default, generate both the
image and the bootloader.
What I don't like about Switchfin:
- 20MB of RAM is taken from the 64MB for the root filesystem, while BAPS
reads the root filesystem directly from NAND
- It downloads 80MB of files into /persistent/sounds/
- Unlike BAPS, Switchfin doesn't install applications through a package
manager: Every application must be compiled in the image
Updating
There are three ways to update an Atcom already running Switchfin:
- If already running Switchfin, by connecting to its embedded Switchfin web server
- By connecting to the Atcom through its serial port or SSH, downloading
uImage-md5 into /persistent/imageupdate/, renaming the file as uImage, and
rebooting: The IP01 will reflash itself automatically
- By connecting to the Atcom through its serial port and a terminal application,
and using tftp + bootm (and if it works OK, burning the image to NAND)
Creating a new image
Here's how to compile the latest source from SVN on an x86 Ubuntu 10.04 host:
- apt-get update
- apt-get upgrade (reboot with new kernel, if applicable)
- Install prerequisites:
apt-get install autoconf automake bash binutils bison bzip2 coreutils
flex gawk gcc gettext grep intltool iputils-ping libtool libz-dev linux-libc-dev
liblzo2-dev liblzo2-2 libncurses5 libreadline5 libreadline5-dev libncurses5-dev
ncurses-dev m4 make pax-utils pkg-config rpm texinfo zlib1g zlib1g-dev subversion
mtd-utils uuid-dev uuid unzip build-essential
Note: On Linux Mint,
libreadline5-dev has been replaced with libreadline-gplv2-dev
- cd /usr/src
- svn co https://switchfin.svn.sourceforge.net/svnroot/switchfin/switchfin/trunk/
switchfin
- cd switchfin
- make menuconfig
Note: Include "SpanDSP based CallerID",
or libspandsp won't be built while it's expected by Asterisk
- make
- vi build_ip01/uClinux-dist/lib/libcurl/Makefile: If it refers to libcurl.so.4,
change this for libcurl.so.5 ; make
- make image: Output will be found in eg. ./build_01/image_01/ (more
infos):
- uImage - uClinux image + file system compressed in a single file.
This image typically you load using the tftp support of u-boot or using
the serial interface support of u-boot.
- uImage-md5 - This is the image above with 32 bytes MD5 check sum
appended. This kind of image you can load directly (http or tftp) from
the GUI of the PBX.
- u-boot.ldr - u-boot image which you can load in your hardware target
using JTAG programmer (like icebear) or serial interface (if you have
already an old u-boot loaded).
- cp build_ip01/image_ip01/uImage /tftpboot
In case you need them, binaries are located under build_ip01/image_ip01/.
Make sure a web server is running on the workstation, with its docroot set
to "/tftpboot". If the Atcom is already running AstFin or Switchfin
with the Asterisk GUI, just aim your browser to its web server, log on as admin/switchfin,
locate Firmware Update, and copy/paste the full URL to uImage-md5 on the workstation.
Reboot the Atcom, and check that it's using the new firmware.
If there's
no GUI available, follow the instructions above to download the image through
TFTP after copying the image in the /tftpboot on the workstation:
- Connect the Atcom to the workstation through the serial cable
- Unplug, replug the Atcom, and hit any key to prevent it from booting
Linux
- Type the following commands (stuff in bold must be customized to fit
your setup):
setenv autostart
setenv ipaddr 192.168.0.9
setenv
netmask 255.255.255.0
setenv gatewayip 192.168.0.254
setenv
serverip 192.168.0.3
setenv bootargs ethaddr=Atcom.MAC.address console=ttyBF0,115200
root=/dev/mtdblock0 rw
save
- Download the image in RAM, and check its size ("Bytes transferred
= 7471104 (720000 hex)):
tftp 0x2000000 uImage
Note:
If the Atcom can't fetch the image, unplug and replug its Ethernet cable,
and give it another try.
- Check that the image works OK by booting it directly from RAM:
bootm
0x2000000
Log on as root/uClinux
- IF OK, redownload image and save it to EEPROM:
nand erase clean
nand
erase
nand write 0x2000000 0x0 0x720000
setenv
setenv autostart yes
save
reset
Note that unlike the BAPS firmware, Switchfin keeps the root filesystem in
RAM and uses the NAND to save persistent files like sound files, etc. Consequently,
only 40MB out of 64MB is available in RAM once Switchfin is up and running.
If you get the error "couldn't allocate a block (no free space)",
it means your uImage is now to big, you need to enable "Cull unused ELF
shared libraries" in the Build options, or remove some applications
when running "make menuconfig" or the built files in the root
filesystem. Alternatively, you can increase the space reserved for the
root filesystem by editing /package/uClinux-dist/vendors/SwitchVoice/vendor.mak
to change the EXT2_BLOCKS variable before running "make image".
Post-install tweakings
Network
If you get "ping: bad address
'downloads.digium.com'", check that the IP address is OK: ifconfig. If
not: ifconfig eth0 192.168.0.9, and connect to the Atcom's web GUI to change
its IP configuration (Admin > Network settings). Click on Reboot when prompted.
Alternatively, the network configuration can be changed by editing
/etc/asterisk/rc_org.conf which Switchfin uses to overwrite /etc/network.conf
at boot-time.
By default, Switchfin provides an SSHd server (dropbear), so you can also
connect to the Atcom through SSH instead of the serial port
Time
/etc/asterisk/rc_org.conf
- #For Central European Time
- TIMEZONE = CET-1CEST,M3.5.0/2,M10.5.0/3
TZNAME=Europe/Paris-
- #For France
- NTPserver = fr.pool.ntp.org
Note: The reason those settings are located in /etc/asterisk is so they are
accessible from the the Asterisk Management Interface (AMI). rc_org.conf is
mapped to network.conf via the /etc/rc script.
Boot errors
If you see error messages related to dahdi/vlan "Permission denied":
- chmod +x /persistent/etc/init.d/dahdi
chmod +x /persistent/etc/init.d/vlan
/persistent/etc/init.d/dahdi
disable
/persistent/etc/init.d/vlan disable
rm /persistent/etc/rc.d/S55vlan
/persistent/etc/init.d/dahdi
enable
/persistent/etc/init.d/vlan enable
ls -al /etc/rc.d/
sync
reboot
Check that the problem went away
Procwatch
/etc/init.d/asteriskwatch calls procwatch, which reboots the host if asterisk
isn't running. You can disable this while you're configuring asterisk:
/etc/init.d/asteriskwatch disable
Dahdi
Switchfin uses Dahdi instead of Zaptel. Its configuration file is located
in /etc/dahdi/system.conf. The equivalent of zapata.conf is /etc/asterisk/chan_dahdi.conf.
Asterisk
To enable full logging for debugging:
How
to Load u-boot in the hardware?
Can
I load the uImage using the web GUI
"In the PBX GUI go to 'Firmware upgrade' (in the advanced options section)
and select HTTP URL": Is it the same as the VoIPTel CE web GUI?
Can
I load the uImage manually using u-boot?
Uprading
an Atcom appliance that was installed using BAPS
Here's what the Switchfin tree contains after downloading the latest SVN
code:
- config/
- Config.in
- CONTRIBUTORS
- COPYING
- Makefile
- package/
- README
- .svn/
- TODO
Next, running "make menuconfig" adds the following two files in
the root directory:
Next, "make" will download and install the Blackfin uClibc toolchain,
followed by the uClinux distribution.
Trying Switchfin 2010
- cd /usr/src
- svn co https://switchfin.svn.sourceforge.net/svnroot/switchfin/switchfin/tags/switchfin-2010R1-RC5/
switchfin-2010R1-RC5
- cd switchfin-2010R1-RC5
- make menuconfig
- make
- make image
Cross-compiling Yate
Todo
- Cross-compiling: Put settings in Bash script before calling configure
- Make: Edit fork() -> vfork() if needed
- Compile
- Install and configure: What files are required where?
- Check that it works with the FXO module: Does it need Zaptel?
From the original source
- Install the toolchain + uclibc
- cd /usr/src
- svn checkout http://voip.null.ro/svn/yate/trunk yate
- cd yate
- ./autogen.sh
- Create a Bash script to pass parameters to "configure":
#!/bin/bash
TARGET=bfin-linux-uclibc
CPP=${TARGET}-cpp
CXX=${TARGET}-g++
CC=${TARGET}-gcc
STAGING_DIR:=/usr/src/switchfin/build_ip01/blackfin-linux-dist/staging
STAGING_INC=${STAGING_DIR}/usr/include
STAGING_LIB=${STAGING_DIR}/usr/lib
YATE_CONFIGURE_OPTS=--host=${TARGET}
--prefix=/usr --sysconfdir=/etc --with-openssl=${STAGING_INC}/.. --with-libspeex=${STAGING_INC}
--with-zlib=${STAGING_INC}/.. --enable-dahdi --disable-zaptel --disable-wpcard
--disable-tdmcard --disable-wanpipe --enable-ilbc --disable-rtti --without-libpq
--without-mysql --without-libgsm --without-amrnb --with-spandsp --without-pwlib
--without-openh323 --without-libqt4
LDFLAGS="-L${STAGING_LIB}"
./configure ${YATE_CONFIGURE_OPTS}
- chmod +x myconfig.bash
- ./myconfig.bash
- make
This is a Bash script to compile Yate for ARM:
http://voip.null.ro/tarballs/xconfigure
Adding Yate to Switchfin as an alternative to Asterisk
Note: By now, patches should be part of Switchfin,
so this is no longer needed
- cd /usr/src
- git clone https://github.com/HaydenTech/switchfin.git
hayden-switchfin
wget -O - https://github.com/HaydenTech/switchfin/commit/558244ca9659b8b0223174300df0432ad6ab1737.diff
| patch -p1
- make menuconfig: Check "Yate"
- make
BAPS as alternative to buildroot (Switch/Astfin/uClinux-dist)
The very first build of Asterisk for the BlackFin processor was a hack of
OpenWRT called uCasterisk, ie. it used the same buildroot approach
("uClinux is the distribution of choice for Media and other embedded products.
OpenWrt on the other hand is the distribution of choice for building a router."
source)
"There are two commonly used build systems for Blackfin Asterisk, Astfin
and BAPS. Astfin builds
a single image containing all software, whereas BAPS is a package-based build
system (like apt-get or rpm). It is easy to move between Astfin and BAPS (they
both use similar Makefiles), so feel free to experiment with both." (source)
As of January 2011, when using the uClinux.mk Makefile, you will use the
2007 version of the uClinux-dist software just to build the kernel with a few applications pre-installed, including
the ipkg application which lets the user download and install packages, just like RPM and apt-get. As
a result, a standard BAPS image from Rowetel is only 2MB, while
a standard uClinux-dist
image is about 7MB.
AstFin is a rewrite of uCasterisk.
At some point, AstFin stalled and BAPS packages picked up. As of June 2010, AstFin2 is apparently
headed in a different direction than just Asterisk, so some developers forked
the code to Switchfin.
Here
is a comparison of BAPS and AstFin2, and here
is a list of BAPS packages. BAPS also comes from the OpenWrt world (ipkg).
Note that the Uboot that ships with BAPS Atcom is very compact, and doesn't
include commands like "mtdparts".
The reason the BAPS software require(d) to first boot Linux entirely in RAM,
copy the RAM root filesystem to NAND, and reboot is because of this
bug in mkyaffs.
uClinux.mk can build different images, such as "make -f uClinux.mk uClinux.mtd0.ip01"
which is for the Atcom IP01 and has root=/dev/mtdblock0 hard-coded so it uses
a RAM-based root filesystem.
Upgrading BAPS-based firmware
Here's how to upgrade an
Atcom currently running a Astfin/Switchfin-based firmware to a BAPS-based firmware:
- Connect to the Atcom through SSH
- cd /persistent
- wget http://rowetel.com/ucasterisk/downloads/uImage_r2.mtd0.ip01
- dd if=uImage_r2.mtd0.ip01 of=/dev/mtdblock1
- reboot
Once back in BAPS as root, the unit uses 192.168.1.30 as its IP address.
To have it configured through DHCP instead, see below.
Building your own BAPS uImage
Based on this article.
Note that unlike other *.mk files, uClinux.mk doesn't create an ipkg package
but a Uboot-compatible, binary image that contains just the Linux kernel and a few basic
applications (shell, ipkg, etc.).
WORKSTATION
- Install prerequisites
- cd /usr/src
- svn co http://svn.astfin.org/software/baps/trunk baps
- cd baps
- wget -c http://blackfin.uclinux.org/gf/download/frsrelease/348/3347/blackfin-toolchain-07r1.1-3.i386.tar.gz
- tar xzf blackfin-toolchain-07r1.1-3.i386.tar.gz
- (if not starting from scratch) make -f uClinux.mk uClinux-clean
- make -f uClinux.mk uClinux
This will download, patch, and compile the uClinux-dist
source code.
To solve a possible PATH_STR error:
vi uClinux-dist/linux-2.6.x/scripts/mod/sumversion.c
add
"#include <limits.h>"
- cp uClinux-dist/images/uImage /tftpboot/uImage
(uImage = uImage.ext2)
- Reboot the Atcom and test/burn this new image as explained below
ATCOM
To try out new image directly
- ip04> set autostart
- ip04> setenv ipaddr 192.168.0.9
- ip04> setenv netmask 255.255.255.0
- ip04> setenv gatewayip 192.168.0.254
- ip04> set bootargs ethaddr=$(ethaddr) root=/dev/mtdblock0 rw
- ip04> setenv serverip 192.168.0.3
serverip
= address of TFTP server from which image will be dowloaded
- ip04> save
- ip04> tftp 0x1000000 uImage
- ip04> bootm
To save new image into NAND
- (In uClinux) # reboot
- ip04> set autostart
- ip04> tftp 0x1000000 uImage
- ip04> nand erase clean
- ip04> nand erase
- ip04> nand write 0x1000000 0x0 0x300000
- ip04> set bootargs ethaddr=Atcom.MAC.address root=/dev/mtdblock0 rw
- ip04> save
- ip04> reset
uClinux is running but using a RAM-based ext2 root file system (mtdblock0).
To make it persistent, we must copy /root into /dev/mtdblock2 in the NAND:
- root:~> copy_rootfs.sh
- root:~> reboot
Next, set up u-boot to mount the root filesystem from /dev/mtdblock2 (type "print" to check
what env variables are already set, if any):
- ip04> tftp 0x1000000 uImage
- ip04> set nandboot 'nboot 0x1000000 0x0'
- ip04> set bootcmd run nandboot
- ip04> set bootargs ethaddr=Atcom.MAC.address root=/dev/mtdblock2 rw
- ip04> set autostart yes
- ip04> save
- ip04> reset
- Let the Atcom reboot and load uClinux
Install packages through ipkg (repository address in /etc/ipkg.conf):
- root:~> ipkg update
- root:~> ipkg list
- root:~> ipkg install zaptel-ip01
- root:~> ipkg install asterisk-1.4.20
- root:~> ipkg install dropbear
- root:~> ipkg install ntp
- root:~> ipkg list_installed
- root:~> reboot
Note:
- The dropbear package (SSH server) doesn't install a boot script in /etc/init.d/
Building BAPS 2008
In case you previously compiled 2007, make sure you rename uClinux-dist to
eg. uClinux-dist2007 and opt/uClinux to opt/uClinux2007.
- cd /usr/src
- svn co http://svn.astfin.org/software/baps/trunk baps
- cd baps
- wget -c http://blackfin.uclinux.org/gf/download/frsrelease/375/4037/blackfin-toolchain-08r1-8.i386.tar.gz
- wget -c http://blackfin.uclinux.org/gf/download/frsrelease/375/4041/blackfin-toolchain-uclibc-default-08r1-8.i386.tar.gz
- tar xzvf blackfin-toolchain-08r1-8.i386.tar.gz
- tar xzvf blackfin-toolchain-uclibc-default-08r1-8.i386.tar.gz
- make -f uClinux2008.mk uClinux
In case you want to check how long compiling takes, edit /usr/src/baps/uClinux2008.mk
thusly:
echo 'date' > time.txt
echo 'date' >> time.txt
Customizing kernel and/or applications
If some applications aren't available as ipkg packages but are available
in the uClinux-dist version downloaded by the uClinux.mk file (2007), you can customize
settings this way, before compiling a new image and find the compiled files
under /usr/src/baps/uClinux-dist/root:
For the kernel: cd uClinux-dist ; make linux_menuconfig
For applications: cd uClinux-dist ; make config_menuconfig
Once done, cd /usr/src/baps/ ; make -f uClinux.mk uClinux-clean ; make -f uClinux.mk uClinux
If the application isn't available in that old version of uClinxux-dist,
download the latest from Blackfin's site and try to compile it with either the
2007 version of the toolchain or, if it doesn't work (likely) with the latest
version of the toolchain, and see if the application works OK on an older uClinux
kernel. If it complains of missing libraries, start by checking its inner-most
Makefile and try to add the missing stuff to its LDFLAGS variable.
Things to try in BAPS
Connect the Atcom to a hub through the WAN interface, and telnet to it from
a PC. By default, the Atcom is set up to use 192.168.1.30, and no username/password
is required to telnet to it (to add a username + password, install the "login"
package, whose default combo is root/uClinux).
Playing with ipkg
ipkg update
ipkg upgrade
ipkg list //uninstalled packages available in repo
ipkg info mypackage
ipkg install mypackage
ipkg status mypackage
ipkg list_installed //packages already installed in host
ipkg files mypackage
ipkg remove mypackage
Note: The wildcard character "*" is allowed, eg. "libstd*".
Installing DropBear (SSH server/client)
- ipkg install dropbear
DropBear is launched through Inetd: cat
/etc/inetd.conf ; netstat -natp
- Log on as root/uClinux
If you get errors in the log file:
- touch /var/log/lastlog
- touch /var/log/wtmp
To set the date/time
First, install ntp:
- ipkg install ntp
- vi /etc/init.d/ntp: Change for NTP servers close to you, eg. "fr.pool.ntp.org"
for France
- /etc/init.d/ntp enable
By default, time is displayed as UTC. To display the time correctly,
"date" provided by Busybox 1.4.1 reads it localization through /etc/TZ,
which is copied to /etc/profile and exported as environment variable by the
/etc/init.d/ntp script:
For Central European Time, vi /etc/TZ to this:
- CET-1CEST,M3.5.0/2,M10.5.0/3
- reboot
- run "date", and check that time is displayed OK
If you can't reboot because you're running a test image in RAM, here's how
to change the current date/time for your location:
- ntpdate fr.pool.ntp.org
- export TZ=CET-1CEST,M3.5.0/2,M10.5.0/3
- date
More information here.
Adding CRON jobs
I couldn't get "ntpd" to work, so resorted to running ntpdate every
hour through a CRON job:
- ipkg install cron
- vi /etc/config/crontab
#BAD @hourly root /sbin/ntpdate -s -b
-p 8 -u fr.pool.ntp.org
0 * * * * root /sbin/ntpdate -s -b -p 8 -u fr.pool.ntp.org
- /etc/init.d/cron enable
- /etc/init.d/cron start
- tail -f /var/log/messages, and wait about a minute for cron to re-read
its contrab automatically
Syslog
By default, syslogd will output "-- MARK --" every 20mn to /var/log/messages.
syslogd is actually provided by Busybox, and this version ignore /etc/syslog.conf.
- vi /etc/inittab
slog:unknown:/bin/syslogd -n -m0
- reboot
If too much data in /var/log/messages, configure syslog
to send data to remote syslogd server or /tmp (not good idea: No trace after
rebooting) to save NAND.
To check network information
root:~> cat /proc/net/
To change the static IP settings
Edit /etc/init.d/network-static
To enable DHCP
- /etc/init.d/network-static disable
- /etc/init.d/network enable
- reboot
If the network link is down, unplug and replug the network cable that connects
the Atcom to the hub/switch, and see if the unit gets an address from the DHCP.
For some reason, the Atcom sometimes has its "link down".
To check the version of ucLinux
> uname -a
Linux ip04 2.6.19.3-ADI-2007R1.1-svn #3 Mon Mar 10 08:53:41 CST 2008 blackfin
unknown
> version
Linux release 2.6.19.3-ADI-2007R1.1-svn, build #3 Mon Mar 10 08:53:41 CST
2008
release 2007R1, build #13 Mon Mar 10 09:55:24 CST 2008
> cat /etc/issue
BlackfinOne BF532 v2 uClinux (http://blackfin.uclinux.org/projects/bf1/)
> cat /etc/firmwareversion
To change the root password
- perl -e 'print "crypt("yourpassword", "yoursalt")","\n"'
- copy/paste this new password in /etc/passwd
To transfer files to/from the Atcom
Use its FTP server by logging on as root/uClinux. wget is also installed by
default.
Installing Lighttp + PHP + SQLite BAPS packages
- By default, the Asterisk web server is running on TCP80. To turn it
off:
vi /etc/asterisk/http.conf: enabled=no
/etc/init.d/asterisk
stop ; /etc/init.d/asterisk start
- To install Lighttp, PHP, and SQLite:
ipkg install lighttpd
ipkg
install php
ipkg install sqlite3
ipkg list_installed
- Aim your browser at http://localhost/ to
check that Lighttpd is up and running. You can also get information on PHP
(http://localhost/test.php), and
play with SQLite (http://localhost/testdb.php)
By
default, Lighttpd starts with /etc/lighttpd.conf, and the document root
is /www
- To configure Lighttp so as to use PHP for CGI calls:
(to create
a symlink in /etc/rc.d/)
/etc/init.d/fastphp
enable
vi /etc/init.d/lighttpd: Change "-f /etc/lighttpd.conf"
to "-f /etc/lighttpd-fastphp.conf"
/etc/init.d/fastphp
start
/etc/init.d/lighttpd stop
/etc/init.d/lighttpd start
ps aux | grep -i php
- ls -al /etc/rc.d/, and make sure Lighttpd is started before the PHP
FastCGI process
Installing Asterisk and Zaptel/Zapata
In case the Atcom didn't come with Asterisk preinstalled or you upgraded
the image:
- ipkg list, and check what the latest Asterisk package is
- ipkg install asterisk-1.4.20
- ipkg install zaptel-ip01
- vi /etc/zaptel.conf: If not living in the US, edit as needed
- cd /etc/asterisk
- mv sip.conf sip.conf.orig
- mv extensions.conf extensions.conf.orig
- mv users.conf users.conf.orig
- vi sip.conf
- vi rtp.conf
- vi extensions.conf
- vi indications.conf
- vi asterisk.conf to move astlogdir to RAM-based
/tmp instead of NAND-based /
- vi asterisk.conf to move astspooldir to
RAM-based /tmp instead of NAND-based /
- vi /etc/init.d/asterisk
#Killall might leave RAM in disarray
stop)
asterisk -rx "stop now";;
- /etc/init.d/asterisk enable
- /etc/init.d/asterisk start
- ps aux | grep -i asterisk
- asterisk -vvvvvvvvvvvvr
- sip show peers
You can edit modules.conf to avoid loading modules you
don't need, eg.
- noload => pbx_gtkconsole.c
- noload => pbx_kdeconsole.c
- noload => app_intercom.c
- noload => chan_modem.c
- noload => chan_modem_aopen.c
- noload => chan_modem_bestdata.c
- noload => chan_modem_i4l.c
-
- load => res_musiconhold.c
-
- noload => chan_alsa.c
- noload => cdr_csv.c
- noload => cdr_custom.c
- noload => res_smdi.c
- noload => chan_iax2.c
- noload => format_g723.so
- noload => format_g726.so
- noload => format_g729.so
- noload => format_gsm.c
- noload => format_h263.so
- noload => format_h264.so
- noload => format_ilbc.so
- noload => format_jpeg.so
- noload => format_sln.so
- noload => format_vox.so
- noload => codec_g726.so
- noload => codec_g729.so
- noload => codec_speex.so
I don't know why some modules in .c and others in .so.
By default, output from launching "asterisk -vvvc" is in reverse
video, making it harder to read. To changed output to standard black text/white
background, edit asterisk.conf, and add this:
- [options]
- nocolor=yes
Asterisk
Checking Asterisk
On the Atcom, run "asterisk -r" to connect to the console, and
check log messages.
Connect to Asterisk from an SIP client, and dial either 2008 (play prompt)
or 2020 (record your voice, and check performance).
Modules
ls -al /usr/lib/asterisk/modules/
root:~> cat /proc/modules
Managing sound files
ls -al /var/lib/asterisk/sounds/
ls -al /var/lib/asterisk/sounds/moh
Asterisk configuration files
They are located in the usual /etc/asterisk/. To restore its configuration
files:
- root:~> ipkg update
- root:~> ipkg remove asterisk
- root:~> ipkg install asterisk
- root:~> reboot
Caller ID
Asterisk requires the asterisk-spandsp package to handle CallerID. To check
if it's installed:
$ ipkg list_installed
If not, here's how to install it:
- $ /etc/init.d/asterisk stop
- $ ipkg remove asterisk
- $ ipkg install asterisk-spandsp
- $ reboot
Configuring Zaptel
To configure the Zaptel interface for your country, edit /etc/init.d/zaptel.
Here's an example for Australia:
start) modprobe wcfxs opermode=AUSTRALIA;
root:~> ls -al /usr/doc/
-rw-r--r-- 1 root root 3142
May 31 01:56 zaptel.txt
root:~> cat /proc/zaptel/1
Adding extension to sip.conf
- tail /var/log/messages
- /etc/init.d/zaptel start
- vi /etc/asterisk/sip.conf
[6000]
type=friend
secret=6000
host=dynamic
qualify=yes
nat=no
context=demo
- /etc/init.d/asterisk start
- From an IP phone, connect to server with above account, and dial 1000
Writing a PHP script to handle call through Asterisk + AGI
- cd /var/lib/asterisk/agi-bin/
- vi myagiscript.php
#!/sbin/php
<?php
print "Hello,
world!";
?>
-
Building a new Busybox
-
On the workstation, in /usr/src/baps, compile uClinux once to get its source tree: make -f uClinux.dist
- Remove object files: make -f uClinux.mk uClinux-clean
- .. cd uClinux-dist, make config_menuconfig, and customize options for Busybox
- cd .. ; make -f uClinux.mk
- If compiling went OK, you should have a new busybox in ./uClinux-dist/root/bin
- On the Atcom, download this file, "chmod 755 busybox" and move (not copy)
it to /bin.
There is no need to copy this file in /sbin, as /sbin is just a symlink to /bin
- In /bin, add the new symlinks, eg. "ln -s busybox unzip".
Atcom firmware
As of June 2010, Atcom provides the AstFin-based VoIPTel
CE firmware (eg. IP01-0.3.7.ext2) so you can update the appliance.
Here's
how to reflash an Atcom that used the BAPS packaging system; Since this firmware
doesn't support a web GUI, we'll use a serial cable to download the latest firmware
from a workstation:
- Hook up a DB9-DB9 male-female serial cable between the workstation and
the Atcom
- On the workstation, install a TFTP server eg. TFTPd32,
copy the ext2 Atcom image in its directory, and start the TFTPd server
- Still on the workstation, open a terminal application with the following
settings:
Choose the right COM port, 115200 bps, 8 data bits and
no parity, hardware flow control off
- Reboot the Atcom
- Hit any key to prevent it from booting, and type the following commands
(you'll have to type: The serial connection is too slow and will probably
drop out some characters):
ip04>setenv
autostart
ip04>setenv ipaddr 192.168.0.9
ip04>setenv netmask
255.255.255.0
ip04>setenv gatewayip 192.168.0.254
ip04>setenv
serverip 192.168.0.1
ip04>save
ip04>tftp 0x1000000 IP01-0.3.7.ext2
Here,
I had a networking problem, where the Atcom couldn't connect to the TFTPd
server. I had to unplug and replug the Ethernet cable connecting the Atcom
to the hub
ip04>nand
erase clean
ip04>nand erase
ip04>nand write 0x1000000 0x0 0x700000
ip04>setenv
bootargs ethaddr=$(ethaddr) console=ttyBF0,115200 root=/dev/mtdblock0 rw
(NOT mtdblock2, or you'll get a kernel panic)
ip04>setenv
autostart yes
ip04>setenv nandboot 'nboot 0x2000000 0x0'
ip04>setenv
bootcmd run nandboot
ip04>save
ip04>reset
- Reboot the Atcom, wait for the unit to download a zillion things and
reboot, and check that it boots up OK:
root:~> uname -a
Linux
IP0x 2.6.22.18-ADI-2008R1astfin-svn #2 Wed Jun 9 03:00:41 EDT 2010 blackfin
unknown
root:~> cat /etc/issue
BlackfinOne BF532 v2 uClinux
(http://blackfin.uclinux.org/projects/bf1/)
root:~> cat /etc/version
Rowetel/IP04
Version 3.2.0 -- Wed Jun 9 03:02:13 EDT 2010
root:~> cat
/etc/firmwareversion
voiptel_ce_IP01-0.3.7
- If you want to have a DHCP server send an IP configuration to the Atcom
(and use a local NTP server pool):
>
vi /etc/network.conf
DHCPD=yes
NTPserver=0.fr.pool.ntp.org
>
reboot
> ping www.google.com
- Aim your browser at eg. http://192.168.0.9/,
and logon as admin / atcom
- If you'd rather connect to the appliance through SSH, use the serial
connection to set a new root password, and then aim your SSH client to the
appliance
Q&A
How to add SSHd, vim, Lighttpd + Lua + SQLite?, CRON?
How to upgrade from VoIPTel CE to own compiled Switchfin or Blackfin uClinux?
How to add alias ll=ls -al?
AstFin2
The image will include uClinux and whatever options you chose:
- cd /usr/src
- svn co https://astfin.svn.sourceforge.net/svnroot/astfin/software/astfin/astfin2/trunk/
astfin2
- cd astfin2
- make menuconfig
- make
- make image
- To update the Atcom appliance, choose one of the two images available
in /usr/src/astinf2/build_xx:
- uImage-md5 to update through the web GUI. Use this image if you
are already running an AstFin2 firmware
- uImage.ext2 to update from u-boot and an RS232 connection. If you
are currently using a BAPS image, use this image to upgrade
Blackfin uClinux-dist
As of June 2010, and unlike Astfin/Switchfin, the uClinux-dist available
directly from the Blackfin subdomain of uClinux (blackfin.uclinux.org)
doesn't support the Atcom IP01, so the only reason to work with that version
is to rip software that hasn't made it to to the Astfin/Switchfin tree. There are plenty
of information in the Blackfin
uClinux wiki.
Here's how to add support for the Atcom IP01 and compile uClinux-dist:
- Download and install the toolchain:
- cd /
- wget -c http://blackfin.uclinux.org/gf/download/frsrelease/501/8378/blackfin-toolchain-2010R1-RC4.i386.tar.bz2
- tar xjvf blackfin-toolchain-2010R1-RC4.i386.tar.bz2
- Add toolchain to PATH:
export PATH=$PATH:/opt/uClinux/bfin-linux-uclibc/bin:/opt/uClinux/bfin-uclinux/bin
echo
$PATH
which bfin-linux-uclibc-gcc
Note: To make this persistent
in Linux Mint, edit /etc/environment
- Download and install the uclibc library:
- cd /
- wget -c http://blackfin.uclinux.org/gf/download/frsrelease/501/8386/blackfin-toolchain-uclibc-full-2010R1-RC4.i386.tar.bz2
- tar xjvf blackfin-toolchain-uclibc-full-2010R1-RC4.i386.tar.bz2
- Download and install the uClinux-dist distribution:
- cd /usr/src
- wget -c http://blackfin.uclinux.org/gf/download/frsrelease/509/8660/blackfin-linux-dist-2010R1-RC5.tar.bz2
- tar xjvf blackfin-linux-dist-2010R1-RC5.tar.bz2
- mv blackfin-linux-dist uClinux-dist-2010R1-RC5
- cd /usr/src/uClinux-dist-2010R1-RC5
- Compare /usr/src/baps/patch/vendors/Rowetel/IP04-2008/*
with /usr/src/uClinux-dist-2010R1-RC5/vendors/AnalogDevices
- mkdir -p vendors/Rowetel/IP04
- cp /usr/src/baps/patch/vendors/Rowetel/IP04-2008/* vendors/Rowetel/IP04
- vi init.sh
#!/bin/bash
#to avoid being prompted a bazillion times when running "make
menuconfig"
#the first time
cp vendors/Rowetel/IP04/config.device .config
chmod u+x config/setconfig
yes "" | config/setconfig defaults
config/setconfig final
- make menuconfig
- make
Compiling applications for Blackfin + uClinux
Tips
Converting an application so that it'll run OK on an MMU-less CPU like the
Blackfin may require making changes to its source code (fixed point DTMF, absence
of fork(), dynamic memory allocation causing memory fragmentation, etc.)
Toolchains from 2010R1 and above will no longer link applications that use
fork() instead of vfork() and display the following error message: "undefined
reference to `_fork'". This is due to its use of AC_FUNC_FORK in configure.ac.
If an application you are trying to compile does handle fork/vfork, ????
More information: Porting
Applications to uClinux and We
have no Fork.
If an application does compile and start, what other issues,
if any, are to expected besides memory fragmentation and can't be solved by
running a watchdog application to reboot the system every night?
In case some applications don't behave and cause memory fragmentation, a
work-around solution until the application has been debugged is to use the procwatch application to keep an eye on them,
and also run nightly CRON job to reboot the device.
The toolchain contains two sets of binaries: One to compile source to FLAT
format, and the other, to FDPIC ELF. If you are running a lot of applications
with shared libraries, FDPIC ELF is a better choice since all the read-only
sections get shared among all the applications; If you are running only a few
applications, choose FLAT since only the functions they actually call will be
compiled into the applications.
If a FLAT binary dies with either SEGV or BUS error, try to increase the
size of its stack and give it another try:
- bfin-uclinux-flthdr -s 0x20000 myapp
If the error goes away, you can recompile the FLAT binary with a bigger stack,
using this option: bfin-uclinux-gcc -Wl,-elf2flt="-s 0x20000" application.c
To have the stack
checked at runtime, you can compile a FLAT binary with either of those options:
- -mstack-check-l1
- -fstack-limit-symbol=_stack_start
The Blackfin toolchain comes in three variations, two of which are used to
compile software for the uClinux OS and one to run without any OS:
- bfin-uclinux (eg. blackfin-toolchain-09r1.1-2.i386.tar.bz2): Those tools
are used to create FLAT files to run under Linux
- bfin-linux-uclibc (eg. blackfin-toolchain-uclibc-default-09r1.1-2.i386.tar.bz2):
Used to create FDPIC ELF files to run under Linux
- bfin-elf: To create ELF files that run on bare metal, ie. without any
underlying OS (so we'll just ignore this toolchain from here)
"The uClinux FLAT executable format, though it doesn't directly affect
applications and their operations, does allow quite a few options that the usual
ELF executables under Linux do not. FLAT format executables come in two basic
flavors, fully relocated and a variation of position-independent code (PIC).
The fully relocated version has relocations for its code and data, while the
PIC version generally needs only a few relocations for its data." (source)
"Program loaders which support Position Independent Code (PIC) have
been added and a new binary object code format named FLAT, which supports PIC,
was created. Other program loaders, such as that for ELF, have been modified
to support other formats which, instead of using PIC, use absolute references.
It is then the responsibility of the kernel to fix-up these references during
run time. Both methods have advantages and disadvantages. Traditionally PIC
is quick and compact but has a size restriction on some architectures. The runtime
fix-up technique removes this size restriction, but incurs overhead when the
program is loaded by the kernel." (source)
Bottom line: To compile stand-alone applications, ie. with all their libraries
compiled statically into the executable, use FLAT; If the application relies
on shared libraries, use ELF.
The toolchains install by default in /opt. Each of those groups contain the
following tools:
- The GCC compiler (eg. bfin-uclinux\bin\bfin-uclinux-gcc)
- The AS assembler
- Thd LD linker
- The AR to turn an ELF file into an archive, ie. static library
To compile C file as FLAT file: bfin-uclinux-gcc -Wl,-elf2flt
hello.c -o hello
To compile C file as FDPIC: bfin-linux-uclibc-gcc hello.c -o hello
You cannot mix FLAT and FDPIC ELF: Either both the library and the executable
are compiled as FLAT, or they are both compiled as FDPIC ELF.
If you get an error such as "cc1: error: unrecognized command line option
"-mcpu=bf518-0.0"", make sure you are using the latest toolchain
+ uClibc from Blackfin.
You can use this utility to remove debugging information from FDPIC ELF binaries:
- bfin-linux-uclibc-strip
hello
Also, before testing a new application, make sure another, different version
isn't already installed in any directory listed in PATH...
As for variables in Makefiles:
- Plain variables are local: If you need to access them from a second,
chained Makefile, you must pass them as parameters. Here's an example:
#myapp.mk
MYVAR=test
all:
cd
myapp; $(MAKE) $(MYVAR)
#./myapp/Makefile
all:
@echo
$(MYVAR)
# make -f myapp.mk
- Alternatively, you can export a plain variable and access it from a
second Makefile since it's now an environment variable (only while "make"
is running). Here's an example:
#myapp.mk
export MYVAR=test
cd
myapp; $(MAKE)
#./myapp/Makefile
@echo $(MYVAR)
# make
-f myapp.mk
- When using "cd" and "make", they must be on the
same line:
cd /tmp && make
Applications that rely on AutoTools instead of a static, plain Makefile provide
a configure.ac file where you can check which options are available for "--enable/with"
and "--disable/without".
Common variables to use in Makefile:
- WARN:= -Wall -Wmissing-prototypes -Wmissing-declarations -ansi -pedantic
- CFLAGS:= -O2 $(WARN)
-
- #Compiling files as FDPIC ELF instead of FLAT
- export PATH:=$(PATH):/opt/uClinux/bfin-linux-uclibc/bin
- export TARGET_CROSS:=bfin-linux-uclibc-
- export CC:=$(TARGET_CROSS)gcc
- export STRIP:=$(TARGET_CROSS)strip
- export AR:=$(TARGET_CROSS)ar rcu
- export RANLIB:=$(TARGET_CROSS)ranlib
Here's a way to call Autotools' configure:
./configure --build=i686-pc-linux-gnu --host=bfin-linux-uclibc CC=/opt/uClinux/bfin-linux-uclibc/bin/bfin-linux-uclibc-gcc
CFLAGS="-O2 -Wall -pedantic -I/usr/src/uClinux-dist/linux-2.6.x/include
-I/usr/src/uClinux-dist/staging/usr/include" AR="/opt/uClinux/bfin-linux-uclibc/bin/bfin-linux-uclibc-ar"
RANLIB="/opt/uClinux/bfin-linux-uclibc/bin/bfin-linux-uclibc-ranlib"
Choose either "-std=c99" or "-ansi", but not both. Some
programs won't compile when using the "-ansi" switch, so try removing
it and recompiling.
Use build/host/targer thusly:
- ./configure --build=i686-pc-linux --host=i686-pc-linux
--target=bfin-linux-uclibc
Note: --target is only needed when building the toolchain. You don't need
this if you use the compiled toolchain from uClinux.
In case AutoTool doesn't include checking support for malloc, you can force
the malloc configure thusly:
- Configure the shell to export this variable:
export ac_cv_func_malloc_0_nonnull=yes
- Write a configuration file, and export its location:
export CONFIG_SITE=$PATH_TO_FILE/config.site
For
reference, you can check uClinux-dist's vendors/config/bfin/config.site
- Pass the variable to configure:
./configure ac_cv_func_malloc_0_nonnull=yes
Using AutoConf's configure, it's possible to know which settings to enable/disable
by checking the configure script and the Makefile it creates.
If libtool can't find libraries the application needs for compiling, you
might have to modify ltmain.sh.
When compiling an application, if some libraries aren't available in the
uClinux-dist used by your firmware, it might be available in other versions
of uClinux-dist.
More information:
Packaging applications with ipkg (BAPS)
Infos
- Download uClinux-dist and check under user/ if the application
has already been ported to uClinux. If that's the case, try to extract its
Makefile and compile it manually before attempting to convert it to an ipkg
package
Note that BAPS uses the 2007 version of uClinux-dist, and
an application that is part of a more recent release of uClinux-dist might
not compile with that 2007 version of the toolchain. OTOH, the Blackfin
uClinux-dist doesn't know anything about the Atcom. YMMV.
- If not part of uClinux-dist, check the application's website to see
if the application could be compiled to run on an MMU-less CPU like the
Blackfin. If there's no indication, give it a shot anyway to see if it compiles,
and test it extensively to see if it seems to run OK without leaking memory
- Check existing *.mk files as reference
- Check the application's home website for information on compiling/installing
- If you get run-time issues, download the latest toolchain, and use its
"ldd" to check which shared libraries the application needs, if
any, and make sure those libraries are available on the Atcom
- Use "#!/bin/sh -x" to debug post/pre inst scripts
- In case ipkg complains about MD5 mismatch: rm /usr/lib/ipkg/lists/snapshots
You can check what a Makefile does using "-d" (for "details"),
-n" (dry-run), and both switches can be combined: Pretty useful to figure
out how the whole thing works.
As of Jan 2011, information about ipkg
is no longer available from the official source (www.handhelds.org/moin/moin.cgi/Ipkg),
but you can learn more from its more recent variant opkg
and by reading how it's used to build packages for the OpenWrt platform.
"An Opkg package is essentially a Debian package with fewer control
fields. If you know how to make a Debian package, you should be well on your
way. In general, a package is an ar archive containing a control tarball (text
+ script), a data tarball (binaries), and a debian-binary file (which simply
contains the string 2.0)" (source)
More information:
opkg-utils
is no longer maintained
Compiling an application into an ipkg package
A Hello, world sample can be found at www.rowetel.com/blog/?page_id=456.
It can then be compiled thusly:
- Compile binary and create package
make -f hello.mk hello-package
- Output can be found in tmp/hello/ and the ipkg package under /usr/src/baps/ipkg/
Here's an example of a .mk file to build a BAPS package for the Lua language:
- #make -f lua.mk
-
- #======== Common to all applications
- include rules.mk
-
- export CC = $(TARGET_CROSS)gcc
- export CFLAGS = -DLUA_USE_LINUX -I$(UCLINUX_DIST)
-I/usr/src/uClinux-dist/staging/usr/include
#Must first compile those
libraries
- export LDFLAGS = -Wl,-E -L$(STAGING_DIR)/usr/lib -lm -ldl -lreadline
-lhistory -lncurses
-
- #======== Application-specific stuff
- LUA_VERSION=5.0.2
- LUA_DIRNAME=lua
- LUA_DIR=$(UCLINUX_DIST)/user/$(LUA_DIRNAME)
-
- TARGET_DIR=$(BUILD_DIR)/tmp/lua/ipkg/lua
- PKG_NAME:=lua
- PKG_VERSION:=$(LUA_VERSION)
- PKG_RELEASE:=1
- PKG_BUILD_DIR:=$(BUILD_DIR)/tmp/lua
-
- #======== Compile application
- all: lua
-
- lua:
- make -C $(LUA_DIR)
-
- mkdir -p $(TARGET_DIR)/bin
- cp $(LUA_DIR)/lua $(TARGET_DIR)/bin/lua
- touch $(PKG_BUILD_DIR)/.built
-
- #======== Build ipkg package
- define Package/$(PKG_NAME)
- SECTION:=lang
- CATEGORY:=Languages
- TITLE:=Lua 5.0.2 interpreter
- DESCRIPTION:=\
- Just the interpreter.
- endef
-
- # post installation
- $(eval $(call BuildPackage,$(PKG_NAME)))
-
- lua-package: lua $(PACKAGE_DIR)/$(PKG_NAME)_$(VERSION)_$(PKGARCH).ipk
Creating and using a repository
Server
We'll assume the build host also runs the web server that will provide users
with packages:
- cd /usr/src/baps/ipkg
- ../scripts/ipkg-make-index.sh . > Packages
- Copy Packages at the root of the web server's document directory
Atcom
- Edit /etc/ipkg.conf: src snapshots http://server
- ipkg update
- ipkg list
Using opkg instead of ipkg
Development of ipkg was abandonned around 2008, but opkg, used in the OpenWrt
world, is alive and well and is compatible with ipkg.
To keep the application as small as possible, I decided to compile opkg-cl
without Curl and OpenSSL. But in case you need to...
Compiling Libcurl
"Opkg by default tries to link against libcurl. If you don't have libcurl,
or disable it at configure time, then you will need wget installed."
- Download the latest Libcurl source code
- CC=bfin-linux-uclibc-gcc ./configure --build=i686-pc-linux-gnu --host=bfin-linux-uclibc
- make
- If you compile opgk-cl with shared libraries, on the Atcom, copy the
library to /lib
Compiling OpenSSL
Note: libcrypto.so.0.9.8 is 1.317.955 bytes and libssl.so.0.9.8 is 258.818,
for a total of 1.576.773 bytes
OpenSSL is part of uClinux-dist, so the includes/libs should be available
and you should only need to point opkg to those directories for a successful
build:
- /usr/src/uClinux-dist-2010R1-RC5# cp staging/usr/lib/libssl.so.0.9.8
/var/www/
- /usr/src/uClinux-dist-2010R1-RC5# cp ./staging/usr/lib/libcrypto.so.0.9.8
/var/www/
- On the Atcom, copy the libraries to /lib
Compiling opkg
Here's how to build opkg-cl without Curl, OpenSSL, and GPG:
- svn checkout http://opkg.googlecode.com/svn/trunk/ /usr/src/opkg
- To avoid having to use an environment
variable, vi libbb/gz_open.c
/* gz_use_vfork = (getenv("OPKG_USE_VFORK")
!= NULL);*/
gz_use_vfork = 1;
If using the 2010 toolchain, which
can't be told to handle the above with a warning instead of an error....
edit gz_open.c thusly:
#define UCLINUX 1
...
/* gz_use_vfork
= (getenv("OPKG_USE_VFORK") != NULL);*/
gz_use_vfork = 1;
...
#ifdef
UCLINUX
//if (gz_use_vfork) {
*pid
= vfork();
#else
//} else {
*pid
= fork();
//}
#endif
- Add the toolchain to the PATH
- apt-get install glib-gettextize libglib2.0-dev libcurl4-openssl-dev
libgpgme11-dev
- ./autogen.sh
- CC=bfin-linux-uclibc-gcc CFLAGS="-I/usr/src/uClinux-dist-2010R1-RC5/linux-2.6.x/include"
LDFLAGS="-static" ./configure --disable-gpg --disable-openssl
--disable-curl ac_cv_func_malloc_0_nonnull=yes --build=i686-pc-linux
--host=bfin-linux-uclibc
- make
- Copy ./src/opkg-cl to the web server, and download + chmod this file from
the Atcom
- Make sure PATH is filled with the usual suspects, eg. /bin:/usr/bin:/sbin:/usr/sbin,
or you might get "pkg_run_script: package "xyz"
postinst script returned status 255" when installing a package
- mkdir -p /usr/lib/opkg
- mkdir /etc/opkg
- vi /etc/opkg/snapshots.conf
src
snapshots http://rowetel.com/ucasterisk/ipkg
dest root /
- ./opkg-cl update
- ./opkg-cl list
No command to list files in uninstalled package?
Packaging an application with opkg
Note: The Section field is completely ignored by opkg. You can put whatever
you want here. The Architecture field is free form, it can be whatever you want,
but it must match one of the arch fields specified in your conf files.
Manually
- mkdir /usr/src/mypackage ; cd mypackage
- mkdir bin ; cd bin ; vi hello.c ; bfin-linux-uclibc-gcc hello.c -o hello
- cd /usr/src/mypackage
- vi debian-binary
2.0
- vi control
Package: opkg-hello (must match
package name, ie. package.opk?)
Version: 0.0.1
Description:
Sample OPKG package
Section: cyanogenmod/applications
Priority: optional
Maintainer:
Jiang Yio
Architecture: all
Homepage: http://inportb.com/
NO!
Note: Do not leave fields empty : "Malformed
package file package.opk"
- vi preinst
#!/bin/sh
echo "The name of this script is
\"$0\"."
- chmod +x preinst
- cp preinst postinst
- cp preinst prerm
- cp preinst postrm
- tar czvf control.tar.gz control preinst postinst prerm
- tar czvfP data.tar.gz ./bin/hello
- ar -r package.opk debian-binary control.tar.gz
data.tar.gz
- cp package.opk /var/www
- On Atcom, download and run:
/var/tmp> wget http://server/package.opk
/var/tmp>
./opkg-cl install package.opk
With opkg-utils
http://svn.openmoko.org/trunk/src/host/opkg-utils/
Requires Python
With OpenWrt's Makefile
To read
Creating a repository
http://wiki.openmoko.org/wiki/Om_2008_Guide#How_to_add_a_Repository_.3F
http://wiki.openwrt.org/doc/devel/feeds
Resources
Changing options for Busybox in BAPS
- Run "make -f uClinux.mk uClinux" once so it downloads the
uClinux-dist source
- cd uClinux-dist
- make clean
- cd uClinux-dist/user/busybox/
- make menuconfig, and choose options
- cd /usr/src/baps
- make -f uClinux.mk uClinux
- Reboot the Atcom with this new image, and check that it works OK
Compiling iptables
As iptables relies on settings in the kernel, you'll need to recompile the
kernel to enable Netfilters.
In addition, some features (eg. the "recent" Netfilter module)
were added in later versions, so you might need to use a more recent release
than the 2007 version of the kernel used in the BAPS firmware.
More information here.
Adding OpenVPN to BAPS uClinux
OpenVPN is a more reliable way than STUN to let remote SIP clients connect to an Asterisk server
through locked-down NAT routers.
A patch
is required to modify the uClinux-dist source code to include OpenVPN before
rebuilding an image; We must also build OpenVPN 2.0.9 package to provide the
/bin/openvpn binary that will talk to the /dev/net/tun virtual interface.
Note: Since OpenVPN requires patching the kernel and compiling/installing
a package, and a VPN burns CPU cycles which would be better left to Asterisk,
you might want to simply locate the VPN on your router instead.
Here's how to apply
the patch, build/test a new image, compile and test the OpenVPN package, and
finally burn the new image in the Atcom:
- cd /usr/src/baps
- wget http://www.rowetel.com/ucasterisk/downloads/openvpn_package.patch
- patch -p0 < openvpn_package.patch
- make -f uClinux.mk uClinux
- cp uClinux-dist/images/uImage /tftpboot/uImage
- On the workstation, start a TFTP server so the Atcom can download this
new image
- On the Atcom, use a serial cable, reboot the appliance to get into the
Uboot loader, and download and run the new image:
ip04>set autostart
ip04>set
bootargs ethaddr=your:mac:address root=/dev/mtdblock0 rw
ip04>save
ip04>tftp
0x1000000 uImage
ip04>bootm
- Check that this new image contains a character device in /dev/net/tun,
write its live root filesystem to NAND (copy_rootfs.sh), and reboot
with "root=/dev/mtdblock2 rw"
- On the workstation, build the OpenVPN package:
make -f libssl.mk
libssl
make -f libssl.mk libssl-package
make -f openvpn.mk openvpn-package
cp
ipkg/libssl_0.9.8d-1_bfin.ipk /var/www
cp ipkg/openvpn_2.0.9-1_bfin.ipk
/var/www/
- From the Atcom, download and install this new package:
cd /var/tmp
wget
-c http://workstation/libssl_0.9.8d-1_bfin.ipk
wget -c http://workstation/openvpn_2.0.9-1_bfin.ipk
ipkg
install libssl_0.9.8d-1_bfin.ipk
ipkg
install openvpn_2.0.9-1_bfin.ipk
The package only includes a single binary /bin/openvpn, which can use configuration
files but is unable to create a Certification Authority (CA) certificate and
its key, and pairs of public/private keys for the server and clients. Those
are needed to use OpenVPN with a Public Key Infrastructure (PKI).
Therefore,
the next steps must be performed on the workstation before copying the files
on the Atcom and the clients:
- On the workstation:
apt-get install openvpn
mkdir /etc/openvpn/easy-rsa
cp
-R /usr/share/doc/openvpn/examples/easy-rsa/2.0/* /etc/openvpn/easy-rsa
- cd /etc/openvpn/easy-rsa
- Create the certificates and keys:
#Make necessary changes
vi
vars
. ./vars
./clean-all
./build-ca
./build-dh
#Use
unique Common names
./build-key-server server
./build-key client1
- Copy certificates + keys to www so server and client can fetch them:
cd
/etc/openvpn/easy-rsa/keys
cp ca.crt dh1024.pem server.crt server.key
client1.crt client1.key /var/www
#So web server can send files
chmod
644 /var/www/server.key
chmod 644 /var/www/client1.key
- Create a configuration file for the server:
vi /var/www/server.ovpn
port
1194
proto udp
dev tun
ca ca.crt
cert server.crt
key
server.key
dh dh1024.pem
server 10.8.0.0 255.255.255.0
ifconfig-pool-persist
ipp.txt
keepalive 10 120
#Uncomment if compiled with compression
#comp-lzo
persist-key
persist-tun
status
openvpn-status.log
verb 3
- Create a configuration file for the client:
vi /var/www/client1.ovpn
dev
tun
proto udp
remote <public IP to reach OpenVPN/Asterisk server>
1194
resolv-retry infinite
nobind
persist-key
persist-tun
ca
ca.crt
cert client1.crt
key client1.key
#comp-lzo
verb 3
- On Atcom, download files and launch server:
Asterisk> cd /etc/openvpn
Asterisk>
wget http://workstation/ca.crt
Asterisk> wget http://workstation/dh1024.pem
Asterisk>
wget http://workstation/server.crt
Asterisk> wget http://workstation/server.key
Asterisk>
chmod 600 server.key
Asterisk> wget http://workstation/server.ovpn
#Let's
test
Asterisk> /bin/openvpn /etc/openvpn/server.ovpn
- On Windows host, install the Windows
OpenVPN package, which includes a GUI, download the required files,
and try to connect to OpenVPN server:
cd c:\program files\openvpn\config
wget
http://workstation/ca.crt
wget http://workstation/client1.crt
wget
http://workstation/client1.key
wget http://workstation/client.ovpn
Start
OpenVPN Service
Start OpenVPN GUI with Admin rights: Right-click on OpenVPN
GUI icon > Connect
ping 10.8.0.1
- If ping OK, configure SIP client to connect to Asterisk through the
server's private IP used by the OpenVPN tunnel, eg. 10.8.0.1, and make a
call
- Edit Asterisk's sip.conf to add a "localnet" for the VPN:
externip=<public
IP>
#local extensions
localnet=192.168.0.0/255.255.255.0
#remote
extensions, through VPN
localnet=10.8.0.0/255.255.255.0
- On Atcom, create /etc/init.d/openvpn script to start app at boot-time:
#!/bin/sh
#
Start up file for OpenVPN
case $1 in
#--daemon
not implemented
start)
openvpn --cd /etc/openvpn --config server.conf&;;
stop)
killall openvpn;;
enable)
rm -f /etc/rc.d/S60openvpn;
ln
-s /etc/init.d/openvpn /etc/rc.d/S60openvpn;;
disable)
rm -f /etc/rc.d/S60openvpn;;
*)
cat <<EOF;;
Syntax: /etc/init.d/openvpn [command]
Available
commands:
start Start
the service
stop Stop
the service
enable Enable
service autostart
disable
Disable service autostart
EOF
esac
Remember to "chmod
755 openvpn"
- Add symlink in /etc/rc.d/: /etc/init.d/openvpn enable
Note that I couldn't get SJPhone and Qutecom to work with the VPN: Either
one-way audio or couldn't even register. Ekiga could register, but couldn't
dial an extension. Try XLite/EyeBeam or Zoiper instead.
More information: Switching
to a software PBX and Setting
up a client
Adding items to Switchfin menuconfig
- To add a new package to the Switchin Buildroot, start by creating a
directory for the application under /package/, eg. myapp/
- This directory must include two files: Config.in which describes the
option when you run "make menuconfig", and myapp.mk which contains
the Makefile that will be run to download, configure, build, and install
the application
If a package lacks a Config.in file, it will not be
shown as an option when running "make menuconfig" and will always
be compiled and included in the image.
- Next, edit /package/Config.in and add this new application.
- Finally, write myapp/myapp.mk. The contents is different depending on
if the package is generic or based on Autotools.
- The actual source code of the application is located in build_ip01/uClinux-dist/user/
if it is part of the uClinux-dist, or in package/sources/myapp/ if you provide
the application yourself.
You can tell an application uses a generic Makefile or an Autotools-based
Makefile, based on whether it has a "configure" scripts, in which
case it's Autotools.
Read:
Checking shared libraries
With ldd or readelf
The Blackfin toolchain already has a binary that you can run on the workstation
to check which shared libraries an application depends on, if any:
- bfin-linux-uclibc-ldd
- bfin-linux-uclibc-readelf
- bfin-uclinux-readelf
On the workstation, you can run this:
find ./romfs/bin -type f -print0 | xargs -0 bfin-linux-uclibc-ldd
I failed compile ldd.c for Blackfin (either from the generic uClinux-dist
distribution or from source files found through Google), but compiling Binutils
went far enough to get a working readelf:
- cd /usr/src/uClinux-dist-2010R1-RC5/binutils-2.21
- CC=bfin-linux-uclibc-gcc ./configure --build=i686-pc-linux-gnu --host=bfin-linux-uclibc
- make
- cp binutils/readelf /var/www/
- find / -xdev -type f -print0 | xargs -0 ./readelf -d
With scanelf
uClinux provides neither ldd nor readelf, but scanelf from the pax-utils
application compiles OK:
- wget -c http://distfiles.gentoo.org/distfiles/pax-utils-0.2.2.tar.bz2
- tar xjvf pax-utils-0.2.2.tar.bz2
- cd pax-utils-0.2.2
- export PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/opt/uClinux/bfin-linux-uclibc/bin
- make CC=bfin-linux-uclibc-gcc
- Copy scanelf to web server
- Download scanelf on Blackfin appliance
- > ./scanelf -qn myapp
Here's a script to build a list of shared libraries, and check all the binaries
recursively to find if any library is unused:
Building a smaller image
- Start by checking romfs/bin for applications you don't need.
- Next, run the script above to check that you don't uselessly pack shared
libraries in /lib that aren't used by any application.
- Strip binaries (any drawback?)
"Hello, word" for uClinux
Here's how to install the toolchain, and compile some test files as either
FLAT or FDPIC ELF binaries, manually and through a Makefile.
Setting up tools
- From the Blackfin
uClinux site, download the two versions of the toolchain (to compile
binaries as FLAT or FDPIC ELF):
cd /
wget -c http://blackfin.uclinux.org/gf/download/frsrelease/501/8378/blackfin-toolchain-2010R1-RC4.i386.tar.bz2
wget
-c http://blackfin.uclinux.org/gf/download/frsrelease/501/8386/blackfin-toolchain-uclibc-full-2010R1-RC4.i386.tar.bz2
- Untar the two packages, and edit the PATH env't variable:
tar
xjvf blackfin-toolchain-2010R1-RC4.i386.tar.bz2
tar xjvf blackfin-toolchain-uclibc-full-2010R1-RC4.i386.tar.bz2
vi
/etc/profile
export PATH=$PATH:/opt/uClinux/bfin-uclinux/bin:/opt/uClinux/bfin-linux-uclibc/bin
source
/etc/profile
echo $PATH
which bfin-uclinux-gcc
which bfin-linux-uclibc-gcc
- mkdir /usr/src/uclinux.test/
- cd /usr/src/uclinux-test/
Compiling an application
Based on Simple
Hello World Application Example
- vi main.c:
#include <stdio.h>
int main(int argc, char **argv)
{
printf("Hello World\n");
return 0;
}
Save
and exit
- To compile main.c as a FLAT executable:
bfin-uclinux-gcc -Wl,-elf2flt
main.c
-o main
file main: "BFLT executable -
version 4 ram"
- To compile main.c as an FDPIC ELF executable:
bfin-linux-uclibc-gcc
-Wall main.c -o main
bfin-linux-uclibc-strip main
file main: "ELF
32-bit LSB executable, Analog Devices Blackfin, version 1 (SYSV), dynamically
linked (uses shared libs), stripped"
Note: To compile source code into an object file instead of an executable,
use the "-c" switch: bfin-uclinux-gcc -Wall -c main.c -o main.o
Compiling a library
First, here's the source code for the library:
- #bar.h
- void mytestfunc(void);
-
- #bar.c
- #include <stdio.h>
-
- void mytestfunc(void) {
- printf("In mytestfunc\n");
- }
Next, here's how to modify main.c to include a call to the library:
- #include <stdio.h>
- #include "bar.h"
-
- int main(int argc, char **argv)
- {
- //mytestfunc() located
in libbar.a, ie. bar.c
- mytestfunc();
- return 0;
- }
FLAT static
First, let's compile the library:
- bfin-uclinux-gcc -Wall -c bar.c -o bar.o
- bfin-uclinux-ar rcu libbar.a bar.o
- bfin-uclinux-ranlib libbar.a
Next, let's recompile main.c to include libbar.a statically:
- bfin-uclinux-gcc main.c -o main -L. -lbar -Wl,-elf2flt
FLAT (shared) NOT RECOMMENDED
FDPIC ELF (static)
- bfin-linux-uclibc-gcc -c bar.c -o bar.o
- bfin-linux-uclibc-ar rcu libbar.a bar.o
-
- bfin-linux-uclibc-gcc main.c -o main -L. -lbar
- bfin-linux-uclibc-strip main
FDPIC ELF (shared)
- bfin-linux-uclibc-gcc -c bar.c -o bar.o
- bfin-linux-uclibc-gcc -shared -Wl,-soname,libbar.so -o libbar.so bar.o
-
- bfin-linux-uclibc-gcc main.c -o main -L. -lbar
- bfin-linux-uclibc-strip main
- bfin-linux-uclibc-strip libbar.so
On the target host, a shared library must be installed in locations where
the system expects to find it, eg. /lib. How to check which
locations uClinux looks for shared libraries?
Compiling libraries and executables through a Makefile
If the application uses "configure", you might need to use "CROSS_COMPILE=bfin-uclinux-
./configure" and/or "CC=bfin-uclinux-gcc ./configure".
FLAT static
- CROSS = bfin-uclinux-
- AR = $(CROSS)ar
- CC = $(CROSS)gcc
- RANLIB = $(CROSS)ranlib
-
- CFLAGS += -Wall
- LDFLAGS_test = $(LDFLAGS) -Wl,-elf2flt
- LDLIBS_test = $(LDLIBS) -L. -lbar
-
- LIBS = libbar.a
- BINS = test
-
- all: $(LIBS) $(BINS)
-
- libbar.a: bar.o api.o
- $(AR) rcu $@ $^
- $(RANLIB) $@
-
- test: test.o
- $(CC) $(CFLAGS) -o $@
$^ $(LDLIBS_$@) $(LDFLAGS_$@)
FLAT (shared) NOT RECOMMENDED
FDPIC ELF (static)
- CROSS = bfin-linux-uclibc-
- AR = $(CROSS)ar
- CC = $(CROSS)gcc
- RANLIB = $(CROSS)ranlib
-
- CFLAGS += -Wall
- LDLIBS_test = $(LDLIBS) -L. -lbar
-
- LIBS = libbar.a
- BINS = test
-
- all: $(LIBS) $(BINS)
-
- libbar.a: bar.o api.o
- $(AR) rcu $@ $^
- $(RANLIB) $@
-
- test: test.o
- $(CC) $(CFLAGS) -o $@
$^ $(LDLIBS_$@) $(LDFLAGS_$@)
FDPIC ELF (shared)
- CROSS = bfin-linux-uclibc-
- CC = $(CROSS)gcc
-
- CFLAGS +=
-Wall
- LDFLAGS_libbar.so = -shared -Wl,-soname,libbar.so
- LDLIBS_test = $(LDLIBS) -L.
-lbar
-
- LIBS = libbar.so
- BINS = test
-
- all: $(LIBS) $(BINS)
-
- libbar.so: bar.o api.o
- $(CC) $(CFLAGS) -o $@
$^ $(LDLIBS_$@) $(LDFLAGS_$@)
-
- test: test.o
- $(CC) $(CFLAGS) -o $@
$^ $(LDLIBS_$@) $(LDFLAGS_$@)
Compiling the Lua interpreter
Note: If you rarely use the Lua interpreter in interactive mode, you can
save space by not including libreadline: Just edit LUA_USE_LINUX in luaconf.h.
First, update the PATH env't variable to where the toolchain is located.
Next, edit /usr/src/lua-5.1.4/src thusly:
- CC=bfin-linux-uclibc-gcc
- LD=bfin-linux-uclibc-ld
- AR= bfin-linux-uclibc-ar rcu
- RANLIB= bfin-linux-uclibc-ranlib
- RM=rm -f
-
- BASE=/usr/src/baps
- STAGING_DIR=$(BASE)/uClinux-dist/staging
- UCLINUX_LIB=$(BASE)/uClinux-dist/lib
- UCLINUX_ROOT_LIB=$(BASE)/uClinux-dist/root/lib
-
- CFLAGS=-O2 -Wall -DLUA_USE_LINUX -I$(BASE)/uClinux-dist/linux-2.6.x/include
-I$(STAGING_DIR)/usr/include
-
- LIBS= -lm -ldl
- LDFLAGS=-Wl,-E -L$(STAGING_DIR)/usr/lib -L$(UCLINUX_LIB) -L$(UCLINUX_ROOT_LIB)
$(LIBS)
-
- ...
-
- uclinux:
- $(MAKE) all
Compiling SQLite3
autoconf version
./configure --build=i686-pc-linux --host=bfin-linux-uclibc target=bfin-linux-uclibc
CC=bfin-linux-uclibc-gcc AR=bfin-linux-uclibc-ar RANLIB=bfin-linux-uclibc-ranlib
CFLAGS="-O2 -Wall -I/usr/src/baps/uClinux-dist/linux-2.6.x/include"
LFLAGS=-L/usr/src/baps/uClinux-dist/lib
make
The command-line client sqlite3, the shared library libsqlite3.so and the
static library libsqlite3.a will be found in ./.libs/
amalgamated version
Unzip the SQLite source file, and create the following Makefile:
- BASE=/opt/toolchain
- CC=bfin-linux-uclibc-gcc
- AR=bfin-linux-uclibc-ar rcu
- RANLIB=bfin-linux-uclibc-ranlib
-
- CFLAGS=-O2 -Wall -DSQLITE_THREADSAFE=0 -I.
- -I$(BASE)/uClinux-dist/linux-2.6.x/include
- LDFLAGS=-Wl,-E -L$(BASE)/uClinux-dist/root/lib -L.
-
- all:
- @echo "No target
specified."
-
- object:
- $(CC) $(CFLAGS) -c sqlite3.c
-o sqlite.o
-
- static:
- $(CC) $(CFLAGS) -c sqlite3.c
-o sqlite3.o
- $(AR) libsqlite3.a sqlite3.o
- $(RANLIB) libsqlite3.a
-
- shared:
- $(CC) $(CFLAGS) $(LDFLAGS)
-shared -Wl,-soname,libsqlite3.so
- -o libsqlite3.so sqlite3.c
-
- cli: static
- $(CC) -static $(CFLAGS)
$(LDFLAGS) -o sqlite3 shell.c
- -lsqlite3 -ldl
-
- clean:
- -rm -rf *\.a *\.o *\.so
sqlite3
Compiling LuaSQL for SQLite3
LuaSQL requires either the SQLite3 static library (libsqlite3.a) or just
the object file (sqlite.o), and will generate sqlite3.so which contains both
SQLite3 and some glue to access SQLite3 from Lua:
/usr/src/luasql-2.1.1/config
- /usr/src/luasql-2.1.1/config
-
- LUA_INC= /usr/src/lua-5.1.4
-
- LIB_OPTION = -shared -Wl,-soname,$(LIBNAME)
-
- DRIVER_INCS = -I/usr/src/sqlite-autoconf-3070601
- #DRIVER_LIBS= -L/usr/src/sqlite-autoconf-3070601/.libs -lsqlite3
- DRIVER_LIBS= /usr/src/sqlite-autoconf-3070601/sqlite3.o
-
- CFLAGS= -O2 -Wall
#assumes exported in PATH
CC=bfin-linux-uclibc-gcc
/usr/src/luasql-2.1.1/Makefile
- ...
- AR= bfin-linux-uclibc-ar rcu
RANLIB= bfin-linux-uclibc-ranlib
src/$(LIBNAME): $(OBJS)
- $(CC) $(CFLAGS) $(LIB_OPTION)
-o $@ $(OBJS) $(DRIVER_LIBS)
Compiling LuaSocket
Compiling lsof
lsof is not part of BAPS and Switchfin, but is available in uClinux-dist
in the "Miscellaneous Applications" section.
However, it won't compile with the 2010R1-RC4 toolchain due to its use of
fork(). Incidently, "netstat -natp" will display the name of the program
that opened the port.
Compiling applications with MPU
While the Blackfin has no MMU, it offers a Memory Protection Unit (MPU) so
that an application won't access RAM that doesn't belong to it.
https://docs.blackfin.uclinux.org/doku.php?id=uclinux-dist:difference_from_linux
https://docs.blackfin.uclinux.org/doku.php?id=bfin:mpu
http://elinux.org/UClinux_Shared_Library
Compiling Samba
Samba 3.0.25a is part of uClinux-dist, and here's how to compile a more recent
release:
To check the version: smbd -V
To check where smbd expects to find smb.conf:
smbd -b | grep CONFIGFILE
Compiling Busybox
Some options you might want to enable:
- Busybox Settings > Build Options > Force NOMMU build
- Busybox Library Tuning > Command line editing + Tab completion +
Fancy shell prompts
- Shells > Hush + options, including Process substitution
By default, uClinux-dist uses simpleinit (in Core Applications), instead
of the one provided by Busybox. You might want to use Busybox's init so that
you use its poweroff/halt/reboot which unmount partitions before rebooting.
Busybox uses a different format for /etc/inittab. Here's
an example:
- # /etc/inittab
- #
- # Copyright (C) 2001 Erik Andersen <andersen@codepoet.org>
- #
- # Note: BusyBox init doesn't support runlevels. The runlevels
field is
- # completely ignored by BusyBox init. If you want runlevels, use
- # sysvinit.
- #
- # Format for each entry: <id>:<runlevels>:<action>:<process>
- #
- # id == tty to run on, or
empty for /dev/console
- # runlevels == ignored
- # action == one of sysinit, respawn, askfirst, wait,
and once
- # process == program to run
-
- # Startup the system
- console::sysinit:/bin/sh /etc/rc
-
- # Set up a console shell
- #Using "console" prevents use of job control, eg. CTRL+c
- #console::respawn:/bin/login -f root
- #Check which tty is in your kernel command line
- ttyBF0::respawn:/bin/login -f root
-
- # Misc services
- null::respawn:/sbin/inetd -f
- null::respawn:/sbin/watchdog -F -T 20 -t 10 /dev/watchdog
-
- # Logging junk
- null::sysinit:/bin/touch /var/log/messages
- null::respawn:/sbin/syslogd -n -m 0
- null::respawn:/sbin/klogd -n
-
- # Stuff to do for the 3-finger salute
- ::ctrlaltdel:/sbin/reboot
-
- # Stuff to do before rebooting
- null::shutdown:/bin/killall klogd
- null::shutdown:/bin/killall syslogd
- null::shutdown:/bin/umount -a -r
Information
Choose a file format for
shared libraries: Shared FLAT, FDPIC ELF. Read how to create
libraries.
Resources
Q&A
What is difference between host, build, and target?
http://gcc.gnu.org/onlinedocs/gccint/Configure-Terms.html
--build=i686-linux-gnu --host=blackfin-unknown-linux-gnu
How to remove unneeded Asterisk modules?
There's no sure-fire way to check which modules Asterisk need. Here's how
to investigate:
- Configure Asterisk to log messages
- Start Asterisk with enough -d and -v, and watch for error messages
- vi /etc/asterisk/modules.conf
autoload=no
(load modules
you think you need)
- Repeat until Asterisk stops complaining about missing modules.
What files do I need for a minimal Asterisk?
Use "readelf -d" to check which shared libraries a binary needs.
If you'd rather run readelf on the Atcom rather than on the workstation,
This is what you need when using SIP and Dahdi:
- Shared libraries in /lib:
- libdl.so.0
- libdl.so.2
- libpthread.so.0
- libncurses.so.5
- libm.so.0
- libresolv.so.0
- libgcc_s.so.1
- libc.so.0
- Shared libraries in /usr/lib:
- libsqlite3.so.0
- libtiff.so.3
- libspeexdsp.so.1
- libtonezone.so.2.0
- libspandsp.so.2
- /bin/asterisk
- Configuration files in /etc/asterisk/
- asterisk.conf
- logger.conf
- modules.conf
- sip.conf
- extensions.conf
- voicemail.conf
- Startup script: /etc/init.d/asterisk
- Modules in /usr/lib/asterisk/modules/
- AGI scripts go in /var/lib/asterisk/agi-bin/
- Sound files in /var/lib/asterisk/sounds/
- Voice-mail in /var/spool/asterisk/
- DAHDI
Read this:
www.wains.be/index.php/2008/04/15/slimming-asterisk-for-the-nslu2-under-debian/
To locate dependency errors, edit logger.conf full => notice,warning,error,debug,verbose
How to monitor the connection to a VoIP provider for quality?
FreeSwitch can be used for this. Does Asterisk offer this feature?
Busybox's ping doesn't stop with CTRL+c
Make sure /etc/inittab uses the "tty" mentionned in the kernel command
line instead of "console". More information
here.
How to restart an application that crashed?
/bin/watchdog
How to check network performance?
Compile and install iperf on a workstation and the Atcom to stress-test the
network part.
Simple TCP test
On the server: iperf -s
On the client: iperf -c server.ip -t 30 -i 1
Simple UDP test
On the server: iperf -s -u
On the client: iperf -c server.ip -u -b 4m -t 30 -i 1
Multiple UDP threads
On the client: iperf -c server.ip -u -b 4m -t 30 -i 1 -P 4
Bigger MTU
On the client: iperf -c server.ip -w 128k -t 30 -i 1 -P4
Finding biggest MTU supported by network
On the server: iperf -s -m
On the client: iperf -c server.ip
On the server, check the line that says "MSS size XXXX bytes"
Checking VoIP performance
Datagrams are 32-byte long and the MTU buffer is 128k:
On the server: iperf -s -u -l 32 -w 128k
On the client: iperf -c server.ip -u -b 1m -l 32 -w 128k -i 1
Upload, and then download data
On the client: iperf -c server.ip -t 30 -i 1 -r
Upload and download data simultaneously
On the client: iperf -c server.ip -t 30 -i 1 -d
Why two versions of the toolchain?
Eg. bfin-uclinux-readelf vs. bfin-linux-uclibc-readelf?
Try compiling FLAT + FDPIC ELF hello, world, and try apps on them to see
Which version of uClibc does uClinux-dist include?
$ printf '#include \n__UCLIBC_MAJOR__ __UCLIBC_MINOR__ __UCLIBC_SUBLEVEL__\n'
| bfin-uclinux-gcc -E - | tail -1
DHCP client crashes at reboot -> Busybox's udhcpc
Patching dm9000.c didn't help, so I dumped the default DHCP client and used
udhcpc provided by Busybox.
Here's the init.d script to be called at boot time:
- OPTIONS="-R -a -S -T 3 -A 1 -t 3"
- INT="-i eth0"
- PID="-p /var/run/udhcpc.eth0.pid"
- SCRIPT="-s /etc/simple.script"
-
- case $1 in
- start) rm -f /var/run/udhcpc.eth0.pid;
- udhcpc
$OPTIONS $INT $PID $SCRIPT;;
/etc/simple.script can be found here.
To ask udhcpc to renew its lease run "killall -USR1 udhcpc ; tail
/var/log/messages".
How to check Switchfin patches
- cd /usr/src
- svn co https://switchfin.svn.sourceforge.net/svnroot/switchfin/switchfin/trunk/
switchfin
- cd switchfin
- find ./package/ -name "*\.patch"
Does Uboot know about the NAND partitions?
No, it's up to you to provide correct offset/length to match the partition
settings in the NAND driver compiled in the kernel.
Generally speaking, what patches are required to run Linux apps on uClinux?
- svn co http://server/somedistro
somedistro
- grep .patch package/* -rs | grep -v .svn
How to find what shared libraries are needed?
On the workstation
find ./romfs/bin/ -executable -type f -print0 | xargs -0 bfin-linux-uclibc-readelf
-d | egrep "File|library"
On the Atcom
Note: Make sure Busybox supports "-xdev"
find /bin -xdev -type f -perm +111 -print0 | xargs -0 ./readelf -d
How to find unused libraries?
for n in romfs/lib/*.* romfs/usr/lib/*.*; do du -sh $n; nn=`basename $n`;
find romfs/ -type f -print0 | xargs -0 grep -l $nn | grep -v $n | grep -v ld.so.cache
| wc -l; done
Alternatively, run "make menuconfig", and in the "uClinux
Distribution Configuration > Blackfin build options" menu, enable "Cull
unused ELF shared libraries", ie. CONFIG_INSTALL_ELF_TRIM_LIBS.
When installing new applications that use shared libraries, you'll have to
check that they are available in /lib or /usr/lib.
What are the different files in ./images/ or build_ipXX/image_ipXX?
- vmlinux: Uncompressed kernel in ELF format. Uboot won't load it ("Bad
Magic Number")
- vmImage: Compressed kernel in ELF format to be loaded with Uboot
- rootfs.*: Root filesystem in different formats (ext2, initramfs, ubifs)
- uImage.*: vmImage + rootfs.*, eg. uImage.ext2 = vmImage + rootfs.ext2
If you just want to upgrade the kernel in the NAND, use vmImage.
Images are compiled through Mfg/Board/Makefile, which calls vendors/AnalogDevices/vendor.mak.
More information in uClinux-dist
Compiled Images
"init: exec rc failed"
Things to try/check:
- romfs/bin: Is there a symlink sh->(the shell)?
- Try either the BusyBox init or the stand-alone Core Applications init
- If you get "Bad inittab entry at line 11", check ./user/inetd/Makefile:
The Busybox init seems unable to process the simple inittab format used
by the stand-alone init "ttyline:termcap-entry:getty-command".
Try "inetd::sysinit:/sbin/inetd". Also, the stand-alon e
init will process /etc/rc first and then execute the lines found in /etc/inittab
- "can't execute '/etc/rc.d/S10network': Permission denied":
chmod 755 /etc/init.d/network
Kernel stuck at "Starting Kernel at = "
Make sure you compiled uClinux for the ADSP-BF532
CPU.
The Hush shell lacks some features
If some features are missing when running the Hush shell (no path completion
through TAB, no command history through the up arrow, etc.), check the Busybox
> Busybox Settings > Busybox Library Tuning section in "make config_menuconfig".
How to monitor applications?
I think there is a standard Unix application that can monitor
if another application is running. It might even be in uClinux-dist. Can't
recall it's name......
Is RAM fred when an application ends?
Not all RAM is freed immediately after an application ends, as VFS file buffers,
network buffers, kernel data structures, etc. can linger in RAM for a while.
Worse, some kernel threads, kernel modules, and service daemons won't exit
and free memory allocated until you force a reboot.
So it's a good idea to 1) run a watchdog to check for memory leaks, and 2)
schedule a nightly reboot to make sure unused memory is returned to the kernel.
How to check SVN version of downloaded source?
svnversion
BAPS ignores my settings
When compiling a new kernel with BAPS and uClinux.mk, it can happen that
the script rewrite configuration files and ignore your settings such as when
compiling Netfilter/iptables in the kernel image.
Looks like it's done by copying patch/vendors/Rowetel/IP04/config.linux-2.6.x
into uClinux-dist/vendors
A solution is to compile uClinux once the usual way (make -f uClinux.mk uClinux),
and modify uClinux.mk to add your own, simpler target:
- mytarget:
- $(MAKE) -C $(UCLINUX_DIR)
ROMFSDIR=$(TARGET_DIR)
- ./src/zeropad uClinux-dist/images/uImage
uClinux-dist/images/uImage_r2.ip08 0x20000
-
- uClinux: $(UCLINUX_DIR)/.unpacked ./src/zeropad
- $(TARGET_DIR)/usr/doc/uImage.txt
- mkdir -p $(UCLINUX_DIR)/vendors/Rowetel/IP04/
- cp -af patch/vendors/*
$(UCLINUX_DIR)/vendors
- $(MAKE) -C $(UCLINUX_DIR)
Rowetel/IP04_config
- $(MAKE) -C $(UCLINUX_DIR)
ROMFSDIR=$(TARGET_DIR)
- ./src/zeropad uClinux-dist/images/uImage
uClinux-dist/images/uImage_r2.ip08 0x20000
FXO is acting funny
If you make a lot of use of FXO/Zaptel during tests, it might act funny after
a while, either displaying error messages (eg. "chan_zap.c:6406 ss_thread:
Got event 18 (Ring Begin)..." instead of handling the call), or not making/answering
calls at all.
In this case, just reboot the Atcom and see if this solves the problem.
How to convert sound files from WAV to Ulaw?
Two easy solutions:
On the workstation, use "sox". If you need to convert a whole directory:
for i in *.wav; do sox $i -r 8000 -c 1 $(basename $i .wav).gsm resample -ql;
done
On the Atcom, enter the Asterisk CLI and use this command:
ip04*CLI> file convert /var/tmp/myfile.wav /var/tmp/myfile.ulaw
Zaptel sometimes goes berzerk
After making a bunch of test calls, Zaptel stops reporting an incoming call:
- root:~> /etc/init.d/asterisk stop
- root:~> /etc/init.d/zaptel stop
- rmmod: wcfxs: Resource temporarily unavailable
- rmmod: bfsi: Resource temporarily unavailable
- rmmod: zaptel: Resource temporarily unavailable
- rmmod: oslec: Resource temporarily unavailable
Must wait a little while before being able to stop/start Zaptel and Asterisk.
[modules.conf] .c instead of .so
Samples on the Net use the .so extension, while the default modules.conf
in the Atcom uses .c, using "noload" with a .c extension doesn't work,
and renaming all items from .c to .so causes Asterisk to start... and die. You'll
have to try each line separately until you know which module can be safely renamed
from .c to .so.
Call files aren't handled by Asterisk
This is due to a bug in Yaffs2 not updating the timestamp on parent directories.
Upgrade uClinux and see if the bug is gone.
If you can't upgrade, edit /etc/asterisk/asterisk.conf so that the spool
directory is located in /var/tmp, and edit /etc/init.d/asterisk so that the
start) part contains this:
- if [ ! -d /var/tmp/asterisk/outgoing ]
- then
- mkdir -p /var/tmp/asterisk/outgoing
- fi
[BAPS] Why two Ethernet devices?
root:~> ifconfig
eth0 Link encap:Ethernet HWaddr 00:09:45:56:72:9B
inet addr:192.168.0.9
Bcast:192.168.0.255 Mask:255.255.255.0
UP BROADCAST
NOTRAILERS RUNNING MULTICAST MTU:1500 Metric:1
RX packets:10
errors:0 dropped:0 overruns:0 frame:0
TX packets:11
errors:0 dropped:0 overruns:0 carrier:0
collisions:0
txqueuelen:1000
Interrupt:48
eth0:9 Link encap:Ethernet HWaddr 00:09:45:56:72:9B
inet addr:192.168.100.30
Bcast:192.168.100.255 Mask:255.255.255.0
UP BROADCAST
NOTRAILERS RUNNING MULTICAST MTU:1500 Metric:1
Interrupt:48
Why use "asterisk -f &"?
-f : Foreground. Starts Asterisk but does not fork as a background daemon.
What are local files?
Asterisk only handles callfile when restarted
Moving a callfile
to Asterisk's outgoing/ directory while Asterisk is already running doesn't
trigger a call: A call will only occur if Asterisk is stopped, the file moved,
and Asterisk restarted. uClinux has inotify enabled. No idea as to the cause
of this problem.
Alternative ways to have Asterisk auto-dial out:
Fails compiling the Asterisk 1.4.4 package
"The existing menuselect.makeopts file did not specify that 'app_flash'
should not be included. However, either some dependencies for this module
were not found or a conflict exists."
- cd asterisk-1.4.4/ ; rm menuselect.makeopts
- cd ..; make -f asterisk.mk asterisk-package
Fails compiling the Asterisk 1.4.20 package
This .mk file actually downloads Asterisk 1.4.21.2
- cd asterisk-1.4.21.2/ ; rm menuselect.makeopts
- vi
pbx/ael/ael_lex.c
- cd ..; make -f asterisk-1.4.20.mk asterisk-package
How to stress-test Asterisk?
What is the recommended way to stop Asterisk?
Instead of "kill", try "asterisk -rx "stop now".
How to enable Asterisk message logging
It might not be enabled by default, so you won't see any Asterisk-related
messages in /var/log/messages.
Provided you have a syslogd server running:
- vi /etc/asterisk/logger.con
syslog.local0 => notice,warning,error
- Connect to Asterisk with "asterisk -vvvvvvvvvr"
- Tell Asterisk to reload its configuration with "logger reload"
- Exit console, and check "tail -f /var/log/messages"
How to restart crashed/rogue applications?
What solution is available to restart an application that crashed, or is
causing memory fragmentation and must be restarted so uClinux can reorganize
RAM?
How to disable LD_DEBUG?
env -u LD_DEBUG didn't work. Had to reboot
What modules do I really need?
By default, Asterisk loads all the modules located in /usr/lib/asterisk/modules/,
unless told otherwise in modules.conf.
The problem is that there doesn't seem to be away to be positive a module
is required or not for your Asterisk server to work OK, but here are modules
you can problably avoid loading without a problem:
Using Asterisk' mini web server
By default, Asterisk supports a basic web server. Its configuration is located
in /etc/asterisk/http.conf, and its docroot is /var/lib/asterisk/static-http/.
Note that documents can be reached through http://srv/static/.
Making sense of MTD
The Atcom uses the MTD
device file to access the NAND flash memory.
Check the dmesg for a bit of information about MTD partitions:
- Creating 1 MTD partitions on "RAM":
- 0x00000000-0x00300000 : "ROMfs"
- uclinux[mtd]: set ROMfs:EXT2 to be root filesystem
-
- Generic platform RAM MTD, (c) 2004 Simtec Electronics
- NAND device: Manufacturer ID: 0xec, Chip ID: 0xda (Samsung NAND 256MiB
3,3V 8-bit)
- Scanning device for bad blocks
- Creating 2 MTD partitions on "NAND 256MiB 3,3V 8-bit":
- 0x00000000-0x00800000 : "linux kernel"
- 0x00800000-0x10000000 : "file system"
In addition to two partitions in the NAND to contain a kernel and a persistent
root filesystem, respectively, the kernel creates another MTD object in RAM
to hold the RAM-based root filesystem attached to the kernel:
> cat /proc/mtd
dev: size erasesize name
mtd0: 00300000 00001000 "ROMfs"
mtd1: 00800000 00020000 "linux kernel"
mtd2: 0f800000 00020000 "file system"
"ROMfs" contains the RAM-based root filesystem that you can use
to boot a new Atcom appliance before writing this root filesystem onto the /dev/mtdblock2
partition in the NAND.
How to access NAND from uClinux?
If the MTD commands are included, you'll need to either build an ipkg package
or recompile a root filesystem or image to include the MTD applications.
What are entrypoints in "mount"?
When running mount, some of the entry points refer to kernel data structures,
not physical devices.
What is /etc/index.html?
Alias ll='ls -al'?
How to check the hardware?
root:~> cat /proc/cpuinfo
root:~> cat /proc/meminfo
How to save space?
Replace FTPd + TelnetD with SSHd?
Remove DHCPd?
Remove Inetd?
Remove IPTables?
Remove rsh and rshd?
Remove rcp?
Remove unneeded Asterisk modules?
HTTPd?
root:~> ls -al home/httpd/
drwxr-xr-x 1 500 500 2048
Mar 9 2008 .
drwxr-xr-x 1 500 500 2048
Mar 9 2008 ..
drwxr-xr-x 1 500 500 2048
Mar 9 2008 cgi-bin
What is OpenIPPbx?
Wiki by Atcom: www.openippbx.com
What is SwitchVoice?
"It was sometime in spring 2006 when a small Bulgarian group (now part
of SwitchVoice Ltd.) started the BlackFin One project. It was a flexible general
purpose Blackfin BF532 based development board. Both the schematics and PCB
layout was open to the public which made the project pretty popular that time.
The platform was ideal for SMB VOIP applications and it was first David Rowe
(Rowetel) who saw its potential. David had already developed the 4FX (FXS/FXO
interface card) and it was only a matter of months before we get complete analog
BPX (IP04) ready. At that time we all were working as perfect team. We got great
contribution from Mark who pointed the team to “build root” way of maintaining
of the software (Astfin). Since then all of our Blackfn based products are Astfin
driven and we are the major Astfin 2.1 contributor.
One year after we started the BlackFin One project, part of the Bulgarian
team joined with Mark created a company uCpbx Ltd.
The team under uCpbx Ltd. entity has developed family of Analog and Digital
(PRI &BRI ) VoIP Appliances based on Blackin and Freescale PowerQUICC CPUs.
Many external telecom. projects have been successfully designed as well.
During second half of 2009 the core development team decided to take a course
for spin-out and this way avoid the management redundancy uCpbx Ltd. has created
among the years.
The result is SwitchVoice Ltd.
!"
Resources
Tools
Books and Tutorial
Sites
- IP04 Four Port
IP-PBX (bunch of information to get started from IP0x author David Rowe)
- EdgePBX
("Edgepbx is dedicated to provide Open Source Computer Telephony
hardware and software product.")
- Blackfin Linux Docs
- "uCdot is the place for all
things uClinux and Embedded Linux"
- "Cooperative Linux (short-named
coLinux) is a port of the Linux kernel that allows it to run cooperatively
alongside another operating system on a single machine"
- "uClinux is a set of patches
for linux to allow it to run on systems without an MMU
(memory management unit)."
- Getting started
with uClinux
- uCLinux on Blackfin processors
(Forum
for Asterisk on Blackfin)
- "uClibc (aka µClibc/pronounced
yew-see-lib-see) is a C library for developing embedded Linux systems. It
is much smaller than the GNU C Library, but nearly all applications supported
by glibc also work perfectly with uClibc. Porting applications from glibc
to uClibc typically involves just recompiling the source code. " (What
is the difference between uC-libc and uClibc)
- "Buildroot is a set
of Makefiles and patches that makes it easy to generate a complete embedded
Linux system. Buildroot can generate any or all of a cross-compilation toolchain,
a root filesystem, a kernel image and a bootloader image. Buildroot is useful
mainly for people working with small or embedded systems, using various
CPU architectures (x86, ARM, MIPS, PowerPC, etc.) : it automates the building
process of your embedded system and eases the cross-compilation process."
- OpenWrt
Buildroot and Creating
Packages
- "Switchfin
is an Open Source uClinux/Asterisk based distribution running on top of
Blackfin CPUs. [...] Switchfin is an branch of Astfin (astfin.org) telephony
uClinux/Asterisk based distribution. [...] At the beginning of 2010 me and
few colleagues I was working with, had become one of the major contributors
for Astfin 2.1 project. The project father Mark however has shared with
us that he wants Astfin to migrate a bit out of telephony area which is
not exactly what we see its future. We want to work on a purely telephony
oriented project and that's why we have created Switchfin." Switchfin
comes from the SwitchVoice people.
- "Astfin is a Blackfin
uClinux Asterisk distribution. The authors have used Buildroot to make the
very complex embedded build process very simple."
- VoIPTel (offers a GUI for the IPx series)
- (French) Ajouter
un package dans Buildroot en 5 minutes
- Busybox manpage
with options for each applet