home *** CD-ROM | disk | FTP | other *** search
/ ftp.ncftp.com / ftp.ncftp.com.zip / ftp.ncftp.com / ncftp / older_versions / ncftp-3.2.2-src.tar.bz2 / ncftp-3.2.2-src.tar / ncftp-3.2.2 / libncftp / lglobr.c < prev    next >
C/C++ Source or Header  |  2005-01-01  |  4KB  |  177 lines

  1. /* lglobr.c
  2.  *
  3.  * Copyright (c) 1996-2005 Mike Gleason, NcFTP Software.
  4.  * All rights reserved.
  5.  *
  6.  */
  7.  
  8. #include "syshdrs.h"
  9. #ifdef PRAGMA_HDRSTOP
  10. #    pragma hdrstop
  11. #endif
  12.  
  13. /* Used by FTPLocalRecursiveFileList */
  14. typedef struct LRFLState {
  15.     int relativePathStartOffset;
  16.     FTPFileInfoListPtr filp;
  17. } LRFLState;
  18.  
  19.  
  20. static int
  21. FTPLocalRecursiveFileListFtwProc(const FtwInfoPtr ftwip)
  22. {
  23.     FTPFileInfo fi;
  24.     mode_t m;
  25.     LRFLState *lrflstate;
  26.     const char *cp;
  27.  
  28.     if ((ftwip->curPath[0] == '\0') || (strcmp(ftwip->curPath, ".") == 0))
  29.         return (0);
  30.  
  31.     lrflstate = (LRFLState *) ftwip->userdata;
  32.     cp = ftwip->curPath;
  33.     if (lrflstate->relativePathStartOffset > 0) {
  34.         cp += lrflstate->relativePathStartOffset;
  35.         if (IsLocalPathDelim(*cp))
  36.             cp++;
  37.     }
  38.     fi.relname = StrDup(cp);
  39.     fi.rname = NULL;
  40.     fi.lname = StrDup(ftwip->curPath);
  41.     fi.mdtm = ftwip->curStat.st_mtime;
  42.     fi.rlinkto = NULL;
  43.     fi.plug = NULL;
  44.  
  45.     m = ftwip->curStat.st_mode;
  46.     if (S_ISREG(m) != 0) {
  47.         /* file */
  48.         fi.type = '-';
  49.         fi.size = (longest_int) ftwip->curStat.st_size;
  50.         (void) AddFileInfo(lrflstate->filp, &fi);
  51. #ifdef LGLOBR_DEBUG
  52.         (void) fprintf(stderr, "- %s\n", fi.lname);
  53. #endif
  54.     } else if (S_ISDIR(m)) {
  55.         /* directory */
  56.         fi.type = 'd';
  57.         fi.size = (longest_int) 0;
  58.         (void) AddFileInfo(lrflstate->filp, &fi);
  59. #ifdef LGLOBR_DEBUG
  60.         (void) fprintf(stderr, "d %s\n", fi.lname);
  61. #endif
  62. #if defined(S_ISLNK) && defined(HAVE_READLINK)
  63.     } else if (S_ISLNK(m)) {
  64.         /* symbolic link */
  65.         fi.type = 'l';
  66.         fi.size = (longest_int) 0;
  67.         fi.rlinkto = calloc(256, 1);
  68.         if (fi.rlinkto != NULL) {
  69.             if (readlink(ftwip->curPath, fi.rlinkto, 255) < 0) {
  70.                 free(fi.rlinkto);
  71.                 fi.rlinkto = NULL;
  72.             } else {
  73.                 (void) AddFileInfo(lrflstate->filp, &fi);
  74.             }
  75.         }
  76.         if (fi.rlinkto == NULL) {
  77.             free(fi.relname);
  78.             free(fi.lname);
  79.         }
  80. #    ifdef LGLOBR_DEBUG
  81.         (void) fprintf(stderr, "l %s -> %s\n", fi.lname, fi.rlinkto);
  82. #    endif
  83. #endif    /* S_ISLNK */
  84.     } else {
  85.         /* Unknown type, skip it */
  86. #ifdef LGLOBR_DEBUG
  87.         (void) fprintf(stderr, "! %s\n", fi.lname);
  88. #endif
  89.         free(fi.relname);
  90.         free(fi.lname);
  91.     }
  92.  
  93.     return (0);
  94. }    /* FTPLocalRecursiveFileListFtwProc */
  95.  
  96.  
  97.  
  98.  
  99. int
  100. FTPLocalRecursiveFileList2(FTPCIPtr cip, FTPLineListPtr fileList, FTPFileInfoListPtr files, int erelative)
  101. {
  102.     FTPLinePtr filePtr, nextFilePtr;
  103.     char *cp;
  104.     FtwInfo ftwi;
  105.     LRFLState lrflstate;
  106.     struct Stat st;
  107.     FTPFileInfo fi;
  108.  
  109.     FtwInit(&ftwi);
  110.     InitFileInfoList(files);
  111.     lrflstate.filp = files;
  112.  
  113.     for (filePtr = fileList->first;
  114.         filePtr != NULL;
  115.         filePtr = nextFilePtr)
  116.     {
  117.         nextFilePtr = filePtr->next;
  118.  
  119.         StrRemoveTrailingLocalPathDelim(filePtr->line);
  120.         cp = NULL;
  121.         if (erelative != 0) {
  122.             /* Relative paths requested */
  123.             cp = filePtr->line;
  124.             lrflstate.relativePathStartOffset = (int) strlen(cp);
  125.         } else if (strcmp(filePtr->line, ".") == 0) {
  126.             /* special case: . */
  127.             lrflstate.relativePathStartOffset = 1;
  128.         } else if (IsLocalPathDelim(filePtr->line[0]) && (filePtr->line[1] == '\0')) {
  129.             /* special case: root directory */
  130.             lrflstate.relativePathStartOffset = 1;
  131.         } else if ((cp = StrRFindLocalPathDelim(filePtr->line)) == NULL) {
  132.             /* Don't skip anything if this is a directory */
  133.             lrflstate.relativePathStartOffset = 0;
  134.             cp = filePtr->line;
  135.         } else {
  136.             /* Skip everything except the basename directory */
  137.             cp++;
  138.             lrflstate.relativePathStartOffset = (int) (cp - filePtr->line);
  139.         }
  140.  
  141.         /* Use Stat rather than Lstat so top level path can be a link. */
  142.         if (Stat(filePtr->line[0] == '\0' ? "." : filePtr->line, &st) < 0) {
  143.             FTPLogError(cip, kDoPerror, "could not stat %s.\n", filePtr->line[0] == '\0' ? "." : filePtr->line);
  144.             continue;
  145.         }
  146.  
  147.         if (S_ISDIR(st.st_mode) == 0) {
  148.             fi.relname = StrDup(cp);
  149.             fi.rname = NULL;
  150.             fi.lname = StrDup(filePtr->line);
  151.             fi.mdtm = st.st_mtime;
  152.             fi.size = (longest_int) st.st_size;
  153.             fi.rlinkto = NULL;
  154.             fi.plug = NULL;
  155.             fi.type = '-';
  156.             (void) AddFileInfo(files, &fi);
  157.             continue;            /* wasn't a directory */
  158.         }
  159.  
  160.         /* Paths collected must be relative. */
  161.         ftwi.userdata = &lrflstate;
  162.         (void) Ftw(&ftwi, filePtr->line, FTPLocalRecursiveFileListFtwProc);
  163.     }
  164.  
  165.     FtwDispose(&ftwi);
  166.     return (kNoErr);
  167. }    /* FTPLocalRecursiveFileList2 */
  168.  
  169.  
  170.  
  171.  
  172. int
  173. FTPLocalRecursiveFileList(FTPCIPtr cip, FTPLineListPtr fileList, FTPFileInfoListPtr files)
  174. {
  175.     return (FTPLocalRecursiveFileList2(cip, fileList, files, 0));
  176. }    /* FTPLocalRecursiveFileList */
  177.