Analog to Digital Converter

Overview

ESP32 integrates two 12-bit SAR (Successive Approximation Register) ADCs (Analog to Digital Converters) and supports measurements on 18 channels (analog enabled pins). Some of these pins can be used to build a programmable gain amplifier which is used for the measurement of small analog signals.

The ADC driver API supports ADC1 (9 channels, attached to GPIOs 32 - 39), and ADC2 (10 channels, attached to GPIOs 0, 2, 4, 12 - 15 and 25 - 27). However, there’re some restrictions for the application to use ADC2:

  1. The application can use ADC2 only when Wi-Fi driver is not started, since the ADC is also used by the Wi-Fi driver, which has higher priority.
  2. Some of the ADC2 pins are used as strapping pins (GPIO 0, 2, 15), so they cannot be used freely. For examples, for official Develop Kits:

Configuration and Reading ADC

The ADC should be configured before reading is taken.

Attenuation configuration is done per channel, see adc1_channel_t and adc2_channel_t, set as a parameter of above functions.

Then it is possible to read ADC conversion result with adc1_get_raw() and adc2_get_raw(). Reading width of ADC2 should be set as a parameter of adc2_get_raw() instead of in the configuration functions.

Note

Since the ADC2 is shared with the WIFI module, which has higher priority, reading operation of adc2_get_raw() will fail between esp_wifi_start() and esp_wifi_stop(). Use the return code to see whether the reading is successful.

It is also possible to read the internal hall effect sensor via ADC1 by calling dedicated function hall_sensor_read(). Note that even the hall sensor is internal to ESP32, reading from it uses channels 0 and 3 of ADC1 (GPIO 36 and 39). Do not connect anything else to these pins and do not change their configuration. Otherwise it may affect the measurement of low value signal from the sesnor.

This API provides convenient way to configure ADC1 for reading from ULP. To do so, call function adc1_ulp_enable() and then set precision and attenuation as discussed above.

There is another specific function adc2_vref_to_gpio() used to route internal reference voltage to a GPIO pin. It comes handy to calibrate ADC reading and this is discussed in section ADC Calibration.

Application Examples

Reading voltage on ADC1 channel 0 (GPIO 36):

#include <driver/adc.h>

...

    adc1_config_width(ADC_WIDTH_BIT_12);
    adc1_config_channel_atten(ADC1_CHANNEL_0,ADC_ATTEN_DB_0);
    int val = adc1_get_raw(ADC1_CHANNEL_0);

The input voltage in above example is from 0 to 1.1V (0 dB attenuation). The input range can be extended by setting higher attenuation, see adc_atten_t. An example using the ADC driver including calibration (discussed below) is available in esp-idf: peripherals/adc

Reading voltage on ADC2 channel 7 (GPIO 27):

#include <driver/adc.h>

...

    int read_raw;
    adc2_config_channel_atten( ADC2_CHANNEL_7, ADC_ATTEN_0db );

    esp_err_t r = adc2_get_raw( ADC2_CHANNEL_7, ADC_WIDTH_12Bit, &read_raw);
    if ( r == ESP_OK ) {
        printf("%d\n", read_raw );
    } else if ( r == ESP_ERR_TIMEOUT ) {
        printf("ADC2 used by Wi-Fi.\n");
    }

The reading may fail due to collision with Wi-Fi, should check it. An example using the ADC2 driver to read the output of DAC is available in esp-idf: peripherals/adc2

Reading the internal hall effect sensor:

#include <driver/adc.h>

...

    adc1_config_width(ADC_WIDTH_BIT_12);
    int val = hall_sensor_read();

The value read in both these examples is 12 bits wide (range 0-4095).

ADC Calibration

The esp_adc_cal/include/esp_adc_cal.h API provides functions to correct for differences in measured voltages caused by non-ideal ADC reference voltages in ESP32s. The ideal ADC reference voltage is 1100 mV however the reference voltage of different ESP32s can range from 1000 mV to 1200 mV.

Correcting the measured voltage using this API involves referencing a lookup table of voltages. The voltage obtained from the lookup table is then scaled and shifted by a gain and offset factor that is based on the ADC’s reference voltage. This is done with function esp_adc_cal_get_characteristics().

The reference voltage of the ADCs can be routed to certain GPIOs and measured manually using the ADC driver’s adc2_vref_to_gpio() function.

Example of Reading Calibrated Values

Reading the ADC and obtaining a result in mV:

#include <driver/adc.h>
#include <esp_adc_cal.h>

...
    #define V_REF 1100  // ADC reference voltage

    // Configure ADC
    adc1_config_width(ADC_WIDTH_12Bit);
    adc1_config_channel_atten(ADC1_CHANNEL_6, ADC_ATTEN_11db);

    // Calculate ADC characteristics i.e. gain and offset factors
    esp_adc_cal_characteristics_t characteristics;
    esp_adc_cal_get_characteristics(V_REF, ADC_ATTEN_DB_11, ADC_WIDTH_BIT_12, &characteristics);

    // Read ADC and obtain result in mV
    uint32_t voltage = adc1_to_voltage(ADC1_CHANNEL_6, &characteristics);
    printf("%d mV\n",voltage);

Routing ADC reference voltage to GPIO, so it can be manually measured and entered in function esp_adc_cal_get_characteristics():

#include <driver/adc.h>
#include <driver/gpio.h>
#include <esp_err.h>

...

    esp_err_t status = adc2_vref_to_gpio(GPIO_NUM_25);
    if (status == ESP_OK){
        printf("v_ref routed to GPIO\n");
    }else{
        printf("failed to route v_ref\n");
    }

An example of using the ADC driver and obtaining calibrated measurements is available in esp-idf: peripherals/adc

GPIO Lookup Macros

There are macros available to specify the GPIO number of a ADC channel, or vice versa. e.g.

  1. ADC1_CHANNEL_0_GPIO_NUM is the GPIO number of ADC1 channel 0 (36);
  2. ADC1_GPIO32_CHANNEL is the ADC1 channel number of GPIO 32 (ADC1 channel 4).

API Reference

This reference covers three components:

ADC driver

Functions

esp_err_t adc1_pad_get_io_num(adc1_channel_t channel, gpio_num_t *gpio_num)

Get the gpio number of a specific ADC1 channel.

Return
  • ESP_OK if success
  • ESP_ERR_INVALID_ARG if channal not valid
Parameters
  • channel: Channel to get the gpio number
  • gpio_num: output buffer to hold the gpio number

esp_err_t adc1_config_width(adc_bits_width_t width_bit)

Configure ADC1 capture width, meanwhile enable output invert for ADC1. The configuration is for all channels of ADC1.

Return
  • ESP_OK success
  • ESP_ERR_INVALID_ARG Parameter error
Parameters
  • width_bit: Bit capture width for ADC1

esp_err_t adc_set_data_width(adc_unit_t adc_unit, adc_bits_width_t width_bit)

Configure ADC capture width.

Return
  • ESP_OK success
  • ESP_ERR_INVALID_ARG Parameter error
Parameters
  • adc_unit: ADC unit index
  • width_bit: Bit capture width for ADC unit.

esp_err_t adc1_config_channel_atten(adc1_channel_t channel, adc_atten_t atten)

Configure the ADC1 channel, including setting attenuation.

The default ADC full-scale voltage is 1.1V. To read higher voltages (up to the pin maximum voltage, usually 3.3V) requires setting >0dB signal attenuation for that ADC channel.

Note
This function also configures the input GPIO pin mux to connect it to the ADC1 channel. It must be called before calling adc1_get_raw() for this channel.

When VDD_A is 3.3V:

  • 0dB attenuaton (ADC_ATTEN_DB_0) gives full-scale voltage 1.1V
  • 2.5dB attenuation (ADC_ATTEN_DB_2_5) gives full-scale voltage 1.5V
  • 6dB attenuation (ADC_ATTEN_DB_6) gives full-scale voltage 2.2V
  • 11dB attenuation (ADC_ATTEN_DB_11) gives full-scale voltage 3.9V (see note below)

Note
The full-scale voltage is the voltage corresponding to a maximum reading (depending on ADC1 configured bit width, this value is: 4095 for 12-bits, 2047 for 11-bits, 1023 for 10-bits, 511 for 9 bits.)
Note
At 11dB attenuation the maximum voltage is limited by VDD_A, not the full scale voltage.
Return
  • ESP_OK success
  • ESP_ERR_INVALID_ARG Parameter error
Parameters
  • channel: ADC1 channel to configure
  • atten: Attenuation level

int adc1_get_raw(adc1_channel_t channel)

Take an ADC1 reading on a single channel.

Note
Call adc1_config_width() before the first time this function is called.
Note
For a given channel, adc1_config_channel_atten(channel) must be called before the first time this function is called.
Return
  • -1: Parameter error
  • Other: ADC1 channel reading.
Parameters
  • channel: ADC1 channel to read

void adc_power_on()

Power on SAR ADC.

void adc_power_off()

Power off SAR ADC.

esp_err_t adc_gpio_init(adc_unit_t adc_unit, adc_channel_t channel)

Initialize ADC pad.

Return
  • ESP_OK success
  • ESP_ERR_INVALID_ARG Parameter error
Parameters
  • adc_unit: ADC unit index
  • channel: ADC channel index

esp_err_t adc_set_data_inv(adc_unit_t adc_unit, bool inv_en)

Set ADC data invert.

Return
  • ESP_OK success
  • ESP_ERR_INVALID_ARG Parameter error
Parameters
  • adc_unit: ADC unit index
  • inv_en: whether enable data invert

esp_err_t adc_set_clk_div(uint8_t clk_div)

Set ADC source clock.

Return
  • ESP_OK success
Parameters
  • clk_div: ADC clock divider, ADC clock is divided from APB clock

esp_err_t adc_set_i2s_data_source(adc_i2s_source_t src)

Set I2S data source.

Return
  • ESP_OK success
Parameters
  • src: I2S DMA data source, I2S DMA can get data from digital signals or from ADC.

esp_err_t adc_i2s_mode_init(adc_unit_t adc_unit, adc_channel_t channel)

Initialize I2S ADC mode.

Return
  • ESP_OK success
  • ESP_ERR_INVALID_ARG Parameter error
Parameters
  • adc_unit: ADC unit index
  • channel: ADC channel index

void adc1_ulp_enable()

Configure ADC1 to be usable by the ULP.

This function reconfigures ADC1 to be controlled by the ULP. Effect of this function can be reverted using adc1_get_raw function.

Note that adc1_config_channel_atten, adc1_config_width functions need to be called to configure ADC1 channels, before ADC1 is used by the ULP.

int hall_sensor_read()

Read Hall Sensor.

Note
The Hall Sensor uses channels 0 and 3 of ADC1. Do not configure these channels for use as ADC channels.
Note
The ADC1 module must be enabled by calling adc1_config_width() before calling hall_sensor_read(). ADC1 should be configured for 12 bit readings, as the hall sensor readings are low values and do not cover the full range of the ADC.
Return
The hall sensor reading.

esp_err_t adc2_pad_get_io_num(adc2_channel_t channel, gpio_num_t *gpio_num)

Get the gpio number of a specific ADC2 channel.

Return
  • ESP_OK if success
  • ESP_ERR_INVALID_ARG if channal not valid
Parameters
  • channel: Channel to get the gpio number
  • gpio_num: output buffer to hold the gpio number

esp_err_t adc2_config_channel_atten(adc2_channel_t channel, adc_atten_t atten)

Configure the ADC2 channel, including setting attenuation.

The default ADC full-scale voltage is 1.1V. To read higher voltages (up to the pin maximum voltage, usually 3.3V) requires setting >0dB signal attenuation for that ADC channel.

Note
This function also configures the input GPIO pin mux to connect it to the ADC2 channel. It must be called before calling adc2_get_raw() for this channel.

When VDD_A is 3.3V:

  • 0dB attenuaton (ADC_ATTEN_0db) gives full-scale voltage 1.1V
  • 2.5dB attenuation (ADC_ATTEN_2_5db) gives full-scale voltage 1.5V
  • 6dB attenuation (ADC_ATTEN_6db) gives full-scale voltage 2.2V
  • 11dB attenuation (ADC_ATTEN_11db) gives full-scale voltage 3.9V (see note below)

Note
The full-scale voltage is the voltage corresponding to a maximum reading (depending on ADC2 configured bit width, this value is: 4095 for 12-bits, 2047 for 11-bits, 1023 for 10-bits, 511 for 9 bits.)
Note
At 11dB attenuation the maximum voltage is limited by VDD_A, not the full scale voltage.
Return
  • ESP_OK success
  • ESP_ERR_INVALID_ARG Parameter error
Parameters
  • channel: ADC2 channel to configure
  • atten: Attenuation level

esp_err_t adc2_get_raw(adc2_channel_t channel, adc_bits_width_t width_bit, int *raw_out)

Take an ADC2 reading on a single channel.

Note
For a given channel, adc2_config_channel_atten() must be called before the first time this function is called. If Wi-Fi is started via esp_wifi_start(), this function will always fail with ESP_ERR_TIMEOUT.
Return
  • ESP_OK if success
  • ESP_ERR_TIMEOUT the WIFI is started, using the ADC2
Parameters
  • channel: ADC2 channel to read
  • width_bit: Bit capture width for ADC2
  • raw_out: the variable to hold the output data.

esp_err_t adc2_vref_to_gpio(gpio_num_t gpio)

Output ADC2 reference voltage to gpio 25 or 26 or 27.

This function utilizes the testing mux exclusive to ADC 2 to route the reference voltage one of ADC2’s channels. Supported gpios are gpios 25, 26, and 27. This refernce voltage can be manually read from the pin and used in the esp_adc_cal component.

Return
  • ESP_OK: v_ref successfully routed to selected gpio
  • ESP_ERR_INVALID_ARG: Unsupported gpio
Parameters
  • gpio: GPIO number (gpios 25,26,27 supported)

Macros

ADC_ATTEN_0db
ADC_ATTEN_2_5db
ADC_ATTEN_6db
ADC_ATTEN_11db
ADC_WIDTH_9Bit
ADC_WIDTH_10Bit
ADC_WIDTH_11Bit
ADC_WIDTH_12Bit

Enumerations

enum adc_atten_t

Values:

ADC_ATTEN_DB_0 = 0

The input voltage of ADC will be reduced to about 1/1

ADC_ATTEN_DB_2_5 = 1

The input voltage of ADC will be reduced to about 1/1.34

ADC_ATTEN_DB_6 = 2

The input voltage of ADC will be reduced to about 1/2

ADC_ATTEN_DB_11 = 3

The input voltage of ADC will be reduced to about 1/3.6

ADC_ATTEN_MAX
enum adc_bits_width_t

Values:

ADC_WIDTH_BIT_9 = 0

ADC capture width is 9Bit

ADC_WIDTH_BIT_10 = 1

ADC capture width is 10Bit

ADC_WIDTH_BIT_11 = 2

ADC capture width is 11Bit

ADC_WIDTH_BIT_12 = 3

ADC capture width is 12Bit

ADC_WIDTH_MAX
enum adc1_channel_t

Values:

ADC1_CHANNEL_0 = 0

ADC1 channel 0 is GPIO36

ADC1_CHANNEL_1

ADC1 channel 1 is GPIO37

ADC1_CHANNEL_2

ADC1 channel 2 is GPIO38

ADC1_CHANNEL_3

ADC1 channel 3 is GPIO39

ADC1_CHANNEL_4

ADC1 channel 4 is GPIO32

ADC1_CHANNEL_5

ADC1 channel 5 is GPIO33

ADC1_CHANNEL_6

ADC1 channel 6 is GPIO34

ADC1_CHANNEL_7

ADC1 channel 7 is GPIO35

ADC1_CHANNEL_MAX
enum adc2_channel_t

Values:

ADC2_CHANNEL_0 = 0

ADC2 channel 0 is GPIO4

ADC2_CHANNEL_1

ADC2 channel 1 is GPIO0

ADC2_CHANNEL_2

ADC2 channel 2 is GPIO2

ADC2_CHANNEL_3

ADC2 channel 3 is GPIO15

ADC2_CHANNEL_4

ADC2 channel 4 is GPIO13

ADC2_CHANNEL_5

ADC2 channel 5 is GPIO12

ADC2_CHANNEL_6

ADC2 channel 6 is GPIO14

ADC2_CHANNEL_7

ADC2 channel 7 is GPIO27

ADC2_CHANNEL_8

ADC2 channel 8 is GPIO25

ADC2_CHANNEL_9

ADC2 channel 9 is GPIO26

ADC2_CHANNEL_MAX
enum adc_channel_t

Values:

ADC_CHANNEL_0 = 0

ADC channel

ADC_CHANNEL_1

ADC channel

ADC_CHANNEL_2

ADC channel

ADC_CHANNEL_3

ADC channel

ADC_CHANNEL_4

ADC channel

ADC_CHANNEL_5

ADC channel

ADC_CHANNEL_6

ADC channel

ADC_CHANNEL_7

ADC channel

ADC_CHANNEL_8

ADC channel

ADC_CHANNEL_9

ADC channel

ADC_CHANNEL_MAX
enum adc_unit_t

Values:

ADC_UNIT_1 = 1

SAR ADC 1

ADC_UNIT_2 = 2

SAR ADC 2, not supported yet

ADC_UNIT_BOTH = 3

SAR ADC 1 and 2, not supported yet

ADC_UNIT_ALTER = 7

SAR ADC 1 and 2 alternative mode, not supported yet

ADC_UNIT_MAX
enum adc_i2s_encode_t

Values:

ADC_ENCODE_12BIT

ADC to I2S data format, [15:12]-channel [11:0]-12 bits ADC data

ADC_ENCODE_11BIT

ADC to I2S data format, [15]-1 [14:11]-channel [10:0]-11 bits ADC data

ADC_ENCODE_MAX
enum adc_i2s_source_t

Values:

ADC_I2S_DATA_SRC_IO_SIG = 0

I2S data from GPIO matrix signal

ADC_I2S_DATA_SRC_ADC = 1

I2S data from ADC

ADC_I2S_DATA_SRC_MAX

ADC Calibration

Functions

void esp_adc_cal_get_characteristics(uint32_t v_ref, adc_atten_t atten, adc_bits_width_t bit_width, esp_adc_cal_characteristics_t *chars)

Calculate characteristics of ADC.

This function will calculate the gain and offset factors based on the reference voltage parameter and the Gain and Offset curve provided in the LUT.

Note
reference voltage of the ADCs can be routed to GPIO using adc2_vref_to_gpio() from the ADC driver
Note
The LUT members have been bit shifted by ADC_CAL_GAIN_SCALE or ADC_CAL_OFFSET_SCALE to make them uint32_t compatible. This bit shifting will accounted for in this function
Parameters
  • v_ref: true reference voltage of the ADC in mV (1000 to 1200mV). Nominal value for reference voltage is 1100mV.
  • atten: attenuation setting used to select the corresponding lookup table
  • bit_width: bit width of ADC
  • chars: pointer to structure used to store ADC characteristics of module

uint32_t esp_adc_cal_raw_to_voltage(uint32_t adc, const esp_adc_cal_characteristics_t *chars)

Convert raw ADC reading to voltage in mV.

This function converts a raw ADC reading to a voltage in mV. This conversion is based on the ADC’s characteristics. The raw ADC reading is referenced against the LUT (pointed to inside characteristics struct) to obtain a voltage. Gain and offset factors are then applied to the voltage in order to obtain the final result.

Return
Calculated voltage in mV
Note
characteristics structure must be initialized using esp_adc_cal_get_characteristics() before this function is used
Parameters
  • adc: ADC reading (different bit widths will be handled)
  • chars: pointer to structure containing ADC characteristics of the module. Structure also contains pointer to the corresponding LUT

uint32_t adc1_to_voltage(adc1_channel_t channel, const esp_adc_cal_characteristics_t *chars)

Reads ADC1 and returns voltage in mV.

This function reads the ADC1 using adc1_get_raw() to obtain a raw ADC reading. The reading is then converted into a voltage value using esp_adc_cal_raw_to_voltage().

Return
voltage Calculated voltage in mV
Note
ADC must be initialized using adc1_config_width() and adc1_config_channel_atten() before this function is used
Note
characteristics structure must be initialized using esp_adc_cal_get_characteristics() before this function is used
Parameters
  • channel: Channel of ADC1 to measure
  • chars: Pointer to ADC characteristics struct

Structures

struct esp_adc_cal_lookup_table_t

Structure storing Lookup Table.

The Lookup Tables (LUT) of a given attenuation contains 33 equally spaced points. The Gain and Offset curves are used to find the appopriate gain and offset factor given a reference voltage v_ref.

Note
A seperate LUT is provided for each attenuation and are defined in esp_adc_cal_lookup_tables.c

Public Members

uint32_t gain_m

Gradient of Gain Curve

uint32_t gain_c

Offset of Gain Curve

uint32_t offset_m

Gradient of Offset Curve

uint32_t offset_c

Offset of Offset Curve

uint32_t bit_shift

Bit shift used find corresponding LUT points given an ADC reading

uint32_t voltage[]

Array of voltages in mV representing the ADC-Voltage curve

struct esp_adc_cal_characteristics_t

Structure storing ADC characteristics of given v_ref.

The ADC Characteristics structure stores the gain and offset factors of an ESP32 module’s ADC. These factors are calculated using the reference voltage, and the Gain and Offset curves provided in the lookup tables.

Note
Call esp_adc_cal_get_characteristics() to initialize the structure

Public Members

uint32_t v_ref

Reference Voltage of current ESP32 Module in mV

uint32_t gain

Scaling factor used to correct LUT voltages to current v_ref. Bit shifted by << ADC_CAL_GAIN_SCALE for uint32 arithmetic

uint32_t offset

Offset in mV used to correct LUT Voltages to current v_ref

uint32_t ideal_offset

Offset in mV at the ideal reference voltage

adc_bits_width_t bit_width

Bit width of ADC e.g. ADC_WIDTH_BIT_12

const esp_adc_cal_lookup_table_t *table

Pointer to LUT

GPIO Lookup Macros

Macros

ADC1_GPIO36_CHANNEL
ADC1_CHANNEL_0_GPIO_NUM
ADC1_GPIO37_CHANNEL
ADC1_CHANNEL_1_GPIO_NUM
ADC1_GPIO38_CHANNEL
ADC1_CHANNEL_2_GPIO_NUM
ADC1_GPIO39_CHANNEL
ADC1_CHANNEL_3_GPIO_NUM
ADC1_GPIO32_CHANNEL
ADC1_CHANNEL_4_GPIO_NUM
ADC1_GPIO33_CHANNEL
ADC1_CHANNEL_5_GPIO_NUM
ADC1_GPIO34_CHANNEL
ADC1_CHANNEL_6_GPIO_NUM
ADC1_GPIO35_CHANNEL
ADC1_CHANNEL_7_GPIO_NUM
ADC2_GPIO4_CHANNEL
ADC2_CHANNEL_0_GPIO_NUM
ADC2_GPIO0_CHANNEL
ADC2_CHANNEL_1_GPIO_NUM
ADC2_GPIO2_CHANNEL
ADC2_CHANNEL_2_GPIO_NUM
ADC2_GPIO15_CHANNEL
ADC2_CHANNEL_3_GPIO_NUM
ADC2_GPIO13_CHANNEL
ADC2_CHANNEL_4_GPIO_NUM
ADC2_GPIO12_CHANNEL
ADC2_CHANNEL_5_GPIO_NUM
ADC2_GPIO14_CHANNEL
ADC2_CHANNEL_6_GPIO_NUM
ADC2_GPIO27_CHANNEL
ADC2_CHANNEL_7_GPIO_NUM
ADC2_GPIO25_CHANNEL
ADC2_CHANNEL_8_GPIO_NUM
ADC2_GPIO26_CHANNEL
ADC2_CHANNEL_9_GPIO_NUM