nopnop2002 / esp-idf-ds3231

DS3231 RTC Driver for esp-idf
29 stars 11 forks source link

Add alarm and interrupt related functions #6

Closed martinberlin closed 1 year ago

martinberlin commented 2 years ago

Hello @nopnop2002

Very glad to find your DS3231 fork which I'm using in an epaper weather station project.

Since I implemented a way to sleep in the night, to save battery, I though about using the RTC alarm functions so I avoid waking up every 10 minutes and compare time.

This is easy to test, just added the set alart in the getClock, and then in main a loop to check the IO state. In my S3 board design INT pin is pulled up with a 10K res and going to IO6:

void getClock(void *pvParameters)
{
    i2c_dev_t dev;
    if (ds3231_init_desc(&dev, I2C_NUM_0, CONFIG_SDA_GPIO, CONFIG_SCL_GPIO) != ESP_OK) {
        ESP_LOGE(pcTaskGetName(0), "Could not init device descriptor.");
        while (1) { vTaskDelay(1); }
    }
    TickType_t xLastWakeTime = xTaskGetTickCount();
        float temp;
        struct tm rtcinfo;

        if (ds3231_get_temp_float(&dev, &temp) != ESP_OK) {
            ESP_LOGE(pcTaskGetName(0), "Could not get temperature.");
            while (1) { vTaskDelay(1); }
        }

        if (ds3231_get_time(&dev, &rtcinfo) != ESP_OK) {
            ESP_LOGE(pcTaskGetName(0), "Could not get time.");
            while (1) { vTaskDelay(1); }
        }

        rtcinfo.tm_min += 1;
        // Set a test alarm
        ds3231_clear_alarm_flags(&dev, DS3231_ALARM_2);
        ds3231_set_alarm(&dev, DS3231_ALARM_2, &rtcinfo, 0,  &rtcinfo, DS3231_ALARM2_MATCH_MINHOUR);
        ds3231_enable_alarm_ints(&dev, DS3231_ALARM_2);

        ESP_LOGI(pcTaskGetName(0), "%04d-%02d-%02d %02d:%02d:%02d, %.2f deg Cel", 
            rtcinfo.tm_year, rtcinfo.tm_mon + 1,
            rtcinfo.tm_mday, rtcinfo.tm_hour, rtcinfo.tm_min, rtcinfo.tm_sec, temp);
    while (1) {
    vTaskDelayUntil(&xLastWakeTime, 1000);
    }
}

void app_main()
{
    gpio_set_direction(GPIO_RTC_INT, GPIO_MODE_INPUT);
    xTaskCreate(getClock, "getClock", 1024*4, NULL, 2, NULL);
    while (true) {
        // Read GPIO state
        if ( gpio_get_level(GPIO_RTC_INT) == 0) {
            ESP_LOGI(TAG, "RTC alarm trigered: %d", gpio_get_level(GPIO_RTC_INT));

        } else {
            ESP_LOGI(TAG, "IO6: %d", gpio_get_level(GPIO_RTC_INT));
        }

        vTaskDelay(1000 / portTICK_PERIOD_MS);
    }
}
}

Additionally adding some extern C wrappers only for C++

If you think it's a nice addition please merge it. Thanks

nopnop2002 commented 2 years ago

Your sample code would place better here.

https://github.com/UncleRus/esp-idf-lib/tree/master/examples

void getClock(void *pvParameters)
{
    i2c_dev_t dev;
    if (ds3231_init_desc(&dev, I2C_NUM_0, CONFIG_SDA_GPIO, CONFIG_SCL_GPIO) != ESP_OK) {
        ESP_LOGE(pcTaskGetName(0), "Could not init device descriptor.");
        while (1) { vTaskDelay(1); }
    }
    TickType_t xLastWakeTime = xTaskGetTickCount();
        float temp;
        struct tm rtcinfo;

        if (ds3231_get_temp_float(&dev, &temp) != ESP_OK) {
            ESP_LOGE(pcTaskGetName(0), "Could not get temperature.");
            while (1) { vTaskDelay(1); }
        }

        if (ds3231_get_time(&dev, &rtcinfo) != ESP_OK) {
            ESP_LOGE(pcTaskGetName(0), "Could not get time.");
            while (1) { vTaskDelay(1); }
        }

        rtcinfo.tm_min += 1;
        // Set a test alarm
        ds3231_clear_alarm_flags(&dev, DS3231_ALARM_2);
        ds3231_set_alarm(&dev, DS3231_ALARM_2, &rtcinfo, 0,  &rtcinfo, DS3231_ALARM2_MATCH_MINHOUR);
        ds3231_enable_alarm_ints(&dev, DS3231_ALARM_2);

        ESP_LOGI(pcTaskGetName(0), "%04d-%02d-%02d %02d:%02d:%02d, %.2f deg Cel", 
            rtcinfo.tm_year, rtcinfo.tm_mon + 1,
            rtcinfo.tm_mday, rtcinfo.tm_hour, rtcinfo.tm_min, rtcinfo.tm_sec, temp);
    while (1) {
    vTaskDelayUntil(&xLastWakeTime, 1000);
    }
}

void app_main()
{
    gpio_set_direction(GPIO_RTC_INT, GPIO_MODE_INPUT);
    xTaskCreate(getClock, "getClock", 1024*4, NULL, 2, NULL);
    while (true) {
        // Read GPIO state
        if ( gpio_get_level(GPIO_RTC_INT) == 0) {
            ESP_LOGI(TAG, "RTC alarm trigered: %d", gpio_get_level(GPIO_RTC_INT));

        } else {
            ESP_LOGI(TAG, "IO6: %d", gpio_get_level(GPIO_RTC_INT));
        }

        vTaskDelay(1000 / portTICK_PERIOD_MS);
    }
}
}
nopnop2002 commented 1 year ago

ds3231.c and ds3231.h are not my original.

ds3231.c and ds3231.h are forked from here.

https://github.com/UncleRus/esp-idf-lib/tree/master/components/ds3231

Your enhance would place better here.

https://github.com/UncleRus/esp-idf-lib/issues

martinberlin commented 1 year ago

Thanks closing this one