summaryrefslogtreecommitdiffstats
path: root/pcp/pcpgmtime.c
diff options
context:
space:
mode:
Diffstat (limited to 'pcp/pcpgmtime.c')
-rw-r--r--pcp/pcpgmtime.c152
1 files changed, 152 insertions, 0 deletions
diff --git a/pcp/pcpgmtime.c b/pcp/pcpgmtime.c
new file mode 100644
index 0000000..be38ac7
--- /dev/null
+++ b/pcp/pcpgmtime.c
@@ -0,0 +1,152 @@
+/*
+** Copyright 2001 Double Precision, Inc. See COPYING for
+** distribution information.
+*/
+
+
+#include "config.h"
+#include "pcp.h"
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <ctype.h>
+#include <time.h>
+#include <fcntl.h>
+#include <errno.h>
+
+#include "pcp.h"
+
+#define leap(y) ( \
+ ((y) % 400) == 0 || \
+ (((y) % 4) == 0 && (y) % 100) )
+
+static unsigned mlength[]={31,28,31,30,31,30,31,31,30,31,30,31};
+#define mdays(m,y) ( (m) != 2 ? mlength[(m)-1] : leap(y) ? 29:28)
+
+
+static int tmcmp(int y1, int m1, int d1,
+ int y2, int m2, int d2)
+{
+ if (y1 < y2)
+ return (-1);
+ if (y1 > y2)
+ return (1);
+ if (m1 < m2)
+ return (-1);
+ if (m1 > m2)
+ return (1);
+ if (d1 < d2)
+ return (-1);
+ if (d1 > d2)
+ return (1);
+ return (0);
+}
+
+time_t pcp_gmtime(int y, int m, int d, int hh, int mm, int ss)
+{
+ time_t t;
+ struct tm *tmptr;
+ struct tm mytm;
+ int n;
+
+ if (y < 1970 || y > 3000 || m < 1 || m > 12 || d < 1 ||
+ d > mdays(m, y) || hh < 0 || mm < 0 || ss < 0 || hh > 23 ||
+ mm > 59 || ss > 59)
+ return (0);
+
+ time(&t);
+
+ tmptr=localtime(&t);
+ if (!tmptr)
+ return (0);
+
+ mytm= *tmptr;
+ mytm.tm_year = y - 1900;
+ mytm.tm_mon = m - 1;
+ mytm.tm_mday = d;
+ mytm.tm_hour=0;
+ mytm.tm_min=0;
+ mytm.tm_sec=0;
+
+ t=mktime(&mytm);
+ if (t == (time_t)-1)
+ return (0);
+
+ /* Do it again, due to a potential timezone change */
+
+ tmptr=localtime(&t);
+ mytm= *tmptr;
+ mytm.tm_year = y - 1900;
+ mytm.tm_mon = m - 1;
+ mytm.tm_mday = d;
+ mytm.tm_hour=0;
+ mytm.tm_min=0;
+ mytm.tm_sec=0;
+
+ t=mktime(&mytm);
+ if (t == (time_t)-1)
+ return (0);
+
+ /* Sanity check */
+
+ tmptr=localtime(&t);
+ if (tmptr->tm_hour || tmptr->tm_min || tmptr->tm_sec)
+ {
+ return (0);
+ }
+
+ tmptr=gmtime(&t);
+
+ n=tmcmp(tmptr->tm_year + 1900,
+ tmptr->tm_mon + 1,
+ tmptr->tm_mday,
+ y, m, d);
+ if (n < 0)
+ {
+ while (n < 0)
+ {
+ t += 24 * 60 * 60;
+ tmptr=gmtime(&t);
+ n=tmcmp(tmptr->tm_year + 1900,
+ tmptr->tm_mon + 1,
+ tmptr->tm_mday,
+ y, m, d);
+ }
+ }
+ else while (n > 0)
+ {
+ t -= 24 * 60 * 60;
+ tmptr=gmtime(&t);
+ n=tmcmp(tmptr->tm_year + 1900,
+ tmptr->tm_mon + 1,
+ tmptr->tm_mday,
+ y, m, d);
+ }
+
+ t -= tmptr->tm_hour * 60 * 60 + tmptr->tm_min * 60 + tmptr->tm_sec;
+
+ return (t + hh * 60 * 60 + mm * 60 + ss);
+}
+
+time_t pcp_gmtime_s(const char *p)
+{
+ int y, m, d, hh, mm, ss;
+
+ if (sscanf(p, "%4d%2d%2d%2d%2d%2d", &y, &m, &d, &hh, &mm, &ss)
+ != 6)
+ return (0);
+ return (pcp_gmtime(y, m, d, hh, mm, ss));
+}
+
+void pcp_gmtimestr(time_t t, char *buf)
+{
+ struct tm *tmptr=gmtime(&t);
+
+ sprintf(buf, "%04d%02d%02d%02d%02d%02d",
+ tmptr->tm_year + 1900,
+ tmptr->tm_mon+1,
+ tmptr->tm_mday,
+ tmptr->tm_hour,
+ tmptr->tm_min,
+ tmptr->tm_sec);
+}