“IIO overview”的版本间的差异
Zhouyuebiao(讨论 | 贡献) |
|||
第1行: | 第1行: | ||
{{DISPLAYTITLE:IIO概述}} | {{DISPLAYTITLE:IIO概述}} | ||
+ | |||
+ | This article gives information about the Linux<sup>®</sup> IIO framework.<br /> | ||
+ | It explains how to activate the IIO interface and, based on examples, how to use it.<br /> | ||
+ | <br /> | ||
+ | |||
+ | ==Framework purpose== | ||
+ | |||
+ | '''IIO''' (Industrial I/O) is a subsystem for Analog to Digital Converters (ADCs), Digital to Analog Converters (DACs) and various types of sensors. It can be used on high speed, high data rates industrial devices. Until recently, it was mostly focused on user-space abstraction. It also includes in-kernel API for other drivers. | ||
+ | |||
+ | The Industrial I/O Linux<sup>®</sup> subsystem offers a unified framework to communicate (read and write) with drivers covering many different types of embedded sensors and a few actuators. It also offers a standard interface to user space applications manipulating sensors through sysfs and devfs. | ||
+ | |||
+ | Here are some examples of supported sensor types in IIO: | ||
+ | * ADC / DAC | ||
+ | * accelerometers | ||
+ | * magnetometers | ||
+ | * gyroscopes | ||
+ | * pressure | ||
+ | * humidity | ||
+ | * temperature | ||
+ | * light and proximity | ||
+ | |||
+ | IIO can be used in many different use cases, as mentioned in [[#How to use the framework|How to use the framework]] section: | ||
+ | * Low speed acquisition for slow varying input signal (example: log temperature to a file) | ||
+ | * High speed acquisition using [[ADC internal peripheral|ADC]], [[DFSDM internal peripheral|DFSDM]] or external devices (example: audio, power meter) | ||
+ | * Read the position of a rotary element using [[TIM internal peripheral|TIM]] or [[LPTIM internal peripheral|LPTIM]] quadrature encoder interface | ||
+ | * Driving an analog source through a [[DAC internal peripheral|DAC]] | ||
+ | * External devices connected via SPI or I2C. | ||
+ | |||
+ | ==System overview== | ||
+ | |||
+ | {{ | ||
+ | ImageMap|Image:IIO-overview.png {{!}} frame {{!}} center{{!}} IIO Implementation architecture | ||
+ | rect 340 125 464 158 [[IIO libiio|libiio]] | ||
+ | rect 829 180 954 213 [[IIO libiio|libiio]] | ||
+ | rect 268 270 582 308 [[#User_space_interface|User space interface]] | ||
+ | rect 614 366 741 397 [[#Kernel_space_interface|Kernel space interface]] | ||
+ | rect 585 305 698 361 [[#How_to_use_IIO_kernel_API|Kernel space user]] | ||
+ | rect 211 489 306 530 [[DAC Linux driver]] | ||
+ | rect 319 489 414 530 [[ADC Linux driver]] | ||
+ | rect 426 489 522 530 [[DFSDM Linux driver]] | ||
+ | rect 534 489 629 530 [[How to use the IIO user space interface#How to set up a TIM or LPTIM trigger using the sysfs interface | IIO timers triggers]] | ||
+ | rect 640 489 737 530 [[#How to write a kernel IIO device driver | kernel IIO device driver]] | ||
+ | rect 211 577 306 618 [[DAC internal peripheral]] | ||
+ | rect 319 577 414 618 [[ADC internal peripheral]] | ||
+ | rect 426 577 522 618 [[DFSDM internal peripheral]] | ||
+ | rect 534 577 629 618 [[:Category:Timers peripherals|Timer internal peripherals]] | ||
+ | rect 640 577 737 618 [[:Category:Low speed interface peripherals|I2C or SPI internal peripherals]] | ||
+ | }} | ||
+ | |||
+ | ===Components description=== | ||
+ | ''From client application to hardware'' | ||
+ | * '''Client Application''' (User Space): An application that configures, read or write data samples to/from ''IIO device(s)'' via [[IIO libiio|libiio]]. | ||
+ | |||
+ | * '''iiod server''' (User Space): It is optional. Applications based on libiio can benefit from a remote access via ''IIO Daemon'' server, to IIO "local" backend through a network link. | ||
+ | |||
+ | * '''libiio''' (User Space): [[IIO libiio | libiio]] is a complete library offering an API for developping an application. It's composed of a high-level API, and two backends: | ||
+ | # The “local” backend, interfacing with the Linux kernel through the IIO API | ||
+ | # The “network” backend, interfacing with the iiod server through a network link. | ||
+ | |||
+ | * '''User Space interface''': It is composed of a standard '''char device''', '''sysfs''', '''configfs''' and [[Debugfs|debugfs]] (see [[#API description|API description]]). | ||
+ | |||
+ | * '''Kernel Space user''': It can be any kernel space IIO consumer, like STM32 DFSDM audio driver or IIO hwmon driver (See [[#How_to_use_IIO_kernel_API|How to use IIO kernel API]]). | ||
+ | |||
+ | * '''Kernel Space interface''': It is composed of a standard [[#Kernel space interface|API]] | ||
+ | |||
+ | * '''IIO framework''' (Kernel Space): It's composed of a core. It manages data buffers, userspace events, triggers. It also handles clients (either in kernel or in User Space). | ||
+ | |||
+ | * '''IIO drivers''' (Kernel Space): Linux kernel drivers to handle internal peripherals or external devices. They includes an interface that provides controls and data to the user (examples: [[ADC Linux driver]], [[DAC Linux driver]], [[DFSDM Linux driver]], [[TIM Linux driver]], [[LPTIM Linux driver]], [[#How to write a kernel IIO device driver | IIO device driver]] connected on [[SPI overview| SPI]] or [[I2C overview | I2C]]). | ||
+ | |||
+ | * '''STM32 peripherals''' (Hardware): connected to the external devices through a specific interface (examples: [[ADC internal peripheral|ADC]], [[DAC internal peripheral|DAC]], [[DFSDM internal peripheral| DFSDM ]], [[TIM internal peripheral|TIM]], [[LPTIM internal peripheral|LPTIM]], [[SPI internal peripheral| SPI]], or [[I2C internal peripheral| I2C]]) | ||
+ | |||
+ | * '''External devices''' (Hardware): connected to the STM32 front-end through a specific interface. These can be analog devices (such as accelerometers, Inertial Measurement Units...), a Sigma Delta ADC Modulator (for audio record, energy measurements...), IIO devices on SPI or I2C... | ||
+ | |||
+ | === API description === | ||
+ | Depending on needs and location (Kernel Space or User Space), several APIs are available to control an IIO device. | ||
+ | |||
+ | ==== libiio ==== | ||
+ | [[IIO libiio | Libiio]] provides a user space high-level API for client applications<ref>[http://analogdevicesinc.github.io/libiio/ libiio High-Level API], libiio API Documentation (Library for interfacing with IIO devices)</ref>. The library abstracts the low-level details of the hardware, and provides a simple yet complete programming interface that can be used for advanced projects. | ||
+ | |||
+ | It is a wrapper on the ''user space interface'' (sysfs and char device) provided by the kernel. | ||
+ | |||
+ | ==== User space interface ==== | ||
+ | The IIO framework provides several interfaces: | ||
+ | * [https://www.kernel.org/doc/html/latest/driver-api/iio/core.html#iio-device-sysfs-interface '''iio device sysfs interface''']: It is used to '''configure which events and data''' should come out of the character device, e.g. ''/sys/bus/iio/devices/iio:deviceX''.<br/> It can be used to '''read''' (poll) or '''write data''' directly '''at low rates'''.<br/>The IIO sysfs ABI is documented in: ''Documentation/ABI/testing/sysfs-bus-iio''<ref>[https://www.kernel.org/doc/Documentation/ABI/testing/sysfs-bus-iio sysfs-bus-iio ABI], Linux standard sysfs IIO interface</ref>.<br/>See [[How to use the IIO user space interface]] and [[How to access information in sysfs]] for further details. | ||
+ | |||
+ | * '''character device'''<ref>[https://bootlin.com/doc/training/linux-kernel/linux-kernel-slides.pdf character device interface], ''Linux Kernel and Driver Development'' training document, see '''Character drivers''' and '''Kernel frameworks for device drivers''' chapter</ref>: It is optional in IIO. It is used to output '''events and sensor data''', e.g. ''/dev/iio:deviceX''.<br/> It is basically a file from application point of view. Standard file API allows to access it: open(), read(), write(), close()...<br/> See [[How to use the IIO user space interface#Convert one or more channels using triggered buffer mode|How to use triggered buffer mode]] and [https://www.kernel.org/doc/html/latest/driver-api/iio/buffers.html#iio-buffer-sysfs-interface The Linux driver implementer’s API guide - Industrial I/O Buffers] for further details. | ||
+ | |||
+ | * '''configfs''': It allows to configure additional IIO features like ''software and hrtimer triggers''.<br/>The IIO configfs interface is documented in: ''Documentation/ABI/testing/configfs-iio''<ref>[https://www.kernel.org/doc/Documentation/ABI/testing/configfs-iio configfs-iio ABI], Linux standard configfs IIO interface</ref> and ''Documentation/iio/iio_configfs.txt''<ref>[https://www.kernel.org/doc/Documentation/iio/iio_configfs.txt iio_configfs interface], Linux standard configfs interface</ref>.<br/>Note: STM32 already provides ''hardware triggers'' (See [[How_to_use_the_IIO_user_space_interface#How_to_set_up_a_TIM_or_LPTIM_trigger_using_the_sysfs_interface|How to use the IIO timers triggers]]). | ||
+ | |||
+ | * [[Debugfs]]: May provide some debug conveniences (like ''direct_reg_access'' entry to read/write registers) depending on the IIO device driver in use. | ||
+ | |||
+ | ==== Kernel space interface ==== | ||
+ | Useful kernel API for users: | ||
+ | *'''devm_iio_channel_get_all()''' or iio_channel_get_all() / iio_channel_release_all(): Used to lookup, get, then release IIO channels. | ||
+ | *'''iio_get_channel_type()''': get the type of a channel, such as IIO_VOLTAGE, IIO_TEMP... | ||
+ | *'''iio_read_channel_processed()''': read channel processed value, e.g. like in micro-volts for voltage, milli-degree for temperature... | ||
+ | *... | ||
+ | |||
+ | Available routines can be found in kernel header file: include/linux/iio/consumer.h<ref name="inkern">{{CodeSource | Linux kernel | include/linux/iio/consumer.h}}, IIO 'inkern' API</ref>. | ||
+ | |||
+ | ==Configuration== | ||
+ | |||
+ | ===Kernel configuration=== | ||
+ | IIO is activated by default in ST deliveries. Nevertheless, if a specific configuration is needed, this section indicates how IIO can be activated/deactivated in the kernel. | ||
+ | |||
+ | Activate IIO in kernel configuration with Linux Menuconfig tool: [[Menuconfig or how to configure kernel]] | ||
+ | |||
+ | Device Drivers ---> | ||
+ | '''<*> Industrial I/O support --->''' | ||
+ | '''[*] Enable buffer support within IIO''' | ||
+ | < > IIO callback buffer used for push in-kernel interfaces | ||
+ | '''<*> Industrial I/O HW buffering''' | ||
+ | '''<*> Industrial I/O buffering based on kfifo''' | ||
+ | < > Enable IIO configuration via configfs | ||
+ | '''[*] Enable triggered sampling support''' | ||
+ | (2) Maximum number of consumers per trigger | ||
+ | < > Enable software triggers support | ||
+ | Accelerometers ---> | ||
+ | Analog to digital converters ---> | ||
+ | Amplifiers ---> | ||
+ | Chemical Sensors ---> | ||
+ | Hid Sensor IIO Common ---- | ||
+ | SSP Sensor Common ---> | ||
+ | Digital to analog converters ---> | ||
+ | IIO dummy driver ---> | ||
+ | Frequency Synthesizers DDS/PLL ---> | ||
+ | Digital gyroscope sensors ---> | ||
+ | Health Sensors ---> | ||
+ | Humidity sensors ---> | ||
+ | Inertial measurement units ---> | ||
+ | Light sensors ---> | ||
+ | Magnetometer sensors ---> | ||
+ | Inclinometer sensors ---- | ||
+ | Triggers - standalone ---> | ||
+ | Digital potentiometers ---> | ||
+ | Pressure sensors ---> | ||
+ | Lightning sensors ---> | ||
+ | Proximity sensors ---> | ||
+ | Temperature sensors ---> | ||
+ | IIO supports several types of sensors and devices. User can select from there any driver among the supported devices. | ||
+ | |||
+ | Please refer to [[ADC Linux driver]], [[DAC Linux driver]], [[DFSDM Linux driver]], [[TIM Linux driver]], [[LPTIM Linux driver]] articles for each peripheral. | ||
+ | |||
+ | ===Device tree configuration=== | ||
+ | ''IIO bindings''<ref name="IIO bindings">{{CodeSource | Linux kernel | Documentation/devicetree/bindings/iio/iio-bindings.txt}}, Linux Foundation, IIO Generic DT bindings</ref> documentation deals with all required or optional IIO generic DT properties. | ||
+ | |||
+ | It also introduces '''IIO providers''' and '''IIO consumers'''.<br> | ||
+ | Example with STM32 ADC: | ||
+ | |||
+ | &adc { | ||
+ | {{highlight|adc2}}: adc@100 { {{highlight|/* IIO provider example */}} | ||
+ | ... | ||
+ | #io-channel-cells = <1>; | ||
+ | st,adc-channels = <{{highlight|12}}>; {{highlight|/* channel 12 in use */}} | ||
+ | }; | ||
+ | }; | ||
+ | / { | ||
+ | consumer_device { {{highlight|/* IIO consumer example */}} | ||
+ | io-channels = <{{highlight|&adc2 12}}>; | ||
+ | io-channel-names = "{{highlight|example}}"; {{highlight|/* IIO consumer driver side: '''devm_iio_channel_get'''(&dev, "example"); */}} | ||
+ | }; | ||
+ | |||
+ | iio-hwmon { {{highlight|/* iio_hwmon<ref name="iio_hwmon">{{CodeSource | Linux kernel | drivers/hwmon/iio_hwmon.c}} IIO HWMON, consumer driver example (kernel space)</ref> is another consumer example (See SENSORS_IIO_HWMON in [[Menuconfig or how to configure kernel|kernel configuration]]) */}} | ||
+ | compatible = "iio-hwmon"; {{highlight|/* See Documentation/devicetree/bindings/iio/iio-bindings.txt<ref name="IIO bindings"/>}} | ||
+ | io-channels = <{{highlight|&adc2 12}}>; | ||
+ | }; | ||
+ | }; | ||
+ | |||
+ | Detailed DT configuration for STM32 internal peripherals: | ||
+ | * [[ADC device tree configuration]] | ||
+ | * [[DAC device tree configuration]] | ||
+ | * [[DFSDM device tree configuration]] | ||
+ | * [[TIM device tree configuration]] | ||
+ | * [[LPTIM device tree configuration]] | ||
+ | |||
+ | Linux kernel provides many other supported devices<ref>{{CodeSource | Linux kernel | Documentation/devicetree/bindings/iio | Kernel DT documentation IIO bindings}}, Linux Foundation, IIO DT bindings documents included in the Kernel sources</ref> in '''Documentation/devicetree/bindings/iio''' directory. | ||
+ | |||
+ | == How to use the framework == | ||
+ | This section describes how to use the IIO framework from: | ||
+ | * User space interface: Please refer to [[IIO_libiio | libiio]] and [[IIO Linux kernel tools]] that run on top of '''sysfs''' and '''character device''' ([[How to use the IIO user space interface]]) | ||
+ | * Kernel space interface: [[#How to use IIO kernel API|How to use IIO kernel API]] | ||
+ | |||
+ | === How to use the IIO user space interface === | ||
+ | Please see examples based on the following use cases: | ||
+ | * How to read a data: [[How to use the IIO user space interface#How to do a simple ADC conversion using the sysfs interface|How to do a simple ADC conversion using the sysfs interface]] | ||
+ | * How to write a data: [[How to use the IIO user space interface#How to do a simple DAC conversion using the sysfs interface|How to do a simple DAC conversion using the sysfs interface]] | ||
+ | * How to setup a trigger source: [[How to use the IIO user space interface#How to set up a TIM or LPTIM trigger using the sysfs interface|How to set up a TIM or LPTIM trigger using the sysfs interface]] | ||
+ | * How to use a trigger source: [[How to use the IIO user space interface#How to perform multiple ADC conversions in triggered buffer mode|How to perform multiple ADC conversions in triggered buffer mode]] | ||
+ | * How to register on an event: [[How to use the IIO user space interface#How to get ADC analog watchdog events|How to get ADC analog watchdog events]] | ||
+ | * How to use quadrature encoder: [[How to use the IIO user space interface#How to use the quadrature encoder with the sysfs interface|How to use the quadrature encoder with the sysfs interface]] | ||
+ | |||
+ | === How to use IIO kernel API === | ||
+ | Several in-kernel drivers use [[#Kernel_space_interface|kernel IIO API]]. See HWMON client example for IIO devices, and STM32 DFSDM audio ALSA IIO client: | ||
+ | * iio_hwmon: ''drivers/hwmon/iio_hwmon.c''<ref name="iio_hwmon"/>. See also [[#Device Tree configuration|device tree configuration]] example to read voltage from ADC. | ||
+ | $ cat /sys/class/hwmon/hwmon0/in1_input | ||
+ | 1809 # '''iio_hwmon''' calls '''iio_read_channel_processed()''': ADC result is in mV. | ||
+ | * stm32-adfsdm: See [[DFSDM Linux driver]] and [[ALSA overview]] for further details | ||
+ | |||
+ | ==How to trace and debug the framework== | ||
+ | |||
+ | === How to trace with dynamic debug === | ||
+ | By default there is no kernel log that shows activity on IIO. However the user could enable dynamic debug for the IIO core and the IIO drivers. | ||
+ | {{Board$}} dmesg -n8 | ||
+ | {{Board$}} echo "file drivers/iio/* +p" > /sys/kernel/debug/dynamic_debug/control | ||
+ | {{Board$}} echo "file drivers/iio/adc/* +p" > /sys/kernel/debug/dynamic_debug/control | ||
+ | {{Board$}} echo "file drivers/iio/dac/* +p" > /sys/kernel/debug/dynamic_debug/control | ||
+ | |||
+ | See [[How to use the kernel dynamic debug|dynamic debug]] for more details. | ||
+ | |||
+ | === How to debug with debugfs === | ||
+ | |||
+ | IIO proposes an optional [[Debugfs|debugfs]] entry to access registers. | ||
+ | It is up to the IIO device driver to implement it (e.g. ''debugfs_reg_access()''). When it is available: | ||
+ | $ cd /sys/kernel/debug/iio/iio:deviceX | ||
+ | To read a register from the device: | ||
+ | $ echo [register offset] > direct_reg_access | ||
+ | $ cat direct_reg_access | ||
+ | 0xhhhh # Register content | ||
+ | To write a register: | ||
+ | $ echo [register offset] [register value] > direct_reg_access | ||
+ | |||
+ | ==To go further== | ||
+ | ===How to write a kernel IIO device driver=== | ||
+ | |||
+ | The Linux Kernel community provides all the documents needed to develop an IIO device driver : | ||
+ | * The Linux driver implementer’s API guide - Industrial I/O<ref>[https://www.kernel.org/doc/html/latest/driver-api/iio/index.html Industrial I/O], The Linux driver implementer’s API guide</ref>: This guide provides the API provided by kernel IIO core components. | ||
+ | * IIO staging documentation<ref>{{CodeSource | Linux kernel | drivers/staging/iio/Documentation | IIO staging documentation}}, Linux Foundation, IIO documents included in the Kernel sources</ref>, included in the Kernel sources ('''drivers/staging/iio/Documentation'''). | ||
+ | * Linux Kernel IIO dummy driver example source code<ref>{{CodeSource | Linux kernel | drivers/iio/dummy/iio_simple_dummy.c}}, Linux Foundation, IIO dummy driver example source code</ref>: Dummy driver source code, included in the kernel sources ('''drivers/iio/dummy/iio_simple_dummy.c'''). | ||
+ | |||
+ | ===Trainings documents=== | ||
+ | * IIO a new subsystem<ref>[https://archive.fosdem.org/2012/schedule/event/693/127_iio-a-new-subsystem.pdf IIO a new subsystem], Free Electrons, Presentation of Kernel IIO subsystem</ref> : Presentation of Kernel IIO subsystem | ||
+ | * Industrial I/O Subsystem: The Home of Linux Sensors<ref>[http://events.linuxfoundation.org/sites/events/files/slides/lceu15_baluta.pdf Industrial I/O Subsystem: The Home of Linux Sensors], Linux Foundation, IIO training</ref>: Why IIO? What is it? Sensor types... | ||
+ | * libiio<ref>[https://events.linuxfoundation.org/sites/events/files/slides/libiio_0.pdf libiio training], Linux Foundation, libiio training</ref> : Linux Foundation libiio training | ||
+ | * Software Defined Radio using the Linux Industrial IO framework<ref>[https://archive.fosdem.org/2015/schedule/event/iiosdr/attachments/slides/708/export/events/attachments/iiosdr/slides/708/fosdem_2015_iio_sdr.pdf Software Defined Radio using the Linux Industrial IO framework], Linux Foundation, User Guide describing how to implement an application by using Linux Industrial IO framework</ref> : User Guide describing how to implement an application by using Linux Industrial IO framework | ||
+ | * Linux Device Drivers, Third Edition<ref>[https://lwn.net/Kernel/LDD3/ Linux Device Drivers, Third Edition], Pdf book, Authors Jonathan Corbet, Alessandro Rubini, and Greg Kroah-Hartman </ref> : Reference book for linux device drivers development, for IIO see Chapter 3, Char Drivers. | ||
+ | |||
+ | ==References== | ||
+ | |||
+ | <references /> | ||
+ | |||
+ | <noinclude> | ||
+ | {{ArticleBasedOnModel | Framework overview article model}} | ||
+ | {{PublicationRequestId | 9282 | 2018-10-17 | BrunoB}} | ||
+ | |||
+ | [[Category:IIO|0]] | ||
+ | [[Category:Timers]] | ||
+ | </noinclude> | ||
+ | |||
+ | |||
[[Category:Linux_Operating_System]][[Category:Analog]][[Category:IIO]] | [[Category:Linux_Operating_System]][[Category:Analog]][[Category:IIO]] |
2020年5月6日 (三) 17:23的版本
This article gives information about the Linux® IIO framework.
It explains how to activate the IIO interface and, based on examples, how to use it.
目录
Framework purpose
IIO (Industrial I/O) is a subsystem for Analog to Digital Converters (ADCs), Digital to Analog Converters (DACs) and various types of sensors. It can be used on high speed, high data rates industrial devices. Until recently, it was mostly focused on user-space abstraction. It also includes in-kernel API for other drivers.
The Industrial I/O Linux® subsystem offers a unified framework to communicate (read and write) with drivers covering many different types of embedded sensors and a few actuators. It also offers a standard interface to user space applications manipulating sensors through sysfs and devfs.
Here are some examples of supported sensor types in IIO:
- ADC / DAC
- accelerometers
- magnetometers
- gyroscopes
- pressure
- humidity
- temperature
- light and proximity
IIO can be used in many different use cases, as mentioned in How to use the framework section:
- Low speed acquisition for slow varying input signal (example: log temperature to a file)
- High speed acquisition using ADC, DFSDM or external devices (example: audio, power meter)
- Read the position of a rotary element using TIM or LPTIM quadrature encoder interface
- Driving an analog source through a DAC
- External devices connected via SPI or I2C.
System overview
![](/images/9/92/IIO-overview.png)
Components description
From client application to hardware
- Client Application (User Space): An application that configures, read or write data samples to/from IIO device(s) via libiio.
- iiod server (User Space): It is optional. Applications based on libiio can benefit from a remote access via IIO Daemon server, to IIO "local" backend through a network link.
- libiio (User Space): libiio is a complete library offering an API for developping an application. It's composed of a high-level API, and two backends:
- The “local” backend, interfacing with the Linux kernel through the IIO API
- The “network” backend, interfacing with the iiod server through a network link.
- User Space interface: It is composed of a standard char device, sysfs, configfs and 调试文件系统(debugfs) (see API description).
- Kernel Space user: It can be any kernel space IIO consumer, like STM32 DFSDM audio driver or IIO hwmon driver (See How to use IIO kernel API).
- Kernel Space interface: It is composed of a standard API
- IIO framework (Kernel Space): It's composed of a core. It manages data buffers, userspace events, triggers. It also handles clients (either in kernel or in User Space).
- IIO drivers (Kernel Space): Linux kernel drivers to handle internal peripherals or external devices. They includes an interface that provides controls and data to the user (examples: ADC Linux driver, DAC Linux driver, DFSDM Linux driver, TIM Linux driver, LPTIM Linux driver, IIO device driver connected on SPI or I2C).
- STM32 peripherals (Hardware): connected to the external devices through a specific interface (examples: ADC, DAC, DFSDM , TIM, LPTIM, SPI, or I2C)
- External devices (Hardware): connected to the STM32 front-end through a specific interface. These can be analog devices (such as accelerometers, Inertial Measurement Units...), a Sigma Delta ADC Modulator (for audio record, energy measurements...), IIO devices on SPI or I2C...
API description
Depending on needs and location (Kernel Space or User Space), several APIs are available to control an IIO device.
libiio
Libiio provides a user space high-level API for client applications[1]. The library abstracts the low-level details of the hardware, and provides a simple yet complete programming interface that can be used for advanced projects.
It is a wrapper on the user space interface (sysfs and char device) provided by the kernel.
User space interface
The IIO framework provides several interfaces:
-
iio device sysfs interface: It is used to configure which events and data should come out of the character device, e.g. /sys/bus/iio/devices/iio:deviceX.
It can be used to read (poll) or write data directly at low rates.
The IIO sysfs ABI is documented in: Documentation/ABI/testing/sysfs-bus-iio[2].
See How to use the IIO user space interface and 如何在sysfs中访问信息 for further details.
-
character device[3]: It is optional in IIO. It is used to output events and sensor data, e.g. /dev/iio:deviceX.
It is basically a file from application point of view. Standard file API allows to access it: open(), read(), write(), close()...
See How to use triggered buffer mode and The Linux driver implementer’s API guide - Industrial I/O Buffers for further details.
-
configfs: It allows to configure additional IIO features like software and hrtimer triggers.
The IIO configfs interface is documented in: Documentation/ABI/testing/configfs-iio[4] and Documentation/iio/iio_configfs.txt[5].
Note: STM32 already provides hardware triggers (See How to use the IIO timers triggers).
- 调试文件系统(debugfs): May provide some debug conveniences (like direct_reg_access entry to read/write registers) depending on the IIO device driver in use.
Kernel space interface
Useful kernel API for users:
- devm_iio_channel_get_all() or iio_channel_get_all() / iio_channel_release_all(): Used to lookup, get, then release IIO channels.
- iio_get_channel_type(): get the type of a channel, such as IIO_VOLTAGE, IIO_TEMP...
- iio_read_channel_processed(): read channel processed value, e.g. like in micro-volts for voltage, milli-degree for temperature...
- ...
Available routines can be found in kernel header file: include/linux/iio/consumer.h[6].
Configuration
Kernel configuration
IIO is activated by default in ST deliveries. Nevertheless, if a specific configuration is needed, this section indicates how IIO can be activated/deactivated in the kernel.
Activate IIO in kernel configuration with Linux Menuconfig tool: Menuconfig or how to configure kernel
Device Drivers ---> <*> Industrial I/O support ---> [*] Enable buffer support within IIO < > IIO callback buffer used for push in-kernel interfaces <*> Industrial I/O HW buffering <*> Industrial I/O buffering based on kfifo < > Enable IIO configuration via configfs [*] Enable triggered sampling support (2) Maximum number of consumers per trigger < > Enable software triggers support Accelerometers ---> Analog to digital converters ---> Amplifiers ---> Chemical Sensors ---> Hid Sensor IIO Common ---- SSP Sensor Common ---> Digital to analog converters ---> IIO dummy driver ---> Frequency Synthesizers DDS/PLL ---> Digital gyroscope sensors ---> Health Sensors ---> Humidity sensors ---> Inertial measurement units ---> Light sensors ---> Magnetometer sensors ---> Inclinometer sensors ---- Triggers - standalone ---> Digital potentiometers ---> Pressure sensors ---> Lightning sensors ---> Proximity sensors ---> Temperature sensors --->
IIO supports several types of sensors and devices. User can select from there any driver among the supported devices.
Please refer to ADC Linux driver, DAC Linux driver, DFSDM Linux driver, TIM Linux driver, LPTIM Linux driver articles for each peripheral.
Device tree configuration
IIO bindings[7] documentation deals with all required or optional IIO generic DT properties.
It also introduces IIO providers and IIO consumers.
Example with STM32 ADC:
&adc { adc2: adc@100 { /* IIO provider example */ ... #io-channel-cells = <1>; st,adc-channels = <12>; /* channel 12 in use */ }; }; / { consumer_device { /* IIO consumer example */ io-channels = <&adc2 12>; io-channel-names = "example"; /* IIO consumer driver side: devm_iio_channel_get(&dev, "example"); */ }; iio-hwmon { /* iio_hwmon[8] is another consumer example (See SENSORS_IIO_HWMON in kernel configuration) */ compatible = "iio-hwmon"; /* See Documentation/devicetree/bindings/iio/iio-bindings.txt[7] io-channels = <&adc2 12>; }; };
Detailed DT configuration for STM32 internal peripherals:
- ADC device tree configuration
- DAC device tree configuration
- DFSDM device tree configuration
- TIM device tree configuration
- LPTIM device tree configuration
Linux kernel provides many other supported devices[9] in Documentation/devicetree/bindings/iio directory.
How to use the framework
This section describes how to use the IIO framework from:
- User space interface: Please refer to libiio and IIO Linux kernel tools that run on top of sysfs and character device (How to use the IIO user space interface)
- Kernel space interface: How to use IIO kernel API
How to use the IIO user space interface
Please see examples based on the following use cases:
- How to read a data: How to do a simple ADC conversion using the sysfs interface
- How to write a data: How to do a simple DAC conversion using the sysfs interface
- How to setup a trigger source: How to set up a TIM or LPTIM trigger using the sysfs interface
- How to use a trigger source: How to perform multiple ADC conversions in triggered buffer mode
- How to register on an event: How to get ADC analog watchdog events
- How to use quadrature encoder: How to use the quadrature encoder with the sysfs interface
How to use IIO kernel API
Several in-kernel drivers use kernel IIO API. See HWMON client example for IIO devices, and STM32 DFSDM audio ALSA IIO client:
- iio_hwmon: drivers/hwmon/iio_hwmon.c[8]. See also device tree configuration example to read voltage from ADC.
$ cat /sys/class/hwmon/hwmon0/in1_input 1809 # iio_hwmon calls iio_read_channel_processed(): ADC result is in mV.
- stm32-adfsdm: See DFSDM Linux driver and ALSA overview for further details
How to trace and debug the framework
How to trace with dynamic debug
By default there is no kernel log that shows activity on IIO. However the user could enable dynamic debug for the IIO core and the IIO drivers.
Board $> dmesg -n8 Board $> echo "file drivers/iio/* +p" > /sys/kernel/debug/dynamic_debug/control Board $> echo "file drivers/iio/adc/* +p" > /sys/kernel/debug/dynamic_debug/control Board $> echo "file drivers/iio/dac/* +p" > /sys/kernel/debug/dynamic_debug/control
See dynamic debug for more details.
How to debug with debugfs
IIO proposes an optional 调试文件系统(debugfs) entry to access registers. It is up to the IIO device driver to implement it (e.g. debugfs_reg_access()). When it is available:
$ cd /sys/kernel/debug/iio/iio:deviceX
To read a register from the device:
$ echo [register offset] > direct_reg_access $ cat direct_reg_access 0xhhhh # Register content
To write a register:
$ echo [register offset] [register value] > direct_reg_access
To go further
How to write a kernel IIO device driver
The Linux Kernel community provides all the documents needed to develop an IIO device driver :
- The Linux driver implementer’s API guide - Industrial I/O[10]: This guide provides the API provided by kernel IIO core components.
- IIO staging documentation[11], included in the Kernel sources (drivers/staging/iio/Documentation).
- Linux Kernel IIO dummy driver example source code[12]: Dummy driver source code, included in the kernel sources (drivers/iio/dummy/iio_simple_dummy.c).
Trainings documents
- IIO a new subsystem[13] : Presentation of Kernel IIO subsystem
- Industrial I/O Subsystem: The Home of Linux Sensors[14]: Why IIO? What is it? Sensor types...
- libiio[15] : Linux Foundation libiio training
- Software Defined Radio using the Linux Industrial IO framework[16] : User Guide describing how to implement an application by using Linux Industrial IO framework
- Linux Device Drivers, Third Edition[17] : Reference book for linux device drivers development, for IIO see Chapter 3, Char Drivers.
References
- ↑ libiio High-Level API, libiio API Documentation (Library for interfacing with IIO devices)
- ↑ sysfs-bus-iio ABI, Linux standard sysfs IIO interface
- ↑ character device interface, Linux Kernel and Driver Development training document, see Character drivers and Kernel frameworks for device drivers chapter
- ↑ configfs-iio ABI, Linux standard configfs IIO interface
- ↑ iio_configfs interface, Linux standard configfs interface
- ↑ include/linux/iio/consumer.h| |}} include/linux/iio/consumer.h , IIO 'inkern' API
- ↑ 7.07.1 Documentation/devicetree/bindings/iio/iio-bindings.txt| |}} Documentation/devicetree/bindings/iio/iio-bindings.txt , Linux Foundation, IIO Generic DT bindings
- ↑ 8.08.1 drivers/hwmon/iio_hwmon.c| |}} drivers/hwmon/iio_hwmon.c IIO HWMON, consumer driver example (kernel space)
- ↑ Documentation/devicetree/bindings/iio | |}} Kernel DT documentation IIO bindings , Linux Foundation, IIO DT bindings documents included in the Kernel sources
- ↑ Industrial I/O, The Linux driver implementer’s API guide
- ↑ drivers/staging/iio/Documentation | |}} IIO staging documentation , Linux Foundation, IIO documents included in the Kernel sources
- ↑ drivers/iio/dummy/iio_simple_dummy.c| |}} drivers/iio/dummy/iio_simple_dummy.c , Linux Foundation, IIO dummy driver example source code
- ↑ IIO a new subsystem, Free Electrons, Presentation of Kernel IIO subsystem
- ↑ Industrial I/O Subsystem: The Home of Linux Sensors, Linux Foundation, IIO training
- ↑ libiio training, Linux Foundation, libiio training
- ↑ Software Defined Radio using the Linux Industrial IO framework, Linux Foundation, User Guide describing how to implement an application by using Linux Industrial IO framework
- ↑ Linux Device Drivers, Third Edition, Pdf book, Authors Jonathan Corbet, Alessandro Rubini, and Greg Kroah-Hartman
<securetransclude src="ProtectedTemplate:ArticleBasedOnModel" params="Framework overview article model"></securetransclude>
<securetransclude src="ProtectedTemplate:PublicationRequestId" params="9282 | 2018-10-17 | BrunoB"></securetransclude>