Wiki

This version (06 Oct 2022 09:46) was approved by Ramona Bolboaca.

IIO DEMO project

IIO DEMO Overview

IIO DEMO project is independent of a physical device and should be used as reference, when creating a new iio application for a new iio device.

IIO DEMO project emulates two devices: 1 16-bit ADC and 1 16-bit DAC by using two emulated drivers: adc_demo and dac_demo.

ADC Demo Driver

ADC Demo Driver Source Code

The source code for ADC Demo driver can be found here:

ADC Demo Code Driver Documentation

Source code documentation for the driver is automatically generated using the Doxygen tool and it is available below:

DAC Demo Driver

DAC Demo Driver Source Code

The source code for DAC Demo driver can be found here:

DAC Demo Code Driver Documentation

Source code documentation for the driver is automatically generated using the Doxygen tool and it is available below:

ADC IIO Demo Driver

ADC IIO Demo Driver Source Code

ADC IIO Demo Code Driver Documentation

Source code documentation for the driver is automatically generated using the Doxygen tool and it is available below:

DAC IIO Demo Driver

DAC IIO Demo Driver Source Code

The source code for DAC IIO Demo driver can be found here:

DAC IIO Demo Code Driver Documentation

Source code documentation for the driver is automatically generated using the Doxygen tool and it is available below:

No-OS Supported Platforms

The following platforms are supported:

  • STM32
  • ADUCM3029
  • XILINX
  • LINUX
  • PICO

No-OS Build Setup

No-OS Clone

NOTE: This build guide is valid for the projects found in the no-OS/projects folder. If your project resides elsewhere under the no-OS repository tree, it is a legacy project. A build guide for legacy projects can be found Build no-OS with GNU make.

Clone NO-OS with the --recursive flag:

git clone --recursive https://github.com/analogdevicesinc/no-OS

If however you've already cloned NO-OS without the --recursive flag, you may initialize all the submodules in an existing NO-OS clone with:

git submodule update --recursive --init

→ Read more...

No-OS Build Prerequisites

Please follow the steps below for No-OS Setup based on the environment you are using. Make sure you use the information for the specific platform you are using (e.g. STM32, ADUCM3029, etc.).

Prior to building a no-OS project, it is required to set up some environment variables so that the build process may find the necessary tools (compiler, linker, SDK etc.).

Use the following commands to prepare your environment for building no-OS projects:

Linux (Click to expand)

Linux (Click to expand)

Make sure the GNU Make version you are using is >= 4.2.

Intel (Click to expand)

Intel (Click to expand)

Assuming the SDK is installed at this path:

/path/to/intel
└── intelFPGA
    └── 18.1

Run:

$ source no-OS/tools/scripts/platform/intel/environment.sh /path/to/intel/intelFPGA 18.1

Xilinx (Click to expand)

Xilinx (Click to expand)

Assuming the Vitis 2022.2 is installed at this path:

/path/to/xilinx
├── DocNav
├── Downloads
└── Vitis
    └── 2022.2

Run:

$ source /path/to/xilinx/Vitis/2022.2/settings64.sh

STM32 (Click to expand)

STM32 (Click to expand)

  • Install stm32cubeide to default location /opt/stm32cubeide. If you'd rather install it at a different location, run export STM32CUBEIDE=/path/to/your/stm32cubeide in the terminal used for building.
  • Install stm32cubemx to default location /opt/stm32cubemx. If you'd rather install it at a different location, run export STM32CUBEMX=/path/to/your/stm32cubemx in the terminal used for building.
  • Currently we are testing projects with CubeMx Version 6.5.0, but other versions should work as well.
  • Install java (openjdk-17), sed and head (if not already present, they normally are).
  • Install python (if not already present) and make sure python command executes Python3 (not Python2). This can be easily achieved by running the following command sudo apt install python-is-python3.

Maxim (Click to expand)

Maxim (Click to expand)

  • Install the Maxim Micros SDK.
  • Set the MAXIM_LIBRARIES environment variable to the MaximSDK/Libraries path (the default should be ~/MaximSDK/Libraries).
  • For visual debugging and building, install Visual Studio Code, and the Cortex-Debug extension.

Mbed (Click to expand)

Mbed (Click to expand)

  • Install Mbed CLI 1 as per guide here: https://os.mbed.com/docs/mbed-os/v6.15/build-tools/install-and-set-up.html .Usually the following steps should be sufficient: sudo apt install python3 python3-pip git mercurial gcc-arm-none-eabi and sudo python3 -m pip install mbed-cli pyelftools==0.29.
  • Configure the compiler location with Mbed CLI. This can be carried out by running the “mbed config -G GCC_ARM_PATH “path-to-your-gcc-compiler”” in Command Prompt.

Pico (Click to expand)

Pico (Click to expand)

  • Set the PICO_SDK_PATH environment variable to the pico-sdk cloned repository path.
  • Install the J-Link software
  • Set the JLINK_SERVER_PATH environment variable to the JLinkGDBServerCLExe path (the default path should be /opt/SEGGER/JLink/JLinkGDBServerCLExe).
  • For visual debugging and building, install Visual Studio Code, and the Cortex-Debug extension.

ADuCM3029 (Click to expand)

ADuCM3029 (Click to expand)

Please install all the necessary packs locally and then manually import them in CrossCore

Common Issues with environment setup:

  • Makefiles searches for the CCES_HOME in its default installation directory. It may happen that multiple version are installed and may not work. To select a CCES_HOME run export CCES_HOME=/opt/analog/cces/2.10.0

Windows (Click to expand)

Windows (Click to expand)

Open up a Git Bash as Administrator once and run the tools/scripts/git-bash.sh script. Close the window. You only need to do this once per Git Bash installation.
Use Git Bash (unelevated) for the rest of your development.

Xilinx (Click to expand)

Xilinx (Click to expand)

Assuming the Vitis 2022.2 is installed at this path:

C:\Xilinx
├── DocNav
├── Downloads
└── Vitis
    └── 2022.2

Run:

$ export PATH=/c/Xilinx/Vitis/2022.2/bin:/c/Xilinx/Vitis/2022.2/gnu/aarch64/nt/aarch64-none/bin/:$PATH

Maxim (Click to expand)

Maxim (Click to expand)

  • Install the Maxim Micros SDK to a path without whitespaces like C:\MaximSDK.
  • Set the MAXIM_LIBRARIES environment variable by running: export MAXIM_LIBRARIES=/c/MaximSDK/Libraries.
  • (Optional) For visual debugging and building, install Visual Studio Code, and the Cortex-Debug extension.

ADuCM3029 (Click to expand)

ADuCM3029 (Click to expand)

No-OS Build Project

The path of the project is no-OS/projects/iio_demo/

Go in the project directory that should be built.

Linux (Click to expand)

Linux (Click to expand)

$ cd no-OS/projects/project_name/
$ tree
.
├── builds.json
├── Makefile
├── src
└── src.mk

Intel (Click to expand)

Intel (Click to expand)

Copy the .sof and .sopcinfo to the project folder.

$ ls
Makefile  profiles  src  src.mk  system_bd.sopcinfo  adrv9009_a10gx.sof	
$ make

# Alternatively you may select a .sopcinfo file explicitly by:
$ make HARDWARE=path/to/system_bd.sopcinfo

Xilinx (Click to expand)

Xilinx (Click to expand)

Copy the .xsa in the project folder.

$ ls
Makefile  profiles  src  src.mk system_top.xsa
$ make

# Alternatively you may select an .xsa file explicitly by:
$ make HARDWARE=path/to/file.xsa

Maxim (Click to expand)

Maxim (Click to expand)

To build a project, type:

make PLATFORM=maxim TARGET=...

The TARGET specifies the chip for which the project is built. If it is missing, max32660 will be used. At the moment, the available targets are: max32650, max32655, max32660, max32665, max32670, max32690 and max78000.

Mbed (Click to expand)

Mbed (Click to expand)

To build a project, type:

make PLATFORM=mbed

Pico (Click to expand)

Pico (Click to expand)

To build a project, type:

make PLATFORM=pico

STM32 (Click to expand)

STM32 (Click to expand)

Make sure you have the .ioc file in the project directory, then type:

$ make PLATFORM=stm32

If during the project generation you get a dialog saying that you are using an .ioc file generated with an old CubeMX version, click Continue. Migrate is also a valid option but only if you know what you are doing.

If you're trying to use an .ioc file generated with a newer CubeMX than the one installed on your machine, you will get a prompt that asks you to upgrade your installation to the new version, there is no other choice than to click OK and then manually upgrade.

ADuCM3029 (Click to expand)

ADuCM3029 (Click to expand)

The ADuCM3029 projects also contain a pinmux_config.c file which contains pin configuration instructions.

# build an ADuCM3029-only project
$ make

# if the platform autodetection picks the wrong platform, explicitly specify the PLATFORM
$ make PLATFORM=aducm3029

Windows (Click to expand)

Windows (Click to expand)

Use Git Bash to run these commands.
$ cd no-OS/projects/project_name

It should contain make-related files and source files:

./no-OS/projects/project_name
├── builds.json
├── Makefile
├── src
└── src.mk

Xilinx (Click to expand)

Xilinx (Click to expand)

Copy the .xsa to the project folder and run:

./no-OS/projects/adrv9009
├── Makefile
├── profiles
├── src
├── src.mk
└── system_top.xsa

$ make

Maxim (Click to expand)

Maxim (Click to expand)

To build a project, type:

$ make PLATFORM=maxim TARGET=...

The TARGET specifies the chip for which the project is built. If it is missing, max32660 will be used. At the moment, the available targets are: max32650, max32655, max32660, max32665, max32670, max32690 and max78000.

ADuCM3029 (Click to expand)

ADuCM3029 (Click to expand)

$ export PLATFORM=aducm3029
$ make

The build process creates a build directory in the project folder:

build
├── app
├── bsp
├── obj
├── project_name.elf
└── tmp

Debug

Once the .elf, .hex or .bin file has been generated, make sure the board is powered on, JTAG cable connected and use the following commands to upload the program to the board or debug.

Uploading the binary to target is generically achieved with:

$ make run

Xilinx (Click to expand)

Xilinx (Click to expand)

For Xilinx project you can flash the board connected to a remote host. On the remote host make sure to start `hw_server`. On your development environment run

$ export XSCT_REMOTE_HOST=<remote host ip>
$ export XSCT_REMOTE_PORT=<remote host hw_server port>
$ make run

By default the `hw_server` port should be 3121.

Use the following command to launch the SDK associated to the used platform in order to be able to debug graphically by clicking the debug button:

$ make sdkopen

Fore more details about the available make rules, check out this page.

Running/Debugging in WSL

Example Project Execution on Linux

IIO Example

Because this project does not require any hardware, it can be run also locally on your Linux OS.

Makefile Selection

In order to build the IIO example project for a specific platform make sure you have the following configuration in the Makefile:

# Select the example you want to enable by choosing y for enabling and n for disabling
IIO_EXAMPLE = y
IIO_TRIGGER_EXAMPLE = n

When running make command, specify the platform you want to build it for, as shown below:

// ADUCM platform
make PLATFORM=aducm3029
// Linux platform
make PLATFORM=linux
// STM32 platform
make PLATFORM=stm32
// XILINX platform
make PLATFORM=xilinx
// PICO platform
make PLATFORM=pico

In this case, we are going to build the project for Linux platform, using the command:

no-OS/projects/iio_demo$ make PLATFORM=linux

Project Execution

After the build is successful we can run the application, using the command:

no-OS/projects/iio_demo$ ./build/iio_demo.out 

Now, by running iio_info in the Linux terminal, we can see the emulated IIO devices, as shown below:

no-OS/projects/iio_demo$ iio_info -u ip:127.0.0.1
Library version: 0.24 (git tag: 735ac65)
Compiled with backends: local xml ip usb serial
IIO context created with network backend.
Backend version: 1.1 (git tag: 0000000)
Backend description string: 127.0.0.1 no-OS analog 1.1.0-g0000000 #1 Tue Nov 26 09:52:32 IST 2019 armv7l
IIO context has 3 attributes:
	no-OS: 1.1.0-g0000000
	ip,ip-addr: 127.0.0.1
	uri: ip:127.0.0.1
IIO context has 2 devices:
	iio:device0: adc_demo (buffer capable)
		2 channels found:
			voltage0: adc_in_ch0 (input, index: 0, format: le:S16/16>>0)
			1 channel-specific attributes found:
				attr  0: adc_channel_attr value: 1111
			voltage1: adc_in_ch1 (input, index: 1, format: le:S16/16>>0)
			1 channel-specific attributes found:
				attr  0: adc_channel_attr value: 1112
		1 device-specific attributes found:
				attr  0: adc_global_attr value: 3333
		1 debug attributes found:
				debug attr  0: direct_reg_access value: 0
ERROR: checking for trigger : Invalid argument (22)
	iio:device1: dac_demo (buffer capable)
		2 channels found:
			voltage0: dac_out_ch0 (output, index: 0, format: le:S16/16>>0)
			1 channel-specific attributes found:
				attr  0: dac_channel_attr value: 1111
			voltage1: dac_out_ch1 (output, index: 1, format: le:S16/16>>0)
			1 channel-specific attributes found:
				attr  0: dac_channel_attr value: 1112
		1 device-specific attributes found:
				attr  0: dac_global_attr value: 4444
		1 debug attributes found:
				debug attr  0: direct_reg_access value: 0
ERROR: checking for trigger : Invalid argument (22)

It can be observed that two iio_devices are found: adc_demo and dac_demo. Each device has a device specific attribute (adc_demo: adc_global_attr and dac_demo: dac_global_attr) and a debug attribute for direct register access.

It can also be observed that each device has two voltage-type channels and each channel has a channel specific attribute:

  • adc_demo: adc_in_ch0, adc_in_ch1
  • dac_demo: dac_out_ch0, dac_out_ch1

If ENABLE_LOOPBACK is not defined in src/app_config.h, then a sine loop will be returned when reading a buffer from adc_demo device. This can be achieved using iio_readdev command or using IIO Osc.

iio_readdev -u ip:127.0.0.1 -b 400 -s 400 adc_demo > samples.dat

For IIO Osc, connect to the device and use the plot functionality to view the data, as shown below:

If ENABLE_LOOPBACK is defined in src/app_config.h, then the dac_demo device can also be used to upload data to the buffer used by adc_demo (the data given to the dac will be looped back to the adc device). If no data is loaded, the default data will be shown, which is 0. In order to write data to dac_demo, you can use either iio_writedev command or DAC Data Manager plugin from IIO Osc. When using iio_writedev, we can use iio_readdev to read back the data we wrote, as shown below:

// write 400 samples to dac
cat sample_sine.dat | iio_writedev -u ip:127.0.0.1 -b 400 -s 400   dac_demo
// read 400 samples from adc -> should be the same as the one we wrote previously 
iio_readdev -u ip:127.0.0.1 -b 400 -s 400 adc_demo > dac_samples.dat

For IIO Osc, connect to the device and use the DAC Data Manager to load data. Then use the plot functionality to view the loaded data. It can be seen how plotted data is changing when new data is loaded:

IIO Trigger Example

Makefile Selection

In order to build the IIO trigger example project for a specific platform make sure you have the following configuration in the Makefile:

# Select the example you want to enable by choosing y for enabling and n for disabling
IIO_EXAMPLE = n
IIO_TRIGGER_EXAMPLE = y

The following steps are perform on Linux platform.

By running iio_info, we can see the emulated IIO devices, as shown below:

no-OS/projects/iio_demo$ iio_info -u ip:127.0.0.1
Library version: 0.24 (git tag: 735ac65)
Compiled with backends: local xml ip usb serial
IIO context created with network backend.
Backend version: 1.1 (git tag: 0000000)
Backend description string: 127.0.0.1 no-OS analog 1.1.0-g0000000 #1 Tue Nov 26 09:52:32 IST 2019 armv7l
IIO context has 3 attributes:
	no-OS: 1.1.0-g0000000
	ip,ip-addr: 127.0.0.1
	uri: ip:127.0.0.1
IIO context has 3 devices:
	iio:device0: adc_demo (buffer capable)
		2 channels found:
			voltage0: adc_in_ch0 (input, index: 0, format: le:S16/16>>0)
			1 channel-specific attributes found:
				attr  0: adc_channel_attr value: 1111
			voltage1: adc_in_ch1 (input, index: 1, format: le:S16/16>>0)
			1 channel-specific attributes found:
				attr  0: adc_channel_attr value: 1112
		1 device-specific attributes found:
				attr  0: adc_global_attr value: 3333
		1 debug attributes found:
				debug attr  0: direct_reg_access value: 0
		No trigger assigned to device
	iio:device1: dac_demo (buffer capable)
		2 channels found:
			voltage0: dac_out_ch0 (output, index: 0, format: le:S16/16>>0)
			1 channel-specific attributes found:
				attr  0: dac_channel_attr value: 1111
			voltage1: dac_out_ch1 (output, index: 1, format: le:S16/16>>0)
			1 channel-specific attributes found:
				attr  0: dac_channel_attr value: 1112
		1 device-specific attributes found:
				attr  0: dac_global_attr value: 4444
		1 debug attributes found:
				debug attr  0: direct_reg_access value: 0
		No trigger assigned to device
	trigger0: adc-demo-sw-trig
		0 channels found:
		1 device-specific attributes found:
				attr  0: trigger_now ERROR: No such file or directory (2)
ERROR: checking for trigger : No such device (19)

It can be observed, that in this case a new device is available, adc-demo-sw-trig. This device can be used as a trigger to sample data from adc_demo device. This is a software trigger, meaning that the trigger is activated by software, when performing writes to its attribute. In this case the name of the attribute is trigger_now.

The writing to the trigger_now attribute can be performed using the iio_attr command as follows:

iio_attr -u ip:127.0.0.1 -d trigger0 trigger_now 1

This command will write the value 1 to the trigger_now attribute of trigger0 device and it will activate the trigger one time. If we want to obtain 10 samples, we need to run the command 10 times.

The following python script can be used to send automatically the iio_attr command:

import sys
import os

my_uri = sys.argv[1] if len(sys.argv) >= 3 else "ip:127.0.0.1"
my_samples = sys.argv[2] if len(sys.argv) >= 3 else 200

print("Executing trigger_now attribute for trigger0");
print("for uri: " + str(my_uri))
print("for " + str(my_samples) + " samples\n");
i = 0
while i < int(my_samples):
    i+=1
    os.system("iio_attr -u "+my_uri+" -d trigger0 trigger_now 1 \n")
    print("triggered "+str(i)+" times\n" )

Below, you can see an example with software trigger usage:

resources/eval/user-guides/iio_demo/no-os-setup.txt · Last modified: 06 Oct 2022 09:45 by Ramona Bolboaca