mirror of
https://github.com/espressif/esp-idf.git
synced 2024-10-05 20:47:46 -04:00
Merge branch 'feature/adc_calibration_version_2_on_c3' into 'master'
adc: upgrade adc calibration algorithm to version 2 on c3 Closes IDF-4557 See merge request espressif/esp-idf!16876
This commit is contained in:
commit
579bd2cd44
@ -1,7 +1,7 @@
|
|||||||
idf_build_get_property(target IDF_TARGET)
|
idf_build_get_property(target IDF_TARGET)
|
||||||
|
|
||||||
set(srcs "esp_adc_cal_common.c")
|
set(srcs "esp_adc_cal_common.c")
|
||||||
set(src_target "esp_adc_cal_${target}.c")
|
set(src_target "${target}/esp_adc_cal.c")
|
||||||
if(EXISTS "${CMAKE_CURRENT_LIST_DIR}/${src_target}")
|
if(EXISTS "${CMAKE_CURRENT_LIST_DIR}/${src_target}")
|
||||||
list(APPEND srcs ${src_target})
|
list(APPEND srcs ${src_target})
|
||||||
endif()
|
endif()
|
||||||
|
@ -15,16 +15,47 @@
|
|||||||
#include "hal/adc_ll.h"
|
#include "hal/adc_ll.h"
|
||||||
#include "esp_efuse_rtc_calib.h"
|
#include "esp_efuse_rtc_calib.h"
|
||||||
#include "esp_adc_cal.h"
|
#include "esp_adc_cal.h"
|
||||||
|
#include "../esp_adc_cal_internal.h"
|
||||||
|
|
||||||
const static char LOG_TAG[] = "adc_calib";
|
const static char LOG_TAG[] = "ADC_CALI";
|
||||||
|
|
||||||
|
|
||||||
/* ------------------------ Characterization Constants ---------------------- */
|
/* ------------------------ Characterization Constants ---------------------- */
|
||||||
|
|
||||||
// coeff_a and coeff_b are actually floats
|
// coeff_a is actually a float number
|
||||||
// they are scaled to put them into uint32_t so that the headers do not have to be changed
|
// it is scaled to put them into uint32_t so that the headers do not have to be changed
|
||||||
static const int coeff_a_scaling = 65536;
|
static const int coeff_a_scaling = 65536;
|
||||||
static const int coeff_b_scaling = 1024;
|
|
||||||
|
/**
|
||||||
|
* @note Error Calculation
|
||||||
|
* Coefficients for calculating the reading voltage error.
|
||||||
|
* Four sets of coefficients for atten0 ~ atten3 respectively.
|
||||||
|
*
|
||||||
|
* For each item, first element is the Coefficient, second element is the Multiple. (Coefficient / Multiple) is the real coefficient.
|
||||||
|
*
|
||||||
|
* @note {0,0} stands for unused item
|
||||||
|
* @note In case of the overflow, these coeffcients are recorded as Absolute Value
|
||||||
|
* @note For atten0 ~ 2, error = (K0 * X^0) + (K1 * X^1) + (K2 * X^2); For atten3, error = (K0 * X^0) + (K1 * X^1) + (K2 * X^2) + (K3 * X^3) + (K4 * X^4);
|
||||||
|
* @note Above formula is rewritten from the original documentation, please note that the coefficients are re-ordered.
|
||||||
|
* @note ADC1 and ADC2 use same coeffients
|
||||||
|
*/
|
||||||
|
const static uint64_t adc_error_coef_atten[4][5][2] = {
|
||||||
|
{{225966470500043, 1e15}, {7265418501948, 1e16}, {109410402681, 1e16}, {0, 0}, {0, 0}}, //atten0
|
||||||
|
{{4229623392600516, 1e16}, {731527490903, 1e16}, {88166562521, 1e16}, {0, 0}, {0, 0}}, //atten1
|
||||||
|
{{1017859239236435, 1e15}, {97159265299153, 1e16}, {149794028038, 1e16}, {0, 0}, {0, 0}}, //atten2
|
||||||
|
{{14912262772850453, 1e16}, {228549975564099, 1e16}, {356391935717, 1e16}, {179964582, 1e16}, {42046, 1e16}} //atten3
|
||||||
|
};
|
||||||
|
/**
|
||||||
|
* Term sign
|
||||||
|
* @note ADC1 and ADC2 use same coeffients
|
||||||
|
*/
|
||||||
|
const static int32_t adc_error_sign[4][5] = {
|
||||||
|
{-1, -1, 1, 0, 0}, //atten0
|
||||||
|
{ 1, -1, 1, 0, 0}, //atten1
|
||||||
|
{-1, -1, 1, 0, 0}, //atten2
|
||||||
|
{-1, -1, 1, -1, 1} //atten3
|
||||||
|
};
|
||||||
|
|
||||||
/* -------------------- Characterization Helper Data Types ------------------ */
|
/* -------------------- Characterization Helper Data Types ------------------ */
|
||||||
typedef struct {
|
typedef struct {
|
||||||
uint32_t voltage;
|
uint32_t voltage;
|
||||||
@ -38,9 +69,9 @@ typedef struct {
|
|||||||
union {
|
union {
|
||||||
adc_calib_data_ver1 ver1;
|
adc_calib_data_ver1 ver1;
|
||||||
} efuse_data;
|
} efuse_data;
|
||||||
} adc_calib_parsed_info;
|
} adc_calib_parsed_info_t;
|
||||||
|
|
||||||
static esp_err_t prepare_calib_data_for(int version_num, adc_unit_t adc_num, adc_atten_t atten, adc_calib_parsed_info *parsed_data_storage)
|
static esp_err_t prepare_calib_data_for(int version_num, adc_unit_t adc_num, adc_atten_t atten, adc_calib_parsed_info_t *parsed_data_storage)
|
||||||
{
|
{
|
||||||
assert(version_num == 1);
|
assert(version_num == 1);
|
||||||
esp_err_t ret;
|
esp_err_t ret;
|
||||||
@ -64,7 +95,7 @@ static esp_err_t prepare_calib_data_for(int version_num, adc_unit_t adc_num, adc
|
|||||||
* Estimate the (assumed) linear relationship btwn the measured raw value and the voltage
|
* Estimate the (assumed) linear relationship btwn the measured raw value and the voltage
|
||||||
* with the previously done measurement when the chip was manufactured.
|
* with the previously done measurement when the chip was manufactured.
|
||||||
*/
|
*/
|
||||||
static void calculate_characterization_coefficients(const adc_calib_parsed_info *parsed_data, esp_adc_cal_characteristics_t *chars)
|
static void calculate_characterization_coefficients(const adc_calib_parsed_info_t *parsed_data, esp_adc_cal_characteristics_t *chars)
|
||||||
{
|
{
|
||||||
ESP_LOGD(LOG_TAG, "Calib V1, Cal Voltage = %d, Digi out = %d\n", parsed_data->efuse_data.ver1.voltage, parsed_data->efuse_data.ver1.digi);
|
ESP_LOGD(LOG_TAG, "Calib V1, Cal Voltage = %d, Digi out = %d\n", parsed_data->efuse_data.ver1.voltage, parsed_data->efuse_data.ver1.digi);
|
||||||
|
|
||||||
@ -93,7 +124,7 @@ esp_adc_cal_value_t esp_adc_cal_characterize(adc_unit_t adc_num,
|
|||||||
esp_adc_cal_characteristics_t *chars)
|
esp_adc_cal_characteristics_t *chars)
|
||||||
{
|
{
|
||||||
esp_err_t ret;
|
esp_err_t ret;
|
||||||
adc_calib_parsed_info efuse_parsed_data = {0};
|
adc_calib_parsed_info_t efuse_parsed_data = {0};
|
||||||
// Check parameters
|
// Check parameters
|
||||||
ESP_RETURN_ON_FALSE(adc_num == ADC_UNIT_1 || adc_num == ADC_UNIT_2, ESP_ADC_CAL_VAL_NOT_SUPPORTED, LOG_TAG, "Invalid unit num");
|
ESP_RETURN_ON_FALSE(adc_num == ADC_UNIT_1 || adc_num == ADC_UNIT_2, ESP_ADC_CAL_VAL_NOT_SUPPORTED, LOG_TAG, "Invalid unit num");
|
||||||
ESP_RETURN_ON_FALSE(chars != NULL, ESP_ADC_CAL_VAL_NOT_SUPPORTED, LOG_TAG, "Ivalid characteristic");
|
ESP_RETURN_ON_FALSE(chars != NULL, ESP_ADC_CAL_VAL_NOT_SUPPORTED, LOG_TAG, "Ivalid characteristic");
|
||||||
@ -126,5 +157,16 @@ esp_adc_cal_value_t esp_adc_cal_characterize(adc_unit_t adc_num,
|
|||||||
uint32_t esp_adc_cal_raw_to_voltage(uint32_t adc_reading, const esp_adc_cal_characteristics_t *chars)
|
uint32_t esp_adc_cal_raw_to_voltage(uint32_t adc_reading, const esp_adc_cal_characteristics_t *chars)
|
||||||
{
|
{
|
||||||
assert(chars != NULL);
|
assert(chars != NULL);
|
||||||
return adc_reading * chars->coeff_a / coeff_a_scaling + chars->coeff_b / coeff_b_scaling;
|
|
||||||
|
int32_t error = 0;
|
||||||
|
uint64_t v_cali_1 = adc_reading * chars->coeff_a / coeff_a_scaling;
|
||||||
|
esp_adc_error_calc_param_t param = {
|
||||||
|
.v_cali_input = v_cali_1,
|
||||||
|
.term_num = (chars->atten == 3) ? 5 : 3,
|
||||||
|
.coeff = &adc_error_coef_atten,
|
||||||
|
.sign = &adc_error_sign,
|
||||||
|
};
|
||||||
|
error = esp_adc_cal_get_reading_error(¶m, chars->atten);
|
||||||
|
|
||||||
|
return (int32_t)v_cali_1 - error;
|
||||||
}
|
}
|
@ -15,6 +15,7 @@
|
|||||||
#include "hal/adc_types.h"
|
#include "hal/adc_types.h"
|
||||||
#include "esp_efuse_rtc_calib.h"
|
#include "esp_efuse_rtc_calib.h"
|
||||||
#include "esp_adc_cal.h"
|
#include "esp_adc_cal.h"
|
||||||
|
#include "../esp_adc_cal_internal.h"
|
||||||
|
|
||||||
const static char LOG_TAG[] = "ADC_CALI";
|
const static char LOG_TAG[] = "ADC_CALI";
|
||||||
|
|
||||||
@ -33,33 +34,35 @@ static const int coeff_a_scaling = 1000000;
|
|||||||
*
|
*
|
||||||
* @note {0,0} stands for unused item
|
* @note {0,0} stands for unused item
|
||||||
* @note In case of the overflow, these coeffcients are recorded as Absolute Value
|
* @note In case of the overflow, these coeffcients are recorded as Absolute Value
|
||||||
* @note For atten0 ~ 2, error = a1 * X^2 + a2 * X + a3; For atten3, error = a1 * X^4 + a2 * X^3 + a3 * X^2 + a4 * X + a5;
|
* @note For atten0 ~ 2, error = (K0 * X^0) + (K1 * X^1) + (K2 * X^2); For atten3, error = (K0 * X^0) + (K1 * X^1) + (K2 * X^2) + (K3 * X^3) + (K4 * X^4);
|
||||||
|
* @note Above formula is rewritten from the original documentation, please note that the coefficients are re-ordered.
|
||||||
*/
|
*/
|
||||||
const static uint64_t adc_error_coef_atten[4][10][2] = {
|
const static uint64_t adc1_error_coef_atten[4][5][2] = {
|
||||||
{{9798249589, 1e15}, {50871540569528, 1e16}, {3, 1}, {0, 0}, {0, 0}, //ADC1 atten0
|
{{27856531419538344, 1e16}, {50871540569528, 1e16}, {9798249589, 1e15}, {0, 0}, {0, 0}}, //ADC1 atten0
|
||||||
{36615265189, 1e16}, {1353548869615, 1e16}, {3, 1}, {0, 0}, {0, 0}}, //ADC2 atten0
|
{{29831022915028695, 1e16}, {49393185868806, 1e16}, {101379430548, 1e16}, {0, 0}, {0, 0}}, //ADC1 atten1
|
||||||
|
{{23285545746296417, 1e16}, {147640181047414, 1e16}, {208385525314, 1e16}, {0, 0}, {0, 0}}, //ADC1 atten2
|
||||||
{{101379430548, 1e16}, {49393185868806, 1e16}, {3, 1}, {0, 0}, {0, 0}, //ADC1 atten1
|
{{644403418269478, 1e15}, {644334888647536, 1e16}, {1297891447611, 1e16}, {70769718, 1e15}, {13515, 1e15}} //ADC1 atten3
|
||||||
{118964995959, 1e16}, {66319894226185, 1e16}, {2, 1}, {0, 0}, {0, 0}}, //ADC2 atten1
|
|
||||||
|
|
||||||
{{208385525314, 1e16}, {147640181047414, 1e16}, {2, 1}, {0, 0}, {0, 0}, //ADC1 atten2
|
|
||||||
{259011467956, 1e16}, {200996773954387, 1e16}, {1, 1}, {0, 0}, {0, 0}}, //ADC2 atten2
|
|
||||||
|
|
||||||
{{13515, 1e15}, {70769718, 1e15}, {1297891447611, 1e16}, {644334888647536, 1e16}, {1,1}, //ADC1 atten3
|
|
||||||
{15038, 1e15}, {79672528, 1e15}, {1478791187119, 1e16}, {755717904943462, 1e16}, {1,1}} //ADC2 atten3
|
|
||||||
};
|
};
|
||||||
const static int32_t adc_error_sign[4][10] = {
|
const static uint64_t adc2_error_coef_atten[4][5][2] = {
|
||||||
{1, -1, -1, 0, 0, //ADC1 atten0
|
{{25668651654328927, 1e16}, {1353548869615, 1e16}, {36615265189, 1e16}, {0, 0}, {0, 0}}, //ADC2 atten0
|
||||||
1, 1, -1, 0, 0}, //ADC2 atten0
|
{{23690184690298404, 1e16}, {66319894226185, 1e16}, {118964995959, 1e16}, {0, 0}, {0, 0}}, //ADC2 atten1
|
||||||
|
{{9452499397020617, 1e16}, {200996773954387, 1e16}, {259011467956, 1e16}, {0, 0}, {0, 0}}, //ADC2 atten2
|
||||||
{1, -1, -1, 0, 0, //ADC1 atten1
|
{{12247719764336924,1e16}, {755717904943462, 1e16}, {1478791187119, 1e16}, {79672528, 1e15}, {15038, 1e15}} //ADC2 atten3
|
||||||
1, -1, -1, 0, 0}, //ADC2 atten1
|
};
|
||||||
|
/**
|
||||||
{1, -1, -1, 0, 0, //ADC1 atten2
|
* Term sign
|
||||||
1, -1, -1, 0, 0}, //ADC2 atten2
|
*/
|
||||||
|
const static int32_t adc1_error_sign[4][5] = {
|
||||||
{1, -1, 1, -1, -1, //ADC1 atten3
|
{-1, -1, 1, 0, 0}, //ADC1 atten0
|
||||||
1, -1, 1, -1, 1} //ADC2 atten3
|
{-1, -1, 1, 0, 0}, //ADC1 atten1
|
||||||
|
{-1, -1, 1, 0, 0}, //ADC1 atten2
|
||||||
|
{-1, -1, 1, -1, 1} //ADC1 atten3
|
||||||
|
};
|
||||||
|
const static int32_t adc2_error_sign[4][5] = {
|
||||||
|
{-1, 1, 1, 0, 0}, //ADC2 atten0
|
||||||
|
{-1, -1, 1, 0, 0}, //ADC2 atten1
|
||||||
|
{-1, -1, 1, 0, 0}, //ADC2 atten2
|
||||||
|
{ 1, -1, 1, -1, 1} //ADC2 atten3
|
||||||
};
|
};
|
||||||
|
|
||||||
/* -------------------- Characterization Helper Data Types ------------------ */
|
/* -------------------- Characterization Helper Data Types ------------------ */
|
||||||
@ -151,47 +154,6 @@ esp_adc_cal_value_t esp_adc_cal_characterize(adc_unit_t adc_num,
|
|||||||
return ESP_ADC_CAL_VAL_EFUSE_TP_FIT;
|
return ESP_ADC_CAL_VAL_EFUSE_TP_FIT;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t get_reading_error(uint64_t v_cali_1, uint8_t adc_num, uint8_t atten)
|
|
||||||
{
|
|
||||||
if (v_cali_1 == 0) {
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
uint8_t term_max = (atten == 3) ? 5 : 3;
|
|
||||||
int32_t error = 0;
|
|
||||||
uint64_t coeff = 0;
|
|
||||||
uint64_t term[5] = {0};
|
|
||||||
|
|
||||||
/**
|
|
||||||
* For atten0 ~ 2:
|
|
||||||
* error = a1 * X^2 + a2 * X + a3;
|
|
||||||
*
|
|
||||||
* For atten3:
|
|
||||||
* error = a1 * X^4 + a2 * X^3 + a3 * X^2 + a4 * X + a5;
|
|
||||||
*/
|
|
||||||
|
|
||||||
//Calculate all the power beforehand
|
|
||||||
term[term_max-1] = 1;
|
|
||||||
term[term_max-2] = v_cali_1;
|
|
||||||
for (int term_id = term_max - 3; term_id >= 0; term_id--) {
|
|
||||||
term[term_id] = term[term_id + 1] * v_cali_1;
|
|
||||||
}
|
|
||||||
|
|
||||||
//Calculate each term
|
|
||||||
uint8_t coef_id_start = (adc_num == ADC_UNIT_1) ? 0 : 5;
|
|
||||||
for (int i = 0; i < term_max; i++) {
|
|
||||||
coeff = adc_error_coef_atten[atten][coef_id_start + i][0];
|
|
||||||
term[i] = term[i] * coeff;
|
|
||||||
ESP_LOGV(LOG_TAG, "big coef is %llu, big term%d is %llu, coef_id is %d", coeff, i, term[i], coef_id_start + i);
|
|
||||||
|
|
||||||
term[i] = term[i] / adc_error_coef_atten[atten][coef_id_start + i][1];
|
|
||||||
error += (int32_t)term[i] * adc_error_sign[atten][i];
|
|
||||||
ESP_LOGV(LOG_TAG, "term%d is %llu, error is %d", i, term[i], error);
|
|
||||||
}
|
|
||||||
|
|
||||||
return error;
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32_t esp_adc_cal_raw_to_voltage(uint32_t adc_reading, const esp_adc_cal_characteristics_t *chars)
|
uint32_t esp_adc_cal_raw_to_voltage(uint32_t adc_reading, const esp_adc_cal_characteristics_t *chars)
|
||||||
{
|
{
|
||||||
assert(chars != NULL);
|
assert(chars != NULL);
|
||||||
@ -209,7 +171,15 @@ uint32_t esp_adc_cal_raw_to_voltage(uint32_t adc_reading, const esp_adc_cal_char
|
|||||||
v_cali_1 = v_cali_1 / coeff_a_scaling;
|
v_cali_1 = v_cali_1 / coeff_a_scaling;
|
||||||
ESP_LOGV(LOG_TAG, "v_cali_1 is %llu", v_cali_1);
|
ESP_LOGV(LOG_TAG, "v_cali_1 is %llu", v_cali_1);
|
||||||
|
|
||||||
error = get_reading_error(v_cali_1, chars->adc_num, chars->atten);
|
//Curve Fitting error correction
|
||||||
|
esp_adc_error_calc_param_t param = {
|
||||||
|
.v_cali_input = v_cali_1,
|
||||||
|
.term_num = (chars->atten == 3) ? 5 : 3,
|
||||||
|
.coeff = (chars->adc_num == ADC_UNIT_1) ? &adc1_error_coef_atten : &adc2_error_coef_atten,
|
||||||
|
.sign = (chars->adc_num == ADC_UNIT_1) ? &adc1_error_sign : &adc2_error_sign,
|
||||||
|
};
|
||||||
|
error = esp_adc_cal_get_reading_error(¶m, chars->atten);
|
||||||
|
|
||||||
voltage = (int32_t)v_cali_1 - error;
|
voltage = (int32_t)v_cali_1 - error;
|
||||||
|
|
||||||
return voltage;
|
return voltage;
|
@ -13,6 +13,7 @@
|
|||||||
#include "driver/adc.h"
|
#include "driver/adc.h"
|
||||||
#include "hal/adc_types.h"
|
#include "hal/adc_types.h"
|
||||||
#include "esp_adc_cal.h"
|
#include "esp_adc_cal.h"
|
||||||
|
#include "esp_adc_cal_internal.h"
|
||||||
|
|
||||||
const __attribute__((unused)) static char *TAG = "ADC_CALI";
|
const __attribute__((unused)) static char *TAG = "ADC_CALI";
|
||||||
|
|
||||||
@ -39,3 +40,49 @@ esp_err_t esp_adc_cal_get_voltage(adc_channel_t channel,
|
|||||||
}
|
}
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if ESP_ADC_CAL_CURVE_FITTING_SUPPORTED
|
||||||
|
/*------------------------------------------------------------------------------
|
||||||
|
* Private API
|
||||||
|
*----------------------------------------------------------------------------*/
|
||||||
|
int32_t esp_adc_cal_get_reading_error(const esp_adc_error_calc_param_t *param, uint8_t atten)
|
||||||
|
{
|
||||||
|
if (param->v_cali_input == 0) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint64_t v_cali_1 = param->v_cali_input;
|
||||||
|
uint8_t term_num = param->term_num;
|
||||||
|
int32_t error = 0;
|
||||||
|
uint64_t coeff = 0;
|
||||||
|
uint64_t variable[term_num];
|
||||||
|
uint64_t term[term_num];
|
||||||
|
memset(variable, 0, term_num * sizeof(uint64_t));
|
||||||
|
memset(term, 0, term_num * sizeof(uint64_t));
|
||||||
|
|
||||||
|
/**
|
||||||
|
* For atten0 ~ 2:
|
||||||
|
* error = (K0 * X^0) + (K1 * X^1) + (K2 * X^2);
|
||||||
|
*
|
||||||
|
* For atten3:
|
||||||
|
* error = (K0 * X^0) + (K1 * X^1) + (K2 * X^2) + (K3 * X^3) + (K4 * X^4);
|
||||||
|
*/
|
||||||
|
variable[0] = 1;
|
||||||
|
coeff = (*param->coeff)[atten][0][0];
|
||||||
|
term[0] = variable[0] * coeff / (*param->coeff)[atten][0][1];
|
||||||
|
error = (int32_t)term[0] * (*param->sign)[atten][0];
|
||||||
|
|
||||||
|
for (int i = 1; i < term_num; i++) {
|
||||||
|
variable[i] = variable[i-1] * v_cali_1;
|
||||||
|
coeff = (*param->coeff)[atten][i][0];
|
||||||
|
term[i] = variable[i] * coeff;
|
||||||
|
ESP_LOGV(TAG, "big coef is %llu, big term%d is %llu, coef_id is %d", coeff, i, term[i], i);
|
||||||
|
|
||||||
|
term[i] = term[i] / (*param->coeff)[atten][i][1];
|
||||||
|
error += (int32_t)term[i] * (*param->sign)[atten][i];
|
||||||
|
ESP_LOGV(TAG, "term%d is %llu, error is %d", i, term[i], error);
|
||||||
|
}
|
||||||
|
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
#endif //#if ESP_ADC_CAL_CURVE_FITTING_SUPPORTED
|
||||||
|
50
components/esp_adc_cal/esp_adc_cal_internal.h
Normal file
50
components/esp_adc_cal/esp_adc_cal_internal.h
Normal file
@ -0,0 +1,50 @@
|
|||||||
|
/*
|
||||||
|
* SPDX-FileCopyrightText: 2020-2022 Espressif Systems (Shanghai) CO LTD
|
||||||
|
*
|
||||||
|
* SPDX-License-Identifier: Apache-2.0
|
||||||
|
*/
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
#include "sdkconfig.h"
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
extern "C" {
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if CONFIG_IDF_TARGET_ESP32C3 || CONFIG_IDF_TARGET_ESP32S3
|
||||||
|
#define ESP_ADC_CAL_CURVE_FITTING_SUPPORTED 1
|
||||||
|
|
||||||
|
#define COEFF_GROUP_NUM 4
|
||||||
|
#define TERM_MAX 5
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if ESP_ADC_CAL_CURVE_FITTING_SUPPORTED
|
||||||
|
/**
|
||||||
|
* Calculation parameters used for curve fitting calibration algorithm error
|
||||||
|
*
|
||||||
|
* @note For atten0 ~ 2, error = (K0 * X^0) + (K1 * X^1) + (K2 * X^2); For atten3, error = (K0 * X^0) + (K1 * X^1) + (K2 * X^2) + (K3 * X^3) + (K4 * X^4);
|
||||||
|
* Where X is the `v_cali_input`.
|
||||||
|
*/
|
||||||
|
typedef struct {
|
||||||
|
uint64_t v_cali_input; //Input to calculate the error
|
||||||
|
uint8_t term_num; //Term number of the algorithm formula
|
||||||
|
const uint64_t (*coeff)[COEFF_GROUP_NUM][TERM_MAX][2]; //Coeff of each term. See `adc_error_coef_atten` for details (and the magic number 2)
|
||||||
|
const int32_t (*sign)[COEFF_GROUP_NUM][TERM_MAX]; //Sign of each term
|
||||||
|
} esp_adc_error_calc_param_t;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Calculate the curve fitting error
|
||||||
|
*
|
||||||
|
* @param param see `esp_adc_error_calc_param_t`
|
||||||
|
* @param atten ADC attenuation
|
||||||
|
*/
|
||||||
|
int32_t esp_adc_cal_get_reading_error(const esp_adc_error_calc_param_t *param, uint8_t atten);
|
||||||
|
|
||||||
|
#endif //#if ESP_ADC_CAL_CURVE_FITTING_SUPPORTED
|
||||||
|
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
}
|
||||||
|
#endif
|
@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* SPDX-FileCopyrightText: 2015-2021 Espressif Systems (Shanghai) CO LTD
|
* SPDX-FileCopyrightText: 2015-2022 Espressif Systems (Shanghai) CO LTD
|
||||||
*
|
*
|
||||||
* SPDX-License-Identifier: Apache-2.0
|
* SPDX-License-Identifier: Apache-2.0
|
||||||
*/
|
*/
|
||||||
|
Loading…
x
Reference in New Issue
Block a user