#!/usr/bin/env perl # Copyright (c) 2009, Douglas Haber # All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # * Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # * Redistributions in binary form must reproduce the above # copyright notice, this list of conditions and the following # disclaimer in the documentation and/or other materials provided # with the distribution. # * The names names of the authors may not be used to endorse or # promote products derived from this software without specific # prior written permission. # # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER AND ITS # CONTRIBUTERS ''AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, # INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF # MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE # DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR ITS # CONTRIBUTERS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, # SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT # LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF # USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND # ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, # OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT # OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF # SUCH DAMAGE. # diffgrep # USAGE diffgrep [regex] [filename] # Display sections of the diff file that match the regex. # WARNING: This is slop. It will work, but there are many cases # where it is unreliable. use strict; my $COLORS = 1; # Don't like colors, turn it off sub color { # scary hardcoded xterm escape sequence for color changes my ($color) = @_; # number (1=red,2=green,3=yellow,etc...) if($COLORS) { print sprintf("%c[3${color}m", 27); } } sub verify_regex { # Check the validity of a regular expression eval { "" =~ /$_[0]/; return(1); } or die "ERROR: Invalid regex '$_[0]'\n"; } sub read_args { # Read args if($#ARGV != 1) { die "USAGE: diffgrep [regex] [filename]\n"; } verify_regex($ARGV[0]); return($ARGV[0], $ARGV[1]); } sub process_line { my($print, $line, $regex) = @_; if($$print) { if($line =~ /^Only in/ || $line =~ /^diff/) { $$print = 0; } else { if($line =~ /^< /) { color(1); } elsif($line =~ /^> /) { color(2); } print $line; color(9); # Turn off colors } } if(!$$print) { if(($line =~ /Only in/ || $line =~ /^diff/) && ($line !~ /\/CVS(\/|:)/ )) { if($line =~ /$regex/) { print $line; $$print = 1; } } } } sub main { my ($regex, $filename) = read_args(); my $print = 0; # boolean to determine if printing is on my $line; if(! open(FD,"<$filename")) { die "ERROR: Can not open file '$filename'\n"; } foreach $line () { process_line(\$print, $line, $regex); } close(FD); } main();