Skip to content

BYOM: software

octaexon edited this page May 26, 2018 · 2 revisions

Preamble

You are here to build your own mule and you want as much control as possible over the build. Well, it is not a short process, but it is relatively straightforward, in the sense that every challenge is surmountable.

The two steepest cliffs from the software side are the provisioning of the tensorflow and opencv libraries. These are not just simple pip install commands. They must be built for the raspberry pi from source. There are existing tutorials online for the opencv build and we reproduce one here. However, we did not manage to build tensorflow ourselves on the pi and we are using a third-party cross-compilation openly available. More on these matters below.

This tutorial is macOS-centric from those commands that require a PC (but that is not many). On the Pi-side, we are expecting a Raspberry Pi 3 Model B, a Picamera (for the Picamera section), a PWM controller (for the I2C section).

Raspberry Pi image

  • Download Jessie Lite to you Mac:
wget http://downloads.raspberrypi.org/raspbian_lite/images/raspbian_lite-2017-06-23/2017-06-21-raspbian-jessie-lite.zip
  • Unzip:
unzip 2017-06-21-raspbian-jessie-lite.zip
  • Insert sdcard into your Mac and find the disk number:
df

The appropriate line of output will be mounted within /Volumes. We are interested in the disk number from the filesystem column, for example, the 2 from:

/dev/disk2s1 
  • Unmount it and burn the image:
sudo diskutil umount /dev/diskXs1
sudo dd bs=32m if=2017-06-21-raspbian-jessie-lite.img of=/dev/rdiskX

where X should be replaced with the appropriate disk number.

  • We wish to conduct a headless setup of the raspberry pi so we need to ensure that ssh is enabled at the outset. With this in mind, remount the card (it should be automatically mounted at /Volumes/boot) and simply create an empty ssh file within this boot folder:
sudo diskutil mount /dev/diskXs1
touch /Volumes/boot/ssh
  • Eject the sdcard:
sudo diskutil eject /dev/diskXs1

Pi initialization

  • Place the sdcard into the raspberry pi, connect the raspberry pi using an ethernet cable to your router and boot up.
  • Find the raspberry pi on your local network. So from you Mac:
arp -a

to find "everything" that is on your network. (Not necessarily, routers are pretty mean at times). In general, the output can be pretty cryptic so it might worth typing the command with the raspberry pi disconnected from the router, in order to see what it new.

  • Once you have its network address, e.g. 192.168.178.33, you are ready to ssh:
ssh pi@192.168.178.33

It may even resolve the default hostname for you, so you might be able to:

ssh pi@raspberrypi

The default user is pi and the default password is raspberry.

  • Perform some initialization and (optional) customization:
sudo raspi-config

Then expand the filesystem (necessary), change hostname (optional), change password (optional but advised obviously). Upon finishing these, you will be directed to perform a reboot (to actually expand the filesystem). Do so, you will be disconnected, so reconnect through ssh once again.

Wifi setup

  • With the ssid and passphrase of your local network, you can generate an encrypted version:
wpa_passphrase <ssid> <passphrase>

For example, on the network "asdfasdf" with passphrase "qwerqwer", the output of:

wpa_passphrase asdfasdf qwerqwer

is

network={
	ssid="asdfasdf"
	#psk="qwerqwer"
	psk=196706ebd5bde679730d964f0f42439a9e9350719d092ff022f684938275de08
}
  • Edit using:
sudo nano /etc/wpa_supplicant/wpa_supplicant.conf

to contain the output of the wpa_passphrase command above. Do not forget to delete the unencrypted password line psk="qwerqwer".

  • Reconfigure the wifi:
wpa_cli -i wlan0 reconfigure

Environment setup

  • Update and upgrade the system:
sudo apt-get update && sudo apt-get upgrade
  • Load awesomeness (version control, editting, shell):
sudo apt-get install git vim zsh
  • Switch to zsh:
chsh -s $(which zsh)

In order for the switch to take effect, logout and back in through ssh.

  • Load even more awesomeness:
cd ~
git clone https://github.com/robbyrussell/oh-my-zsh.git
cp ~/.oh-my-zsh/templates/zshrc.zsh-template ~/.zshrc

oh-my-zsh is simply a fantastic set of plugins for zsh that allows for wonderful customizations.

Python setup

  • On Jessie-Lite, no python3 is installed by default, do so:
sudo apt-get install python3

This should install install python 3.4.2. (We want 3.4 for later tensorflow compatibility.)

  • Get python package installers for python2 and python3:
sudo apt-get python-pip
sudo apt-get python3-pip
  • Python virtual environments are must:
sudo pip install virtualenv virtualenvwrapper

after which, we should append to our .zshrc file:

export WORKON_HOME=$HOME/.virtualenvs
VIRTUALENVWRAPPER_PYTHON=/usr/bin/python3
source /usr/local/bin/virtualenvwrapper.sh
  • Create a new (empty) virtual environment for the mule:
mkvirtualenv mule

Now append to your .zshrc file:

workon mule

To automatically load this virtualenv every time you log in. We are assuming that you use this raspberry pi for running the muleAI. In general, to leave:

deactivate mule

and to enter:

workon mule

Tensorflow installation

Now for the first of the 3rd-party installs. It would be nice of course to think that we could compile from source the tensorflow code directly on the raspberry pi all on our own, but not only is this an arduous task, it is unlikely to succeed.

  • Create a directory for the code:
cd ~
mkdir ThirdParty && cd $_
  • Load libraries necessary for the installation of the tensorflow wheel:
sudo apt-get install libblas-dev liblapack-dev libatlas-base-dev gfortran python3-dev python3-setuptools
  • Check out the website: http://ci.tensorflow.org/view/Nightly/job/nightly-pi-python3/buildTimeTrend for the version that you want. There are two things to note. First, a lot of builds are red, meaning that they failed. You can neglect these. Second, of the builds that passed, not all will work. For example, build 8 (tensorflow-1.3.0) passed yet after installation, importing tensorflow throws the error: /home/pi/.virtualenvs/mule/lib/python3.4/site-packages/tensorflow/python/_pywrap_tensorflow_internal.so: undefined symbol: _Py_ZeroStruct In general a _Py_ZeroStruct error means that the so was built with some python2 headers. I don't know if that was on our side or in the original wheel.
  • Download your chosen wheel:
wget -O tensorflow-1.5.0-cp34-none-any.whl http://ci.tensorflow.org/view/Nightly/job/nightly-pi-python3/122/artifact/output-artifacts/tensorflow-1.5.0-cp34-none-any.whl
  • Install the wheel (into the mule virtualenv):
pip install tensorflow-1.5.0-cp34-none-any.whl

There you go.

Opencv installation

Computer vision!!! Once again, not a simple pip install, we need to build from source, but we can and it only takes 3hrs. Yeah! (Note: it takes 3hrs). For more information, you should check out: https://www.pyimagesearch.com/2017/09/04/raspbian-stretch-install-opencv-3-python-on-your-raspberry-pi/ Your tensorflow installation should have installed numpy for you as a prerequisite. Importantly, it is the only python prerequisite for opencv. Check that is in the mule virtualenv with:

pip list

It is going to be there, but if for some reason it is not (and that reason is unlikely to be good, e.g. did you ensure that you were in the mule virtualenv when you installed tensorflow????), then:

pip install numpy

Note that you do not just lay down a pip install command for a heavily cythonized library on a raspberry pi. You will be left twiddling your thumbs for a while.

  • Get the libraries:
sudo apt-get install build-essential cmake pkg-config
sudo apt-get install libjpeg-dev libtiff5-dev libjasper-dev libpng12-dev
sudo apt-get install libavcodec-dev libavformat-dev libswscale-dev libv4l-dev
sudo apt-get install libxvidcore-dev libx264-dev
sudo apt-get install libgtk2.0-dev libgtk-3-dev
sudo apt-get install libatlas-base-dev gfortran
sudo apt-get install python3-dev
  • Get the source code:
cd ~/ThirdParty
wget -O opencv.zip https://github.com/Itseez/opencv/archive/3.4.0.zip
unzip opencv.zip
wget -O opencv_contrib.zip https://github.com/Itseez/opencv_contrib/archive/3.4.0.zip
unzip opencv_contrib.zip
cd ~/opencv-3.4.0/
  • Setup the build environment:
mkdir build && cd build
cmake -D CMAKE_BUILD_TYPE=RELEASE \
    -D CMAKE_INSTALL_PREFIX=/usr/local \
    -D INSTALL_PYTHON_EXAMPLES=ON \
    -D OPENCV_EXTRA_MODULES_PATH=~/ThirdParty/opencv_contrib-3.4.0/modules \
    -D BUILD_EXAMPLES=ON ..
  • Setup swap for build:
sudo nano /etc/dphys-swapfile 

comment the current CONF_SWAPSIZE line and add:

CONF_SWAPSIZE=1024

Then restart the process:

sudo /etc/init.d/dphys-swapfile stop
sudo /etc/init.d/dphys-swapfile start
  • Make:
make -j4
sudo make install
sudo ldconfig

This takes a while.

  • Check that the shared object file is installed and rename it to something simpler:
ls -l /usr/local/lib/python3.4/site-packages/
cd $_
mv cv2.cpython-34m.so cv2.so
  • Now link the file to mule virtualenv:
cd ~/.virtualenvs/mule/lib/python3.4/site-packages
ln -s /usr/local/lib/python3.4/site-packages/cv2.so cv2.so
  • Revert the swapfile to its original state (IMPORTANT: you will degrade your sdcard quickly if not) and restart the process.

muleAI

At last ready for some intelligence. Let's get the mule going.

mkdir Development  && cd $_
git clone https://github.com/MarcusJones/muleAI.git
Clone this wiki locally