]> git.sur5r.net Git - bacula/bacula/blobdiff - bacula/src/findlib/find.c
kes Apply patch supplied in bug #656 to pass priority field
[bacula/bacula] / bacula / src / findlib / find.c
index ce6d210a73b804daaabba9aa095b7deddb13b8db..95ee92e1499b2530444903ca8401edc15df6fef7 100644 (file)
  *   Version $Id$
  */
 /*
  *   Version $Id$
  */
 /*
-   Copyright (C) 2000-2005 Kern Sibbald
+   Copyright (C) 2000-2006 Kern Sibbald
 
    This program is free software; you can redistribute it and/or
    modify it under the terms of the GNU General Public License
 
    This program is free software; you can redistribute it and/or
    modify it under the terms of the GNU General Public License
-   version 2 as ammended with additional clauses defined in the
+   version 2 as amended with additional clauses defined in the
    file LICENSE in the main source directory.
 
    This program is distributed in the hope that it will be useful,
    file LICENSE in the main source directory.
 
    This program is distributed in the hope that it will be useful,
@@ -38,13 +38,7 @@ int32_t path_max;              /* path name max length */
 static int our_callback(FF_PKT *ff, void *hpkt, bool top_level);
 static bool accept_file(FF_PKT *ff);
 
 static int our_callback(FF_PKT *ff, void *hpkt, bool top_level);
 static bool accept_file(FF_PKT *ff);
 
-/* Fold case in fnmatch() on Win32 */
-#ifdef WIN32
-static const int fnmode = FNM_CASEFOLD;
-#else
 static const int fnmode = 0;
 static const int fnmode = 0;
-#endif
-
 
 /*
  * Initialize the find files "global" variables
 
 /*
  * Initialize the find files "global" variables
@@ -103,7 +97,7 @@ get_win32_driveletters(FF_PKT *ff, char* szDrives)
 {
    /* szDrives must be at least 27 bytes long */
 
 {
    /* szDrives must be at least 27 bytes long */
 
-#ifndef WIN32
+#if !defined(HAVE_WIN32)
    return 0;
 #endif
 
    return 0;
 #endif
 
@@ -121,8 +115,8 @@ get_win32_driveletters(FF_PKT *ff, char* szDrives)
          for (j=0; j<incexe->name_list.size(); j++) {
             char *fname = (char *)incexe->name_list.get(j);
             /* fname should match x:/ */
          for (j=0; j<incexe->name_list.size(); j++) {
             char *fname = (char *)incexe->name_list.get(j);
             /* fname should match x:/ */
-            if (strlen (fname) > 3 && B_ISALPHA(fname[0]) 
-               && fname[1] == ':' && fname[2] == '/') {
+            if (strlen(fname) >= 2 && B_ISALPHA(fname[0]) 
+               && fname[1] == ':') {
                
                /* always add in uppercase */
                char ch = toupper(fname[0]);
                
                /* always add in uppercase */
                char ch = toupper(fname[0]);
@@ -180,12 +174,13 @@ find_files(JCR *jcr, FF_PKT *ff, int callback(FF_PKT *ff_pkt, void *hpkt, bool t
             ff->flags |= fo->flags;
             ff->GZIP_level = fo->GZIP_level;
             ff->fstypes = fo->fstype;
             ff->flags |= fo->flags;
             ff->GZIP_level = fo->GZIP_level;
             ff->fstypes = fo->fstype;
+            ff->drivetypes = fo->drivetype;
             bstrncat(ff->VerifyOpts, fo->VerifyOpts, sizeof(ff->VerifyOpts));
          }
          for (j=0; j<incexe->name_list.size(); j++) {
             Dmsg1(100, "F %s\n", (char *)incexe->name_list.get(j));
             bstrncat(ff->VerifyOpts, fo->VerifyOpts, sizeof(ff->VerifyOpts));
          }
          for (j=0; j<incexe->name_list.size(); j++) {
             Dmsg1(100, "F %s\n", (char *)incexe->name_list.get(j));
-            char *fname = (char *)incexe->name_list.get(j);
-            if (find_one_file(jcr, ff, our_callback, his_pkt, fname, (dev_t)-1, true) == 0) {
+            ff->top_fname = (char *)incexe->name_list.get(j);
+            if (find_one_file(jcr, ff, our_callback, his_pkt, ff->top_fname, (dev_t)-1, true) == 0) {
                return 0;                  /* error return */
             }
          }
                return 0;                  /* error return */
             }
          }
@@ -197,9 +192,22 @@ find_files(JCR *jcr, FF_PKT *ff, int callback(FF_PKT *ff_pkt, void *hpkt, bool t
 static bool accept_file(FF_PKT *ff)
 {
    int i, j, k;
 static bool accept_file(FF_PKT *ff)
 {
    int i, j, k;
-   int ic;
+   int fnm_flags;
    findFILESET *fileset = ff->fileset;
    findINCEXE *incexe = fileset->incexe;
    findFILESET *fileset = ff->fileset;
    findINCEXE *incexe = fileset->incexe;
+   const char *basename;
+   int (*match_func)(const char *pattern, const char *string, int flags);
+
+   if (ff->flags & FO_ENHANCEDWILD) {
+      match_func = enh_fnmatch;
+      if ((basename = strrchr(ff->fname, '/')) != NULL)
+         basename++;
+      else
+         basename = ff->fname;
+   } else {
+      match_func = fnmatch;
+      basename = ff->fname;
+   }
 
    for (j=0; j<incexe->opts_list.size(); j++) {
       findFOPTS *fo = (findFOPTS *)incexe->opts_list.get(j);
 
    for (j=0; j<incexe->opts_list.size(); j++) {
       findFOPTS *fo = (findFOPTS *)incexe->opts_list.get(j);
@@ -208,21 +216,25 @@ static bool accept_file(FF_PKT *ff)
       ff->reader = fo->reader;
       ff->writer = fo->writer;
       ff->fstypes = fo->fstype;
       ff->reader = fo->reader;
       ff->writer = fo->writer;
       ff->fstypes = fo->fstype;
-      ic = (ff->flags & FO_IGNORECASE) ? FNM_CASEFOLD : 0;
+      ff->drivetypes = fo->drivetype;
+
+      fnm_flags = (ff->flags & FO_IGNORECASE) ? FNM_CASEFOLD : 0;
+      fnm_flags |= (ff->flags & FO_ENHANCEDWILD) ? FNM_PATHNAME : 0;
+
       if (S_ISDIR(ff->statp.st_mode)) {
          for (k=0; k<fo->wilddir.size(); k++) {
       if (S_ISDIR(ff->statp.st_mode)) {
          for (k=0; k<fo->wilddir.size(); k++) {
-            if (fnmatch((char *)fo->wilddir.get(k), ff->fname, fnmode|ic) == 0) {
+            if (match_func((char *)fo->wilddir.get(k), ff->fname, fnmode|fnm_flags) == 0) {
                if (ff->flags & FO_EXCLUDE) {
                   Dmsg2(100, "Exclude wilddir: %s file=%s\n", (char *)fo->wilddir.get(k),
                      ff->fname);
                if (ff->flags & FO_EXCLUDE) {
                   Dmsg2(100, "Exclude wilddir: %s file=%s\n", (char *)fo->wilddir.get(k),
                      ff->fname);
-                  return false;       /* reject file */
+                  return false;       /* reject dir */
                }
                }
-               return true;           /* accept file */
+               return true;           /* accept dir */
             }
          }
       } else {
          for (k=0; k<fo->wildfile.size(); k++) {
             }
          }
       } else {
          for (k=0; k<fo->wildfile.size(); k++) {
-            if (fnmatch((char *)fo->wildfile.get(k), ff->fname, fnmode|ic) == 0) {
+            if (match_func((char *)fo->wildfile.get(k), ff->fname, fnmode|fnm_flags) == 0) {
                if (ff->flags & FO_EXCLUDE) {
                   Dmsg2(100, "Exclude wildfile: %s file=%s\n", (char *)fo->wildfile.get(k),
                      ff->fname);
                if (ff->flags & FO_EXCLUDE) {
                   Dmsg2(100, "Exclude wildfile: %s file=%s\n", (char *)fo->wildfile.get(k),
                      ff->fname);
@@ -231,9 +243,20 @@ static bool accept_file(FF_PKT *ff)
                return true;           /* accept file */
             }
          }
                return true;           /* accept file */
             }
          }
+
+         for (k=0; k<fo->wildbase.size(); k++) {
+            if (match_func((char *)fo->wildbase.get(k), basename, fnmode|fnm_flags) == 0) {
+               if (ff->flags & FO_EXCLUDE) {
+                  Dmsg2(100, "Exclude wildbase: %s file=%s\n", (char *)fo->wildbase.get(k),
+                     basename);
+                  return false;       /* reject file */
+               }
+               return true;           /* accept file */
+            }
+         }
       }
       for (k=0; k<fo->wild.size(); k++) {
       }
       for (k=0; k<fo->wild.size(); k++) {
-         if (fnmatch((char *)fo->wild.get(k), ff->fname, fnmode|ic) == 0) {
+         if (match_func((char *)fo->wild.get(k), ff->fname, fnmode|fnm_flags) == 0) {
             if (ff->flags & FO_EXCLUDE) {
                Dmsg2(100, "Exclude wild: %s file=%s\n", (char *)fo->wild.get(k),
                   ff->fname);
             if (ff->flags & FO_EXCLUDE) {
                Dmsg2(100, "Exclude wild: %s file=%s\n", (char *)fo->wild.get(k),
                   ff->fname);
@@ -242,7 +265,6 @@ static bool accept_file(FF_PKT *ff)
             return true;              /* accept file */
          }
       }
             return true;              /* accept file */
          }
       }
-#ifndef WIN32
       if (S_ISDIR(ff->statp.st_mode)) {
          for (k=0; k<fo->regexdir.size(); k++) {
             const int nmatch = 30;
       if (S_ISDIR(ff->statp.st_mode)) {
          for (k=0; k<fo->regexdir.size(); k++) {
             const int nmatch = 30;
@@ -276,7 +298,6 @@ static bool accept_file(FF_PKT *ff)
             return true;              /* accept file */
          }
       }
             return true;              /* accept file */
          }
       }
-#endif
       /*
        * If we have an empty Options clause with exclude, then
        *  exclude the file
       /*
        * If we have an empty Options clause with exclude, then
        *  exclude the file
@@ -284,7 +305,8 @@ static bool accept_file(FF_PKT *ff)
       if (ff->flags & FO_EXCLUDE &&
           fo->regex.size() == 0     && fo->wild.size() == 0 &&
           fo->regexdir.size() == 0  && fo->wilddir.size() == 0 &&
       if (ff->flags & FO_EXCLUDE &&
           fo->regex.size() == 0     && fo->wild.size() == 0 &&
           fo->regexdir.size() == 0  && fo->wilddir.size() == 0 &&
-          fo->regexfile.size() == 0 && fo->wildfile.size() == 0) {
+          fo->regexfile.size() == 0 && fo->wildfile.size() == 0 &&
+          fo->wildbase.size() == 0) {
          return false;              /* reject file */
       }
    }
          return false;              /* reject file */
       }
    }
@@ -294,18 +316,18 @@ static bool accept_file(FF_PKT *ff)
       findINCEXE *incexe = (findINCEXE *)fileset->exclude_list.get(i);
       for (j=0; j<incexe->opts_list.size(); j++) {
          findFOPTS *fo = (findFOPTS *)incexe->opts_list.get(j);
       findINCEXE *incexe = (findINCEXE *)fileset->exclude_list.get(i);
       for (j=0; j<incexe->opts_list.size(); j++) {
          findFOPTS *fo = (findFOPTS *)incexe->opts_list.get(j);
-         ic = (fo->flags & FO_IGNORECASE) ? FNM_CASEFOLD : 0;
+         fnm_flags = (fo->flags & FO_IGNORECASE) ? FNM_CASEFOLD : 0;
          for (k=0; k<fo->wild.size(); k++) {
          for (k=0; k<fo->wild.size(); k++) {
-            if (fnmatch((char *)fo->wild.get(k), ff->fname, fnmode|ic) == 0) {
+            if (fnmatch((char *)fo->wild.get(k), ff->fname, fnmode|fnm_flags) == 0) {
                Dmsg1(100, "Reject wild1: %s\n", ff->fname);
                return false;          /* reject file */
             }
          }
       }
                Dmsg1(100, "Reject wild1: %s\n", ff->fname);
                return false;          /* reject file */
             }
          }
       }
-      ic = (incexe->current_opts != NULL && incexe->current_opts->flags & FO_IGNORECASE)
+      fnm_flags = (incexe->current_opts != NULL && incexe->current_opts->flags & FO_IGNORECASE)
              ? FNM_CASEFOLD : 0;
       for (j=0; j<incexe->name_list.size(); j++) {
              ? FNM_CASEFOLD : 0;
       for (j=0; j<incexe->name_list.size(); j++) {
-         if (fnmatch((char *)incexe->name_list.get(j), ff->fname, fnmode|ic) == 0) {
+         if (fnmatch((char *)incexe->name_list.get(j), ff->fname, fnmode|fnm_flags) == 0) {
             Dmsg1(100, "Reject wild2: %s\n", ff->fname);
             return false;          /* reject file */
          }
             Dmsg1(100, "Reject wild2: %s\n", ff->fname);
             return false;          /* reject file */
          }
@@ -333,6 +355,7 @@ static int our_callback(FF_PKT *ff, void *hpkt, bool top_level)
    case FT_NORECURSE:
    case FT_NOFSCHG:
    case FT_INVALIDFS:
    case FT_NORECURSE:
    case FT_NOFSCHG:
    case FT_INVALIDFS:
+   case FT_INVALIDDT:
    case FT_NOOPEN:
 //    return ff->callback(ff, hpkt, top_level);
 
    case FT_NOOPEN:
 //    return ff->callback(ff, hpkt, top_level);