#!/usr/sbin/perl # findtext - recursively descend a directory hierarchy searching for text # # This software is Public Domain. Please maintain version history. # Report all bugs to Greg Ercolano (erco@3dsite.com). # # 1.00 erco@3dsite.com # 1.10 erco@3dsite.com - added -name/-i/-d/-v, and gzip/pack/uncompress # 1.20 erco@3dsite.com - small fixes, 'set iflag=""', etc # 2.00 erco@3dsite.com - perl4 compatible rewrite # 2.01 erco@3dsite.com - Added '-type f' # $G_debug = 0; $G_verbose = 0; $G_search = ""; $G_iflags = ""; # MAIN { local ($name) = ""; local ($follow) = ""; local ($i, $filename, @list); if ( $#ARGV < 0 ) { &HelpAndExit(); } for ( $i=0; $i <= $#ARGV; $i++ ) { if ( $ARGV[$i] eq "-follow" ) { $follow = "-follow"; next; } if ( $ARGV[$i] eq "-i" ) { $G_iflags = "i"; next; } if ( $ARGV[$i] eq "-v" ) { $G_verbose = 1; next; } if ( $ARGV[$i] eq "-d" ) { $G_debug = 1; next; } if ( $ARGV[$i] eq "-h" || $ARGV[$i] eq "-help" ) { &HelpAndExit(); } if ( $ARGV[$i] eq "-name" ) { $name = sprintf("-name '%s'",$ARGV[++$i]); next; } if ( $G_search eq "" ) { $G_search = $ARGV[$i]; } else { push(@list, $ARGV[$i]); } } # WALK EACH DIRECTORY foreach ( @list ) { $filename = "find $_ $name -type f $follow -print"; if ( $G_debug ) { print STDERR "Executing: $filename\n"; } unless ( open(FDIR, "$filename|") ) { print STDERR "$0: $filename: $!\n"; next; } # WALK EACH FILE while ( ) { local ($cmd) = "cat"; local ($filename) = $_; chop($filename); if ( $G_debug || $G_verbose ) { print "--- " . $filename . "\n"; } if ( /\.z/ ) { $cmd = "pcat"; } # unpack man pages if ( /\.Z/ ) { $cmd = "uncompress -c"; } # compress(1)ed files if ( /\.gz/ ) { $cmd = "gunzip -c"; } # gzip'ed files &Search("$cmd $filename | col -bx", $filename); # col: for man pages } close(FDIR); } } # SEARCH FILE sub Search { local ( $cmd, $filename ) = @_; if ( $G_debug ) { print STDERR "Executing: $cmd\n"; } unless ( open ( FILE, "$cmd|" ) ) { print STDERR "$cmd: $!\n"; return(0); } while ( ) { if ( $G_iflags eq "i" ) { if ( /$G_search/i ) { print "$filename: $_"; } } else { if ( /$G_search/ ) { print "$filename: $_"; } } } close(FILE); return(0); } sub HelpAndExit { print STDERR <<"EOF"; findtext - recursively search files for a string of text Searches plain ascii files, .gz, .Z and .z files usage: findtext [-v] [-name pat] [-i] regex dir [dir ..] -------- ----- --- Underlined items must be specified. OPTIONS -name pat - search for filename pattern 'pat' (eg. find(1) '-name') -follow - follow symbolic links -i - ignore case -v - verbose - print expansion commands -d - debug 'regex' - a perl regular expression, ie. 'Jeff|Rob' [similar to egrep(1)] 'dir' - a directory EXAMPLES findtext -i 'pagesize|page.size' /usr/share/catman/u_man/cat1 findtext 'memory.*alloc' /usr/include findtext 'NPROC' /var/sysgen /usr/include /usr/tmp/kernel.new findtext -name '*.c' 'include|define' ./src EOF exit(1); }