=================================================================== RCS file: /cvsrepo/anoncvs/cvs/src/usr.bin/file/file.c,v retrieving revision 1.17 retrieving revision 1.18 diff -c -r1.17 -r1.18 *** src/usr.bin/file/file.c 2007/02/19 13:02:08 1.17 --- src/usr.bin/file/file.c 2008/05/08 01:40:56 1.18 *************** *** 1,4 **** ! /* $OpenBSD: file.c,v 1.17 2007/02/19 13:02:08 tom Exp $ */ /* * Copyright (c) Ian F. Darwin 1986-1995. * Software written by Ian F. Darwin and others; --- 1,4 ---- ! /* $OpenBSD: file.c,v 1.18 2008/05/08 01:40:56 chl Exp $ */ /* * Copyright (c) Ian F. Darwin 1986-1995. * Software written by Ian F. Darwin and others; *************** *** 40,46 **** #include #include /* for MAXPATHLEN */ #include - #include /* for open() */ #ifdef RESTORE_TIME # if (__COHERENT__ >= 0x420) # include --- 40,45 ---- *************** *** 73,90 **** #include "patchlevel.h" #ifndef lint ! FILE_RCSID("@(#)$Id: file.c,v 1.17 2007/02/19 13:02:08 tom Exp $") #endif /* lint */ #ifdef S_IFLNK ! #define SYMLINKFLAG "L" #else #define SYMLINKFLAG "" #endif ! #define USAGE "Usage: %s [-bck" SYMLINKFLAG "Nnrsvz] [-F separator] [-f namefile] [-m magicfiles] file ...\n" \ ! " %s [-m magicfiles] -C\n" #ifndef MAXPATHLEN #define MAXPATHLEN 512 --- 72,89 ---- #include "patchlevel.h" #ifndef lint ! FILE_RCSID("@(#)$Id: file.c,v 1.18 2008/05/08 01:40:56 chl Exp $") #endif /* lint */ #ifdef S_IFLNK ! #define SYMLINKFLAG "Lh" #else #define SYMLINKFLAG "" #endif ! # define USAGE "Usage: %s [-bck" SYMLINKFLAG "nNrsvz0] [-e test] [-f namefile] [-F separator] [-m magicfiles] file...\n" \ ! " %s [-m magicfiles] -C\n" #ifndef MAXPATHLEN #define MAXPATHLEN 512 *************** *** 93,107 **** private int /* Global command-line options */ bflag = 0, /* brief output format */ nopad = 0, /* Don't pad output */ ! nobuffer = 0; /* Do not buffer stdout */ private const char *magicfile = 0; /* where the magic is */ private const char *default_magicfile = MAGIC; ! private char *separator = ":"; /* Default field separator */ - private char *progname; /* used throughout */ - private struct magic_set *magic; private void unwrap(char *); private void usage(void); --- 92,106 ---- private int /* Global command-line options */ bflag = 0, /* brief output format */ nopad = 0, /* Don't pad output */ ! nobuffer = 0, /* Do not buffer stdout */ ! nulsep = 0; /* Append '\0' to the separator */ private const char *magicfile = 0; /* where the magic is */ private const char *default_magicfile = MAGIC; ! private const char *separator = ":"; /* Default field separator */ private struct magic_set *magic; + extern char *__progname; private void unwrap(char *); private void usage(void); *************** *** 124,149 **** int main(int argc, char *argv[]) { ! int c; int action = 0, didsomefiles = 0, errflg = 0; int flags = 0; char *home, *usermagic; struct stat sb; ! #define OPTSTRING "bcCdf:F:kLm:nNprsvz" #ifdef HAVE_GETOPT_LONG int longindex; ! private struct option long_options[] = { {"version", 0, 0, 'v'}, {"help", 0, 0, 0}, {"brief", 0, 0, 'b'}, {"checking-printout", 0, 0, 'c'}, {"debug", 0, 0, 'd'}, {"files-from", 1, 0, 'f'}, {"separator", 1, 0, 'F'}, {"keep-going", 0, 0, 'k'}, #ifdef S_IFLNK {"dereference", 0, 0, 'L'}, #endif {"magic-file", 1, 0, 'm'}, #if defined(HAVE_UTIME) || defined(HAVE_UTIMES) --- 123,151 ---- int main(int argc, char *argv[]) { ! int c, i; int action = 0, didsomefiles = 0, errflg = 0; int flags = 0; char *home, *usermagic; struct stat sb; ! static const char hmagic[] = "/.magic"; ! #define OPTSTRING "bcCde:f:F:hkLm:nNprsvz0" #ifdef HAVE_GETOPT_LONG int longindex; ! static const struct option long_options[] = { {"version", 0, 0, 'v'}, {"help", 0, 0, 0}, {"brief", 0, 0, 'b'}, {"checking-printout", 0, 0, 'c'}, {"debug", 0, 0, 'd'}, + {"exclude", 1, 0, 'e' }, {"files-from", 1, 0, 'f'}, {"separator", 1, 0, 'F'}, {"keep-going", 0, 0, 'k'}, #ifdef S_IFLNK {"dereference", 0, 0, 'L'}, + {"no-dereference", 0, 0, 'h'}, #endif {"magic-file", 1, 0, 'm'}, #if defined(HAVE_UTIME) || defined(HAVE_UTIMES) *************** *** 155,166 **** {"no-pad", 0, 0, 'N'}, {"special-files", 0, 0, 's'}, {"compile", 0, 0, 'C'}, {0, 0, 0, 0}, }; #endif #ifdef LC_CTYPE ! setlocale(LC_CTYPE, ""); /* makes islower etc work for other langs */ #endif #ifdef __EMX__ --- 157,185 ---- {"no-pad", 0, 0, 'N'}, {"special-files", 0, 0, 's'}, {"compile", 0, 0, 'C'}, + {"print0", 0, 0, '0'}, {0, 0, 0, 0}, }; #endif + static const struct { + const char *name; + int value; + } nv[] = { + { "apptype", MAGIC_NO_CHECK_APPTYPE }, + { "ascii", MAGIC_NO_CHECK_ASCII }, + { "compress", MAGIC_NO_CHECK_COMPRESS }, + { "elf", MAGIC_NO_CHECK_ELF }, + { "fortran", MAGIC_NO_CHECK_FORTRAN }, + { "soft", MAGIC_NO_CHECK_SOFT }, + { "tar", MAGIC_NO_CHECK_TAR }, + { "tokens", MAGIC_NO_CHECK_TOKENS }, + { "troff", MAGIC_NO_CHECK_TROFF }, + }; + #ifdef LC_CTYPE ! /* makes islower etc work for other langs */ ! (void)setlocale(LC_CTYPE, ""); #endif #ifdef __EMX__ *************** *** 168,187 **** _wildcard(&argc, &argv); #endif - if ((progname = strrchr(argv[0], '/')) != NULL) - progname++; - else - progname = argv[0]; - magicfile = default_magicfile; if ((usermagic = getenv("MAGIC")) != NULL) magicfile = usermagic; else if ((home = getenv("HOME")) != NULL) { ! size_t len = strlen(home) + 8; if ((usermagic = malloc(len)) != NULL) { (void)strlcpy(usermagic, home, len); ! (void)strlcat(usermagic, "/.magic", len); if (stat(usermagic, &sb)<0) free(usermagic); else --- 187,201 ---- _wildcard(&argc, &argv); #endif magicfile = default_magicfile; if ((usermagic = getenv("MAGIC")) != NULL) magicfile = usermagic; else if ((home = getenv("HOME")) != NULL) { ! size_t len = strlen(home) + sizeof(hmagic); if ((usermagic = malloc(len)) != NULL) { (void)strlcpy(usermagic, home, len); ! (void)strlcat(usermagic, hmagic, len); if (stat(usermagic, &sb)<0) free(usermagic); else *************** *** 189,194 **** --- 203,211 ---- } } + #ifdef S_IFLNK + flags |= getenv("POSIXLY_CORRECT") ? MAGIC_SYMLINK : 0; + #endif #ifndef HAVE_GETOPT_LONG while ((c = getopt(argc, argv, OPTSTRING)) != -1) #else *************** *** 202,207 **** --- 219,227 ---- help(); break; #endif + case '0': + nulsep = 1; + break; case 'b': ++bflag; break; *************** *** 214,219 **** --- 234,250 ---- case 'd': flags |= MAGIC_DEBUG|MAGIC_CHECK; break; + case 'e': + for (i = 0; i < sizeof(nv) / sizeof(nv[0]); i++) + if (strcmp(nv[i].name, optarg) == 0) + break; + + if (i == sizeof(nv) / sizeof(nv[0])) + errflg++; + else + flags |= nv[i].value; + break; + case 'f': if(action) usage(); *************** *** 248,256 **** flags |= MAGIC_DEVICES; break; case 'v': ! (void) fprintf(stdout, "%s-%d.%.2d\n", progname, FILE_VERSION_MAJOR, patchlevel); ! (void) fprintf(stdout, "magic file from %s\n", magicfile); return 1; case 'z': --- 279,287 ---- flags |= MAGIC_DEVICES; break; case 'v': ! (void)fprintf(stdout, "%s-%d.%.2d\n", __progname, FILE_VERSION_MAJOR, patchlevel); ! (void)fprintf(stdout, "magic file from %s\n", magicfile); return 1; case 'z': *************** *** 260,265 **** --- 291,299 ---- case 'L': flags |= MAGIC_SYMLINK; break; + case 'h': + flags &= ~MAGIC_SYMLINK; + break; #endif case '?': default: *************** *** 276,289 **** case FILE_COMPILE: magic = magic_open(flags|MAGIC_CHECK); if (magic == NULL) { ! (void)fprintf(stderr, "%s: %s\n", progname, strerror(errno)); return 1; } c = action == FILE_CHECK ? magic_check(magic, magicfile) : magic_compile(magic, magicfile); if (c == -1) { ! (void)fprintf(stderr, "%s: %s\n", progname, magic_error(magic)); return -1; } --- 310,323 ---- case FILE_COMPILE: magic = magic_open(flags|MAGIC_CHECK); if (magic == NULL) { ! (void)fprintf(stderr, "%s: %s\n", __progname, strerror(errno)); return 1; } c = action == FILE_CHECK ? magic_check(magic, magicfile) : magic_compile(magic, magicfile); if (c == -1) { ! (void)fprintf(stderr, "%s: %s\n", __progname, magic_error(magic)); return -1; } *************** *** 309,331 **** process(argv[optind], wid); } return 0; } private void load(const char *m, int flags) { ! if (magic) return; magic = magic_open(flags); if (magic == NULL) { ! (void)fprintf(stderr, "%s: %s\n", progname, strerror(errno)); exit(1); } if (magic_load(magic, magicfile) == -1) { (void)fprintf(stderr, "%s: %s\n", ! progname, magic_error(magic)); exit(1); } } --- 343,367 ---- process(argv[optind], wid); } + magic_close(magic); return 0; } private void + /*ARGSUSED*/ load(const char *m, int flags) { ! if (magic || m == NULL) return; magic = magic_open(flags); if (magic == NULL) { ! (void)fprintf(stderr, "%s: %s\n", __progname, strerror(errno)); exit(1); } if (magic_load(magic, magicfile) == -1) { (void)fprintf(stderr, "%s: %s\n", ! __progname, magic_error(magic)); exit(1); } } *************** *** 346,357 **** } else { if ((f = fopen(fn, "r")) == NULL) { (void)fprintf(stderr, "%s: Cannot open `%s' (%s).\n", ! progname, fn, strerror(errno)); exit(1); } while (fgets(buf, sizeof(buf), f) != NULL) { ! cwid = file_mbswidth(buf) - 1; if (cwid > wid) wid = cwid; } --- 382,394 ---- } else { if ((f = fopen(fn, "r")) == NULL) { (void)fprintf(stderr, "%s: Cannot open `%s' (%s).\n", ! __progname, fn, strerror(errno)); exit(1); } while (fgets(buf, sizeof(buf), f) != NULL) { ! buf[strcspn(buf, "\n")] = '\0'; ! cwid = file_mbswidth(buf); if (cwid > wid) wid = cwid; } *************** *** 360,389 **** } while (fgets(buf, sizeof(buf), f) != NULL) { ! buf[file_mbswidth(buf)-1] = '\0'; process(buf, wid); if(nobuffer) ! (void) fflush(stdout); } ! (void) fclose(f); } private void process(const char *inname, int wid) { const char *type; int std_in = strcmp(inname, "-") == 0; ! if (wid > 0 && !bflag) ! (void) printf("%s%s%*s ", std_in ? "/dev/stdin" : inname, ! separator, (int) (nopad ? 0 : (wid - file_mbswidth(inname))), ""); type = magic_file(magic, std_in ? NULL : inname); if (type == NULL) ! printf("ERROR: %s\n", magic_error(magic)); else ! printf("%s\n", type); } --- 397,435 ---- } while (fgets(buf, sizeof(buf), f) != NULL) { ! buf[strcspn(buf, "\n")] = '\0'; process(buf, wid); if(nobuffer) ! (void)fflush(stdout); } ! (void)fclose(f); } + /* + * Called for each input file on the command line (or in a list of files) + */ private void process(const char *inname, int wid) { const char *type; int std_in = strcmp(inname, "-") == 0; ! if (wid > 0 && !bflag) { ! (void)printf("%s", std_in ? "/dev/stdin" : inname); ! if (nulsep) ! (void)putc('\0', stdout); ! else ! (void)printf("%s", separator); ! (void)printf("%*s ", ! (int) (nopad ? 0 : (wid - file_mbswidth(inname))), ""); ! } type = magic_file(magic, std_in ? NULL : inname); if (type == NULL) ! (void)printf("ERROR: %s\n", magic_error(magic)); else ! (void)printf("%s\n", type); } *************** *** 447,453 **** size_t file_mbswidth(const char *s) { ! #ifdef HAVE_WCHAR_H size_t bytesconsumed, old_n, n, width = 0; mbstate_t state; wchar_t nextchar; --- 493,499 ---- size_t file_mbswidth(const char *s) { ! #if defined(HAVE_WCHAR_H) && defined(HAVE_MBRTOWC) && defined(HAVE_WCWIDTH) size_t bytesconsumed, old_n, n, width = 0; mbstate_t state; wchar_t nextchar; *************** *** 481,487 **** private void usage(void) { ! (void)fprintf(stderr, USAGE, progname, progname); #ifdef HAVE_GETOPT_LONG (void)fputs("Try `file --help' for more information.\n", stderr); #endif --- 527,533 ---- private void usage(void) { ! (void)fprintf(stderr, USAGE, __progname, __progname); #ifdef HAVE_GETOPT_LONG (void)fputs("Try `file --help' for more information.\n", stderr); #endif *************** *** 492,498 **** private void help(void) { ! puts( "Usage: file [OPTION]... [FILE]...\n" "Determine file type of FILEs.\n" "\n" --- 538,544 ---- private void help(void) { ! (void)puts( "Usage: file [OPTION]... [FILE]...\n" "Determine file type of FILEs.\n" "\n" *************** *** 503,508 **** --- 549,557 ---- " -c, --checking-printout print the parsed form of the magic file, use in\n" " conjunction with -m to debug a new magic file\n" " before installing it\n" + " -e, --exclude exclude test from the list of test to be\n" + " performed for file. Valid tests are:\n" + " ascii, apptype, elf, compress, soft, tar\n" " -f, --files-from FILE read the filenames to be examined from FILE\n" " -F, --separator string use string as separator instead of `:'\n" " -k, --keep-going don't stop at the first match\n" *************** *** 513,520 **** --- 562,573 ---- " -r, --raw don't translate unprintable chars to \\ooo\n" " -s, --special-files treat special (block/char devices) files as\n" " ordinary ones\n" + "or\n" " --help display this help and exit\n" + "or\n" " --version output version information and exit\n" + "or\n" + " -C, --compile compile file specified by -m\n" ); exit(0); }