This is an old version of this course, from Spring 2015. A newer version is available here.
This is an individual lab. You are expected to do all of this lab on your own. While you are free to discuss the lab with other students, you should not show your own solution to other students or look at theirs. This includes not only code, but also the diagrams and analysis. However, you are free to discuss your solution technique and even demonstrate it using examples different from the ones in this lab. Please allow other students the maximum opportunity to gain experience on this lab by working it themselves, and please work this lab yourself
Prelab
Read through the Lab Procedure. Do what you can without the check-out hardware. This includes downloading and installing several large files -- a good thing to do in the background while you work on something else.
Also to do before lab:
- Install and run the virtual machine
- Flash the new beaglebone image on the microSD card.
- Flash the the microSD card to the beaglebone.
- Run the beaglebone and ssh into it with the new image (perhaps even from the virtual machine -- this could be a challenge!).
Please demonstrate all your pre-lab accomplishments at the beginning of lab.
Introduction
In this lab, you will re-image your beaglebone, set up a virtual machine, and start some basic development with a cross-compiler system.
Virtual Machine setup
To develop for the Beaglebone, we will use a Debian virtual machine.1
The Linux distribution you are using will execute using the VirtualBox virtual machine software . You will need to download this and install the VirtualBox software on your laptop (latest version will work ). You will need to install the appropriate version of the software, which is 64 bit for the MSOE machines.
Make sure you check the "Reinitialize the MAC address of all network cards" checkbox as in the iamge below. If you didn't please contact me for how to fix your VM
When you have completed installing Virtual box, you will need to download and install the Linux virtual machine image from the instructor's website. (BIG download)
When asked where to install your disk image, choose a hard-drive with LOTS of space! For example, I replaced the default value of C:\Users\yoder\VirtualBox VMs\SE3910 Virtual Machine Student Baseline\SE3910 Virtual Machine Student Baseline-disk2_1.vmdk with D:\VirtualBox VMs\SE3910 Virtual Machine Student Baseline\SE3910 Virtual Machine Student Baseline-disk2_1.vmdk since I have much more space on my D drive than my C drive.
Before you use the system, configure your network settings to use a bridged network adapter. If you forget, or just try to start it anyway, you will likely get an error message like this
Then you can click "Change Network Settings" and it will take you to the right configuration page, as shown in the figure below. (Note: Your laptop may use a different name as you may have different network capabilities on your machine. Also, you'll want to come back here occassionally to switch between bridging to your wired and wireless connections.)
Once the Virtual machine is downloaded and setup, log onto the operating system. The default user is se3910, and the default password is se3910. Install the guest additions software on the virtual machine, and create a shared folder between the windows workstation and the virtual machine. This shared folder allows you to share data between the two operating systems as well as reliably back up you work from the virtual machine. You can use any location that you would like for the share point. Useful shares might be the entire d drive of your laptop, the Box.com folder if you use Box.com to automatically back up and synchronize your data, or a subfolder of your personal SE3910 folder (Dr. Yoder: I prefer the latter for my own work).
Creating your bootable flash image
Either after or before installing the virtual machine, you will need to make a bootable flash image for the Beaglebone Black. To do this, you will need at least one 8GB (or 4GB?) microSD card. This card will be used to reprogram the memory on your Beaglebone to boot the latest and greatest version of the operating system. In the event that your Beaglebone operating system becomes disabled, THIS MICRO SD CARD CAN ALSO BE USED TO RESTORE YOUR Beaglebone to a bootable state.
The first step involves downloading the Win32DiskImager software. This software will allow you to burn an SD card from windows with a binary image. This is a simple program that can be executed without full installation on your machine.
To burn the image, first insert the SD Card into a MicroSD card adapter or a USB to micro SD card reader. Pay extreme attention to where the drive is mounted. IT IS HIGHLY RECCOMENDED THAT YOU REMOVE ANY AND ALL EXTRA STORAGE MEDIA FROM YOUR MACHINE. Start up the Win32Disk Imager software and select the image file that you want to burn as well as the destination drive. When you are ready, press write and the disk image will be written. Writing the image will take about 5 minutes. (Note: Before burning the image, you will need to extract the xz file using 7zip or another extraction program.)
Updating the image on your Beaglebone
Once writing the image has completed, you will have a burned image of the operating system on the SD card. With the power to the beaglebone turned off, insert the microsd card into the sdcard slot. Boot the Beaglebone, and you should see the lights sequence back and forth in a "Knight rider" pattern.
When the device is done programming, the lights will turn off. Unplug the device and remove the micro sd card from the slot. Keep it somewhwre where you know where it is at, as it will revert the Beaglebone back to this default configuration. Programming the beaglebone in this manner will take approximately 10 minutes.
Changing your Beaglebone's name
When your Beaglebone boots, it will, by default, have the name beaglebone. That is somewhat non-intuitive, so we want to change it to something unique. To do so, we will ssh into the bone and edit a file.
To do this, open Putty (a terminal window in your Bone MIGHT work...) and ssh to root on the bone, as in Lab 1. From the shell on your bone run the command
With this started up, also try issuing the command ping beaglebone.local. The two of these commands, issued together, should give you the ip address for your beaglebone.
Run the command sudo nano /etc/hostname
(or sudo vim /etc/hostname
if you like that editor better). This will open up the editor and allow you to change the hostname. Change the hostname of your beaglebone to <yourusername>beaglebone. An example of this is shown below. Press Ctrl-O to write the file out and Ctrl-X to exit (in vim: type :x and then enter to save & exit).
When this is done, edit the /etc/hosts file, again replacing the text beaglebone with <yourusername>beaglebone.
With this being done, issue the command sudo reboot
(followed by exit) to reboot your beaglebone. Your connection will drop.
Reconnecting to the Beaglebone
The Beaglebone will reboot quite quickly after you issue the previous command. You should be able to connect to it exactly as you did when changing its name.
Some VM and Linux Tips
Use right-control to excape from the virtual machine.
To open terminal: Applications->Accessories->Terminal
Linux equivalent of ipconfig: /sbin/ifconfig
, or, if the path is set up right, ifconfig
. (I hear that ifconfig
, if it works, may not give as complete results as /sbin/ifconfig
. I haven't confirmed this yet.
On windows with cygwin, ipconfig | grep "IPv4"
gives a summary of IP addresses.
On linux, use /sbin/ifconfig | grep 'inet addr'
to get the same effect.
Connecting to the Beaglebone from the Virtual Machine
According to BeagleBoard.org, "[v]irtual machines are not recommended when using the direct USB connection. It is recommended you use only network connections to your board if you are using a virtual machine."
So wire up your board to one of the hardware switches in the lab as follows: The BeagleBone should be wired to the hub. Your laptop should also be wired to the HUB. (Thanks to Dr. Schilling and several others for doing a lot of work to get these here for us!)
If you want to get by for now with just one wire, you can set up your laptop as a "hub" of sorts, and plug the Beaglebone into it. Ask me for details. In future labs, we will want to connect multiple bones, and having multiple ethernet cables will be important.
Another alternative is to manually set the bone's IP address using something like ifconfig eth0 192.168.1.100 netmask 255.255.255.0
, and your computer's address using the Windows GUI (e.g. to 192.168.1.101). You will also need to set your virtual machine's IP address — this is possible to do with the GUI (e.g. to 192.168.1.102).
Connect to the Bone through Putty and USB to find its IP address(es). Then, from a windows command prompt, find the IP address of your laptop. The subnet of two of these should match. For example, on my system, the bone had one IP address that was 192.168.1.100, and my computer had an IP address that was 192.168.1.103. The switch is acting as a 192.168.1.X subnet DHCP server. When I turn on my virtual machine in bridging mode, it gets an IP of 192.168.1.104, so it virtually appears as another device on the same subnet.
Connect to the Bone through the virtual machine. Open a terminal window in the virtual machine, and type 'ssh root@___.___.___.___', filling in the blanks with the IP address of the bone you found above.
If you always connect your devices to the hub in the same order that you used today, you may find that they have the same IP addresses in the future, which can make this process simpler to work through.
Verifying that C++ programs compile and execute
Once the tools have been installed, open up an editor on your virtual machine and enter the program shown below. This is a simple C++ program that will test out the cross compiler on your virtual machine. Unlike a traditional compiler, a cross compiler will write code for a different platform. In this case, you will be writing the code on your Linux Virtual machine, but it will be targeting the ARM architecture on the Beaglebone.
Sample C++ (arm2.cpp) program for cross compilation
#include <iostream> int main(int argc, char* argv[]) { std::cout << "Hello Dr. Schilling" << std::endl; }
Once you have entered the program, type the command:
arm-linux-gnueabihf-g++ arm2.cpp -o test2
to compile the code. You should see that the code compiles successfully. Try and execute the program on your Virtual machine by issuing the command ./test2. You should receive an error message.
Open up a second terminal window on your virtual machine and change to the directory where the code you are developing resides. Issue the command
sftp debian@your.bone's.IP
to connect to your Beaglebone. The password (as is shown on the login screen) is temppwd. Type the command
put test2
to transfer the program to the Beaglebone. Now open a third terminal window and change into the directory where your code was developed. Issue the command
ssh debian@your.bone's.IP.local
to open a secured connection with the Beaglebone. Log on using the temppwd password and type the command
./test2
to run the program. With this program successfully running, we now know that C programs can be cross compiled to our embedded board.
To compile a C program instead of a C++ program, use arm-linux-gnueabihf-gcc
instead of the ...-g++
command.
Full disclosure: I have not completed the following section this year. There may be dragons.
Measuring latency
Latency can be defined as "the time that elapses between a stimulus and the response to it." (And is closely related to response time, if not synonymous with it.) As we design our computer system, there is always latency. In the computer system, the latency is caused by the delay between an input signal changing and the appropriate output action being taken.
We would like to determine the latency between a push button being pressed and the LED changing state. To do this, you will need to use the program given in this file, respond.cpp, which sets up an interrupt-driven response to the button in C. You will read the input from pushbutton, and based upon whether the pushbutton is pressed or not, turn the LED either off or on.
Once you have completed this task, test the program using the setup that you now have. You should see that pressing the button turns off the light and releasing the button turns the light on.
To measure latency, we will need to change the input ever so slightly as well as connect your Analog discovery device to the unit. We will connect the second oscilloscope channel to the device so that we can see exactly when the pushbutton is pressed and when the LED changes state.
The figure below shows a sample capture of the oscilloscope in operation. Channel 1 (green) represents the output of the signal generator while channel 2 (blue) represents the output of the LED. Notice the slight, in this case 9.45 us, delay between the change in the input and the change in the output.
You may find it handy to hook up the function generator to your circuit to simulate continous clicking of the button. Make sure the function generator is ALWAYS powered off if the bone is EVER off.
Excellent Credit Ideas
To go above and beyond, you might try measuring other latencies on your system and describing why they are (hopefully) different than the interrupt-driven latency we measured above.
All the instructions beyond this point are subject to significant change.
Appendix: Cross Compiling with Eclipse
In the virtual machine, start eclipse under Linux using the command eclipse & from the console. Select a workspace that you would like to use (ideally in the shared library segment that you can access from both Windows and Linux). In Eclipse, select "File" and "New C Project". Enter a project name of "Lab1Part3". Click on next until you get to the Cross GCC Command screen. Enter the prefix for the compiler and the path, as is shown in Figure 9.
Add a new C file to the project, named Part3.c, and enter the code which is shown in Figure 10.
Build the code. It should build cleanly. Goto the Window -> Show View -> Other -> Remote Systems -> Remote Systems tool. This will open up the RSE functionality tab. Right click on "Local" and select "New Connection". Select "Linux" and configure the connection to your Beaglebone to match that shown in the Figure 11. Figure 11 shows multiple screens.
#include <stdio.h> #include <stdlib.h> #include <unistd.h> int bss_var; /* This is an uninitialized global variable. */ int data_var = 1; /* This is an initialized global variable. */ static int lv; static int lv2 = 1; int main(int argc, char* argv[]) { void *stack_var; /* This is a local variable declared on the stack.*/ char hostname[1024]; // This is an array declared on the stack which will hold the hostname. stack_var = (void*) main; printf("Hello WOrld! Main is executing at address %p\n", stack_var); printf("This address (%p) is in our stack frame\n", &stack_var); printf("The printf function is located at location %p.\n", printf); /* The bss section contains uninitialzed data. */ printf("This address (%p) is our bss section\n", &bss_var); /* Data section contains initialized data */ printf("This address (%p) is in our data section\n", &data_var); /* This is a static variable which is uninitialized. */ printf("The address of the static variable which is uninitialized is %p.\n", &lv); /* This is a static variable which is initialized. */ printf("The address of an initialized lv variable is %p\n", &lv2); /* read the hostname. */ gethostname(hostname, 1024); /* Print out the hostname to the console.*/ printf("Hostname: %s\n", hostname); return 0; }
Right click on your Beaglebone and click connect. Enter debian as the user id and temppwd as the password, as is shown in Figure 12.
With the connection made, select the built binary, right click, and select copy. Copy the binary to the remote machine. On the remote system, right click on ssh terminals on the beaglebone machine and "launch terminal". You should now be able to run the program on the remote machine. (Note: You may have to change permissions to allow you to execute the program. These were the permission commands talked about in operating systems.)
When the program runs, take note of the various addresses for main, the stack, the bss section, and the data section.
Now in Eclipse right click on the project and select properties. Select the Tool chain editor and change the current toolchain to LinuxGCC. This will cause Eclipse to build for your Linux virtual machine instead of the Beaglebone target. Go to Project -> Build all to build your source code. Then go to run -> run as -> Local C/C++ Application and execute the program. Note the addresses for main, the stack, the bss section, and the data section. Are they different and if so, how are they different?
Once you are done with this, set your environment back to the default settings. You can do this by going to the Properties page for the project and selecting the C/C++ Build entry and Settings.
Appendix: Building our first calculator
Now that we have gotten this far, we are going to build a more substantial program which serves as a calculator. Create a new cross compiled project in Eclipse and download the tar file from the course website. Extract the tar file into the directory, and the source code should be included into your project. Click on build and you should see the error messages shown in Figure 15. What kind of error is this message indicating?
Right click on the project and select settings. Select libraries and add the lib m library to the project (adding the math library. Remember from OS that libraries are in the format lib
Now that you have the program working on the Beaglebone, switch back to the command console and connect to the Beaglebone using the ssh command. Verify that you can start the program from a plain console independent of Eclipse.
Deliverables / Submission
If you have any questions, consult your instructor.
The Fine Print
1Debian has become the defacto standard for those who wish to work with the latest default Beaglebone OS (which is also Debian). If you have used the very-popular linux distribution Ubuntu, the transition will be easy because Ubuntu is based on Debian.
Submission Instructions for Dr. Yoder
Submission due 11pm, Friday of Week 3
Please upload a screenshot containing two traces — one for the button input and one for the LED output from the beaglebone, showing the latency between when the button is pressed and the LED changes its state.
Also include a text file including the latency as you read it from the screenshot. Put your name and the date at the top of this text file.