home *** CD-ROM | disk | FTP | other *** search
/ rtsi.com / 2014.01.www.rtsi.com.tar / www.rtsi.com / OS9 / OSK / CMDS / cowen_tools.lzh / delbak.c < prev    next >
C/C++ Source or Header  |  1992-03-06  |  7KB  |  286 lines

  1. /*
  2. ** Delbak
  3. **  Deletes all files in current directory with names
  4. **  ending in _bak (or alternative given -f option)
  5. **  and optionaly recursively down the tree.
  6. **  optionally will merely list files instead of deleting them.
  7. **
  8. **     options are:
  9. **            -n = no recursion
  10. **            -l = list only
  11. **            -f = extension to delete on, default = _bak
  12. **            -? = report usage
  13. **
  14. ** 
  15. **  copyright 1991 by Cowen Software Ltd
  16. **  23 Bristol Ave, Levenshulme, Manchester,
  17. **  GB-M19 3NU, England, UK
  18. **  released to the public domain for non-commercial use
  19. **  
  20. */
  21.  
  22.  
  23. #include <stdio.h>
  24. #include <modes.h>
  25. #include <ctype.h>
  26.  
  27. #define TRUE  1
  28. #define FALSE 0
  29. #define trace FALSE
  30. #define FNSIZ     132
  31. #define dirlength 300
  32. #define maxf      20
  33.  
  34. struct dirent {
  35.      char dir_name[29];
  36.      char dir_addr[3];
  37.      } ;
  38.  
  39. char  rflag = TRUE;                            /* recursive*/
  40. char  lflag = FALSE;                           /* list only*/
  41. char  fflag = FALSE;                           /* file specified 
  42.                                                   (default = curr dir */
  43. char  defdir[] = ".";                          /* default directory */
  44.  
  45. char  dirname[dirlength];                      /* holds expanded filenames*/ 
  46. char  filename[32];                            /* holds each file name */ 
  47.  
  48. char  *fptr[maxf];
  49. int   flen[maxf];
  50. int   numf = 0;
  51.  
  52. int   i;
  53.  
  54. char  dext[] = "_bak";
  55.  
  56. /*page*/
  57. main(argc,argv)
  58. int   argc;
  59. char  **argv;
  60.    {
  61.    char *p;
  62.  
  63.    getflags(argc,argv);
  64.    
  65.    if (numf == 0) fptr[numf++] = dext;
  66.    for (i=0;i<numf;i++)
  67.        flen[i] = strlen(fptr[i]);
  68.    
  69.    if ( fflag )
  70.       {
  71.       while (--argc) 
  72.          if (*(p = *++argv) != '-')
  73.             dodel(p);
  74.       }
  75.    else
  76.       dodel(defdir);
  77.    }   
  78.  
  79.  
  80.  
  81. getflags(carg,varg)
  82.  int   carg;
  83. char  **varg;
  84.    {
  85.    char  *p, c;
  86.    while ( (--carg) )
  87.       {
  88.       if (*(p = *++varg) == '-')
  89.          {
  90.          while (c = *++p)
  91.             {
  92.             switch (c)
  93.                {
  94.                case 'n' :
  95.                      rflag = FALSE;                   /* not recursive*/
  96.                      break; 
  97.                case 'l' :                             /*list only*/
  98.                      lflag = TRUE;
  99.                      break;
  100.                case 'f' :
  101.                      while(*++p == ' ');
  102.                      if (*p++ != '=') error ("no suffix for -f option",0);
  103.                      if (*p == '\0') error ("null suffix for -f option",0);
  104.                      if (numf >= maxf) error("Too many -f parameters",0);
  105.                      fptr[numf++] = p;
  106.                      while (c = *p) p++;   /* skip past extension name */
  107.                      p--;                  /* and point to the closing null */
  108.                      break;
  109.                case '?' :
  110.                      help();
  111.                default  :
  112.                      error("bad option",0);
  113.                }
  114.             }
  115.          }
  116.       else
  117.          fflag = TRUE;
  118.  
  119.       }
  120.    }   
  121.  
  122.  
  123.  
  124. dodel(rootname)
  125. char  *rootname;
  126. /*    This procedure is called for each root directory 
  127.       which is to be cleaned up.
  128.       It copies the root dir to dirname, then starts the 
  129.       recursive calls to donext. 
  130.       NOTE if the total path name ever goes beyond 300 words
  131.       then this procedure will fail!!!.
  132. */
  133.       
  134.    {
  135.    int fd;
  136.    int nlen;                                /* length of filename*/
  137.  
  138.    strcpy(dirname, rootname); 
  139.    nlen = strlen(dirname);
  140.    if ( (fd = open(dirname,S_IFDIR + S_IREAD) ) == -1)
  141.           error ("Can't open file ",dirname);
  142.    donext(fd,nlen);
  143.  
  144.    }
  145.  
  146.  
  147.  
  148. donext(fd,nlen)
  149. int   fd;                                /* dir path */
  150. int nlen;                                /* length of filename*/
  151.  
  152. /*    This procedure is called for each directory 
  153.       which is to be cleaned up.
  154.       It opens the directory, and reads all files in it.
  155.       Each valid file is passed to checkfile for processing
  156.       NOTE the file name as given on entry has each 
  157.       filename in turn appended to it, then the original length restored
  158.       this means that we must check to see if the tree of directories
  159.       has got too long, and overflowed the dirname buffer.
  160. */
  161.       
  162.    {
  163.    struct dirent     dirbuf;                /* single dir ent read buf */
  164.  
  165.  
  166. #if trace
  167. fprintf(stderr,"donext %d \n",fd);
  168. fflush(stderr);
  169. #endif
  170.  
  171.    while(read(fd, &dirbuf, sizeof(dirbuf)))       /* now copy names */
  172.        {
  173.       if (isalpha(dirbuf.dir_name[0] & 0x7f))
  174.             {
  175.             strhcpy(filename, &dirbuf);
  176.             filename[28] = '\0';                  /* shouldn't be needed
  177.                                                   but I am a pessimist */
  178.             if (nlen + 2 + strlen(filename) > dirlength)
  179.                 error ("Tree structure has too many levels", dirname);
  180.             
  181.             dirname[nlen] = '/';
  182.             dirname[nlen+1] = '\0';                                       
  183.             strcat(dirname,filename);             /* stick the next element
  184.                                                   on to the filename*/ 
  185.             checkfile();                          /* check this file */ 
  186.             dirname[nlen] = '\0';                 /* restore original length*/
  187.             }
  188.       }
  189.  
  190.    close(fd);
  191.    }
  192.  
  193.  
  194.  
  195. checkfile()
  196.  
  197. /*   now check each file, as follows
  198.      1, try to open it as a directory, if it is one then 
  199.         pass it back to donext (unless rflag is false  ie -n) .
  200.      2. otherwise look at the filename.  if it is .bak 
  201.         then delete the file, unless lflag is true - ie -l.
  202.         in which case just output the file name.
  203. */
  204.  
  205.    {
  206.    int fd;
  207.    int nlen;
  208.    
  209.    nlen = strlen(dirname);
  210.    if ( ( (fd = open(dirname,S_IFDIR + S_IREAD) ) != -1) && rflag)
  211.           donext(fd,nlen);
  212.    else 
  213.           for (i=0;i<numf;i++)
  214.              {
  215.  
  216.              if ( ! strucmp(fptr[i],&dirname[nlen-flen[i]]) )
  217.                 {
  218.                 delfile();
  219.                 break;
  220.                 }
  221.  
  222.              }
  223.    }
  224.    
  225.   
  226.  
  227. delfile()
  228. /* Now we have a file to delete - delete it or if lflag just
  229. list it.
  230. */
  231.    {
  232.    int x;
  233.  
  234.    if (lflag)   printf(" %s\n",dirname);    
  235.    else
  236.        {
  237.        if (!lflag) (x = unlink(dirname) );   
  238.        printf(" %s ", dirname);
  239.        if (!x) printf("deleted\n");
  240.        else   printf("delete failed\n");
  241.        }
  242.    }
  243.    
  244.                             
  245.  
  246.  
  247.  
  248.  
  249.  
  250. error(s1, s2)
  251. char  *s1, *s2;
  252.  
  253. /*
  254. ** write the two strings passed and then a <cr>
  255. */
  256.  
  257.    {
  258.  
  259.    if (s1)
  260.          fprintf(stderr, "%s", s1 );
  261.    if (s2)
  262.          fprintf(stderr, "%s", s2 );
  263.    fprintf(stderr, "\n");
  264.    fflush(stderr);
  265.    exit (1);
  266.    }
  267.  
  268.  
  269.  
  270. help()
  271.  
  272. /*
  273. ** provide usage info for this command
  274. */
  275.  
  276.    {
  277.    fprintf(stderr, "Usage: delbak [-options] [directory] [-options]\n" );
  278.    fprintf(stderr, "     -n      = no recursion\n" );
  279.    fprintf(stderr, "     -l      = list only   \n" );
  280.    fprintf(stderr, "     -f=<ext>= extension to delete, default _bak\n" );
  281.    fprintf(stderr, "     -?      = report help \n" );
  282.    fprintf(stderr, "\n");
  283.    fflush(stderr);
  284.    exit (0);
  285.    }
  286.