home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / misc / volume2 / checklink < prev    next >
Internet Message Format  |  1991-08-07  |  5KB

  1. From: jason@violet.berkeley.edu (Jason Venner)
  2. Newsgroups: comp.sources.misc
  3. Subject: v02i072: checklink - check for symlinks in limbo
  4. Message-ID: <7489@ncoast.UUCP>
  5. Date: 9 Mar 88 23:22:50 GMT
  6. Approved: allbery@ncoast.UUCP
  7.  
  8. Comp.sources.misc: Volume 2, Issue 72
  9. Submitted-By: "Jason Venner" <jason@violet.berkeley.edu>
  10. Archive-Name: checklink
  11.  
  12. This is the first pass of a program that walks through the directories
  13. listed on the command link, and prints out the names of the
  14. unresolvable symbolic links, and what they point to on stdout.
  15. Error messages are reported on stderr.
  16. the exit code is the sum of the unresolved symbolic links + sum of non
  17. fatal errors.
  18. It has only tested on BSD systems.  [So how many non-BSD systems have symbolic
  19. links?  ++bsa]
  20.  
  21. #--------------------------------CUT HERE-------------------------------------
  22. #! /bin/sh
  23. #
  24. # This is a shell archive.  Save this into a file, edit it
  25. # and delete all lines above this comment.  Then give this
  26. # file to sh by executing the command "sh file".  The files
  27. # will be extracted into the current directory owned by
  28. # you with default permissions.
  29. #
  30. # The files contained herein are:
  31. #
  32. # -rw-rw-rw-   1 allbery  uucp        3108 Mar  9 18:17 checklink.c
  33. #
  34. echo 'x - checklink.c'
  35. if test -f checklink.c; then echo 'shar: not overwriting checklink.c'; else
  36. sed 's/^X//' << '________This_Is_The_END________' > checklink.c
  37. X#include    <stdio.h>
  38. X#include    <sys/types.h>
  39. X#include    <sys/dir.h>
  40. X#include    <sys/stat.h>
  41. X#include    <sys/file.h>
  42. X
  43. Xchar    *name;
  44. X
  45. Xmain( argc, argv )
  46. Xint    argc;
  47. Xchar    **argv;
  48. X{
  49. X
  50. X    char    *dir;
  51. X    char    *path;
  52. X    char    cwd[MAXNAMLEN+1];
  53. X    char*    getcwd();
  54. X    char*    rindex();
  55. X    int    err_count;
  56. X
  57. X    name = argv[0];
  58. X    cwd[MAXNAMLEN] = '\0';
  59. X    if( !getwd( cwd ) ) {
  60. X        fprintf( stderr, "%s:unable to get current working directory, %s", name, cwd );
  61. X        exit( 1 );
  62. X    }
  63. X    for( argc--, argv++, err_count = 0; argc; argc--, argv++ ) {
  64. X        if( chdir( argv[0] ) == -1 ) {
  65. X            fprintf( stderr, "%s:unable to chdir to %s\n", name, dir );
  66. X            perror( "" );
  67. X            err_count++;
  68. X        }
  69. X        if( (dir = rindex( argv[0], '/' )) ) {
  70. X            *dir++ = '\0';
  71. X            path = argv[0];
  72. X        } else {
  73. X            dir = argv[0];
  74. X            path = ".";
  75. X        }
  76. X        err_count += check_link( dir, path );
  77. X        if( chdir( cwd ) == -1 ) {
  78. X            fprintf( stderr, "%s:unable to chdir to %s\n", name, cwd );
  79. X            perror( "" );
  80. X            exit( 2 );
  81. X        }
  82. X    }
  83. X    exit( err_count );
  84. X}
  85. X
  86. Xcheck_link( top, path )
  87. Xchar    *top;
  88. Xchar    *path;
  89. X{
  90. X
  91. X    DIR    *dptr;
  92. X    DIR*    opendir();
  93. X    char    cwd[MAXNAMLEN+1];
  94. X    char    link_name[MAXNAMLEN+1];
  95. X    char*    sprintf();
  96. X    extern    char    *name;
  97. X    int    err_count;
  98. X    int    link_size;
  99. X    off_t    offset;
  100. X    off_t    telldir();
  101. X    struct    direct    *dent;
  102. X    struct    direct*    readdir();
  103. X    struct    stat    stat;
  104. X
  105. X    (void) sprintf( cwd, "%s/%s", path, top );
  106. X    if( !(dptr = opendir( "." )) ) {
  107. X        fprintf( stderr, "%s:unable to open directory %s", name, cwd );
  108. X        perror( "" );
  109. X        return 1;
  110. X    }
  111. X    if( !readdir( dptr )  || !readdir( dptr ) ) {
  112. X        fprintf( stderr, "%s:unable to read '.' or '..' in %s\n",
  113. X                  name, cwd );
  114. X        perror( "" );
  115. X        (void) closedir( dptr );
  116. X        return 1;
  117. X    }
  118. X    err_count = 0;
  119. X    link_name[MAXNAMLEN] = '\0';
  120. X    while( (dent = readdir( dptr )) ) {
  121. X        if( lstat( dent->d_name, &stat ) == -1 ) {
  122. X            fprintf( stderr, "%s:unable to lstat %s/%s", name, cwd, dent->d_name );
  123. X            perror( "" );
  124. X            err_count++;
  125. X            continue;
  126. X        }
  127. X        switch( stat.st_mode & S_IFMT ) {
  128. X        case    S_IFDIR:
  129. X            if( (offset = telldir( dptr )) == -1 ) {
  130. X                fprintf( stderr, "%s:unable to telldir on %s\n", cwd );
  131. X                perror( "" );
  132. X                err_count++;
  133. X                continue;
  134. X            }
  135. X            (void) closedir( dptr );
  136. X            if( chdir( dent->d_name ) == -1 ) {
  137. X                fprintf( stderr, "%s:unable to chdir to %s/%s", name, cwd, dent->d_name );
  138. X                perror( "" );
  139. X                return ++err_count;
  140. X            }
  141. X            err_count += check_link( dent->d_name, cwd );
  142. X            if( chdir( ".." ) == -1 && chdir( cwd ) == -1 ) {
  143. X                fprintf( stderr, "%s:unable to chdir up to %s", name, cwd);
  144. X                return ++err_count;
  145. X            }
  146. X            if( !(dptr = opendir( "." )) ) {
  147. X                fprintf( stderr, "%s:unable to reopendir %s", name, cwd );
  148. X                perror( "" );
  149. X                return ++err_count;
  150. X            }
  151. X            seekdir( dptr, offset, 0 );
  152. X            break;
  153. X        case    S_IFLNK:
  154. X            if( (link_size = readlink( dent->d_name, link_name, MAXNAMLEN )) == -1 ) {
  155. X                fprintf( stderr, "%s:unable to readlink on %s/%s", cwd, dent->d_name );
  156. X                perror( "" );
  157. X                err_count++;
  158. X                continue;
  159. X            }
  160. X            link_name[link_size] = '\0';
  161. X            if( access( link_name, F_OK ) == -1 ) {
  162. X                printf( "%s/%s %s\n", cwd, dent->d_name, link_name );
  163. X                err_count++;
  164. X            }
  165. X            break;
  166. X        default:
  167. X            break;
  168. X        }
  169. X    }
  170. X    (void) closedir( dptr );
  171. X    return err_count;
  172. X}
  173. ________This_Is_The_END________
  174. if test `wc -c < checklink.c` -ne 3108; then
  175.     echo 'shar: checklink.c was damaged during transit (should have been 3108 bytes)'
  176. fi
  177. fi        ; : end of overwriting check
  178. exit 0
  179.