home *** CD-ROM | disk | FTP | other *** search
/ The UNIX CD Bookshelf / OREILLY_TUCB_UNIX_CD.iso / upt / examples / SOURCES / DELETE / PART02.Z / PART02 / util.c < prev   
Encoding:
C/C++ Source or Header  |  1998-07-24  |  7.9 KB  |  410 lines

  1. /*
  2.  * $Source: /afs/athena.mit.edu/astaff/project/delete/src/RCS/util.c,v $
  3.  * $Author: jik $
  4.  *
  5.  * This program is a replacement for rm.  Instead of actually deleting
  6.  * files, it marks them for deletion by prefixing them with a ".#"
  7.  * prefix.
  8.  *
  9.  * Copyright (c) 1989 by the Massachusetts Institute of Technology.
  10.  * For copying and distribution information, see the file "mit-copyright.h."
  11.  */
  12.  
  13. #if (!defined(lint) && !defined(SABER))
  14.      static char rcsid_util_c[] = "$Header: /afs/athena.mit.edu/astaff/project/delete/src/RCS/util.c,v 1.21 91/02/20 17:28:11 jik Exp $";
  15. #endif
  16.  
  17. #include <stdio.h>
  18. #include <sys/param.h>
  19. #include <sys/types.h>
  20. #ifdef SYSV /* SYSV doesn't define uid_t */
  21. typedef unsigned short uid_t;
  22. #endif
  23. #include <sys/dir.h>
  24. #ifdef SYSV
  25. #include <string.h>
  26. #define index strchr
  27. #define rindex strrchr
  28. #else
  29. #include <strings.h>
  30. #endif /* SYSV */
  31. #include <pwd.h>
  32. #include <errno.h>
  33. #ifdef AFS_MOUNTPOINTS
  34. #include <sys/ioctl.h>
  35. #include <afs/param.h>
  36. #include <afs/vice.h>
  37. #include <afs/venus.h>
  38. #endif
  39. #include "delete_errs.h"
  40. #include "util.h"
  41. #include "directories.h"
  42. #include "mit-copyright.h"
  43. #include "errors.h"
  44.  
  45. extern char *getenv();
  46. extern uid_t getuid();
  47. extern int errno;
  48.  
  49. char *convert_to_user_name(real_name, user_name)
  50. char real_name[];
  51. char user_name[];  /* RETURN */
  52. {
  53.      char *ptr, *q;
  54.      
  55.      (void) strcpy(user_name, real_name);
  56.      while (ptr = strrindex(user_name, ".#")) {
  57.       for (q = ptr; *(q + 2); q++)
  58.            *q = *(q + 2);
  59.       *q = '\0';
  60.      }
  61.      return (user_name);
  62. }
  63.  
  64.      
  65.  
  66.  
  67.  
  68. char *strindex(str, sub_str)
  69. char *str, *sub_str;
  70. {
  71.      char *ptr = str;
  72.      while (ptr = index(ptr, *sub_str)) {
  73.       if (! strncmp(ptr, sub_str, strlen(sub_str)))
  74.            return(ptr);
  75.       ptr++;
  76.      }
  77.      return ((char *) NULL);
  78. }
  79.  
  80.  
  81.  
  82. char *strrindex(str, sub_str)
  83. char *str, *sub_str;
  84. {
  85.      char *ptr;
  86.  
  87.      if (strlen(str))
  88.       ptr = &str[strlen(str) - 1];
  89.      else
  90.       return((char *) NULL);
  91.      while ((*ptr != *sub_str) && (ptr != str)) ptr--;
  92.      while (ptr != str) {
  93.       if (! strncmp(ptr, sub_str, strlen(sub_str)))
  94.            return(ptr);
  95.       ptr--;
  96.       while ((*ptr != *sub_str) && (ptr != str)) ptr--;
  97.      }
  98.      if (! strncmp(ptr, sub_str, strlen(sub_str)))
  99.       return(str);
  100.      else
  101.       return ((char *) NULL);
  102. }
  103.      
  104.      
  105. /*
  106.  * NOTE: Append uses a static array, so its return value must be
  107.  * copied immediately.
  108.  */
  109. char *append(filepath, filename)
  110. char *filepath, *filename;
  111. {
  112.      static char buf[MAXPATHLEN];
  113.  
  114.      (void) strcpy(buf, filepath);
  115.      if ((! *filename) || (! *filepath)) {
  116.       (void) strcpy(buf, filename);
  117.       return(buf);
  118.      }
  119.      if (buf[strlen(buf) - 1] == '/')
  120.       buf[strlen(buf) - 1] = '\0';
  121.      if (strlen(buf) + strlen(filename) + 2 > MAXPATHLEN) {
  122.       set_error(ENAMETOOLONG);
  123.       strncat(buf, "/", MAXPATHLEN - strlen(buf) - 1);
  124.       strncat(buf, filename, MAXPATHLEN - strlen(buf) - 1);
  125.       error(buf);
  126.        *buf = '\0';
  127.       return buf;
  128.      }
  129.      (void) strcat(buf, "/");
  130.      (void) strcat(buf, filename);
  131.      return buf;
  132. }
  133.  
  134.  
  135.  
  136.  
  137. yes() {
  138.      char buf[BUFSIZ];
  139.      char *val;
  140.      
  141.      val = fgets(buf, BUFSIZ, stdin);
  142.      if (! val) {
  143.       printf("\n");
  144.       exit(1);
  145.      }
  146.      if (! index(buf, '\n')) do
  147.       (void) fgets(buf + 1, BUFSIZ - 1, stdin);
  148.      while (! index(buf + 1, '\n'));
  149.      return(*buf == 'y');
  150. }
  151.  
  152.  
  153.  
  154.  
  155. char *lastpart(filename)
  156. char *filename;
  157. {
  158.      char *part;
  159.  
  160.      part = rindex(filename, '/');
  161.  
  162.      if (! part)
  163.       part = filename;
  164.      else if (part == filename)
  165.       part++;
  166.      else if (part - filename + 1 == strlen(filename)) {
  167.       part = rindex(--part, '/');
  168.       if (! part)
  169.            part = filename;
  170.       else
  171.            part++;
  172.      }
  173.      else
  174.       part++;
  175.  
  176.      return(part);
  177. }
  178.  
  179.  
  180.  
  181.  
  182. char *firstpart(filename, rest)
  183. char *filename;
  184. char *rest; /* RETURN */
  185. {
  186.      char *part;
  187.      static char buf[MAXPATHLEN];
  188.  
  189.      (void) strcpy(buf, filename);
  190.      part = index(buf, '/');
  191.      if (! part) {
  192.       *rest = '\0';
  193.       return(buf);
  194.      }
  195.      (void) strcpy(rest, part + 1);
  196.      *part = '\0';
  197.      return(buf);
  198. }
  199.  
  200.  
  201.  
  202.  
  203.  
  204. get_home(buf)
  205. char *buf;
  206. {
  207.      char *user;
  208.      struct passwd *psw;
  209.      
  210.      (void) strcpy(buf, getenv("HOME"));
  211.      
  212.      if (*buf)
  213.       return(0);
  214.  
  215.      user = getenv("USER");
  216.      psw = getpwnam(user);
  217.  
  218.      if (psw) {
  219.       (void) strcpy(buf, psw->pw_dir);
  220.       return(0);
  221.      }
  222.      
  223.      psw = getpwuid((int) getuid());
  224.  
  225.      if (psw) {
  226.       (void) strcpy(buf, psw->pw_dir);
  227.       return(0);
  228.      }
  229.  
  230.      set_error(NO_HOME_DIR);
  231.      error("get_home");
  232.      return error_code;
  233. }
  234.  
  235.  
  236.  
  237.  
  238. timed_out(file_ent, current_time, min_days)
  239. filerec *file_ent;
  240. time_t current_time, min_days;
  241. {
  242.      if ((current_time - file_ent->specs.st_ctime) / 86400 >= min_days)
  243.       return(1);
  244.      else
  245.       return(0);
  246. }
  247.  
  248.  
  249.  
  250. int directory_exists(dirname)
  251. char *dirname;
  252. {
  253.      struct stat stat_buf;
  254.  
  255.      if (stat(dirname, &stat_buf))
  256.       return(0);
  257.      else if ((stat_buf.st_mode & S_IFMT) == S_IFDIR)
  258.       return(1);
  259.      else
  260.       return(0);
  261. }
  262.  
  263.  
  264.  
  265. is_link(name, oldbuf)
  266. char *name;
  267. struct stat *oldbuf;
  268. {
  269. #ifdef S_IFLNK
  270.      struct stat statbuf;
  271.  
  272.      if (oldbuf)
  273.       statbuf = *oldbuf;
  274.      else if (lstat(name, &statbuf) < 0) {
  275.       set_error(errno);
  276.       error("is_link");
  277.       return(0);
  278.      }
  279.  
  280.      if ((statbuf.st_mode & S_IFMT) == S_IFLNK)
  281.       return 1;
  282.      else
  283. #endif
  284.       return 0;
  285. }
  286.  
  287.  
  288.  
  289. /*
  290.  * This is one of the few procedures that is allowed to break the
  291.  * rule of always returning an error value if an error occurs.  That's
  292.  * because it's stupid to expect a boolean function to do that, and
  293.  * because defaulting to not being a mountpoint if there is an error
  294.  * is a reasonable thing to do.
  295.  */
  296. /*
  297.  * The second parameter is optional -- if it is non-NULL, it is
  298.  * presumed to be a stat structure for the file being passed in.
  299.  */
  300. int is_mountpoint(name, oldbuf)
  301. char *name;
  302. struct stat *oldbuf;
  303. {
  304.      struct stat statbuf;
  305.      dev_t device;
  306.      char buf[MAXPATHLEN];
  307. #ifdef AFS_MOUNTPOINTS
  308.      struct ViceIoctl blob;
  309.      char retbuf[MAXPATHLEN];
  310.      int retval;
  311.      char *shortname;
  312. #endif
  313.  
  314.      /* First way to check for a mount point -- if the device number */
  315.      /* of name is different from the device number of name/..       */
  316.      if (oldbuf)
  317.       statbuf = *oldbuf;
  318.      else if (lstat(name, &statbuf) < 0) {
  319.       set_error(errno);
  320.       error(name);
  321.       return 0;
  322.      }
  323.  
  324.      device = statbuf.st_dev;
  325.  
  326.      if (strlen(name) + 4 /* length of "/.." + a NULL */ > MAXPATHLEN) {
  327.       set_error(ENAMETOOLONG);
  328.       error(name);
  329.       return 0;
  330.      }
  331.  
  332.      strcpy(buf, name);
  333.      strcat(buf, "/..");
  334.      if (lstat(buf, &statbuf) < 0) {
  335.       set_error(errno);
  336.       error(name);
  337.       return 0;
  338.      }
  339.  
  340.      if (statbuf.st_dev != device)
  341.       return 1;
  342.  
  343. #ifdef AFS_MOUNTPOINTS
  344.      /* Check for AFS mountpoint using the AFS pioctl call. */
  345.      if ((shortname = lastpart(name)) == name) {
  346.       strcpy(buf, ".");
  347.       blob.in = name;
  348.       blob.in_size = strlen(name) + 1;
  349.       blob.out = retbuf;
  350.       blob.out_size = MAXPATHLEN;
  351.       bzero(retbuf, MAXPATHLEN);
  352.      }
  353.      else {
  354.       strncpy(buf, name, shortname - name - 1);
  355.       buf[shortname - name - 1] = '\0';
  356.       if (*buf == '\0')
  357.            strcpy(buf, "/");
  358.       blob.in = shortname;
  359.       blob.in_size = strlen(shortname) + 1;
  360.       blob.out = retbuf;
  361.       blob.out_size = MAXPATHLEN;
  362.       bzero(retbuf, MAXPATHLEN);
  363.      }
  364.  
  365.      retval = pioctl(buf, VIOC_AFS_STAT_MT_PT, &blob, 0);
  366.  
  367.      if (retval == 0) {
  368. #ifdef DEBUG
  369.       printf("%s is an AFS mountpoint, is_mountpoint returning true.\n",
  370.          name);
  371. #endif
  372.       return 1;
  373.      }
  374.      else {
  375.       if (errno != EINVAL) {
  376.            set_error(errno);
  377.            error(name);
  378.       }
  379.      }
  380. #endif /* AFS_MOUNTPOINTS */
  381.  
  382.      return 0;
  383. }
  384.  
  385. #ifdef MALLOC_DEBUG
  386. char *Malloc(size)
  387. unsigned size;
  388. {
  389.      extern char *malloc();
  390.  
  391.      static int count = 0;
  392.      char buf[10];
  393.      
  394.      count++;
  395.  
  396.      fprintf(stderr, "This is call number %d to Malloc, for %u bytes.\n",
  397.          count, size);
  398.      fprintf(stdout, "Shall I return NULL for this malloc? ");
  399.      fgets(buf, 10, stdin);
  400.      if ((*buf == 'y') || (*buf == 'Y')) {
  401.       errno = ENOMEM;
  402.       return ((char *) NULL);
  403.      }
  404.      else
  405.       return (malloc(size));
  406. }
  407. #endif
  408.  
  409.       
  410.