allbery@ncoast.UUCP (07/09/87)
I wrote this one day trying to solve the problem of the file modification dates of restored files. Someone in comp.unix.questions wanted something like this, so here it is. Bugs - doesn't know about DST, and barely knows how to get the hours in the first place. No manual page, this program works kind of like the settime command that I remember from Version 7 days. Also, the inode changed time will always be set to the time you changed the file times. Enjoy! John. (jfh@killer.UUCP) ------------------------ cut somewheres near here ---------------------- #include <stdio.h> #include <sys/types.h> #include <sys/stat.h> /* * settime - change the access and modification dates of files * * This is mine. You steal, and you die. Ha, Ha. */ static char sccsid[] = "@(#)settime.c 1.0 John F. Haugh 08/05/86"; #define SECPERMIN 60 #define MINPERHR 60 #define HRPERDAY 24 #define SECPERHR (MINPERHR*SECPERMIN) #define SECPERDAY (HRPERDAY*MINPERHR*SECPERMIN) #define YEAR(y) (y & 03 ? 365:366) #define MONTH(m,y) (m != 2 ? months[(m - 1)]:(y & 03 ? 28:29)) extern long timezone; int months[12] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 }; conversion () { fprintf (stderr, "settime: conversion error\n"); exit (1); } usage () { fprintf (stderr, "usage: settime [ mmddHHMMyy | -f file ] name ...\n"); exit (1); } twodigits (s) char *s; { if (s[0] == 0 || s[1] == 0) { fprintf (stderr, "settime: bad date string\n"); exit (1); } return ((s[0] - '0') * 10 + s[1] - '0'); } month (m, y) int m, y; { int i; int days = 0; for (i = 1; i < m;i++) days += MONTH (i, y); return (SECPERDAY * days); } year (y) int y; { int i; int days = 0; for (i = 70;i < y;i++) days += YEAR (i); return (days * SECPERDAY); } time_t date (ds) char *ds; { time_t seconds = 0; int len; int mm, dd, HH, MM, yy; len = strlen (ds); if (len & 01) { mm = ds[0] - '0'; ds++; } else { mm = twodigits (ds); ds += 2; } dd = twodigits (ds); ds += 2; HH = twodigits (ds); ds += 2; MM = twodigits (ds); ds += 2; yy = twodigits (ds); if (MM > 59) conversion (); if (mm > 12 || mm == 0) conversion (); if (HH > 23) conversion (); if (yy < 70) conversion (); if (dd > MONTH (mm, yy) || dd == 0) conversion (); seconds = year (yy) + month (mm, yy) + (SECPERDAY * (dd - 1)) + (SECPERHR * HH) + (SECPERMIN * MM) + timezone; return (seconds); } main (argc, argv) int argc; char **argv; { struct utimbuf { time_t actime; time_t modtime; } utimbuf; struct stat statbuf; int i; if (argc < 3) usage (); tzset (); if (argv[1][0] == '-') { if (argv[1][1] != 'f') usage (); if (stat (argv[2], &statbuf) != 0) { perror (argv[2]); exit (2); } utimbuf.actime = statbuf.st_atime; utimbuf.modtime = statbuf.st_mtime; i = 3; } else { utimbuf.actime = utimbuf.modtime = date (argv[1]); i = 2; } for (;argv[i] != (char *) 0;i++) if (utime (argv[i], &utimbuf) != 0) perror (argv[i]); }