mzahran001 / Infotainment-System-Yocto

Building infotainment system using the Yocto project

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Infotainment-System-Yocto

This repo if for ITI-Intake 40 graduation project

What is a car infotainment system?

An in-vehicle infotainment system is a combination of systems that deliver entertainment and information to the driver and passengers. They do it using audio and video interfaces, touch screen displays, button panels, voice commands, and many other features. check more!

Table of Contents

  1. Building the image using Yocto
    1. Setting up environment
    2. Configuring network settings
    3. Adding VNC server
    4. Adding Qt
    5. Adding bluetooth
    6. Adding sound
    7. Video setup
    8. Adding debugging tools
    9. Baking and flashing the image
    10. Known issues
  2. Creating UI
    1. Setting up environment
    2. Configuring the cross compiling and remote deployment settings on Qt creator
    3. Creating Qt project with C++
    4. Running multimedia Mp3 and Mp4
  3. Conclusion
  4. References

General setup

Host machine: Ubuntu 18.04.4 LTS
Target machine: Raspberry Pi 3B+


Building the image using Yocto

Setting up environment

  1. Download the Poky build system (zeus branch)
$ git clone -b zeus git://git.yoctoproject.org/poky
  1. Download RPI BSP (zeus branch)
$ git clone -b zeus https://github.com/agherzan/meta-raspberrypi.git 
  1. Download openembedded (zeus branch)
$ git clone -b zeus https://github.com/openembedded/meta-openembedded.git

Note: for my steps, both poky, meta-raspberrypi and meta-openembedded repos are in the same path

  1. Source “oe-init-build-env” script
$ source poky/oe-init-build-env rpi-build
  1. Edit rpi-build/bblayers.conf and add layers to BBLAYERS variable
BBLAYERS ?= " \
/ABSOLUTE/PATH/poky/meta \
/ABSOLUTE/PATH/poky/meta-poky \
/ABSOLUTE/PATH/poky/meta-yocto-bsp \
/ABSOLUTE/PATH/meta-raspberrypi \
/ABSOLUTE/PATH/meta-openembedded/meta-oe \
/ABSOLUTE/PATH/meta-openembedded/meta-python \
/ABSOLUTE/PATH/meta-openembedded/meta-networking \
/ABSOLUTE/PATH/meta-openembedded/meta-multimedia \
"
  1. Edit rpi-build/local.conf by changing MACHINE ??= "qemux86-64" to be MACHINE ?= "raspberrypi3-64"

  2. Edit rpi-build/local.conf and add the following line

LICENSE_FLAGS_WHITELIST_append = " commercial_faad2"
VIRTUAL-RUNTIME_init_manager = "systemd"
DISTRO_FEATURES_append = " systemd"
DISTRO_FEATURES_BACKFILL_CONSIDERED = "sysvinit"
  1. For developing you might need rootfs extra space, to add extra size as 5G edit rpi-build/local.conf and add the following line
IMAGE_ROOTFS_EXTRA_SPACE = "5242880"

Adding VNC server

To connect to your target through VNC server, then edit rpi-build/local.conf and add x11vnc to IMAGE_INSTALL_append variable

IMAGE_INSTALL_append = " x11vnc"

There is an issue with x11vnc setup mentioned in the Known issues section in issue no.1

Configuring network settings (Wifi)

  1. Create new custom layer $ bitbake-layers create-layer meta-customInfotainment
  2. Add the layer to BBLAYERS variable as previuos
  3. Create new folder for network configuration recipes, recipes-network will hold overlaying network files (.bbappend files)
$ cd meta-customInfotainment/recipes-network

The tree should be as following

recipes-network
    ├── base-files
    │   ├── base-files
    │   │   └── profile
    │   └── base-files_%.bbappend
    ├── init-ifupdown
    │   ├── init-ifupdown
    │   │   └── interfaces
    │   └── init-ifupdown_%.bbappend
    └── wpa-supplicant
        ├── wpa-supplicant
        │   ├── 0001-AP-Silently-ignore-management-frame-from-unexpected-.patch
        │   ├── 0001-replace-systemd-install-Alias-with-WantedBy.patch
        │   ├── 99_wpa_supplicant
        │   ├── defconfig
        │   ├── wpa_supplicant.conf
        │   ├── wpa_supplicant.conf-sane
        │   └── wpa-supplicant.sh
        └── wpa-supplicant_%.bbappend

  1. To add input wifi access point: /etc/wpa_supplicant.conf file is required, which is produced by wpa-supplicant recipe
$ echo 'FILESEXTRAPATHS_prepend := "${THISDIR}/${PN}:"' >  wpa-supplicant_%.bbappend  

Copy the original wpa_supplicant.conf-sane file then add your modifications. It should be as following

ctrl_interface=/var/run/wpa_supplicant
ctrl_interface_group=0
update_config=1

network={
	ssid="NETWORK_NAME"
	psk="NETWORK_PASSWORD"
}

network={
        key_mgmt=NONE
}
  1. To enable wifi and set static ip address: /etc/network/interfaces file is required, which is produced by init-ifupdown recipe
$ echo 'FILESEXTRAPATHS_prepend := "${THISDIR}/${PN}:"' >  init-ifupdown_%.bbappend  

Copy the original interfaces file then add your modifications. It should be as following

# Wireless interfaces
auto wlan0

allow-hotplug wlan0
iface wlan0 inet static
	address 192.168.1.2  
	netmask 255.255.255.0  
	gateway 192.168.1.1  
	wpa-conf /etc/wpa_supplicant.conf  
iface default inet dhcp
  1. In case of X11VNC installed, then you need to enable server at booting time: /etc/profile file is required, which is produced by base-files recipe. Also for unkonwn reason your wifi may be blocked by rfkill, then you need to unlbock and enable it again
$ echo 'FILESEXTRAPATHS_prepend := "${THISDIR}/${PN}:"' >  init-ifupdown_%.bbappend  

Copy the original profile file then add these to the end of the file

rfkill unblock wifi

ifconfig wlan0 up
x11vnc &

Note: To know the recipe producing the path, after sourcing run $ oe-pkgdata-util find-path /etc/profile The output will look like base-files: /etc/profile
There is an issue in the netwrok setup mentioned in the Known issues section in issue no.2

Adding Qt

  1. Download the qt5 layer (zeus branch)
$ git clone -b zeus https://github.com/meta-qt5/meta-qt5
  1. Edit rpi-build/bblayers.conf and add the layer to BBLAYERS variable
BBLAYERS ?= " \
....
/ABSOLUTE/PATH/meta-qt5 \
"
  1. To support Qt5 on image, edit rpi-build/local.conf and add
IMAGE_INSTALL_append = " make cmake"
IMAGE_INSTALL_append = " qtbase-tools qtbase qtdeclarative qtimageformats qtmultimedia qtquickcontrols2 qtquickcontrols qtbase-plugins cinematicexperience liberation-fonts"
PACKAGECONFIG_FONTS_append_pn-qtbase = " fontconfig"
  1. To enable remote deployment on RPI using Qt platform, you need to add extra network configuration to rpi-build/local.conf
IMAGE_INSTALL_append = " openssh-sftp-server rsync"

Adding bluetooth

Edit rpi-build/local.conf to add required firmwares and bluez

MACHINE_FEATURES += " bluetooth"
CORE_IMAGE_EXTRA_INSTALL = " rsync "
DISTRO_FEATURES_append = " pi-bluetooth bluez5 bluetooth linux-firmware-bcm43430 linux-firmware-brcmfmac43430"
IMAGE_INSTALL_append = " pi-bluetooth bluez5 bluez5-testtools linux-firmware-bcm43430 i2c-tools hostapd dhcp-server udev-rules-rpi bridge-utils iptables linux-firmware-ralink linux-firmware-rtl8192ce linux-firmware-rtl8192cu linux-firmware-rtl8192su linux-firmware-rpidistro-bcm43430"
ENABLE_UART = "1"

There is an issue in the netwrok setup mentioned in the Known issues section in issue no.3

Adding sound

  1. Edit rpi-build/local.conf and add the following to enable GStreamer or mgp123. Fot Qt Media modules GStreamer is required
IMAGE_INSTALL_append = " gstreamer1.0-plugins-good gstreamer1.0-plugins-base gstreamer1.0-plugins-ugly"
LICENSE_FLAGS_WHITELIST_append = " commercial  commercial_gstreamer1.0-plugins-ugly commercial_gstreamer1.0-plugins-ugly"
PACKAGECONFIG_append_pn-qtmultimedia = " gstreamer alsa" 
  1. Pulseaudio is required to stream audio over bluetooth
DISTRO_FEATURES_append = " pulseaudio"
IMAGE_INSTALL_append = " pulseaudio pulseaudio-module-dbus-protocol pulseaudio-server pulseaudio-module-bluetooth-discover pulseaudio-module-bluetooth-policy pulseaudio-module-bluez5-device pulseaudio-module-bluez5-discover alsa-utils alsa-plugins"

Video setup

For displaying video in proper way you may need to set HDMI_MODE and HDMI_GROUP in rpi-build/local.conf

Adding debugging tools

To enable debugging you will need to add strace in local.conf IMAGE_INSTALL_append = " strace"

Baking and flashing the image

  1. Build the image using the build engine BitBake
    It may take many hours to finish the build process
$ bitbake core-image-sato

core-image-sato is selected as it supports X11 and a GUI server is required. But it has a bug mentioned in the Known issues section in issues no.4 and no.5

  1. If the build process was successful, the raspberry pi image will be under rpi-build/tmp/deploy/images/raspberrypi3-64/core-image-sato-raspberrypi3-64.rpi-sdimg

  2. Flash the image on the SD card and make sure that it's formatted as free space
    my SD card is /dev/mmcblk0

$ sudo dd if=tmp/deploy/images/raspberrypi3-64/core-image-sato-raspberrypi3-64.rpi-sdimg of=/dev/mmcblk0 status=progress conv=fsync bs=4M
  1. After the image is ready, connect RPI with HDMI having the next interface

Known issues

Issue 1: Running Qt5 will disable X11 then it will disable x11vnc
Workaround: Enable x11vnc and run it on your host machine before you deploy with Qt

Issue 2: Although network setup, the RPI doesn't connect automatically to wifi after deploying image
Workaround: I need to connect my RPI to HDMI and connect to my wifi manually only for the first time. HDMI is the best choice so far

Issue 3: Bluetooth configurations enables bluetooth connections and parinig with any device, but it seems that the bluetooth driver has a bug which fails in attaching serial to bluez stack and leads to block the audio streaming via bluetooth

Issue 4: The halt function in core-image-sato has a bug, where any restart/shutdown/reboot operation interrupts the image every time
Workaround: Cut the power off temporarly each time

Issue 5: Date and time cannot be set by default in core-image-sato


Creating UI

Setting up environment

  1. Install Qt5 Creator command line launcher, my Qt version is 5.9.5
$ sudo apt-get install qtcreator  
  1. Install Qt5 tool chain for cross compilation. The installation path may differ, just check your terminal output
$ bitbake meta-toolchain-qt5  
$ cd tmp/deploy/sdk
$ ./poky-glibc-x86_64-meta-toolchain-qt5-aarch64-raspberrypi3-64-toolchain-3.0.2.sh 

Configuring the cross compiling and remote deployment settings on Qt creator

  1. Frist you need to source the sdk tool chain. The source path may differ depending on the output of your SDK installation
$ source rpi-build/tmp/deploy/sdk/yes/environment-setup-aarch64-poky-linux  
  1. From the same terminal launch qtcreator
$ qtcreator 
  1. After Qt creator launches, you need to configure the device from Tools -> Devices
    1. Add new Generic Linux Device providing the name you want, the hostname/IP address of your device and the username
    2. Make sure that the device is connected on the same ethernet network to your device and that you did step 4 in Adding Qt
    3. Do the device Test, if anything goes wrong you need the review your network configurations

  2. Then configure your build and run options from Tools -> Build & Run
    1. Qt Versions -> add the path of the SDK qmake rpi-build/tmp/deploy/sdk/yes/sysroots/x86_64-pokysdk-linux/usr/bin/qmake with any name

    2. Compilers -> add the path of C and C++ compilers rpi-build/tmp/deploy/sdk/yes/sysroots/x86_64-pokysdk-linux/usr/bin/aarch64-poky-linux/aarch64-poky-linux-g++ with any name

    3. Debuggers -> add the remote debugger path rpi-build/tmp/deploy/sdk/yes/sysroots/x86_64-pokysdk-linux/usr/bin/aarch64-poky-linux/aarch64-poky-linux-gdb with any name

    4. CMake -> it might be auto detected, in case if not add the path rpi-build/tmp/deploy/sdk/yes/sysroots/x86_64-pokysdk-linux/usr/bin/cmake

    5. Kits -> add the previous setups with:
      Device type -> Generic Linux Device
      sysroot -> path rpi-build/tmp/deploy/sdk/yes/sysroots/aarch64-poky-linux
      QT mkspec -> linux-oe-g++

Creating Qt project with C++

  1. Create new project as Application -> Qt Widgets Application
  2. When it comes to Kit Selection choose your pc and your device, if your pc is not listed add it from devices window
  3. Following the steps will create main.cpp which is the whole project main function, source/header and ui files for your main class and .pro file which configure your project
  4. The pro file is updated automatically on each file creation/deletion. You will only need to add the remote executable path where your application is going to be deployed in your image as
	target.path = /home/root/app
	INSTALLS += target
  1. Executing system commands may require root permessions on pc such as mount, mkdir, date.. etc. You can launch your application as sudoer to avoid this problem in testing your application sudo qtcreator
  2. In my Qt project there is a configuration file targetconfiguration.h to specify on each target the application is going to run because of some commands that don't run on both

Running multimedia Mp3 and Mp4

  1. Qt helpful classes for Mp3 are QMediaPlayer and QMediaPlaylist
  2. Qt helpful classes for Mp4 are QGraphicsScene, QGraphicsVideoItem, QMediaPlayer and QMediaPlaylist
  3. Using QMediaPlayer module requires some packages, make sure they are installed
$ sudo apt-get install qtmultimedia5-dev libqt5multimediawidgets5 libqt5multimedia5-plugins libqt5multimedia5
  1. Make sure that qmake selected in Qt version for your PC is Qt5 not Qt4 /usr/lib/qt5/bin/qmake
  2. Clean your project, add QT += multimedia multimediawidgets to your .pro file and run qmake again (right click on your project)
  3. Qt media moudles rely on GStreamer, make sure that it's enabled as mentioned in Adding Sound section

Conclusion

  • Applied features:

    1. Mp3 Player (.mp3 files)
    2. Mp4 Player (.mp4 files)
    3. Bluetooth connection (Audio streaming)
    4. Settings Panel (Dark theme and date/time)
  • Audio streaming via bluetooth and setting time/date are not working on RPI due to previous mentioned issues

  • The image selection may not be the best for the issues I faced, you can try another with the same configuartions

  • I tried to go with rpi-basic-image but after building I got the following warning

The image 'rpi-basic-image' is deprecated, please use 'core-image-base' instead

References

  1. Qt Documentation
  2. Using Qt Creator to cross-compile and debug Raspberry Pi Qt5 apps
  3. Qt C++ GUI Tutorial for Beginners
  4. Intel Edison audio output to bluetooth speaker

About

Building infotainment system using the Yocto project


Languages

Language:BitBake 66.2%Language:PHP 9.7%Language:C 8.2%Language:Shell 7.5%Language:Roff 3.7%Language:C++ 1.9%Language:Makefile 0.8%Language:M4 0.8%Language:Python 0.5%Language:NASL 0.2%Language:BlitzBasic 0.2%Language:Assembly 0.1%Language:Pawn 0.1%Language:Perl 0.1%Language:QMake 0.0%Language:HTML 0.0%Language:Lua 0.0%