]> granicus.if.org Git - file/commitdiff
changes from mycroft@gnu.ai.mit.edu (Charles Hannum) for unsigned
authorChristos Zoulas <christos@zoulas.com>
Tue, 3 May 1994 17:58:23 +0000 (17:58 +0000)
committerChristos Zoulas <christos@zoulas.com>
Tue, 3 May 1994 17:58:23 +0000 (17:58 +0000)
doc/magic.man
src/apprentice.c
src/file.h
src/patchlevel.h
src/print.c
src/softmagic.c

index d504a5d762c40f12ee9ba5ffd903d23ddeb6ddbf..7c2788e9b434e0cb94c299c93b87e33d97c8457e 100644 (file)
@@ -51,11 +51,14 @@ A four-byte value (on most systems) in little-endian byte order.
 A four-byte value (on most systems) in little-endian byte order,
 interpreted as a unix date.
 .RE
+.PP
 The numeric types may optionally be followed by
 .B &
 and a numeric value,
 to specify that the value is to be AND'ed with the
-numeric value before any comparisons are done.
+numeric value before any comparisons are done.  Prepending a
+.B u
+to the type indicates that ordered comparisons should be unsigned.
 .IP test
 The value to be compared with the value from the file.  If the type is
 numeric, this value
@@ -188,4 +191,4 @@ indirect offsets.
 .\" the changes I posted to the S5R2 version.
 .\"
 .\" Modified for Ian Darwin's version of the file command.
-.\" @(#)$Id: magic.man,v 1.10 1993/02/19 14:22:46 ian Exp $
+.\" @(#)$Id: magic.man,v 1.11 1994/05/03 17:58:23 christos Exp $
index 6fad93c1805b2eb33459f4ea5e1356af7a0761a1..e1b4f4553070a2d88bb4b9ec4453fc9e26a27aef 100644 (file)
 
 #ifndef        lint
 static char *moduleid = 
-       "@(#)$Id: apprentice.c,v 1.18 1993/09/23 20:19:42 christos Exp $";
+       "@(#)$Id: apprentice.c,v 1.19 1994/05/03 17:58:23 christos Exp $";
 #endif /* lint */
 
 #define        EATAB {while (isascii((unsigned char) *l) && \
                      isspace((unsigned char) *l))  ++l;}
 
 
-static int getvalue __P((struct magic *, char **));
-static int hextoint __P((int));
-static char *getstr __P((char *, char *, int, int *));
-static int parse    __P((char *, int *, int));
+static int getvalue    __P((struct magic *, char **));
+static int hextoint    __P((int));
+static char *getstr    __P((char *, char *, int, int *));
+static int parse       __P((char *, int *, int));
 
 static int maxmagic = 0;
 
@@ -75,7 +75,7 @@ int check;                    /* non-zero? checking-only run. */
                else
                        exit(1);
        }
-
+  
        /* parse it */
        if (check)      /* print silly verbose header for USG compat. */
                (void) printf("cont\toffset\ttype\topcode\tmask\tvalue\tdesc\n");
@@ -94,6 +94,47 @@ int check;                   /* non-zero? checking-only run. */
        return errs ? -1 : 0;
 }
 
+/*
+ * extend the sign bit if the comparison is to be signed
+ */
+unsigned long
+signextend(m, v)
+struct magic *m;
+unsigned long v;
+{
+       if (!(m->flag & UNSIGNED))
+               switch(m->type) {
+               /*
+                * Do not remove the casts below.  They are
+                * vital.  When later compared with the data,
+                * the sign extension must have happened.
+                */
+               case BYTE:
+                       v = (char) v;
+                       break;
+               case SHORT:
+               case BESHORT:
+               case LESHORT:
+                       v = (short) v;
+                       break;
+               case DATE:
+               case BEDATE:
+               case LEDATE:
+               case LONG:
+               case BELONG:
+               case LELONG:
+                       v = (long) v;
+                       break;
+               case STRING:
+                       break;
+               default:
+                       magwarn("can't happen: m->type=%d\n",
+                               m->type);
+                       return -1;
+               }
+       return v;
+}
+
 /*
  * parse one line from magic file, put into magic[index++] if valid
  */
@@ -191,6 +232,11 @@ int *ndx, check;
 #define NLELONG                6
 #define NLEDATE                6
 
+       if (*l == 'u') {
+               ++l;
+               m->flag |= UNSIGNED;
+       }
+
        /* get type, skip it */
        if (strncmp(l, "byte", NBYTE)==0) {
                m->type = BYTE;
@@ -232,9 +278,9 @@ int *ndx, check;
        /* New-style anding: "0 byte&0x80 =0x80 dynamically linked" */
        if (*l == '&') {
                ++l;
-               m->mask = strtol(l, &l, 0);
+               m->mask = signextend(m, strtol(l, &l, 0));
        } else
-               m->mask = 0L;
+               m->mask = ~0L;
        EATAB;
   
        switch (*l) {
@@ -313,36 +359,9 @@ char **p;
        if (m->type == STRING) {
                *p = getstr(*p, m->value.s, sizeof(m->value.s), &slen);
                m->vallen = slen;
-       } else {
-               if (m->reln != 'x') {
-                       switch(m->type) {
-                       /*
-                        * Do not remove the casts below.  They are vital.
-                        * When later compared with the data, the sign
-                        * extension must have happened.
-                        */
-                       case BYTE:
-                               m->value.l = (char) strtol(*p,p,0);
-                               break;
-                       case SHORT:
-                       case BESHORT:
-                       case LESHORT:
-                               m->value.l = (short) strtol(*p,p,0);
-                               break;
-                       case DATE:
-                       case BEDATE:
-                       case LEDATE:
-                       case LONG:
-                       case BELONG:
-                       case LELONG:
-                               m->value.l = (long) strtol(*p,p,0);
-                               break;
-                       default:
-                               magwarn("can't happen: m->type=%d\n", m->type);
-                               return -1;
-                       }
-               }
-       }
+       } else
+               if (m->reln != 'x')
+                       m->value.l = signextend(m, strtol(*p, p, 0));
        return 0;
 }
 
index 39874a1b842b5c4d4124879cac312659ea8a63fd..12d5c6f9571bcf360490b858b9d03db2064caf72 100644 (file)
@@ -1,6 +1,6 @@
 /*
  * file.h - definitions for file(1) program
- * @(#)$Id: file.h,v 1.18 1993/10/27 20:59:05 christos Exp $
+ * @(#)$Id: file.h,v 1.19 1994/05/03 17:58:23 christos Exp $
  *
  * Copyright (c) Ian F. Darwin, 1987.
  * Written by Ian F. Darwin.
@@ -34,6 +34,7 @@
 struct magic {
        short flag;             
 #define INDIR  1               /* if '>(...)' appears,  */
+#define        UNSIGNED 2              /* comparison is unsigned */
        short cont_level;       /* level of ">" */
        struct {
                char type;      /* byte short long */
@@ -55,14 +56,14 @@ struct magic {
 #define                                LELONG  11
 #define                                LEDATE  12
        union VALUETYPE {
-               char b;
-               short h;
-               long l;
+               unsigned char b;
+               unsigned short h;
+               unsigned long l;
                char s[MAXstring];
                unsigned char hs[2];    /* 2 bytes of a fixed-endian "short" */
                unsigned char hl[4];    /* 2 bytes of a fixed-endian "long" */
        } value;                /* either number or string */
-       long mask;              /* mask before comparison with value */
+       unsigned long mask;     /* mask before comparison with value */
        char nospflag;          /* supress space character */
        char desc[MAXDESC];     /* description */
 };
@@ -94,6 +95,7 @@ extern int   softmagic                __P((unsigned char *, int));
 extern void  tryit             __P((unsigned char *, int, int));
 extern int   zmagic            __P((unsigned char *, int));
 extern void  ckfprintf         __P((FILE *, const char *, ...));
+extern unsigned long signextend        __P((struct magic *, unsigned long));
 
 
 
index 499609d585382a096f14565b131f17c23fe38c20..490a7d53a2ca30de31d34f7516e65dca5851676b 100644 (file)
@@ -1,12 +1,15 @@
 #define        FILE_VERSION_MAJOR      3
-#define        patchlevel              13
+#define        patchlevel              14
 
 /*
  * Patchlevel file for Ian Darwin's MAGIC command.
- * $Id: patchlevel.h,v 1.13 1994/01/21 01:27:01 christos Exp $
+ * $Id: patchlevel.h,v 1.14 1994/05/03 17:58:23 christos Exp $
  *
  * $Log: patchlevel.h,v $
- * Revision 1.13  1994/01/21 01:27:01  christos
+ * Revision 1.14  1994/05/03 17:58:23  christos
+ * changes from mycroft@gnu.ai.mit.edu (Charles Hannum) for unsigned
+ *
+ * Revision 1.13  1994/01/21  01:27:01  christos
  * Fixed null termination bug from Don Seeley at BSDI in ascmagic.c
  *
  * Revision 1.12  1993/10/27  20:59:05  christos
index 7114a7bd571910e1423c0a37862343c37f769b53..a91f4297e61596f6ce2415a4139a464c96ec2615 100644 (file)
@@ -40,7 +40,7 @@
 
 #ifndef lint
 static char *moduleid =
-       "@(#)$Id: print.c,v 1.20 1993/09/23 20:26:25 christos Exp $";
+       "@(#)$Id: print.c,v 1.21 1994/05/03 17:58:23 christos Exp $";
 #endif  /* lint */
 
 #define SZOF(a)        (sizeof(a) / sizeof(a[0]))
@@ -49,33 +49,29 @@ void
 mdump(m)
 struct magic *m;
 {
-       static char *offs[] = {  "absolute", "offset", 
-                                "indirect", "indirect-offset" };
        static char *typ[] = {   "invalid", "byte", "short", "invalid",
                                 "long", "string", "date", "beshort",
                                 "belong", "bedate", "leshort", "lelong",
                                 "ledate" };
-       (void) fprintf(stderr, "[%s,%d,",
-               (m->flag >= 0 && m->flag < SZOF(offs) ? offs[m->flag]: "*bad*"),
-               m->offset);
-
+       (void) fputc('[', stderr);
+       (void) fprintf(stderr, ">>>>>>>> %d" + 8 - (m->cont_level & 7),
+                      m->offset);
 
        if (m->flag & INDIR)
-           (void) fprintf(stderr, "(%s,%d),",
-               (m->in.type >= 0 && 
-                m->in.type < SZOF(typ) ? 
-                   typ[(unsigned char) m->in.type] : "*bad*"),
-               m->in.offset);
+               (void) fprintf(stderr, "(%s,%d),",
+                              (m->in.type >= 0 && m->in.type < SZOF(typ)) ? 
+                                       typ[(unsigned char) m->in.type] :
+                                       "*bad*",
+                              m->in.offset);
 
-       (void) fputs((m->type >= 0 && m->type < SZOF(typ)) ? 
-                       typ[(unsigned char) m->type] : 
-                       "*bad*", 
-                    stderr);
+       (void) fprintf(stderr, " %s%s", (m->flag & UNSIGNED) ? "u" : "",
+                      (m->type >= 0 && m->type < SZOF(typ)) ? 
+                               typ[(unsigned char) m->type] : 
+                               "*bad*");
+       if (m->mask != ~0L)
+               (void) fprintf(stderr, " & %.8x", m->mask);
 
-       if (m->reln == 'x')
-           (void) fputs(",*any*", stderr);
-       else
-           (void) fprintf(stderr, ",%c", m->reln);
+       (void) fprintf(stderr, ",%c", m->reln);
 
        if (m->reln != 'x') {
            switch (m->type) {
index 5bcf0bf8c35134000506efb91ce19d54e192092e..a89b0a76f586239d0fcc24f81ffd1b28725d4865 100644 (file)
@@ -34,7 +34,7 @@
 
 #ifndef        lint
 static char *moduleid = 
-       "@(#)$Id: softmagic.c,v 1.24 1993/10/27 20:59:05 christos Exp $";
+       "@(#)$Id: softmagic.c,v 1.25 1994/05/03 17:58:23 christos Exp $";
 #endif /* lint */
 
 static int match       __P((unsigned char *, int));
@@ -173,22 +173,26 @@ union VALUETYPE *p;
 struct magic *m;
 {
        char *pp, *rt;
-       unsigned long mask = m->mask ? m->mask : ~0;
+       unsigned long v;
+
 
        switch (m->type) {
        case BYTE:
-               (void) printf(m->desc, (unsigned char) p->b & mask);
-               break;
+               v = p->b;
+               break;
+
        case SHORT:
        case BESHORT:
        case LESHORT:
-               (void) printf(m->desc, (unsigned short) p->h & mask);
-               break;
+               v = p->h;
+               break;
+
        case LONG:
        case BELONG:
        case LELONG:
-               (void) printf(m->desc, (unsigned long) p->l & mask);
+               v = p->l;
                break;
+
        case STRING:
                if (m->reln == '=') {
                        (void) printf(m->desc, m->value.s);
@@ -198,7 +202,8 @@ struct magic *m;
                                *rt = '\0';
                        (void) printf(m->desc, p->s);
                }
-               break;
+               return;
+
        case DATE:
        case BEDATE:
        case LEDATE:
@@ -206,11 +211,14 @@ struct magic *m;
                if ((rt = strchr(pp, '\n')) != NULL)
                        *rt = '\0';
                (void) printf(m->desc, pp);
-               break;
+               return;
        default:
                error("invalid m->type (%d) in mprint().\n", m->type);
                /*NOTREACHED*/
        }
+
+       v = signextend(m, v) & m->mask;
+       (void) printf(m->desc, (unsigned char) v);
 }
 
 /*
@@ -321,8 +329,9 @@ mcheck(p, m)
 union VALUETYPE* p;
 struct magic *m;
 {
-       register long l = m->value.l;
-       register long v;
+       register unsigned long l = m->value.l;
+       register unsigned long v;
+       int matched;
 
        if ( (m->value.s[0] == 'x') && (m->value.s[1] == '\0') ) {
                fprintf(stderr, "BOINK");
@@ -373,42 +382,58 @@ struct magic *m;
                return 0;/*NOTREACHED*/
        }
 
-       if (m->mask != 0L)
-               v &= m->mask;
+       v = signextend(m, v) & m->mask;
 
        switch (m->reln) {
        case 'x':
                if (debug)
                        (void) fprintf(stderr, "%d == *any* = 1\n", v);
-               return 1;
+               matched = 1;
+               break;
+
        case '!':
                if (debug)
                        (void) fprintf(stderr, "%d != %d = %d\n", v, l, v != l);
-               return v != l;
+               matched = v != l;
+               break;
+
        case '=':
                if (debug)
                        (void) fprintf(stderr, "%d == %d = %d\n", v, l, v == l);
-               return v == l;
+               matched = v == l;
+               break;
+
        case '>':
                if (debug)
                        (void) fprintf(stderr, "%d > %d = %d\n", v, l, v > l);
-               return v > l;
+               matched = v > l;
+               break;
+
        case '<':
                if (debug)
                        (void) fprintf(stderr, "%d < %d = %d\n", v, l, v < l);
-               return v < l;
+               matched = v < l;
+               break;
+
        case '&':
                if (debug)
                        (void) fprintf(stderr, "((%x & %x) == %x) = %d\n",
                                       v, l, l, (v & l) == l);
-               return (v & l) == l;
+               matched = (v & l) == l;
+               break;
+
        case '^':
                if (debug)
                        (void) fprintf(stderr, "((%x & %x) != %x) = %d\n",
                                       v, l, l, (v & l) != l);
-               return (v & l) != l;
+               matched = (v & l) != l;
+               break;
+
        default:
+               matched = 0;
                error("mcheck: can't happen: invalid relation %d.\n", m->reln);
-               return 0;/*NOTREACHED*/
+               break;/*NOTREACHED*/
        }
+
+       return matched;
 }