Applications - ADC

Last modified by Microchip on 2024/01/04 17:15


This topic is intended to be a quick start guide to the Analog-to-Digital (ADC) device on the ATSAMA5D2 Series MPU under Linux®.

The Industrial I/O (IIO) subsystem provides support for ADC and Digital-to-Analog (DAC) converters. Device driver support for the ATSAMA5D2 Series MPUs has been added to the mainline Linux source tree as of version 4.14 to provide software trigger, hardware trigger, and Direct Memory Access (DMA) support.

It is easy to access the ADC device in user space via sysfs or device node. The hands-on section of this topic explains how to access the ADC in user space.

Additional information on the ADC device of the ATSAMA5D2 Series MPUs can be found on the Linux4SAM website.


This application is developed for the ATSAMA5D27-SOM1-EK1 development platform:

This application is developed using the Buildroot build system.

Back to Top


For this application, you will be controlling a single ADC pin of the mikroBUS™ 1 expansion socket of the ATSAMA5D27-SOM1-EK1. The figure below shows the expansion capability of the SOM1-EK1.

Expansion features of the ATSAMA5D27-SOM1-EK1

You will control pin PD25 (ADC channel AD6) from the ATSAMA5D27 SOM1, which connects to J24 pin 1 of the mikroBUS 1 connector (labeled AN_mBUS1 on the schematic).

​For more details on the Package and Pinout of the SAMA5D2, refer to “Table 6-2. Pinouts” in the SAMA5D2 Series datasheet.

Schematic of mikrobus sockets on the ATSAMA5D27-SOM1-EK1

Back to Top

Buildroot Configuration

Objective: Using Buildroot, build a bootable image and Flash it onto an SD Memory Card for the ATSAMA5D27-SOM1-EK1 development board.

Follow the steps for building the image in the topic "Create Project with Default Configuration". In the topic, you will use the default configuration file: atmel_sama5d27_som1_ek_mmc_dev_defconfig

Back to Top

Device Tree

Objective: Observe how the peripheral I/O pins were configured as General Purpose Input/Output (GPIO) in the device tree. There may be one change needed in at91-sama5d27_som1_ek.dts file, as shown in line 313 below.

Once Buildroot has completed its build, the ADC definitions for the ATSAMA5D27-SOM1-EK1 are configured by a device tree. The device tree source include file (*.dtsi) is located in the Buildroot output directory: /output/build/linux-linux4sam_6.0/arch/arm/boot/dts/

Examine the sama5d2.dtsi file and observe the ADC device assignments:

775  adc_clk: adc_clk {
776      #clock-cells = <0>;
777      reg = <40>;
778      atmel,clk-output-range = <0 83000000>;
779  };

1467  adc: adc@fc030000 {
1468    compatible = "atmel,sama5d2-adc";
1469    reg = <0xfc030000 0x100>;
1470    interrupts = <40 IRQ_TYPE_LEVEL_HIGH 7>;
1471    clocks = <&adc_clk>;
1472    clock-names = "adc_clk";
1473    dmas = <&dma0 (AT91_XDMAC_DT_MEM_IF(0) | \
        AT91_XDMAC_DT_PER_IF(1) | AT91_XDMAC_DT_PERID(25))>;
1474    dma-names = "rx";
1475    atmel,min-sample-rate-hz = <200000>;
1476    atmel,max-sample-rate-hz = <20000000>;
1477    atmel,startup-time-ms = <4>;
1478    atmel,trigger-edge-type = <IRQ_TYPE_EDGE_RISING>;
1479    #io-channel-cells = <1>;
1480    status = "disabled";
1481  };

Line 777 the PID of the ADC is 40. This definition of the offset will be used to enable the ADC clock in the Power Management Controller (PMC).

Line 778 sets the ADC input clock to the maximum frequency of 83 MHz.

Line 1468 specifies which driver is used for the ADC device.

Line 1469 the ADC base address is 0xfc030000, size is 0x100.

Line 1470 the PID of the ADC is 40. The interrupt (AIC) is high-level triggered; priority is 7.

Lines 1471 and 1472 define the ADC clock source.

Lines 1473 and 1474 define one DMA channel used by the ADC.

Line 1475 defines the minimum sample rate.

Line 1476 defines the maximum sample rate.

Line 1477 defines the startup time as 4 ms.

Line 1478 defines the trigger mode as a rising edge.

Line 1480 status is defined as disabled which is the default. It will be set to “okay” in the next code segment.

Examine the at91-sama5d27_som1_ek.dts file and observe the ADC device assignments:

309  adc: adc@fc030000 {
310      vddana-supply = <&vddana>;
311      vref-supply = <&advref>;
313      status = "okay";
314  };

Line 310 defines analog power supply for the ADC.

Line 311 defines the reference voltage for the ADC.

Line 313 ensures that status is defined as okay (enabled).

Back to Top


Objective: Observe how ADC functionality was configured in the Linux kernel. No changes are required.

From the buildroot directory, run the Linux kernel menuconfig:

$ make linux-menuconfig

The top-level menu will be displayed:

Linux menuconfig top menu

Back to Top

Device Driver

Select Device Drivers ---->

Linux menuconfig device drivers

Back to Top

Industrial I/O Support

Scroll down and select <*> Industrial I/O support --->

Linux menuconfig industrial I/O support

Back to Top

Analog-to-Digital Converter

Select Analog to digital converters ---->

Linux menuconfig Analog to digital converters

Finally, observe that <*>Atmel® AT91 SAMA5D2 ADC has been selected. This setting compiles the ADC driver for the ATSAMA5D2 series MPU into the Linux kernel.

Linux menuconfig Analog to digital converters: Atmel ADC selected

Back to Top


After Linux boot-up, two paths will be created to access the ADC driver:

This is the main entry of IIO support for the ADC device (iio:device0).

IIO device node is used to read converted data from the ADC driver.

Back to Top

Hands On

There are two methods to request ADC conversion:

  1. Software trigger
  2. Hardware trigger

Software Trigger

Internal synchronous trigger, by writing ADC register ADC_CR.START

When reading the ADC channel raw file directly, a software trigger action will be performed by the ADC driver:

# cat /sys/bus/iio/devices/iio:device0/in_voltage6_raw
# cat /sys/bus/iio/devices/iio:device0/in_voltage_scale

The converted raw data is 16380 and the scaling ratio is 0.201416015. Voltage value is: 16380 x 0.201416015 = 3.299 mV

Hardware Triggers

Asynchronous trigger, asserted by an internal or external signal (pins or periodic event). Refer to ADC_TRGR.TRGMOD for more information.

Hardware triggers are an operating mode of the ADC device that are triggered directly by hardware. In general, the ADTRG pin is used to receive the external hardware trigger signal.

  • In SAMA5D2, the pin ADTRG is multiplexed with GPIO PD31.
  • In SAMA5D27-SOM1-EK1, GPIO PD31 was not exported to any connector and thus, a workaround is used to handle this unexpected case.
# echo 1 > /sys/bus/iio/devices/iio:device0/scan_elements/in_voltage6_en
# cat /sys/bus/iio/devices/trigger0/name
# echo fc030000.adc-dev0-external_rising > /sys/bus/iio/devices/iio:device0/trigger/current_trigger
# echo 100 > /sys/bus/iio/devices/iio:device0/buffer/length
# echo 1 > /sys/bus/iio/devices/iio:device0/buffer/enable
~/~/ workaround: use ADC internal periodic trigger instead of external trigger
# devmem2 0xfc0300C0 w 0xffff0005
~/~/ Written 0xFFFF0005; readback 0xFFFF0005
# hexdump -e '/2 "%d\n"' -v /dev/iio:device0

The converted raw data is 16380 and the scaling ratio is 0.201416015. The voltage value is:
16380 x 0.201416015 = 3.299 mV

Back to Top


In this topic, you used Buildroot to build an image with the IIO support for the ATSAMA5D2 Series MPU. You used software and hardware triggers to initiate an ADC. You walked through the device tree and kernel to observe how the embedded Linux system configures the source code for building.

Back to Top