From 1d5e760e8907b088324f1ef8c367fd90e4ef33de Mon Sep 17 00:00:00 2001 From: leo Date: Sat, 3 Dec 2022 21:45:24 +0100 Subject: [PATCH] battery ? --- components/BTlib/BTlib_nimble.c | 77 ++++++++++++++++-- components/BTlib/include/BTlib_nimble.h | 17 ++++ components/configuration/CMakeLists.txt | 2 +- components/configuration/configuration.c | 42 +++++++++- .../configuration/include/configuration.h | 22 ++++- default_conf.csv | 7 ++ main/CO2_Sense.c | 47 +++++++++-- main/CO2_Sense.h | 4 + main/Kconfig.projbuild | 14 ++++ nvs.bin | Bin 24576 -> 24576 bytes sdkconfig | 7 ++ 11 files changed, 217 insertions(+), 22 deletions(-) diff --git a/components/BTlib/BTlib_nimble.c b/components/BTlib/BTlib_nimble.c index fc4db3b..abad4ff 100644 --- a/components/BTlib/BTlib_nimble.c +++ b/components/BTlib/BTlib_nimble.c @@ -1,5 +1,6 @@ #include "host/ble_gap.h" #include "nimble/hci_common.h" +#include "os/os_mbuf.h" #include "sdkconfig.h" #ifdef CONFIG_BT_NIMBLE_ENABLED @@ -16,7 +17,8 @@ static configuration_data_t* main_app_conf; static uint8_t ble_addr_type; static uint16_t conn_handle; -static uint16_t hrm_handle[ES_CHAR_NB]; +static uint16_t es_handle[ES_CHAR_NB]; +static uint16_t batt_handle[BATT_CHAR_NB]; static uint8_t notify_state[ES_CHAR_NB]; static int ble_gap_event(struct ble_gap_event *event, void* arg); @@ -25,6 +27,8 @@ static int gatt_svr_chr_access_co2(uint16_t conn_handle, uint16_t attr_handle, s static int gatt_svr_chr_access_temp(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg); static int gatt_svr_chr_access_hum(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg); +static int gatt_svr_chr_access_batt_level(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg); + static int gatt_svr_init(void); ES_char_descr_t CO2_char_descr = { @@ -60,6 +64,14 @@ char_pres_format_t CO2_char_pres_format = { .descr = NSP_DESC_MAIN, }; +char_pres_format_t batt_level_char_pres_format = { + .format = FORMAT_UINT8, + .exponent = 0, + .unit = PERCENT_UNIT_UUID, + .namespc = 1, + .descr = NSP_DESC_MAIN, +}; + struct ble_hs_adv_fields adv_fields = { .flags = BLE_HS_ADV_F_DISC_GEN | BLE_HS_ADV_F_BREDR_UNSUP, .tx_pwr_lvl_is_present = 1, @@ -97,7 +109,7 @@ static struct ble_gatt_svc_def gatt_svr_svcs[] = { [ES_CHAR_CO2] = { .uuid = BLE_UUID16_DECLARE(CHAR_CO2_UUID), .access_cb = gatt_svr_chr_access_co2, - .val_handle = &hrm_handle[ES_CHAR_CO2], + .val_handle = &es_handle[ES_CHAR_CO2], .flags = BLE_GATT_CHR_F_READ | BLE_GATT_CHR_F_NOTIFY, .descriptors = (struct ble_gatt_dsc_def[]){ { @@ -117,7 +129,7 @@ static struct ble_gatt_svc_def gatt_svr_svcs[] = { [ES_CHAR_TEMP] = { .uuid = BLE_UUID16_DECLARE(CHAR_TEMP_UUID), .access_cb = gatt_svr_chr_access_temp, - .val_handle = &hrm_handle[ES_CHAR_TEMP], + .val_handle = &es_handle[ES_CHAR_TEMP], .flags = BLE_GATT_CHR_F_READ | BLE_GATT_CHR_F_NOTIFY, .descriptors = (struct ble_gatt_dsc_def[]){ { @@ -133,7 +145,7 @@ static struct ble_gatt_svc_def gatt_svr_svcs[] = { [ES_CHAR_HUM] = { .uuid = BLE_UUID16_DECLARE(CHAR_HUM_UUID), .access_cb = gatt_svr_chr_access_hum, - .val_handle = &hrm_handle[ES_CHAR_HUM], + .val_handle = &es_handle[ES_CHAR_HUM], .flags = BLE_GATT_CHR_F_READ | BLE_GATT_CHR_F_NOTIFY, .descriptors = (struct ble_gatt_dsc_def[]){ { @@ -148,6 +160,28 @@ static struct ble_gatt_svc_def gatt_svr_svcs[] = { { 0 }, }, }, + [BATT_SVC_IDX] = { + // Battery service + .type = BLE_GATT_SVC_TYPE_PRIMARY, + .uuid = BLE_UUID16_DECLARE(BATT_SVC_UUID), + .characteristics = (struct ble_gatt_chr_def[]){ + [BATT_CHAR_LEVEL] = { + .uuid = BLE_UUID16_DECLARE(BATT_LEVEL_UUID), + .access_cb = gatt_svr_chr_access_batt_level, + .val_handle = &batt_handle[BATT_CHAR_LEVEL], + .flags = BLE_GATT_CHR_F_READ | BLE_GATT_CHR_F_NOTIFY, + .descriptors = (struct ble_gatt_dsc_def[]){ + { + .uuid = BLE_UUID16_DECLARE(CHAR_PRES_FORMAT), + .att_flags = BLE_ATT_F_READ, + .access_cb = gatt_svr_chr_access_batt_level, + }, + { 0 }, + }, + }, + { 0 }, + }, + }, { 0 }, }; @@ -215,7 +249,31 @@ static int gatt_svr_chr_access_hum(uint16_t conn_handle, uint16_t attr_handle, s } - +static int gatt_svr_chr_access_batt_level(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg){ + int rc = 0; + + ESP_LOGI(NIMBLE_LOG_TAG, "batt_level access event"); + + switch(ctxt->op){ + case BLE_GATT_ACCESS_OP_READ_CHR: + { + uint8_t battery_level = main_app_conf->battery_conf->data->battery_percent; + rc = os_mbuf_append(ctxt->om, &battery_level, sizeof(battery_level)); + } + break; + case BLE_GATT_ACCESS_OP_READ_DSC: + { + uint16_t uuid = ble_uuid_u16(ctxt->dsc->uuid); + switch(uuid){ + case CHAR_PRES_FORMAT: + rc = os_mbuf_append(ctxt->om, &batt_level_char_pres_format, 7); + break; + } + } + break; + } + return rc == 0 ? 0 : BLE_ATT_ERR_INSUFFICIENT_RES; +} static void ble_advertise(void){ ESP_ERROR_CHECK(ble_gap_adv_set_fields(&adv_fields)); @@ -245,7 +303,7 @@ static int ble_gap_event(struct ble_gap_event *event, void* arg){ case BLE_GAP_EVENT_SUBSCRIBE: ESP_LOGI(NIMBLE_LOG_TAG, "subscribe event notify : %d", event->subscribe.attr_handle); for(int i=0; isubscribe.attr_handle == hrm_handle[i]){ + if(event->subscribe.attr_handle == es_handle[i]){ ESP_LOGI(NIMBLE_LOG_TAG, "enabling notifs for %d", i); notify_state[i] = event->subscribe.cur_notify; } @@ -288,6 +346,7 @@ static void ble_host_task(void* param){ void initBle(configuration_data_t* main_conf){ main_app_conf = main_conf; + ESP_LOGI("MAIN", "%s\n", main_conf->hostname); adv_fields.name = (uint8_t*)&main_conf->hostname; adv_fields.name_len = strlen(main_conf->hostname); //ESP_ERROR_CHECK(esp_nimble_hci_and_controller_init()); @@ -306,19 +365,19 @@ void ble_sensor_notify(){ ESP_LOGI(NIMBLE_LOG_TAG, "notify co2"); uint16_t co2 = main_app_conf->measure->co2; struct os_mbuf* om = ble_hs_mbuf_from_flat(&co2, sizeof(co2)); - ESP_ERROR_CHECK(ble_gattc_notify_custom(conn_handle, hrm_handle[ES_CHAR_CO2], om)); + ESP_ERROR_CHECK(ble_gattc_notify_custom(conn_handle, es_handle[ES_CHAR_CO2], om)); } if(notify_state[ES_CHAR_TEMP]){ ESP_LOGI(NIMBLE_LOG_TAG, "notify temp"); int16_t temp = main_app_conf->measure->temperature / 10; struct os_mbuf* om = ble_hs_mbuf_from_flat(&temp, sizeof(temp)); - ESP_ERROR_CHECK(ble_gattc_notify_custom(conn_handle, hrm_handle[ES_CHAR_TEMP], om)); + ESP_ERROR_CHECK(ble_gattc_notify_custom(conn_handle, es_handle[ES_CHAR_TEMP], om)); } if(notify_state[ES_CHAR_HUM]){ ESP_LOGI(NIMBLE_LOG_TAG, "notify hum"); int16_t hum = main_app_conf->measure->humidity / 10; struct os_mbuf* om = ble_hs_mbuf_from_flat(&hum, sizeof(hum)); - ESP_ERROR_CHECK(ble_gattc_notify_custom(conn_handle, hrm_handle[ES_CHAR_HUM], om)); + ESP_ERROR_CHECK(ble_gattc_notify_custom(conn_handle, es_handle[ES_CHAR_HUM], om)); } } #endif diff --git a/components/BTlib/include/BTlib_nimble.h b/components/BTlib/include/BTlib_nimble.h index 07ef39c..829659e 100644 --- a/components/BTlib/include/BTlib_nimble.h +++ b/components/BTlib/include/BTlib_nimble.h @@ -15,9 +15,15 @@ #define CHAR_HUM_UUID 0x2A6F #define CO2_SENSOR_APPEARANCE 0x054A #define CHAR_PRES_FORMAT 0x2904 + #define PPM_UNIT_UUID 0x27C4 +#define PERCENT_UNIT_UUID 0x27AD + #define NSP_DESC_MAIN 0x0106 +#define BATT_SVC_UUID 0x180F +#define BATT_LEVEL_UUID 0x2A19 + #define DEFAULT_NAME "CO2_ble" #define DEFAULT_NAME_LEN 7 @@ -104,7 +110,9 @@ enum { enum{ ES_SVC_IDX, + BATT_SVC_IDX, }; + enum{ ES_CHAR_CO2, ES_CHAR_TEMP, @@ -131,6 +139,15 @@ struct char_pres_format { }; typedef struct char_pres_format char_pres_format_t; +enum{ + BATT_CHAR_LEVEL, + BATT_CHAR_NB, +}; + +struct batt_level_char_descr { + +}; + void initBle(configuration_data_t* main_conf); void ble_sensor_notify(); #endif diff --git a/components/configuration/CMakeLists.txt b/components/configuration/CMakeLists.txt index 3d5ff75..3855e2e 100644 --- a/components/configuration/CMakeLists.txt +++ b/components/configuration/CMakeLists.txt @@ -1,3 +1,3 @@ idf_component_register(SRCS "configuration.c" INCLUDE_DIRS "include" - REQUIRES sensirion_i2c_scd4x APlib ledController nvs_flash) + REQUIRES sensirion_i2c_scd4x APlib ledController nvs_flash esp_adc) diff --git a/components/configuration/configuration.c b/components/configuration/configuration.c index 470bbba..efc0a8c 100644 --- a/components/configuration/configuration.c +++ b/components/configuration/configuration.c @@ -1,15 +1,51 @@ +#include #include +#include +#include #include "configuration.h" #include "scd4x_data.h" #include "nvs_flash.h" +#include "sdkconfig.h" +#include "esp_log.h" -void init_conf_from_nvs(configuration_data_t* conf, nvs_handle_t nvs){ +void init_conf_from_nvs(configuration_data_t* conf){ + nvs_handle_t nvs; + ESP_ERROR_CHECK(nvs_open("battms", NVS_READONLY, &nvs)); + conf->battery_conf = get_battery_configuration(nvs); + + ESP_ERROR_CHECK(nvs_open("leds", NVS_READONLY, &nvs)); conf->leds = get_led_configuration(nvs); nvs_get_u8(nvs, "led_nb", &conf->led_nb); + + ESP_ERROR_CHECK(nvs_open("main", NVS_READONLY, &nvs)); // todo: move to namespaces conf->sensor = get_sensor_configuration(nvs); conf->measure = conf->sensor->measure; nvs_get_u8(nvs, "wireless_conf", &conf->wireless); conf->wifi_config = get_ap_config(nvs); - size_t str_size; - nvs_get_str(nvs, "name", conf->hostname, &str_size); + size_t str_size = sizeof(conf->hostname); + ESP_ERROR_CHECK(nvs_get_str(nvs, "name", conf->hostname, &str_size)); + ESP_LOGI("AAA", "%d", str_size); } + +battery_conf_t* get_battery_configuration(nvs_handle_t nvs){ + battery_conf_t* conf = malloc(sizeof(battery_conf_t)); + ESP_ERROR_CHECK(nvs_get_u16(nvs, "poll_delay", &conf->poll_delay)); + + uint16_t min_v, max_v; + nvs_get_u16(nvs, "min_v", &min_v); + nvs_get_u16(nvs, "max_v", &max_v); + + uint16_t min_raw = min_v * (1<data = data_h; + conf->adc_channel = CONFIG_BATTMS_CHANNEL; + return conf; +} \ No newline at end of file diff --git a/components/configuration/include/configuration.h b/components/configuration/include/configuration.h index cf50190..b99723f 100644 --- a/components/configuration/include/configuration.h +++ b/components/configuration/include/configuration.h @@ -1,12 +1,31 @@ #ifndef CONFIGURATION_H #define CONFIGURATION_H +#include "nvs.h" #include "nvs_flash.h" +#include "esp_adc/adc_oneshot.h" #include "scd4x_data.h" #include "APlib.h" #include "ledController.h" +struct battery_data { + uint8_t battery_percent; + uint16_t min_raw; // 0% as a raw adc reading + uint16_t scale; // scaling between raw adc reading and percent +}; +typedef struct battery_data battery_data_t; + +struct battery_conf { + battery_data_t* data; + adc_channel_t adc_channel; + adc_oneshot_unit_handle_t* adc_handle; + uint16_t poll_delay; +}; +typedef struct battery_conf battery_conf_t; + +battery_conf_t* get_battery_configuration(nvs_handle_t nvs); + struct configuration_data { scd4x_data_t* measure; scd4x_config_t* sensor; @@ -15,9 +34,10 @@ struct configuration_data { uint8_t wireless; wifi_config_t* wifi_config; char hostname[16]; + battery_conf_t* battery_conf; }; typedef struct configuration_data configuration_data_t; -void init_conf_from_nvs(configuration_data_t* conf, nvs_handle_t nvs); +void init_conf_from_nvs(configuration_data_t* conf); #endif diff --git a/default_conf.csv b/default_conf.csv index edff8e1..c048d2a 100644 --- a/default_conf.csv +++ b/default_conf.csv @@ -6,7 +6,14 @@ wireless_conf,data,u8,4 ap_ssid,data,string,CO2Sense ap_pass,data,string,testtest sensor_conf,data,u16,22 +# +leds,namespace,, led_nb,data,u8,3 led1_conf,data,hex2bin,0400DC051027640001FF led2_conf,data,hex2bin,0500BC02DB05640001FF led3_conf,data,hex2bin,06000000BB02640001FF +# +battms,namespace,, +poll_delay,data,u16,10000 +min_v,data,u16,370 +max_v,data,u16,420 \ No newline at end of file diff --git a/main/CO2_Sense.c b/main/CO2_Sense.c index dfbfdca..10d5f52 100644 --- a/main/CO2_Sense.c +++ b/main/CO2_Sense.c @@ -1,5 +1,6 @@ #include "CO2_Sense.h" #include +#include "configuration.h" #include "freertos/FreeRTOS.h" #include "freertos/portmacro.h" #include "freertos/task.h" @@ -15,9 +16,11 @@ #include "esp_pm.h" #include "driver/gpio.h" #include "driver/i2c.h" +#include "esp_adc/adc_oneshot.h" #include "ledController.h" #include "scd4x_i2c.h" +#include "sdkconfig.h" #include "sensirion_i2c_hal.h" #include "scd4x_data.h" #include "BTlib_nimble.h" @@ -26,9 +29,6 @@ void app_main(void){ init_nvs(); - nvs_handle_t nvs_handle; - ESP_ERROR_CHECK(nvs_open("main", NVS_READWRITE, &nvs_handle)); - // setup GPIOs gpio_config_t VBAT_OK_c = { GPIO_NUM_3, @@ -44,14 +44,12 @@ void app_main(void){ .min_freq_mhz = 40, .light_sleep_enable = true, // enable light sleep }; - ESP_ERROR_CHECK(esp_pm_configure(&pm_config)); + //ESP_ERROR_CHECK(esp_pm_configure(&pm_config)); configuration_data_t* conf = malloc(sizeof(configuration_data_t)); - init_conf_from_nvs(conf, nvs_handle); + init_conf_from_nvs(conf); - uint8_t led_nb=0; - ESP_ERROR_CHECK(nvs_get_u8(nvs_handle, "led_nb", &led_nb)); // init LEDs driver init_led_driver(conf->leds, conf->led_nb); @@ -61,7 +59,11 @@ void app_main(void){ // start sensor init_i2c(); init_scd4x(); - + + init_battery_level_adc(conf->battery_conf); + TaskHandle_t battms_update_handle; + xTaskCreate(update_battery_level, "BATTMS_update", 4096, conf->battery_conf, tskIDLE_PRIORITY, &battms_update_handle); + uint8_t id=0; MMC56x3_get_product_ID(&id); ESP_LOGI("MAIN", "MMC5603 product id %d", id); @@ -134,3 +136,32 @@ void init_scd4x(){ scd4x_stop_periodic_measurement(); scd4x_reinit(); } + +void init_battery_level_adc(battery_conf_t* batt_conf){ + adc_oneshot_unit_init_cfg_t init_config1 = { + .unit_id = ADC_UNIT_1, + .ulp_mode = ADC_ULP_MODE_DISABLE, + }; + ESP_ERROR_CHECK(adc_oneshot_new_unit(&init_config1, batt_conf->adc_handle)); + + adc_oneshot_chan_cfg_t config = { + .bitwidth = ADC_BITWIDTH_DEFAULT, + .atten = ADC_ATTEN_DB_11, + }; + ESP_ERROR_CHECK(adc_oneshot_config_channel(*batt_conf->adc_handle, batt_conf->adc_channel, &config)); +} + +void update_battery_level(void* pvParameters){// battery_data_t* data, uint8_t channel, adc_oneshot_unit_handle_t* handle){ + battery_conf_t* batt_conf = pvParameters; + int val_raw = 0; + while(1){ + esp_err_t res = adc_oneshot_read(*(batt_conf->adc_handle), batt_conf->adc_channel, &val_raw); + if(res != ESP_ERR_TIMEOUT){ // valeur invalide + ESP_ERROR_CHECK(res); + battery_data_t* data = batt_conf->data; + data->battery_percent = (val_raw - data->min_raw) * data->scale; + ESP_LOGI("BATTMS", "raw : %d, percent : %d", val_raw, data->battery_percent); + } + vTaskDelay(batt_conf->poll_delay / portTICK_PERIOD_MS); + } +} \ No newline at end of file diff --git a/main/CO2_Sense.h b/main/CO2_Sense.h index 407ecff..e1852fc 100644 --- a/main/CO2_Sense.h +++ b/main/CO2_Sense.h @@ -1,6 +1,7 @@ #include "ledController.h" #include "nvs.h" #include "configuration.h" +#include "esp_adc/adc_oneshot.h" void fetch_sensor_task(void* pvParameters); void init_nvs(void); @@ -9,3 +10,6 @@ void init_http_server(configuration_data_t* main_conf); void init_i2c(); void init_scd4x(); led_disp_config_t* generate_led_conf(nvs_handle_t nvs, unsigned int nb); + +void init_battery_level_adc(battery_conf_t* batt_conf); +void update_battery_level(void* pvParameters); diff --git a/main/Kconfig.projbuild b/main/Kconfig.projbuild index 56d8827..21930a6 100644 --- a/main/Kconfig.projbuild +++ b/main/Kconfig.projbuild @@ -14,4 +14,18 @@ menu "CO2Sense config" help The SCL pin endmenu + menu "Battery" + config BATTMS_CHANNEL + int "channel" + range 0 10 + default 4 + help + BATTMS channel, the pin where the battery voltage divider is connected (!ADC Channel NOT pin, see datasheet) + config BATTMS_ADC_BITWIDTH + int "bitwidth" + range 9 13 + default 9 + help + adc sample bitwidth + endmenu endmenu diff --git a/nvs.bin b/nvs.bin index 12dcf1bd46d56c7cb6bad8d990cc9157c9236378..dfd5f4c6651443efd38b4359ac9ccaa05a83d664 100644 GIT binary patch delta 350 zcmZoTz}Rqrae@lds#TL0GD&T8P+;_6U}XG%`0T3o-@!pu+!DykuKWN{G`0)FJ)=$=}?_t&^LX7hi_(B|{M-SYG-+NWs#%$INpR SD^L_HVcfis=@`!g8LL zS1?*=FnTclFEJ9R04g?&PtMOvgDU3&(u@rM|AQ32O!zD~nS%+Uc=`rDW}sptT#7d` fx#dmHV6u<{napW?We!lWF{a|piULWziv$7y*vB@` diff --git a/sdkconfig b/sdkconfig index e2889f8..ee3345b 100644 --- a/sdkconfig +++ b/sdkconfig @@ -362,6 +362,13 @@ CONFIG_PARTITION_TABLE_MD5=y CONFIG_SDA_PIN=10 CONFIG_SCL_PIN=9 # end of I2C pins + +# +# Battery +# +CONFIG_BATTMS_CHANNEL=4 +CONFIG_BATTMS_ADC_BITWIDTH=9 +# end of Battery # end of CO2Sense config #