Changes

Jump to: navigation, search
no edit summary
{{AppliesToAxel}}
{{AppliesToAxelLite}}
{{AppliesToAXEL Lite AN}}
{{AppliesToSBCX}}
{{InfoBoxBottom}}
{{WarningMessage|text=This application note was validated against specific versions of the kit only. It may not work with other versions. Supported versions are listed in the ''History'' section.}}
== History ==
{| class="wikitable" border="1"
|Update for XELK 2.0.0 release
|-
|[httphttps://www.dave.eu/siteslinks/defaultp/files/files/an-xelk-001-amp-linux-freertos.pdf 0qKejH20HFSu3oWn 0.9.3]
|April 2015
|2.0.0
|April 2018
|2.1.0
|wiki versionUpdate for '''amp-feat-2.1.0-amp''' branch|-|1.0.1|October 2018|2.1.0|Minor improvements|-|1.0.2|October 2018|2.1.0|Added some details about <code>latencystat</code> test application
|}
==Introduction==
This application note describe how to build the software components required to set up asymmetric multi-processing (AMP for short) configuration required to run Linux OS on first Cortex®-A9 core and FreeRTOS on second Cortex®-A9 core of the Freescale i.MX6 SOC.
The following configuration required to run Linux OS on first Cortex®-A9 core and FreeRTOS on second Cortex®-A9 core of the Freescale i.MX6 SOC.
* '''N.B.''' For the sake of simplicity, in this application note, we are going to use two of the four core inside the iMX6Q cpu. Other configuration are possible but are not relevant for this demo.
The latencystat demo is a RPMsg-based application that exploits sophisticated techniques to handle inter-processors communication and synchronization.
These architectures allows the implementation of processing schemes that were not feasible with traditional single-core CPUs. Among these, one of the most interesting is asymmetric multiprocessing (AMP for short). This configuration permits to address several requirements that the embedded system developers struggle to handle in case of single-core systems.
This application note describes in detail the implementation of Linux/FreeRTOS asymmetric multiprocessing configuration on DAVE Embedded Systems AXEL LITE SoM. This configuration is a typical example about how to leverage AMP flexibility to combine, on one single piece of silicon, the versatility of Linux o.s. for general purpose computation, connectivity and HMI and the determinism of an RTOS to satisfy real-time constraints. Since AXEL family products are all based on Freescale i.MX6 processors, what is described here described applies to AXEL ULTRA too.
As known, AMP allows a multicore system to run simultaneously[1] multiple Operating Systems (OS) that are independent of each other. In other words, each core has its own private memory space, which contains the OS and the applications that are to run on that core. In addition, there can be some shared memory space that is used for inter-core communication. This is in contrast to Symmetric Multiprocessing (SMP), in which one OS runs on multiple cores using a public shared memory space.
Thanks to AMP, developers can use open-source Linux and FreeRTOS operating systems and the RPMsg Inter Processor Communication (IPC) framework to quickly implement applications that need to deliver deterministic, real-time responsiveness for markets such as automotive, industrial and others with similar requirements, while preserving the openness of Linux.
[1] This is true simultaneity because multiple instructions are executed at the same time
The following picture depicts the structure of the system.
 
[[File:XELK-amp-config.png|thumb|center|400px|AMP configuration]]
 
Core #0:
* takes care of boot process
* once Linux gets control of the processor, initializes core #1 in SMP mode
* stops core #1 and switches it to AMP mode
* loads binary image of FreeRTOS that is then executed by core #1
 
[1] This is true simultaneity because multiple instructions are executed at the same time.
=== Inter-core communication ===
Inter-core communication is based on RPMsg framework2framework (please refer to http://omappedia. The adoption of a standardized org/wiki/Category:RPMsg and mainlined protocol improves dramatically the portability and the maintainability of the application codehttps://www.kernel.org/doc/Documentation/rpmsg.txt for more details).
The adoption of a standardized and mainlined protocol improves dramatically the portability and the maintainability of the application code. On Linux kernel, this framework is supported by the kernel 3.10.17_GA – released by Freescale itself along with L3.10.17_1.0.0_IMX6QDLS_BUNDLE BSP – upon which the XELK 2.02.0 is based.
The picture below shows how the system memory is fragmented. The portion of memory used to create a shared area between the two cores – ring buffers – is allocated inside the 256 MByte region used by FreeRTOS.
DAVE Embedded Systems provides all the customization required (in particular at bootloader and Linux kernel levels) to enable customers use the standard i.MX6 development tools for building all the firmware/software components that will run on the target system.
 
In order to be able to compile the software required in this demo, it is necessary to:
 
* extract the *.ova inside the SDcard
* install the VM in Virtualbox
* boot the Virtual machine and run the following comand
 
dvdk@dvdk:~$ sh sdk-mount.sh xelk
Please refer to the [[Axel_Embedded_Linux_Kit_(XELK)#Quick_start_guide | XELK Quick Start Guide]] for further details on XELK.
* cloning the <code>FreeRTOS</code> repository:
<pre class="board-terminal">
dvdk@dvdk:~/xelk$ git clone git@git.dave.eu :dave/axel/freertos.git
</pre>
* cloning the <code>latencystat</code> repository:
<pre class="board-terminal">
dvdk@dvdk:~/xelk$ git clone git@git.dave.eu :dave/axel/latencystat.git
</pre>
The file <code>arch/arm/boot/uImage</code> is the binary image of the kernel that must be used to boot the system, together with the file <code>arch/arm/boot/dts/imx6q-xelk-l.dtb</code>, which is the binary image of the device tree with the XELK hardware configuration.
The following kernel modules, resulting from for the kernel build procedureAMP application, must should be copied from the building directory to the installed on root -file system (usually into : this can be easily done using the <code>/lib/modules/<kernel version>/kernelmodules_install</code>, but any other directory can be used):make parameter
<preclass="board-terminal"> LD [M] driversdvdk@dvdk:~/remoteprocxelk/remoteproclinux-2.ko LD [M] drivers6-imx$ sudo chmod go+rwx /home/dvdk/xelk/remoteprocrfs/mx6_remoteproc.ko LD [M] driversaxel-base/rpmsglib/rpmsg_freertos_statistic.komodules LD [M] driversdvdk@dvdk:~/rpmsgxelk/virtio_rpmsg_buslinux-2.ko LD [M] drivers6-imx$ make INSTALL_MOD_PATH=/home/virtiodvdk/virtio.ko LD [M] driversxelk/virtiorfs/virtio_ring.koaxel-base modules_install
</pre>
 
<b>N.B.</b> the previous commands assume that the XELK root file system used is <code>axel-base</code> installed on XELK VM (i.e. <code>/home/dvdk/xelk/rfs/axel-base</code>)
=== Build FreeRTOS ===
For building the FreeRTOS, a proper toolchain has to be used, then for example, the official arm Linux toolchain [https://developer.arm.com/open-source/gnu-toolchain/gnu-rm/downloads ref]. Specifically, the example here described was tested with the <code>7-2017-q4-major</code>, which is available for download [https://armkeil.blob.core.windows.net/developer/Files/downloads/gnu-rm/7-2017q4/gcc-arm-none-eabi-7-2017-q4-major-linux.tar.bz2 here]. To install it, just decompress the archive. Once the toolchain is downloaded and installed, enter the following commandsto set up the cross-building environment accordingly:
<pre class="board-terminal">
</pre>
and then Then run <code>make</code> to build the RTOS binary image:
<pre class="board-terminal">
dvdk@dvdk:~/xelk/freertos$ make
</pre>
This command will build the FreeRTOS kernel and an example application, named <code>Rpmsg-Demo</code>.
The output of When the build process is completede, the example application executable is contained into in the directory <code>output/mx6dq/Rpmsg-Demo/axellite_rev_a/Rpmsg-Demo.elf</code> (N.B: In order to run this application on the elf file must be usedtarget, not the bin) e must be renamed as <code>freertosRpmsg-Demo.elf</code> and installed into * has to be copied to the <code>/lib/firmware</code> directory of the target's root file system* it must be renamed as <code>freertos</code>.
=== Building latencystat ===
For building the <code>latercystat</code> example, enter the <code>latecystat</code> directory and then una <code>make</code>:
<pre class="board-terminal">
dvdk@dvdk:~/xelk$ source ~/xelk/env.sh
dvdk@dvdk:~/xelk$ cd latencystat
dvdk@dvdk:~/xelk/latencystat$ make
The resulting binary must be copied from the building directory to the root file system, e.g. on the <code>/home/root</code> directory of the root-file system.
=== Running the AMP example application on the target ===
As stated before, this example shows a sophisticated approach that allows for:
* using a standardized communication channel between the two cores
Move the device tree binary load address (the default 0x18000000 conflicts the AMP kernel loadaddr, it must be moved to a higher address) by changing u-boot environment for example as:
<pre>
=U-Boot > setenv fdtaddr 0x1c000000</pre> Moreover, it is possible to force the linux kernel to use only 2 CPUs adding the <code>maxcpus</code> parameter (i.e. on ''addmisc''):<pre>U-Boot > setenv addmisc 'setenv bootargs ${bootargs} vmalloc=400M ${mtdparts}\\;${mtdparts_spi} maxcpus=2'
</pre>
For a complete uboot enviromente refert to this: <pre class="mw-collapsible mw-collapsed wikitable">U-Boot > printenvaddcons=setenv bootargs ${bootargs} console=ttymxc2,115200n8adddisp0=setenv bootargs ${bootargs} video=mxcfb0:dev=lcd,LCD-AM-800480STMQW-TA1,if=RGB666addhdmi=setenv bootargs ${bootargs} video=mxcfb0:dev=hdmi,1920x1080M@60,bpp=32addip=setenv bootargs ${bootargs} ip=${ipaddr}:${serverip}:${gatewayip}:${netmask}:${hostname}:${netdev}:off panic=1 fec_mac=${ethaddr}addlvds0=setenv bootargs ${bootargs}video=mxcfb0:dev=ldb,LDB-AM-800480STMQW-TA1,if=RGB666 ldb=sin0addlvds1=setenv bootargs ${bootargs}video=mxcfb0:dev=ldb,LDB-AM-800480STMQW-TA1,if=RGB666 ldb=sin1addmisc=setenv bootargs ${bootargs} vmalloc=400M ${mtdparts}\\;${mtdparts_spi} maxcpus=2baudrate=115200bootcmd=mmc dev 0;mmc rescan;if run loadbootscript; then run bootscript; else run mmcboot ; fi; run net_nfsbootdelay=3bootfile=xelk/axel-lite/uImagebootscript=echo Running bootscript from mmc ...; sourcedisable_giga=1ethact=FECethaddr=00:50:c2:1e:af:ccethprime=FEC0fdt_high=FFFFFFFFfdtaddr=0x1c000000fdtfile=xelk/axel-lite/imx6q-xelk-l.dtbhostname=xelkipaddr=192.168.0.154load=tftp ${loadaddr} ${uboot}loadaddr=0x12000000loadbootscript=fatload mmc 0:1 ${loadaddr} ${script};loadfdt=tftpboot ${fdtaddr} ${serverip}:${fdtfile}loadk=tftpboot ${loadaddr} ${serverip}:${bootfile}mmcargs=setenv bootargs root=${mmcroot}mmcboot=run mmcargs addcons addmisc adddisp0 mmcloadk; bootm ${loadaddr}mmcloadk=fatload mmc 0:1 ${loadaddr} uImagemmcroot=/dev/mmcblk0p2 rootwait rwmodule_id#=0x3mtdids=nand0=gpmi-nandmtdparts=mtdparts=gpmi-nand:8M(nand-uboot),1M(nand-env1),1M(nand-env2),1M(nand-dtb),1M(nand-spare),8M(nand-kernel),-(nand-ubi)mtdparts_spi=spi32766.0:1M(spi-uboot),256k(spi-env1),256k(spi-env2),512k(spi-dtb),6M(spi-kernel),-(spi-free)net_nfs=run loadk loadfdt nfsargs addip addcons addmisc adddisp0; bootm ${loadaddr} - ${fdtaddr}netdev=eth0netmask=255.255.255.0nfsargs=setenv bootargs root=/dev/nfs rw nfsroot=${serverip}:${rootpath},v3,tcprootpath=/home/dvdk/xelk/rfs/axel-basescript=boot.scrserverip=192.168.0.153spi_update=sf probe; sf erase 0 80000;sf write ${loadaddr} 400 80000stderr=serialstdin=serialstdout=serialuboot=axel/u-boot.imxver=U-Boot 2013.04 (Nov 21 2014 - 16:21:37)-xelk-2.0.0 Environment size: 2303/262139 bytesU-Boot ></pre>Once all the components are built, please boot the system and launch the following commands:./
<pre class="board-terminal">
echo "start remote proc AMP"
insmod modprobe virtio.koinsmod modprobe virtio_ring.koinsmod modprobe virtio_rpmsg_bus.koinsmod modprobe remoteproc.koinsmod modprobe mx6_remoteproc.koinsmod modprobe rpmsg_freertos_statistic.ko
echo "everything done"
echo "now Linux is running with $(cat /proc/cpuinfo | grep processor | wc -l) processors"
</pre>
It is worth remembering that the previous commands load the required drivers to run the AMP configuration. Specifically, they:
*Release one of the Cortex A9 cores; the released core will be used to run the FreeRTOS-based example application
*Set up the RPmsg communication channel between the Linux kernel and the FreeRTOS kernel
*Load the code of the FreeRTOS-based example application into SDRAM memory (the code is retrieved from the <code>/lib/freertos</code> ELF file)
*Set up the devoted core to run the FreeRTOS-based example application.
Then On Linux side, run the <code>latencystat</code> application as shown below. <code>latencystat</code> application will communicate with the firmware running on the FreeRTOS-dedicated core through RPMsg. The typical output will look like this:
<pre class="board-terminal">
root@axel-lite:~# ./latencystat -b
Linux FreeRTOS AMP Demo.
0: Command 0 ACKed 1: Command 1 ACKed
Waiting for samples...
2: Command 2 ACKed 3: Command 3 ACKed 4: Command 4 ACKed
-----------------------------------------------------------
Histogram Bucket Values:
Bucket 323 393 ns (36 26 ticks) had 38 1 frequency Bucket 409 ns (27 ticks) had 475 frequency Bucket 341 424 ns (38 28 ticks) had 299 1058 frequency Bucket 512 439 ns (57 29 ticks) had 1 57 frequency Bucket 746 681 ns (83 45 ticks) had 1 frequency
-----------------------------------------------------------
Histogram Data:
min: 323 393 ns (36 26 ticks) avg: 332 409 ns (37 27 ticks) max: 746 681 ns (83 45 ticks) out of range: 0 total samples: 3391592
-----------------------------------------------------------
</pre>
 This application is extremely useful for evaluating measuring interrupt latency and for verifying how it is affected by relevant parameters such as the CPU load on the first core, memory bandwidth utilization, the amount/rate of interrupts to be processed by the first core affects IRQ , operating frequency, etc. For instance, the previous data refer to the following configuration:*[[FAQs_(Axel)#Q:_How_can_I_change_the_CPU_clock_frequency.3F|governor]]: <code>userspace</code>*nominal operating frequency: 800 MHz (actual: 792 MHz)*core #0 (running Linux) lightly loaded with minimal I/O activity.  In general, it is strongly recommended to characterize the latencyon the basis of a '''realistic testbed that is as close as possible to the actual use case'''. In It is also worth remembering that, in case of latency does not satisfy the application's real-time requirements, it may be necessary is possible to adjust the arbitration priorities of processor's interconnect subsystemto reduce it.
8,184
edits

Navigation menu