| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501 |
- /*
- * SPDX-FileCopyrightText: 2022 Espressif Systems (Shanghai) CO LTD
- *
- * SPDX-License-Identifier: Apache-2.0
- */
- #include <stdio.h>
- #include "sdkconfig.h"
- #include "freertos/FreeRTOS.h"
- #include "freertos/task.h"
- #include "unity.h"
- #include "driver/gptimer.h"
- #include "soc/soc_caps.h"
- #include "esp_attr.h"
- #if CONFIG_GPTIMER_ISR_IRAM_SAFE
- #define TEST_ALARM_CALLBACK_ATTR IRAM_ATTR
- #else
- #define TEST_ALARM_CALLBACK_ATTR
- #endif // CONFIG_GPTIMER_ISR_IRAM_SAFE
- TEST_CASE("gptimer_set_get_raw_count", "[gptimer]")
- {
- gptimer_config_t config = {
- .clk_src = GPTIMER_CLK_SRC_DEFAULT,
- .direction = GPTIMER_COUNT_UP,
- .resolution_hz = 1 * 1000 * 1000,
- };
- gptimer_handle_t timers[SOC_TIMER_GROUP_TOTAL_TIMERS];
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_new_timer(&config, &timers[i]));
- }
- TEST_ASSERT_EQUAL(ESP_ERR_NOT_FOUND, gptimer_new_timer(&config, &timers[0]));
- unsigned long long get_value = 0;
- printf("check gptimer initial count value\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_get_raw_count(timers[i], &get_value));
- TEST_ASSERT_EQUAL(0, get_value);
- }
- unsigned long long set_values[] = {100, 500, 666};
- for (size_t j = 0; j < sizeof(set_values) / sizeof(set_values[0]); j++) {
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- printf("set raw count to %llu for gptimer %d\r\n", set_values[j], i);
- TEST_ESP_OK(gptimer_set_raw_count(timers[i], set_values[j]));
- }
- vTaskDelay(pdMS_TO_TICKS(10));
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_get_raw_count(timers[i], &get_value));
- printf("get raw count of gptimer %d: %llu\r\n", i, get_value);
- TEST_ASSERT_EQUAL(set_values[j], get_value);
- }
- }
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_del_timer(timers[i]));
- }
- }
- TEST_CASE("gptimer_wallclock_with_various_clock_sources", "[gptimer]")
- {
- gptimer_clock_source_t test_clk_srcs[] = SOC_GPTIMER_CLKS;
- // test with various clock sources
- for (size_t i = 0; i < sizeof(test_clk_srcs) / sizeof(test_clk_srcs[0]); i++) {
- gptimer_config_t timer_config = {
- .clk_src = test_clk_srcs[i],
- .direction = GPTIMER_COUNT_UP,
- .resolution_hz = 1 * 1000 * 1000,
- };
- gptimer_handle_t timers[SOC_TIMER_GROUP_TOTAL_TIMERS];
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_new_timer(&timer_config, &timers[i]));
- }
- // start timer before enable should fail
- TEST_ESP_ERR(ESP_ERR_INVALID_STATE, gptimer_start(timers[0]));
- printf("enable timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_enable(timers[i]));
- }
- printf("start timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_start(timers[i]));
- }
- vTaskDelay(pdMS_TO_TICKS(20)); // 20ms = 20_000 ticks
- unsigned long long value = 0;
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_get_raw_count(timers[i], &value));
- TEST_ASSERT_UINT_WITHIN(1000, 20000, value);
- }
- printf("stop timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_stop(timers[i]));
- }
- printf("check whether timers have stopped\r\n");
- vTaskDelay(pdMS_TO_TICKS(20));
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_get_raw_count(timers[i], &value));
- printf("get raw count of gptimer %d: %llu\r\n", i, value);
- TEST_ASSERT_UINT_WITHIN(1000, 20000, value);
- }
- printf("restart timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_start(timers[i]));
- }
- vTaskDelay(pdMS_TO_TICKS(20));
- printf("stop timers again\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_stop(timers[i]));
- }
- printf("check whether timers have stopped\r\n");
- vTaskDelay(pdMS_TO_TICKS(20));
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_get_raw_count(timers[i], &value));
- printf("get raw count of gptimer %d: %llu\r\n", i, value);
- TEST_ASSERT_UINT_WITHIN(2000, 40000, value);
- }
- printf("disable timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_disable(timers[i]));
- }
- printf("delete timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_del_timer(timers[i]));
- }
- }
- }
- TEST_ALARM_CALLBACK_ATTR static bool test_gptimer_alarm_stop_callback(gptimer_handle_t timer, const gptimer_alarm_event_data_t *edata, void *user_data)
- {
- TaskHandle_t task_handle = (TaskHandle_t)user_data;
- BaseType_t high_task_wakeup;
- gptimer_stop(timer);
- esp_rom_printf("count=%lld @alarm\n", edata->count_value);
- vTaskNotifyGiveFromISR(task_handle, &high_task_wakeup);
- return high_task_wakeup == pdTRUE;
- }
- TEST_CASE("gptimer_stop_on_alarm", "[gptimer]")
- {
- TaskHandle_t task_handle = xTaskGetCurrentTaskHandle();
- gptimer_config_t timer_config = {
- .resolution_hz = 1 * 1000 * 1000,
- .clk_src = GPTIMER_CLK_SRC_DEFAULT,
- .direction = GPTIMER_COUNT_UP,
- };
- gptimer_handle_t timers[SOC_TIMER_GROUP_TOTAL_TIMERS];
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_new_timer(&timer_config, &timers[i]));
- }
- gptimer_event_callbacks_t cbs = {
- .on_alarm = test_gptimer_alarm_stop_callback,
- };
- gptimer_alarm_config_t alarm_config = {};
- printf("start timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- alarm_config.alarm_count = 100000 * (i + 1);
- TEST_ESP_OK(gptimer_set_alarm_action(timers[i], &alarm_config));
- TEST_ESP_OK(gptimer_register_event_callbacks(timers[i], &cbs, task_handle));
- TEST_ESP_OK(gptimer_enable(timers[i]));
- TEST_ESP_OK(gptimer_start(timers[i]));
- printf("alarm value for gptimer %d: %llu\r\n", i, alarm_config.alarm_count);
- }
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(1000)));
- }
- printf("check whether the timers have stopped in the ISR\r\n");
- vTaskDelay(pdMS_TO_TICKS(20));
- unsigned long long value = 0;
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_get_raw_count(timers[i], &value));
- printf("get raw count of gptimer %d: %llu\r\n", i, value);
- TEST_ASSERT_UINT_WITHIN(40, 100000 * (i + 1), value);
- }
- printf("restart timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- alarm_config.alarm_count = 100000 * (i + 1);
- // reset counter value to zero
- TEST_ESP_OK(gptimer_set_raw_count(timers[i], 0));
- TEST_ESP_OK(gptimer_start(timers[i]));
- }
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(1000)));
- }
- printf("check whether the timers have stopped in the ISR\r\n");
- vTaskDelay(pdMS_TO_TICKS(20));
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_get_raw_count(timers[i], &value));
- printf("get raw count of gptimer %d: %llu\r\n", i, value);
- TEST_ASSERT_UINT_WITHIN(40, 100000 * (i + 1), value);
- }
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_disable(timers[i]));
- TEST_ESP_OK(gptimer_del_timer(timers[i]));
- }
- }
- TEST_ALARM_CALLBACK_ATTR static bool test_gptimer_alarm_reload_callback(gptimer_handle_t timer, const gptimer_alarm_event_data_t *edata, void *user_data)
- {
- TaskHandle_t task_handle = (TaskHandle_t)user_data;
- BaseType_t high_task_wakeup;
- esp_rom_printf("alarm isr count=%llu\r\n", edata->count_value);
- // check if the count value has been reloaded
- TEST_ASSERT_UINT_WITHIN(20, 100, edata->count_value);
- vTaskNotifyGiveFromISR(task_handle, &high_task_wakeup);
- return high_task_wakeup == pdTRUE;
- }
- TEST_CASE("gptimer_auto_reload_on_alarm", "[gptimer]")
- {
- TaskHandle_t task_handle = xTaskGetCurrentTaskHandle();
- gptimer_config_t timer_config = {
- .resolution_hz = 1 * 1000 * 1000,
- .clk_src = GPTIMER_CLK_SRC_DEFAULT,
- .direction = GPTIMER_COUNT_UP,
- };
- gptimer_handle_t timers[SOC_TIMER_GROUP_TOTAL_TIMERS];
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_new_timer(&timer_config, &timers[i]));
- }
- gptimer_event_callbacks_t cbs = {
- .on_alarm = test_gptimer_alarm_reload_callback,
- };
- gptimer_alarm_config_t alarm_config = {
- .reload_count = 100,
- .alarm_count = 100000,
- .flags.auto_reload_on_alarm = true,
- };
- printf("start timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_set_alarm_action(timers[i], &alarm_config));
- TEST_ESP_OK(gptimer_register_event_callbacks(timers[i], &cbs, task_handle));
- TEST_ESP_OK(gptimer_enable(timers[i]));
- TEST_ESP_OK(gptimer_start(timers[i]));
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(1000)));
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(1000)));
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(1000)));
- // delete should fail if timer is not disabled
- TEST_ESP_ERR(ESP_ERR_INVALID_STATE, gptimer_del_timer(timers[i]));
- TEST_ESP_OK(gptimer_stop(timers[i]));
- }
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_disable(timers[i]));
- TEST_ESP_OK(gptimer_del_timer(timers[i]));
- }
- }
- TEST_ALARM_CALLBACK_ATTR static bool test_gptimer_alarm_normal_callback(gptimer_handle_t timer, const gptimer_alarm_event_data_t *edata, void *user_data)
- {
- TaskHandle_t task_handle = (TaskHandle_t)user_data;
- BaseType_t high_task_wakeup;
- esp_rom_printf("alarm isr count=%llu\r\n", edata->count_value);
- // check the count value at alarm event
- vTaskNotifyGiveFromISR(task_handle, &high_task_wakeup);
- return high_task_wakeup == pdTRUE;
- }
- TEST_CASE("gptimer_one_shot_alarm", "[gptimer]")
- {
- TaskHandle_t task_handle = xTaskGetCurrentTaskHandle();
- gptimer_config_t timer_config = {
- .resolution_hz = 1 * 1000 * 1000,
- .clk_src = GPTIMER_CLK_SRC_DEFAULT,
- .direction = GPTIMER_COUNT_UP,
- };
- gptimer_handle_t timers[SOC_TIMER_GROUP_TOTAL_TIMERS];
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_new_timer(&timer_config, &timers[i]));
- }
- gptimer_event_callbacks_t cbs = {
- .on_alarm = test_gptimer_alarm_normal_callback,
- };
- gptimer_alarm_config_t alarm_config = {
- .reload_count = 0,
- .alarm_count = 100000, // 100ms
- };
- printf("start timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_set_alarm_action(timers[i], &alarm_config));
- TEST_ESP_OK(gptimer_register_event_callbacks(timers[i], &cbs, task_handle));
- TEST_ESP_OK(gptimer_enable(timers[i]));
- TEST_ESP_OK(gptimer_start(timers[i]));
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(1000)));
- // no alarm event should trigger again, as auto-reload is not enabled and alarm value hasn't changed in the isr
- TEST_ASSERT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(1000)));
- // the alarm is stopped, but the counter should still work
- uint64_t value = 0;
- TEST_ESP_OK(gptimer_get_raw_count(timers[i], &value));
- TEST_ASSERT_UINT_WITHIN(1000, 1100000, value); // 1100000 = 100ms alarm + 1s delay
- TEST_ESP_OK(gptimer_stop(timers[i]));
- }
- printf("restart timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_start(timers[i]));
- // alarm should be triggered immediately as the counter value has across the target alarm value already
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, 0));
- TEST_ESP_OK(gptimer_stop(timers[i]));
- }
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_disable(timers[i]));
- TEST_ESP_OK(gptimer_del_timer(timers[i]));
- }
- }
- TEST_ALARM_CALLBACK_ATTR static bool test_gptimer_alarm_update_callback(gptimer_handle_t timer, const gptimer_alarm_event_data_t *edata, void *user_data)
- {
- TaskHandle_t task_handle = (TaskHandle_t)user_data;
- BaseType_t high_task_wakeup;
- esp_rom_printf("alarm isr count=%llu\r\n", edata->count_value);
- gptimer_alarm_config_t alarm_config = {
- .alarm_count = edata->count_value + 100000, // alarm in next 100ms again
- };
- gptimer_set_alarm_action(timer, &alarm_config);
- vTaskNotifyGiveFromISR(task_handle, &high_task_wakeup);
- return high_task_wakeup == pdTRUE;
- }
- TEST_CASE("gptimer_update_alarm_dynamically", "[gptimer]")
- {
- TaskHandle_t task_handle = xTaskGetCurrentTaskHandle();
- gptimer_config_t timer_config = {
- .resolution_hz = 1 * 1000 * 1000,
- .clk_src = GPTIMER_CLK_SRC_DEFAULT,
- .direction = GPTIMER_COUNT_UP,
- };
- gptimer_handle_t timers[SOC_TIMER_GROUP_TOTAL_TIMERS];
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_new_timer(&timer_config, &timers[i]));
- }
- gptimer_event_callbacks_t cbs = {
- .on_alarm = test_gptimer_alarm_update_callback,
- };
- gptimer_alarm_config_t alarm_config = {
- .alarm_count = 100000, // initial alarm count, 100ms
- };
- printf("start timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_set_alarm_action(timers[i], &alarm_config));
- TEST_ESP_OK(gptimer_register_event_callbacks(timers[i], &cbs, task_handle));
- TEST_ESP_OK(gptimer_enable(timers[i]));
- TEST_ESP_OK(gptimer_start(timers[i]));
- // check the alarm event for multiple times
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(500)));
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(500)));
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(500)));
- TEST_ESP_OK(gptimer_stop(timers[i]));
- // check there won't be more interrupts triggered than expected
- TEST_ASSERT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(500)));
- }
- printf("restart timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_start(timers[i]));
- // check the alarm event for multiple times
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(500)));
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(500)));
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(500)));
- TEST_ESP_OK(gptimer_stop(timers[i]));
- // check there won't be more interrupts triggered than expected
- TEST_ASSERT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(500)));
- }
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_disable(timers[i]));
- TEST_ESP_OK(gptimer_del_timer(timers[i]));
- }
- }
- TEST_ALARM_CALLBACK_ATTR static bool test_gptimer_count_down_reload_alarm_callback(gptimer_handle_t timer, const gptimer_alarm_event_data_t *edata, void *user_data)
- {
- TaskHandle_t task_handle = (TaskHandle_t)user_data;
- BaseType_t high_task_wakeup;
- esp_rom_printf("alarm isr count=%llu\r\n", edata->count_value);
- // check if the count value has been reloaded
- TEST_ASSERT_UINT_WITHIN(20, 200000, edata->count_value);
- vTaskNotifyGiveFromISR(task_handle, &high_task_wakeup);
- return high_task_wakeup == pdTRUE;
- }
- TEST_CASE("gptimer_count_down_reload", "[gptimer]")
- {
- TaskHandle_t task_handle = xTaskGetCurrentTaskHandle();
- gptimer_config_t timer_config = {
- .resolution_hz = 1 * 1000 * 1000,
- .clk_src = GPTIMER_CLK_SRC_DEFAULT,
- .direction = GPTIMER_COUNT_DOWN,
- };
- gptimer_handle_t timers[SOC_TIMER_GROUP_TOTAL_TIMERS];
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_new_timer(&timer_config, &timers[i]));
- TEST_ESP_OK(gptimer_set_raw_count(timers[i], 200000));
- }
- gptimer_event_callbacks_t cbs = {
- .on_alarm = test_gptimer_count_down_reload_alarm_callback,
- };
- gptimer_alarm_config_t alarm_config = {
- .reload_count = 200000, // 200ms
- .alarm_count = 0,
- .flags.auto_reload_on_alarm = true,
- };
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_set_alarm_action(timers[i], &alarm_config));
- TEST_ESP_OK(gptimer_register_event_callbacks(timers[i], &cbs, task_handle));
- TEST_ESP_OK(gptimer_enable(timers[i]));
- TEST_ESP_OK(gptimer_start(timers[i]));
- // check twice, as it's a period event
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(1000)));
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(1000)));
- TEST_ESP_OK(gptimer_stop(timers[i]));
- }
- printf("restart gptimer with previous configuration\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_start(timers[i]));
- // check twice, as it's a period event
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(1000)));
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(1000)));
- TEST_ESP_OK(gptimer_stop(timers[i]));
- }
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_disable(timers[i]));
- TEST_ESP_OK(gptimer_del_timer(timers[i]));
- }
- }
- TEST_ALARM_CALLBACK_ATTR static bool test_gptimer_overflow_reload_callback(gptimer_handle_t timer, const gptimer_alarm_event_data_t *edata, void *user_data)
- {
- TaskHandle_t task_handle = (TaskHandle_t)user_data;
- BaseType_t high_task_wakeup;
- // Note: esp_rom_printf can't print value with 64 bit length, so the following print result is meaningless, but as an incidator for test that the alarm has fired
- esp_rom_printf("alarm isr count=%llu\r\n", edata->count_value);
- vTaskNotifyGiveFromISR(task_handle, &high_task_wakeup);
- return high_task_wakeup == pdTRUE;
- }
- TEST_CASE("gptimer_overflow", "[gptimer]")
- {
- TaskHandle_t task_handle = xTaskGetCurrentTaskHandle();
- gptimer_config_t timer_config = {
- .resolution_hz = 1 * 1000 * 1000,
- .clk_src = GPTIMER_CLK_SRC_DEFAULT,
- .direction = GPTIMER_COUNT_UP,
- };
- gptimer_handle_t timers[SOC_TIMER_GROUP_TOTAL_TIMERS];
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_new_timer(&timer_config, &timers[i]));
- }
- #if SOC_TIMER_GROUP_COUNTER_BIT_WIDTH == 64
- uint64_t reload_at = UINT64_MAX - 100000;
- #else
- uint64_t reload_at = (1ULL << SOC_TIMER_GROUP_COUNTER_BIT_WIDTH) - 100000;
- #endif
- gptimer_event_callbacks_t cbs = {
- .on_alarm = test_gptimer_overflow_reload_callback,
- };
- gptimer_alarm_config_t alarm_config = {
- .reload_count = reload_at,
- .alarm_count = 100000, // 100ms
- .flags.auto_reload_on_alarm = true,
- };
- // The counter should start from [COUNTER_MAX-100000] and overflows to [0] and continue, then reached to alarm value [100000], reloaded to [COUNTER_MAX-100000] automatically
- // thus the period should be 200ms
- printf("start timers\r\n");
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_set_alarm_action(timers[i], &alarm_config));
- TEST_ESP_OK(gptimer_register_event_callbacks(timers[i], &cbs, task_handle));
- // we start from the reload value
- TEST_ESP_OK(gptimer_set_raw_count(timers[i], reload_at));
- TEST_ESP_OK(gptimer_enable(timers[i]));
- TEST_ESP_OK(gptimer_start(timers[i]));
- TEST_ASSERT_NOT_EQUAL(0, ulTaskNotifyTake(pdFALSE, pdMS_TO_TICKS(400)));
- TEST_ESP_OK(gptimer_stop(timers[i]));
- }
- for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) {
- TEST_ESP_OK(gptimer_disable(timers[i]));
- TEST_ESP_OK(gptimer_del_timer(timers[i]));
- }
- }
|