about summary refs log tree commit diff
path: root/mytimegm.c
diff options
context:
space:
mode:
authorLeah Neukirchen <leah@vuxu.org>2020-03-28 21:29:34 +0100
committerLeah Neukirchen <leah@vuxu.org>2020-03-28 21:29:34 +0100
commit604afb501107cf9f7b0d0a60fbeade525e8ab1fd (patch)
tree13c52145452dcc6d97e14a1540fb3f0ebc18dc91 /mytimegm.c
parent7e6b1c97e617ba75b4c8fdedffa02133a8393552 (diff)
downloadmblaze-604afb501107cf9f7b0d0a60fbeade525e8ab1fd.tar.gz
mblaze-604afb501107cf9f7b0d0a60fbeade525e8ab1fd.tar.xz
mblaze-604afb501107cf9f7b0d0a60fbeade525e8ab1fd.zip
mytimegm: replace with own implementation
Diffstat (limited to 'mytimegm.c')
-rw-r--r--mytimegm.c104
1 files changed, 23 insertions, 81 deletions
diff --git a/mytimegm.c b/mytimegm.c
index 7b63b2f..3f9cca0 100644
--- a/mytimegm.c
+++ b/mytimegm.c
@@ -1,86 +1,28 @@
 #include <time.h>
 
-// from musl@1cc81f5cb, slightly tweaked
-
-static long long
-__year_to_secs(long long year, int *is_leap)
-{
-	if (year-2ULL <= 136) {
-		int y = year;
-		int leaps = (y-68)>>2;
-		if (!((y-68)&3)) {
-			leaps--;
-			if (is_leap) *is_leap = 1;
-		} else if (is_leap) *is_leap = 0;
-		return 31536000*(y-70) + 86400*leaps;
-	}
-
-	int cycles, centuries, leaps, rem;
-
-	cycles = (year-100) / 400;
-	rem = (year-100) % 400;
-	if (rem < 0) {
-		cycles--;
-		rem += 400;
-	}
-	if (!rem) {
-		*is_leap = 1;
-		centuries = 0;
-		leaps = 0;
-	} else {
-		if (rem >= 200) {
-			if (rem >= 300) centuries = 3, rem -= 300;
-			else centuries = 2, rem -= 200;
-		} else {
-			if (rem >= 100) centuries = 1, rem -= 100;
-			else centuries = 0;
-		}
-		if (!rem) {
-			*is_leap = 0;
-			leaps = 0;
-		} else {
-			leaps = rem / 4U;
-			rem %= 4U;
-			*is_leap = !rem;
-		}
-	}
-
-	leaps += 97*cycles + 24*centuries - *is_leap;
-
-	return (year-100) * 31536000LL + leaps * 86400LL + 946684800 + 86400;
-}
-
-static int
-__month_to_secs(int month, int is_leap)
-{
-	static const int secs_through_month[] = {
-		0, 31*86400, 59*86400, 90*86400,
-		120*86400, 151*86400, 181*86400, 212*86400,
-		243*86400, 273*86400, 304*86400, 334*86400 };
-	int t = secs_through_month[month];
-	if (is_leap && month >= 2) t+=86400;
-	return t;
-}
-
-time_t tm_to_secs(const struct tm *tm)
+time_t
+mytimegm(struct tm *tm)
 {
-	int is_leap;
-	long long year = tm->tm_year;
-	int month = tm->tm_mon;
-	if (month >= 12 || month < 0) {
-		int adj = month / 12;
-		month %= 12;
-		if (month < 0) {
-			adj--;
-			month += 12;
-		}
-		year += adj;
-	}
-	long long t = __year_to_secs(year, &is_leap);
-	t += __month_to_secs(month, is_leap);
-	t += 86400LL * (tm->tm_mday-1);
-	t += 3600LL * tm->tm_hour;
-	t += 60LL * tm->tm_min;
-	t += tm->tm_sec;
+	int mon = tm->tm_mon + 1 - 2;  /* put March first, Feb last */
+	long long year = tm->tm_year + 1900;
+
+        if (mon <= 0 || mon >= 12) {
+                int adj = mon / 12;
+                mon %= 12;
+                if (mon <= 0) {
+                        adj--;
+                        mon += 12;
+                }
+                year += adj;
+        }
+
+	time_t t = 0;
+	t +=            tm->tm_sec;
+	t +=       60 * tm->tm_min;
+	t +=    60*60 * tm->tm_hour;
+	t += 24*60*60 * (tm->tm_mday - 1);
+	t += 24*60*60 * (367*mon/12);
+	t += 24*60*60 * (year/4 - year/100 + year/400);
+	t += 24*60*60 * (365*year - 719498L);
 	return t;
 }