The Computer Corner Take II (#23) by Bill Kibler

To see more Computer Corner articles look here: CCII page or check out the Home Page .

BeagleBone - the hardware report

Some Hardware information

There are two ways that developers view hardware - the first group, which is pretty much what the CCII 21 article covers, are the people who open the BeagleBone package, put in the supplied SD Rom, hook up the USB cord, and start playing with the software. However, even those people become the second group, who checkout what the chip can do and how to tweak anything and everything. This article is for those of the second group and contains some words of advice for even the first group who don't normally think about hardware.

The BeagleBone is a mature product composed of the latest inovations in arm devices and embedded design concepts. The market has been heading towards more features in smaller sizes and with greater horsepower to get jobs done with less than the finest software. By that I mean, assembly language skills not needed, any programmer should be able to make something work to their needs. Now I might disagree with those concepts since I am considered a senior programer and have been around long enough to know that some skill is really needed to create great programs. Unfortunately the industry doesn't care anymore and thus throwing more power at it to cover bad design seems to be the name of the game. This system is one of those where it should have enough horsepower to cover all your sins.

Whether you are using the BeagleBone as an embedded system, or just a small server, there are some things that you might like to know. The simple ones are, it is a ARM version 7 cpu based on the CortexA8 design. It has a hardware vector floating point co-processor built in that is designed to help do graphics. The chip is 3.3V and as such none of the I/O pins can take 5V, although I understand some have survived after having 5V applied to pins - your luck may be different however. The floating point supports the IEEE754 standard. The cpu chip is from TI and is an AM3359ZCZ and has a NEON Media Co-Processor. Most of the supporting software is supplied by TI and comes in "psp" support packages. The TI manual on the chip is over 4200 pages of data. A quick note that gcc 4.5 or greater is needed to compile armhf code, as previous compiler versions do not provide the correct code for hardware floating point operations.

Like all modern embedded processors, most of the I/O pins serve multiple purposes and thus any specific embedded work will require changes to the registers controlling the I/O pins you may be interested in. The exact values and how to apply them will be in the manual for the chip and generally not covered by me - except as it relates to using serial I/O and already setup drivers in the kernel. Since my interests are in the workstation/server area, my focus is more on what the kernel can provide without any special processes. The projects I work on all use serial ports for pushing and collecting data and as such we have found the USB converters to be more problematic than useful. We are using the BeagleBone due to it's 4 free serial ports and builtin networking support.

A few simple facts

The board that I bought is a rev A5 version. This appears to be the latest shipping design with a few minor fixes from the A4 version. Version A6 of the design should be in the pipeline by fall 2012, again with only minor changes. The cpu is setup to have two processor speeds, depending on whether it is powered from external 5V or off of the USB connection. While on the 5V source, you should have enough power to run simple USB devices, however there are limits (about 250ma), so it is best to use USB hubs with their own power for anything other than a simple flash drive. I have used my unit on both 5V and USB power and noticed it can get a bit warm. At first I though it might be speed related, but it still gets hot, just not as hot, from the USB power.

A quick note about the design and it's cousins. There are several other versions of TI AM33?? based boards available - about 5 or 6 I think. The kernel software and some of the tools support the whole class of chips, not just the BeagleBone. The main problem I have seen relates to the AM335XEVM or the chip set evaluation board and modules. This EVM setup has several daughter boards that provide serial support, LCD screen, and I/O interfaces. It appears that the kernel and some OS system builders are using the EVM for their testing and development work. This has caused minor issues and some failures to be seen that normally BONE only testing would find. So keep in mind to check closely that what your doing is correct for the BONE and the AM3359ZCZ device. Note that the AM3359ZCE has a different pinout and pin function tables with some different features.

As I said earlier, there are 4 usable serial ports out of 6 possible. UART3 was connected in previous boards, but is no longer available on the headers. UART0 is connected to an FTDI USB serial interface and will appear on your system as /dev/ttyUSB1, not "0". Please note that using your terminal program to talk to /dev/ttyUSB0 will most likely just cause it to reboot when keystrokes are entered. This is one place that not reading the documentation or paying close attention to what they mean will get you into trouble. The /dev/ttyUSB0 is a direct USB port into the chip and is intended for software USB functions - all features I doubt I will use as I normally work over ssh connections. It really is just a software JTAG interface.

The BeagleBone has an ethernet connection (RJ45) and network support that works when enabled by the standard linux network tools. One item that is missing in many small systems is a USB "host" port. You use USB client when your workstation is talking to the target, but you then use USB host ports when the target is talking to other USB devices such as hard drives or data collection systems. Many of my previous boards turned out to be useless for me, when the documented USB port turned out to be a client only setup. The BeagleBone USB port and connector is an internal HUB and as such will support many devices. Speaking of devices or functions, the cpu has lots to chose from, but not all brought to pins on the board. The rev A5 dropped the UART3 pins for GPIO1-15 and 16. So that means we have 4 UARTs available, two I2C sets, one SPI port, 4 timers, 2 PWM ports, 7 analog pins, and 35 GPIO pins. However, keep in mind that software support for these features in the kernel is optional and at present 33 of those pins are not what is listed in the SRM with the current angstrom release.

That above list of functions came from looking at the two headers that are on the sides of the board. The idea is that you plug in a "cape" or "shield" board that has your own components that do the talking to external devices. In our case we will be needing to build a 4 port serial interface cape. There is an available serial cape - one port - that will be shipping at the end of August 2012 - mine is back ordered. This cape currently only supports one of the 4 possible uarts - a driver only limit. I ordered a beagleboard prototype board with my inital order and find it mostly useless. Other than power and ground, nothing is brought out from the headers to the prototype area. This means you need to put pins in the headers and jumper wires from there to the prototype area. Doing that prevents you from putting another cape on the board. We will most likely be wanting to have a 4 port serial cape, and plugged on top of it will be our I/O interfaces.

All is not lost however, as "adafruit" has a "proto cape" (#572) for $9.95 and two headers (#706) for $4.95 that do pull out the header pins to the proto area. In a later article I will provide the design and results of using their cape to create a 4 port serial cape. You can see their site and the proto board here. As with other systems just coming to market, the number of support products is currently low, however expect that to change very quickly as everyone starts whipping out cape designs overnight. I will try and update this or other articles as new designs I like become available.

It is important to note that the SRM covers the capes in detail, as to how they are intended to work. The idea for capes is something like this - four max, each cape has eeprom that contains data to tell system that it is hooked up, OS when seeing cape "X" will alter registers to provide needed functionality. Capes that need power will get it from off board, as system power is very limited. The entire system can be powered from capes as well. The kernel code supporting the serial cape has a message that it only supports a single uart and you must jumper accordingly.

The problem I see with the cape setup is the need for eeprom and that it will control how the registers are setup. I believe you will be able to build your own capes, but the setting up of the registers will be the problem. Put your own cape on, tweak the registers to work, add new cape, your cape stops working as the new one un-did your tweaks. Will need to dig deeper into this issue as we go on.

What the Kernel supports

In the above section, I listed what the schematic for the proto board showed as to connections and functions of those pins. To be a bit more correct, the headers are connected directly to cpu pins, without buffering. So the functions that those pins actually have depends on the settings done by one of the BIOSs. So remember from article #22, there are three BIOSs for the BB, internal flash setup code - flash BIOS as I call it, the MLO/u-boot.img or boot BIOS, and the kernel driver code or modules. Each of those steps can be setting registers in the cpu initially or alter them later if something changes. All of that is some what out of your control and in the hands of the kernel hackers.

The best place to get a look of what those pins can be defined as, is in the "BeagleBone_revA5_SRM.pdf" - the manual if you will for this system. I got mine from the CircuitCo Main Page where you will find the links at the bottom of the page. Please note that there will be rev A6 board soon and as such you should get the appropriate manual for your revision. What we need to look at is section 17.3 in my A5 manual, where we cover the expansion headers. Table 9 shows us that the name chosen for the pin is but one of many possible functions those pins can have. If you take the "proc" column and look at the AM3359 chip pin layout you will see that they match up. Most pins have more than one function and just because the header names are used, doesn't mean anything really but what a designer had in mind when they laid out the board. What we need are real facts, not some past idea.

The AM3359ZCZ device is a memory mapped chip, where the function registers are addressed as memory and you read that memory to see what your settings are. Since these settings are in higher memory and outside of Linux user space, either a special device driver or some kernel tools are needed to access them. For Linux there has been for some time, the debugfs filesystem. This "filesystem", which does not have any files, but is just a set of routines inside the kernel, can read and write kernel space. To have this tool requires that the kernel be compiled with the "DEBUGFS" configuration setting turned on - which angstrom's kernel has. Further more, it must be mounted and typically that mount point is "/sys/kernel/debug". "angstrom" mounts the debugfs by default, but if you are on a system where it is not mounted, and debug is compiled in, a simple "mount -t debugfs none /sys/kernel/debug" as root will mount it.

The debugfs is intended to be used by kernel developers to look into the kernel and make changes as they debug their work. For us, it is for now our only way to change register settings without modifying kernel code or writing our own driver. This non-filesystem however, is accessed much as any filesystem with a limited set of options. You can do finds, cat, and ls as you would expect. When doing a cat of a filename, you get a set of responses based on the function of that chips features. Some "cat" responses are of great detail, while others are a single value. You can "echo" values to the files as well, and if it supports writing data it will change the registers value. We will later do some writing to change the preset functions to what they are suppose to be. For now however we need to find out how close our settings are to those of the P8 and P9 tables in the SRM.

As I said, you can use regular file commands to see what is going on, and my first pass was to do a "find /sys/kernel/debug -type f | xargs -i -t cat {}". This will produce a very long output of every item in the debugfs structure. Some are values and a few return nothing or errors. You can see this output at the bottom of this page a5_pin_tbl.html. Since what we are really interested in is just the setting as they relate to P8 and P9, we can limit our search to "/sys/kernel/debug/omap_mux/", as it is TI's omap mux items we are interested in. This returns just the settings and informational data that is in the drivers inside the kernel. Keep in mind that the displayed MODE settings are for the AM33x registers, and not all informational data is correct for the AM3359ZCZ.

I took the data from the "find" output and combined it with the SRM's table 8 through table 13 to create the two tables in "a5_pin_tbl" page. From those pages you can see that all but 33 pin settings are currently being setup by the kernel as defined in the SRM. On that page are links and snapshots of a shell script that (hopefully) sets those 33 pins to the listed functions. I believe a combination of not tested, different EVM boards, and just time are why these values are not the default. I expect over time for this situation to change - but for now you can use my script to set them up as listed.

The Kernel Source

It might help to talk about the kernel source, even for those not likely to use it directly. There are several way to get the kernel source, often you can download a tar of the source as used by the distribution team, or clone a "git" repo from several sources. The main source is of course where you will find all platforms supported. However there is usually for embedded systems, some group, in this case TI, who is maintaining a "fork" or branch of the kernel tree that is testing changes for inclusion into the main kernel. My arch kernel is from the "linux-am33x" git repo, there is also a "linux-omap" repo, but the git log shows that the current work is happening on the am33x repo. To get a copy of this repo do:

> git clone git://
Use the command "git log" to see latest changes, or "git branch -a" to see a list of branches current in the repo. The tar files will give you the kernel source, but you loose the "log" data that can tell you of changes put in and taken out. I noticed the other day a fix to the network setup that got put in and pulled out as it didn't work. I think my kernel still has the bad code, and so I know it should be fixed in the next update.

I used this command the other day to see how many files had code specific to the "bone"

find arm -type f | xargs -i grep -H -i bone {}
arm/mach-omap2/board-am335xevm.c: * FIXME: Some BeagleBones reuire a ramp_delay to settle down the set
arm/mach-omap2/board-am335xevm.c: * The reason for extended ramp time requirement on BeagleBone is not
arm/mach-omap2/board-am335xevm.c:static struct tps65217_board beaglebone_tps65217_info = {
arm/mach-omap2/board-am335xevm.c:	case BEAGLE_BONE_A3:
arm/mach-omap2/board-am335xevm.c:	case BEAGLE_BONE_OLD:
arm/mach-omap2/board-am335xevm.c:		.platform_data  = &beaglebone_tps65217_info,
arm/mach-omap2/board-am335xevm.c:static int beaglebone_phy_fixup(struct phy_device *phydev)
arm/mach-omap2/board-am335xevm.c:/* Beaglebone < Rev A3 */
arm/mach-omap2/board-am335xevm.c:static struct evm_dev_cfg beaglebone_old_dev_cfg[] = {
arm/mach-omap2/board-am335xevm.c:/* Beaglebone Rev A3 and after */
arm/mach-omap2/board-am335xevm.c:static struct evm_dev_cfg beaglebone_dev_cfg[] = {
arm/mach-omap2/board-am335xevm.c:/* BeagleBone < Rev A3 */
arm/mach-omap2/board-am335xevm.c:static void setup_beaglebone_old(void)
arm/mach-omap2/board-am335xevm.c:	pr_info("The board is a AM335x Beaglebone < Rev A3.\n");
arm/mach-omap2/board-am335xevm.c:	/* Beagle Bone has Micro-SD slot which doesn't have Write Protect pin */
arm/mach-omap2/board-am335xevm.c:	_configure_device(BEAGLE_BONE_OLD, beaglebone_old_dev_cfg,
arm/mach-omap2/board-am335xevm.c:					beaglebone_phy_fixup);
arm/mach-omap2/board-am335xevm.c:/* BeagleBone after Rev A3 */
arm/mach-omap2/board-am335xevm.c:static void setup_beaglebone(void)
arm/mach-omap2/board-am335xevm.c:	pr_info("The board is a AM335x Beaglebone.\n");
arm/mach-omap2/board-am335xevm.c:	/* Beagle Bone has Micro-SD slot which doesn't have Write Protect pin */
arm/mach-omap2/board-am335xevm.c:	_configure_device(BEAGLE_BONE_A3, beaglebone_dev_cfg, PROFILE_NONE);
arm/mach-omap2/board-am335xevm.c:	if (!strncmp("A335BONE",, 8)) {
arm/mach-omap2/board-am335xevm.c:			setup_beaglebone_old();
arm/mach-omap2/board-am335xevm.c:			setup_beaglebone();
arm/mach-omap2/include/mach/board-am335xevm.h:#define BEAGLE_BONE_OLD		2
arm/mach-omap2/include/mach/board-am335xevm.h:#define BEAGLE_BONE_A3		3
arm/mach-pxa/capc7117.c:	mxm_8x10_barebones_init();
arm/mach-pxa/mxm8x10.c:void __init mxm_8x10_barebones_init(void)
arm/mach-pxa/icontrol.c:	mxm_8x10_barebones_init();
arm/mach-pxa/include/mach/mxm8x10.h:extern void mxm_8x10_barebones_init(void);
arm/mach-u300/clock.c: * is not modeled currently. Instead we have the backbone AMBA bus on
From that we can see the few files that have supporting code for the "bone". Note that the true bone files are in the arch/arm/mach-omap2 directory and only the file board-am335xevm.c and the include board-am335xevm.h file are found. I will leave further exploration up to you as hopefully we can rely on TI and their kernel team to fix any bugs that pop up. It might help to watch my ccii_21 article, as it contains links to the current TI PSP releases and will be updated if any major changes happen related to the BeagleBone.

There is a lot of information in the kernel source tree and for the arm devices, you need to look in the "arch/arm" directory for the intilization source code. Don't forget that setup is done in the u-boot code, where the git repo u-boot-am33x can be cloned so you can see what it does. Try: "git clone git://".

Some Serial Testing

Now that I have a script to set all the P8 and P9 functions correctly, it is time to see if we can use the uarts for serial communications. Previously, all my testing was for naught, as the pins were setup for everything but uarts, and I didn't know that at the time. This time I know several things, I have set the correct I/O usage and direction, which pins are for what devices, and that uart3 is no longer an option. By looking at the dmesg, it appears by default that all the uarts are seen and initialized, even if the pins are not.

I am doing all this testing on the Arch setup using the arch filesystem - so it is stock arch all the way. The advantage for this testing is the use of standard linux setup tools, where as I found angstrom using their stuff. The method will be similar, just the files to edit are not for angstrom. I have tested the script on both systems and it did initialize the uart pins correctly. I used in some cases "26" to turn on the RX pin as it seemed to be the value used by other article writters. I felt that "36" might be more correct, but both seemed to work for me - your milage might be different. The difference between "26" and "36" is simply wether it is a pullup or pulldown enabled pin. I show "26" as pulldown, but it didn't seem to matter. What did matter is baud rate.

Basically you can test if all works by doing one of two tests. If your project will be special programs, you will probably want to turn off the "inittab" "agetty" settings and talk directly to the port. To test that option use "minicom" or "screen" to talk both ways (PC Host and Bone), where you type on one system, see the results on the other, and then flip your typing directions. I did that and it worked. The other option I used with arch, was relying on the agetty deamon to see a connected terminal on the uart port and prompt me for a "linux" login. I got it to work once or twice, but had problems. I finally tried using "stty -F /dev/ttyO1" only to see baud set at 9600. I used "stty" to set it to "115200", only to run the command again and see that it had changed to "115200", and then on a second run, it was back to 9600. Keep in mind that the getty is suppose to be setting it to "115200" as well, so seeing the 9600 "always" doesn't agree with the settings or tools.

When I hooked up my 3.3v serial converters and talk at 115200, for the most part I got nothing. Sometimes, I was able to send data from the Bone, but I never saw anything from the PC host. Always a oneway stream. However when I saw the stty 9600 and changed the PC's baud rate to 9600 as well, I finally got all my serial ports coming up with linux logins. So my guess is that using minicom on the Bone, you can set the baud rate correctly, as long as the minicom is in control of the port. Once back to agetty controlling things, 9600 is what you get. Clearly I will need to figure why we can't control baud rate properly, but for now I know all my ports work, I haven't fried any RX pins with wrong voltages, and you can setup a serial port as the login port. It might help to note that on the arch, I took the mount debugfs and the echo lines from my posted script and put them in a /etc/rc.d/pinmux file, followed by adding "pinmux" to the rc.conf line for DEAMONS. You will note that ntp goes there as well, just after the "network" item. This is the extra tools you want started at init time, and my pins are now set up by default on bootup.

I expect to keep making changes to these articles and write another one on creating a 4 port serial cape with 3.3 to 12v serial interfaces. For now however, I think I have provided enough information to hopefully keep you from too much trouble as you work and play with the BeagleBone.


BeagleBone Capes support page
adafruit proto board
debian-administration - good site for help articles.

Kibler Electronics, PO Box 535, Lincoln, CA 95648-0535, USA.
Copyright © 2012, Kibler Electronics