From: Christos Zoulas Date: Thu, 10 Jul 2003 17:41:24 +0000 (+0000) Subject: Utime/utimes support X-Git-Tag: FILE5_05~969 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=03d6ce7068c0cd89a9bdde6facc5ee612636d647;p=file Utime/utimes support --- diff --git a/src/Makefile.in b/src/Makefile.in index 9494f3be..4dbb177b 100644 --- a/src/Makefile.in +++ b/src/Makefile.in @@ -1,7 +1,7 @@ -# Makefile.in generated by automake 1.7.3 from Makefile.am. +# Makefile.in generated by automake 1.7.2 from Makefile.am. # @configure_input@ -# Copyright 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003 +# Copyright 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002 # Free Software Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, @@ -92,7 +92,6 @@ ac_ct_STRIP = @ac_ct_STRIP@ am__fastdepCC_FALSE = @am__fastdepCC_FALSE@ am__fastdepCC_TRUE = @am__fastdepCC_TRUE@ am__include = @am__include@ -am__leading_dot = @am__leading_dot@ am__quote = @am__quote@ bindir = @bindir@ build = @build@ diff --git a/src/file.c b/src/file.c index 3217669c..a2e795ee 100644 --- a/src/file.c +++ b/src/file.c @@ -72,7 +72,7 @@ #include "patchlevel.h" #ifndef lint -FILE_RCSID("@(#)$Id: file.c,v 1.78 2003/07/10 17:01:38 christos Exp $") +FILE_RCSID("@(#)$Id: file.c,v 1.79 2003/07/10 17:41:24 christos Exp $") #endif /* lint */ @@ -96,7 +96,8 @@ private int /* Global command-line options */ bflag = 0, /* brief output format */ nopad = 0, /* Don't pad output */ nobuffer = 0, /* Do not buffer stdout */ - kflag = 0; /* Keep going after the first match */ + kflag = 0, /* Keep going after the first match */ + rflag = 0; /* Restore access times of files */ private const char *magicfile = 0; /* where the magic is */ private const char *default_magicfile = MAGIC; @@ -132,7 +133,7 @@ main(int argc, char *argv[]) int flags = 0; char *mime, *home, *usermagic; struct stat sb; -#define OPTSTRING "bcdf:F:ikm:nNsvzCL" +#define OPTSTRING "bcCdf:F:ikLm:nNpsvz" #ifdef HAVE_GETOPT_LONG int longindex; private struct option long_options[] = @@ -150,6 +151,9 @@ main(int argc, char *argv[]) {"dereference", 0, 0, 'L'}, #endif {"magic-file", 1, 0, 'm'}, +#if defined(HAVE_UTIME) || defined(HAVE_UTIMES) + {"preserve-dates", 0, 0, 'p'}, +#endif {"uncompress", 0, 0, 'z'}, {"no-buffer", 0, 0, 'n'}, {"no-pad", 0, 0, 'N'}, @@ -243,6 +247,11 @@ main(int argc, char *argv[]) case 'N': ++nopad; break; +#if defined(HAVE_UTIME) || defined(HAVE_UTIMES) + case 'p': + flags |= MAGIC_PRESERVE_ATIME; + break; +#endif case 's': flags |= MAGIC_DEVICES; break; diff --git a/src/magic.c b/src/magic.c index f88efa30..61f1a335 100644 --- a/src/magic.c +++ b/src/magic.c @@ -41,20 +41,21 @@ #ifdef QUICK #include #endif -#ifdef RESTORE_TIME -# if (__COHERENT__ >= 0x420) + +#if defined(HAVE_UTIME) +# if defined(HAVE_SYS_UTIME_H) # include -# else -# ifdef USE_UTIMES -# include -# else -# include -# endif +# elif defined(HAVE_UTIME_H) +# include # endif +#elif defined(HAVE_UTIMES) +# include #endif + #ifdef HAVE_UNISTD_H #include /* for read() */ #endif + #ifdef HAVE_LOCALE_H #include #endif @@ -64,7 +65,7 @@ #include "patchlevel.h" #ifndef lint -FILE_RCSID("@(#)$Id: magic.c,v 1.8 2003/06/10 18:28:37 christos Exp $") +FILE_RCSID("@(#)$Id: magic.c,v 1.9 2003/07/10 17:41:24 christos Exp $") #endif /* lint */ #ifdef __EMX__ @@ -78,12 +79,19 @@ protected int file_os2_apptype(struct magic_set *ms, const char *fn, #endif private void free_mlist(struct mlist *); +private void close_and_restore(const struct magic_set *, const char *, int, + const struct stat *); public struct magic_set * magic_open(int flags) { struct magic_set *ms; + if (magic_setflags(ms, flags) == -1) { + errno = EINVAL; + return NULL; + } + if ((ms = malloc(sizeof(struct magic_set))) == NULL) return NULL; ms->o.ptr = ms->o.buf = malloc(ms->o.size = 1024); @@ -98,7 +106,6 @@ magic_open(int flags) free(ms); return NULL; } - ms->flags = flags; ms->haderr = 0; ms->mlist = NULL; return ms; @@ -183,6 +190,34 @@ magic_check(struct magic_set *ms, const char *magicfile) return ml ? 0 : -1; } +private void +close_and_restore(const struct magic_set *ms, const char *name, int fd, + const struct stat *sb) +{ + (void) close(fd); + if (fd != STDIN_FILENO && (ms->flags & MAGIC_PRESERVE_ATIME) != 0) { + /* + * Try to restore access, modification times if read it. + * This is really *bad* because it will modify the status + * time of the file... And of course this will affect + * backup programs + */ +#ifdef HAVE_UTIMES + struct timeval utsbuf[2]; + utsbuf[0].tv_sec = sb->st_atime; + utsbuf[1].tv_sec = sb->st_mtime; + + (void) utimes(name, utsbuf); /* don't care if loses */ +#elif defined(HAVE_UTIME_H) || defined(HAVE_SYS_UTIME_H) + struct utimbuf utbuf; + + utbuf.actime = sb->st_atime; + utbuf.modtime = sb->st_mtime; + (void) utime(name, &utbuf); /* don't care if loses */ +#endif + } +} + /* * find type of named file */ @@ -227,33 +262,29 @@ magic_file(struct magic_set *ms, const char *inname) */ if ((nbytes = read(fd, (char *)buf, HOWMANY)) == -1) { file_error(ms, "Cannot read `%s' %s", inname, strerror(errno)); - (void)close(fd); - return NULL; + goto done; } if (nbytes == 0) { if (file_printf(ms, (ms->flags & MAGIC_MIME) ? "application/x-empty" : "empty") == -1) { (void)close(fd); - return NULL; + goto done; } } else { buf[nbytes++] = '\0'; /* null-terminate it */ #ifdef __EMX__ switch (file_os2_apptype(ms, inname, buf, nbytes)) { case -1: - (void)close(fd); - return NULL; + goto done; case 0: break; default: return ms->o.buf; } #endif - if (file_buffer(ms, buf, (size_t)nbytes) == -1) { - (void)close(fd); - return NULL; - } + if (file_buffer(ms, buf, (size_t)nbytes) == -1) + goto done; #ifdef BUILTIN_ELF if (nbytes > 5) { /* @@ -269,8 +300,11 @@ magic_file(struct magic_set *ms, const char *inname) #endif } - close(fd); + close_and_restore(ms, inname, fd, &sb); return ms->haderr ? NULL : ms->o.buf; +done: + close_and_restore(ms, inname, fd, &sb); + return NULL; } @@ -295,8 +329,13 @@ magic_error(struct magic_set *ms) return ms->haderr ? ms->o.buf : NULL; } -public void +public int magic_setflags(struct magic_set *ms, int flags) { +#if !defined(HAVE_UTIME) && !defined(HAVE_UTIMES) + if (flags & MAGIC_PRESERVE_ATIME) + return -1; +#endif ms->flags = flags; + return 0; } diff --git a/src/magic.h b/src/magic.h index c4e09ad9..ee120d2f 100644 --- a/src/magic.h +++ b/src/magic.h @@ -31,14 +31,15 @@ #include -#define MAGIC_NONE 0x00 /* No flags */ -#define MAGIC_DEBUG 0x01 /* Turn on debugging */ -#define MAGIC_SYMLINK 0x02 /* Follow symlinks */ -#define MAGIC_COMPRESS 0x04 /* Check inside compressed files */ -#define MAGIC_DEVICES 0x08 /* Look at the contents of devices */ -#define MAGIC_MIME 0x10 /* Return a mime string */ -#define MAGIC_CONTINUE 0x20 /* Return all matches, not just the first */ -#define MAGIC_CHECK 0x40 /* Print warnings to stderr */ +#define MAGIC_NONE 0x00 /* No flags */ +#define MAGIC_DEBUG 0x01 /* Turn on debugging */ +#define MAGIC_SYMLINK 0x02 /* Follow symlinks */ +#define MAGIC_COMPRESS 0x04 /* Check inside compressed files */ +#define MAGIC_DEVICES 0x08 /* Look at the contents of devices */ +#define MAGIC_MIME 0x10 /* Return a mime string */ +#define MAGIC_CONTINUE 0x20 /* Return all matches */ +#define MAGIC_CHECK 0x40 /* Print warnings to stderr */ +#define MAGIC_PRESERVE_ATIME 0x80 /* Restore access time on exit */ #ifdef __cplusplus @@ -53,7 +54,7 @@ const char *magic_file(magic_t, const char *); const char *magic_buffer(magic_t, const void *, size_t); const char *magic_error(magic_t); -void magic_setflags(magic_t, int); +int magic_setflags(magic_t, int); int magic_load(magic_t, const char *); int magic_compile(magic_t, const char *);