Bell 32V development
[unix-history] / usr / src / cmd / date.c
/*
* date : print date
* date YYMMDDHHMM[.SS] : set date, if allowed
* date -u ... : date in GMT
*/
#include <time.h>
#include <sys/types.h>
#include <sys/timeb.h>
#include <utmp.h>
long timbuf;
char *ap, *ep, *sp;
int uflag;
char *timezone();
static int dmsize[12] =
{
31,
28,
31,
30,
31,
30,
31,
31,
30,
31,
30,
31
};
struct utmp wtmp[2] = { {"|", "", 0}, {"{", "", 0}};
char *ctime();
char *asctime();
struct tm *localtime();
struct tm *gmtime();
main(argc, argv)
char *argv[];
{
register char *tzn;
struct timeb info;
int wf, rc;
rc = 0;
ftime(&info);
if (argc>1 && argv[1][0]=='-' && argv[1][1]=='u') {
argc--;
argv++;
uflag++;
}
if(argc > 1) {
ap = argv[1];
if (gtime()) {
printf("date: bad conversion\n");
exit(1);
}
/* convert to GMT assuming local time */
if (uflag==0) {
timbuf += (long)info.timezone*60;
/* now fix up local daylight time */
if(localtime(&timbuf)->tm_isdst)
timbuf -= 60*60;
}
time(&wtmp[0].ut_time);
if(stime(&timbuf) < 0) {
rc++;
printf("date: no permission\n");
} else if ((wf = open("/usr/adm/wtmp", 1)) >= 0) {
time(&wtmp[1].ut_time);
lseek(wf, 0L, 2);
write(wf, (char *)wtmp, sizeof(wtmp));
close(wf);
}
}
if (rc==0)
time(&timbuf);
if(uflag) {
ap = asctime(gmtime(&timbuf));
tzn = "GMT";
} else {
struct tm *tp;
tp = localtime(&timbuf);
ap = asctime(tp);
tzn = timezone(info.timezone, tp->tm_isdst);
}
printf("%.20s", ap);
if (tzn)
printf("%s", tzn);
printf("%s", ap+19);
exit(rc);
}
gtime()
{
register int i, year, month;
int day, hour, mins, secs;
struct tm *L;
char x;
ep=ap;
while(*ep) ep++;
sp=ap;
while(sp<ep) {
x = *sp;
*sp++ = *--ep;
*ep = x;
}
sp=ap;
time(&timbuf);
L=localtime(&timbuf);
secs = gp(-1);
if(*sp!='.') {
mins=secs;
secs=0;
} else {sp++;
mins = gp(-1);
}
hour = gp(-1);
day = gp(L->tm_mday);
month = gp(L->tm_mon+1);
year = gp(L->tm_year);
if(*sp)
return(1);
if( month<1 || month>12 ||
day<1 || day>31 ||
mins<0 || mins>59 ||
secs<0 || secs>59)
return(1);
if (hour==24) {
hour=0; day++;
}
if (hour<0 || hour>23)
return(1);
timbuf = 0;
year += 1900;
for(i=1970; i<year; i++)
timbuf += dysize(i);
/* Leap year */
if (dysize(year)==366 && month >= 3)
timbuf++;
while(--month)
timbuf += dmsize[month-1];
timbuf += day-1;
timbuf = 24*timbuf + hour;
timbuf = 60*timbuf + mins;
timbuf = 60*timbuf + secs;
return(0);
}
gp(dfault)
{
register int c, d;
if(*sp==0)
return(dfault);
c = (*sp++)-'0';
d = (*sp ? (*sp++)-'0' : 0);
if(c<0 || c>9 || d<0 || d>9)
return(-1);
return(c+10*d);
}