Dell XPS 15 L502x RAM upgrade

Back in 2011 the Dell XPS 15 L502x offered a lot of goods considering its price. The build quality was very good and it also looked quite appealing given its competitors at that time. On the performance side there we’re a lot of options to customize the XPS up to your needs, including GeForce MX, 8GB RAM, a SSD, i7, …

I started with a more budget friendly configuration including a traditional HDD, Intel i5-2410M, 4GB RAM and Windows 7. Over the years my demand for higher performance hardware has lead me to replace the HDD with a SDD, and upgrade the RAM to 8Gb. I’ve also dropped Windows entirely in favor of Ubuntu.

I’ve now come to a point where i’m doing most of my work in Linux and so the current hardware is still decent enough to pull it all together. Though once in a while you bump into software that is only supported on Windows / MacOs and so like many of you there is a need for running software in some sort of virtual machine. For me that is VirtualBox, it’s not perfect but frankly I don’t need it all that often so I can perfectly live with it.

Since Windows10 is quite the memory hog I found that running it inside a VM would sometimes put me in the situation where I’m running out of RAM. As a result paging would kick in and performance would drop tremendously. As a quick and relatively cheap fix (at least compared buying a new machine) I decided to upgrade my RAM to 16Gb since decent kits can be found for roughly €80.

What I had:
4Gb Adata RAM 1333MHz + 4Gb Corsair ValueSelect RAM 1066MHz

What I’ve upgraded to:
2 x 8Gb Corsair Vengeance RAM 1600MHz

Note that officially this configuration is not supported by Dell because at the time this laptop was sold the 8Gb DRAM stick was non-existing.

Wether to check if the upgrade was worth the deal I ran I couple of tests using the Phoronix automated benchmark suite. Here are the results for running it native under Ubuntu 18.04 LTS:

nativelinux

We notice an overall system performance improvement from our RAM upgrade, though the difference is in most occasions rather small given that we’re never utilizing more than 8Gb of memory. The only performance increase can come from the lower latency RAM. Regarding the negative results in Gimp, I bet that’s an anomaly in my tests so take that results with a grain of salt.

More interestingly is to see what happens inside the VM since this is where we may run into problems. After the upgrade I was able to higher the virtual DRAM size from 5Gb to 8Gb. Note that the Intel HD3000 is used as GPU. It also uses the system DRAM which make it compete with the CPU for memory access. I also suggest not to compare these results with running them under Linux native since the Windows 10VM is running on a HDD instead. Here are the results when running the benchmark inside Windows 10 virtual machine hosted by Ubuntu 18.04LTS:

vmwindows10

chart

We can clearly see a bigger improvement here as expected. The main point of the article is that now our Windows 10 VM can take up to 8Gb RAM which at least gives us enough headroom to run some memory exhaustive applications.

Advertisements

Running Doom on a i.MX6 with Yocto Linux

Although I’ve missed most of the hype around the original Doom game back in the 90’s, I did get to play it at a friends place. But it was only until I started programming that I picked it up again after reading Master’s of Doom.

When I started working on a embedded Linux device last year based on the i.MX6 processor the idea began to grow to compile Doom for our custom Linux based OS as some sort of easter egg. Unfortunately the world is real and deadlines are always too short and I had to let go of this idea. More recently however some of our dev-boards had to be archived and so I took this opportunity to take one home for a short period of time and finally get this one settled for once and for all.

One way to get it working is to setup a cross-compilation toolchain and cross-compile one of the many source ports of the doom engine. Another way would be to properly integrate it with the build of our custom Linux OS. Since we’re using Yocto to build our image the idea was to create a separate meta-layer that includes everything you need. You can find the meta-layer at github/geoffrey-vl/meta-doom.

Initially I started integrating the prboom engine. I found out that the out-of-three build  wasn’t working so well and I’ve bumped into some other issues’s as well. I had more luck using chocolate-doom which is better maintained. Chocolate-doom only recently switched over to using the SDL2 library so to be on the safe side I went to the latest version that runs on SDL(1). The game engine also requires libsdl-net which is currently not available in the official yocto repo’s. Luck was on my side when I bumped into a working libsdl-net recipe through google-search.

With the engine compiling happily I stumbled upon licensing issues. You have to own the game (and its game aka WAD files), so I couldn’t distribute anything that would be playable unless the user would copy its WAD files to our embedded system. Luckily there is the Freedoom project, a open-source implementation of the doom game. I also found a working recipe for Freedoom and so moments later my workstation produced a ready-to-play open-source implementation of the immensely populair Doom game.

Just for the kicks I also loaded my own WAD files, here is the result:

 

Raspberry Pi Community BSP

From past experiences with the Freescale Community BSP I was recently wondering if the same tooling was already setup for one of the largest community targetted board around: the Raspberry PI. And it seems it is not!

I went ahead and put it together. You can now easily initialize, synchronize and get your builds running by using Google’s Repo tool in conjuction with Yocto.
The repo can be found below together with instructions:

https://github.com/geoffrey-vl/rpi-community-bsp-platform

To get the BSP you need to have repo installed and use it as:

Install the repo utility:

$: mkdir ~/bin
$: curl http://commondatastorage.googleapis.com/git-repo-downloads/repo > ~/bin/repo
$: chmod a+x ~/bin/repo
$: PATH=${PATH}:~/bin

Download the BSP source:

$: mkdir rpi-community-bsp
$: cd rpi-community-bsp
$: repo init -u https://github.com/geoffrey-vl/rpi-community-bsp-platform -b rocko
$: repo sync

At the end of the commands you have every metadata you need to start work with. The source code is checked out at rpi-community-bsp/sources. You can use any directory to host your build. As a personal favor I’m using rpi-community-bsp/build as build folder.

To configure the build:

$: chmod a+x .repo/manifests/setup
$: .repo/manifests/setup

Afterwards you may want to edit the build/conf/local.conf to set the correct machine.

To start a simple image build:

$: source sources/poky/oe-init-build-env build
$: bitbake console-image

Other images:

  • ap-image
  • audio-image
  • console-basic-image
  • console-image
  • flask-image
  • gumsense-image
  • iot-image
  • pyqt5-image
  • qt5-basic-image
  • qt5-image

More documentation at http://www.jumpnowtek.com/rpi/Raspberry-Pi-Systems-with-Yocto.html

Creating an IoT thermostat (part IV)

Dealing with driver issue’s

Setup Wifi

In order to connect to the pi wireless I’ve added a RTL8192CU based WiFi adapter. To use the wireless connection we must do 3 things:

Setup wpa_supplicant:

root@thermopi2:~# vi /etc/wpa_supplicant.conf

And enter your wireless credentials:

</pre>
<h3>Next enable wlan0:</h3>
<pre>

root@thermopi2:~# vi /etc/wpa_supplicant.conf

Make sure auto wlan0 is not commented.

auto lo
iface lo inet loopback

auto eth0
iface eth0 inet dhcp

auto wlan0
iface wlan0 inet dhcp
        wireless_mode managed
        wpa-conf /etc/wpa_supplicant.conf

Restart the pi, or restart the wlan0 inteface:

root@thermopi2:~# ifdown wlan0
root@thermopi2:~# ifup wlan0
Successfully initialized wpa_supplicant
udhcpc (v1.24.1) started
Sending discover...
Sending discover...
Sending select for 192.168.0.203...
Lease of 192.168.0.203 obtained, lease time 3600
RTNETLINK answers: File exists
/etc/udhcpc.d/50default: Adding DNS 195.130.130.2
/etc/udhcpc.d/50default: Adding DNS 195.130.131.2
root@thermopi2:~# ifconfig
eth0      Link encap:Ethernet  HWaddr B8:27:EB:FA:03:83
          inet addr:192.168.0.186  Bcast:192.168.0.255  Mask:255.255.255.0
          inet6 addr: 2a02:1812:2521:3400:ba27:ebff:fefa:383%1/64 Scope:Global
          inet6 addr: fe80::ba27:ebff:fefa:383%lo/64 Scope:Link
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
          RX packets:1222 errors:0 dropped:1 overruns:0 frame:0
          TX packets:945 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:1000
          RX bytes:111800 (109.1 KiB)  TX bytes:183704 (179.3 KiB)

lo        Link encap:Local Loopback
          inet addr:127.0.0.1  Mask:255.0.0.0
          inet6 addr: ::1%1/128 Scope:Host
          UP LOOPBACK RUNNING  MTU:65536  Metric:1
          RX packets:0 errors:0 dropped:0 overruns:0 frame:0
          TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:1
          RX bytes:0 (0.0 B)  TX bytes:0 (0.0 B)

wlan0     Link encap:Ethernet  HWaddr 74:DA:38:8A:EA:3B
          inet addr:192.168.0.203  Bcast:192.168.0.255  Mask:255.255.255.0
          inet6 addr: 2a02:1812:2521:3400:76da:38ff:fe8a:ea3b%1/64 Scope:Global
          inet6 addr: fe80::76da:38ff:fe8a:ea3b%lo/64 Scope:Link
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
          RX packets:11 errors:0 dropped:0 overruns:0 frame:0
          TX packets:11 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:1000
          RX bytes:2790 (2.7 KiB)  TX bytes:1738 (1.6 KiB)

Dealing with driver issue's

I noticed on the first yocto image that I've made there were some issue's regarding the wireless connection. I was not sure exactly what went wrong, but it seemed to be a kernel/driver issue. The rtl8192cu wifi interface had connection problems whenever I disconnected the eth0 interface. I din't find a lot of clue's except from some folks complaining about the 8192cu kernel module not really working out to well. Through lsmod I found out that I was using this module. When using the adapter on my Ubuntu machine I noticed other drivers and modules got loaded - not the pesky 8192cu module - and the wireless interface was indeed working out well.

First idea would be to swap kernel modules by reconfiguring the kernel config in Yocto. However, since I'm recompiling I might as well pull in the latest sources for my working branch and just recompile the entire image. As a result I'd upgrade from Linux 4.4 to 4.9.
I also wrapped some of my work into script so that updating another time later on would make life much easier. Here is what I did:

Updating yocto to latest sources

The script below will pull in all latest meta-layers from the morty branch. Although newer branches are available like pyro and rocko, I'm not yet thinking about pulling these in since this will have a bigger impact on the package versions. Here is the script:

#!/bin/bash
BRANCH=morty
echo "##############################################"
echo "# upgrading sources to latest [$BRANCH]"
echo "##############################################"
echo ""
echo "####################################################################"
echo "### upgrading yocto-poky                                           #"
echo "####################################################################"
cd poky-morty/
git pull origin $BRANCH
echo ""
echo "####################################################################"
echo "### upgrading meta-openembedded                                    #"
echo "####################################################################"
cd meta-openembedded/
git pull origin $BRANCH
echo ""
echo "####################################################################"
echo "### upgrading meta-qt5                                             #"
echo "####################################################################"
cd ../meta-qt5/
git pull origin $BRANCH
echo ""
echo "####################################################################"
echo "### upgrading meta-raspberrypi                                     #"
echo "####################################################################"
cd ../meta-raspberrypi/
git pull origin $BRANCH
echo ""
echo "####################################################################"
echo "### upgrading meta-rpi (jumpnowtek)                                #"
echo "####################################################################"
cd ../../rpi/meta-rpi/
git pull origin $BRANCH

Save it in the directory directly above poky-morty, make it executable, and run it. Feel free to alter the script to pull in newer branches.

Rebuilding the image

Following script rebuilds the entire image:

#!/bin/bash
source poky-morty/oe-init-build-env /media/geoffrey/Data/yocto-pi/rpi/build
bitbake -c cleanall qt5-image
bitbake qt5-image

Again, save it to the same directoy, make it executable and run it (overnight).

Deploy the image to SD card

Jumpnowtek already provided some tools to automate some of the task that need to be done to get all your binaries on a SD card. The following script just wraps some of these tools for convenience:

#!/bin/bash
echo "##############################################"
echo "# Choose your SD card                        #"
echo "##############################################"
lsblk -dn -o NAME,SIZE
while true; do
	echo "# Device to format: "
	read SDCARD
	echo "selected: $SDCARD"
	if lsblk -dn -o NAME | grep "$SDCARD"; then

		break;
	else
		echo "Device not supported... retry"
	fi
done
echo "##############################################"
echo "# using card [$SDCARD]"
echo "##############################################"
echo ""
echo "##############################################"
echo "# making preparations                        #"
echo "##############################################"
MOUNTDIR="/media/card"
if [ ! -d "$MOUNTDIR" ]; then
	echo "Creating directory $MOUNTDIR"
	sudo mkdir "$MOUNTDIR"
else
	echo "Using $MOUNTDIR"
	umount "/media/card"
fi	

echo "exporting variables"
export OETMP=/media/geoffrey/Data/yocto-pi/rpi/build/tmp
export MACHINE=raspberrypi2

echo "unmounting stuff"
PART1="/dev/$SDCARD""p1"
PART2="/dev/$SDCARD""p2"
umount $PART1
umount $PART2

echo "##############################################"
echo "# copy boot partition                        #"
echo "##############################################"
./rpi/meta-rpi/scripts/copy_boot.sh $SDCARD

echo "##############################################"
echo "# copy boot partition                        #"
echo "##############################################"
IMAGENAME="qt5"
HOSTNME="thermopi2"
./rpi/meta-rpi/scripts/copy_rootfs.sh $SDCARD $IMAGENAME $HOSTNME

Once again, save the script and run it.

Boot the new system

With the system back up you first may want to check if you get the wlan0 interface working this time. But let's check the kernel version and driver modules first:

root@thermopi2:~# uname -a
Linux thermopi2 4.9.30 #1 SMP Sun Nov 5 20:10:01 CET 2017 armv7l armv7l armv7l GNU/Linux
root@thermopi2:~# lsmod
Module                  Size  Used by
ctr                     4263  2
ccm                     9163  1
ipv6                  412068  32
i2c_dev                 7169  0
arc4                    2211  2
rtl8192cu              81389  0
rtl_usb                12772  1 rtl8192cu
rtl8192c_common        58586  1 rtl8192cu
rtlwifi                88883  3 rtl_usb,rtl8192c_common,rtl8192cu
mac80211              664199  3 rtl_usb,rtlwifi,rtl8192cu
cfg80211              554896  2 mac80211,rtlwifi
rfkill                 21968  2 cfg80211
joydev                  9988  0
evdev                  12423  0
bcm2835_gpiomem         3900  0
i2c_bcm2835             7231  0
rpi_ft5406              5447  0
uio_pdrv_genirq         3923  0
rpi_backlight           2632  0
fixed                   3285  0
uio                    10396  1 uio_pdrv_genirq

We notice the newer 4.9 kernel is in use, and furthermore we also see the rtl8192cu and some other related modules loaded just as I saw on my Ubuntu machine. I went ahead and configured wlan again as mentioned earlier, é voila problem solved!

Deploying custom software

I'm not yet about to open source the entire codebase for my thermostat, I think there's already lots of stuff here to get you going. I also haven't yet made a decicated recipe in Yocto included my own made binaries. For now I will deploy my thermostat software by hand and create a little init script so that it gets loaded automatically at system boot.
For starters create the init script with following content:

#!/bin/bash

case "$1" in
        start)
                source /etc/profile.d/qt5-env.sh
		source /etc/profile.d/tslib.sh
                cd /usr/bin && ./QuickTemp &
                ;;
        stop)
                killall QuickTemp
                ;;
        reload|force-reload)
                ;;
        restart)
                ;;
        status)
                ;;
        *)
                echo"Usage: $SCRIPTNAME{start|stop|restart|force-reload|reload|status}" >&2
                exit 3
                ;;
esac

exit 0

Save it as /etc/init.d/quicktemp.sh and make it executable.

Next make sure the quicktemp executable is installed in the /usr/bin directoy. When this is done we can test our script:

root@thermopi2:~# mv QuickTemp /usr/bin/QuickTemp
root@thermopi2:~# /etc/init.d/quicktemp.sh start

To stop the service again:

root@thermopi2:~# /etc/init.d/quicktemp.sh stop

We turned our software into a service that can be started through the init daemon by executing the start and stop commands. One last step is need to be made for the service to automatically start at boot: we must link it to runlevel 5 so that the init service picks it up when going through all services connected to the runlevel.

root@thermopi2:/etc/rc5.d# ls -al
total 8
drwxr-xr-x  2 root root 4096 Nov  5 23:41 .
drwxr-xr-x 35 root root 4096 Nov  7 21:12 ..
lrwxrwxrwx  1 root root   20 Nov  5 23:41 S01networking -> ../init.d/networking
lrwxrwxrwx  1 root root   16 Nov  5 23:40 S02dbus-1 -> ../init.d/dbus-1
lrwxrwxrwx  1 root root   14 Nov  5 23:41 S09sshd -> ../init.d/sshd
lrwxrwxrwx  1 root root   21 Nov  5 19:46 S15mountnfs.sh -> ../init.d/mountnfs.sh
lrwxrwxrwx  1 root root   28 Nov  5 23:41 S15pi-blaster.boot.sh -> ../init.d/pi-blaster.boot.sh
lrwxrwxrwx  1 root root   14 Nov  5 23:41 S20ntpd -> ../init.d/ntpd
lrwxrwxrwx  1 root root   18 Nov  5 23:41 S20samba.sh -> ../init.d/samba.sh
lrwxrwxrwx  1 root root   16 Nov  5 23:40 S20syslog -> ../init.d/syslog
lrwxrwxrwx  1 root root   22 Nov  5 19:46 S99rmnologin.sh -> ../init.d/rmnologin.sh
lrwxrwxrwx  1 root root   23 Nov  5 20:56 S99stop-bootlogd -> ../init.d/stop-bootlogd
root@thermopi2:/etc/rc5.d# ln -s ../init.d/quicktemp.sh S95quicktemp
root@thermopi2:/etc/rc5.d# ls -al
total 8
drwxr-xr-x  2 root root 4096 Nov  7 23:29 .
drwxr-xr-x 35 root root 4096 Nov  7 21:12 ..
lrwxrwxrwx  1 root root   20 Nov  5 23:41 S01networking -> ../init.d/networking
lrwxrwxrwx  1 root root   16 Nov  5 23:40 S02dbus-1 -> ../init.d/dbus-1
lrwxrwxrwx  1 root root   14 Nov  5 23:41 S09sshd -> ../init.d/sshd
lrwxrwxrwx  1 root root   21 Nov  5 19:46 S15mountnfs.sh -> ../init.d/mountnfs.sh
lrwxrwxrwx  1 root root   28 Nov  5 23:41 S15pi-blaster.boot.sh -> ../init.d/pi-blaster.boot.sh
lrwxrwxrwx  1 root root   14 Nov  5 23:41 S20ntpd -> ../init.d/ntpd
lrwxrwxrwx  1 root root   18 Nov  5 23:41 S20samba.sh -> ../init.d/samba.sh
lrwxrwxrwx  1 root root   16 Nov  5 23:40 S20syslog -> ../init.d/syslog
lrwxrwxrwx  1 root root   22 Nov  7 23:29 S95quicktemp -> ../init.d/quicktemp.sh
lrwxrwxrwx  1 root root   22 Nov  5 19:46 S99rmnologin.sh -> ../init.d/rmnologin.sh
lrwxrwxrwx  1 root root   23 Nov  5 20:56 S99stop-bootlogd -> ../init.d/stop-bootlogd

Reboot the pi, you'll now see that your software is auto loaded at boot!

Extending the SD card lifetime

As I've mentioned in other blog post having your logs written to a tempfs volatile file system (in RAM) extends the SD card life time a lot. I wont go into detail again here, just have a look here. Note that in our Yocto image there is already the tmpfs created for you so actually we don't have to do anything extra here.

Edit

Although the RTL8192CU driver brought some improvements, it didn't offer a permanent solution. To fix it I've blacklisted the driver again:

root@thermopi2:/etc/rc5.d# echo "blacklist rtl8192cu" >> /etc/modprobe.d/blacklist.conf

Using Supervisord and tmpfs ramdisks on a Raspberry Pi

The Supervisor daemon is an easy to use utility which makes sure your services are running and never stop. It has its own logging infrastructure which you can check when things go wrong, aside of your own logging infrastructure. However, logging can degrade the SD card on embedded Raspberry Pi systems. Tmpfs to the resque!

Tmpfs allows us to make a filesystem in RAM so that no write cycli is made on the SD card. It can easily be made be editing /etc/fstab:

sudo vim /etc/fstab

And add:

tmpfs /var/log tmpfs defaults,noatime,mode=0755 0 0

When you reboot your system the content of /var/log, where all log messages are usually found, is now stored on the RAM based filesystem, hence improving SD card lifetime.

Enter Supervisor. To install supervisor:

sudo apt-get install supervisor

Configure your service by editing /etc/supervisor/conf.d/, for example I have a service running in Mono so I edit /etc/supervisor/conf.d/shutterservice.conf. Inside you’ll find following content:

[program:shutterservice]
command=mono /var/www/shutterservice/ShutterService.exe -d
user=www-data
stderr_logfile = /var/log/supervisor/shutterservice-err.log
stdout_logfile = /var/log/supervisor/shutterservice-stdout.log
directory=/var/www/shutterservice/

When you reboot your system again you’ll find that your service might not be available. You can verify this be starting and stopping the service by hand using supervisorctl. This tool will generate some obscure errors at this stage.

The problem here is that the supervisor daemon was not able to create its /var/log/supervisor logging directory when the system boots. You may create the directory yourself and restart supervisor manually using:

sudo mkdir /var/log/supervisor
sudo service supervisor restart

This time supervisor should be able to start, double check the logging files to make sure. However when you reboot your Pi again the tmpfs system will be cleared again, and once again supervisor will not be able to start automatically because of the missing log folder. We can fix this by using a config file for systemd which automatically creates temporary files.

Go ahead and create this config file:

sudo vim /etc/tmpfiles.d/supervisor.conf

Enter following content:

d /var/log/supervisor 0777 root root

When you reboot your system everything should be working as expected, plus you have just extended your SD card’s lifetime!

Creating an IoT thermostat (part III)

Improving our Yocto based distribution

Intro

Previously we made ourselves a Linux distribution ourselves for our target embedded system. We included basic Qt5 support which allows us to create a fast and responsive C++ frontend. This time we will further develop our embedded system and prepare it for usage.

Adding QtQuick – QML support

In the previous article we succeeded in created a QtWidget based application. However, with QtQuick there is a new UI framework available which has its own set of benefits. You may already have noticed that QtCreator comes with lots of examples and you may have even tried some of them. However, if you (like me) created your Yocto based OS using the bitbake qt5-basic-image command you will find that some programs may not work when yo run them on your embedded device:

root@raspberryyocto:~# ./clocks
./clocks: error while loading shared libraries: libQt5Quick.so.5: cannot open shared object file: No such file or directory
root@raspberryyocto:~#

Basically we didn’t include support for QtQuick when we compiled our OS. So if you’re into using QtQuick go back through your Yocto working folder and bitbake the qt5-image:

geoffrey@geoffrey-Dell-XPS-L502X:/media/geoffrey/Data/yocto-pi/rpi/build$ bitbake qt5-image
Loading cache: 100% |############################################| Time: 0:00:00
Loaded 2660 entries from dependency cache.
Parsing recipes: 100% |##########################################| Time: 0:00:01
Parsing of 1972 .bb files complete (1964 cached, 8 parsed). 2668 targets, 353 skipped, 0 masked, 0 errors.
NOTE: Resolving any missing task queue dependencies

Build Configuration:
BB_VERSION = "1.32.0"
BUILD_SYS = "x86_64-linux"
NATIVELSBSTRING = "universal"
TARGET_SYS = "arm-poky-linux-gnueabi"
MACHINE = "raspberrypi"
DISTRO = "poky"
DISTRO_VERSION = "2.2.1"
TUNE_FEATURES = "arm armv6 vfp arm1176jzfs callconvention-hard"
TARGET_FPU = "hard"
meta
meta-poky = "morty:a3fa5ce87619e81d7acfa43340dd18d8f2b2d7dc"
meta-oe
meta-multimedia
meta-networking
meta-python = "morty:1efa5d623bc64659b57389e50be2568b1355d5f7"
meta-qt5 = "morty:9aa870eecf6dc7a87678393bd55b97e21033ab48"
meta-raspberrypi = "master:e1f69daa805cb02ddd123ae2d4d48035cb5b41d0"
meta-rpi = "morty:03841471ccaed549a2a14a896c13f71af76cf482"

Initialising tasks: 100% |#######################################| Time: 0:00:08
NOTE: Executing SetScene Tasks
NOTE: Executing RunQueue Tasks
NOTE: Tasks Summary: Attempted 3619 tasks of which 3538 didn't need to be rerun and all succeeded.
geoffrey@geoffrey-Dell-XPS-L502X:/media/geoffrey/Data/yocto-pi/rpi/build$

Notice how fast compiling the image goes this time compared to when we build the qt5-basic-image. The reason for this faster build time is because the qt5-image inherits the qt5-basic-image and Yocto just needed to recompile some of the components that were not yet compiled. Also note that you don’t need a new SDK and you shouldn’t need to re-configure QtCreator.

With your SD card already formatted you only need to copy the compiled files to your SD card:

geoffrey@geoffrey-Dell-XPS-L502X:/media/geoffrey/Data/yocto-pi/rpi/build$ cd ../meta-rpi/scripts/
geoffrey@geoffrey-Dell-XPS-L502X:/media/geoffrey/Data/yocto-pi/rpi/meta-rpi/scripts$ sudo umount /dev/mmcblk0p1
geoffrey@geoffrey-Dell-XPS-L502X:/media/geoffrey/Data/yocto-pi/rpi/meta-rpi/scripts$ sudo umount /dev/mmcblk0p2
geoffrey@geoffrey-Dell-XPS-L502X:/media/geoffrey/Data/yocto-pi/rpi/meta-rpi/scripts$ export MACHINE=raspberrypi
geoffrey@geoffrey-Dell-XPS-L502X:/media/geoffrey/Data/yocto-pi/rpi/meta-rpi/scripts$ export OETMP=/media/geoffrey/Data/yocto-pi/rpi/build/tmp
geoffrey@geoffrey-Dell-XPS-L502X:/media/geoffrey/Data/yocto-pi/rpi/meta-rpi/scripts$ ./copy_rootfs.sh mmcblk0 qt5 raspberryyocto

OETMP: /media/geoffrey/Data/yocto-pi/rpi/build/tmp
IMAGE: qt5
HOSTNAME: raspberryyocto

File found: /media/geoffrey/Data/yocto-pi/rpi/build/tmp/deploy/images/raspberrypi/qt5-image-raspberrypi.tar.xz

Block device not found: /dev/mmcblk02, trying p2

Formatting /dev/mmcblk0p2 as ext4
[sudo] wachtwoord voor geoffrey:
/dev/mmcblk0p2 bevat een ext4-bestandssysteem met label 'ROOT'
laatst aangekoppeld op / op Sun Feb 19 22:07:51 2017
Toch doorgaan? (j,n) j
Mounting /dev/mmcblk0p2
Extracting qt5-image-raspberrypi.tar.xz to /media/card
Writing raspberryyocto to /etc/hostname
Unmounting /dev/mmcblk0p2
Done
geoffrey@geoffrey-Dell-XPS-L502X:/media/geoffrey/Data/yocto-pi/rpi/meta-rpi/scripts$

With that done we need to have a QtQuick test application. If you haven’t yet tried on of the QtCreator’s QtQuick examples do so now. Get back to your embedded device, insert the SD card and boot. Once booted, retrieve the device’s IP address and copy over any QtQuick test application. I’ve used the clocks application. Once you have the application compiled and copied over to the raspberry pi, ssh into your pi and start the application (or launch it from within QtCreator if you’ve had it still openened). You should see more or less something like this:

qtquick-demo-clocks-small

If you happen to run into “out of memory” errors:

root@raspberryyocto:~# ./clocks
QML debugging is enabled. Only use this in a safe environment.
Unable to query physical screen size, defaulting to 100 dpi.
To override, set QT_QPA_EGLFS_PHYSICAL_WIDTH and QT_QPA_EGLFS_PHYSICAL_HEIGHT (in millimeters).
JIT is disabled for QML. Property bindings and animations will be very slow. Visit https://wiki.qt.io/V4 to learn about possible solutions for your platform.
glGetError 0x505
QSGTextureAtlas: texture atlas allocation failed, out of memory

… then you should tweak the CPU/GPU memory allocation settings. This settings is loaded at boot and it is also saved in a config file on your boot partition. To adjust the config file we first need to mount the boot partition, and next we can edit the file using the vi editor:

root@raspberryyocto:~# mkdir /mnt/fat
root@raspberryyocto:~# mount /dev/mmcblk0p1 /mnt/fat
root@raspberryyocto:~# vi /mnt/fat/config.txt

Add gpu_mem=256 to this file and reboot your pi. Try again running the clocks application, things should go now as intended:

root@raspberryyocto:~# ./clocks
QML debugging is enabled. Only use this in a safe environment.
Unable to query physical screen size, defaulting to 100 dpi.
To override, set QT_QPA_EGLFS_PHYSICAL_WIDTH and QT_QPA_EGLFS_PHYSICAL_HEIGHT (in millimeters).
JIT is disabled for QML. Property bindings and animations will be very slow. Visit https://wiki.qt.io/V4 to learn about possible solutions for your platform.

Setting the timezone

To show the current time we will rely on NTP. RaspberryPi does not come with a RTC see I don’t see any other option. NTP is already added via Yocto, we only have to set the correct timezone:

root@yoctopi:~# ls -l /etc/localtime
lrwxrwxrwx 1 root root 27 Apr 10 18:36 /etc/localtime -> /usr/share/zoneinfo/EST5EDT
root@yoctopi:~# rm /etc/localtime
root@yoctopi:~# ln -s /usr/share/zoneinfo/Europe/Paris /etc/localtime
root@yoctopi:~# date
Sun Apr 16 12:30:40 CEST 2017

Adding a touch screen

The RaspberryPi community has a very decent 7″ touch screen. There is not much to say about, I got one, followed the instructions to hook it op and basically started testing some my applications straight away!

2033-01

Side note: I used the same housing as show above. This one has the display upside down, the rotate the display through software we must again edit the config file on the boot partition:

root@raspberryyocto:~# mkdir /mnt/fat
root@raspberryyocto:~# mount /dev/mmcblk0p1 /mnt/fat
root@raspberryyocto:~# vi /mnt/fat/config.txt

and add:

display_rotate=2

Restart to apply your changes.

Adding a HTU21D I²C temperature sensor

The HTU21D is a decent temperature and humidity sensor which perfectly suits our needs. To hook it up to our Raspberry Pi 2:

htu21d-block-s

Before we can use the I2C bus we must again edit the Pi’s config file:

root@raspberryyocto:~# mkdir /mnt/fat
root@raspberryyocto:~# mount /dev/mmcblk0p1 /mnt/fat
root@raspberryyocto:~# vi /mnt/fat/config.txt

and add:

dtparam=i2c_arm=on

Restart to apply your changes.
After the system has booted into Linux again we will first check if the i2c_bcm2708 module has been loaded:

root@yoctopi:~# lsmod
Module                  Size  Used by
ipv6                  350447  28
i2c_dev                 6115  2
evdev                  11396  1
joydev                  8960  0
bcm2835_gpiomem         3036  0
i2c_bcm2708             4834  0
bcm2835_wdt             3225  0
rpi_ft5406              4612  0
uio_pdrv_genirq         3164  0
rpi_backlight           2064  0
uio                     8128  1 uio_pdrv_genirq

Now we must add the i2c device by doing:

root@yoctopi:~# touch /etc/modules
root@yoctopi:~# echo 'i2c-dev' >> /etc/modules

Reboot again. When all went good we can now use the ic2detect tool to see if the Pi is able to communicate with our temperature sensor:

root@yoctopi:~# i2cdetect -y 1
     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f
00:          -- -- -- -- -- -- -- -- -- -- -- -- --
10: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
20: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
30: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
40: 40 -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
50: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
60: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
70: -- -- -- -- -- -- -- --

With everything setup and good to go I can now start developing my application. Stay tuned for more!