"Fossies" - the Fresh Open Source Software Archive

Member "afio-2.5.2/match.c" (30 Nov 2018, 4957 Bytes) of package /linux/misc/afio-2.5.2.tgz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "match.c" see the Fossies "Dox" file reference documentation.

    1 #include <stdio.h>
    2 #include <errno.h>
    3 #include <unistd.h>
    4 #include <string.h>
    5 #include <stdlib.h>
    6 #include <sys/signal.h>
    7 #include <sys/types.h>
    8 #include <sys/ioctl.h>
    9 #include <sys/stat.h>
   10 #include <pwd.h>
   11 #include <grp.h>
   12 #include "patchlevel.h"
   13 
   14 #ifdef HAVEFNMATCH
   15 
   16 #include <fnmatch.h>
   17 
   18 #else
   19 
   20 /* A limited fnmatch replacement. Only accepts patterns
   21    in the form "ccccc" or "ccccc*". (These were the patterns accepted
   22    by older afio versions.)
   23 
   24 */
   25 
   26 int fnmatch(const char *p, const char *s, int flag)
   27 {
   28   if(p[strlen(p)-1]=='*')
   29       return strncmp(p,s,strlen(p)-1);
   30   else
   31       return strcmp(p,s);
   32 }
   33 
   34 #endif
   35 
   36 #ifdef linux
   37 #include <utime.h>
   38 #endif
   39 
   40 #include "afio.h"
   41 
   42 STATIC int ignoreslash=1;
   43 
   44 /*
   45  * Pathnames to (or not to) be processed.
   46  */
   47 typedef struct pattern
   48 {
   49   struct pattern *p_forw;   /* Forward chain */
   50   char *p_str;          /* String */
   51   int p_len;            /* Length of string */
   52   int p_ptype;          /* Pattern type */
   53                                 /* types are: PATTYPE_MATCH, _NOMATCH, _EXT. */
   54   int p_noglob;                 /* influenced by used of -7 flag */
   55 } Pattern;
   56 
   57 STATIC Pattern *pattern;    /* Pathname matching patterns */
   58 
   59 /*
   60  * nameadd()
   61  *
   62  * Add a name to the pattern list.
   63  */
   64 STATIC void
   65 nameadd (name, ptype)
   66      reg char *name;
   67      int ptype;
   68 {
   69   reg Pattern *px;
   70 
   71   px = (Pattern *) memget (sizeof (Pattern));
   72   px->p_forw = pattern;
   73   px->p_str = strdup(name);
   74    if(px->p_str==NULL) fatal(name,"out of memory.");
   75   px->p_len = strlen (name);
   76   px->p_ptype = ptype;
   77   px->p_noglob = noglob;
   78   pattern = px;
   79 
   80   /* fprintf(stderr,"--%s added\n",name); */
   81 }
   82 
   83 /*
   84  * nameaddfile()
   85  *
   86  * Add a file of patterns to the pattern list.
   87  * Returns 0 on failure, 1 on success.
   88 */
   89 
   90 STATIC int
   91 nameaddfile(fname,ptype,parsewith0)
   92      char *fname;
   93      int ptype;
   94      int parsewith0;
   95 {
   96  FILE *infile;
   97  char pat[PATHSIZE+1];
   98  int c,i;
   99 
  100  infile=fopen(fname,"r");
  101  if(infile==0) return 0;
  102 
  103  if(parsewith0)
  104  {
  105      i=0;
  106      while((c = fgetc(infile))!=EOF)
  107      {
  108          if(i > sizeof(pat))
  109          fatal(pat,"Path name too long");
  110 
  111          pat[i]=c;
  112 
  113          if(c == '\0')
  114          {
  115               if(i>0) nameadd(pat,ptype);
  116               i=0;
  117               continue;
  118          }
  119          i++;
  120      }
  121      /* handle case where the last entry in the file does not end in \0 */
  122      if(i>0 && i<sizeof(pat))
  123        {
  124      pat[i]=0;
  125          nameadd(pat,ptype);
  126        }
  127  }
  128  else
  129  {
  130  while(fgets(pat,PATHSIZE,infile)!=NULL)
  131    {
  132     /* remove \n */
  133      pat[strlen(pat)-1]='\0';
  134 
  135      if(strlen(pat)==0) continue; /* skip empty lines in file */
  136 
  137      if(pat[strlen(pat)-1]==' ')
  138        {
  139         warn(pat,"warning: trailing space in this pattern.");
  140        }
  141 
  142      nameadd(pat,ptype);
  143    }
  144  }
  145 
  146  fclose(infile);
  147  return 1;
  148 }
  149 
  150 
  151 /*
  152  * namecmp()
  153  *
  154  * Compare a pathname with the pattern list. Returns 0 for
  155  * a match, -1 otherwise.
  156  *
  157  * This new version uses the GCC library function fnmatch()
  158  * to provide real pattern matching.
  159  *
  160  * Also, this implementation assures that if a file matches a pattern
  161  * in the `not to process' list, it is never processed.
  162  * In the old version, this depended on several implementation details
  163  * and the names in the `to process' list.
  164  *
  165  * Control files always match.
  166  */
  167 STATIC int
  168 namecmp (name, asb)
  169      reg char *name;
  170      Stat *asb;
  171 {
  172   reg Pattern *px;
  173   int existpospat; /* there are `to process' patterns in the list */
  174   char *namedot,*p,*n;
  175   char namec[PATHSIZE];
  176 
  177   /* fprintf(stderr,"name:\"%s\" rdev:%d\n",name,
  178      asb->sb_rdev);
  179   */
  180 
  181   if(asb && ISCONTROL(asb)) return 0;
  182 
  183   strcpy(namec,name);
  184   namedot = strrchr (namec, '.');
  185   if (Zflag && asb && (asb->sb_mode & S_IFMT) == S_IFREG
  186       && asb->sb_rdev == 0
  187       && namedot && namedot[1] == 'z' && !namedot[2]
  188      )
  189       *namedot = '\0';
  190     else
  191       namedot = 0;
  192 
  193   n=namec;
  194   if(ignoreslash && (n[0]=='/')) n++;
  195 
  196   for(px=pattern; px; px=px->p_forw)
  197    if((px->p_ptype)==PATTYPE_NOMATCH)
  198      {
  199        p=px->p_str;
  200        if(ignoreslash && (p[0]=='/')) p++;
  201 
  202        if (px->p_noglob)
  203      {
  204        if(strcmp(p,n)==0) return -1;
  205      }
  206        else
  207      {
  208        if(fnmatch(p,n,0)==0) return -1;
  209      }
  210      }
  211 
  212   existpospat=0;
  213 
  214   for(px=pattern; px; px=px->p_forw)
  215    if((px->p_ptype)==PATTYPE_MATCH)
  216      {
  217        existpospat=1;
  218 
  219        p=px->p_str;
  220        if(ignoreslash && (p[0]=='/')) p++;
  221 
  222        if (px->p_noglob)
  223      {
  224        if(strcmp(p,n)==0) return 0;
  225      }
  226        else
  227      {
  228        if(fnmatch(p,n,0)==0) return 0;
  229      }
  230      }
  231 
  232   if(!existpospat) return 0; else return -1;
  233 
  234 }
  235 
  236 
  237 /*
  238  * namecmp_ext()
  239  *
  240  * Compare a pathname with the extensions list. Returns 0 for
  241  * a match, -1 otherwise.
  242  *
  243  */
  244 STATIC int
  245 namecmp_ext (name)
  246      reg char *name;
  247 {
  248   reg Pattern *px;
  249   char *p,*n;
  250 
  251   n=name;
  252   if(ignoreslash && (n[0]=='/')) n++;
  253 
  254   for(px=pattern; px; px=px->p_forw)
  255    if((px->p_ptype)==PATTYPE_EXT)
  256      {
  257        p=px->p_str;
  258        if(ignoreslash && (p[0]=='/')) p++;
  259 
  260        if(fnmatch(p,n,0)==0) return 0;
  261      }
  262 
  263   return -1;
  264 }
  265 
  266