/* Time Keeping Bugs Abound! */
+#define _POSIX_C_SOURCE 200112L
+
#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
#include <time.h>
+#include "util.h"
+#include "conf.h"
#include "date.h"
/* Global data */
/* Initialize */
void date_init(void)
{
- time_t sec = time(NULL);
- struct tm *tm = localtime(&sec);
+ /* Sync current time */
+ NOW = get_date(0);
- SEL.year = tm->tm_year+1900;
- SEL.month = tm->tm_mon;
- SEL.day = tm->tm_mday-1;
+ /* Sync selection */
+ SEL.year = NOW.year;
+ SEL.month = NOW.month;
+ SEL.day = NOW.day;
+}
- date_sync();
+void date_config(const char *group, const char *name, const char *key, const char *value)
+{
+ if (match(group, "date") && match(key, "timezone") && value)
+ setenv("TZ", get_string(value), 1);
}
void date_sync(void)
{
- time_t sec = time(NULL);
- struct tm *tm = localtime(&sec);
-
- NOW.year = tm->tm_year+1900;
- NOW.month = tm->tm_mon;
- NOW.day = tm->tm_mday-1;
- NOW.hour = tm->tm_hour;
- NOW.min = tm->tm_min;
- NOW.sec = tm->tm_sec;
+ NOW = get_date(0);
}
/* Time functions */
void add_days(year_t *year, month_t *month, day_t *day, int days)
{
- time_t time = mktime(&(struct tm){
- .tm_year = *year-1900,
- .tm_mon = *month,
- .tm_mday = *day+1,
- .tm_hour = 12});
- time += days*24*60*60;
- struct tm *tm = localtime(&time);
- *year = tm->tm_year+1900;
- *month = tm->tm_mon;
- *day = tm->tm_mday-1;
+ date_t date = {
+ .year = *year,
+ .month = *month,
+ .day = *day,
+ .hour = 12
+ };
+ stamp_t stamp = get_stamp(date);
+ date_t then = get_date(stamp + days*24*60*60);
+ *year = then.year;
+ *month = then.month;
+ *day = then.day;
}
void add_months(year_t *year, month_t *month, int months)
*month = total % 12;
}
-stamp_t get_time(date_t *date)
+/* Date functions */
+date_t get_date(stamp_t stamp)
+{
+ time_t t = stamp ? stamp : time(NULL);
+ struct tm *tm = localtime(&t);
+ date_t date = {
+ .year = tm->tm_year+1900,
+ .month = tm->tm_mon,
+ .day = tm->tm_mday-1,
+ .hour = tm->tm_hour,
+ .min = tm->tm_min,
+ .sec = tm->tm_sec,
+ };
+ return date;
+}
+
+stamp_t get_stamp(date_t date)
{
- return mktime(&(struct tm){
- .tm_year = date->year-1900,
- .tm_mon = date->month,
- .tm_mday = date->day+1,
- .tm_hour = date->hour,
- .tm_min = date->min});
+ struct tm tm = {
+ .tm_year = date.year-1900,
+ .tm_mon = date.month,
+ .tm_mday = date.day+1,
+ .tm_hour = date.hour,
+ .tm_min = date.min,
+ .tm_sec = date.sec,
+ };
+ time_t t = mktime(&tm);
+ return (stamp_t)t;
}
int get_mins(date_t *start, date_t *end)
{
- return (get_time(end)-get_time(start))/60;
+ return (get_stamp(*end)-get_stamp(*start))/60;
}
int compare(date_t *a, date_t *b)
/* Test functions */
void date_test(void)
{
+ setenv("TZ", "US/Central", 1);
+
+ time_t timet = time(NULL);
+ date_t date = get_date(timet);
+ stamp_t stamp = get_stamp(date);
+
+ printf("Time\n");
+ printf(" time %ld\n", timet);
+ printf(" stamp %lld\n", stamp);
+ printf(" date %04d-%02d-%02d %02d:%02d %02ds\n",
+ date.year, date.month, date.day,
+ date.hour, date.min, date.sec);
+
printf("Info\n");
printf(" Year Month Start Weeks Days\n");
for (int y = 2012; y <= 2012; y++)