diff --git a/include/timespec.h b/include/timespec.h index 3977477..c612340 100644 --- a/include/timespec.h +++ b/include/timespec.h @@ -43,5 +43,7 @@ struct mgos_timespec; struct mgos_timespec *timespec_create(); bool timespec_destroy(struct mgos_timespec **ts); bool timespec_add_spec(struct mgos_timespec *ts, const char *spec); +bool timespec_clear_spec(struct mgos_timespec *ts); +bool timespec_get_spec(struct mgos_timespec *ts, char *ret, int retlen); bool timespec_match(const struct mgos_timespec *ts, const struct tm *tm); bool timespec_match_now(const struct mgos_timespec *ts); diff --git a/src/timespec.c b/src/timespec.c index b3dc196..953b15a 100644 --- a/src/timespec.c +++ b/src/timespec.c @@ -124,17 +124,7 @@ bool timespec_destroy(struct mgos_timespec **ts) { if (!ts) { return false; } - while (!SLIST_EMPTY(&(*ts)->specs)) { - struct mgos_timespec_spec *t_spec; - - t_spec = SLIST_FIRST(&(*ts)->specs); - SLIST_REMOVE_HEAD(&(*ts)->specs, entries); - if (t_spec) { -// LOG(LL_DEBUG, ("Removed mgos_timespec_spec")); - free(t_spec); - } - } - + timespec_clear_spec(*ts); free(*ts); *ts = NULL; return true; @@ -206,3 +196,57 @@ bool timespec_match_now(const struct mgos_timespec *ts) { } return timespec_match(ts, tm); } + +// Clear the timespec linked list +// Returns true on success, false otherwise. +bool timespec_clear_spec(struct mgos_timespec *ts) { + if (!ts) { + return false; + } + while (!SLIST_EMPTY(&ts->specs)) { + struct mgos_timespec_spec *t_spec; + + t_spec = SLIST_FIRST(&ts->specs); + SLIST_REMOVE_HEAD(&ts->specs, entries); + if (t_spec) { + free(t_spec); + } + } + + return true; +} + +// Return a null terminated string in 'ret' of max retlen-1 which is a +// comma separated set of timespec elements from the linked list. +// Returns true on success, false otherwise. +bool timespec_get_spec(struct mgos_timespec *ts, char *ret, int retlen) { + struct mgos_timespec_spec *t_spec; + + if (!ts) { + return false; + } + + if (!ts) { + return false; + } + + if (!ret) { + return false; + } + *ret = '\0'; + + SLIST_FOREACH(t_spec, &ts->specs, entries) { + char spec_str[20]; + + snprintf(spec_str, sizeof(spec_str) - 1, "%02d:%02d:%02d-%02d:%02d:%02d", t_spec->start_h, t_spec->start_m, t_spec->start_s, + t_spec->stop_h, t_spec->stop_m, t_spec->stop_s); + if (strlen(spec_str) + strlen(ret) > retlen - 1) { + return false; + } + if (strlen(ret) > 0) { + strncat(ret, ",", retlen); + } + strncat(ret, spec_str, retlen); + } + return true; +} diff --git a/unittest/test_timespec.c b/unittest/test_timespec.c index f452b55..7a77fdb 100644 --- a/unittest/test_timespec.c +++ b/unittest/test_timespec.c @@ -88,8 +88,12 @@ static void test_timespec_flips_and_seconds(const struct mgos_timespec *ts, cons static void test_timespec_state(void) { struct mgos_timespec *ts = timespec_create(); struct tm target; + char buf[500]; ASSERT(ts, "Created timespec"); + timespec_get_spec(ts, buf, sizeof(buf)-1); + ASSERT(0 == strcmp(buf, ""), "timespec_get_spec() didn't match input spec(s)"); + ASSERT(timespec_add_spec(ts, "08-10"), "Added timespec"); ASSERT(timespec_add_spec(ts, "12:00-13:00"), "Added timespec"); ASSERT(timespec_add_spec(ts, "14:11:05-14:59:52"), "Added timespec"); @@ -150,6 +154,11 @@ static void test_timespec_state(void) { target.tm_sec = 3; target.tm_min = 2; target.tm_hour = 1; ASSERT(!timespec_match(ts, &target), "No match at 01:02:03"); + // Test timespec retrieval + timespec_get_spec(ts, buf, sizeof(buf)-1); + ASSERT(0 == strcmp(buf, "23:01:02-01:02:03,14:11:05-14:59:52,12:00:00-13:00:00,08:00:00-10:00:00"), "timespec_get_spec() didn't match input spec(s)"); + LOG(LL_INFO, ("Spec: '%s'", buf)); + ASSERT(timespec_destroy(&ts), "Destroyed timespec"); // Some time counting tests @@ -174,6 +183,10 @@ static void test_timespec_state(void) { ASSERT(timespec_add_spec(ts, "03:02:03-04:03:04"), "Added timespec"); test_timespec_flips_and_seconds(ts, 9, 7200 + 0 + 7200 + 1 + 3661); + // Test timespec retrieval + timespec_get_spec(ts, buf, sizeof(buf)-1); + ASSERT(0 == strcmp(buf, "03:02:03-04:03:04,02:00:00-02:00:01,23:00:00-01:00:00,00:00:00-00:00:00,08:00:00-10:00:00"), "timespec_get_spec() didn't match input spec(s)"); + ASSERT(timespec_destroy(&ts), "Destroyed timespec"); // Some other time counting tests @@ -184,6 +197,10 @@ static void test_timespec_state(void) { ASSERT(timespec_add_spec(ts, "12-00"), "Added timespec"); test_timespec_flips_and_seconds(ts, 1, 24 * 60 * 60); + // Test timespec retrieval + timespec_get_spec(ts, buf, sizeof(buf)-1); + ASSERT(0 == strcmp(buf, "12:00:00-00:00:00,00:00:00-12:00:00"), "timespec_get_spec() didn't match input spec(s)"); + ASSERT(timespec_destroy(&ts), "Destroyed timespec"); }