From 25e6afd831b94b9735cc6691ee19c8edc921aca7 Mon Sep 17 00:00:00 2001 From: root Date: Sun, 8 Apr 2018 01:14:30 +0100 Subject: working decoding --- app/time_fn.c | 225 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 225 insertions(+) create mode 100644 app/time_fn.c (limited to 'app/time_fn.c') diff --git a/app/time_fn.c b/app/time_fn.c new file mode 100644 index 0000000..5636ef1 --- /dev/null +++ b/app/time_fn.c @@ -0,0 +1,225 @@ +#include "project.h" + +static int is_leap (unsigned year) +{ + if (year % 4) + return 0; + + if (year % 100) + return 1; + + if (year % 400) + return 0; + + return 1; +} + + +UTC time_epoch_to_utc (EPOCH epoch) +{ + UTC u; + uint64_t day; + unsigned y400, y100, y4; + + day = epoch.s / 86400; + epoch.s -= day * 86400; + + day += 134774; + + u.wday = day % 7; + u.wday++; + + + y400 = day / 146097; /*146097 days in 400 years */ + day -= (y400 * 146097); + + y100 = day / 36524; /*36524 days in 100 years */ + day -= (y100 * 36524); + + y4 = day / 1461; /*1461 days in 4 years */ + day -= (y4 * 1461); + + /* This may look redundant but 31 Dec in year 4 is special case */ + if (day < 1095) { /*1095 days in 3 years */ + u.year = day / 365; /*365 days in a year */ + day -= (365 * u.year); + } else { + u.year = 3; + day -= 1095; + } + + + /* Now put it all back together */ + u.year += 1601; + u.year += 4 * y4; + u.year += 100 * y100; + u.year += 400 * y400; + + + u.jday = day + 1; + + u.is_leap = is_leap (u.year); + + + if (!u.is_leap) { + /*Days and months for ordinary years */ + if (u.jday < 32) { + u.month = 1; + u.mday = u.jday; + } else if (u.jday < 60) { + u.month = 2; + u.mday = u.jday - 31; + } else if (u.jday < 91) { + u.month = 3; + u.mday = u.jday - 59; + } else if (u.jday < 121) { + u.month = 4; + u.mday = u.jday - 90; + } else if (u.jday < 152) { + u.month = 5; + u.mday = u.jday - 120; + } else if (u.jday < 182) { + u.month = 6; + u.mday = u.jday - 151; + } else if (u.jday < 213) { + u.month = 7; + u.mday = u.jday - 181; + } else if (u.jday < 244) { + u.month = 8; + u.mday = u.jday - 212; + } else if (u.jday < 274) { + u.month = 9; + u.mday = u.jday - 243; + } else if (u.jday < 305) { + u.month = 10; + u.mday = u.jday - 273; + } else if (u.jday < 335) { + u.month = 11; + u.mday = u.jday - 304; + } else { + u.month = 12; + u.mday = u.jday - 334; + } + } else { + /*And leap years */ + if (u.jday < 32) { + u.month = 1; + u.mday = u.jday; + } else if (u.jday < 61) { + u.month = 2; + u.mday = u.jday - 31; + } else if (u.jday < 92) { + u.month = 3; + u.mday = u.jday - 60; + } else if (u.jday < 122) { + u.month = 4; + u.mday = u.jday - 91; + } else if (u.jday < 153) { + u.month = 5; + u.mday = u.jday - 121; + } else if (u.jday < 183) { + u.month = 6; + u.mday = u.jday - 152; + } else if (u.jday < 214) { + u.month = 7; + u.mday = u.jday - 182; + } else if (u.jday < 245) { + u.month = 8; + u.mday = u.jday - 213; + } else if (u.jday < 275) { + u.month = 9; + u.mday = u.jday - 244; + } else if (u.jday < 306) { + u.month = 10; + u.mday = u.jday - 274; + } else if (u.jday < 336) { + u.month = 11; + u.mday = u.jday - 305; + } else { + u.month = 12; + u.mday = u.jday - 335; + } + } + + u.hour = epoch.s / 3600; + epoch.s -= u.hour * 3600; + u.minute = epoch.s / 60; + epoch.s -= u.minute * 60; + u.second = epoch.s; + + u.nanosecond = epoch.ns; + + return u; +} + + + + +EPOCH time_utc_to_epoch (UTC u) +{ + unsigned y400; + unsigned y100; + unsigned y4; + + EPOCH ret; + + static int const mdays[] = + { 0, 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334 }; + static int const lmdays[] = + { 0, 0, 31, 60, 91, 121, 152, 182, 213, 244, 274, 305, 335 }; + + u.is_leap = is_leap (u.year); + + if (u.year < 100) u.year += 2000; + + + if (!u.jday) { + if (u.is_leap) + u.jday = u.mday + lmdays[u.month]; + else + u.jday = u.mday + mdays[u.month]; + } + + u.year -= 1601; + y400 = u.year / 400; + u.year -= y400 * 400; + y100 = u.year / 100; + u.year -= y100 * 100; + y4 = u.year / 4; + u.year -= y4 * 4; + + + + ret.s = u.jday - 1; + ret.s += u.year * 365; + ret.s += y4 * 1461; + ret.s += y100 * 36524; + ret.s += y400 * 146097; + + ret.s -= 134774; + + ret.s *= 86400; + + ret.s += u.second; + ret.s += u.minute * 60; + ret.s += u.hour * 3600; + + ret.ns = u.nanosecond; + + return ret; +} + + +void time_print_utc (UTC u) +{ + const char *dname[] = {"Sun", "Mon", "Tue", "Wed", "Thr", "Fri", "Sat", "Sun"}; + const char *mname[] = {"", "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"}; + printf ("%s %04d-%s-%02d %02d:%02d:%02d.%09d\r\n", dname[u.wday], u.year, mname[u.month], u.mday, u.hour, u.minute, u.second, u.nanosecond); +} + +void time_print_epoch (EPOCH e) +{ + UTC u = time_epoch_to_utc (e); + time_print_utc (u); +} + -- cgit v1.2.3