diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index 1d68d2f601..703e011c35 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -46,6 +46,10 @@ build_template_app: - sed -i.bak -e's/CONFIG_OPTIMIZATION_LEVEL_DEBUG\=y/CONFIG_OPTIMIZATION_LEVEL_RELEASE=y/' sdkconfig - make defconfig - make all V=1 + # Check if there are any stray printf/ets_printf references in WiFi libs + - cd ../components/esp32/lib + - test $(xtensa-esp32-elf-nm *.a | grep -w printf | wc -l) -eq 0 + - test $(xtensa-esp32-elf-nm *.a | grep -w ets_printf | wc -l) -eq 0 .build_gitlab: &build_template @@ -88,7 +92,7 @@ build_esp_idf_tests: - cd tools/unit-test-app - git checkout ${CI_BUILD_REF_NAME} || echo "Using default branch..." - make defconfig - - make + - make TESTS_ALL=1 build_examples: <<: *build_template @@ -288,7 +292,7 @@ deploy_docs: variables: # jobs MUST set CONFIG_FILE in before_script, and overwrite the variables above if necessary LOCAL_ENV_CONFIG_PATH: /home/gitlab-runner/LocalConfig/ESP32_IDF - BIN_PATH: "$CI_PROJECT_DIR/esp-idf-tests/build/" + BIN_PATH: "$CI_PROJECT_DIR/tools/unit-test-app/build/" LOG_PATH: "$CI_PROJECT_DIR/$CI_BUILD_REF" APP_NAME: "ut" TEST_CASE_FILE_PATH: "$CI_PROJECT_DIR/components/idf_test/unit_test" diff --git a/components/app_update/component.mk b/components/app_update/component.mk new file mode 100755 index 0000000000..c2c4c03a1a --- /dev/null +++ b/components/app_update/component.mk @@ -0,0 +1,5 @@ +# +# Component Makefile +# +# (Uses default behaviour of compiling all source files in directory, adding 'include' to include path.) + diff --git a/components/app_update/esp_ota_ops.c b/components/app_update/esp_ota_ops.c new file mode 100644 index 0000000000..0c1a413370 --- /dev/null +++ b/components/app_update/esp_ota_ops.c @@ -0,0 +1,381 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "esp_err.h" +#include "esp_partition.h" +#include "esp_spi_flash.h" +#include "esp_image_format.h" +#include "esp_secure_boot.h" +#include "sdkconfig.h" + +#include "esp_ota_ops.h" +#include "rom/queue.h" +#include "rom/crc.h" +#include "esp_log.h" + + +#define OTA_MAX(a,b) ((a) >= (b) ? (a) : (b)) +#define OTA_MIN(a,b) ((a) <= (b) ? (a) : (b)) +#define SUB_TYPE_ID(i) (i & 0x0F) + +typedef struct ota_ops_entry_ { + uint32_t handle; + esp_partition_t part; + uint32_t erased_size; + uint32_t wrote_size; + LIST_ENTRY(ota_ops_entry_) entries; +} ota_ops_entry_t; + +/* OTA selection structure (two copies in the OTA data partition.) + Size of 32 bytes is friendly to flash encryption */ +typedef struct { + uint32_t ota_seq; + uint8_t seq_label[24]; + uint32_t crc; /* CRC32 of ota_seq field only */ +} ota_select; + +static LIST_HEAD(ota_ops_entries_head, ota_ops_entry_) s_ota_ops_entries_head = + LIST_HEAD_INITIALIZER(s_ota_ops_entries_head); + +static uint32_t s_ota_ops_last_handle = 0; +static ota_select s_ota_select[2]; + +const static char *TAG = "esp_ota_ops"; + +esp_err_t esp_ota_begin(const esp_partition_t *partition, size_t image_size, esp_ota_handle_t *out_handle) +{ + esp_err_t ret = ESP_OK; + + if ((partition == NULL) || (out_handle == NULL)) { + return ESP_ERR_INVALID_ARG; + } + + ota_ops_entry_t *new_entry = (ota_ops_entry_t *) calloc(sizeof(ota_ops_entry_t), 1); + + if (new_entry == 0) { + return ESP_ERR_NO_MEM; + } + + // if input image size is 0 or OTA_SIZE_UNKNOWN, will erase all areas in this partition + if ((image_size == 0) || (image_size == OTA_SIZE_UNKNOWN)) { + ret = esp_partition_erase_range(partition, 0, partition->size); + } else { + ret = esp_partition_erase_range(partition, 0, (image_size / SPI_FLASH_SEC_SIZE + 1) * SPI_FLASH_SEC_SIZE); + } + + if (ret != ESP_OK) { + free(new_entry); + new_entry = NULL; + return ret; + } + + LIST_INSERT_HEAD(&s_ota_ops_entries_head, new_entry, entries); + + if ((image_size == 0) || (image_size == OTA_SIZE_UNKNOWN)) { + new_entry->erased_size = partition->size; + } else { + new_entry->erased_size = image_size; + } + + memcpy(&new_entry->part, partition, sizeof(esp_partition_t)); + new_entry->handle = ++s_ota_ops_last_handle; + *out_handle = new_entry->handle; + return ESP_OK; +} + +esp_err_t esp_ota_write(esp_ota_handle_t handle, const void *data, size_t size) +{ + esp_err_t ret; + ota_ops_entry_t *it; + + if (data == NULL) { + ESP_LOGE(TAG, "write data is invalid"); + return ESP_ERR_INVALID_ARG; + } + + // find ota handle in linked list + for (it = LIST_FIRST(&s_ota_ops_entries_head); it != NULL; it = LIST_NEXT(it, entries)) { + if (it->handle == handle) { + // must erase the partition before writing to it + assert(it->erased_size > 0 && "must erase the partition before writing to it"); + ret = esp_partition_write(&it->part, it->wrote_size, data, size); + if(ret == ESP_OK){ + it->wrote_size += size; + } + return ret; + } + } + + //if go to here ,means don't find the handle + ESP_LOGE(TAG,"not found the handle") + return ESP_ERR_INVALID_ARG; +} + +esp_err_t esp_ota_end(esp_ota_handle_t handle) +{ + esp_err_t ret; + ota_ops_entry_t *it; + size_t image_size; + for (it = LIST_FIRST(&s_ota_ops_entries_head); it != NULL; it = LIST_NEXT(it, entries)) { + if (it->handle == handle) { + // an ota handle need to be ended after erased and wrote data in it + if ((it->erased_size == 0) || (it->wrote_size == 0)) { + return ESP_ERR_INVALID_ARG; + } + +#ifdef CONFIG_SECUREBOOTLOADER + if (esp_image_basic_verify(it->part.address, &image_size) != ESP_OK) { + return ESP_ERR_OTA_VALIDATE_FAILED; + } + ret = esp_secure_boot_verify_signature(it->part.address, image_size); + if (ret != ESP_OK) { + return ESP_ERR_OTA_VALIDATE_FAILED; + } +#endif + + LIST_REMOVE(it, entries); + break; + } + } + + if (it == NULL) { + return ESP_ERR_NOT_FOUND; + } + + free(it); + return ESP_OK; +} + +static uint32_t ota_select_crc(const ota_select *s) +{ + return crc32_le(UINT32_MAX, (uint8_t *)&s->ota_seq, 4); +} + +static bool ota_select_valid(const ota_select *s) +{ + return s->ota_seq != UINT32_MAX && s->crc == ota_select_crc(s); +} + +static esp_err_t rewrite_ota_seq(uint32_t seq, uint8_t sec_id, const esp_partition_t *ota_data_partition) +{ + esp_err_t ret; + + if (sec_id == 0 || sec_id == 1) { + s_ota_select[sec_id].ota_seq = seq; + s_ota_select[sec_id].crc = ota_select_crc(&s_ota_select[sec_id]); + ret = esp_partition_erase_range(ota_data_partition, sec_id * SPI_FLASH_SEC_SIZE, SPI_FLASH_SEC_SIZE); + if (ret != ESP_OK) { + return ret; + } else { + return esp_partition_write(ota_data_partition, SPI_FLASH_SEC_SIZE * sec_id, &s_ota_select[sec_id].ota_seq, sizeof(ota_select)); + } + } else { + return ESP_ERR_INVALID_ARG; + } +} + +static uint8_t get_ota_partition_count(void) +{ + uint16_t ota_app_count = 0; + while (esp_partition_find_first(ESP_PARTITION_TYPE_APP, ESP_PARTITION_SUBTYPE_APP_OTA_MIN + ota_app_count, NULL) != NULL) { + assert(ota_app_count < 16 && "must erase the partition before writing to it"); + ota_app_count++; + } + return ota_app_count; +} + +static esp_err_t esp_rewrite_ota_data(esp_partition_subtype_t subtype) +{ + esp_err_t ret; + const esp_partition_t *find_partition = NULL; + uint16_t ota_app_count = 0; + uint32_t i = 0; + uint32_t seq; + static spi_flash_mmap_memory_t ota_data_map; + const void *result = NULL; + + find_partition = esp_partition_find_first(ESP_PARTITION_TYPE_DATA, ESP_PARTITION_SUBTYPE_DATA_OTA, NULL); + if (find_partition != NULL) { + ota_app_count = get_ota_partition_count(); + //esp32_idf use two sector for store information about which partition is running + //it defined the two sector as ota data partition,two structure ota_select is saved in the two sector + //named data in first sector as s_ota_select[0], second sector data as s_ota_select[1] + //e.g. + //if s_ota_select[0].ota_seq == s_ota_select[1].ota_seq == 0xFFFFFFFF,means ota info partition is in init status + //so it will boot factory application(if there is),if there's no factory application,it will boot ota[0] application + //if s_ota_select[0].ota_seq != 0 and s_ota_select[1].ota_seq != 0,it will choose a max seq ,and get value of max_seq%max_ota_app_number + //and boot a subtype (mask 0x0F) value is (max_seq - 1)%max_ota_app_number,so if want switch to run ota[x],can use next formulas. + //for example, if s_ota_select[0].ota_seq = 4, s_ota_select[1].ota_seq = 5, and there are 8 ota application, + //current running is (5-1)%8 = 4,running ota[4],so if we want to switch to run ota[7], + //we should add s_ota_select[0].ota_seq (is 4) to 4 ,(8-1)%8=7,then it will boot ota[7] + //if A=(B - C)%D + //then B=(A + C)%D + D*n ,n= (0,1,2...) + //so current ota app sub type id is x , dest bin subtype is y,total ota app count is n + //seq will add (x + n*1 + 1 - seq)%n + if (SUB_TYPE_ID(subtype) >= ota_app_count) { + return ESP_ERR_NOT_FOUND; + } + + ret = esp_partition_mmap(find_partition, 0, find_partition->size, SPI_FLASH_MMAP_DATA, &result, &ota_data_map); + if (ret != ESP_OK) { + result = NULL; + return ret; + } else { + memcpy(&s_ota_select[0], result, sizeof(ota_select)); + memcpy(&s_ota_select[1], result + SPI_FLASH_SEC_SIZE, sizeof(ota_select)); + spi_flash_munmap(ota_data_map); + } + + if (ota_select_valid(&s_ota_select[0]) && ota_select_valid(&s_ota_select[1])) { + seq = OTA_MAX(s_ota_select[0].ota_seq, s_ota_select[1].ota_seq); + while (seq > (SUB_TYPE_ID(subtype) + 1) % ota_app_count + i * ota_app_count) { + i++; + } + + if (s_ota_select[0].ota_seq >= s_ota_select[1].ota_seq) { + return rewrite_ota_seq((SUB_TYPE_ID(subtype) + 1) % ota_app_count + i * ota_app_count, 0, find_partition); + } else { + return rewrite_ota_seq((SUB_TYPE_ID(subtype) + 1) % ota_app_count + i * ota_app_count, 1, find_partition); + } + + } else if (ota_select_valid(&s_ota_select[0])) { + while (s_ota_select[0].ota_seq > (SUB_TYPE_ID(subtype) + 1) % ota_app_count + i * ota_app_count) { + i++; + } + return rewrite_ota_seq((SUB_TYPE_ID(subtype) + 1) % ota_app_count + i * ota_app_count, 1, find_partition); + + } else if (ota_select_valid(&s_ota_select[1])) { + while (s_ota_select[1].ota_seq > (SUB_TYPE_ID(subtype) + 1) % ota_app_count + i * ota_app_count) { + i++; + } + return rewrite_ota_seq((SUB_TYPE_ID(subtype) + 1) % ota_app_count + i * ota_app_count, 0, find_partition); + + } else if (s_ota_select[0].ota_seq == 0xFFFFFFFF && s_ota_select[1].ota_seq == 0xFFFFFFFF) { + return rewrite_ota_seq(SUB_TYPE_ID(subtype) + 1, 0, find_partition); + + } else { + return ESP_ERR_OTA_SELECT_INFO_INVALID; + } + + } else { + return ESP_ERR_NOT_FOUND; + } +} + +esp_err_t esp_ota_set_boot_partition(const esp_partition_t *partition) +{ + const esp_partition_t *find_partition = NULL; + size_t image_size; + if (partition == NULL) { + return ESP_ERR_INVALID_ARG; + } + +#ifdef CONFIG_SECUREBOOTLOADER + if (esp_image_basic_verify(partition->address, &image_size) != ESP_OK) { + return ESP_ERR_OTA_VALIDATE_FAILED; + } + ret = esp_secure_boot_verify_signature(partition->address, image_size); + if (ret != ESP_OK) { + return ESP_ERR_OTA_VALIDATE_FAILED; + } +#endif + // if set boot partition to factory bin ,just format ota info partition + if (partition->type == ESP_PARTITION_TYPE_APP) { + if (partition->subtype == ESP_PARTITION_SUBTYPE_APP_FACTORY) { + find_partition = esp_partition_find_first(ESP_PARTITION_TYPE_DATA, ESP_PARTITION_SUBTYPE_DATA_OTA, NULL); + if (find_partition != NULL) { + return esp_partition_erase_range(find_partition, 0, find_partition->size); + } else { + return ESP_ERR_NOT_FOUND; + } + } else { + // try to find this partition in flash,if not find it ,return error + find_partition = esp_partition_find_first(ESP_PARTITION_TYPE_DATA, ESP_PARTITION_SUBTYPE_DATA_OTA, NULL); + if (find_partition != NULL) { + return esp_rewrite_ota_data(partition->subtype); + } else { + return ESP_ERR_NOT_FOUND; + } + } + } else { + return ESP_ERR_INVALID_ARG; + } +} + +const esp_partition_t *esp_ota_get_boot_partition(void) +{ + esp_err_t ret; + const esp_partition_t *find_partition = NULL; + static spi_flash_mmap_memory_t ota_data_map; + const void *result = NULL; + uint16_t ota_app_count = 0; + find_partition = esp_partition_find_first(ESP_PARTITION_TYPE_DATA, ESP_PARTITION_SUBTYPE_DATA_OTA, NULL); + + if (find_partition == NULL) { + ESP_LOGE(TAG, "not found ota data"); + return NULL; + } + + ret = esp_partition_mmap(find_partition, 0, find_partition->size, SPI_FLASH_MMAP_DATA, &result, &ota_data_map); + if (ret != ESP_OK) { + spi_flash_munmap(ota_data_map); + ESP_LOGE(TAG, "mmap ota data filed"); + return NULL; + } else { + memcpy(&s_ota_select[0], result, sizeof(ota_select)); + memcpy(&s_ota_select[1], result + 0x1000, sizeof(ota_select)); + spi_flash_munmap(ota_data_map); + } + ota_app_count = get_ota_partition_count(); + + ESP_LOGD(TAG, "found ota bin max = %d", ota_app_count); + if (s_ota_select[0].ota_seq == 0xFFFFFFFF && s_ota_select[1].ota_seq == 0xFFFFFFFF) { + ESP_LOGD(TAG, "finding factory bin......"); + + return esp_partition_find_first(ESP_PARTITION_TYPE_APP, ESP_PARTITION_SUBTYPE_APP_FACTORY, NULL); + } else if (ota_select_valid(&s_ota_select[0]) && ota_select_valid(&s_ota_select[1])) { + ESP_LOGD(TAG, "finding ota_%d bin......", \ + ESP_PARTITION_SUBTYPE_APP_OTA_MIN + ((OTA_MAX(s_ota_select[0].ota_seq, s_ota_select[1].ota_seq) - 1) % ota_app_count)); + + return esp_partition_find_first(ESP_PARTITION_TYPE_APP, \ + ESP_PARTITION_SUBTYPE_APP_OTA_MIN + ((OTA_MAX(s_ota_select[0].ota_seq, s_ota_select[1].ota_seq) - 1) % ota_app_count), NULL); + } else if (ota_select_valid(&s_ota_select[0])) { + ESP_LOGD(TAG, "finding ota_%d bin......", \ + ESP_PARTITION_SUBTYPE_APP_OTA_MIN + (s_ota_select[0].ota_seq - 1) % ota_app_count); + + return esp_partition_find_first(ESP_PARTITION_TYPE_APP, \ + ESP_PARTITION_SUBTYPE_APP_OTA_MIN + (s_ota_select[0].ota_seq - 1) % ota_app_count, NULL); + + } else if (ota_select_valid(&s_ota_select[1])) { + ESP_LOGD(TAG, "finding ota_%d bin......", \ + ESP_PARTITION_SUBTYPE_APP_OTA_MIN + (s_ota_select[1].ota_seq - 1) % ota_app_count); + + return esp_partition_find_first(ESP_PARTITION_TYPE_APP, \ + ESP_PARTITION_SUBTYPE_APP_OTA_MIN + (s_ota_select[1].ota_seq - 1) % ota_app_count, NULL); + + } else { + ESP_LOGE(TAG, "not found current bin"); + return NULL; + } +} \ No newline at end of file diff --git a/components/app_update/include/esp_ota_ops.h b/components/app_update/include/esp_ota_ops.h new file mode 100755 index 0000000000..846aa2b2cf --- /dev/null +++ b/components/app_update/include/esp_ota_ops.h @@ -0,0 +1,110 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#ifndef _OTA_OPS_H +#define _OTA_OPS_H + +#include +#include +#include +#include "esp_err.h" +#include "esp_partition.h" +#include "esp_spi_flash.h" + +#ifdef __cplusplus +extern "C" +{ +#endif + +#define OTA_SIZE_UNKNOWN 0xffffffff + +#define ESP_ERR_OTA_BASE 0x1500 /*!< base error code for ota_ops api */ +#define ESP_ERR_OTA_PARTITION_CONFLICT (ESP_ERR_OTA_BASE + 0x01) /*!< want to write or erase current running partition */ +#define ESP_ERR_OTA_SELECT_INFO_INVALID (ESP_ERR_OTA_BASE + 0x02) /*!< ota data partition info is error */ +#define ESP_ERR_OTA_VALIDATE_FAILED (ESP_ERR_OTA_BASE + 0x03) /*!< validate ota image failed */ + +/** + * @brief Opaque handle for application update obtained from app_ops. + */ +typedef uint32_t esp_ota_handle_t; + +/** + * @brief format input partition in flash to 0xFF as input image size, + * if unkown image size ,pass 0x0 or 0xFFFFFFFF, it will erase all the + * partition ,Otherwise, erase the required range + * + * @param partition Pointer to partition structure which need to be updated + * Must be non-NULL. + * @param image_size size of image need to be updated + * @param out_handle handle which should be used for esp_ota_write or esp_ota_end call + + * @return: + * - ESP_OK: if format ota image OK + * - ESP_ERR_OTA_PARTITION_CONFLICT: operate current running bin + * - ESP_ERR_OTA_SELECT_INFO_INVALID: ota bin select info invalid + */ +esp_err_t esp_ota_begin(const esp_partition_t* partition, size_t image_size, esp_ota_handle_t* out_handle); + +/** + * @brief Write data to input input partition + * + * @param handle Handle obtained from esp_ota_begin + * @param data Pointer to data write to flash + * @param size data size of recieved data + * + * @return: + * - ESP_OK: if write flash data OK + * - ESP_ERR_OTA_PARTITION_CONFLICT: operate current running bin + * - ESP_ERR_OTA_SELECT_INFO_INVALID: ota bin select info invalid + */ +esp_err_t esp_ota_write(esp_ota_handle_t handle, const void* data, size_t size); + +/** + * @brief Finish the update and validate written data + * + * @param handle Handle obtained from esp_ota_begin + * + * @return: + * - ESP_OK: if validate ota image pass + * - ESP_ERR_OTA_VALIDATE_FAILED: validate the ota image is invalid + */ +esp_err_t esp_ota_end(esp_ota_handle_t handle); + +/** + * @brief Set next boot partition, call system_restart() will switch to run it + * + * @note if you want switch to run a bin file + * has never been checked before,please validate it's signature firstly + * + * @param partition Pointer to partition structure which need to boot + * + * @return: + * - ESP_OK: if set next boot partition OK + * - ESP_ERR_OTA_SELECT_INFO_INVALID: ota bin select info invalid + */ +esp_err_t esp_ota_set_boot_partition(const esp_partition_t* partition); + +/** + * @brief Get partition info of current running image + * + * @return pointer to esp_partition_t structure, or NULL if no partition is found or + * operate flash failed,This pointer is valid for the lifetime of the application. + */ +const esp_partition_t* esp_ota_get_boot_partition(void); + +#ifdef __cplusplus +} +#endif + +#endif /* OTA_OPS_H */ diff --git a/components/bootloader/src/main/bootloader_start.c b/components/bootloader/src/main/bootloader_start.c index 6b92aaf346..8dd163fe33 100644 --- a/components/bootloader/src/main/bootloader_start.c +++ b/components/bootloader/src/main/bootloader_start.c @@ -272,27 +272,31 @@ void bootloader_main() bootloader_munmap(ota_select_map); if(sa.ota_seq == 0xFFFFFFFF && sb.ota_seq == 0xFFFFFFFF) { - // init status flash - load_part_pos = bs.ota[0]; - sa.ota_seq = 0x01; - sa.crc = ota_select_crc(&sa); - sb.ota_seq = 0x00; - sb.crc = ota_select_crc(&sb); + // init status flash + if (bs.factory.offset != 0) { // if have factory bin,boot factory bin + load_part_pos = bs.factory; + } else { + load_part_pos = bs.ota[0]; + sa.ota_seq = 0x01; + sa.crc = ota_select_crc(&sa); + sb.ota_seq = 0x00; + sb.crc = ota_select_crc(&sb); - Cache_Read_Disable(0); - spiRet1 = SPIEraseSector(bs.ota_info.offset/0x1000); - spiRet2 = SPIEraseSector(bs.ota_info.offset/0x1000+1); - if (spiRet1 != SPI_FLASH_RESULT_OK || spiRet2 != SPI_FLASH_RESULT_OK ) { - ESP_LOGE(TAG, SPI_ERROR_LOG); - return; - } - spiRet1 = SPIWrite(bs.ota_info.offset,(uint32_t *)&sa,sizeof(esp_ota_select_entry_t)); - spiRet2 = SPIWrite(bs.ota_info.offset + 0x1000,(uint32_t *)&sb,sizeof(esp_ota_select_entry_t)); - if (spiRet1 != SPI_FLASH_RESULT_OK || spiRet2 != SPI_FLASH_RESULT_OK ) { - ESP_LOGE(TAG, SPI_ERROR_LOG); - return; - } - Cache_Read_Enable(0); + Cache_Read_Disable(0); + spiRet1 = SPIEraseSector(bs.ota_info.offset/0x1000); + spiRet2 = SPIEraseSector(bs.ota_info.offset/0x1000+1); + if (spiRet1 != SPI_FLASH_RESULT_OK || spiRet2 != SPI_FLASH_RESULT_OK ) { + ESP_LOGE(TAG, SPI_ERROR_LOG); + return; + } + spiRet1 = SPIWrite(bs.ota_info.offset,(uint32_t *)&sa,sizeof(esp_ota_select_entry_t)); + spiRet2 = SPIWrite(bs.ota_info.offset + 0x1000,(uint32_t *)&sb,sizeof(esp_ota_select_entry_t)); + if (spiRet1 != SPI_FLASH_RESULT_OK || spiRet2 != SPI_FLASH_RESULT_OK ) { + ESP_LOGE(TAG, SPI_ERROR_LOG); + return; + } + Cache_Read_Enable(0); + } //TODO:write data in ota info } else { if(ota_select_valid(&sa) && ota_select_valid(&sb)) { diff --git a/components/bootloader_support/src/secure_boot_signatures.c b/components/bootloader_support/src/secure_boot_signatures.c index f7e435e86d..076dfb335c 100644 --- a/components/bootloader_support/src/secure_boot_signatures.c +++ b/components/bootloader_support/src/secure_boot_signatures.c @@ -25,7 +25,6 @@ typedef SHA_CTX sha_context; #else #include "hwcrypto/sha.h" -typedef esp_sha_context sha_context; #endif typedef struct { @@ -42,7 +41,9 @@ extern const uint8_t signature_verification_key_end[] asm("_binary_signature_ver esp_err_t esp_secure_boot_verify_signature(uint32_t src_addr, uint32_t length) { - sha_context sha; +#ifdef BOOTLOADER_BUILD + SHA_CTX sha; +#endif uint8_t digest[32]; ptrdiff_t keylen; const uint8_t *data; @@ -83,12 +84,8 @@ esp_err_t esp_secure_boot_verify_signature(uint32_t src_addr, uint32_t length) ets_sha_finish(&sha, SHA2_256, digest); ets_sha_disable(); #else - /* Use thread-safe esp-idf SHA layer */ - esp_sha256_init(&sha); - esp_sha256_start(&sha, false); - esp_sha256_update(&sha, data, length); - esp_sha256_finish(&sha, digest); - esp_sha256_free(&sha); + /* Use thread-safe esp-idf SHA function */ + esp_sha(SHA2_256, data, length, digest); #endif keylen = signature_verification_key_end - signature_verification_key_start; diff --git a/components/bt/Kconfig b/components/bt/Kconfig index 4e8e317927..c2f8a86504 100644 --- a/components/bt/Kconfig +++ b/components/bt/Kconfig @@ -8,22 +8,9 @@ config BT_ENABLED help This compiles in the low-level BT stack. -menu "BT UTILITY OPTION" -visible if BT_ENABLED - -config BT_USE_ETS_PRINT - bool "BT use print which has lock" - default y - depends on BT_ENABLED - help - This select use print or ets_print - -endmenu #menu - config BTC_TASK_STACK_SIZE int "BT event (callback to application) task stack size" default 2048 - depends on BT_ENABLED help This select btc task stack size diff --git a/components/bt/bluedroid/api/esp_app_sec.c b/components/bt/bluedroid/api/esp_app_sec.c deleted file mode 100644 index e1ec079b4a..0000000000 --- a/components/bt/bluedroid/api/esp_app_sec.c +++ /dev/null @@ -1,106 +0,0 @@ -// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at - -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -#include // standard library -#include - -#include "esp_sec_api.h" - - -extern void srand (unsigned int seed); -extern int random (void); - -/// Application Security Environment Structure -tAPP_SEC_ENV app_sec_env; - - -/******************************************************************************* -** -** Function app_ble_sec_gen_tk -** -** Description This function is called to generate the ble tk -** -** Returns the generate tk value -** -*******************************************************************************/ -UINT32 app_ble_sec_gen_tk(void) -{ - // Generate a PIN Code (Between 100000 and 999999) - return (100000 + (random() % 900000)); -} - -/******************************************************************************* -** -** Function app_ble_sec_gen_ltk -** -** Description This function is called to generate the ble ltk -** -** Returns NULL -** -*******************************************************************************/ -void app_ble_sec_gen_ltk(UINT8 key_size) -{ - // Counter - UINT8 i; - app_sec_env.key_size = key_size; - - // Randomly generate the LTK and the Random Number - for (i = 0; i < RAND_NB_LEN; i++) { - app_sec_env.rand_nb.nb[i] = random() % 256; - } - - // Randomly generate the end of the LTK - for (i = 0; i < SEC_KEY_LEN; i++) { - app_sec_env.ltk.key[i] = (((key_size) < (16 - i)) ? 0 : random() % 256); - } - - // Randomly generate the EDIV - app_sec_env.ediv = random() % 65536; -} - - -/******************************************************************************* -** -** Function app_ble_sec_init -** -** Description This function is init the security env and function -** -** Returns NULL -** -*******************************************************************************/ -void app_ble_sec_init() -{ - // Reset Security Environment - memset(&app_sec_env, 0, sizeof(app_sec_env)); -} - - -/******************************************************************************* -** -** Function app_ble_security_start -** -** Description This function is called by the slave when the seurity start -** -** Returns NULL -** -*******************************************************************************/ -void app_ble_security_start(void) -{ - -} - - - - - diff --git a/components/bt/bluedroid/api/esp_gap_ble_api.c b/components/bt/bluedroid/api/esp_gap_ble_api.c index 7f4950a9f2..ebe1d81947 100644 --- a/components/bt/bluedroid/api/esp_gap_ble_api.c +++ b/components/bt/bluedroid/api/esp_gap_ble_api.c @@ -172,7 +172,7 @@ esp_err_t esp_ble_gap_config_local_privacy (bool privacy_enable) return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gap_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } -esp_err_t esp_ble_gap_set_device_name(char *name) +esp_err_t esp_ble_gap_set_device_name(const char *name) { btc_msg_t msg; btc_ble_gap_args_t arg; @@ -189,21 +189,7 @@ esp_err_t esp_ble_gap_set_device_name(char *name) return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gap_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } - -/******************************************************************************* -** -** Function esp_ble_resolve_adv_data -** -** Description This function is called to get ADV data for a specific type. -** -** Parameters p_adv - pointer of ADV data -** type - finding ADV data type -** p_length - return the length of ADV data not including type -** -** Returns pointer of ADV data -** -*******************************************************************************/ -uint8_t *esp_ble_resolve_adv_data( uint8_t *p_adv, uint8_t type, uint8_t *p_length) +uint8_t *esp_ble_resolve_adv_data( uint8_t *adv_data, uint8_t type, uint8_t *length) { if (((type < ESP_BLE_AD_TYPE_FLAG) || (type > ESP_BLE_AD_TYPE_128SERVICE_DATA)) && (type != ESP_BLE_AD_MANUFACTURER_SPECIFIC_TYPE)) { @@ -211,11 +197,11 @@ uint8_t *esp_ble_resolve_adv_data( uint8_t *p_adv, uint8_t type, uint8_t *p_leng return NULL; } - if (p_adv == NULL) { + if (adv_data == NULL) { LOG_ERROR("Invalid p_eir data.\n"); return NULL; } - return (BTM_CheckAdvData( p_adv, type, p_length)); + return (BTM_CheckAdvData( adv_data, type, length)); } diff --git a/components/bt/bluedroid/api/esp_gattc_api.c b/components/bt/bluedroid/api/esp_gattc_api.c index c59e94ad92..3c17f73371 100644 --- a/components/bt/bluedroid/api/esp_gattc_api.c +++ b/components/bt/bluedroid/api/esp_gattc_api.c @@ -18,18 +18,6 @@ #include "btc_manage.h" #include "btc_gattc.h" -/******************************************************************************* -** -** @function esp_ble_gattc_app_register_callback -** -** @brief This function is called to register application callbacks -** with GATTC module. -** -** @param[in] callback - pointer to the application callback function. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ esp_err_t esp_ble_gattc_register_callback(esp_profile_cb_t callback) { if (callback == NULL) { @@ -40,23 +28,16 @@ esp_err_t esp_ble_gattc_register_callback(esp_profile_cb_t callback) return ESP_OK; } -/******************************************************************************* -** -** @function esp_ble_gattc_app_register -** -** @brief This function is called to register application -** with GATTC module. -** -** @param[in] app_id : Application Identitfy (UUID), for different application -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ esp_err_t esp_ble_gattc_app_register(uint16_t app_id) { btc_msg_t msg; btc_ble_gattc_args_t arg; + //if (app_id < ESP_APP_ID_MIN || app_id > ESP_APP_ID_MAX) { + if (app_id > ESP_APP_ID_MAX) { + return ESP_ERR_INVALID_ARG; + } + msg.sig = BTC_SIG_API_CALL; msg.pid = BTC_PID_GATTC; msg.act = BTC_GATTC_ACT_APP_REGISTER; @@ -65,18 +46,6 @@ esp_err_t esp_ble_gattc_app_register(uint16_t app_id) return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } -/******************************************************************************* -** -** @function esp_ble_gattc_app_unregister -** -** @brief This function is called to unregister an application -** from GATTC module. -** -** @param[in] client_if - client interface identifier. -** -** @return None -** -*******************************************************************************/ esp_err_t esp_ble_gattc_app_unregister(esp_gatt_if_t gatt_if) { btc_msg_t msg; @@ -90,20 +59,6 @@ esp_err_t esp_ble_gattc_app_unregister(esp_gatt_if_t gatt_if) return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } -/******************************************************************************* -** -** @function esp_ble_gattc_conn -** -** @brief Open a direct connection or add a background auto connection -** bd address -** -** @param[in] gatt_if: application identity. -** @param[in] remote_bda: remote device BD address. -** @param[in] is_direct: direct connection or background auto connection -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ esp_err_t esp_ble_gattc_open(esp_gatt_if_t gatt_if, esp_bd_addr_t remote_bda, bool is_direct) { btc_msg_t msg; @@ -119,17 +74,6 @@ esp_err_t esp_ble_gattc_open(esp_gatt_if_t gatt_if, esp_bd_addr_t remote_bda, bo return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } -/******************************************************************************* -** -** @function esp_ble_gattc_close -** -** @brief Close a connection to a GATT server. -** -** @param[in] conn_id: connectino ID to be closed. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ esp_err_t esp_ble_gattc_close (uint16_t conn_id) { btc_msg_t msg; @@ -143,20 +87,6 @@ esp_err_t esp_ble_gattc_close (uint16_t conn_id) return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } - -/******************************************************************************* -** -** @function esp_ble_gattc_config_mtu -** -** @brief Configure the MTU size in the GATT channel. This can be done -** only once per connection. -** -** @param[in] conn_id: connection ID. -** mtu: desired MTU size to use. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ esp_err_t esp_ble_gattc_config_mtu (uint16_t conn_id, uint16_t mtu) { btc_msg_t msg; @@ -175,22 +105,6 @@ esp_err_t esp_ble_gattc_config_mtu (uint16_t conn_id, uint16_t mtu) return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } -/******************************************************************************* -** -** @function esp_ble_gattc_search_service -** -** @brief This function is called to request a GATT service discovery -** on a GATT server. This function report service search result -** by a callback event, and followed by a service search complete -** event. -** -** @param[in] conn_id: connection ID. -** @param[in] filter_uuid: a UUID of the service application is interested in. -** If Null, discover for all services. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ esp_err_t esp_ble_gattc_search_service(uint16_t conn_id, esp_bt_uuid_t *filter_uuid) { btc_msg_t msg; @@ -210,24 +124,6 @@ esp_err_t esp_ble_gattc_search_service(uint16_t conn_id, esp_bt_uuid_t *filter_u return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } - -/**************************************************************************************************** -** -** @function esp_ble_gattc_get_characteristic -** -** @brief This function is called to find the first characteristic of the -** service on the given server. -** -** @param[in] conn_id: connection ID which identify the server. -** -** @param[in] srvc_id: serivce ID -** -** @param[in] start_char_id: the start characteristic ID -** -** @return ESP_OK - success, other - failed -** -*****************************************************************************************************/ - esp_err_t esp_ble_gattc_get_characteristic(uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *start_char_id) @@ -251,23 +147,6 @@ esp_err_t esp_ble_gattc_get_characteristic(uint16_t conn_id, return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } - -/**************************************************************************************************** -** -** @function esp_ble_gattc_get_descriptor -** -** @brief This function is called to find the descriptor of the -** service on the given server. -** -** @param[in] conn_id: connection ID which identify the server. -** @param[in] srvc_id: the service ID of which the characteristic is belonged to. -** @param[in] char_id: Characteristic ID, if NULL find the first available -** characteristic. -** @param[in] start_descr_id: the sctart descriptor id -** -** @return ESP_OK - success, other - failed -** -*****************************************************************************************************/ esp_err_t esp_ble_gattc_get_descriptor(uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id, @@ -295,23 +174,6 @@ esp_err_t esp_ble_gattc_get_descriptor(uint16_t conn_id, return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } - -/**************************************************************************************************** -** -** @function esp_ble_gattc_get_include_service -** -** @brief This function is called to find the first characteristic of the -** service on the given server. -** -** @param[in] conn_id: connection ID which identify the server. -** @param[in] srvc_id: the service ID of which the characteristic is belonged to. -** @param[in] start_incl_srvc_id: the start include service id -** -** @return ESP_OK - success, other - failed -** -*****************************************************************************************************/ - - esp_err_t esp_ble_gattc_get_included_service(uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_srvc_id_t *start_incl_srvc_id) @@ -336,21 +198,6 @@ esp_err_t esp_ble_gattc_get_included_service(uint16_t conn_id, return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } -/******************************************************************************* -** -** @function esp_ble_gattc_read_char -** -** @brief This function is called to read a service's characteristics of -** the given characteritisc ID.UTH_REQ_NO_SCATTERNET -** -** @param[in] conn_id - connectino ID. -** @param[in] srvc_id - serivcie ID. -** @param[in] char_id - characteritic ID to read. -** @param[in] auth_req - authenticate request type -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ esp_err_t esp_ble_gattc_read_char (uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id, esp_gatt_auth_req_t auth_req) { @@ -368,20 +215,6 @@ esp_err_t esp_ble_gattc_read_char (uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } -/******************************************************************************* -** -** @function esp_ble_gattc_read_char_descr -** -** @brief This function is called to read a characteristics descriptor. -** -** @param[in] conn_id - connection ID. -** @param[in] srvc_id - serivcie ID. -** @param[in] descr_id - characteritic descriptor ID to read. -** @param[in] auth_req - authenticate request type -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ esp_err_t esp_ble_gattc_read_char_descr (uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id, @@ -403,26 +236,12 @@ esp_err_t esp_ble_gattc_read_char_descr (uint16_t conn_id, return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } -/******************************************************************************* -** -** @function esp_ble_gattc_write_char -** -** @brief This function is called to write characteristic value. -** -** @param[in] conn_id - connection ID. -** @param[in] srvc_id - serivcie ID. -** @param[in] char_id - characteristic ID to write. -** @param[in] value_len: length of the value to be written. -** @param[in] value - the value to be written. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ esp_err_t esp_ble_gattc_write_char( uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id, uint16_t value_len, uint8_t *value, + esp_gatt_write_type_t write_type, esp_gatt_auth_req_t auth_req) { btc_msg_t msg; @@ -436,33 +255,19 @@ esp_err_t esp_ble_gattc_write_char( uint16_t conn_id, memcpy(&arg.write_char.char_id, char_id, sizeof(esp_gatt_id_t)); arg.write_char.value_len = value_len > ESP_GATT_MAX_ATTR_LEN ? ESP_GATT_MAX_ATTR_LEN : value_len; arg.write_char.value = value; + arg.write_char.write_type = write_type; arg.write_char.auth_req = auth_req; return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), btc_gattc_arg_deep_copy) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } -/******************************************************************************* -** -** @function esp_ble_gattc_write_char_descr -** -** @brief This function is called to write characteristic descriptor value. -** -** @param[in] conn_id - connection ID -** @param[in] srvc_id - serivcie ID. -** @param[in] char_id - characteristic ID. -** @param[in] descr_id - characteristic descriptor ID to write. -** @param[in] value_len: length of the value to be written. -** @param[in] value - the value to be written. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ esp_err_t esp_ble_gattc_write_char_descr (uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id, esp_gatt_id_t *descr_id, uint16_t value_len, uint8_t *value, + esp_gatt_write_type_t write_type, esp_gatt_auth_req_t auth_req) { btc_msg_t msg; @@ -477,26 +282,12 @@ esp_err_t esp_ble_gattc_write_char_descr (uint16_t conn_id, memcpy(&arg.write_descr.descr_id, descr_id, sizeof(esp_gatt_id_t)); arg.write_descr.value_len = value_len > ESP_GATT_MAX_ATTR_LEN ? ESP_GATT_MAX_ATTR_LEN : value_len; arg.write_descr.value = value; + arg.write_descr.write_type = write_type; arg.write_descr.auth_req = auth_req; return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), btc_gattc_arg_deep_copy) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } -/******************************************************************************* -** -** @function esp_ble_gattc_prepare_write -** -** @brief This function is called to prepare write a characteristic value. -** -** @param[in] conn_id - connection ID. -** @param[in] char_id - GATT characteritic ID of the service. -** @param[in] offset - offset of the write value. -** @param[in] value_len: length of the value to be written. -** @param[in] value - the value to be written. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ esp_err_t esp_ble_gattc_prepare_write(uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id, @@ -523,20 +314,6 @@ esp_err_t esp_ble_gattc_prepare_write(uint16_t conn_id, return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), btc_gattc_arg_deep_copy) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } - - -/******************************************************************************* -** -** @function esp_ble_gattc_execu_write -** -** @brief This function is called to execute write a prepare write sequence. -** -** @param[in] conn_id - connection ID. -** @param[in] is_execute - execute or cancel. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ esp_err_t esp_ble_gattc_execute_write (uint16_t conn_id, bool is_execute) { btc_msg_t msg; @@ -551,22 +328,6 @@ esp_err_t esp_ble_gattc_execute_write (uint16_t conn_id, bool is_execute) return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } - - -/******************************************************************************* -** -** @function esp_ble_gattc_register_for_notify -** -** @brief This function is called to register for notification of a service. -** -** @param[in] gatt_if - gatt interface id. -** @param[in] bda - target GATT server. -** @param[in] srvc_id - pointer to GATT service ID. -** @param[in] char_id - pointer to GATT characteristic ID. -** -** @return OK if registration succeed, otherwise failed. -** -*******************************************************************************/ esp_gatt_status_t esp_ble_gattc_register_for_notify (esp_gatt_if_t gatt_if, esp_bd_addr_t server_bda, esp_gatt_srvc_id_t *srvc_id, @@ -586,22 +347,6 @@ esp_gatt_status_t esp_ble_gattc_register_for_notify (esp_gatt_if_t gatt_if, return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gattc_args_t), NULL) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } - - -/******************************************************************************* -** -** @function esp_ble_gattc_unregister_ntf -** -** @brief This function is called to de-register for notification of a service. -** -** @param[in] gatt_if - gatt interface id. -** @param[in] bda - target GATT server. -** @param[in] srvc_id - pointer to GATT service ID. -** @param[in] char_id - pointer to GATT characteristic ID. -** -** @return OK if deregistration succeed, otherwise failed. -** -*******************************************************************************/ esp_gatt_status_t esp_ble_gattc_unregister_for_notify (esp_gatt_if_t gatt_if, esp_bd_addr_t server_bda, esp_gatt_srvc_id_t *srvc_id, diff --git a/components/bt/bluedroid/api/esp_gatts_api.c b/components/bt/bluedroid/api/esp_gatts_api.c index 3004ee8beb..803ff030dd 100644 --- a/components/bt/bluedroid/api/esp_gatts_api.c +++ b/components/bt/bluedroid/api/esp_gatts_api.c @@ -30,7 +30,8 @@ esp_err_t esp_ble_gatts_app_register(uint16_t app_id) btc_msg_t msg; btc_ble_gatts_args_t arg; - if (app_id < APP_ID_MIN || app_id > APP_ID_MAX) { + //if (app_id < ESP_APP_ID_MIN || app_id > ESP_APP_ID_MAX) { + if (app_id > ESP_APP_ID_MAX) { return ESP_ERR_INVALID_ARG; } @@ -73,7 +74,7 @@ esp_err_t esp_ble_gatts_create_service(esp_gatt_if_t gatt_if, } -esp_err_t esp_ble_gatts_add_include_service(uint16_t service_handle, uint16_t included_service_handle) +esp_err_t esp_ble_gatts_add_included_service(uint16_t service_handle, uint16_t included_service_handle) { btc_msg_t msg; btc_ble_gatts_args_t arg; diff --git a/components/bt/bluedroid/api/esp_sdp_api.c b/components/bt/bluedroid/api/esp_sdp_api.c deleted file mode 100644 index 382f6dc021..0000000000 --- a/components/bt/bluedroid/api/esp_sdp_api.c +++ /dev/null @@ -1,125 +0,0 @@ -// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at - -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -#include "esp_sdp_api.h" - - -esp_err_t esp_bt_sdp_enable(bt_sdp_cb_t *cback) -{ - tBTA_SDP_STATUS status = BTA_SdpEnable((tBTA_SDP_DM_CBACK *)cback); - - return (status == BTA_SDP_SUCCESS) ? ESP_OK : ESP_FAIL; -} - -esp_err_t esp_bt_sdp_search(esp_bd_addr_t bd_addr, esp_bt_uuid_t *uuid) -{ - tBTA_SDP_STATUS status = BTA_SdpSearch(bd_addr, (tSDP_UUID *)uuid); - return (status == BTA_SDP_SUCCESS) ? ESP_OK : ESP_FAIL; -} - -esp_err_t esp_bt_sdp_create_record_by_user(void *user_data) -{ - tBTA_SDP_STATUS status = BTA_SdpCreateRecordByUser(user_data); - return (status == BTA_SDP_SUCCESS) ? ESP_OK : ESP_FAIL; -} - -esp_err_t esp_bt_sdp_remove_record_by_user(void *user_data) -{ - tBTA_SDP_STATUS status = BTA_SdpRemoveRecordByUser(user_data); - return (status == BTA_SDP_SUCCESS) ? ESP_OK : ESP_FAIL; -} - - -/**********************************************************************************************/ -/**********************************************************************************************/ -/* API into SDP for local service database updates */ -/* these APIs are indended to be called in callback function in the context of stack task, - * to handle BT_SDP_CREATE_RECORD_USER_EVT and BT_SDP_REMOVE_RECORD_USER_EVT - */ -uint32_t esp_bt_sdp_create_record(void) -{ - return SDP_CreateRecord(); -} - -bool esp_bt_sdp_delete_record(uint32_t handle) -{ - return SDP_DeleteRecord(handle); -} - -int32_t esp_bt_sdp_read_record(uint32_t handle, uint8_t *data, int32_t *data_len) -{ - return SDP_ReadRecord(handle, data, data_len); -} - -bool esp_bt_sdp_add_attribute (uint32_t handle, uint16_t attr_id, - uint8_t attr_type, uint32_t attr_len, - uint8_t *p_val) -{ - return SDP_AddAttribute(handle, attr_id, attr_type, attr_len, p_val); -} - -bool esp_bt_sdp_add_sequence (uint32_t handle, uint16_t attr_id, - uint16_t num_elem, uint8_t type[], - uint8_t len[], uint8_t *p_val[]) -{ - return SDP_AddSequence(handle, attr_id, num_elem, type, len, p_val); -} - -bool esp_bt_sdp_add_uuid_sequence (uint32_t handle, uint16_t attr_id, - uint16_t num_uuids, uint16_t *p_uuids) -{ - return SDP_AddUuidSequence(handle, attr_id, num_uuids, p_uuids); -} - - -bool esp_bt_sdp_add_protocol_list (uint32_t handle, uint16_t num_elem, - sdp_proto_elem_t *p_elem_list) -{ - return SDP_AddProtocolList(handle, num_elem, (tSDP_PROTOCOL_ELEM *)p_elem_list); -} - -bool esp_bt_sdp_add_addition_protocol_lists(uint32_t handle, uint16_t num_elem, - sdp_proto_list_elem_t *p_proto_list) -{ - return SDP_AddAdditionProtoLists(handle, num_elem, (tSDP_PROTO_LIST_ELEM *)p_proto_list); -} - -bool esp_bt_sdp_add_profile_dscp_list (uint32_t handle, - uint16_t profile_uuid, - uint16_t version) -{ - return SDP_AddProfileDescriptorList(handle, profile_uuid, version); -} - -bool esp_bt_sdp_add_lang_base_attr_id_list(uint32_t handle, - uint16_t lang, uint16_t char_enc, - uint16_t base_id) -{ - return SDP_AddLanguageBaseAttrIDList(handle, lang, char_enc, base_id); -} - -bool esp_bt_sdp_add_service_class_id_list(uint32_t handle, - uint16_t num_services, - uint16_t *p_service_uuids) -{ - return SDP_AddServiceClassIdList(handle, num_services, p_service_uuids); -} - -bool esp_bt_sdp_delete_attribute(uint32_t handle, uint16_t attr_id) -{ - return SDP_DeleteAttribute(handle, attr_id); -} - -/**********************************************************************************************/ -/**********************************************************************************************/ diff --git a/components/bt/bluedroid/api/include/esp_blufi_api.h b/components/bt/bluedroid/api/include/esp_blufi_api.h index 45790f8e84..b8ba382d0e 100644 --- a/components/bt/bluedroid/api/include/esp_blufi_api.h +++ b/components/bt/bluedroid/api/include/esp_blufi_api.h @@ -21,89 +21,95 @@ #include "bta_gatt_api.h" #include "esp_err.h" -#define ESP_BLUFI_RECV_DATA_LEN_MAX 128 +#define ESP_BLUFI_RECV_DATA_LEN_MAX (64+1) #define ESP_BLUFI_EVENT_INIT_FINISH 0 #define ESP_BLUFI_EVENT_DEINIT_FINISH 1 #define ESP_BLUFI_EVENT_RECV_DATA 2 +/// BLUFI config status typedef enum { ESP_BLUFI_CONFIG_OK = 0, ESP_BLUFI_CONFIG_FAILED, } esp_blufi_config_state_t; +/// BLUFI init status typedef enum { ESP_BLUFI_INIT_OK = 0, ESP_BLUFI_INIT_FAILED = 0, } esp_blufi_init_state_t; +/// BLUFI deinit status typedef enum { ESP_BLUFI_DEINIT_OK = 0, ESP_BLUFI_DEINIT_FAILED = 0, } esp_blufi_deinit_state_t; +/** + * @brief BLUFI callback parameters union + */ typedef union { - //ESP_BLUFI_EVENT_INIT_FINISH + /** + * @brief ESP_BLUFI_EVENT_INIT_FINISH + */ struct blufi_init_finish_evt_param { - esp_blufi_init_state_t state; - } init_finish; - //ESP_BLUFI_EVENT_DEINIT_FINISH + esp_blufi_init_state_t state; /*!< Initial status */ + } init_finish; /*!< Blufi callback param of ESP_BLUFI_EVENT_INIT_FINISH */ + + /** + * @brief ESP_BLUFI_EVENT_DEINIT_FINISH + */ struct blufi_deinit_finish_evt_param { - esp_blufi_deinit_state_t state; - } deinit_finish; - //ESP_BLUFI_EVENT_RECV_DATA + esp_blufi_deinit_state_t state; /*!< De-initial status */ + } deinit_finish; /*!< Blufi callback param of ESP_BLUFI_EVENT_DEINIT_FINISH */ + + /** + * @brief ESP_BLUFI_EVENT_RECV_DATA + */ struct blufi_recv_evt_param { - uint8_t data[ESP_BLUFI_RECV_DATA_LEN_MAX]; - uint8_t data_len; - } recv_data; + uint8_t data[ESP_BLUFI_RECV_DATA_LEN_MAX]; /*!< Blufi receive data */ + uint8_t data_len; /*!< Blufi receive data length */ + } recv_data; /*!< Blufi callback param of ESP_BLUFI_EVENT_RECV_DATA */ } esp_blufi_cb_param_t; -/******************************************************************************* -** -** @function esp_blufi_register_callback -** -** @brief This function is called to receive blufi callback event -** -** @param[in] callback: callback function -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * + * @brief This function is called to receive blufi callback event + * + * @param[in] callback: callback function + * + * @return ESP_OK - success, other - failed + * + */ esp_err_t esp_blufi_register_callback(esp_profile_cb_t callback); -/******************************************************************************* -** -** @function esp_blufi_send_config_state -** -** @brief This function is called to send config state to phone -** -** @param[in] state: blufi config ok or not -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * + * @brief This function is called to send config state to phone + * + * @param[in] state: blufi config OK or not + * + * @return ESP_OK - success, other - failed + * + */ esp_err_t esp_blufi_send_config_state(esp_blufi_config_state_t state); -/******************************************************************************* -** -** @function esp_blufi_profile_init -** -** @brief This function is called to init blufi_profile -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * + * @brief This function is called to initialize blufi_profile + * + * @return ESP_OK - success, other - failed + * + */ esp_err_t esp_blufi_profile_init(void); -/******************************************************************************* -** -** @function esp_blufi_profile_deinit -** -** @brief This function is called to init blufi_profile -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * + * @brief This function is called to de-initialize blufi_profile + * + * @return ESP_OK - success, other - failed + * + */ esp_err_t esp_blufi_profile_deinit(void); diff --git a/components/bt/bluedroid/api/include/esp_bt_defs.h b/components/bt/bluedroid/api/include/esp_bt_defs.h index f968669ce3..a19d89e856 100644 --- a/components/bt/bluedroid/api/include/esp_bt_defs.h +++ b/components/bt/bluedroid/api/include/esp_bt_defs.h @@ -18,7 +18,7 @@ #include #include -/* Status Return Value */ +/// Status Return Value typedef enum { ESP_BT_STATUS_SUCCESS = 0, /* Successful operation. */ ESP_BT_STATUS_FAILURE = 1, /* Generic failure. */ @@ -28,32 +28,40 @@ typedef enum { ESP_BT_STATUS_WRONG_MODE = 5, } esp_bt_status_t; +/// Default GATT interface id #define ESP_DEFAULT_GATT_IF 0xff +/// Default BLE connection param, if the value doesn't be overwritten #define ESP_BLE_CONN_PARAM_UNDEF 0xffff /* use this value when a specific value not to be overwritten */ +/// Check the param is valid or not #define ESP_BLE_IS_VALID_PARAM(x, min, max) (((x) >= (min) && (x) <= (max)) || ((x) == ESP_BLE_CONN_PARAM_UNDEF)) +/// UUID type typedef struct { #define ESP_UUID_LEN_16 2 #define ESP_UUID_LEN_32 4 #define ESP_UUID_LEN_128 16 - uint16_t len; + uint16_t len; /*!< UUID length, 16bit, 32bit or 128bit */ union { uint16_t uuid16; uint32_t uuid32; uint8_t uuid128[ESP_UUID_LEN_128]; - } uuid; -} __attribute__((packed)) esp_bt_uuid_t; /* tBT_UUID in "bt_types.h" */ + } uuid; /*!< UUID */ +} __attribute__((packed)) esp_bt_uuid_t; +/// Bluetooth device type typedef enum { ESP_BT_DEVICE_TYPE_BREDR = 0x01, ESP_BT_DEVICE_TYPE_BLE = 0x02, ESP_BT_DEVICE_TYPE_DUMO = 0x03, } esp_bt_dev_type_t; +/// Bluetooth address length #define ESP_BD_ADDR_LEN 6 -typedef uint8_t esp_bd_addr_t[ESP_BD_ADDR_LEN]; /* BD_ADDR in bt_types.h */ + +/// Bluetooth device address +typedef uint8_t esp_bd_addr_t[ESP_BD_ADDR_LEN]; /// Own BD address source of the device typedef enum { @@ -71,6 +79,7 @@ typedef enum { BD_ADDR_PROVIDED_RECON, } esp_bd_addr_type_t; +/// BLE device address type typedef enum { BLE_ADDR_TYPE_PUBLIC = 0x00, BLE_ADDR_TYPE_RANDOM = 0x01, @@ -78,11 +87,16 @@ typedef enum { BLE_ADDR_TYPE_RPA_RANDOM = 0x03, } esp_ble_addr_type_t; -#define APP_ID_MIN 0x0000 -#define APP_ID_MAX 0x7fff +/// Minimum of the application id +#define ESP_APP_ID_MIN 0x0000 +/// Maximum of the application id +#define ESP_APP_ID_MAX 0x7fff +/** + * @brief Each profile callback function type + * @param event : Event type + * @param param : Point to callback parameter, currently is union type + */ typedef void (* esp_profile_cb_t)(uint32_t event, void *param); -#define API_BLE_ISVALID_PARAM(x, min, max) (((x) >= (min) && (x) <= (max)) || ((x) == ESP_BLE_CONN_PARAM_UNDEF)) - #endif ///__ESP_BT_DEFS_H__ diff --git a/components/bt/bluedroid/api/include/esp_bt_main.h b/components/bt/bluedroid/api/include/esp_bt_main.h index dd7ec7116d..2bb7b8977b 100644 --- a/components/bt/bluedroid/api/include/esp_bt_main.h +++ b/components/bt/bluedroid/api/include/esp_bt_main.h @@ -18,12 +18,40 @@ #include "btc_main.h" #include "esp_err.h" +/** + * @brief Enable bluetooth, must after esp_init_bluetooth() + * + * @return + * - ESP_OK : Succeed + * - Other : Failed + */ esp_err_t esp_enable_bluetooth(void); +/** + * @brief Disable bluetooth, must prior to esp_deinit_bluetooth() + * + * @return + * - ESP_OK : Succeed + * - Other : Failed + */ esp_err_t esp_disable_bluetooth(void); +/** + * @brief Init and alloc the resource for bluetooth, must be prior to every bluetooth stuff + * + * @return + * - ESP_OK : Succeed + * - Other : Failed + */ esp_err_t esp_init_bluetooth(void); +/** + * @brief Deinit and free the resource for bluetooth, must be after every bluetooth stuff + * + * @return + * - ESP_OK : Succeed + * - Other : Failed + */ esp_err_t esp_deinit_bluetooth(void); diff --git a/components/bt/bluedroid/api/include/esp_gap_ble_api.h b/components/bt/bluedroid/api/include/esp_gap_ble_api.h index 08190eec82..29ffbe38ff 100644 --- a/components/bt/bluedroid/api/include/esp_gap_ble_api.h +++ b/components/bt/bluedroid/api/include/esp_gap_ble_api.h @@ -21,42 +21,45 @@ #include "esp_err.h" #include "esp_bt_defs.h" -#define ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT 0 -#define ESP_GAP_BLE_SCAN_RSP_DATA_SET_COMPLETE_EVT 1 -#define ESP_GAP_BLE_SCAN_PARAM_SET_COMPLETE_EVT 2 -#define ESP_GAP_BLE_SCAN_RESULT_EVT 3 +/// GAP BLE callback event type +typedef enum { + ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT = 0, /*!< When advertising data set complete, the event comes */ + ESP_GAP_BLE_SCAN_RSP_DATA_SET_COMPLETE_EVT , /*!< When scan response data set complete, the event comes */ + ESP_GAP_BLE_SCAN_PARAM_SET_COMPLETE_EVT, /*!< When scan parameters set complete, the event comes */ + ESP_GAP_BLE_SCAN_RESULT_EVT, /*!< When one scan result ready, the event comes each time */ +}esp_gap_ble_cb_event_t; +/// Advertising data maximum length #define ESP_BLE_ADV_DATA_LEN_MAX 31 -/****************** define the adv type macro***************************************/ -#define ESP_BLE_AD_TYPE_FLAG 0x01 -#define ESP_BLE_AD_TYPE_16SRV_PART 0x02 -#define ESP_BLE_AD_TYPE_16SRV_CMPL 0x03 -#define ESP_BLE_AD_TYPE_32SRV_PART 0x04 -#define ESP_BLE_AD_TYPE_32SRV_CMPL 0x05 -#define ESP_BLE_AD_TYPE_128SRV_PART 0x06 -#define ESP_BLE_AD_TYPE_128SRV_CMPL 0x07 -#define ESP_BLE_AD_TYPE_NAME_SHORT 0x08 -#define ESP_BLE_AD_TYPE_NAME_CMPL 0x09 -#define ESP_BLE_AD_TYPE_TX_PWR 0x0A -#define ESP_BLE_AD_TYPE_DEV_CLASS 0x0D -#define ESP_BLE_AD_TYPE_SM_TK 0x10 -#define ESP_BLE_AD_TYPE_SM_OOB_FLAG 0x11 -#define ESP_BLE_AD_TYPE_INT_RANGE 0x12 -#define ESP_BLE_AD_TYPE_SOL_SRV_UUID 0x14 -#define ESP_BLE_AD_TYPE_128SOL_SRV_UUID 0x15 -#define ESP_BLE_AD_TYPE_SERVICE_DATA 0x16 -#define ESP_BLE_AD_TYPE_PUBLIC_TARGET 0x17 -#define ESP_BLE_AD_TYPE_RANDOM_TARGET 0x18 -#define ESP_BLE_AD_TYPE_APPEARANCE 0x19 -#define ESP_BLE_AD_TYPE_ADV_INT 0x1A -#define ESP_BLE_AD_TYPE_32SOL_SRV_UUID 0x1B -#define ESP_BLE_AD_TYPE_32SERVICE_DATA 0x1C -#define ESP_BLE_AD_TYPE_128SERVICE_DATA 0x1D -#define ESP_BLE_AD_MANUFACTURER_SPECIFIC_TYPE 0xFF - - -typedef uint32_t esp_gap_ble_event_t; +/// The type of advertising data(not adv_type) +typedef enum { + ESP_BLE_AD_TYPE_FLAG = 0x01, + ESP_BLE_AD_TYPE_16SRV_PART = 0x02, + ESP_BLE_AD_TYPE_16SRV_CMPL = 0x03, + ESP_BLE_AD_TYPE_32SRV_PART = 0x04, + ESP_BLE_AD_TYPE_32SRV_CMPL = 0x05, + ESP_BLE_AD_TYPE_128SRV_PART = 0x06, + ESP_BLE_AD_TYPE_128SRV_CMPL = 0x07, + ESP_BLE_AD_TYPE_NAME_SHORT = 0x08, + ESP_BLE_AD_TYPE_NAME_CMPL = 0x09, + ESP_BLE_AD_TYPE_TX_PWR = 0x0A, + ESP_BLE_AD_TYPE_DEV_CLASS = 0x0D, + ESP_BLE_AD_TYPE_SM_TK = 0x10, + ESP_BLE_AD_TYPE_SM_OOB_FLAG = 0x11, + ESP_BLE_AD_TYPE_INT_RANGE = 0x12, + ESP_BLE_AD_TYPE_SOL_SRV_UUID = 0x14, + ESP_BLE_AD_TYPE_128SOL_SRV_UUID = 0x15, + ESP_BLE_AD_TYPE_SERVICE_DATA = 0x16, + ESP_BLE_AD_TYPE_PUBLIC_TARGET = 0x17, + ESP_BLE_AD_TYPE_RANDOM_TARGET = 0x18, + ESP_BLE_AD_TYPE_APPEARANCE = 0x19, + ESP_BLE_AD_TYPE_ADV_INT = 0x1A, + ESP_BLE_AD_TYPE_32SOL_SRV_UUID = 0x1B, + ESP_BLE_AD_TYPE_32SERVICE_DATA = 0x1C, + ESP_BLE_AD_TYPE_128SERVICE_DATA = 0x1D, + ESP_BLE_AD_MANUFACTURER_SPECIFIC_TYPE = 0xFF, +} esp_ble_adv_data_type; /// Advertising mode typedef enum { @@ -67,6 +70,7 @@ typedef enum { ADV_TYPE_DIRECT_IND_LOW = 0x04, } esp_ble_adv_type_t; +/// Advertising channel mask typedef enum { ADV_CHNL_37 = 0x01, ADV_CHNL_38 = 0x02, @@ -86,32 +90,39 @@ typedef enum { ///Enumeration end value for advertising filter policy value check } esp_ble_adv_filter_t; - +/// Advertising parameters typedef struct { - uint16_t adv_int_min; - uint16_t adv_int_max; - esp_ble_adv_type_t adv_type; - esp_ble_addr_type_t own_addr_type; - esp_bd_addr_t peer_addr; - esp_ble_addr_type_t peer_addr_type; - esp_ble_adv_channel_t channel_map; - esp_ble_adv_filter_t adv_filter_policy; + uint16_t adv_int_min; /*!< Minimum advertising interval for + undirected and low duty cycle directed advertising. + Range: 0x0020 to 0x4000 Default: N = 0x0800 (1.28 second) + Time = N * 0.625 msec Time Range: 20 ms to 10.24 sec */ + uint16_t adv_int_max; /*!< Maximum advertising interval for + undirected and low duty cycle directed advertising. + Range: 0x0020 to 0x4000 Default: N = 0x0800 (1.28 second) + Time = N * 0.625 msec Time Range: 20 ms to 10.24 sec Advertising max interval */ + esp_ble_adv_type_t adv_type; /*!< Advertising type */ + esp_ble_addr_type_t own_addr_type; /*!< Owner bluetooth device address type */ + esp_bd_addr_t peer_addr; /*!< Peer device bluetooth device address */ + esp_ble_addr_type_t peer_addr_type; /*!< Peer device bluetooth device address type */ + esp_ble_adv_channel_t channel_map; /*!< Advertising channel map */ + esp_ble_adv_filter_t adv_filter_policy; /*!< Advertising filter policy */ } esp_ble_adv_params_t; +/// Advertising data content, according to "Supplement to the Bluetooth Core Specification" typedef struct { - bool set_scan_rsp; - bool include_name; - bool include_txpower; - int min_interval; - int max_interval; - int appearance; - uint16_t manufacturer_len; - uint8_t *p_manufacturer_data; - uint16_t service_data_len; - uint8_t *p_service_data; - uint16_t service_uuid_len; - uint8_t *p_service_uuid; - uint8_t flag; + bool set_scan_rsp; /*!< Set this advertising data as scan response or not*/ + bool include_name; /*!< Advertising data include device name or not */ + bool include_txpower; /*!< Advertising data include TX power */ + int min_interval; /*!< Advertising data show advertising min interval */ + int max_interval; /*!< Advertising data show advertising max interval */ + int appearance; /*!< External appearance of device */ + uint16_t manufacturer_len; /*!< Manufacturer data length */ + uint8_t *p_manufacturer_data; /*!< Manufacturer data point */ + uint16_t service_data_len; /*!< Service data length */ + uint8_t *p_service_data; /*!< Service data point */ + uint16_t service_uuid_len; /*!< Service uuid length */ + uint8_t *p_service_uuid; /*!< Service uuid array point */ + uint8_t flag; /*!< Advertising flag of discovery mode */ } esp_ble_adv_data_t; /// Own BD address source of the device @@ -130,261 +141,284 @@ typedef enum { ESP_PROVIDED_RECON_ADDR, } esp_ble_own_addr_src_t; - +/// Ble scan type typedef enum { - BLE_SCAN_TYPE_PASSIVE = 0x0, - BLE_SCAN_TYPE_ACTIVE = 0x1, + BLE_SCAN_TYPE_PASSIVE = 0x0, /*!< Passive scan */ + BLE_SCAN_TYPE_ACTIVE = 0x1, /*!< Active scan */ } esp_ble_scan_type_t; +/// Ble scan filter type typedef enum { - BLE_SCAN_FILTER_ALLOW_ALL = 0x0, - BLE_SCAN_FILTER_ALLOW_ONLY_WLST = 0x1, - BLE_SCAN_FILTER_ALLOW_UND_RPA_DIR = 0x2, - BLE_SCAN_FILTER_ALLOW_WLIST_PRA_DIR = 0x3, + BLE_SCAN_FILTER_ALLOW_ALL = 0x0, /*!< Accept all : + 1. advertisement packets except directed advertising packets not addressed to this device (default). */ + BLE_SCAN_FILTER_ALLOW_ONLY_WLST = 0x1, /*!< Accept only : + 1. advertisement packets from devices where the advertiser’s address is in the White list. + 2. Directed advertising packets which are not addressed for this device shall be ignored. */ + BLE_SCAN_FILTER_ALLOW_UND_RPA_DIR = 0x2, /*!< Accept all : + 1. undirected advertisement packets, and + 2. directed advertising packets where the initiator address is a resolvable private address, and + 3. directed advertising packets addressed to this device. */ + BLE_SCAN_FILTER_ALLOW_WLIST_PRA_DIR = 0x3, /*!< Accept all : + 1. advertisement packets from devices where the advertiser’s address is in the White list, and + 2. directed advertising packets where the initiator address is a resolvable private address, and + 3. directed advertising packets addressed to this device.*/ } esp_ble_scan_filter_t; +/// Ble scan parameters typedef struct { - esp_ble_scan_type_t scan_type; - esp_ble_addr_type_t own_addr_type; - esp_ble_scan_filter_t scan_filter_policy; - uint16_t scan_interval; - uint16_t scan_window; + esp_ble_scan_type_t scan_type; /*!< Scan type */ + esp_ble_addr_type_t own_addr_type; /*!< Owner address type */ + esp_ble_scan_filter_t scan_filter_policy; /*!< Scan filter policy */ + uint16_t scan_interval; /*!< Scan interval. This is defined as the time interval from + when the Controller started its last LE scan until it begins the subsequent LE scan. + Range: 0x0004 to 0x4000 Default: 0x0010 (10 ms) + Time = N * 0.625 msec + Time Range: 2.5 msec to 10.24 seconds*/ + uint16_t scan_window; /*!< Scan window. The duration of the LE scan. LE_Scan_Window + shall be less than or equal to LE_Scan_Interval + Range: 0x0004 to 0x4000 Default: 0x0010 (10 ms) + Time = N * 0.625 msec + Time Range: 2.5 msec to 10240 msec */ } esp_ble_scan_params_t; +/// Connection update parameters typedef struct { - esp_bd_addr_t bda; - uint16_t min_int; - uint16_t max_int; - uint16_t latency; - uint16_t timeout; + esp_bd_addr_t bda; /*!< Bluetooth device address */ + uint16_t min_int; /*!< Min connection interval */ + uint16_t max_int; /*!< Max connection interval */ + uint16_t latency; /*!< Slave latency for the connection in number of connection events. Range: 0x0000 to 0x01F3 */ + uint16_t timeout; /*!< Supervision timeout for the LE Link. Range: 0x000A to 0x0C80. + Mandatory Range: 0x000A to 0x0C80 Time = N * 10 msec + Time Range: 100 msec to 32 seconds */ } esp_ble_conn_update_params_t; -typedef void (*esp_gap_ble_cb_t)(esp_gap_ble_event_t event, void *param); - +/// Sub Event of ESP_GAP_BLE_SCAN_RESULT_EVT typedef enum { - /* Search callback events */ - ESP_GAP_SEARCH_INQ_RES_EVT = 0, /* Inquiry result for a peer device. */ - ESP_GAP_SEARCH_INQ_CMPL_EVT = 1, /* Inquiry complete. */ - ESP_GAP_SEARCH_DISC_RES_EVT = 2, /* Discovery result for a peer device. */ - ESP_GAP_SEARCH_DISC_BLE_RES_EVT = 3, /* Discovery result for BLE GATT based servoce on a peer device. */ - ESP_GAP_SEARCH_DISC_CMPL_EVT = 4, /* Discovery complete. */ - ESP_GAP_SEARCH_DI_DISC_CMPL_EVT = 5, /* Discovery complete. */ - ESP_GAP_SEARCH_SEARCH_CANCEL_CMPL_EVT = 6, /* Search cancelled */ + ESP_GAP_SEARCH_INQ_RES_EVT = 0, /*!< Inquiry result for a peer device. */ + ESP_GAP_SEARCH_INQ_CMPL_EVT = 1, /*!< Inquiry complete. */ + ESP_GAP_SEARCH_DISC_RES_EVT = 2, /*!< Discovery result for a peer device. */ + ESP_GAP_SEARCH_DISC_BLE_RES_EVT = 3, /*!< Discovery result for BLE GATT based service on a peer device. */ + ESP_GAP_SEARCH_DISC_CMPL_EVT = 4, /*!< Discovery complete. */ + ESP_GAP_SEARCH_DI_DISC_CMPL_EVT = 5, /*!< Discovery complete. */ + ESP_GAP_SEARCH_SEARCH_CANCEL_CMPL_EVT = 6, /*!< Search cancelled */ } esp_gap_search_evt_t; +/** + * @brief Ble scan result event type, to indicate the + * result is scan response or advertising data or other + */ +typedef enum { + ESP_BLE_EVT_CONN_ADV = 0x00, /*!< Connectable undirected advertising (ADV_IND) */ + ESP_BLE_EVT_CONN_DIR_ADV = 0x01, /*!< Connectable directed advertising (ADV_DIRECT_IND) */ + ESP_BLE_EVT_DISC_ADV = 0x02, /*!< Scannable undirected advertising (ADV_SCAN_IND) */ + ESP_BLE_EVT_NON_CONN_ADV = 0x03, /*!< Non connectable undirected advertising (ADV_NONCONN_IND) */ + ESP_BLE_EVT_SCAN_RSP = 0x04, /*!< Scan Response (SCAN_RSP) */ +} esp_ble_evt_type_t; + +/** + * @brief Gap callback parameters union + */ typedef union { - //ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT 0 + /** + * @brief ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT + */ struct ble_adv_data_cmpl_evt_param { - esp_bt_status_t status; - } adv_data_cmpl; - //ESP_GAP_BLE_SCAN_RSP_DATA_SET_COMPLETE_EVT 1 + esp_bt_status_t status; /*!< Indicate the set advertising data operation success status */ + } adv_data_cmpl; /*!< Event parameter of ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT */ + /** + * @brief ESP_GAP_BLE_SCAN_RSP_DATA_SET_COMPLETE_EVT + */ struct ble_scan_rsp_data_cmpl_evt_param { - esp_bt_status_t status; - } scan_rsp_data_cmpl; - //ESP_GAP_BLE_SCAN_PARAM_SET_COMPLETE_EVT 2 + esp_bt_status_t status; /*!< Indicate the set scan response data operation success status */ + } scan_rsp_data_cmpl; /*!< Event parameter of ESP_GAP_BLE_SCAN_RSP_DATA_SET_COMPLETE_EVT */ + /** + * @brief ESP_GAP_BLE_SCAN_PARAM_SET_COMPLETE_EVT + */ struct ble_scan_param_cmpl_evt_param { - esp_bt_status_t status; - } scan_param_cmpl; - //ESP_GAP_BLE_SCAN_RESULT_EVT 3 + esp_bt_status_t status; /*!< Indicate the set scan param operation success status */ + } scan_param_cmpl; /*!< Event parameter of ESP_GAP_BLE_SCAN_PARAM_SET_COMPLETE_EVT */ + /** + * @brief ESP_GAP_BLE_SCAN_RESULT_EVT + */ struct ble_scan_result_evt_param { - esp_gap_search_evt_t search_evt; - esp_bd_addr_t bda; - esp_bt_dev_type_t dev_type; - esp_ble_addr_type_t ble_addr_type; - int rssi; - uint8_t ble_adv[ESP_BLE_ADV_DATA_LEN_MAX]; /* received EIR */ - int flag; - int num_resps; - } scan_rst; + esp_gap_search_evt_t search_evt; /*!< Search event type */ + esp_bd_addr_t bda; /*!< Bluetooth device address which has been searched */ + esp_bt_dev_type_t dev_type; /*!< Device type */ + esp_ble_addr_type_t ble_addr_type; /*!< Ble device address type */ + esp_ble_evt_type_t ble_evt_type; /*!< Ble scan result event type */ + int rssi; /*!< Searched device's RSSI */ + uint8_t ble_adv[ESP_BLE_ADV_DATA_LEN_MAX]; /*!< Received EIR */ + int flag; /*!< Advertising data flag bit */ + int num_resps; /*!< Scan result number */ + } scan_rst; /*!< Event parameter of ESP_GAP_BLE_SCAN_RESULT_EVT */ } esp_ble_gap_cb_param_t; -/******************************************************************************* -** -** @function esp_ble_gap_register_callback -** -** @brief This function is called to occur gap event, such as scan result -** -** @param[in] callback: callback function -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ - +/** + * @brief This function is called to occur gap event, such as scan result + * + * @param[in] callback: callback function + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gap_register_callback(esp_profile_cb_t callback); -/******************************************************************************* -** -** @function esp_ble_gap_config_adv_data -** -** @brief This function is called to override the BTA default ADV parameters. -** -** @param[in] adv_data: Pointer to User defined ADV data structure. This -** memory space can not be freed until p_adv_data_cback -** is received. -** @param[in|out] adv_data_cback: set adv data complete callback. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to override the BTA default ADV parameters. + * + * @param[in] adv_data: Pointer to User defined ADV data structure. This + * memory space can not be freed until callback of config_adv_data + * is received. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gap_config_adv_data (esp_ble_adv_data_t *adv_data); -/******************************************************************************* -** -** @function esp_ble_gap_set_scan_params -** -** @brief This function is called to set scan parameters -** -** @param[in] esp_ble_scan_params: Pointer to User defined scan_params data structure. This -** memory space can not be freed until scan_param_setup_cback -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to set scan parameters + * + * @param[in] scan_params: Pointer to User defined scan_params data structure. This + * memory space can not be freed until callback of set_scan_params + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gap_set_scan_params(esp_ble_scan_params_t *scan_params); -/******************************************************************************* -** -** @function esp_ble_gap_start_scanning -** -** @brief This procedure keep the device scanning the peer device whith advertising on the air -** -** @param[in] duration: Keeping the scaning time, the unit is second. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This procedure keep the device scanning the peer device which advertising on the air + * + * @param[in] duration: Keeping the scanning time, the unit is second. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gap_start_scanning(uint32_t duration); -/******************************************************************************* -** -** @function esp_ble_gap_stop_scanning -** -** @brief This function call to stop the device scanning the peer device whith advertising on the air -** @param void -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function call to stop the device scanning the peer device which advertising on the air + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gap_stop_scanning(void); -/******************************************************************************* -** -** @function esp_ble_gap_start_advertising -** -** @brief This function is called to start advertising. -** -** @param[in] esp_ble_adv_params_all_t: ointer to User defined adv_params data structure. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to start advertising. + * + * @param[in] adv_params: pointer to User defined adv_params data structure. + + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gap_start_advertising (esp_ble_adv_params_t *adv_params); -/******************************************************************************* -** -** @function esp_gap_ble_stop_advertising -** -** @brief This function is called to stop advertising. -** -** @param None -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to stop advertising. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gap_stop_advertising(void); -/******************************************************************************* -** -** @function esp_ble_update_conn_params -** -** @brief Update connection parameters, can only be used when connection is up. -** -** @param[in] param - connection update params -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief Update connection parameters, can only be used when connection is up. + * + * @param[in] params - connection update parameters + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gap_update_conn_params(esp_ble_conn_update_params_t *params); -/******************************************************************************* -** -** @function esp_ble_gap_set_pkt_data_len -** -** @brief This function is to set maximum LE data packet size -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is to set maximum LE data packet size + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gap_set_pkt_data_len(esp_bd_addr_t remote_device, uint16_t tx_data_length); -/******************************************************************************* -** -** @function esp_ble_gap_set_rand_addr -** -** @brief This function set the random address for the appliction -** -** @param[in] rand_addr: the random address whith should be setting -** -** @return ESP_OK - success, other - failed -** -** -*******************************************************************************/ +/** + * @brief This function set the random address for the application + * + * @param[in] rand_addr: the random address which should be setting + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gap_set_rand_addr(esp_bd_addr_t rand_addr); -/******************************************************************************* -** -** @function esp_ble_gap_config_local_privacy -** -** @brief Enable/disable privacy on the local device -** -** @param[in] privacy_enable - enable/disabe privacy on remote device. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief Enable/disable privacy on the local device + * + * @param[in] privacy_enable - enable/disable privacy on remote device. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gap_config_local_privacy (bool privacy_enable); -/******************************************************************************* -** -** @function esp_ble_gap_set_device_name -** -** @brief Set device name to the local device -** -** @param[in] name - device name. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ -esp_err_t esp_ble_gap_set_device_name(char *name); +/** + * @brief Set device name to the local device + * + * @param[in] name - device name. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ +esp_err_t esp_ble_gap_set_device_name(const char *name); -/******************************************************************************* -** -** @function esp_ble_resolve_adv_data -** -** @brief This function is called to get ADV data for a specific type. -** -** @param[in] p_adv - pointer of ADV data whitch to be resolved -** @param[in] type - finding ADV data type -** @param[out] p_length - return the length of ADV data not including type -** -** @return pointer of ADV data -** -*******************************************************************************/ -uint8_t *esp_ble_resolve_adv_data( uint8_t *p_adv, uint8_t type, uint8_t *p_length ); +/** + * @brief This function is called to get ADV data for a specific type. + * + * @param[in] adv_data - pointer of ADV data which to be resolved + * @param[in] type - finding ADV data type + * @param[out] length - return the length of ADV data not including type + * + * @return pointer of ADV data + * + */ +uint8_t *esp_ble_resolve_adv_data(uint8_t *adv_data, uint8_t type, uint8_t *length); #endif /* __ESP_GAP_BLE_API_H__ */ diff --git a/components/bt/bluedroid/api/include/esp_gatt_defs.h b/components/bt/bluedroid/api/include/esp_gatt_defs.h index 05cf6de7dc..479be983b7 100644 --- a/components/bt/bluedroid/api/include/esp_gatt_defs.h +++ b/components/bt/bluedroid/api/include/esp_gatt_defs.h @@ -17,11 +17,15 @@ #include "esp_bt_defs.h" -/* attribute request data from the client */ -#define ESP_GATT_PREP_WRITE_CANCEL 0x00 -#define ESP_GATT_PREP_WRITE_EXEC 0x01 +/// Attribute write data type from the client +typedef enum { + ESP_GATT_PREP_WRITE_CANCEL = 0x00, /*!< Prepare write cancel */ + ESP_GATT_PREP_WRITE_EXEC = 0x01, /*!< Prepare write execute */ +} esp_gatt_prep_write_type; -/* Success code and error codes */ +/** + * @brief GATT success code and error codes + */ typedef enum { ESP_GATT_OK = 0x0, ESP_GATT_INVALID_HANDLE = 0x01, /* 0x0001 */ @@ -69,28 +73,41 @@ typedef enum { ESP_GATT_OUT_OF_RANGE = 0xff, /* 0xFFAttribute value out of range */ } esp_gatt_status_t; +/** + * @brief Gatt Connection reason enum + */ typedef enum { - ESP_GATT_CONN_UNKNOWN = 0, - ESP_GATT_CONN_L2C_FAILURE = 1, /* general L2cap failure */ - ESP_GATT_CONN_TIMEOUT = 0x08, /* 0x08 connection timeout */ - ESP_GATT_CONN_TERMINATE_PEER_USER = 0x13, /* 0x13 connection terminate by peer user */ - ESP_GATT_CONN_TERMINATE_LOCAL_HOST = 0x16, /* 0x16 connectionterminated by local host */ - ESP_GATT_CONN_FAIL_ESTABLISH = 0x3e, /* 0x03E connection fail to establish */ - // ESP_GATT_CONN_LMP_TIMEOUT = 0x22, /* 0x22 connection fail for LMP response tout */ - ESP_GATT_CONN_CONN_CANCEL = 0x0100, /* 0x0100 L2CAP connection cancelled */ - ESP_GATT_CONN_NONE = 0x0101 /* 0x0101 no connection to cancel */ -} esp_gatt_reason_t; + ESP_GATT_CONN_UNKNOWN = 0, /*!< Gatt connection unknown */ + ESP_GATT_CONN_L2C_FAILURE = 1, /*!< General L2cap failure */ + ESP_GATT_CONN_TIMEOUT = 0x08, /*!< Connection timeout */ + ESP_GATT_CONN_TERMINATE_PEER_USER = 0x13, /*!< Connection terminate by peer user */ + ESP_GATT_CONN_TERMINATE_LOCAL_HOST = 0x16, /*!< Connectionterminated by local host */ + ESP_GATT_CONN_FAIL_ESTABLISH = 0x3e, /*!< Connection fail to establish */ + ESP_GATT_CONN_LMP_TIMEOUT = 0x22, /*!< Connection fail for LMP response tout */ + ESP_GATT_CONN_CONN_CANCEL = 0x0100, /*!< L2CAP connection cancelled */ + ESP_GATT_CONN_NONE = 0x0101 /*!< No connection to cancel */ +} esp_gatt_conn_reason_t; +/** + * @brief Gatt id, include uuid and instance id + */ typedef struct { - esp_bt_uuid_t uuid; - uint8_t inst_id; + esp_bt_uuid_t uuid; /*!< UUID */ + uint8_t inst_id; /*!< Instance id */ } __attribute__((packed)) esp_gatt_id_t; +/** + * @brief Gatt service id, include id + * (uuid and instance id) and primary flag + */ typedef struct { - esp_gatt_id_t id; - bool is_primary; + esp_gatt_id_t id; /*!< Gatt id, include uuid and instance */ + bool is_primary; /*!< This service is primary or not */ } __attribute__((packed)) esp_gatt_srvc_id_t; +/** + * @brief Gatt authentication request type + */ typedef enum { AUTH_REQ_NO_SCATTERNET, /* Device doesn't support scatternet, it might support "role switch during connection" for @@ -103,8 +120,9 @@ typedef enum { and slave roles */ } esp_gatt_auth_req_t; -/* Attribute permissions -*/ +/** + * @brief Attribute permissions + */ typedef enum { ESP_GATT_PERM_READ = (1 << 0), /* bit 0 - 0x0001 */ ESP_GATT_PERM_READ_ENCRYPTED = (1 << 1), /* bit 1 - 0x0002 */ @@ -128,22 +146,32 @@ typedef enum { ESP_GATT_CHAR_PROP_BIT_EXT_PROP = (1 << 7), /* 0x80 */ } esp_gatt_char_prop_t; +/// GATT maximum attribute length #define ESP_GATT_MAX_ATTR_LEN 600 //as same as GATT_MAX_ATTR_LEN +/// Gatt attribute value typedef struct { - uint8_t value[ESP_GATT_MAX_ATTR_LEN]; - uint16_t handle; - uint16_t offset; - uint16_t len; - uint8_t auth_req; + uint8_t value[ESP_GATT_MAX_ATTR_LEN]; /*!< Gatt attribute value */ + uint16_t handle; /*!< Gatt attribute handle */ + uint16_t offset; /*!< Gatt attribute value offset */ + uint16_t len; /*!< Gatt attribute value length */ + uint8_t auth_req; /*!< Gatt authentication request */ } esp_gatt_value_t; -/** GATT remote read request response type */ +/// GATT remote read request response type typedef union { - esp_gatt_value_t attr_value; - uint16_t handle; + esp_gatt_value_t attr_value; /*!< Gatt attribute structure */ + uint16_t handle; /*!< Gatt attribute handle */ } esp_gatt_rsp_t; -typedef uint32_t esp_gatt_if_t; +/** + * @brief Gatt write type + */ +typedef enum { + ESP_GATT_WRITE_TYPE_NO_RSP = 1, /*!< Gatt write attribute need no response */ + ESP_GATT_WRITE_TYPE_RSP, /*!< Gatt write attribute need remote response */ +} esp_gatt_write_type_t; + +typedef uint32_t esp_gatt_if_t; /*!< Gatt interface type, different application on GATT client use different gatt_if */ #endif /* __ESP_GATT_DEFS_H__ */ diff --git a/components/bt/bluedroid/api/include/esp_gattc_api.h b/components/bt/bluedroid/api/include/esp_gattc_api.h old mode 100644 new mode 100755 index 5b5fff5fb7..4cf5113eb1 --- a/components/bt/bluedroid/api/include/esp_gattc_api.h +++ b/components/bt/bluedroid/api/include/esp_gattc_api.h @@ -20,402 +20,424 @@ #include "esp_gatt_defs.h" #include "esp_err.h" -/* Client callback function events */ -#define ESP_GATTC_REG_EVT 0 /* GATT client is registered. */ -#define ESP_GATTC_UNREG_EVT 1 /* GATT client unregistered event */ -#define ESP_GATTC_OPEN_EVT 2 /* GATTC open request status event */ -#define ESP_GATTC_READ_CHAR_EVT 3 /* GATT read characteristic event */ -#define ESP_GATTC_WRITE_CHAR_EVT 4 /* GATT write characteristic or char descriptor event */ -#define ESP_GATTC_CLOSE_EVT 5 /* GATTC close request status event */ -#define ESP_GATTC_SEARCH_CMPL_EVT 6 /* GATT discovery complete event */ -#define ESP_GATTC_SEARCH_RES_EVT 7 /* GATT discovery result event */ -#define ESP_GATTC_READ_DESCR_EVT 8 /* GATT read characterisitc descriptor event */ -#define ESP_GATTC_WRITE_DESCR_EVT 9 /* GATT write characteristic descriptor event */ -#define ESP_GATTC_NOTIFY_EVT 10 /* GATT attribute notification event */ -#define ESP_GATTC_PREP_WRITE_EVT 11 /* GATT prepare write event */ -#define ESP_GATTC_EXEC_EVT 12 /* execute write complete event */ -#define ESP_GATTC_ACL_EVT 13 /* ACL up event */ -#define ESP_GATTC_CANCEL_OPEN_EVT 14 /* cancel open event */ -#define ESP_GATTC_SRVC_CHG_EVT 15 /* service change event */ -#define ESP_GATTC_ENC_CMPL_CB_EVT 17 /* encryption complete callback event */ -#define ESP_GATTC_CFG_MTU_EVT 18 /* configure MTU complete event */ -#define ESP_GATTC_ADV_DATA_EVT 19 /* ADV data event */ -#define ESP_GATTC_MULT_ADV_ENB_EVT 20 /* Enable Multi ADV event */ -#define ESP_GATTC_MULT_ADV_UPD_EVT 21 /* Update parameter event */ -#define ESP_GATTC_MULT_ADV_DATA_EVT 22 /* Multi ADV data event */ -#define ESP_GATTC_MULT_ADV_DIS_EVT 23 /* Disable Multi ADV event */ -#define ESP_GATTC_CONGEST_EVT 24 /* Congestion event */ -#define ESP_GATTC_BTH_SCAN_ENB_EVT 25 /* Enable batch scan event */ -#define ESP_GATTC_BTH_SCAN_CFG_EVT 26 /* Config storage event */ -#define ESP_GATTC_BTH_SCAN_RD_EVT 27 /* Batch scan reports read event */ -#define ESP_GATTC_BTH_SCAN_THR_EVT 28 /* Batch scan threshold event */ -#define ESP_GATTC_BTH_SCAN_PARAM_EVT 29 /* Batch scan param event */ -#define ESP_GATTC_BTH_SCAN_DIS_EVT 30 /* Disable batch scan event */ -#define ESP_GATTC_SCAN_FLT_CFG_EVT 31 /* Scan filter config event */ -#define ESP_GATTC_SCAN_FLT_PARAM_EVT 32 /* Param filter event */ -#define ESP_GATTC_SCAN_FLT_STATUS_EVT 33 /* Filter status event */ -#define ESP_GATTC_ADV_VSC_EVT 34 /* ADV VSC event */ - -#define ESP_GATTC_GET_CHAR_EVT 35 /* get characteristic event */ -#define ESP_GATTC_GET_DESCR_EVT 36 /* get characteristic descriptor event */ -#define ESP_GATTC_GET_INCL_SRVC_EVT 37 /* get included service event */ -#define ESP_GATTC_REG_FOR_NOTIFY_EVT 38 /* register for notification event */ -#define ESP_GATTC_UNREG_FOR_NOTIFY_EVT 39 /* unregister for notification event */ - +/// GATT Client callback function events +typedef enum { + ESP_GATTC_REG_EVT = 0, /*!< When GATT client is registered, the event comes */ + ESP_GATTC_UNREG_EVT = 1, /*!< When GATT client is unregistered, the event comes */ + ESP_GATTC_OPEN_EVT = 2, /*!< When GATT connection is set up, the event comes */ + ESP_GATTC_READ_CHAR_EVT = 3, /*!< When GATT characteristic is read, the event comes */ + ESP_GATTC_WRITE_CHAR_EVT = 4, /*!< When GATT characteristic write operation completes, the event comes */ + ESP_GATTC_CLOSE_EVT = 5, /*!< When GATT connection is closed, the event comes */ + ESP_GATTC_SEARCH_CMPL_EVT = 6, /*!< When GATT service discovery is completed, the event comes */ + ESP_GATTC_SEARCH_RES_EVT = 7, /*!< When GATT service discovery result is got, the event comes */ + ESP_GATTC_READ_DESCR_EVT = 8, /*!< When GATT characteristic descriptor read completes, the event comes */ + ESP_GATTC_WRITE_DESCR_EVT = 9, /*!< When GATT characteristic descriptor write completes, the event comes */ + ESP_GATTC_NOTIFY_EVT = 10, /*!< When GATT notification or indication arrives, the event comes */ + ESP_GATTC_PREP_WRITE_EVT = 11, /*!< When GATT prepare-write operation completes, the event comes */ + ESP_GATTC_EXEC_EVT = 12, /*!< When write execution completes, the event comes */ + ESP_GATTC_ACL_EVT = 13, /*!< When ACL connection is up, the event comes */ + ESP_GATTC_CANCEL_OPEN_EVT = 14, /*!< When GATT client ongoing connection is cancelled, the event comes */ + ESP_GATTC_SRVC_CHG_EVT = 15, /*!< When "service changed" occurs, the event comes */ + ESP_GATTC_ENC_CMPL_CB_EVT = 17, /*!< When encryption procedure completes, the event comes */ + ESP_GATTC_CFG_MTU_EVT = 18, /*!< When configuration of MTU completes, the event comes */ + ESP_GATTC_ADV_DATA_EVT = 19, /*!< When advertising of data, the event comes */ + ESP_GATTC_MULT_ADV_ENB_EVT = 20, /*!< When multi-advertising is enabled, the event comes */ + ESP_GATTC_MULT_ADV_UPD_EVT = 21, /*!< When multi-advertising parameters are updated, the event comes */ + ESP_GATTC_MULT_ADV_DATA_EVT = 22, /*!< When multi-advertising data arrives, the event comes */ + ESP_GATTC_MULT_ADV_DIS_EVT = 23, /*!< When multi-advertising is disabled, the event comes */ + ESP_GATTC_CONGEST_EVT = 24, /*!< When GATT connection congestion comes, the event comes */ + ESP_GATTC_BTH_SCAN_ENB_EVT = 25, /*!< When batch scan is enabled, the event comes */ + ESP_GATTC_BTH_SCAN_CFG_EVT = 26, /*!< When batch scan storage is configured, the event comes */ + ESP_GATTC_BTH_SCAN_RD_EVT = 27, /*!< When Batch scan read event is reported, the event comes */ + ESP_GATTC_BTH_SCAN_THR_EVT = 28, /*!< When Batch scan threshold is set, the event comes */ + ESP_GATTC_BTH_SCAN_PARAM_EVT = 29, /*!< When Batch scan parameters are set, the event comes */ + ESP_GATTC_BTH_SCAN_DIS_EVT = 30, /*!< When Batch scan is disabled, the event comes */ + ESP_GATTC_SCAN_FLT_CFG_EVT = 31, /*!< When Scan filter configuration completes, the event comes */ + ESP_GATTC_SCAN_FLT_PARAM_EVT = 32, /*!< When Scan filter parameters are set, the event comes */ + ESP_GATTC_SCAN_FLT_STATUS_EVT = 33, /*!< When Scan filter status is reported, the event comes */ + ESP_GATTC_ADV_VSC_EVT = 34, /*!< When advertising vendor spec content event is reported, the event comes */ + ESP_GATTC_GET_CHAR_EVT = 35, /*!< When characteristic is got from GATT server, the event comes */ + ESP_GATTC_GET_DESCR_EVT = 36, /*!< When characteristic descriptor is got from GATT server, the event comes */ + ESP_GATTC_GET_INCL_SRVC_EVT = 37, /*!< When included service is got from GATT server, the event comes */ + ESP_GATTC_REG_FOR_NOTIFY_EVT = 38, /*!< When register for notification of a service completes, the event comes */ + ESP_GATTC_UNREG_FOR_NOTIFY_EVT = 39, /*!< When unregister for notification of a service completes, the event comes */ +} esp_gattc_cb_event_t; +/// Maximum Transmission Unit used in GATT #define ESP_GATT_DEF_BLE_MTU_SIZE 23 + +/// Maximum Transmission Unit allowed in GATT #define ESP_GATT_MAX_MTU_SIZE 517 -/* esp_ble_gattc_cb_param_t */ +/** + * @brief Gatt client callback parameters union + */ typedef union { - /*registration data for ESP_GATTC_REG_EVT */ - struct gattc_reg_evt_param { - esp_gatt_status_t status; - esp_gatt_if_t gatt_if; - esp_bt_uuid_t uuid; /* btla-specific ++ */ - } reg; + /** + * @brief ESP_GATTC_REG_EVT + */ + struct gattc_reg_evt_param { + esp_gatt_status_t status; /*!< Operation status */ + esp_gatt_if_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + uint16_t app_id; /*!< Application id which input in register API */ + } reg; /*!< Gatt client callback param of ESP_GATTC_REG_EVT */ - /* ESP_GATTC_OPEN_EVT */ + /** + * @brief ESP_GATTC_OPEN_EVT + */ struct gattc_open_evt_param { - esp_gatt_status_t status; - uint16_t conn_id; - esp_gatt_if_t gatt_if; - esp_bd_addr_t remote_bda; - // tBTA_TRANSPORT transport; - uint16_t mtu; - } open; + esp_gatt_status_t status; /*!< Operation status */ + uint16_t conn_id; /*!< Connection id */ + esp_gatt_if_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + esp_bd_addr_t remote_bda; /*!< Remote bluetooth device address */ + uint16_t mtu; /*!< MTU size */ + } open; /*!< Gatt client callback param of ESP_GATTC_OPEN_EVT */ - /* ESP_GATTC_CLOSE_EVT */ + /** + * @brief ESP_GATTC_CLOSE_EVT + */ struct gattc_close_evt_param { - esp_gatt_status_t status; - uint16_t conn_id; - esp_gatt_if_t gatt_if; - esp_bd_addr_t remote_bda; - esp_gatt_reason_t reason; - } close; + esp_gatt_status_t status; /*!< Operation status */ + uint16_t conn_id; /*!< Connection id */ + esp_gatt_if_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + esp_bd_addr_t remote_bda; /*!< Remote bluetooth device address */ + esp_gatt_conn_reason_t reason; /*!< The reason of gatt connection close */ + } close; /*!< Gatt client callback param of ESP_GATTC_CLOSE_EVT */ - /* ESP_GATTC_CFG_MTU_EVT */ + /** + * @brief ESP_GATTC_CFG_MTU_EVT + */ struct gattc_cfg_mtu_evt_param { - uint16_t conn_id; - esp_gatt_status_t status; - uint16_t mtu; - } cfg_mtu; + esp_gatt_status_t status; /*!< Operation status */ + uint16_t conn_id; /*!< Connection id */ + uint16_t mtu; /*!< MTU size */ + } cfg_mtu; /*!< Gatt client callback param of ESP_GATTC_CFG_MTU_EVT */ - /* ESP_GATTC_SEARCH_CMPL_EVT */ + /** + * @brief ESP_GATTC_SEARCH_CMPL_EVT + */ struct gattc_search_cmpl_evt_param { - uint16_t conn_id; - esp_gatt_status_t status; - } search_cmpl; + esp_gatt_status_t status; /*!< Operation status */ + uint16_t conn_id; /*!< Connection id */ + } search_cmpl; /*!< Gatt client callback param of ESP_GATTC_SEARCH_CMPL_EVT */ - /* ESP_GATTC_SEARCH_RES_EVT */ + /** + * @brief ESP_GATTC_SEARCH_RES_EVT + */ struct gattc_search_res_evt_param { - uint16_t conn_id; - esp_gatt_srvc_id_t service_id; - } search_res; + uint16_t conn_id; /*!< Connection id */ + esp_gatt_srvc_id_t srvc_id; /*!< Service id, include service uuid and other information */ + } search_res; /*!< Gatt client callback param of ESP_GATTC_SEARCH_RES_EVT */ - /* ESP_GATTC_READ_CHAR_EVT, ESP_GATTC_READ_DESCR_EVT */ + /** + * @brief ESP_GATTC_READ_CHAR_EVT, ESP_GATTC_READ_DESCR_EVT + */ struct gattc_read_char_evt_param { - uint16_t conn_id; - esp_gatt_status_t status; - esp_gatt_srvc_id_t srvc_id; - esp_gatt_id_t char_id; - esp_gatt_id_t descr_id; - uint8_t *value; - uint16_t value_type; - uint16_t value_len; - } read; /* ESP_GATTC_READ_CHAR_EVT */ + esp_gatt_status_t status; /*!< Operation status */ + uint16_t conn_id; /*!< Connection id */ + esp_gatt_srvc_id_t srvc_id; /*!< Service id, include service uuid and other information */ + esp_gatt_id_t char_id; /*!< Characteristic id, include characteristic uuid and other information */ + esp_gatt_id_t descr_id; /*!< Descriptor id, include descriptor uuid and other information */ + uint8_t *value; /*!< Characteristic value */ + uint16_t value_type; /*!< Characteristic value type */ + uint16_t value_len; /*!< Characteristic value length */ + } read; /*!< Gatt client callback param of ESP_GATTC_READ_CHAR_EVT */ - /* ESP_GATTC_WRITE_CHAR_EVT, ESP_GATTC_PREP_WRITE_EVT, ESP_GATTC_WRITE_DESCR_EVT */ + /** + * @brief ESP_GATTC_WRITE_CHAR_EVT, ESP_GATTC_PREP_WRITE_EVT, ESP_GATTC_WRITE_DESCR_EVT + */ struct gattc_write_evt_param { - uint16_t conn_id; - esp_gatt_status_t status; - esp_gatt_srvc_id_t srvc_id; - esp_gatt_id_t char_id; - esp_gatt_id_t descr_id; - } write; + esp_gatt_status_t status; /*!< Operation status */ + uint16_t conn_id; /*!< Connection id */ + esp_gatt_srvc_id_t srvc_id; /*!< Service id, include service uuid and other information */ + esp_gatt_id_t char_id; /*!< Characteristic id, include characteristic uuid and other information */ + esp_gatt_id_t descr_id; /*!< Descriptor id, include descriptor uuid and other information */ + } write; /*!< Gatt client callback param of ESP_GATTC_WRITE_DESCR_EVT */ - /* ESP_GATTC_EXEC_EVT */ + /** + * @brief ESP_GATTC_EXEC_EVT + */ struct gattc_exec_cmpl_evt_param { - uint16_t conn_id; - esp_gatt_status_t status; - } exec_cmpl; + esp_gatt_status_t status; /*!< Operation status */ + uint16_t conn_id; /*!< Connection id */ + } exec_cmpl; /*!< Gatt client callback param of ESP_GATTC_EXEC_EVT */ - /* ESP_GATTC_NOTIF_EVT */ + /** + * @brief ESP_GATTC_NOTIFY_EVT + */ struct gattc_notify_evt_param { - uint16_t conn_id; - esp_bd_addr_t bda; - esp_gatt_srvc_id_t srvc_id; - esp_gatt_id_t char_id; - esp_gatt_id_t descr_id; - uint16_t value_len; - uint8_t *value; - bool is_notify; - } notify; + uint16_t conn_id; /*!< Connection id */ + esp_bd_addr_t remote_bda; /*!< Remote bluetooth device address */ + esp_gatt_srvc_id_t srvc_id; /*!< Service id, include service uuid and other information */ + esp_gatt_id_t char_id; /*!< Characteristic id, include characteristic uuid and other information */ + esp_gatt_id_t descr_id; /*!< Descriptor id, include descriptor uuid and other information */ + uint16_t value_len; /*!< Notify attribute value */ + uint8_t *value; /*!< Notify attribute value */ + bool is_notify; /*!< True means notify, false means indicate */ + } notify; /*!< Gatt client callback param of ESP_GATTC_NOTIFY_EVT */ - /* ESP_GATTC_SRVC_CHG_EVT*/ + /** + * @brief ESP_GATTC_SRVC_CHG_EVT + */ struct gattc_srvc_chg_evt_param { - esp_bd_addr_t remote_bda; - } srvc_chg; + esp_bd_addr_t remote_bda; /*!< Remote bluetooth device address */ + } srvc_chg; /*!< Gatt client callback param of ESP_GATTC_SRVC_CHG_EVT */ - /* ESP_GATTC_CONGEST_EVT */ + /** + * @brief ESP_GATTC_CONGEST_EVT + */ struct gattc_congest_evt_param { - uint16_t conn_id; - bool congested; - } congest; + uint16_t conn_id; /*!< Connection id */ + bool congested; /*!< Congested or not */ + } congest; /*!< Gatt client callback param of ESP_GATTC_CONGEST_EVT */ - /* ESP_GATTC_GET_CHAR_EVT */ + /** + * @brief ESP_GATTC_GET_CHAR_EVT + */ struct gattc_get_char_evt_param { - uint16_t conn_id; - esp_gatt_status_t status; - esp_gatt_srvc_id_t srvc_id; - esp_gatt_id_t char_id; - esp_gatt_char_prop_t char_prop; - } get_char; + esp_gatt_status_t status; /*!< Operation status */ + uint16_t conn_id; /*!< Connection id */ + esp_gatt_srvc_id_t srvc_id; /*!< Service id, include service uuid and other information */ + esp_gatt_id_t char_id; /*!< Characteristic id, include characteristic uuid and other information */ + esp_gatt_char_prop_t char_prop; /*!< Characteristic property */ + } get_char; /*!< Gatt client callback param of ESP_GATTC_GET_CHAR_EVT */ - /* ESP_GATTC_GET_DESCR_EVT */ + /** + * @brief ESP_GATTC_GET_DESCR_EVT + */ struct gattc_get_descr_evt_param { - uint16_t conn_id; - esp_gatt_status_t status; - esp_gatt_srvc_id_t srvc_id; - esp_gatt_id_t char_id; - esp_gatt_id_t descr_id; - } get_descr; + esp_gatt_status_t status; /*!< Operation status */ + uint16_t conn_id; /*!< Connection id */ + esp_gatt_srvc_id_t srvc_id; /*!< Service id, include service uuid and other information */ + esp_gatt_id_t char_id; /*!< Characteristic id, include characteristic uuid and other information */ + esp_gatt_id_t descr_id; /*!< Descriptor id, include descriptor uuid and other information */ + } get_descr; /*!< Gatt client callback param of ESP_GATTC_GET_DESCR_EVT */ - /* ESP_GATTC_GET_INCL_SRVC_EVT */ + /** + * @brief ESP_GATTC_GET_INCL_SRVC_EVT + */ struct gattc_get_incl_srvc_evt_param { - uint16_t conn_id; - esp_gatt_status_t status; - esp_gatt_srvc_id_t srvc_id; - esp_gatt_srvc_id_t incl_srvc_id; - } get_incl_srvc; + esp_gatt_status_t status; /*!< Operation status */ + uint16_t conn_id; /*!< Connection id */ + esp_gatt_srvc_id_t srvc_id; /*!< Service id, include service uuid and other information */ + esp_gatt_srvc_id_t incl_srvc_id;/*!< Included service id, include service uuid and other information */ + } get_incl_srvc; /*!< Gatt client callback param of ESP_GATTC_GET_INCL_SRVC_EVT */ - /* ESP_GATTC_REG_FOR_NOTIF_EVT, ESP_GATTC_UNREG_FOR_NOTIF_EVT */ + /** + * @brief ESP_GATTC_REG_FOR_NOTIFY_EVT + */ struct gattc_reg_for_notify_evt_param { - esp_gatt_status_t status; - esp_gatt_srvc_id_t srvc_id; - esp_gatt_id_t char_id; - } reg_for_notify; + esp_gatt_status_t status; /*!< Operation status */ + esp_gatt_srvc_id_t srvc_id; /*!< Service id, include service uuid and other information */ + esp_gatt_id_t char_id; /*!< Characteristic id, include characteristic uuid and other information */ + } reg_for_notify; /*!< Gatt client callback param of ESP_GATTC_REG_FOR_NOTIFY_EVT */ + /** + * @brief ESP_GATTC_UNREG_FOR_NOTIFY_EVT + */ struct gattc_unreg_for_notify_evt_param { - esp_gatt_status_t status; - esp_gatt_srvc_id_t srvc_id; - esp_gatt_id_t char_id; - } unreg_for_notify; + esp_gatt_status_t status; /*!< Operation status */ + esp_gatt_srvc_id_t srvc_id; /*!< Service id, include service uuid and other information */ + esp_gatt_id_t char_id; /*!< Characteristic id, include characteristic uuid and other information */ + } unreg_for_notify; /*!< Gatt client callback param of ESP_GATTC_UNREG_FOR_NOTIFY_EVT */ -} esp_ble_gattc_cb_param_t; +} esp_ble_gattc_cb_param_t; /*!< GATT client callback parameter union type */ -/******************************************************************************* -** -** @function esp_ble_gattc_app_register_callback -** -** @brief This function is called to register application callbacks -** with GATTC module. -** -** @param[in] callback - pointer to the application callback function. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to register application callbacks + * with GATTC module. + * + * @param[in] callback : pointer to the application callback function. + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_register_callback(esp_profile_cb_t callback); - -/******************************************************************************* -** -** @function esp_ble_gattc_app_register -** -** @brief This function is called to register application callbacks -** with GATTC module. -** -** @param[in] app_id : Application Identitfy (UUID), for different application -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to register application callbacks + * with GATTC module. + * + * @param[in] app_id : Application Identify (UUID), for different application + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_app_register(uint16_t app_id); -/******************************************************************************* -** -** @function esp_ble_gattc_app_unregister -** -** @brief This function is called to unregister an application -** from GATTC module. -** -** @param[in] gatt_if - app identifier. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to unregister an application + * from GATTC module. + * + * @param[in] gatt_if : app identifier. + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_app_unregister(esp_gatt_if_t gatt_if); -/******************************************************************************* -** -** @function esp_ble_gattc_conn -** -** @brief Open a direct connection or add a background auto connection -** bd address -** -** @param[in] gatt_if: application identity. -** @param[in] remote_bda: remote device BD address. -** @param[in] is_direct: direct connection or background auto connection -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief Open a direct connection or add a background auto connection + * + * @param[in] gatt_if: application identity. + * @param[in] remote_bda: remote device bluetooth device address. + * @param[in] is_direct: direct connection or background auto connection + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_open(esp_gatt_if_t gatt_if, esp_bd_addr_t remote_bda, bool is_direct); -/******************************************************************************* -** -** @function esp_ble_gattc_close -** -** @brief Close a connection to a GATT server. -** -** @param[in] conn_id: connectino ID to be closed. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ -esp_err_t esp_ble_gattc_close (uint16_t conn_id); + +/** + * @brief Close a connection to a GATT server. + * + * @param[in] conn_id: connection ID to be closed. + * + * @return + * - ESP_OK: success + * - other: failed + * + */ +esp_err_t esp_ble_gattc_close(uint16_t conn_id); - -/******************************************************************************* -** -** @function esp_ble_gattc_config_mtu -** -** @brief Configure the MTU size in the GATT channel. This can be done -** only once per connection. -** -** @param[in] conn_id: connection ID. -** mtu: desired MTU size to use. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ -esp_err_t esp_ble_gattc_config_mtu (uint16_t conn_id, uint16_t mtu); +/** + * @brief Configure the MTU size in the GATT channel. This can be done + * only once per connection. + * + * @param[in] conn_id: connection ID. + * @param[in] mtu: desired MTU size to use. + * + * @return + * - ESP_OK: success + * - other: failed + * + */ +esp_err_t esp_ble_gattc_config_mtu(uint16_t conn_id, uint16_t mtu); -/******************************************************************************* -** -** @function esp_ble_gattc_search_service -** -** @brief This function is called to request a GATT service discovery -** on a GATT server. This function report service search result -** by a callback event, and followed by a service search complete -** event. -** -** @param[in] conn_id: connection ID. -** @param[in] filter_uuid: a UUID of the service application is interested in. -** If Null, discover for all services. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to request a GATT service discovery + * on a GATT server. This function report service search result + * by a callback event, and followed by a service search complete + * event. + * + * @param[in] conn_id: connection ID. + * @param[in] filter_uuid: a UUID of the service application is interested in. + * If Null, discover for all services. + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_search_service(uint16_t conn_id, esp_bt_uuid_t *filter_uuid); -/**************************************************************************************************** -** -** @function esp_ble_gattc_get_characteristic -** -** @brief This function is called to find the first characteristic of the -** service on the given server. -** -** @param[in] conn_id: connection ID which identify the server. -** -** @param[in] srvc_id: serivce ID -** -** @param[in] start_char_id: the start characteristic ID -** -** @return ESP_OK - success, other - failed -** -*****************************************************************************************************/ - +/** + * @brief This function is called to find the first characteristic of the + * service on the given server. + * + * @param[in] conn_id: connection ID which identify the server. + * + * @param[in] srvc_id: service ID + * + * @param[in] start_char_id: the start characteristic ID + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_get_characteristic(uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *start_char_id); -/**************************************************************************************************** -** -** @function esp_ble_gattc_get_descriptor -** -** @brief This function is called to find the descriptor of the -** service on the given server. -** -** @param[in] conn_id: connection ID which identify the server. -** @param[in] srvc_id: the service ID of which the characteristic is belonged to. -** @param[in] char_id: Characteristic ID, if NULL find the first available -** characteristic. -** @param[in] start_descr_id: the sctart descriptor id -** -** @return ESP_OK - success, other - failed -** -*****************************************************************************************************/ + +/** + * @brief This function is called to find the descriptor of the + * service on the given server. + * + * @param[in] conn_id: connection ID which identify the server. + * @param[in] srvc_id: the service ID of which the characteristic is belonged to. + * @param[in] char_id: Characteristic ID, if NULL find the first available + * characteristic. + * @param[in] start_descr_id: the start descriptor id + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_get_descriptor(uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id, esp_gatt_id_t *start_descr_id); -/**************************************************************************************************** -** -** @function esp_ble_gattc_get_include_service -** -** @brief This function is called to find the first characteristic of the -** service on the given server. -** -** @param[in] conn_id: connection ID which identify the server. -** @param[in] srvc_id: the service ID of which the characteristic is belonged to. -** @param[in] start_incl_srvc_id: the start include service id -** -** @return ESP_OK - success, other - failed -** -*****************************************************************************************************/ - - +/** + * @brief This function is called to find the first characteristic of the + * service on the given server. + * + * @param[in] conn_id: connection ID which identify the server. + * @param[in] srvc_id: the service ID of which the characteristic is belonged to. + * @param[in] start_incl_srvc_id: the start include service id + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_get_included_service(uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_srvc_id_t *start_incl_srvc_id); - -/******************************************************************************* -** -** @function esp_ble_gattc_read_char -** -** @brief This function is called to read a service's characteristics of -** the given characteritisc ID.UTH_REQ_NO_SCATTERNET -** -** @param[in] conn_id - connectino ID. -** @param[in] srvc_id - serivcie ID. -** @param[in] char_id - characteritic ID to read. -** @param[in] auth_req - authenticate request type -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to read a service's characteristics of + * the given characteriistic ID + * + * @param[in] conn_id : connection ID. + * @param[in] srvc_id : service ID. + * @param[in] char_id : characteristic ID to read. + * @param[in] auth_req : authenticate request type + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_read_char (uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id, esp_gatt_auth_req_t auth_req); - -/******************************************************************************* -** -** @function esp_ble_gattc_read_char_descr -** -** @brief This function is called to read a characteristics descriptor. -** -** @param[in] conn_id - connection ID. -** @param[in] srvc_id - serivcie ID. -** @param[in] descr_id - characteritic descriptor ID to read. -** @param[in] auth_req - authenticate request type -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to read a characteristics descriptor. + * + * @param[in] conn_id : connection ID. + * @param[in] srvc_id : service ID. + * @param[in] char_id : characteristic ID to read. + * @param[in] descr_id : characteristic descriptor ID to read. + * @param[in] auth_req : authenticate request type + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_read_char_descr (uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id, @@ -423,70 +445,74 @@ esp_err_t esp_ble_gattc_read_char_descr (uint16_t conn_id, esp_gatt_auth_req_t auth_req); -/******************************************************************************* -** -** @function esp_ble_gattc_write_char -** -** @brief This function is called to write characteristic value. -** -** @param[in] conn_id - connection ID. -** @param[in] srvc_id - serivcie ID. -** @param[in] char_id - characteristic ID to write. -** @param[in] value_len: length of the value to be written. -** @param[in] value - the value to be written. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to write characteristic value. + * + * @param[in] conn_id : connection ID. + * @param[in] srvc_id : service ID. + * @param[in] char_id : characteristic ID to write. + * @param[in] value_len: length of the value to be written. + * @param[in] value : the value to be written. + * @param[in] write_type : the type of attribute write operation. + * @param[in] auth_req : authentication request. + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_write_char( uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id, uint16_t value_len, uint8_t *value, + esp_gatt_write_type_t write_type, esp_gatt_auth_req_t auth_req); -/******************************************************************************* -** -** @function esp_ble_gattc_write_char_descr -** -** @brief This function is called to write characteristic descriptor value. -** -** @param[in] conn_id - connection ID -** @param[in] srvc_id - serivcie ID. -** @param[in] char_id - characteristic ID. -** @param[in] descr_id - characteristic descriptor ID to write. -** @param[in] value_len: length of the value to be written. -** @param[in] value - the value to be written. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to write characteristic descriptor value. + * + * @param[in] conn_id : connection ID + * @param[in] srvc_id : service ID. + * @param[in] char_id : characteristic ID. + * @param[in] descr_id : characteristic descriptor ID to write. + * @param[in] value_len: length of the value to be written. + * @param[in] value : the value to be written. + * @param[in] write_type : the type of attribute write operation. + * @param[in] auth_req : authentication request. + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_write_char_descr (uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id, esp_gatt_id_t *descr_id, uint16_t value_len, uint8_t *value, + esp_gatt_write_type_t write_type, esp_gatt_auth_req_t auth_req); - -/******************************************************************************* -** -** @function esp_ble_gattc_prepare_write -** -** @brief This function is called to prepare write a characteristic value. -** -** @param[in] conn_id - connection ID. -** @param[in] char_id - GATT characteritic ID of the service. -** @param[in] offset - offset of the write value. -** @param[in] value_len: length of the value to be written. -** @param[in] value - the value to be written. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to prepare write a characteristic value. + * + * @param[in] conn_id : connection ID. + * @param[in] srvc_id : service ID. + * @param[in] char_id : GATT characteristic ID of the service. + * @param[in] offset : offset of the write value. + * @param[in] value_len: length of the value to be written. + * @param[in] value : the value to be written. + * @param[in] auth_req : authentication request. + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_prepare_write(uint16_t conn_id, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id, @@ -495,56 +521,52 @@ esp_err_t esp_ble_gattc_prepare_write(uint16_t conn_id, uint8_t *value, esp_gatt_auth_req_t auth_req); -/******************************************************************************* -** -** @function esp_ble_gattc_execu_write -** -** @brief This function is called to execute write a prepare write sequence. -** -** @param[in] conn_id - connection ID. -** @param[in] is_execute - execute or cancel. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to execute write a prepare write sequence. + * + * @param[in] conn_id : connection ID. + * @param[in] is_execute : execute or cancel. + * + * @return + * - ESP_OK: success + * - other: failed + * + */ esp_err_t esp_ble_gattc_execute_write (uint16_t conn_id, bool is_execute); -/******************************************************************************* -** -** @function esp_ble_gattc_register_for_notify -** -** @brief This function is called to register for notification of a service. -** -** @param[in] gatt_if - gatt interface id. -** @param[in] bda - target GATT server. -** @param[in] srvc_id - pointer to GATT service ID. -** @param[in] char_id - pointer to GATT characteristic ID. -** -** @return OK if registration succeed, otherwise failed. -** -*******************************************************************************/ +/** + * @brief This function is called to register for notification of a service. + * + * @param[in] gatt_if : gatt interface id. + * @param[in] server_bda : target GATT server. + * @param[in] srvc_id : pointer to GATT service ID. + * @param[in] char_id : pointer to GATT characteristic ID. + * + * @return + * - ESP_OK: registration succeeds + * - other: failed + * + */ esp_gatt_status_t esp_ble_gattc_register_for_notify (esp_gatt_if_t gatt_if, esp_bd_addr_t server_bda, esp_gatt_srvc_id_t *srvc_id, esp_gatt_id_t *char_id); - -/******************************************************************************* -** -** @function esp_ble_gattc_unregister_ntf -** -** @brief This function is called to de-register for notification of a service. -** -** @param[in] gatt_if - gatt interface id. -** @param[in] bda - target GATT server. -** @param[in] srvc_id - pointer to GATT service ID. -** @param[in] char_id - pointer to GATT characteristic ID. -** -** @return OK if deregistration succeed, otherwise failed. -** -*******************************************************************************/ +/** + * @brief This function is called to de-register for notification of a service. + * + * @param[in] gatt_if : gatt interface id. + * @param[in] server_bda : target GATT server. + * @param[in] srvc_id : pointer to GATT service ID. + * @param[in] char_id : pointer to GATT characteristic ID. + * + * @return + * - ESP_OK: unregister succeeds + * - other: failed + * + */ esp_gatt_status_t esp_ble_gattc_unregister_for_notify (esp_gatt_if_t gatt_if, esp_bd_addr_t server_bda, esp_gatt_srvc_id_t *srvc_id, diff --git a/components/bt/bluedroid/api/include/esp_gatts_api.h b/components/bt/bluedroid/api/include/esp_gatts_api.h index c2420379d3..3d858d5b7e 100644 --- a/components/bt/bluedroid/api/include/esp_gatts_api.h +++ b/components/bt/bluedroid/api/include/esp_gatts_api.h @@ -21,397 +21,441 @@ #include "bta_gatt_api.h" #include "esp_err.h" -/* GATT Server Data Structure */ -/* Server callback function events */ -#define ESP_GATTS_REG_EVT 0 -#define ESP_GATTS_READ_EVT 1 -#define ESP_GATTS_WRITE_EVT 2 -#define ESP_GATTS_EXEC_WRITE_EVT 3 -#define ESP_GATTS_MTU_EVT 4 -#define ESP_GATTS_CONF_EVT 5 -#define ESP_GATTS_UNREG_EVT 6 -#define ESP_GATTS_CREATE_EVT 7 -#define ESP_GATTS_ADD_INCL_SRVC_EVT 8 -#define ESP_GATTS_ADD_CHAR_EVT 9 -#define ESP_GATTS_ADD_CHAR_DESCR_EVT 10 -#define ESP_GATTS_DELELTE_EVT 11 -#define ESP_GATTS_START_EVT 12 -#define ESP_GATTS_STOP_EVT 13 -#define ESP_GATTS_CONNECT_EVT 14 -#define ESP_GATTS_DISCONNECT_EVT 15 -#define ESP_GATTS_OPEN_EVT 16 -#define ESP_GATTS_CANCEL_OPEN_EVT 17 -#define ESP_GATTS_CLOSE_EVT 18 -#define ESP_GATTS_LISTEN_EVT 19 -#define ESP_GATTS_CONGEST_EVT 20 -/* following is extra event */ -#define ESP_GATTS_RESPONSE_EVT 21 +/// GATT Server callback function events +typedef enum { + ESP_GATTS_REG_EVT = 0, /*!< When register application id, the event comes */ + ESP_GATTS_READ_EVT = 1, /*!< When gatt client request read operation, the event comes */ + ESP_GATTS_WRITE_EVT = 2, /*!< When gatt client request write operation, the event comes */ + ESP_GATTS_EXEC_WRITE_EVT = 3, /*!< When gatt client request execute write, the event comes */ + ESP_GATTS_MTU_EVT = 4, /*!< When set mtu complete, the event comes */ + ESP_GATTS_CONF_EVT = 5, /*!< When receive confirm, the event comes */ + ESP_GATTS_UNREG_EVT = 6, /*!< When unregister application id, the event comes */ + ESP_GATTS_CREATE_EVT = 7, /*!< When create service complete, the event comes */ + ESP_GATTS_ADD_INCL_SRVC_EVT = 8, /*!< When add included service complete, the event comes */ + ESP_GATTS_ADD_CHAR_EVT = 9, /*!< When add characteristic complete, the event comes */ + ESP_GATTS_ADD_CHAR_DESCR_EVT = 10, /*!< When add descriptor complete, the event comes */ + ESP_GATTS_DELETE_EVT = 11, /*!< When delete service complete, the event comes */ + ESP_GATTS_START_EVT = 12, /*!< When start service complete, the event comes */ + ESP_GATTS_STOP_EVT = 13, /*!< When stop service complete, the event comes */ + ESP_GATTS_CONNECT_EVT = 14, /*!< When gatt client connect, the event comes */ + ESP_GATTS_DISCONNECT_EVT = 15, /*!< When gatt client disconnect, the event comes */ + ESP_GATTS_OPEN_EVT = 16, /*!< When connect to peer, the event comes */ + ESP_GATTS_CANCEL_OPEN_EVT = 17, /*!< When disconnect from peer, the event comes */ + ESP_GATTS_CLOSE_EVT = 18, /*!< When gatt server close, the event comes */ + ESP_GATTS_LISTEN_EVT = 19, /*!< When gatt listen to be connected the event comes */ + ESP_GATTS_CONGEST_EVT = 20, /*!< When congest happen, the event comes */ + /* following is extra event */ + ESP_GATTS_RESPONSE_EVT = 21, /*!< When gatt send response complete, the event comes */ +} esp_gatts_cb_event_t; -/* esp_ble_gatts_cb_param_t */ +/** + * @brief Gatt server callback parameters union + */ typedef union { - //ESP_GATTS_REG_EVT + /** + * @brief ESP_GATTS_REG_EVT + */ struct gatts_reg_evt_param { - int status; - uint16_t gatt_if; - uint16_t app_id; - } reg; - // param for ESP_GATTS_READ_EVT + esp_gatt_status_t status; /*!< Operation status */ + uint16_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + uint16_t app_id; /*!< Application id which input in register API */ + } reg; /*!< Gatt server callback param of ESP_GATTS_REG_EVT */ + + /** + * @brief ESP_GATTS_READ_EVT + */ struct gatts_read_evt_param { - uint16_t conn_id; - uint32_t trans_id; - esp_bd_addr_t bda; - uint16_t handle; - uint16_t offset; - bool is_long; - } read; - // param for ESP_GATTS_WRITE_EVT + uint16_t conn_id; /*!< Connection id */ + uint32_t trans_id; /*!< Transfer id */ + esp_bd_addr_t bda; /*!< The bluetooth device address which been read */ + uint16_t handle; /*!< The attribute handle */ + uint16_t offset; /*!< Offset of the value, if the value is too long */ + bool is_long; /*!< The value is too long or not */ + } read; /*!< Gatt server callback param of ESP_GATTS_READ_EVT */ + + /** + * @brief ESP_GATTS_WRITE_EVT + */ struct gatts_write_evt_param { - uint16_t conn_id; - uint32_t trans_id; - esp_bd_addr_t bda; - uint16_t handle; - uint16_t offset; - bool need_rsp; - bool is_prep; - uint16_t len; - uint8_t *value; - } write; - // param for ESP_GATTS_EXEC_WRITE_EVT + uint16_t conn_id; /*!< Connection id */ + uint32_t trans_id; /*!< Transfer id */ + esp_bd_addr_t bda; /*!< The bluetooth device address which been written */ + uint16_t handle; /*!< The attribute handle */ + uint16_t offset; /*!< Offset of the value, if the value is too long */ + bool need_rsp; /*!< The write operation need to do response */ + bool is_prep; /*!< This write operation is prepare write */ + uint16_t len; /*!< The write attribute value length */ + uint8_t *value; /*!< The write attribute value */ + } write; /*!< Gatt server callback param of ESP_GATTS_WRITE_EVT */ + + /** + * @brief ESP_GATTS_EXEC_WRITE_EVT + */ struct gatts_exec_write_evt_param { - uint16_t conn_id; - uint32_t trans_id; - esp_bd_addr_t bda; + uint16_t conn_id; /*!< Connection id */ + uint32_t trans_id; /*!< Transfer id */ + esp_bd_addr_t bda; /*!< The bluetooth device address which been written */ #define ESP_GATT_PREP_WRITE_CANCEL 0x00 #define ESP_GATT_PREP_WRITE_EXEC 0x01 - uint8_t exec_write_flag; - } exec_write; - // param for ESP_GATTS_MTU_EVT + uint8_t exec_write_flag; /*!< Execute write flag */ + } exec_write; /*!< Gatt server callback param of ESP_GATTS_EXEC_WRITE_EVT */ + + /** + * @brief ESP_GATTS_MTU_EVT + */ struct gatts_mtu_evt_param { - uint16_t conn_id; - uint16_t mtu; - } mtu; - // param for ESP_GATTS_CONF_EVT + uint16_t conn_id; /*!< Connection id */ + uint16_t mtu; /*!< MTU size */ + } mtu; /*!< Gatt server callback param of ESP_GATTS_MTU_EVT */ + + /** + * @brief ESP_GATTS_CONF_EVT + */ struct gatts_conf_evt_param { - uint16_t conn_id; - int status; - } conf; - // param for ESP_GATTS_DEREG_EVT, NONE - // param for ESP_GATTS_CREATE_EVT + esp_gatt_status_t status; /*!< Operation status */ + uint16_t conn_id; /*!< Connection id */ + } conf; /*!< Gatt server callback param of ESP_GATTS_CONF_EVT (confirm) */ + + /** + * @brief ESP_GATTS_UNREG_EVT + */ + + /** + * @brief ESP_GATTS_CREATE_EVT + */ struct gatts_create_evt_param { - int status; - uint16_t gatt_if; - uint16_t service_handle; //handle - esp_gatt_srvc_id_t service_id; //id - } create; - // param for ESP_GATTS_ADD_INCL_SRVC_EVT + esp_gatt_status_t status; /*!< Operation status */ + uint16_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + uint16_t service_handle; /*!< Service attribute handle */ + esp_gatt_srvc_id_t service_id; /*!< Service id, include service uuid and other information */ + } create; /*!< Gatt server callback param of ESP_GATTS_CREATE_EVT */ + + /** + * @brief ESP_GATTS_ADD_INCL_SRVC_EVT + */ struct gatts_add_incl_srvc_evt_param { - int status; - uint16_t gatt_if; - uint16_t attr_handle; //handle - uint16_t service_handle; //handle - } add_incl_srvc; - // param for ESP_GATTS_ADD_CHAR_EVT + esp_gatt_status_t status; /*!< Operation status */ + uint16_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + uint16_t attr_handle; /*!< Included service attribute handle */ + uint16_t service_handle; /*!< Service attribute handle */ + } add_incl_srvc; /*!< Gatt server callback param of ESP_GATTS_ADD_INCL_SRVC_EVT */ + + /** + * @brief ESP_GATTS_ADD_CHAR_EVT + */ struct gatts_add_char_evt_param { - int status; - uint16_t gatt_if; - uint16_t attr_handle; //handle - uint16_t service_handle; //handle - esp_bt_uuid_t char_uuid; - } add_char; - // param for ESP_GATTS_ADD_CHAR_DESCR_EVT + esp_gatt_status_t status; /*!< Operation status */ + uint16_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + uint16_t attr_handle; /*!< Characteristic attribute handle */ + uint16_t service_handle; /*!< Service attribute handle */ + esp_bt_uuid_t char_uuid; /*!< Characteristic uuid */ + } add_char; /*!< Gatt server callback param of ESP_GATTS_ADD_CHAR_EVT */ + + /** + * @brief ESP_GATTS_ADD_CHAR_DESCR_EVT + */ struct gatts_add_char_descr_evt_param { - int status; - uint16_t gatt_if; - uint16_t attr_handle; //handle - uint16_t service_handle; //handle - esp_bt_uuid_t char_uuid; - } add_char_descr; - // param for ESP_GATTS_DELELTE_EVT + esp_gatt_status_t status; /*!< Operation status */ + uint16_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + uint16_t attr_handle; /*!< Descriptor attribute handle */ + uint16_t service_handle; /*!< Service attribute handle */ + esp_bt_uuid_t char_uuid; /*!< Characteristic uuid */ + } add_char_descr; /*!< Gatt server callback param of ESP_GATTS_ADD_CHAR_DESCR_EVT */ + + /** + * @brief ESP_GATTS_DELETE_EVT + */ struct gatts_delete_evt_param { - int status; - uint16_t gatt_if; - uint16_t service_handle; //handle - } del; - // param for ESP_GATTS_START_EVT + esp_gatt_status_t status; /*!< Operation status */ + uint16_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + uint16_t service_handle; /*!< Service attribute handle */ + } del; /*!< Gatt server callback param of ESP_GATTS_DELETE_EVT */ + + /** + * @brief ESP_GATTS_START_EVT + */ struct gatts_start_evt_param { - int status; - uint16_t gatt_if; - uint16_t service_handle; //handle - } start; - // param for ESP_GATTS_STOP_EVT + esp_gatt_status_t status; /*!< Operation status */ + uint16_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + uint16_t service_handle; /*!< Service attribute handle */ + } start; /*!< Gatt server callback param of ESP_GATTS_START_EVT */ + + /** + * @brief ESP_GATTS_STOP_EVT + */ struct gatts_stop_evt_param { - int status; - uint16_t gatt_if; - uint16_t service_handle; //handle - } stop; - // param for ESP_GATTS_CONNECT_EVT + esp_gatt_status_t status; /*!< Operation status */ + uint16_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + uint16_t service_handle; /*!< Service attribute handle */ + } stop; /*!< Gatt server callback param of ESP_GATTS_STOP_EVT */ + + /** + * @brief ESP_GATTS_CONNECT_EVT + */ struct gatts_connect_evt_param { - uint16_t conn_id; - uint16_t gatt_if; - esp_bd_addr_t remote_bda; - bool is_connected; - } connect; - // param for ESP_GATTS_DISCONNECT_EVT + uint16_t conn_id; /*!< Connection id */ + uint16_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + esp_bd_addr_t remote_bda; /*!< Remote bluetooth device address */ + bool is_connected; /*!< Indicate it is connected or not */ + } connect; /*!< Gatt server callback param of ESP_GATTS_CONNECT_EVT */ + + /** + * @brief ESP_GATTS_DISCONNECT_EVT + */ struct gatts_disconnect_evt_param { - uint16_t conn_id; - uint16_t gatt_if; - esp_bd_addr_t remote_bda; - bool is_connected; - } disconnect; - // param for ESP_GATTS_OPEN_EVT none - // param for ESP_GATTS_CANCEL_OPEN_EVT none - // param for ESP_GATTS_CLOSE_EVT none - // param for ESP_GATTS_LISTEN_EVT none - // param for ESP_GATTS_CONGEST_EVT + uint16_t conn_id; /*!< Connection id */ + uint16_t gatt_if; /*!< Gatt interface id, different application on gatt client different gatt_if */ + esp_bd_addr_t remote_bda; /*!< Remote bluetooth device address */ + bool is_connected; /*!< Indicate it is connected or not */ + } disconnect; /*!< Gatt server callback param of ESP_GATTS_DISCONNECT_EVT */ + + /** + * @brief ESP_GATTS_OPEN_EVT + */ + /** + * @brief ESP_GATTS_CANCEL_OPEN_EVT + */ + /** + * @brief ESP_GATTS_CLOSE_EVT + */ + /** + * @brief ESP_GATTS_LISTEN_EVT + */ + /** + * @brief ESP_GATTS_CONGEST_EVT + */ struct gatts_congest_evt_param { - uint16_t conn_id; - bool congested; - } congest; - // param for ESP_GATTS_RESPONSE_EVT + uint16_t conn_id; /*!< Connection id */ + bool congested; /*!< Congested or not */ + } congest; /*!< Gatt server callback param of ESP_GATTS_CONGEST_EVT */ + + /** + * @brief ESP_GATTS_RESPONSE_EVT + */ struct gatts_rsp_evt_param { - int status; //response status, 0 is success - uint16_t handle; //attribute handle which send response - } rsp; + esp_gatt_status_t status; /*!< Operation status */ + uint16_t handle; /*!< Attribute handle which send response */ + } rsp; /*!< Gatt server callback param of ESP_GATTS_RESPONSE_EVT */ } esp_ble_gatts_cb_param_t; -/******************************************************************************* -** -** @function esp_ble_gatts_register_callback -** -** @brief This function is called to register application callbacks -** with BTA GATTS module. -** -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to register application callbacks + * with BTA GATTS module. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_register_callback(esp_profile_cb_t callback); -/******************************************************************************* -** -** @function esp_ble_gatts_app_register -** -** @brief This function is called to register application identity -** -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to register application identifier + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_app_register(uint16_t app_id); -/******************************************************************************* -** -** @function esp_ble_gatts_app_unregister -** -** @brief un-register with GATT Server. -** -** @param[in] gatt_if: gatt interface id. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief unregister with GATT Server. + * + * @param[in] gatt_if: gatt interface id. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_app_unregister(esp_gatt_if_t gatt_if); -/******************************************************************************* -** -** @function esp_ble_gatts_create_service -** -** @brief Create a service. When service creation is done, a callback -** event BTA_GATTS_CREATE_SRVC_EVT is called to report status -** and service ID to the profile. The service ID obtained in -** the callback function needs to be used when adding included -** service and characteristics/descriptors into the service. -** -** @param[in] gatt_if: gatt interface ID -** @param[in] service_id: service ID. -** @param[in] num_handle: numble of handle requessted for this service. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief Create a service. When service creation is done, a callback + * event BTA_GATTS_CREATE_SRVC_EVT is called to report status + * and service ID to the profile. The service ID obtained in + * the callback function needs to be used when adding included + * service and characteristics/descriptors into the service. + * + * @param[in] gatt_if: gatt interface ID + * @param[in] service_id: service ID. + * @param[in] num_handle: number of handle requested for this service. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_create_service(esp_gatt_if_t gatt_if, esp_gatt_srvc_id_t *service_id, uint16_t num_handle); -/******************************************************************************* -** -** @function esp_ble_gatts_add_include_service -** -** @brief This function is called to add an included service. After included -** service is included, a callback event BTA_GATTS_ADD_INCL_SRVC_EVT -** is reported the included service ID. -** -** @param[in] service_handle: service handle to which this included service is to -** be added. -** @param[in] included_service_handle: the service ID to be included. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ -esp_err_t esp_ble_gatts_add_include_service(uint16_t service_handle, uint16_t included_service_handle); +/** + * @brief This function is called to add an included service. After included + * service is included, a callback event BTA_GATTS_ADD_INCL_SRVC_EVT + * is reported the included service ID. + * + * @param[in] service_handle: service handle to which this included service is to + * be added. + * @param[in] included_service_handle: the service ID to be included. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ +esp_err_t esp_ble_gatts_add_included_service(uint16_t service_handle, uint16_t included_service_handle); -/******************************************************************************* -** -** @function esp_ble_gatts_add_char -** -** @brief This function is called to add a characteristic into a service. -** -** @param[in] service_handle: service handle to which this included service is to -** be added. -** @param[in] char_uuid : Characteristic UUID. -** @param[in] perm : Characteristic value declaration attribute permission. -** @param[in] property : Characteristic Properties -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to add a characteristic into a service. + * + * @param[in] service_handle: service handle to which this included service is to + * be added. + * @param[in] char_uuid : Characteristic UUID. + * @param[in] perm : Characteristic value declaration attribute permission. + * @param[in] property : Characteristic Properties + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_add_char(uint16_t service_handle, esp_bt_uuid_t *char_uuid, esp_gatt_perm_t perm, esp_gatt_char_prop_t property); - - -/******************************************************************************* -** -** @function esp_ble_gatts_add_char_descr -** -** @brief This function is called to add characteristic descriptor. When -** it's done, a callback event BTA_GATTS_ADD_DESCR_EVT is called -** to report the status and an ID number for this descriptor. -** -** @param[in] service_handle: service handle to which this charatceristic descriptor is to -** be added. -** @param[in] perm: descriptor access permission. -** @param[in] descr_uuid: descriptor UUID. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to add characteristic descriptor. When + * it's done, a callback event BTA_GATTS_ADD_DESCR_EVT is called + * to report the status and an ID number for this descriptor. + * + * @param[in] service_handle: service handle to which this characteristic descriptor is to + * be added. + * @param[in] perm: descriptor access permission. + * @param[in] descr_uuid: descriptor UUID. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_add_char_descr (uint16_t service_handle, esp_bt_uuid_t *descr_uuid, esp_gatt_perm_t perm); -/******************************************************************************* -** -** @function esp_ble_gatts_delete_service -** -** @brief This function is called to delete a service. When this is done, -** a callback event BTA_GATTS_DELETE_EVT is report with the status. -** -** @param[in] service_handled: service_handle to be deleted. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to delete a service. When this is done, + * a callback event BTA_GATTS_DELETE_EVT is report with the status. + * + * @param[in] service_handle: service_handle to be deleted. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_delete_service(uint16_t service_handle); -/******************************************************************************* -** -** @function esp_ble_gatts_start_service -** -** @brief This function is called to start a service. -** -** @param[in] service_handle: the service handle to be started. -** @param[in] sup_transport: supported trasnport. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to start a service. + * + * @param[in] service_handle: the service handle to be started. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_start_service(uint16_t service_handle); -/******************************************************************************* -** -** @function esp_ble_gatts_stop_service -** -** @brief This function is called to stop a service. -** -** @param[in] service_handle - service to be topped. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to stop a service. + * + * @param[in] service_handle - service to be topped. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_stop_service(uint16_t service_handle); -/******************************************************************************* -** -** @function esp_ble_gatts_send_indicate -** -** @brief This function is called to read a characteristics descriptor. -** -** @param[in] conn_id - connection id to indicate. -** @param[in] attribute_handle - attribute handle to indicate. -** @param[in] value_len - indicate value length. -** @param[in] value: value to indicate. -** @param[in] need_confirm - if this indication expects a confirmation or not. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to read a characteristics descriptor. + * + * @param[in] conn_id - connection id to indicate. + * @param[in] attr_handle - attribute handle to indicate. + * @param[in] value_len - indicate value length. + * @param[in] value: value to indicate. + * @param[in] need_confirm - if this indication expects a confirmation or not. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_send_indicate(uint16_t conn_id, uint16_t attr_handle, uint16_t value_len, uint8_t *value, bool need_confirm); -/******************************************************************************* -** -** @function esp_ble_gatts_send_rsp -** -** @brief This function is called to send a response to a request. -** -** @param[in] conn_id - connection identifier. -** @param[in] trans_id - transfe id -** @param[in] status - response status -** @param[in] rsp - response data. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief This function is called to send a response to a request. + * + * @param[in] conn_id - connection identifier. + * @param[in] trans_id - transfer id + * @param[in] status - response status + * @param[in] rsp - response data. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_send_response(uint16_t conn_id, uint32_t trans_id, esp_gatt_status_t status, esp_gatt_rsp_t *rsp); -/******************************************************************************* -** -** @function esp_ble_gatts_open -** -** @brief Open a direct open connection or add a background auto connection -** bd address -** -** @param[in] gatt_if: application ID. -** @param[in] remote_bda: remote device BD address. -** @param[in] is_direct: direct connection or background auto connection -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief Open a direct open connection or add a background auto connection + * + * @param[in] gatt_if: application ID. + * @param[in] remote_bda: remote device bluetooth device address. + * @param[in] is_direct: direct connection or background auto connection + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_open(esp_gatt_if_t gatt_if, esp_bd_addr_t remote_bda, bool is_direct); -/******************************************************************************* -** -** @function esp_ble_gatts_close -** -** @brief Close a connection a remote device. -** -** @param[in] conn_id: connectino ID to be closed. -** -** @return ESP_OK - success, other - failed -** -*******************************************************************************/ +/** + * @brief Close a connection a remote device. + * + * @param[in] conn_id: connection ID to be closed. + * + * @return + * - ESP_OK : success + * - other : failed + * + */ esp_err_t esp_ble_gatts_close(uint16_t conn_id); diff --git a/components/bt/bluedroid/api/include/esp_sdp_api.h b/components/bt/bluedroid/api/include/esp_sdp_api.h deleted file mode 100644 index 81add1e206..0000000000 --- a/components/bt/bluedroid/api/include/esp_sdp_api.h +++ /dev/null @@ -1,129 +0,0 @@ -// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at - -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -#ifndef __ESP_SDP_API_H__ -#define __ESP_SDP_API_H__ - -#include -#include "esp_err.h" -#include "esp_bt_defs.h" -#include "bta_sdp_api.h" -#include "bt_sdp.h" - -#define BT_SDP_STAT_SUCCESS BTA_SDP_SUCCESS -#define BT_SDP_STAT_FAILURE BTA_SDP_FAILURE -#define BT_SDP_STAT_BUSY BTA_SDP_BUSY - -#define BT_SDP_ENABLE_EVT BTA_SDP_ENABLE_EVT -#define BT_SDP_SEARCH_EVT BTA_SDP_SEARCH_EVT -#define BT_SDP_SEARCH_COMP_EVT BTA_SDP_SEARCH_COMP_EVT -#define BT_SDP_CREATE_RECORD_USER_EVT BTA_SDP_CREATE_RECORD_USER_EVT -#define BT_SDP_REMOVE_RECORD_USER_EVT BTA_SDP_REMOVE_RECORD_USER_EVT -#define BT_SDP_MAX_EVT BTA_SDP_MAX_EVT - -#define BT_SDP_MAX_RECORDS BTA_SDP_MAX_RECORDS - -typedef tBTA_SDP_STATUS bt_sdp_status_t; - -typedef tBTA_SDP_EVT bt_sdp_evt_t; - -typedef bluetooth_sdp_record bt_sdp_record_t; - -/* tBTA_SEARCH_COMP, bta_sdp_api.h */ -typedef struct { - bt_sdp_status_t status; - esp_bd_addr_t remote_addr; - esp_bt_uuid_t uuid; - int record_count; - bt_sdp_record_t records[BT_SDP_MAX_RECORDS]; -} bt_sdp_search_comp_t; - -/* tBTA_SDP, bta_sdp_api.h */ -typedef union { - bt_sdp_status_t status; - bt_sdp_search_comp_t sdp_search_comp; -} bt_sdp_t; - -typedef void (bt_sdp_cb_t)(bt_sdp_evt_t event, bt_sdp_t *p_data, void *user_data); - -esp_err_t esp_bt_sdp_enable(bt_sdp_cb_t *cback); - -esp_err_t esp_bt_sdp_search(esp_bd_addr_t bd_addr, esp_bt_uuid_t *uuid); - -esp_err_t esp_bt_sdp_create_record_by_user(void *user_data); - -esp_err_t esp_bt_sdp_remove_record_by_user(void *user_data); - - -/**********************************************************************************************/ -/**********************************************************************************************/ -/* API into SDP for local service database updates - * these APIs are indended to be called in callback function in the context of stack task, - * to handle BT_SDP_CREATE_RECORD_USER_EVT and BT_SDP_REMOVE_RECORD_USER_EVT - */ - -/* This structure is used to add protocol lists and find protocol elements */ -#define ESP_BT_SDP_MAX_PROTOCOL_PARAMS SDP_MAX_PROTOCOL_PARAMS // bt_target.h -typedef struct { - uint16_t protocol_uuid; - uint16_t num_params; - uint16_t params[ESP_BT_SDP_MAX_PROTOCOL_PARAMS]; -} sdp_proto_elem_t; // tSDP_PROTOCOL_ELEM, sdp_api.h - -#define ESP_BT_SDP_MAX_LIST_ELEMS SDP_MAX_LIST_ELEMS // sdp_api.h -typedef struct { - uint16_t num_elems; - sdp_proto_elem_t list_elem[ESP_BT_SDP_MAX_LIST_ELEMS]; -} sdp_proto_list_elem_t; // tSDP_PROTO_LIST_ELEM, sdp_api.h - - -uint32_t esp_bt_sdp_create_record(void); - -bool esp_bt_sdp_delete_record(uint32_t handle); - -int32_t esp_bt_sdp_read_record(uint32_t handle, uint8_t *data, int32_t *data_len); - -bool esp_bt_sdp_add_attribute (uint32_t handle, uint16_t attr_id, - uint8_t attr_type, uint32_t attr_len, - uint8_t *p_val); - -bool esp_bt_sdp_add_sequence (uint32_t handle, uint16_t attr_id, - uint16_t num_elem, uint8_t type[], - uint8_t len[], uint8_t *p_val[]); - -bool esp_bt_sdp_add_uuid_sequence (uint32_t handle, uint16_t attr_id, - uint16_t num_uuids, uint16_t *p_uuids); - - -bool esp_bt_sdp_add_protocol_list (uint32_t handle, uint16_t num_elem, - sdp_proto_elem_t *p_elem_list); - -bool esp_bt_sdp_add_addition_protocol_lists(uint32_t handle, uint16_t num_elem, - sdp_proto_list_elem_t *p_proto_list); - -bool esp_bt_sdp_add_profile_dscp_list (uint32_t handle, - uint16_t profile_uuid, - uint16_t version); - -bool esp_bt_sdp_add_lang_base_attr_id_list(uint32_t handle, - uint16_t lang, uint16_t char_enc, - uint16_t base_id); - -bool esp_bt_sdp_add_service_class_id_list(uint32_t handle, - uint16_t num_services, - uint16_t *p_service_uuids); - -bool esp_bt_sdp_delete_attribute(uint32_t handle, uint16_t attr_id); - -#endif /* __ESP_SDP_API_H__ */ diff --git a/components/bt/bluedroid/api/include/esp_sec_api.h b/components/bt/bluedroid/api/include/esp_sec_api.h deleted file mode 100644 index f9b0f9ec14..0000000000 --- a/components/bt/bluedroid/api/include/esp_sec_api.h +++ /dev/null @@ -1,79 +0,0 @@ -// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at - -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -#ifndef __ESP_SEC_API_H__ -#define __ESP_SEC_API_H__ - -#include "bt_types.h" - -#define APP_SEC_IRK_FLAG (0) -#define RAND_NB_LEN 0x08 -#define SEC_KEY_LEN 0x10 - -/* - * STRUCTURES DEFINITIONS - **************************************************************************************** - */ - - -/// Generic Security key structure -typedef struct { - /// Key value MSB -> LSB - UINT8 key[SEC_KEY_LEN]; -} smp_sec_key; - -///Random number structure -typedef struct { - ///8-byte array for random number - UINT8 nb[RAND_NB_LEN]; -} rand_nb; - -typedef struct { - // LTK - smp_sec_key ltk; - // Random Number - rand_nb rand_nb; - // EDIV - UINT16 ediv; - // LTK key size - UINT8 key_size; - - // Last paired peer address type - UINT8 peer_addr_type; - // Last paired peer address - BD_ADDR peer_addr; - - // authentication level - UINT8 auth; - -} tAPP_SEC_ENV; - -extern tAPP_SEC_ENV app_sec_env; - -/* -* GLOBAL FUNCTIONS DECLARATIONS -**************************************************************************************** -*/ - -void app_ble_sec_init(void); - -void app_ble_sec_pairing_cmp_evt_send(UINT8); - -UINT32 app_ble_sec_gen_tk(void); - -void app_ble_sec_gen_ltk(UINT8 key_size); - -void app_ble_security_start(void); - -#endif /* __ESP_SEC_API_H__ */ diff --git a/components/bt/bluedroid/bta/gatt/bta_gattc_api.c b/components/bt/bluedroid/bta/gatt/bta_gattc_api.c index 628b83b51b..b791538d78 100644 --- a/components/bt/bluedroid/bta/gatt/bta_gattc_api.c +++ b/components/bt/bluedroid/bta/gatt/bta_gattc_api.c @@ -196,7 +196,7 @@ void BTA_GATTC_CancelOpen(tBTA_GATTC_IF client_if, BD_ADDR remote_bda, BOOLEAN i ** ** Description Close a connection to a GATT server. ** -** Parameters conn_id: connectino ID to be closed. +** Parameters conn_id: connection ID to be closed. ** ** Returns void ** @@ -542,7 +542,7 @@ tBTA_GATT_STATUS BTA_GATTC_GetNextIncludedService(UINT16 conn_id, ** Description This function is called to read a service's characteristics of ** the given characteritisc ID. ** -** Parameters conn_id - connectino ID. +** Parameters conn_id - connection ID. ** p_char_id - characteritic ID to read. ** ** Returns None @@ -613,7 +613,7 @@ void BTA_GATTC_ReadCharDescr (UINT16 conn_id, ** Description This function is called to read multiple characteristic or ** characteristic descriptors. ** -** Parameters conn_id - connectino ID. +** Parameters conn_id - connection ID. ** p_read_multi - pointer to the read multiple parameter. ** ** Returns None diff --git a/components/bt/bluedroid/bta/gatt/bta_gatts_act.c b/components/bt/bluedroid/bta/gatt/bta_gatts_act.c index 7197120220..aa00bf287d 100644 --- a/components/bt/bluedroid/bta/gatt/bta_gatts_act.c +++ b/components/bt/bluedroid/bta/gatt/bta_gatts_act.c @@ -818,7 +818,7 @@ static void bta_gatts_send_request_cback (UINT16 conn_id, APPL_TRACE_ERROR("connection request on gatt_if[%d] is not interested", gatt_if); } } else { - APPL_TRACE_ERROR("request received on unknown connectino ID: %d", conn_id); + APPL_TRACE_ERROR("request received on unknown connection ID: %d", conn_id); } } diff --git a/components/bt/bluedroid/bta/gatt/bta_gatts_api.c b/components/bt/bluedroid/bta/gatt/bta_gatts_api.c index 757ab8ff08..d54935120c 100644 --- a/components/bt/bluedroid/bta/gatt/bta_gatts_api.c +++ b/components/bt/bluedroid/bta/gatt/bta_gatts_api.c @@ -501,7 +501,7 @@ void BTA_GATTS_CancelOpen(tBTA_GATTS_IF server_if, BD_ADDR remote_bda, BOOLEAN i ** ** Description Close a connection a remote device. ** -** Parameters conn_id: connectino ID to be closed. +** Parameters conn_id: connection ID to be closed. ** ** Returns void ** diff --git a/components/bt/bluedroid/bta/include/bta_gatt_api.h b/components/bt/bluedroid/bta/include/bta_gatt_api.h index 446c4bb3ae..d10ca46aee 100644 --- a/components/bt/bluedroid/bta/include/bta_gatt_api.h +++ b/components/bt/bluedroid/bta/include/bta_gatt_api.h @@ -679,7 +679,7 @@ extern void BTA_GATTC_CancelOpen(tBTA_GATTC_IF client_if, BD_ADDR remote_bda, BO ** ** Description Close a connection to a GATT server. ** -** Parameters conn_id: connectino ID to be closed. +** Parameters conn_id: connection ID to be closed. ** ** Returns void ** @@ -850,7 +850,7 @@ extern tBTA_GATT_STATUS BTA_GATTC_GetNextIncludedService(UINT16 conn_id, ** Description This function is called to read a service's characteristics of ** the given characteritisc ID. ** -** Parameters conn_id - connectino ID. +** Parameters conn_id - connection ID. ** p_char_id - characteritic ID to read. ** ** Returns None @@ -1010,7 +1010,7 @@ extern void BTA_GATTC_ExecuteWrite (UINT16 conn_id, BOOLEAN is_execute); ** Description This function is called to read multiple characteristic or ** characteristic descriptors. ** -** Parameters conn_id - connectino ID. +** Parameters conn_id - connection ID. ** p_read_multi - read multiple parameters. ** ** Returns None @@ -1337,7 +1337,7 @@ extern void BTA_GATTS_CancelOpen(tBTA_GATTS_IF server_if, BD_ADDR remote_bda, BO ** ** Description Close a connection a remote device. ** -** Parameters conn_id: connectino ID to be closed. +** Parameters conn_id: connection ID to be closed. ** ** Returns void ** diff --git a/components/bt/bluedroid/bta/sdp/bta_sdp_api.c b/components/bt/bluedroid/bta/sdp/bta_sdp_api.c index e69451197e..3969b45d8e 100644 --- a/components/bt/bluedroid/bta/sdp/bta_sdp_api.c +++ b/components/bt/bluedroid/bta/sdp/bta_sdp_api.c @@ -59,7 +59,7 @@ tBTA_SDP_STATUS BTA_SdpEnable(tBTA_SDP_DM_CBACK *p_cback) tBTA_SDP_STATUS status = BTA_SDP_FAILURE; tBTA_SDP_API_ENABLE *p_buf; - APPL_TRACE_API(__FUNCTION__); + APPL_TRACE_API("%s\n", __FUNCTION__); if (p_cback && FALSE == bta_sys_is_register(BTA_ID_SDP)) { memset(&bta_sdp_cb, 0, sizeof(tBTA_SDP_CB)); @@ -95,7 +95,7 @@ tBTA_SDP_STATUS BTA_SdpSearch(BD_ADDR bd_addr, tSDP_UUID *uuid) tBTA_SDP_STATUS ret = BTA_SDP_FAILURE; tBTA_SDP_API_SEARCH *p_msg; - APPL_TRACE_API(__FUNCTION__); + APPL_TRACE_API("%s\n", __FUNCTION__); if ((p_msg = (tBTA_SDP_API_SEARCH *)GKI_getbuf(sizeof(tBTA_SDP_API_SEARCH))) != NULL) { p_msg->hdr.event = BTA_SDP_API_SEARCH_EVT; bdcpy(p_msg->bd_addr, bd_addr); @@ -125,7 +125,7 @@ tBTA_SDP_STATUS BTA_SdpCreateRecordByUser(void *user_data) tBTA_SDP_STATUS ret = BTA_SDP_FAILURE; tBTA_SDP_API_RECORD_USER *p_msg; - APPL_TRACE_API(__FUNCTION__); + APPL_TRACE_API("%s\n", __FUNCTION__); if ((p_msg = (tBTA_SDP_API_RECORD_USER *)GKI_getbuf(sizeof(tBTA_SDP_API_RECORD_USER))) != NULL) { p_msg->hdr.event = BTA_SDP_API_CREATE_RECORD_USER_EVT; p_msg->user_data = user_data; @@ -153,7 +153,7 @@ tBTA_SDP_STATUS BTA_SdpRemoveRecordByUser(void *user_data) tBTA_SDP_STATUS ret = BTA_SDP_FAILURE; tBTA_SDP_API_RECORD_USER *p_msg; - APPL_TRACE_API(__FUNCTION__); + APPL_TRACE_API("%s\n", __FUNCTION__); if ((p_msg = (tBTA_SDP_API_RECORD_USER *)GKI_getbuf(sizeof(tBTA_SDP_API_RECORD_USER))) != NULL) { p_msg->hdr.event = BTA_SDP_API_REMOVE_RECORD_USER_EVT; p_msg->user_data = user_data; diff --git a/components/bt/bluedroid/btc/profile/std/gap/btc_gap_ble.c b/components/bt/bluedroid/btc/profile/std/gap/btc_gap_ble.c index 3c879984e0..ba9e962238 100644 --- a/components/bt/bluedroid/btc/profile/std/gap/btc_gap_ble.c +++ b/components/bt/bluedroid/btc/profile/std/gap/btc_gap_ble.c @@ -367,8 +367,8 @@ void btc_ble_start_advertising (esp_ble_adv_params_t *ble_adv_params) disc_mode = BTA_DM_BLE_NON_DISCOVERABLE; } - if (!API_BLE_ISVALID_PARAM(ble_adv_params->adv_int_min, BTM_BLE_ADV_INT_MIN, BTM_BLE_ADV_INT_MAX) || - !API_BLE_ISVALID_PARAM(ble_adv_params->adv_int_max, BTM_BLE_ADV_INT_MIN, BTM_BLE_ADV_INT_MAX)) { + if (!BLE_ISVALID_PARAM(ble_adv_params->adv_int_min, BTM_BLE_ADV_INT_MIN, BTM_BLE_ADV_INT_MAX) || + !BLE_ISVALID_PARAM(ble_adv_params->adv_int_max, BTM_BLE_ADV_INT_MIN, BTM_BLE_ADV_INT_MAX)) { LOG_ERROR("Invalid advertisting interval parameters.\n"); return ; } @@ -424,8 +424,8 @@ static void btc_scan_params_callback(tGATT_IF gatt_if, tBTM_STATUS status) static void btc_ble_set_scan_params(esp_ble_scan_params_t *scan_params, tBLE_SCAN_PARAM_SETUP_CBACK scan_param_setup_cback) { - if (API_BLE_ISVALID_PARAM(scan_params->scan_interval, BTM_BLE_SCAN_INT_MIN, BTM_BLE_SCAN_INT_MAX) && - API_BLE_ISVALID_PARAM(scan_params->scan_window, BTM_BLE_SCAN_WIN_MIN, BTM_BLE_SCAN_WIN_MAX) && + if (BLE_ISVALID_PARAM(scan_params->scan_interval, BTM_BLE_SCAN_INT_MIN, BTM_BLE_SCAN_INT_MAX) && + BLE_ISVALID_PARAM(scan_params->scan_window, BTM_BLE_SCAN_WIN_MIN, BTM_BLE_SCAN_WIN_MAX) && (scan_params->scan_type == BTM_BLE_SCAN_MODE_ACTI || scan_params->scan_type == BTM_BLE_SCAN_MODE_PASS)) { BTA_DmSetBleScanFilterParams(0 /*client_if*/, scan_params->scan_interval, @@ -453,6 +453,7 @@ static void btc_search_callback(tBTA_DM_SEARCH_EVT event, tBTA_DM_SEARCH *p_data param.scan_rst.dev_type = p_data->inq_res.device_type; param.scan_rst.rssi = p_data->inq_res.rssi; param.scan_rst.ble_addr_type = p_data->inq_res.ble_addr_type; + param.scan_rst.ble_evt_type = p_data->inq_res.ble_evt_type; param.scan_rst.flag = p_data->inq_res.flag; memcpy(param.scan_rst.ble_adv, p_data->inq_res.p_eir, ESP_BLE_ADV_DATA_LEN_MAX); diff --git a/components/bt/bluedroid/btc/profile/std/gatt/btc_gattc.c b/components/bt/bluedroid/btc/profile/std/gatt/btc_gattc.c index 8fe99c5e63..92cd5001db 100644 --- a/components/bt/bluedroid/btc/profile/std/gatt/btc_gattc.c +++ b/components/bt/bluedroid/btc/profile/std/gatt/btc_gattc.c @@ -346,15 +346,13 @@ static void btc_gattc_read_char_descr(btc_ble_gattc_args_t *arg) static void btc_gattc_write_char(btc_ble_gattc_args_t *arg) { - //TODO: check the write type tBTA_GATTC_CHAR_ID in_char_id; - tBTA_GATTC_WRITE_TYPE write_type = BTA_GATTC_TYPE_WRITE; btc_to_bta_srvc_id(&in_char_id.srvc_id, &arg->write_char.service_id); btc_to_bta_gatt_id(&in_char_id.char_id, &arg->write_char.char_id); BTA_GATTC_WriteCharValue(arg->write_char.conn_id, &in_char_id, - write_type, + arg->write_char.write_type, arg->write_char.value_len, arg->write_char.value, arg->write_char.auth_req); @@ -362,10 +360,8 @@ static void btc_gattc_write_char(btc_ble_gattc_args_t *arg) static void btc_gattc_write_char_descr(btc_ble_gattc_args_t *arg) { - //TODO: check the write type tBTA_GATTC_CHAR_DESCR_ID in_char_descr_id; tBTA_GATT_UNFMT descr_val; - tBTA_GATTC_WRITE_TYPE write_type = BTA_GATTC_TYPE_WRITE; btc_to_bta_srvc_id(&in_char_descr_id.char_id.srvc_id, &arg->write_descr.service_id); btc_to_bta_gatt_id(&in_char_descr_id.char_id.char_id, &arg->write_descr.char_id); btc_to_bta_gatt_id(&in_char_descr_id.descr_id, &arg->write_descr.descr_id); @@ -374,7 +370,7 @@ static void btc_gattc_write_char_descr(btc_ble_gattc_args_t *arg) descr_val.p_value = arg->write_descr.value; BTA_GATTC_WriteCharDescr(arg->write_descr.conn_id, &in_char_descr_id, - write_type, &descr_val, + arg->write_descr.write_type, &descr_val, arg->write_descr.auth_req); } @@ -521,7 +517,7 @@ void btc_gattc_cb_handler(btc_msg_t *msg) tBTA_GATTC_REG *reg_oper = &arg->reg_oper; param.reg.status = reg_oper->status; param.reg.gatt_if = reg_oper->client_if; - memcpy(¶m.reg.uuid, ®_oper->app_uuid, sizeof(esp_bt_uuid_t)); + param.reg.app_id = reg_oper->app_uuid.uu.uuid16; BTC_GATTC_CB_TO_APP(ESP_GATTC_REG_EVT, ¶m); break; } @@ -566,7 +562,7 @@ void btc_gattc_cb_handler(btc_msg_t *msg) case BTA_GATTC_SEARCH_RES_EVT: { tBTA_GATTC_SRVC_RES *srvc_res = &arg->srvc_res; param.search_res.conn_id = srvc_res->conn_id; - bta_to_btc_srvc_id(¶m.search_res.service_id, &srvc_res->service_uuid); + bta_to_btc_srvc_id(¶m.search_res.srvc_id, &srvc_res->service_uuid); BTC_GATTC_CB_TO_APP(ESP_GATTC_SEARCH_RES_EVT, ¶m); break; } @@ -588,7 +584,7 @@ void btc_gattc_cb_handler(btc_msg_t *msg) case BTA_GATTC_NOTIF_EVT: { tBTA_GATTC_NOTIFY *notify = &arg->notify; param.notify.conn_id = notify->conn_id; - memcpy(¶m.notify.bda, ¬ify->bda, sizeof(esp_bd_addr_t)); + memcpy(¶m.notify.remote_bda, ¬ify->bda, sizeof(esp_bd_addr_t)); bta_to_btc_srvc_id(¶m.notify.srvc_id, ¬ify->char_id.srvc_id); bta_to_btc_gatt_id(¶m.notify.char_id, ¬ify->char_id.char_id); bta_to_btc_gatt_id(¶m.notify.descr_id, ¬ify->descr_type); diff --git a/components/bt/bluedroid/btc/profile/std/gatt/btc_gatts.c b/components/bt/bluedroid/btc/profile/std/gatt/btc_gatts.c index 39e5f79363..8a844f6258 100644 --- a/components/bt/bluedroid/btc/profile/std/gatt/btc_gatts.c +++ b/components/bt/bluedroid/btc/profile/std/gatt/btc_gatts.c @@ -382,7 +382,7 @@ void btc_gatts_cb_handler(btc_msg_t *msg) param.del.gatt_if = p_data->srvc_oper.server_if; param.del.service_handle = p_data->srvc_oper.service_id; - BTC_GATTS_CB_TO_APP(ESP_GATTS_DELELTE_EVT, ¶m); + BTC_GATTS_CB_TO_APP(ESP_GATTS_DELETE_EVT, ¶m); break; case BTA_GATTS_START_EVT: param.start.status = p_data->srvc_oper.status; @@ -433,11 +433,4 @@ void btc_gatts_cb_handler(btc_msg_t *msg) } btc_gatts_cb_param_copy_free(msg, p_data); - - //ets_printf("yyy\n"); } - - - - - diff --git a/components/bt/bluedroid/btc/profile/std/include/btc_gap_ble.h b/components/bt/bluedroid/btc/profile/std/include/btc_gap_ble.h index 64f1ff3246..9a35db4083 100644 --- a/components/bt/bluedroid/btc/profile/std/include/btc_gap_ble.h +++ b/components/bt/bluedroid/btc/profile/std/include/btc_gap_ble.h @@ -18,6 +18,8 @@ #include "esp_bt_defs.h" #include "esp_gap_ble_api.h" +#define BLE_ISVALID_PARAM(x, min, max) (((x) >= (min) && (x) <= (max)) || ((x) == ESP_BLE_CONN_PARAM_UNDEF)) + typedef enum { BTC_GAP_BLE_ACT_CFG_ADV_DATA = 0, BTC_GAP_BLE_ACT_SET_SCAN_PARAM, diff --git a/components/bt/bluedroid/btc/profile/std/include/btc_gattc.h b/components/bt/bluedroid/btc/profile/std/include/btc_gattc.h index 0768b1d0ab..4bca4ae5ab 100644 --- a/components/bt/bluedroid/btc/profile/std/include/btc_gattc.h +++ b/components/bt/bluedroid/btc/profile/std/include/btc_gattc.h @@ -131,6 +131,7 @@ typedef union { esp_gatt_srvc_id_t service_id; esp_gatt_id_t char_id; uint8_t *value; + esp_gatt_write_type_t write_type; esp_gatt_auth_req_t auth_req; } write_char; //BTC_GATTC_ACT_WRITE_CHAR_DESCR, @@ -141,6 +142,7 @@ typedef union { esp_gatt_id_t char_id; esp_gatt_id_t descr_id; uint8_t *value; + esp_gatt_write_type_t write_type; esp_gatt_auth_req_t auth_req; } write_descr; //BTC_GATTC_ACT_PREPARE_WRITE, diff --git a/components/bt/bluedroid/include/bt_trace.h b/components/bt/bluedroid/include/bt_trace.h index 14f258a601..fd92f6e8c5 100644 --- a/components/bt/bluedroid/include/bt_trace.h +++ b/components/bt/bluedroid/include/bt_trace.h @@ -22,13 +22,11 @@ #include #include "bt_types.h" -#include "rom/ets_sys.h" +#include "esp_log.h" -#ifdef CONFIG_BT_USE_ETS_PRINT -#define BT_PRINTF ets_printf -#else -#define BT_PRINTF printf -#endif +#define TAG "BT" + +#define BT_PRINTF(fmt, ...) ESP_LOGE(TAG, fmt, ##__VA_ARGS__) #ifndef assert #define assert(x) do { if (!(x)) BT_PRINTF("bt host error %s %u\n", __FILE__, __LINE__); } while (0) @@ -273,7 +271,7 @@ inline void trc_dump_buffer(uint8_t *prefix, uint8_t *data, uint16_t len) #ifndef LOG_LEVEL #define LOG_LEVEL LOG_LEVEL_INFO #endif -#define LOG_ERROR(fmt, args...) do {if (LOG_LEVEL >= LOG_LEVEL_ERROR) printf(fmt,## args);} while(0) +#define LOG_ERROR(fmt, args...) do {if (LOG_LEVEL >= LOG_LEVEL_ERROR) BT_PRINTF(fmt,## args);} while(0) #define LOG_WARN(fmt, args...) do {if (LOG_LEVEL >= LOG_LEVEL_WARN) BT_PRINTF(fmt,## args);} while(0) #define LOG_INFO(fmt, args...) do {if (LOG_LEVEL >= LOG_LEVEL_INFO) BT_PRINTF(fmt,## args);} while(0) #define LOG_DEBUG(fmt, args...) do {if (LOG_LEVEL >= LOG_LEVEL_DEBUG) BT_PRINTF(fmt,## args);} while(0) diff --git a/components/bt/bluedroid/osi/include/thread.h b/components/bt/bluedroid/osi/include/thread.h index d4d41542b8..f29a525d81 100644 --- a/components/bt/bluedroid/osi/include/thread.h +++ b/components/bt/bluedroid/osi/include/thread.h @@ -56,12 +56,12 @@ enum { #define BTU_TASK_STACK_SIZE 4096 #define BTU_TASK_PRIO (configMAX_PRIORITIES - 1) #define BTU_TASK_NAME "btuT" -#define BTU_QUEUE_NUM 30 +#define BTU_QUEUE_NUM 50 -#define BTC_TASK_QUEUE_NUM 20 #define BTC_TASK_STACK_SIZE CONFIG_BTC_TASK_STACK_SIZE //by menuconfig #define BTC_TASK_NAME "btcT" #define BTC_TASK_PRIO (configMAX_PRIORITIES - 5) +#define BTC_TASK_QUEUE_NUM 20 void btu_task_post(uint32_t sig); void hci_host_task_post(void); diff --git a/components/bt/bluedroid/stack/btm/btm_ble_bgconn.c b/components/bt/bluedroid/stack/btm/btm_ble_bgconn.c index f53f71a5d4..af89677ee2 100644 --- a/components/bt/bluedroid/stack/btm/btm_ble_bgconn.c +++ b/components/bt/bluedroid/stack/btm/btm_ble_bgconn.c @@ -441,7 +441,7 @@ BOOLEAN btm_ble_start_auto_conn(BOOLEAN start) ** p_select_cback: callback function to return application ** selection. ** -** Returns BOOLEAN: selective connectino procedure is started. +** Returns BOOLEAN: selective connection procedure is started. ** *******************************************************************************/ BOOLEAN btm_ble_start_select_conn(BOOLEAN start, tBTM_BLE_SEL_CBACK *p_select_cback) @@ -523,7 +523,7 @@ BOOLEAN btm_ble_start_select_conn(BOOLEAN start, tBTM_BLE_SEL_CBACK *p_select_cb ** p_select_cback: callback function to return application ** selection. ** -** Returns BOOLEAN: selective connectino procedure is started. +** Returns BOOLEAN: selective connection procedure is started. ** *******************************************************************************/ void btm_ble_initiate_select_conn(BD_ADDR bda) diff --git a/components/bt/bluedroid/stack/btm/btm_ble_gap.c b/components/bt/bluedroid/stack/btm/btm_ble_gap.c index 906300a8a8..b7311dfd63 100644 --- a/components/bt/bluedroid/stack/btm/btm_ble_gap.c +++ b/components/bt/bluedroid/stack/btm/btm_ble_gap.c @@ -1353,11 +1353,10 @@ tBTM_STATUS BTM_BleWriteAdvData(tBTM_BLE_AD_MASK data_mask, tBTM_BLE_ADV_DATA *p BOOLEAN BTM_BleSetRandAddress(BD_ADDR rand_addr) { BOOLEAN set_flag = false; - UINT8 len = sizeof(rand_addr); - if (len != BD_ADDR_LEN) { - APPL_TRACE_ERROR("Invalid random adress"); - return false; - } + + if (rand_addr == NULL) + return set_flag; + //send the set random address to the controller set_flag = btsnd_hcic_ble_set_random_addr(rand_addr); return set_flag; diff --git a/components/bt/bluedroid/stack/gatt/att_protocol.c b/components/bt/bluedroid/stack/gatt/att_protocol.c index 48ccfd49da..50150fa32a 100644 --- a/components/bt/bluedroid/stack/gatt/att_protocol.c +++ b/components/bt/bluedroid/stack/gatt/att_protocol.c @@ -496,7 +496,7 @@ tGATT_STATUS attp_cl_send_cmd(tGATT_TCB *p_tcb, UINT16 clcb_idx, UINT8 cmd_code, ** Description This function sends the client request or confirmation message ** to server. ** -** Parameter p_tcb: pointer to the connectino control block. +** Parameter p_tcb: pointer to the connection control block. ** clcb_idx: clcb index ** op_code: message op code. ** p_msg: pointer to message parameters structure. diff --git a/components/bt/bluedroid/stack/include/btm_ble_api.h b/components/bt/bluedroid/stack/include/btm_ble_api.h index 2c4d1f1d59..c6ff180761 100644 --- a/components/bt/bluedroid/stack/include/btm_ble_api.h +++ b/components/bt/bluedroid/stack/include/btm_ble_api.h @@ -167,7 +167,7 @@ typedef UINT8 tBTM_BLE_SFP; #define BTM_BLE_CONN_INT_MIN_DEF 24 /* recommended min: 30ms = 24 * 1.25 */ #endif -/* default connectino interval max */ +/* default connection interval max */ #ifndef BTM_BLE_CONN_INT_MAX_DEF #define BTM_BLE_CONN_INT_MAX_DEF 40 /* recommended max: 50 ms = 56 * 1.25 */ #endif diff --git a/components/bt/bt.c b/components/bt/bt.c index 4e5ef4db48..ef9a063d69 100644 --- a/components/bt/bt.c +++ b/components/bt/bt.c @@ -115,7 +115,7 @@ static struct osi_funcs_t osi_funcs = { ._mutex_create = mutex_create_wrapper, ._mutex_lock = mutex_lock_wrapper, ._mutex_unlock = mutex_unlock_wrapper, - ._read_efuse_mac = system_efuse_read_mac, + ._read_efuse_mac = esp_efuse_read_mac, }; static void bt_controller_task(void *pvParam) diff --git a/components/bt/lib b/components/bt/lib index a0f2d0a961..91657e0c40 160000 --- a/components/bt/lib +++ b/components/bt/lib @@ -1 +1 @@ -Subproject commit a0f2d0a961eef1a4926218b26b77011a89e8188f +Subproject commit 91657e0c4025f5a694b0a89f449c347b0f2fdf79 diff --git a/components/driver/include/driver/pcnt.h b/components/driver/include/driver/pcnt.h new file mode 100644 index 0000000000..deff781839 --- /dev/null +++ b/components/driver/include/driver/pcnt.h @@ -0,0 +1,359 @@ +#ifndef __PCNT_H__ +#define __PCNT_H__ + +#include +#include "esp_intr.h" +#include "esp_err.h" +#include "freertos/FreeRTOS.h" +#include "freertos/semphr.h" +#include "freertos/xtensa_api.h" +#include "soc/soc.h" +#include "soc/pcnt_reg.h" +#include "soc/pcnt_struct.h" +#include "soc/gpio_sig_map.h" +#include "driver/gpio.h" + +#ifdef __cplusplus +extern "C" { +#endif + +#define PCNT_PIN_NOT_USED (-1) /*!< Pin are not used */ + +typedef enum { + PCNT_MODE_KEEP = 0, /*!< Control mode: won't change counter mode*/ + PCNT_MODE_REVERSE = 1, /*!< Control mode: invert counter mode(increase -> decrease, decrease -> increase);*/ + PCNT_MODE_DISABLE = 2, /*!< Control mode: Inhibit counter(counter value will not change in this condition)*/ + PCNT_MODE_MAX +} pcnt_ctrl_mode_t; + +typedef enum { + PCNT_COUNT_DIS = 0, /*!< Counter mode: Decrease counter value*/ + PCNT_COUNT_INC = 1, /*!< Counter mode: Increase counter value*/ + PCNT_COUNT_DEC = 2, /*!< Counter mode: Inhibit counter(counter value will not change in this condition)*/ + PCNT_COUNT_MAX +} pcnt_count_mode_t; + +typedef enum { + PCNT_UNIT_0 = 0, /*!< PCNT unit0 */ + PCNT_UNIT_1 = 1, /*!< PCNT unit1 */ + PCNT_UNIT_2 = 2, /*!< PCNT unit2 */ + PCNT_UNIT_3 = 3, /*!< PCNT unit3 */ + PCNT_UNIT_4 = 4, /*!< PCNT unit4 */ + PCNT_UNIT_5 = 5, /*!< PCNT unit5 */ + PCNT_UNIT_6 = 6, /*!< PCNT unit6 */ + PCNT_UNIT_7 = 7, /*!< PCNT unit7 */ + PCNT_UNIT_MAX, +} pcnt_unit_t; + +typedef enum{ + PCNT_CHANNEL_0 = 0x00, /*!< PCNT channel0 */ + PCNT_CHANNEL_1 = 0x01, /*!< PCNT channel1 */ + PCNT_CHANNEL_MAX, +} pcnt_channel_t; + +typedef enum { + PCNT_EVT_L_LIM = 0, /*!< PCNT watch point event: Minimum counter value */ + PCNT_EVT_H_LIM = 1, /*!< PCNT watch point event: Maximum counter value*/ + PCNT_EVT_THRES_0 = 2, /*!< PCNT watch point event: threshold0 value event*/ + PCNT_EVT_THRES_1 = 3, /*!< PCNT watch point event: threshold1 value event*/ + PCNT_EVT_ZERO = 4, /*!< PCNT watch point event: counter value zero event*/ + PCNT_EVT_MAX +} pcnt_evt_type_t; + +/** + * @brief Pulse Counter configure struct + */ +typedef struct { + int pulse_gpio_num; /*!< Pulse input gpio_num, if you want to use gpio16, pulse_gpio_num = 16, a negative value will be ignored */ + int ctrl_gpio_num; /*!< Contol signal input gpio_num, a negative value will be ignored*/ + pcnt_ctrl_mode_t lctrl_mode; /*!< PCNT low control mode*/ + pcnt_ctrl_mode_t hctrl_mode; /*!< PCNT high control mode*/ + pcnt_count_mode_t pos_mode; /*!< PCNT positive edge count mode*/ + pcnt_count_mode_t neg_mode; /*!< PCNT negative edge count mode*/ + int16_t counter_h_lim; /*!< Maximum counter value */ + int16_t counter_l_lim; /*!< Minimum counter value */ + pcnt_unit_t unit; /*!< PCNT unit number */ + pcnt_channel_t channel; /*!< the PCNT channel */ +} pcnt_config_t; + +/** + * @brief Configure Pulse Counter unit + * + * @param pcnt_config Pointer of Pulse Counter unit configure parameter + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_unit_config(pcnt_config_t *pcnt_config); + +/** + * @brief Get pulse counter value + * + * @param pcnt_unit Pulse Counter unit number + * @param count Pointer to accept counter value + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_get_counter_value(pcnt_unit_t pcnt_unit, int16_t* count); + +/** + * @brief Pause PCNT counter of PCNT unit + * + * @param pcnt_unit PCNT unit number + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_counter_pause(pcnt_unit_t pcnt_unit); + +/** + * @brief Resume counting for PCNT counter + * + * @param pcnt_unit PCNT unit number, select from pcnt_unit_t + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_counter_resume(pcnt_unit_t pcnt_unit); + +/** + * @brief Clear and reset PCNT counter value to zero + * + * @param pcnt_unit PCNT unit number, select from pcnt_unit_t + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_counter_clear(pcnt_unit_t pcnt_unit); + +/** + * @brief Enable PCNT interrupt for PCNT unit + * @note + * Each Pulse counter unit has five watch point events that share the same interrupt. + * Configure events with pcnt_event_enable() and pcnt_event_disable() + * + * @param pcnt_unit PCNT unit number + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_intr_enable(pcnt_unit_t pcnt_unit); + +/** + * @brief Disable PCNT interrupt for PCNT uint + * + * @param pcnt_unit PCNT unit number + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_intr_disable(pcnt_unit_t pcnt_unit); + +/** + * @brief Enable PCNT event of PCNT unit + * + * @param unit PCNT unit number + * @param evt_type Watch point event type. + * All enabled events share the same interrupt (one interrupt per pulse counter unit). + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_event_enable(pcnt_unit_t unit, pcnt_evt_type_t evt_type); + +/** + * @brief Disable PCNT event of PCNT unit + * + * @param unit PCNT unit number + * @param evt_type Watch point event type. + * All enabled events share the same interrupt (one interrupt per pulse counter unit). + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_event_disable(pcnt_unit_t unit, pcnt_evt_type_t evt_type); + +/** + * @brief Set PCNT event value of PCNT unit + * + * @param unit PCNT unit number + * @param evt_type Watch point event type. + * All enabled events share the same interrupt (one interrupt per pulse counter unit). + * + * @param value Counter value for PCNT event + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_set_event_value(pcnt_unit_t unit, pcnt_evt_type_t evt_type, int16_t value); + +/** + * @brief Get PCNT event value of PCNT unit + * + * @param unit PCNT unit number + * @param evt_type Watch point event type. + * All enabled events share the same interrupt (one interrupt per pulse counter unit). + * @param value Pointer to accept counter value for PCNT event + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_get_event_value(pcnt_unit_t unit, pcnt_evt_type_t evt_type, int16_t *value); + +/** + * @brief Register PCNT interrupt handler, the handler is an ISR. + * The handler will be attached to the same CPU core that this function is running on. + * @note + * Users should know that which CPU is running and then pick a INUM that is not used by system. + * We can find the information of INUM and interrupt level in soc.h. + * + * @param pcnt_intr_num PCNT interrupt number, check the info in soc.h, and please see the core-isa.h for more details + * @param fn Interrupt handler function. + * @note + * Note that the handler function MUST be defined with attribution of "IRAM_ATTR". + * @param arg Parameter for handler function + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Function pointer error. + */ +esp_err_t pcnt_isr_register(uint32_t pcnt_intr_num, void (*fn)(void*), void * arg); + +/** + * @brief Configure PCNT pulse signal input pin and control input pin + * + * @param unit PCNT unit number + * @param channel PCNT channel number + * @param pulse_io Pulse signal input GPIO + * @note + * Set to PCNT_PIN_NOT_USED if unused. + * @param ctrl_io Control signal input GPIO + * @note + * Set to PCNT_PIN_NOT_USED if unused. + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_set_pin(pcnt_unit_t unit, pcnt_channel_t channel, int pulse_io, int ctrl_io); + +/** + * @brief Enable PCNT input filter + * + * @param unit PCNT unit number + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_filter_enable(pcnt_unit_t unit); + +/** + * @brief Disable PCNT input filter + * + * @param unit PCNT unit number + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_filter_disable(pcnt_unit_t unit); + +/** + * @brief Set PCNT filter value + * + * @param unit PCNT unit number + * @param filter_val PCNT signal filter value, counter in APB_CLK cycles. + * Any pulses lasting shorter than this will be ignored when the filter is enabled. + * @note + * filter_val is a 10-bit value, so the maximum filter_val should be limited to 1023. + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_set_filter_value(pcnt_unit_t unit, uint16_t filter_val); + +/** + * @brief Get PCNT filter value + * + * @param unit PCNT unit number + * @param filter_val Pointer to accept PCNT filter value. + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_get_filter_value(pcnt_unit_t unit, uint16_t *filter_val); + +/** + * @brief Set PCNT counter mode + * + * @param unit PCNT unit number + * @param channel PCNT channel number + * @param pos_mode Counter mode when detecting positive edge + * @param neg_mode Counter mode when detecting negative edge + * @param hctrl_mode Counter mode when control signal is high level + * @param lctrl_mode Counter mode when control signal is low level + * + * @return + * - ESP_OK Success + * - ESP_ERR_INVALID_ARG Parameter error + */ +esp_err_t pcnt_set_mode(pcnt_unit_t unit, pcnt_channel_t channel, + pcnt_count_mode_t pos_mode, pcnt_count_mode_t neg_mode, + pcnt_ctrl_mode_t hctrl_mode, pcnt_ctrl_mode_t lctrl_mode); + + +/** + * @addtogroup pcnt-examples + * + * @{ + * + * EXAMPLE OF PCNT CONFIGURATION + * ============================== + * @code{c} + * //1. Config PCNT unit + * pcnt_config_t pcnt_config = { + * .pulse_gpio_num = 4, //set gpio4 as pulse input gpio + * .ctrl_gpio_num = 5, //set gpio5 as control gpio + * .channel = PCNT_CHANNEL_0, //use unit 0 channel 0 + * .lctrl_mode = PCNT_MODE_REVERSE, //when control signal is low ,reverse the primary counter mode(inc->dec/dec->inc) + * .hctrl_mode = PCNT_MODE_KEEP, //when control signal is high,keep the primary counter mode + * .pos_mode = PCNT_COUNT_INC, //increment the counter + * .neg_mode = PCNT_COUNT_DIS, //keep the counter value + * .counter_h_lim = 10, + * .counter_l_lim = -10, + * }; + * pcnt_unit_config(&pcnt_config); //init unit + * @endcode + * + * EXAMPLE OF PCNT EVENT SETTING + * ============================== + * @code{c} + * //2. Configure PCNT watchpoint event. + * pcnt_set_event_value(PCNT_UNIT_0, PCNT_EVT_THRES_1, 5); //set thres1 value + * pcnt_event_enable(PCNT_UNIT_0, PCNT_EVT_THRES_1); //enable thres1 event + * @endcode + * + * For more examples please refer to PCNT example code in IDF_PATH/examples + * + * @} + */ + +#ifdef __cplusplus +} +#endif + + +#endif diff --git a/components/driver/include/driver/periph_ctrl.h b/components/driver/include/driver/periph_ctrl.h index d7a98284b7..8c404e5b13 100644 --- a/components/driver/include/driver/periph_ctrl.h +++ b/components/driver/include/driver/periph_ctrl.h @@ -40,6 +40,7 @@ typedef enum { PERIPH_UHCI0_MODULE, PERIPH_UHCI1_MODULE, PERIPH_RMT_MODULE, + PERIPH_PCNT_MODULE, } periph_module_t; /** diff --git a/components/driver/include/driver/timer.h b/components/driver/include/driver/timer.h new file mode 100644 index 0000000000..c0ad7116e4 --- /dev/null +++ b/components/driver/include/driver/timer.h @@ -0,0 +1,349 @@ +// Copyright 2010-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#ifndef _DRIVER_TIMER_H_ +#define _DRIVER_TIMER_H_ +#include "esp_err.h" +#include "esp_attr.h" +#include "soc/soc.h" +#include "soc/timer_group_reg.h" +#include "soc/timer_group_struct.h" + +#ifdef __cplusplus +extern "C" { +#endif + + +#define TIMER_BASE_CLK (APB_CLK_FREQ) +/** + * @brief Selects a Timer-Group out of 2 available groups + */ +typedef enum { + TIMER_GROUP_0 = 0, /*! LEDC_TIMER_3) { - ESP_LOGE(LEDC_TAG, "Time Select %u", timer_num); + ESP_LOGE(LEDC_TAG, "invalid timer #%u", timer_num); return ESP_ERR_INVALID_ARG; } esp_err_t ret = ESP_OK; - uint32_t precision = (0x1 << bit_num); //2**depth - uint64_t div_param = ((uint64_t) LEDC_APB_CLK_HZ << 8) / freq_hz / precision; //8bit fragment - int timer_clk_src; - /*Fail ,because the div_num overflow or too small*/ - if(div_param <= 256 || div_param > LEDC_DIV_NUM_HSTIMER0_V) { //REF TICK - /*Selet the reference tick*/ + uint32_t precision = (0x1 << bit_num); // 2**depth + // Try calculating divisor based on LEDC_APB_CLK + ledc_clk_src_t timer_clk_src = LEDC_APB_CLK; + // div_param is a Q10.8 fixed point value + uint64_t div_param = ((uint64_t) LEDC_APB_CLK_HZ << 8) / freq_hz / precision; + if (div_param < 256) { + // divisor is too low + ESP_LOGE(LEDC_TAG, "requested frequency and bit depth can not be achieved, try reducing freq_hz or bit_num. div_param=%d", (uint32_t) div_param); + ret = ESP_FAIL; + } + if (div_param > LEDC_DIV_NUM_HSTIMER0_V) { + // APB_CLK results in divisor which too high. Try using REF_TICK as clock source. + timer_clk_src = LEDC_REF_TICK; div_param = ((uint64_t) LEDC_REF_CLK_HZ << 8) / freq_hz / precision; - if(div_param <= 256 || div_param > LEDC_DIV_NUM_HSTIMER0_V) { - ESP_LOGE(LEDC_TAG, "div param err,div_param=%u", (uint32_t)div_param); + if(div_param < 256 || div_param > LEDC_DIV_NUM_HSTIMER0_V) { + ESP_LOGE(LEDC_TAG, "requested frequency and bit depth can not be achieved, try increasing freq_hz or bit_num. div_param=%d", (uint32_t) div_param); ret = ESP_FAIL; } - timer_clk_src = LEDC_REF_TICK; - } else { //APB TICK - timer_clk_src = LEDC_APB_CLK; } - /*set timer parameters*/ - /*timer settings decide the clk of counter and the period of PWM*/ + // set timer parameters ledc_timer_set(speed_mode, timer_num, div_param, bit_num, timer_clk_src); - /* reset timer.*/ + // reset timer ledc_timer_rst(speed_mode, timer_num); return ret; } @@ -174,7 +177,8 @@ esp_err_t ledc_set_pin(int gpio_num, ledc_mode_t speed_mode, ledc_channel_t ledc if(speed_mode == LEDC_HIGH_SPEED_MODE) { gpio_matrix_out(gpio_num, LEDC_HS_SIG_OUT0_IDX + ledc_channel, 0, 0); } else { - + ESP_LOGE(LEDC_TAG, "low speed mode is not implemented"); + return ESP_ERR_NOT_SUPPORTED; } return ESP_OK; } @@ -191,6 +195,7 @@ esp_err_t ledc_channel_config(ledc_channel_config_t* ledc_conf) LEDC_CHECK(speed_mode < LEDC_SPEED_MODE_MAX, "ledc mode error", ESP_ERR_INVALID_ARG); LEDC_CHECK(GPIO_IS_VALID_OUTPUT_GPIO(gpio_num), "ledc GPIO output number error", ESP_ERR_INVALID_ARG); LEDC_CHECK(timer_select <= LEDC_TIMER_3, "ledc timer error", ESP_ERR_INVALID_ARG); + periph_module_enable(PERIPH_LEDC_MODULE); esp_err_t ret = ESP_OK; /*set channel parameters*/ /* channel parameters decide how the waveform looks like in one period*/ diff --git a/components/driver/pcnt.c b/components/driver/pcnt.c new file mode 100644 index 0000000000..b39d53a800 --- /dev/null +++ b/components/driver/pcnt.c @@ -0,0 +1,278 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +#include "esp_log.h" +#include "driver/pcnt.h" +#include "driver/periph_ctrl.h" + +#define PCNT_CHANNEL_ERR_STR "PCNT CHANNEL ERROR" +#define PCNT_UNIT_ERR_STR "PCNT UNIT ERROR" +#define PCNT_GPIO_ERR_STR "PCNT GPIO NUM ERROR" +#define PCNT_ADDRESS_ERR_STR "PCNT ADDRESS ERROR" +#define PCNT_PARAM_ERR_STR "PCNT PARAM ERROR" +#define PCNT_COUNT_MODE_ERR_STR "PCNT COUNTER MODE ERROR" +#define PCNT_CTRL_MODE_ERR_STR "PCNT CTRL MODE ERROR" +#define PCNT_EVT_TYPE_ERR_STR "PCNT value type error" +#define PCNT_CHECK(a,str,ret_val) if(!(a)) { \ + ESP_LOGE(PCNT_TAG,"%s:%d (%s):%s", __FILE__, __LINE__, __FUNCTION__, str); \ + return (ret_val); \ + } + +static const char* PCNT_TAG = "PCNT"; +static portMUX_TYPE pcnt_spinlock = portMUX_INITIALIZER_UNLOCKED; + +#define PCNT_ENTER_CRITICAL(mux) portENTER_CRITICAL(mux) +#define PCNT_EXIT_CRITICAL(mux) portEXIT_CRITICAL(mux) +#define PCNT_ENTER_CRITICAL_ISR(mux) portENTER_CRITICAL_ISR(mux) +#define PCNT_EXIT_CRITICAL_ISR(mux) portEXIT_CRITICAL_ISR(mux) + +esp_err_t pcnt_unit_config(pcnt_config_t *pcnt_config) +{ + uint8_t unit = pcnt_config->channel; + uint8_t channel = pcnt_config->unit; + int input_io = pcnt_config->pulse_gpio_num; + int ctrl_io = pcnt_config->ctrl_gpio_num; + + PCNT_CHECK(unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(channel < PCNT_CHANNEL_MAX, PCNT_CHANNEL_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(input_io < 0 || (GPIO_IS_VALID_GPIO(input_io) && (input_io != ctrl_io)), "PCNT pluse input io error", ESP_ERR_INVALID_ARG); + PCNT_CHECK(ctrl_io < 0 || GPIO_IS_VALID_GPIO(ctrl_io), "PCNT ctrl io error", ESP_ERR_INVALID_ARG); + PCNT_CHECK((pcnt_config->pos_mode < PCNT_COUNT_MAX) && (pcnt_config->neg_mode < PCNT_COUNT_MAX), PCNT_COUNT_MODE_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK((pcnt_config->hctrl_mode < PCNT_MODE_MAX) && (pcnt_config->lctrl_mode < PCNT_MODE_MAX), PCNT_CTRL_MODE_ERR_STR, ESP_ERR_INVALID_ARG); + /*Enalbe hardware module*/ + periph_module_enable(PERIPH_PCNT_MODULE); + /*Set counter range*/ + pcnt_set_event_value(unit, PCNT_EVT_H_LIM, pcnt_config->counter_h_lim); + pcnt_set_event_value(unit, PCNT_EVT_L_LIM, pcnt_config->counter_l_lim); + /*Default value after reboot is positive, we disable these events like others*/ + pcnt_event_disable(unit, PCNT_EVT_H_LIM); + pcnt_event_disable(unit, PCNT_EVT_L_LIM); + pcnt_event_disable(unit, PCNT_EVT_ZERO); + pcnt_filter_disable(unit); + /*set pulse input and control mode*/ + pcnt_set_mode(unit, channel, pcnt_config->pos_mode, pcnt_config->neg_mode, pcnt_config->hctrl_mode, pcnt_config->lctrl_mode); + /*Set pulse input and control pins*/ + pcnt_set_pin(unit, channel, input_io, ctrl_io); + return ESP_OK; +} + +esp_err_t pcnt_set_mode(pcnt_unit_t unit, pcnt_channel_t channel, pcnt_count_mode_t pos_mode, pcnt_count_mode_t neg_mode, pcnt_ctrl_mode_t hctrl_mode, pcnt_ctrl_mode_t lctrl_mode) +{ + PCNT_CHECK(unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(channel < PCNT_CHANNEL_MAX, PCNT_CHANNEL_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK((pos_mode < PCNT_COUNT_MAX) && (neg_mode < PCNT_COUNT_MAX), PCNT_COUNT_MODE_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK((hctrl_mode < PCNT_MODE_MAX) && (lctrl_mode < PCNT_MODE_MAX), PCNT_CTRL_MODE_ERR_STR, ESP_ERR_INVALID_ARG); + + if(channel == 0) { + PCNT.conf_unit[unit].conf0.ch0_pos_mode = pos_mode; + PCNT.conf_unit[unit].conf0.ch0_neg_mode = neg_mode; + PCNT.conf_unit[unit].conf0.ch0_hctrl_mode = hctrl_mode; + PCNT.conf_unit[unit].conf0.ch0_lctrl_mode = lctrl_mode; + } else { + PCNT.conf_unit[unit].conf0.ch1_pos_mode = pos_mode; + PCNT.conf_unit[unit].conf0.ch1_neg_mode = neg_mode; + PCNT.conf_unit[unit].conf0.ch1_hctrl_mode = hctrl_mode; + PCNT.conf_unit[unit].conf0.ch1_lctrl_mode = lctrl_mode; + } + return ESP_OK; +} + +esp_err_t pcnt_set_pin(pcnt_unit_t unit, pcnt_channel_t channel, int pulse_io, int ctrl_io) +{ + PCNT_CHECK(unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(channel < PCNT_CHANNEL_MAX, PCNT_CHANNEL_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(GPIO_IS_VALID_GPIO(pulse_io) || pulse_io < 0, PCNT_GPIO_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(GPIO_IS_VALID_GPIO(ctrl_io) || ctrl_io < 0, PCNT_GPIO_ERR_STR, ESP_ERR_INVALID_ARG); + int input_sig_index = (channel == 0 ? PCNT_SIG_CH0_IN0_IDX + 4 * unit : PCNT_SIG_CH1_IN0_IDX + 4 * unit); + int ctrl_sig_index = (channel == 0 ? PCNT_CTRL_CH0_IN0_IDX + 4 * unit : PCNT_CTRL_CH1_IN0_IDX + 4 * unit); + if(pulse_io >= 0) { + PIN_FUNC_SELECT(GPIO_PIN_MUX_REG[pulse_io], PIN_FUNC_GPIO); + gpio_set_direction(pulse_io, GPIO_MODE_INPUT); + gpio_set_pull_mode(pulse_io, GPIO_PULLUP_ONLY); + gpio_matrix_in(pulse_io, input_sig_index, 0); + } + if(ctrl_io >= 0) { + PIN_FUNC_SELECT(GPIO_PIN_MUX_REG[ctrl_io], PIN_FUNC_GPIO); + gpio_set_direction(ctrl_io, GPIO_MODE_INPUT); + gpio_set_pull_mode(ctrl_io, GPIO_PULLUP_ONLY); + gpio_matrix_in(ctrl_io, ctrl_sig_index, 0); + } + return ESP_OK; +} + +esp_err_t pcnt_get_counter_value(pcnt_unit_t pcnt_unit, int16_t* count) +{ + PCNT_CHECK(pcnt_unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(count != NULL, PCNT_ADDRESS_ERR_STR, ESP_ERR_INVALID_ARG); + *count = (int16_t) PCNT.cnt_unit[pcnt_unit].cnt_val; + return ESP_OK; +} + +esp_err_t pcnt_counter_pause(pcnt_unit_t pcnt_unit) +{ + PCNT_CHECK(pcnt_unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_ENTER_CRITICAL(&pcnt_spinlock); + PCNT.ctrl.val |= BIT(PCNT_CNT_PAUSE_U0_S + (pcnt_unit * 2)); + PCNT_EXIT_CRITICAL(&pcnt_spinlock); + return ESP_OK; +} + +esp_err_t pcnt_counter_resume(pcnt_unit_t pcnt_unit) +{ + PCNT_CHECK(pcnt_unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_ENTER_CRITICAL(&pcnt_spinlock); + PCNT.ctrl.val &= (~(BIT(PCNT_CNT_PAUSE_U0_S + (pcnt_unit * 2)))); + PCNT_EXIT_CRITICAL(&pcnt_spinlock); + return ESP_OK; +} + +esp_err_t pcnt_counter_clear(pcnt_unit_t pcnt_unit) +{ + PCNT_CHECK(pcnt_unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_ENTER_CRITICAL(&pcnt_spinlock); + PCNT.ctrl.val &= (~(BIT(PCNT_PLUS_CNT_RST_U0_S + (pcnt_unit * 2)))); + PCNT_EXIT_CRITICAL(&pcnt_spinlock); + return ESP_OK; +} + +esp_err_t pcnt_intr_enable(pcnt_unit_t pcnt_unit) +{ + PCNT_CHECK(pcnt_unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_ENTER_CRITICAL(&pcnt_spinlock); + PCNT.int_ena.val |= BIT(PCNT_CNT_THR_EVENT_U0_INT_ENA_S + pcnt_unit); + PCNT_EXIT_CRITICAL(&pcnt_spinlock); + return ESP_OK; +} + +esp_err_t pcnt_intr_disable(pcnt_unit_t pcnt_unit) +{ + PCNT_CHECK(pcnt_unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_ENTER_CRITICAL(&pcnt_spinlock); + PCNT.int_ena.val &= (~(BIT(PCNT_CNT_THR_EVENT_U0_INT_ENA_S + pcnt_unit))); + PCNT_EXIT_CRITICAL(&pcnt_spinlock); + return ESP_OK; +} + +esp_err_t pcnt_event_enable(pcnt_unit_t unit, pcnt_evt_type_t evt_type) +{ + PCNT_CHECK(unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(evt_type < PCNT_EVT_MAX, PCNT_EVT_TYPE_ERR_STR, ESP_ERR_INVALID_ARG); + if(evt_type == PCNT_EVT_L_LIM) { + PCNT.conf_unit[unit].conf0.thr_l_lim_en = 1; + } else if(evt_type == PCNT_EVT_H_LIM) { + PCNT.conf_unit[unit].conf0.thr_h_lim_en = 1; + } else if(evt_type == PCNT_EVT_THRES_0) { + PCNT.conf_unit[unit].conf0.thr_thres0_en = 1; + } else if(evt_type == PCNT_EVT_THRES_1) { + PCNT.conf_unit[unit].conf0.thr_thres1_en = 1; + } else if(evt_type == PCNT_EVT_ZERO) { + PCNT.conf_unit[unit].conf0.thr_zero_en = 1; + } + return ESP_OK; +} + +esp_err_t pcnt_event_disable(pcnt_unit_t unit, pcnt_evt_type_t evt_type) +{ + PCNT_CHECK(unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(evt_type < PCNT_EVT_MAX, PCNT_EVT_TYPE_ERR_STR, ESP_ERR_INVALID_ARG); + if(evt_type == PCNT_EVT_L_LIM) { + PCNT.conf_unit[unit].conf0.thr_l_lim_en = 0; + } else if(evt_type == PCNT_EVT_H_LIM) { + PCNT.conf_unit[unit].conf0.thr_h_lim_en = 0; + } else if(evt_type == PCNT_EVT_THRES_0) { + PCNT.conf_unit[unit].conf0.thr_thres0_en = 0; + } else if(evt_type == PCNT_EVT_THRES_1) { + PCNT.conf_unit[unit].conf0.thr_thres1_en = 0; + } else if(evt_type == PCNT_EVT_ZERO) { + PCNT.conf_unit[unit].conf0.thr_zero_en = 0; + } + return ESP_OK; +} + +esp_err_t pcnt_set_event_value(pcnt_unit_t unit, pcnt_evt_type_t evt_type, int16_t value) +{ + PCNT_CHECK(unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(evt_type < PCNT_EVT_MAX, PCNT_EVT_TYPE_ERR_STR, ESP_ERR_INVALID_ARG); + if(evt_type == PCNT_EVT_L_LIM) { + PCNT.conf_unit[unit].conf2.cnt_l_lim = value; + } else if(evt_type == PCNT_EVT_H_LIM) { + PCNT.conf_unit[unit].conf2.cnt_h_lim = value; + } else if(evt_type == PCNT_EVT_THRES_0) { + PCNT.conf_unit[unit].conf1.cnt_thres0 = value; + } else if(evt_type == PCNT_EVT_THRES_1) { + PCNT.conf_unit[unit].conf1.cnt_thres1 = value; + } + return ESP_OK; +} + +esp_err_t pcnt_get_event_value(pcnt_unit_t unit, pcnt_evt_type_t evt_type, int16_t *value) +{ + PCNT_CHECK(unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(evt_type < PCNT_EVT_MAX, PCNT_EVT_TYPE_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(value != NULL, PCNT_ADDRESS_ERR_STR, ESP_ERR_INVALID_ARG); + + if(evt_type == PCNT_EVT_L_LIM) { + *value = (int16_t) PCNT.conf_unit[unit].conf2.cnt_l_lim; + } else if(evt_type == PCNT_EVT_H_LIM) { + *value = (int16_t) PCNT.conf_unit[unit].conf2.cnt_h_lim; + } else if(evt_type == PCNT_EVT_THRES_0) { + *value = (int16_t) PCNT.conf_unit[unit].conf1.cnt_thres0; + } else if(evt_type == PCNT_EVT_THRES_1) { + *value = (int16_t) PCNT.conf_unit[unit].conf1.cnt_thres1; + } else { + *value = 0; + } + return ESP_OK; +} + +esp_err_t pcnt_set_filter_value(pcnt_unit_t unit, uint16_t filter_val) +{ + PCNT_CHECK(unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(filter_val < 1024, PCNT_PARAM_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT.conf_unit[unit].conf0.filter_thres = filter_val; + return ESP_OK; +} + +esp_err_t pcnt_get_filter_value(pcnt_unit_t unit, uint16_t *filter_val) +{ + PCNT_CHECK(unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT_CHECK(filter_val != NULL, PCNT_ADDRESS_ERR_STR, ESP_ERR_INVALID_ARG); + + *filter_val = PCNT.conf_unit[unit].conf0.filter_thres; + return ESP_OK; +} + +esp_err_t pcnt_filter_enable(pcnt_unit_t unit) +{ + PCNT_CHECK(unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT.conf_unit[unit].conf0.filter_en = 1; + return ESP_OK; +} + +esp_err_t pcnt_filter_disable(pcnt_unit_t unit) +{ + PCNT_CHECK(unit < PCNT_UNIT_MAX, PCNT_UNIT_ERR_STR, ESP_ERR_INVALID_ARG); + PCNT.conf_unit[unit].conf0.filter_en = 0; + return ESP_OK; +} + +esp_err_t pcnt_isr_register(uint32_t pcnt_intr_num, void (*fun)(void*), void * arg) +{ + PCNT_CHECK(fun != NULL, PCNT_ADDRESS_ERR_STR, ESP_ERR_INVALID_ARG); + ESP_INTR_DISABLE(pcnt_intr_num); + intr_matrix_set(xPortGetCoreID(), ETS_PCNT_INTR_SOURCE, pcnt_intr_num); + xt_set_interrupt_handler(pcnt_intr_num, fun, arg); + ESP_INTR_ENABLE(pcnt_intr_num); + return ESP_OK; +} + diff --git a/components/driver/periph_ctrl.c b/components/driver/periph_ctrl.c index 00987768af..7fc4091aa5 100644 --- a/components/driver/periph_ctrl.c +++ b/components/driver/periph_ctrl.c @@ -93,6 +93,10 @@ void periph_module_enable(periph_module_t periph) SET_PERI_REG_MASK(DPORT_PERIP_CLK_EN_REG, DPORT_UHCI1_CLK_EN); CLEAR_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG, DPORT_UHCI1_RST); break; + case PERIPH_PCNT_MODULE: + SET_PERI_REG_MASK(DPORT_PERIP_CLK_EN_REG, DPORT_PCNT_CLK_EN); + CLEAR_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG, DPORT_PCNT_RST); + break; default: break; } @@ -103,6 +107,10 @@ void periph_module_disable(periph_module_t periph) { portENTER_CRITICAL(&periph_spinlock); switch(periph) { + case PERIPH_RMT_MODULE: + CLEAR_PERI_REG_MASK(DPORT_PERIP_CLK_EN_REG, DPORT_RMT_CLK_EN); + SET_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG, DPORT_RMT_RST); + break; case PERIPH_LEDC_MODULE: CLEAR_PERI_REG_MASK(DPORT_PERIP_CLK_EN_REG, DPORT_LEDC_CLK_EN); SET_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG, DPORT_LEDC_RST); @@ -167,6 +175,10 @@ void periph_module_disable(periph_module_t periph) CLEAR_PERI_REG_MASK(DPORT_PERIP_CLK_EN_REG, DPORT_UHCI1_CLK_EN); SET_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG, DPORT_UHCI1_RST); break; + case PERIPH_PCNT_MODULE: + CLEAR_PERI_REG_MASK(DPORT_PERIP_CLK_EN_REG, DPORT_PCNT_CLK_EN); + SET_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG, DPORT_PCNT_RST); + break; default: break; } diff --git a/components/driver/timer.c b/components/driver/timer.c new file mode 100644 index 0000000000..b305a41468 --- /dev/null +++ b/components/driver/timer.c @@ -0,0 +1,275 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +#include +#include "esp_log.h" +#include "esp_err.h" +#include "esp_intr.h" +#include "freertos/FreeRTOS.h" +#include "freertos/xtensa_api.h" +#include "driver/timer.h" +#include "driver/periph_ctrl.h" + +static const char* TIMER_TAG = "TIMER_GROUP"; +#define TIMER_CHECK(a, str, ret_val) if (!(a)) { \ + ESP_LOGE(TIMER_TAG,"%s:%d (%s):%s", __FILE__, __LINE__, __FUNCTION__, str); \ + return (ret_val); \ + } +#define TIMER_GROUP_NUM_ERROR "TIMER GROUP NUM ERROR" +#define TIMER_NUM_ERROR "HW TIMER NUM ERROR" +#define TIMER_PARAM_ADDR_ERROR "HW TIMER PARAM ADDR ERROR" +#define TIMER_COUNT_DIR_ERROR "HW TIMER COUNTER DIR ERROR" +#define TIMER_AUTORELOAD_ERROR "HW TIMER AUTORELOAD ERROR" +#define TIMER_SCALE_ERROR "HW TIMER SCALE ERROR" +#define TIMER_ALARM_ERROR "HW TIMER ALARM ERROR" +static timg_dev_t *TG[2] = {&TIMERG0, &TIMERG1}; +static portMUX_TYPE timer_spinlock[TIMER_GROUP_MAX] = {portMUX_INITIALIZER_UNLOCKED, portMUX_INITIALIZER_UNLOCKED}; + +#define TIMER_ENTER_CRITICAL(mux) portENTER_CRITICAL(mux); +#define TIMER_EXIT_CRITICAL(mux) portEXIT_CRITICAL(mux); + +esp_err_t timer_get_counter_value(timer_group_t group_num, timer_idx_t timer_num, uint64_t* timer_val) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_val != NULL, TIMER_PARAM_ADDR_ERROR, ESP_ERR_INVALID_ARG); + portENTER_CRITICAL(&timer_spinlock[group_num]); + TG[group_num]->hw_timer[timer_num].update = 1; + *timer_val = ((uint64_t) TG[group_num]->hw_timer[timer_num].cnt_high << 32) + | (TG[group_num]->hw_timer[timer_num].cnt_low); + portEXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_get_counter_time_sec(timer_group_t group_num, timer_idx_t timer_num, double* time) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(time != NULL, TIMER_PARAM_ADDR_ERROR, ESP_ERR_INVALID_ARG); + + uint64_t timer_val; + esp_err_t err = timer_get_counter_value(group_num, timer_num, &timer_val); + if (err == ESP_OK) { + uint16_t div = TG[group_num]->hw_timer[timer_num].config.divider; + *time = (double)timer_val * div / TIMER_BASE_CLK; + } + return err; +} + +esp_err_t timer_set_counter_value(timer_group_t group_num, timer_idx_t timer_num, uint64_t load_val) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_ENTER_CRITICAL(&timer_spinlock[group_num]); + TG[group_num]->hw_timer[timer_num].load_high = (uint32_t) (load_val >> 32); + TG[group_num]->hw_timer[timer_num].load_low = (uint32_t) load_val; + TG[group_num]->hw_timer[timer_num].reload = 1; + TIMER_EXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_start(timer_group_t group_num, timer_idx_t timer_num) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_ENTER_CRITICAL(&timer_spinlock[group_num]); + TG[group_num]->hw_timer[timer_num].config.enable = 1; + TIMER_EXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_pause(timer_group_t group_num, timer_idx_t timer_num) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_ENTER_CRITICAL(&timer_spinlock[group_num]); + TG[group_num]->hw_timer[timer_num].config.enable = 0; + TIMER_EXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_set_counter_mode(timer_group_t group_num, timer_idx_t timer_num, timer_count_dir_t counter_dir) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(counter_dir < TIMER_COUNT_MAX, TIMER_COUNT_DIR_ERROR, ESP_ERR_INVALID_ARG); + TIMER_ENTER_CRITICAL(&timer_spinlock[group_num]); + TG[group_num]->hw_timer[timer_num].config.increase = counter_dir; + TIMER_EXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_set_auto_reload(timer_group_t group_num, timer_idx_t timer_num, timer_autoreload_t reload) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(reload < TIMER_AUTORELOAD_MAX, TIMER_AUTORELOAD_ERROR, ESP_ERR_INVALID_ARG); + TIMER_ENTER_CRITICAL(&timer_spinlock[group_num]); + TG[group_num]->hw_timer[timer_num].config.autoreload = reload; + TIMER_EXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_set_divider(timer_group_t group_num, timer_idx_t timer_num, uint16_t divider) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_ENTER_CRITICAL(&timer_spinlock[group_num]); + int timer_en = TG[group_num]->hw_timer[timer_num].config.enable; + TG[group_num]->hw_timer[timer_num].config.enable = 0; + TG[group_num]->hw_timer[timer_num].config.divider = divider; + TG[group_num]->hw_timer[timer_num].config.enable = timer_en; + TIMER_EXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_set_alarm_value(timer_group_t group_num, timer_idx_t timer_num, uint64_t alarm_value) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_ENTER_CRITICAL(&timer_spinlock[group_num]); + TG[group_num]->hw_timer[timer_num].alarm_high = (uint32_t) (alarm_value >> 32); + TG[group_num]->hw_timer[timer_num].alarm_low = (uint32_t) alarm_value; + TIMER_EXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_get_alarm_value(timer_group_t group_num, timer_idx_t timer_num, uint64_t* alarm_value) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(alarm_value != NULL, TIMER_PARAM_ADDR_ERROR, ESP_ERR_INVALID_ARG); + portENTER_CRITICAL(&timer_spinlock[group_num]); + *alarm_value = ((uint64_t) TG[group_num]->hw_timer[timer_num].alarm_high << 32) + | (TG[group_num]->hw_timer[timer_num].alarm_low); + portEXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_set_alarm(timer_group_t group_num, timer_idx_t timer_num, timer_alarm_t alarm_en) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(alarm_en < TIMER_ALARM_MAX, TIMER_ALARM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_ENTER_CRITICAL(&timer_spinlock[group_num]); + TG[group_num]->hw_timer[timer_num].config.alarm_en = alarm_en; + TIMER_EXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_isr_register(timer_group_t group_num, timer_idx_t timer_num, int timer_intr_num, + timer_intr_mode_t intr_type, void (*fn)(void*), void * arg) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(fn != NULL, TIMER_PARAM_ADDR_ERROR, ESP_ERR_INVALID_ARG); + + ESP_INTR_DISABLE(timer_intr_num); + int intr_source = 0; + switch(group_num) { + case TIMER_GROUP_0: + default: + if(intr_type == TIMER_INTR_LEVEL) { + intr_source = ETS_TG0_T0_LEVEL_INTR_SOURCE + timer_num; + } else { + intr_source = ETS_TG0_T0_EDGE_INTR_SOURCE + timer_num; + } + break; + case TIMER_GROUP_1: + if(intr_type == TIMER_INTR_LEVEL) { + intr_source = ETS_TG1_T0_LEVEL_INTR_SOURCE + timer_num; + } else { + intr_source = ETS_TG1_T0_EDGE_INTR_SOURCE + timer_num; + } + break; + } + intr_matrix_set(xPortGetCoreID(), intr_source, timer_intr_num); + xt_set_interrupt_handler(timer_intr_num, fn, arg); + ESP_INTR_ENABLE(timer_intr_num); + return ESP_OK; +} + +esp_err_t timer_init(timer_group_t group_num, timer_idx_t timer_num, timer_config_t *config) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(config != NULL, TIMER_PARAM_ADDR_ERROR, ESP_ERR_INVALID_ARG); + + if(group_num == 0) { + periph_module_enable(PERIPH_TIMG0_MODULE); + } else if(group_num == 1) { + periph_module_enable(PERIPH_TIMG1_MODULE); + } + TIMER_ENTER_CRITICAL(&timer_spinlock[group_num]); + TG[group_num]->hw_timer[timer_num].config.autoreload = config->auto_reload; + TG[group_num]->hw_timer[timer_num].config.divider = config->divider; + TG[group_num]->hw_timer[timer_num].config.enable = config->counter_en; + TG[group_num]->hw_timer[timer_num].config.increase = config->counter_dir; + TG[group_num]->hw_timer[timer_num].config.alarm_en = config->alarm_en; + TG[group_num]->hw_timer[timer_num].config.level_int_en = (config->intr_type == TIMER_INTR_LEVEL ? 1 : 0); + TG[group_num]->hw_timer[timer_num].config.edge_int_en = (config->intr_type == TIMER_INTR_LEVEL ? 0 : 1); + TIMER_EXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_get_config(timer_group_t group_num, timer_idx_t timer_num, timer_config_t *config) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(config != NULL, TIMER_PARAM_ADDR_ERROR, ESP_ERR_INVALID_ARG); + TIMER_ENTER_CRITICAL(&timer_spinlock[group_num]); + config->alarm_en = TG[group_num]->hw_timer[timer_num].config.alarm_en; + config->auto_reload = TG[group_num]->hw_timer[timer_num].config.autoreload; + config->counter_dir = TG[group_num]->hw_timer[timer_num].config.increase; + config->counter_dir = TG[group_num]->hw_timer[timer_num].config.divider; + config->counter_en = TG[group_num]->hw_timer[timer_num].config.enable; + if(TG[group_num]->hw_timer[timer_num].config.level_int_en) { + config->intr_type =TIMER_INTR_LEVEL; + } + TIMER_EXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_group_intr_enable(timer_group_t group_num, uint32_t en_mask) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + portENTER_CRITICAL(&timer_spinlock[group_num]); + TG[group_num]->int_ena.val |= en_mask; + portEXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_group_intr_disable(timer_group_t group_num, uint32_t disable_mask) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + portENTER_CRITICAL(&timer_spinlock[group_num]); + TG[group_num]->int_ena.val &= (~disable_mask); + portEXIT_CRITICAL(&timer_spinlock[group_num]); + return ESP_OK; +} + +esp_err_t timer_enable_intr(timer_group_t group_num, timer_idx_t timer_num) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + return timer_group_intr_enable(group_num, BIT(timer_num)); +} + +esp_err_t timer_disable_intr(timer_group_t group_num, timer_idx_t timer_num) +{ + TIMER_CHECK(group_num < TIMER_GROUP_MAX, TIMER_GROUP_NUM_ERROR, ESP_ERR_INVALID_ARG); + TIMER_CHECK(timer_num < TIMER_MAX, TIMER_NUM_ERROR, ESP_ERR_INVALID_ARG); + return timer_group_intr_disable(group_num, BIT(timer_num)); +} + + diff --git a/components/esp32/component.mk b/components/esp32/component.mk index 8059d157c5..6c0d65d9c5 100644 --- a/components/esp32/component.mk +++ b/components/esp32/component.mk @@ -4,7 +4,7 @@ COMPONENT_SRCDIRS := . hwcrypto -LIBS := core net80211 phy rtc pp wpa smartconfig coexist wps +LIBS := core net80211 phy rtc pp wpa smartconfig coexist wps wpa2 LINKER_SCRIPTS += -T esp32_out.ld -T esp32.common.ld -T esp32.rom.ld -T esp32.peripherals.ld diff --git a/components/esp32/cpu_freq.c b/components/esp32/cpu_freq.c index c9d3104594..c68dd4f078 100644 --- a/components/esp32/cpu_freq.c +++ b/components/esp32/cpu_freq.c @@ -16,25 +16,8 @@ #include "rom/ets_sys.h" #include "rom/uart.h" #include "sdkconfig.h" - -typedef enum{ - XTAL_40M = 40, - XTAL_26M = 26, - XTAL_24M = 24, - XTAL_AUTO = 0 -} xtal_freq_t; - -typedef enum{ - CPU_80M = 1, - CPU_160M = 2, - CPU_240M = 3, -} cpu_freq_t; - -extern void phy_get_romfunc_addr(); - -// TODO: these functions need to be moved from librtc to ESP-IDF -extern void rtc_init_lite(xtal_freq_t xtal_freq); -extern void rtc_set_cpu_freq(cpu_freq_t cpu_freq); +#include "phy.h" +#include "rtc.h" /* * This function is not exposed as an API at this point, diff --git a/components/esp32/cpu_start.c b/components/esp32/cpu_start.c index c4b9a7e247..1641ab3f0a 100644 --- a/components/esp32/cpu_start.c +++ b/components/esp32/cpu_start.c @@ -117,9 +117,7 @@ void IRAM_ATTR call_start_cpu0() //Flush and enable icache for APP CPU Cache_Flush(1); Cache_Read_Enable(1); - //Un-stall the app cpu; the panic handler may have stalled it. - CLEAR_PERI_REG_MASK(RTC_CNTL_SW_CPU_STALL_REG, RTC_CNTL_SW_STALL_APPCPU_C1_M); - CLEAR_PERI_REG_MASK(RTC_CNTL_OPTIONS0_REG, RTC_CNTL_SW_STALL_APPCPU_C0_M); + esp_cpu_unstall(1); //Enable clock gating and reset the app cpu. SET_PERI_REG_MASK(DPORT_APPCPU_CTRL_B_REG, DPORT_APPCPU_CLKGATE_EN); CLEAR_PERI_REG_MASK(DPORT_APPCPU_CTRL_C_REG, DPORT_APPCPU_RUNSTALL); @@ -155,6 +153,7 @@ void IRAM_ATTR call_start_cpu1() void start_cpu0_default(void) { + esp_setup_syscall_table(); //Enable trace memory and immediately start trace. #if CONFIG_MEMMAP_TRACEMEM #if CONFIG_MEMMAP_TRACEMEM_TWOBANKS @@ -175,7 +174,6 @@ void start_cpu0_default(void) #if CONFIG_TASK_WDT esp_task_wdt_init(); #endif - esp_setup_syscall_table(); esp_setup_time_syscalls(); esp_vfs_dev_uart_register(); esp_reent_init(_GLOBAL_REENT); diff --git a/components/esp32/cpu_util.c b/components/esp32/cpu_util.c new file mode 100644 index 0000000000..cff61ab796 --- /dev/null +++ b/components/esp32/cpu_util.c @@ -0,0 +1,44 @@ +// Copyright 2013-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#include "esp_attr.h" +#include "soc/cpu.h" +#include "soc/soc.h" +#include "soc/rtc_cntl_reg.h" + +void IRAM_ATTR esp_cpu_stall(int cpu_id) +{ + if (cpu_id == 1) { + CLEAR_PERI_REG_MASK(RTC_CNTL_SW_CPU_STALL_REG, RTC_CNTL_SW_STALL_APPCPU_C1_M); + SET_PERI_REG_MASK(RTC_CNTL_SW_CPU_STALL_REG, 0x21<> 32, time_in_us, period, &cycle_h, &cycle_l); + rtc_slp_prep_lite(1, 0); + rtc_sleep(cycle_h, cycle_l, TIMER_EXPIRE_EN, 0); + while (1) { + ; + } +} + +void system_deep_sleep(uint64_t) __attribute__((alias("esp_deep_sleep"))); diff --git a/components/esp32/event_default_handlers.c b/components/esp32/event_default_handlers.c index d3bf57fc89..c09775ab9d 100644 --- a/components/esp32/event_default_handlers.c +++ b/components/esp32/event_default_handlers.c @@ -22,6 +22,8 @@ #include "esp_event.h" #include "esp_event_loop.h" #include "esp_task.h" +#include "esp_eth.h" + #include "rom/ets_sys.h" #include "freertos/FreeRTOS.h" @@ -59,6 +61,11 @@ static esp_err_t system_event_sta_connected_handle_default(system_event_t *event static esp_err_t system_event_sta_disconnected_handle_default(system_event_t *event); static esp_err_t system_event_sta_got_ip_default(system_event_t *event); +static esp_err_t system_event_eth_start_handle_default(system_event_t *event); +static esp_err_t system_event_eth_stop_handle_default(system_event_t *event); +static esp_err_t system_event_eth_connected_handle_default(system_event_t *event); +static esp_err_t system_event_eth_disconnected_handle_default(system_event_t *event); + static system_event_handle_t g_system_event_handle_table[] = { {SYSTEM_EVENT_WIFI_READY, NULL}, {SYSTEM_EVENT_SCAN_DONE, NULL}, @@ -77,9 +84,74 @@ static system_event_handle_t g_system_event_handle_table[] = { {SYSTEM_EVENT_AP_STACONNECTED, NULL}, {SYSTEM_EVENT_AP_STADISCONNECTED, NULL}, {SYSTEM_EVENT_AP_PROBEREQRECVED, NULL}, + {SYSTEM_EVENT_AP_STA_GOT_IP6, NULL}, + {SYSTEM_EVENT_ETH_START, system_event_eth_start_handle_default}, + {SYSTEM_EVENT_ETH_STOP, system_event_eth_stop_handle_default}, + {SYSTEM_EVENT_ETH_CONNECTED, system_event_eth_connected_handle_default}, + {SYSTEM_EVENT_ETH_DISCONNECTED, system_event_eth_disconnected_handle_default}, + {SYSTEM_EVENT_ETH_GOT_IP, NULL}, {SYSTEM_EVENT_MAX, NULL}, }; +esp_err_t system_event_eth_start_handle_default(system_event_t *event) +{ + tcpip_adapter_ip_info_t eth_ip; + uint8_t eth_mac[6]; + + esp_eth_get_mac(eth_mac); + tcpip_adapter_get_ip_info(TCPIP_ADAPTER_IF_ETH, ð_ip); + tcpip_adapter_start(TCPIP_ADAPTER_IF_ETH, eth_mac, ð_ip); + + return ESP_OK; +} + +esp_err_t system_event_eth_stop_handle_default(system_event_t *event) +{ + tcpip_adapter_stop(TCPIP_ADAPTER_IF_ETH); + + return ESP_OK; +} + +esp_err_t system_event_eth_connected_handle_default(system_event_t *event) +{ + tcpip_adapter_dhcp_status_t status; + + tcpip_adapter_up(TCPIP_ADAPTER_IF_ETH); + + tcpip_adapter_dhcpc_get_status(TCPIP_ADAPTER_IF_ETH, &status); + + if (status == TCPIP_ADAPTER_DHCP_INIT) { + + tcpip_adapter_dhcpc_start(TCPIP_ADAPTER_IF_ETH); + } else if (status == TCPIP_ADAPTER_DHCP_STOPPED) { + tcpip_adapter_ip_info_t eth_ip; + + tcpip_adapter_get_ip_info(TCPIP_ADAPTER_IF_ETH, ð_ip); + + if (!(ip4_addr_isany_val(eth_ip.ip) || ip4_addr_isany_val(eth_ip.netmask) || ip4_addr_isany_val(eth_ip.gw))) { + system_event_t evt; + + //notify event + evt.event_id = SYSTEM_EVENT_ETH_GOT_IP; + memcpy(&evt.event_info.got_ip.ip_info, ð_ip, sizeof(tcpip_adapter_ip_info_t)); + + esp_event_send(&evt); + } else { + ESP_LOGE(TAG, "invalid static ip"); + } + } + + return ESP_OK; +} + +esp_err_t system_event_eth_disconnected_handle_default(system_event_t *event) +{ + tcpip_adapter_down(TCPIP_ADAPTER_IF_ETH); + return ESP_OK; +} + + + static esp_err_t system_event_sta_got_ip_default(system_event_t *event) { WIFI_API_CALL_CHECK("esp_wifi_internal_set_sta_ip", esp_wifi_internal_set_sta_ip(), ESP_OK); @@ -97,8 +169,8 @@ esp_err_t system_event_ap_start_handle_default(system_event_t *event) tcpip_adapter_ip_info_t ap_ip; uint8_t ap_mac[6]; - WIFI_API_CALL_CHECK("esp_wifi_internal_reg_rxcb", esp_wifi_internal_reg_rxcb(WIFI_IF_AP, (wifi_rxcb_t)tcpip_adapter_ap_input), ESP_OK); - WIFI_API_CALL_CHECK("esp_wifi_mac_get", esp_wifi_get_mac(WIFI_IF_AP, ap_mac), ESP_OK); + WIFI_API_CALL_CHECK("esp_wifi_internal_reg_rxcb", esp_wifi_internal_reg_rxcb(ESP_IF_WIFI_AP, (wifi_rxcb_t)tcpip_adapter_ap_input), ESP_OK); + WIFI_API_CALL_CHECK("esp_wifi_mac_get", esp_wifi_get_mac(ESP_IF_WIFI_AP, ap_mac), ESP_OK); tcpip_adapter_get_ip_info(TCPIP_ADAPTER_IF_AP, &ap_ip); tcpip_adapter_start(TCPIP_ADAPTER_IF_AP, ap_mac, &ap_ip); @@ -108,7 +180,7 @@ esp_err_t system_event_ap_start_handle_default(system_event_t *event) esp_err_t system_event_ap_stop_handle_default(system_event_t *event) { - WIFI_API_CALL_CHECK("esp_wifi_internal_reg_rxcb", esp_wifi_internal_reg_rxcb(WIFI_IF_AP, NULL), ESP_OK); + WIFI_API_CALL_CHECK("esp_wifi_internal_reg_rxcb", esp_wifi_internal_reg_rxcb(ESP_IF_WIFI_AP, NULL), ESP_OK); tcpip_adapter_stop(TCPIP_ADAPTER_IF_AP); @@ -120,7 +192,7 @@ esp_err_t system_event_sta_start_handle_default(system_event_t *event) tcpip_adapter_ip_info_t sta_ip; uint8_t sta_mac[6]; - WIFI_API_CALL_CHECK("esp_wifi_mac_get", esp_wifi_get_mac(WIFI_IF_STA, sta_mac), ESP_OK); + WIFI_API_CALL_CHECK("esp_wifi_mac_get", esp_wifi_get_mac(ESP_IF_WIFI_STA, sta_mac), ESP_OK); tcpip_adapter_get_ip_info(TCPIP_ADAPTER_IF_STA, &sta_ip); tcpip_adapter_start(TCPIP_ADAPTER_IF_STA, sta_mac, &sta_ip); @@ -138,7 +210,7 @@ esp_err_t system_event_sta_connected_handle_default(system_event_t *event) { tcpip_adapter_dhcp_status_t status; - WIFI_API_CALL_CHECK("esp_wifi_internal_reg_rxcb", esp_wifi_internal_reg_rxcb(WIFI_IF_STA, (wifi_rxcb_t)tcpip_adapter_sta_input), ESP_OK); + WIFI_API_CALL_CHECK("esp_wifi_internal_reg_rxcb", esp_wifi_internal_reg_rxcb(ESP_IF_WIFI_STA, (wifi_rxcb_t)tcpip_adapter_sta_input), ESP_OK); tcpip_adapter_up(TCPIP_ADAPTER_IF_STA); @@ -170,7 +242,7 @@ esp_err_t system_event_sta_connected_handle_default(system_event_t *event) esp_err_t system_event_sta_disconnected_handle_default(system_event_t *event) { tcpip_adapter_down(TCPIP_ADAPTER_IF_STA); - WIFI_API_CALL_CHECK("esp_wifi_internal_reg_rxcb", esp_wifi_internal_reg_rxcb(WIFI_IF_STA, NULL), ESP_OK); + WIFI_API_CALL_CHECK("esp_wifi_internal_reg_rxcb", esp_wifi_internal_reg_rxcb(ESP_IF_WIFI_STA, NULL), ESP_OK); return ESP_OK; } @@ -267,6 +339,27 @@ static esp_err_t esp_system_event_debug(system_event_t *event) MAC2STR(ap_probereqrecved->mac)); break; } + case SYSTEM_EVENT_ETH_START: { + ESP_LOGD(TAG, "SYSTEM_EVENT_ETH_START"); + break; + } + case SYSTEM_EVENT_ETH_STOP: { + ESP_LOGD(TAG, "SYSTEM_EVENT_ETH_STOP"); + break; + } + case SYSTEM_EVENT_ETH_CONNECTED: { + ESP_LOGD(TAG, "SYSTEM_EVENT_ETH_CONNECETED"); + break; + } + case SYSTEM_EVENT_ETH_DISCONNECTED: { + ESP_LOGD(TAG, "SYSTEM_EVENT_ETH_DISCONNECETED"); + break; + } + case SYSTEM_EVENT_ETH_GOT_IP: { + ESP_LOGD(TAG, "SYSTEM_EVENT_ETH_GOT_IP"); + break; + } + default: { ESP_LOGW(TAG, "no such kind of event!"); break; diff --git a/components/esp32/hw_random.c b/components/esp32/hw_random.c new file mode 100644 index 0000000000..11c7af936b --- /dev/null +++ b/components/esp32/hw_random.c @@ -0,0 +1,41 @@ +// Copyright 2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + + +#include +#include +#include +#include "esp_attr.h" +#include "soc/wdev_reg.h" +#include "freertos/FreeRTOSConfig.h" +#include "xtensa/core-macros.h" + +uint32_t IRAM_ATTR esp_random(void) +{ + /* The PRNG which implements WDEV_RANDOM register gets 2 bits + * of extra entropy from a hardware randomness source every APB clock cycle. + * To make sure entropy is not drained faster than it is added, + * this function needs to wait for at least 16 APB clock cycles after reading + * previous word. This implementation may actually wait a bit longer + * due to extra time spent in arithmetic and branch statements. + */ + + static uint32_t last_ccount = 0; + uint32_t ccount; + do { + ccount = XTHAL_GET_CCOUNT(); + } while (ccount - last_ccount < XT_CLOCK_FREQ / APB_CLK_FREQ * 16); + last_ccount = ccount; + return REG_READ(WDEV_RND_REG); +} diff --git a/components/esp32/hwcrypto/aes.c b/components/esp32/hwcrypto/aes.c index 169465822d..8f27cd17c2 100644 --- a/components/esp32/hwcrypto/aes.c +++ b/components/esp32/hwcrypto/aes.c @@ -28,6 +28,7 @@ #include #include "hwcrypto/aes.h" #include "rom/aes.h" +#include "soc/dport_reg.h" #include static _lock_t aes_lock; @@ -36,14 +37,23 @@ void esp_aes_acquire_hardware( void ) { /* newlib locks lazy initialize on ESP-IDF */ _lock_acquire(&aes_lock); - ets_aes_enable(); + /* Enable AES hardware */ + REG_SET_BIT(DPORT_PERI_CLK_EN_REG, DPORT_PERI_EN_AES); + /* Clear reset on digital signature & secure boot units, + otherwise AES unit is held in reset also. */ + REG_CLR_BIT(DPORT_PERI_RST_EN_REG, + DPORT_PERI_EN_AES + | DPORT_PERI_EN_DIGITAL_SIGNATURE + | DPORT_PERI_EN_SECUREBOOT); } void esp_aes_release_hardware( void ) { - uint8_t zero[256/8] = { 0 }; - ets_aes_setkey_enc(zero, AES256); - ets_aes_disable(); + /* Disable AES hardware */ + REG_SET_BIT(DPORT_PERI_RST_EN_REG, DPORT_PERI_EN_AES); + /* Don't return other units to reset, as this pulls + reset on RSA & SHA units, respectively. */ + REG_CLR_BIT(DPORT_PERI_CLK_EN_REG, DPORT_PERI_EN_AES); _lock_release(&aes_lock); } diff --git a/components/esp32/hwcrypto/sha.c b/components/esp32/hwcrypto/sha.c index 06b00c54ab..61e37b01d2 100644 --- a/components/esp32/hwcrypto/sha.c +++ b/components/esp32/hwcrypto/sha.c @@ -26,242 +26,264 @@ */ #include +#include #include +#include +#include + #include "hwcrypto/sha.h" #include "rom/ets_sys.h" +#include "soc/dport_reg.h" +#include "soc/hwcrypto_reg.h" - -static _lock_t sha_lock; - -void esp_sha_acquire_hardware( void ) -{ - /* newlib locks lazy initialize on ESP-IDF */ - _lock_acquire(&sha_lock); - ets_sha_enable(); +inline static uint32_t SHA_LOAD_REG(esp_sha_type sha_type) { + return SHA_1_LOAD_REG + sha_type * 0x10; } -void esp_sha_release_hardware( void ) -{ - /* Want to empty internal SHA buffers where possible, - need to check if this is sufficient for this. */ - SHA_CTX zero = { 0 }; - ets_sha_init(&zero); - ets_sha_disable(); - _lock_release(&sha_lock); +inline static uint32_t SHA_BUSY_REG(esp_sha_type sha_type) { + return SHA_1_BUSY_REG + sha_type * 0x10; } -/* Generic esp_shaX_update implementation */ -static void esp_sha_update( esp_sha_context *ctx, const unsigned char *input, size_t ilen, size_t block_size) +inline static uint32_t SHA_START_REG(esp_sha_type sha_type) { + return SHA_1_START_REG + sha_type * 0x10; +} + +inline static uint32_t SHA_CONTINUE_REG(esp_sha_type sha_type) { + return SHA_1_CONTINUE_REG + sha_type * 0x10; +} + +/* Single lock for SHA engine memory block +*/ +static _lock_t memory_block_lock; + +typedef struct { + _lock_t lock; + bool in_use; +} sha_engine_state; + +/* Pointer to state of each concurrent SHA engine. + + Indexes: + 0 = SHA1 + 1 = SHA2_256 + 2 = SHA2_384 or SHA2_512 +*/ +static sha_engine_state engine_states[3]; + +/* Index into the sha_engine_state array */ +inline static size_t sha_engine_index(esp_sha_type type) { + switch(type) { + case SHA1: + return 0; + case SHA2_256: + return 1; + default: + return 2; + } +} + +/* Return digest length (in bytes) for a given SHA type */ +inline static size_t sha_length(esp_sha_type type) { + switch(type) { + case SHA1: + return 20; + case SHA2_256: + return 32; + case SHA2_384: + return 48; + case SHA2_512: + return 64; + default: + return 0; + } +} + +/* Return block size (in bytes) for a given SHA type */ +inline static size_t block_length(esp_sha_type type) { + switch(type) { + case SHA1: + case SHA2_256: + return 64; + case SHA2_384: + case SHA2_512: + return 128; + default: + return 0; + } +} + +void esp_sha_lock_memory_block(void) { - /* Feed the SHA engine one block at a time */ + _lock_acquire(&memory_block_lock); +} + +void esp_sha_unlock_memory_block(void) +{ + _lock_release(&memory_block_lock); +} + +/* Lock to hold when changing SHA engine state, + allows checking of sha_engines_all_idle() +*/ +static _lock_t state_change_lock; + +inline static bool sha_engines_all_idle() { + return !engine_states[0].in_use + && !engine_states[1].in_use + && !engine_states[2].in_use; +} + +static void esp_sha_lock_engine_inner(sha_engine_state *engine); + +bool esp_sha_try_lock_engine(esp_sha_type sha_type) +{ + sha_engine_state *engine = &engine_states[sha_engine_index(sha_type)]; + if(_lock_try_acquire(&engine->lock) != 0) { + /* This SHA engine is already in use */ + return false; + } else { + esp_sha_lock_engine_inner(engine); + return true; + } +} + +void esp_sha_lock_engine(esp_sha_type sha_type) +{ + sha_engine_state *engine = &engine_states[sha_engine_index(sha_type)]; + _lock_acquire(&engine->lock); + esp_sha_lock_engine_inner(engine); +} + +static void esp_sha_lock_engine_inner(sha_engine_state *engine) +{ + _lock_acquire(&state_change_lock); + + if (sha_engines_all_idle()) { + /* Enable SHA hardware */ + REG_SET_BIT(DPORT_PERI_CLK_EN_REG, DPORT_PERI_EN_SHA); + /* also clear reset on secure boot, otherwise SHA is held in reset */ + REG_CLR_BIT(DPORT_PERI_RST_EN_REG, + DPORT_PERI_EN_SHA + | DPORT_PERI_EN_SECUREBOOT); + ets_sha_enable(); + } + + _lock_release(&state_change_lock); + + assert( !engine->in_use && "in_use flag should be cleared" ); + engine->in_use = true; +} + + +void esp_sha_unlock_engine(esp_sha_type sha_type) +{ + sha_engine_state *engine = &engine_states[sha_engine_index(sha_type)]; + + _lock_acquire(&state_change_lock); + + assert( engine->in_use && "in_use flag should be set" ); + engine->in_use = false; + + if (sha_engines_all_idle()) { + /* Disable SHA hardware */ + /* Don't assert reset on secure boot, otherwise AES is held in reset */ + REG_SET_BIT(DPORT_PERI_RST_EN_REG, DPORT_PERI_EN_SHA); + REG_CLR_BIT(DPORT_PERI_CLK_EN_REG, DPORT_PERI_EN_SHA); + } + + _lock_release(&state_change_lock); + + _lock_release(&engine->lock); +} + +void esp_sha_wait_idle(void) +{ + while(REG_READ(SHA_1_BUSY_REG) == 1) {} + while(REG_READ(SHA_256_BUSY_REG) == 1) {} + while(REG_READ(SHA_384_BUSY_REG) == 1) {} + while(REG_READ(SHA_512_BUSY_REG) == 1) {} +} + +void esp_sha_read_digest_state(esp_sha_type sha_type, void *digest_state) +{ + sha_engine_state *engine = &engine_states[sha_engine_index(sha_type)]; + assert(engine->in_use && "SHA engine should be locked" ); + + esp_sha_lock_memory_block(); + + esp_sha_wait_idle(); + + REG_WRITE(SHA_LOAD_REG(sha_type), 1); + while(REG_READ(SHA_BUSY_REG(sha_type)) == 1) { } + + uint32_t *digest_state_words = (uint32_t *)digest_state; + uint32_t *reg_addr_buf = (uint32_t *)(SHA_TEXT_BASE); + if(sha_type == SHA2_384 || sha_type == SHA2_512) { + /* for these ciphers using 64-bit states, swap each pair of words */ + for(int i = 0; i < sha_length(sha_type)/4; i += 2) { + digest_state_words[i+1] = reg_addr_buf[i]; + digest_state_words[i]= reg_addr_buf[i+1]; + } + } else { + memcpy(digest_state_words, reg_addr_buf, sha_length(sha_type)); + } + asm volatile ("memw"); + + esp_sha_unlock_memory_block(); +} + +void esp_sha_block(esp_sha_type sha_type, const void *data_block, bool is_first_block) +{ + sha_engine_state *engine = &engine_states[sha_engine_index(sha_type)]; + assert(engine->in_use && "SHA engine should be locked" ); + + esp_sha_lock_memory_block(); + + esp_sha_wait_idle(); + + /* Fill the data block */ + uint32_t *reg_addr_buf = (uint32_t *)(SHA_TEXT_BASE); + uint32_t *data_words = (uint32_t *)data_block; + for (int i = 0; i < block_length(sha_type) / 4; i++) { + reg_addr_buf[i] = __bswap_32(data_words[i]); + } + asm volatile ("memw"); + + if(is_first_block) { + REG_WRITE(SHA_START_REG(sha_type), 1); + } else { + REG_WRITE(SHA_CONTINUE_REG(sha_type), 1); + } + + esp_sha_unlock_memory_block(); + + /* Note: deliberately not waiting for this operation to complete, + as a performance tweak - delay waiting until the next time we need the SHA + unit, instead. + */ +} + +void esp_sha(esp_sha_type sha_type, const unsigned char *input, size_t ilen, unsigned char *output) +{ + size_t block_len = block_length(sha_type); + + esp_sha_lock_engine(sha_type); + + SHA_CTX ctx; + ets_sha_init(&ctx); while(ilen > 0) { - size_t chunk_len = (ilen > block_size) ? block_size : ilen; - ets_sha_update(&ctx->context, ctx->context_type, input, chunk_len * 8); + size_t chunk_len = (ilen > block_len) ? block_len : ilen; + esp_sha_lock_memory_block(); + esp_sha_wait_idle(); + ets_sha_update(&ctx, sha_type, input, chunk_len * 8); + esp_sha_unlock_memory_block(); input += chunk_len; ilen -= chunk_len; } + esp_sha_lock_memory_block(); + esp_sha_wait_idle(); + ets_sha_finish(&ctx, sha_type, output); + esp_sha_unlock_memory_block(); + + esp_sha_unlock_engine(sha_type); } - -void esp_sha1_init( esp_sha_context *ctx ) -{ - bzero( ctx, sizeof( esp_sha_context ) ); -} - -void esp_sha1_free( esp_sha_context *ctx ) -{ - if ( ctx == NULL ) { - return; - } - - bzero( ctx, sizeof( esp_sha_context ) ); -} - -void esp_sha1_clone( esp_sha_context *dst, const esp_sha_context *src ) -{ - *dst = *src; -} - -/* - * SHA-1 context setup - */ -void esp_sha1_start( esp_sha_context *ctx ) -{ - ctx->context_type = SHA1; - esp_sha_acquire_hardware(); - ets_sha_init(&ctx->context); -} - -/* - * SHA-1 process buffer - */ -void esp_sha1_update( esp_sha_context *ctx, const unsigned char *input, size_t ilen ) -{ - esp_sha_update(ctx, input, ilen, 64); -} - -/* - * SHA-1 final digest - */ -void esp_sha1_finish( esp_sha_context *ctx, unsigned char output[20] ) -{ - ets_sha_finish(&ctx->context, ctx->context_type, output); - esp_sha_release_hardware(); -} - -/* Full SHA-1 calculation */ -void esp_sha1( const unsigned char *input, size_t ilen, unsigned char output[20] ) -{ - esp_sha_context ctx; - - esp_sha1_init( &ctx ); - esp_sha1_start( &ctx ); - esp_sha1_update( &ctx, input, ilen ); - esp_sha1_finish( &ctx, output ); - esp_sha1_free( &ctx ); -} - -void esp_sha256_init( esp_sha_context *ctx ) -{ - bzero( ctx, sizeof( esp_sha_context ) ); -} - -void esp_sha256_free( esp_sha_context *ctx ) -{ - if ( ctx == NULL ) { - return; - } - - bzero( ctx, sizeof( esp_sha_context ) ); -} - -void esp_sha256_clone( esp_sha_context *dst, const esp_sha_context *src ) -{ - *dst = *src; -} - -/* - * SHA-256 context setup - */ -void esp_sha256_start( esp_sha_context *ctx, int is224 ) -{ - if ( is224 == 0 ) { - /* SHA-256 */ - ctx->context_type = SHA2_256; - esp_sha_acquire_hardware(); - ets_sha_init(&ctx->context); - } else { - /* SHA-224 is not supported! */ - ctx->context_type = SHA_INVALID; - } -} - -/* - * SHA-256 process buffer - */ -void esp_sha256_update( esp_sha_context *ctx, const unsigned char *input, size_t ilen ) -{ - if( ctx->context_type == SHA2_256 ) { - esp_sha_update(ctx, input, ilen, 64); - } - /* SHA-224 is a no-op */ -} - -/* - * SHA-256 final digest - */ -void esp_sha256_finish( esp_sha_context *ctx, unsigned char output[32] ) -{ - if ( ctx->context_type == SHA2_256 ) { - ets_sha_finish(&ctx->context, ctx->context_type, output); - esp_sha_release_hardware(); - } else { - /* No hardware SHA-224 support, but mbedTLS API doesn't allow failure. - For now, zero the output to make it clear it's not valid. */ - bzero( output, 28 ); - } -} - -/* - * Full SHA-256 calculation - */ -void esp_sha256( const unsigned char *input, size_t ilen, unsigned char output[32], int is224 ) -{ - esp_sha_context ctx; - - esp_sha256_init( &ctx ); - esp_sha256_start( &ctx, is224 ); - esp_sha256_update( &ctx, input, ilen ); - esp_sha256_finish( &ctx, output ); - esp_sha256_free( &ctx ); -} - - -///// -void esp_sha512_init( esp_sha_context *ctx ) -{ - memset( ctx, 0, sizeof( esp_sha_context ) ); -} - -void esp_sha512_free( esp_sha_context *ctx ) -{ - if ( ctx == NULL ) { - return; - } - - bzero( ctx, sizeof( esp_sha_context ) ); -} - -void esp_sha512_clone( esp_sha_context *dst, const esp_sha_context *src ) -{ - *dst = *src; -} - -/* - * SHA-512 context setup - */ -void esp_sha512_start( esp_sha_context *ctx, int is384 ) -{ - if ( is384 == 0 ) { - /* SHA-512 */ - ctx->context_type = SHA2_512; - } else { - /* SHA-384 */ - ctx->context_type = SHA2_384; - } - esp_sha_acquire_hardware(); - ets_sha_init(&ctx->context); -} - -/* - * SHA-512 process buffer - */ -void esp_sha512_update( esp_sha_context *ctx, const unsigned char *input, size_t ilen ) -{ - esp_sha_update(ctx, input, ilen, 128); -} - -/* - * SHA-512 final digest - */ -void esp_sha512_finish( esp_sha_context *ctx, unsigned char output[64] ) -{ - ets_sha_finish(&ctx->context, ctx->context_type, output); - esp_sha_release_hardware(); -} - -/* - * Full SHA-512 calculation - */ -void esp_sha512( const unsigned char *input, size_t ilen, unsigned char output[64], int is384 ) -{ - esp_sha_context ctx; - - esp_sha512_init( &ctx ); - esp_sha512_start( &ctx, is384 ); - esp_sha512_update( &ctx, input, ilen ); - esp_sha512_finish( &ctx, output ); - esp_sha512_free( &ctx ); -} - -//// - diff --git a/components/esp32/include/esp_deepsleep.h b/components/esp32/include/esp_deepsleep.h index 59b3129185..051ad14c3c 100644 --- a/components/esp32/include/esp_deepsleep.h +++ b/components/esp32/include/esp_deepsleep.h @@ -30,25 +30,34 @@ extern "C" { */ /** - * @brief Set the chip to deep-sleep mode. - * - * The device will automatically wake up after the deep-sleep time set - * by the users. Upon waking up, the device boots up from user_init. - * - * @attention The parameter time_in_us to be "uint64" is for further development. - * Only the low 32 bits of parameter time_in_us are avalable now. - * - * @param uint64 time_in_us : deep-sleep time, only the low 32bits are avalable now. unit: microsecond - * - * @return null - */ -void system_deep_sleep(uint64_t time_in_us); + * @brief Enter deep-sleep mode + * + * The device will automatically wake up after the deep-sleep time + * Upon waking up, the device calls deep sleep wake stub, and then proceeds + * to load application. + * + * This function does not return. + * + * @param time_in_us deep-sleep time, unit: microsecond + */ +void esp_deep_sleep(uint64_t time_in_us) __attribute__((noreturn)); + + +/** + * @brief Enter deep-sleep mode + * + * Function has been renamed to esp_deep_sleep. + * This name is deprecated and will be removed in a future version. + * + * @param time_in_us deep-sleep time, unit: microsecond + */ +void system_deep_sleep(uint64_t time_in_us) __attribute__((noreturn, deprecated)); /** * @brief Default stub to run on wake from deep sleep. * * Allows for executing code immediately on wake from sleep, before - * the software bootloader or esp-idf app has started up. + * the software bootloader or ESP-IDF app has started up. * * This function is weak-linked, so you can implement your own version * to run code immediately when the chip wakes from diff --git a/components/esp32/include/esp_event.h b/components/esp32/include/esp_event.h index 06e35d6ad6..8e6e1833d4 100644 --- a/components/esp32/include/esp_event.h +++ b/components/esp32/include/esp_event.h @@ -45,6 +45,11 @@ typedef enum { SYSTEM_EVENT_AP_STADISCONNECTED, /**< a station disconnected from ESP32 soft-AP */ SYSTEM_EVENT_AP_PROBEREQRECVED, /**< Receive probe request packet in soft-AP interface */ SYSTEM_EVENT_AP_STA_GOT_IP6, /**< ESP32 station or ap interface v6IP addr is preferred */ + SYSTEM_EVENT_ETH_START, /**< ESP32 ethernet start */ + SYSTEM_EVENT_ETH_STOP, /**< ESP32 ethernet stop */ + SYSTEM_EVENT_ETH_CONNECTED, /**< ESP32 ethernet phy link up */ + SYSTEM_EVENT_ETH_DISCONNECTED, /**< ESP32 ethernet phy link down */ + SYSTEM_EVENT_ETH_GOT_IP, /**< ESP32 ethernet got IP from connected AP */ SYSTEM_EVENT_MAX } system_event_id_t; diff --git a/examples/13_bt_sdp/main/demo_main.c b/components/esp32/include/esp_interface.h old mode 100755 new mode 100644 similarity index 50% rename from examples/13_bt_sdp/main/demo_main.c rename to components/esp32/include/esp_interface.h index 5489abb4ed..950c05bb22 --- a/examples/13_bt_sdp/main/demo_main.c +++ b/components/esp32/include/esp_interface.h @@ -12,31 +12,26 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include -#include -#include -#include "bt.h" -#include "freertos/FreeRTOS.h" -#include "freertos/task.h" -#include "string.h" +#ifndef __ESP_INTERFACE_H__ +#define __ESP_INTERFACE_H__ -extern void bte_main_boot_entry(void *); -extern void bt_app_task_start_up(void); -extern void bt_app_core_start(void); +#include -void pingTask(void *pvParameters) -{ - while (1) { - vTaskDelay(1000 / portTICK_PERIOD_MS); - printf("ping\n"); - } +#ifdef __cplusplus +extern "C" { +#endif + +typedef enum { + ESP_IF_WIFI_STA = 0, /**< ESP32 station interface */ + ESP_IF_WIFI_AP, /**< ESP32 soft-AP interface */ + ESP_IF_ETH, /**< ESP32 ethernet interface */ + ESP_IF_MAX +} esp_interface_t; + +#ifdef __cplusplus } +#endif -void app_main() -{ - bt_controller_init(); - xTaskCreatePinnedToCore(&pingTask, "pingTask", 2048, NULL, 5, NULL, 0); - bt_app_task_start_up(); - // bte_main_boot_entry(bt_app_core_start); -} + +#endif /* __ESP_INTERFACE_TYPES_H__ */ diff --git a/components/esp32/include/esp_system.h b/components/esp32/include/esp_system.h index d416e23d07..40ebd8403c 100644 --- a/components/esp32/include/esp_system.h +++ b/components/esp32/include/esp_system.h @@ -16,7 +16,7 @@ #define __ESP_SYSTEM_H__ #include - +#include #include "esp_err.h" #include "esp_deepsleep.h" @@ -24,166 +24,107 @@ extern "C" { #endif -/** \defgroup System_APIs System APIs - * @brief System APIs - */ - -/** @addtogroup System_APIs - * @{ - */ - /** * @attention application don't need to call this function anymore. It do nothing and will * be removed in future version. */ void system_init(void) __attribute__ ((deprecated)); - -/** - * @brief Get information of the SDK version. - * - * @param null - * - * @return Information of the SDK version. - */ -const char *system_get_sdk_version(void); - /** * @brief Reset to default settings. * - * Reset to default settings of the following APIs : wifi_station_set_auto_connect, - * wifi_set_phy_mode, wifi_softap_set_config related, wifi_station_set_config - * related, and wifi_set_opmode. - * - * @param null - * - * @return null + * Function has been deprecated, please use esp_wifi_restore instead. + * This name will be removed in a future release. */ -void system_restore(void); +void system_restore(void) __attribute__ ((deprecated)); + +/** + * @brief Restart PRO and APP CPUs. + * + * This function can be called both from PRO and APP CPUs. + * After successful restart, CPU reset reason will be SW_CPU_RESET. + * Peripherals (except for WiFi, BT, UART0, SPI1, and legacy timers) are not reset. + * This function does not return. + */ +void esp_restart(void) __attribute__ ((noreturn)); /** * @brief Restart system. * - * @param null - * - * @return null + * Function has been renamed to esp_restart. + * This name will be removed in a future release. */ -void system_restart(void); +void system_restart(void) __attribute__ ((deprecated, noreturn)); /** * @brief Get system time, unit: microsecond. * - * @param null - * - * @return System time, unit: microsecond. + * This function is deprecated. Use 'gettimeofday' function for 64-bit precision. + * This definition will be removed in a future release. */ -uint32_t system_get_time(void); +uint32_t system_get_time(void) __attribute__ ((deprecated)); /** * @brief Get the size of available heap. * - * @param null + * Note that the returned value may be larger than the maximum contiguous block + * which can be allocated. * - * @return Available heap size. + * @return Available heap size, in bytes. */ -uint32_t system_get_free_heap_size(void); +uint32_t esp_get_free_heap_size(void); /** - * @brief Get RTC time, unit: RTC clock cycle. + * @brief Get the size of available heap. * - * @param null + * Function has been renamed to esp_get_free_heap_size. + * This name will be removed in a future release. * - * @return RTC time. + * @return Available heap size, in bytes. */ -uint64_t system_get_rtc_time(void); +uint32_t system_get_free_heap_size(void) __attribute__ ((deprecated)); /** - * @brief Read user data from the RTC memory. - * - * The user data segment (1024 bytes, as shown below) is used to store user data. - * - * |<---- system data(512 bytes) ---->|<----------- user data(1024 bytes) --------->| - * - * @attention Read and write unit for data stored in the RTC memory is 4 bytes. - * @attention src_addr is the block number (4 bytes per block). So when reading data - * at the beginning of the user data segment, src_addr will be 512/4 = 128, - * n will be data length. - * - * @param uint16 src : source address of rtc memory, src_addr >= 128 - * @param void *dst : data pointer - * @param uint16 n : data length, unit: byte - * - * @return true : succeed - * @return false : fail - */ -bool system_rtc_mem_read(uint16_t src, void *dst, uint16_t n); - -/** - * @brief Write user data to the RTC memory. - * - * During deep-sleep, only RTC is working. So users can store their data - * in RTC memory if it is needed. The user data segment below (1024 bytes) - * is used to store the user data. - * - * |<---- system data(512 bytes) ---->|<----------- user data(1024 bytes) --------->| - * - * @attention Read and write unit for data stored in the RTC memory is 4 bytes. - * @attention src_addr is the block number (4 bytes per block). So when storing data - * at the beginning of the user data segment, src_addr will be 512/4 = 128, - * n will be data length. - * - * @param uint16 src : source address of rtc memory, src_addr >= 128 - * @param void *dst : data pointer - * @param uint16 n : data length, unit: byte - * - * @return true : succeed - * @return false : fail - */ -bool system_rtc_mem_write(uint16_t dst, const void *src, uint16_t n); - -/** \defgroup System_boot_APIs Boot APIs - * @brief boot APIs - */ - -/** @addtogroup System_boot_APIs - * @{ - */ - -/** - * @} - */ - -/** \defgroup Hardware_MAC_APIs Hardware MAC APIs - * @brief Hardware MAC address APIs - * - * In WiFi MAC, only ESP32 station MAC is the hardware MAC, ESP32 softAP MAC is a software MAC - * calculated from ESP32 station MAC. - * So users need to call wifi_get_macaddr to query the ESP32 softAP MAC if ESP32 station MAC changed. - * - */ - -/** @addtogroup Hardware_MAC_APIs - * @{ - */ + * @brief Get one random 32-bit word from hardware RNG + * + * @return random value between 0 and UINT32_MAX + */ +uint32_t esp_random(void); /** * @brief Read hardware MAC address. * - * @param uint8 mac[6] : the hardware MAC address, length: 6 bytes. + * In WiFi MAC, only ESP32 station MAC is the hardware MAC, ESP32 softAP MAC is a software MAC + * calculated from ESP32 station MAC. + * So users need to call esp_wifi_get_macaddr to query the ESP32 softAP MAC if ESP32 station MAC changed. * - * @return esp_err_t + * @param mac hardware MAC address, length: 6 bytes. + * + * @return ESP_OK on success */ -esp_err_t system_efuse_read_mac(uint8_t mac[6]); - +esp_err_t esp_efuse_read_mac(uint8_t* mac); /** - * @} + * @brief Read hardware MAC address. + * + * Function has been renamed to esp_efuse_read_mac. + * This name will be removed in a future release. + * + * @param mac hardware MAC address, length: 6 bytes. + * @return ESP_OK on success */ - +esp_err_t system_efuse_read_mac(uint8_t mac[6]) __attribute__ ((deprecated)); /** - * @} - */ + * Get SDK version + * + * This function is deprecated and will be removed in a future release. + * + * @return constant string "master" + */ +const char* system_get_sdk_version(void) __attribute__ ((deprecated)); + + #ifdef __cplusplus } diff --git a/components/esp32/include/esp_types.h b/components/esp32/include/esp_types.h index c142aee687..547024e3f7 100755 --- a/components/esp32/include/esp_types.h +++ b/components/esp32/include/esp_types.h @@ -22,52 +22,4 @@ #include #include -#define __ATTRIB_PACK __attribute__ ((packed)) -#define __ATTRIB_PRINTF __attribute__ ((format (printf, 1, 2))) -#define __ATTRIB_NORETURN __attribute__ ((noreturn)) -#define __ATTRIB_ALIGN(x) __attribute__ ((aligned((x)))) -#define INLINE __inline__ - -#define LOCAL static - -/* probably should not put STATUS here */ -typedef enum { - OK = 0, - FAIL, - PENDING, - BUSY, - CANCEL, -} STATUS; - -//#define _LITTLE_ENDIAN 1234 -//#define _BYTE_ORDER == _LITTLE_ENDIAN - -#define ASSERT( x ) do { \ - if (!(x)) { \ - printf("%s %u\n", __FILE__, __LINE__); \ - while (1) { \ - asm volatile("nop"); \ - }; \ - } \ -} while (0) - -/* #if __GNUC_PREREQ__(4, 1) */ -#ifndef __GNUC__ -#if 1 -#define __offsetof(type, field) __builtin_offsetof(type, field) -#else -#define __offsetof(type, field) ((size_t)(&((type *)0)->field)) -#endif -#endif /* __GNUC__ */ - - -/* Macros for counting and rounding. */ -#ifndef howmany -#define howmany(x, y) (((x)+((y)-1))/(y)) -#endif - -#define container_of(ptr, type, member) ({ \ - const typeof( ((type *)0)->member ) *__mptr = (ptr); \ - (type *)( (char *)__mptr - __offsetof(type,member) );}) - #endif /* __ESP_TYPES_H__ */ diff --git a/components/esp32/include/esp_wifi.h b/components/esp32/include/esp_wifi.h index 65a91929dd..00e9ec1d6e 100644 --- a/components/esp32/include/esp_wifi.h +++ b/components/esp32/include/esp_wifi.h @@ -87,6 +87,7 @@ extern "C" { #define ESP_ERR_WIFI_SSID (ESP_ERR_WIFI_BASE + 9) /*!< SSID is invalid */ #define ESP_ERR_WIFI_PASSWORD (ESP_ERR_WIFI_BASE + 10) /*!< Passord is invalid */ #define ESP_ERR_WIFI_TIMEOUT (ESP_ERR_WIFI_BASE + 11) /*!< Timeout error */ +#define ESP_ERR_WIFI_WAKE_FAIL (ESP_ERR_WIFI_BASE + 12) /*!< WiFi is in sleep state(RF closed) and wakeup fail */ /** * @brief WiFi stack configuration parameters passed to esp_wifi_init call. @@ -186,6 +187,21 @@ esp_err_t esp_wifi_start(void); */ esp_err_t esp_wifi_stop(void); +/** + * @brief Restore WiFi stack persistent settings to default values + * + * This function will reset settings made using the following APIs: + * - esp_wifi_get_auto_connect, + * - esp_wifi_set_protocol, + * - esp_wifi_set_config related + * - esp_wifi_set_mode + * + * @return + * - ESP_OK: succeed + * - ESP_ERR_WIFI_NOT_INIT: WiFi is not initialized by eps_wifi_init + */ +esp_err_t esp_wifi_restore(void); + /** * @brief Connect the ESP32 WiFi station to the AP. * @@ -312,6 +328,8 @@ esp_err_t esp_wifi_sta_get_ap_info(wifi_ap_record_t *ap_info); /** * @brief Set current power save type * + * @attention Default power save type is WIFI_PS_NONE. + * * @param type power save type * * @return ESP_ERR_WIFI_NOT_SUPPORT: not supported yet @@ -321,6 +339,8 @@ esp_err_t esp_wifi_set_ps(wifi_ps_type_t type); /** * @brief Get current power save type * + * @attention Default power save type is WIFI_PS_NONE. + * * @param[out] type: store current power save type * * @return ESP_ERR_WIFI_NOT_SUPPORT: not supported yet diff --git a/components/esp32/include/esp_wifi_internal.h b/components/esp32/include/esp_wifi_internal.h index 2015b5063d..09813bfa1b 100644 --- a/components/esp32/include/esp_wifi_internal.h +++ b/components/esp32/include/esp_wifi_internal.h @@ -43,10 +43,9 @@ extern "C" { /** * @brief get whether the wifi driver is allowed to transmit data or not * - * @param none - * - * @return true : upper layer should stop to transmit data to wifi driver - * @return false : upper layer can transmit data to wifi driver + * @return + * - true : upper layer should stop to transmit data to wifi driver + * - false : upper layer can transmit data to wifi driver */ bool esp_wifi_internal_tx_is_stop(void); @@ -54,8 +53,6 @@ bool esp_wifi_internal_tx_is_stop(void); * @brief free the rx buffer which allocated by wifi driver * * @param void* buffer: rx buffer pointer - * - * @return nonoe */ void esp_wifi_internal_free_rx_buffer(void* buffer); @@ -78,7 +75,6 @@ int esp_wifi_internal_tx(wifi_interface_t wifi_if, void *buffer, u16_t len); * @brief The WiFi RX callback function * * Each time the WiFi need to forward the packets to high layer, the callback function will be called - * */ typedef esp_err_t (*wifi_rxcb_t)(void *buffer, uint16_t len, void *eb); @@ -90,18 +86,18 @@ typedef esp_err_t (*wifi_rxcb_t)(void *buffer, uint16_t len, void *eb); * @param wifi_interface_t ifx : interface * @param wifi_rxcb_t fn : WiFi RX callback * - * @return ESP_OK : succeed - * @return others : fail + * @return + * - ESP_OK : succeed + * - others : fail */ esp_err_t esp_wifi_internal_reg_rxcb(wifi_interface_t ifx, wifi_rxcb_t fn); /** * @brief Notify WIFI driver that the station got ip successfully * - * @param none - * - * @return ESP_OK : succeed - * @return others : fail + * @return + * - ESP_OK : succeed + * - others : fail */ esp_err_t esp_wifi_internal_set_sta_ip(void); diff --git a/components/esp32/include/esp_wifi_types.h b/components/esp32/include/esp_wifi_types.h index fb19aa8fc3..c5dd021fe7 100644 --- a/components/esp32/include/esp_wifi_types.h +++ b/components/esp32/include/esp_wifi_types.h @@ -21,6 +21,7 @@ #include "rom/queue.h" #include "esp_err.h" #include "esp_wifi_types.h" +#include "esp_interface.h" #ifdef __cplusplus extern "C" { @@ -34,11 +35,10 @@ typedef enum { WIFI_MODE_MAX } wifi_mode_t; -typedef enum { - WIFI_IF_STA = 0, /**< ESP32 station interface */ - WIFI_IF_AP, /**< ESP32 soft-AP interface */ - WIFI_IF_MAX -} wifi_interface_t; +typedef esp_interface_t wifi_interface_t; + +#define WIFI_IF_STA ESP_IF_WIFI_STA +#define WIFI_IF_AP ESP_IF_WIFI_AP typedef enum { WIFI_COUNTRY_CN = 0, /**< country China, channel range [1, 14] */ @@ -114,8 +114,6 @@ typedef struct { typedef enum { WIFI_PS_NONE, /**< No power save */ WIFI_PS_MODEM, /**< Modem power save */ - WIFI_PS_LIGHT, /**< Light power save */ - WIFI_PS_MAC, /**< MAC power save */ } wifi_ps_type_t; #define WIFI_PROTOCOL_11B 1 diff --git a/components/esp32/include/esp_wpa2.h b/components/esp32/include/esp_wpa2.h new file mode 100644 index 0000000000..1857d19a16 --- /dev/null +++ b/components/esp32/include/esp_wpa2.h @@ -0,0 +1,166 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#ifndef ESP_WPA2_H +#define ESP_WPA2_H + +#include "esp_err.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @brief Enable wpa2 enterprise authentication. + * + * @attention wpa2 enterprise authentication can only be used when ESP32 station is enabled. + * wpa2 enterprise authentication can only support TLS, PEAP-MSCHAPv2 and TTLS-MSCHAPv2 method. + * + * @return ESP_ERR_WIFI_OK: succeed. + * ESP_ERR_WIFI_NO_MEM: fail(internal memory malloc fail) + */ +esp_err_t esp_wifi_sta_wpa2_ent_enable(void); + +/** + * @brief Disable wpa2 enterprise authentication. + * + * @attention wpa2 enterprise authentication can only be used when ESP32 station is enabled. + * wpa2 enterprise authentication can only support TLS, PEAP-MSCHAPv2 and TTLS-MSCHAPv2 method. + * + * @return ESP_ERR_WIFI_OK: succeed. + */ +esp_err_t esp_wifi_sta_wpa2_ent_disable(void); + +/** + * @brief Set username for PEAP/TTLS method. + * + * @attention The API only passes the parameter username to the global pointer variable in wpa2 enterprise module. + * + * @param username: point to address where stores the username; + * len: length of username, limited to 1~127 + * + * @return ESP_ERR_WIFI_OK: succeed + * ESP_ERR_WIFI_ARG: fail(len <= 0 or len >= 128) + * ESP_ERR_WIFI_NO_MEM: fail(internal memory malloc fail) + */ +esp_err_t esp_wifi_sta_wpa2_ent_set_username(unsigned char *username, int len); + +/** + * @brief Clear username for PEAP/TTLS method. + */ +void esp_wifi_sta_wpa2_ent_clear_username(void); + +/** + * @brief Set password for PEAP/TTLS method.. + * + * @attention The API only passes the parameter password to the global pointer variable in wpa2 enterprise module. + * + * @param password: point to address where stores the password; + * len: length of password(len > 0) + * + * @return ESP_ERR_WIFI_OK: succeed + * ESP_ERR_WIFI_ARG: fail(len <= 0) + * ESP_ERR_WIFI_NO_MEM: fail(internal memory malloc fail) + */ +esp_err_t esp_wifi_sta_wpa2_ent_set_password(unsigned char *password, int len); + +/** + * @brief Clear password for PEAP/TTLS method.. + */ +void esp_wifi_sta_wpa2_ent_clear_password(void); + +/** + * @brief Set new password for MSCHAPv2 method.. + * + * @attention The API only passes the parameter password to the global pointer variable in wpa2 enterprise module. + * The new password is used to substitute the old password when eap-mschapv2 failure request message with error code ERROR_PASSWD_EXPIRED is received. + * + * @param password: point to address where stores the password; + * len: length of password + * + * @return ESP_ERR_WIFI_OK: succeed + * ESP_ERR_WIFI_ARG: fail(len <= 0) + * ESP_ERR_WIFI_NO_MEM: fail(internal memory malloc fail) + */ + +esp_err_t esp_wifi_sta_wpa2_ent_set_new_password(unsigned char *password, int len); + +/** + * @brief Clear new password for MSCHAPv2 method.. + */ +void esp_wifi_sta_wpa2_ent_clear_new_password(void); + +/** + * @brief Set CA certificate for PEAP/TTLS method. + * + * @attention The API only passes the parameter ca_cert to the global pointer variable in wpa2 enterprise module. + * The ca_cert should be zero terminated. + * + * @param ca_cert: point to address where stores the CA certificate; + * len: length of ca_cert + * + * @return ESP_ERR_WIFI_OK: succeed + */ +esp_err_t esp_wifi_sta_wpa2_ent_set_ca_cert(unsigned char *ca_cert, int len); + +/** + * @brief Clear CA certificate for PEAP/TTLS method. + */ +void esp_wifi_sta_wpa2_ent_clear_ca_cert(void); + +/** + * @brief Set client certificate and key. + * + * @attention The API only passes the parameter client_cert, private_key and private_key_passwd to the global pointer variable in wpa2 enterprise module. + * The client_cert, private_key and private_key_passwd should be zero terminated. + * + * @param client_cert: point to address where stores the client certificate; + * client_cert_len: length of client certificate; + * private_key: point to address where stores the private key; + * private_key_len: length of private key, limited to 1~2048; + * private_key_password: point to address where stores the private key password; + * private_key_password_len: length of private key password; + * + * @return ESP_ERR_WIFI_OK: succeed + */ +esp_err_t esp_wifi_sta_wpa2_ent_set_cert_key(unsigned char *client_cert, int client_cert_len, unsigned char *private_key, int private_key_len, unsigned char *private_key_passwd, int private_key_passwd_len); + +/** + * @brief Clear client certificate and key. + */ +void esp_wifi_sta_wpa2_ent_clear_cert_key(void); + +/** + * @brief Set wpa2 enterprise certs time check(disable or not). + * + * @param true: disable wpa2 enterprise certs time check + * false: enable wpa2 enterprise certs time check + * + * @return ESP_OK: succeed + */ +esp_err_t esp_wifi_sta_wpa2_ent_set_disable_time_check(bool disable); + +/** + * @brief Get wpa2 enterprise certs time check(disable or not). + * + * @param disable: store disable value + * + * @return ESP_OK: succeed + */ +esp_err_t esp_wifi_sta_wpa2_ent_get_disable_time_check(bool *disable); + +#ifdef __cplusplus +} +#endif +#endif diff --git a/components/esp32/include/hwcrypto/sha.h b/components/esp32/include/hwcrypto/sha.h index a165c46c1c..921f597fdd 100644 --- a/components/esp32/include/hwcrypto/sha.h +++ b/components/esp32/include/hwcrypto/sha.h @@ -1,246 +1,203 @@ -/* - * ESP32 hardware accelerated SHA1/256/512 implementation - * based on mbedTLS FIPS-197 compliant version. - * - * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved - * Additions Copyright (C) 2016, Espressif Systems (Shanghai) PTE Ltd - * SPDX-License-Identifier: Apache-2.0 - * - * Licensed under the Apache License, Version 2.0 (the "License"); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - */ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. #ifndef _ESP_SHA_H_ #define _ESP_SHA_H_ #include "rom/sha.h" - #include "esp_types.h" +/** @brief Low-level support functions for the hardware SHA engine + * + * @note If you're looking for a SHA API to use, try mbedtls component + * mbedtls/shaXX.h. That API supports hardware acceleration. + * + * The API in this header provides some building blocks for implementing a + * full SHA API such as the one in mbedtls, and also a basic SHA function esp_sha(). + * + * Some technical details about the hardware SHA engine: + * + * - SHA accelerator engine calculates one digest at a time, per SHA + * algorithm type. It initialises and maintains the digest state + * internally. It is possible to read out an in-progress SHA digest + * state, but it is not possible to restore a SHA digest state + * into the engine. + * + * - The memory block SHA_TEXT_BASE is shared between all SHA digest + * engines, so all engines must be idle before this memory block is + * modified. + * + */ + #ifdef __cplusplus extern "C" { #endif -/** - * \brief SHA-1 context structure - */ -typedef struct { - /* both types defined in rom/sha.h */ - SHA_CTX context; - enum SHA_TYPE context_type; -} esp_sha_context; +/* Defined in rom/sha.h */ +typedef enum SHA_TYPE esp_sha_type; -/** - * \brief Lock access to SHA hardware unit +/** @brief Calculate SHA1 or SHA2 sum of some data, using hardware SHA engine * - * SHA hardware unit can only be used by one - * consumer at a time. + * @note For more versatile SHA calculations, where data doesn't need + * to be passed all at once, try the mbedTLS mbedtls/shaX.h APIs. The + * hardware-accelerated mbedTLS implementation is also faster when + * hashing large amounts of data. * - * esp_sha_xxx API calls automatically manage locking & unlocking of - * hardware, this function is only needed if you want to call - * ets_sha_xxx functions directly. - */ -void esp_sha_acquire_hardware( void ); - -/** - * \brief Unlock access to SHA hardware unit + * @note It is not necessary to lock any SHA hardware before calling + * this function, thread safety is managed internally. * - * esp_sha_xxx API calls automatically manage locking & unlocking of - * hardware, this function is only needed if you want to call - * ets_sha_xxx functions directly. - */ -void esp_sha_release_hardware( void ); - -/** - * \brief Initialize SHA-1 context + * @note If a TLS connection is open then this function may block + * indefinitely waiting for a SHA engine to become available. Use the + * mbedTLS SHA API to avoid this problem. * - * \param ctx SHA-1 context to be initialized - */ -void esp_sha1_init( esp_sha_context *ctx ); - -/** - * \brief Clear SHA-1 context + * @param sha_type SHA algorithm to use. * - * \param ctx SHA-1 context to be cleared - */ -void esp_sha1_free( esp_sha_context *ctx ); - -/** - * \brief Clone (the state of) a SHA-1 context + * @param input Input data buffer. * - * \param dst The destination context - * \param src The context to be cloned - */ -void esp_sha1_clone( esp_sha_context *dst, const esp_sha_context *src ); - -/** - * \brief SHA-1 context setup + * @param ilen Length of input data in bytes. * - * \param ctx context to be initialized + * @param output Buffer for output SHA digest. Output is 20 bytes for + * sha_type SHA1, 32 bytes for sha_type SHA2_256, 48 bytes for + * sha_type SHA2_384, 64 bytes for sha_type SHA2_512. */ -void esp_sha1_start( esp_sha_context *ctx ); +void esp_sha(esp_sha_type sha_type, const unsigned char *input, size_t ilen, unsigned char *output); -/** - * \brief SHA-1 process buffer +/* @brief Begin to execute a single SHA block operation * - * \param ctx SHA-1 context - * \param input buffer holding the data - * \param ilen length of the input data - */ -void esp_sha1_update( esp_sha_context *ctx, const unsigned char *input, size_t ilen ); - -/** - * \brief SHA-1 final digest + * @note This is a piece of a SHA algorithm, rather than an entire SHA + * algorithm. * - * \param ctx SHA-1 context - * \param output SHA-1 checksum result - */ -void esp_sha1_finish( esp_sha_context *ctx, unsigned char output[20] ); - -/** - * \brief Calculate SHA-1 of input buffer + * @note Call esp_sha_try_lock_engine() before calling this + * function. Do not call esp_sha_lock_memory_block() beforehand, this + * is done inside the function. * - * \param input buffer holding the data - * \param ilen length of the input data - * \param output SHA-1 checksum result - */ -void esp_sha1( const unsigned char *input, size_t ilen, unsigned char output[20] ); - -/** - * \brief SHA-256 context structure - */ - -/** - * \brief Initialize SHA-256 context + * @param sha_type SHA algorithm to use. * - * \param ctx SHA-256 context to be initialized - */ -void esp_sha256_init( esp_sha_context *ctx ); - -/** - * \brief Clear SHA-256 context + * @param data_block Pointer to block of data. Block size is + * determined by algorithm (SHA1/SHA2_256 = 64 bytes, + * SHA2_384/SHA2_512 = 128 bytes) * - * \param ctx SHA-256 context to be cleared - */ -void esp_sha256_free( esp_sha_context *ctx ); - -/** - * \brief Clone (the state of) a SHA-256 context + * @param is_first_block If this parameter is true, the SHA state will + * be initialised (with the initial state of the given SHA algorithm) + * before the block is calculated. If false, the existing state of the + * SHA engine will be used. * - * \param dst The destination context - * \param src The context to be cloned + * @return As a performance optimisation, this function returns before + * the SHA block operation is complete. Both this function and + * esp_sha_read_state() will automatically wait for any previous + * operation to complete before they begin. If using the SHA registers + * directly in another way, call esp_sha_wait_idle() after calling this + * function but before accessing the SHA registers. */ -void esp_sha256_clone( esp_sha_context *dst, const esp_sha_context *src ); +void esp_sha_block(esp_sha_type sha_type, const void *data_block, bool is_first_block); -/** - * \brief SHA-256 context setup +/** @brief Read out the current state of the SHA digest loaded in the engine. * - * \param ctx context to be initialized - * \param is224 0 = use SHA256, 1 = use SHA224 - */ -void esp_sha256_start( esp_sha_context *ctx, int is224 ); - -/** - * \brief SHA-256 process buffer + * @note This is a piece of a SHA algorithm, rather than an entire SHA algorithm. * - * \param ctx SHA-256 context - * \param input buffer holding the data - * \param ilen length of the input data - */ -void esp_sha256_update( esp_sha_context *ctx, const unsigned char *input, size_t ilen ); - -/** - * \brief SHA-256 final digest + * @note Call esp_sha_try_lock_engine() before calling this + * function. Do not call esp_sha_lock_memory_block() beforehand, this + * is done inside the function. * - * \param ctx SHA-256 context - * \param output SHA-224/256 checksum result - */ -void esp_sha256_finish( esp_sha_context *ctx, unsigned char output[32] ); - -/** - * \brief Calculate SHA-256 of input buffer + * If the SHA suffix padding block has been executed already, the + * value that is read is the SHA digest (in big endian + * format). Otherwise, the value that is read is an interim SHA state. * - * \param input buffer holding the data - * \param ilen length of the input data - * \param output SHA-224/256 checksum result - * \param is224 0 = use SHA256, 1 = use SHA224 - */ -void esp_sha256( const unsigned char *input, size_t ilen, unsigned char output[32], int is224 ); - -// - -/** - * \brief SHA-512 context structure - */ - -/** - * \brief Initialize SHA-512 context + * @note If sha_type is SHA2_384, only 48 bytes of state will be read. + * This is enough for the final SHA2_384 digest, but if you want the + * interim SHA-384 state (to continue digesting) then pass SHA2_512 instead. + * + * @param sha_type SHA algorithm in use. + * + * @param state Pointer to a memory buffer to hold the SHA state. Size + * is 20 bytes (SHA1), 32 bytes (SHA2_256), 48 bytes (SHA2_384) or 64 bytes (SHA2_512). * - * \param ctx SHA-512 context to be initialized */ -void esp_sha512_init( esp_sha_context *ctx ); +void esp_sha_read_digest_state(esp_sha_type sha_type, void *digest_state); /** - * \brief Clear SHA-512 context + * @brief Obtain exclusive access to a particular SHA engine * - * \param ctx SHA-512 context to be cleared + * @param sha_type Type of SHA engine to use. + * + * Blocks until engine is available. Note: Can block indefinitely + * while a TLS connection is open, suggest using + * esp_sha_try_lock_engine() and failing over to software SHA. */ -void esp_sha512_free( esp_sha_context *ctx ); +void esp_sha_lock_engine(esp_sha_type sha_type); /** - * \brief Clone (the state of) a SHA-512 context + * @brief Try and obtain exclusive access to a particular SHA engine * - * \param dst The destination context - * \param src The context to be cloned + * @param sha_type Type of SHA engine to use. + * + * @return Returns true if the SHA engine is locked for exclusive + * use. Call esp_sha_unlock_sha_engine() when done. Returns false if + * the SHA engine is already in use, caller should use software SHA + * algorithm for this digest. */ -void esp_sha512_clone( esp_sha_context *dst, const esp_sha_context *src ); +bool esp_sha_try_lock_engine(esp_sha_type sha_type); /** - * \brief SHA-512 context setup + * @brief Unlock an engine previously locked with esp_sha_lock_engine() or esp_sha_try_lock_engine() * - * \param ctx context to be initialized - * \param is384 0 = use SHA512, 1 = use SHA384 + * @param sha_type Type of engine to release. */ -void esp_sha512_start( esp_sha_context *ctx, int is384 ); +void esp_sha_unlock_engine(esp_sha_type sha_type); /** - * \brief SHA-512 process buffer + * @brief Acquire exclusive access to the SHA shared memory block at SHA_TEXT_BASE * - * \param ctx SHA-512 context - * \param input buffer holding the data - * \param ilen length of the input data + * This memory block is shared across all the SHA algorithm types. + * + * Caller should have already locked a SHA engine before calling this function. + * + * Note that it is possible to obtain exclusive access to the memory block even + * while it is in use by the SHA engine. Caller should use esp_sha_wait_idle() + * to ensure the SHA engine is not reading from the memory block in hardware. + * + * @note You do not need to lock the memory block before calling esp_sha_block() or esp_sha_read_digest_state(), these functions handle memory block locking internally. + * + * Call esp_sha_unlock_memory_block() when done. */ -void esp_sha512_update( esp_sha_context *ctx, const unsigned char *input, size_t ilen ); +void esp_sha_lock_memory_block(void); /** - * \brief SHA-512 final digest + * @brief Release exclusive access to the SHA register memory block at SHA_TEXT_BASE * - * \param ctx SHA-512 context - * \param output SHA-384/512 checksum result - */ -void esp_sha512_finish( esp_sha_context *ctx, unsigned char output[64] ); - -/** - * \brief Calculate SHA-512 of input buffer. + * Caller should have already locked a SHA engine before calling this function. * - * \param input buffer holding the data - * \param ilen length of the input data - * \param output SHA-384/512 checksum result - * \param is384 0 = use SHA512, 1 = use SHA384 + * Call following esp_sha_lock_memory_block(). */ -void esp_sha512( const unsigned char *input, size_t ilen, unsigned char output[64], int is384 ); +void esp_sha_unlock_memory_block(void); -// +/** @brief Wait for the SHA engine to finish any current operation + * + * @note This function does not ensure exclusive access to any SHA + * engine. Caller should use esp_sha_try_lock_engine() and + * esp_sha_lock_memory_block() as required. + * + * @note Functions declared in this header file wait for SHA engine + * completion automatically, so you don't need to use this API for + * these. However if accessing SHA registers directly, you will need + * to call this before accessing SHA registers if using the + * esp_sha_block() function. + * + * @note This function busy-waits, so wastes CPU resources. + * Best to delay calling until you are about to need it. + * + */ +void esp_sha_wait_idle(void); #ifdef __cplusplus } diff --git a/components/esp32/include/rom/ets_sys.h b/components/esp32/include/rom/ets_sys.h index c412c9b41f..690691675a 100644 --- a/components/esp32/include/rom/ets_sys.h +++ b/components/esp32/include/rom/ets_sys.h @@ -605,6 +605,14 @@ void intr_matrix_set(int cpu_no, uint32_t model_num, uint32_t intr_num); #define ETS_MEM_BAR() asm volatile ( "" : : : "memory" ) +typedef enum { + OK = 0, + FAIL, + PENDING, + BUSY, + CANCEL, +} STATUS; + /** * @} */ diff --git a/components/esp32/include/rom/sha.h b/components/esp32/include/rom/sha.h index 8082a394c9..5dd9c9981f 100644 --- a/components/esp32/include/rom/sha.h +++ b/components/esp32/include/rom/sha.h @@ -1,9 +1,10 @@ /* ROM functions for hardware SHA support. - It is not recommended to use these functions directly, - use the wrapper functions in hwcrypto/sha.h instead. - + It is not recommended to use these functions directly. If using + them from esp-idf then use the esp_sha_lock_engine() and + esp_sha_lock_memory_block() functions in hwcrypto/sha.h to ensure + exclusive access. */ // Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD // @@ -38,6 +39,8 @@ enum SHA_TYPE { SHA2_256, SHA2_384, SHA2_512, + + SHA_INVALID = -1, }; diff --git a/components/esp32/include/rom/spi_flash.h b/components/esp32/include/rom/spi_flash.h index 1f14c6617a..32f018477a 100644 --- a/components/esp32/include/rom/spi_flash.h +++ b/components/esp32/include/rom/spi_flash.h @@ -384,7 +384,8 @@ SpiFlashOpResult SPIParamCfg(uint32_t deviceId, uint32_t chip_size, uint32_t blo SpiFlashOpResult SPIEraseChip(void); /** - * @brief Erase a block of flash. + * @brief Erase a 32KB block of flash + * Uses SPI flash command 52h. * Please do not call this function in SDK. * * @param uint32_t block_num : Which block to erase. @@ -411,6 +412,12 @@ SpiFlashOpResult SPIEraseSector(uint32_t sector_num); * @brief Erase some sectors. * Please do not call this function in SDK. * + * @note If calling this function, first set + * g_rom_flashchip.block_size = 32768; or call SPIParamCfg() + * with appropriate parameters. This is due to a ROM bug, the + * block erase command in use is a 32KB erase but after reset + * the block_size field is incorrectly set to 65536. + * * @param uint32_t start_addr : Start addr to erase, should be sector aligned. * * @param uint32_t area_len : Length to erase, should be sector aligned. diff --git a/components/esp32/include/rom/uart.h b/components/esp32/include/rom/uart.h index 8e3125133c..aa3cf59217 100644 --- a/components/esp32/include/rom/uart.h +++ b/components/esp32/include/rom/uart.h @@ -17,6 +17,7 @@ #include "esp_types.h" #include "esp_attr.h" +#include "ets_sys.h" #ifdef __cplusplus extern "C" { diff --git a/components/esp32/include/soc/cpu.h b/components/esp32/include/soc/cpu.h index ee2907493e..4457c81a22 100644 --- a/components/esp32/include/soc/cpu.h +++ b/components/esp32/include/soc/cpu.h @@ -51,7 +51,10 @@ static inline void cpu_write_itlb(unsigned vpn, unsigned attr) asm volatile ("witlb %1, %0; isync\n" :: "r" (vpn), "r" (attr)); } -/* Make page 0 access raise an exception. +/** + * @brief Configure memory region protection + * + * Make page 0 access raise an exception. * Also protect some other unused pages so we can catch weirdness. * Useful attribute values: * 0 — cached, RW @@ -70,9 +73,7 @@ static inline void cpu_configure_region_protection() cpu_write_itlb(0x20000000, 0); } - - -/* +/** * @brief Set CPU frequency to the value defined in menuconfig * * Called from cpu_start.c, not intended to be called from other places. @@ -81,4 +82,16 @@ static inline void cpu_configure_region_protection() */ void esp_set_cpu_freq(void); +/** + * @brief Stall CPU using RTC controller + * @param cpu_id ID of the CPU to stall (0 = PRO, 1 = APP) + */ +void esp_cpu_stall(int cpu_id); + +/** + * @brief Un-stall CPU using RTC controller + * @param cpu_id ID of the CPU to un-stall (0 = PRO, 1 = APP) + */ +void esp_cpu_unstall(int cpu_id); + #endif diff --git a/components/esp32/include/soc/dport_reg.h b/components/esp32/include/soc/dport_reg.h index 1be0fdee14..f84346717c 100644 --- a/components/esp32/include/soc/dport_reg.h +++ b/components/esp32/include/soc/dport_reg.h @@ -94,6 +94,16 @@ #define DPORT_PERI_RST_EN_V 0xFFFFFFFF #define DPORT_PERI_RST_EN_S 0 +/* The following bits apply to DPORT_PERI_CLK_EN_REG, DPORT_PERI_RST_EN_REG + */ +#define DPORT_PERI_EN_AES (1<<0) +#define DPORT_PERI_EN_SHA (1<<1) +#define DPORT_PERI_EN_RSA (1<<2) +/* NB: Secure boot reset will hold SHA & AES in reset */ +#define DPORT_PERI_EN_SECUREBOOT (1<<3) +/* NB: Digital signature reset will hold AES & RSA in reset */ +#define DPORT_PERI_EN_DIGITAL_SIGNATURE (1<<4) + #define DPORT_WIFI_BB_CFG_REG (DR_REG_DPORT_BASE + 0x024) /* DPORT_WIFI_BB_CFG : R/W ;bitpos:[31:0] ;default: 32'h0 ; */ /*description: */ diff --git a/components/esp32/include/soc/emac_ex_reg.h b/components/esp32/include/soc/emac_ex_reg.h new file mode 100644 index 0000000000..9b7c590966 --- /dev/null +++ b/components/esp32/include/soc/emac_ex_reg.h @@ -0,0 +1,101 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +#ifndef _EMAC_EX_H_ +#define _EMAC_EX_H_ + +#ifdef __cplusplus +extern "C" { +#endif + +#include "soc.h" +#define REG_EMAC_EX_BASE (DR_REG_EMAC_BASE + 0x800) + +#define EMAC_EX_CLKOUT_CONF_REG (REG_EMAC_EX_BASE + 0x0000) +#define EMAC_EX_CLK_OUT_DLY_NUM 0x00000003 +#define EMAC_EX_CLK_OUT_DLY_NUM_S 8 +#define EMAC_EX_CLK_OUT_H_DIV_NUM 0x0000000F +#define EMAC_EX_CLK_OUT_H_DIV_NUM_S 4 +#define EMAC_EX_CLK_OUT_DIV_NUM 0x0000000F +#define EMAC_EX_CLK_OUT_DIV_NUM_S 0 + +#define EMAC_EX_OSCCLK_CONF_REG (REG_EMAC_EX_BASE + 0x0004) +#define EMAC_EX_OSC_CLK_SEL (BIT(24)) +#define EMAC_EX_OSC_CLK_SEL_S 24 +#define EMAC_EX_OSC_H_DIV_NUM_100M 0x0000003F +#define EMAC_EX_OSC_H_DIV_NUM_100M_S 18 +#define EMAC_EX_OSC_DIV_NUM_100M 0x0000003F +#define EMAC_EX_OSC_DIV_NUM_100M_S 12 +#define EMAC_EX_OSC_H_DIV_NUM_10M 0x0000003F +#define EMAC_EX_OSC_H_DIV_NUM_10M_S 6 +#define EMAC_EX_OSC_DIV_NUM_10M 0x0000003F +#define EMAC_EX_OSC_DIV_NUM_10M_S 0 + +#define EMAC_EX_CLK_CTRL_REG (REG_EMAC_EX_BASE + 0x0008) +#define EMAC_EX_CLK_EN (BIT(5)) +#define EMAC_EX_CLK_EN_S 5 +#define EMAC_EX_MII_CLK_RX_EN (BIT(4)) +#define EMAC_EX_MII_CLK_RX_EN_S 4 +#define EMAC_EX_MII_CLK_TX_EN (BIT(3)) +#define EMAC_EX_MII_CLK_TX_EN_S 3 +#define EMAC_EX_RX_125_CLK_EN (BIT(2)) +#define EMAC_EX_RX_125_CLK_EN_S 2 +#define EMAC_EX_INT_OSC_EN (BIT(1)) +#define EMAC_EX_INT_OSC_EN_S 1 +#define EMAC_EX_EXT_OSC_EN (BIT(0)) +#define EMAC_EX_EXT_OSC_EN_S 0 + +#define EMAC_EX_PHYINF_CONF_REG (REG_EMAC_EX_BASE + 0x000c) +#define EMAC_EX_TX_ERR_OUT_EN (BIT(20)) +#define EMAC_EX_TX_ERR_OUT_EN_S 20 +#define EMAC_EX_SCR_SMI_DLY_RX_SYNC (BIT(19)) +#define EMAC_EX_SCR_SMI_DLY_RX_SYNC_S 19 +#define EMAC_EX_PMT_CTRL_EN (BIT(18)) +#define EMAC_EX_PMT_CTRL_EN_S 18 +#define EMAC_EX_SBD_CLK_GATING_EN (BIT(17)) +#define EMAC_EX_SBD_CLK_GATING_EN_S 17 +#define EMAC_EX_SS_MODE (BIT(16)) +#define EMAC_EX_SS_MODE_S 16 +#define EMAC_EX_PHY_INTF_SEL 0x00000007 +#define EMAC_EX_PHY_INTF_SEL_S 13 +#define EMAC_EX_REVMII_PHY_ADDR 0x0000001F +#define EMAC_EX_REVMII_PHY_ADDR_S 8 +#define EMAC_EX_CORE_PHY_ADDR 0x0000001F +#define EMAC_EX_CORE_PHY_ADDR_S 3 +#define EMAC_EX_SBD_FLOWCTRL (BIT(2)) +#define EMAC_EX_SBD_FLOWCTRL_S 2 +#define EMAC_EX_EXT_REVMII_RX_CLK_SEL (BIT(1)) +#define EMAC_EX_EXT_REVMII_RX_CLK_SEL_S 1 +#define EMAC_EX_INT_REVMII_RX_CLK_SEL (BIT(0)) +#define EMAC_EX_INT_REVMII_RX_CLK_SEL_S 0 + +#define EMAC_EX_PHY_INTF_RMII 4 + +#define EMAC_EX_EMAC_PD_SEL_REG (REG_EMAC_EX_BASE + 0x0010) +#define EMAC_EX_RAM_PD_EN 0x00000003 +#define EMAC_EX_RAM_PD_EN_S 0 + +#define EMAC_EX_DATE_REG (REG_EMAC_EX_BASE + 0x00fc) +#define EMAC_EX_DATE 0xFFFFFFFF +#define EMAC_EX_DATE_S 0 +#define EMAC_EX_DATE_VERSION 0x16042200 + +#define EMAC_CLK_EN_REG 0x3ff000cc +#define EMAC_CLK_EN (BIT(14)) + +#ifdef __cplusplus +} +#endif + +#endif + diff --git a/components/esp32/include/soc/emac_reg_v2.h b/components/esp32/include/soc/emac_reg_v2.h new file mode 100644 index 0000000000..6ab1afe033 --- /dev/null +++ b/components/esp32/include/soc/emac_reg_v2.h @@ -0,0 +1,714 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#ifndef _EMAC_H_ +#define _EMAC_H_ + +#ifdef __cplusplus +extern "C" { +#endif + +#include "soc.h" +#define REG_EMAC_BASE DR_REG_EMAC_BASE + +#define EMAC_DMABUSMODE_REG (REG_EMAC_BASE + 0x0000) +#define EMAC_DMAREBINCRBURST (BIT(31)) +#define EMAC_DMAREBINCRBURST_S 31 +#define EMAC_DMACHANNELPRIOWT 0x00000003 +#define EMAC_DMACHANNELPRIOWT_S 28 +#define EMAC_DMATXRXPRIO (BIT(27)) +#define EMAC_DMATXRXPRIO_S 27 +#define EMAC_DMAMIXEDBURST (BIT(26)) +#define EMAC_DMAMIXEDBURST_S 26 +#define EMAC_DMAADDRALIBEA (BIT(25)) +#define EMAC_DMAADDRALIBEA_S 25 +#define EMAC_PBLX8_MODE (BIT(24)) +#define EMAC_PBLX8_MODE_S 24 +#define EMAC_USE_SEP_PBL (BIT(23)) +#define EMAC_USE_SEP_PBL_S 23 +#define EMAC_RX_DMA_PBL 0x0000003F +#define EMAC_RX_DMA_PBL_S 17 +#define EMAC_FIXED_BURST (BIT(16)) +#define EMAC_FIXED_BURST_S 16 +#define EMAC_PRI_RATIO 0x00000003 +#define EMAC_PRI_RATIO_S 14 +#define EMAC_PROG_BURST_LEN 0x0000003F +#define EMAC_PROG_BURST_LEN_S 8 +#define EMAC_ALT_DESC_SIZE (BIT(7)) +#define EMAC_ALT_DESC_SIZE_S 7 +#define EMAC_DESC_SKIP_LEN 0x0000001F +#define EMAC_DESC_SKIP_LEN_S 2 +#define EMAC_DMA_ARB_SCH (BIT(1)) +#define EMAC_DMA_ARB_SCH_S 1 +#define EMAC_SW_RST (BIT(0)) +#define EMAC_SW_RST_S 0 + +#define EMAC_DMATXPOLLDEMAND_REG (REG_EMAC_BASE + 0x0004) +#define EMAC_TRANS_POLL_DEMAND 0xFFFFFFFF +#define EMAC_TRANS_POLL_DEMAND_S 0 + +#define EMAC_DMARXPOLLDEMAND_REG (REG_EMAC_BASE + 0x0008) +#define EMAC_RECV_POLL_DEMAND 0xFFFFFFFF +#define EMAC_RECV_POLL_DEMAND_S 0 + +#define EMAC_DMARXBASEADDR_REG (REG_EMAC_BASE + 0x000C) +#define EMAC_START_RECV_LIST 0xFFFFFFFF +#define EMAC_START_RECV_LIST_S 0 + +#define EMAC_DMATXBASEADDR_REG (REG_EMAC_BASE + 0x0010) +#define EMAC_START_TRANS_LIST 0xFFFFFFFF +#define EMAC_START_TRANS_LIST_S 0 + +#define EMAC_DMASTATUS_REG (REG_EMAC_BASE + 0x0014) +#define EMAC_GMAC_LPI_INT (BIT(30)) +#define EMAC_GMAC_LPI_INT_S 30 +#define EMAC_TS_TRI_INT (BIT(29)) +#define EMAC_TS_TRI_INT_S 29 +#define EMAC_GMAC_PMT_INT (BIT(28)) +#define EMAC_GMAC_PMT_INT_S 28 +#define EMAC_GMAC_MMC_INT (BIT(27)) +#define EMAC_GMAC_MMC_INT_S 27 +#define EMAC_GMAC_LINE_INF_INT (BIT(26)) +#define EMAC_GMAC_LINE_INF_INT_S 26 +#define EMAC_ERROR_BITS 0x00000007 +#define EMAC_ERROR_BITS_S 23 +#define EMAC_TRANS_PROC_STATE 0x00000007 +#define EMAC_TRANS_PROC_STATE_S 20 +#define EMAC_RECV_PROC_STATE 0x00000007 +#define EMAC_RECV_PROC_STATE_S 17 +#define EMAC_NORM_INT_SUMM (BIT(16)) +#define EMAC_NORM_INT_SUMM_S 16 +#define EMAC_ABN_INT_SUMM (BIT(15)) +#define EMAC_ABN_INT_SUMM_S 15 +#define EMAC_EARLY_RECV_INT (BIT(14)) +#define EMAC_EARLY_RECV_INT_S 14 +#define EMAC_FATAL_BUS_ERR_INT (BIT(13)) +#define EMAC_FATAL_BUS_ERR_INT_S 13 +#define EMAC_EARLY_TRANS_INT (BIT(10)) +#define EMAC_EARLY_TRANS_INT_S 10 +#define EMAC_RECV_WDT_TO (BIT(9)) +#define EMAC_RECV_WDT_TO_S 9 +#define EMAC_RECV_PROC_STOP (BIT(8)) +#define EMAC_RECV_PROC_STOP_S 8 +#define EMAC_RECV_BUF_UNAVAIL (BIT(7)) +#define EMAC_RECV_BUF_UNAVAIL_S 7 +#define EMAC_RECV_INT (BIT(6)) +#define EMAC_RECV_INT_S 6 +#define EMAC_TRANS_UNDFLOW (BIT(5)) +#define EMAC_TRANS_UNDFLOW_S 5 +#define EMAC_RECV_OVFLOW (BIT(4)) +#define EMAC_RECV_OVFLOW_S 4 +#define EMAC_TRANS_JABBER_TO (BIT(3)) +#define EMAC_TRANS_JABBER_TO_S 3 +#define EMAC_TRANS_BUF_UNAVAIL (BIT(2)) +#define EMAC_TRANS_BUF_UNAVAIL_S 2 +#define EMAC_TRANS_PROC_STOP (BIT(1)) +#define EMAC_TRANS_PROC_STOP_S 1 +#define EMAC_TRANS_INT (BIT(0)) +#define EMAC_TRANS_INT_S 0 + +#define EMAC_DMAOPERATION_MODE_REG (REG_EMAC_BASE + 0x0018) +#define EMAC_DIS_DROP_TCPIP_CHKSUM_ERR_FRAM (BIT(26)) +#define EMAC_DIS_DROP_TCPIP_CHKSUM_ERR_FRAM_S 26 +#define EMAC_RECV_STORE_FORWARD (BIT(25)) +#define EMAC_RECV_STORE_FORWARD_S 25 +#define EMAC_DIS_FLUSH_RECV_FRAMES (BIT(24)) +#define EMAC_DIS_FLUSH_RECV_FRAMES_S 24 +#define EMAC_MSB_THRESHOLD_ACTIVATING_FLOW_CONTROL (BIT(23)) +#define EMAC_MSB_THRESHOLD_ACTIVATING_FLOW_CONTROL_S 23 +#define EMAC_MSB_THRESHOLD_DEACTIVATING_FLOW_CONTROL (BIT(22)) +#define EMAC_MSB_THRESHOLD_DEACTIVATING_FLOW_CONTROL_S 22 +#define EMAC_TRANSMIT_STORE_FORWARD (BIT(21)) +#define EMAC_TRANSMIT_STORE_FORWARD_S 21 +#define EMAC_FLUSH_TRANSMIT_FIFO (BIT(20)) +#define EMAC_FLUSH_TRANSMIT_FIFO_S 20 +#define EMAC_TRANSMIT_THRESHOLD_CONTROL 0x00000007 +#define EMAC_TRANSMIT_THRESHOLD_CONTROL_S 14 +#define EMAC_START_STOP_TRANSMISSION_COMMAND (BIT(13)) +#define EMAC_START_STOP_TRANSMISSION_COMMAND_S 13 +#define EMAC_THRESHOLD_DEACTIVATING_FLOW_CONTROL 0x00000003 +#define EMAC_THRESHOLD_DEACTIVATING_FLOW_CONTROL_S 11 +#define EMAC_THRESHOLD_ACTIVATING_FLOW_CONTROL 0x00000003 +#define EMAC_THRESHOLD_ACTIVATING_FLOW_CONTROL_S 9 +#define EMAC_ENABLE_HW_FLOW_CONTROL (BIT(8)) +#define EMAC_ENABLE_HW_FLOW_CONTROL_S 8 +#define EMAC_FORWARD_ERROR_FRAMES (BIT(7)) +#define EMAC_FORWARD_ERROR_FRAMES_S 7 +#define EMAC_FORWARD_UNDERSIZED_GOOD_FRAMES (BIT(6)) +#define EMAC_FORWARD_UNDERSIZED_GOOD_FRAMES_S 6 +#define EMAC_DROP_GIANT_FRAMES (BIT(5)) +#define EMAC_DROP_GIANT_FRAMES_S 5 +#define EMAC_RECEIVE_THRESHOLD_CONTROL 0x00000003 +#define EMAC_RECEIVE_THRESHOLD_CONTROL_S 3 +#define EMAC_OPERATE_SECOND_FRAME (BIT(2)) +#define EMAC_OPERATE_SECOND_FRAME_S 2 +#define EMAC_START_STOP_RECEIVE (BIT(1)) +#define EMAC_START_STOP_RECEIVE_S 1 + +#define EMAC_DMAINTERRUPT_EN_REG (REG_EMAC_BASE + 0x001C) +#define EMAC_NORMAL_INTERRUPT_SUMMARY_ENABLE (BIT(16)) +#define EMAC_NORMAL_INTERRUPT_SUMMARY_ENABLE_S 16 +#define EMAC_ABNORMAL_INTERRUPT_SUMMARY_ENABLE (BIT(15)) +#define EMAC_ABNORMAL_INTERRUPT_SUMMARY_ENABLE_S 15 +#define EMAC_EARLY_RECEIVE_INTERRUPT_ENABLE (BIT(14)) +#define EMAC_EARLY_RECEIVE_INTERRUPT_ENABLE_S 14 +#define EMAC_FATAL_BUS_ERROR_ENABLE (BIT(13)) +#define EMAC_FATAL_BUS_ERROR_ENABLE_S 13 +#define EMAC_EARLY_TRANSMIT_INTERRUPT_ENABLE (BIT(10)) +#define EMAC_EARLY_TRANSMIT_INTERRUPT_ENABLE_S 10 +#define EMAC_RECEIVE_WATCHDOG_TIMEOUT_ENABLE (BIT(9)) +#define EMAC_RECEIVE_WATCHDOG_TIMEOUT_ENABLE_S 9 +#define EMAC_RECEIVE_STOPPED_ENABLE (BIT(8)) +#define EMAC_RECEIVE_STOPPED_ENABLE_S 8 +#define EMAC_RECEIVE_BUFFER_UNAVAILABLE_ENABLE (BIT(7)) +#define EMAC_RECEIVE_BUFFER_UNAVAILABLE_ENABLE_S 7 +#define EMAC_RECEIVE_INTERRUPT_ENABLE (BIT(6)) +#define EMAC_RECEIVE_INTERRUPT_ENABLE_S 6 +#define EMAC_UNDERFLOW_INTERRUPT_ENABLE (BIT(5)) +#define EMAC_UNDERFLOW_INTERRUPT_ENABLE_S 5 +#define EMAC_OVERFLOW_INTERRUPT_ENABLE (BIT(4)) +#define EMAC_OVERFLOW_INTERRUPT_ENABLE_S 4 +#define EMAC_TRANSMIT_JABBER_TIMEOUT_ENABLE (BIT(3)) +#define EMAC_TRANSMIT_JABBER_TIMEOUT_ENABLE_S 3 +#define EMAC_TRANSMIT_BUFFER_UNAVAILABLE_ENABLE (BIT(2)) +#define EMAC_TRANSMIT_BUFFER_UNAVAILABLE_ENABLE_S 2 +#define EMAC_TRANSMIT_STOPPED_ENABLE (BIT(1)) +#define EMAC_TRANSMIT_STOPPED_ENABLE_S 1 +#define EMAC_TRANSMIT_INTERRUPT_ENABLE (BIT(0)) +#define EMAC_TRANSMIT_INTERRUPT_ENABLE_S 0 + +#define EMAC_DMAMISSEDFR_REG (REG_EMAC_BASE + 0x0020) +#define EMAC_OVERFLOW_BIT_FIFO_OVERFLOW_COUNTER (BIT(28)) +#define EMAC_OVERFLOW_BIT_FIFO_OVERFLOW_COUNTER_S 28 +#define EMAC_OVERFLOW_FRAME_COUNTER 0x000007FF +#define EMAC_OVERFLOW_FRAME_COUNTER_S 17 +#define EMAC_OVERFLOW_BIT_MISSED_FRAME_COUNTER (BIT(16)) +#define EMAC_OVERFLOW_BIT_MISSED_FRAME_COUNTER_S 16 +#define EMAC_MISSED_FRAME_COUNTER 0x0000FFFF +#define EMAC_MISSED_FRAME_COUNTER_S 0 + +#define EMAC_DMARECEIVE_INTERRUPT_WATCHDOG_TIMER_REG (REG_EMAC_BASE + 0x0024) +#define EMAC_RI_WATCHDOG_TIMER_COUNT 0x000000FF +#define EMAC_RI_WATCHDOG_TIMER_COUNT_S 0 + +#define EMAC_DMATXCURRDESC_REG (REG_EMAC_BASE + 0x0048) +#define EMAC_HOST_TRANSMIT_DESCRIPTOR_ADDRESS_POINTER 0xFFFFFFFF +#define EMAC_HOST_TRANSMIT_DESCRIPTOR_ADDRESS_POINTER_S 0 + +#define EMAC_DMARXCURRDESC_REG (REG_EMAC_BASE + 0x004C) +#define EMAC_HOST_RECEIVE_DESCRIPTOR_ADDRESS_POINTER 0xFFFFFFFF +#define EMAC_HOST_RECEIVE_DESCRIPTOR_ADDRESS_POINTER_S 0 + +#define EMAC_DMATXCURRADDR_BUF_REG (REG_EMAC_BASE + 0x0050) +#define EMAC_HOST_TRANSMIT_BUFFER_ADDRESS_POINTER 0xFFFFFFFF +#define EMAC_HOST_TRANSMIT_BUFFER_ADDRESS_POINTER_S 0 + +#define EMAC_DMARXCURRADDR_BUF_REG (REG_EMAC_BASE + 0x0054) +#define EMAC_HOST_RECEIVE_BUFFER_ADDRESS_POINTER 0xFFFFFFFF +#define EMAC_HOST_RECEIVE_BUFFER_ADDRESS_POINTER_S 0 + +#define EMAC_DMAHWFEATURE_REG (REG_EMAC_BASE + 0x0058) +#define EMAC_SELECTED_PHY_INTERFACE 0x00000007 +#define EMAC_SELECTED_PHY_INTERFACE_S 28 +#define EMAC_SOURCE_ADDRESS_VLAN_INSERTION (BIT(27)) +#define EMAC_SOURCE_ADDRESS_VLAN_INSERTION_S 27 +#define EMAC_FLEXIBLE_PULSE_PER_SECOND_OUTPUT (BIT(26)) +#define EMAC_FLEXIBLE_PULSE_PER_SECOND_OUTPUT_S 26 +#define EMAC_TIMESTAMPING_INTERNAL_SYSTEM_TIME (BIT(25)) +#define EMAC_TIMESTAMPING_INTERNAL_SYSTEM_TIME_S 25 +#define EMAC_ENHANCED_DESCRIPTOR (BIT(24)) +#define EMAC_ENHANCED_DESCRIPTOR_S 24 +#define EMAC_NUMBER_ADDITIONAL_TX_CHANNELS 0x00000003 +#define EMAC_NUMBER_ADDITIONAL_TX_CHANNELS_S 22 +#define EMAC_NUMBER_ADDITIONAL_RX_CHANNELS 0x00000003 +#define EMAC_NUMBER_ADDITIONAL_RX_CHANNELS_S 20 +#define EMAC_RXFIFOSIZE (BIT(19)) +#define EMAC_RXFIFOSIZE_S 19 +#define EMAC_IP_CHECKSUM_OFFLOAD_TYPE2 (BIT(18)) +#define EMAC_IP_CHECKSUM_OFFLOAD_TYPE2_S 18 +#define EMAC_IP_CHECKSUM_OFFLOAD_TYPE1 (BIT(17)) +#define EMAC_IP_CHECKSUM_OFFLOAD_TYPE1_S 17 +#define EMAC_CHECKSUM_OFFLOAD_TX (BIT(16)) +#define EMAC_CHECKSUM_OFFLOAD_TX_S 16 +#define EMAC_AV_FEATURE_SEL (BIT(15)) +#define EMAC_AV_FEATURE_SEL_S 15 +#define EMAC_EEE_SEL (BIT(14)) +#define EMAC_EEE_SEL_S 14 +#define EMAC_TSVER2_SEL (BIT(13)) +#define EMAC_TSVER2_SEL_S 13 +#define EMAC_TSVER1_SEL (BIT(12)) +#define EMAC_TSVER1_SEL_S 12 +#define EMAC_MMC_SEL (BIT(11)) +#define EMAC_MMC_SEL_S 11 +#define EMAC_MGK_SEL (BIT(10)) +#define EMAC_MGK_SEL_S 10 +#define EMAC_RWK_SEL (BIT(9)) +#define EMAC_RWK_SEL_S 9 +#define EMAC_SMA_SEL (BIT(8)) +#define EMAC_SMA_SEL_S 8 +#define EMAC_L3L4FLTR_EN (BIT(7)) +#define EMAC_L3L4FLTR_EN_S 7 +#define EMAC_PCS_SEL (BIT(6)) +#define EMAC_PCS_SEL_S 6 +#define EMAC_ADDMACADR_SEL (BIT(5)) +#define EMAC_ADDMACADR_SEL_S 5 +#define EMAC_HASH_SEL (BIT(4)) +#define EMAC_HASH_SEL_S 4 +#define EMAC_EXTHASH_EN (BIT(3)) +#define EMAC_EXTHASH_EN_S 3 +#define EMAC_HD_SEL (BIT(2)) +#define EMAC_HD_SEL_S 2 +#define EMAC_GMII_SEL (BIT(1)) +#define EMAC_GMII_SEL_S 1 +#define EMAC_MII_SEL (BIT(0)) +#define EMAC_MII_SEL_S 0 + +#define EMAC_DMASLOTFNCTRLSTS_REG (REG_EMAC_BASE + 0x0130) +#define EMAC_REFERENCE_SLOT_NUMBER 0x0000000F +#define EMAC_REFERENCE_SLOT_NUMBER_S 16 +#define EMAC_ADVANCE_SLOT_CHECK (BIT(1)) +#define EMAC_ADVANCE_SLOT_CHECK_S 1 +#define EMAC_ENABLE_SLOT_COMPARISON (BIT(0)) +#define EMAC_ENABLE_SLOT_COMPARISON_S 0 + +#define EMAC_DMACHANNELCTRL_REG (REG_EMAC_BASE + 0x0160) +#define EMAC_AVERAGE_BITS_PER_SLOT_INTERRUPT_ENABLE (BIT(17)) +#define EMAC_AVERAGE_BITS_PER_SLOT_INTERRUPT_ENABLE_S 17 +#define EMAC_SLOT_COUNT 0x00000007 +#define EMAC_SLOT_COUNT_S 4 +#define EMAC_CREDIT_CONTROL (BIT(1)) +#define EMAC_CREDIT_CONTROL_S 1 +#define EMAC_CREDIT_BASED_SHAPER_DISABLE (BIT(0)) +#define EMAC_CREDIT_BASED_SHAPER_DISABLE_S 0 + +#define EMAC_DMACHANNELAVSTS_REG (REG_EMAC_BASE + 0x0064) +#define EMAC_ABS_UPDATED (BIT(17)) +#define EMAC_ABS_UPDATED_S 17 +#define EMAC_AVERAGE_BITS_PER_SLOT 0x0001FFFF +#define EMAC_AVERAGE_BITS_PER_SLOT_S 0 + +#define EMAC_DMAIDLESLOPECREDIT_REG (REG_EMAC_BASE + 0x0068) +#define EMAC_IDLESLOPECREDIT 0x00003FFF +#define EMAC_IDLESLOPECREDIT_S 0 + +#define EMAC_DMASENDSLOPECREDIT_REG (REG_EMAC_BASE + 0x006C) +#define EMAC_SENDSLOPECREDIT 0x00003FFF +#define EMAC_SENDSLOPECREDIT_S 0 + +#define EMAC_DMAHIGHCREDIT_REG (REG_EMAC_BASE + 0x0070) +#define EMAC_HICREDIT 0x1FFFFFFF +#define EMAC_HICREDIT_S 0 + +#define EMAC_DMALOCREDIT_REG (REG_EMAC_BASE + 0x0074) +#define EMAC_LOCREDIT 0x1FFFFFFF +#define EMAC_LOCREDIT_S 0 + +#define EMAC_GMACCONFIG_REG (REG_EMAC_BASE + 0x1000) +#define EMAC_SOURCE_ADDRESS_INSERTION_REPLACEMENT_CONTROL 0x00000007 +#define EMAC_SOURCE_ADDRESS_INSERTION_REPLACEMENT_CONTROL_S 28 +#define EMAC_AS_SUPPORT_2K_PACKETS (BIT(27)) +#define EMAC_AS_SUPPORT_2K_PACKETS_S 27 +#define EMAC_SMII_FORCE_TRANSMIT_ERROR (BIT(26)) +#define EMAC_SMII_FORCE_TRANSMIT_ERROR_S 26 +#define EMAC_CRC_STRIPPING_TYPE_FRAMES (BIT(25)) +#define EMAC_CRC_STRIPPING_TYPE_FRAMES_S 25 +#define EMAC_TRANSMIT_CONFIGURATION (BIT(24)) +#define EMAC_TRANSMIT_CONFIGURATION_S 24 +#define EMAC_GMACWATCHDOG (BIT(23)) +#define EMAC_GMACWATCHDOG_S 23 +#define EMAC_GMACJABBER (BIT(22)) +#define EMAC_GMACJABBER_S 22 +#define EMAC_GMACFRAMEBURST (BIT(21)) +#define EMAC_GMACFRAMEBURST_S 21 +#define EMAC_GMACJUMBOFRAME (BIT(20)) +#define EMAC_GMACJUMBOFRAME_S 20 +#define EMAC_GMACINTERFRAMEGAP 0x00000007 +#define EMAC_GMACINTERFRAMEGAP_S 17 +#define EMAC_GMACDISABLECRS (BIT(16)) +#define EMAC_GMACDISABLECRS_S 16 +#define EMAC_GMACMIIGMII (BIT(15)) +#define EMAC_GMACMIIGMII_S 15 +#define EMAC_GMACFESPEED (BIT(14)) +#define EMAC_GMACFESPEED_S 14 +#define EMAC_GMACRXOWN (BIT(13)) +#define EMAC_GMACRXOWN_S 13 +#define EMAC_GMACLOOPBACK (BIT(12)) +#define EMAC_GMACLOOPBACK_S 12 +#define EMAC_GMACDUPLEX (BIT(11)) +#define EMAC_GMACDUPLEX_S 11 +#define EMAC_GMACRXIPCOFFLOAD (BIT(10)) +#define EMAC_GMACRXIPCOFFLOAD_S 10 +#define EMAC_GMACRETRY (BIT(9)) +#define EMAC_GMACRETRY_S 9 +#define EMAC_GMACLINK (BIT(8)) +#define EMAC_GMACLINK_S 8 +#define EMAC_GMACPADCRCSTRIP (BIT(7)) +#define EMAC_GMACPADCRCSTRIP_S 7 +#define EMAC_GMACBACKOFFLIMIT 0x00000003 +#define EMAC_GMACBACKOFFLIMIT_S 5 +#define EMAC_GMACDEFERRALCHECK (BIT(4)) +#define EMAC_GMACDEFERRALCHECK_S 4 +#define EMAC_GMACTX (BIT(3)) +#define EMAC_GMACTX_S 3 +#define EMAC_GMACRX (BIT(2)) +#define EMAC_GMACRX_S 2 +#define EMAC_PREAMBLE_LENGTH_TRANSMIT_FRAMES 0x00000003 +#define EMAC_PREAMBLE_LENGTH_TRANSMIT_FRAMES_S 0 + +#define EMAC_GMACFRAMEFILTER_REG (REG_EMAC_BASE + 0x1004) +#define EMAC_RECEIVEALL (BIT(31)) +#define EMAC_RECEIVEALL_S 31 +#define EMAC_DROP_NON_TCP_UDP_IP_FRAMES (BIT(21)) +#define EMAC_DROP_NON_TCP_UDP_IP_FRAMES_S 21 +#define EMAC_LAYER_3_AND_LAYER_4_FILTER_ENABLE (BIT(20)) +#define EMAC_LAYER_3_AND_LAYER_4_FILTER_ENABLE_S 20 +#define EMAC_VLAN_TAG_FILTER_ENABLE (BIT(16)) +#define EMAC_VLAN_TAG_FILTER_ENABLE_S 16 +#define EMAC_HASH_OR_PERFECT_FILTE (BIT(10)) +#define EMAC_HASH_OR_PERFECT_FILTE_S 10 +#define EMAC_SOURCE_ADDRESS_FILTER_ENABLE (BIT(9)) +#define EMAC_SOURCE_ADDRESS_FILTER_ENABLE_S 9 +#define EMAC_SA_INVERSE_FILTERING (BIT(8)) +#define EMAC_SA_INVERSE_FILTERING_S 8 +#define EMAC_PASS_CONTROL_FRAMES 0x00000003 +#define EMAC_PASS_CONTROL_FRAMES_S 6 +#define EMAC_DISABLE_BROADCAST_FRAMES (BIT(5)) +#define EMAC_DISABLE_BROADCAST_FRAMES_S 5 +#define EMAC_PASS_ALL_MULTICAST (BIT(4)) +#define EMAC_PASS_ALL_MULTICAST_S 4 +#define EMAC_DA_INVERSE_FILTERING (BIT(3)) +#define EMAC_DA_INVERSE_FILTERING_S 3 +#define EMAC_HASH_MULTICAST (BIT(2)) +#define EMAC_HASH_MULTICAST_S 2 +#define EMAC_HASH_UNICAST (BIT(1)) +#define EMAC_HASH_UNICAST_S 1 +#define EMAC_PROMISCUOUS_MODE (BIT(0)) +#define EMAC_PROMISCUOUS_MODE_S 0 + +#define EMAC_GMACHASHHIGH_REG (REG_EMAC_BASE + 0x1008) +#define EMAC_HASH_TABLE_HIGH 0xFFFFFFFF +#define EMAC_HASH_TABLE_HIGH_S 0 + +#define EMAC_GMACHASHLOW_REG (REG_EMAC_BASE + 0x100C) +#define EMAC_HASH_TABLE_LOW 0xFFFFFFFF +#define EMAC_HASH_TABLE_LOW_S 0 + +#define EMAC_GMACGMIIADDR_REG (REG_EMAC_BASE + 0x1010) +#define EMAC_GMIIDEV 0x0000001F +#define EMAC_GMIIDEV_S 11 +#define EMAC_GMIIREG 0x0000001F +#define EMAC_GMIIREG_S 6 +#define EMAC_GMIICSRCLK 0x0000000F +#define EMAC_GMIICSRCLK_S 2 +#define EMAC_GMIIWRITE (BIT(1)) +#define EMAC_GMIIWRITE_S 1 +#define EMAC_GMIIBUSY (BIT(0)) +#define EMAC_GMIIBUSY_S 0 + +#define EMAC_GMACGMIIDATA_REG (REG_EMAC_BASE + 0x1014) +#define EMAC_GMII_DATA 0x0000FFFF +#define EMAC_GMII_DATA_S 0 + +#define EMAC_GMACFLOWCONTROL_REG (REG_EMAC_BASE + 0x1018) +#define EMAC_PAUSE_TIME 0x0000FFFF +#define EMAC_PAUSE_TIME_S 16 +#define EMAC_DISABLE_ZERO_QUANTA_PAUSE (BIT(7)) +#define EMAC_DISABLE_ZERO_QUANTA_PAUSE_S 7 +#define EMAC_PAUSE_LOW_THRESHOLD 0x00000003 +#define EMAC_PAUSE_LOW_THRESHOLD_S 4 +#define EMAC_UNICAST_PAUSE_FRAME_DETECT (BIT(3)) +#define EMAC_UNICAST_PAUSE_FRAME_DETECT_S 3 +#define EMAC_RECEIVE_FLOW_CONTROL_ENABLE (BIT(2)) +#define EMAC_RECEIVE_FLOW_CONTROL_ENABLE_S 2 +#define EMAC_TRANSMIT_FLOW_CONTROL_ENABLE (BIT(1)) +#define EMAC_TRANSMIT_FLOW_CONTROL_ENABLE_S 1 +#define EMAC_FLOW_CONTROL_BUSY_BACKPRESSURE_ACTIVATE (BIT(0)) +#define EMAC_FLOW_CONTROL_BUSY_BACKPRESSURE_ACTIVATE_S 0 + +#define EMAC_GMACVLAN_REG (REG_EMAC_BASE + 0x101C) +#define EMAC_VLAN_TAG_HASH_TABLE_MATCH_ENABLE (BIT(19)) +#define EMAC_VLAN_TAG_HASH_TABLE_MATCH_ENABLE_S 19 +#define EMAC_ENABLE_S_VLAN (BIT(18)) +#define EMAC_ENABLE_S_VLAN_S 18 +#define EMAC_VLAN_TAG_INVERSE_MATCH_ENABLE (BIT(17)) +#define EMAC_VLAN_TAG_INVERSE_MATCH_ENABLE_S 17 +#define EMAC_ENABLE_VLAN_TAG_COMPARISON (BIT(16)) +#define EMAC_ENABLE_VLAN_TAG_COMPARISON_S 16 +#define EMAC_VLAN_TAG_IDENTIFIER_RECEIVE_FRAMES 0x0000FFFF +#define EMAC_VLAN_TAG_IDENTIFIER_RECEIVE_FRAMES_S 0 + +#define EMAC_GMACVERSION_REG (REG_EMAC_BASE + 0x1020) +#define EMAC_USERVER 0x000000FF +#define EMAC_USERVER_S 8 +#define EMAC_SNPSVER 0x000000FF +#define EMAC_SNPSVER_S 0 + +#define EMAC_GMACDEBUG_REG (REG_EMAC_BASE + 0x1024) +#define EMAC_MTL_TXSTATUS_FIFO_FULL_STATUS (BIT(25)) +#define EMAC_MTL_TXSTATUS_FIFO_FULL_STATUS_S 25 +#define EMAC_MTL_TX_FIFO_NOT_EMPTY_STATUS (BIT(24)) +#define EMAC_MTL_TX_FIFO_NOT_EMPTY_STATUS_S 24 +#define EMAC_MTL_TX_FIFO_WRITE_CONTROLLER_STATUS (BIT(22)) +#define EMAC_MTL_TX_FIFO_WRITE_CONTROLLER_STATUS_S 22 +#define EMAC_MTL_TX_FIFO_READ_CONTROLLER_STATUS 0x00000003 +#define EMAC_MTL_TX_FIFO_READ_CONTROLLER_STATUS_S 20 +#define EMAC_MAC_TRANSMITTER_PAUSE (BIT(19)) +#define EMAC_MAC_TRANSMITTER_PAUSE_S 19 +#define EMAC_MAC_TRANSMIT_FRAME_CONTROLLER_STATUS 0x00000003 +#define EMAC_MAC_TRANSMIT_FRAME_CONTROLLER_STATUS_S 17 +#define EMAC_MAC_TRANSMIT_PROTOCOL_ENGINE_STATUS (BIT(16)) +#define EMAC_MAC_TRANSMIT_PROTOCOL_ENGINE_STATUS_S 16 +#define EMAC_MTL_RXFIFO_FILL_LEVEL_STATUS 0x00000003 +#define EMAC_MTL_RXFIFO_FILL_LEVEL_STATUS_S 8 +#define EMAC_MTL_RXFIFO_READ_CONTROLLER_STATE 0x00000003 +#define EMAC_MTL_RXFIFO_READ_CONTROLLER_STATE_S 5 +#define EMAC_MTL_RX_FIFO_WRITE_CONTROLLER_ACTIVE_STATUS (BIT(4)) +#define EMAC_MTL_RX_FIFO_WRITE_CONTROLLER_ACTIVE_STATUS_S 4 +#define EMAC_MAC_RECEIVE_FRAME_FIFO_CONTROLLER_STATUS 0x00000003 +#define EMAC_MAC_RECEIVE_FRAME_FIFO_CONTROLLER_STATUS_S 1 +#define EMAC_MAC_RECEIVE_PROTOCOL_ENGINE_STATUS (BIT(0)) +#define EMAC_MAC_RECEIVE_PROTOCOL_ENGINE_STATUS_S 0 + +#define EMAC_GMACLPITIMERSCONTROL_REG (REG_EMAC_BASE + 0x1034) +#define EMAC_LPI_LS_TIMER 0x000003FF +#define EMAC_LPI_LS_TIMER_S 16 +#define EMAC_LPI_TW_TIMER 0x0000FFFF +#define EMAC_LPI_TW_TIMER_S 0 + +#define EMAC_GMACINTERRUPTSTATUS_REG (REG_EMAC_BASE + 0x1038) +#define EMAC_GPI_INTERRUPT_STATUS (BIT(11)) +#define EMAC_GPI_INTERRUPT_STATUS_S 11 +#define EMAC_LPI_INTERRUPT_STATUS (BIT(10)) +#define EMAC_LPI_INTERRUPT_STATUS_S 10 +#define EMAC_TIMESTAMP_INTERRUP_STATUS (BIT(9)) +#define EMAC_TIMESTAMP_INTERRUP_STATUS_S 9 +#define EMAC_MMC_RECEIVE_CHECKSUM_OFFLOAD_INTERRUPT_STATUS (BIT(7)) +#define EMAC_MMC_RECEIVE_CHECKSUM_OFFLOAD_INTERRUPT_STATUS_S 7 +#define EMAC_MMC_TRANSMIT_INTERRUPT_STATUS (BIT(6)) +#define EMAC_MMC_TRANSMIT_INTERRUPT_STATUS_S 6 +#define EMAC_MMC_RECEIVE_INTERRUPT_STATUS (BIT(5)) +#define EMAC_MMC_RECEIVE_INTERRUPT_STATUS_S 5 +#define EMAC_MMC_INTERRUPT_STATUS (BIT(4)) +#define EMAC_MMC_INTERRUPT_STATUS_S 4 +#define EMAC_PMT_INTERRUPT_STATUS (BIT(3)) +#define EMAC_PMT_INTERRUPT_STATUS_S 3 +#define EMAC_PCS_AUTO_NEGOTIATION_COMPLETE (BIT(2)) +#define EMAC_PCS_AUTO_NEGOTIATION_COMPLETE_S 2 +#define EMAC_PCS_LINK_STATUS_CHANGED (BIT(1)) +#define EMAC_PCS_LINK_STATUS_CHANGED_S 1 +#define EMAC_INTERRUPT_STATUS (BIT(0)) +#define EMAC_INTERRUPT_STATUS_S 0 + +#define EMAC_GMACINTERRUPTMASK_REG (REG_EMAC_BASE + 0x103C) +#define EMAC_LPI_INTERRUPT_MASK (BIT(10)) +#define EMAC_LPI_INTERRUPT_MASK_S 10 +#define EMAC_TIMESTAMP_INTERRUPT_MASK (BIT(9)) +#define EMAC_TIMESTAMP_INTERRUPT_MASK_S 9 +#define EMAC_PMT_INTERRUPT_MASK (BIT(3)) +#define EMAC_PMT_INTERRUPT_MASK_S 3 +#define EMAC_PCS_AN_COMPLETION_INTERRUPT_MASK (BIT(2)) +#define EMAC_PCS_AN_COMPLETION_INTERRUPT_MASK_S 2 +#define EMAC_PCS_LINK_STATUS_INTERRUPT_MASK (BIT(1)) +#define EMAC_PCS_LINK_STATUS_INTERRUPT_MASK_S 1 +#define EMAC_INTERRUPT_MASK (BIT(0)) +#define EMAC_INTERRUPT_MASK_S 0 + +#define EMAC_GMACADDR0HIGH_REG (REG_EMAC_BASE + 0x1040) +#define EMAC_ADDRESS_ENABLE0 (BIT(31)) +#define EMAC_ADDRESS_ENABLE0_S 31 +#define EMAC_MAC_ADDRESS0_HI 0x0000FFFF +#define EMAC_MAC_ADDRESS0_HI_S 0 + +#define EMAC_GMACADDR0LOW_REG (REG_EMAC_BASE + 0x1044) +#define EMAC_MAC_ADDRESS0_LOW 0xFFFFFFFF +#define EMAC_MAC_ADDRESS0_LOW_S 0 + +#define EMAC_GMACADDR1HIGH_REG (REG_EMAC_BASE + 0x1048) +#define EMAC_ADDRESS_ENABLE1 (BIT(31)) +#define EMAC_ADDRESS_ENABLE1_S 31 +#define EMAC_SOURCE_ADDRESS (BIT(30)) +#define EMAC_SOURCE_ADDRESS_S 30 +#define EMAC_MASK_BYTE_CONTROL 0x0000003F +#define EMAC_MASK_BYTE_CONTROL_S 24 +#define EMAC_MAC_ADDRESS1_HI 0x0000FFFF +#define EMAC_MAC_ADDRESS1_HI_S 0 + +#define EMAC_GMACADDR1LOW_REG (REG_EMAC_BASE + 0x104C) +#define EMAC_MAC_ADDRESS1_LOW 0xFFFFFFFF +#define EMAC_MAC_ADDRESS1_LOW_S 0 + +#define EMAC_GMAC_AN_CONTROL_REG (REG_EMAC_BASE + 0x10C0) +#define EMAC_SGMII_RAL_CONTROL (BIT(18)) +#define EMAC_SGMII_RAL_CONTROL_S 18 +#define EMAC_LOCK_REFERENCE (BIT(17)) +#define EMAC_LOCK_REFERENCE_S 17 +#define EMAC_ENABLE_COMMA_DETECT (BIT(16)) +#define EMAC_ENABLE_COMMA_DETECT_S 16 +#define EMAC_EXTERNAL_LOOPBACK_ENABLE (BIT(14)) +#define EMAC_EXTERNAL_LOOPBACK_ENABLE_S 14 +#define EMAC_AUTO_NEGOTIATION_ENABLE (BIT(12)) +#define EMAC_AUTO_NEGOTIATION_ENABLE_S 12 +#define EMAC_RESTART_AUTO_NEGOTIATION (BIT(9)) +#define EMAC_RESTART_AUTO_NEGOTIATION_S 9 + +#define EMAC_GMAC_AN_STATUS_REG (REG_EMAC_BASE + 0x10C4) +#define EMAC_EXTENDED_STATUS (BIT(8)) +#define EMAC_EXTENDED_STATUS_S 8 +#define EMAC_AUTO_NEGOTIATION_COMPLETE (BIT(5)) +#define EMAC_AUTO_NEGOTIATION_COMPLETE_S 5 +#define EMAC_AUTO_NEGOTIATION_ABILITY (BIT(3)) +#define EMAC_AUTO_NEGOTIATION_ABILITY_S 3 +#define EMAC_LINK_AN_STATUS (BIT(2)) +#define EMAC_LINK_AN_STATUS_S 2 + +#define EMAC_GMAC_AUTO_NEGOTIATION_ADVERTISEMENT_REG (REG_EMAC_BASE + 0x10C8) +#define EMAC_ADV_NEXT_PAGE_SUPPORT (BIT(15)) +#define EMAC_ADV_NEXT_PAGE_SUPPORT_S 15 +#define EMAC_ADV_REMOTE_FAULT_ENCODING 0x00000003 +#define EMAC_ADV_REMOTE_FAULT_ENCODING_S 12 +#define EMAC_ADV_PAUSE_ENCODING 0x00000003 +#define EMAC_ADV_PAUSE_ENCODING_S 7 +#define EMAC_ADV_HALF_DUPLEX (BIT(6)) +#define EMAC_ADV_HALF_DUPLEX_S 6 +#define EMAC_ADV_FULL_DUPLEX (BIT(5)) +#define EMAC_ADV_FULL_DUPLEX_S 5 + +#define EMAC_GMAC_AUTO_NEGOTIATION_LINK_PARTNER_ABILITY_REG (REG_EMAC_BASE + 0x10CC) +#define EMAC_LINK_NEXT_PAGE_SUPPORT (BIT(15)) +#define EMAC_LINK_NEXT_PAGE_SUPPORT_S 15 +#define EMAC_LINK_ACKNOWLEDGE (BIT(14)) +#define EMAC_LINK_ACKNOWLEDGE_S 14 +#define EMAC_LINK_REMOTE_FAULT_ENCODING 0x00000003 +#define EMAC_LINK_REMOTE_FAULT_ENCODING_S 12 +#define EMAC_LINK_PAUSE_ENCODING 0x00000003 +#define EMAC_LINK_PAUSE_ENCODING_S 7 +#define EMAC_LINK_HALF_DUPLEX (BIT(6)) +#define EMAC_LINK_HALF_DUPLEX_S 6 +#define EMAC_LINK_FULL_DUPLEX (BIT(5)) +#define EMAC_LINK_FULL_DUPLEX_S 5 + +#define EMAC_GMAC_AUTO_NEGOTIATION_EXPANSION_REG (REG_EMAC_BASE + 0x10D0) +#define EMAC_NEXT_PAGE_ABILITY (BIT(2)) +#define EMAC_NEXT_PAGE_ABILITY_S 2 +#define EMAC_NEW_PAGE_RECEIVED (BIT(1)) +#define EMAC_NEW_PAGE_RECEIVED_S 1 + +#define EMAC_GMAC_TBI_EXTENDED_STATUS_REG (REG_EMAC_BASE + 0x10D4) +#define EMAC_1000BASE_X_FULL_DUPLEX_CAPABLE (BIT(15)) +#define EMAC_1000BASE_X_FULL_DUPLEX_CAPABLE_S 15 +#define EMAC_1000BASE_X_HALF_DUPLEX_CAPABLE (BIT(14)) +#define EMAC_1000BASE_X_HALF_DUPLEX_CAPABLE_S 14 + +#define EMAC_GMAC_CONTROL_STATUS_REG (REG_EMAC_BASE + 0x10D8) +#define EMAC_SMIDRXS (BIT(16)) +#define EMAC_SMIDRXS_S 16 +#define EMAC_FALSE_CARRIER_DETECTED (BIT(5)) +#define EMAC_FALSE_CARRIER_DETECTED_S 5 +#define EMAC_JABBER_TIMEOUT (BIT(4)) +#define EMAC_JABBER_TIMEOUT_S 4 +#define EMAC_LINK_STATUS (BIT(3)) +#define EMAC_LINK_STATUS_S 3 +#define EMAC_LINK_SPEED 0x00000003 +#define EMAC_LINK_SPEED_S 1 +#define EMAC_LINK_MODE (BIT(0)) +#define EMAC_LINK_MODE_S 0 + +#define EMAC_GMAC_WATCHDOG_TIMEOUT_REG (REG_EMAC_BASE + 0x10DC) +#define EMAC_PROGRAMMABLE_WATCHDOG_ENABLE (BIT(16)) +#define EMAC_PROGRAMMABLE_WATCHDOG_ENABLE_S 16 +#define EMAC_WATCHDOG_TIMEOUT 0x00003FFF +#define EMAC_WATCHDOG_TIMEOUT_S 0 + +#define EMAC_GMAC_GENERAL_PURPOSE_IO_REG (REG_EMAC_BASE + 0x10E0) +#define EMAC_GPI_TYPE 0x0000000F +#define EMAC_GPI_TYPE_S 24 +#define EMAC_GPI_INTERRUPT_ENABLE 0x0000000F +#define EMAC_GPI_INTERRUPT_ENABLE_S 16 +#define EMAC_GENERAL_PURPOSE_OUTPUT 0x0000000F +#define EMAC_GENERAL_PURPOSE_OUTPUT_S 8 +#define EMAC_GENERAL_PURPOSE_INPUT_STATUS 0x0000000F +#define EMAC_GENERAL_PURPOSE_INPUT_STATUS_S 0 + +#define EMAC_GMAC_LAYER3_LAYER4_CONTROL0_REG (REG_EMAC_BASE + 0x1400) +#define EMAC_LAYER4_DESTINATION_PORT_INVERSE_MATCH_ENABLE (BIT(21)) +#define EMAC_LAYER4_DESTINATION_PORT_INVERSE_MATCH_ENABLE_S 21 +#define EMAC_LAYER4_DESTINATION_PORT_MATCH_ENABLE (BIT(20)) +#define EMAC_LAYER4_DESTINATION_PORT_MATCH_ENABLE_S 20 +#define EMAC_LAYER4_SOURCE_PORT_INVERSE_MATCH_ENABLE (BIT(19)) +#define EMAC_LAYER4_SOURCE_PORT_INVERSE_MATCH_ENABLE_S 19 +#define EMAC_LAYER4_SOURCE_PORT_MATCH_ENABLE (BIT(18)) +#define EMAC_LAYER4_SOURCE_PORT_MATCH_ENABLE_S 18 +#define EMAC_LAYER4_PROTOCOL_ENABLE (BIT(16)) +#define EMAC_LAYER4_PROTOCOL_ENABLE_S 16 +#define EMAC_LAYER3_IP_DA_HIGHER_BITS_MATCH 0x0000001F +#define EMAC_LAYER3_IP_DA_HIGHER_BITS_MATCH_S 11 +#define EMAC_LAYER3_IP_SA_HIGHER_BITS_MATCH 0x0000001F +#define EMAC_LAYER3_IP_SA_HIGHER_BITS_MATCH_S 6 +#define EMAC_LAYER3_IP_DA_INVERSE_MATCH_ENABLE (BIT(5)) +#define EMAC_LAYER3_IP_DA_INVERSE_MATCH_ENABLE_S 5 +#define EMAC_LAYER3_IP_DA_MATCH_ENABLE (BIT(4)) +#define EMAC_LAYER3_IP_DA_MATCH_ENABLE_S 4 +#define EMAC_LAYER3_IP_SA_INVERSE_MATCH_ENABLE (BIT(3)) +#define EMAC_LAYER3_IP_SA_INVERSE_MATCH_ENABLE_S 3 +#define EMAC_LAYER3_IP_SA_MATCH_ENABLE (BIT(2)) +#define EMAC_LAYER3_IP_SA_MATCH_ENABLE_S 2 +#define EMAC_LAYER3_PROTOCOL_ENABLE (BIT(0)) +#define EMAC_LAYER3_PROTOCOL_ENABLE_S 0 + +#define EMAC_GMAC_LAYER4_ADDRESS0_REG (REG_EMAC_BASE + 0x1404) +#define EMAC_LAYER4_DESTINATION_PORT_NUMBER_FIELD 0x0000FFFF +#define EMAC_LAYER4_DESTINATION_PORT_NUMBER_FIELD_S 16 +#define EMAC_LAYER4_SOURCE_PORT_NUMBER_FIELD 0x0000FFFF +#define EMAC_LAYER4_SOURCE_PORT_NUMBER_FIELD_S 0 + +#define EMAC_GMAC_LAYER3_ADDRESS0_REG (REG_EMAC_BASE + 0x1410) +#define EMAC_LAYER3_ADDRESS0_FIELD 0xFFFFFFFF +#define EMAC_LAYER3_ADDRESS0_FIELD_S 0 + +#define EMAC_GMAC_LAYER3_ADDRESS1_REG (REG_EMAC_BASE + 0x1414) +#define EMAC_LAYER3_ADDRESS1_FIELD 0xFFFFFFFF +#define EMAC_LAYER3_ADDRESS1_FIELD_S 0 + +#define EMAC_GMAC_LAYER3_ADDRESS2_REG (REG_EMAC_BASE + 0x1418) +#define EMAC_LAYER3_ADDRESS2_FIELD 0xFFFFFFFF +#define EMAC_LAYER3_ADDRESS2_FIELD_S 0 + +#define EMAC_GMAC_LAYER3_ADDRESS3_REG (REG_EMAC_BASE + 0x141C) +#define EMAC_LAYER3_ADDRESS3_FIELD 0xFFFFFFFF +#define EMAC_LAYER3_ADDRESS3_FIELD_S 0 + +#define EMAC_GMAC_HASH_TABLE0_REG (REG_EMAC_BASE + 0x1500) +#define EMAC_FIRST32_BITS_HASH_TABLE 0xFFFFFFFF +#define EMAC_FIRST32_BITS_HASH_TABLE_S 0 + +#define EMAC_GMAC_VLAN_TAG_INCLUSION_REPLACEMENT_REG (REG_EMAC_BASE + 0x1584) +#define EMAC_VLAN_C_VLAN_S_VLAN (BIT(19)) +#define EMAC_VLAN_C_VLAN_S_VLAN_S 19 +#define EMAC_VLAN_PRIORITY_CONTROL (BIT(18)) +#define EMAC_VLAN_PRIORITY_CONTROL_S 18 +#define EMAC_VLAN_TAG_CONTROL_TRANSMIT_FRAMES 0x00000003 +#define EMAC_VLAN_TAG_CONTROL_TRANSMIT_FRAMES_S 16 +#define EMAC_VLAN_TAG_TRANSMIT_FRAMES 0x0000FFFF +#define EMAC_VLAN_TAG_TRANSMIT_FRAMES_S 0 + +#define EMAC_GMAC_VLAN_HASH_TABLE_REG (REG_EMAC_BASE + 0x1588) +#define EMAC_VLAN_HASH_TABLE 0x0000FFFF +#define EMAC_VLAN_HASH_TABLE_S 0 + +#ifdef __cplusplus +} +#endif + +#endif + diff --git a/components/esp32/include/soc/hwcrypto_reg.h b/components/esp32/include/soc/hwcrypto_reg.h index 4f38b1ba93..10e80d935f 100644 --- a/components/esp32/include/soc/hwcrypto_reg.h +++ b/components/esp32/include/soc/hwcrypto_reg.h @@ -30,8 +30,31 @@ #define RSA_MULT_MODE_REG (DR_REG_RSA_BASE + 0x80c) #define RSA_MULT_START_REG (DR_REG_RSA_BASE + 0x810) -#define RSA_INTERRUPT_REG (DR_REG_RSA_BASE + 0X814) +#define RSA_INTERRUPT_REG (DR_REG_RSA_BASE + 0x814) -#define RSA_CLEAN_ADDR (DR_REG_RSA_BASE + 0X818) +#define RSA_CLEAN_REG (DR_REG_RSA_BASE + 0x818) + +/* SHA acceleration registers */ +#define SHA_TEXT_BASE ((DR_REG_SHA_BASE) + 0x00) + +#define SHA_1_START_REG ((DR_REG_SHA_BASE) + 0x80) +#define SHA_1_CONTINUE_REG ((DR_REG_SHA_BASE) + 0x84) +#define SHA_1_LOAD_REG ((DR_REG_SHA_BASE) + 0x88) +#define SHA_1_BUSY_REG ((DR_REG_SHA_BASE) + 0x8c) + +#define SHA_256_START_REG ((DR_REG_SHA_BASE) + 0x90) +#define SHA_256_CONTINUE_REG ((DR_REG_SHA_BASE) + 0x94) +#define SHA_256_LOAD_REG ((DR_REG_SHA_BASE) + 0x98) +#define SHA_256_BUSY_REG ((DR_REG_SHA_BASE) + 0x9c) + +#define SHA_384_START_REG ((DR_REG_SHA_BASE) + 0xa0) +#define SHA_384_CONTINUE_REG ((DR_REG_SHA_BASE) + 0xa4) +#define SHA_384_LOAD_REG ((DR_REG_SHA_BASE) + 0xa8) +#define SHA_384_BUSY_REG ((DR_REG_SHA_BASE) + 0xac) + +#define SHA_512_START_REG ((DR_REG_SHA_BASE) + 0xb0) +#define SHA_512_CONTINUE_REG ((DR_REG_SHA_BASE) + 0xb4) +#define SHA_512_LOAD_REG ((DR_REG_SHA_BASE) + 0xb8) +#define SHA_512_BUSY_REG ((DR_REG_SHA_BASE) + 0xbc) #endif diff --git a/components/esp32/include/soc/pcnt_reg.h b/components/esp32/include/soc/pcnt_reg.h index 7a3a78bf2d..9809faf736 100644 --- a/components/esp32/include/soc/pcnt_reg.h +++ b/components/esp32/include/soc/pcnt_reg.h @@ -1319,6 +1319,36 @@ #define PCNT_CORE_STATUS_U0_M ((PCNT_CORE_STATUS_U0_V)<<(PCNT_CORE_STATUS_U0_S)) #define PCNT_CORE_STATUS_U0_V 0xFFFFFFFF #define PCNT_CORE_STATUS_U0_S 0 +/*0: positive value to zero; 1: negative value to zero; 2: counter value negative ; 3: counter value positive*/ +#define PCNT_STATUS_CNT_MODE 0x3 +#define PCNT_STATUS_CNT_MODE_M ((PCNT_STATUS_CNT_MODE_V)<<(PCNT_STATUS_CNT_MODE_S)) +#define PCNT_STATUS_CNT_MODE_V 0x3 +#define PCNT_STATUS_CNT_MODE_S 0 +/* counter value equals to thresh1*/ +#define PCNT_STATUS_THRES1 BIT(2) +#define PCNT_STATUS_THRES1_M BIT(2) +#define PCNT_STATUS_THRES1_V 0x1 +#define PCNT_STATUS_THRES1_S 2 +/* counter value equals to thresh0*/ +#define PCNT_STATUS_THRES0 BIT(3) +#define PCNT_STATUS_THRES0_M BIT(3) +#define PCNT_STATUS_THRES0_V 0x1 +#define PCNT_STATUS_THRES0_S 3 +/* counter value reaches h_lim*/ +#define PCNT_STATUS_L_LIM BIT(4) +#define PCNT_STATUS_L_LIM_M BIT(4) +#define PCNT_STATUS_L_LIM_V 0x1 +#define PCNT_STATUS_L_LIM_S 4 +/* counter value reaches l_lim*/ +#define PCNT_STATUS_H_LIM BIT(5) +#define PCNT_STATUS_H_LIM_M BIT(5) +#define PCNT_STATUS_H_LIM_V 0x1 +#define PCNT_STATUS_H_LIM_S 5 +/* counter value equals to zero*/ +#define PCNT_STATUS_ZERO BIT(6) +#define PCNT_STATUS_ZERO_M BIT(6) +#define PCNT_STATUS_ZERO_V 0x1 +#define PCNT_STATUS_ZERO_S 6 #define PCNT_U1_STATUS_REG (DR_REG_PCNT_BASE + 0x0094) /* PCNT_CORE_STATUS_U1 : RO ;bitpos:[31:0] ;default: 32'h0 ; */ diff --git a/components/esp32/include/soc/pcnt_struct.h b/components/esp32/include/soc/pcnt_struct.h index eef64a336f..506141ba10 100644 --- a/components/esp32/include/soc/pcnt_struct.h +++ b/components/esp32/include/soc/pcnt_struct.h @@ -113,7 +113,18 @@ typedef volatile struct { }; uint32_t val; } int_clr; - uint32_t status_unit[8]; + union { + struct { + uint32_t cnt_mode:2; /*0: positive value to zero; 1: negative value to zero; 2: counter value negative ; 3: counter value positive*/ + uint32_t thres1_lat:1; /* counter value equals to thresh1*/ + uint32_t thres0_lat:1; /* counter value equals to thresh0*/ + uint32_t l_lim_lat:1; /* counter value reaches h_lim*/ + uint32_t h_lim_lat:1; /* counter value reaches l_lim*/ + uint32_t zero_lat:1; /* counter value equals zero*/ + uint32_t reserved7:25; + }; + uint32_t val; + } status_unit[8]; union { struct { uint32_t cnt_rst_u0: 1; /*Set this bit to clear unit0's counter.*/ diff --git a/components/esp32/include/soc/soc.h b/components/esp32/include/soc/soc.h index da81d75bdd..04551f61fe 100755 --- a/components/esp32/include/soc/soc.h +++ b/components/esp32/include/soc/soc.h @@ -129,10 +129,10 @@ //}} //Periheral Clock {{ -#define APB_CLK_FREQ_ROM 26*1000000 +#define APB_CLK_FREQ_ROM ( 26*1000000 ) #define CPU_CLK_FREQ_ROM APB_CLK_FREQ_ROM #define CPU_CLK_FREQ APB_CLK_FREQ -#define APB_CLK_FREQ 80*1000000 //unit: Hz +#define APB_CLK_FREQ ( 80*1000000 ) //unit: Hz #define UART_CLK_FREQ APB_CLK_FREQ #define WDT_CLK_FREQ APB_CLK_FREQ #define TIMER_CLK_FREQ (80000000>>4) //80MHz divided by 16 @@ -142,6 +142,7 @@ #define DR_REG_DPORT_BASE 0x3ff00000 #define DR_REG_RSA_BASE 0x3ff02000 +#define DR_REG_SHA_BASE 0x3ff03000 #define DR_REG_UART_BASE 0x3ff40000 #define DR_REG_SPI1_BASE 0x3ff42000 #define DR_REG_SPI0_BASE 0x3ff43000 @@ -270,7 +271,7 @@ * 6 1 timer FreeRTOS Tick(L1) FreeRTOS Tick(L1) * 7 1 software Reserved Reserved * 8 1 extern level BLE Controller - * 9 1 extern level + * 9 1 extern level EMAC * 10 1 extern edge Internal Timer * 11 3 profiling * 12 1 extern level @@ -302,6 +303,7 @@ #define ETS_FROM_CPU_INUM 2 #define ETS_T0_WDT_INUM 3 #define ETS_WBB_INUM 4 +#define ETS_EMAC_INUM 9 #define ETS_TG0_T1_INUM 10 /**< use edge interrupt*/ #define ETS_FRC1_INUM 22 #define ETS_T1_WDT_INUM 24 diff --git a/components/bt/bluedroid/api/esp_gap_bt_api.c b/components/esp32/include/soc/wdev_reg.h similarity index 78% rename from components/bt/bluedroid/api/esp_gap_bt_api.c rename to components/esp32/include/soc/wdev_reg.h index 179832af33..7189c9ec39 100644 --- a/components/bt/bluedroid/api/esp_gap_bt_api.c +++ b/components/esp32/include/soc/wdev_reg.h @@ -1,9 +1,9 @@ -// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// Copyright 2010-2016 Espressif Systems (Shanghai) PTE LTD // // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at - +// // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software @@ -12,7 +12,7 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include "esp_gap_bt_api.h" -#include "bta_api.h" -#include "bt_trace.h" +#pragma once +/* Hardware random number generator register */ +#define WDEV_RND_REG 0x60035144 diff --git a/components/esp32/include/xtensa/core-macros.h b/components/esp32/include/xtensa/core-macros.h index 663d29478a..c8f7e34762 100755 --- a/components/esp32/include/xtensa/core-macros.h +++ b/components/esp32/include/xtensa/core-macros.h @@ -42,7 +42,7 @@ * share the name with the existing functions from hal.h. * Including this header file will define XTHAL_USE_CACHE_MACROS * which directs hal.h not to use the functions. - * + */ /* * Single-cache-line operations in C-callable inline assembly. diff --git a/components/esp32/int_wdt.c b/components/esp32/int_wdt.c index fe3ddab370..9d9bbe94c4 100644 --- a/components/esp32/int_wdt.c +++ b/components/esp32/int_wdt.c @@ -28,6 +28,7 @@ #include "esp_freertos_hooks.h" #include "soc/timer_group_struct.h" #include "soc/timer_group_reg.h" +#include "driver/timer.h" #include "esp_int_wdt.h" @@ -85,7 +86,7 @@ void esp_int_wdt_init() { TIMERG1.wdt_feed=1; TIMERG1.wdt_wprotect=0; TIMERG1.int_clr_timers.wdt=1; - TIMERG1.int_ena.wdt=1; + timer_group_intr_enable(TIMER_GROUP_1, TIMG_WDT_INT_ENA_M); esp_register_freertos_tick_hook(tick_hook); ESP_INTR_DISABLE(WDT_INT_NUM); intr_matrix_set(xPortGetCoreID(), ETS_TG1_WDT_LEVEL_INTR_SOURCE, WDT_INT_NUM); @@ -97,4 +98,4 @@ void esp_int_wdt_init() { -#endif \ No newline at end of file +#endif diff --git a/components/esp32/lib b/components/esp32/lib index 93fcc0324c..3a412c08af 160000 --- a/components/esp32/lib +++ b/components/esp32/lib @@ -1 +1 @@ -Subproject commit 93fcc0324cd9b4de8ae381a876d371dfd4eff8e3 +Subproject commit 3a412c08af1ace47a58d1f8722a8fed5b8d3b944 diff --git a/components/esp32/lib_printf.c b/components/esp32/lib_printf.c new file mode 100644 index 0000000000..a2aff4cf56 --- /dev/null +++ b/components/esp32/lib_printf.c @@ -0,0 +1,133 @@ +// Copyright 2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +/** + * @file lib_printf.c + * + * This file contains library-specific printf functions + * used by WiFi libraries in the `lib` directory. + * These function are used to catch any output which gets printed + * by libraries, and redirect it to ESP_LOG macros. + * + * Eventually WiFi libraries will use ESP_LOG functions internally + * and these definitions will be removed. + */ + +#include +#include +#include "esp_log.h" +#include "esp_attr.h" + +#define VPRINTF_STACK_BUFFER_SIZE 80 + +static int lib_printf(const char* tag, const char* format, va_list arg) +{ + char temp[VPRINTF_STACK_BUFFER_SIZE]; + int len = vsnprintf(temp, sizeof(temp) - 1, format, arg); + temp[sizeof(temp) - 1] = 0; + int i; + for (i = len - 1; i >= 0; --i) { + if (temp[i] != '\n' && temp[i] != '\r' && temp[i] != ' ') { + break; + } + temp[i] = 0; + } + if (i > 0) { + ESP_EARLY_LOGI(tag, "%s", temp); + } + va_end(arg); + return len; +} + +int phy_printf(const char* format, ...) +{ + va_list arg; + va_start(arg, format); + int res = lib_printf("phy", format, arg); + va_end(arg); + return res; +} + + +int rtc_printf(const char* format, ...) +{ + va_list arg; + va_start(arg, format); + int res = lib_printf("rtc", format, arg); + va_end(arg); + return res; +} + +int wpa_printf(const char* format, ...) +{ + va_list arg; + va_start(arg, format); + int res = lib_printf("wpa", format, arg); + va_end(arg); + return res; +} + +int wpa2_printf(const char* format, ...) +{ + va_list arg; + va_start(arg, format); + int res = lib_printf("wpa2", format, arg); + va_end(arg); + return res; +} + +int wps_printf(const char* format, ...) +{ + va_list arg; + va_start(arg, format); + int res = lib_printf("wps", format, arg); + va_end(arg); + return res; +} + +int pp_printf(const char* format, ...) +{ + va_list arg; + va_start(arg, format); + int res = lib_printf("pp", format, arg); + va_end(arg); + return res; +} + +int sc_printf(const char* format, ...) +{ + va_list arg; + va_start(arg, format); + int res = lib_printf("smartconfig", format, arg); + va_end(arg); + return res; +} + +int core_printf(const char* format, ...) +{ + va_list arg; + va_start(arg, format); + int res = lib_printf("core", format, arg); + va_end(arg); + return res; +} + +int net80211_printf(const char* format, ...) +{ + va_list arg; + va_start(arg, format); + int res = lib_printf("net80211", format, arg); + va_end(arg); + return res; +} diff --git a/components/esp32/panic.c b/components/esp32/panic.c index c5d8aa669e..8f51994401 100644 --- a/components/esp32/panic.c +++ b/components/esp32/panic.c @@ -27,6 +27,7 @@ #include "soc/rtc_cntl_reg.h" #include "soc/timer_group_struct.h" #include "soc/timer_group_reg.h" +#include "soc/cpu.h" #include "esp_gdbstub.h" #include "esp_panic.h" @@ -108,21 +109,10 @@ static const char *edesc[]={ void commonErrorHandler(XtExcFrame *frame); //The fact that we've panic'ed probably means the other CPU is now running wild, possibly -//messing up the serial output, so we kill it here. -static void haltOtherCore() { - if (xPortGetCoreID()==0) { - //Kill app cpu - CLEAR_PERI_REG_MASK(RTC_CNTL_SW_CPU_STALL_REG, RTC_CNTL_SW_STALL_APPCPU_C1_M); - SET_PERI_REG_MASK(RTC_CNTL_SW_CPU_STALL_REG, 0x21< +#include +#include "soc/soc.h" + +#ifdef __cplusplus +extern "C" { +#endif + + +typedef enum{ + XTAL_40M = 40, + XTAL_26M = 26, + XTAL_24M = 24, + XTAL_AUTO = 0 +} xtal_freq_t; + +typedef enum{ + CPU_XTAL = 0, + CPU_80M = 1, + CPU_160M = 2, + CPU_240M = 3, + CPU_2M = 4 +} cpu_freq_t; + +typedef enum { + CALI_RTC_MUX = 0, + CALI_8MD256 = 1, + CALI_32K_XTAL = 2 +} cali_clk_t; + +/** + * This function must be called to initialize RTC library + * @param xtal_freq Frequency of main crystal + */ +void rtc_init_lite(xtal_freq_t xtal_freq); + +/** + * Switch CPU frequency + * @param cpu_freq new CPU frequency + */ +void rtc_set_cpu_freq(cpu_freq_t cpu_freq); + +/** + * @brief Return RTC slow clock's period + * @param cali_clk clock to calibrate + * @param slow_clk_cycles number of slow clock cycles to average + * @param xtal_freq chip's main XTAL freq + * @return average slow clock period in microseconds, Q13.19 fixed point format + */ +uint32_t rtc_slowck_cali(cali_clk_t cali_clk, uint32_t slow_clk_cycles); + +/** + * @brief Convert from microseconds to slow clock cycles + * @param time_in_us_h Time in microseconds, higher 32 bit part + * @param time_in_us_l Time in microseconds, lower 32 bit part + * @param slow_clk_period Period of slow clock in microseconds, Q13.19 fixed point format (as returned by rtc_slowck_cali). + * @param[out] cylces_h output, higher 32 bit part of number of slow clock cycles + * @param[out] cycles_l output, lower 32 bit part of number of slow clock cycles + */ +void rtc_usec2rtc(uint32_t time_in_us_h, uint32_t time_in_us_l, uint32_t slow_clk_period, uint32_t *cylces_h, uint32_t *cycles_l); + + +#define DEEP_SLEEP_PD_NORMAL BIT(0) /*!< Base deep sleep mode */ +#define DEEP_SLEEP_PD_RTC_PERIPH BIT(1) /*!< Power down RTC peripherals */ +#define DEEP_SLEEP_PD_RTC_SLOW_MEM BIT(2) /*!< Power down RTC SLOW memory */ +#define DEEP_SLEEP_PD_RTC_FAST_MEM BIT(3) /*!< Power down RTC FAST memory */ + +/** + * @brief Prepare for entering sleep mode + * @param deep_slp DEEP_SLEEP_PD_ flags combined with OR (DEEP_SLEEP_PD_NORMAL must be included) + * @param cpu_lp_mode for deep sleep, should be 0 + */ +void rtc_slp_prep_lite(uint32_t deep_slp, uint32_t cpu_lp_mode); + + +#define RTC_EXT_EVENT0_TRIG BIT(0) +#define RTC_EXT_EVENT1_TRIG BIT(1) +#define RTC_GPIO_TRIG BIT(2) +#define RTC_TIMER_EXPIRE BIT(3) +#define RTC_SDIO_TRIG BIT(4) +#define RTC_MAC_TRIG BIT(5) +#define RTC_UART0_TRIG BIT(6) +#define RTC_UART1_TRIG BIT(7) +#define RTC_TOUCH_TRIG BIT(8) +#define RTC_SAR_TRIG BIT(9) +#define RTC_BT_TRIG BIT(10) + + +#define RTC_EXT_EVENT0_TRIG_EN RTC_EXT_EVENT0_TRIG +#define RTC_EXT_EVENT1_TRIG_EN RTC_EXT_EVENT1_TRIG +#define RTC_GPIO_TRIG_EN RTC_GPIO_TRIG +#define RTC_TIMER_EXPIRE_EN RTC_TIMER_EXPIRE +#define RTC_SDIO_TRIG_EN RTC_SDIO_TRIG +#define RTC_MAC_TRIG_EN RTC_MAC_TRIG +#define RTC_UART0_TRIG_EN RTC_UART0_TRIG +#define RTC_UART1_TRIG_EN RTC_UART1_TRIG +#define RTC_TOUCH_TRIG_EN RTC_TOUCH_TRIG +#define RTC_SAR_TRIG_EN RTC_SAR_TRIG +#define RTC_BT_TRIG_EN RTC_BT_TRIG + +/** + * @brief Enter sleep mode for given number of cycles + * @param cycles_h higher 32 bit part of number of slow clock cycles + * @param cycles_l lower 32 bit part of number of slow clock cycles + * @param wakeup_opt wake up reason to enable (RTC_xxx_EN flags combined with OR) + * @param reject_opt reserved, should be 0 + * @return TBD + */ +uint32_t rtc_sleep(uint32_t cycles_h, uint32_t cycles_l, uint32_t wakeup_opt, uint32_t reject_opt); + + +#ifdef __cplusplus +} +#endif + diff --git a/components/esp32/system_api.c b/components/esp32/system_api.c new file mode 100644 index 0000000000..36a5f806da --- /dev/null +++ b/components/esp32/system_api.c @@ -0,0 +1,158 @@ +// Copyright 2013-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#include "esp_system.h" +#include "esp_attr.h" +#include "esp_wifi.h" +#include "esp_wifi_internal.h" +#include "esp_log.h" +#include "rom/efuse.h" +#include "rom/cache.h" +#include "rom/uart.h" +#include "soc/dport_reg.h" +#include "soc/efuse_reg.h" +#include "soc/rtc_cntl_reg.h" +#include "soc/timer_group_reg.h" +#include "soc/timer_group_struct.h" +#include "soc/cpu.h" +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "freertos/xtensa_api.h" + +static const char* TAG = "system_api"; + +void system_init() +{ +} + +esp_err_t esp_efuse_read_mac(uint8_t* mac) +{ + uint8_t efuse_crc; + uint8_t calc_crc; + uint32_t mac_low = REG_READ(EFUSE_BLK0_RDATA1_REG); + uint32_t mac_high = REG_READ(EFUSE_BLK0_RDATA2_REG); + + mac[0] = mac_high >> 8; + mac[1] = mac_high; + mac[2] = mac_low >> 24; + mac[3] = mac_low >> 16; + mac[4] = mac_low >> 8; + mac[5] = mac_low; + + efuse_crc = mac_high >> 16; + calc_crc = esp_crc8(mac, 6); + + if (efuse_crc != calc_crc) { + // Small range of MAC addresses are accepted even if CRC is invalid. + // These addresses are reserved for Espressif internal use. + if ((mac_high & 0xFFFF) == 0x18fe) { + if ((mac_low >= 0x346a85c7) && (mac_low <= 0x346a85f8)) { + return ESP_OK; + } + } else { + ESP_LOGE(TAG, "MAC address CRC error, efuse_crc = 0x%02x; calc_crc = 0x%02x", efuse_crc, calc_crc); + abort(); + } + } + return ESP_OK; +} + +esp_err_t system_efuse_read_mac(uint8_t mac[6]) __attribute__((alias("esp_efuse_read_mac"))); + + +void IRAM_ATTR esp_restart(void) +{ + esp_wifi_stop(); + + // Disable scheduler on this core. + vTaskSuspendAll(); + const uint32_t core_id = xPortGetCoreID(); + const uint32_t other_core_id = core_id == 0 ? 1 : 0; + esp_cpu_stall(other_core_id); + + // We need to disable TG0/TG1 watchdogs + // First enable RTC watchdog to be on the safe side + REG_WRITE(RTC_CNTL_WDTWPROTECT_REG, RTC_CNTL_WDT_WKEY_VALUE); + REG_WRITE(RTC_CNTL_WDTCONFIG0_REG, + RTC_CNTL_WDT_FLASHBOOT_MOD_EN_M | + (1 << RTC_CNTL_WDT_SYS_RESET_LENGTH_S) | + (1 << RTC_CNTL_WDT_CPU_RESET_LENGTH_S) ); + REG_WRITE(RTC_CNTL_WDTCONFIG1_REG, 128000); + + // Disable TG0/TG1 watchdogs + TIMERG0.wdt_wprotect=TIMG_WDT_WKEY_VALUE; + TIMERG0.wdt_config0.en = 0; + TIMERG0.wdt_wprotect=0; + TIMERG1.wdt_wprotect=TIMG_WDT_WKEY_VALUE; + TIMERG1.wdt_config0.en = 0; + TIMERG1.wdt_wprotect=0; + + // Disable all interrupts + xt_ints_off(0xFFFFFFFF); + + // Disable cache + Cache_Read_Disable(0); + Cache_Read_Disable(1); + + // Flush any data left in UART FIFO + uart_tx_flush(0); + uart_tx_flush(1); + uart_tx_flush(2); + + // Reset wifi/bluetooth (bb/mac) + SET_PERI_REG_MASK(DPORT_WIFI_RST_EN_REG, 0x1f); + REG_WRITE(DPORT_WIFI_RST_EN_REG, 0); + + // Reset timer/spi/uart + SET_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG, + DPORT_TIMERS_RST | DPORT_SPI_RST_1 | DPORT_UART_RST); + REG_WRITE(DPORT_PERIP_RST_EN_REG, 0); + + // Reset CPUs + if (core_id == 0) { + // Running on PRO CPU: APP CPU is stalled. Can reset both CPUs. + SET_PERI_REG_MASK(RTC_CNTL_OPTIONS0_REG, + RTC_CNTL_SW_PROCPU_RST_M | RTC_CNTL_SW_APPCPU_RST_M); + } else { + // Running on APP CPU: need to reset PRO CPU and unstall it, + // then stall APP CPU + SET_PERI_REG_MASK(RTC_CNTL_OPTIONS0_REG, RTC_CNTL_SW_PROCPU_RST_M); + esp_cpu_unstall(0); + esp_cpu_stall(1); + } + while(true) { + ; + } +} + +void system_restart(void) __attribute__((alias("esp_restart"))); + +void system_restore(void) +{ + esp_wifi_restore(); +} + +uint32_t esp_get_free_heap_size(void) +{ + return xPortGetFreeHeapSize(); +} + +uint32_t system_get_free_heap_size(void) __attribute__((alias("esp_get_free_heap_size"))); + +const char* system_get_sdk_version(void) +{ + return "master"; +} + + diff --git a/components/esp32/task_wdt.c b/components/esp32/task_wdt.c index 6f39591259..860556b8c5 100644 --- a/components/esp32/task_wdt.c +++ b/components/esp32/task_wdt.c @@ -32,6 +32,7 @@ #include "soc/timer_group_struct.h" #include "soc/timer_group_reg.h" #include "esp_log.h" +#include "driver/timer.h" #include "esp_task_wdt.h" @@ -204,9 +205,9 @@ void esp_task_wdt_init() { intr_matrix_set(xPortGetCoreID(), ETS_TG0_WDT_LEVEL_INTR_SOURCE, ETS_T0_WDT_INUM); xt_set_interrupt_handler(ETS_T0_WDT_INUM, task_wdt_isr, NULL); TIMERG0.int_clr_timers.wdt=1; - TIMERG0.int_ena.wdt=1; + timer_group_intr_enable(TIMER_GROUP_0, TIMG_WDT_INT_ENA_M); ESP_INTR_ENABLE(ETS_T0_WDT_INUM); } -#endif \ No newline at end of file +#endif diff --git a/components/esp32/test/Kconfig b/components/esp32/test/Kconfig deleted file mode 100644 index af5e5b45e7..0000000000 --- a/components/esp32/test/Kconfig +++ /dev/null @@ -1,9 +0,0 @@ -menu "TESTS" - -config FP_TEST_ENABLE - bool "Enable test fp" - default "y" - help - For FPGA single core CPU which has no floating point support, floating point test should be disabled. - -endmenu diff --git a/components/esp32/test/test_fp.c b/components/esp32/test/test_fp.c index 5c2573b227..1b88e9722c 100644 --- a/components/esp32/test/test_fp.c +++ b/components/esp32/test/test_fp.c @@ -4,7 +4,6 @@ #include "freertos/task.h" #include "unity.h" -#if CONFIG_FP_TEST_ENABLE static float addsf(float a, float b) { float result; @@ -192,4 +191,3 @@ TEST_CASE("context switch saves FP registers", "[fp]") } TEST_ASSERT(state.fail == 0); } -#endif diff --git a/components/ethernet/Kconfig b/components/ethernet/Kconfig new file mode 100644 index 0000000000..cbd3bfbe47 --- /dev/null +++ b/components/ethernet/Kconfig @@ -0,0 +1,20 @@ +menuconfig ETHERNET + bool "Enable Ethernet" + default n + help + Enable this option to enable ethernet driver and show the menu with ethernet features. + + +config DMA_RX_BUF_NUM + int "Dma Rx Buf Num" + default 10 + depends on ETHERNET + help + Dma rx buf num ,can not be 0 . + +config DMA_TX_BUF_NUM + int "Dma Tx Buf Num" + default 10 + depends on ETHERNET + help + Dma tx Buf num ,can not be 0. diff --git a/components/ethernet/component.mk b/components/ethernet/component.mk new file mode 100755 index 0000000000..c2c4c03a1a --- /dev/null +++ b/components/ethernet/component.mk @@ -0,0 +1,5 @@ +# +# Component Makefile +# +# (Uses default behaviour of compiling all source files in directory, adding 'include' to include path.) + diff --git a/components/ethernet/emac_common.h b/components/ethernet/emac_common.h new file mode 100644 index 0000000000..48f71fd90f --- /dev/null +++ b/components/ethernet/emac_common.h @@ -0,0 +1,125 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#ifndef _EMAC_COMMON_H_ +#define _EMAC_COMMON_H_ + +#include + +#include "esp_err.h" +#include "emac_dev.h" + +#ifdef __cplusplus +extern "C" { +#endif + +typedef uint32_t emac_sig_t; +typedef uint32_t emac_par_t; + +typedef struct { + emac_sig_t sig; + emac_par_t par; +} emac_event_t; + +enum emac_mode { + EMAC_MODE_RMII = 0, + EMAC_MDOE_MII, +}; + +enum emac_runtime_status { + EMAC_RUNTIME_NOT_INIT = 0, + EMAC_RUNTIME_INIT, + EMAC_RUNTIME_START, + EMAC_RUNTIME_STOP, +}; + +enum { + SIG_EMAC_TX_DONE, + SIG_EMAC_RX_DONE, + SIG_EMAC_TX, + SIG_EMAC_START, + SIG_EMAC_STOP, + SIG_EMAC_MAX +}; + +typedef void (*emac_phy_fun)(void); +typedef esp_err_t (*emac_tcpip_input_fun)(void *buffer, uint16_t len, void *eb); +typedef void (*emac_gpio_config_func)(void); + +struct emac_config_data { + unsigned int phy_addr; + enum emac_mode mac_mode; + struct dma_extended_desc *dma_etx; + unsigned int cur_tx; + unsigned int dirty_tx; + signed int cnt_tx; + struct dma_extended_desc *dma_erx; + unsigned int cur_rx; + unsigned int dirty_rx; + signed int cnt_rx; + unsigned int rx_need_poll; + bool phy_link_up; + enum emac_runtime_status emac_status; + uint8_t macaddr[6]; + emac_phy_fun phy_init; + emac_tcpip_input_fun emac_tcpip_input; + emac_gpio_config_func emac_gpio_config; +}; + +enum emac_post_type { + EMAC_POST_ASYNC, + EMAC_POST_SYNC, +}; + +struct emac_post_cmd { + void *cmd; + enum emac_post_type post_type; +}; + +struct emac_tx_cmd { + uint8_t *buf; + uint16_t size; + int8_t err; +}; + +struct emac_open_cmd { + int8_t err; +}; + +struct emac_close_cmd { + int8_t err; +}; +#if CONFIG_ETHERNET +#define DMA_RX_BUF_NUM CONFIG_DMA_RX_BUF_NUM +#define DMA_TX_BUF_NUM CONFIG_DMA_TX_BUF_NUM +#else +#define DMA_RX_BUF_NUM 1 +#define DMA_TX_BUF_NUM 1 +#endif +#define DMA_RX_BUF_SIZE 1600 +#define DMA_TX_BUF_SIZE 1600 + +//lwip err +#define ERR_OK 0 +#define ERR_MEM -1 +#define ERR_IF -16 + +#define EMAC_CMD_OK 0 +#define EMAC_CMD_FAIL -1 + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/components/ethernet/emac_desc.h b/components/ethernet/emac_desc.h new file mode 100644 index 0000000000..48bdab1276 --- /dev/null +++ b/components/ethernet/emac_desc.h @@ -0,0 +1,204 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#ifndef _EMAC_DESC_H_ +#define _EMAC_DESC_H_ + +#include "soc/soc.h" + +#ifdef __cplusplus +extern "C" { +#endif + +#define REG_EMAC_DESC_BASE 0 +#define EMAC_DESC_TDES0_REG (REG_EMAC_DESC_BASE + 0x0000) +#define EMAC_DESC_TX_OWN (BIT(31)) +#define EMAC_DESC_TX_OWN_S 31 +#define EMAC_DESC_INT_COMPL (BIT(30)) +#define EMAC_DESC_INT_COMPL_S 30 +#define EMAC_DESC_LAST_SEGMENT (BIT(29)) +#define EMAC_DESC_LAST_SEGMENT_S 29 +#define EMAC_DESC_FIRST_SEGMENT (BIT(28)) +#define EMAC_DESC_FIRST_SEGMENT_S 28 +#define EMAC_DESC_DIS_CRC (BIT(27)) +#define EMAC_DESC_DIS_CRC_S 27 +#define EMAC_DESC_DIS_PAD (BIT(26)) +#define EMAC_DESC_DIS_PAD_S 26 +#define EMAC_DESC_TX_TS_EN (BIT(25)) +#define EMAC_DESC_TX_TS_EN_S 25 +#define EMAC_DESC_CRC_REPLACE_CTRL (BIT(24)) +#define EMAC_DESC_CRC_REPLACE_CTRL_S 24 +#define EMAC_DESC_CHECKSUM_INSERT_CTRL 0x00000003 +#define EMAC_DESC_CHECKSUM_INSERT_CTRL_S 22 +#define EMAC_DESC_TX_END_OF_RING (BIT(21)) +#define EMAC_DESC_TX_END_OF_RING_S 21 +#define EMAC_DESC_SECOND_ADDR_CHAIN (BIT(20)) +#define EMAC_DESC_SECOND_ADDR_CHAIN_S 20 +#define EMAC_DESC_VLAN_INSERT_CTRL 0x00000003 +#define EMAC_DESC_VLAN_INSERT_CTRL_S 18 +#define EMAC_DESC_TX_TS_STATUS (BIT(17)) +#define EMAC_DESC_TX_TS_STATUS_S 17 +#define EMAC_DESC_TX_IP_HEAD_ERR (BIT(16)) +#define EMAC_DESC_TX_IP_HEAD_ERR_S 16 +#define EMAC_DESC_ERR_SUMMARY (BIT(15)) +#define EMAC_DESC_ERR_SUMMARY_S 15 +#define EMAC_DESC_JABBER_TO (BIT(14)) +#define EMAC_DESC_JABBER_TO_S 14 +#define EMAC_DESC_FRAME_FLUSH (BIT(13)) +#define EMAC_DESC_FRAME_FLUSH_S 13 +#define EMAC_DESC_TX_IP_PAYLAD_ERR (BIT(12)) +#define EMAC_DESC_TX_IP_PAYLAD_ERR_S 12 +#define EMAC_DESC_LOSS_OF_CARRIER (BIT(11)) +#define EMAC_DESC_LOSS_OF_CARRIER_S 11 +#define EMAC_DESC_NO_CARRIER (BIT(10)) +#define EMAC_DESC_NO_CARRIER_S 10 +#define EMAC_DESC_LATE_COLLISION_T (BIT(9)) +#define EMAC_DESC_LATE_COLLISION_T_S 9 +#define EMAC_DESC_EXCESSIVE_COLLISION (BIT(8)) +#define EMAC_DESC_EXCESSIVE_COLLISION_S 8 +#define EMAC_DESC_VLAN_FRAME (BIT(7)) +#define EMAC_DESC_VLAN_FRAME_S 7 +#define EMAC_DESC_COLLISION_COUNT 0x0000000F +#define EMAC_DESC_COLLISION_COUNT_S 3 +#define EMAC_DESC_EXCESSIVE_DEFERRAL (BIT(2)) +#define EMAC_DESC_EXCESSIVE_DEFERRAL_S 2 +#define EMAC_DESC_UNDERFLOW_ERR (BIT(1)) +#define EMAC_DESC_UNDERFLOW_ERR_S 1 +#define EMAC_DESC_DEFFER_BIT (BIT(0)) +#define EMAC_DESC_DEFFER_BIT_S 0 + +#define EMAC_DESC_TDES1_REG (REG_EMAC_DESC_BASE + 0x0004) +#define EMAC_DESC_SA_INSERT_CRTL 0x00000007 +#define EMAC_DESC_SA_INSERT_CRTL_S 29 +#define EMAC_DESC_TX_BUFFER1_SIZE 0x00001FFF +#define EMAC_DESC_TX_BUFFER1_SIZE_S 0 + +#define EMAC_DESC_TDES2_REG (REG_EMAC_DESC_BASE + 0x0008) +#define EMAC_DESC_TX_BUFFER1_ADDR_PTR 0xFFFFFFFF +#define EMAC_DESC_TX_BUFFER1_ADDR_PTR_S 0 + +#define EMAC_DESC_TDES3_REG (REG_EMAC_DESC_BASE + 0x000C) +#define EMAC_DESC_TX_NEXT_DESC_ADDR 0xFFFFFFFF +#define EMAC_DESC_TX_NEXT_DESC_ADDR_S 0 + +#define EMAC_DESC_TDES4_REG (REG_EMAC_DESC_BASE + 0x0010) + +#define EMAC_DESC_TDES5_REG (REG_EMAC_DESC_BASE + 0x0014) + +#define EMAC_DESC_TDES6_REG (REG_EMAC_DESC_BASE + 0x0018) +#define EMAC_DESC_TX_FRAME_TS_LOW 0xFFFFFFFF +#define EMAC_DESC_TX_FRAME_TS_LOW_S 0 + +#define EMAC_DESC_TDES7_REG (REG_EMAC_DESC_BASE + 0x001C) +#define EMAC_DESC_TX_FRAME_TS_HIGH 0xFFFFFFFF +#define EMAC_DESC_TX_FRAME_TS_HIGH_S 0 + +#define EMAC_DESC_RDES0_REG (REG_EMAC_DESC_BASE + 0x0000) +#define EMAC_DESC_RX_OWN (BIT(31)) +#define EMAC_DESC_RX_OWN_S 31 +#define EMAC_DESC_DEST_ADDR_FILTER_FAIL (BIT(30)) +#define EMAC_DESC_DEST_ADDR_FILTER_FAIL_S 30 +#define EMAC_DESC_FRAME_LENGTH 0x00003FFF +#define EMAC_DESC_FRAME_LENGTH_S 16 +#define EMAC_DESC_ERROR_SUMMARY (BIT(15)) +#define EMAC_DESC_ERROR_SUMMARY_S 15 +#define EMAC_DESC_DESC_ERR (BIT(14)) +#define EMAC_DESC_DESC_ERR_S 14 +#define EMAC_DESC_SOURCE_ADDR_FILTER_FAIL (BIT(13)) +#define EMAC_DESC_SOURCE_ADDR_FILTER_FAIL_S 13 +#define EMAC_DESC_LENGTH_ERR (BIT(12)) +#define EMAC_DESC_LENGTH_ERR_S 12 +#define EMAC_DESC_OVERFLOW_ERR (BIT(11)) +#define EMAC_DESC_OVERFLOW_ERR_S 11 +#define EMAC_DESC_VLAN_TAG (BIT(10)) +#define EMAC_DESC_VLAN_TAG_S 10 +#define EMAC_DESC_FRIST_DESC (BIT(9)) +#define EMAC_DESC_FRIST_DESC_S 9 +#define EMAC_DESC_LAST_DESC (BIT(8)) +#define EMAC_DESC_LAST_DESC_S 8 +#define EMAC_DESC_TS_AV_IP_CHK_ERR (BIT(7)) +#define EMAC_DESC_TS_AV_IP_CHK_ERR_S 7 +#define EMAC_DESC_LATE_COLLISION (BIT(6)) +#define EMAC_DESC_LATE_COLLISION_S 6 +#define EMAC_DESC_FRAME_TYPE (BIT(5)) +#define EMAC_DESC_FRAME_TYPE_S 5 +#define EMAC_DESC_RX_WDT_TO (BIT(4)) +#define EMAC_DESC_RX_WDT_TO_S 4 +#define EMAC_DESC_RX_ERR (BIT(3)) +#define EMAC_DESC_RX_ERR_S 3 +#define EMAC_DESC_DRIBBLE_BIT_ERR (BIT(2)) +#define EMAC_DESC_DRIBBLE_BIT_ERR_S 2 +#define EMAC_DESC_CRC_ERR (BIT(1)) +#define EMAC_DESC_CRC_ERR_S 1 +#define EMAC_DESC_EXT_STATUS_AVAIL (BIT(0)) +#define EMAC_DESC_EXT_STATUS_AVAIL_S 0 + +#define EMAC_DESC_RDES1_REG (REG_EMAC_DESC_BASE + 0x0004) +#define EMAC_DESC_DIS_INT_ON_COMPLET (BIT(31)) +#define EMAC_DESC_DIS_INT_ON_COMPLET_S 31 +#define EMAC_DESC_RX_END_OF_RING (BIT(15)) +#define EMAC_DESC_RX_END_OF_RING_S 15 +#define EMAC_DESC_RX_SECOND_ADDR_CHAIN (BIT(14)) +#define EMAC_DESC_RX_SECOND_ADDR_CHAIN_S 14 +#define EMAC_DESC_RX_BUFFER1_SIZE 0x00001FFF +#define EMAC_DESC_RX_BUFFER1_SIZE_S 0 + +#define EMAC_DESC_RDES2_REG (REG_EMAC_DESC_BASE + 0x0008) +#define EMAC_DESC_RX_BUFFER1_ADDR_PTR 0xFFFFFFFF +#define EMAC_DESC_RX_BUFFER1_ADDR_PTR_S 0 + +#define EMAC_DESC_RDES3_REG (REG_EMAC_DESC_BASE + 0x000c) +#define EMAC_DESC_RX_NEXT_DESC_ADDR 0xFFFFFFFF +#define EMAC_DESC_RX_NEXT_DESC_ADDR_S 0 + +#define EMAC_DESC_RDES4_REG (REG_EMAC_DESC_BASE + 0x0010) +#define EMAC_DESC_VLAN_TAG_PRIOR_VALUE 0x00000007 +#define EMAC_DESC_VLAN_TAG_PRIOR_VALUE_S 18 +#define EMAC_DESC_TS_DROP (BIT(14)) +#define EMAC_DESC_TS_DROP_S 14 +#define EMAC_DESC_PTP_VERSION (BIT(13)) +#define EMAC_DESC_PTP_VERSION_S 13 +#define EMAC_DESC_PTP_FRAME_TYPE (BIT(12)) +#define EMAC_DESC_PTP_FRAME_TYPE_S 12 +#define EMAC_DESC_MESSAGE_TYPE 0x0000000F +#define EMAC_DESC_MESSAGE_TYPE_S 8 +#define EMAC_DESC_IPV6_PACK_RECEIVE (BIT(7)) +#define EMAC_DESC_IPV6_PACK_RECEIVE_S 7 +#define EMAC_DESC_IPV4_PACK_RECEIVE (BIT(6)) +#define EMAC_DESC_IPV4_PACK_RECEIVE_S 6 +#define EMAC_DESC_IP_CHECKSUM_BYPASS (BIT(5)) +#define EMAC_DESC_IP_CHECKSUM_BYPASS_S 5 +#define EMAC_DESC_RX_IP_PAYLAD_ERR (BIT(4)) +#define EMAC_DESC_RX_IP_PAYLAD_ERR_S 4 +#define EMAC_DESC_RX_IP_HEAD_ERR (BIT(3)) +#define EMAC_DESC_RX_IP_HEAD_ERR_S 3 +#define EMAC_DESC_IP_PAYLOAD_TYPE 0x00000007 +#define EMAC_DESC_IP_PAYLOAD_TYPE_S 0 + +#define EMAC_DESC_RDES5_REG (REG_EMAC_DESC_BASE + 0x0014) + +#define EMAC_DESC_RDES6_REG (REG_EMAC_DESC_BASE + 0x0018) +#define EMAC_DESC_RX_FRAME_TS_LOW 0xFFFFFFFF +#define EMAC_DESC_RX_FRAME_TS_LOW_S 0 + +#define EMAC_DESC_RDES7_REG (REG_EMAC_DESC_BASE + 0x001C) +#define EMAC_DESC_RX_FRAME_TS_HIGH 0xFFFFFFFF +#define EMAC_DESC_RX_FRAME_TS_HIGH_S 0 + +#ifdef __cplusplus +} +#endif + +#endif + diff --git a/components/ethernet/emac_dev.c b/components/ethernet/emac_dev.c new file mode 100644 index 0000000000..a8095fecba --- /dev/null +++ b/components/ethernet/emac_dev.c @@ -0,0 +1,142 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#include +#include + +#include "rom/ets_sys.h" +#include "rom/gpio.h" + +#include "soc/dport_reg.h" +#include "soc/io_mux_reg.h" +#include "soc/rtc_cntl_reg.h" +#include "soc/gpio_reg.h" +#include "soc/gpio_sig_map.h" +#include "soc/emac_reg_v2.h" +#include "soc/emac_ex_reg.h" + +#include "esp_log.h" +#include "driver/gpio.h" +#include "sdkconfig.h" + +#include "emac_common.h" + +static const char *TAG = "emac"; + +void emac_poll_tx_cmd(void) +{ + //write any to wake up dma + REG_WRITE(EMAC_DMATXPOLLDEMAND_REG, 1); +} + +void emac_poll_rx_cmd(void) +{ + //write any to wake up dma + REG_WRITE(EMAC_DMARXPOLLDEMAND_REG, 1); +} + +void emac_enable_dma_tx(void) +{ + REG_SET_BIT(EMAC_DMAOPERATION_MODE_REG, EMAC_START_STOP_TRANSMISSION_COMMAND); +} + +void emac_enable_dma_rx(void) +{ + REG_SET_BIT(EMAC_DMAOPERATION_MODE_REG, EMAC_START_STOP_RECEIVE); +} + +void emac_disable_dma_tx(void) +{ + REG_CLR_BIT(EMAC_DMAOPERATION_MODE_REG, EMAC_OPERATE_SECOND_FRAME); +} + +void emac_disable_dma_rx(void) +{ + REG_CLR_BIT(EMAC_DMAOPERATION_MODE_REG, EMAC_START_STOP_RECEIVE); +} + +uint32_t emac_read_tx_cur_reg(void) +{ + return REG_READ(EMAC_DMATXCURRDESC_REG); +} + +uint32_t emac_read_rx_cur_reg(void) +{ + return REG_READ(EMAC_DMARXCURRDESC_REG); +} + +uint32_t emac_read_mac_version(void) +{ + uint32_t data = 0; + data = REG_READ(EMAC_GMACVERSION_REG); + return data; +} + +void emac_reset(void) +{ + REG_SET_BIT(EMAC_DMABUSMODE_REG, EMAC_SW_RST); + + while (REG_GET_BIT(EMAC_DMABUSMODE_REG, EMAC_SW_RST) == 1) { + //nothing to do ,if stop here,maybe emac have not clk input. + ESP_LOGI(TAG, "emac reseting ...."); + } + + ESP_LOGI(TAG, "emac reset done"); +} + +void emac_enable_clk(bool enable) +{ + if (enable == true) { + REG_SET_BIT(EMAC_CLK_EN_REG, EMAC_CLK_EN); + } else { + REG_CLR_BIT(EMAC_CLK_EN_REG, EMAC_CLK_EN); + } +} + +void emac_set_clk_mii(void) +{ + //select ex clock source + REG_SET_BIT(EMAC_EX_CLK_CTRL_REG, EMAC_EX_EXT_OSC_EN); + //ex clk enable + REG_SET_BIT(EMAC_EX_OSCCLK_CONF_REG, EMAC_EX_OSC_CLK_SEL); + + //set mii mode rx/tx clk enable + REG_SET_BIT(EMAC_EX_CLK_CTRL_REG, EMAC_EX_MII_CLK_RX_EN); + REG_SET_BIT(EMAC_EX_CLK_CTRL_REG, EMAC_EX_MII_CLK_TX_EN); +} + +void emac_dma_init(void) +{ + REG_SET_BIT(EMAC_DMAOPERATION_MODE_REG, EMAC_FORWARD_UNDERSIZED_GOOD_FRAMES); + REG_SET_BIT(EMAC_DMAOPERATION_MODE_REG, EMAC_OPERATE_SECOND_FRAME); + REG_SET_FIELD(EMAC_DMABUSMODE_REG, EMAC_PROG_BURST_LEN, 4); +} + +void emac_mac_init(void) +{ + REG_SET_BIT(EMAC_GMACCONFIG_REG, EMAC_GMACRX); + REG_SET_BIT(EMAC_GMACCONFIG_REG, EMAC_GMACTX); + REG_SET_BIT(EMAC_GMACCONFIG_REG, EMAC_GMACDUPLEX); + REG_SET_BIT(EMAC_GMACCONFIG_REG, EMAC_GMACMIIGMII); + REG_SET_BIT(EMAC_GMACCONFIG_REG, EMAC_GMACFESPEED); + REG_SET_BIT(EMAC_GMACFRAMEFILTER_REG, EMAC_PROMISCUOUS_MODE); +} + +void emac_set_clk_rmii(void) +{ + //select ex clock source + REG_SET_BIT(EMAC_EX_CLK_CTRL_REG, EMAC_EX_EXT_OSC_EN); + //ex clk enable + REG_SET_BIT(EMAC_EX_OSCCLK_CONF_REG, EMAC_EX_OSC_CLK_SEL); +} diff --git a/components/ethernet/emac_dev.h b/components/ethernet/emac_dev.h new file mode 100644 index 0000000000..ede15271eb --- /dev/null +++ b/components/ethernet/emac_dev.h @@ -0,0 +1,65 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#ifndef _EMAC_DEV_H_ +#define _EMAC_DEV_H_ + +#include +#include "soc/emac_reg_v2.h" + +#ifdef __cplusplus +extern "C" { +#endif + +#define EMAC_INTR_ENABLE_BIT (EMAC_TRANSMIT_INTERRUPT_ENABLE | EMAC_RECEIVE_INTERRUPT_ENABLE | EMAC_RECEIVE_BUFFER_UNAVAILABLE_ENABLE | EMAC_NORMAL_INTERRUPT_SUMMARY_ENABLE) + +struct dma_desc { + uint32_t desc0; + uint32_t desc1; + uint32_t desc2; + uint32_t desc3; +}; + +struct dma_extended_desc { + struct dma_desc basic; + uint32_t desc4; + uint32_t desc5; + uint32_t desc6; + uint32_t desc7; +}; + +void emac_enable_clk(bool enable); +void emac_set_clk_rmii(void); +void emac_set_clk_mii(void); +void emac_reset(void); +void emac_set_gpio_pin_rmii(void); +void emac_set_gpio_pin_mii(void); +uint32_t emac_read_mac_version(void); +void emac_dma_init(void); +void emac_mac_init(void); +void emac_enable_dma_tx(void); +void emac_poll_tx_cmd(void); +uint32_t emac_read_tx_cur_reg(void); +void emac_enable_dma_rx(void); +uint32_t emac_read_rx_cur_reg(void); +void emac_poll_rx_cmd(void); +void emac_disable_dma_tx(void); +void emac_disable_dma_rx(void); + +#ifdef __cplusplus +} +#endif + +#endif + diff --git a/components/ethernet/emac_main.c b/components/ethernet/emac_main.c new file mode 100644 index 0000000000..cbbab5149e --- /dev/null +++ b/components/ethernet/emac_main.c @@ -0,0 +1,768 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#include +#include + +#include "rom/ets_sys.h" +#include "rom/gpio.h" +#include "soc/dport_reg.h" +#include "soc/io_mux_reg.h" +#include "soc/rtc_cntl_reg.h" +#include "soc/gpio_reg.h" +#include "soc/dport_reg.h" +#include "soc/emac_ex_reg.h" +#include "soc/emac_reg_v2.h" +#include "soc/soc.h" + +#include "tcpip_adapter.h" +#include "sdkconfig.h" + +#include "esp_task_wdt.h" +#include "esp_event.h" +#include "esp_system.h" +#include "esp_err.h" +#include "esp_log.h" +#include "esp_eth.h" + +#include "emac_common.h" +#include "emac_desc.h" + +#include "freertos/xtensa_api.h" +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "freertos/queue.h" +#include "freertos/semphr.h" +#include "freertos/timers.h" + +#define EMAC_EVT_QNUM 200 +#define EMAC_SIG_MAX 50 + +static struct emac_config_data emac_config; + +static uint8_t emac_dma_rx_chain_buf[32 * DMA_RX_BUF_NUM]; +static uint8_t emac_dma_tx_chain_buf[32 * DMA_TX_BUF_NUM]; +static uint8_t emac_dma_rx_buf[DMA_RX_BUF_SIZE * DMA_RX_BUF_NUM]; +static uint8_t emac_dma_tx_buf[DMA_TX_BUF_SIZE * DMA_TX_BUF_NUM]; + +static SemaphoreHandle_t emac_g_sem; +static portMUX_TYPE g_emac_mux = portMUX_INITIALIZER_UNLOCKED; +static xTaskHandle emac_task_hdl; +static xQueueHandle emac_xqueue; +static uint8_t emac_sig_cnt[EMAC_SIG_MAX] = {0}; +static TimerHandle_t emac_timer = NULL; + +static const char *TAG = "emac"; + +static esp_err_t emac_ioctl(emac_sig_t sig, emac_par_t par); +esp_err_t emac_post(emac_sig_t sig, emac_par_t par); + +static void emac_macaddr_init(void) +{ + esp_efuse_read_mac(&(emac_config.macaddr[0])); + emac_config.macaddr[5] = emac_config.macaddr[5] + 3; +} + +void esp_eth_get_mac(uint8_t mac[6]) +{ + memcpy(mac, &(emac_config.macaddr[0]), 6); +} + +static void emac_setup_tx_desc(struct dma_extended_desc *tx_desc , uint32_t size) +{ + tx_desc->basic.desc0 = EMAC_DESC_TX_OWN | EMAC_DESC_INT_COMPL | EMAC_DESC_LAST_SEGMENT | EMAC_DESC_FIRST_SEGMENT | EMAC_DESC_SECOND_ADDR_CHAIN; + tx_desc->basic.desc1 = size & 0xfff; +} + +static void emac_clean_tx_desc(struct dma_extended_desc *tx_desc) +{ + tx_desc->basic.desc0 = 0; + tx_desc->basic.desc1 = 0; +} + +static void emac_clean_rx_desc(struct dma_extended_desc *rx_desc) +{ + rx_desc->basic.desc0 = EMAC_DESC_RX_OWN; + rx_desc->basic.desc1 = EMAC_DESC_RX_SECOND_ADDR_CHAIN | DMA_RX_BUF_SIZE; +} + +static void emac_set_tx_base_reg(void) +{ + REG_WRITE(EMAC_DMATXBASEADDR_REG, (uint32_t)(emac_config.dma_etx)); +} + +static void emac_set_rx_base_reg(void) +{ + REG_WRITE(EMAC_DMARXBASEADDR_REG, (uint32_t)(emac_config.dma_erx)); +} + +static void emac_reset_dma_chain(void) +{ + emac_config.cnt_tx = 0; + emac_config.cur_tx = 0; + emac_config.dirty_tx = 0; + + emac_config.cnt_rx = 0; + emac_config.cur_rx = 0; + emac_config.dirty_rx = 0; +} + +static void emac_init_dma_chain(void) +{ + int i; + uint32_t dma_phy; + struct dma_extended_desc *p = NULL; + + //init tx chain + emac_config.dma_etx = (struct dma_extended_desc *)(&emac_dma_tx_chain_buf[0]); + emac_config.cnt_tx = 0; + emac_config.cur_tx = 0; + emac_config.dirty_tx = 0; + + dma_phy = (uint32_t)(emac_config.dma_etx); + p = emac_config.dma_etx; + + for (i = 0; i < (DMA_TX_BUF_NUM - 1); i++ ) { + dma_phy += sizeof(struct dma_extended_desc); + emac_clean_tx_desc(p); + p->basic.desc3 = dma_phy; + p->basic.desc2 = (uint32_t)(&emac_dma_tx_buf[0]) + (i * DMA_TX_BUF_SIZE); + p++; + } + p->basic.desc3 = (uint32_t)(emac_config.dma_etx); + p->basic.desc2 = (uint32_t)(&emac_dma_tx_buf[0]) + (i * DMA_TX_BUF_SIZE); + + //init desc0 desc1 + emac_clean_tx_desc(p); + + //init rx chain + emac_config.dma_erx = (struct dma_extended_desc *)(&emac_dma_rx_chain_buf[0]); + emac_config.cnt_rx = 0; + emac_config.cur_rx = 0; + emac_config.dirty_rx = 0; + + dma_phy = (uint32_t)(emac_config.dma_erx); + p = emac_config.dma_erx; + + for (i = 0; i < (DMA_TX_BUF_NUM - 1); i++ ) { + dma_phy += sizeof(struct dma_extended_desc); + emac_clean_rx_desc(p); + p->basic.desc3 = dma_phy; + p->basic.desc2 = (uint32_t)(&emac_dma_rx_buf[0]) + (i * DMA_RX_BUF_SIZE); + p++; + } + p->basic.desc3 = (uint32_t)(emac_config.dma_erx); + p->basic.desc2 = (uint32_t)(&emac_dma_rx_buf[0]) + (i * DMA_RX_BUF_SIZE); + + //init desc0 desc1 + emac_clean_rx_desc(p); +} + +void esp_eth_smi_write(uint32_t reg_num, uint16_t value) +{ + uint32_t phy_num = emac_config.phy_addr; + + while (REG_GET_BIT(EMAC_GMACGMIIADDR_REG, EMAC_GMIIBUSY) == 1 ) { + } + + REG_WRITE(EMAC_GMACGMIIDATA_REG, value); + REG_WRITE(EMAC_GMACGMIIADDR_REG, 0x3 | ((reg_num & 0x1f) << 6) | ((phy_num & 0x1f) << 11) | ((0x3) << 2)); + + while (REG_GET_BIT(EMAC_GMACGMIIADDR_REG, EMAC_GMIIBUSY) == 1 ) { + } +} + +uint16_t esp_eth_smi_read(uint32_t reg_num) +{ + uint32_t phy_num = emac_config.phy_addr; + uint16_t value = 0; + + while (REG_GET_BIT(EMAC_GMACGMIIADDR_REG, EMAC_GMIIBUSY) == 1 ) { + } + + REG_WRITE(EMAC_GMACGMIIADDR_REG, 0x1 | ((reg_num & 0x1f) << 6) | ((phy_num & 0x1f) << 11) | (0x3 << 2)); + while (REG_GET_BIT(EMAC_GMACGMIIADDR_REG, EMAC_GMIIBUSY) == 1 ) { + } + value = (REG_READ(EMAC_GMACGMIIDATA_REG) & 0xffff); + + return value; +} + +static void emac_set_user_config_data(eth_config_t *config ) +{ + emac_config.phy_addr = config->phy_addr; + emac_config.mac_mode = config->mac_mode; + emac_config.phy_init = config->phy_init; + emac_config.emac_tcpip_input = config->tcpip_input; + emac_config.emac_gpio_config = config->gpio_config; +} + +static esp_err_t emac_verify_args(void) +{ + esp_err_t ret = ESP_OK; + + if (emac_config.phy_addr > 31) { + ESP_LOGE(TAG, "phy addr err"); + ret = ESP_FAIL; + } + + if (emac_config.mac_mode != EMAC_MODE_RMII) { + ESP_LOGE(TAG, "mac mode err,now only support RMII"); + ret = ESP_FAIL; + } + + if (emac_config.phy_init == NULL) { + ESP_LOGE(TAG, "phy_init func is null"); + ret = ESP_FAIL; + } + + if (emac_config.emac_tcpip_input == NULL) { + ESP_LOGE(TAG, "tcpip_input func is null"); + ret = ESP_FAIL; + } + + if (emac_config.emac_gpio_config == NULL) { + ESP_LOGE(TAG, "gpio config func is null"); + ret = ESP_FAIL; + } + + return ret; +} + +//TODO for mac filter +void emac_set_mac_addr(void) +{ +} + +//TODO +void emac_check_mac_addr(void) +{ +} + +static void emac_process_tx(void) +{ + uint32_t cur_tx_desc = emac_read_tx_cur_reg(); + + while (((uint32_t) & (emac_config.dma_etx[emac_config.dirty_tx].basic.desc0) != cur_tx_desc)) { + emac_clean_tx_desc(&(emac_config.dma_etx[emac_config.dirty_tx])); + emac_config.dirty_tx = (emac_config.dirty_tx + 1) % DMA_TX_BUF_NUM; + emac_config.cnt_tx --; + + if (emac_config.cnt_tx < 0) { + ESP_LOGE(TAG, "emac tx chain err"); + } + } +} + +static void emac_process_rx(void) +{ + uint32_t cur_rx_desc = emac_read_rx_cur_reg(); + + while (((uint32_t) & (emac_config.dma_erx[emac_config.dirty_rx].basic.desc0) != cur_rx_desc)) { + //copy data to lwip + emac_config.emac_tcpip_input((void *)(emac_config.dma_erx[emac_config.dirty_rx].basic.desc2), + (((emac_config.dma_erx[emac_config.dirty_rx].basic.desc0) >> EMAC_DESC_FRAME_LENGTH_S) & EMAC_DESC_FRAME_LENGTH) , NULL); + + emac_clean_rx_desc(&(emac_config.dma_erx[emac_config.dirty_rx])); + emac_config.dirty_rx = (emac_config.dirty_rx + 1) % DMA_RX_BUF_NUM; + if (emac_config.rx_need_poll != 0) { + emac_poll_rx_cmd(); + emac_config.rx_need_poll = 0; + } + //if open this ,one intr can do many intrs ? + //cur_rx_desc = emac_read_rx_cur_reg(); + } +} + +//TODO other events need to do something +static void IRAM_ATTR emac_process_intr(void *arg) +{ + uint32_t event; + event = REG_READ(EMAC_DMASTATUS_REG); + + //clr intrs + REG_WRITE(EMAC_DMASTATUS_REG, event); + + if (event & EMAC_RECV_BUF_UNAVAIL) { + emac_config.rx_need_poll = 1; + } else if (event & EMAC_TRANS_INT) { + emac_post(SIG_EMAC_TX_DONE, 0); + } else if (event & EMAC_RECV_INT) { + emac_post(SIG_EMAC_RX_DONE, 0); + } else { + //other events + } +} + +static void emac_enable_intr() +{ + //init emac intr + REG_SET_FIELD(DPORT_PRO_EMAC_INT_MAP_REG, DPORT_PRO_EMAC_INT_MAP, ETS_EMAC_INUM); + xt_set_interrupt_handler(ETS_EMAC_INUM, emac_process_intr, NULL); + xt_ints_on(1 << ETS_EMAC_INUM); + + REG_WRITE(EMAC_DMAINTERRUPT_EN_REG, EMAC_INTR_ENABLE_BIT); +} + +static void emac_disable_intr() +{ + xt_ints_off(1 << ETS_EMAC_INUM); + REG_WRITE(EMAC_DMAINTERRUPT_EN_REG, 0); +} + +static bool emac_check_phy_link_status(void) +{ + return ((esp_eth_smi_read(1) & 0x4) == 0x4 ); +} + +static void emac_process_link_updown(bool link_status) +{ + system_event_t evt; + + emac_config.phy_link_up = link_status; + + if (link_status == true) { + ESP_LOGI(TAG, "eth link_up!!!"); + emac_enable_dma_tx(); + emac_enable_dma_rx(); + ets_delay_us(200000); + evt.event_id = SYSTEM_EVENT_ETH_CONNECTED; + } else { + ESP_LOGI(TAG, "eth link_down!!!"); + emac_disable_dma_tx(); + emac_disable_dma_rx(); + evt.event_id = SYSTEM_EVENT_ETH_DISCONNECTED; + } + + esp_event_send(&evt); +} + +static void emac_hw_init(void) +{ + //init chain + emac_init_dma_chain(); + + //get hw features TODO + + //ipc TODO +} + +static esp_err_t emac_xmit(void *param) +{ + struct emac_post_cmd *post_cmd = (struct emac_post_cmd *)param; + struct emac_tx_cmd *cmd = (struct emac_tx_cmd *)(post_cmd->cmd); + esp_err_t ret = ESP_OK; + + void *buf = cmd->buf; + uint16_t size = cmd->size; + + if (emac_config.emac_status != EMAC_RUNTIME_START || emac_config.emac_status == EMAC_RUNTIME_NOT_INIT) { + ESP_LOGI(TAG, "tx netif close"); + cmd->err = ERR_IF; + ret = ESP_FAIL; + goto _exit; + } + + if (emac_config.cnt_tx == DMA_TX_BUF_NUM) { + ESP_LOGI(TAG, "tx buf full"); + cmd->err = ERR_MEM; + ret = ESP_FAIL; + goto _exit; + } + + memcpy((uint8_t *)(emac_config.dma_etx[emac_config.cur_tx].basic.desc2), (uint8_t *)buf, size); + + emac_setup_tx_desc(&(emac_config.dma_etx[emac_config.cur_tx]), size); + + emac_config.cnt_tx ++; + emac_config.cur_tx = (emac_config.cur_tx + 1) % DMA_TX_BUF_NUM ; + + emac_poll_tx_cmd(); + +_exit: + + if (post_cmd->post_type == EMAC_POST_SYNC) { + xSemaphoreGive(emac_g_sem); + } + + return ret; +} + +static void emac_init_default_data(void) +{ + emac_config.rx_need_poll = 0; +} + +void emac_link_check_func(void *pv_parameters) +{ + if (emac_config.emac_status != EMAC_RUNTIME_START || + emac_config.emac_status == EMAC_RUNTIME_NOT_INIT) { + return; + } + + if (emac_check_phy_link_status() == true ) { + if (emac_config.phy_link_up == false) { + emac_process_link_updown(true); + } + } else { + if (emac_config.phy_link_up == true) { + emac_process_link_updown(false); + } + } +} + +static bool emac_link_check_timer_init(void) +{ + emac_timer = xTimerCreate("emac_timer", (1000 / portTICK_RATE_MS), + pdTRUE, (void *)rand(), emac_link_check_func); + if (emac_timer == NULL) { + return false; + } else { + return true; + } +} + +static bool emac_link_check_timer_start(void) +{ + if (xTimerStart(emac_timer, portMAX_DELAY) != pdPASS) { + return false; + } else { + return true; + } +} + +static bool emac_link_check_timer_stop(void) +{ + if (xTimerStop(emac_timer, portMAX_DELAY) != pdPASS) { + return false; + } else { + return true; + } +} + +static bool emac_link_check_timer_delete(void) +{ + xTimerDelete(emac_timer, portMAX_DELAY); + emac_timer = NULL; + return true; +} + +static void emac_start(void *param) +{ + struct emac_post_cmd *post_cmd = (struct emac_post_cmd *)param; + struct emac_open_cmd *cmd = (struct emac_open_cmd *)(post_cmd->cmd); + + ESP_LOGI(TAG , "emac start !!!\n"); + cmd->err = EMAC_CMD_OK; + emac_enable_clk(true); + + emac_macaddr_init(); + + emac_check_mac_addr(); + + emac_set_mac_addr(); + + emac_set_tx_base_reg(); + emac_set_rx_base_reg(); + emac_mac_init(); + + emac_config.phy_init(); + + //for test + //emac_wait_linkup(); + + //mmc not support + + //ptp TODO + + //enable emac intr + emac_enable_intr(); + + emac_config.emac_status = EMAC_RUNTIME_START; + + system_event_t evt; + evt.event_id = SYSTEM_EVENT_ETH_START; + esp_event_send(&evt); + + //set a timer to check link up status + if (emac_link_check_timer_init() == true) { + if (emac_link_check_timer_start() != true) { + cmd->err = EMAC_CMD_FAIL; + emac_link_check_timer_delete(); + } + } else { + cmd->err = EMAC_CMD_FAIL; + } + + if (post_cmd->post_type == EMAC_POST_SYNC) { + xSemaphoreGive(emac_g_sem); + } + + ESP_LOGI(TAG, "emac start success !!!"); +} + +esp_err_t esp_eth_enable(void) +{ + struct emac_post_cmd post_cmd; + struct emac_open_cmd open_cmd; + + post_cmd.cmd = (void *)(&open_cmd); + open_cmd.err = EMAC_CMD_OK; + + if (emac_config.emac_status == EMAC_RUNTIME_START) { + open_cmd.err = EMAC_CMD_OK; + return open_cmd.err; + } + + if (emac_config.emac_status != EMAC_RUNTIME_NOT_INIT) { + if (emac_ioctl(SIG_EMAC_START, (emac_par_t)(&post_cmd)) != 0) { + open_cmd.err = EMAC_CMD_FAIL; + } + } else { + open_cmd.err = EMAC_CMD_FAIL; + } + return open_cmd.err; +} + +static void emac_stop(void *param) +{ + struct emac_post_cmd *post_cmd = (struct emac_post_cmd *)param; + ESP_LOGI(TAG, "emac stop"); + + emac_link_check_timer_stop(); + emac_link_check_timer_delete(); + + emac_process_link_updown(false); + + emac_disable_intr(); + emac_reset_dma_chain(); + emac_reset(); + emac_enable_clk(false); + + emac_config.emac_status = EMAC_RUNTIME_STOP; + system_event_t evt; + evt.event_id = SYSTEM_EVENT_ETH_STOP; + esp_event_send(&evt); + + if (post_cmd->post_type == EMAC_POST_SYNC) { + xSemaphoreGive(emac_g_sem); + } + + ESP_LOGI(TAG, "emac stop success !!!"); +} + +esp_err_t esp_eth_disable(void) +{ + struct emac_post_cmd post_cmd; + struct emac_close_cmd close_cmd; + + post_cmd.cmd = (void *)(&close_cmd); + close_cmd.err = EMAC_CMD_OK; + + if (emac_config.emac_status == EMAC_RUNTIME_STOP) { + close_cmd.err = EMAC_CMD_OK; + return close_cmd.err; + } + + if (emac_config.emac_status != EMAC_RUNTIME_NOT_INIT) { + if (emac_ioctl(SIG_EMAC_STOP, (emac_par_t)(&post_cmd)) != 0) { + close_cmd.err = EMAC_CMD_FAIL; + } + } else { + close_cmd.err = EMAC_CMD_FAIL; + } + return close_cmd.err; +} + +static esp_err_t emac_ioctl(emac_sig_t sig, emac_par_t par) +{ + esp_err_t ret = ESP_OK; + struct emac_post_cmd *post_cmd = (struct emac_post_cmd *)par; + xTaskHandle task_hdl = xTaskGetCurrentTaskHandle(); + + if (emac_task_hdl != task_hdl) { + post_cmd->post_type = EMAC_POST_SYNC; + if (emac_post(sig, par) != ESP_OK) { + ret = ESP_FAIL; + return ret; + }; + + if (xSemaphoreTake(emac_g_sem, portMAX_DELAY) == pdTRUE) { + return ret; + } + } else { + post_cmd->post_type = EMAC_POST_ASYNC; + switch (sig) { + case SIG_EMAC_RX_DONE: + emac_process_rx(); + break; + case SIG_EMAC_TX_DONE: + emac_process_tx(); + break; + case SIG_EMAC_TX: + emac_xmit((void *)par); + break; + case SIG_EMAC_START: + emac_start((void *)par); + break; + case SIG_EMAC_STOP: + emac_stop((void *)par); + break; + default: + ESP_LOGE(TAG, "unexpect sig %d", sig); + break; + } + } + + return ret; +} + +esp_err_t esp_eth_tx(uint8_t *buf, uint16_t size) +{ + struct emac_post_cmd post_cmd; + struct emac_tx_cmd tx_cmd; + + post_cmd.cmd = (void *)(&tx_cmd); + + if (emac_check_phy_link_status() == false) { + emac_process_link_updown(false); + tx_cmd.err = ERR_IF; + } else { + tx_cmd.buf = buf; + tx_cmd.size = size; + tx_cmd.err = ERR_OK; + + if (emac_ioctl(SIG_EMAC_TX, (emac_par_t)(&post_cmd)) != 0) { + tx_cmd.err = ERR_MEM; + } + } + + return tx_cmd.err; +} + +void emac_task(void *pv) +{ + emac_event_t e; + + for (;;) { + if (xQueueReceive(emac_xqueue, &e, (portTickType)portMAX_DELAY) == pdTRUE) { + portENTER_CRITICAL(&g_emac_mux); + emac_sig_cnt[e.sig]--; + portEXIT_CRITICAL(&g_emac_mux); + switch (e.sig) { + case SIG_EMAC_RX_DONE: + emac_process_rx(); + break; + case SIG_EMAC_TX_DONE: + emac_process_tx(); + break; + case SIG_EMAC_TX: + emac_xmit((void *)e.par); + break; + case SIG_EMAC_START: + emac_start((void *)e.par); + break; + case SIG_EMAC_STOP: + emac_stop((void *)e.par); + break; + default: + ESP_LOGE(TAG, "unexpect sig %d", e.sig); + break; + } + } + } +} + +esp_err_t IRAM_ATTR emac_post(emac_sig_t sig, emac_par_t par) +{ + portENTER_CRITICAL(&g_emac_mux); + + if (emac_sig_cnt[sig] && sig != SIG_EMAC_TX) { + portEXIT_CRITICAL(&g_emac_mux); + return ESP_OK; + } else { + emac_sig_cnt[sig]++; + portEXIT_CRITICAL(&g_emac_mux); + emac_event_t evt; + evt.sig = sig; + evt.par = par; + if (sig <= SIG_EMAC_RX_DONE) { + portBASE_TYPE tmp; + + if (xQueueSendFromISR(emac_xqueue, &evt, &tmp) != pdPASS) { + return ESP_FAIL; + } + } else { + if (xQueueSend(emac_xqueue, &evt, 10 / portTICK_RATE_MS) != pdTRUE) { + return ESP_FAIL; + } + } + } + + return ESP_OK; +} + +esp_err_t esp_eth_init(eth_config_t *config) +{ + esp_err_t ret = ESP_OK; +#if !CONFIG_ETHERNET + ESP_LOGI(TAG, "eth driver init fail,please make menuconfig and enable ethernet ."); + ret = ESP_FAIL; + goto _exit; +#endif + + emac_init_default_data(); + + if (config != NULL ) { + emac_set_user_config_data(config); + } + + ret = emac_verify_args(); + + if (ret != ESP_OK) { + goto _exit; + } + + //before set emac reg must enable clk + emac_enable_clk(true); + REG_SET_FIELD(EMAC_EX_PHYINF_CONF_REG, EMAC_EX_PHY_INTF_SEL, EMAC_EX_PHY_INTF_RMII); + + emac_dma_init(); + if (emac_config.mac_mode == EMAC_MODE_RMII) { + emac_set_clk_rmii(); + } else { + emac_set_clk_mii(); + } + + emac_config.emac_gpio_config(); + + ESP_LOGI(TAG, "mac version %04xa", emac_read_mac_version()); + emac_hw_init(); + + //watchdog TODO + + //init task for emac + emac_g_sem = xSemaphoreCreateBinary(); + emac_xqueue = xQueueCreate(EMAC_EVT_QNUM, sizeof(emac_event_t)); + xTaskCreate(emac_task, "emacT", 2048 * 4, NULL, (19), &emac_task_hdl); + + emac_reset(); + emac_enable_clk(false); + + emac_config.emac_status = EMAC_RUNTIME_INIT; + +_exit: + return ret; +} + diff --git a/components/ethernet/include/esp_eth.h b/components/ethernet/include/esp_eth.h new file mode 100644 index 0000000000..b97289dd2b --- /dev/null +++ b/components/ethernet/include/esp_eth.h @@ -0,0 +1,167 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#ifndef __ESP_ETH_H__ +#define __ESP_ETH_H__ + +#include +#include "esp_err.h" + +#ifdef __cplusplus +extern "C" { +#endif + +typedef void (*eth_phy_fun)(void); +typedef esp_err_t (*eth_tcpip_input_fun)(void *buffer, uint16_t len, void *eb); +typedef void (*eth_gpio_config_func)(void); + +typedef enum { + ETH_MODE_RMII = 0, + ETH_MDOE_MII, +} eth_mode_t; + +typedef enum { + PHY0 = 0, + PHY1, + PHY2, + PHY3, + PHY4, + PHY5, + PHY6, + PHY7, + PHY8, + PHY9, + PHY10, + PHY11, + PHY12, + PHY13, + PHY14, + PHY15, + PHY16, + PHY17, + PHY18, + PHY19, + PHY20, + PHY21, + PHY22, + PHY23, + PHY24, + PHY25, + PHY26, + PHY27, + PHY28, + PHY29, + PHY30, + PHY31, +} eth_phy_base_t; + +/** + * @brief ethernet configuration + * + */ +typedef struct { + eth_phy_base_t phy_addr; /*!< phy base addr (0~31) */ + eth_mode_t mac_mode; /*!< mac mode only support RMII now */ + eth_tcpip_input_fun tcpip_input; /*!< tcpip input func */ + eth_phy_fun phy_init; /*!< phy init func */ + eth_gpio_config_func gpio_config; /*!< gpio config func */ +} eth_config_t; + +/** + * @brief Init ethernet mac + * + * @note config can not be NULL,and phy chip must be suitable to phy init func. + * + * @param[in] config mac init data. + * + * @return + * - ESP_OK + * - ESP_FAIL + */ +esp_err_t esp_eth_init(eth_config_t *config); + +/** + * @brief Send packet from tcp/ip to mac + * + * @note buf can not be NULL,size must be less than 1580 + * + * @param[in] buf: start address of packet data. + * + * @param[in] size: size (byte) of packet data. + * + * @return + * - ESP_OK + * - ESP_FAIL + */ +esp_err_t esp_eth_tx(uint8_t *buf, uint16_t size); + +/** + * @brief Enable ethernet interface + * + * @note Shout be called after esp_eth_init + * + * @return + * - ESP_OK + * - ESP_FAIL + */ +esp_err_t esp_eth_enable(void); + +/** + * @brief Disable ethernet interface + * + * @note Shout be called after esp_eth_init + * + * @return + * - ESP_OK + * - ESP_FAIL + */ +esp_err_t esp_eth_disable(void); + +/** + * @brief Get mac addr + * + * @note mac addr must be a valid unicast address + * + * @param[out] mac: start address of mac address. + */ +void esp_eth_get_mac(uint8_t mac[6]); + +/** + * @brief Read phy reg with smi interface. + * + * @note phy base addr must be right. + * + * @param[in] reg_num: phy reg num. + * + * @param[in] value: value which write to phy reg. + */ +void esp_eth_smi_write(uint32_t reg_num, uint16_t value); + +/** + * @brief Write phy reg with smi interface. + * + * @note phy base addr must be right. + * + * @param[in] reg_num: phy reg num. + * + * @return value what read from phy reg + */ +uint16_t esp_eth_smi_read(uint32_t reg_num); + +#ifdef __cplusplus +} +#endif + +#endif + diff --git a/components/freertos/ringbuf.c b/components/freertos/ringbuf.c index 67323e3276..7074eb537d 100644 --- a/components/freertos/ringbuf.c +++ b/components/freertos/ringbuf.c @@ -609,9 +609,9 @@ void *xRingbufferReceiveUpToFromISR(RingbufHandle_t ringbuf, size_t *item_size, void vRingbufferReturnItem(RingbufHandle_t ringbuf, void *item) { ringbuf_t *rb=(ringbuf_t *)ringbuf; - portENTER_CRITICAL_ISR(&rb->mux); + portENTER_CRITICAL(&rb->mux); rb->returnItemToRingbufImpl(rb, item); - portEXIT_CRITICAL_ISR(&rb->mux); + portEXIT_CRITICAL(&rb->mux); xSemaphoreGive(rb->free_space_sem); } diff --git a/components/idf_test/unit_test/CIConfigs/UT_Function_SYS_01.yml b/components/idf_test/unit_test/CIConfigs/UT_Function_SYS_01.yml index c3561aa0c5..f4755dfec4 100644 --- a/components/idf_test/unit_test/CIConfigs/UT_Function_SYS_01.yml +++ b/components/idf_test/unit_test/CIConfigs/UT_Function_SYS_01.yml @@ -2,7 +2,6 @@ Config: {execute count: 1, execute order: in order} DUT: [UT1] Filter: - Add: - ID: [SYS_OS_0102, SYS_MISC_0103, SYS_MISC_0102, SYS_MISC_0105, SYS_MISC_0104, - SYS_MISC_0107, SYS_MISC_0106, SYS_MISC_0109, SYS_MISC_0108, SYS_MISC_0112, SYS_MISC_0113, - SYS_MISC_0110, SYS_MISC_0111, SYS_MISC_0115, SYS_LIB_0103, SYS_LIB_0102, SYS_LIB_0101, - SYS_LIB_0106, SYS_LIB_0105, SYS_LIB_0104] + ID: [SYS_OS_0102, SYS_MISC_0102, SYS_MISC_0107, SYS_MISC_0106, SYS_MISC_0109, + SYS_MISC_0108, SYS_MISC_0112, SYS_MISC_0113, SYS_MISC_0110, SYS_MISC_0111, SYS_LIB_0103, + SYS_LIB_0102, SYS_LIB_0101, SYS_LIB_0106, SYS_LIB_0105, SYS_LIB_0104] diff --git a/components/log/include/esp_log.h b/components/log/include/esp_log.h index f4b9aa2885..33bc10b42a 100644 --- a/components/log/include/esp_log.h +++ b/components/log/include/esp_log.h @@ -18,10 +18,7 @@ #include #include #include "sdkconfig.h" - -#ifdef BOOTLOADER_BUILD #include -#endif #ifdef __cplusplus extern "C" { diff --git a/components/lwip/Kconfig b/components/lwip/Kconfig index bf7bff15b4..2e7e31a8a9 100644 --- a/components/lwip/Kconfig +++ b/components/lwip/Kconfig @@ -19,7 +19,7 @@ config L2_TO_L3_COPY config LWIP_MAX_SOCKETS int "Max number of open sockets" range 1 16 - default 4 + default 10 help Sockets take up a certain amount of memory, and allowing fewer sockets to be open at the same time conserves memory. Specify diff --git a/components/lwip/api/api_msg.c b/components/lwip/api/api_msg.c index d504bfb877..2d98734b67 100755 --- a/components/lwip/api/api_msg.c +++ b/components/lwip/api/api_msg.c @@ -128,6 +128,7 @@ recv_raw(void *arg, struct raw_pcb *pcb, struct pbuf *p, len = q->tot_len; if (sys_mbox_trypost(&conn->recvmbox, buf) != ERR_OK) { + ESP_STATS_INC(esp.rx_rawmbox_post_fail); netbuf_delete(buf); return 0; } else { @@ -203,6 +204,7 @@ recv_udp(void *arg, struct udp_pcb *pcb, struct pbuf *p, len = p->tot_len; if (sys_mbox_trypost(&conn->recvmbox, buf) != ERR_OK) { + ESP_STATS_INC(esp.rx_udpmbox_post_fail); netbuf_delete(buf); return; } else { @@ -262,6 +264,7 @@ recv_tcp(void *arg, struct tcp_pcb *pcb, struct pbuf *p, err_t err) } if (sys_mbox_trypost(&conn->recvmbox, p) != ERR_OK) { + ESP_STATS_INC(esp.rx_tcpmbox_post_fail); /* don't deallocate p: it is presented to us later again from tcp_fasttmr! */ return ERR_MEM; } else { @@ -391,12 +394,16 @@ err_tcp(void *arg, err_t err) /* pass NULL-message to recvmbox to wake up pending recv */ if (sys_mbox_valid(&conn->recvmbox)) { /* use trypost to prevent deadlock */ - sys_mbox_trypost(&conn->recvmbox, NULL); + if (sys_mbox_trypost(&conn->recvmbox, NULL) != ERR_OK){ + ESP_STATS_INC(esp.err_tcp_rxmbox_post_fail); + } } /* pass NULL-message to acceptmbox to wake up pending accept */ if (sys_mbox_valid(&conn->acceptmbox)) { /* use trypost to preven deadlock */ - sys_mbox_trypost(&conn->acceptmbox, NULL); + if (sys_mbox_trypost(&conn->acceptmbox, NULL) != ERR_OK) { + ESP_STATS_INC(esp.err_tcp_rxmbox_post_fail); + } } if ((old_state == NETCONN_WRITE) || (old_state == NETCONN_CLOSE) || @@ -476,6 +483,7 @@ accept_function(void *arg, struct tcp_pcb *newpcb, err_t err) newconn->last_err = err; if (sys_mbox_trypost(&conn->acceptmbox, newconn) != ERR_OK) { + ESP_STATS_INC(esp.acceptmbox_post_fail); /* When returning != ERR_OK, the pcb is aborted in tcp_process(), so do nothing here! */ /* remove all references to this netconn from the pcb */ diff --git a/components/lwip/api/lwip_debug.c b/components/lwip/api/lwip_debug.c index d73a23e1a3..89a0712b60 100644 --- a/components/lwip/api/lwip_debug.c +++ b/components/lwip/api/lwip_debug.c @@ -18,6 +18,9 @@ #include "lwip/tcp.h" #include "lwip/udp.h" #include "lwip/priv/tcp_priv.h" +#include "lwip/stats.h" +#include "lwip/priv/memp_priv.h" +#include "lwip/memp.h" #define DBG_LWIP_IP_SHOW(info, ip) printf("%s type=%d ip=%x\n", (info), (ip).type, (ip).u_addr.ip4.addr) #define DBG_LWIP_IP_PCB_SHOW(pcb) \ @@ -127,3 +130,42 @@ void dbg_lwip_udp_rxtx_show(void) printf("TBC\n"); } +void dbg_lwip_stats_show(void) +{ + TCP_STATS_DISPLAY(); + UDP_STATS_DISPLAY(); + ICMP_STATS_DISPLAY(); + IGMP_STATS_DISPLAY(); + IP_STATS_DISPLAY(); + IPFRAG_STATS_DISPLAY(); + ETHARP_STATS_DISPLAY(); + LINK_STATS_DISPLAY(); + MEM_STATS_DISPLAY(); + SYS_STATS_DISPLAY(); + IP6_STATS_DISPLAY(); + ICMP6_STATS_DISPLAY(); + IP6_FRAG_STATS_DISPLAY(); + MLD6_STATS_DISPLAY(); + ND6_STATS_DISPLAY(); + ESP_STATS_DISPLAY(); +} + +#if (ESP_CNT_DEBUG == 1) + +uint32_t g_lwip_mem_cnt[MEMP_MAX][2]; +extern const struct memp_desc * const memp_pools[MEMP_MAX]; + +void dbg_lwip_cnt_show(void) +{ + int i=0; + + printf("-----lwip memory counter-----\n"); + printf("%6s %8s %8s\n", "index", "alloc", "free"); + for (i=0; imsg.inp.netif = inp; msg->msg.inp.input_fn = input_fn; if (sys_mbox_trypost(&mbox, msg) != ERR_OK) { -#if ESP_PERF - g_rx_post_mbox_fail_cnt ++; -#endif + ESP_STATS_INC(esp.tcpip_inpkt_post_fail); memp_free(MEMP_TCPIP_MSG_INPKT, msg); return ERR_MEM; } @@ -282,6 +277,7 @@ tcpip_callback_with_block(tcpip_callback_fn function, void *ctx, u8_t block) sys_mbox_post(&mbox, msg); } else { if (sys_mbox_trypost(&mbox, msg) != ERR_OK) { + ESP_STATS_INC(esp.tcpip_cb_post_fail); memp_free(MEMP_TCPIP_MSG_API, msg); return ERR_MEM; } @@ -497,8 +493,13 @@ tcpip_init(tcpip_init_done_fn initfunc, void *arg) #if ESP_LWIP +#if ESP_DUAL_CORE + sys_thread_t xLwipTaskHandle = 0; + xTaskCreatePinnedToCore(tcpip_thread, TCPIP_THREAD_NAME, TCPIP_THREAD_STACKSIZE, NULL, TCPIP_THREAD_PRIO, NULL, 1); +#else sys_thread_t xLwipTaskHandle = sys_thread_new(TCPIP_THREAD_NAME , tcpip_thread, NULL, TCPIP_THREAD_STACKSIZE, TCPIP_THREAD_PRIO); +#endif printf("tcpip_task_hdlxxx : %x, prio:%d,stack:%d\n", (u32_t)xLwipTaskHandle,TCPIP_THREAD_PRIO,TCPIP_THREAD_STACKSIZE); diff --git a/components/lwip/apps/dhcpserver.c b/components/lwip/apps/dhcpserver.c index 22443e8cde..fcb27f0b05 100644 --- a/components/lwip/apps/dhcpserver.c +++ b/components/lwip/apps/dhcpserver.c @@ -266,7 +266,7 @@ static u8_t *add_offer_options(u8_t *optptr) //bzero(&if_ip, sizeof(struct ip_info)); memset(&if_ip , 0x00, sizeof(tcpip_adapter_ip_info_t)); - tcpip_adapter_get_ip_info(WIFI_IF_AP, &if_ip); + tcpip_adapter_get_ip_info(ESP_IF_WIFI_AP, &if_ip); *optptr++ = DHCP_OPTION_ROUTER; *optptr++ = 4; diff --git a/components/lwip/core/ipv4/dhcp.c b/components/lwip/core/ipv4/dhcp.c index 33d13fb326..887af91fe3 100755 --- a/components/lwip/core/ipv4/dhcp.c +++ b/components/lwip/core/ipv4/dhcp.c @@ -713,7 +713,11 @@ void dhcp_cleanup(struct netif *netif) * @param netif the netif from which to remove the struct dhcp * @param cb callback for dhcp */ +#ifdef ESP_LWIP +void dhcp_set_cb(struct netif *netif, void (*cb)(struct netif*)) +#else void dhcp_set_cb(struct netif *netif, void (*cb)(void)) +#endif { LWIP_ASSERT("netif != NULL", netif != NULL); @@ -1141,7 +1145,11 @@ dhcp_bind(struct netif *netif) /* Espressif add start. */ if (dhcp->cb != NULL) { +#ifdef ESP_LWIP + dhcp->cb(netif); +#else dhcp->cb(); +#endif } /* Espressif add end. */ } diff --git a/components/lwip/core/stats.c b/components/lwip/core/stats.c index b47ab0b7fa..9936615918 100755 --- a/components/lwip/core/stats.c +++ b/components/lwip/core/stats.c @@ -180,5 +180,23 @@ stats_display(void) } #endif /* LWIP_STATS_DISPLAY */ +#if ESP_STATS +void stats_display_esp(struct stats_esp *esp) +{ + LWIP_PLATFORM_DIAG(("\nESP\n\t")); + LWIP_PLATFORM_DIAG(("esp.rx_rawmbox_post_fail: %"U32_F"\n\t", (u32_t)esp->rx_rawmbox_post_fail)); + LWIP_PLATFORM_DIAG(("esp.rx_udpmbox_post_fail: %"U32_F"\n\t", (u32_t)esp->rx_udpmbox_post_fail)); + LWIP_PLATFORM_DIAG(("esp.rx_tcpmbox_post_fail: %"U32_F"\n\t", (u32_t)esp->rx_tcpmbox_post_fail)); + LWIP_PLATFORM_DIAG(("esp.err_tcp_rxmbox_post_fail: %"U32_F"\n\t", (u32_t)esp->err_tcp_rxmbox_post_fail)); + LWIP_PLATFORM_DIAG(("esp.err_tcp_acceptmbox_post_fail: %"U32_F"\n\t", (u32_t)esp->err_tcp_acceptmbox_post_fail)); + LWIP_PLATFORM_DIAG(("esp.acceptmbox_post_fail: %"U32_F"\n\t", (u32_t)esp->acceptmbox_post_fail)); + LWIP_PLATFORM_DIAG(("esp.free_mbox_post_fail: %"U32_F"\n\t", (u32_t)esp->free_mbox_post_fail)); + LWIP_PLATFORM_DIAG(("esp.tcpip_inpkt_post_fail: %"U32_F"\n\t", (u32_t)esp->tcpip_inpkt_post_fail)); + LWIP_PLATFORM_DIAG(("esp.tcpip_cb_post_fail: %"U32_F"\n\t", (u32_t)esp->tcpip_cb_post_fail)); + LWIP_PLATFORM_DIAG(("esp.wlanif_input_pbuf_fail: %"U32_F"\n\t", (u32_t)esp->wlanif_input_pbuf_fail)); + LWIP_PLATFORM_DIAG(("esp.wlanif_outut_pbuf_fail: %"U32_F"\n\t", (u32_t)esp->wlanif_outut_pbuf_fail)); +} +#endif + #endif /* LWIP_STATS */ diff --git a/components/lwip/core/tcp.c b/components/lwip/core/tcp.c index 627df6d293..5be6864356 100755 --- a/components/lwip/core/tcp.c +++ b/components/lwip/core/tcp.c @@ -1389,59 +1389,58 @@ tcp_kill_timewait(void) } #if ESP_LWIP -/** - * Kills the oldest connection that is in FIN_WAIT_2 state. - * Called from tcp_alloc() if no more connections are available. - */ -static void tcp_kill_finwait2(void) -{ - struct tcp_pcb *pcb, *inactive; - u32_t inactivity; - /* Go through the list of FIN_WAIT_2 pcbs and get the oldest pcb. */ - inactivity = 0; - inactive = NULL; - for (pcb = tcp_active_pcbs; pcb != NULL; pcb = pcb->next) { - if (pcb->state == FIN_WAIT_2) { - if ((u32_t) (tcp_ticks - pcb->tmr) >= inactivity) { - inactivity = tcp_ticks - pcb->tmr; - inactive = pcb; - } - } - } - if (inactive != NULL) { - tcp_pcb_remove(&tcp_active_pcbs, inactive); - memp_free(MEMP_TCP_PCB, inactive); - } -} +typedef struct { + u8_t time_wait; + u8_t closing; + u8_t fin_wait2; + u8_t last_ack; + u8_t fin_wait1; + u8_t listen; + u8_t bound; + u8_t total; +}tcp_pcb_num_t; -/** - * Kills the oldest connection that is in LAST_ACK state. - * Called from tcp_alloc() if no more connections are available. - */ -static void tcp_kill_lastack(void) +void tcp_pcb_num_cal(tcp_pcb_num_t *tcp_pcb_num) { - struct tcp_pcb *pcb, *inactive; - u32_t inactivity; - /* Go through the list of LAST_ACK pcbs and get the oldest pcb. */ - inactivity = 0; - inactive = NULL; - for (pcb = tcp_active_pcbs; pcb != NULL; pcb = pcb->next) { - if (pcb->state == LAST_ACK) { - if ((u32_t) (tcp_ticks - pcb->tmr) >= inactivity) { - inactivity = tcp_ticks - pcb->tmr; - inactive = pcb; - } - } - } - if (inactive != NULL) { - tcp_pcb_remove(&tcp_active_pcbs, inactive); - memp_free(MEMP_TCP_PCB, inactive); - } + struct tcp_pcb_listen *listen; + struct tcp_pcb *pcb; + + if (!tcp_pcb_num){ + return; + } + + memset(tcp_pcb_num, 0, sizeof(*tcp_pcb_num)); + for(pcb = tcp_tw_pcbs; pcb != NULL; pcb = pcb->next) { + tcp_pcb_num->total ++; + tcp_pcb_num->time_wait ++; + } + + for (pcb = tcp_active_pcbs; pcb != NULL; pcb = pcb->next){ + tcp_pcb_num->total ++; + if (pcb->state == FIN_WAIT_2){ + tcp_pcb_num->fin_wait2 ++; + } else if (pcb->state == LAST_ACK) { + tcp_pcb_num->last_ack ++; + } else if (pcb->state == CLOSING) { + tcp_pcb_num->closing ++; + } else if (pcb->state == FIN_WAIT_1){ + tcp_pcb_num->fin_wait1 ++; + } + } + + for (listen = tcp_listen_pcbs.listen_pcbs; listen != NULL; listen = listen->next){ + tcp_pcb_num->total ++; + tcp_pcb_num->listen ++; + } + + for (pcb = tcp_bound_pcbs; pcb != NULL; pcb = pcb->next){ + tcp_pcb_num->total ++; + tcp_pcb_num->bound ++; + } } #endif - /** * Allocate a new tcp_pcb structure. * @@ -1455,34 +1454,34 @@ tcp_alloc(u8_t prio) u32_t iss; #if ESP_LWIP - /*Kills the oldest connection that is in TIME_WAIT state.*/ - u8_t time_wait_num = 0; - for(pcb = tcp_tw_pcbs; pcb != NULL; pcb = pcb->next) { - time_wait_num ++; + tcp_pcb_num_t tcp_pcb_num; + + tcp_pcb_num_cal(&tcp_pcb_num); + + if (tcp_pcb_num.total >= MEMP_NUM_TCP_PCB){ + if (tcp_pcb_num.time_wait > 0){ + tcp_kill_timewait(); + } else if (tcp_pcb_num.last_ack > 0){ + tcp_kill_state(LAST_ACK); + } else if (tcp_pcb_num.closing > 0){ + tcp_kill_state(CLOSING); + } else if (tcp_pcb_num.fin_wait2 > 0){ + tcp_kill_state(FIN_WAIT_2); + } else if (tcp_pcb_num.fin_wait1 > 0){ + tcp_kill_state(FIN_WAIT_1); + } else { + tcp_kill_prio(prio); + } } - if (time_wait_num >= MEMP_NUM_TCP_PCB) - tcp_kill_timewait(); - - /*Kills the oldest connection that is in FIN_WAIT_2 state.*/ - time_wait_num = 0; - for (pcb = tcp_active_pcbs; pcb != NULL; pcb = pcb->next){ - if (pcb->state == FIN_WAIT_2) - time_wait_num ++; + tcp_pcb_num_cal(&tcp_pcb_num); + if (tcp_pcb_num.total >= MEMP_NUM_TCP_PCB){ + LWIP_DEBUGF(TCP_DEBUG, ("tcp_alloc: no available tcp pcb %d %d %d %d %d %d %d %d\n", + tcp_pcb_num.total, tcp_pcb_num.time_wait, tcp_pcb_num.last_ack, tcp_pcb_num.closing, + tcp_pcb_num.fin_wait2, tcp_pcb_num.fin_wait1, tcp_pcb_num.listen, tcp_pcb_num.bound)); + return NULL; } - if (time_wait_num >= MEMP_NUM_TCP_PCB) - tcp_kill_finwait2(); - - /*Kills the oldest connection that is in LAST_ACK state.*/ - time_wait_num = 0; - for (pcb = tcp_active_pcbs; pcb != NULL; pcb = pcb->next){ - if (pcb->state == LAST_ACK) - time_wait_num ++; - } - - if (time_wait_num >= MEMP_NUM_TCP_PCB) - tcp_kill_lastack(); #endif pcb = (struct tcp_pcb *)memp_malloc(MEMP_TCP_PCB); diff --git a/components/lwip/core/tcp_out.c b/components/lwip/core/tcp_out.c index 35a8aa145d..fbe879124a 100755 --- a/components/lwip/core/tcp_out.c +++ b/components/lwip/core/tcp_out.c @@ -176,7 +176,8 @@ tcp_create_segment(struct tcp_pcb *pcb, struct pbuf *p, u8_t flags, u32_t seqno, struct tcp_seg *seg; u8_t optlen = LWIP_TCP_OPT_LENGTH(optflags); - if ((seg = (struct tcp_seg *)memp_malloc(MEMP_TCP_SEG)) == NULL) { + seg = (struct tcp_seg *)memp_malloc(MEMP_TCP_SEG); + if (seg == NULL) { LWIP_DEBUGF(TCP_OUTPUT_DEBUG | LWIP_DBG_LEVEL_SERIOUS, ("tcp_create_segment: no memory.\n")); pbuf_free(p); return NULL; diff --git a/components/lwip/include/lwip/lwip/dhcp.h b/components/lwip/include/lwip/lwip/dhcp.h index 76ce1543ff..c3a057ac0f 100755 --- a/components/lwip/include/lwip/lwip/dhcp.h +++ b/components/lwip/include/lwip/lwip/dhcp.h @@ -96,7 +96,11 @@ struct dhcp #endif /* LWIP_DHCP_BOOTPFILE */ /* Espressif add start. */ +#ifdef ESP_LWIP + void (*cb)(struct netif*); /* callback for dhcp, add a parameter to show dhcp status if needed */ +#else void (*cb)(void); /* callback for dhcp, add a parameter to show dhcp status if needed */ +#endif /* Espressif add end. */ }; @@ -146,7 +150,11 @@ void dhcp_set_struct(struct netif *netif, struct dhcp *dhcp); void dhcp_cleanup(struct netif *netif); /* Espressif add start. */ /** set callback for DHCP */ +#ifdef ESP_LWIP +void dhcp_set_cb(struct netif *netif, void (*cb)(struct netif*)); +#else void dhcp_set_cb(struct netif *netif, void (*cb)(void)); +#endif /* Espressif add end. */ /** start DHCP configuration */ err_t dhcp_start(struct netif *netif); diff --git a/components/lwip/include/lwip/lwip/lwip_debug.h b/components/lwip/include/lwip/lwip/lwip_debug.h index abfcd2c1c3..4da520269a 100644 --- a/components/lwip/include/lwip/lwip/lwip_debug.h +++ b/components/lwip/include/lwip/lwip/lwip_debug.h @@ -20,5 +20,6 @@ void dbg_lwip_tcp_pcb_show(void); void dbg_lwip_udp_pcb_show(void); void dbg_lwip_tcp_rxtx_show(void); void dbg_lwip_udp_rxtx_show(void); +void dbg_lwip_mem_cnt_show(void); #endif diff --git a/components/lwip/include/lwip/lwip/memp.h b/components/lwip/include/lwip/lwip/memp.h index d7463f2b33..fc45d54ad4 100755 --- a/components/lwip/include/lwip/lwip/memp.h +++ b/components/lwip/include/lwip/lwip/memp.h @@ -71,8 +71,25 @@ extern const struct memp_desc* const memp_pools[MEMP_MAX]; #include "lwip/mem.h" #define memp_init() +#if ESP_CNT_DEBUG +static inline void* memp_malloc(int type) +{ + ESP_CNT_MEM_MALLOC_INC(type); + return mem_malloc(memp_pools[type]->size); +} + +static inline void memp_free(int type, void *mem) +{ + ESP_CNT_MEM_FREE_INC(type); + mem_free(mem); +} + +//#define memp_malloc(type) mem_malloc(memp_pools[type]->size); ESP_CNT_MEM_MALLOC_INC(type) +//#define memp_free(type, mem) mem_free(mem); ESP_CNT_MEM_FREE_INC(type) +#else #define memp_malloc(type) mem_malloc(memp_pools[type]->size) #define memp_free(type, mem) mem_free(mem) +#endif #define LWIP_MEMPOOL_DECLARE(name,num,size,desc) \ const struct memp_desc memp_ ## name = { \ diff --git a/components/lwip/include/lwip/lwip/priv/memp_priv.h b/components/lwip/include/lwip/lwip/priv/memp_priv.h index 34edb9d971..7bfa94d789 100755 --- a/components/lwip/include/lwip/lwip/priv/memp_priv.h +++ b/components/lwip/include/lwip/lwip/priv/memp_priv.h @@ -140,6 +140,16 @@ struct memp_desc { #endif /* MEMP_MEM_MALLOC */ }; +#if (ESP_CNT_DEBUG == 1) +extern uint32_t g_lwip_mem_cnt[MEMP_MAX][2]; +#define ESP_CNT_MEM_MALLOC_INC(type) g_lwip_mem_cnt[type][0]++ +#define ESP_CNT_MEM_FREE_INC(type) g_lwip_mem_cnt[type][1]++ +#else +#define ESP_CNT_MEM_MALLOC_INC(type) +#define ESP_CNT_MEM_FREE_INC(type) +#endif + + #ifdef LWIP_DEBUG #define DECLARE_LWIP_MEMPOOL_DESC(desc) (desc), #else diff --git a/components/lwip/include/lwip/lwip/stats.h b/components/lwip/include/lwip/lwip/stats.h index 176723d27f..fd6a4076a7 100755 --- a/components/lwip/include/lwip/lwip/stats.h +++ b/components/lwip/include/lwip/lwip/stats.h @@ -213,6 +213,23 @@ struct stats_mib2_netif_ctrs { u32_t ifouterrors; }; +struct stats_esp { + /* mbox post fail stats */ + u32_t rx_rawmbox_post_fail; + u32_t rx_udpmbox_post_fail; + u32_t rx_tcpmbox_post_fail; + u32_t err_tcp_rxmbox_post_fail; + u32_t err_tcp_acceptmbox_post_fail; + u32_t acceptmbox_post_fail; + u32_t free_mbox_post_fail; + u32_t tcpip_inpkt_post_fail; + u32_t tcpip_cb_post_fail; + + /* memory malloc/free/failed stats */ + u32_t wlanif_input_pbuf_fail; + u32_t wlanif_outut_pbuf_fail; +}; + struct stats_ { #if LINK_STATS struct stats_proto link; @@ -265,6 +282,9 @@ struct stats_ { #if MIB2_STATS struct stats_mib2 mib2; #endif +#if ESP_STATS + struct stats_esp esp; +#endif }; extern struct stats_ lwip_stats; @@ -438,6 +458,14 @@ void stats_init(void); #define MIB2_STATS_INC(x) #endif +#if ESP_STATS +#define ESP_STATS_INC(x) STATS_INC(x) +#define ESP_STATS_DISPLAY() stats_display_esp(&lwip_stats.esp); +#else +#define ESP_STATS_INC(x) +#define ESP_STATS_DISPLAY() +#endif + /* Display of statistics */ #if LWIP_STATS_DISPLAY void stats_display(void); @@ -446,6 +474,7 @@ void stats_display_igmp(struct stats_igmp *igmp, const char *name); void stats_display_mem(struct stats_mem *mem, const char *name); void stats_display_memp(struct stats_mem *mem, int index); void stats_display_sys(struct stats_sys *sys); +void stats_display_esp(struct stats_esp *esp); #else /* LWIP_STATS_DISPLAY */ #define stats_display() #define stats_display_proto(proto, name) @@ -453,6 +482,7 @@ void stats_display_sys(struct stats_sys *sys); #define stats_display_mem(mem, name) #define stats_display_memp(mem, index) #define stats_display_sys(sys) +#define stats_display_esp(esp) #endif /* LWIP_STATS_DISPLAY */ #ifdef __cplusplus diff --git a/components/lwip/include/lwip/port/lwipopts.h b/components/lwip/include/lwip/port/lwipopts.h index 6786ff711a..8612eb11b0 100755 --- a/components/lwip/include/lwip/port/lwipopts.h +++ b/components/lwip/include/lwip/port/lwipopts.h @@ -379,22 +379,21 @@ * The queue size value itself is platform-dependent, but is passed to * sys_mbox_new() when tcpip_init is called. */ -#define TCPIP_MBOX_SIZE 16 +#define TCPIP_MBOX_SIZE 32 /** * DEFAULT_UDP_RECVMBOX_SIZE: The mailbox size for the incoming packets on a * NETCONN_UDP. The queue size value itself is platform-dependent, but is passed * to sys_mbox_new() when the recvmbox is created. */ -#define DEFAULT_UDP_RECVMBOX_SIZE 16 +#define DEFAULT_UDP_RECVMBOX_SIZE 6 /** * DEFAULT_TCP_RECVMBOX_SIZE: The mailbox size for the incoming packets on a * NETCONN_TCP. The queue size value itself is platform-dependent, but is passed * to sys_mbox_new() when the recvmbox is created. */ -#define DEFAULT_TCP_RECVMBOX_SIZE 16 -//#define DEFAULT_TCP_RECVMBOX_SIZE 6 +#define DEFAULT_TCP_RECVMBOX_SIZE 6 /** * DEFAULT_ACCEPTMBOX_SIZE: The mailbox size for the incoming connections. @@ -556,6 +555,7 @@ */ #define TCPIP_DEBUG LWIP_DBG_OFF + /* Enable all Espressif-only options */ #define ESP_LWIP 1 @@ -571,6 +571,8 @@ #define ESP_IP4_ATON 1 #define ESP_LIGHT_SLEEP 1 #define ESP_L2_TO_L3_COPY CONFIG_L2_TO_L3_COPY +#define ESP_CNT_DEBUG 0 +#define ESP_DUAL_CORE 0 #define TCP_WND_DEFAULT (4*TCP_MSS) #define TCP_SND_BUF_DEFAULT (2*TCP_MSS) @@ -593,7 +595,6 @@ extern unsigned char misc_prof_get_tcp_snd_buf(void); #define DHCP_DEBUG LWIP_DBG_OFF #define LWIP_DEBUG LWIP_DBG_OFF #define TCP_DEBUG LWIP_DBG_OFF -#define ESP_THREAD_SAFE_DEBUG LWIP_DBG_OFF #define CHECKSUM_CHECK_UDP 0 #define CHECKSUM_CHECK_IP 0 diff --git a/components/lwip/include/lwip/port/netif/ethernetif.h b/components/lwip/include/lwip/port/netif/ethernetif.h new file mode 100755 index 0000000000..134e8eb5fe --- /dev/null +++ b/components/lwip/include/lwip/port/netif/ethernetif.h @@ -0,0 +1,35 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + + +#ifndef _ETH_LWIP_IF_H_ +#define _ETH_LWIP_IF_H_ + +#include "lwip/err.h" + +#ifdef __cplusplus +extern "C" { +#endif + +err_t ethernetif_init(struct netif *netif); + +void ethernetif_input(struct netif *netif, void *buffer, u16_t len); + +void netif_reg_addr_change_cb(void* cb); + +#ifdef __cplusplus +} +#endif + +#endif /* _ETH_LWIP_IF_H_ */ diff --git a/components/lwip/include/lwip/port/netif/wlanif.h b/components/lwip/include/lwip/port/netif/wlanif.h index c6f7831b3d..5a93640f19 100755 --- a/components/lwip/include/lwip/port/netif/wlanif.h +++ b/components/lwip/include/lwip/port/netif/wlanif.h @@ -1,7 +1,17 @@ -/* - * Copyright (c) 2010-2011 Espressif System - * -*/ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + #ifndef _WLAN_LWIP_IF_H_ #define _WLAN_LWIP_IF_H_ diff --git a/components/lwip/port/freertos/sys_arch.c b/components/lwip/port/freertos/sys_arch.c index 15ba3011d9..8d0dd08c58 100755 --- a/components/lwip/port/freertos/sys_arch.c +++ b/components/lwip/port/freertos/sys_arch.c @@ -37,6 +37,7 @@ #include "lwip/sys.h" #include "lwip/mem.h" #include "arch/sys_arch.h" +#include "lwip/stats.h" /* This is the number of threads that can be started with sys_thread_new() */ #define SYS_THREAD_MAX 4 @@ -370,6 +371,7 @@ sys_mbox_free(sys_mbox_t *mbox) if (post_null){ LWIP_DEBUGF(ESP_THREAD_SAFE_DEBUG, ("sys_mbox_free: post null to mbox\n")); if (sys_mbox_trypost( mbox, NULL) != ERR_OK){ + ESP_STATS_INC(esp.free_mbox_post_fail); LWIP_DEBUGF(ESP_THREAD_SAFE_DEBUG, ("sys_mbox_free: post null mbox fail\n")); } else { post_null = false; diff --git a/components/lwip/port/netif/ethernetif.c b/components/lwip/port/netif/ethernetif.c new file mode 100755 index 0000000000..c6f08ec832 --- /dev/null +++ b/components/lwip/port/netif/ethernetif.c @@ -0,0 +1,235 @@ +/** + * @file + * Ethernet Interface Skeleton + * + */ + +/* + * Copyright (c) 2001-2004 Swedish Institute of Computer Science. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT + * SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT + * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY + * OF SUCH DAMAGE. + * + * This file is part of the lwIP TCP/IP stack. + * + * Author: Adam Dunkels + * + */ + +#include "lwip/opt.h" + +#include "lwip/def.h" +#include "lwip/mem.h" +#include "lwip/pbuf.h" +#include "lwip/stats.h" +#include "lwip/snmp.h" +#include "lwip/ethip6.h" +#include "netif/etharp.h" +#include +#include + +#include "esp_eth.h" +#include "tcpip_adapter.h" + +/* Define those to better describe your network interface. */ +#define IFNAME0 'e' +#define IFNAME1 'n' + +static char hostname[16]; +#if ESP_PERF +uint32_t g_rx_alloc_pbuf_fail_cnt = 0; +#endif + +/** + * In this function, the hardware should be initialized. + * Called from ethernetif_init(). + * + * @param netif the already initialized lwip network interface structure + * for this ethernetif + */ +static void +ethernet_low_level_init(struct netif *netif) +{ + /* set MAC hardware address length */ + netif->hwaddr_len = ETHARP_HWADDR_LEN; + + /* set MAC hardware address */ + + /* maximum transfer unit */ + netif->mtu = 1500; + + /* device capabilities */ + /* don't set NETIF_FLAG_ETHARP if this device is not an ethernet one */ + netif->flags = NETIF_FLAG_BROADCAST | NETIF_FLAG_ETHARP | NETIF_FLAG_LINK_UP; + +#if ESP_LWIP +#if LWIP_IGMP + + netif->flags |= NETIF_FLAG_IGMP; +#endif +#endif + /* Do whatever else is needed to initialize interface. */ +} + +/** + * This function should do the actual transmission of the packet. The packet is + * contained in the pbuf that is passed to the function. This pbuf + * might be chained. + * + * @param netif the lwip network interface structure for this ethernetif + * @param p the MAC packet to send (e.g. IP packet including MAC addresses and type) + * @return ERR_OK if the packet could be sent + * an err_t value if the packet couldn't be sent + * + * @note Returning ERR_MEM here if a DMA queue of your MAC is full can lead to + * strange results. You might consider waiting for space in the DMA queue + * to become availale since the stack doesn't retry to send a packet + * dropped because of memory failure (except for the TCP timers). + */ +static err_t +ethernet_low_level_output(struct netif *netif, struct pbuf *p) +{ + struct pbuf *q; + esp_interface_t eth_if = tcpip_adapter_get_esp_if(netif); + + if (eth_if != ESP_IF_ETH) { + printf("eth_if=%d netif=%p pbuf=%p len=%d\n", eth_if, netif, p, p->len); + return ERR_IF; + } + +#if ESP_LWIP + q = p; + u16_t pbuf_x_len = 0; + pbuf_x_len = q->len; + if(q->next !=NULL) + { + //char cnt = 0; + struct pbuf *tmp = q->next; + while(tmp != NULL) + { + memcpy( (u8_t *)( (u8_t *)(q->payload) + pbuf_x_len), (u8_t *)tmp->payload , tmp->len ); + pbuf_x_len += tmp->len; + //cnt++; + tmp = tmp->next; + } + } + + //printf("netif=%p pbuf=%p len=%d\n", netif, p, p->len); + return esp_eth_tx(q->payload, pbuf_x_len); +#else + for(q = p; q != NULL; q = q->next) { + return esp_emac_tx(q->payload, q->len); + } + return ERR_OK; +#endif +} + +/** + * This function should be called when a packet is ready to be read + * from the interface. It uses the function low_level_input() that + * should handle the actual reception of bytes from the network + * interface. Then the type of the received packet is determined and + * the appropriate input function is called. + * + * @param netif the lwip network interface structure for this ethernetif + */ +void +ethernetif_input(struct netif *netif, void *buffer, uint16_t len) +{ + struct pbuf *p; + + if(buffer== NULL || netif == NULL) + goto _exit; + + p = pbuf_alloc(PBUF_RAW, len, PBUF_RAM); + if (p == NULL) { + //g_rx_alloc_pbuf_fail_cnt++; + return; + } + memcpy(p->payload, buffer, len); + + /* full packet send to tcpip_thread to process */ + if (netif->input(p, netif) != ERR_OK) { + LWIP_DEBUGF(NETIF_DEBUG, ("ethernetif_input: IP input error\n")); + pbuf_free(p); + } + +_exit: +; +} + +/** + * Should be called at the beginning of the program to set up the + * network interface. It calls the function low_level_init() to do the + * actual setup of the hardware. + * + * This function should be passed as a parameter to netif_add(). + * + * @param netif the lwip network interface structure for this ethernetif + * @return ERR_OK if the loopif is initialized + * ERR_MEM if private data couldn't be allocated + * any other err_t on error + */ +err_t +ethernetif_init(struct netif *netif) +{ + LWIP_ASSERT("netif != NULL", (netif != NULL)); + +#if LWIP_NETIF_HOSTNAME + /* Initialize interface hostname */ + +#if ESP_LWIP + sprintf(hostname, "ESP_%02X%02X%02X", netif->hwaddr[3], netif->hwaddr[4], netif->hwaddr[5]); + netif->hostname = hostname; + +#else + sprintf(hostname, "ESP_%02X%02X%02X", netif->hwaddr[3], netif->hwaddr[4], netif->hwaddr[5]); + netif->hostname = hostname; +#endif + +#endif /* LWIP_NETIF_HOSTNAME */ + + /* + * Initialize the snmp variables and counters inside the struct netif. + * The last argument should be replaced with your link speed, in units + * of bits per second. + */ + NETIF_INIT_SNMP(netif, snmp_ifType_ethernet_csmacd, LINK_SPEED_OF_YOUR_NETIF_IN_BPS); + + netif->name[0] = IFNAME0; + netif->name[1] = IFNAME1; + /* We directly use etharp_output() here to save a function call. + * You can instead declare your own function an call etharp_output() + * from it if you have to do some checks before sending (e.g. if link + * is available...) */ + netif->output = etharp_output; +#if LWIP_IPV6 + netif->output_ip6 = ethip6_output; +#endif /* LWIP_IPV6 */ + netif->linkoutput = ethernet_low_level_output; + + /* initialize the hardware */ + ethernet_low_level_init(netif); + + return ERR_OK; +} diff --git a/components/lwip/port/netif/wlanif.c b/components/lwip/port/netif/wlanif.c index f5d34179af..efaa76a73f 100755 --- a/components/lwip/port/netif/wlanif.c +++ b/components/lwip/port/netif/wlanif.c @@ -118,11 +118,11 @@ low_level_init(struct netif *netif) static err_t low_level_output(struct netif *netif, struct pbuf *p) { - wifi_interface_t wifi_if = tcpip_adapter_get_wifi_if(netif); + wifi_interface_t wifi_if = tcpip_adapter_get_esp_if(netif); struct pbuf *q = p; err_t ret; - if (wifi_if >= WIFI_IF_MAX) { + if (wifi_if >= ESP_IF_MAX) { return ERR_IF; } @@ -161,12 +161,9 @@ wlanif_input(struct netif *netif, void *buffer, u16_t len, void* eb) goto _exit; #if (ESP_L2_TO_L3_COPY == 1) - //p = pbuf_alloc(PBUF_IP, len, PBUF_POOL); p = pbuf_alloc(PBUF_RAW, len, PBUF_RAM); if (p == NULL) { - #if ESP_PERF - g_rx_alloc_pbuf_fail_cnt++; - #endif + ESP_STATS_INC(esp.wlanif_input_pbuf_fail); esp_wifi_internal_free_rx_buffer(eb); return; } @@ -175,9 +172,7 @@ wlanif_input(struct netif *netif, void *buffer, u16_t len, void* eb) #else p = pbuf_alloc(PBUF_RAW, len, PBUF_REF); if (p == NULL){ - #if ESP_PERF - g_rx_alloc_pbuf_fail_cnt++; - #endif + ESP_STATS_INC(esp.wlanif_input_pbuf_fail); return; } p->payload = buffer; @@ -241,7 +236,7 @@ wlanif_init(struct netif *netif) * The last argument should be replaced with your link speed, in units * of bits per second. */ - NETIF_INIT_SNMP(netif, snmp_ifType_ethernet_csmacd, LINK_SPEED_OF_YOUR_NETIF_IN_BPS); + NETIF_INIT_SNMP(netif, snmp_ifType_ethernet_csmacd, 100); netif->name[0] = IFNAME0; netif->name[1] = IFNAME1; diff --git a/components/mbedtls/Kconfig b/components/mbedtls/Kconfig index d6e2a2dcb7..1e347582f0 100644 --- a/components/mbedtls/Kconfig +++ b/components/mbedtls/Kconfig @@ -69,4 +69,16 @@ config MBEDTLS_MPI_INTERRUPT_NUM CPU interrupt number for MPI interrupt to connect to. Must be otherwise unused. Eventually this assignment will be handled automatically at runtime. +config MBEDTLS_HARDWARE_SHA + bool "Enable hardware SHA acceleration" + default y + help + Enable hardware accelerated SHA1, SHA256, SHA384 & SHA512 in mbedTLS. + + Due to a hardware limitation, hardware acceleration is only + guaranteed if SHA digests are calculated one at a time. If more + than one SHA digest is calculated at the same time, only will + be calculated fully in hardware and the rest will be calculated + (at least partially calculated) in software. + endmenu diff --git a/components/mbedtls/component.mk b/components/mbedtls/component.mk index bd7209a926..d2cd0455f5 100644 --- a/components/mbedtls/component.mk +++ b/components/mbedtls/component.mk @@ -5,4 +5,3 @@ COMPONENT_ADD_INCLUDEDIRS := port/include include COMPONENT_SRCDIRS := library port - diff --git a/components/mbedtls/port/esp_bignum.c b/components/mbedtls/port/esp_bignum.c index ec2e420398..2fe4d920c3 100644 --- a/components/mbedtls/port/esp_bignum.c +++ b/components/mbedtls/port/esp_bignum.c @@ -34,6 +34,8 @@ #include "esp_intr.h" #include "esp_attr.h" +#include "soc/dport_reg.h" + #include "freertos/FreeRTOS.h" #include "freertos/task.h" #include "freertos/semphr.h" @@ -72,7 +74,16 @@ void esp_mpi_acquire_hardware( void ) { /* newlib locks lazy initialize on ESP-IDF */ _lock_acquire(&mpi_lock); - ets_bigint_enable(); + REG_SET_BIT(DPORT_PERI_CLK_EN_REG, DPORT_PERI_EN_RSA); + /* also clear reset on digital signature, otherwise RSA is held in reset */ + REG_CLR_BIT(DPORT_PERI_RST_EN_REG, + DPORT_PERI_EN_RSA + | DPORT_PERI_EN_DIGITAL_SIGNATURE); + + REG_CLR_BIT(DPORT_RSA_PD_CTRL_REG, DPORT_RSA_PD); + + while(REG_READ(RSA_CLEAN_REG) != 1); + #ifdef CONFIG_MBEDTLS_MPI_USE_INTERRUPT rsa_isr_initialise(); #endif @@ -80,7 +91,12 @@ void esp_mpi_acquire_hardware( void ) void esp_mpi_release_hardware( void ) { - ets_bigint_disable(); + REG_SET_BIT(DPORT_RSA_PD_CTRL_REG, DPORT_RSA_PD); + + /* don't reset digital signature unit, as this resets AES also */ + REG_SET_BIT(DPORT_PERI_RST_EN_REG, DPORT_PERI_EN_RSA); + REG_CLR_BIT(DPORT_PERI_CLK_EN_REG, DPORT_PERI_EN_RSA); + _lock_release(&mpi_lock); } diff --git a/components/mbedtls/port/esp_sha1.c b/components/mbedtls/port/esp_sha1.c new file mode 100644 index 0000000000..6751596933 --- /dev/null +++ b/components/mbedtls/port/esp_sha1.c @@ -0,0 +1,395 @@ +/* + * SHA-1 implementation with hardware ESP32 support added. + * Uses mbedTLS software implementation for failover when concurrent + * SHA operations are in use. + * + * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved + * Additions Copyright (C) 2016, Espressif Systems (Shanghai) PTE LTD + * SPDX-License-Identifier: Apache-2.0 + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ +/* + * The SHA-1 standard was published by NIST in 1993. + * + * http://www.itl.nist.gov/fipspubs/fip180-1.htm + */ + +#if !defined(MBEDTLS_CONFIG_FILE) +#include "mbedtls/config.h" +#else +#include MBEDTLS_CONFIG_FILE +#endif + +#if defined(MBEDTLS_SHA1_C) && defined(MBEDTLS_SHA1_ALT) + +#include "mbedtls/sha1.h" + +#include + +#if defined(MBEDTLS_SELF_TEST) +#if defined(MBEDTLS_PLATFORM_C) +#include "mbedtls/platform.h" +#else +#include +#define mbedtls_printf printf +#endif /* MBEDTLS_PLATFORM_C */ +#endif /* MBEDTLS_SELF_TEST */ + +#include "hwcrypto/sha.h" + +/* Implementation that should never be optimized out by the compiler */ +static void mbedtls_zeroize( void *v, size_t n ) { + volatile unsigned char *p = (unsigned char*)v; while( n-- ) *p++ = 0; +} + +/* + * 32-bit integer manipulation macros (big endian) + */ +#ifndef GET_UINT32_BE +#define GET_UINT32_BE(n,b,i) \ +{ \ + (n) = ( (uint32_t) (b)[(i) ] << 24 ) \ + | ( (uint32_t) (b)[(i) + 1] << 16 ) \ + | ( (uint32_t) (b)[(i) + 2] << 8 ) \ + | ( (uint32_t) (b)[(i) + 3] ); \ +} +#endif + +#ifndef PUT_UINT32_BE +#define PUT_UINT32_BE(n,b,i) \ +{ \ + (b)[(i) ] = (unsigned char) ( (n) >> 24 ); \ + (b)[(i) + 1] = (unsigned char) ( (n) >> 16 ); \ + (b)[(i) + 2] = (unsigned char) ( (n) >> 8 ); \ + (b)[(i) + 3] = (unsigned char) ( (n) ); \ +} +#endif + +void mbedtls_sha1_init( mbedtls_sha1_context *ctx ) +{ + memset( ctx, 0, sizeof( mbedtls_sha1_context ) ); +} + +void mbedtls_sha1_free( mbedtls_sha1_context *ctx ) +{ + if( ctx == NULL ) + return; + + if (ctx->mode == ESP_MBEDTLS_SHA1_HARDWARE) { + esp_sha_unlock_engine(SHA1); + } + mbedtls_zeroize( ctx, sizeof( mbedtls_sha1_context ) ); +} + +void mbedtls_sha1_clone( mbedtls_sha1_context *dst, + const mbedtls_sha1_context *src ) +{ + *dst = *src; + + if (src->mode == ESP_MBEDTLS_SHA1_HARDWARE) { + /* Copy hardware digest state out to cloned state, + which will be a software digest. + */ + esp_sha_read_digest_state(SHA1, dst->state); + dst->mode = ESP_MBEDTLS_SHA1_SOFTWARE; + } +} + + +/* + * SHA-1 context setup + */ +void mbedtls_sha1_starts( mbedtls_sha1_context *ctx ) +{ + ctx->total[0] = 0; + ctx->total[1] = 0; + + ctx->state[0] = 0x67452301; + ctx->state[1] = 0xEFCDAB89; + ctx->state[2] = 0x98BADCFE; + ctx->state[3] = 0x10325476; + ctx->state[4] = 0xC3D2E1F0; + + if (ctx->mode == ESP_MBEDTLS_SHA1_HARDWARE) { + esp_sha_unlock_engine(SHA1); + } + ctx->mode = ESP_MBEDTLS_SHA1_UNUSED; +} + +static void mbedtls_sha1_software_process( mbedtls_sha1_context *ctx, const unsigned char data[64] ); + +void mbedtls_sha1_process( mbedtls_sha1_context *ctx, const unsigned char data[64] ) +{ + bool first_block = false; + if (ctx->mode == ESP_MBEDTLS_SHA1_UNUSED) { + /* try to use hardware for this digest */ + if (esp_sha_try_lock_engine(SHA1)) { + ctx->mode = ESP_MBEDTLS_SHA1_HARDWARE; + first_block = true; + } else { + ctx->mode = ESP_MBEDTLS_SHA1_SOFTWARE; + } + } + + if (ctx->mode == ESP_MBEDTLS_SHA1_HARDWARE) { + esp_sha_block(SHA1, data, first_block); + } else { + mbedtls_sha1_software_process(ctx, data); + } +} + + +static void mbedtls_sha1_software_process( mbedtls_sha1_context *ctx, const unsigned char data[64] ) +{ + uint32_t temp, W[16], A, B, C, D, E; + + GET_UINT32_BE( W[ 0], data, 0 ); + GET_UINT32_BE( W[ 1], data, 4 ); + GET_UINT32_BE( W[ 2], data, 8 ); + GET_UINT32_BE( W[ 3], data, 12 ); + GET_UINT32_BE( W[ 4], data, 16 ); + GET_UINT32_BE( W[ 5], data, 20 ); + GET_UINT32_BE( W[ 6], data, 24 ); + GET_UINT32_BE( W[ 7], data, 28 ); + GET_UINT32_BE( W[ 8], data, 32 ); + GET_UINT32_BE( W[ 9], data, 36 ); + GET_UINT32_BE( W[10], data, 40 ); + GET_UINT32_BE( W[11], data, 44 ); + GET_UINT32_BE( W[12], data, 48 ); + GET_UINT32_BE( W[13], data, 52 ); + GET_UINT32_BE( W[14], data, 56 ); + GET_UINT32_BE( W[15], data, 60 ); + +#define S(x,n) ((x << n) | ((x & 0xFFFFFFFF) >> (32 - n))) + +#define R(t) \ +( \ + temp = W[( t - 3 ) & 0x0F] ^ W[( t - 8 ) & 0x0F] ^ \ + W[( t - 14 ) & 0x0F] ^ W[ t & 0x0F], \ + ( W[t & 0x0F] = S(temp,1) ) \ +) + +#define P(a,b,c,d,e,x) \ +{ \ + e += S(a,5) + F(b,c,d) + K + x; b = S(b,30); \ +} + + A = ctx->state[0]; + B = ctx->state[1]; + C = ctx->state[2]; + D = ctx->state[3]; + E = ctx->state[4]; + +#define F(x,y,z) (z ^ (x & (y ^ z))) +#define K 0x5A827999 + + P( A, B, C, D, E, W[0] ); + P( E, A, B, C, D, W[1] ); + P( D, E, A, B, C, W[2] ); + P( C, D, E, A, B, W[3] ); + P( B, C, D, E, A, W[4] ); + P( A, B, C, D, E, W[5] ); + P( E, A, B, C, D, W[6] ); + P( D, E, A, B, C, W[7] ); + P( C, D, E, A, B, W[8] ); + P( B, C, D, E, A, W[9] ); + P( A, B, C, D, E, W[10] ); + P( E, A, B, C, D, W[11] ); + P( D, E, A, B, C, W[12] ); + P( C, D, E, A, B, W[13] ); + P( B, C, D, E, A, W[14] ); + P( A, B, C, D, E, W[15] ); + P( E, A, B, C, D, R(16) ); + P( D, E, A, B, C, R(17) ); + P( C, D, E, A, B, R(18) ); + P( B, C, D, E, A, R(19) ); + +#undef K +#undef F + +#define F(x,y,z) (x ^ y ^ z) +#define K 0x6ED9EBA1 + + P( A, B, C, D, E, R(20) ); + P( E, A, B, C, D, R(21) ); + P( D, E, A, B, C, R(22) ); + P( C, D, E, A, B, R(23) ); + P( B, C, D, E, A, R(24) ); + P( A, B, C, D, E, R(25) ); + P( E, A, B, C, D, R(26) ); + P( D, E, A, B, C, R(27) ); + P( C, D, E, A, B, R(28) ); + P( B, C, D, E, A, R(29) ); + P( A, B, C, D, E, R(30) ); + P( E, A, B, C, D, R(31) ); + P( D, E, A, B, C, R(32) ); + P( C, D, E, A, B, R(33) ); + P( B, C, D, E, A, R(34) ); + P( A, B, C, D, E, R(35) ); + P( E, A, B, C, D, R(36) ); + P( D, E, A, B, C, R(37) ); + P( C, D, E, A, B, R(38) ); + P( B, C, D, E, A, R(39) ); + +#undef K +#undef F + +#define F(x,y,z) ((x & y) | (z & (x | y))) +#define K 0x8F1BBCDC + + P( A, B, C, D, E, R(40) ); + P( E, A, B, C, D, R(41) ); + P( D, E, A, B, C, R(42) ); + P( C, D, E, A, B, R(43) ); + P( B, C, D, E, A, R(44) ); + P( A, B, C, D, E, R(45) ); + P( E, A, B, C, D, R(46) ); + P( D, E, A, B, C, R(47) ); + P( C, D, E, A, B, R(48) ); + P( B, C, D, E, A, R(49) ); + P( A, B, C, D, E, R(50) ); + P( E, A, B, C, D, R(51) ); + P( D, E, A, B, C, R(52) ); + P( C, D, E, A, B, R(53) ); + P( B, C, D, E, A, R(54) ); + P( A, B, C, D, E, R(55) ); + P( E, A, B, C, D, R(56) ); + P( D, E, A, B, C, R(57) ); + P( C, D, E, A, B, R(58) ); + P( B, C, D, E, A, R(59) ); + +#undef K +#undef F + +#define F(x,y,z) (x ^ y ^ z) +#define K 0xCA62C1D6 + + P( A, B, C, D, E, R(60) ); + P( E, A, B, C, D, R(61) ); + P( D, E, A, B, C, R(62) ); + P( C, D, E, A, B, R(63) ); + P( B, C, D, E, A, R(64) ); + P( A, B, C, D, E, R(65) ); + P( E, A, B, C, D, R(66) ); + P( D, E, A, B, C, R(67) ); + P( C, D, E, A, B, R(68) ); + P( B, C, D, E, A, R(69) ); + P( A, B, C, D, E, R(70) ); + P( E, A, B, C, D, R(71) ); + P( D, E, A, B, C, R(72) ); + P( C, D, E, A, B, R(73) ); + P( B, C, D, E, A, R(74) ); + P( A, B, C, D, E, R(75) ); + P( E, A, B, C, D, R(76) ); + P( D, E, A, B, C, R(77) ); + P( C, D, E, A, B, R(78) ); + P( B, C, D, E, A, R(79) ); + +#undef K +#undef F + + ctx->state[0] += A; + ctx->state[1] += B; + ctx->state[2] += C; + ctx->state[3] += D; + ctx->state[4] += E; +} + +/* + * SHA-1 process buffer + */ +void mbedtls_sha1_update( mbedtls_sha1_context *ctx, const unsigned char *input, size_t ilen ) +{ + size_t fill; + uint32_t left; + + if( ilen == 0 ) + return; + + left = ctx->total[0] & 0x3F; + fill = 64 - left; + + ctx->total[0] += (uint32_t) ilen; + ctx->total[0] &= 0xFFFFFFFF; + + if( ctx->total[0] < (uint32_t) ilen ) + ctx->total[1]++; + + if( left && ilen >= fill ) + { + memcpy( (void *) (ctx->buffer + left), input, fill ); + mbedtls_sha1_process( ctx, ctx->buffer ); + input += fill; + ilen -= fill; + left = 0; + } + + while( ilen >= 64 ) + { + mbedtls_sha1_process( ctx, input ); + input += 64; + ilen -= 64; + } + + if( ilen > 0 ) + memcpy( (void *) (ctx->buffer + left), input, ilen ); +} + +static const unsigned char sha1_padding[64] = +{ + 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 +}; + +/* +* SHA-1 final digest + */ +void mbedtls_sha1_finish( mbedtls_sha1_context *ctx, unsigned char output[20] ) +{ + uint32_t last, padn; + uint32_t high, low; + unsigned char msglen[8]; + + high = ( ctx->total[0] >> 29 ) + | ( ctx->total[1] << 3 ); + low = ( ctx->total[0] << 3 ); + + PUT_UINT32_BE( high, msglen, 0 ); + PUT_UINT32_BE( low, msglen, 4 ); + + last = ctx->total[0] & 0x3F; + padn = ( last < 56 ) ? ( 56 - last ) : ( 120 - last ); + + mbedtls_sha1_update( ctx, sha1_padding, padn ); + mbedtls_sha1_update( ctx, msglen, 8 ); + + /* if state is in hardware, read it out */ + if (ctx->mode == ESP_MBEDTLS_SHA1_HARDWARE) { + esp_sha_read_digest_state(SHA1, ctx->state); + esp_sha_unlock_engine(SHA1); + ctx->mode = ESP_MBEDTLS_SHA1_SOFTWARE; + } + + PUT_UINT32_BE( ctx->state[0], output, 0 ); + PUT_UINT32_BE( ctx->state[1], output, 4 ); + PUT_UINT32_BE( ctx->state[2], output, 8 ); + PUT_UINT32_BE( ctx->state[3], output, 12 ); + PUT_UINT32_BE( ctx->state[4], output, 16 ); + +} + +#endif /* MBEDTLS_SHA1_C && MBEDTLS_SHA1_ALT */ diff --git a/components/mbedtls/port/esp_sha256.c b/components/mbedtls/port/esp_sha256.c new file mode 100644 index 0000000000..fd136062a4 --- /dev/null +++ b/components/mbedtls/port/esp_sha256.c @@ -0,0 +1,367 @@ +/* + * SHA-256 implementation with hardware ESP32 support added. + * Uses mbedTLS software implementation for failover when concurrent + * SHA operations are in use. + * + * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved + * Additions Copyright (C) 2016, Espressif Systems (Shanghai) PTE LTD + * SPDX-License-Identifier: Apache-2.0 + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +/* + * The SHA-256 Secure Hash Standard was published by NIST in 2002. + * + * http://csrc.nist.gov/publications/fips/fips180-2/fips180-2.pdf + */ + +#if !defined(MBEDTLS_CONFIG_FILE) +#include "mbedtls/config.h" +#else +#include MBEDTLS_CONFIG_FILE +#endif + +#if defined(MBEDTLS_SHA256_C) && defined(MBEDTLS_SHA256_ALT) + +#include "mbedtls/sha256.h" + +#include + +#if defined(MBEDTLS_SELF_TEST) +#if defined(MBEDTLS_PLATFORM_C) +#include "mbedtls/platform.h" +#else +#include +#define mbedtls_printf printf +#endif /* MBEDTLS_PLATFORM_C */ +#endif /* MBEDTLS_SELF_TEST */ + +#include "hwcrypto/sha.h" + +/* Implementation that should never be optimized out by the compiler */ +static void mbedtls_zeroize( void *v, size_t n ) { + volatile unsigned char *p = v; while( n-- ) *p++ = 0; +} + +/* + * 32-bit integer manipulation macros (big endian) + */ +#ifndef GET_UINT32_BE +#define GET_UINT32_BE(n,b,i) \ +do { \ + (n) = ( (uint32_t) (b)[(i) ] << 24 ) \ + | ( (uint32_t) (b)[(i) + 1] << 16 ) \ + | ( (uint32_t) (b)[(i) + 2] << 8 ) \ + | ( (uint32_t) (b)[(i) + 3] ); \ +} while( 0 ) +#endif + +#ifndef PUT_UINT32_BE +#define PUT_UINT32_BE(n,b,i) \ +do { \ + (b)[(i) ] = (unsigned char) ( (n) >> 24 ); \ + (b)[(i) + 1] = (unsigned char) ( (n) >> 16 ); \ + (b)[(i) + 2] = (unsigned char) ( (n) >> 8 ); \ + (b)[(i) + 3] = (unsigned char) ( (n) ); \ +} while( 0 ) +#endif + +void mbedtls_sha256_init( mbedtls_sha256_context *ctx ) +{ + memset( ctx, 0, sizeof( mbedtls_sha256_context ) ); +} + +void mbedtls_sha256_free( mbedtls_sha256_context *ctx ) +{ + if( ctx == NULL ) + return; + + if (ctx->mode == ESP_MBEDTLS_SHA256_HARDWARE) { + esp_sha_unlock_engine(SHA2_256); + } + mbedtls_zeroize( ctx, sizeof( mbedtls_sha256_context ) ); +} + +void mbedtls_sha256_clone( mbedtls_sha256_context *dst, + const mbedtls_sha256_context *src ) +{ + *dst = *src; + + if (src->mode == ESP_MBEDTLS_SHA256_HARDWARE) { + /* Copy hardware digest state out to cloned state, + which will become a software digest. + */ + esp_sha_read_digest_state(SHA2_256, dst->state); + dst->mode = ESP_MBEDTLS_SHA256_SOFTWARE; + } +} + +/* + * SHA-256 context setup + */ +void mbedtls_sha256_starts( mbedtls_sha256_context *ctx, int is224 ) +{ + ctx->total[0] = 0; + ctx->total[1] = 0; + + if( is224 == 0 ) + { + /* SHA-256 */ + ctx->state[0] = 0x6A09E667; + ctx->state[1] = 0xBB67AE85; + ctx->state[2] = 0x3C6EF372; + ctx->state[3] = 0xA54FF53A; + ctx->state[4] = 0x510E527F; + ctx->state[5] = 0x9B05688C; + ctx->state[6] = 0x1F83D9AB; + ctx->state[7] = 0x5BE0CD19; + } + else + { + /* SHA-224 */ + ctx->state[0] = 0xC1059ED8; + ctx->state[1] = 0x367CD507; + ctx->state[2] = 0x3070DD17; + ctx->state[3] = 0xF70E5939; + ctx->state[4] = 0xFFC00B31; + ctx->state[5] = 0x68581511; + ctx->state[6] = 0x64F98FA7; + ctx->state[7] = 0xBEFA4FA4; + } + + ctx->is224 = is224; + if (ctx->mode == ESP_MBEDTLS_SHA256_HARDWARE) { + esp_sha_unlock_engine(SHA2_256); + } + ctx->mode = ESP_MBEDTLS_SHA256_UNUSED; +} + +#if !defined(MBEDTLS_SHA256_PROCESS_ALT) +static const uint32_t K[] = +{ + 0x428A2F98, 0x71374491, 0xB5C0FBCF, 0xE9B5DBA5, + 0x3956C25B, 0x59F111F1, 0x923F82A4, 0xAB1C5ED5, + 0xD807AA98, 0x12835B01, 0x243185BE, 0x550C7DC3, + 0x72BE5D74, 0x80DEB1FE, 0x9BDC06A7, 0xC19BF174, + 0xE49B69C1, 0xEFBE4786, 0x0FC19DC6, 0x240CA1CC, + 0x2DE92C6F, 0x4A7484AA, 0x5CB0A9DC, 0x76F988DA, + 0x983E5152, 0xA831C66D, 0xB00327C8, 0xBF597FC7, + 0xC6E00BF3, 0xD5A79147, 0x06CA6351, 0x14292967, + 0x27B70A85, 0x2E1B2138, 0x4D2C6DFC, 0x53380D13, + 0x650A7354, 0x766A0ABB, 0x81C2C92E, 0x92722C85, + 0xA2BFE8A1, 0xA81A664B, 0xC24B8B70, 0xC76C51A3, + 0xD192E819, 0xD6990624, 0xF40E3585, 0x106AA070, + 0x19A4C116, 0x1E376C08, 0x2748774C, 0x34B0BCB5, + 0x391C0CB3, 0x4ED8AA4A, 0x5B9CCA4F, 0x682E6FF3, + 0x748F82EE, 0x78A5636F, 0x84C87814, 0x8CC70208, + 0x90BEFFFA, 0xA4506CEB, 0xBEF9A3F7, 0xC67178F2, +}; + +#define SHR(x,n) ((x & 0xFFFFFFFF) >> n) +#define ROTR(x,n) (SHR(x,n) | (x << (32 - n))) + +#define S0(x) (ROTR(x, 7) ^ ROTR(x,18) ^ SHR(x, 3)) +#define S1(x) (ROTR(x,17) ^ ROTR(x,19) ^ SHR(x,10)) + +#define S2(x) (ROTR(x, 2) ^ ROTR(x,13) ^ ROTR(x,22)) +#define S3(x) (ROTR(x, 6) ^ ROTR(x,11) ^ ROTR(x,25)) + +#define F0(x,y,z) ((x & y) | (z & (x | y))) +#define F1(x,y,z) (z ^ (x & (y ^ z))) + +#define R(t) \ +( \ + W[t] = S1(W[t - 2]) + W[t - 7] + \ + S0(W[t - 15]) + W[t - 16] \ +) + +#define P(a,b,c,d,e,f,g,h,x,K) \ +{ \ + temp1 = h + S3(e) + F1(e,f,g) + K + x; \ + temp2 = S2(a) + F0(a,b,c); \ + d += temp1; h = temp1 + temp2; \ +} + +static void mbedtls_sha256_software_process( mbedtls_sha256_context *ctx, const unsigned char data[64] ); + +void mbedtls_sha256_process( mbedtls_sha256_context *ctx, const unsigned char data[64] ) +{ + bool first_block = false; + + if (ctx->mode == ESP_MBEDTLS_SHA256_UNUSED) { + /* try to use hardware for this digest */ + if (!ctx->is224 && esp_sha_try_lock_engine(SHA2_256)) { + ctx->mode = ESP_MBEDTLS_SHA256_HARDWARE; + first_block = true; + } else { + ctx->mode = ESP_MBEDTLS_SHA256_SOFTWARE; + } + } + + if (ctx->mode == ESP_MBEDTLS_SHA256_HARDWARE) { + esp_sha_block(SHA2_256, data, first_block); + } else { + mbedtls_sha256_software_process(ctx, data); + } +} + + +static void mbedtls_sha256_software_process( mbedtls_sha256_context *ctx, const unsigned char data[64] ) +{ + uint32_t temp1, temp2, W[64]; + uint32_t A[8]; + unsigned int i; + + for( i = 0; i < 8; i++ ) + A[i] = ctx->state[i]; + +#if defined(MBEDTLS_SHA256_SMALLER) + for( i = 0; i < 64; i++ ) + { + if( i < 16 ) + GET_UINT32_BE( W[i], data, 4 * i ); + else + R( i ); + + P( A[0], A[1], A[2], A[3], A[4], A[5], A[6], A[7], W[i], K[i] ); + + temp1 = A[7]; A[7] = A[6]; A[6] = A[5]; A[5] = A[4]; A[4] = A[3]; + A[3] = A[2]; A[2] = A[1]; A[1] = A[0]; A[0] = temp1; + } +#else /* MBEDTLS_SHA256_SMALLER */ + for( i = 0; i < 16; i++ ) + GET_UINT32_BE( W[i], data, 4 * i ); + + for( i = 0; i < 16; i += 8 ) + { + P( A[0], A[1], A[2], A[3], A[4], A[5], A[6], A[7], W[i+0], K[i+0] ); + P( A[7], A[0], A[1], A[2], A[3], A[4], A[5], A[6], W[i+1], K[i+1] ); + P( A[6], A[7], A[0], A[1], A[2], A[3], A[4], A[5], W[i+2], K[i+2] ); + P( A[5], A[6], A[7], A[0], A[1], A[2], A[3], A[4], W[i+3], K[i+3] ); + P( A[4], A[5], A[6], A[7], A[0], A[1], A[2], A[3], W[i+4], K[i+4] ); + P( A[3], A[4], A[5], A[6], A[7], A[0], A[1], A[2], W[i+5], K[i+5] ); + P( A[2], A[3], A[4], A[5], A[6], A[7], A[0], A[1], W[i+6], K[i+6] ); + P( A[1], A[2], A[3], A[4], A[5], A[6], A[7], A[0], W[i+7], K[i+7] ); + } + + for( i = 16; i < 64; i += 8 ) + { + P( A[0], A[1], A[2], A[3], A[4], A[5], A[6], A[7], R(i+0), K[i+0] ); + P( A[7], A[0], A[1], A[2], A[3], A[4], A[5], A[6], R(i+1), K[i+1] ); + P( A[6], A[7], A[0], A[1], A[2], A[3], A[4], A[5], R(i+2), K[i+2] ); + P( A[5], A[6], A[7], A[0], A[1], A[2], A[3], A[4], R(i+3), K[i+3] ); + P( A[4], A[5], A[6], A[7], A[0], A[1], A[2], A[3], R(i+4), K[i+4] ); + P( A[3], A[4], A[5], A[6], A[7], A[0], A[1], A[2], R(i+5), K[i+5] ); + P( A[2], A[3], A[4], A[5], A[6], A[7], A[0], A[1], R(i+6), K[i+6] ); + P( A[1], A[2], A[3], A[4], A[5], A[6], A[7], A[0], R(i+7), K[i+7] ); + } +#endif /* MBEDTLS_SHA256_SMALLER */ + + for( i = 0; i < 8; i++ ) + ctx->state[i] += A[i]; +} +#endif /* !MBEDTLS_SHA256_PROCESS_ALT */ + +/* + * SHA-256 process buffer + */ +void mbedtls_sha256_update( mbedtls_sha256_context *ctx, const unsigned char *input, + size_t ilen ) +{ + size_t fill; + uint32_t left; + + if( ilen == 0 ) + return; + + left = ctx->total[0] & 0x3F; + fill = 64 - left; + + ctx->total[0] += (uint32_t) ilen; + ctx->total[0] &= 0xFFFFFFFF; + + if( ctx->total[0] < (uint32_t) ilen ) + ctx->total[1]++; + + if( left && ilen >= fill ) + { + memcpy( (void *) (ctx->buffer + left), input, fill ); + mbedtls_sha256_process( ctx, ctx->buffer ); + input += fill; + ilen -= fill; + left = 0; + } + + while( ilen >= 64 ) + { + mbedtls_sha256_process( ctx, input ); + input += 64; + ilen -= 64; + } + + if( ilen > 0 ) + memcpy( (void *) (ctx->buffer + left), input, ilen ); +} + +static const unsigned char sha256_padding[64] = +{ + 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 +}; + +/* + * SHA-256 final digest + */ +void mbedtls_sha256_finish( mbedtls_sha256_context *ctx, unsigned char output[32] ) +{ + uint32_t last, padn; + uint32_t high, low; + unsigned char msglen[8]; + + high = ( ctx->total[0] >> 29 ) + | ( ctx->total[1] << 3 ); + low = ( ctx->total[0] << 3 ); + + PUT_UINT32_BE( high, msglen, 0 ); + PUT_UINT32_BE( low, msglen, 4 ); + + last = ctx->total[0] & 0x3F; + padn = ( last < 56 ) ? ( 56 - last ) : ( 120 - last ); + + mbedtls_sha256_update( ctx, sha256_padding, padn ); + mbedtls_sha256_update( ctx, msglen, 8 ); + + /* if state is in hardware, read it out */ + if (ctx->mode == ESP_MBEDTLS_SHA256_HARDWARE) { + esp_sha_read_digest_state(SHA2_256, ctx->state); + esp_sha_unlock_engine(SHA2_256); + ctx->mode = ESP_MBEDTLS_SHA256_SOFTWARE; + } + + PUT_UINT32_BE( ctx->state[0], output, 0 ); + PUT_UINT32_BE( ctx->state[1], output, 4 ); + PUT_UINT32_BE( ctx->state[2], output, 8 ); + PUT_UINT32_BE( ctx->state[3], output, 12 ); + PUT_UINT32_BE( ctx->state[4], output, 16 ); + PUT_UINT32_BE( ctx->state[5], output, 20 ); + PUT_UINT32_BE( ctx->state[6], output, 24 ); + + if( ctx->is224 == 0 ) + PUT_UINT32_BE( ctx->state[7], output, 28 ); +} + +#endif /* MBEDTLS_SHA256_C && MBEDTLS_SHA256_ALT */ diff --git a/components/mbedtls/port/esp_sha512.c b/components/mbedtls/port/esp_sha512.c new file mode 100644 index 0000000000..7a2bb15cb7 --- /dev/null +++ b/components/mbedtls/port/esp_sha512.c @@ -0,0 +1,412 @@ +/* + * SHA-512 implementation with hardware ESP32 support added. + * Uses mbedTLS software implementation for failover when concurrent + * SHA operations are in use. + * + * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved + * Additions Copyright (C) 2016, Espressif Systems (Shanghai) PTE LTD + * SPDX-License-Identifier: Apache-2.0 + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +/* + * The SHA-512 Secure Hash Standard was published by NIST in 2002. + * + * http://csrc.nist.gov/publications/fips/fips180-2/fips180-2.pdf + */ + +#if !defined(MBEDTLS_CONFIG_FILE) +#include "mbedtls/config.h" +#else +#include MBEDTLS_CONFIG_FILE +#endif + +#if defined(MBEDTLS_SHA512_C) && defined(MBEDTLS_SHA512_ALT) + +#include "mbedtls/sha512.h" + +#if defined(_MSC_VER) || defined(__WATCOMC__) + #define UL64(x) x##ui64 +#else + #define UL64(x) x##ULL +#endif + +#include + +#if defined(MBEDTLS_SELF_TEST) +#if defined(MBEDTLS_PLATFORM_C) +#include "mbedtls/platform.h" +#else +#include +#define mbedtls_printf printf +#endif /* MBEDTLS_PLATFORM_C */ +#endif /* MBEDTLS_SELF_TEST */ + +#include "hwcrypto/sha.h" + +inline static esp_sha_type sha_type(const mbedtls_sha512_context *ctx) +{ + return ctx->is384 ? SHA2_384 : SHA2_512; +} + +/* Implementation that should never be optimized out by the compiler */ +static void mbedtls_zeroize( void *v, size_t n ) { + volatile unsigned char *p = v; while( n-- ) *p++ = 0; +} + +/* + * 64-bit integer manipulation macros (big endian) + */ +#ifndef GET_UINT64_BE +#define GET_UINT64_BE(n,b,i) \ +{ \ + (n) = ( (uint64_t) (b)[(i) ] << 56 ) \ + | ( (uint64_t) (b)[(i) + 1] << 48 ) \ + | ( (uint64_t) (b)[(i) + 2] << 40 ) \ + | ( (uint64_t) (b)[(i) + 3] << 32 ) \ + | ( (uint64_t) (b)[(i) + 4] << 24 ) \ + | ( (uint64_t) (b)[(i) + 5] << 16 ) \ + | ( (uint64_t) (b)[(i) + 6] << 8 ) \ + | ( (uint64_t) (b)[(i) + 7] ); \ +} +#endif /* GET_UINT64_BE */ + +#ifndef PUT_UINT64_BE +#define PUT_UINT64_BE(n,b,i) \ +{ \ + (b)[(i) ] = (unsigned char) ( (n) >> 56 ); \ + (b)[(i) + 1] = (unsigned char) ( (n) >> 48 ); \ + (b)[(i) + 2] = (unsigned char) ( (n) >> 40 ); \ + (b)[(i) + 3] = (unsigned char) ( (n) >> 32 ); \ + (b)[(i) + 4] = (unsigned char) ( (n) >> 24 ); \ + (b)[(i) + 5] = (unsigned char) ( (n) >> 16 ); \ + (b)[(i) + 6] = (unsigned char) ( (n) >> 8 ); \ + (b)[(i) + 7] = (unsigned char) ( (n) ); \ +} +#endif /* PUT_UINT64_BE */ + +void mbedtls_sha512_init( mbedtls_sha512_context *ctx ) +{ + memset( ctx, 0, sizeof( mbedtls_sha512_context ) ); +} + +void mbedtls_sha512_free( mbedtls_sha512_context *ctx ) +{ + if( ctx == NULL ) + return; + + if (ctx->mode == ESP_MBEDTLS_SHA512_HARDWARE) { + esp_sha_unlock_engine(sha_type(ctx)); + } + mbedtls_zeroize( ctx, sizeof( mbedtls_sha512_context ) ); +} + +void mbedtls_sha512_clone( mbedtls_sha512_context *dst, + const mbedtls_sha512_context *src ) +{ + *dst = *src; + + if (src->mode == ESP_MBEDTLS_SHA512_HARDWARE) { + /* Copy hardware digest state out to cloned state, + which will be a software digest. + + Always read 512 bits of state, even for SHA-384 + (SHA-384 state is identical to SHA-512, only + digest is truncated.) + */ + esp_sha_read_digest_state(SHA2_512, dst->state); + dst->mode = ESP_MBEDTLS_SHA512_SOFTWARE; + } +} + + +/* + * SHA-512 context setup + */ +void mbedtls_sha512_starts( mbedtls_sha512_context *ctx, int is384 ) +{ + ctx->total[0] = 0; + ctx->total[1] = 0; + + if( is384 == 0 ) + { + /* SHA-512 */ + ctx->state[0] = UL64(0x6A09E667F3BCC908); + ctx->state[1] = UL64(0xBB67AE8584CAA73B); + ctx->state[2] = UL64(0x3C6EF372FE94F82B); + ctx->state[3] = UL64(0xA54FF53A5F1D36F1); + ctx->state[4] = UL64(0x510E527FADE682D1); + ctx->state[5] = UL64(0x9B05688C2B3E6C1F); + ctx->state[6] = UL64(0x1F83D9ABFB41BD6B); + ctx->state[7] = UL64(0x5BE0CD19137E2179); + } + else + { + /* SHA-384 */ + ctx->state[0] = UL64(0xCBBB9D5DC1059ED8); + ctx->state[1] = UL64(0x629A292A367CD507); + ctx->state[2] = UL64(0x9159015A3070DD17); + ctx->state[3] = UL64(0x152FECD8F70E5939); + ctx->state[4] = UL64(0x67332667FFC00B31); + ctx->state[5] = UL64(0x8EB44A8768581511); + ctx->state[6] = UL64(0xDB0C2E0D64F98FA7); + ctx->state[7] = UL64(0x47B5481DBEFA4FA4); + } + + ctx->is384 = is384; + if (ctx->mode == ESP_MBEDTLS_SHA512_HARDWARE) { + esp_sha_unlock_engine(sha_type(ctx)); + } + ctx->mode = ESP_MBEDTLS_SHA512_UNUSED; +} + + +/* + * Round constants + */ +static const uint64_t K[80] = +{ + UL64(0x428A2F98D728AE22), UL64(0x7137449123EF65CD), + UL64(0xB5C0FBCFEC4D3B2F), UL64(0xE9B5DBA58189DBBC), + UL64(0x3956C25BF348B538), UL64(0x59F111F1B605D019), + UL64(0x923F82A4AF194F9B), UL64(0xAB1C5ED5DA6D8118), + UL64(0xD807AA98A3030242), UL64(0x12835B0145706FBE), + UL64(0x243185BE4EE4B28C), UL64(0x550C7DC3D5FFB4E2), + UL64(0x72BE5D74F27B896F), UL64(0x80DEB1FE3B1696B1), + UL64(0x9BDC06A725C71235), UL64(0xC19BF174CF692694), + UL64(0xE49B69C19EF14AD2), UL64(0xEFBE4786384F25E3), + UL64(0x0FC19DC68B8CD5B5), UL64(0x240CA1CC77AC9C65), + UL64(0x2DE92C6F592B0275), UL64(0x4A7484AA6EA6E483), + UL64(0x5CB0A9DCBD41FBD4), UL64(0x76F988DA831153B5), + UL64(0x983E5152EE66DFAB), UL64(0xA831C66D2DB43210), + UL64(0xB00327C898FB213F), UL64(0xBF597FC7BEEF0EE4), + UL64(0xC6E00BF33DA88FC2), UL64(0xD5A79147930AA725), + UL64(0x06CA6351E003826F), UL64(0x142929670A0E6E70), + UL64(0x27B70A8546D22FFC), UL64(0x2E1B21385C26C926), + UL64(0x4D2C6DFC5AC42AED), UL64(0x53380D139D95B3DF), + UL64(0x650A73548BAF63DE), UL64(0x766A0ABB3C77B2A8), + UL64(0x81C2C92E47EDAEE6), UL64(0x92722C851482353B), + UL64(0xA2BFE8A14CF10364), UL64(0xA81A664BBC423001), + UL64(0xC24B8B70D0F89791), UL64(0xC76C51A30654BE30), + UL64(0xD192E819D6EF5218), UL64(0xD69906245565A910), + UL64(0xF40E35855771202A), UL64(0x106AA07032BBD1B8), + UL64(0x19A4C116B8D2D0C8), UL64(0x1E376C085141AB53), + UL64(0x2748774CDF8EEB99), UL64(0x34B0BCB5E19B48A8), + UL64(0x391C0CB3C5C95A63), UL64(0x4ED8AA4AE3418ACB), + UL64(0x5B9CCA4F7763E373), UL64(0x682E6FF3D6B2B8A3), + UL64(0x748F82EE5DEFB2FC), UL64(0x78A5636F43172F60), + UL64(0x84C87814A1F0AB72), UL64(0x8CC702081A6439EC), + UL64(0x90BEFFFA23631E28), UL64(0xA4506CEBDE82BDE9), + UL64(0xBEF9A3F7B2C67915), UL64(0xC67178F2E372532B), + UL64(0xCA273ECEEA26619C), UL64(0xD186B8C721C0C207), + UL64(0xEADA7DD6CDE0EB1E), UL64(0xF57D4F7FEE6ED178), + UL64(0x06F067AA72176FBA), UL64(0x0A637DC5A2C898A6), + UL64(0x113F9804BEF90DAE), UL64(0x1B710B35131C471B), + UL64(0x28DB77F523047D84), UL64(0x32CAAB7B40C72493), + UL64(0x3C9EBE0A15C9BEBC), UL64(0x431D67C49C100D4C), + UL64(0x4CC5D4BECB3E42B6), UL64(0x597F299CFC657E2A), + UL64(0x5FCB6FAB3AD6FAEC), UL64(0x6C44198C4A475817) +}; + +static void mbedtls_sha512_software_process( mbedtls_sha512_context *ctx, const unsigned char data[128] ); + +void mbedtls_sha512_process( mbedtls_sha512_context *ctx, const unsigned char data[128] ) +{ + bool first_block = false; + + if (ctx->mode == ESP_MBEDTLS_SHA512_UNUSED) { + /* try to use hardware for this digest */ + if (esp_sha_try_lock_engine(sha_type(ctx))) { + ctx->mode = ESP_MBEDTLS_SHA512_HARDWARE; + first_block = true; + } else { + ctx->mode = ESP_MBEDTLS_SHA512_SOFTWARE; + } + } + + if (ctx->mode == ESP_MBEDTLS_SHA512_HARDWARE) { + esp_sha_block(sha_type(ctx), data, first_block); + } else { + mbedtls_sha512_software_process(ctx, data); + } +} + + + +static void mbedtls_sha512_software_process( mbedtls_sha512_context *ctx, const unsigned char data[128] ) +{ + int i; + uint64_t temp1, temp2, W[80]; + uint64_t A, B, C, D, E, F, G, H; + +#define SHR(x,n) (x >> n) +#define ROTR(x,n) (SHR(x,n) | (x << (64 - n))) + +#define S0(x) (ROTR(x, 1) ^ ROTR(x, 8) ^ SHR(x, 7)) +#define S1(x) (ROTR(x,19) ^ ROTR(x,61) ^ SHR(x, 6)) + +#define S2(x) (ROTR(x,28) ^ ROTR(x,34) ^ ROTR(x,39)) +#define S3(x) (ROTR(x,14) ^ ROTR(x,18) ^ ROTR(x,41)) + +#define F0(x,y,z) ((x & y) | (z & (x | y))) +#define F1(x,y,z) (z ^ (x & (y ^ z))) + +#define P(a,b,c,d,e,f,g,h,x,K) \ +{ \ + temp1 = h + S3(e) + F1(e,f,g) + K + x; \ + temp2 = S2(a) + F0(a,b,c); \ + d += temp1; h = temp1 + temp2; \ +} + + for( i = 0; i < 16; i++ ) + { + GET_UINT64_BE( W[i], data, i << 3 ); + } + + for( ; i < 80; i++ ) + { + W[i] = S1(W[i - 2]) + W[i - 7] + + S0(W[i - 15]) + W[i - 16]; + } + + A = ctx->state[0]; + B = ctx->state[1]; + C = ctx->state[2]; + D = ctx->state[3]; + E = ctx->state[4]; + F = ctx->state[5]; + G = ctx->state[6]; + H = ctx->state[7]; + i = 0; + + do + { + P( A, B, C, D, E, F, G, H, W[i], K[i] ); i++; + P( H, A, B, C, D, E, F, G, W[i], K[i] ); i++; + P( G, H, A, B, C, D, E, F, W[i], K[i] ); i++; + P( F, G, H, A, B, C, D, E, W[i], K[i] ); i++; + P( E, F, G, H, A, B, C, D, W[i], K[i] ); i++; + P( D, E, F, G, H, A, B, C, W[i], K[i] ); i++; + P( C, D, E, F, G, H, A, B, W[i], K[i] ); i++; + P( B, C, D, E, F, G, H, A, W[i], K[i] ); i++; + } + while( i < 80 ); + + ctx->state[0] += A; + ctx->state[1] += B; + ctx->state[2] += C; + ctx->state[3] += D; + ctx->state[4] += E; + ctx->state[5] += F; + ctx->state[6] += G; + ctx->state[7] += H; +} + +/* + * SHA-512 process buffer + */ +void mbedtls_sha512_update( mbedtls_sha512_context *ctx, const unsigned char *input, + size_t ilen ) +{ + size_t fill; + unsigned int left; + + if( ilen == 0 ) + return; + + left = (unsigned int) (ctx->total[0] & 0x7F); + fill = 128 - left; + + ctx->total[0] += (uint64_t) ilen; + + if( ctx->total[0] < (uint64_t) ilen ) + ctx->total[1]++; + + if( left && ilen >= fill ) + { + memcpy( (void *) (ctx->buffer + left), input, fill ); + mbedtls_sha512_process( ctx, ctx->buffer ); + input += fill; + ilen -= fill; + left = 0; + } + + while( ilen >= 128 ) + { + mbedtls_sha512_process( ctx, input ); + input += 128; + ilen -= 128; + } + + if( ilen > 0 ) + memcpy( (void *) (ctx->buffer + left), input, ilen ); +} + +static const unsigned char sha512_padding[128] = +{ + 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 +}; + +/* + * SHA-512 final digest + */ +void mbedtls_sha512_finish( mbedtls_sha512_context *ctx, unsigned char output[64] ) +{ + size_t last, padn; + uint64_t high, low; + unsigned char msglen[16]; + + high = ( ctx->total[0] >> 61 ) + | ( ctx->total[1] << 3 ); + low = ( ctx->total[0] << 3 ); + + PUT_UINT64_BE( high, msglen, 0 ); + PUT_UINT64_BE( low, msglen, 8 ); + + last = (size_t)( ctx->total[0] & 0x7F ); + padn = ( last < 112 ) ? ( 112 - last ) : ( 240 - last ); + + mbedtls_sha512_update( ctx, sha512_padding, padn ); + mbedtls_sha512_update( ctx, msglen, 16 ); + + /* if state is in hardware, read it out */ + if (ctx->mode == ESP_MBEDTLS_SHA512_HARDWARE) { + esp_sha_read_digest_state(sha_type(ctx), ctx->state); + esp_sha_unlock_engine(sha_type(ctx)); + ctx->mode = ESP_MBEDTLS_SHA512_SOFTWARE; + } + + PUT_UINT64_BE( ctx->state[0], output, 0 ); + PUT_UINT64_BE( ctx->state[1], output, 8 ); + PUT_UINT64_BE( ctx->state[2], output, 16 ); + PUT_UINT64_BE( ctx->state[3], output, 24 ); + PUT_UINT64_BE( ctx->state[4], output, 32 ); + PUT_UINT64_BE( ctx->state[5], output, 40 ); + + if( ctx->is384 == 0 ) + { + PUT_UINT64_BE( ctx->state[6], output, 48 ); + PUT_UINT64_BE( ctx->state[7], output, 56 ); + } +} + +#endif /* MBEDTLS_SHA512_C && MBEDTLS_SHA512_ALT */ diff --git a/components/mbedtls/port/include/mbedtls/esp_config.h b/components/mbedtls/port/include/mbedtls/esp_config.h index db87c6ef31..cd9f87e698 100644 --- a/components/mbedtls/port/include/mbedtls/esp_config.h +++ b/components/mbedtls/port/include/mbedtls/esp_config.h @@ -243,11 +243,14 @@ #define MBEDTLS_AES_ALT #endif -/* Currently hardware SHA does not work with TLS handshake, - due to concurrency issue. Internal TW#7111. */ -//#define MBEDTLS_SHA1_ALT -//#define MBEDTLS_SHA256_ALT -//#define MBEDTLS_SHA512_ALT +/* MBEDTLS_SHAxx_ALT to enable hardware SHA support + with software fallback. +*/ +#ifdef CONFIG_MBEDTLS_HARDWARE_SHA +#define MBEDTLS_SHA1_ALT +#define MBEDTLS_SHA256_ALT +#define MBEDTLS_SHA512_ALT +#endif /* The following MPI (bignum) functions have ESP32 hardware support, Uncommenting these macros will use the hardware-accelerated diff --git a/components/mbedtls/port/include/sha1_alt.h b/components/mbedtls/port/include/sha1_alt.h index f5e69b3f95..fbe740c7e0 100644 --- a/components/mbedtls/port/include/sha1_alt.h +++ b/components/mbedtls/port/include/sha1_alt.h @@ -1,16 +1,25 @@ -// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at - -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. +/* + * SHA-1 implementation with hardware ESP32 support added. + * Uses mbedTLS software implementation for failover when concurrent + * SHA operations are in use. + * + * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved + * Additions Copyright (C) 2016, Espressif Systems (Shanghai) PTE LTD + * SPDX-License-Identifier: Apache-2.0 + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ #ifndef _SHA1_ALT_H_ #define _SHA1_ALT_H_ @@ -20,17 +29,73 @@ extern "C" { #if defined(MBEDTLS_SHA1_ALT) -#include "hwcrypto/sha.h" +typedef enum { + ESP_MBEDTLS_SHA1_UNUSED, /* first block hasn't been processed yet */ + ESP_MBEDTLS_SHA1_HARDWARE, /* using hardware SHA engine */ + ESP_MBEDTLS_SHA1_SOFTWARE, /* using software SHA */ +} esp_mbedtls_sha1_mode; -typedef esp_sha_context mbedtls_sha1_context; +/** + * \brief SHA-1 context structure + */ +typedef struct +{ + uint32_t total[2]; /*!< number of bytes processed */ + uint32_t state[5]; /*!< intermediate digest state */ + unsigned char buffer[64]; /*!< data block being processed */ + esp_mbedtls_sha1_mode mode; +} +mbedtls_sha1_context; -#define mbedtls_sha1_init esp_sha1_init -#define mbedtls_sha1_starts esp_sha1_start -#define mbedtls_sha1_clone esp_sha1_clone -#define mbedtls_sha1_update esp_sha1_update -#define mbedtls_sha1_finish esp_sha1_finish -#define mbedtls_sha1_free esp_sha1_free -#define mbedtls_sha1_process(...) +/** + * \brief Initialize SHA-1 context + * + * \param ctx SHA-1 context to be initialized + */ +void mbedtls_sha1_init( mbedtls_sha1_context *ctx ); + +/** + * \brief Clear SHA-1 context + * + * \param ctx SHA-1 context to be cleared + */ +void mbedtls_sha1_free( mbedtls_sha1_context *ctx ); + +/** + * \brief Clone (the state of) a SHA-1 context + * + * \param dst The destination context + * \param src The context to be cloned + */ +void mbedtls_sha1_clone( mbedtls_sha1_context *dst, + const mbedtls_sha1_context *src ); + +/** + * \brief SHA-1 context setup + * + * \param ctx context to be initialized + */ +void mbedtls_sha1_starts( mbedtls_sha1_context *ctx ); + +/** + * \brief SHA-1 process buffer + * + * \param ctx SHA-1 context + * \param input buffer holding the data + * \param ilen length of the input data + */ +void mbedtls_sha1_update( mbedtls_sha1_context *ctx, const unsigned char *input, size_t ilen ); + +/** + * \brief SHA-1 final digest + * + * \param ctx SHA-1 context + * \param output SHA-1 checksum result + */ +void mbedtls_sha1_finish( mbedtls_sha1_context *ctx, unsigned char output[20] ); + +/* Internal use */ +void mbedtls_sha1_process( mbedtls_sha1_context *ctx, const unsigned char data[64] ); #endif diff --git a/components/mbedtls/port/include/sha256_alt.h b/components/mbedtls/port/include/sha256_alt.h index 143d8c75e1..cc87333aaa 100644 --- a/components/mbedtls/port/include/sha256_alt.h +++ b/components/mbedtls/port/include/sha256_alt.h @@ -1,16 +1,25 @@ -// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at - -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. +/* + * SHA-256 implementation with hardware ESP32 support added. + * Uses mbedTLS software implementation for failover when concurrent + * SHA operations are in use. + * + * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved + * Additions Copyright (C) 2016, Espressif Systems (Shanghai) PTE LTD + * SPDX-License-Identifier: Apache-2.0 + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ #ifndef _SHA256_ALT_H_ #define _SHA256_ALT_H_ @@ -20,17 +29,76 @@ extern "C" { #if defined(MBEDTLS_SHA256_ALT) -#include "hwcrypto/sha.h" +typedef enum { + ESP_MBEDTLS_SHA256_UNUSED, /* first block hasn't been processed yet */ + ESP_MBEDTLS_SHA256_HARDWARE, /* using hardware SHA engine */ + ESP_MBEDTLS_SHA256_SOFTWARE, /* using software SHA */ +} esp_mbedtls_sha256_mode; -typedef esp_sha_context mbedtls_sha256_context; +/** + * \brief SHA-256 context structure + */ +typedef struct +{ + uint32_t total[2]; /*!< number of bytes processed */ + uint32_t state[8]; /*!< intermediate digest state */ + unsigned char buffer[64]; /*!< data block being processed */ + int is224; /*!< 0 => SHA-256, else SHA-224 */ + esp_mbedtls_sha256_mode mode; +} +mbedtls_sha256_context; -#define mbedtls_sha256_init esp_sha256_init -#define mbedtls_sha256_clone esp_sha256_clone -#define mbedtls_sha256_starts esp_sha256_start -#define mbedtls_sha256_update esp_sha256_update -#define mbedtls_sha256_finish esp_sha256_finish -#define mbedtls_sha256_free esp_sha256_free -#define mbedtls_sha256_process(...) +/** + * \brief Initialize SHA-256 context + * + * \param ctx SHA-256 context to be initialized + */ +void mbedtls_sha256_init( mbedtls_sha256_context *ctx ); + +/** + * \brief Clear SHA-256 context + * + * \param ctx SHA-256 context to be cleared + */ +void mbedtls_sha256_free( mbedtls_sha256_context *ctx ); + +/** + * \brief Clone (the state of) a SHA-256 context + * + * \param dst The destination context + * \param src The context to be cloned + */ +void mbedtls_sha256_clone( mbedtls_sha256_context *dst, + const mbedtls_sha256_context *src ); + +/** + * \brief SHA-256 context setup + * + * \param ctx context to be initialized + * \param is224 0 = use SHA256, 1 = use SHA224 + */ +void mbedtls_sha256_starts( mbedtls_sha256_context *ctx, int is224 ); + +/** + * \brief SHA-256 process buffer + * + * \param ctx SHA-256 context + * \param input buffer holding the data + * \param ilen length of the input data + */ +void mbedtls_sha256_update( mbedtls_sha256_context *ctx, const unsigned char *input, + size_t ilen ); + +/** + * \brief SHA-256 final digest + * + * \param ctx SHA-256 context + * \param output SHA-224/256 checksum result + */ +void mbedtls_sha256_finish( mbedtls_sha256_context *ctx, unsigned char output[32] ); + +/* Internal use */ +void mbedtls_sha256_process( mbedtls_sha256_context *ctx, const unsigned char data[64] ); #endif diff --git a/components/mbedtls/port/include/sha512_alt.h b/components/mbedtls/port/include/sha512_alt.h index 8044b42754..70ae24e166 100644 --- a/components/mbedtls/port/include/sha512_alt.h +++ b/components/mbedtls/port/include/sha512_alt.h @@ -1,16 +1,25 @@ -// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at - -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. +/* + * SHA-512 implementation with hardware ESP32 support added. + * Uses mbedTLS software implementation for failover when concurrent + * SHA operations are in use. + * + * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved + * Additions Copyright (C) 2016, Espressif Systems (Shanghai) PTE LTD + * SPDX-License-Identifier: Apache-2.0 + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ #ifndef _SHA512_ALT_H_ #define _SHA512_ALT_H_ @@ -19,17 +28,77 @@ extern "C" { #endif #if defined(MBEDTLS_SHA512_ALT) -#include "hwcrypto/sha.h" -typedef esp_sha_context mbedtls_sha512_context; +typedef enum { + ESP_MBEDTLS_SHA512_UNUSED, /* first block hasn't been processed yet */ + ESP_MBEDTLS_SHA512_HARDWARE, /* using hardware SHA engine */ + ESP_MBEDTLS_SHA512_SOFTWARE, /* using software SHA */ +} esp_mbedtls_sha512_mode; -#define mbedtls_sha512_init esp_sha512_init -#define mbedtls_sha512_clone esp_sha512_clone -#define mbedtls_sha512_starts esp_sha512_start -#define mbedtls_sha512_update esp_sha512_update -#define mbedtls_sha512_finish esp_sha512_finish -#define mbedtls_sha512_free esp_sha512_free -#define mbedtls_sha512_process(...) +/** + * \brief SHA-512 context structure + */ +typedef struct +{ + uint64_t total[2]; /*!< number of bytes processed */ + uint64_t state[8]; /*!< intermediate digest state */ + unsigned char buffer[128]; /*!< data block being processed */ + int is384; /*!< 0 => SHA-512, else SHA-384 */ + esp_mbedtls_sha512_mode mode; +} +mbedtls_sha512_context; + +/** + * \brief Initialize SHA-512 context + * + * \param ctx SHA-512 context to be initialized + */ +void mbedtls_sha512_init( mbedtls_sha512_context *ctx ); + +/** + * \brief Clear SHA-512 context + * + * \param ctx SHA-512 context to be cleared + */ +void mbedtls_sha512_free( mbedtls_sha512_context *ctx ); + +/** + * \brief Clone (the state of) a SHA-512 context + * + * \param dst The destination context + * \param src The context to be cloned + */ +void mbedtls_sha512_clone( mbedtls_sha512_context *dst, + const mbedtls_sha512_context *src ); + +/** + * \brief SHA-512 context setup + * + * \param ctx context to be initialized + * \param is384 0 = use SHA512, 1 = use SHA384 + */ +void mbedtls_sha512_starts( mbedtls_sha512_context *ctx, int is384 ); + +/** + * \brief SHA-512 process buffer + * + * \param ctx SHA-512 context + * \param input buffer holding the data + * \param ilen length of the input data + */ +void mbedtls_sha512_update( mbedtls_sha512_context *ctx, const unsigned char *input, + size_t ilen ); + +/** + * \brief SHA-512 final digest + * + * \param ctx SHA-512 context + * \param output SHA-384/512 checksum result + */ +void mbedtls_sha512_finish( mbedtls_sha512_context *ctx, unsigned char output[64] ); + +/* Internal use */ +void mbedtls_sha512_process( mbedtls_sha512_context *ctx, const unsigned char data[128] ); #endif diff --git a/components/mbedtls/test/test_mbedtls.c b/components/mbedtls/test/test_mbedtls.c index 797c107efb..acde6e9dd3 100644 --- a/components/mbedtls/test/test_mbedtls.c +++ b/components/mbedtls/test/test_mbedtls.c @@ -1,27 +1,25 @@ -/* mbedTLS internal tests wrapped into Unity +/* mbedTLS self-tests as unit tests Focus on testing functionality where we use ESP32 hardware accelerated crypto features. - See also test_hwcrypto.c + See also test_hwcrypto.c in esp32 component, which tests hardware crypto without mbedTLS. */ #include #include +#include +#include #include "mbedtls/sha1.h" #include "mbedtls/sha256.h" #include "mbedtls/sha512.h" #include "mbedtls/aes.h" #include "mbedtls/bignum.h" +#include "mbedtls/rsa.h" +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "freertos/semphr.h" #include "unity.h" - -static int mbedtls_alt_sha256_self_test( int verbose ); - -TEST_CASE("mbedtls SHA self-tests", "[mbedtls]") -{ - TEST_ASSERT_FALSE_MESSAGE(mbedtls_sha1_self_test(1), "SHA1 self-tests should pass."); - TEST_ASSERT_FALSE_MESSAGE(mbedtls_alt_sha256_self_test(1), "SHA256 self-tests should pass."); - TEST_ASSERT_FALSE_MESSAGE(mbedtls_sha512_self_test(1), "SHA512 self-tests should pass."); -} +#include "sdkconfig.h" TEST_CASE("mbedtls AES self-tests", "[aes]") { @@ -33,102 +31,8 @@ TEST_CASE("mbedtls MPI self-tests", "[bignum]") TEST_ASSERT_FALSE_MESSAGE(mbedtls_mpi_self_test(1), "MPI self-tests should pass."); } - -/* Following code is a copy of the mbedtls_sha256 test vectors, - with the SHA-224 support removed as we don't currently support this hash. -*/ - -/* - * FIPS-180-2 test vectors - */ -static const unsigned char sha256_test_buf[3][57] = { - { "abc" }, - { "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq" }, - { "" } -}; - -static const int sha256_test_buflen[3] = { - 3, 56, 1000 -}; - -static const unsigned char sha256_test_sum[6][32] = { - /* - * SHA-256 test vectors - */ - { - 0xBA, 0x78, 0x16, 0xBF, 0x8F, 0x01, 0xCF, 0xEA, - 0x41, 0x41, 0x40, 0xDE, 0x5D, 0xAE, 0x22, 0x23, - 0xB0, 0x03, 0x61, 0xA3, 0x96, 0x17, 0x7A, 0x9C, - 0xB4, 0x10, 0xFF, 0x61, 0xF2, 0x00, 0x15, 0xAD - }, - { - 0x24, 0x8D, 0x6A, 0x61, 0xD2, 0x06, 0x38, 0xB8, - 0xE5, 0xC0, 0x26, 0x93, 0x0C, 0x3E, 0x60, 0x39, - 0xA3, 0x3C, 0xE4, 0x59, 0x64, 0xFF, 0x21, 0x67, - 0xF6, 0xEC, 0xED, 0xD4, 0x19, 0xDB, 0x06, 0xC1 - }, - { - 0xCD, 0xC7, 0x6E, 0x5C, 0x99, 0x14, 0xFB, 0x92, - 0x81, 0xA1, 0xC7, 0xE2, 0x84, 0xD7, 0x3E, 0x67, - 0xF1, 0x80, 0x9A, 0x48, 0xA4, 0x97, 0x20, 0x0E, - 0x04, 0x6D, 0x39, 0xCC, 0xC7, 0x11, 0x2C, 0xD0 - } -}; - -/* - * Checkup routine - */ -static int mbedtls_alt_sha256_self_test( int verbose ) +TEST_CASE("mbedtls RSA self-tests", "[bignum]") { - int j, n, buflen, ret = 0; - unsigned char buf[1024]; - unsigned char sha256sum[32]; - mbedtls_sha256_context ctx; - - for ( j = 0; j < 3; j++ ) { - mbedtls_sha256_init( &ctx ); - - if ( verbose != 0 ) { - printf( " SHA-%d test #%d: ", 256, j + 1 ); - } - - mbedtls_sha256_starts( &ctx, 0 ); - - if ( j == 2 ) { - memset( buf, 'a', buflen = 1000 ); - - for ( n = 0; n < 1000; n++ ) { - mbedtls_sha256_update( &ctx, buf, buflen ); - } - } else - mbedtls_sha256_update( &ctx, sha256_test_buf[j], - sha256_test_buflen[j] ); - - mbedtls_sha256_finish( &ctx, sha256sum ); - - if ( memcmp( sha256sum, sha256_test_sum[j], 32 ) != 0 ) { - if ( verbose != 0 ) { - printf( "failed\n" ); - } - - mbedtls_sha256_free( &ctx ); - - ret = 1; - goto exit; - } - - if ( verbose != 0 ) { - printf( "passed\n" ); - } - - mbedtls_sha256_free( &ctx ); - } - - if ( verbose != 0 ) { - printf( "\n" ); - } - -exit: - - return ( ret ); + TEST_ASSERT_FALSE_MESSAGE(mbedtls_rsa_self_test(1), "RSA self-tests should pass."); } + diff --git a/components/mbedtls/test/test_mbedtls_mpi.c b/components/mbedtls/test/test_mbedtls_mpi.c new file mode 100644 index 0000000000..515f9d3058 --- /dev/null +++ b/components/mbedtls/test/test_mbedtls_mpi.c @@ -0,0 +1,168 @@ +/* mbedTLS bignum (MPI) self-tests as unit tests +*/ +#include +#include +#include +#include +#include "mbedtls/bignum.h" +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "freertos/semphr.h" +#include "unity.h" +#include "sdkconfig.h" + + +/* Debugging function to print an MPI number to stdout. Happens to + print output that can be copy-pasted directly into a Python shell. +*/ +void mbedtls_mpi_printf(const char *name, const mbedtls_mpi *X) +{ + static char buf[1024]; + size_t n; + memset(buf, 0, sizeof(buf)); + mbedtls_mpi_write_string(X, 16, buf, sizeof(buf)-1, &n); + if(n) { + printf("%s = 0x%s\n", name, buf); + } else { + printf("%s = TOOLONG\n", name); + } +} + +/* Assert E = A * B */ +static void test_bignum_mult(const char *a_str, const char *b_str, const char *e_str, size_t mod_bits) +{ + mbedtls_mpi A, B, X, E, M; + char x_buf[1024] = { 0 }; + size_t x_buf_len = 0; + + mbedtls_mpi_init(&A); + mbedtls_mpi_init(&B); + mbedtls_mpi_init(&X); + mbedtls_mpi_init(&E); + + TEST_ASSERT_FALSE(mbedtls_mpi_read_string(&A, 16, a_str)); + TEST_ASSERT_FALSE(mbedtls_mpi_read_string(&B, 16, b_str)); + + /* E = A * B */ + TEST_ASSERT_FALSE(mbedtls_mpi_read_string(&E, 16, e_str)); + TEST_ASSERT_FALSE(mbedtls_mpi_mul_mpi(&X, &A, &B)); + + mbedtls_mpi_write_string(&X, 16, x_buf, sizeof(x_buf)-1, &x_buf_len); + TEST_ASSERT_EQUAL_STRING_MESSAGE(e_str, x_buf, "mbedtls_mpi_mul_mpi result wrong"); + + /* if mod_bits arg is set, also do a esp_mpi_mul_mod() call */ + if (mod_bits > 0) { + mbedtls_mpi_init(&M); + for(int i = 0; i < mod_bits; i++) { + mbedtls_mpi_set_bit(&M, i, 1); + } + + TEST_ASSERT_FALSE(esp_mpi_mul_mpi_mod(&X, &A, &B, &M)); + + mbedtls_mpi_write_string(&X, 16, x_buf, sizeof(x_buf)-1, &x_buf_len); + TEST_ASSERT_EQUAL_STRING_MESSAGE(e_str, x_buf, "esp_mpi_mul_mpi_mod result wrong"); + + mbedtls_mpi_free(&M); + } + + + mbedtls_mpi_free(&A); + mbedtls_mpi_free(&B); + mbedtls_mpi_free(&X); + mbedtls_mpi_free(&E); +} + +TEST_CASE("test MPI multiplication", "[bignum]") +{ + /* Run some trivial numbers tests w/ various high modulo bit counts, + should make no difference to the result + */ + for(int i = 512; i <= 4096; i+= 512) { + test_bignum_mult("10", "100", "1000", + i); + } + + test_bignum_mult("60006FA8D3E3BD746BE39B860FFAADB4F108E15CF2ED8F685FB0E86CC4CB107A488720B41C3F1E18550F00619CD3CA8442296ECB54D2F52ECEE5346D310195700000000", + "BF474CA7", + "047BB102CAF58A48D3D97E4231BC0B753051D8232B9B939A2A4E310F88E65FEFD7762FC2DE0E2BAD6AA51A391DFFABD120653A312E4998F42E2C03AA404EE63B67275BC100000000", + 1024); + + test_bignum_mult("49493AC229831EC01EEB01EAF3BBEBC44768EADF9ABC30C87D1791F5E04245756ED4965361EC0599626884DF079B6B5738985CE76BD66FAA67E3AAAD60775D5C9D44C09FDF9E27C033696C007BE1C540D718CA148BA01FFA4A358541E9E9F02F72BE37AFAB037DAEA5E3669A770400D2F4A5DBBD83A83919D05E3DD64787BC80000000", + "B878CC29", + "34CF37013066D5BDA2C86CF1FE7BDA66604E0D55DAFF9864B6E727BFF5871012B0AB73D28D4E100BA1E4607AA2A247C912FDBC435C6BF7C5F8E00278AE1381B1E5F6E3D52D2CBE819F0D65CB37370666D156E7A7B1FD4698D8C9D3165FC8A83F9293C839521993619CCF8180E521300C4306206C9121D629754F1FCC7839BF6DFAF33080000000", + 3072); + + test_bignum_mult("24BF6185468786FDD303083D25E64EFC66CA472BC44D253102F8B4A9D3BFA75091386C0077937FE33FA3252D28855837AE1B484A8A9A45F7EE8C0C634F9E8CDDF79C5CE07EE72C7F123142198164234CABB724CF78B8173B9F880FC86322407AF1FEDFDDE2BEB674CA15F3E81A1521E071513A1E85B5DFA031F21ECAE9A34D", + "010001", + "24BF8644A80CCD855A00DB402E2374E2B5C6ADF60B78E97E2829B7A288697B103888FD38E393F776BF8664D04DB280BD0652F665D2E4D0923483FAEF5C01DC7C847A547CDBC7AB663EB0544AC37DA4B0CF03D0869D878FF3B6C3AF5072EAA39D3279D1DCC29C9933808ABDFE0DFD3BF59331AB6FBFD46556119250BD086E36A34D", + 1536); + + test_bignum_mult("-5D88B669C417EDD02213723546A906B7E9DA7683780E9B54856A2147467ADA316F8819D69486FC8056FE1E8EA7DEC5D5EF12340B95C4FC966F4B348D35893620", + "9AE7FBC99546432DF71896FC239EADAEF38D18D2B2F0E2DD275AA977E2BF4411F5A3B2A5D33605AEBBCCBA7FEB9F2D2FA74206CEC169D74BF5A8C50D6F48EA08", + "-38990016EB21810E3B5E6AEE339AEE72BB7CD629C4C9270A3D832701A2949BC82B2BE5A7F900C0C9937464699862821976095187D646884E8FBF01DE8C3442F3BC97B670AF573EFB74A9BBEBE4432EE74B0A83BBCDF59485D332B1FF49EB461A3A8B12C38FD72C7772D75EC6EBA5633199540C47678BD2F4ADEEA40830C2F100", + 2048); + + + /* 1 << 2050 * 0X1234 */ + test_bignum_mult("400000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "1234", + "48D000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + 3072); + + /* multiply a 1178 bit number by a 2050 bit number */ + test_bignum_mult("AAAAAAAAAA75124938ABBECD0EEEEE333333333333333333333FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFAAAAAAABBBBBBBBBBBBBBBBBBBB000000000000000000000000000000000004988A5293848932948872398400000000000FFFFFFFFFFF0000000000000EDFABC0204048975876873487387478327482374871327482347328742837483247283748234723874238", + "390587293875124938ABBECD0EEEEE3333333333333333333333333333333399999888000AAAAAAAAAAAAAAAAAAAAABBBBBBBBBBBBBBBBBBBB00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000EDFABC0204048975876873487387478327482374871327482347328742837483247283748234723874238478327400000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000003012111111111111111100000000000000000000000111111111111111111111111", + "02603AF70D0421C1AD82CE623F28F70B128118D06D00C27D433EC25BA86E6105C3890A0B1973B8BE068CA68E159A21078785DDB37F94216FBF4AEC939958AF4B8CEA2A48895CECA87562FC846EAAE0C866AF9D41EEABFB1D579F5828E9666A15E2AF946F16A189B5C645872FDCA247D309AB0BCAFB0D112881186FCFFEDC87061B4AE4A375E9BBCF579A7BC87A8EAC8C6F66E107986FC603F920F5E1A0FD8C619D88D90066FFFC8F4DB77437EBD7E3BD7E398C4C01F93426E347E039DCA7B0A73C0C90A9C4271BB761ADFF88971D190CE5DA98EFC5D7390D33BC034908AF81D784A4D7F32D0902E0C5DABC706635D5A28FC0E3A364EDEB21E8E117041D0E4B51CA6F9684F434057E7FCF2AF6BD050334B1D11E043B0967154E57354B681161D3C618974D5A7E0385755B80B931AE9B59DD4402BAEC206F04B8440741B3C4CA6D9F7DAF0AE6B3BF1B24B76C2F12B9E9A7C50D32E2093608FC9A30CBD852329E64A9AE0BC3F513899EBFA28629C1DF38081FB8C6630408F70D7B9A37701ABA4176C8B7DCB8CC78BD7783B861A7FC50862E75191DB8", + 4096); +} + +static void test_bignum_modexp(const char *z_str, const char *x_str, const char *y_str, const char *m_str) +{ + mbedtls_mpi Z, X, Y, M; + char z_buf[400] = { 0 }; + size_t z_buf_len = 0; + + mbedtls_mpi_init(&Z); + mbedtls_mpi_init(&X); + mbedtls_mpi_init(&Y); + mbedtls_mpi_init(&M); + + TEST_ASSERT_FALSE(mbedtls_mpi_read_string(&X, 16, x_str)); + TEST_ASSERT_FALSE(mbedtls_mpi_read_string(&Y, 16, y_str)); + TEST_ASSERT_FALSE(mbedtls_mpi_read_string(&M, 16, m_str)); + + //mbedtls_mpi_printf("X", &X); + //mbedtls_mpi_printf("X", &Y); + //mbedtls_mpi_printf("M", &M); + + /* Z = (X ^ Y) mod M */ + TEST_ASSERT_FALSE(mbedtls_mpi_exp_mod(&Z, &X, &Y, &M, NULL)); + + mbedtls_mpi_write_string(&Z, 16, z_buf, sizeof(z_buf)-1, &z_buf_len); + TEST_ASSERT_EQUAL_STRING_MESSAGE(z_str, z_buf, "mbedtls_mpi_exp_mod incorrect"); +} + +TEST_CASE("test MPI modexp", "[bignum]") +{ + test_bignum_modexp("01000000", "1000", "2", "FFFFFFFF"); + test_bignum_modexp("014B5A90", "1234", "2", "FFFFFFF"); + test_bignum_modexp("01234321", "1111", "2", "FFFFFFFF"); + test_bignum_modexp("02", "5", "1", "3"); + test_bignum_modexp("22", "55", "1", "33"); + test_bignum_modexp("0222", "555", "1", "333"); + test_bignum_modexp("2222", "5555", "1", "3333"); + test_bignum_modexp("11", "5555", "1", "33"); + + test_bignum_modexp("55", "1111", "1", "77"); + test_bignum_modexp("88", "1111", "2", "BB"); + + test_bignum_modexp("01000000", "2", "128", + "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"); + + /* failures below here... */ + test_bignum_modexp("0ABCDEF12345", "ABCDEF12345", "1", "FFFFFFFFFFFF"); + test_bignum_modexp("0ABCDE", "ABCDE", "1", "FFFFF"); + + test_bignum_modexp("04", "2", "2", "9"); +} + diff --git a/components/mbedtls/test/test_mbedtls_sha.c b/components/mbedtls/test/test_mbedtls_sha.c new file mode 100644 index 0000000000..721c59b761 --- /dev/null +++ b/components/mbedtls/test/test_mbedtls_sha.c @@ -0,0 +1,250 @@ +/* mbedTLS SHA unit tests + */ + +#include +#include +#include +#include +#include "mbedtls/sha1.h" +#include "mbedtls/sha256.h" +#include "mbedtls/sha512.h" +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "freertos/semphr.h" +#include "unity.h" +#include "sdkconfig.h" + +TEST_CASE("mbedtls SHA self-tests", "[mbedtls]") +{ + TEST_ASSERT_FALSE_MESSAGE(mbedtls_sha1_self_test(1), "SHA1 self-tests should pass."); + TEST_ASSERT_FALSE_MESSAGE(mbedtls_sha256_self_test(1), "SHA256 self-tests should pass."); + TEST_ASSERT_FALSE_MESSAGE(mbedtls_sha512_self_test(1), "SHA512 self-tests should pass."); + TEST_ASSERT_FALSE_MESSAGE(mbedtls_sha512_self_test(1), "SHA512 self-tests should pass."); +} + +static const unsigned char *one_hundred_as = (unsigned char *) + "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"; + +static const unsigned char *one_hundred_bs = (unsigned char *) + "bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb"; + +static const uint8_t sha256_thousand_as[32] = { + 0x41, 0xed, 0xec, 0xe4, 0x2d, 0x63, 0xe8, 0xd9, 0xbf, 0x51, 0x5a, 0x9b, 0xa6, 0x93, 0x2e, 0x1c, + 0x20, 0xcb, 0xc9, 0xf5, 0xa5, 0xd1, 0x34, 0x64, 0x5a, 0xdb, 0x5d, 0xb1, 0xb9, 0x73, 0x7e, 0xa3 }; + +static const uint8_t sha256_thousand_bs[32] = { + 0xf6, 0xf1, 0x18, 0xe1, 0x20, 0xe5, 0x2b, 0xe0, 0xbd, 0x0c, 0xfd, 0xf2, 0x79, 0x4c, 0xd1, 0x2c, 0x07, 0x68, 0x6c, 0xc8, 0x71, 0x23, 0x5a, 0xc2, 0xf1, 0x14, 0x59, 0x37, 0x8e, 0x6d, 0x23, 0x5b +}; + +static const uint8_t sha512_thousand_bs[64] = { + 0xa6, 0x68, 0x68, 0xa3, 0x73, 0x53, 0x2a, 0x5c, 0xc3, 0x3f, 0xbf, 0x43, 0x4e, 0xba, 0x10, 0x86, 0xb3, 0x87, 0x09, 0xe9, 0x14, 0x3f, 0xbf, 0x37, 0x67, 0x8d, 0x43, 0xd9, 0x9b, 0x95, 0x08, 0xd5, 0x80, 0x2d, 0xbe, 0x9d, 0xe9, 0x1a, 0x54, 0xab, 0x9e, 0xbc, 0x8a, 0x08, 0xa0, 0x1a, 0x89, 0xd8, 0x72, 0x68, 0xdf, 0x52, 0x69, 0x7f, 0x1c, 0x70, 0xda, 0xe8, 0x3f, 0xe5, 0xae, 0x5a, 0xfc, 0x9d +}; + +static const uint8_t sha384_thousand_bs[48] = { + 0x6d, 0xe5, 0xf5, 0x88, 0x57, 0x60, 0x83, 0xff, 0x7c, 0x94, 0x61, 0x5f, 0x8d, 0x96, 0xf2, 0x76, 0xd5, 0x3f, 0x77, 0x0c, 0x8e, 0xc1, 0xbf, 0xb6, 0x04, 0x27, 0xa4, 0xba, 0xea, 0x6c, 0x68, 0x44, 0xbd, 0xb0, 0x9c, 0xef, 0x6a, 0x09, 0x28, 0xe8, 0x1f, 0xfc, 0x95, 0x03, 0x69, 0x99, 0xab, 0x1a +}; + +static const uint8_t sha1_thousand_as[20] = { + 0x29, 0x1e, 0x9a, 0x6c, 0x66, 0x99, 0x49, 0x49, 0xb5, 0x7b, 0xa5, + 0xe6, 0x50, 0x36, 0x1e, 0x98, 0xfc, 0x36, 0xb1, 0xba }; + +TEST_CASE("mbedtls SHA interleaving", "[mbedtls]") +{ + mbedtls_sha1_context sha1_ctx; + mbedtls_sha256_context sha256_ctx; + mbedtls_sha512_context sha512_ctx; + unsigned char sha1[20], sha256[32], sha512[64]; + + mbedtls_sha1_init(&sha1_ctx); + mbedtls_sha256_init(&sha256_ctx); + mbedtls_sha512_init(&sha512_ctx); + + mbedtls_sha1_starts(&sha1_ctx); + mbedtls_sha256_starts(&sha256_ctx, false); + mbedtls_sha512_starts(&sha512_ctx, false); + + for (int i = 0; i < 10; i++) { + mbedtls_sha1_update(&sha1_ctx, one_hundred_as, 100); + mbedtls_sha256_update(&sha256_ctx, one_hundred_as, 100); + mbedtls_sha512_update(&sha512_ctx, one_hundred_bs, 100); + } + + mbedtls_sha1_finish(&sha1_ctx, sha1); + mbedtls_sha256_finish(&sha256_ctx, sha256); + mbedtls_sha512_finish(&sha512_ctx, sha512); + + TEST_ASSERT_EQUAL_MEMORY_MESSAGE(sha512_thousand_bs, sha512, 64, "SHA512 calculation"); + TEST_ASSERT_EQUAL_MEMORY_MESSAGE(sha256_thousand_as, sha256, 32, "SHA256 calculation"); + TEST_ASSERT_EQUAL_MEMORY_MESSAGE(sha1_thousand_as, sha1, 20, "SHA1 calculation"); +} + +static xSemaphoreHandle done_sem; +static void tskRunSHA1Test(void *pvParameters) +{ + mbedtls_sha1_context sha1_ctx; + unsigned char sha1[20]; + + for (int i = 0; i < 1000; i++) { + mbedtls_sha1_init(&sha1_ctx); + mbedtls_sha1_starts(&sha1_ctx); + for (int j = 0; j < 10; j++) { + mbedtls_sha1_update(&sha1_ctx, (unsigned char *)one_hundred_as, 100); + } + mbedtls_sha1_finish(&sha1_ctx, sha1); + TEST_ASSERT_EQUAL_MEMORY_MESSAGE(sha1_thousand_as, sha1, 20, "SHA1 calculation"); + } + xSemaphoreGive(done_sem); + vTaskDelete(NULL); +} + +static void tskRunSHA256Test(void *pvParameters) +{ + mbedtls_sha256_context sha256_ctx; + unsigned char sha256[32]; + + for (int i = 0; i < 1000; i++) { + mbedtls_sha256_init(&sha256_ctx); + mbedtls_sha256_starts(&sha256_ctx, false); + for (int j = 0; j < 10; j++) { + mbedtls_sha256_update(&sha256_ctx, (unsigned char *)one_hundred_bs, 100); + } + mbedtls_sha256_finish(&sha256_ctx, sha256); + + TEST_ASSERT_EQUAL_MEMORY_MESSAGE(sha256_thousand_bs, sha256, 32, "SHA256 calculation"); + } + xSemaphoreGive(done_sem); + vTaskDelete(NULL); +} + +TEST_CASE("mbedtls SHA multithreading", "[mbedtls]") +{ + done_sem = xSemaphoreCreateCounting(4, 0); + xTaskCreate(tskRunSHA1Test, "SHA1Task1", 8192, NULL, 3, NULL); + xTaskCreate(tskRunSHA1Test, "SHA1Task2", 8192, NULL, 3, NULL); + xTaskCreate(tskRunSHA256Test, "SHA256Task1", 8192, NULL, 3, NULL); + xTaskCreate(tskRunSHA256Test, "SHA256Task2", 8192, NULL, 3, NULL); + + for(int i = 0; i < 4; i++) { + if(!xSemaphoreTake(done_sem, 10000/portTICK_PERIOD_MS)) { + TEST_FAIL_MESSAGE("done_sem not released by test task"); + } + } + vSemaphoreDelete(done_sem); +} + +void tskRunSHASelftests(void *param) +{ + for (int i = 0; i < 5; i++) { + if(mbedtls_sha1_self_test(1)) { + printf("SHA1 self-tests failed.\n"); + while(1) {} + } + + if(mbedtls_sha256_self_test(1)) { + printf("SHA256 self-tests failed.\n"); + while(1) {} + } + + if(mbedtls_sha512_self_test(1)) { + printf("SHA512 self-tests failed.\n"); + while(1) {} + } + + if(mbedtls_sha512_self_test(1)) { + printf("SHA512 self-tests failed.\n"); + while(1) {} + } + } + xSemaphoreGive(done_sem); + vTaskDelete(NULL); +} + +TEST_CASE("mbedtls SHA self-tests multithreaded", "[mbedtls]") +{ + done_sem = xSemaphoreCreateCounting(2, 0); + xTaskCreate(tskRunSHASelftests, "SHASelftests1", 8192, NULL, 3, NULL); + xTaskCreate(tskRunSHASelftests, "SHASelftests2", 8192, NULL, 3, NULL); + + for(int i = 0; i < 2; i++) { + if(!xSemaphoreTake(done_sem, 10000/portTICK_PERIOD_MS)) { + TEST_FAIL_MESSAGE("done_sem not released by test task"); + } + } + vSemaphoreDelete(done_sem); +} + +TEST_CASE("mbedtls SHA512 clone", "[mbedtls]") +{ + mbedtls_sha512_context ctx; + mbedtls_sha512_context clone; + unsigned char sha512[64]; + + mbedtls_sha512_init(&ctx); + mbedtls_sha512_starts(&ctx, false); + for (int i = 0; i < 5; i++) { + mbedtls_sha512_update(&ctx, one_hundred_bs, 100); + } + + mbedtls_sha512_clone(&clone, &ctx); + for (int i = 0; i < 5; i++) { + mbedtls_sha512_update(&ctx, one_hundred_bs, 100); + mbedtls_sha512_update(&clone, one_hundred_bs, 100); + } + mbedtls_sha512_finish(&ctx, sha512); + + TEST_ASSERT_EQUAL_MEMORY_MESSAGE(sha512_thousand_bs, sha512, 64, "SHA512 original calculation"); + + mbedtls_sha512_finish(&clone, sha512); + TEST_ASSERT_EQUAL_MEMORY_MESSAGE(sha512_thousand_bs, sha512, 64, "SHA512 cloned calculation"); +} + +TEST_CASE("mbedtls SHA384 clone", "[mbedtls]") +{ + mbedtls_sha512_context ctx; + mbedtls_sha512_context clone; + unsigned char sha384[48]; + + mbedtls_sha512_init(&ctx); + mbedtls_sha512_starts(&ctx, true); + for (int i = 0; i < 5; i++) { + mbedtls_sha512_update(&ctx, one_hundred_bs, 100); + } + + mbedtls_sha512_clone(&clone, &ctx); + for (int i = 0; i < 5; i++) { + mbedtls_sha512_update(&ctx, one_hundred_bs, 100); + mbedtls_sha512_update(&clone, one_hundred_bs, 100); + } + mbedtls_sha512_finish(&ctx, sha384); + + TEST_ASSERT_EQUAL_MEMORY_MESSAGE(sha384_thousand_bs, sha384, 48, "SHA512 original calculation"); + + mbedtls_sha512_finish(&clone, sha384); + TEST_ASSERT_EQUAL_MEMORY_MESSAGE(sha384_thousand_bs, sha384, 48, "SHA512 cloned calculation"); +} + + +TEST_CASE("mbedtls SHA256 clone", "[mbedtls]") +{ + mbedtls_sha256_context ctx; + mbedtls_sha256_context clone; + unsigned char sha256[64]; + + mbedtls_sha256_init(&ctx); + mbedtls_sha256_starts(&ctx, false); + for (int i = 0; i < 5; i++) { + mbedtls_sha256_update(&ctx, one_hundred_as, 100); + } + + mbedtls_sha256_clone(&clone, &ctx); + for (int i = 0; i < 5; i++) { + mbedtls_sha256_update(&ctx, one_hundred_as, 100); + mbedtls_sha256_update(&clone, one_hundred_as, 100); + } + mbedtls_sha256_finish(&ctx, sha256); + + TEST_ASSERT_EQUAL_MEMORY_MESSAGE(sha256_thousand_as, sha256, 32, "SHA256 original calculation"); + + mbedtls_sha256_finish(&clone, sha256); + TEST_ASSERT_EQUAL_MEMORY_MESSAGE(sha256_thousand_as, sha256, 32, "SHA256 cloned calculation"); +} diff --git a/components/newlib/time.c b/components/newlib/time.c index 3426a01bfb..1baa955759 100644 --- a/components/newlib/time.c +++ b/components/newlib/time.c @@ -184,3 +184,29 @@ int settimeofday(const struct timeval *tv, const struct timezone *tz) return -1; #endif } + +uint32_t system_get_time(void) +{ +#if defined( WITH_FRC1 ) || defined( WITH_RTC ) + return get_time_since_boot(); +#else + return 0; +#endif +} + +uint32_t system_get_current_time(void) __attribute__((alias("system_get_time"))); + +uint32_t system_relative_time(uint32_t current_time) +{ + return system_get_time() - current_time; +} + +uint64_t system_get_rtc_time(void) +{ +#ifdef WITH_RTC + return get_rtc_time_us(); +#else + return 0; +#endif +} + diff --git a/components/openssl/platform/ssl_pm.c b/components/openssl/platform/ssl_pm.c index a5986dc3ee..522721ad7c 100644 --- a/components/openssl/platform/ssl_pm.c +++ b/components/openssl/platform/ssl_pm.c @@ -215,7 +215,7 @@ static int ssl_pm_reload_crt(SSL *ssl) * Perform the mbedtls SSL handshake instead of mbedtls_ssl_handshake. * We can add debug here. */ -LOCAL int mbedtls_handshake( mbedtls_ssl_context *ssl ) +static int mbedtls_handshake( mbedtls_ssl_context *ssl ) { int ret = 0; diff --git a/components/spi_flash/flash_ops.c b/components/spi_flash/flash_ops.c index 3358c550f2..db3ac042f0 100644 --- a/components/spi_flash/flash_ops.c +++ b/components/spi_flash/flash_ops.c @@ -31,6 +31,9 @@ #include "esp_log.h" #include "cache_utils.h" +/* bytes erased by SPIEraseBlock() ROM function */ +#define BLOCK_ERASE_SIZE 32768 + #if CONFIG_SPI_FLASH_ENABLE_COUNTERS static const char* TAG = "spi_flash"; static spi_flash_counters_t s_flash_stats; @@ -100,7 +103,7 @@ esp_err_t IRAM_ATTR spi_flash_erase_range(uint32_t start_addr, uint32_t size) } size_t start = start_addr / SPI_FLASH_SEC_SIZE; size_t end = start + size / SPI_FLASH_SEC_SIZE; - const size_t sectors_per_block = 16; + const size_t sectors_per_block = BLOCK_ERASE_SIZE / SPI_FLASH_SEC_SIZE; COUNTER_START(); spi_flash_disable_interrupts_caches_and_other_cpu(); SpiFlashOpResult rc; @@ -129,34 +132,90 @@ esp_err_t IRAM_ATTR spi_flash_write(size_t dest_addr, const void *src, size_t si // Destination alignment is also checked in ROM code, but we can give // better error code here // TODO: add handling of unaligned destinations - if (dest_addr % 4 != 0) { - return ESP_ERR_INVALID_ARG; - } - if (size % 4 != 0) { - return ESP_ERR_INVALID_SIZE; - } - if ((uint32_t) src < 0x3ff00000) { - // if source address is in DROM, we won't be able to read it - // from within SPIWrite - // TODO: consider buffering source data using heap and writing it anyway? - return ESP_ERR_INVALID_ARG; - } + uint8_t *temp_write_buf = NULL; + uint8_t pad_head = 0; + uint8_t pad_end = 0; + SpiFlashOpResult rc; // Out of bound writes are checked in ROM code, but we can give better // error code here if (dest_addr + size > g_rom_flashchip.chip_size) { return ESP_ERR_INVALID_SIZE; } - COUNTER_START(); - spi_flash_disable_interrupts_caches_and_other_cpu(); - SpiFlashOpResult rc; - rc = spi_flash_unlock(); - if (rc == SPI_FLASH_RESULT_OK) { - rc = SPIWrite((uint32_t) dest_addr, (const uint32_t*) src, (int32_t) size); - COUNTER_ADD_BYTES(write, size); + + while(size >= 1024) { + // max need pad byte num for 1024 is 4 + temp_write_buf = (uint8_t*)malloc(1024 + 4); + if(temp_write_buf == NULL) { + return ESP_ERR_NO_MEM; + } + + if(dest_addr%4 != 0) { + pad_head = dest_addr%4; + pad_end = 4 - pad_head; + } + memset(temp_write_buf,0xFF,pad_head); + memcpy(temp_write_buf + pad_head ,src,1024); + memset(temp_write_buf + pad_head + 1024, 0xFF,pad_end); + COUNTER_START(); + spi_flash_disable_interrupts_caches_and_other_cpu(); + rc = spi_flash_unlock(); + if (rc == SPI_FLASH_RESULT_OK) { + rc = SPIWrite((uint32_t) (dest_addr - pad_head), (const uint32_t*) temp_write_buf, (int32_t) (1024 + pad_head + pad_end)); + COUNTER_ADD_BYTES(write, 1024 + pad_head + pad_end); + } + COUNTER_STOP(write); + spi_flash_enable_interrupts_caches_and_other_cpu(); + if(rc != ESP_OK) { + free(temp_write_buf); + temp_write_buf = NULL; + return spi_flash_translate_rc(rc); + } + + free(temp_write_buf); + temp_write_buf = NULL; + size -= 1024; + dest_addr += 1024; + src = (uint8_t*)src + 1024; } - spi_flash_enable_interrupts_caches_and_other_cpu(); - COUNTER_STOP(write); - return spi_flash_translate_rc(rc); + if(size > 0) { + // max need pad byte num for rand size is 6 + temp_write_buf = (uint8_t*)malloc(size + 6); + if(temp_write_buf == NULL) { + return ESP_ERR_NO_MEM; + } + if(dest_addr%4 != 0) { + pad_head = dest_addr%4; + } + if ((pad_head + size)%4 != 0){ + pad_end = 4 - (pad_head + size) % 4; + } + memset(temp_write_buf,0xFF,pad_head); + memcpy(temp_write_buf + pad_head, src, size); + memset(temp_write_buf + pad_head + size, 0xFF,pad_end); + COUNTER_START(); + spi_flash_disable_interrupts_caches_and_other_cpu(); + rc = spi_flash_unlock(); + if (rc == SPI_FLASH_RESULT_OK) { + rc = SPIWrite((uint32_t) (dest_addr - pad_head), (const uint32_t*) temp_write_buf, (int32_t) (size + pad_head + pad_end)); + COUNTER_ADD_BYTES(write, size + pad_head + pad_end); + } + COUNTER_STOP(write); + spi_flash_enable_interrupts_caches_and_other_cpu(); + if(rc != ESP_OK) { + free(temp_write_buf); + temp_write_buf = NULL; + return spi_flash_translate_rc(rc); + } + + free(temp_write_buf); + temp_write_buf = NULL; + size = 0; + dest_addr += size; + src = (uint8_t*)src + size; + return spi_flash_translate_rc(rc); + } + return spi_flash_translate_rc(SPI_FLASH_RESULT_OK); + } esp_err_t IRAM_ATTR spi_flash_read(size_t src_addr, void *dest, size_t size) diff --git a/components/spi_flash/partition.c b/components/spi_flash/partition.c index 21013d96fa..c54da24caa 100644 --- a/components/spi_flash/partition.c +++ b/components/spi_flash/partition.c @@ -208,6 +208,10 @@ esp_err_t esp_partition_write(const esp_partition_t* partition, size_t dst_offset, const void* src, size_t size) { assert(partition != NULL); + //todo : need add ecrypt write support ,size must be 32-bytes align + if(partition->encrypted == true) { + return ESP_FAIL; + } if (dst_offset > partition->size) { return ESP_ERR_INVALID_ARG; } diff --git a/components/tcpip_adapter/include/tcpip_adapter.h b/components/tcpip_adapter/include/tcpip_adapter.h index f7063a8e17..861f7ccb8d 100644 --- a/components/tcpip_adapter/include/tcpip_adapter.h +++ b/components/tcpip_adapter/include/tcpip_adapter.h @@ -98,6 +98,7 @@ typedef struct { typedef enum { TCPIP_ADAPTER_IF_STA = 0, /**< ESP32 station interface */ TCPIP_ADAPTER_IF_AP, /**< ESP32 soft-AP interface */ + TCPIP_ADAPTER_IF_ETH, /**< ESP32 ethernet interface */ TCPIP_ADAPTER_IF_MAX } tcpip_adapter_if_t; @@ -354,6 +355,10 @@ esp_err_t tcpip_adapter_dhcpc_start(tcpip_adapter_if_t tcpip_if); */ esp_err_t tcpip_adapter_dhcpc_stop(tcpip_adapter_if_t tcpip_if); + + +esp_err_t tcpip_adapter_eth_input(void *buffer, uint16_t len, void *eb); + /** * @brief Get data from station interface * @@ -387,11 +392,12 @@ esp_err_t tcpip_adapter_ap_input(void *buffer, uint16_t len, void *eb); * * @param[in] void *dev: adapter interface * - * @return WIFI_IF_STA - * WIFI_IF_AP - * WIFI_IF_MAX + * @return ESP_IF_WIFI_STA + * ESP_IF_WIFI_AP + ESP_IF_ETH + * ESP_IF_MAX */ -wifi_interface_t tcpip_adapter_get_wifi_if(void *dev); +esp_interface_t tcpip_adapter_get_esp_if(void *dev); /** * @brief Get the station information list @@ -418,6 +424,18 @@ esp_err_t tcpip_adapter_get_sta_list(wifi_sta_list_t *wifi_sta_list, tcpip_adapt */ esp_err_t tcpip_adapter_set_hostname(tcpip_adapter_if_t tcpip_if, const char *hostname); +/** + * @brief Get the hostname from the interface + * + * @param[in] tcpip_if: the interface which we will get the hostname + * @param[in] hostname: the host name from the interfce + * + * @return ESP_OK:success + * ESP_ERR_TCPIP_ADAPTER_IF_NOT_READY:interface status error + * ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS:parameter error + */ +esp_err_t tcpip_adapter_get_hostname(tcpip_adapter_if_t tcpip_if, const char **hostname); + #ifdef __cplusplus } #endif diff --git a/components/tcpip_adapter/tcpip_adapter_lwip.c b/components/tcpip_adapter/tcpip_adapter_lwip.c index 25c801bd01..222e8017eb 100644 --- a/components/tcpip_adapter/tcpip_adapter_lwip.c +++ b/components/tcpip_adapter/tcpip_adapter_lwip.c @@ -26,6 +26,7 @@ #include "lwip/ip6_addr.h" #include "lwip/nd6.h" #include "netif/wlanif.h" +#include "netif/ethernetif.h" #include "apps/dhcpserver.h" @@ -36,9 +37,10 @@ static tcpip_adapter_ip_info_t esp_ip[TCPIP_ADAPTER_IF_MAX]; static tcpip_adapter_ip6_info_t esp_ip6[TCPIP_ADAPTER_IF_MAX]; static tcpip_adapter_dhcp_status_t dhcps_status = TCPIP_ADAPTER_DHCP_INIT; -static tcpip_adapter_dhcp_status_t dhcpc_status = TCPIP_ADAPTER_DHCP_INIT; +static tcpip_adapter_dhcp_status_t dhcpc_status[TCPIP_ADAPTER_IF_MAX] = {TCPIP_ADAPTER_DHCP_INIT}; #define TCPIP_ADAPTER_DEBUG(...) +//#define TCPIP_ADAPTER_DEBUG printf void tcpip_adapter_init(void) { @@ -67,7 +69,11 @@ esp_err_t tcpip_adapter_start(tcpip_adapter_if_t tcpip_if, uint8_t *mac, tcpip_a return ESP_ERR_NO_MEM; } memcpy(esp_netif[tcpip_if]->hwaddr, mac, NETIF_MAX_HWADDR_LEN); - netif_add(esp_netif[tcpip_if], &ip_info->ip, &ip_info->netmask, &ip_info->gw, NULL, wlanif_init, tcpip_input); + if (tcpip_if == TCPIP_ADAPTER_IF_AP || tcpip_if == TCPIP_ADAPTER_IF_STA) { + netif_add(esp_netif[tcpip_if], &ip_info->ip, &ip_info->netmask, &ip_info->gw, NULL, wlanif_init, tcpip_input); + } else if (tcpip_if == TCPIP_ADAPTER_IF_ETH) { + netif_add(esp_netif[tcpip_if], &ip_info->ip, &ip_info->netmask, &ip_info->gw, NULL, ethernetif_init, tcpip_input); + } } if (tcpip_if == TCPIP_ADAPTER_IF_AP) { @@ -77,7 +83,7 @@ esp_err_t tcpip_adapter_start(tcpip_adapter_if_t tcpip_if, uint8_t *mac, tcpip_a dhcps_start(esp_netif[tcpip_if], ip_info->ip); printf("dhcp server start:(ip: " IPSTR ", mask: " IPSTR ", gw: " IPSTR ")\n", - IP2STR(&ip_info->ip), IP2STR(&ip_info->netmask), IP2STR(&ip_info->gw)); + IP2STR(&ip_info->ip), IP2STR(&ip_info->netmask), IP2STR(&ip_info->gw)); dhcps_status = TCPIP_ADAPTER_DHCP_STARTED; } @@ -88,6 +94,8 @@ esp_err_t tcpip_adapter_start(tcpip_adapter_if_t tcpip_if, uint8_t *mac, tcpip_a netif_set_default(esp_netif[TCPIP_ADAPTER_IF_AP]); } else if (esp_netif[TCPIP_ADAPTER_IF_STA]) { netif_set_default(esp_netif[TCPIP_ADAPTER_IF_STA]); + } else if (esp_netif[TCPIP_ADAPTER_IF_ETH] ) { + netif_set_default(esp_netif[TCPIP_ADAPTER_IF_ETH]); } return ESP_OK; @@ -105,15 +113,15 @@ esp_err_t tcpip_adapter_stop(tcpip_adapter_if_t tcpip_if) if (tcpip_if == TCPIP_ADAPTER_IF_AP) { dhcps_stop(esp_netif[tcpip_if]); // TODO: dhcps checks status by its self - if (TCPIP_ADAPTER_DHCP_STOPPED != dhcps_status){ + if (TCPIP_ADAPTER_DHCP_STOPPED != dhcps_status) { dhcps_status = TCPIP_ADAPTER_DHCP_INIT; } - } else if (tcpip_if == TCPIP_ADAPTER_IF_STA) { + } else if (tcpip_if == TCPIP_ADAPTER_IF_STA || tcpip_if == TCPIP_ADAPTER_IF_ETH) { dhcp_release(esp_netif[tcpip_if]); dhcp_stop(esp_netif[tcpip_if]); dhcp_cleanup(esp_netif[tcpip_if]); - dhcpc_status = TCPIP_ADAPTER_DHCP_INIT; + dhcpc_status[tcpip_if] = TCPIP_ADAPTER_DHCP_INIT; ip4_addr_set_zero(&esp_ip[tcpip_if].ip); ip4_addr_set_zero(&esp_ip[tcpip_if].gw); @@ -135,8 +143,8 @@ esp_err_t tcpip_adapter_stop(tcpip_adapter_if_t tcpip_if) esp_err_t tcpip_adapter_up(tcpip_adapter_if_t tcpip_if) { - if (tcpip_if == TCPIP_ADAPTER_IF_STA) { - if (esp_netif[tcpip_if] == NULL){ + if (tcpip_if == TCPIP_ADAPTER_IF_STA || tcpip_if == TCPIP_ADAPTER_IF_ETH ) { + if (esp_netif[tcpip_if] == NULL) { return ESP_ERR_TCPIP_ADAPTER_IF_NOT_READY; } @@ -150,15 +158,15 @@ esp_err_t tcpip_adapter_up(tcpip_adapter_if_t tcpip_if) esp_err_t tcpip_adapter_down(tcpip_adapter_if_t tcpip_if) { - if (tcpip_if == TCPIP_ADAPTER_IF_STA) { + if (tcpip_if == TCPIP_ADAPTER_IF_STA || tcpip_if == TCPIP_ADAPTER_IF_ETH ) { if (esp_netif[tcpip_if] == NULL) { return ESP_ERR_TCPIP_ADAPTER_IF_NOT_READY; } - if (dhcpc_status == TCPIP_ADAPTER_DHCP_STARTED) { + if (dhcpc_status[tcpip_if] == TCPIP_ADAPTER_DHCP_STARTED) { dhcp_stop(esp_netif[tcpip_if]); - dhcpc_status = TCPIP_ADAPTER_DHCP_INIT; + dhcpc_status[tcpip_if] = TCPIP_ADAPTER_DHCP_INIT; ip4_addr_set_zero(&esp_ip[tcpip_if].ip); ip4_addr_set_zero(&esp_ip[tcpip_if].gw); @@ -215,7 +223,7 @@ esp_err_t tcpip_adapter_set_ip_info(tcpip_adapter_if_t tcpip_if, tcpip_adapter_i if (status != TCPIP_ADAPTER_DHCP_STOPPED) { return ESP_ERR_TCPIP_ADAPTER_DHCP_NOT_STOPPED; } - } else if (tcpip_if == TCPIP_ADAPTER_IF_STA) { + } else if (tcpip_if == TCPIP_ADAPTER_IF_STA || tcpip_if == TCPIP_ADAPTER_IF_ETH ) { tcpip_adapter_dhcpc_get_status(tcpip_if, &status); if (status != TCPIP_ADAPTER_DHCP_STOPPED) { @@ -247,8 +255,8 @@ static void tcpip_adapter_nd6_cb(struct netif *p_netif, uint8_t ip_idex) if (p_netif == esp_netif[TCPIP_ADAPTER_IF_STA]) { ip6_info = &esp_ip6[TCPIP_ADAPTER_IF_STA]; - } else if(p_netif == esp_netif[TCPIP_ADAPTER_IF_AP]) { - ip6_info = &esp_ip6[TCPIP_ADAPTER_IF_AP]; + } else if (p_netif == esp_netif[TCPIP_ADAPTER_IF_AP]) { + ip6_info = &esp_ip6[TCPIP_ADAPTER_IF_AP]; } else { return; } @@ -272,7 +280,7 @@ esp_err_t tcpip_adapter_create_ip6_linklocal(tcpip_adapter_if_t tcpip_if) } p_netif = esp_netif[tcpip_if]; - if(p_netif != NULL && netif_is_up(p_netif)) { + if (p_netif != NULL && netif_is_up(p_netif)) { netif_create_ip6_linklocal_address(p_netif, 1); nd6_set_cb(p_netif, tcpip_adapter_nd6_cb); @@ -353,23 +361,20 @@ esp_err_t tcpip_adapter_dhcps_option(tcpip_adapter_option_mode_t opt_op, tcpip_a } switch (opt_id) { - case IP_ADDRESS_LEASE_TIME: - { - *(uint32_t*)opt_val = *(uint32_t*)opt_info; - break; - } - case REQUESTED_IP_ADDRESS: - { - memcpy(opt_val, opt_info, opt_len); - break; - } - case ROUTER_SOLICITATION_ADDRESS: - { - *(uint8_t *)opt_val = (*(uint8_t *)opt_info) & OFFER_ROUTER; - break; - } - default: - break; + case IP_ADDRESS_LEASE_TIME: { + *(uint32_t *)opt_val = *(uint32_t *)opt_info; + break; + } + case REQUESTED_IP_ADDRESS: { + memcpy(opt_val, opt_info, opt_len); + break; + } + case ROUTER_SOLICITATION_ADDRESS: { + *(uint8_t *)opt_val = (*(uint8_t *)opt_info) & OFFER_ROUTER; + break; + } + default: + break; } } else if (opt_op == TCPIP_ADAPTER_OP_SET) { if (dhcps_status == TCPIP_ADAPTER_DHCP_STARTED) { @@ -377,53 +382,54 @@ esp_err_t tcpip_adapter_dhcps_option(tcpip_adapter_option_mode_t opt_op, tcpip_a } switch (opt_id) { - case IP_ADDRESS_LEASE_TIME: - { - if (*(uint32_t*)opt_val != 0) - *(uint32_t*)opt_info = *(uint32_t*)opt_val; - else - *(uint32_t*)opt_info = DHCPS_LEASE_TIME_DEF; - break; + case IP_ADDRESS_LEASE_TIME: { + if (*(uint32_t *)opt_val != 0) { + *(uint32_t *)opt_info = *(uint32_t *)opt_val; + } else { + *(uint32_t *)opt_info = DHCPS_LEASE_TIME_DEF; } - case REQUESTED_IP_ADDRESS: - { - tcpip_adapter_ip_info_t info; - uint32_t softap_ip = 0; - uint32_t start_ip = 0; - uint32_t end_ip = 0; - dhcps_lease_t *poll = opt_val; + break; + } + case REQUESTED_IP_ADDRESS: { + tcpip_adapter_ip_info_t info; + uint32_t softap_ip = 0; + uint32_t start_ip = 0; + uint32_t end_ip = 0; + dhcps_lease_t *poll = opt_val; + if (poll->enable) { memset(&info, 0x00, sizeof(tcpip_adapter_ip_info_t)); - tcpip_adapter_get_ip_info(WIFI_IF_AP, &info); + tcpip_adapter_get_ip_info(ESP_IF_WIFI_AP, &info); softap_ip = htonl(info.ip.addr); start_ip = htonl(poll->start_ip.addr); end_ip = htonl(poll->end_ip.addr); /*config ip information can't contain local ip*/ - if ((start_ip <= softap_ip) && (softap_ip <= end_ip)) - return ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS; + if ((start_ip <= softap_ip) && (softap_ip <= end_ip)) { + return ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS; + } /*config ip information must be in the same segment as the local ip*/ softap_ip >>= 8; if ((start_ip >> 8 != softap_ip) - || (end_ip >> 8 != softap_ip)) { - return ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS; + || (end_ip >> 8 != softap_ip)) { + return ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS; } if (end_ip - start_ip > DHCPS_MAX_LEASE) { - return ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS; + return ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS; } + } - memcpy(opt_info, opt_val, opt_len); - break; - } - case ROUTER_SOLICITATION_ADDRESS: - { - *(uint8_t *)opt_info = (*(uint8_t *)opt_val) & OFFER_ROUTER; - break; - } - default: - break; + memcpy(opt_info, opt_val, opt_len); + break; + } + case ROUTER_SOLICITATION_ADDRESS: { + *(uint8_t *)opt_info = (*(uint8_t *)opt_val) & OFFER_ROUTER; + break; + } + default: + break; } } else { return ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS; @@ -452,7 +458,7 @@ esp_err_t tcpip_adapter_dhcps_start(tcpip_adapter_if_t tcpip_if) if (p_netif != NULL && netif_is_up(p_netif)) { tcpip_adapter_ip_info_t default_ip; - tcpip_adapter_get_ip_info(WIFI_IF_AP, &default_ip); + tcpip_adapter_get_ip_info(ESP_IF_WIFI_AP, &default_ip); dhcps_start(p_netif, default_ip.ip); dhcps_status = TCPIP_ADAPTER_DHCP_STARTED; TCPIP_ADAPTER_DEBUG("dhcp server start successfully\n"); @@ -501,22 +507,25 @@ esp_err_t tcpip_adapter_dhcpc_option(tcpip_adapter_option_mode_t opt_op, tcpip_a return ESP_OK; } -static void tcpip_adapter_dhcpc_cb(void) +static void tcpip_adapter_dhcpc_cb(struct netif *netif) { - struct netif *netif = esp_netif[TCPIP_ADAPTER_IF_STA]; - if (!netif) { TCPIP_ADAPTER_DEBUG("null netif=%p\n", netif); return; } + if (netif != esp_netif[TCPIP_ADAPTER_IF_STA] && netif != esp_netif[TCPIP_ADAPTER_IF_ETH]) { + TCPIP_ADAPTER_DEBUG("err netif=%p\n", netif); + return; + } + if ( !ip4_addr_cmp(ip_2_ip4(&netif->ip_addr), IP4_ADDR_ANY) ) { tcpip_adapter_ip_info_t *ip_info = &esp_ip[TCPIP_ADAPTER_IF_STA]; //check whether IP is changed if ( !ip4_addr_cmp(ip_2_ip4(&netif->ip_addr), &ip_info->ip) || - !ip4_addr_cmp(ip_2_ip4(&netif->netmask), &ip_info->netmask) || - !ip4_addr_cmp(ip_2_ip4(&netif->gw), &ip_info->gw) ) { + !ip4_addr_cmp(ip_2_ip4(&netif->netmask), &ip_info->netmask) || + !ip4_addr_cmp(ip_2_ip4(&netif->gw), &ip_info->gw) ) { system_event_t evt; ip4_addr_set(&ip_info->ip, ip_2_ip4(&netif->ip_addr)); @@ -524,7 +533,12 @@ static void tcpip_adapter_dhcpc_cb(void) ip4_addr_set(&ip_info->gw, ip_2_ip4(&netif->gw)); //notify event - evt.event_id = SYSTEM_EVENT_STA_GOT_IP; + if (netif == esp_netif[TCPIP_ADAPTER_IF_STA]) { + evt.event_id = SYSTEM_EVENT_STA_GOT_IP; + } else if (netif == esp_netif[TCPIP_ADAPTER_IF_ETH]) { + evt.event_id = SYSTEM_EVENT_ETH_GOT_IP; + } + memcpy(&evt.event_info.got_ip.ip_info, ip_info, sizeof(tcpip_adapter_ip_info_t)); esp_event_send(&evt); @@ -538,7 +552,7 @@ static void tcpip_adapter_dhcpc_cb(void) esp_err_t tcpip_adapter_dhcpc_get_status(tcpip_adapter_if_t tcpip_if, tcpip_adapter_dhcp_status_t *status) { - *status = dhcpc_status; + *status = dhcpc_status[tcpip_if]; return ESP_OK; } @@ -546,12 +560,12 @@ esp_err_t tcpip_adapter_dhcpc_get_status(tcpip_adapter_if_t tcpip_if, tcpip_adap esp_err_t tcpip_adapter_dhcpc_start(tcpip_adapter_if_t tcpip_if) { /* only support sta now, need to support ethernet */ - if (tcpip_if != TCPIP_ADAPTER_IF_STA || tcpip_if >= TCPIP_ADAPTER_IF_MAX) { + if ((tcpip_if != TCPIP_ADAPTER_IF_STA && tcpip_if != TCPIP_ADAPTER_IF_ETH) || tcpip_if >= TCPIP_ADAPTER_IF_MAX) { TCPIP_ADAPTER_DEBUG("dhcp client invalid if=%d\n", tcpip_if); return ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS; } - if (dhcpc_status != TCPIP_ADAPTER_DHCP_STARTED) { + if (dhcpc_status[tcpip_if] != TCPIP_ADAPTER_DHCP_STARTED) { struct netif *p_netif = esp_netif[tcpip_if]; ip4_addr_set_zero(&esp_ip[tcpip_if].ip); @@ -566,7 +580,7 @@ esp_err_t tcpip_adapter_dhcpc_start(tcpip_adapter_if_t tcpip_if) ip_addr_set_zero(&p_netif->gw); } else { TCPIP_ADAPTER_DEBUG("dhcp client re init\n"); - dhcpc_status = TCPIP_ADAPTER_DHCP_INIT; + dhcpc_status[tcpip_if] = TCPIP_ADAPTER_DHCP_INIT; return ESP_OK; } @@ -578,11 +592,11 @@ esp_err_t tcpip_adapter_dhcpc_start(tcpip_adapter_if_t tcpip_if) dhcp_set_cb(p_netif, tcpip_adapter_dhcpc_cb); TCPIP_ADAPTER_DEBUG("dhcp client start successfully\n"); - dhcpc_status = TCPIP_ADAPTER_DHCP_STARTED; + dhcpc_status[tcpip_if] = TCPIP_ADAPTER_DHCP_STARTED; return ESP_OK; } else { TCPIP_ADAPTER_DEBUG("dhcp client re init\n"); - dhcpc_status = TCPIP_ADAPTER_DHCP_INIT; + dhcpc_status[tcpip_if] = TCPIP_ADAPTER_DHCP_INIT; return ESP_OK; } } @@ -599,7 +613,7 @@ esp_err_t tcpip_adapter_dhcpc_stop(tcpip_adapter_if_t tcpip_if) return ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS; } - if (dhcpc_status == TCPIP_ADAPTER_DHCP_STARTED) { + if (dhcpc_status[tcpip_if] == TCPIP_ADAPTER_DHCP_STARTED) { struct netif *p_netif = esp_netif[tcpip_if]; if (p_netif != NULL) { @@ -612,13 +626,19 @@ esp_err_t tcpip_adapter_dhcpc_stop(tcpip_adapter_if_t tcpip_if) TCPIP_ADAPTER_DEBUG("dhcp client if not ready\n"); return ESP_ERR_TCPIP_ADAPTER_IF_NOT_READY; } - } else if (dhcpc_status == TCPIP_ADAPTER_DHCP_STOPPED) { + } else if (dhcpc_status[tcpip_if] == TCPIP_ADAPTER_DHCP_STOPPED) { TCPIP_ADAPTER_DEBUG("dhcp client already stoped\n"); return ESP_ERR_TCPIP_ADAPTER_DHCP_ALREADY_STOPPED; } TCPIP_ADAPTER_DEBUG("dhcp client stop successfully\n"); - dhcpc_status = TCPIP_ADAPTER_DHCP_STOPPED; + dhcpc_status[tcpip_if] = TCPIP_ADAPTER_DHCP_STOPPED; + return ESP_OK; +} + +esp_err_t tcpip_adapter_eth_input(void *buffer, uint16_t len, void *eb) +{ + ethernetif_input(esp_netif[TCPIP_ADAPTER_IF_ETH], buffer, len); return ESP_OK; } @@ -642,29 +662,32 @@ bool tcpip_dep_output(wifi_interface_t wifi_if, void *buffer, uint16_t len) } #endif -wifi_interface_t tcpip_adapter_get_wifi_if(void *dev) +esp_interface_t tcpip_adapter_get_esp_if(void *dev) { struct netif *p_netif = (struct netif *)dev; if (p_netif == esp_netif[TCPIP_ADAPTER_IF_STA]) { - return WIFI_IF_STA; + return ESP_IF_WIFI_STA; } else if (p_netif == esp_netif[TCPIP_ADAPTER_IF_AP]) { - return WIFI_IF_AP; + return ESP_IF_WIFI_AP; + } else if (p_netif == esp_netif[TCPIP_ADAPTER_IF_ETH]) { + return ESP_IF_ETH; } - return WIFI_IF_MAX; + return ESP_IF_MAX; } esp_err_t tcpip_adapter_get_sta_list(wifi_sta_list_t *wifi_sta_list, tcpip_adapter_sta_list_t *tcpip_sta_list) { int i; - if ((wifi_sta_list == NULL) || (tcpip_sta_list == NULL)) + if ((wifi_sta_list == NULL) || (tcpip_sta_list == NULL)) { return ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS; + } memset(tcpip_sta_list, 0, sizeof(tcpip_adapter_sta_list_t)); tcpip_sta_list->num = wifi_sta_list->num; - for (i=0; inum; i++){ + for (i = 0; i < wifi_sta_list->num; i++) { memcpy(tcpip_sta_list->sta[i].mac, wifi_sta_list->sta[i].mac, 6); dhcp_search_ip_on_mac(tcpip_sta_list->sta[i].mac, &tcpip_sta_list->sta[i].ip); } @@ -700,4 +723,20 @@ esp_err_t tcpip_adapter_set_hostname(tcpip_adapter_if_t tcpip_if, const char *ho } } +esp_err_t tcpip_adapter_get_hostname(tcpip_adapter_if_t tcpip_if, const char **hostname) +{ + struct netif *p_netif = NULL; + if (tcpip_if >= TCPIP_ADAPTER_IF_MAX || hostname == NULL) { + return ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS; + } + + p_netif = esp_netif[tcpip_if]; + if (p_netif != NULL) { + *hostname = p_netif->hostname; + return ESP_OK; + } else { + return ESP_ERR_TCPIP_ADAPTER_INVALID_PARAMS; + } +} + #endif diff --git a/components/wpa_supplicant/component.mk b/components/wpa_supplicant/component.mk index b01eb83be9..daac5ca70e 100644 --- a/components/wpa_supplicant/component.mk +++ b/components/wpa_supplicant/component.mk @@ -1,4 +1,4 @@ COMPONENT_ADD_INCLUDEDIRS := include port/include -COMPONENT_SRCDIRS := src/crypto +COMPONENT_SRCDIRS := src/crypto port CFLAGS += -DEMBEDDED_SUPP -D__ets__ -Wno-strict-aliasing diff --git a/components/wpa_supplicant/include/crypto/ms_funcs.h b/components/wpa_supplicant/include/crypto/ms_funcs.h new file mode 100644 index 0000000000..dadb7d9321 --- /dev/null +++ b/components/wpa_supplicant/include/crypto/ms_funcs.h @@ -0,0 +1,60 @@ +/* + * WPA Supplicant / shared MSCHAPV2 helper functions + * + * + */ + +#ifndef MS_FUNCS_H +#define MS_FUNCS_H + +int generate_nt_response(const u8 *auth_challenge, const u8 *peer_challenge, + const u8 *username, size_t username_len, + const u8 *password, size_t password_len, + u8 *response); + +int generate_nt_response_pwhash(const u8 *auth_challenge, + const u8 *peer_challenge, + const u8 *username, size_t username_len, + const u8 *password_hash, + u8 *response); +int generate_authenticator_response(const u8 *password, size_t password_len, + const u8 *peer_challenge, + const u8 *auth_challenge, + const u8 *username, size_t username_len, + const u8 *nt_response, u8 *response); +int generate_authenticator_response_pwhash( + const u8 *password_hash, + const u8 *peer_challenge, const u8 *auth_challenge, + const u8 *username, size_t username_len, + const u8 *nt_response, u8 *response); +int nt_challenge_response(const u8 *challenge, const u8 *password, + size_t password_len, u8 *response); + +void challenge_response(const u8 *challenge, const u8 *password_hash, + u8 *response); +int nt_password_hash(const u8 *password, size_t password_len, + u8 *password_hash); +int hash_nt_password_hash(const u8 *password_hash, u8 *password_hash_hash); +int get_master_key(const u8 *password_hash_hash, const u8 *nt_response, + u8 *master_key); +int get_asymetric_start_key(const u8 *master_key, u8 *session_key, + size_t session_key_len, int is_send, + int is_server); +int encrypt_pw_block_with_password_hash( + const u8 *password, size_t password_len, + const u8 *password_hash, u8 *pw_block); +int __must_check encry_pw_block_with_password_hash( + const u8 *password, size_t password_len, + const u8 *password_hash, u8 *pw_block); +int __must_check new_password_encrypted_with_old_nt_password_hash( + const u8 *new_password, size_t new_password_len, + const u8 *old_password, size_t old_password_len, + u8 *encrypted_pw_block); +void nt_password_hash_encrypted_with_block(const u8 *password_hash, + const u8 *block, u8 *cypher); +int old_nt_password_hash_encrypted_with_new_nt_password_hash( + const u8 *new_password, size_t new_password_len, + const u8 *old_password, size_t old_password_len, + u8 *encrypted_password_hash); + +#endif /* MS_FUNCS_H */ diff --git a/components/wpa_supplicant/include/wpa/common.h b/components/wpa_supplicant/include/wpa/common.h index ca80c2394f..2e6012f868 100644 --- a/components/wpa_supplicant/include/wpa/common.h +++ b/components/wpa_supplicant/include/wpa/common.h @@ -19,6 +19,19 @@ #endif /* ets */ #include "os.h" +/* Define platform specific variable type macros */ +#if defined(ESP_PLATFORM) +#include +typedef uint64_t u64; +typedef uint32_t u32; +typedef uint16_t u16; +typedef uint8_t u8; +typedef int64_t s64; +typedef int32_t s32; +typedef int16_t s16; +typedef int8_t s8; +#endif /*ESP_PLATFORM*/ + #if defined(__XTENSA__) #include #define __BYTE_ORDER BYTE_ORDER diff --git a/components/wpa_supplicant/port/include/endian.h b/components/wpa_supplicant/port/include/endian.h index e2df616b79..5e6a876fda 100644 --- a/components/wpa_supplicant/port/include/endian.h +++ b/components/wpa_supplicant/port/include/endian.h @@ -119,6 +119,7 @@ typedef __uint64_t uint64_t; #endif /* _BYTE_ORDER == _LITTLE_ENDIAN */ /* Alignment-agnostic encode/decode bytestream to/from little/big endian. */ +#define INLINE __inline__ static INLINE uint16_t be16dec(const void *pp) diff --git a/components/wpa_supplicant/port/os_xtensa.c b/components/wpa_supplicant/port/os_xtensa.c new file mode 100644 index 0000000000..9ecde1f113 --- /dev/null +++ b/components/wpa_supplicant/port/os_xtensa.c @@ -0,0 +1,64 @@ +/* + * wpa_supplicant/hostapd / Internal implementation of OS specific functions + * Copyright (c) 2005-2006, Jouni Malinen + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * Alternatively, this software may be distributed under the terms of BSD + * license. + * + * See README and COPYING for more details. + * + * This file is an example of operating system specific wrapper functions. + * This version implements many of the functions internally, so it can be used + * to fill in missing functions from the target system C libraries. + * + * Some of the functions are using standard C library calls in order to keep + * this file in working condition to allow the functions to be tested on a + * Linux target. Please note that OS_NO_C_LIB_DEFINES needs to be defined for + * this file to work correctly. Note that these implementations are only + * examples and are not optimized for speed. + */ + +#include "crypto/common.h" +#include "os.h" +#include +#include +#include +#include "esp_system.h" + +int os_get_time(struct os_time *t) +{ + return gettimeofday((struct timeval*) t, NULL); +} + +unsigned long os_random(void) +{ + return esp_random(); +} + +unsigned long r_rand(void) __attribute__((alias("os_random"))); + + +int os_get_random(unsigned char *buf, size_t len) +{ + int i, j; + unsigned long tmp; + + for (i = 0; i < ((len + 3) & ~3) / 4; i++) { + tmp = r_rand(); + + for (j = 0; j < 4; j++) { + if ((i * 4 + j) < len) { + buf[i * 4 + j] = (uint8_t)(tmp >> (j * 8)); + } else { + break; + } + } + } + + return 0; +} + diff --git a/components/wpa_supplicant/src/crypto/des-internal.c b/components/wpa_supplicant/src/crypto/des-internal.c new file mode 100644 index 0000000000..410199a7bc --- /dev/null +++ b/components/wpa_supplicant/src/crypto/des-internal.c @@ -0,0 +1,494 @@ +/* + * DES and 3DES-EDE ciphers + * + * Modifications to LibTomCrypt implementation: + * Copyright (c) 2006-2009, Jouni Malinen + * + * This software may be distributed under the terms of the BSD license. + * See README for more details. + */ + + +#include "wpa/includes.h" + +#include "wpa/common.h" +#include "crypto/crypto.h" +//#include "des_i.h" + +/* + * This implementation is based on a DES implementation included in + * LibTomCrypt. The version here is modified to fit in wpa_supplicant/hostapd + * coding style. + */ + +/* LibTomCrypt, modular cryptographic library -- Tom St Denis + * + * LibTomCrypt is a library that provides various cryptographic + * algorithms in a highly modular and flexible manner. + * + * The library is free for all purposes without any express + * guarantee it works. + * + * Tom St Denis, tomstdenis@gmail.com, http://libtomcrypt.com + */ + +/** + DES code submitted by Dobes Vandermeer +*/ + +#define ROLc(x, y) \ + ((((unsigned long) (x) << (unsigned long) ((y) & 31)) | \ + (((unsigned long) (x) & 0xFFFFFFFFUL) >> \ + (unsigned long) (32 - ((y) & 31)))) & 0xFFFFFFFFUL) +#define RORc(x, y) \ + (((((unsigned long) (x) & 0xFFFFFFFFUL) >> \ + (unsigned long) ((y) & 31)) | \ + ((unsigned long) (x) << (unsigned long) (32 - ((y) & 31)))) & \ + 0xFFFFFFFFUL) + + +static const u32 bytebit[8] = +{ + 0200, 0100, 040, 020, 010, 04, 02, 01 +}; + +static const u32 bigbyte[24] = +{ + 0x800000UL, 0x400000UL, 0x200000UL, 0x100000UL, + 0x80000UL, 0x40000UL, 0x20000UL, 0x10000UL, + 0x8000UL, 0x4000UL, 0x2000UL, 0x1000UL, + 0x800UL, 0x400UL, 0x200UL, 0x100UL, + 0x80UL, 0x40UL, 0x20UL, 0x10UL, + 0x8UL, 0x4UL, 0x2UL, 0x1L +}; + +/* Use the key schedule specific in the standard (ANSI X3.92-1981) */ + +static const u8 pc1[56] = { + 56, 48, 40, 32, 24, 16, 8, 0, 57, 49, 41, 33, 25, 17, + 9, 1, 58, 50, 42, 34, 26, 18, 10, 2, 59, 51, 43, 35, + 62, 54, 46, 38, 30, 22, 14, 6, 61, 53, 45, 37, 29, 21, + 13, 5, 60, 52, 44, 36, 28, 20, 12, 4, 27, 19, 11, 3 +}; + +static const u8 totrot[16] = { + 1, 2, 4, 6, + 8, 10, 12, 14, + 15, 17, 19, 21, + 23, 25, 27, 28 +}; + +static const u8 pc2[48] = { + 13, 16, 10, 23, 0, 4, 2, 27, 14, 5, 20, 9, + 22, 18, 11, 3, 25, 7, 15, 6, 26, 19, 12, 1, + 40, 51, 30, 36, 46, 54, 29, 39, 50, 44, 32, 47, + 43, 48, 38, 55, 33, 52, 45, 41, 49, 35, 28, 31 +}; + + +static const u32 SP1[64] = +{ + 0x01010400UL, 0x00000000UL, 0x00010000UL, 0x01010404UL, + 0x01010004UL, 0x00010404UL, 0x00000004UL, 0x00010000UL, + 0x00000400UL, 0x01010400UL, 0x01010404UL, 0x00000400UL, + 0x01000404UL, 0x01010004UL, 0x01000000UL, 0x00000004UL, + 0x00000404UL, 0x01000400UL, 0x01000400UL, 0x00010400UL, + 0x00010400UL, 0x01010000UL, 0x01010000UL, 0x01000404UL, + 0x00010004UL, 0x01000004UL, 0x01000004UL, 0x00010004UL, + 0x00000000UL, 0x00000404UL, 0x00010404UL, 0x01000000UL, + 0x00010000UL, 0x01010404UL, 0x00000004UL, 0x01010000UL, + 0x01010400UL, 0x01000000UL, 0x01000000UL, 0x00000400UL, + 0x01010004UL, 0x00010000UL, 0x00010400UL, 0x01000004UL, + 0x00000400UL, 0x00000004UL, 0x01000404UL, 0x00010404UL, + 0x01010404UL, 0x00010004UL, 0x01010000UL, 0x01000404UL, + 0x01000004UL, 0x00000404UL, 0x00010404UL, 0x01010400UL, + 0x00000404UL, 0x01000400UL, 0x01000400UL, 0x00000000UL, + 0x00010004UL, 0x00010400UL, 0x00000000UL, 0x01010004UL +}; + +static const u32 SP2[64] = +{ + 0x80108020UL, 0x80008000UL, 0x00008000UL, 0x00108020UL, + 0x00100000UL, 0x00000020UL, 0x80100020UL, 0x80008020UL, + 0x80000020UL, 0x80108020UL, 0x80108000UL, 0x80000000UL, + 0x80008000UL, 0x00100000UL, 0x00000020UL, 0x80100020UL, + 0x00108000UL, 0x00100020UL, 0x80008020UL, 0x00000000UL, + 0x80000000UL, 0x00008000UL, 0x00108020UL, 0x80100000UL, + 0x00100020UL, 0x80000020UL, 0x00000000UL, 0x00108000UL, + 0x00008020UL, 0x80108000UL, 0x80100000UL, 0x00008020UL, + 0x00000000UL, 0x00108020UL, 0x80100020UL, 0x00100000UL, + 0x80008020UL, 0x80100000UL, 0x80108000UL, 0x00008000UL, + 0x80100000UL, 0x80008000UL, 0x00000020UL, 0x80108020UL, + 0x00108020UL, 0x00000020UL, 0x00008000UL, 0x80000000UL, + 0x00008020UL, 0x80108000UL, 0x00100000UL, 0x80000020UL, + 0x00100020UL, 0x80008020UL, 0x80000020UL, 0x00100020UL, + 0x00108000UL, 0x00000000UL, 0x80008000UL, 0x00008020UL, + 0x80000000UL, 0x80100020UL, 0x80108020UL, 0x00108000UL +}; + +static const u32 SP3[64] = +{ + 0x00000208UL, 0x08020200UL, 0x00000000UL, 0x08020008UL, + 0x08000200UL, 0x00000000UL, 0x00020208UL, 0x08000200UL, + 0x00020008UL, 0x08000008UL, 0x08000008UL, 0x00020000UL, + 0x08020208UL, 0x00020008UL, 0x08020000UL, 0x00000208UL, + 0x08000000UL, 0x00000008UL, 0x08020200UL, 0x00000200UL, + 0x00020200UL, 0x08020000UL, 0x08020008UL, 0x00020208UL, + 0x08000208UL, 0x00020200UL, 0x00020000UL, 0x08000208UL, + 0x00000008UL, 0x08020208UL, 0x00000200UL, 0x08000000UL, + 0x08020200UL, 0x08000000UL, 0x00020008UL, 0x00000208UL, + 0x00020000UL, 0x08020200UL, 0x08000200UL, 0x00000000UL, + 0x00000200UL, 0x00020008UL, 0x08020208UL, 0x08000200UL, + 0x08000008UL, 0x00000200UL, 0x00000000UL, 0x08020008UL, + 0x08000208UL, 0x00020000UL, 0x08000000UL, 0x08020208UL, + 0x00000008UL, 0x00020208UL, 0x00020200UL, 0x08000008UL, + 0x08020000UL, 0x08000208UL, 0x00000208UL, 0x08020000UL, + 0x00020208UL, 0x00000008UL, 0x08020008UL, 0x00020200UL +}; + +static const u32 SP4[64] = +{ + 0x00802001UL, 0x00002081UL, 0x00002081UL, 0x00000080UL, + 0x00802080UL, 0x00800081UL, 0x00800001UL, 0x00002001UL, + 0x00000000UL, 0x00802000UL, 0x00802000UL, 0x00802081UL, + 0x00000081UL, 0x00000000UL, 0x00800080UL, 0x00800001UL, + 0x00000001UL, 0x00002000UL, 0x00800000UL, 0x00802001UL, + 0x00000080UL, 0x00800000UL, 0x00002001UL, 0x00002080UL, + 0x00800081UL, 0x00000001UL, 0x00002080UL, 0x00800080UL, + 0x00002000UL, 0x00802080UL, 0x00802081UL, 0x00000081UL, + 0x00800080UL, 0x00800001UL, 0x00802000UL, 0x00802081UL, + 0x00000081UL, 0x00000000UL, 0x00000000UL, 0x00802000UL, + 0x00002080UL, 0x00800080UL, 0x00800081UL, 0x00000001UL, + 0x00802001UL, 0x00002081UL, 0x00002081UL, 0x00000080UL, + 0x00802081UL, 0x00000081UL, 0x00000001UL, 0x00002000UL, + 0x00800001UL, 0x00002001UL, 0x00802080UL, 0x00800081UL, + 0x00002001UL, 0x00002080UL, 0x00800000UL, 0x00802001UL, + 0x00000080UL, 0x00800000UL, 0x00002000UL, 0x00802080UL +}; + +static const u32 SP5[64] = +{ + 0x00000100UL, 0x02080100UL, 0x02080000UL, 0x42000100UL, + 0x00080000UL, 0x00000100UL, 0x40000000UL, 0x02080000UL, + 0x40080100UL, 0x00080000UL, 0x02000100UL, 0x40080100UL, + 0x42000100UL, 0x42080000UL, 0x00080100UL, 0x40000000UL, + 0x02000000UL, 0x40080000UL, 0x40080000UL, 0x00000000UL, + 0x40000100UL, 0x42080100UL, 0x42080100UL, 0x02000100UL, + 0x42080000UL, 0x40000100UL, 0x00000000UL, 0x42000000UL, + 0x02080100UL, 0x02000000UL, 0x42000000UL, 0x00080100UL, + 0x00080000UL, 0x42000100UL, 0x00000100UL, 0x02000000UL, + 0x40000000UL, 0x02080000UL, 0x42000100UL, 0x40080100UL, + 0x02000100UL, 0x40000000UL, 0x42080000UL, 0x02080100UL, + 0x40080100UL, 0x00000100UL, 0x02000000UL, 0x42080000UL, + 0x42080100UL, 0x00080100UL, 0x42000000UL, 0x42080100UL, + 0x02080000UL, 0x00000000UL, 0x40080000UL, 0x42000000UL, + 0x00080100UL, 0x02000100UL, 0x40000100UL, 0x00080000UL, + 0x00000000UL, 0x40080000UL, 0x02080100UL, 0x40000100UL +}; + +static const u32 SP6[64] = +{ + 0x20000010UL, 0x20400000UL, 0x00004000UL, 0x20404010UL, + 0x20400000UL, 0x00000010UL, 0x20404010UL, 0x00400000UL, + 0x20004000UL, 0x00404010UL, 0x00400000UL, 0x20000010UL, + 0x00400010UL, 0x20004000UL, 0x20000000UL, 0x00004010UL, + 0x00000000UL, 0x00400010UL, 0x20004010UL, 0x00004000UL, + 0x00404000UL, 0x20004010UL, 0x00000010UL, 0x20400010UL, + 0x20400010UL, 0x00000000UL, 0x00404010UL, 0x20404000UL, + 0x00004010UL, 0x00404000UL, 0x20404000UL, 0x20000000UL, + 0x20004000UL, 0x00000010UL, 0x20400010UL, 0x00404000UL, + 0x20404010UL, 0x00400000UL, 0x00004010UL, 0x20000010UL, + 0x00400000UL, 0x20004000UL, 0x20000000UL, 0x00004010UL, + 0x20000010UL, 0x20404010UL, 0x00404000UL, 0x20400000UL, + 0x00404010UL, 0x20404000UL, 0x00000000UL, 0x20400010UL, + 0x00000010UL, 0x00004000UL, 0x20400000UL, 0x00404010UL, + 0x00004000UL, 0x00400010UL, 0x20004010UL, 0x00000000UL, + 0x20404000UL, 0x20000000UL, 0x00400010UL, 0x20004010UL +}; + +static const u32 SP7[64] = +{ + 0x00200000UL, 0x04200002UL, 0x04000802UL, 0x00000000UL, + 0x00000800UL, 0x04000802UL, 0x00200802UL, 0x04200800UL, + 0x04200802UL, 0x00200000UL, 0x00000000UL, 0x04000002UL, + 0x00000002UL, 0x04000000UL, 0x04200002UL, 0x00000802UL, + 0x04000800UL, 0x00200802UL, 0x00200002UL, 0x04000800UL, + 0x04000002UL, 0x04200000UL, 0x04200800UL, 0x00200002UL, + 0x04200000UL, 0x00000800UL, 0x00000802UL, 0x04200802UL, + 0x00200800UL, 0x00000002UL, 0x04000000UL, 0x00200800UL, + 0x04000000UL, 0x00200800UL, 0x00200000UL, 0x04000802UL, + 0x04000802UL, 0x04200002UL, 0x04200002UL, 0x00000002UL, + 0x00200002UL, 0x04000000UL, 0x04000800UL, 0x00200000UL, + 0x04200800UL, 0x00000802UL, 0x00200802UL, 0x04200800UL, + 0x00000802UL, 0x04000002UL, 0x04200802UL, 0x04200000UL, + 0x00200800UL, 0x00000000UL, 0x00000002UL, 0x04200802UL, + 0x00000000UL, 0x00200802UL, 0x04200000UL, 0x00000800UL, + 0x04000002UL, 0x04000800UL, 0x00000800UL, 0x00200002UL +}; + +static const u32 SP8[64] = +{ + 0x10001040UL, 0x00001000UL, 0x00040000UL, 0x10041040UL, + 0x10000000UL, 0x10001040UL, 0x00000040UL, 0x10000000UL, + 0x00040040UL, 0x10040000UL, 0x10041040UL, 0x00041000UL, + 0x10041000UL, 0x00041040UL, 0x00001000UL, 0x00000040UL, + 0x10040000UL, 0x10000040UL, 0x10001000UL, 0x00001040UL, + 0x00041000UL, 0x00040040UL, 0x10040040UL, 0x10041000UL, + 0x00001040UL, 0x00000000UL, 0x00000000UL, 0x10040040UL, + 0x10000040UL, 0x10001000UL, 0x00041040UL, 0x00040000UL, + 0x00041040UL, 0x00040000UL, 0x10041000UL, 0x00001000UL, + 0x00000040UL, 0x10040040UL, 0x00001000UL, 0x00041040UL, + 0x10001000UL, 0x00000040UL, 0x10000040UL, 0x10040000UL, + 0x10040040UL, 0x10000000UL, 0x00040000UL, 0x10001040UL, + 0x00000000UL, 0x10041040UL, 0x00040040UL, 0x10000040UL, + 0x10040000UL, 0x10001000UL, 0x10001040UL, 0x00000000UL, + 0x10041040UL, 0x00041000UL, 0x00041000UL, 0x00001040UL, + 0x00001040UL, 0x00040040UL, 0x10000000UL, 0x10041000UL +}; + +static void cookey(const u32 *raw1, u32 *keyout) +{ + u32 *cook; + const u32 *raw0; + u32 dough[32]; + int i; + + cook = dough; + for (i = 0; i < 16; i++, raw1++) { + raw0 = raw1++; + *cook = (*raw0 & 0x00fc0000L) << 6; + *cook |= (*raw0 & 0x00000fc0L) << 10; + *cook |= (*raw1 & 0x00fc0000L) >> 10; + *cook++ |= (*raw1 & 0x00000fc0L) >> 6; + *cook = (*raw0 & 0x0003f000L) << 12; + *cook |= (*raw0 & 0x0000003fL) << 16; + *cook |= (*raw1 & 0x0003f000L) >> 4; + *cook++ |= (*raw1 & 0x0000003fL); + } + + os_memcpy(keyout, dough, sizeof(dough)); +} + + +static void deskey(const u8 *key, int decrypt, u32 *keyout) +{ + u32 i, j, l, m, n, kn[32]; + u8 pc1m[56], pcr[56]; + + for (j = 0; j < 56; j++) { + l = (u32) pc1[j]; + m = l & 7; + pc1m[j] = (u8) + ((key[l >> 3U] & bytebit[m]) == bytebit[m] ? 1 : 0); + } + + for (i = 0; i < 16; i++) { + if (decrypt) + m = (15 - i) << 1; + else + m = i << 1; + n = m + 1; + kn[m] = kn[n] = 0L; + for (j = 0; j < 28; j++) { + l = j + (u32) totrot[i]; + if (l < 28) + pcr[j] = pc1m[l]; + else + pcr[j] = pc1m[l - 28]; + } + for (/* j = 28 */; j < 56; j++) { + l = j + (u32) totrot[i]; + if (l < 56) + pcr[j] = pc1m[l]; + else + pcr[j] = pc1m[l - 28]; + } + for (j = 0; j < 24; j++) { + if ((int) pcr[(int) pc2[j]] != 0) + kn[m] |= bigbyte[j]; + if ((int) pcr[(int) pc2[j + 24]] != 0) + kn[n] |= bigbyte[j]; + } + } + + cookey(kn, keyout); +} + + +static void desfunc(u32 *block, const u32 *keys) +{ + u32 work, right, leftt; + int cur_round; + + leftt = block[0]; + right = block[1]; + + work = ((leftt >> 4) ^ right) & 0x0f0f0f0fL; + right ^= work; + leftt ^= (work << 4); + + work = ((leftt >> 16) ^ right) & 0x0000ffffL; + right ^= work; + leftt ^= (work << 16); + + work = ((right >> 2) ^ leftt) & 0x33333333L; + leftt ^= work; + right ^= (work << 2); + + work = ((right >> 8) ^ leftt) & 0x00ff00ffL; + leftt ^= work; + right ^= (work << 8); + + right = ROLc(right, 1); + work = (leftt ^ right) & 0xaaaaaaaaL; + + leftt ^= work; + right ^= work; + leftt = ROLc(leftt, 1); + + for (cur_round = 0; cur_round < 8; cur_round++) { + work = RORc(right, 4) ^ *keys++; + leftt ^= SP7[work & 0x3fL] + ^ SP5[(work >> 8) & 0x3fL] + ^ SP3[(work >> 16) & 0x3fL] + ^ SP1[(work >> 24) & 0x3fL]; + work = right ^ *keys++; + leftt ^= SP8[ work & 0x3fL] + ^ SP6[(work >> 8) & 0x3fL] + ^ SP4[(work >> 16) & 0x3fL] + ^ SP2[(work >> 24) & 0x3fL]; + + work = RORc(leftt, 4) ^ *keys++; + right ^= SP7[ work & 0x3fL] + ^ SP5[(work >> 8) & 0x3fL] + ^ SP3[(work >> 16) & 0x3fL] + ^ SP1[(work >> 24) & 0x3fL]; + work = leftt ^ *keys++; + right ^= SP8[ work & 0x3fL] + ^ SP6[(work >> 8) & 0x3fL] + ^ SP4[(work >> 16) & 0x3fL] + ^ SP2[(work >> 24) & 0x3fL]; + } + + right = RORc(right, 1); + work = (leftt ^ right) & 0xaaaaaaaaL; + leftt ^= work; + right ^= work; + leftt = RORc(leftt, 1); + work = ((leftt >> 8) ^ right) & 0x00ff00ffL; + right ^= work; + leftt ^= (work << 8); + /* -- */ + work = ((leftt >> 2) ^ right) & 0x33333333L; + right ^= work; + leftt ^= (work << 2); + work = ((right >> 16) ^ leftt) & 0x0000ffffL; + leftt ^= work; + right ^= (work << 16); + work = ((right >> 4) ^ leftt) & 0x0f0f0f0fL; + leftt ^= work; + right ^= (work << 4); + + block[0] = right; + block[1] = leftt; +} + + +/* wpa_supplicant/hostapd specific wrapper */ + +void des_encrypt(const u8 *clear, const u8 *key, u8 *cypher) +{ + u8 pkey[8], next, tmp; + int i; + u32 ek[32], work[2]; + + /* Add parity bits to the key */ + next = 0; + for (i = 0; i < 7; i++) { + tmp = key[i]; + pkey[i] = (tmp >> i) | next | 1; + next = tmp << (7 - i); + } + pkey[i] = next | 1; + + deskey(pkey, 0, ek); + + work[0] = WPA_GET_BE32(clear); + work[1] = WPA_GET_BE32(clear + 4); + desfunc(work, ek); + WPA_PUT_BE32(cypher, work[0]); + WPA_PUT_BE32(cypher + 4, work[1]); + + os_memset(pkey, 0, sizeof(pkey)); + os_memset(ek, 0, sizeof(ek)); +} + +/* +void des_key_setup(const u8 *key, u32 *ek, u32 *dk) +{ + deskey(key, 0, ek); + deskey(key, 1, dk); +} + + +void des_block_encrypt(const u8 *plain, const u32 *ek, u8 *crypt) +{ + u32 work[2]; + work[0] = WPA_GET_BE32(plain); + work[1] = WPA_GET_BE32(plain + 4); + desfunc(work, ek); + WPA_PUT_BE32(crypt, work[0]); + WPA_PUT_BE32(crypt + 4, work[1]); +} + + +void des_block_decrypt(const u8 *crypt, const u32 *dk, u8 *plain) +{ + u32 work[2]; + work[0] = WPA_GET_BE32(crypt); + work[1] = WPA_GET_BE32(crypt + 4); + desfunc(work, dk); + WPA_PUT_BE32(plain, work[0]); + WPA_PUT_BE32(plain + 4, work[1]); +} + + +void des3_key_setup(const u8 *key, struct des3_key_s *dkey) +{ + deskey(key, 0, dkey->ek[0]); + deskey(key + 8, 1, dkey->ek[1]); + deskey(key + 16, 0, dkey->ek[2]); + + deskey(key, 1, dkey->dk[2]); + deskey(key + 8, 0, dkey->dk[1]); + deskey(key + 16, 1, dkey->dk[0]); +} + + +void des3_encrypt(const u8 *plain, const struct des3_key_s *key, u8 *crypt) +{ + u32 work[2]; + + work[0] = WPA_GET_BE32(plain); + work[1] = WPA_GET_BE32(plain + 4); + desfunc(work, key->ek[0]); + desfunc(work, key->ek[1]); + desfunc(work, key->ek[2]); + WPA_PUT_BE32(crypt, work[0]); + WPA_PUT_BE32(crypt + 4, work[1]); +} + + +void des3_decrypt(const u8 *crypt, const struct des3_key_s *key, u8 *plain) +{ + u32 work[2]; + + work[0] = WPA_GET_BE32(crypt); + work[1] = WPA_GET_BE32(crypt + 4); + desfunc(work, key->dk[0]); + desfunc(work, key->dk[1]); + desfunc(work, key->dk[2]); + WPA_PUT_BE32(plain, work[0]); + WPA_PUT_BE32(plain + 4, work[1]); +}*/ + diff --git a/components/wpa_supplicant/src/crypto/md4-internal.c b/components/wpa_supplicant/src/crypto/md4-internal.c new file mode 100644 index 0000000000..a3ad58129a --- /dev/null +++ b/components/wpa_supplicant/src/crypto/md4-internal.c @@ -0,0 +1,201 @@ +/* + * MD4 hash implementation + * + * This software may be distributed under the terms of BSD license. + */ + +#include "crypto/includes.h" +#include "crypto/common.h" +#include "crypto/crypto.h" + +#define MD4_BLOCK_LENGTH 64 +#define MD4_DIGEST_LENGTH 16 + +typedef struct MD4Context { + u32 state[4]; + u64 count; + u8 buffer[MD4_BLOCK_LENGTH]; +} MD4_CTX; + +static void MD4Init(MD4_CTX *ctx); +static void MD4Update(MD4_CTX *ctx, const unsigned char *input, size_t len); +static void MD4Final(unsigned char digest[MD4_DIGEST_LENGTH], MD4_CTX *ctx); + +int md4_vector(size_t num_elem, const u8 *addr[], const size_t *len, u8 *mac) +{ + MD4_CTX ctx; + size_t i; + + MD4Init(&ctx); + for (i = 0; i < num_elem; i++) + MD4Update(&ctx, addr[i], len[i]); + MD4Final(mac, &ctx); + return 0; +} + +#define MD4_DIGEST_STRING_LENGTH (MD4_DIGEST_LENGTH * 2 + 1) + +static void MD4Transform(u32 state[4], const u8 block[MD4_BLOCK_LENGTH]); + +#define PUT_64BIT_LE(cp, value) do { \ + (cp)[7] = (value) >> 56; \ + (cp)[6] = (value) >> 48; \ + (cp)[5] = (value) >> 40; \ + (cp)[4] = (value) >> 32; \ + (cp)[3] = (value) >> 24; \ + (cp)[2] = (value) >> 16; \ + (cp)[1] = (value) >> 8; \ + (cp)[0] = (value); } while (0) + +#define PUT_32BIT_LE(cp, value) do { \ + (cp)[3] = (value) >> 24; \ + (cp)[2] = (value) >> 16; \ + (cp)[1] = (value) >> 8; \ + (cp)[0] = (value); } while (0) + +static u8 PADDING[MD4_BLOCK_LENGTH] = { + 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 +}; + +static void MD4Init(MD4_CTX *ctx) +{ + ctx->count = 0; + ctx->state[0] = 0x67452301; + ctx->state[1] = 0xefcdab89; + ctx->state[2] = 0x98badcfe; + ctx->state[3] = 0x10325476; +} + +static void MD4Update(MD4_CTX *ctx, const unsigned char *input, size_t len) +{ + size_t have, need; + + have = (size_t)((ctx->count >> 3) & (MD4_BLOCK_LENGTH - 1)); + need = MD4_BLOCK_LENGTH - have; + + ctx->count += (u64)len << 3; + + if (len >= need) { + if (have != 0) { + os_memcpy(ctx->buffer + have, input, need); + MD4Transform(ctx->state, ctx->buffer); + input += need; + len -= need; + have = 0; + } + + while (len >= MD4_BLOCK_LENGTH) { + MD4Transform(ctx->state, input); + input += MD4_BLOCK_LENGTH; + len -= MD4_BLOCK_LENGTH; + } + } + + if (len != 0) + os_memcpy(ctx->buffer + have, input, len); +} + +static void MD4Pad(MD4_CTX *ctx) +{ + u8 count[8]; + size_t padlen; + + PUT_64BIT_LE(count, ctx->count); + + padlen = MD4_BLOCK_LENGTH - + ((ctx->count >> 3) & (MD4_BLOCK_LENGTH - 1)); + if (padlen < 1 + 8) + padlen += MD4_BLOCK_LENGTH; + MD4Update(ctx, PADDING, padlen - 8); + MD4Update(ctx, count, 8); +} + +static void MD4Final(unsigned char digest[MD4_DIGEST_LENGTH], MD4_CTX *ctx) +{ + int i; + + MD4Pad(ctx); + if (digest != NULL) { + for (i = 0; i < 4; i ++) + PUT_32BIT_LE(digest + i * 4, ctx->state[i]); + os_memset(ctx, 0, sizeof(*ctx)); + } +} + +#define F1(x, y, z) (z ^ (x & (y ^ z))) +#define F2(x, y, z) ((x & y) | (x & z) | (y & z)) +#define F3(x, y, z) (x ^ y ^ z) + +#define MD4SETP(f, w, x, y, z, data, s) \ + ( w += f(x, y, z) + data, w = w<>(32-s) ) + +static void MD4Transform(u32 state[4], const u8 block[MD4_BLOCK_LENGTH]) +{ + u32 a, b, c, d, in[MD4_BLOCK_LENGTH / 4]; + + os_memcpy(in, block, sizeof(in)); + + a = state[0]; + b = state[1]; + c = state[2]; + d = state[3]; + + MD4SETP(F1, a, b, c, d, in[ 0], 3); + MD4SETP(F1, d, a, b, c, in[ 1], 7); + MD4SETP(F1, c, d, a, b, in[ 2], 11); + MD4SETP(F1, b, c, d, a, in[ 3], 19); + MD4SETP(F1, a, b, c, d, in[ 4], 3); + MD4SETP(F1, d, a, b, c, in[ 5], 7); + MD4SETP(F1, c, d, a, b, in[ 6], 11); + MD4SETP(F1, b, c, d, a, in[ 7], 19); + MD4SETP(F1, a, b, c, d, in[ 8], 3); + MD4SETP(F1, d, a, b, c, in[ 9], 7); + MD4SETP(F1, c, d, a, b, in[10], 11); + MD4SETP(F1, b, c, d, a, in[11], 19); + MD4SETP(F1, a, b, c, d, in[12], 3); + MD4SETP(F1, d, a, b, c, in[13], 7); + MD4SETP(F1, c, d, a, b, in[14], 11); + MD4SETP(F1, b, c, d, a, in[15], 19); + + MD4SETP(F2, a, b, c, d, in[ 0] + 0x5a827999, 3); + MD4SETP(F2, d, a, b, c, in[ 4] + 0x5a827999, 5); + MD4SETP(F2, c, d, a, b, in[ 8] + 0x5a827999, 9); + MD4SETP(F2, b, c, d, a, in[12] + 0x5a827999, 13); + MD4SETP(F2, a, b, c, d, in[ 1] + 0x5a827999, 3); + MD4SETP(F2, d, a, b, c, in[ 5] + 0x5a827999, 5); + MD4SETP(F2, c, d, a, b, in[ 9] + 0x5a827999, 9); + MD4SETP(F2, b, c, d, a, in[13] + 0x5a827999, 13); + MD4SETP(F2, a, b, c, d, in[ 2] + 0x5a827999, 3); + MD4SETP(F2, d, a, b, c, in[ 6] + 0x5a827999, 5); + MD4SETP(F2, c, d, a, b, in[10] + 0x5a827999, 9); + MD4SETP(F2, b, c, d, a, in[14] + 0x5a827999, 13); + MD4SETP(F2, a, b, c, d, in[ 3] + 0x5a827999, 3); + MD4SETP(F2, d, a, b, c, in[ 7] + 0x5a827999, 5); + MD4SETP(F2, c, d, a, b, in[11] + 0x5a827999, 9); + MD4SETP(F2, b, c, d, a, in[15] + 0x5a827999, 13); + + MD4SETP(F3, a, b, c, d, in[ 0] + 0x6ed9eba1, 3); + MD4SETP(F3, d, a, b, c, in[ 8] + 0x6ed9eba1, 9); + MD4SETP(F3, c, d, a, b, in[ 4] + 0x6ed9eba1, 11); + MD4SETP(F3, b, c, d, a, in[12] + 0x6ed9eba1, 15); + MD4SETP(F3, a, b, c, d, in[ 2] + 0x6ed9eba1, 3); + MD4SETP(F3, d, a, b, c, in[10] + 0x6ed9eba1, 9); + MD4SETP(F3, c, d, a, b, in[ 6] + 0x6ed9eba1, 11); + MD4SETP(F3, b, c, d, a, in[14] + 0x6ed9eba1, 15); + MD4SETP(F3, a, b, c, d, in[ 1] + 0x6ed9eba1, 3); + MD4SETP(F3, d, a, b, c, in[ 9] + 0x6ed9eba1, 9); + MD4SETP(F3, c, d, a, b, in[ 5] + 0x6ed9eba1, 11); + MD4SETP(F3, b, c, d, a, in[13] + 0x6ed9eba1, 15); + MD4SETP(F3, a, b, c, d, in[ 3] + 0x6ed9eba1, 3); + MD4SETP(F3, d, a, b, c, in[11] + 0x6ed9eba1, 9); + MD4SETP(F3, c, d, a, b, in[ 7] + 0x6ed9eba1, 11); + MD4SETP(F3, b, c, d, a, in[15] + 0x6ed9eba1, 15); + + state[0] += a; + state[1] += b; + state[2] += c; + state[3] += d; +} diff --git a/components/wpa_supplicant/src/crypto/ms_funcs.c b/components/wpa_supplicant/src/crypto/ms_funcs.c new file mode 100644 index 0000000000..9fc671298f --- /dev/null +++ b/components/wpa_supplicant/src/crypto/ms_funcs.c @@ -0,0 +1,528 @@ +/* + * WPA Supplicant / shared MSCHAPV2 helper functions / RFC 2433 / RFC 2759 + * Copyright (c) 2004-2012, Jouni Malinen + * + * This software may be distributed under the terms of the BSD license. + * See README for more details. + */ + + +#include "wpa/includes.h" + +#include "wpa/common.h" +#include "crypto/sha1.h" +#include "crypto/ms_funcs.h" +#include "crypto/crypto.h" + +/** + * utf8_to_ucs2 - Convert UTF-8 string to UCS-2 encoding + * @utf8_string: UTF-8 string (IN) + * @utf8_string_len: Length of utf8_string (IN) + * @ucs2_buffer: UCS-2 buffer (OUT) + * @ucs2_buffer_size: Length of UCS-2 buffer (IN) + * @ucs2_string_size: Number of 2-byte words in the resulting UCS-2 string + * Returns: 0 on success, -1 on failure + */ +static int utf8_to_ucs2(const u8 *utf8_string, size_t utf8_string_len, + u8 *ucs2_buffer, size_t ucs2_buffer_size, + size_t *ucs2_string_size) +{ + size_t i, j; + + for (i = 0, j = 0; i < utf8_string_len; i++) { + u8 c = utf8_string[i]; + if (j >= ucs2_buffer_size) { + /* input too long */ + return -1; + } + if (c <= 0x7F) { + WPA_PUT_LE16(ucs2_buffer + j, c); + j += 2; + } else if (i == utf8_string_len - 1 || + j >= ucs2_buffer_size - 1) { + /* incomplete surrogate */ + return -1; + } else { + u8 c2 = utf8_string[++i]; + if ((c & 0xE0) == 0xC0) { + /* two-byte encoding */ + WPA_PUT_LE16(ucs2_buffer + j, + ((c & 0x1F) << 6) | (c2 & 0x3F)); + j += 2; + } else if (i == utf8_string_len || + j >= ucs2_buffer_size - 1) { + /* incomplete surrogate */ + return -1; + } else { + /* three-byte encoding */ + u8 c3 = utf8_string[++i]; + WPA_PUT_LE16(ucs2_buffer + j, + ((c & 0xF) << 12) | + ((c2 & 0x3F) << 6) | (c3 & 0x3F)); + } + } + } + + if (ucs2_string_size) + *ucs2_string_size = j / 2; + return 0; +} + + +/** + * challenge_hash - ChallengeHash() - RFC 2759, Sect. 8.2 + * @peer_challenge: 16-octet PeerChallenge (IN) + * @auth_challenge: 16-octet AuthenticatorChallenge (IN) + * @username: 0-to-256-char UserName (IN) + * @username_len: Length of username + * @challenge: 8-octet Challenge (OUT) + * Returns: 0 on success, -1 on failure + */ +static int challenge_hash(const u8 *peer_challenge, const u8 *auth_challenge, + const u8 *username, size_t username_len, + u8 *challenge) +{ + u8 hash[SHA1_MAC_LEN]; + const unsigned char *addr[3]; + size_t len[3]; + + addr[0] = peer_challenge; + len[0] = 16; + addr[1] = auth_challenge; + len[1] = 16; + addr[2] = username; + len[2] = username_len; + + if (sha1_vector(3, addr, len, hash)) + return -1; + os_memcpy(challenge, hash, 8); + return 0; +} + + +/** + * nt_password_hash - NtPasswordHash() - RFC 2759, Sect. 8.3 + * @password: 0-to-256-unicode-char Password (IN; UTF-8) + * @password_len: Length of password + * @password_hash: 16-octet PasswordHash (OUT) + * Returns: 0 on success, -1 on failure + */ +int nt_password_hash(const u8 *password, size_t password_len, + u8 *password_hash) +{ + u8 buf[512], *pos; + size_t len, max_len; + + max_len = sizeof(buf); + if (utf8_to_ucs2(password, password_len, buf, max_len, &len) < 0) + return -1; + + len *= 2; + pos = buf; + return md4_vector(1, (const u8 **) &pos, &len, password_hash); +} + + +/** + * hash_nt_password_hash - HashNtPasswordHash() - RFC 2759, Sect. 8.4 + * @password_hash: 16-octet PasswordHash (IN) + * @password_hash_hash: 16-octet PasswordHashHash (OUT) + * Returns: 0 on success, -1 on failure + */ +int hash_nt_password_hash(const u8 *password_hash, u8 *password_hash_hash) +{ + size_t len = 16; + return md4_vector(1, &password_hash, &len, password_hash_hash); +} + + +/** + * challenge_response - ChallengeResponse() - RFC 2759, Sect. 8.5 + * @challenge: 8-octet Challenge (IN) + * @password_hash: 16-octet PasswordHash (IN) + * @response: 24-octet Response (OUT) + */ +void challenge_response(const u8 *challenge, const u8 *password_hash, + u8 *response) +{ + u8 zpwd[7]; + des_encrypt(challenge, password_hash, response); + des_encrypt(challenge, password_hash + 7, response + 8); + zpwd[0] = password_hash[14]; + zpwd[1] = password_hash[15]; + os_memset(zpwd + 2, 0, 5); + des_encrypt(challenge, zpwd, response + 16); +} + + +/** + * generate_nt_response - GenerateNTResponse() - RFC 2759, Sect. 8.1 + * @auth_challenge: 16-octet AuthenticatorChallenge (IN) + * @peer_challenge: 16-octet PeerChallenge (IN) + * @username: 0-to-256-char UserName (IN) + * @username_len: Length of username + * @password: 0-to-256-unicode-char Password (IN; UTF-8) + * @password_len: Length of password + * @response: 24-octet Response (OUT) + * Returns: 0 on success, -1 on failure + */ +int generate_nt_response(const u8 *auth_challenge, const u8 *peer_challenge, + const u8 *username, size_t username_len, + const u8 *password, size_t password_len, + u8 *response) +{ + u8 challenge[8]; + u8 password_hash[16]; + + if (challenge_hash(peer_challenge, auth_challenge, username, + username_len, challenge)) + return -1; + if (nt_password_hash(password, password_len, password_hash)) + return -1; + challenge_response(challenge, password_hash, response); + return 0; +} + + +/** + * generate_nt_response_pwhash - GenerateNTResponse() - RFC 2759, Sect. 8.1 + * @auth_challenge: 16-octet AuthenticatorChallenge (IN) + * @peer_challenge: 16-octet PeerChallenge (IN) + * @username: 0-to-256-char UserName (IN) + * @username_len: Length of username + * @password_hash: 16-octet PasswordHash (IN) + * @response: 24-octet Response (OUT) + * Returns: 0 on success, -1 on failure + */ +int generate_nt_response_pwhash(const u8 *auth_challenge, + const u8 *peer_challenge, + const u8 *username, size_t username_len, + const u8 *password_hash, + u8 *response) +{ + u8 challenge[8]; + + if (challenge_hash(peer_challenge, auth_challenge, + username, username_len, + challenge)) + return -1; + challenge_response(challenge, password_hash, response); + return 0; +} + + +/** + * generate_authenticator_response_pwhash - GenerateAuthenticatorResponse() - RFC 2759, Sect. 8.7 + * @password_hash: 16-octet PasswordHash (IN) + * @nt_response: 24-octet NT-Response (IN) + * @peer_challenge: 16-octet PeerChallenge (IN) + * @auth_challenge: 16-octet AuthenticatorChallenge (IN) + * @username: 0-to-256-char UserName (IN) + * @username_len: Length of username + * @response: 20-octet AuthenticatorResponse (OUT) (note: this value is usually + * encoded as a 42-octet ASCII string (S=hexdump_of_response) + * Returns: 0 on success, -1 on failure + */ +int generate_authenticator_response_pwhash( + const u8 *password_hash, + const u8 *peer_challenge, const u8 *auth_challenge, + const u8 *username, size_t username_len, + const u8 *nt_response, u8 *response) +{ + static const u8 magic1[39] = { + 0x4D, 0x61, 0x67, 0x69, 0x63, 0x20, 0x73, 0x65, 0x72, 0x76, + 0x65, 0x72, 0x20, 0x74, 0x6F, 0x20, 0x63, 0x6C, 0x69, 0x65, + 0x6E, 0x74, 0x20, 0x73, 0x69, 0x67, 0x6E, 0x69, 0x6E, 0x67, + 0x20, 0x63, 0x6F, 0x6E, 0x73, 0x74, 0x61, 0x6E, 0x74 + }; + static const u8 magic2[41] = { + 0x50, 0x61, 0x64, 0x20, 0x74, 0x6F, 0x20, 0x6D, 0x61, 0x6B, + 0x65, 0x20, 0x69, 0x74, 0x20, 0x64, 0x6F, 0x20, 0x6D, 0x6F, + 0x72, 0x65, 0x20, 0x74, 0x68, 0x61, 0x6E, 0x20, 0x6F, 0x6E, + 0x65, 0x20, 0x69, 0x74, 0x65, 0x72, 0x61, 0x74, 0x69, 0x6F, + 0x6E + }; + + u8 password_hash_hash[16], challenge[8]; + const unsigned char *addr1[3]; + const size_t len1[3] = { 16, 24, sizeof(magic1) }; + const unsigned char *addr2[3]; + const size_t len2[3] = { SHA1_MAC_LEN, 8, sizeof(magic2) }; + + addr1[0] = password_hash_hash; + addr1[1] = nt_response; + addr1[2] = magic1; + + addr2[0] = response; + addr2[1] = challenge; + addr2[2] = magic2; + + if (hash_nt_password_hash(password_hash, password_hash_hash)) + return -1; + if (sha1_vector(3, addr1, len1, response)) + return -1; + + if (challenge_hash(peer_challenge, auth_challenge, username, + username_len, challenge)) + return -1; + return sha1_vector(3, addr2, len2, response); +} + + +/** + * generate_authenticator_response - GenerateAuthenticatorResponse() - RFC 2759, Sect. 8.7 + * @password: 0-to-256-unicode-char Password (IN; UTF-8) + * @password_len: Length of password + * @nt_response: 24-octet NT-Response (IN) + * @peer_challenge: 16-octet PeerChallenge (IN) + * @auth_challenge: 16-octet AuthenticatorChallenge (IN) + * @username: 0-to-256-char UserName (IN) + * @username_len: Length of username + * @response: 20-octet AuthenticatorResponse (OUT) (note: this value is usually + * encoded as a 42-octet ASCII string (S=hexdump_of_response) + * Returns: 0 on success, -1 on failure + */ +int generate_authenticator_response(const u8 *password, size_t password_len, + const u8 *peer_challenge, + const u8 *auth_challenge, + const u8 *username, size_t username_len, + const u8 *nt_response, u8 *response) +{ + u8 password_hash[16]; + if (nt_password_hash(password, password_len, password_hash)) + return -1; + return generate_authenticator_response_pwhash( + password_hash, peer_challenge, auth_challenge, + username, username_len, nt_response, response); +} + + +/** + * nt_challenge_response - NtChallengeResponse() - RFC 2433, Sect. A.5 + * @challenge: 8-octet Challenge (IN) + * @password: 0-to-256-unicode-char Password (IN; UTF-8) + * @password_len: Length of password + * @response: 24-octet Response (OUT) + * Returns: 0 on success, -1 on failure + */ +int nt_challenge_response(const u8 *challenge, const u8 *password, + size_t password_len, u8 *response) +{ + u8 password_hash[16]; + if (nt_password_hash(password, password_len, password_hash)) + return -1; + challenge_response(challenge, password_hash, response); + return 0; +} + + +/** + * get_master_key - GetMasterKey() - RFC 3079, Sect. 3.4 + * @password_hash_hash: 16-octet PasswordHashHash (IN) + * @nt_response: 24-octet NTResponse (IN) + * @master_key: 16-octet MasterKey (OUT) + * Returns: 0 on success, -1 on failure + */ +int get_master_key(const u8 *password_hash_hash, const u8 *nt_response, + u8 *master_key) +{ + static const u8 magic1[27] = { + 0x54, 0x68, 0x69, 0x73, 0x20, 0x69, 0x73, 0x20, 0x74, + 0x68, 0x65, 0x20, 0x4d, 0x50, 0x50, 0x45, 0x20, 0x4d, + 0x61, 0x73, 0x74, 0x65, 0x72, 0x20, 0x4b, 0x65, 0x79 + }; + const unsigned char *addr[3]; + const size_t len[3] = { 16, 24, sizeof(magic1) }; + u8 hash[SHA1_MAC_LEN]; + + addr[0] = password_hash_hash; + addr[1] = nt_response; + addr[2] = magic1; + + if (sha1_vector(3, addr, len, hash)) + return -1; + os_memcpy(master_key, hash, 16); + return 0; +} + + +/** + * get_asymetric_start_key - GetAsymetricStartKey() - RFC 3079, Sect. 3.4 + * @master_key: 16-octet MasterKey (IN) + * @session_key: 8-to-16 octet SessionKey (OUT) + * @session_key_len: SessionKeyLength (Length of session_key) (IN) + * @is_send: IsSend (IN, BOOLEAN) + * @is_server: IsServer (IN, BOOLEAN) + * Returns: 0 on success, -1 on failure + */ +int get_asymetric_start_key(const u8 *master_key, u8 *session_key, + size_t session_key_len, int is_send, + int is_server) +{ + static const u8 magic2[84] = { + 0x4f, 0x6e, 0x20, 0x74, 0x68, 0x65, 0x20, 0x63, 0x6c, 0x69, + 0x65, 0x6e, 0x74, 0x20, 0x73, 0x69, 0x64, 0x65, 0x2c, 0x20, + 0x74, 0x68, 0x69, 0x73, 0x20, 0x69, 0x73, 0x20, 0x74, 0x68, + 0x65, 0x20, 0x73, 0x65, 0x6e, 0x64, 0x20, 0x6b, 0x65, 0x79, + 0x3b, 0x20, 0x6f, 0x6e, 0x20, 0x74, 0x68, 0x65, 0x20, 0x73, + 0x65, 0x72, 0x76, 0x65, 0x72, 0x20, 0x73, 0x69, 0x64, 0x65, + 0x2c, 0x20, 0x69, 0x74, 0x20, 0x69, 0x73, 0x20, 0x74, 0x68, + 0x65, 0x20, 0x72, 0x65, 0x63, 0x65, 0x69, 0x76, 0x65, 0x20, + 0x6b, 0x65, 0x79, 0x2e + }; + static const u8 magic3[84] = { + 0x4f, 0x6e, 0x20, 0x74, 0x68, 0x65, 0x20, 0x63, 0x6c, 0x69, + 0x65, 0x6e, 0x74, 0x20, 0x73, 0x69, 0x64, 0x65, 0x2c, 0x20, + 0x74, 0x68, 0x69, 0x73, 0x20, 0x69, 0x73, 0x20, 0x74, 0x68, + 0x65, 0x20, 0x72, 0x65, 0x63, 0x65, 0x69, 0x76, 0x65, 0x20, + 0x6b, 0x65, 0x79, 0x3b, 0x20, 0x6f, 0x6e, 0x20, 0x74, 0x68, + 0x65, 0x20, 0x73, 0x65, 0x72, 0x76, 0x65, 0x72, 0x20, 0x73, + 0x69, 0x64, 0x65, 0x2c, 0x20, 0x69, 0x74, 0x20, 0x69, 0x73, + 0x20, 0x74, 0x68, 0x65, 0x20, 0x73, 0x65, 0x6e, 0x64, 0x20, + 0x6b, 0x65, 0x79, 0x2e + }; + static const u8 shs_pad1[40] = { + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 + }; + + static const u8 shs_pad2[40] = { + 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, + 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, + 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, + 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2 + }; + u8 digest[SHA1_MAC_LEN]; + const unsigned char *addr[4]; + const size_t len[4] = { 16, 40, 84, 40 }; + + addr[0] = master_key; + addr[1] = shs_pad1; + if (is_send) { + addr[2] = is_server ? magic3 : magic2; + } else { + addr[2] = is_server ? magic2 : magic3; + } + addr[3] = shs_pad2; + + if (sha1_vector(4, addr, len, digest)) + return -1; + + if (session_key_len > SHA1_MAC_LEN) + session_key_len = SHA1_MAC_LEN; + os_memcpy(session_key, digest, session_key_len); + return 0; +} + + +#define PWBLOCK_LEN 516 + +/** + * encrypt_pw_block_with_password_hash - EncryptPwBlockWithPasswordHash() - RFC 2759, Sect. 8.10 + * @password: 0-to-256-unicode-char Password (IN; UTF-8) + * @password_len: Length of password + * @password_hash: 16-octet PasswordHash (IN) + * @pw_block: 516-byte PwBlock (OUT) + * Returns: 0 on success, -1 on failure + */ +int encrypt_pw_block_with_password_hash( + const u8 *password, size_t password_len, + const u8 *password_hash, u8 *pw_block) +{ + size_t ucs2_len, offset; + u8 *pos; + + os_memset(pw_block, 0, PWBLOCK_LEN); + + if (utf8_to_ucs2(password, password_len, pw_block, 512, &ucs2_len) < 0) + return -1; + + if (ucs2_len > 256) + return -1; + + offset = (256 - ucs2_len) * 2; + if (offset != 0) { + os_memmove(pw_block + offset, pw_block, ucs2_len * 2); + if (os_get_random(pw_block, offset) < 0) + return -1; + } + /* + * PasswordLength is 4 octets, but since the maximum password length is + * 256, only first two (in little endian byte order) can be non-zero. + */ + pos = &pw_block[2 * 256]; + WPA_PUT_LE16(pos, password_len * 2); + rc4_skip(password_hash, 16, 0, pw_block, PWBLOCK_LEN); + return 0; +} + + +/** + * new_password_encrypted_with_old_nt_password_hash - NewPasswordEncryptedWithOldNtPasswordHash() - RFC 2759, Sect. 8.9 + * @new_password: 0-to-256-unicode-char NewPassword (IN; UTF-8) + * @new_password_len: Length of new_password + * @old_password: 0-to-256-unicode-char OldPassword (IN; UTF-8) + * @old_password_len: Length of old_password + * @encrypted_pw_block: 516-octet EncryptedPwBlock (OUT) + * Returns: 0 on success, -1 on failure + */ +int new_password_encrypted_with_old_nt_password_hash( + const u8 *new_password, size_t new_password_len, + const u8 *old_password, size_t old_password_len, + u8 *encrypted_pw_block) +{ + u8 password_hash[16]; + + if (nt_password_hash(old_password, old_password_len, password_hash)) + return -1; + if (encrypt_pw_block_with_password_hash(new_password, new_password_len, + password_hash, + encrypted_pw_block)) + return -1; + return 0; +} + + +/** + * nt_password_hash_encrypted_with_block - NtPasswordHashEncryptedWithBlock() - RFC 2759, Sect 8.13 + * @password_hash: 16-octer PasswordHash (IN) + * @block: 16-octet Block (IN) + * @cypher: 16-octer Cypher (OUT) + */ +void nt_password_hash_encrypted_with_block(const u8 *password_hash, + const u8 *block, u8 *cypher) +{ + des_encrypt(password_hash, block, cypher); + des_encrypt(password_hash + 8, block + 7, cypher + 8); +} + + +/** + * old_nt_password_hash_encrypted_with_new_nt_password_hash - OldNtPasswordHashEncryptedWithNewNtPasswordHash() - RFC 2759, Sect. 8.12 + * @new_password: 0-to-256-unicode-char NewPassword (IN; UTF-8) + * @new_password_len: Length of new_password + * @old_password: 0-to-256-unicode-char OldPassword (IN; UTF-8) + * @old_password_len: Length of old_password + * @encrypted_password_hash: 16-octet EncryptedPasswordHash (OUT) + * Returns: 0 on success, -1 on failure + */ +int old_nt_password_hash_encrypted_with_new_nt_password_hash( + const u8 *new_password, size_t new_password_len, + const u8 *old_password, size_t old_password_len, + u8 *encrypted_password_hash) +{ + u8 old_password_hash[16], new_password_hash[16]; + + if (nt_password_hash(old_password, old_password_len, + old_password_hash) || + nt_password_hash(new_password, new_password_len, + new_password_hash)) + return -1; + nt_password_hash_encrypted_with_block(old_password_hash, + new_password_hash, + encrypted_password_hash); + return 0; +} + diff --git a/docs/Doxyfile b/docs/Doxyfile old mode 100644 new mode 100755 index eeb4fe740d..11921dfe06 --- a/docs/Doxyfile +++ b/docs/Doxyfile @@ -18,12 +18,15 @@ PROJECT_NAME = "ESP32 Programming Guide" INPUT = ../components/esp32/include/esp_wifi.h \ ../components/driver/include/driver \ ../components/bt/include \ + ../components/bt/bluedroid/api/include \ ../components/nvs_flash/include \ ../components/log/include \ ../components/vfs/include \ ../components/spi_flash/include \ ../components/esp32/include/esp_int_wdt.h \ - ../components/esp32/include/esp_task_wdt.h + ../components/esp32/include/esp_task_wdt.h \ + ../components/app_update/include/esp_ota_ops.h \ + ../components/ethernet/include/esp_eth.h ## Get warnings for functions that have no documentation for their parameters or return value ## diff --git a/docs/api/bt.rst b/docs/api/bt.rst index 1824bc454a..924e855c2f 100644 --- a/docs/api/bt.rst +++ b/docs/api/bt.rst @@ -1,41 +1,10 @@ Bluetooth ========= -Overview --------- +.. toctree:: + :caption: Bluetooth APIs -`Instructions`_ - -Application Example -------------------- - -Check `/examples `_ folder of `espressif/esp-idf `_ repository, that contains the following example: - -`05_ble_adv `_ - - This is a BLE advertising demo with virtual HCI interface. Send Reset/ADV_PARAM/ADV_DATA/ADV_ENABLE HCI command for BLE advertising. - -`Instructions`_ - -.. _Instructions: template.html - -API Reference -------------- - -Header Files -^^^^^^^^^^^^ - - * `bt/include/bt.h `_ - -Type Definitions -^^^^^^^^^^^^^^^^ - -.. doxygenstruct:: vhci_host_callback - -Functions -^^^^^^^^^ - -.. doxygenfunction:: API_vhci_host_check_send_available -.. doxygenfunction:: API_vhci_host_register_callback -.. doxygenfunction:: API_vhci_host_send_packet -.. doxygenfunction:: bt_controller_init + Bluetooth VHCI + Bluetooth Common + Bluetooth Classic + Bluetooth LE diff --git a/docs/api/bt_common.rst b/docs/api/bt_common.rst new file mode 100644 index 0000000000..eaa6b8d31f --- /dev/null +++ b/docs/api/bt_common.rst @@ -0,0 +1,8 @@ +BT COMMON +========= + +.. toctree:: + :caption: Bluetooth Common Defines and APIs + + Bluetooth DEFINE + Bluetooth MAIN diff --git a/docs/api/bt_le.rst b/docs/api/bt_le.rst new file mode 100644 index 0000000000..6ae4869372 --- /dev/null +++ b/docs/api/bt_le.rst @@ -0,0 +1,10 @@ +BT COMMON +========= + +.. toctree:: + :caption: Bluetooth LE + + BLE GAP + BLE GATT DEFINE + BLE GATT SERVER + BLE GATT CLIENT diff --git a/docs/api/esp_bt_defs.rst b/docs/api/esp_bt_defs.rst new file mode 100644 index 0000000000..9a2131f74c --- /dev/null +++ b/docs/api/esp_bt_defs.rst @@ -0,0 +1,60 @@ +BT GENERIC DEFINES +================== + +Overview +-------- + +`Instructions`_ + +Application Example +------------------- + +`Instructions`_ + +.. _Instructions: template.html + + +API Reference +------------- + +Header Files +^^^^^^^^^^^^ + + * `bt/bluedroid/api/include/esp_bt_defs.h `_ + + +Macros +^^^^^^ + +.. doxygendefine:: ESP_DEFAULT_GATT_IF +.. doxygendefine:: ESP_BLE_CONN_PARAM_UNDEF +.. doxygendefine:: ESP_BLE_IS_VALID_PARAM +.. doxygendefine:: ESP_UUID_LEN_16 +.. doxygendefine:: ESP_UUID_LEN_32 +.. doxygendefine:: ESP_UUID_LEN_128 +.. doxygendefine:: ESP_BD_ADDR_LEN +.. doxygendefine:: ESP_APP_ID_MIN +.. doxygendefine:: ESP_APP_ID_MAX + +Type Definitions +^^^^^^^^^^^^^^^^ + +.. doxygentypedef:: esp_bd_addr_t +.. doxygentypedef:: esp_profile_cb_t + +Enumerations +^^^^^^^^^^^^ + +.. doxygenenum:: esp_bt_status_t +.. doxygenenum:: esp_bt_dev_type_t +.. doxygenenum:: esp_bd_addr_type_t +.. doxygenenum:: esp_ble_addr_type_t + +Structures +^^^^^^^^^^ + + +Functions +^^^^^^^^^ + + diff --git a/docs/api/esp_bt_main.rst b/docs/api/esp_bt_main.rst new file mode 100644 index 0000000000..dc317c584f --- /dev/null +++ b/docs/api/esp_bt_main.rst @@ -0,0 +1,49 @@ +BT MAIN API +=========== + +Overview +-------- + +`Instructions`_ + +Application Example +------------------- + +`Instructions`_ + +.. _Instructions: template.html + + +API Reference +------------- + +Header Files +^^^^^^^^^^^^ + + * `bt/bluedroid/api/include/esp_bt_main.h `_ + + +Macros +^^^^^^ + + +Type Definitions +^^^^^^^^^^^^^^^^ + + +Enumerations +^^^^^^^^^^^^ + + +Structures +^^^^^^^^^^ + + +Functions +^^^^^^^^^ + +.. doxygenfunction:: esp_enable_bluetooth +.. doxygenfunction:: esp_disable_bluetooth +.. doxygenfunction:: esp_init_bluetooth +.. doxygenfunction:: esp_deinit_bluetooth + diff --git a/docs/api/esp_eth.rst b/docs/api/esp_eth.rst new file mode 100644 index 0000000000..f8f19092d1 --- /dev/null +++ b/docs/api/esp_eth.rst @@ -0,0 +1,51 @@ +ETHERNET +======== + +Application Example +------------------- + +ethernet example: `examples/14_ethernet `_. + +API Reference +------------- + +Header Files +^^^^^^^^^^^^ + + * `components/ethernet/include/esp_eth.h `_ + +Macros +^^^^^^ + + +Type Definitions +^^^^^^^^^^^^^^^^ + +.. doxygentypedef:: eth_phy_fun +.. doxygentypedef:: eth_tcpip_input_fun +.. doxygentypedef:: eth_gpio_config_func + +Enumerations +^^^^^^^^^^^^ + +.. doxygenenum:: eth_mode_t +.. doxygenenum:: eth_phy_base_t + +Structures +^^^^^^^^^^ + +.. doxygenstruct:: eth_config_t + :members: + + +Functions +^^^^^^^^^ + +.. doxygenfunction:: esp_eth_init +.. doxygenfunction:: esp_eth_tx +.. doxygenfunction:: esp_eth_enable +.. doxygenfunction:: esp_eth_disable +.. doxygenfunction:: esp_eth_get_mac +.. doxygenfunction:: esp_eth_smi_write +.. doxygenfunction:: esp_eth_smi_read + diff --git a/docs/api/esp_gap_ble.rst b/docs/api/esp_gap_ble.rst new file mode 100644 index 0000000000..f1837d4025 --- /dev/null +++ b/docs/api/esp_gap_ble.rst @@ -0,0 +1,103 @@ +GAP API +======== + +Overview +-------- + +`Instructions`_ + +Application Example +------------------- + +Check `/examples `_ folder of `espressif/esp-idf `_ repository, that contains the following example: + +`14_gatts_demo `_ +`15_gattc_demo `_ + +The two demos use different gap api, such like advertising, scan, set device name and others. + +`Instructions`_ + +.. _Instructions: template.html + + +API Reference +------------- + +Header Files +^^^^^^^^^^^^ + + * `bt/bluedroid/api/include/esp_gap_ble_api.h `_ + + +Macros +^^^^^^ + +.. doxygendefine:: ESP_BLE_ADV_DATA_LEN_MAX + +Type Definitions +^^^^^^^^^^^^^^^^ + + +Enumerations +^^^^^^^^^^^^ + +.. doxygenenum:: esp_gap_ble_cb_event_t +.. doxygenenum:: esp_ble_adv_data_type +.. doxygenenum:: esp_ble_adv_type_t +.. doxygenenum:: esp_ble_adv_channel_t +.. doxygenenum:: esp_ble_adv_filter_t +.. doxygenenum:: esp_ble_own_addr_src_t +.. doxygenenum:: esp_ble_scan_type_t +.. doxygenenum:: esp_ble_scan_filter_t +.. doxygenenum:: esp_gap_search_evt_t +.. doxygenenum:: esp_ble_evt_type_t + +Structures +^^^^^^^^^^ + +.. doxygenstruct:: esp_ble_adv_params_t + :members: + +.. doxygenstruct:: esp_ble_adv_data_t + :members: + +.. doxygenstruct:: esp_ble_scan_params_t + :members: + +.. doxygenstruct:: esp_ble_conn_update_params_t + :members: + +.. doxygenstruct:: esp_ble_gap_cb_param_t + :members: + +.. doxygenstruct:: esp_ble_gap_cb_param_t::ble_adv_data_cmpl_evt_param + :members: + +.. doxygenstruct:: esp_ble_gap_cb_param_t::ble_scan_rsp_data_cmpl_evt_param + :members: + +.. doxygenstruct:: esp_ble_gap_cb_param_t::ble_scan_param_cmpl_evt_param + :members: + +.. doxygenstruct:: esp_ble_gap_cb_param_t::ble_scan_result_evt_param + :members: + + +Functions +^^^^^^^^^ + +.. doxygenfunction:: esp_ble_gap_register_callback +.. doxygenfunction:: esp_ble_gap_config_adv_data +.. doxygenfunction:: esp_ble_gap_set_scan_params +.. doxygenfunction:: esp_ble_gap_start_scanning +.. doxygenfunction:: esp_ble_gap_stop_scanning +.. doxygenfunction:: esp_ble_gap_start_advertising +.. doxygenfunction:: esp_ble_gap_stop_advertising +.. doxygenfunction:: esp_ble_gap_update_conn_params +.. doxygenfunction:: esp_ble_gap_set_pkt_data_len +.. doxygenfunction:: esp_ble_gap_set_rand_addr +.. doxygenfunction:: esp_ble_gap_config_local_privacy +.. doxygenfunction:: esp_ble_gap_set_device_name +.. doxygenfunction:: esp_ble_resolve_adv_data + diff --git a/docs/api/esp_gatt_defs.rst b/docs/api/esp_gatt_defs.rst new file mode 100644 index 0000000000..a4cfe918cd --- /dev/null +++ b/docs/api/esp_gatt_defs.rst @@ -0,0 +1,60 @@ +GATT DEFINES +============ + +Overview +-------- + +`Instructions`_ + +Application Example +------------------- + +`Instructions`_ + +.. _Instructions: template.html + + +API Reference +------------- + +Header Files +^^^^^^^^^^^^ + + * `bt/bluedroid/api/include/esp_gatt_defs.h `_ + + +Macros +^^^^^^ + +.. doxygendefine:: ESP_GATT_MAX_ATTR_LEN + +Type Definitions +^^^^^^^^^^^^^^^^ + +.. doxygentypedef:: esp_gatt_if_t + +Enumerations +^^^^^^^^^^^^ + +.. doxygenenum:: esp_gatt_prep_write_type +.. doxygenenum:: esp_gatt_status_t +.. doxygenenum:: esp_gatt_conn_reason_t +.. doxygenenum:: esp_gatt_auth_req_t +.. doxygenenum:: esp_gatt_perm_t +.. doxygenenum:: esp_gatt_char_prop_t +.. doxygenenum:: esp_gatt_write_type_t + +Structures +^^^^^^^^^^ + +.. doxygenstruct:: esp_gatt_value_t + :members: + +.. doxygenstruct:: esp_gatt_rsp_t + :members: + + +Functions +^^^^^^^^^ + + diff --git a/docs/api/esp_gattc.rst b/docs/api/esp_gattc.rst new file mode 100644 index 0000000000..efd2623ad9 --- /dev/null +++ b/docs/api/esp_gattc.rst @@ -0,0 +1,125 @@ +GATT CLIENT API +=============== + +Overview +-------- + +`Instructions`_ + +Application Example +------------------- + +Check `/examples `_ folder of `espressif/esp-idf `_ repository, that contains the following example: + +`15_gattc_demo `_ + +This is a gatt client demo. This demo can scan devices, connect to the gatt server and discover the service. + +`Instructions`_ + +.. _Instructions: template.html + + +API Reference +------------- + +Header Files +^^^^^^^^^^^^ + + * `bt/bluedroid/api/include/esp_gattc_api.h `_ + +Macros +^^^^^^ + +.. doxygendefine:: ESP_GATT_DEF_BLE_MTU_SIZE +.. doxygendefine:: ESP_GATT_MAX_MTU_SIZE + +Type Definitions +^^^^^^^^^^^^^^^^ + + +Enumerations +^^^^^^^^^^^^ + +.. doxygenenum:: esp_gattc_cb_event_t + +Structures +^^^^^^^^^^ + +.. doxygenstruct:: esp_ble_gattc_cb_param_t + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_reg_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_open_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_close_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_cfg_mtu_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_search_cmpl_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_search_res_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_read_char_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_write_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_exec_cmpl_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_notify_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_srvc_chg_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_congest_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_get_char_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_get_descr_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_get_incl_srvc_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_reg_for_notify_evt_param + :members: + +.. doxygenstruct:: esp_ble_gattc_cb_param_t::gattc_unreg_for_notify_evt_param + :members: + + +Functions +^^^^^^^^^ + +.. doxygenfunction:: esp_ble_gattc_register_callback +.. doxygenfunction:: esp_ble_gattc_app_register +.. doxygenfunction:: esp_ble_gattc_app_unregister +.. doxygenfunction:: esp_ble_gattc_open +.. doxygenfunction:: esp_ble_gattc_close +.. doxygenfunction:: esp_ble_gattc_config_mtu +.. doxygenfunction:: esp_ble_gattc_search_service +.. doxygenfunction:: esp_ble_gattc_get_characteristic +.. doxygenfunction:: esp_ble_gattc_get_descriptor +.. doxygenfunction:: esp_ble_gattc_get_included_service +.. doxygenfunction:: esp_ble_gattc_read_char +.. doxygenfunction:: esp_ble_gattc_read_char_descr +.. doxygenfunction:: esp_ble_gattc_write_char +.. doxygenfunction:: esp_ble_gattc_write_char_descr +.. doxygenfunction:: esp_ble_gattc_prepare_write +.. doxygenfunction:: esp_ble_gattc_execute_write +.. doxygenfunction:: esp_ble_gattc_register_for_notify +.. doxygenfunction:: esp_ble_gattc_unregister_for_notify + diff --git a/docs/api/esp_gatts.rst b/docs/api/esp_gatts.rst new file mode 100644 index 0000000000..fdb0e055a9 --- /dev/null +++ b/docs/api/esp_gatts.rst @@ -0,0 +1,121 @@ +GATT SERVER API +=============== + +Overview +-------- + +`Instructions`_ + +Application Example +------------------- + +Check `/examples `_ folder of `espressif/esp-idf `_ repository, that contains the following example: + +`14_gatts_demo `_ + +This is a gatt server demo. Use gatt api to create a gatt server with send advertising. This gatt server can be connected and the service can be discovery. + +`Instructions`_ + +.. _Instructions: template.html + + +API Reference +------------- + +Header Files +^^^^^^^^^^^^ + + * `bt/bluedroid/api/include/esp_gatts_api.h `_ + +Macros +^^^^^^ + +.. doxygendefine:: ESP_GATT_PREP_WRITE_CANCEL +.. doxygendefine:: ESP_GATT_PREP_WRITE_EXEC + +Type Definitions +^^^^^^^^^^^^^^^^ + + +Enumerations +^^^^^^^^^^^^ + +.. doxygenenum:: esp_gatts_cb_event_t + +Structures +^^^^^^^^^^ + +.. doxygenstruct:: esp_ble_gatts_cb_param_t + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_reg_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_read_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_write_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_exec_write_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_mtu_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_conf_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_create_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_add_incl_srvc_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_add_char_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_add_char_descr_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_delete_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_start_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_stop_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_connect_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_disconnect_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_congest_evt_param + :members: + +.. doxygenstruct:: esp_ble_gatts_cb_param_t::gatts_rsp_evt_param + :members: + + +Functions +^^^^^^^^^ + +.. doxygenfunction:: esp_ble_gatts_register_callback +.. doxygenfunction:: esp_ble_gatts_app_register +.. doxygenfunction:: esp_ble_gatts_app_unregister +.. doxygenfunction:: esp_ble_gatts_create_service +.. doxygenfunction:: esp_ble_gatts_add_included_service +.. doxygenfunction:: esp_ble_gatts_add_char +.. doxygenfunction:: esp_ble_gatts_add_char_descr +.. doxygenfunction:: esp_ble_gatts_delete_service +.. doxygenfunction:: esp_ble_gatts_start_service +.. doxygenfunction:: esp_ble_gatts_stop_service +.. doxygenfunction:: esp_ble_gatts_send_indicate +.. doxygenfunction:: esp_ble_gatts_send_response +.. doxygenfunction:: esp_ble_gatts_open +.. doxygenfunction:: esp_ble_gatts_close + diff --git a/docs/api/ota.rst b/docs/api/ota.rst new file mode 100644 index 0000000000..a4984620f6 --- /dev/null +++ b/docs/api/ota.rst @@ -0,0 +1,32 @@ +OTA +=== + +API Reference +------------- + +Header Files +^^^^^^^^^^^^ + + * `app_update/include/esp_ota_ops.h `_ + +Macros +^^^^^^ + +.. doxygendefine:: ESP_ERR_OTA_BASE +.. doxygendefine:: ESP_ERR_OTA_PARTITION_CONFLICT +.. doxygendefine:: ESP_ERR_OTA_SELECT_INFO_INVALID +.. doxygendefine:: ESP_ERR_OTA_VALIDATE_FAILED + +Type Definitions +^^^^^^^^^^^^^^^^ + +.. doxygentypedef:: esp_ota_handle_t + +Functions +^^^^^^^^^ + +.. doxygenfunction:: esp_ota_begin +.. doxygenfunction:: esp_ota_write +.. doxygenfunction:: esp_ota_end +.. doxygenfunction:: esp_ota_set_boot_partition +.. doxygenfunction:: esp_ota_get_boot_partition diff --git a/docs/api/pcnt.rst b/docs/api/pcnt.rst new file mode 100644 index 0000000000..848fa55267 --- /dev/null +++ b/docs/api/pcnt.rst @@ -0,0 +1,66 @@ +Pulse Counter +======== + +Overview +-------- + +The PCNT (Pulse Counter) module is designed to count the number of rising and/or falling edges of an input signal. Each pulse counter unit has a 16-bit signed counter register and two channels that can be configured to either increment or decrement the counter. Each channel has a signal input that accepts signal edges to be detected, as well as a control input that can be used to enable or disable the signal input. The inputs have optional filters that can be used to discard unwanted glitches in the signal. + +Application Example +------------------- + +Pulse counter with control signal and event interrupt example: `examples/12_pcnt `_. + +API Reference +------------- + +Header Files +^^^^^^^^^^^^ + + * `driver/pcnt.h `_ + + +Macros +^^^^^^ + + +Type Definitions +^^^^^^^^^^^^^^^^ + + +Enumerations +^^^^^^^^^^^^ + +.. doxygenenum:: pcnt_ctrl_mode_t +.. doxygenenum:: pcnt_count_mode_t +.. doxygenenum:: pcnt_unit_t +.. doxygenenum:: pcnt_channel_t +.. doxygenenum:: pcnt_evt_type_t + +Structures +^^^^^^^^^^ + +.. doxygenstruct:: pcnt_config_t + +Functions +^^^^^^^^^ + +.. doxygenfunction:: pcnt_unit_config +.. doxygenfunction:: pcnt_get_counter_value +.. doxygenfunction:: pcnt_counter_pause +.. doxygenfunction:: pcnt_counter_resume +.. doxygenfunction:: pcnt_counter_clear +.. doxygenfunction:: pcnt_intr_enable +.. doxygenfunction:: pcnt_intr_disable +.. doxygenfunction:: pcnt_event_enable +.. doxygenfunction:: pcnt_event_disable +.. doxygenfunction:: pcnt_set_event_value +.. doxygenfunction:: pcnt_get_event_value +.. doxygenfunction:: pcnt_isr_register +.. doxygenfunction:: pcnt_set_pin +.. doxygenfunction:: pcnt_filter_enable +.. doxygenfunction:: pcnt_filter_disable +.. doxygenfunction:: pcnt_set_filter_value +.. doxygenfunction:: pcnt_get_filter_value +.. doxygenfunction:: pcnt_set_mode + diff --git a/docs/api/timer.rst b/docs/api/timer.rst new file mode 100644 index 0000000000..0db0a12c23 --- /dev/null +++ b/docs/api/timer.rst @@ -0,0 +1,73 @@ +TIMER +======== + +Overview +-------- + +ESP32 chip contains two hardware timer groups, each containing two general-purpose hardware timers. + +They are all 64-bit generic timers based on 16-bit prescalers and 64-bit auto-reload-capable up/down counters. + + +Application Example +------------------- + +64-bit hardware timer example: `examples/13_timer_group `_. + +API Reference +------------- + +Header Files +^^^^^^^^^^^^ + + * `components/driver/timer.h `_ + +Macros +^^^^^^ + +.. doxygendefine:: TIMER_BASE_CLK + +Type Definitions +^^^^^^^^^^^^^^^^ + + +Enumerations +^^^^^^^^^^^^ + +.. doxygenenum:: timer_group_t +.. doxygenenum:: timer_idx_t +.. doxygenenum:: timer_count_dir_t +.. doxygenenum:: timer_start_t +.. doxygenenum:: timer_alarm_t +.. doxygenenum:: timer_intr_mode_t +.. doxygenenum:: timer_autoreload_t + +Structures +^^^^^^^^^^ + +.. doxygenstruct:: timer_config_t + :members: + + +Functions +^^^^^^^^^ + +.. doxygenfunction:: timer_get_counter_value +.. doxygenfunction:: timer_get_counter_time_sec +.. doxygenfunction:: timer_set_counter_value +.. doxygenfunction:: timer_start +.. doxygenfunction:: timer_pause +.. doxygenfunction:: timer_set_counter_mode +.. doxygenfunction:: timer_set_auto_reload +.. doxygenfunction:: timer_set_divider +.. doxygenfunction:: timer_set_alarm_value +.. doxygenfunction:: timer_get_alarm_value +.. doxygenfunction:: timer_set_alarm +.. doxygenfunction:: timer_isr_register +.. doxygenfunction:: timer_init +.. doxygenfunction:: timer_get_config +.. doxygenfunction:: timer_group_intr_enable +.. doxygenfunction:: timer_group_intr_disable +.. doxygenfunction:: timer_enable_intr +.. doxygenfunction:: timer_disable_intr + diff --git a/docs/api/vhci.rst b/docs/api/vhci.rst new file mode 100644 index 0000000000..0d5d8b5fff --- /dev/null +++ b/docs/api/vhci.rst @@ -0,0 +1,41 @@ +VHCI +==== + +Overview +-------- + +`Instructions`_ + +Application Example +------------------- + +Check `/examples `_ folder of `espressif/esp-idf `_ repository, that contains the following example: + +`05_ble_adv `_ + + This is a BLE advertising demo with virtual HCI interface. Send Reset/ADV_PARAM/ADV_DATA/ADV_ENABLE HCI command for BLE advertising. + +`Instructions`_ + +.. _Instructions: template.html + +API Reference +------------- + +Header Files +^^^^^^^^^^^^ + + * `bt/include/bt.h `_ + +Type Definitions +^^^^^^^^^^^^^^^^ + +.. doxygenstruct:: vhci_host_callback + +Functions +^^^^^^^^^ + +.. doxygenfunction:: API_vhci_host_check_send_available +.. doxygenfunction:: API_vhci_host_register_callback +.. doxygenfunction:: API_vhci_host_send_packet +.. doxygenfunction:: bt_controller_init diff --git a/docs/build_system.rst b/docs/build_system.rst index 4ba89f8652..ad263da7af 100644 --- a/docs/build_system.rst +++ b/docs/build_system.rst @@ -244,6 +244,7 @@ The following variables can be set inside ``component.mk`` to control the build settings. Component-specific additions can be made via ``CXXFLAGS +=``. It is also possible (although not recommended) to override this variable completely for a component. +- ``FLAGS_basename`` allows you to set compilation flags to apply to a single source file only. For example, this can useful for disabling warnings in a single upstream source file. The ``basename`` portion is the directory (relative to ``COMPONENT_PATH``) and the base filename (without extension) of the source file. For example, if a file inside ``COMPONENT_PATH`` is ``library/alpha/widget.c`` then you can set variable ``FLAGS_library/alpha/widget := -DTEST`` to pass the TEST macro when compiling this source file only. Component Configuration ----------------------- diff --git a/docs/index.rst b/docs/index.rst old mode 100644 new mode 100755 index 829ce0334e..be6a372b4b --- a/docs/index.rst +++ b/docs/index.rst @@ -97,15 +97,18 @@ Contents: Wi-Fi Bluetooth Watchdogs - - api/gpio - api/uart - api/ledc - api/rmt + OTA + GPIO + UART + LED Control + Remote Control + Timer + Pulse Counter SPI Flash and Partition APIs Logging Non-Volatile Storage Virtual Filesystem + Ethernet deep-sleep-stub Template diff --git a/examples/01_hello_world/main/hello_world_main.c b/examples/01_hello_world/main/hello_world_main.c index 1ff190acef..0e872522fa 100644 --- a/examples/01_hello_world/main/hello_world_main.c +++ b/examples/01_hello_world/main/hello_world_main.c @@ -21,7 +21,7 @@ void hello_task(void *pvParameter) } printf("Restarting now.\n"); fflush(stdout); - system_restart(); + esp_restart(); } void app_main() diff --git a/examples/03_http_request/main/http_request_main.c b/examples/03_http_request/main/http_request_main.c index 2c203f8394..9fe1933373 100644 --- a/examples/03_http_request/main/http_request_main.c +++ b/examples/03_http_request/main/http_request_main.c @@ -88,7 +88,7 @@ static void initialise_wifi(void) }; ESP_LOGI(TAG, "Setting WiFi configuration SSID %s...", wifi_config.sta.ssid); ESP_ERROR_CHECK( esp_wifi_set_mode(WIFI_MODE_STA) ); - ESP_ERROR_CHECK( esp_wifi_set_config(WIFI_IF_STA, &wifi_config) ); + ESP_ERROR_CHECK( esp_wifi_set_config(ESP_IF_WIFI_STA, &wifi_config) ); ESP_ERROR_CHECK( esp_wifi_start() ); } diff --git a/examples/04_https_request/main/https_request_main.c b/examples/04_https_request/main/https_request_main.c index 1f7112bc86..1d6115d08c 100644 --- a/examples/04_https_request/main/https_request_main.c +++ b/examples/04_https_request/main/https_request_main.c @@ -169,7 +169,7 @@ static void initialise_wifi(void) }; ESP_LOGI(TAG, "Setting WiFi configuration SSID %s...", wifi_config.sta.ssid); ESP_ERROR_CHECK( esp_wifi_set_mode(WIFI_MODE_STA) ); - ESP_ERROR_CHECK( esp_wifi_set_config(WIFI_IF_STA, &wifi_config) ); + ESP_ERROR_CHECK( esp_wifi_set_config(ESP_IF_WIFI_STA, &wifi_config) ); ESP_ERROR_CHECK( esp_wifi_start() ); } diff --git a/examples/06_sntp/main/sntp_main.c b/examples/06_sntp/main/sntp_main.c index 83f33b9656..c3edb9e2bd 100644 --- a/examples/06_sntp/main/sntp_main.c +++ b/examples/06_sntp/main/sntp_main.c @@ -88,7 +88,7 @@ void app_main() const int deep_sleep_sec = 10; ESP_LOGI(TAG, "Entering deep sleep for %d seconds", deep_sleep_sec); - system_deep_sleep(1000000LL * deep_sleep_sec); + esp_deep_sleep(1000000LL * deep_sleep_sec); } static void obtain_time(void) @@ -136,7 +136,7 @@ static void initialise_wifi(void) }; ESP_LOGI(TAG, "Setting WiFi configuration SSID %s...", wifi_config.sta.ssid); ESP_ERROR_CHECK( esp_wifi_set_mode(WIFI_MODE_STA) ); - ESP_ERROR_CHECK( esp_wifi_set_config(WIFI_IF_STA, &wifi_config) ); + ESP_ERROR_CHECK( esp_wifi_set_config(ESP_IF_WIFI_STA, &wifi_config) ); ESP_ERROR_CHECK( esp_wifi_start() ); } diff --git a/examples/07_nvs_rw_value/main/nvs_rw_value.c b/examples/07_nvs_rw_value/main/nvs_rw_value.c index 978c48edb8..dac2d4077e 100644 --- a/examples/07_nvs_rw_value/main/nvs_rw_value.c +++ b/examples/07_nvs_rw_value/main/nvs_rw_value.c @@ -76,5 +76,5 @@ void app_main() } printf("Restarting now.\n"); fflush(stdout); - system_restart(); + esp_restart(); } diff --git a/examples/08_nvs_rw_blob/main/nvs_rw_blob.c b/examples/08_nvs_rw_blob/main/nvs_rw_blob.c index 3fbdfcacd6..7c13c15ba7 100644 --- a/examples/08_nvs_rw_blob/main/nvs_rw_blob.c +++ b/examples/08_nvs_rw_blob/main/nvs_rw_blob.c @@ -170,7 +170,7 @@ void app_main() if (err != ESP_OK) printf("Error (%d) saving run time blob to NVS!\n", err); printf("Restarting...\n"); fflush(stdout); - system_restart(); + esp_restart(); } } vTaskDelay(200 / portTICK_RATE_MS); diff --git a/examples/09_openssl_client/main/openssl_client.c b/examples/09_openssl_client/main/openssl_client.c index c6b0e449ac..69e16141be 100644 --- a/examples/09_openssl_client/main/openssl_client.c +++ b/examples/09_openssl_client/main/openssl_client.c @@ -213,7 +213,7 @@ static void wifi_conn_init(void) }, }; ESP_ERROR_CHECK( esp_wifi_set_mode(WIFI_MODE_STA) ); - ESP_ERROR_CHECK( esp_wifi_set_config(WIFI_IF_STA, &wifi_config) ); + ESP_ERROR_CHECK( esp_wifi_set_config(ESP_IF_WIFI_STA, &wifi_config) ); ESP_LOGI(TAG, "start the WIFI SSID:[%s] password:[%s]\n", EXAMPLE_WIFI_SSID, EXAMPLE_WIFI_PASS); ESP_ERROR_CHECK( esp_wifi_start() ); } diff --git a/examples/10_openssl_server/main/openssl_server.c b/examples/10_openssl_server/main/openssl_server.c index 53b6050d57..756c1407f5 100644 --- a/examples/10_openssl_server/main/openssl_server.c +++ b/examples/10_openssl_server/main/openssl_server.c @@ -236,7 +236,7 @@ static void wifi_conn_init(void) }, }; ESP_ERROR_CHECK( esp_wifi_set_mode(WIFI_MODE_STA) ); - ESP_ERROR_CHECK( esp_wifi_set_config(WIFI_IF_STA, &wifi_config) ); + ESP_ERROR_CHECK( esp_wifi_set_config(ESP_IF_WIFI_STA, &wifi_config) ); ESP_LOGI(TAG, "start the WIFI SSID:[%s] password:[%s]\n", EXAMPLE_WIFI_SSID, EXAMPLE_WIFI_PASS); ESP_ERROR_CHECK( esp_wifi_start() ); } diff --git a/examples/12_blufi/Makefile b/examples/12_blufi/Makefile index 924da7c330..7e7548444f 100644 --- a/examples/12_blufi/Makefile +++ b/examples/12_blufi/Makefile @@ -9,3 +9,10 @@ COMPONENT_ADD_INCLUDEDIRS := components/include include $(IDF_PATH)/make/project.mk +# Copy some defaults into the sdkconfig by default +# so BT stack is enabled +sdkconfig: sdkconfig.defaults + $(Q) cp $< $@ + +menuconfig: sdkconfig +defconfig: sdkconfig diff --git a/examples/12_blufi/components/blufi/component.mk b/examples/12_blufi/components/blufi/component.mk index 6e8166489b..297e63f919 100644 --- a/examples/12_blufi/components/blufi/component.mk +++ b/examples/12_blufi/components/blufi/component.mk @@ -11,5 +11,3 @@ COMPONENT_SRCDIRS := . CFLAGS += -Wno-error=unused-label -Wno-error=return-type -Wno-error=missing-braces -Wno-error=pointer-sign -Wno-error=parentheses -I./include - -include $(IDF_PATH)/make/component_common.mk diff --git a/examples/12_blufi/main/component.mk b/examples/12_blufi/main/component.mk index 24356f23ed..79edf031d3 100644 --- a/examples/12_blufi/main/component.mk +++ b/examples/12_blufi/main/component.mk @@ -6,5 +6,3 @@ # lib(subdirectory_name).a in the build directory. This behaviour is entirely configurable, # please read the ESP-IDF documents if you need to do this. # - -include $(IDF_PATH)/make/component_common.mk diff --git a/examples/12_blufi/main/demo_main.c b/examples/12_blufi/main/demo_main.c index 31a315d218..f1c3807741 100644 --- a/examples/12_blufi/main/demo_main.c +++ b/examples/12_blufi/main/demo_main.c @@ -127,7 +127,6 @@ void app_main() esp_err_t ret; nvs_flash_init(); - system_init(); initialise_wifi(); //vTaskDelay(3000 / portTICK_PERIOD_MS); diff --git a/examples/12_blufi/sdkconfig.defaults b/examples/12_blufi/sdkconfig.defaults new file mode 100644 index 0000000000..e435f383c8 --- /dev/null +++ b/examples/12_blufi/sdkconfig.defaults @@ -0,0 +1,14 @@ +# Override some defaults so BT stack is enabled +# in this example + +# +# BT config +# +CONFIG_BT_ENABLED=y + +# +# ESP32-specific config +# +CONFIG_ESP32_ENABLE_STACK_BT=y +# CONFIG_ESP32_ENABLE_STACK_NONE is not set +CONFIG_MEMMAP_BT=y diff --git a/examples/13_bt_sdp/README.rst b/examples/13_bt_sdp/README.rst deleted file mode 100755 index c55040a510..0000000000 --- a/examples/13_bt_sdp/README.rst +++ /dev/null @@ -1,5 +0,0 @@ -ESP-IDF 08 SDP Server and Client -======================= - -Demo of bluetooth SDP server and client - diff --git a/examples/13_bt_sdp/components/bluedroid_demos/app_core/bt_app_core.c b/examples/13_bt_sdp/components/bluedroid_demos/app_core/bt_app_core.c deleted file mode 100755 index b6661067b8..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/app_core/bt_app_core.c +++ /dev/null @@ -1,188 +0,0 @@ -// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at - -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -#include -#include -#include - -#include "fixed_queue.h" -#include "gki.h" -#include "bt_defs.h" -#include "bt_trace.h" -#include "bt_types.h" -#include "allocator.h" - -#include "bta_api.h" -#include "bta_gatt_api.h" -#include "bt_app_common.h" - -#include "controller.h" -#include "thread.h" -#include "bt_app_common.h" - -static fixed_queue_t *bt_app_msg_queue; - -xQueueHandle xBtAppQueue; -xTaskHandle xBtAppTaskHandle; - -static void bt_app_context_switched(void *p_msg); -static void bt_app_send_msg(void *p_msg); -static void bt_app_task_handler(void *arg); -static void bta_app_msg_ready(fixed_queue_t *queue); -static void bt_app_task_shut_down(void); - - -extern void app_main_entry(void); - -static void bt_app_task_handler(void *arg) -{ - app_main_entry(); - TaskEvt_t *e; - for (;;) { - if (pdTRUE == xQueueReceive(xBtAppQueue, &e, (portTickType)portMAX_DELAY)) { - if (e->sig == 0xff) { - fixed_queue_process(bt_app_msg_queue); - } - osi_free(e); - } - } -} - -static void bt_app_task_post(void) -{ - TaskEvt_t *evt = (TaskEvt_t *)osi_malloc(sizeof(TaskEvt_t)); - if (evt == NULL) - return; - - evt->sig = 0xff; - evt->par = 0; - - if (xQueueSend(xBtAppQueue, &evt, 10/portTICK_RATE_MS) != pdTRUE) { - ets_printf("btdm_post failed\n"); - } -} - -static void bta_app_msg_ready(fixed_queue_t *queue) { - BT_HDR *p_msg; - while (!fixed_queue_is_empty(queue)) { - p_msg = (BT_HDR *)fixed_queue_dequeue(queue); - LOG_ERROR("bta_app_msg_ready, evt: %d\n", p_msg->event); - switch (p_msg->event) { - case BT_EVT_APP_CONTEXT_SWITCH: - bt_app_context_switched(p_msg); - break; - default: - LOG_ERROR("unhandled BT_APP event (%d)\n", p_msg->event & BT_EVT_MASK); - break; - } - GKI_freebuf(p_msg); - } -} - -static void bt_app_context_switched(void *p_msg) -{ - tBTAPP_CONTEXT_SWITCH_CBACK *p = (tBTAPP_CONTEXT_SWITCH_CBACK *) p_msg; - - if (p->p_cb) - p->p_cb(p->event, p->p_param); -} - -static void bt_app_send_msg(void *p_msg) -{ - if (bt_app_msg_queue) { - fixed_queue_enqueue(bt_app_msg_queue, p_msg); - bt_app_task_post(); - } -} - -bt_status_t bt_app_transfer_context (tBTAPP_CBACK *p_cback, UINT16 event, char* p_params, int param_len, tBTAPP_COPY_CBACK *p_copy_cback) -{ - tBTAPP_CONTEXT_SWITCH_CBACK *p_msg; - - LOG_ERROR("btapp_transfer_context evt %d, len %d\n", event, param_len); - - /* allocate and send message that will be executed in btif context */ - if ((p_msg = (tBTAPP_CONTEXT_SWITCH_CBACK *) GKI_getbuf(sizeof(tBTAPP_CONTEXT_SWITCH_CBACK) + param_len)) != NULL) - { - p_msg->hdr.event = BT_EVT_APP_CONTEXT_SWITCH; /* internal event */ - p_msg->p_cb = p_cback; - - p_msg->event = event; /* callback event */ - - /* check if caller has provided a copy callback to do the deep copy */ - if (p_copy_cback) - { - p_copy_cback(event, p_msg->p_param, p_params); - } - else if (p_params) - { - memcpy(p_msg->p_param, p_params, param_len); /* callback parameter data */ - } - - bt_app_send_msg(p_msg); - return BT_STATUS_SUCCESS; - } - else - { - /* let caller deal with a failed allocation */ - return BT_STATUS_NOMEM; - } -} - -void bt_app_task_start_up(void) -{ - bt_app_msg_queue = fixed_queue_new(SIZE_MAX); - if (bt_app_msg_queue == NULL) - goto error_exit; - //ke_event_callback_set(KE_EVENT_BT_APP_TASK, &bt_app_task_handler); - - xBtAppQueue = xQueueCreate(3, sizeof(void *)); - xTaskCreate(bt_app_task_handler, "BtaApp1T", 8192, NULL, configMAX_PRIORITIES - 3, xBtAppTaskHandle); - - fixed_queue_register_dequeue(bt_app_msg_queue, bta_app_msg_ready); - - return; - -error_exit: - LOG_ERROR("%s Unable to allocate resources for bt_app\n", __func__); - bt_app_task_shut_down(); -} - -static void bt_app_task_shut_down(void) -{ - fixed_queue_unregister_dequeue(bt_app_msg_queue); - fixed_queue_free(bt_app_msg_queue, NULL); - bt_app_msg_queue = NULL; - - vTaskDelete(xBtAppTaskHandle); - vQueueDelete(xBtAppQueue); -} - -/* -static void bt_app_upstreams_evt(UINT16 event, char *p_param) -{ - tBTA_DM_SEC *p_data = (tBTA_DM_SEC*)p_param; - switch (event) { - default: - break; - } -} - -static void bt_stack_evt(tBTA_DM_SEC_EVT event, tBTA_DM_SEC* p_data) -{ - LOG_ERROR("bt_stack_evt: %d\n", (uint16_t)event); - bt_app_transfer_context(bt_app_upstreams_evt, (uint16_t)event, - (void *)p_data, sizeof(tBTA_DM_SEC), NULL); -} -*/ diff --git a/examples/13_bt_sdp/components/bluedroid_demos/app_project/SampleBtSdp.c b/examples/13_bt_sdp/components/bluedroid_demos/app_project/SampleBtSdp.c deleted file mode 100644 index 691199c004..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/app_project/SampleBtSdp.c +++ /dev/null @@ -1,154 +0,0 @@ -// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at - -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -#include -#include -#include -#include - - -#include "freertos/FreeRTOS.h" -#include "freertos/task.h" - -#include "bt_app_common.h" -#include "btif_stack_manager.h" -#include "btif_sdp.h" -#include "bt_gap_api.h" - -#include "bta_api.h" - -typedef enum { - BT_APP_EVT_STACK_ON, - BT_APP_EVT_STACK_OFF, - BT_APP_EVT -} tBT_APP_EVT; - -typedef union { - uint32_t dummy; -} tBT_APP_EVT_DATA; - -static void bt_stack_state_changed(bt_state_t state); -static int bt_sdp_add_record(void); -static void bt_sdp_search_complete(bt_status_t status, bt_bdaddr_t *bd_addr, uint8_t* uuid, int num_records, bluetooth_sdp_record *records); - -// static bt_bdaddr_t peer_bd_addr = {{0x00, 0x1b, 0xdc, 0x08, 0x0f, 0xe7}}; -static bt_bdaddr_t peer_bd_addr = {{0xfc, 0x3f, 0x7c, 0xf1, 0x2c, 0x78}}; - -/* root browse -static const uint8_t target_uuid[16] = { 0x00, 0x00, 0x10, 0x02, 0x00, 0x00, 0x10, 0x00, - 0x80, 0x00, 0x00, 0x80, 0x5F, 0x9B, 0x34, 0xFB }; -*/ - -/* UUID_MAP_MAS */ -static const uint8_t target_uuid[] = {0x00, 0x00, 0x11, 0x32, 0x00, 0x00, 0x10, 0x00, - 0x80, 0x00, 0x00, 0x80, 0x5F, 0x9B, 0x34, 0xFB}; - -/* UUID AUDIO Source */ -/* -static const uint8_t target_uuid[] = {0x00, 0x00, 0x11, 0x0A, 0x00, 0x00, 0x10, 0x00, - 0x80, 0x00, 0x00, 0x80, 0x5F, 0x9B, 0x34, 0xFB}; -*/ - -static bt_callbacks_t bt_callbacks = { - bt_stack_state_changed -}; - -static btsdp_callbacks_t btsdp_callbacks = { - bt_sdp_search_complete -}; - -static void bt_app_stack_evt(UINT16 event, char *p_param) -{ - switch (event) { - case BT_APP_EVT_STACK_ON: { - char *dev_name = "SDP_SERVER_CLIENT"; - BTM_SetTraceLevel(BT_TRACE_LEVEL_DEBUG); - BTA_DmSetDeviceName(dev_name); - - esp_bt_gap_set_scan_mode(BT_SCAN_MODE_CONNECTABLE_DISCOVERABLE); - BTIF_SdpInit(&btsdp_callbacks); - - vTaskDelay(1000 / portTICK_PERIOD_MS); - bt_sdp_add_record(); - - vTaskDelay(20000/portTICK_PERIOD_MS); - BTIF_SdpSearch(&peer_bd_addr, target_uuid); - } - break; - default: - break; - } -} - -static void bt_stack_evt(tBT_APP_EVT event, tBT_APP_EVT_DATA *p_data) -{ - LOG_ERROR("bt_stack_evt: %d\n", (uint16_t)event); - bt_app_transfer_context(bt_app_stack_evt, (uint16_t)event, - (void *)p_data, sizeof(tBT_APP_EVT_DATA), NULL); -} - -static void bt_stack_state_changed(bt_state_t state) -{ - if (state == BT_STATE_ON) { - bt_stack_evt(BT_APP_EVT_STACK_ON, NULL); - } -} - -static int bt_sdp_add_record(void) -{ - int handle; - bluetooth_sdp_sap_record sap_svr; - memset (&sap_svr, 0, sizeof(bluetooth_sdp_sap_record)); - - sap_svr.hdr.type = SDP_TYPE_SAP_SERVER; - sap_svr.hdr.rfcomm_channel_number = 2; - sap_svr.hdr.service_name = "SIM ACCESS"; - sap_svr.hdr.service_name_length = 10; - sap_svr.hdr.profile_version = 0x0100; - - BTIF_SdpCreateRecord((bluetooth_sdp_record *)(&sap_svr), &handle); - return handle; -} - -static void bt_sdp_search_complete(bt_status_t status, bt_bdaddr_t *bd_addr, uint8_t* uuid, int num_records, bluetooth_sdp_record *records) -{ - uint8_t *addr = bd_addr->address; - bluetooth_sdp_hdr_overlay *p = &records->mas.hdr; - LOG_ERROR("sdp search cmpl: st %d, bd_addr: %02x:%02x:%02x:%02x:%02x:%02x, records %d\n", - status, addr[0], addr[1], addr[2], addr[3], addr[4], addr[5], num_records); - if (p->service_name_length > 0) { - LOG_ERROR("service name: %s\n", p->service_name); - } - LOG_ERROR("rfc_chl_num %d, l2cap_psm %d, version %02x\n", - p->rfcomm_channel_number, p->l2cap_psm, p->profile_version); -#if 0 - uint8_t *addr = bd_addr->address; - bluetooth_sdp_hdr_overlay *p = &records->hdr; - LOG_ERROR("sdp search cmpl: st %d, bd_addr: %02x:%02x:%02x:%02x:%02x:%02x, records %d, len:%d\n", - status, addr[0], addr[1], addr[2], addr[3], addr[4], addr[5], num_records, p->user1_ptr_len); - if (p->service_name_length > 0) { - LOG_ERROR("service name: %s\n", p->service_name); - } -#endif -} - -void app_main_entry(void) -{ - bt_status_t stat; - stat = BTIF_InitStack(&bt_callbacks); - if (stat == BT_STATUS_SUCCESS) { - BTIF_EnableStack(); - } -} - diff --git a/examples/13_bt_sdp/components/bluedroid_demos/btif/btif_core.c b/examples/13_bt_sdp/components/bluedroid_demos/btif/btif_core.c deleted file mode 100755 index 2ca63a0b69..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/btif/btif_core.c +++ /dev/null @@ -1,483 +0,0 @@ -/****************************************************************************** - * - * Copyright (C) 2014 The Android Open Source Project - * Copyright (C) 2009-2012 Broadcom Corporation - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at: - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - ******************************************************************************/ - -/************************************************************************************ - * - * Filename: btif_core.c - * - * Description: Contains core functionality related to interfacing between - * Bluetooth HAL and BTE core stack. - * - ***********************************************************************************/ - -#include -// #include -// #include -// #include -// #include -#include -#include -// #include -// #include - -#define LOG_TAG "bt_btif_core" -// #include "btcore/include/bdaddr.h" - -#include "bdaddr.h" -// #include "bt_utils.h" -#include "bta_api.h" -#include "bte.h" -#include "btif_api.h" -// #include "btif_av.h" -// #include "btif_config.h" -// #include "btif_pan.h" -// #include "btif_profile_queue.h" -// #include "btif_config.h" -// #include "btif_sock.h" -// #include "btif_storage.h" -#include "btif_util.h" -#include "btu.h" -#include "controller.h" -#include "fixed_queue.h" -#include "future.h" -#include "gki.h" -#include "osi.h" -// #include "osi/include/log.h" -#include "stack_manager.h" -#include "thread.h" -#include "btif_common.h" -#include "btif_dm.h" -/************************************************************************************ -** Constants & Macros -************************************************************************************/ - -/************************************************************************************ -** Local type definitions -************************************************************************************/ - -/************************************************************************************ -** Static variables -************************************************************************************/ - -static tBTA_SERVICE_MASK btif_enabled_services = 0; - -static fixed_queue_t *btif_msg_queue = NULL; -static xTaskHandle xBtifTaskHandle = NULL; - -/************************************************************************************ -** Static functions -************************************************************************************/ - -/* sends message to btif task */ -static void btif_sendmsg(void *p_msg); -static void btif_thread_post(uint32_t sig); -/************************************************************************************ -** Externs -************************************************************************************/ -static QueueHandle_t xBtifQueue = NULL; - -/** TODO: Move these to _common.h */ -void bte_main_boot_entry(void *); -void bte_main_disable(void); -void bte_main_shutdown(void); -void btif_dm_execute_service_request(UINT16 event, char *p_param); - -/******************************************************************************* -** -** Function btif_context_switched -** -** Description Callback used to execute transferred context callback -** -** p_msg : message to be executed in btif context -** -** Returns void -** -*******************************************************************************/ - -static void btif_context_switched(void *p_msg) -{ - - BTIF_TRACE_VERBOSE("btif_context_switched"); - - tBTIF_CONTEXT_SWITCH_CBACK *p = (tBTIF_CONTEXT_SWITCH_CBACK *) p_msg; - - /* each callback knows how to parse the data */ - if (p->p_cb) - p->p_cb(p->event, p->p_param); -} - - -/******************************************************************************* -** -** Function btif_transfer_context -** -** Description This function switches context to btif task -** -** p_cback : callback used to process message in btif context -** event : event id of message -** p_params : parameter area passed to callback (copied) -** param_len : length of parameter area -** p_copy_cback : If set this function will be invoked for deep copy -** -** Returns void -** -*******************************************************************************/ - -bt_status_t btif_transfer_context (tBTIF_CBACK *p_cback, UINT16 event, char* p_params, int param_len, tBTIF_COPY_CBACK *p_copy_cback) -{ - tBTIF_CONTEXT_SWITCH_CBACK *p_msg; - - BTIF_TRACE_VERBOSE("btif_transfer_context event %d, len %d", event, param_len); - - /* allocate and send message that will be executed in btif context */ - if ((p_msg = (tBTIF_CONTEXT_SWITCH_CBACK *) GKI_getbuf(sizeof(tBTIF_CONTEXT_SWITCH_CBACK) + param_len)) != NULL) - { - p_msg->hdr.event = BT_EVT_CONTEXT_SWITCH_EVT; /* internal event */ - p_msg->p_cb = p_cback; - - p_msg->event = event; /* callback event */ - - /* check if caller has provided a copy callback to do the deep copy */ - if (p_copy_cback) - { - p_copy_cback(event, p_msg->p_param, p_params); - } - else if (p_params) - { - memcpy(p_msg->p_param, p_params, param_len); /* callback parameter data */ - } - - btif_sendmsg(p_msg); - return BT_STATUS_SUCCESS; - } - else - { - /* let caller deal with a failed allocation */ - return BT_STATUS_NOMEM; - } -} - -int btif_is_enabled(void) -{ - return (stack_manager_is_stack_running()); -} - -void btif_init_ok(void) { - BTIF_TRACE_DEBUG("btif_task: received trigger stack init event"); - future_ready(stack_manager_get_hack_future(), FUTURE_SUCCESS); -} - -/******************************************************************************* -** -** Function btif_enable_bluetooth_evt -** -** Description Event indicating bluetooth enable is completed -** Notifies HAL user with updated adapter state -** -** Returns void -** -*******************************************************************************/ - -void btif_enable_bluetooth_evt(tBTA_STATUS status) -{ - if (status == BTA_SUCCESS) { - future_ready(stack_manager_get_hack_future(), FUTURE_SUCCESS); - } else { - future_ready(stack_manager_get_hack_future(), FUTURE_FAIL); - } -} - -/******************************************************************************* -** -** Function btif_disable_bluetooth_evt -** -** Description Event notifying BT disable is now complete. -** Terminates main stack tasks and notifies HAL -** user with updated BT state. -** -** Returns void -** -*******************************************************************************/ - -void btif_disable_bluetooth_evt(void) -{ - BTIF_TRACE_DEBUG("%s", __FUNCTION__); - - /* callback to HAL */ - future_ready(stack_manager_get_hack_future(), FUTURE_SUCCESS); -} - -/******************************************************************************* -** -** Function btif_task -** -** Description BTIF task handler managing all messages being passed -** Bluetooth HAL and BTA. -** -** Returns void -** -*******************************************************************************/ -static void bt_jni_msg_ready(fixed_queue_t *queue) { - BT_HDR *p_msg; - while (!fixed_queue_is_empty(queue)) { - p_msg = (BT_HDR *)fixed_queue_dequeue(queue); - BTIF_TRACE_VERBOSE("btif task fetched event %x", p_msg->event); - switch (p_msg->event) { - case BT_EVT_CONTEXT_SWITCH_EVT: - btif_context_switched(p_msg); - break; - default: - BTIF_TRACE_ERROR("unhandled btif event (%d)", p_msg->event & BT_EVT_MASK); break; - } - GKI_freebuf(p_msg); - } -} - -/******************************************************************************* -** -** Function btif_sendmsg -** -** Description Sends msg to BTIF task -** -** Returns void -** -*******************************************************************************/ - -void btif_sendmsg(void *p_msg) -{ - fixed_queue_enqueue(btif_msg_queue, p_msg); - btif_thread_post(SIG_BTIF_WORK); -} - -static void btif_thread_post(uint32_t sig) { - TaskEvt_t *evt = (TaskEvt_t *)osi_malloc(sizeof(TaskEvt_t)); - if (evt == NULL) - return; - - evt->sig = sig; - evt->par = 0; - - if (xQueueSend(xBtifQueue, &evt, 10/portTICK_RATE_MS) != pdTRUE) { - ets_printf("xBtifQueue failed\n"); - } -} - -/***************************************************************************** -** -** Function btif_task_thread_handler -** -** Description Process BTif Task Thread. -******************************************************************************/ -void btif_task_thread_handler(void *arg) -{ - TaskEvt_t *e; - - for (;;) { - if (pdTRUE == xQueueReceive(xBtifQueue, &e, (portTickType)portMAX_DELAY)) { - - if (e->sig == SIG_BTIF_WORK) { - fixed_queue_process(btif_msg_queue); - } - osi_free(e); - } - } -} - -/******************************************************************************* -** -** Function btif_init_bluetooth -** -** Description Creates BTIF task and prepares BT scheduler for startup -** -** Returns bt_status_t -** -*******************************************************************************/ -bt_status_t btif_init_bluetooth(void) { - bte_main_boot_entry(btif_init_ok); - - btif_msg_queue = fixed_queue_new(SIZE_MAX); - if (btif_msg_queue == NULL) { - goto error_exit; - } - xBtifQueue = xQueueCreate(60, sizeof(void *)); - xTaskCreate(btif_task_thread_handler, "BtifT", 8192, NULL, configMAX_PRIORITIES - 1, &xBtifTaskHandle); - fixed_queue_register_dequeue(btif_msg_queue, bt_jni_msg_ready); - - return BT_STATUS_SUCCESS; - -error_exit:; - btif_shutdown_bluetooth(); - - return BT_STATUS_FAIL; -} - -/******************************************************************************* -** -** Function btif_enable_bluetooth -** -** Description Inititates shutdown of Bluetooth system. -** Any active links will be dropped and device entering -** non connectable/discoverable mode -** -** Returns void -** -*******************************************************************************/ -bt_status_t btif_enable_bluetooth(void) -{ - BTIF_TRACE_DEBUG("BTIF ENABLE BLUETOOTH"); - - BTA_EnableBluetooth(bte_dm_evt); - - return BT_STATUS_SUCCESS; -} - -/******************************************************************************* -** -** Function btif_disable_bluetooth -** -** Description Inititates shutdown of Bluetooth system. -** Any active links will be dropped and device entering -** non connectable/discoverable mode -** -** Returns void -** -*******************************************************************************/ -bt_status_t btif_disable_bluetooth(void) -{ - BTIF_TRACE_DEBUG("BTIF DISABLE BLUETOOTH"); - - // btif_dm_on_disable(); - /* cleanup rfcomm & l2cap api */ - // btif_sock_cleanup(); - // btif_pan_cleanup(); - BTA_DisableBluetooth(); - - return BT_STATUS_SUCCESS; -} - -/******************************************************************************* -** -** Function btif_shutdown_bluetooth -** -** Description Finalizes BT scheduler shutdown and terminates BTIF -** task. -** -** Returns void -** -*******************************************************************************/ - -bt_status_t btif_shutdown_bluetooth(void) -{ - BTIF_TRACE_DEBUG("%s", __FUNCTION__); - - fixed_queue_unregister_dequeue(btif_msg_queue); - fixed_queue_free(btif_msg_queue, NULL); - btif_msg_queue = NULL; - - vTaskDelete(xBtifTaskHandle); - xBtifTaskHandle = NULL; - - vQueueDelete(xBtifQueue); - xBtifQueue = NULL; - - bte_main_shutdown(); - - return BT_STATUS_SUCCESS; -} - -/******************************************************************************* -** -** Function btif_get_enabled_services_mask -** -** Description Fetches currently enabled services -** -** Returns tBTA_SERVICE_MASK -** -*******************************************************************************/ - -tBTA_SERVICE_MASK btif_get_enabled_services_mask(void) -{ - return btif_enabled_services; -} - -/******************************************************************************* -** -** Function btif_enable_service -** -** Description Enables the service 'service_ID' to the service_mask. -** Upon BT enable, BTIF core shall invoke the BTA APIs to -** enable the profiles -** -** Returns bt_status_t -** -*******************************************************************************/ -bt_status_t btif_enable_service(tBTA_SERVICE_ID service_id) -{ - tBTA_SERVICE_ID *p_id = &service_id; - - /* If BT is enabled, we need to switch to BTIF context and trigger the - * enable for that profile - * - * Otherwise, we just set the flag. On BT_Enable, the DM will trigger - * enable for the profiles that have been enabled */ - - btif_enabled_services |= (1 << service_id); - - BTIF_TRACE_DEBUG("%s: current services:0x%x", __FUNCTION__, btif_enabled_services); - - if (btif_is_enabled()) { - btif_transfer_context(btif_dm_execute_service_request, - BTIF_DM_ENABLE_SERVICE, - (char*)p_id, sizeof(tBTA_SERVICE_ID), NULL); - } - - return BT_STATUS_SUCCESS; -} -/******************************************************************************* -** -** Function btif_disable_service -** -** Description Disables the service 'service_ID' to the service_mask. -** Upon BT disable, BTIF core shall invoke the BTA APIs to -** disable the profiles -** -** Returns bt_status_t -** -*******************************************************************************/ -bt_status_t btif_disable_service(tBTA_SERVICE_ID service_id) -{ - tBTA_SERVICE_ID *p_id = &service_id; - - /* If BT is enabled, we need to switch to BTIF context and trigger the - * disable for that profile so that the appropriate uuid_property_changed will - * be triggerred. Otherwise, we just need to clear the service_id in the mask - */ - - btif_enabled_services &= (tBTA_SERVICE_MASK)(~(1< -// #include -#include -#include -#include -// #include -// #include - -// #include - -// #include -#include "gki.h" -#include "btu.h" -// #include "btcore/include/bdaddr.h" -#include "bta_api.h" -#include "btif_api.h" -#include "btif_util.h" -#include "btif_dm.h" -// #include "btif_storage.h" -// #include "btif_hh.h" -// #include "btif_config.h" -// #include "btif_sdp.h" -// #include "bta_gatt_api.h" -// #include "device/include/interop.h" -// #include "include/stack_config.h" -// #include "osi/include/log.h" -#include "allocator.h" -#include "btm_int.h" -#include "bt_defs.h" -#include "future.h" -#include "stack_manager.h" - -/****************************************************************************** -** Constants & Macros -******************************************************************************/ -#define BTA_SERVICE_ID_TO_SERVICE_MASK(id) (1 << (id)) - -/************************************************************************************ -** Static variables -************************************************************************************/ -/****************************************************************************** -** Static functions -******************************************************************************/ -/****************************************************************************** -** Externs -******************************************************************************/ -extern bt_status_t btif_sdp_execute_service(BOOLEAN b_enable); - -/****************************************************************************** -** Functions -******************************************************************************/ - -static void btif_dm_data_copy(uint16_t event, char *dst, char *src) -{ - tBTA_DM_SEC *dst_dm_sec = (tBTA_DM_SEC*)dst; - tBTA_DM_SEC *src_dm_sec = (tBTA_DM_SEC*)src; - - if (!src_dm_sec) - return; - - assert(dst_dm_sec); - memcpy(dst_dm_sec, src_dm_sec, sizeof(tBTA_DM_SEC)); - - if (event == BTA_DM_BLE_KEY_EVT) { - dst_dm_sec->ble_key.p_key_value = osi_malloc(sizeof(tBTM_LE_KEY_VALUE)); - assert(src_dm_sec->ble_key.p_key_value); - assert(dst_dm_sec->ble_key.p_key_value); - memcpy(dst_dm_sec->ble_key.p_key_value, src_dm_sec->ble_key.p_key_value, sizeof(tBTM_LE_KEY_VALUE)); - } -} - -static void btif_dm_data_free(uint16_t event, tBTA_DM_SEC *dm_sec) -{ - if (event == BTA_DM_BLE_KEY_EVT) { - osi_free(dm_sec->ble_key.p_key_value); - } -} - -bt_status_t btif_in_execute_service_request(tBTA_SERVICE_ID service_id, - BOOLEAN b_enable) -{ - BTIF_TRACE_DEBUG("%s service_id: %d\n", __FUNCTION__, service_id); - /* Check the service_ID and invoke the profile's BT state changed API */ - switch (service_id) { - case BTA_SDP_SERVICE_ID: - btif_sdp_execute_service(b_enable); - break; - default: - BTIF_TRACE_ERROR("%s: Unknown service being enabled\n", __FUNCTION__); - return BT_STATUS_FAIL; - } - return BT_STATUS_SUCCESS; -} - -void btif_dm_execute_service_request(UINT16 event, char *p_param) -{ - BOOLEAN b_enable = FALSE; - if (event == BTIF_DM_ENABLE_SERVICE) { - b_enable = TRUE; - } - - btif_in_execute_service_request(*((tBTA_SERVICE_ID*)p_param), b_enable); -} - -/******************************************************************************* -** -** Function btif_dm_upstreams_cback -** -** Description Executes UPSTREAMS events in btif context -** -** Returns void -** -*******************************************************************************/ -static void btif_dm_upstreams_evt(UINT16 event, char* p_param) -{ - tBTA_DM_SEC *p_data = (tBTA_DM_SEC*)p_param; - tBTA_SERVICE_MASK service_mask; - uint32_t i; - BTIF_TRACE_EVENT("btif_dm_upstreams_cback ev: %d\n", event); - - switch (event) { - case BTA_DM_ENABLE_EVT: - /* for each of the enabled services in the mask, trigger the profile - * enable */ - service_mask = btif_get_enabled_services_mask(); - for (i=0; i <= BTA_MAX_SERVICE_ID; i++) { - if (service_mask & - (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(i))) { - btif_in_execute_service_request(i, TRUE); - } - } - btif_enable_bluetooth_evt(p_data->enable.status); - break; - case BTA_DM_DISABLE_EVT: - /* for each of the enabled services in the mask, trigger the profile - * disable */ - service_mask = btif_get_enabled_services_mask(); - for (i=0; i <= BTA_MAX_SERVICE_ID; i++) { - if (service_mask & - (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(i))) { - btif_in_execute_service_request(i, FALSE); - } - } - btif_disable_bluetooth_evt(); - break; - case BTA_DM_PIN_REQ_EVT: - case BTA_DM_AUTH_CMPL_EVT: - case BTA_DM_BOND_CANCEL_CMPL_EVT: - case BTA_DM_SP_CFM_REQ_EVT: - case BTA_DM_SP_KEY_NOTIF_EVT: - - case BTA_DM_DEV_UNPAIRED_EVT: - case BTA_DM_BUSY_LEVEL_EVT: - case BTA_DM_LINK_UP_EVT: - case BTA_DM_LINK_DOWN_EVT: - case BTA_DM_HW_ERROR_EVT: - -#if (defined(BLE_INCLUDED) && (BLE_INCLUDED == TRUE)) - case BTA_DM_BLE_KEY_EVT: - case BTA_DM_BLE_SEC_REQ_EVT: - case BTA_DM_BLE_PASSKEY_NOTIF_EVT: - case BTA_DM_BLE_PASSKEY_REQ_EVT: - case BTA_DM_BLE_NC_REQ_EVT: - case BTA_DM_BLE_OOB_REQ_EVT: - case BTA_DM_BLE_LOCAL_IR_EVT: - case BTA_DM_BLE_LOCAL_ER_EVT: - case BTA_DM_BLE_AUTH_CMPL_EVT: - case BTA_DM_LE_FEATURES_READ: - case BTA_DM_ENER_INFO_READ: -#endif - - case BTA_DM_AUTHORIZE_EVT: - case BTA_DM_SIG_STRENGTH_EVT: - case BTA_DM_SP_RMT_OOB_EVT: - case BTA_DM_SP_KEYPRESS_EVT: - case BTA_DM_ROLE_CHG_EVT: - - default: - BTIF_TRACE_WARNING( "btif_dm_cback : unhandled event (%d)\n", event ); - break; - } - - btif_dm_data_free(event, p_data); -} - -/******************************************************************************* -** -** Function bte_dm_evt -** -** Description Switches context from BTE to BTIF for all DM events -** -** Returns void -** -*******************************************************************************/ - -void bte_dm_evt(tBTA_DM_SEC_EVT event, tBTA_DM_SEC *p_data) -{ - /* switch context to btif task context (copy full union size for convenience) */ - bt_status_t status = btif_transfer_context(btif_dm_upstreams_evt, (uint16_t)event, - (void*)p_data, sizeof(tBTA_DM_SEC), btif_dm_data_copy); - - /* catch any failed context transfers */ - ASSERTC(status == BT_STATUS_SUCCESS, "context transfer failed\n", status); -} diff --git a/examples/13_bt_sdp/components/bluedroid_demos/btif/btif_sdp.c b/examples/13_bt_sdp/components/bluedroid_demos/btif/btif_sdp.c deleted file mode 100755 index d77f61869a..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/btif/btif_sdp.c +++ /dev/null @@ -1,175 +0,0 @@ -/****************************************************************************** - * - * Copyright (C) 2014 Samsung System LSI - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at: - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - ******************************************************************************/ - -/************************************************************************************ - * - * Filename: btif_sdp.c - * Description: SDP Bluetooth Interface. - * Implements the generic message handling and search functionality. - * References btif_sdp_server.c for SDP record creation. - * - ***********************************************************************************/ - -#include "btif_sdp.h" -#include -#include - -#define LOG_TAG "BTIF_SDP" -#include "btif_common.h" -#include "btif_util.h" -#include "bta_api.h" - -#include "bt_sdp_api.h" - -/***************************************************************************** -** Functions implemented in sdp_server.c -******************************************************************************/ -bt_status_t sdp_server_init(); -void sdp_server_cleanup(); -void on_create_record_event(int handle); -void on_remove_record_event(int handle); - -// Utility functions: -int get_sdp_records_size(bluetooth_sdp_record* in_record, int count); -void copy_sdp_records(bluetooth_sdp_record* in_records, - bluetooth_sdp_record* out_records, int count); - - -/***************************************************************************** -** Static variables -******************************************************************************/ - -static btsdp_callbacks_t *bt_sdp_callbacks = NULL; - -static void btif_sdp_search_comp_evt(UINT16 event, char *p_param) -{ - bt_sdp_search_comp_t *evt_data = (bt_sdp_search_comp_t *) p_param; - bt_bdaddr_t addr; - BTIF_TRACE_DEBUG("%s: event = %d\n", __FUNCTION__, event); - - if (event != BT_SDP_SEARCH_COMP_EVT) - return; - - bdcpy(addr.address, evt_data->remote_addr); - - HAL_CBACK(bt_sdp_callbacks, sdp_search_cb, evt_data->status, - &addr, (uint8_t*)(evt_data->uuid.uu.uuid128), - evt_data->record_count, evt_data->records); -} - -static void sdp_search_comp_copy_cb(UINT16 event, char *p_dest, char *p_src) -{ - bt_sdp_search_comp_t *p_dest_data = (bt_sdp_search_comp_t *) p_dest; - bt_sdp_search_comp_t *p_src_data = (bt_sdp_search_comp_t *) p_src; - if (!p_src) - return; - - if (event != BT_SDP_SEARCH_COMP_EVT) - return; - - memcpy(p_dest_data, p_src_data, sizeof(bt_sdp_search_comp_t)); - - copy_sdp_records(p_src_data->records, p_dest_data->records, p_src_data->record_count); -} - - -static void sdp_dm_cback(bt_sdp_evt_t event, bt_sdp_t *p_data, void * user_data) -{ - switch (event) - { - case BT_SDP_SEARCH_COMP_EVT: - { - int size = sizeof(bt_sdp_t); - size += get_sdp_records_size(p_data->sdp_search_comp.records, - p_data->sdp_search_comp.record_count); - - BTIF_TRACE_DEBUG("%s: stat %d, record_cnt = %d\n", __FUNCTION__, p_data->sdp_search_comp.status, p_data->sdp_search_comp.record_count); - /* need to deep copy the record content */ - btif_transfer_context(btif_sdp_search_comp_evt, event, - (char*)p_data, size, sdp_search_comp_copy_cb); - break; - } - case BT_SDP_CREATE_RECORD_USER_EVT: - { - on_create_record_event((int)user_data); - break; - } - case BT_SDP_REMOVE_RECORD_USER_EVT: - { - on_remove_record_event((int)user_data); - break; - } - default: - break; - } -} - -bt_status_t BTIF_SdpInit(btsdp_callbacks_t *callbacks) -{ - BTIF_TRACE_DEBUG("Sdp Search %s\n", __FUNCTION__); - - bt_sdp_callbacks = callbacks; - sdp_server_init(); - - btif_enable_service(BTA_SDP_SERVICE_ID); - - return BT_STATUS_SUCCESS; -} - -bt_status_t BTIF_SdpDeinit(void) -{ - BTIF_TRACE_DEBUG("Sdp Search %s\n", __FUNCTION__); - - bt_sdp_callbacks = NULL; - sdp_server_cleanup(); - btif_disable_service(BTA_SDP_SERVICE_ID); - - return BT_STATUS_SUCCESS; -} - -bt_status_t BTIF_SdpSearch(bt_bdaddr_t *bd_addr, const uint8_t* uuid) -{ - esp_bt_uuid_t sdp_uuid; - sdp_uuid.len = 16; - memcpy(sdp_uuid.uu.uuid128, uuid, sizeof(sdp_uuid.uu.uuid128)); - - esp_bt_sdp_search(bd_addr->address, &sdp_uuid); - return BT_STATUS_SUCCESS; -} - -/******************************************************************************* -** -** Function btif_sdp_execute_service -** -** Description Initializes/Shuts down the service -** -** Returns BT_STATUS_SUCCESS on success, BT_STATUS_FAIL otherwise -** -*******************************************************************************/ -bt_status_t btif_sdp_execute_service(BOOLEAN b_enable) -{ - BTIF_TRACE_DEBUG("%s enable:%d\n", __FUNCTION__, b_enable); - - if (b_enable) { - esp_bt_sdp_enable(sdp_dm_cback); - } else { - /* This is called on BT disable so no need to extra cleanup */ - } - return BT_STATUS_SUCCESS; -} - diff --git a/examples/13_bt_sdp/components/bluedroid_demos/btif/btif_sdp_server.c b/examples/13_bt_sdp/components/bluedroid_demos/btif/btif_sdp_server.c deleted file mode 100755 index ebb3f8422f..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/btif/btif_sdp_server.c +++ /dev/null @@ -1,777 +0,0 @@ -/****************************************************************************** - * - * Copyright (C) 2014 Samsung System LSI - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at: - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - ******************************************************************************/ - -/************************************************************************************ - * - * Filename: btif_sdp_server.c - * Description: SDP server Bluetooth Interface to create and remove SDP records. - * To be used in combination with the RFCOMM/L2CAP(LE) sockets. - * - * - ***********************************************************************************/ - -#include "btif_sdp.h" -#include -#include -#define LOG_TAG "BTIF_SDP_SERVER" -#include "allocator.h" -#include "btif_common.h" -#include "bta_sys.h" -#include "utl.h" -#include "bt_sdp_api.h" - -static pthread_mutex_t sdp_lock; - -/** - * The need for a state variable have been reduced to two states. - * The remaining state control is handled by program flow - */ -typedef enum { - SDP_RECORD_FREE = 0, - SDP_RECORD_ALLOCED, -} sdp_state_t; - -typedef struct { - sdp_state_t state; - int sdp_handle; - bluetooth_sdp_record* record_data; -} sdp_slot_t; - -#define MAX_SDP_SLOTS 128 -static sdp_slot_t sdp_slots[MAX_SDP_SLOTS]; - -/***************************************************************************** - * LOCAL Functions - *****************************************************************************/ -static int add_maps_sdp(const bluetooth_sdp_mas_record* rec); -static int add_mapc_sdp(const bluetooth_sdp_mns_record* rec); -static int add_pbaps_sdp(const bluetooth_sdp_pse_record* rec); -static int add_opps_sdp(const bluetooth_sdp_ops_record* rec); -static int add_saps_sdp(const bluetooth_sdp_sap_record* rec); -bt_status_t remove_sdp_record(int record_id); -static int free_sdp_slot(int id); - -/****************************************************************************** - * WARNING: Functions below are not called in BTU context. - * Introduced to make it possible to create SDP records from JAVA with both a - * RFCOMM channel and a L2CAP PSM. - * Overall architecture: - * 1) JAVA calls createRecord() which returns a pseudo ID which at a later - * point will be linked to a specific SDP handle. - * 2) createRecord() requests the BTU task(thread) to call a callback in SDP - * which creates the actual record, and updates the ID<->SDPHandle map - * based on the ID beeing passed to BTA as user_data. - *****************************************************************************/ - -static void init_sdp_slots() -{ - int i; - memset(sdp_slots, 0, sizeof(sdp_slot_t)*MAX_SDP_SLOTS); - /* if SDP_RECORD_FREE is zero - no need to set the value */ - if(SDP_RECORD_FREE != 0) { - for(i = 0; i < MAX_SDP_SLOTS; i++) - { - sdp_slots[i].state = SDP_RECORD_FREE; - } - } -} - -bt_status_t sdp_server_init() -{ - BTIF_TRACE_DEBUG("Sdp Server %s\n", __FUNCTION__); - pthread_mutex_init(&sdp_lock, NULL); - init_sdp_slots(); - return BT_STATUS_SUCCESS; -} - -void sdp_server_cleanup() -{ - BTIF_TRACE_DEBUG("Sdp Server %s\n", __FUNCTION__); - pthread_mutex_lock(&sdp_lock); - int i; - for(i = 0; i < MAX_SDP_SLOTS; i++) - { - /*remove_sdp_record(i); we cannot send messages to the other threads, since they might - * have been shut down already. Just do local cleanup. - */ - free_sdp_slot(i); - } - pthread_mutex_unlock(&sdp_lock); - pthread_mutex_destroy(&sdp_lock); -} - -int get_sdp_records_size(bluetooth_sdp_record* in_record, int count) { - bluetooth_sdp_record* record = in_record; - int records_size = 0; - int i; - for(i=0; ihdr.service_name_length; - if(record->hdr.service_name_length > 0){ - records_size++; /* + '\0' termination of string */ - } - records_size += record->hdr.user1_ptr_len; - records_size += record->hdr.user2_ptr_len; - } - return records_size; -} - -/* Deep copy all content of in_records into out_records. - * out_records must point to a chunk of memory large enough to contain all - * the data. Use getSdpRecordsSize() to calculate the needed size. */ -void copy_sdp_records(bluetooth_sdp_record* in_records, - bluetooth_sdp_record* out_records, int count) { - int i; - bluetooth_sdp_record* in_record; - bluetooth_sdp_record* out_record; - char* free_ptr = (char*)(&out_records[count]); /* set pointer to after the last entry */ - - for(i=0; ihdr.service_name == NULL || in_record->hdr.service_name_length == 0) { - out_record->hdr.service_name = NULL; - out_record->hdr.service_name_length = 0; - } else { - out_record->hdr.service_name = free_ptr; // Update service_name pointer - // Copy string - memcpy(free_ptr, in_record->hdr.service_name, in_record->hdr.service_name_length); - free_ptr += in_record->hdr.service_name_length; - *(free_ptr) = '\0'; // Set '\0' termination of string - free_ptr++; - } - if(in_record->hdr.user1_ptr != NULL) { - out_record->hdr.user1_ptr = (UINT8*)free_ptr; // Update pointer - memcpy(free_ptr, in_record->hdr.user1_ptr, in_record->hdr.user1_ptr_len); // Copy content - free_ptr += in_record->hdr.user1_ptr_len; - } - if(in_record->hdr.user2_ptr != NULL) { - out_record->hdr.user2_ptr = (UINT8*)free_ptr; // Update pointer - memcpy(free_ptr, in_record->hdr.user2_ptr, in_record->hdr.user2_ptr_len); // Copy content - free_ptr += in_record->hdr.user2_ptr_len; - } - } - return; -} - -/* Reserve a slot in sdp_slots, copy data and set a reference to the copy. - * The record_data will contain both the record and any data pointed to by - * the record. - * Currently this covers: - * service_name string, - * user1_ptr and - * user2_ptr. */ -static int alloc_sdp_slot(bluetooth_sdp_record* in_record) { - int i; - int record_size = get_sdp_records_size(in_record, 1); - bluetooth_sdp_record* record = osi_malloc(record_size); - - copy_sdp_records(in_record, record, 1); - - /* We are optimists here, and preallocate the record. - * This is to reduce the time we hold the sdp_lock. */ - pthread_mutex_lock(&sdp_lock); - for(i = 0; i < MAX_SDP_SLOTS; i++) - { - if(sdp_slots[i].state == SDP_RECORD_FREE) { - sdp_slots[i].state = SDP_RECORD_ALLOCED; - sdp_slots[i].record_data = record; - break; - } - } - pthread_mutex_unlock(&sdp_lock); - if(i >= MAX_SDP_SLOTS) { - APPL_TRACE_ERROR("%s() failed - no more free slots!\n", __func__); - /* Rearly the optimist is too optimistic, and cleanup is needed...*/ - osi_free(record); - return -1; - } - return i; -} - -static int free_sdp_slot(int id) { - int handle = -1; - bluetooth_sdp_record* record = NULL; - if(id >= MAX_SDP_SLOTS) { - APPL_TRACE_ERROR("%s() failed - id %d is invalid\n", __func__, id); - return handle; - } - pthread_mutex_lock(&sdp_lock); - handle = sdp_slots[id].sdp_handle; - sdp_slots[id].sdp_handle = 0; - if(sdp_slots[id].state != SDP_RECORD_FREE) - { - /* safe a copy of the pointer, and free after unlock() */ - record = sdp_slots[id].record_data; - } - sdp_slots[id].state = SDP_RECORD_FREE; - pthread_mutex_unlock(&sdp_lock); - - if(record != NULL) { - osi_free(record); - } else { - // Record have already been freed - handle = -1; - } - return handle; -} - -/*** - * Use this to get a reference to a SDP slot AND change the state to - * SDP_RECORD_CREATE_INITIATED. - */ -static const sdp_slot_t* start_create_sdp(int id) { - sdp_slot_t* sdp_slot; - if(id >= MAX_SDP_SLOTS) { - APPL_TRACE_ERROR("%s() failed - id %d is invalid\n", __func__, id); - return NULL; - } - pthread_mutex_lock(&sdp_lock); - if(sdp_slots[id].state == SDP_RECORD_ALLOCED) { - sdp_slot = &(sdp_slots[id]); - } else { - /* The record have been removed before this event occurred - e.g. deinit */ - sdp_slot = NULL; - } - pthread_mutex_unlock(&sdp_lock); - if(sdp_slot == NULL) { - APPL_TRACE_ERROR("%s() failed - state for id %d is \n" - "sdp_slots[id].state = %d expected %d\n", __func__, - id, sdp_slots[id].state, SDP_RECORD_ALLOCED); - } - return sdp_slot; -} - -static void set_sdp_handle(int id, int handle) { - pthread_mutex_lock(&sdp_lock); - sdp_slots[id].sdp_handle = handle; - pthread_mutex_unlock(&sdp_lock); - BTIF_TRACE_DEBUG("%s() id=%d to handle=0x%08x\n", __FUNCTION__, id, handle); -} - -bt_status_t BTIF_SdpCreateRecord(bluetooth_sdp_record *record, int* record_handle) { - int handle; - - handle = alloc_sdp_slot(record); - BTIF_TRACE_DEBUG("%s() handle = 0x%08x\n", __FUNCTION__, handle); - - if(handle < 0) - return BT_STATUS_FAIL; - - esp_bt_sdp_create_record_by_user((void*) handle); - - *record_handle = handle; - - return BT_STATUS_SUCCESS; -} - -bt_status_t BTIF_SdpRemoveRecord(int record_handle) { - int handle; - - /* Get the Record handle, and free the slot */ - handle = free_sdp_slot(record_handle); - BTIF_TRACE_DEBUG("Sdp Server %s id=%d to handle=0x%08x\n", - __FUNCTION__, record_handle, handle); - - /* Pass the actual record handle */ - if(handle > 0) { - esp_bt_sdp_remove_record_by_user((void *)handle); - return BT_STATUS_SUCCESS; - } - BTIF_TRACE_DEBUG("Sdp Server %s - record already removed - or never created\n", __FUNCTION__); - return BT_STATUS_FAIL; -} - - -/****************************************************************************** - * CALLBACK FUNCTIONS - * Called in BTA context to create/remove SDP records. - ******************************************************************************/ - -void on_create_record_event(int id) { - /* - * 1) Fetch the record pointer, and change its state? - * 2) switch on the type to create the correct record - * 3) Update state on completion - * 4) What to do at fail? - * */ - BTIF_TRACE_DEBUG("Sdp Server %s\n", __FUNCTION__); - const sdp_slot_t* sdp_slot = start_create_sdp(id); - /* In the case we are shutting down, sdp_slot is NULL */ - if(sdp_slot != NULL) { - bluetooth_sdp_record* record = sdp_slot->record_data; - int handle = -1; - switch(record->hdr.type) { - case SDP_TYPE_MAP_MAS: - handle = add_maps_sdp(&record->mas); - break; - case SDP_TYPE_MAP_MNS: - handle = add_mapc_sdp(&record->mns); - break; - case SDP_TYPE_PBAP_PSE: - handle = add_pbaps_sdp(&record->pse); - break; - case SDP_TYPE_OPP_SERVER: - handle = add_opps_sdp(&record->ops); - break; - case SDP_TYPE_SAP_SERVER: - handle = add_saps_sdp(&record->sap); - break; - case SDP_TYPE_PBAP_PCE: - // break; not yet supported - default: - BTIF_TRACE_DEBUG("Record type %d is not supported\n",record->hdr.type); - break; - } - if(handle != -1) { - set_sdp_handle(id, handle); - } - } -} - -void on_remove_record_event(int handle) { - BTIF_TRACE_DEBUG("Sdp Server %s\n", __FUNCTION__); - - // User data carries the actual SDP handle, not the ID. - if(handle != -1 && handle != 0) { - BOOLEAN result; - result = SDP_DeleteRecord( handle ); - if(result == FALSE) { - BTIF_TRACE_ERROR(" Unable to remove handle 0x%08x\n", handle); - } - } -} - -/**** - * Below the actual functions accessing BTA context data - hence only call from BTA context! - */ - -/* Create a MAP MAS SDP record based on information stored in a bluetooth_sdp_mas_record */ -static int add_maps_sdp(const bluetooth_sdp_mas_record* rec) -{ - - sdp_proto_elem_t protoList[3]; - UINT16 service = UUID_SERVCLASS_MESSAGE_ACCESS; - UINT16 browse = UUID_SERVCLASS_PUBLIC_BROWSE_GROUP; - BOOLEAN status = TRUE; - UINT32 sdp_handle = 0; - UINT8 temp[4]; - UINT8* p_temp = temp; - - APPL_TRACE_DEBUG("%s(): MASID = 0x%02x, scn 0x%02x, psm = 0x%04x\n service name %s\n", __func__, - rec->mas_instance_id, rec->hdr.rfcomm_channel_number, - rec->hdr.l2cap_psm, rec->hdr.service_name); - - APPL_TRACE_DEBUG(" msg_types: 0x%02x, feature_bits: 0x%08x\n", - rec->supported_message_types, rec->supported_features); - - if ((sdp_handle = esp_bt_sdp_create_record()) == 0) - { - APPL_TRACE_ERROR("%s() - Unable to register MAPS Service\n", __func__); - return sdp_handle; - } - - /* add service class */ - status &= esp_bt_sdp_add_service_class_id_list(sdp_handle, 1, &service); - memset( protoList, 0 , 3*sizeof(sdp_proto_elem_t) ); - - /* add protocol list, including RFCOMM scn */ - protoList[0].protocol_uuid = UUID_PROTOCOL_L2CAP; - protoList[0].num_params = 0; - protoList[1].protocol_uuid = UUID_PROTOCOL_RFCOMM; - protoList[1].num_params = 1; - protoList[1].params[0] = rec->hdr.rfcomm_channel_number; - protoList[2].protocol_uuid = UUID_PROTOCOL_OBEX; - protoList[2].num_params = 0; - status &= esp_bt_sdp_add_protocol_list(sdp_handle, 3, protoList); - - /* Add a name entry */ - status &= esp_bt_sdp_add_attribute(sdp_handle, - (UINT16)ATTR_ID_SERVICE_NAME, - (UINT8)TEXT_STR_DESC_TYPE, - (UINT32)(rec->hdr.service_name_length + 1), - (UINT8 *)rec->hdr.service_name); - - /* Add in the Bluetooth Profile Descriptor List */ - status &= esp_bt_sdp_add_profile_dscp_list(sdp_handle, - UUID_SERVCLASS_MAP_PROFILE, - rec->hdr.profile_version); - - /* Add MAS instance ID */ - status &= esp_bt_sdp_add_attribute(sdp_handle, ATTR_ID_MAS_INSTANCE_ID, UINT_DESC_TYPE, - (UINT32)1, (UINT8*)&rec->mas_instance_id); - - /* Add supported message types */ - status &= esp_bt_sdp_add_attribute(sdp_handle, ATTR_ID_SUPPORTED_MSG_TYPE, UINT_DESC_TYPE, - (UINT32)1, (UINT8*)&rec->supported_message_types); - - /* Add supported feature */ - UINT32_TO_BE_STREAM(p_temp, rec->supported_features); - status &= esp_bt_sdp_add_attribute(sdp_handle, ATTR_ID_MAP_SUPPORTED_FEATURES, - UINT_DESC_TYPE, (UINT32)4, temp); - - /* Add the L2CAP PSM if present */ - if(rec->hdr.l2cap_psm != -1) { - p_temp = temp;// The macro modifies p_temp, hence rewind. - UINT16_TO_BE_STREAM(p_temp, rec->hdr.l2cap_psm); - status &= esp_bt_sdp_add_attribute(sdp_handle, ATTR_ID_GOEP_L2CAP_PSM, - UINT_DESC_TYPE, (UINT32)2, temp); - } - - /* Make the service browseable */ - status &= esp_bt_sdp_add_uuid_sequence (sdp_handle, ATTR_ID_BROWSE_GROUP_LIST, 1, &browse); - - if (!status) - { - esp_bt_sdp_delete_record(sdp_handle); - sdp_handle = 0; - APPL_TRACE_ERROR("%s() FAILED\n", __func__); - } - else - { - bta_sys_add_uuid(service); /* UUID_SERVCLASS_MESSAGE_ACCESS */ - APPL_TRACE_DEBUG("%s(): SDP Registered (handle 0x%08x)\n", __func__, sdp_handle); - } - return sdp_handle; -} - - -/* Create a MAP MNS SDP record based on information stored in a bluetooth_sdp_mns_record */ -static int add_mapc_sdp(const bluetooth_sdp_mns_record* rec) -{ - - sdp_proto_elem_t protoList [3]; - UINT16 service = UUID_SERVCLASS_MESSAGE_NOTIFICATION; - UINT16 browse = UUID_SERVCLASS_PUBLIC_BROWSE_GROUP; - BOOLEAN status = TRUE; - UINT32 sdp_handle = 0; - UINT8 temp[4]; - UINT8* p_temp = temp; - - APPL_TRACE_DEBUG("%s(): scn 0x%02x, psm = 0x%04x\n service name %s\n", __func__, - rec->hdr.rfcomm_channel_number, rec->hdr.l2cap_psm, rec->hdr.service_name); - - APPL_TRACE_DEBUG(" feature_bits: 0x%08x\n", rec->supported_features); - - if ((sdp_handle = esp_bt_sdp_create_record()) == 0) - { - APPL_TRACE_ERROR("%s(): Unable to register MAP Notification Service\n", __func__); - return sdp_handle; - } - - /* add service class */ - status &= esp_bt_sdp_add_service_class_id_list(sdp_handle, 1, &service); - memset( protoList, 0 , 3*sizeof(sdp_proto_elem_t) ); - - /* add protocol list, including RFCOMM scn */ - protoList[0].protocol_uuid = UUID_PROTOCOL_L2CAP; - protoList[0].num_params = 0; - protoList[1].protocol_uuid = UUID_PROTOCOL_RFCOMM; - protoList[1].num_params = 1; - protoList[1].params[0] = rec->hdr.rfcomm_channel_number; - protoList[2].protocol_uuid = UUID_PROTOCOL_OBEX; - protoList[2].num_params = 0; - status &= esp_bt_sdp_add_protocol_list(sdp_handle, 3, protoList); - - /* Add a name entry */ - status &= esp_bt_sdp_add_attribute(sdp_handle, - (UINT16)ATTR_ID_SERVICE_NAME, - (UINT8)TEXT_STR_DESC_TYPE, - (UINT32)(rec->hdr.service_name_length + 1), - (UINT8 *)rec->hdr.service_name); - - /* Add in the Bluetooth Profile Descriptor List */ - status &= esp_bt_sdp_add_profile_dscp_list(sdp_handle, - UUID_SERVCLASS_MAP_PROFILE, - rec->hdr.profile_version); - - /* Add supported feature */ - UINT32_TO_BE_STREAM(p_temp, rec->supported_features); - status &= esp_bt_sdp_add_attribute(sdp_handle, ATTR_ID_MAP_SUPPORTED_FEATURES, - UINT_DESC_TYPE, (UINT32)4, temp); - - /* Add the L2CAP PSM if present */ - if(rec->hdr.l2cap_psm != -1) { - p_temp = temp;// The macro modifies p_temp, hence rewind. - UINT16_TO_BE_STREAM(p_temp, rec->hdr.l2cap_psm); - status &= esp_bt_sdp_add_attribute(sdp_handle, ATTR_ID_GOEP_L2CAP_PSM, - UINT_DESC_TYPE, (UINT32)2, temp); - } - - /* Make the service browseable */ - status &= esp_bt_sdp_add_uuid_sequence (sdp_handle, ATTR_ID_BROWSE_GROUP_LIST, 1, &browse); - - if (!status) - { - esp_bt_sdp_delete_record(sdp_handle); - sdp_handle = 0; - APPL_TRACE_ERROR("%s() FAILED\n", __func__); - } - else - { - bta_sys_add_uuid(service); /* UUID_SERVCLASS_MESSAGE_ACCESS */ - APPL_TRACE_DEBUG("%s(): SDP Registered (handle 0x%08x)\n", __func__, sdp_handle); - } - return sdp_handle; -} - -/* Create a PBAP Server SDP record based on information stored in a bluetooth_sdp_pse_record */ -static int add_pbaps_sdp(const bluetooth_sdp_pse_record* rec) -{ - - sdp_proto_elem_t protoList [3]; - UINT16 service = UUID_SERVCLASS_PBAP_PSE; - UINT16 browse = UUID_SERVCLASS_PUBLIC_BROWSE_GROUP; - BOOLEAN status = TRUE; - UINT32 sdp_handle = 0; - UINT8 temp[4]; - UINT8* p_temp = temp; - - APPL_TRACE_DEBUG("%s(): scn 0x%02x, psm = 0x%04x\n service name %s\n", __func__, - rec->hdr.rfcomm_channel_number, rec->hdr.l2cap_psm, rec->hdr.service_name); - - APPL_TRACE_DEBUG(" supported_repositories: 0x%08x, feature_bits: 0x%08x\n", - rec->supported_repositories, rec->supported_features); - - if ((sdp_handle = esp_bt_sdp_create_record()) == 0) - { - APPL_TRACE_ERROR("%s(): Unable to register PBAP Server Service\n", __func__); - return sdp_handle; - } - - /* add service class */ - status &= esp_bt_sdp_add_service_class_id_list(sdp_handle, 1, &service); - memset( protoList, 0 , 3*sizeof(sdp_proto_elem_t) ); - - /* add protocol list, including RFCOMM scn */ - protoList[0].protocol_uuid = UUID_PROTOCOL_L2CAP; - protoList[0].num_params = 0; - protoList[1].protocol_uuid = UUID_PROTOCOL_RFCOMM; - protoList[1].num_params = 1; - protoList[1].params[0] = rec->hdr.rfcomm_channel_number; - protoList[2].protocol_uuid = UUID_PROTOCOL_OBEX; - protoList[2].num_params = 0; - status &= esp_bt_sdp_add_protocol_list(sdp_handle, 3, protoList); - - /* Add a name entry */ - status &= esp_bt_sdp_add_attribute(sdp_handle, - (UINT16)ATTR_ID_SERVICE_NAME, - (UINT8)TEXT_STR_DESC_TYPE, - (UINT32)(rec->hdr.service_name_length + 1), - (UINT8 *)rec->hdr.service_name); - - /* Add in the Bluetooth Profile Descriptor List */ - status &= esp_bt_sdp_add_profile_dscp_list(sdp_handle, - UUID_SERVCLASS_PHONE_ACCESS, - rec->hdr.profile_version); - - /* Add supported repositories 1 byte */ - status &= esp_bt_sdp_add_attribute(sdp_handle, ATTR_ID_SUPPORTED_REPOSITORIES, - UINT_DESC_TYPE, (UINT32)1, (UINT8*)&rec->supported_repositories); - - /* Add supported feature 4 bytes*/ - UINT32_TO_BE_STREAM(p_temp, rec->supported_features); - status &= esp_bt_sdp_add_attribute(sdp_handle, ATTR_ID_PBAP_SUPPORTED_FEATURES, - UINT_DESC_TYPE, (UINT32)4, temp); - - /* Add the L2CAP PSM if present */ - if(rec->hdr.l2cap_psm != -1) { - p_temp = temp;// The macro modifies p_temp, hence rewind. - UINT16_TO_BE_STREAM(p_temp, rec->hdr.l2cap_psm); - status &= esp_bt_sdp_add_attribute(sdp_handle, ATTR_ID_GOEP_L2CAP_PSM, - UINT_DESC_TYPE, (UINT32)2, temp); - } - - /* Make the service browseable */ - status &= esp_bt_sdp_add_uuid_sequence (sdp_handle, ATTR_ID_BROWSE_GROUP_LIST, 1, &browse); - - if (!status) - { - esp_bt_sdp_delete_record(sdp_handle); - sdp_handle = 0; - APPL_TRACE_ERROR("%s() FAILED\n", __func__); - } - else - { - bta_sys_add_uuid(service); /* UUID_SERVCLASS_MESSAGE_ACCESS */ - APPL_TRACE_DEBUG("%s(): SDP Registered (handle 0x%08x)\n", __func__, sdp_handle); - } - return sdp_handle; -} - - -/* Create a OPP Server SDP record based on information stored in a bluetooth_sdp_ops_record */ -static int add_opps_sdp(const bluetooth_sdp_ops_record* rec) -{ - - sdp_proto_elem_t protoList [3]; - UINT16 service = UUID_SERVCLASS_OBEX_OBJECT_PUSH; - UINT16 browse = UUID_SERVCLASS_PUBLIC_BROWSE_GROUP; - UINT8 type_len[rec->supported_formats_list_len]; - UINT8 desc_type[rec->supported_formats_list_len]; - UINT8 *type_value[rec->supported_formats_list_len]; - BOOLEAN status = TRUE; - UINT32 sdp_handle = 0; - UINT8 temp[4]; - UINT8* p_temp = temp; - tBTA_UTL_COD cod; - int i,j; - - APPL_TRACE_DEBUG("%s(): scn 0x%02x, psm = 0x%04x\n service name %s\n", __func__, - rec->hdr.rfcomm_channel_number, rec->hdr.l2cap_psm, rec->hdr.service_name); - - APPL_TRACE_DEBUG(" supported formats count: %d\n", - rec->supported_formats_list_len); - - if ((sdp_handle = esp_bt_sdp_create_record()) == 0) - { - APPL_TRACE_ERROR("%s(): Unable to register Object Push Server Service\n", __func__); - return sdp_handle; - } - - /* add service class */ - status &= esp_bt_sdp_add_service_class_id_list(sdp_handle, 1, &service); - memset( protoList, 0 , 3*sizeof(sdp_proto_elem_t) ); - - /* add protocol list, including RFCOMM scn */ - protoList[0].protocol_uuid = UUID_PROTOCOL_L2CAP; - protoList[0].num_params = 0; - protoList[1].protocol_uuid = UUID_PROTOCOL_RFCOMM; - protoList[1].num_params = 1; - protoList[1].params[0] = rec->hdr.rfcomm_channel_number; - protoList[2].protocol_uuid = UUID_PROTOCOL_OBEX; - protoList[2].num_params = 0; - status &= esp_bt_sdp_add_protocol_list(sdp_handle, 3, protoList); - - /* Add a name entry */ - status &= esp_bt_sdp_add_attribute(sdp_handle, - (UINT16)ATTR_ID_SERVICE_NAME, - (UINT8)TEXT_STR_DESC_TYPE, - (UINT32)(rec->hdr.service_name_length + 1), - (UINT8 *)rec->hdr.service_name); - - /* Add in the Bluetooth Profile Descriptor List */ - status &= esp_bt_sdp_add_profile_dscp_list(sdp_handle, - UUID_SERVCLASS_OBEX_OBJECT_PUSH, - rec->hdr.profile_version); - - /* add sequence for supported types */ - for (i = 0, j = 0; i < rec->supported_formats_list_len; i++) - { - type_value[j] = (UINT8 *) &rec->supported_formats_list[i]; - desc_type[j] = UINT_DESC_TYPE; - type_len[j++] = 1; - } - - status &= esp_bt_sdp_add_sequence(sdp_handle, (UINT16) ATTR_ID_SUPPORTED_FORMATS_LIST, - (UINT8) rec->supported_formats_list_len, desc_type, type_len, type_value); - - /* Add the L2CAP PSM if present */ - if(rec->hdr.l2cap_psm != -1) { - p_temp = temp;// The macro modifies p_temp, hence rewind. - UINT16_TO_BE_STREAM(p_temp, rec->hdr.l2cap_psm); - status &= esp_bt_sdp_add_attribute(sdp_handle, ATTR_ID_GOEP_L2CAP_PSM, - UINT_DESC_TYPE, (UINT32)2, temp); - } - - /* Make the service browseable */ - status &= esp_bt_sdp_add_uuid_sequence (sdp_handle, ATTR_ID_BROWSE_GROUP_LIST, 1, &browse); - - if (!status) - { - esp_bt_sdp_delete_record(sdp_handle); - sdp_handle = 0; - APPL_TRACE_ERROR("%s() FAILED\n", __func__); - } - else - { - /* set class of device */ - cod.service = BTM_COD_SERVICE_OBJ_TRANSFER; - utl_set_device_class(&cod, BTA_UTL_SET_COD_SERVICE_CLASS); - - bta_sys_add_uuid(service); /* UUID_SERVCLASS_OBEX_OBJECT_PUSH */ - APPL_TRACE_DEBUG("%s(): SDP Registered (handle 0x%08x)\n", __func__, sdp_handle); - } - return sdp_handle; -} - -// Create a Sim Access Profile SDP record based on information stored in a bluetooth_sdp_sap_record. -static int add_saps_sdp(const bluetooth_sdp_sap_record* rec) -{ - sdp_proto_elem_t protoList [2]; - UINT16 services[2]; - UINT16 browse = UUID_SERVCLASS_PUBLIC_BROWSE_GROUP; - BOOLEAN status = TRUE; - UINT32 sdp_handle = 0; - - APPL_TRACE_DEBUG("%s(): scn 0x%02x, service name %s\n", __func__, - rec->hdr.rfcomm_channel_number, rec->hdr.service_name); - - if ((sdp_handle = esp_bt_sdp_create_record()) == 0) - { - APPL_TRACE_ERROR("%s(): Unable to register SAPS Service\n", __func__); - return sdp_handle; - } - - services[0] = UUID_SERVCLASS_SAP; - services[1] = UUID_SERVCLASS_GENERIC_TELEPHONY; - - // add service class - status &= esp_bt_sdp_add_service_class_id_list(sdp_handle, 2, services); - memset(protoList, 0, 2 * sizeof(sdp_proto_elem_t)); - - // add protocol list, including RFCOMM scn - protoList[0].protocol_uuid = UUID_PROTOCOL_L2CAP; - protoList[0].num_params = 0; - protoList[1].protocol_uuid = UUID_PROTOCOL_RFCOMM; - protoList[1].num_params = 1; - protoList[1].params[0] = rec->hdr.rfcomm_channel_number; - status &= esp_bt_sdp_add_protocol_list(sdp_handle, 2, protoList); - - // Add a name entry - status &= esp_bt_sdp_add_attribute(sdp_handle, - (UINT16)ATTR_ID_SERVICE_NAME, - (UINT8)TEXT_STR_DESC_TYPE, - (UINT32)(rec->hdr.service_name_length + 1), - (UINT8 *)rec->hdr.service_name); - - // Add in the Bluetooth Profile Descriptor List - status &= esp_bt_sdp_add_profile_dscp_list(sdp_handle, - UUID_SERVCLASS_SAP, - rec->hdr.profile_version); - - // Make the service browseable - status &= esp_bt_sdp_add_uuid_sequence (sdp_handle, ATTR_ID_BROWSE_GROUP_LIST, 1, &browse); - - if (!status) - { - esp_bt_sdp_delete_record(sdp_handle); - sdp_handle = 0; - APPL_TRACE_ERROR("%s(): FAILED deleting record\n", __func__); - } - else - { - bta_sys_add_uuid(UUID_SERVCLASS_SAP); - APPL_TRACE_DEBUG("%s(): SDP Registered (handle 0x%08x)\n", __func__, sdp_handle); - } - return sdp_handle; -} - diff --git a/examples/13_bt_sdp/components/bluedroid_demos/btif/btif_util.c b/examples/13_bt_sdp/components/bluedroid_demos/btif/btif_util.c deleted file mode 100755 index b64e7fdeb2..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/btif/btif_util.c +++ /dev/null @@ -1,159 +0,0 @@ -/****************************************************************************** - * - * Copyright (c) 2014 The Android Open Source Project - * Copyright (C) 2009-2012 Broadcom Corporation - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at: - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - ******************************************************************************/ - -/************************************************************************************ - * - * Filename: btif_util.c - * - * Description: Miscellaneous helper functions - * - * - ***********************************************************************************/ - -// #include -// #include -// #include -// #include -#include -#include -#include -#include - - -#define LOG_TAG "bt_btif_util" -// #include "btif_common.h" -// #include "bta_api.h" -// #include "gki.h" -// #include "btu.h" -// #include "bte.h" -// #include "btif_dm.h" -#include "btif_util.h" -// #include "bta_ag_api.h" -// #include "bta_av_api.h" -// #include "bta_hh_api.h" -// #include "bta_hf_client_api.h" -// #include "avrc_defs.h" -#include "bt_defs.h" - -/************************************************************************************ -** Constants & Macros -************************************************************************************/ -#define ISDIGIT(a) ((a>='0') && (a<='9')) -#define ISXDIGIT(a) (((a>='0') && (a<='9'))||((a>='A') && (a<='F'))||((a>='a') && (a<='f'))) - -/************************************************************************************ -** Local type definitions -************************************************************************************/ - -/************************************************************************************ -** Static variables -************************************************************************************/ - -/************************************************************************************ -** Static functions -************************************************************************************/ - -/************************************************************************************ -** Externs -************************************************************************************/ - -/************************************************************************************ -** Functions -************************************************************************************/ - -/***************************************************************************** -** Logging helper functions -*****************************************************************************/ - -UINT32 devclass2uint(DEV_CLASS dev_class) -{ - UINT32 cod = 0; - - if(dev_class != NULL) - { - /* if COD is 0, irrespective of the device type set it to Unclassified device */ - cod = (dev_class[2]) | (dev_class[1] << 8) | (dev_class[0] << 16); - } - return cod; -} -void uint2devclass(UINT32 cod, DEV_CLASS dev_class) -{ - dev_class[2] = (UINT8)cod; - dev_class[1] = (UINT8)(cod >> 8); - dev_class[0] = (UINT8)(cod >> 16); -} - -static const UINT8 sdp_base_uuid[] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00, - 0x80, 0x00, 0x00, 0x80, 0x5F, 0x9B, 0x34, 0xFB}; - -void uuid16_to_uuid128(uint16_t uuid16, bt_uuid_t* uuid128) -{ - uint16_t uuid16_bo; - memset(uuid128, 0, sizeof(bt_uuid_t)); - - memcpy(uuid128->uu, sdp_base_uuid, MAX_UUID_SIZE); - uuid16_bo = ntohs(uuid16); - memcpy(uuid128->uu + 2, &uuid16_bo, sizeof(uint16_t)); -} - -void string_to_uuid(char *str, bt_uuid_t *p_uuid) -{ - uint32_t uuid0, uuid4; - uint16_t uuid1, uuid2, uuid3, uuid5; - - sscanf(str, "%08x-%04hx-%04hx-%04hx-%08x%04hx", - &uuid0, &uuid1, &uuid2, &uuid3, &uuid4, &uuid5); - - uuid0 = htonl(uuid0); - uuid1 = htons(uuid1); - uuid2 = htons(uuid2); - uuid3 = htons(uuid3); - uuid4 = htonl(uuid4); - uuid5 = htons(uuid5); - - memcpy(&(p_uuid->uu[0]), &uuid0, 4); - memcpy(&(p_uuid->uu[4]), &uuid1, 2); - memcpy(&(p_uuid->uu[6]), &uuid2, 2); - memcpy(&(p_uuid->uu[8]), &uuid3, 2); - memcpy(&(p_uuid->uu[10]), &uuid4, 4); - memcpy(&(p_uuid->uu[14]), &uuid5, 2); - - return; - -} - -void uuid_to_string_legacy(bt_uuid_t *p_uuid, char *str) -{ - uint32_t uuid0, uuid4; - uint16_t uuid1, uuid2, uuid3, uuid5; - - memcpy(&uuid0, &(p_uuid->uu[0]), 4); - memcpy(&uuid1, &(p_uuid->uu[4]), 2); - memcpy(&uuid2, &(p_uuid->uu[6]), 2); - memcpy(&uuid3, &(p_uuid->uu[8]), 2); - memcpy(&uuid4, &(p_uuid->uu[10]), 4); - memcpy(&uuid5, &(p_uuid->uu[14]), 2); - - sprintf((char *)str, "%.8x-%.4x-%.4x-%.4x-%.8x%.4x", - ntohl(uuid0), ntohs(uuid1), - ntohs(uuid2), ntohs(uuid3), - ntohl(uuid4), ntohs(uuid5)); - return; -} - diff --git a/examples/13_bt_sdp/components/bluedroid_demos/btif/stack_manager.c b/examples/13_bt_sdp/components/bluedroid_demos/btif/stack_manager.c deleted file mode 100644 index 37843cdea2..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/btif/stack_manager.c +++ /dev/null @@ -1,160 +0,0 @@ -#include -#include -#include "btif_stack_manager.h" -#include "stack_manager.h" -#include "bt_defs.h" -#include "bt_trace.h" -#include "future.h" -#include "btif_common.h" -#include "btif_api.h" -#include "btif_dm.h" - -/************************************************************************************ -** Constants & Macros -************************************************************************************/ -/************************************************************************************ -** Local type definitions -************************************************************************************/ -/************************************************************************************ -** Static variables -************************************************************************************/ -static bool stack_is_initialized = false; -static bool stack_is_running = false; -static bt_callbacks_t *bt_hal_cbacks = NULL; -static future_t *hack_future = NULL; - -static bt_status_t event_init_stack(bt_callbacks_t *cb); -static bt_status_t event_start_up_stack(void); -static bt_status_t event_shut_down_stack(void); -static bt_status_t event_clean_up_stack(void); -static void event_signal_stack_up(UNUSED_ATTR uint16_t event, UNUSED_ATTR char *p_param); -static void event_signal_stack_down(UNUSED_ATTR uint16_t event, UNUSED_ATTR char *p_param); - -static bt_status_t event_init_stack(bt_callbacks_t *cb) -{ - bt_status_t ret; - if (!stack_is_initialized) { - hack_future = future_new(); - ret = btif_init_bluetooth(); - if (future_await(hack_future) != FUTURE_SUCCESS) { - return BT_STATUS_FAIL; - } - if (ret == BT_STATUS_SUCCESS) { - bt_hal_cbacks = cb; - stack_is_initialized = true; - } - return ret; - } - else { - return BT_STATUS_DONE; - } -} - -static bt_status_t event_start_up_stack(void) -{ - if (!stack_is_initialized) { - LOG_DEBUG("%s stack not initialized yet.\n", __func__); - return BT_STATUS_NOT_READY; - } - - if (stack_is_running) { - LOG_DEBUG("%s stack already brought up.\n", __func__); - return BT_STATUS_DONE; - } - - LOG_DEBUG("%s is bringing up the stack.\n", __func__); - hack_future = future_new(); - - btif_enable_bluetooth(); - - if (future_await(hack_future) != FUTURE_SUCCESS) { - stack_is_running = true; // So stack shutdown actually happens - event_shut_down_stack(); - return BT_STATUS_FAIL; - } - - stack_is_running = true; - LOG_DEBUG("%s finished\n", __func__); - btif_transfer_context(event_signal_stack_up, 0, NULL, 0, NULL); - return BT_STATUS_SUCCESS; -} - -static bt_status_t event_shut_down_stack(void) -{ - if (!stack_is_running) { - LOG_DEBUG("%s stack is already brought down.\n", __func__); - return BT_STATUS_DONE; - } - - LOG_DEBUG("%s is bringing down the stack.\n", __func__); - hack_future = future_new(); - stack_is_running = false; - - btif_disable_bluetooth(); - - future_await(hack_future); - - LOG_DEBUG("%s finished.\n", __func__); - btif_transfer_context(event_signal_stack_down, 0, NULL, 0, NULL); - return BT_STATUS_SUCCESS; -} - -static bt_status_t event_clean_up_stack(void) -{ - if (!stack_is_initialized) { - LOG_DEBUG("%s found the stack already in a clean state.\n", __func__); - return BT_STATUS_DONE; - } - - if (stack_is_running) { - event_shut_down_stack(); - } - - LOG_DEBUG("%s is cleaning up the stack.\n", __func__); - - stack_is_initialized = false; - - btif_shutdown_bluetooth(); - - return BT_STATUS_SUCCESS; -} - -static void event_signal_stack_up(UNUSED_ATTR uint16_t event, UNUSED_ATTR char *p_param) -{ - HAL_CBACK(bt_hal_cbacks, adapter_state_changed_cb, BT_STATE_ON); -} - -static void event_signal_stack_down(UNUSED_ATTR uint16_t event, UNUSED_ATTR char *p_param) -{ - HAL_CBACK(bt_hal_cbacks, adapter_state_changed_cb, BT_STATE_OFF); -} - -bt_status_t BTIF_InitStack(bt_callbacks_t *cb) -{ - return event_init_stack(cb); -} - -bt_status_t BTIF_EnableStack(void) -{ - return event_start_up_stack(); -} - -bt_status_t BTIF_DisableStack(void) -{ - return event_shut_down_stack(); -} - -bt_status_t BTIF_CleanUpStack(void) -{ - return event_clean_up_stack(); -} - -bool stack_manager_is_stack_running(void) -{ - return stack_is_running; -} - -future_t *stack_manager_get_hack_future(void) -{ - return hack_future; -} diff --git a/examples/13_bt_sdp/components/bluedroid_demos/component.mk b/examples/13_bt_sdp/components/bluedroid_demos/component.mk deleted file mode 100755 index 98cb290800..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/component.mk +++ /dev/null @@ -1,18 +0,0 @@ -# -# Main Makefile. This is basically the same as a component makefile. -# -# This Makefile should, at the very least, just include $(SDK_PATH)/make/component_common.mk. By default, -# this will take the sources in the src/ directory, compile them and link them into -# lib(subdirectory_name).a in the build directory. This behaviour is entirely configurable, -# please read the ESP-IDF documents if you need to do this. -# - -COMPONENT_SRCDIRS := \ - app_core \ - app_project \ - btif - -CFLAGS += -Wno-error=unused-label -Wno-error=return-type -Wno-error=missing-braces -Wno-error=pointer-sign -Wno-error=parentheses -I./include - - -include $(IDF_PATH)/make/component_common.mk diff --git a/examples/13_bt_sdp/components/bluedroid_demos/include/bt_app_common.h b/examples/13_bt_sdp/components/bluedroid_demos/include/bt_app_common.h deleted file mode 100755 index c16ff19060..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/include/bt_app_common.h +++ /dev/null @@ -1,44 +0,0 @@ -// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at - -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -#ifndef __BT_APP_COMMON_H__ -#define __BT_APP_COMMON_H__ - -#include -#include "osi.h" -#include "bt_common_types.h" -#include "bt_defs.h" - -/* BT APP Events */ -#define BT_EVT_APP (0xB000) -#define BT_EVT_APP_CONTEXT_SWITCH (0x0001 | BT_EVT_APP) - -typedef void (tBTAPP_CBACK) (uint16_t event, char *p_param); -typedef void (tBTAPP_COPY_CBACK) (uint16_t event, char *p_dest, char *p_src); - -typedef struct -{ - BT_HDR hdr; - tBTAPP_CBACK* p_cb; /* context switch callback */ - - /* parameters passed to callback */ - UINT16 event; /* message event id */ - char p_param[0]; /* parameter area needs to be last */ -} tBTAPP_CONTEXT_SWITCH_CBACK; - -bt_status_t bt_app_transfer_context (tBTAPP_CBACK *p_cback, UINT16 event, char* p_params, int param_len, tBTAPP_COPY_CBACK *p_copy_cback); - -void bt_app_task_start_up(void); - -#endif /* __BT_APP_COMMON_H__ */ diff --git a/examples/13_bt_sdp/components/bluedroid_demos/include/btif_api.h b/examples/13_bt_sdp/components/bluedroid_demos/include/btif_api.h deleted file mode 100755 index 753fec100d..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/include/btif_api.h +++ /dev/null @@ -1,88 +0,0 @@ -/****************************************************************************** - * - * Copyright (C) 2009-2012 Broadcom Corporation - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at: - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - ******************************************************************************/ - -/******************************************************************************* - * - * Filename: btif_api.h - * - * Description: Main API header file for all BTIF functions accessed - * from main bluetooth HAL. All HAL extensions will not - * require headerfiles as they would be accessed through - * callout/callins. - * - *******************************************************************************/ - -#ifndef BTIF_API_H -#define BTIF_API_H - -#include "btif_common.h" -#include "btif_dm.h" - -/******************************************************************************* -** BTIF CORE API -********************************************************************************/ - -/******************************************************************************* -** -** Function btif_init_bluetooth -** -** Description Creates BTIF task and prepares BT scheduler for startup -** -** Returns bt_status_t -** -*******************************************************************************/ -bt_status_t btif_init_bluetooth(void); - -/******************************************************************************* -** -** Function btif_enable_bluetooth -** -** Description Performs chip power on and kickstarts OS scheduler -** -** Returns bt_status_t -** -*******************************************************************************/ -bt_status_t btif_enable_bluetooth(void); - -/******************************************************************************* -** -** Function btif_disable_bluetooth -** -** Description Inititates shutdown of Bluetooth system. -** Any active links will be dropped and device entering -** non connectable/discoverable mode -** -** Returns void -** -*******************************************************************************/ -bt_status_t btif_disable_bluetooth(void); - -/******************************************************************************* -** -** Function btif_shutdown_bluetooth -** -** Description Finalizes BT scheduler shutdown and terminates BTIF -** task. -** -** -** Returns void -** -*******************************************************************************/ -bt_status_t btif_shutdown_bluetooth(void); - -#endif /* BTIF_API_H */ diff --git a/examples/13_bt_sdp/components/bluedroid_demos/include/btif_common.h b/examples/13_bt_sdp/components/bluedroid_demos/include/btif_common.h deleted file mode 100755 index ca6168c52b..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/include/btif_common.h +++ /dev/null @@ -1,122 +0,0 @@ -/****************************************************************************** - * - * Copyright (c) 2014 The Android Open Source Project - * Copyright (C) 2009-2012 Broadcom Corporation - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at: - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - ******************************************************************************/ - -#ifndef BTIF_COMMON_H -#define BTIF_COMMON_H - -#include -// #include - -#include "bt_types.h" -#include "bta_api.h" -#include "osi.h" - -// #include "osi/include/log.h" - -/******************************************************************************* -** Constants & Macros -********************************************************************************/ -#define ASSERTC(cond, msg, val) if (!(cond)) { LOG_ERROR( \ - "### ASSERT : %s line %d %s (%d) ###", __FILE__, __LINE__, msg, val);} - -/* Calculate start of event enumeration; id is top 8 bits of event */ -#define BTIF_SIG_START(id) ((id) << 8) - -/* For upstream the MSB bit is always SET */ -#define BTIF_SIG_CB_BIT (0x8000) -#define BTIF_SIG_CB_START(id) (((id) << 8) | BTIF_SIG_CB_BIT) - -/* BTIF sub-systems */ -#define BTIF_CORE 0 -#define BTIF_DM 1 -// #define BTIF_HFP 2 -// #define BTIF_AV 3 -// #define BTIF_PAN 4 -// #define BTIF_HF_CLIENT 5 - -#define HAL_CBACK(P_CB, P_CBACK, ...)\ - if (P_CB && P_CB->P_CBACK) { \ - BTIF_TRACE_API("HAL %s->%s", #P_CB, #P_CBACK); \ - P_CB->P_CBACK(__VA_ARGS__); \ - } \ - else { \ - ASSERTC(0, "Callback is NULL", 0); \ - } - -/** - * BTIF events for requests that require context switch to btif task - * on downstreams path - */ -enum -{ - BTIF_CORE_API_START = BTIF_SIG_START(BTIF_CORE), - /* add here */ - - BTIF_DM_API_START = BTIF_SIG_START(BTIF_DM), - BTIF_DM_ENABLE_SERVICE, - BTIF_DM_DISABLE_SERVICE, - /* add here */ - -}; - - -/******************************************************************************* -** Type definitions for callback functions -********************************************************************************/ - -typedef void (tBTIF_CBACK) (UINT16 event, char *p_param); -typedef void (tBTIF_COPY_CBACK) (UINT16 event, char *p_dest, char *p_src); - - -/******************************************************************************* -** Type definitions and return values -********************************************************************************/ - -/* this type handles all btif context switches between BTU and HAL */ -typedef struct -{ - BT_HDR hdr; - tBTIF_CBACK* p_cb; /* context switch callback */ - - /* parameters passed to callback */ - UINT16 event; /* message event id */ - char p_param[0]; /* parameter area needs to be last */ -} tBTIF_CONTEXT_SWITCH_CBACK; - - -/******************************************************************************* -** Functions -********************************************************************************/ - -bt_status_t btif_transfer_context (tBTIF_CBACK *p_cback, UINT16 event, char* p_params, - int param_len, tBTIF_COPY_CBACK *p_copy_cback); -tBTA_SERVICE_MASK btif_get_enabled_services_mask(void); -bt_status_t btif_enable_service(tBTA_SERVICE_ID service_id); -bt_status_t btif_disable_service(tBTA_SERVICE_ID service_id); -int btif_is_enabled(void); - -/** - * BTIF_Events - */ -void btif_enable_bluetooth_evt(tBTA_STATUS status); -void btif_disable_bluetooth_evt(void); - - - -#endif /* BTIF_COMMON_H */ diff --git a/examples/13_bt_sdp/components/bluedroid_demos/include/btif_dm.h b/examples/13_bt_sdp/components/bluedroid_demos/include/btif_dm.h deleted file mode 100755 index 58f535c30b..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/include/btif_dm.h +++ /dev/null @@ -1,32 +0,0 @@ -/****************************************************************************** - * - * Copyright (C) 2009-2012 Broadcom Corporation - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at: - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - ******************************************************************************/ - -#ifndef BTIF_DM_H -#define BTIF_DM_H - -#include "bta_api.h" -/************************************************************************************ -** Functions -********************************************************************************/ - -/** - * BTIF callback to switch context from bte to btif - */ -void bte_dm_evt(tBTA_DM_SEC_EVT event, tBTA_DM_SEC *p_data); - -#endif diff --git a/examples/13_bt_sdp/components/bluedroid_demos/include/btif_sdp.h b/examples/13_bt_sdp/components/bluedroid_demos/include/btif_sdp.h deleted file mode 100644 index e345ef03f2..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/include/btif_sdp.h +++ /dev/null @@ -1,38 +0,0 @@ -#ifndef __BTIF_SDP_H__ -#define __BTIF_SDP_H__ - -#include "bt_sdp.h" - -/** Callback for SDP search */ -typedef void (*btsdp_search_callback)(bt_status_t status, bt_bdaddr_t *bd_addr, uint8_t* uuid, int num_records, bluetooth_sdp_record *records); - -typedef struct { - btsdp_search_callback sdp_search_cb; -} btsdp_callbacks_t; - -/** Register BT SDP search callbacks */ -bt_status_t BTIF_SdpInit(btsdp_callbacks_t *callbacks); - -/** Unregister BT SDP */ -bt_status_t BTIF_SdpDeinit(void); - -/** Search for SDP records with specific uuid on remote device */ -bt_status_t BTIF_SdpSearch(bt_bdaddr_t *bd_addr, const uint8_t* uuid); - -/** - * Use listen in the socket interface to create rfcomm and/or l2cap PSM channels, - * (without UUID and service_name and set the BTSOCK_FLAG_NO_SDP flag in flags). - * Then use createSdpRecord to create the SDP record associated with the rfcomm/l2cap channels. - * - * Returns a handle to the SDP record, which can be parsed to remove_sdp_record. - * - * record (in) The SDP record to create - * record_handle (out)The corresponding record handle will be written to this pointer. - */ -bt_status_t BTIF_SdpCreateRecord(bluetooth_sdp_record *record, int* record_handle); - -/** Remove a SDP record created by BTIF_SdpCreateRecord */ -bt_status_t BTIF_SdpRemoveRecord(int record_handle); - - -#endif /* __BTIF_SDP_H__ */ diff --git a/examples/13_bt_sdp/components/bluedroid_demos/include/btif_stack_manager.h b/examples/13_bt_sdp/components/bluedroid_demos/include/btif_stack_manager.h deleted file mode 100644 index a780fded25..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/include/btif_stack_manager.h +++ /dev/null @@ -1,31 +0,0 @@ -#ifndef __BTIF_STACK_MANAGER_H__ -#define __BTIF_STACK_MANAGER_H__ - -#include "bt_defs.h" - -/** Bluetooth Adapter State */ -typedef enum { - BT_STATE_OFF, - BT_STATE_ON -} bt_state_t; - -/** Bluetooth Interface callbacks */ - -/** Bluetooth Enable/Disable Callback. */ -typedef void (*adapter_state_changed_callback)(bt_state_t state); - - -/** Bluetooth Device callback structure. */ -typedef struct { - adapter_state_changed_callback adapter_state_changed_cb; -} bt_callbacks_t; - -bt_status_t BTIF_InitStack(bt_callbacks_t *cb); - -bt_status_t BTIF_EnableStack(void); - -bt_status_t BTIF_DisableStack(void); - -bt_status_t BTIF_CleanUpStack(void); - -#endif /* __BTIF_STACK_MANAGER_H__ */ diff --git a/examples/13_bt_sdp/components/bluedroid_demos/include/btif_util.h b/examples/13_bt_sdp/components/bluedroid_demos/include/btif_util.h deleted file mode 100755 index 9f2595b1d8..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/include/btif_util.h +++ /dev/null @@ -1,52 +0,0 @@ -/****************************************************************************** - * - * Copyright (c) 2014 The Android Open Source Project - * Copyright (C) 2009-2012 Broadcom Corporation - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at: - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - ******************************************************************************/ - -#ifndef BTIF_UTIL_H -#define BTIF_UTIL_H - -// #include -// #include -#include -// #include - -#include "bt_types.h" -#include "bt_utils.h" -#include "bt_defs.h" - -/******************************************************************************* -** Constants & Macros -********************************************************************************/ -/******************************************************************************* -** Type definitions for callback functions -********************************************************************************/ - -typedef char bdstr_t[18]; - - -/******************************************************************************* -** Functions -********************************************************************************/ -UINT32 devclass2uint(DEV_CLASS dev_class); -void uint2devclass(UINT32 dev, DEV_CLASS dev_class); -void uuid16_to_uuid128(uint16_t uuid16, bt_uuid_t* uuid128); - -void uuid_to_string_legacy(bt_uuid_t *p_uuid, char *str); -void string_to_uuid(char *str, bt_uuid_t *p_uuid); - -#endif /* BTIF_UTIL_H */ diff --git a/examples/13_bt_sdp/components/bluedroid_demos/include/stack_manager.h b/examples/13_bt_sdp/components/bluedroid_demos/include/stack_manager.h deleted file mode 100755 index 466cdca122..0000000000 --- a/examples/13_bt_sdp/components/bluedroid_demos/include/stack_manager.h +++ /dev/null @@ -1,29 +0,0 @@ -/****************************************************************************** - * - * Copyright (C) 2014 Google, Inc. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at: - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - ******************************************************************************/ - -#ifndef __STACK_MANAGER_H__ -#define __STACK_MANAGER_H__ - -#include -#include "future.h" - -bool stack_manager_is_stack_running(void); - -future_t *stack_manager_get_hack_future(void); - -#endif /* __STACK_MANAGER_H__*/ diff --git a/examples/13_bt_sdp/main/component.mk b/examples/13_bt_sdp/main/component.mk deleted file mode 100755 index 24356f23ed..0000000000 --- a/examples/13_bt_sdp/main/component.mk +++ /dev/null @@ -1,10 +0,0 @@ -# -# Main Makefile. This is basically the same as a component makefile. -# -# This Makefile should, at the very least, just include $(SDK_PATH)/make/component_common.mk. By default, -# this will take the sources in the src/ directory, compile them and link them into -# lib(subdirectory_name).a in the build directory. This behaviour is entirely configurable, -# please read the ESP-IDF documents if you need to do this. -# - -include $(IDF_PATH)/make/component_common.mk diff --git a/examples/13_bt_sdp/Makefile b/examples/13_timer_group/Makefile old mode 100755 new mode 100644 similarity index 65% rename from examples/13_bt_sdp/Makefile rename to examples/13_timer_group/Makefile index 1e91bbb891..b55e8c13d0 --- a/examples/13_bt_sdp/Makefile +++ b/examples/13_timer_group/Makefile @@ -3,9 +3,7 @@ # project subdirectory. # -PROJECT_NAME := bluedroid_demos - -COMPONENT_ADD_INCLUDEDIRS := components/include +PROJECT_NAME := timer_group include $(IDF_PATH)/make/project.mk diff --git a/examples/13_timer_group/main/component.mk b/examples/13_timer_group/main/component.mk new file mode 100644 index 0000000000..0b9d7585e7 --- /dev/null +++ b/examples/13_timer_group/main/component.mk @@ -0,0 +1,5 @@ +# +# "main" pseudo-component makefile. +# +# (Uses default behaviour of compiling all source files in directory, adding 'include' to include path.) + diff --git a/examples/13_timer_group/main/timer_group.c b/examples/13_timer_group/main/timer_group.c new file mode 100644 index 0000000000..15d1ca2c05 --- /dev/null +++ b/examples/13_timer_group/main/timer_group.c @@ -0,0 +1,205 @@ +/* Timer group-hardware timer example + + This example code is in the Public Domain (or CC0 licensed, at your option.) + + Unless required by applicable law or agreed to in writing, this + software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR + CONDITIONS OF ANY KIND, either express or implied. +*/ + +#include +#include "esp_types.h" +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "freertos/queue.h" +#include "soc/timer_group_struct.h" +#include "driver/periph_ctrl.h" +#include "driver/timer.h" + +#define TIMER_INTR_NUM_0 17 /*!< Interrupt number for hardware timer 0 */ +#define TIMER_INTR_NUM_1 18 /*!< Interrupt number for hardware timer 1*/ +#define TIMER_INTR_SEL TIMER_INTR_LEVEL /*!< Timer level interrupt */ +#define TIMER_GROUP TIMER_GROUP_0 /*!< Test on timer group 0 */ +#define TIMER_DIVIDER 16 /*!< Hardware timer clock divider */ +#define TIMER_SCALE (TIMER_BASE_CLK / TIMER_DIVIDER) /*!< used to calculate counter value */ +#define TIMER_FINE_ADJ (1.4*(TIMER_BASE_CLK / TIMER_DIVIDER)/1000000) /*!< used to compensate alarm value */ +#define TIMER_INTERVAL0_SEC (3.4179) /*!< test interval for timer 0 */ +#define TIMER_INTERVAL1_SEC (5.78) /*!< test interval for timer 1 */ +#define TEST_WITHOUT_RELOAD 0 /*!< example of auto-reload mode */ +#define TEST_WITH_RELOAD 1 /*!< example without auto-reload mode */ + +typedef struct { + int type; /*!< event type */ + int group; /*!< timer group */ + int idx; /*!< timer number */ + uint64_t counter_val; /*!< timer counter value */ + double time_sec; /*!< calculated time from counter value */ +} timer_event_t; + +xQueueHandle timer_queue; + +/* + * @brief Print a uint64_t value + */ +static void inline print_u64(uint64_t val) +{ + printf("0x%08x%08x\n", (uint32_t) (val >> 32), (uint32_t) (val)); +} + +void timer_evt_task(void *arg) +{ + while(1) { + timer_event_t evt; + xQueueReceive(timer_queue, &evt, portMAX_DELAY); + if(evt.type == TEST_WITHOUT_RELOAD) { + printf("\n\n example of count-up-timer \n"); + } else if(evt.type == TEST_WITH_RELOAD) { + printf("\n\n example of reload-timer \n"); + + } + /*Show timer event from interrupt*/ + printf("-------INTR TIME EVT--------\n"); + printf("TG[%d] timer[%d] alarm evt\n", evt.group, evt.idx); + printf("reg: "); + print_u64(evt.counter_val); + printf("time: %.8f S\n", evt.time_sec); + /*Read timer value from task*/ + printf("======TASK TIME======\n"); + uint64_t timer_val; + timer_get_counter_value(evt.group, evt.idx, &timer_val); + double time; + timer_get_counter_time_sec(evt.group, evt.idx, &time); + printf("TG[%d] timer[%d] alarm evt\n", evt.group, evt.idx); + printf("reg: "); + print_u64(timer_val); + printf("time: %.8f S\n", time); + } +} + +/* + * @brief timer group0 ISR handler + */ +void IRAM_ATTR timer_group0_isr(void *para) +{ + int timer_idx = (int) para; + uint32_t intr_status = TIMERG0.int_st_timers.val; + timer_event_t evt; + if((intr_status & BIT(timer_idx)) && timer_idx == TIMER_0) { + /*Timer0 is an example that don't reload counter value*/ + TIMERG0.hw_timer[timer_idx].update = 1; + + /*We don't call a API here because they are not declared with IRAM_ATTR*/ + TIMERG0.int_clr_timers.t0 = 1; + uint64_t timer_val = ((uint64_t) TIMERG0.hw_timer[timer_idx].cnt_high) << 32 + | TIMERG0.hw_timer[timer_idx].cnt_low; + double time = (double) timer_val / (TIMER_BASE_CLK / TIMERG0.hw_timer[timer_idx].config.divider); + + /*Post an event to out example task*/ + evt.type = TEST_WITHOUT_RELOAD; + evt.group = 0; + evt.idx = timer_idx; + evt.counter_val = timer_val; + evt.time_sec = time; + xQueueSendFromISR(timer_queue, &evt, NULL); + + /*For a timer that will not reload, we need to set the next alarm value each time. */ + timer_val += + (uint64_t) (TIMER_INTERVAL0_SEC * (TIMER_BASE_CLK / TIMERG0.hw_timer[timer_idx].config.divider)); + /*Fine adjust*/ + timer_val -= TIMER_FINE_ADJ; + TIMERG0.hw_timer[timer_idx].alarm_high = (uint32_t) (timer_val >> 32); + TIMERG0.hw_timer[timer_idx].alarm_low = (uint32_t) timer_val; + /*After set alarm, we set alarm_en bit if we want to enable alarm again.*/ + TIMERG0.hw_timer[timer_idx].config.alarm_en = 1; + + } else if((intr_status & BIT(timer_idx)) && timer_idx == TIMER_1) { + /*Timer1 is an example that will reload counter value*/ + TIMERG0.hw_timer[timer_idx].update = 1; + /*We don't call a API here because they are not declared with IRAM_ATTR*/ + TIMERG0.int_clr_timers.t1 = 1; + uint64_t timer_val = ((uint64_t) TIMERG0.hw_timer[timer_idx].cnt_high) << 32 + | TIMERG0.hw_timer[timer_idx].cnt_low; + double time = (double) timer_val / (TIMER_BASE_CLK / TIMERG0.hw_timer[timer_idx].config.divider); + /*Post an event to out example task*/ + evt.type = TEST_WITH_RELOAD; + evt.group = 0; + evt.idx = timer_idx; + evt.counter_val = timer_val; + evt.time_sec = time; + xQueueSendFromISR(timer_queue, &evt, NULL); + /*For a auto-reload timer, we still need to set alarm_en bit if we want to enable alarm again.*/ + TIMERG0.hw_timer[timer_idx].config.alarm_en = 1; + } +} + +/* + * @brief timer group0 hardware timer0 init + */ +void tg0_timer0_init() +{ + int timer_group = TIMER_GROUP_0; + int timer_idx = TIMER_0; + timer_config_t config; + config.alarm_en = 1; + config.auto_reload = 0; + config.counter_dir = TIMER_COUNT_UP; + config.divider = TIMER_DIVIDER; + config.intr_type = TIMER_INTR_SEL; + config.counter_en = TIMER_PAUSE; + /*Configure timer*/ + timer_init(timer_group, timer_idx, &config); + /*Stop timer counter*/ + timer_pause(timer_group, timer_idx); + /*Load counter value */ + timer_set_counter_value(timer_group, timer_idx, 0x00000000ULL); + /*Set alarm value*/ + timer_set_alarm_value(timer_group, timer_idx, TIMER_INTERVAL0_SEC * TIMER_SCALE - TIMER_FINE_ADJ); + /*Enable timer interrupt*/ + timer_enable_intr(timer_group, timer_idx); + /*Set ISR handler*/ + timer_isr_register(timer_group, timer_idx, TIMER_INTR_NUM_0, TIMER_INTR_SEL, timer_group0_isr, (void*) timer_idx); + /*Start timer counter*/ + timer_start(timer_group, timer_idx); +} + +/* + * @brief timer group0 hardware timer1 init + */ +void tg0_timer1_init() +{ + int timer_group = TIMER_GROUP_0; + int timer_idx = TIMER_1; + timer_config_t config; + config.alarm_en = 1; + config.auto_reload = 1; + config.counter_dir = TIMER_COUNT_UP; + config.divider = TIMER_DIVIDER; + config.intr_type = TIMER_INTR_SEL; + config.counter_en = TIMER_PAUSE; + /*Configure timer*/ + timer_init(timer_group, timer_idx, &config); + /*Stop timer counter*/ + timer_pause(timer_group, timer_idx); + /*Load counter value */ + timer_set_counter_value(timer_group, timer_idx, 0x00000000ULL); + /*Set alarm value*/ + timer_set_alarm_value(timer_group, timer_idx, TIMER_INTERVAL1_SEC * TIMER_SCALE); + /*Enable timer interrupt*/ + timer_enable_intr(timer_group, timer_idx); + /*Set ISR handler*/ + timer_isr_register(timer_group, timer_idx, TIMER_INTR_NUM_1, TIMER_INTR_SEL, timer_group0_isr, (void*) timer_idx); + /*Start timer counter*/ + timer_start(timer_group, timer_idx); +} + +/** + * @brief In this test, we will test hardware timer0 and timer1 of timer group0. + */ +void app_main() +{ + tg0_timer0_init(); + tg0_timer1_init(); + timer_queue = xQueueCreate(10, sizeof(timer_event_t)); + xTaskCreate(timer_evt_task, "timer_evt_task", 1024, NULL, 5, NULL); +} + diff --git a/examples/14_ethernet/Makefile b/examples/14_ethernet/Makefile new file mode 100644 index 0000000000..f16d4d2d7a --- /dev/null +++ b/examples/14_ethernet/Makefile @@ -0,0 +1,9 @@ +# +# This is a project Makefile. It is assumed the directory this Makefile resides in is a +# project subdirectory. +# + +PROJECT_NAME := ethernet_demo + +include $(IDF_PATH)/make/project.mk + diff --git a/examples/14_ethernet/README.md b/examples/14_ethernet/README.md new file mode 100644 index 0000000000..71c2590457 --- /dev/null +++ b/examples/14_ethernet/README.md @@ -0,0 +1,6 @@ +# ethernet Example + +Init ethernet interface and enable it ,then you can ping it if it got ip address. + + +See the README.md file in the upper level 'examples' directory for more information about examples. diff --git a/examples/14_ethernet/main/component.mk b/examples/14_ethernet/main/component.mk new file mode 100644 index 0000000000..a98f634eae --- /dev/null +++ b/examples/14_ethernet/main/component.mk @@ -0,0 +1,4 @@ +# +# "main" pseudo-component makefile. +# +# (Uses default behaviour of compiling all source files in directory, adding 'include' to include path.) diff --git a/examples/14_ethernet/main/ethernet_main.c b/examples/14_ethernet/main/ethernet_main.c new file mode 100644 index 0000000000..836e977f48 --- /dev/null +++ b/examples/14_ethernet/main/ethernet_main.c @@ -0,0 +1,112 @@ +/* ethernet Example + + This example code is in the Public Domain (or CC0 licensed, at your option.) + + Unless required by applicable law or agreed to in writing, this + software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR + CONDITIONS OF ANY KIND, either express or implied. +*/ +#include +#include + +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" + +#include "esp_system.h" +#include "esp_err.h" +#include "esp_event_loop.h" +#include "esp_event.h" +#include "esp_attr.h" +#include "esp_log.h" +#include "esp_eth.h" + +#include "rom/ets_sys.h" +#include "rom/gpio.h" + +#include "soc/dport_reg.h" +#include "soc/io_mux_reg.h" +#include "soc/rtc_cntl_reg.h" +#include "soc/gpio_reg.h" +#include "soc/gpio_sig_map.h" + +#include "tcpip_adapter.h" +#include "nvs_flash.h" +#include "driver/gpio.h" + +static const char *TAG = "eth_demo"; + +void phy_tlk110_init(void) +{ + esp_eth_smi_write(0x1f, 0x8000); + ets_delay_us(20000); + + while (esp_eth_smi_read(0x2) != 0x2000) { + } + + esp_eth_smi_write(0x9, 0x7400); + esp_eth_smi_write(0x9, 0xf400); + ets_delay_us(20000); +} + +void eth_gpio_config_rmii(void) +{ + //txd0 to gpio19 ,can not change + PIN_FUNC_SELECT(PERIPHS_IO_MUX_GPIO19_U, 5); + //rx_en to gpio21 ,can not change + PIN_FUNC_SELECT(PERIPHS_IO_MUX_GPIO21_U, 5); + //txd1 to gpio22 , can not change + PIN_FUNC_SELECT(PERIPHS_IO_MUX_GPIO22_U, 5); + //rxd0 to gpio25 , can not change + gpio_set_direction(25, GPIO_MODE_INPUT); + //rxd1 to gpio26 ,can not change + gpio_set_direction(26, GPIO_MODE_INPUT); + //rmii clk ,can not change + gpio_set_direction(0, GPIO_MODE_INPUT); + + //mdc to gpio4 + gpio_matrix_out(4, EMAC_MDC_O_IDX, 0, 0); + //mdio to gpio2 + gpio_matrix_out(2, EMAC_MDO_O_IDX, 0, 0); + gpio_matrix_in(2, EMAC_MDI_I_IDX, 0); +} + +void eth_task(void *pvParameter) +{ + tcpip_adapter_ip_info_t ip; + memset(&ip, 0, sizeof(tcpip_adapter_ip_info_t)); + vTaskDelay(2000 / portTICK_RATE_MS); + + while (1) { + + vTaskDelay(2000 / portTICK_RATE_MS); + + if (tcpip_adapter_get_ip_info(ESP_IF_ETH, &ip) == 0) { + ESP_LOGI(TAG, "\n~~~~~~~~~~~\n"); + ESP_LOGI(TAG, "ETHIP:"IPSTR, IP2STR(&ip.ip)); + ESP_LOGI(TAG, "ETHPMASK:"IPSTR, IP2STR(&ip.netmask)); + ESP_LOGI(TAG, "ETHPGW:"IPSTR, IP2STR(&ip.gw)); + ESP_LOGI(TAG, "\n~~~~~~~~~~~\n"); + } + } +} + +void app_main() +{ + esp_err_t ret = ESP_OK; + tcpip_adapter_init(); + esp_event_loop_init(NULL, NULL); + + eth_config_t config; + config.phy_addr = PHY31; + config.mac_mode = ETH_MODE_RMII; + config.phy_init = phy_tlk110_init; + config.gpio_config = eth_gpio_config_rmii; + config.tcpip_input = tcpip_adapter_eth_input; + + ret = esp_eth_init(&config); + if(ret == ESP_OK) { + esp_eth_enable(); + xTaskCreate(eth_task, "eth_task", 2048, NULL, (tskIDLE_PRIORITY + 2), NULL); + } + +} diff --git a/examples/14_gatt_server/Makefile b/examples/14_gatt_server/Makefile index fae1ac6f5f..d7732bd280 100644 --- a/examples/14_gatt_server/Makefile +++ b/examples/14_gatt_server/Makefile @@ -9,3 +9,10 @@ COMPONENT_ADD_INCLUDEDIRS := components/include include $(IDF_PATH)/make/project.mk +# Copy some defaults into the sdkconfig by default +# so BT stack is enabled +sdkconfig: sdkconfig.defaults + $(Q) cp $< $@ + +menuconfig: sdkconfig +defconfig: sdkconfig diff --git a/examples/14_gatt_server/main/gatts_demo.c b/examples/14_gatt_server/main/gatts_demo.c index 615b66af6b..7ba9447eaa 100644 --- a/examples/14_gatt_server/main/gatts_demo.c +++ b/examples/14_gatt_server/main/gatts_demo.c @@ -174,7 +174,7 @@ static void gatts_event_handler(uint32_t event, void *param) LOG_INFO("ADD_DESCR_EVT, status %d, gatt_if %d, attr_handle %d, service_handle %d\n", p->add_char.status, p->add_char.gatt_if, p->add_char.attr_handle, p->add_char.service_handle); break; - case ESP_GATTS_DELELTE_EVT: + case ESP_GATTS_DELETE_EVT: break; case ESP_GATTS_START_EVT: LOG_INFO("SERVICE_START_EVT, status %d, gatt_if %d, service_handle %d\n", diff --git a/examples/14_gatt_server/sdkconfig.defaults b/examples/14_gatt_server/sdkconfig.defaults new file mode 100644 index 0000000000..e435f383c8 --- /dev/null +++ b/examples/14_gatt_server/sdkconfig.defaults @@ -0,0 +1,14 @@ +# Override some defaults so BT stack is enabled +# in this example + +# +# BT config +# +CONFIG_BT_ENABLED=y + +# +# ESP32-specific config +# +CONFIG_ESP32_ENABLE_STACK_BT=y +# CONFIG_ESP32_ENABLE_STACK_NONE is not set +CONFIG_MEMMAP_BT=y diff --git a/examples/15_gatt_client/Makefile b/examples/15_gatt_client/Makefile index a0428347ad..93f793308f 100644 --- a/examples/15_gatt_client/Makefile +++ b/examples/15_gatt_client/Makefile @@ -9,3 +9,10 @@ COMPONENT_ADD_INCLUDEDIRS := components/include include $(IDF_PATH)/make/project.mk +# Copy some defaults into the sdkconfig by default +# so BT stack is enabled +sdkconfig: sdkconfig.defaults + $(Q) cp $< $@ + +menuconfig: sdkconfig +defconfig: sdkconfig diff --git a/examples/15_gatt_client/main/gattc_demo.c b/examples/15_gatt_client/main/gattc_demo.c index 0732dc8a4e..3dc6af6d75 100644 --- a/examples/15_gatt_client/main/gattc_demo.c +++ b/examples/15_gatt_client/main/gattc_demo.c @@ -135,7 +135,7 @@ static void esp_gattc_cb(uint32_t event, void *param) esp_ble_gattc_search_service(conn_id, NULL); break; case ESP_GATTC_SEARCH_RES_EVT: { - esp_gatt_srvc_id_t *srvc_id = &p_data->search_res.service_id; + esp_gatt_srvc_id_t *srvc_id = &p_data->search_res.srvc_id; conn_id = p_data->open.conn_id; LOG_INFO("SEARCH RES: conn_id = %x\n", conn_id); if (srvc_id->id.uuid.len == ESP_UUID_LEN_16) { diff --git a/examples/15_gatt_client/sdkconfig.defaults b/examples/15_gatt_client/sdkconfig.defaults new file mode 100644 index 0000000000..e435f383c8 --- /dev/null +++ b/examples/15_gatt_client/sdkconfig.defaults @@ -0,0 +1,14 @@ +# Override some defaults so BT stack is enabled +# in this example + +# +# BT config +# +CONFIG_BT_ENABLED=y + +# +# ESP32-specific config +# +CONFIG_ESP32_ENABLE_STACK_BT=y +# CONFIG_ESP32_ENABLE_STACK_NONE is not set +CONFIG_MEMMAP_BT=y diff --git a/examples/16_pcnt/Makefile b/examples/16_pcnt/Makefile new file mode 100644 index 0000000000..5ae4b0b53f --- /dev/null +++ b/examples/16_pcnt/Makefile @@ -0,0 +1,9 @@ +# +# This is a project Makefile. It is assumed the directory this Makefile resides in is a +# project subdirectory. +# + +PROJECT_NAME := pcnt + +include $(IDF_PATH)/make/project.mk + diff --git a/examples/16_pcnt/main/component.mk b/examples/16_pcnt/main/component.mk new file mode 100644 index 0000000000..44bd2b5273 --- /dev/null +++ b/examples/16_pcnt/main/component.mk @@ -0,0 +1,3 @@ +# +# Main Makefile. This is basically the same as a component makefile. +# diff --git a/examples/16_pcnt/main/pcnt_test.c b/examples/16_pcnt/main/pcnt_test.c new file mode 100644 index 0000000000..1da4cca56e --- /dev/null +++ b/examples/16_pcnt/main/pcnt_test.c @@ -0,0 +1,226 @@ +/* Pulse counter module - Example + + For other examples please check: + https://github.com/espressif/esp-idf/tree/master/examples + + This example code is in the Public Domain (or CC0 licensed, at your option.) + + Unless required by applicable law or agreed to in writing, this + software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR + CONDITIONS OF ANY KIND, either express or implied. +*/ +#include +#include "freertos/FreeRTOS.h" +#include "freertos/portmacro.h" +#include "freertos/task.h" +#include "freertos/queue.h" +#include "driver/periph_ctrl.h" +#include "driver/ledc.h" +#include "driver/gpio.h" +#include "driver/pcnt.h" +#include "esp_attr.h" +#include "esp_log.h" +#include "soc/gpio_sig_map.h" + +/** + * TEST CODE BRIEF + * Use PCNT module to count rising edges generated by LEDC module. + * GPIO18 is used as output pin, GPIO4 is used as pulse input pin and GPIO5 is used as control input pin + * + * Open serial port to view the message printed on your screen + * + * To do this test, you should connect GPIO18 with GPIO4 + * GPIO5 is the control signal, you can leave it floating with internal pulled up, or connect it to ground. + * If you connect gpio5 to GND ,you will found the count value decreasing. + * + * When counter value reaches thresh1 or thresh0 value, it will trigger interrupt. + * When counter value reaches l_lim value or h_lim value, counter value will be reset to zero and trigger interrupt. + */ +static const char* TAG = "PCNT_TEST"; +#define PCNT_TEST_UNIT PCNT_UNIT_0 +#define PCNT_H_LIM_VAL (10) +#define PCNT_L_LIM_VAL (-10) +#define PCNT_THRESH1_VAL (5) +#define PCNT_THRESH0_VAL (-5) +#define PCNT_INTR_NUM (18) +#define PCNT_INPUT_SIG_IO (4) +#define PCNT_INPUT_CTRL_IO (5) +#define LEDC_OUPUT_IO (18) + +xQueueHandle pcnt_evt_queue; /*A queue to handle pulse counter event*/ + + +typedef struct { + int unit; /*pulse counter unit*/ + uint32_t status; /*pulse counter internal status*/ +} pcnt_evt_t; + +void IRAM_ATTR pcnt_intr_handler(void* arg) +{ + uint32_t intr_status = PCNT.int_st.val; + int i; + pcnt_evt_t evt; + portBASE_TYPE HPTaskAwoken = pdFALSE; + + for(i = 0; i < PCNT_UNIT_MAX; i++) { + if(intr_status & (BIT(i))) { + evt.unit = i; + evt.status = PCNT.status_unit[i].val; + PCNT.int_clr.val = BIT(i); + /*H LIM EVT*/ + if(PCNT.status_unit[i].h_lim_lat) { + //do something + } + /*L LIM EVT*/ + if(PCNT.status_unit[i].l_lim_lat) { + //do something + } + /*THRES0 EVT*/ + if(PCNT.status_unit[i].thres0_lat) { + //do something + } + /*THRES1 EVT*/ + if(PCNT.status_unit[i].thres1_lat) { + //do something + } + /*ZERO EVT*/ + if(PCNT.status_unit[i].zero_lat) { + //do something + } + xQueueSendFromISR(pcnt_evt_queue, &evt, &HPTaskAwoken); + if(HPTaskAwoken == pdTRUE) { + portYIELD_FROM_ISR(); + } + } + } +} + +static void ledc_init(void) +{ + ledc_channel_config_t ledc_channel; + /*use GPIO18 as output pin*/ + ledc_channel.gpio_num = LEDC_OUPUT_IO; + /*LEDC high speed mode */ + ledc_channel.speed_mode = LEDC_HIGH_SPEED_MODE; + /*use LEDC channel 1*/ + ledc_channel.channel = LEDC_CHANNEL_1; + /*Disable LEDC interrupt*/ + ledc_channel.intr_type = LEDC_INTR_DISABLE; + /*Select LEDC timer 1 */ + ledc_channel.timer_sel = LEDC_TIMER_1; + /*Set duty 100 */ + ledc_channel.duty = 100; + ledc_channel_config(&ledc_channel); //ledc config + + ledc_timer_config_t ledc_timer; + /*LEDC timer high speed mode*/ + ledc_timer.speed_mode = LEDC_HIGH_SPEED_MODE; + /*10 bit PWM*/ + ledc_timer.bit_num = LEDC_TIMER_10_BIT; + /*Select timer 1*/ + ledc_timer.timer_num = LEDC_TIMER_1; + /*Set frequency 1 Hz */ + ledc_timer.freq_hz = 1; + ledc_timer_config(&ledc_timer); +} + +static void pcnt_init(void) +{ + pcnt_config_t pcnt_config = { + /*Set GPIO4 as pulse input gpio */ + .pulse_gpio_num = PCNT_INPUT_SIG_IO, + /*set gpio5 as control gpio */ + .ctrl_gpio_num = PCNT_INPUT_CTRL_IO, + /*Choose channel 0 */ + .channel = PCNT_CHANNEL_0, + /*Choose unit 0 */ + .unit = PCNT_TEST_UNIT, + /*Set counter and control mode*/ + /*Counter increase for positive edge on pulse input GPIO*/ + .pos_mode = PCNT_COUNT_INC, + /*Counter decrease for negative edge on pulse input GPIO*/ + .neg_mode = PCNT_COUNT_DIS, //keep the counter value + /*Counter mode reverse when control input is low level*/ + .lctrl_mode = PCNT_MODE_REVERSE, + /*Counter mode does not change when control input is high level*/ + .hctrl_mode = PCNT_MODE_KEEP, //when control signal is high,keep the primary counter mode + /*Set maximum value for increasing counter*/ + .counter_h_lim = PCNT_H_LIM_VAL, + /*Set minimum value for decreasing counter*/ + .counter_l_lim = PCNT_L_LIM_VAL, + }; + /*Initialize PCNT unit */ + pcnt_unit_config(&pcnt_config); + + /*Configure input filter value*/ + pcnt_set_filter_value(PCNT_TEST_UNIT, 100); + /*Enable input filter*/ + pcnt_filter_enable(PCNT_TEST_UNIT); + + /*Set value for watch point thresh1*/ + pcnt_set_event_value(PCNT_TEST_UNIT, PCNT_EVT_THRES_1, PCNT_THRESH1_VAL); + /*Enable watch point event of thresh1*/ + pcnt_event_enable(PCNT_TEST_UNIT, PCNT_EVT_THRES_1); + /*Set value for watch point thresh0*/ + pcnt_set_event_value(PCNT_TEST_UNIT, PCNT_EVT_THRES_0, PCNT_THRESH0_VAL); + /*Enable watch point event of thresh0*/ + pcnt_event_enable(PCNT_TEST_UNIT, PCNT_EVT_THRES_0); + /*Enable watch point event of h_lim*/ + pcnt_event_enable(PCNT_TEST_UNIT, PCNT_EVT_H_LIM); + /*Enable watch point event of l_lim*/ + pcnt_event_enable(PCNT_TEST_UNIT, PCNT_EVT_L_LIM); + /*Enable watch point event of zero*/ + pcnt_event_enable(PCNT_TEST_UNIT, PCNT_EVT_ZERO); + + /*Pause counter*/ + pcnt_counter_pause(PCNT_TEST_UNIT); + /*Reset counter value*/ + pcnt_counter_clear(PCNT_TEST_UNIT); + /*Register ISR handler*/ + pcnt_isr_register(PCNT_INTR_NUM, pcnt_intr_handler, NULL); + /*Enable interrupt for PCNT unit*/ + pcnt_intr_enable(PCNT_TEST_UNIT); + /*Resume counting*/ + pcnt_counter_resume(PCNT_TEST_UNIT); +} + +void app_main() +{ + /*Init LEDC for pulse input signal */ + ledc_init(); + /*Init PCNT event queue */ + pcnt_evt_queue = xQueueCreate(10, sizeof(pcnt_evt_t)); + /*Init PCNT functions*/ + pcnt_init(); + + int16_t count = 0; + pcnt_evt_t evt; + portBASE_TYPE res; + while(1) + { + res = xQueueReceive(pcnt_evt_queue, &evt, 1000 / portTICK_RATE_MS); + if(res == pdTRUE) { + pcnt_get_counter_value(PCNT_TEST_UNIT, &count); + printf("Event PCNT unit[%d]; cnt: %d\n", evt.unit, count); + if(evt.status & PCNT_STATUS_THRES1_M) { + printf("THRES1 EVT\n"); + } + if(evt.status & PCNT_STATUS_THRES0_M) { + printf("THRES0 EVT\n"); + } + if(evt.status & PCNT_STATUS_L_LIM_M) { + printf("L_LIM EVT\n"); + } + if(evt.status & PCNT_STATUS_H_LIM_M) { + printf("H_LIM EVT\n"); + } + if(evt.status & PCNT_STATUS_ZERO_M) { + printf("ZERO EVT\n"); + } + } else { + pcnt_get_counter_value(PCNT_TEST_UNIT, &count); + printf("Current counter value :%d\n", count); + } + } +} + diff --git a/make/component_wrapper.mk b/make/component_wrapper.mk index c6ea52a2bf..63f687d930 100644 --- a/make/component_wrapper.mk +++ b/make/component_wrapper.mk @@ -155,17 +155,17 @@ endif # This pattern is generated for each COMPONENT_SRCDIR to compile the files in it. define GenerateCompileTargets # $(1) - directory containing source files, relative to $(COMPONENT_PATH) -$(1)/%.o: $$(COMPONENT_PATH)/$(1)/%.c | $(1) +$(1)/%.o: $$(COMPONENT_PATH)/$(1)/%.c $(COMMON_MAKEFILES) $(COMPONENT_MAKEFILE) | $(1) $$(summary) CC $$@ - $$(CC) $$(CFLAGS) $$(CPPFLAGS) $$(addprefix -I ,$$(COMPONENT_INCLUDES)) $$(addprefix -I ,$$(COMPONENT_EXTRA_INCLUDES)) -I$(1) -c $$< -o $$@ + $$(CC) $$(CFLAGS) $$(CPPFLAGS) $$(FLAGS_$$(subst .o,,$$(@))) $$(addprefix -I ,$$(COMPONENT_INCLUDES)) $$(addprefix -I ,$$(COMPONENT_EXTRA_INCLUDES)) -I$(1) -c $$< -o $$@ -$(1)/%.o: $$(COMPONENT_PATH)/$(1)/%.cpp | $(1) +$(1)/%.o: $$(COMPONENT_PATH)/$(1)/%.cpp $(COMMON_MAKEFILES) $(COMPONENT_MAKEFILE) | $(1) $$(summary) CXX $$@ - $$(CXX) $$(CXXFLAGS) $$(CPPFLAGS) $$(addprefix -I,$$(COMPONENT_INCLUDES)) $$(addprefix -I,$$(COMPONENT_EXTRA_INCLUDES)) -I$(1) -c $$< -o $$@ + $$(CXX) $$(CXXFLAGS) $$(CPPFLAGS) $$(FLAGS_$$(subst .o,,$$(@))) $$(addprefix -I,$$(COMPONENT_INCLUDES)) $$(addprefix -I,$$(COMPONENT_EXTRA_INCLUDES)) -I$(1) -c $$< -o $$@ -$(1)/%.o: $$(COMPONENT_PATH)/$(1)/%.S | $(1) +$(1)/%.o: $$(COMPONENT_PATH)/$(1)/%.S $(COMMON_MAKEFILES) $(COMPONENT_MAKEFILE) | $(1) $$(summary) AS $$@ - $$(CC) $$(CPPFLAGS) $$(addprefix -I ,$$(COMPONENT_INCLUDES)) $$(addprefix -I ,$$(COMPONENT_EXTRA_INCLUDES)) -I$(1) -c $$< -o $$@ + $$(CC) $$(CPPFLAGS) $$(FLAGS_$$(subst .o,,$$(@))) $$(addprefix -I ,$$(COMPONENT_INCLUDES)) $$(addprefix -I ,$$(COMPONENT_EXTRA_INCLUDES)) -I$(1) -c $$< -o $$@ # CWD is build dir, create the build subdirectory if it doesn't exist $(1): diff --git a/tools/unit-test-app/sdkconfig b/tools/unit-test-app/sdkconfig index cde49f3c8d..7121dcc8a9 100644 --- a/tools/unit-test-app/sdkconfig +++ b/tools/unit-test-app/sdkconfig @@ -9,6 +9,25 @@ CONFIG_TOOLPREFIX="xtensa-esp32-elf-" CONFIG_PYTHON="python" +# +# Bootloader config +# +# CONFIG_LOG_BOOTLOADER_LEVEL_NONE is not set +# CONFIG_LOG_BOOTLOADER_LEVEL_ERROR is not set +CONFIG_LOG_BOOTLOADER_LEVEL_WARN=y +# CONFIG_LOG_BOOTLOADER_LEVEL_INFO is not set +# CONFIG_LOG_BOOTLOADER_LEVEL_DEBUG is not set +# CONFIG_LOG_BOOTLOADER_LEVEL_VERBOSE is not set +CONFIG_LOG_BOOTLOADER_LEVEL=2 + +# +# Secure boot configuration +# +CONFIG_SECURE_BOOTLOADER_DISABLED=y +# CONFIG_SECURE_BOOTLOADER_ONE_TIME_FLASH is not set +# CONFIG_SECURE_BOOTLOADER_REFLASHABLE is not set +# CONFIG_SECURE_BOOTLOADER_ENABLED is not set + # # Serial flasher config # @@ -31,6 +50,12 @@ CONFIG_ESPTOOLPY_FLASHFREQ_40M=y # CONFIG_ESPTOOLPY_FLASHFREQ_26M is not set # CONFIG_ESPTOOLPY_FLASHFREQ_20M is not set CONFIG_ESPTOOLPY_FLASHFREQ="40m" +# CONFIG_ESPTOOLPY_FLASHSIZE_1MB is not set +CONFIG_ESPTOOLPY_FLASHSIZE_2MB=y +# CONFIG_ESPTOOLPY_FLASHSIZE_4MB is not set +# CONFIG_ESPTOOLPY_FLASHSIZE_8MB is not set +# CONFIG_ESPTOOLPY_FLASHSIZE_16MB is not set +CONFIG_ESPTOOLPY_FLASHSIZE="2MB" # # Partition Table @@ -42,10 +67,14 @@ CONFIG_PARTITION_TABLE_CUSTOM_FILENAME="partitions.csv" CONFIG_PARTITION_TABLE_CUSTOM_APP_BIN_OFFSET=0x10000 CONFIG_PARTITION_TABLE_FILENAME="partitions_singleapp.csv" CONFIG_APP_OFFSET=0x10000 +CONFIG_PHY_DATA_OFFSET=0xf000 +CONFIG_OPTIMIZATION_LEVEL_DEBUG=y +# CONFIG_OPTIMIZATION_LEVEL_RELEASE is not set # # Component config # +CONFIG_BT_RESERVE_DRAM=0 # # ESP32-specific config @@ -59,11 +88,30 @@ CONFIG_ESP32_DEFAULT_CPU_FREQ_MHZ=240 CONFIG_ESP32_ENABLE_STACK_NONE=y CONFIG_MEMMAP_SMP=y # CONFIG_MEMMAP_TRACEMEM is not set -# CONFIG_MEMMAP_SPISRAM is not set +CONFIG_TRACEMEM_RESERVE_DRAM=0x0 CONFIG_SYSTEM_EVENT_QUEUE_SIZE=32 CONFIG_SYSTEM_EVENT_TASK_STACK_SIZE=2048 CONFIG_MAIN_TASK_STACK_SIZE=4096 CONFIG_NEWLIB_STDOUT_ADDCR=y +# CONFIG_ULP_COPROC_ENABLED is not set +CONFIG_ULP_COPROC_RESERVE_MEM=0 +# CONFIG_ESP32_PANIC_PRINT_HALT is not set +CONFIG_ESP32_PANIC_PRINT_REBOOT=y +# CONFIG_ESP32_PANIC_SILENT_REBOOT is not set +# CONFIG_ESP32_PANIC_GDBSTUB is not set +CONFIG_ESP32_DEBUG_OCDAWARE=y +CONFIG_INT_WDT=y +CONFIG_INT_WDT_TIMEOUT_MS=300 +CONFIG_INT_WDT_CHECK_CPU1=y +# CONFIG_TASK_WDT is not set +# CONFIG_ESP32_TIME_SYSCALL_USE_RTC is not set +CONFIG_ESP32_TIME_SYSCALL_USE_RTC_FRC1=y +# CONFIG_ESP32_TIME_SYSCALL_USE_FRC1 is not set +# CONFIG_ESP32_TIME_SYSCALL_USE_NONE is not set +CONFIG_ESP32_RTC_CLOCK_SOURCE_INTERNAL_RC=y +CONFIG_ESP32_PHY_AUTO_INIT=y +# CONFIG_ESP32_PHY_INIT_DATA_IN_PARTITION is not set +CONFIG_ESP32_PHY_MAX_TX_POWER=20 # # FreeRTOS @@ -73,20 +121,18 @@ CONFIG_FREERTOS_CORETIMER_0=y # CONFIG_FREERTOS_CORETIMER_1 is not set # CONFIG_FREERTOS_CORETIMER_2 is not set CONFIG_FREERTOS_HZ=1000 +CONFIG_FREERTOS_ASSERT_ON_UNTESTED_FUNCTION=y # CONFIG_FREERTOS_CHECK_STACKOVERFLOW_NONE is not set # CONFIG_FREERTOS_CHECK_STACKOVERFLOW_PTRVAL is not set CONFIG_FREERTOS_CHECK_STACKOVERFLOW_CANARY=y CONFIG_FREERTOS_THREAD_LOCAL_STORAGE_POINTERS=3 -# CONFIG_FREERTOS_PANIC_PRINT_HALT is not set -CONFIG_FREERTOS_PANIC_PRINT_REBOOT=y -# CONFIG_FREERTOS_PANIC_SILENT_REBOOT is not set -# CONFIG_FREERTOS_PANIC_GDBSTUB is not set -CONFIG_FREERTOS_DEBUG_OCDAWARE=y CONFIG_FREERTOS_ASSERT_FAIL_ABORT=y # CONFIG_FREERTOS_ASSERT_FAIL_PRINT_CONTINUE is not set # CONFIG_FREERTOS_ASSERT_DISABLE is not set CONFIG_FREERTOS_BREAK_ON_SCHEDULER_START_JTAG=y # CONFIG_ENABLE_MEMORY_DEBUG is not set +CONFIG_FREERTOS_ISR_STACKSIZE=1536 +# CONFIG_FREERTOS_LEGACY_HOOKS is not set # CONFIG_FREERTOS_DEBUG_INTERNALS is not set # @@ -104,22 +150,24 @@ CONFIG_LOG_COLORS=y # # LWIP # +# CONFIG_L2_TO_L3_COPY is not set CONFIG_LWIP_MAX_SOCKETS=4 CONFIG_LWIP_THREAD_LOCAL_STORAGE_INDEX=0 # CONFIG_LWIP_SO_REUSE is not set +CONFIG_LWIP_DHCP_MAX_NTP_SERVERS=1 # # mbedTLS # CONFIG_MBEDTLS_SSL_MAX_CONTENT_LEN=16384 # CONFIG_MBEDTLS_DEBUG is not set +CONFIG_MBEDTLS_HARDWARE_AES=y +CONFIG_MBEDTLS_HARDWARE_MPI=y +CONFIG_MBEDTLS_MPI_USE_INTERRUPT=y +CONFIG_MBEDTLS_MPI_INTERRUPT_NUM=18 +CONFIG_MBEDTLS_HARDWARE_SHA=y # # SPI Flash driver # # CONFIG_SPI_FLASH_ENABLE_COUNTERS is not set - -# -# TESTS -# -CONFIG_FP_TEST_ENABLE=y