3 # This file, ack, is generated code. 
   4 # Please DO NOT EDIT or send patches for it. 
   6 # Please take a look at the source from 
   7 # https://github.com/petdance/ack2 
   8 # and submit patches against the individual files 
  17 our $VERSION = '2.15_01'; # Check http://beyondgrep.com/ for updates 
  20 use Getopt
::Long 
2.38 (); 
  26 # XXX Don't make this so brute force 
  27 # See also: https://github.com/petdance/ack2/issues/89 
  29 our $opt_after_context; 
  30 our $opt_before_context; 
  35 our $opt_show_filename; 
  48 # flag if we need any context tracking 
  49 our $is_tracking_context; 
  51 # These are all our globals. 
  54     $App::Ack
::orig_program_name 
= $0; 
  55     $0 = join(' ', 'ack', $0); 
  56     if ( $App::Ack
::VERSION 
ne $main::VERSION 
) { 
  57         App
::Ack
::die( "Program/library version mismatch\n\t$0 is $main::VERSION\n\t$INC{'App/Ack.pm'} is $App::Ack::VERSION" ); 
  60     # Do preliminary arg checking; 
  61     my $env_is_usable = 1; 
  62     for my $arg ( @ARGV ) { 
  63         last if ( $arg eq '--' ); 
  65         # Get the --thpppt, --bar, --cathy checking out of the way. 
  66         $arg =~ /^--th[pt]+t+$/ and App
::Ack
::_thpppt
($arg); 
  67         $arg eq '--bar'         and App
::Ack
::_bar
(); 
  68         $arg eq '--cathy'       and App
::Ack
::_cathy
(); 
  70         # See if we want to ignore the environment. (Don't tell Al Gore.) 
  71         $arg eq '--env'         and $env_is_usable = 1; 
  72         $arg eq '--noenv'       and $env_is_usable = 0; 
  75     if ( !$env_is_usable ) { 
  76         my @keys = ( 'ACKRC', grep { /^ACK_/ } keys %ENV ); 
  81     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); 
  82     Getopt
::Long
::Configure
('pass_through', 'no_auto_abbrev'); 
  83     Getopt
::Long
::GetOptions
( 
  84         'help'       => sub { App
::Ack
::show_help
(); exit; }, 
  85         'version'    => sub { App
::Ack
::print_version_statement
(); exit; }, 
  86         'man'        => sub { App
::Ack
::show_man
(); exit; }, 
  88     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); 
  91         App
::Ack
::show_help
(); 
  98 sub _compile_descend_filter 
{ 
 102     my $dont_ignore_dirs = 0; 
 104     for my $filter (@{$opt->{idirs
} || []}) { 
 105         if ($filter->is_inverted()) { 
 113     # if we have one or more --noignore-dir directives, we can't ignore 
 114     # entire subdirectory hierarchies, so we return an "accept all" 
 115     # filter and scrutinize the files more in _compile_file_filter 
 116     return if $dont_ignore_dirs; 
 117     return unless $idirs; 
 119     $idirs = $opt->{idirs
}; 
 122         my $resource = App
::Ack
::Resource
::Basic-
>new($File::Next
::dir
); 
 123         return !grep { $_->filter($resource) } @{$idirs}; 
 127 sub _compile_file_filter 
{ 
 128     my ( $opt, $start ) = @_; 
 130     my $ifiles_filters = $opt->{ifiles
}; 
 132     my $filters         = $opt->{'filters'} || []; 
 133     my $direct_filters = App
::Ack
::Filter
::Collection-
>new(); 
 134     my $inverse_filters = App
::Ack
::Filter
::Collection-
>new(); 
 136     foreach my $filter (@{$filters}) { 
 137         if ($filter->is_inverted()) { 
 138             # We want to check if files match the uninverted filters 
 139             $inverse_filters->add($filter->invert()); 
 142             $direct_filters->add($filter); 
 146     my %is_member_of_starting_set = map { (get_file_id
($_) => 1) } @{$start}; 
 148     my @ignore_dir_filter = @{$opt->{idirs
} || []}; 
 149     my @is_inverted       = map { $_->is_inverted() } @ignore_dir_filter; 
 150     # this depends on InverseFilter->invert returning the original 
 151     # filter (for optimization) 
 152     @ignore_dir_filter         = map { $_->is_inverted() ? $_->invert() : $_ } @ignore_dir_filter; 
 153     my $dont_ignore_dir_filter = grep { $_ } @is_inverted; 
 154     my $previous_dir = ''; 
 155     my $previous_dir_ignore_result; 
 159             if ( $File::Next
::name 
=~ /$opt_regex/ && $opt_v ) { 
 162             if ( $File::Next
::name 
!~ /$opt_regex/ && !$opt_v ) { 
 166         # ack always selects files that are specified on the command 
 167         # line, regardless of filetype.  If you want to ack a JPEG, 
 168         # and say "ack foo whatever.jpg" it will do it for you. 
 169         return 1 if $is_member_of_starting_set{ get_file_id
($File::Next
::name
) }; 
 171         if ( $dont_ignore_dir_filter ) { 
 172             if ( $previous_dir eq $File::Next
::dir 
) { 
 173                 if ( $previous_dir_ignore_result ) { 
 178                 my @dirs = File
::Spec-
>splitdir($File::Next
::dir
); 
 182                 for ( my $i = 0; $i < @dirs; $i++) { 
 183                     my $dir_rsrc = App
::Ack
::Resource
::Basic-
>new(File
::Spec-
>catfile(@dirs[0 .. $i])); 
 186                     for my $filter (@ignore_dir_filter) { 
 187                         if ( $filter->filter($dir_rsrc) ) { 
 188                             $is_ignoring = !$is_inverted[$j]; 
 194                 $previous_dir               = $File::Next
::dir
; 
 195                 $previous_dir_ignore_result = $is_ignoring; 
 197                 if ( $is_ignoring ) { 
 203         # Ignore named pipes found in directory searching.  Named 
 204         # pipes created by subprocesses get specified on the command 
 205         # line, so the rule of "always select whatever is on the 
 206         # command line" wins. 
 207         return 0 if -p 
$File::Next
::name
; 
 209         # We can't handle unreadable filenames; report them. 
 211             use filetest 
'access'; 
 213             if ( not -R 
$File::Next
::name 
) { 
 214                 if ( $App::Ack
::report_bad_filenames 
) { 
 215                     App
::Ack
::warn( "${File::Next::name}: cannot open file for reading" ); 
 221         my $resource = App
::Ack
::Resource
::Basic-
>new($File::Next
::name
); 
 223         if ( $ifiles_filters && $ifiles_filters->filter($resource) ) { 
 227         my $match_found = $direct_filters->filter($resource); 
 229         # Don't bother invoking inverse filters unless we consider the current resource a match 
 230         if ( $match_found && $inverse_filters->filter( $resource ) ) { 
 238     my $resource = shift; 
 241     my @types = filetypes
( $resource ); 
 242     my $types = join( ',', @types ); 
 243     my $arrow = @types ? ' => ' : ' =>'; 
 244     App
::Ack
::print( $resource->name, $arrow, join( ',', @types ), $ors ); 
 249 # Set default colors, load Term::ANSIColor 
 251     eval 'use Term::ANSIColor 1.10 ()'; 
 252     eval 'use Win32::Console::ANSI' if $App::Ack
::is_windows
; 
 254     $ENV{ACK_COLOR_MATCH
}    ||= 'black on_yellow'; 
 255     $ENV{ACK_COLOR_FILENAME
} ||= 'bold green'; 
 256     $ENV{ACK_COLOR_LINENO
}   ||= 'bold yellow'; 
 262     my ( $resource ) = @_; 
 266     foreach my $k (keys %App::Ack
::mappings
) { 
 267         my $filters = $App::Ack
::mappings
{$k}; 
 269         foreach my $filter (@{$filters}) { 
 271             my $clone = $resource->clone; 
 272             if ( $filter->filter($clone) ) { 
 279     # http://search.cpan.org/dist/Perl-Critic/lib/Perl/Critic/Policy/Subroutines/ProhibitReturnSort.pm 
 280     @matches = sort @matches; 
 284 # Returns a (fairly) unique identifier for a file. 
 285 # Use this function to compare two files to see if they're 
 286 # equal (ie. the same file, but with a different path/links/etc). 
 288     my ( $filename ) = @_; 
 290     if ( $App::Ack
::is_windows 
) { 
 291         return File
::Next
::reslash
( $filename ); 
 294         # XXX is this the best method? it always hits the FS 
 295         if( my ( $dev, $inode ) = (stat($filename))[0, 1] ) { 
 296             return join(':', $dev, $inode); 
 299             # XXX this could be better 
 305 # Returns a regex object based on a string and command-line options. 
 306 # Dies when the regex $str is undefined (i.e. not given on command line). 
 312     defined $str or App
::Ack
::die( 'No regular expression found.' ); 
 314     $str = quotemeta( $str ) if $opt->{Q
}; 
 316         my $pristine_str = $str; 
 319         $str = "\\b$str" if $pristine_str =~ /^\w/; 
 320         $str = "$str\\b" if $pristine_str =~ /\w$/; 
 323     my $regex_is_lc = $str eq lc $str; 
 324     if ( $opt->{i
} || ($opt->{smart_case
} && $regex_is_lc) ) { 
 328     my $re = eval { qr/$str/m }; 
 330         die "Invalid regex '$str':\n  $@"; 
 337 my $match_column_number; 
 341 # number of context lines 
 342 my $n_before_ctx_lines; 
 343 my $n_after_ctx_lines; 
 345 # array to keep track of lines that might be required for a "before" context 
 346 my @before_context_buf; 
 347 # position to insert next line in @before_context_buf 
 348 my $before_context_pos; 
 350 # number of "after" context lines still pending 
 351 my $after_context_pending; 
 353 # number of latest line that got printed 
 359 my $has_printed_something; 
 362     $has_printed_something = 0; 
 365 # setup context tracking variables 
 366 sub setup_line_context 
{ 
 368     $n_before_ctx_lines = $opt_output ? 0 : ($opt_before_context || 0); 
 369     $n_after_ctx_lines  = $opt_output ? 0 : ($opt_after_context || 0); 
 371     @before_context_buf = (undef) x 
$n_before_ctx_lines; 
 372     $before_context_pos = 0; 
 374     $is_tracking_context = $n_before_ctx_lines || $n_after_ctx_lines; 
 381 # adjust context tracking variables when entering a new file 
 382 sub setup_line_context_for_file 
{ 
 384     $printed_line_no = 0; 
 385     $after_context_pending = 0; 
 386     if ( $opt_heading && !$opt_lines ) { 
 395 This subroutine jumps through a number of optimization hoops to 
 396 try to be fast in the more common use cases of ack.  For one thing, 
 397 in non-context tracking searches (not using -A, -B, or -C), 
 398 conditions that normally would be checked inside the loop happen 
 399 outside, resulting in three nearly identical loops for -v, --passthru, 
 400 and normal searching.  Any changes that happen to one should propagate 
 401 to the others if they make sense.  The non-context branches also inline 
 402 does_match for performance reasons; any relevant changes that happen here 
 403 must also happen there. 
 407 sub print_matches_in_resource 
{ 
 408     my ( $resource, $opt ) = @_; 
 410     my $max_count      = $opt_m || -1; 
 412     my $filename       = $resource->name; 
 413     my $ors            = $opt_print0 ? "\0" : "\n"; 
 415     my $has_printed_for_this_resource = 0; 
 419     my $fh = $resource->open(); 
 421         if ( $App::Ack
::report_bad_filenames 
) { 
 422             App
::Ack
::warn( "$filename: $!" ); 
 427     my $display_filename = $filename; 
 428     if ( $opt_show_filename && $opt_heading && $opt_color ) { 
 429         $display_filename = Term
::ANSIColor
::colored
($display_filename, $ENV{ACK_COLOR_FILENAME
}); 
 432     # check for context before the main loop, so we don't 
 433     # pay for it if we don't need it 
 434     if ( $is_tracking_context ) { 
 435         $after_context_pending = 0; 
 437             if ( does_match
($opt, $_) && $max_count ) { 
 438                 if ( !$has_printed_for_this_resource ) { 
 439                     if ( $opt_break && $has_printed_something ) { 
 440                         App
::Ack
::print_blank_line
(); 
 442                     if ( $opt_show_filename && $opt_heading ) { 
 443                         App
::Ack
::print_filename
( $display_filename, $ors ); 
 446                 print_line_with_context
($opt, $filename, $_, $.); 
 447                 $has_printed_for_this_resource = 1; 
 451             elsif ( $opt_passthru ) { 
 452                 chomp; # XXX proper newline handling? 
 453                 # XXX inline this call? 
 454                 if ( $opt_break && !$has_printed_for_this_resource && $has_printed_something ) { 
 455                     App
::Ack
::print_blank_line
(); 
 457                 print_line_with_options
($opt, $filename, $_, $., ':'); 
 458                 $has_printed_for_this_resource = 1; 
 461                 chomp; # XXX proper newline handling? 
 462                 print_line_if_context
($opt, $filename, $_, $., '-'); 
 465             last if ($max_count == 0) && ($after_context_pending == 0); 
 471         if ( $opt_passthru ) { 
 473                 $match_column_number = undef; 
 474                 if ( $opt_v ? !/$opt_regex/o : /$opt_regex/o ) { 
 476                         $match_column_number = $-[0] + 1; 
 478                     if ( !$has_printed_for_this_resource ) { 
 479                         if ( $opt_break && $has_printed_something ) { 
 480                             App
::Ack
::print_blank_line
(); 
 482                         if ( $opt_show_filename && $opt_heading ) { 
 483                             App
::Ack
::print_filename
( $display_filename, $ors ); 
 486                     print_line_with_context
($opt, $filename, $_, $.); 
 487                     $has_printed_for_this_resource = 1; 
 492                     chomp; # XXX proper newline handling? 
 493                     if ( $opt_break && !$has_printed_for_this_resource && $has_printed_something ) { 
 494                         App
::Ack
::print_blank_line
(); 
 496                     print_line_with_options
($opt, $filename, $_, $., ':'); 
 497                     $has_printed_for_this_resource = 1; 
 499                 last unless $max_count != 0; 
 503             $match_column_number = undef; 
 505                 if ( !/$opt_regex/o ) { 
 506                     if ( !$has_printed_for_this_resource ) { 
 507                         if ( $opt_break && $has_printed_something ) { 
 508                             App
::Ack
::print_blank_line
(); 
 510                         if ( $opt_show_filename && $opt_heading ) { 
 511                             App
::Ack
::print_filename
( $display_filename, $ors ); 
 514                     print_line_with_context
($opt, $filename, $_, $.); 
 515                     $has_printed_for_this_resource = 1; 
 519                 last unless $max_count != 0; 
 523             # XXX unroll first match check ($has_printed_for_this_resource) 
 524             # XXX what if this is a *huge* file? (see also -l) 
 530             my $prev_match_end = 0; 
 533             $match_column_number = undef; 
 534             while ( $contents =~ /$opt_regex/og ) { 
 535                 my $match_start = $-[0]; 
 536                 my $match_end   = $+[0]; 
 538                 pos($contents)  = $prev_match_end; 
 539                 $prev_match_end = $match_end; 
 541                 while ( $contents =~ /\n/og && $-[0] < $match_start ) { 
 545                 my $start_line = rindex($contents, "\n", $match_start); 
 546                 my $end_line   = index($contents, "\n", $match_end); 
 548                 if ( $start_line == -1 ) { 
 555                 if ( $end_line == -1 ) { 
 556                     $end_line = length($contents); 
 561                 $match_column_number = $match_start - $start_line + 1; 
 562                 if ( !$has_printed_for_this_resource ) { 
 563                     if ( $opt_break && $has_printed_something ) { 
 564                         App
::Ack
::print_blank_line
(); 
 566                     if ( $opt_show_filename && $opt_heading ) { 
 567                         App
::Ack
::print_filename
( $display_filename, $ors ); 
 570                 my $line = substr($contents, $start_line, $end_line - $start_line + 1); 
 571                 $line =~ s/[\r\n]+$//g; 
 572                 print_line_with_options
($opt, $filename, $line, $line_no, ':'); 
 574                 pos($contents) = $end_line + 1; 
 576                 $has_printed_for_this_resource = 1; 
 580                 last unless $max_count != 0; 
 586     $is_iterating = 0; # XXX this won't happen on an exception 
 587                        #     then again, do we care? ack doesn't really 
 588                        #     handle exceptions anyway. 
 593 sub print_line_with_options 
{ 
 594     my ( $opt, $filename, $line, $line_no, $separator ) = @_; 
 596     $has_printed_something = 1; 
 597     $printed_line_no = $line_no; 
 599     my $ors = $opt_print0 ? "\0" : "\n"; 
 604         $filename = Term
::ANSIColor
::colored
($filename, 
 605             $ENV{ACK_COLOR_FILENAME
}); 
 606         $line_no  = Term
::ANSIColor
::colored
($line_no, 
 607             $ENV{ACK_COLOR_LINENO
}); 
 610     if($opt_show_filename) { 
 612             push @line_parts, $line_no; 
 615             push @line_parts, $filename, $line_no; 
 619             push @line_parts, get_match_column
(); 
 623         while ( $line =~ /$opt_regex/og ) { 
 624             # XXX We need to stop using eval() for --output.  See https://github.com/petdance/ack2/issues/421 
 625             my $output = eval $opt_output; 
 626             App
::Ack
::print( join( $separator, @line_parts, $output ), $ors ); 
 631             $line =~ /$opt_regex/o; # this match is redundant, but we need 
 632                                        # to perfom it in order to get if 
 633                                        # capture groups are set 
 635             if ( @+ > 1 ) { # if we have captures 
 636                 while ( $line =~ /$opt_regex/og ) { 
 637                     my $offset = 0; # additional offset for when we add stuff 
 638                     my $previous_match_end = 0; 
 640                     for ( my $i = 1; $i < @+; $i++ ) { 
 641                         my ( $match_start, $match_end ) = ( $-[$i], $+[$i] ); 
 643                         next unless defined($match_start); 
 644                         next if $match_start < $previous_match_end; 
 646                         my $substring = substr( $line, 
 647                             $offset + $match_start, $match_end - $match_start ); 
 648                         my $substitution = Term
::ANSIColor
::colored
( $substring, 
 649                             $ENV{ACK_COLOR_MATCH
} ); 
 651                         substr( $line, $offset + $match_start, 
 652                             $match_end - $match_start, $substitution ); 
 654                         $previous_match_end  = $match_end; # offsets do not need to be applied 
 655                         $offset             += length( $substitution ) - length( $substring ); 
 658                     pos($line) = $+[0] + $offset; 
 662                 my $matched = 0; # flag; if matched, need to escape afterwards 
 664                 while ( $line =~ /$opt_regex/og ) { 
 667                     my ( $match_start, $match_end ) = ($-[0], $+[0]); 
 668                     next unless defined($match_start); 
 670                     my $substring = substr( $line, $match_start, 
 671                         $match_end - $match_start ); 
 672                     my $substitution = Term
::ANSIColor
::colored
( $substring, 
 673                         $ENV{ACK_COLOR_MATCH
} ); 
 675                     substr( $line, $match_start, $match_end - $match_start, 
 678                     pos($line) = $match_end + 
 679                     (length( $substitution ) - length( $substring )); 
 681                 # XXX why do we do this? 
 682                 $line .= "\033[0m\033[K" if $matched; 
 686         push @line_parts, $line; 
 687         App
::Ack
::print( join( $separator, @line_parts ), $ors ); 
 694     my ( $resource, $opt, $cb ) = @_; 
 698     my $fh = $resource->open(); 
 700         if ( $App::Ack
::report_bad_filenames 
) { 
 701             App
::Ack
::warn( $resource->name . ': ' . $! ); 
 706     # Check for context before the main loop, so we don't pay for it if we don't need it. 
 707     if ( $is_tracking_context ) { 
 708         $after_context_pending = 0; 
 722     $is_iterating = 0; # XXX this won't happen on an exception 
 723                        #     then again, do we care? ack doesn't really 
 724                        #     handle exceptions anyway. 
 729 sub print_line_with_context 
{ 
 730     my ( $opt, $filename, $matching_line, $line_no ) = @_; 
 732     my $ors                 = $opt_print0 ? "\0" : "\n"; 
 733     my $is_tracking_context = $opt_after_context || $opt_before_context; 
 735     $matching_line =~ s/[\r\n]+$//g; 
 737     # check if we need to print context lines first 
 738     if( $is_tracking_context ) { 
 739         my $before_unprinted = $line_no - $printed_line_no - 1; 
 740         if ( !$is_first_match && ( !$printed_line_no || $before_unprinted > $n_before_ctx_lines ) ) { 
 741             App
::Ack
::print('--', $ors); 
 744         # We want at most $n_before_ctx_lines of context 
 745         if ( $before_unprinted > $n_before_ctx_lines ) { 
 746             $before_unprinted = $n_before_ctx_lines; 
 749         while ( $before_unprinted > 0 ) { 
 750             my $line = $before_context_buf[($before_context_pos - $before_unprinted + $n_before_ctx_lines) % $n_before_ctx_lines]; 
 754             # Disable $opt->{column} since there are no matches in the context lines 
 755             local $opt_column = 0; 
 757             print_line_with_options
($opt, $filename, $line, $line_no-$before_unprinted, '-'); 
 762     print_line_with_options
($opt, $filename, $matching_line, $line_no, ':'); 
 764     # We want to get the next $n_after_ctx_lines printed 
 765     $after_context_pending = $n_after_ctx_lines; 
 772 # print the line only if it's part of a context we need to display 
 773 sub print_line_if_context 
{ 
 774     my ( $opt, $filename, $line, $line_no, $separator ) = @_; 
 776     if ( $after_context_pending ) { 
 777         # Disable $opt->{column} since there are no matches in the context lines 
 778         local $opt_column = 0; 
 779         print_line_with_options
( $opt, $filename, $line, $line_no, $separator ); 
 780         --$after_context_pending; 
 782     elsif ( $n_before_ctx_lines ) { 
 783         # save line for "before" context 
 784         $before_context_buf[$before_context_pos] = $_; 
 785         $before_context_pos = ($before_context_pos+1) % $n_before_ctx_lines; 
 793 # does_match() MUST have an $opt_regex set. 
 797 This subroutine is inlined a few places in print_matches_in_resource 
 798 for performance reasons, so any changes here must be copied there as 
 804     my ( $opt, $line ) = @_; 
 806     $match_column_number = undef; 
 809         return ( $line !~ /$opt_regex/o ); 
 812         if ( $line =~ /$opt_regex/o ) { 
 813             # @- = @LAST_MATCH_START 
 814             # @+ = @LAST_MATCH_END 
 815             $match_column_number = $-[0] + 1; 
 824 sub get_match_column 
{ 
 825     return $match_column_number; 
 828 sub resource_has_match 
{ 
 829     my ( $resource, $opt ) = @_; 
 832     my $fh = $resource->open(); 
 834         if ( $App::Ack
::report_bad_filenames 
) { 
 835             App
::Ack
::warn( $resource->name . ': ' . $! ); 
 841                 if (!/$opt_regex/o) { 
 849             # XXX only do this for certain file sizes? 
 854             $has_match = $content =~ /$opt_regex/o; 
 862 sub count_matches_in_resource 
{ 
 863     my ( $resource, $opt ) = @_; 
 866     my $fh = $resource->open(); 
 868         if ( $App::Ack
::report_bad_filenames 
) { 
 869             App
::Ack
::warn( $resource->name . ': ' . $! ); 
 875                 ++$nmatches if (!/$opt_regex/o); 
 883             $nmatches =()= ($content =~ /$opt_regex/og); 
 892     my @arg_sources = App
::Ack
::ConfigLoader
::retrieve_arg_sources
(); 
 894     my $opt = App
::Ack
::ConfigLoader
::process_args
( @arg_sources ); 
 896     $opt_after_context  = $opt->{after_context
}; 
 897     $opt_before_context = $opt->{before_context
}; 
 898     $opt_output         = $opt->{output
}; 
 899     $opt_print0         = $opt->{print0
}; 
 900     $opt_color          = $opt->{color
}; 
 901     $opt_heading        = $opt->{heading
}; 
 902     $opt_show_filename  = $opt->{show_filename
}; 
 903     $opt_regex          = $opt->{regex
}; 
 904     $opt_break          = $opt->{break}; 
 905     $opt_count          = $opt->{count
}; 
 910     $opt_lines          = $opt->{lines
}; 
 913     $opt_passthru       = $opt->{passthru
}; 
 914     $opt_column         = $opt->{column
}; 
 916     $App::Ack
::report_bad_filenames 
= !$opt->{dont_report_bad_filenames
}; 
 918     if ( $opt->{flush
} ) { 
 922     if ( !defined($opt_color) && !$opt_g ) { 
 923         my $windows_color = 1; 
 924         if ( $App::Ack
::is_windows 
) { 
 925             $windows_color = eval { require Win32
::Console
::ANSI
; }; 
 927         $opt_color = !App
::Ack
::output_to_pipe
() && $windows_color; 
 929     if ( not defined $opt_heading and not defined $opt_break  ) { 
 930         $opt_heading = $opt_break = $opt->{break} = !App
::Ack
::output_to_pipe
(); 
 933     if ( defined($opt->{H
}) || defined($opt->{h
}) ) { 
 934         $opt_show_filename = $opt->{show_filename
} = $opt->{H
} && !$opt->{h
}; 
 937     if ( my $output = $opt_output ) { 
 938         $output        =~ s{\\}{\\\\}g; 
 939         $output        =~ s{"}{\\"}g; 
 940         $opt_output = qq{"$output"}; 
 944     if ( $App::Ack
::is_filter_mode 
&& !$opt->{files_from
} ) { # probably -x 
 945         $resources    = App
::Ack
::Resources-
>from_stdin( $opt ); 
 946         $opt_regex = shift @ARGV if not defined $opt_regex; 
 947         $opt_regex = $opt->{regex
} = build_regex
( $opt_regex, $opt ); 
 950         if ( $opt_f || $opt_lines ) { 
 952                 App
::Ack
::warn( "regex ($opt_regex) specified with -f or --lines" ); 
 953                 App
::Ack
::exit_from_ack
( 0 ); # XXX the 0 is misleading 
 957             $opt_regex = shift @ARGV if not defined $opt_regex; 
 958             $opt_regex = $opt->{regex
} = build_regex
( $opt_regex, $opt ); 
 960         if ( $opt_regex && $opt_regex =~ /\n/ ) { 
 961             App
::Ack
::exit_from_ack
( 0 ); 
 964         if ( not defined $opt->{files_from
} ) { 
 967         if ( !exists($opt->{show_filename
}) ) { 
 968             unless(@start == 1 && !(-d 
$start[0])) { 
 969                 $opt_show_filename = $opt->{show_filename
} = 1; 
 973         if ( defined $opt->{files_from
} ) { 
 974             $resources = App
::Ack
::Resources-
>from_file( $opt, $opt->{files_from
} ); 
 975             exit 1 unless $resources; 
 978             @start = ('.') unless @start; 
 979             foreach my $target (@start) { 
 980                 if ( !-e 
$target && $App::Ack
::report_bad_filenames
) { 
 981                     App
::Ack
::warn( "$target: No such file or directory" ); 
 985             $opt->{file_filter
}    = _compile_file_filter
($opt, \
@start); 
 986             $opt->{descend_filter
} = _compile_descend_filter
($opt); 
 988             $resources = App
::Ack
::Resources-
>from_argv( $opt, \
@start ); 
 991     App
::Ack
::set_up_pager
( $opt->{pager
} ) if defined $opt->{pager
}; 
 993     my $ors        = $opt_print0 ? "\0" : "\n"; 
 994     my $only_first = $opt->{1}; 
 999     setup_line_context
( $opt ); 
1002     while ( my $resource = $resources->next ) { 
1003         if ($is_tracking_context) { 
1004             setup_line_context_for_file
($opt); 
1007         # XXX Combine the -f and -g functions 
1009             # XXX printing should probably happen inside of App::Ack 
1010             if ( $opt->{show_types
} ) { 
1011                 show_types
( $resource, $ors ); 
1014                 App
::Ack
::print( $resource->name, $ors ); 
1017             last RESOURCES 
if defined($opt_m) && $nmatches >= $opt_m; 
1020             if ( $opt->{show_types
} ) { 
1021                 show_types
( $resource, $ors ); 
1024                 local $opt_show_filename = 0; # XXX Why is this local? 
1026                 print_line_with_options
($opt, '', $resource->name, 0, $ors); 
1029             last RESOURCES 
if defined($opt_m) && $nmatches >= $opt_m; 
1031         elsif ( $opt_lines ) { 
1033             foreach my $line ( @{ $opt_lines } ) { 
1034                 my @lines             = split /,/, $line; 
1040                 @line_numbers{@lines} = (1) x 
@lines; 
1043             my $filename = $resource->name; 
1045             local $opt_color = 0; 
1047             iterate
($resource, $opt, sub { 
1050                 if ( $line_numbers{$.} ) { 
1051                     print_line_with_context
($opt, $filename, $_, $.); 
1053                 elsif ( $opt_passthru ) { 
1054                     print_line_with_options
($opt, $filename, $_, $., ':'); 
1056                 elsif ( $is_tracking_context ) { 
1057                     print_line_if_context
($opt, $filename, $_, $., '-'); 
1062         elsif ( $opt_count ) { 
1063             my $matches_for_this_file = count_matches_in_resource
( $resource, $opt ); 
1065             if ( not $opt_show_filename ) { 
1066                 $total_count += $matches_for_this_file; 
1070             if ( !$opt_l || $matches_for_this_file > 0) { 
1071                 if ( $opt_show_filename ) { 
1072                     App
::Ack
::print( $resource->name, ':', $matches_for_this_file, $ors ); 
1075                     App
::Ack
::print( $matches_for_this_file, $ors ); 
1079         elsif ( $opt_l || $opt_L ) { 
1080             my $is_match = resource_has_match
( $resource, $opt ); 
1082             if ( $opt_L ? !$is_match : $is_match ) { 
1083                 App
::Ack
::print( $resource->name, $ors ); 
1086                 last RESOURCES 
if $only_first; 
1087                 last RESOURCES 
if defined($opt_m) && $nmatches >= $opt_m; 
1091             $nmatches += print_matches_in_resource
( $resource, $opt ); 
1092             if ( $nmatches && $only_first ) { 
1098     if ( $opt_count && !$opt_show_filename ) { 
1099         App
::Ack
::print( $total_count, "\n" ); 
1102     close $App::Ack
::fh
; 
1103     App
::Ack
::exit_from_ack
( $nmatches ); 
1110 ack - grep-like text finder 
1114     ack [options] PATTERN [FILE...] 
1115     ack -f [options] [DIRECTORY...] 
1119 Ack is designed as an alternative to F<grep> for programmers. 
1121 Ack searches the named input FILEs (or standard input if no files 
1122 are named, or the file name - is given) for lines containing a match 
1123 to the given PATTERN.  By default, ack prints the matching lines. 
1125 PATTERN is a Perl regular expression.  Perl regular expressions 
1126 are commonly found in other programming languages, but for the particulars 
1127 of their behavior, please consult 
1128 L<http://perldoc.perl.org/perlreref.html|perlreref>.  If you don't know 
1129 how to use regular expression but are interested in learning, you may 
1130 consult L<http://perldoc.perl.org/perlretut.html|perlretut>.  If you do not 
1131 need or want ack to use regular expressions, please see the 
1132 C<-Q>/C<--literal> option. 
1134 Ack can also list files that would be searched, without actually 
1135 searching them, to let you take advantage of ack's file-type filtering 
1138 =head1 FILE SELECTION 
1140 If files are not specified for searching, either on the command 
1141 line or piped in with the C<-x> option, I<ack> delves into 
1142 subdirectories selecting files for searching. 
1144 I<ack> is intelligent about the files it searches.  It knows about 
1145 certain file types, based on both the extension on the file and, 
1146 in some cases, the contents of the file.  These selections can be 
1147 made with the B<--type> option. 
1149 With no file selection, I<ack> searches through regular files that 
1150 are not explicitly excluded by B<--ignore-dir> and B<--ignore-file> 
1151 options, either present in F<ackrc> files or on the command line. 
1153 The default options for I<ack> ignore certain files and directories.  These 
1158 =item * Backup files: Files matching F<#*#> or ending with F<~>. 
1160 =item * Coredumps: Files matching F<core.\d+> 
1162 =item * Version control directories like F<.svn> and F<.git>. 
1166 Run I<ack> with the C<--dump> option to see what settings are set. 
1168 However, I<ack> always searches the files given on the command line, 
1169 no matter what type.  If you tell I<ack> to search in a coredump, 
1170 it will search in a coredump. 
1172 =head1 DIRECTORY SELECTION 
1174 I<ack> descends through the directory tree of the starting directories 
1175 specified.  If no directories are specified, the current working directory is 
1176 used.  However, it will ignore the shadow directories used by 
1177 many version control systems, and the build directories used by the 
1178 Perl MakeMaker system.  You may add or remove a directory from this 
1179 list with the B<--[no]ignore-dir> option. The option may be repeated 
1180 to add/remove multiple directories from the ignore list. 
1182 For a complete list of directories that do not get searched, run 
1185 =head1 WHEN TO USE GREP 
1187 I<ack> trumps I<grep> as an everyday tool 99% of the time, but don't 
1188 throw I<grep> away, because there are times you'll still need it. 
1190 E.g., searching through huge files looking for regexes that can be 
1191 expressed with I<grep> syntax should be quicker with I<grep>. 
1193 If your script or parent program uses I<grep> C<--quiet> or C<--silent> 
1194 or needs exit 2 on IO error, use I<grep>. 
1202 Specifies an ackrc file to load after all others; see L</"ACKRC LOCATION SEMANTICS">. 
1204 =item B<-A I<NUM>>, B<--after-context=I<NUM>> 
1206 Print I<NUM> lines of trailing context after matching lines. 
1208 =item B<-B I<NUM>>, B<--before-context=I<NUM>> 
1210 Print I<NUM> lines of leading context before matching lines. 
1212 =item B<--[no]break> 
1214 Print a break between results from different files. On by default 
1215 when used interactively. 
1217 =item B<-C [I<NUM>]>, B<--context[=I<NUM>]> 
1219 Print I<NUM> lines (default 2) of context around matching lines. 
1221 =item B<-c>, B<--count> 
1223 Suppress normal output; instead print a count of matching lines for 
1224 each input file.  If B<-l> is in effect, it will only show the 
1225 number of lines for each file that has lines matching.  Without 
1226 B<-l>, some line counts may be zeroes. 
1228 If combined with B<-h> (B<--no-filename>) ack outputs only one total 
1231 =item B<--[no]color>, B<--[no]colour> 
1233 B<--color> highlights the matching text.  B<--nocolor> suppresses 
1234 the color.  This is on by default unless the output is redirected. 
1236 On Windows, this option is off by default unless the 
1237 L<Win32::Console::ANSI> module is installed or the C<ACK_PAGER_COLOR> 
1238 environment variable is used. 
1240 =item B<--color-filename=I<color>> 
1242 Sets the color to be used for filenames. 
1244 =item B<--color-match=I<color>> 
1246 Sets the color to be used for matches. 
1248 =item B<--color-lineno=I<color>> 
1250 Sets the color to be used for line numbers. 
1252 =item B<--[no]column> 
1254 Show the column number of the first match.  This is helpful for 
1255 editors that can place your cursor at a given position. 
1257 =item B<--create-ackrc> 
1259 Dumps the default ack options to standard output.  This is useful for 
1260 when you want to customize the defaults. 
1264 Writes the list of options loaded and where they came from to standard 
1265 output.  Handy for debugging. 
1269 B<--noenv> disables all environment processing. No F<.ackrc> is 
1270 read and all environment variables are ignored. By default, F<ack> 
1271 considers F<.ackrc> and settings in the environment. 
1275 B<--flush> flushes output immediately.  This is off by default 
1276 unless ack is running interactively (when output goes to a pipe or 
1281 Only print the files that would be searched, without actually doing 
1282 any searching.  PATTERN must not be specified, or it will be taken 
1283 as a path to search. 
1285 =item B<--files-from=I<FILE>> 
1287 The list of files to be searched is specified in I<FILE>.  The list of 
1288 files are separated by newlines.  If I<FILE> is C<->, the list is loaded 
1289 from standard input. 
1291 =item B<--[no]filter> 
1293 Forces ack to act as if it were receiving input via a pipe. 
1295 =item B<--[no]follow> 
1297 Follow or don't follow symlinks, other than whatever starting files 
1298 or directories were specified on the command line. 
1300 This is off by default. 
1302 =item B<-g I<PATTERN>> 
1304 Print files where the relative path + filename matches I<PATTERN>. 
1305 This option can be combined with B<--color> to make it easier to spot 
1308 =item B<--[no]group> 
1310 B<--group> groups matches by file name.  This is the default 
1311 when used interactively. 
1313 B<--nogroup> prints one result per line, like grep.  This is the 
1314 default when output is redirected. 
1316 =item B<-H>, B<--with-filename> 
1318 Print the filename for each match. This is the default unless searching 
1319 a single explicitly specified file. 
1321 =item B<-h>, B<--no-filename> 
1323 Suppress the prefixing of filenames on output when multiple files are 
1326 =item B<--[no]heading> 
1328 Print a filename heading above each file's results.  This is the default 
1329 when used interactively. 
1331 =item B<--help>, B<-?> 
1333 Print a short help statement. 
1335 =item B<--help-types>, B<--help=types> 
1337 Print all known types. 
1339 =item B<-i>, B<--ignore-case> 
1341 Ignore case distinctions in PATTERN 
1343 =item B<--ignore-ack-defaults> 
1345 Tells ack to completely ignore the default definitions provided with ack. 
1346 This is useful in combination with B<--create-ackrc> if you I<really> want 
1349 =item B<--[no]ignore-dir=I<DIRNAME>>, B<--[no]ignore-directory=I<DIRNAME>> 
1351 Ignore directory (as CVS, .svn, etc are ignored). May be used 
1352 multiple times to ignore multiple directories. For example, mason 
1353 users may wish to include B<--ignore-dir=data>. The B<--noignore-dir> 
1354 option allows users to search directories which would normally be 
1355 ignored (perhaps to research the contents of F<.svn/props> directories). 
1357 The I<DIRNAME> must always be a simple directory name. Nested 
1358 directories like F<foo/bar> are NOT supported. You would need to 
1359 specify B<--ignore-dir=foo> and then no files from any foo directory 
1360 are taken into account by ack unless given explicitly on the command 
1363 =item B<--ignore-file=I<FILTERTYPE:FILTERARGS>> 
1365 Ignore files matching I<FILTERTYPE:FILTERARGS>.  The filters are specified 
1366 identically to file type filters as seen in L</"Defining your own types">. 
1368 =item B<-k>, B<--known-types> 
1370 Limit selected files to those with types that ack knows about.  This is 
1371 equivalent to the default behavior found in ack 1. 
1373 =item B<--lines=I<NUM>> 
1375 Only print line I<NUM> of each file. Multiple lines can be given with multiple 
1376 B<--lines> options or as a comma separated list (B<--lines=3,5,7>). B<--lines=4-7> 
1377 also works. The lines are always output in ascending order, no matter the 
1378 order given on the command line. 
1380 =item B<-l>, B<--files-with-matches> 
1382 Only print the filenames of matching files, instead of the matching text. 
1384 =item B<-L>, B<--files-without-matches> 
1386 Only print the filenames of files that do I<NOT> match. 
1388 =item B<--match I<PATTERN>> 
1390 Specify the I<PATTERN> explicitly. This is helpful if you don't want to put the 
1391 regex as your first argument, e.g. when executing multiple searches over the 
1394     # search for foo and bar in given files 
1395     ack file1 t/file* --match foo 
1396     ack file1 t/file* --match bar 
1398 =item B<-m=I<NUM>>, B<--max-count=I<NUM>> 
1400 Stop reading a file after I<NUM> matches. 
1404 Print this manual page. 
1406 =item B<-n>, B<--no-recurse> 
1408 No descending into subdirectories. 
1412 Show only the part of each line matching PATTERN (turns off text 
1415 =item B<--output=I<expr>> 
1417 Output the evaluation of I<expr> for each line (turns off text 
1419 If PATTERN matches more than once then a line is output for each non-overlapping match. 
1420 For more information please see the section L</"Examples of F<--output>">. 
1422 =item B<--pager=I<program>>, B<--nopager> 
1424 B<--pager> directs ack's output through I<program>.  This can also be specified 
1425 via the C<ACK_PAGER> and C<ACK_PAGER_COLOR> environment variables. 
1427 Using --pager does not suppress grouping and coloring like piping 
1428 output on the command-line does. 
1430 B<--nopager> cancels any setting in ~/.ackrc, C<ACK_PAGER> or C<ACK_PAGER_COLOR>. 
1431 No output will be sent through a pager. 
1435 Prints all lines, whether or not they match the expression.  Highlighting 
1436 will still work, though, so it can be used to highlight matches while 
1437 still seeing the entire file, as in: 
1439     # Watch a log file, and highlight a certain IP address 
1440     $ tail -f ~/access.log | ack --passthru 123.45.67.89 
1444 Only works in conjunction with -f, -g, -l or -c (filename output). The filenames 
1445 are output separated with a null byte instead of the usual newline. This is 
1446 helpful when dealing with filenames that contain whitespace, e.g. 
1448     # remove all files of type html 
1449     ack -f --html --print0 | xargs -0 rm -f 
1451 =item B<-Q>, B<--literal> 
1453 Quote all metacharacters in PATTERN, it is treated as a literal. 
1455 =item B<-r>, B<-R>, B<--recurse> 
1457 Recurse into sub-directories. This is the default and just here for 
1458 compatibility with grep. You can also use it for turning B<--no-recurse> off. 
1462 Suppress error messages about nonexistent or unreadable files.  This is taken 
1465 =item B<--[no]smart-case>, B<--no-smart-case> 
1467 Ignore case in the search strings if PATTERN contains no uppercase 
1468 characters. This is similar to C<smartcase> in vim. This option is 
1469 off by default, and ignored if C<-i> is specified. 
1471 B<-i> always overrides this option. 
1473 =item B<--sort-files> 
1475 Sorts the found files lexicographically.  Use this if you want your file 
1476 listings to be deterministic between runs of I<ack>. 
1478 =item B<--show-types> 
1480 Outputs the filetypes that ack associates with each file. 
1482 Works with B<-f> and B<-g> options. 
1484 =item B<--type=[no]TYPE> 
1486 Specify the types of files to include or exclude from a search. 
1487 TYPE is a filetype, like I<perl> or I<xml>.  B<--type=perl> can 
1488 also be specified as B<--perl>, and B<--type=noperl> can be done 
1491 If a file is of both type "foo" and "bar", specifying --foo and 
1492 --nobar will exclude the file, because an exclusion takes precedence 
1495 Type specifications can be repeated and are ORed together. 
1497 See I<ack --help=types> for a list of valid types. 
1499 =item B<--type-add I<TYPE>:I<FILTER>:I<FILTERARGS>> 
1501 Files with the given FILTERARGS applied to the given FILTER 
1502 are recognized as being of (the existing) type TYPE. 
1503 See also L</"Defining your own types">. 
1506 =item B<--type-set I<TYPE>:I<FILTER>:I<FILTERARGS>> 
1508 Files with the given FILTERARGS applied to the given FILTER are recognized as 
1509 being of type TYPE. This replaces an existing definition for type TYPE.  See 
1510 also L</"Defining your own types">. 
1512 =item B<--type-del I<TYPE>> 
1514 The filters associated with TYPE are removed from Ack, and are no longer considered 
1517 =item B<-v>, B<--invert-match> 
1519 Invert match: select non-matching lines 
1523 Display version and copyright information. 
1525 =item B<-w>, B<--word-regexp> 
1527 Force PATTERN to match only whole words.  The PATTERN is wrapped with 
1528 C<\b> metacharacters. 
1532 An abbreviation for B<--files-from=->; the list of files to search are read 
1533 from standard input, with one line per file. 
1537 Stops after reporting first match of any kind.  This is different 
1538 from B<--max-count=1> or B<-m1>, where only one match per file is 
1539 shown.  Also, B<-1> works with B<-f> and B<-g>, where B<-m> does 
1544 Display the all-important Bill The Cat logo.  Note that the exact 
1545 spelling of B<--thpppppt> is not important.  It's checked against 
1546 a regular expression. 
1550 Check with the admiral for traps. 
1554 Chocolate, Chocolate, Chocolate! 
1558 =head1 THE .ackrc FILE 
1560 The F<.ackrc> file contains command-line options that are prepended 
1561 to the command line before processing.  Multiple options may live 
1562 on multiple lines.  Lines beginning with a # are ignored.  A F<.ackrc> 
1563 might look like this: 
1565     # Always sort the files 
1568     # Always color, even if piping to a another program 
1571     # Use "less -r" as my pager 
1574 Note that arguments with spaces in them do not need to be quoted, 
1575 as they are not interpreted by the shell. Basically, each I<line> 
1576 in the F<.ackrc> file is interpreted as one element of C<@ARGV>. 
1578 F<ack> looks in several locations for F<.ackrc> files; the searching 
1579 process is detailed in L</"ACKRC LOCATION SEMANTICS">.  These 
1580 files are not considered if B<--noenv> is specified on the command line. 
1582 =head1 Defining your own types 
1584 ack allows you to define your own types in addition to the predefined 
1585 types. This is done with command line options that are best put into 
1586 an F<.ackrc> file - then you do not have to define your types over and 
1587 over again. In the following examples the options will always be shown 
1588 on one command line so that they can be easily copy & pasted. 
1590 I<ack --perl foo> searches for foo in all perl files. I<ack --help=types> 
1591 tells you, that perl files are files ending 
1592 in .pl, .pm, .pod or .t. So what if you would like to include .xs 
1593 files as well when searching for --perl files? I<ack --type-add perl:ext:xs --perl foo> 
1594 does this for you. B<--type-add> appends 
1595 additional extensions to an existing type. 
1597 If you want to define a new type, or completely redefine an existing 
1598 type, then use B<--type-set>. I<ack --type-set eiffel:ext:e,eiffel> defines 
1599 the type I<eiffel> to include files with 
1600 the extensions .e or .eiffel. So to search for all eiffel files 
1601 containing the word Bertrand use I<ack --type-set eiffel:ext:e,eiffel --eiffel Bertrand>. 
1602 As usual, you can also write B<--type=eiffel> 
1603 instead of B<--eiffel>. Negation also works, so B<--noeiffel> excludes 
1604 all eiffel files from a search. Redefining also works: I<ack --type-set cc:ext:c,h> 
1605 and I<.xs> files no longer belong to the type I<cc>. 
1607 When defining your own types in the F<.ackrc> file you have to use 
1610   --type-set=eiffel:ext:e,eiffel 
1612 or writing on separate lines 
1617 The following does B<NOT> work in the F<.ackrc> file: 
1619   --type-set eiffel:ext:e,eiffel 
1622 In order to see all currently defined types, use I<--help-types>, e.g. 
1623 I<ack --type-set backup:ext:bak --type-add perl:ext:perl --help-types> 
1625 In addition to filtering based on extension (like ack 1.x allowed), ack 2 
1626 offers additional filter types.  The generic syntax is 
1627 I<--type-set TYPE:FILTER:FILTERARGS>; I<FILTERARGS> depends on the value 
1632 =item is:I<FILENAME> 
1634 I<is> filters match the target filename exactly.  It takes exactly one 
1635 argument, which is the name of the file to match. 
1639     --type-set make:is:Makefile 
1641 =item ext:I<EXTENSION>[,I<EXTENSION2>[,...]] 
1643 I<ext> filters match the extension of the target file against a list 
1644 of extensions.  No leading dot is needed for the extensions. 
1648     --type-set perl:ext:pl,pm,t 
1650 =item match:I<PATTERN> 
1652 I<match> filters match the target filename against a regular expression. 
1653 The regular expression is made case insensitive for the search. 
1657     --type-set make:match:/(gnu)?makefile/ 
1659 =item firstlinematch:I<PATTERN> 
1661 I<firstlinematch> matches the first line of the target file against a 
1662 regular expression.  Like I<match>, the regular expression is made 
1667     --type-add perl:firstlinematch:/perl/ 
1671 More filter types may be made available in the future. 
1673 =head1 ENVIRONMENT VARIABLES 
1675 For commonly-used ack options, environment variables can make life 
1676 much easier.  These variables are ignored if B<--noenv> is specified 
1677 on the command line. 
1683 Specifies the location of the user's F<.ackrc> file.  If this file doesn't 
1684 exist, F<ack> looks in the default location. 
1688 This variable specifies default options to be placed in front of 
1689 any explicit options on the command line. 
1691 =item ACK_COLOR_FILENAME 
1693 Specifies the color of the filename when it's printed in B<--group> 
1694 mode.  By default, it's "bold green". 
1696 The recognized attributes are clear, reset, dark, bold, underline, 
1697 underscore, blink, reverse, concealed black, red, green, yellow, 
1698 blue, magenta, on_black, on_red, on_green, on_yellow, on_blue, 
1699 on_magenta, on_cyan, and on_white.  Case is not significant. 
1700 Underline and underscore are equivalent, as are clear and reset. 
1701 The color alone sets the foreground color, and on_color sets the 
1704 This option can also be set with B<--color-filename>. 
1706 =item ACK_COLOR_MATCH 
1708 Specifies the color of the matching text when printed in B<--color> 
1709 mode.  By default, it's "black on_yellow". 
1711 This option can also be set with B<--color-match>. 
1713 See B<ACK_COLOR_FILENAME> for the color specifications. 
1715 =item ACK_COLOR_LINENO 
1717 Specifies the color of the line number when printed in B<--color> 
1718 mode.  By default, it's "bold yellow". 
1720 This option can also be set with B<--color-lineno>. 
1722 See B<ACK_COLOR_FILENAME> for the color specifications. 
1726 Specifies a pager program, such as C<more>, C<less> or C<most>, to which 
1727 ack will send its output. 
1729 Using C<ACK_PAGER> does not suppress grouping and coloring like 
1730 piping output on the command-line does, except that on Windows 
1731 ack will assume that C<ACK_PAGER> does not support color. 
1733 C<ACK_PAGER_COLOR> overrides C<ACK_PAGER> if both are specified. 
1735 =item ACK_PAGER_COLOR 
1737 Specifies a pager program that understands ANSI color sequences. 
1738 Using C<ACK_PAGER_COLOR> does not suppress grouping and coloring 
1739 like piping output on the command-line does. 
1741 If you are not on Windows, you never need to use C<ACK_PAGER_COLOR>. 
1745 =head1 AVAILABLE COLORS 
1747 F<ack> uses the colors available in Perl's L<Term::ANSIColor> module, which 
1748 provides the following listed values. Note that case does not matter when using 
1751 =head2 Foreground colors 
1753     black  red  green  yellow  blue  magenta  cyan  white 
1755     bright_black  bright_red      bright_green  bright_yellow 
1756     bright_blue   bright_magenta  bright_cyan   bright_white 
1758 =head2 Background colors 
1760     on_black  on_red      on_green  on_yellow 
1761     on_blue   on_magenta  on_cyan   on_white 
1763     on_bright_black  on_bright_red      on_bright_green  on_bright_yellow 
1764     on_bright_blue   on_bright_magenta  on_bright_cyan   on_bright_white 
1766 =head1 ACK & OTHER TOOLS 
1768 =head2 Vim integration 
1770 F<ack> integrates easily with the Vim text editor. Set this in your 
1771 F<.vimrc> to use F<ack> instead of F<grep>: 
1775 That example uses C<-k> to search through only files of the types ack 
1776 knows about, but you may use other default flags. Now you can search 
1777 with F<ack> and easily step through the results in Vim: 
1779   :grep Dumper perllib 
1781 Miles Sterrett has written a Vim plugin for F<ack> which allows you to use 
1782 C<:Ack> instead of C<:grep>, as well as several other advanced features. 
1784 L<https://github.com/mileszs/ack.vim> 
1786 =head2 Emacs integration 
1788 Phil Jackson put together an F<ack.el> extension that "provides a 
1789 simple compilation mode ... has the ability to guess what files you 
1790 want to search for based on the major-mode." 
1792 L<http://www.shellarchive.co.uk/content/emacs.html> 
1794 =head2 TextMate integration 
1796 Pedro Melo is a TextMate user who writes "I spend my day mostly 
1797 inside TextMate, and the built-in find-in-project sucks with large 
1798 projects.  So I hacked a TextMate command that was using find + 
1799 grep to use ack.  The result is the Search in Project with ack, and 
1800 you can find it here: 
1801 L<http://www.simplicidade.org/notes/archives/2008/03/search_in_proje.html>" 
1803 =head2 Shell and Return Code 
1805 For greater compatibility with I<grep>, I<ack> in normal use returns 
1806 shell return or exit code of 0 only if something is found and 1 if 
1809 (Shell exit code 1 is C<$?=256> in perl with C<system> or backticks.) 
1811 The I<grep> code 2 for errors is not used. 
1813 If C<-f> or C<-g> are specified, then 0 is returned if at least one 
1814 file is found.  If no files are found, then 1 is returned. 
1818 =head1 DEBUGGING ACK PROBLEMS 
1820 If ack gives you output you're not expecting, start with a few simple steps. 
1822 =head2 Use B<--noenv> 
1824 Your environment variables and F<.ackrc> may be doing things you're 
1825 not expecting, or forgotten you specified.  Use B<--noenv> to ignore 
1826 your environment and F<.ackrc>. 
1828 =head2 Use B<-f> to see what files have been selected 
1830 Ack's B<-f> was originally added as a debugging tool.  If ack is 
1831 not finding matches you think it should find, run F<ack -f> to see 
1832 what files have been selected.  You can also add the C<--show-types> 
1833 options to show the type of each file selected. 
1835 =head2 Use B<--dump> 
1837 This lists the ackrc files that are loaded and the options loaded 
1839 So for example you can find a list of directories that do not get searched or where filetypes are defined. 
1843 =head2 Use the F<.ackrc> file. 
1845 The F<.ackrc> is the place to put all your options you use most of 
1846 the time but don't want to remember.  Put all your --type-add and 
1847 --type-set definitions in it.  If you like --smart-case, set it 
1848 there, too.  I also set --sort-files there. 
1850 =head2 Use F<-f> for working with big codesets 
1852 Ack does more than search files.  C<ack -f --perl> will create a 
1853 list of all the Perl files in a tree, ideal for sending into F<xargs>. 
1856     # Change all "this" to "that" in all Perl files in a tree. 
1857     ack -f --perl | xargs perl -p -i -e's/this/that/g' 
1861     perl -p -i -e's/this/that/g' $(ack -f --perl) 
1863 =head2 Use F<-Q> when in doubt about metacharacters 
1865 If you're searching for something with a regular expression 
1866 metacharacter, most often a period in a filename or IP address, add 
1867 the -Q to avoid false positives without all the backslashing.  See 
1868 the following example for more... 
1870 =head2 Use ack to watch log files 
1872 Here's one I used the other day to find trouble spots for a website 
1873 visitor.  The user had a problem loading F<troublesome.gif>, so I 
1874 took the access log and scanned it with ack twice. 
1876     ack -Q aa.bb.cc.dd /path/to/access.log | ack -Q -B5 troublesome.gif 
1878 The first ack finds only the lines in the Apache log for the given 
1879 IP.  The second finds the match on my troublesome GIF, and shows 
1880 the previous five lines from the log in each case. 
1882 =head2 Examples of F<--output> 
1884 Following variables are useful in the expansion string: 
1890 The whole string matched by PATTERN. 
1892 =item C<$1>, C<$2>, ... 
1894 The contents of the 1st, 2nd ... bracketed group in PATTERN. 
1898 The string before the match. 
1902 The string after the match. 
1906 For more details and other variables see 
1907 L<http://perldoc.perl.org/perlvar.html#Variables-related-to-regular-expressions|perlvar>. 
1909 This example shows how to add text around a particular pattern 
1910 (in this case adding _ around word with "e") 
1912     ack2.pl "\w*e\w*" quick.txt --output="$`_$&_$'" 
1913     _The_ quick brown fox jumps over the lazy dog 
1914     The quick brown fox jumps _over_ the lazy dog 
1915     The quick brown fox jumps over _the_ lazy dog 
1917 This shows how to pick out particular parts of a match using ( ) within regular expression. 
1919   ack '=head(\d+)\s+(.*)' --output=' $1 : $2' 
1920   input file contains "=head1 NAME" 
1923 =head2 Share your knowledge 
1925 Join the ack-users mailing list.  Send me your tips and I may add 
1930 =head2 Why isn't ack finding a match in (some file)? 
1932 Probably because it's of a type that ack doesn't recognize.  ack's 
1933 searching behavior is driven by filetype.  B<If ack doesn't know 
1934 what kind of file it is, ack ignores the file.> 
1936 Use the C<-f> switch to see a list of files that ack will search 
1937 for you.  You can use the C<--show-types> switch to show which type 
1938 ack thinks each file is. 
1940 =head2 Wouldn't it be great if F<ack> did search & replace? 
1942 No, ack will always be read-only.  Perl has a perfectly good way 
1943 to do search & replace in files, using the C<-i>, C<-p> and C<-n> 
1946 You can certainly use ack to select your files to update.  For 
1947 example, to change all "foo" to "bar" in all PHP files, you can do 
1948 this from the Unix shell: 
1950     $ perl -i -p -e's/foo/bar/g' $(ack -f --php) 
1952 =head2 Can I make ack recognize F<.xyz> files? 
1954 Yes!  Please see L</"Defining your own types">.  If you think 
1955 that F<ack> should recognize a type by default, please see 
1958 =head2 There's already a program/package called ack. 
1962 =head2 Why is it called ack if it's called ack-grep? 
1964 The name of the program is "ack".  Some packagers have called it 
1965 "ack-grep" when creating packages because there's already a package 
1966 out there called "ack" that has nothing to do with this ack. 
1968 I suggest you make a symlink named F<ack> that points to F<ack-grep> 
1969 because one of the crucial benefits of ack is having a name that's 
1970 so short and simple to type. 
1972 To do that, run this with F<sudo> or as root: 
1974    ln -s /usr/bin/ack-grep /usr/bin/ack 
1976 Alternatively, you could use a shell alias: 
1984 =head2 What does F<ack> mean? 
1986 Nothing.  I wanted a name that was easy to type and that you could 
1987 pronounce as a single syllable. 
1989 =head2 Can I do multi-line regexes? 
1991 No, ack does not support regexes that match multiple lines.  Doing 
1992 so would require reading in the entire file at a time. 
1994 If you want to see lines near your match, use the C<--A>, C<--B> 
1995 and C<--C> switches for displaying context. 
1997 =head2 Why is ack telling me I have an invalid option when searching for C<+foo>? 
1999 ack treats command line options beginning with C<+> or C<-> as options; if you 
2000 would like to search for these, you may prefix your search term with C<--> or 
2001 use the C<--match> option.  (However, don't forget that C<+> is a regular 
2002 expression metacharacter!) 
2004 =head2 Why does C<"ack '.{40000,}'"> fail?  Isn't that a valid regex? 
2006 The Perl language limits the repetition quanitifier to 32K.  You 
2007 can search for C<.{32767}> but not C<.{32768}>. 
2009 =head1 ACKRC LOCATION SEMANTICS 
2011 Ack can load its configuration from many sources.  The following list 
2012 specifies the sources Ack looks for configuration files; each one 
2013 that is found is loaded in the order specified here, and 
2014 each one overrides options set in any of the sources preceding 
2015 it.  (For example, if I set --sort-files in my user ackrc, and 
2016 --nosort-files on the command line, the command line takes 
2023 Defaults are loaded from App::Ack::ConfigDefaults.  This can be omitted 
2024 using C<--ignore-ack-defaults>. 
2026 =item * Global ackrc 
2028 Options are then loaded from the global ackrc.  This is located at 
2029 C</etc/ackrc> on Unix-like systems. 
2031 Under Windows XP and earlier, the global ackrc is at 
2032 C<C:\Documents and Settings\All Users\Application Data\ackrc> 
2034 Under Windows Vista/7, the global ackrc is at 
2035 C<C:\ProgramData\ackrc> 
2037 The C<--noenv> option prevents all ackrc files from being loaded. 
2041 Options are then loaded from the user's ackrc.  This is located at 
2042 C<$HOME/.ackrc> on Unix-like systems. 
2044 Under Windows XP and earlier, the user's ackrc is at 
2045 C<C:\Documents and Settings\$USER\Application Data\ackrc>. 
2047 Under Windows Vista/7, the user's ackrc is at 
2048 C<C:\Users\$USER\AppData\Roaming\ackrc>. 
2050 If you want to load a different user-level ackrc, it may be specified 
2051 with the C<$ACKRC> environment variable. 
2053 The C<--noenv> option prevents all ackrc files from being loaded. 
2055 =item * Project ackrc 
2057 Options are then loaded from the project ackrc.  The project ackrc is 
2058 the first ackrc file with the name C<.ackrc> or C<_ackrc>, first searching 
2059 in the current directory, then the parent directory, then the grandparent 
2060 directory, etc.  This can be omitted using C<--noenv>. 
2064 The C<--ackrc> option may be included on the command line to specify an 
2065 ackrc file that can override all others.  It is consulted even if C<--noenv> 
2070 Options are then loaded from the environment variable C<ACK_OPTIONS>.  This can 
2071 be omitted using C<--noenv>. 
2073 =item * Command line 
2075 Options are then loaded from the command line. 
2079 =head1 DIFFERENCES BETWEEN ACK 1.X AND ACK 2.X 
2081 A lot of changes were made for ack 2; here is a list of them. 
2083 =head2 GENERAL CHANGES 
2089 When no selectors are specified, ack 1.x only searches through files that 
2090 it can map to a file type.  ack 2.x, by contrast, will search through 
2091 every regular, non-binary file that is not explicitly ignored via 
2092 B<--ignore-file> or B<--ignore-dir>.  This is similar to the behavior of the 
2093 B<-a/--all> option in ack 1.x. 
2097 A more flexible filter system has been added, so that more powerful file types 
2098 may be created by the user.  For details, please consult 
2099 L</"Defining your own types">. 
2103 ack now loads multiple ackrc files; see L</"ACKRC LOCATION SEMANTICS"> for 
2108 ack's default filter definitions aren't special; you may tell ack to 
2109 completely disregard them if you don't like them. 
2113 =head2 REMOVED OPTIONS 
2119 Because of the change in default search behavior, the B<-a/--all> and 
2120 B<-u/--unrestricted> options have been removed.  In addition, the 
2121 B<-k/--known-types> option was added to cause ack to behave with 
2122 the default search behavior of ack 1.x. 
2126 The B<-G> option has been removed.  Two regular expressions on the 
2127 command line was considered too confusing; to simulate B<-G>'s functionality, 
2128 you may use the new B<-x> option to pipe filenames from one invocation of 
2133 The B<--binary> option has been removed. 
2137 The B<--skipped> option has been removed. 
2141 The B<--text> option has been removed. 
2145 The B<--invert-file-match> option has been removed.  Instead, you may 
2146 use B<-v> with B<-g>. 
2150 =head2 CHANGED OPTIONS 
2156 The options that modify the regular expression's behavior (B<-i>, B<-w>, 
2157 B<-Q>, and B<-v>) may now be used with B<-g>. 
2161 =head2 ADDED OPTIONS 
2167 B<--files-from> was added so that a user may submit a list of filenames as 
2168 a list of files to search. 
2172 B<-x> was added to tell ack to accept a list of filenames via standard input; 
2173 this list is the list of filenames that will be used for the search. 
2177 B<-s> was added to tell ack to suppress error messages about non-existent or 
2182 B<--ignore-directory> and B<--noignore-directory> were added as aliases for 
2183 B<--ignore-dir> and B<--noignore-dir> respectively. 
2187 B<--ignore-file> was added so that users may specify patterns of files to 
2188 ignore (ex. /.*~$/). 
2192 B<--dump> was added to allow users to easily find out which options are 
2197 B<--create-ackrc> was added so that users may create custom ackrc files based 
2198 on the default settings loaded by ack, and so that users may easily view those 
2203 B<--type-del> was added to selectively remove file type definitions. 
2207 B<--ignore-ack-defaults> was added so that users may ignore ack's default 
2208 options in favor of their own. 
2212 B<--bar> was added so ack users may consult Admiral Ackbar. 
2218 Andy Lester, C<< <andy at petdance.com> >> 
2222 Please report any bugs or feature requests to the issues list at 
2223 Github: L<https://github.com/petdance/ack2/issues> 
2227 All enhancement requests MUST first be posted to the ack-users 
2228 mailing list at L<http://groups.google.com/group/ack-users>.  I 
2229 will not consider a request without it first getting seen by other 
2230 ack users.  This includes requests for new filetypes. 
2232 There is a list of enhancements I want to make to F<ack> in the ack 
2233 issues list at Github: L<https://github.com/petdance/ack2/issues> 
2235 Patches are always welcome, but patches with tests get the most 
2240 Support for and information about F<ack> can be found at: 
2244 =item * The ack homepage 
2246 L<http://beyondgrep.com/> 
2248 =item * The ack-users mailing list 
2250 L<http://groups.google.com/group/ack-users> 
2252 =item * The ack issues list at Github 
2254 L<https://github.com/petdance/ack2/issues> 
2256 =item * AnnoCPAN: Annotated CPAN documentation 
2258 L<http://annocpan.org/dist/ack> 
2260 =item * CPAN Ratings 
2262 L<http://cpanratings.perl.org/d/ack> 
2266 L<http://search.cpan.org/dist/ack> 
2268 =item * Git source repository 
2270 L<https://github.com/petdance/ack2> 
2274 =head1 ACKNOWLEDGEMENTS 
2276 How appropriate to have I<ack>nowledgements! 
2278 Thanks to everyone who has contributed to ack in any way, including 
2283 RaE<uacute>l GundE<iacute>n, 
2289 RaE<aacute>l GundE<aacute>n, 
2325 Eric Van Dewoestine, 
2334 Christopher J. Madsen, 
2346 GE<aacute>bor SzabE<oacute>, 
2349 E<AElig>var ArnfjE<ouml>rE<eth> Bjarmason, 
2353 Mark Leighton Fisher, 
2359 Nilson Santos F. Jr, 
2364 Ask BjE<oslash>rn Hansen, 
2368 Slaven ReziE<0x107>, 
2378 =head1 COPYRIGHT & LICENSE 
2380 Copyright 2005-2015 Andy Lester. 
2382 This program is free software; you can redistribute it and/or modify 
2383 it under the terms of the Artistic License v2.0. 
2385 See http://www.perlfoundation.org/artistic_license_2_0 or the LICENSE.md 
2386 file that comes with the ack distribution. 
2398     $VERSION = '2.15_01'; 
2399     $COPYRIGHT = 'Copyright 2005-2015 Andy Lester.'; 
2414 our $is_filter_mode; 
2415 our $output_to_pipe; 
2421 use File
::Spec 
1.00015 (); 
2424     # These have to be checked before any filehandle diddling. 
2425     $output_to_pipe  = not -t 
*STDOUT
; 
2426     $is_filter_mode = -p STDIN
; 
2428     $is_cygwin       = ($^O eq 'cygwin'); 
2429     $is_windows      = ($^O eq 'MSWin32'); 
2430     $dir_sep_chars   = $is_windows ? quotemeta( '\\/' ) : quotemeta( File
::Spec-
>catfile( '', '' ) ); 
2435 sub remove_dir_sep 
{ 
2437     $path =~ s/[$dir_sep_chars]$//; 
2445     return CORE
::warn( _my_program
(), ': ', @_, "\n" ); 
2450     return CORE
::die( _my_program
(), ': ', @_, "\n" ); 
2454     require File
::Basename
; 
2455     return File
::Basename
::basename
( $0 ); 
2460 sub filetypes_supported 
{ 
2461     return keys %mappings; 
2465     my $y = q{_   /|,\\'!.x',=(www)=,   U   }; 
2466     $y =~ tr/,x!w/\nOo_/; 
2471     my $y = _get_thpppt
(); 
2472     App
::Ack
::print( "$y ack $_[0]!\n" ); 
2480  3~!I#7#I"7#I!?!+!="+"="+!:! 
2481  2?#I!7!I!?#I!7!I"+"=%+"=# 
2482  1?"+!?*+!=#~"=!+#?"="+! 
2483  0?"+!?"I"?&+!="~!=!~"=!+%="+" 
2484  /I!+!?)+!?!+!=$~!=!~!="+!="+"?!="?! 
2486  ,,!?%I"?(+$=$~!=#:"~$:!~! 
2487  ,I!?!I!?"I"?!+#?"+!?!+#="~$:!~!:!~!:!,!:!,":#~! 
2488  +I!?&+!="+!?#+$=!~":!~!:!~!:!,!:#,!:!,%:" 
2489  *+!I!?!+$=!+!=!+!?$+#=!~":!~":#,$:",#:!,!:! 
2490  *I!?"+!?!+!=$+!?#+#=#~":$,!:",!:!,&:" 
2491  )I!?$=!~!=#+"?!+!=!+!=!~!="~!:!~":!,'.!,%:!~! 
2492  (=!?"+!?!=!~$?"+!?!+!=#~"=",!="~$,$.",#.!:!=! 
2493  (I"+"="~"=!+&=!~"=!~!,!~!+!=!?!+!?!=!I!?!+"=!.",!.!,":! 
2494  %I$?!+!?!=%+!~!+#~!=!~#:#=!~!+!~!=#:!,%.!,!.!:" 
2495  $I!?!=!?!I!+!?"+!=!~!=!~!?!I!?!=!+!=!~#:",!~"=!~!:"~!=!:",&:" '-/ 
2496  $?!+!I!?"+"=!+"~!,!:"+#~#:#,"=!~"=!,!~!,!.",!:".!:! */! !I!t!'!s! !a! !g!r!e!p!!! !/! 
2497  $+"=!+!?!+"~!=!:!~!:"I!+!,!~!=!:!~!,!:!,$:!~".&:"~!,# (-/ 
2498  %~!=!~!=!:!.!+"~!:!,!.!,!~!=!:$.!,":!,!.!:!~!,!:!=!.#="~!,!:" ./! 
2499  %=!~!?!+"?"+!=!~",!.!:!?!~!.!:!,!:!,#.!,!:","~!:!=!~!=!:",!~! ./! 
2500  %+"~":!~!=#~!:!~!,!.!~!:",!~!=!~!.!:!,!.",!:!,":!=":!.!,!:!7! -/! 
2501  %~",!:".#:!=!:!,!:"+!:!~!:!.!,!~!,!.#,!.!,$:"~!,":"~!=! */! 
2502  &=!~!=#+!=!~",!.!:",#:#,!.",+:!,!.",!=!+!?! 
2503  &~!=!~!=!~!:"~#:",!.!,#~!:!.!+!,!.",$.",$.#,!+!I!?! 
2504  &~!="~!:!~":!~",!~!=!~":!,!:!~!,!:!,&.$,#."+!?!I!?!I! 
2505  &~!=!~!=!+!,!:!~!:!=!,!:!~&:$,!.!,".!,".!,#."~!+!?$I! 
2506  &~!=!~!="~!=!:!~":!,!~%:#,!:",!.!,#.",#I!7"I!?!+!?"I" 
2507  &+!I!7!:#~"=!~!:!,!:"~$.!=!.!,!~!,$.#,!~!7!I#?!+!?"I"7! 
2508  %7#?!+!~!:!=!~!=!~":!,!:"~":#.!,)7#I"?"I!7& 
2509  %7#I!=":!=!~!:"~$:"~!:#,!:!,!:!~!:#,!7#I!?#7) 
2510  $7$+!,!~!=#~!:!~!:!~$:#,!.!~!:!=!,":!7#I"?#7+=!?! 
2511  $7#I!~!,!~#=!~!:"~!:!,!:!,#:!=!~",":!7$I!?#I!7*+!=!+" 
2512  "I!7$I!,":!,!.!=":$,!:!,$:$7$I!+!?"I!7+?"I!7!I!7!,! 
2513  !,!7%I!:",!."~":!,&.!,!:!~!I!7$I!+!?"I!7,?!I!7',! 
2514  !7(,!.#~":!,%.!,!7%I!7!?#I"7,+!?!7* 
2515 7+:!,!~#,"=!7'I!?#I"7/+!7+ 
2516 77I!+!7!?!7!I"71+!7, 
2519     return App
::Ack
::__pic
($x); 
2525  0|! "C!H!O!C!O!L!A!T!E!!! !|! 
2526  0|! "C!H!O!C!O!L!A!T!E!!! !|! 
2527  0|! "C!H!O!C!O!L!A!T!E!!! !|! 
2533  4.! $\! /M!~!.!8! +.!M# 4 
2534  0,!.! (\! .~!M!N! ,+!I!.!M!.! 3 
2535  /?!O!.!M!:! '\! .O!.! +~!Z!=!N!.! 4 
2536  ..! !D!Z!.!Z!.! '\! 9=!M".! 6 
2537  /.! !.!~!M".! '\! 8~! 9 
2539  4.! &:!M! !N"M# !M"N!M! #D!M&=! = 
2540  :M!7!M#:! !~!M!7!,!$!M!:! #.! !O!N!.!M!:!M# ; 
2541  8Z!M"~!N!$!D!.!N!?! !I!N!.! (?!M! !M!,!D!M".! 9 
2542  (?!Z!M!N!:! )=!M!O!8!.!M!+!M! !M!,! !O!M! +,!M!.!M!~!Z!N!M!:! &:!~! 0 
2543  &8!7!.!~!M"D!M!,! &M!?!=!8! !M!,!O! !M!+! !+!O!.!M! $M#~! !.!8!M!Z!.!M! !O!M"Z! %:!~!M!Z!M!Z!.! + 
2544  &:!M!7!,! *M!.!Z!M! !8"M!.!M!~! !.!M!.!=! #~!8!.!M! !7!M! "N!Z#I! !D!M!,!M!.! $."M!,! !M!.! * 
2545  2$!O! "N! !.!M!I! !7" "M! "+!O! !~!M! !d!O!.!7!I!M!.! !.!O!=!M!.! !M",!M!.! %.!$!O!D! + 
2546  1~!O! "M!+! !8!$! "M! "?!O! %Z!8!D!M!?!8!I!O!7!M! #M!.!M! "M",!M! 4 
2547  07!~! ".!8! !.!M! "I!+! !.!M! &Z!D!.!7!=!M! !:!.!M! #:!8"+! !.!+!8! !8! 3 
2548  /~!M! #N! !~!M!$! !.!M! !.!M" &~!M! "~!M!O! "D! $M! !8! "M!,!M!+!D!.! 1 
2549  #.! #?!M!N!.! #~!O! $M!.!7!$! "?" !?!~!M! '7!8!?!M!.!+!M"O! $?"$!D! !.!O! !$!7!I!.! 0 
2550  $,!M!:!O!?! ".! !?!=! $=!:!O! !M! "M! !M! !+!$! (.! +.!M! !M!.! !8! !+"Z!~! $:!M!$! !.! ' 
2551  #.!8!.!I!$! $7!I! %M" !=!M! !~!M!D! "7!I! .I!O! %?!=!,!D! !,!M! !D!~!8!~! %D!M! ( 
2552  #.!M"?! $=!O! %=!N! "8!.! !Z!M! #M!~! (M!:! #.!M" &O! !M!.! !?!,! !8!.!N!~! $8!N!M!,!.! % 
2553  *$!O! &M!,! "O! !.!M!.! #M! (~!M( &O!.! !7! "M! !.!M!.!M!,! #.!M! !M! & 
2554  )=!8!.! $.!M!O!.! "$!.!I!N! !I!M# (7!M(I! %D"Z!M! "=!I! "M! !M!:! #~!D! ' 
2555  )D! &8!N!:! ".!O! !M!="M! "M! (7!M) %." !M!D!."M!.! !$!=! !M!,! + 
2556  (M! &+!.!M! #Z!7!O!M!.!~!8! +,!M#D!?!M#D! #.!Z!M#,!Z!?! !~!N! "N!.! !M! + 
2557  'D!:! %$!D! !?! #M!Z! !8!.! !M"?!7!?!7! '+!I!D! !?!O!:!M!:! ":!M!:! !M!7".!M! "8!+! !:!D! !.!M! * 
2558  %.!O!:! $.!O!+! !D!.! #M! "M!.!+!N!I!Z! "7!M!N!M!N!?!I!7!Z!=!M'D"~! #M!.!8!$! !:! !.!M! "N!?! !,!O! ) 
2559  !.!?!M!:!M!I! %8!,! "M!.! #M! "N! !M!.! !M!.! !+!~! !.!M!.! ':!M! $M! $M!Z!$! !M!.! "D! "M! "?!M! ( 
2560  !7!8! !+!I! ".! "$!=! ":!$! "+! !M!.! !O! !M!I!M".! !=!~! ",!O! '=!M! $$!,! #N!:! ":!8!.! !D!~! !,!M!.! !:!M!.! & 
2561  !:!,!.! &Z" #D! !.!8!."M!.! !8!?!Z!M!.!M! #Z!~! !?!M!Z!.! %~!O!.!8!$!N!8!O!I!:!~! !+! #M!.! !.!M!.! !+!M! ".!~!M!+! $ 
2562  !.! 'D!I! #?!M!.!M!,! !.!Z! !.!8! #M&O!I!?! (~!I!M"." !M!Z!.! !M!N!.! "+!$!.! "M!.! !M!?!.! "8!M! $ 
2563  (O!8! $M! !M!.! ".!:! !+!=! #M! #.!M! !+" *$!M":!.! !M!~! "M!7! #M! #7!Z! "M"$!M!.! !.! # 
2564  '$!Z! #.!7!+!M! $.!,! !+!:! #N! #.!M!.!+!M! +D!M! #=!N! ":!O! #=!M! #Z!D! $M!I! % 
2565  $,! ".! $.!M" %$!.! !?!~! "+!7!." !.!M!,! !M! *,!N!M!.$M!?! "D!,! #M!.! #N! + 
2566  ,M!Z! &M! "I!,! "M! %I!M! !?!=!.! (Z!8!M! $:!M!.! !,!M! $D! #.!M!.! ) 
2567  +8!O! &.!8! "I!,! !~!M! &N!M! !M!D! '?!N!O!." $?!7! "?!~! #M!.! #I!D!.! ( 
2568  3M!,! "N!.! !D" &.!+!M!.! !M":!.":!M!7!M!D! 'M!.! "M!.! "M!,! $I! ) 
2569  3I! #M! "M!,! !:! &.!M" ".!,! !.!$!M!I! #.! !:! !.!M!?! "N!+! ".! / 
2570  1M!,! #.!M!8!M!=!.! +~!N"O!Z"~! *+!M!.! "M! 2 
2571  0.!M! &M!.! 8:! %.!M!Z! "M!=! *O!,! % 
2572  0?!$! &N! )." .,! %."M! ":!M!.! 0 
2573  0N!:! %?!O! #.! ..! &,! &.!D!,! "N!I! 0 
2575     return App
::Ack
::__pic
($x); 
2579     my($compressed) = @_; 
2580     $compressed =~ s/(.)(.)/$1x(ord($2)-32)/eg; 
2581     App
::Ack
::print( $compressed ); 
2587     my $help_arg = shift || 0; 
2589     return show_help_types
() if $help_arg =~ /^types?/; 
2591     App
::Ack
::print( <<"END_OF_HELP" ); 
2592 Usage: ack [OPTION]... PATTERN [FILES OR DIRECTORIES] 
2594 Search for PATTERN in each source file in the tree from the current 
2595 directory on down.  If any files or directories are specified, then 
2596 only those files and directories are checked.  ack may also search 
2597 STDIN, but only if no file or directory arguments are specified, 
2598 or if one of them is "-". 
2600 Default switches may be specified in ACK_OPTIONS environment variable or 
2601 an .ackrc file. If you want no dependency on the environment, turn it 
2604 Example: ack -i select 
2607   -i, --ignore-case             Ignore case distinctions in PATTERN 
2608   --[no]smart-case              Ignore case distinctions in PATTERN, 
2609                                 only if PATTERN contains no upper case. 
2610                                 Ignored if -i is specified 
2611   -v, --invert-match            Invert match: select non-matching lines 
2612   -w, --word-regexp             Force PATTERN to match only whole words 
2613   -Q, --literal                 Quote all metacharacters; PATTERN is literal 
2616   --lines=NUM                   Only print line(s) NUM of each file 
2617   -l, --files-with-matches      Only print filenames containing matches 
2618   -L, --files-without-matches   Only print filenames with no matches 
2619   --output=expr                 Output the evaluation of expr for each line 
2620                                 (turns off text highlighting) 
2621   -o                            Show only the part of a line matching PATTERN 
2622                                 Same as --output='\$&' 
2623   --passthru                    Print all lines, whether matching or not 
2624   --match PATTERN               Specify PATTERN explicitly. 
2625   -m, --max-count=NUM           Stop searching in each file after NUM matches 
2626   -1                            Stop searching after one match of any kind 
2627   -H, --with-filename           Print the filename for each match (default: 
2628                                 on unless explicitly searching a single file) 
2629   -h, --no-filename             Suppress the prefixing filename on output 
2630   -c, --count                   Show number of lines matching per file 
2631   --[no]column                  Show the column number of the first match 
2633   -A NUM, --after-context=NUM   Print NUM lines of trailing context after 
2635   -B NUM, --before-context=NUM  Print NUM lines of leading context before 
2637   -C [NUM], --context[=NUM]     Print NUM lines (default 2) of output context. 
2639   --print0                      Print null byte as separator between filenames, 
2640                                 only works with -f, -g, -l, -L or -c. 
2642   -s                            Suppress error messages about nonexistent or 
2647   --pager=COMMAND               Pipes all ack output through COMMAND.  For 
2648                                 example, --pager="less -R".  Ignored if output 
2650   --nopager                     Do not send output through a pager.  Cancels 
2651                                 any setting in ~/.ackrc, ACK_PAGER or 
2653   --[no]heading                 Print a filename heading above each file's 
2654                                 results.  (default: on when used interactively) 
2655   --[no]break                   Print a break between results from different 
2656                                 files.  (default: on when used interactively) 
2657   --group                       Same as --heading --break 
2658   --nogroup                     Same as --noheading --nobreak 
2659   --[no]color                   Highlight the matching text (default: on unless 
2660                                 output is redirected, or on Windows) 
2661   --[no]colour                  Same as --[no]color 
2662   --color-filename=COLOR 
2664   --color-lineno=COLOR          Set the color for filenames, matches, and line 
2666   --flush                       Flush output immediately, even when ack is used 
2667                                 non-interactively (when output goes to a pipe or 
2672   -f                            Only print the files selected, without 
2673                                 searching.  The PATTERN must not be specified. 
2674   -g                            Same as -f, but only select files matching 
2676   --sort-files                  Sort the found files lexically. 
2677   --show-types                  Show which types each file has. 
2678   --files-from=FILE             Read the list of files to search from FILE. 
2679   -x                            Read the list of files to search from STDIN. 
2681 File inclusion/exclusion: 
2682   --[no]ignore-dir=name         Add/remove directory from list of ignored dirs 
2683   --[no]ignore-directory=name   Synonym for ignore-dir 
2684   --ignore-file=filter          Add filter for ignoring files 
2685   -r, -R, --recurse             Recurse into subdirectories (default: on) 
2686   -n, --no-recurse              No descending into subdirectories 
2687   --[no]follow                  Follow symlinks.  Default is off. 
2688   -k, --known-types             Include only files of types that ack recognizes. 
2690   --type=X                      Include only X files, where X is a recognized 
2692   --type=noX                    Exclude X files. 
2693                                 See "ack --help-types" for supported filetypes. 
2695 File type specification: 
2696   --type-set TYPE:FILTER:FILTERARGS 
2697                                 Files with the given FILTERARGS applied to the 
2698                                 given FILTER are recognized as being of type 
2699                                 TYPE. This replaces an existing definition for 
2701   --type-add TYPE:FILTER:FILTERARGS 
2702                                 Files with the given FILTERARGS applied to the 
2703                                 given FILTER are recognized as being type TYPE. 
2704   --type-del TYPE               Removes all filters associated with TYPE. 
2708   --[no]env                     Ignore environment variables and global ackrc 
2709                                 files.  --env is legal but redundant. 
2710   --ackrc=filename              Specify an ackrc file to use 
2711   --ignore-ack-defaults         Ignore default definitions included with ack. 
2712   --create-ackrc                Outputs a default ackrc for your customization 
2714   --help, -?                    This help 
2715   --help-types                  Display all known types 
2716   --dump                        Dump information on which options are loaded 
2718   --[no]filter                  Force ack to treat standard input as a pipe 
2719                                 (--filter) or tty (--nofilter) 
2721   --version                     Display version & copyright 
2722   --thpppt                      Bill the Cat 
2723   --bar                         The warning admiral 
2724   --cathy                       Chocolate! Chocolate! Chocolate! 
2726 Exit status is 0 if match, 1 if no match. 
2728 ack's home page is at http://beyondgrep.com/ 
2730 The full ack manual is available by running "ack --man". 
2732 This is version $VERSION of ack.  Run "ack --version" for full version info. 
2740 sub show_help_types 
{ 
2741     App
::Ack
::print( <<'END_OF_HELP' ); 
2742 Usage: ack [OPTION]... PATTERN [FILES OR DIRECTORIES] 
2744 The following is the list of filetypes supported by ack.  You can 
2745 specify a file type with the --type=TYPE format, or the --TYPE 
2746 format.  For example, both --type=perl and --perl work. 
2748 Note that some extensions may appear in multiple types.  For example, 
2749 .pod files are both Perl and Parrot. 
2753     my @types = filetypes_supported
(); 
2756         $maxlen = length if $maxlen < length; 
2758     for my $type ( sort @types ) { 
2759         next if $type =~ /^-/; # Stuff to not show 
2760         my $ext_list = $mappings{$type}; 
2762         if ( ref $ext_list ) { 
2763             $ext_list = join( '; ', map { $_->to_string } @{$ext_list} ); 
2765         App
::Ack
::print( sprintf( "    --[no]%-*.*s %s\n", $maxlen, $maxlen, $type, $ext_list ) ); 
2774     Pod
::Usage
::pod2usage
({ 
2775         -input   
=> $App::Ack
::orig_program_name
, 
2784 sub get_version_statement 
{ 
2787     my $copyright = get_copyright
(); 
2788     my $this_perl = $Config::Config
{perlpath
}; 
2790         my $ext = $Config::Config
{_exe
}; 
2791         $this_perl .= $ext unless $this_perl =~ m/$ext$/i; 
2793     my $ver = sprintf( '%vd', $^V ); 
2795     return <<"END_OF_VERSION"; 
2797 Running under Perl $ver at $this_perl 
2801 This program is free software.  You may modify or distribute it 
2802 under the terms of the Artistic License v2.0. 
2807 sub print_version_statement 
{ 
2808     App
::Ack
::print( get_version_statement
() ); 
2819 # print*() subs added in order to make it easy for a third party 
2820 # module (such as App::Wack) to redefine the display methods 
2821 # and show the results in a different way. 
2822 sub print                   { print {$fh} @_; return; } 
2823 sub print_first_filename    
{ App
::Ack
::print( $_[0], "\n" ); return; } 
2824 sub print_blank_line        
{ App
::Ack
::print( "\n" ); return; } 
2825 sub print_separator         
{ App
::Ack
::print( "--\n" ); return; } 
2826 sub print_filename          
{ App
::Ack
::print( $_[0], $_[1] ); return; } 
2827 sub print_line_no           
{ App
::Ack
::print( $_[0], $_[1] ); return; } 
2828 sub print_column_no         
{ App
::Ack
::print( $_[0], $_[1] ); return; } 
2830     my $filename = shift; 
2831     my $nmatches = shift; 
2834     my $show_filename = shift; 
2836     if ($show_filename) { 
2837         App
::Ack
::print( $filename ); 
2838         App
::Ack
::print( ':', $nmatches ) if $count; 
2841         App
::Ack
::print( $nmatches ) if $count; 
2843     App
::Ack
::print( $ors ); 
2849     my $filename = shift; 
2851     my $show_filename = shift; 
2853     if ($show_filename) { 
2854         App
::Ack
::print( $filename, ':0', $ors ); 
2857         App
::Ack
::print( '0', $ors ); 
2864     my $command = shift; 
2866     return if App
::Ack
::output_to_pipe
(); 
2869     if ( not open( $pager, '|-', $command ) ) { 
2870         App
::Ack
::die( qq{Unable to pipe to pager "$command": $!} ); 
2878 sub output_to_pipe 
{ 
2879     return $output_to_pipe; 
2884     my $nmatches = shift; 
2886     my $rc = $nmatches ? 0 : 1; 
2892 1; # End of App::Ack 
2893 package App
::Ack
::Resource
; 
2903     Carp
::confess
( 'Must be overloaded' ); 
2932 sub needs_line_scan 
{ 
2957 package App
::Ack
::Resources
; 
2964 sub _generate_error_handler 
{ 
2967     if ( $opt->{dont_report_bad_filenames
} ) { 
2970             # XXX restricting to specific error messages for now; I would 
2971             #     prefer a different way of doing this 
2972             if ( $msg =~ /Permission denied/ ) { 
2975             App
::Ack
::warn( $msg ); 
2981             App
::Ack
::warn( $msg ); 
2992     my $self = bless {}, $class; 
2994     my $file_filter    = undef; 
2995     my $descend_filter = $opt->{descend_filter
}; 
2998         $descend_filter = sub { 
3004         File
::Next
::files
( { 
3005             file_filter     
=> $opt->{file_filter
}, 
3006             descend_filter  
=> $descend_filter, 
3007             error_handler   
=> _generate_error_handler
($opt), 
3008             warning_handler 
=> sub {}, 
3009             sort_files      
=> $opt->{sort_files
}, 
3010             follow_symlinks 
=> $opt->{follow
}, 
3023         File
::Next
::from_file
( { 
3024             error_handler   
=> _generate_error_handler
($opt), 
3025             warning_handler 
=> _generate_error_handler
($opt), 
3026             sort_files      
=> $opt->{sort_files
}, 
3027         }, $file ) or return undef; 
3034 # This is for reading input lines from STDIN, not the list of files from STDIN 
3039     my $self  = bless {}, $class; 
3041     my $has_been_called = 0; 
3043     $self->{iter
} = sub { 
3044         if ( !$has_been_called ) { 
3045             $has_been_called = 1; 
3057     my $file = $self->{iter
}->() or return; 
3059     return App
::Ack
::Resource
::Basic-
>new( $file ); 
3063 package App
::Ack
::Resource
::Basic
; 
3073     our @ISA = 'App::Ack::Resource'; 
3080     my $filename = shift; 
3083         filename 
=> $filename, 
3088     if ( $self->{filename
} eq '-' ) { 
3089         $self->{fh
}     = *STDIN
; 
3090         $self->{opened
} = 1; 
3098     return $_[0]->{filename
}; 
3104     # XXX definedness? pre-populate the slot with an undef? 
3105     unless ( exists $self->{basename
} ) { 
3106         $self->{basename
} = (File
::Spec-
>splitpath($self->name))[2]; 
3109     return $self->{basename
}; 
3113 sub needs_line_scan 
{ 
3117     return 1 if $opt->{v
}; 
3119     my $size = -s 
$self->{fh
}; 
3123     elsif ( $size > 100_000 ) { 
3128     my $rc = sysread( $self->{fh
}, $buffer, $size ); 
3129     if ( !defined($rc) && $App::Ack
::report_bad_filenames 
) { 
3130         App
::Ack
::warn( "$self->{filename}: $!" ); 
3133     return 0 unless $rc && ( $rc == $size ); 
3135     my $regex = $opt->{regex
}; 
3136     return $buffer =~ /$regex/m; 
3143     # return if we haven't opened the file yet 
3144     if ( !defined($self->{fh
}) ) { 
3148     if( !seek( $self->{fh
}, 0, 0 ) && $App::Ack
::report_bad_filenames 
) { 
3149         App
::Ack
::warn( "$self->{filename}: $!" ); 
3159     # return if we haven't opened the file yet 
3160     if ( !defined($self->{fh
}) ) { 
3164     if ( !close($self->{fh
}) && $App::Ack
::report_bad_filenames 
) { 
3165         App
::Ack
::warn( $self->name() . ": $!" ); 
3168     $self->{opened
} = 0; 
3177     return __PACKAGE__-
>new($self->name); 
3183     my $fh = $self->open(); 
3185     if ( !exists $self->{firstliney
} ) { 
3187         my $rc     = sysread( $fh, $buffer, 250 ); 
3188         unless($rc) { # XXX handle this better? 
3191         $buffer =~ s/[\r\n].*//s; 
3192         $self->{firstliney
} = $buffer; 
3198     return $self->{firstliney
}; 
3204     return $self->{fh
} if $self->{opened
}; 
3206     if ( ! open $self->{fh
}, '<', $self->{filename
} ) { 
3210     $self->{opened
} = 1; 
3216 package App
::Ack
::ConfigDefault
; 
3224     return split( /\n/, _options_block
() ); 
3229     return grep { /./ && !/^#/ } options
(); 
3233 sub _options_block 
{ 
3234     my $lines = <<'HERE'; 
3235 # This is the default ackrc for ack version ==VERSION==. 
3237 # There are four different ways to match 
3239 # is:  Match the filename exactly 
3241 # ext: Match the extension of the filename exactly 
3243 # match: Match the filename against a Perl regular expression 
3245 # firstlinematch: Match the first 250 characters of the first line 
3246 #   of text against a Perl regular expression.  This is only for 
3247 #   the --type-add option. 
3250 ### Directories to ignore 
3253 # http://bazaar.canonical.com/ 
3254 --ignore-directory=is:.bzr 
3257 # http://freecode.com/projects/codeville 
3258 --ignore-directory=is:.cdv 
3260 # Interface Builder (Xcode) 
3261 # http://en.wikipedia.org/wiki/Interface_Builder 
3262 --ignore-directory=is:~.dep 
3263 --ignore-directory=is:~.dot 
3264 --ignore-directory=is:~.nib 
3265 --ignore-directory=is:~.plst 
3268 # http://git-scm.com/ 
3269 --ignore-directory=is:.git 
3272 # http://mercurial.selenic.com/ 
3273 --ignore-directory=is:.hg 
3276 # http://directory.fsf.org/wiki/Quilt 
3277 --ignore-directory=is:.pc 
3280 # http://subversion.tigris.org/ 
3281 --ignore-directory=is:.svn 
3284 # http://www.monotone.ca/ 
3285 --ignore-directory=is:_MTN 
3288 # http://savannah.nongnu.org/projects/cvs 
3289 --ignore-directory=is:CVS 
3292 # http://www.gnu.org/software/rcs/ 
3293 --ignore-directory=is:RCS 
3296 # http://en.wikipedia.org/wiki/Source_Code_Control_System 
3297 --ignore-directory=is:SCCS 
3301 --ignore-directory=is:_darcs 
3304 --ignore-directory=is:_sgbak 
3307 # http://www.gnu.org/software/autoconf/ 
3308 --ignore-directory=is:autom4te.cache 
3310 # Perl module building 
3311 --ignore-directory=is:blib 
3312 --ignore-directory=is:_build 
3314 # Perl Devel::Cover module's output directory 
3315 # https://metacpan.org/release/Devel-Cover 
3316 --ignore-directory=is:cover_db 
3318 # Node modules created by npm 
3319 --ignore-directory=is:node_modules 
3322 # http://www.cmake.org/ 
3323 --ignore-directory=is:CMakeFiles 
3325 # Eclipse workspace folder 
3326 # http://eclipse.org/ 
3327 --ignore-directory=is:.metadata 
3329 # Cabal (Haskell) sandboxes 
3330 # http://www.haskell.org/cabal/users-guide/installing-packages.html 
3331 --ignore-directory=is:.cabal-sandbox 
3336 --ignore-file=ext:bak 
3337 --ignore-file=match:/~$/ 
3340 --ignore-file=match:/^#.+#$/ 
3342 # vi/vim swap files http://vim.org/ 
3343 --ignore-file=match:/[._].*\.swp$/ 
3346 --ignore-file=match:/core\.\d+$/ 
3348 # minified Javascript 
3349 --ignore-file=match:/[.-]min[.]js$/ 
3350 --ignore-file=match:/[.]js[.]min$/ 
3353 --ignore-file=match:/[.]min[.]css$/ 
3354 --ignore-file=match:/[.]css[.]min$/ 
3356 # JS and CSS source maps 
3357 --ignore-file=match:/[.]js[.]map$/ 
3358 --ignore-file=match:/[.]css[.]map$/ 
3360 # PDFs, because they pass Perl's -T detection 
3361 --ignore-file=ext:pdf 
3363 # Common graphics, just as an optimization 
3364 --ignore-file=ext:gif,jpg,jpeg,png 
3367 ### Filetypes defined 
3371 --type-add=perl:ext:pl,pm,pod,t,psgi 
3372 --type-add=perl:firstlinematch:/^#!.*\bperl/ 
3375 --type-add=perltest:ext:t 
3378 # http://www.gnu.org/s/make/ 
3379 --type-add=make:ext:mk 
3380 --type-add=make:ext:mak 
3381 --type-add=make:is:makefile 
3382 --type-add=make:is:Makefile 
3383 --type-add=make:is:Makefile.Debug 
3384 --type-add=make:is:Makefile.Release 
3387 # http://rake.rubyforge.org/ 
3388 --type-add=rake:is:Rakefile 
3391 # http://www.cmake.org/ 
3392 --type-add=cmake:is:CMakeLists.txt 
3393 --type-add=cmake:ext:cmake 
3396 --type-add=actionscript:ext:as,mxml 
3399 # http://www.adaic.org/ 
3400 --type-add=ada:ext:ada,adb,ads 
3403 # http://msdn.microsoft.com/en-us/library/aa286483.aspx 
3404 --type-add=asp:ext:asp 
3407 # http://www.asp.net/ 
3408 --type-add=aspx:ext:master,ascx,asmx,aspx,svc 
3411 --type-add=asm:ext:asm,s 
3414 --type-add=batch:ext:bat,cmd 
3417 # http://en.wikipedia.org/wiki/ColdFusion 
3418 --type-add=cfmx:ext:cfc,cfm,cfml 
3421 # http://clojure.org/ 
3422 --type-add=clojure:ext:clj 
3425 # .xs are Perl C files 
3426 --type-add=cc:ext:c,h,xs 
3432 # http://coffeescript.org/ 
3433 --type-add=coffeescript:ext:coffee 
3436 --type-add=cpp:ext:cpp,cc,cxx,m,hpp,hh,h,hxx 
3439 --type-add=hpp:ext:hpp,hh,h,hxx 
3442 --type-add=csharp:ext:cs 
3445 # http://www.w3.org/Style/CSS/ 
3446 --type-add=css:ext:css 
3449 # http://www.dartlang.org/ 
3450 --type-add=dart:ext:dart 
3453 # http://en.wikipedia.org/wiki/Embarcadero_Delphi 
3454 --type-add=delphi:ext:pas,int,dfm,nfm,dof,dpk,dproj,groupproj,bdsgroup,bdsproj 
3457 # http://elixir-lang.org/ 
3458 --type-add=elixir:ext:ex,exs 
3461 # http://www.gnu.org/software/emacs 
3462 --type-add=elisp:ext:el 
3465 # http://www.erlang.org/ 
3466 --type-add=erlang:ext:erl,hrl 
3469 # http://en.wikipedia.org/wiki/Fortran 
3470 --type-add=fortran:ext:f,f77,f90,f95,f03,for,ftn,fpp 
3473 # http://golang.org/ 
3474 --type-add=go:ext:go 
3477 # http://groovy.codehaus.org/ 
3478 --type-add=groovy:ext:groovy,gtmpl,gpp,grunit,gradle 
3481 # http://www.haskell.org/ 
3482 --type-add=haskell:ext:hs,lhs 
3485 --type-add=html:ext:htm,html 
3488 # http://jade-lang.com/ 
3489 --type-add=jade:ext:jade 
3492 # http://www.oracle.com/technetwork/java/index.html 
3493 --type-add=java:ext:java,properties 
3496 --type-add=js:ext:js 
3499 # http://www.oracle.com/technetwork/java/javaee/jsp/index.html 
3500 --type-add=jsp:ext:jsp,jspx,jhtm,jhtml 
3503 # http://www.json.org/ 
3504 --type-add=json:ext:json 
3507 # http://www.lesscss.org/ 
3508 --type-add=less:ext:less 
3511 # http://common-lisp.net/ 
3512 --type-add=lisp:ext:lisp,lsp 
3515 # http://www.lua.org/ 
3516 --type-add=lua:ext:lua 
3517 --type-add=lua:firstlinematch:/^#!.*\blua(jit)?/ 
3520 --type-add=objc:ext:m,h 
3523 --type-add=objcpp:ext:mm,h 
3526 # http://caml.inria.fr/ 
3527 --type-add=ocaml:ext:ml,mli 
3530 # http://en.wikipedia.org/wiki/MATLAB 
3531 --type-add=matlab:ext:m 
3534 # http://www.parrot.org/ 
3535 --type-add=parrot:ext:pir,pasm,pmc,ops,pod,pg,tg 
3538 # http://www.php.net/ 
3539 --type-add=php:ext:php,phpt,php3,php4,php5,phtml 
3540 --type-add=php:firstlinematch:/^#!.*\bphp/ 
3544 --type-add=plone:ext:pt,cpt,metadata,cpy,py 
3547 # http://www.python.org/ 
3548 --type-add=python:ext:py 
3549 --type-add=python:firstlinematch:/^#!.*\bpython/ 
3552 # http://www.r-project.org/ 
3556 # http://docutils.sourceforge.net/rst.html 
3557 --type-add=rst:ext:rst 
3560 # http://www.ruby-lang.org/ 
3561 --type-add=ruby:ext:rb,rhtml,rjs,rxml,erb,rake,spec 
3562 --type-add=ruby:is:Rakefile 
3563 --type-add=ruby:firstlinematch:/^#!.*\bruby/ 
3566 # http://www.rust-lang.org/ 
3567 --type-add=rust:ext:rs 
3570 # http://sass-lang.com 
3571 --type-add=sass:ext:sass,scss 
3574 # http://www.scala-lang.org/ 
3575 --type-add=scala:ext:scala 
3578 # http://groups.csail.mit.edu/mac/projects/scheme/ 
3579 --type-add=scheme:ext:scm,ss 
3582 --type-add=shell:ext:sh,bash,csh,tcsh,ksh,zsh,fish 
3583 --type-add=shell:firstlinematch:/^#!.*\b(?:ba|t?c|k|z|fi)?sh\b/ 
3586 # http://www.smalltalk.org/ 
3587 --type-add=smalltalk:ext:st 
3590 # http://www.smarty.net/ 
3591 --type-add=smarty:ext:tpl 
3594 # http://www.iso.org/iso/catalogue_detail.htm?csnumber=45498 
3595 --type-add=sql:ext:sql,ctl 
3598 # http://learnboost.github.io/stylus/ 
3599 --type-add=stylus:ext:styl 
3602 # http://www.tcl.tk/ 
3603 --type-add=tcl:ext:tcl,itcl,itk 
3606 # http://www.latex-project.org/ 
3607 --type-add=tex:ext:tex,cls,sty 
3609 # Template Toolkit (Perl) 
3610 # http://template-toolkit.org/ 
3611 --type-add=tt:ext:tt,tt2,ttml 
3614 --type-add=vb:ext:bas,cls,frm,ctl,vb,resx 
3617 --type-add=verilog:ext:v,vh,sv 
3620 # http://www.eda.org/twiki/bin/view.cgi/P1076/WebHome 
3621 --type-add=vhdl:ext:vhd,vhdl 
3624 # http://www.vim.org/ 
3625 --type-add=vim:ext:vim 
3628 # http://www.w3.org/TR/REC-xml/ 
3629 --type-add=xml:ext:xml,dtd,xsl,xslt,ent 
3630 --type-add=xml:firstlinematch:/<[?]xml/ 
3634 --type-add=yaml:ext:yaml,yml 
3636     $lines =~ s/==VERSION==/$App::Ack::VERSION/sm; 
3642 package App
::Ack
::ConfigFinder
; 
3649 use File
::Spec 
3.00; 
3651 use if ($^O eq 'MSWin32'), 'Win32'; 
3657     return bless {}, $class; 
3661 sub _remove_redundancies 
{ 
3665     foreach my $config (@configs) { 
3666         my $key = $config->{path
}; 
3667         if ( not $App::Ack
::is_windows 
) { 
3668             # On Unix, uniquify on inode. 
3669             my ($dev, $inode) = (stat $key)[0, 1]; 
3670             $key = "$dev:$inode" if defined $dev; 
3672         undef $config if $seen{$key}++; 
3674     return grep { defined } @configs; 
3678 sub _check_for_ackrc 
{ 
3679     return unless defined $_[0]; 
3681     my @files = grep { -f 
} 
3682                 map { File
::Spec-
>catfile(@_, $_) } 
3685     die File
::Spec-
>catdir(@_) . " contains both .ackrc and _ackrc.\n" . 
3686         "Please remove one of those files.\n" 
3689     return wantarray ? @files : $files[0]; 
3690 } # end _check_for_ackrc 
3694 sub find_config_files 
{ 
3697     if ( $App::Ack
::is_windows 
) { 
3698         push @config_files, map { +{ path 
=> File
::Spec-
>catfile($_, 'ackrc') } } ( 
3699             Win32
::GetFolderPath
(Win32
::CSIDL_COMMON_APPDATA
()), 
3700             Win32
::GetFolderPath
(Win32
::CSIDL_APPDATA
()), 
3704         push @config_files, { path 
=> '/etc/ackrc' }; 
3708     if ( $ENV{'ACKRC'} && -f 
$ENV{'ACKRC'} ) { 
3709         push @config_files, { path 
=> $ENV{'ACKRC'} }; 
3712         push @config_files, map { +{ path 
=> $_ } } _check_for_ackrc
($ENV{'HOME'}); 
3715     # XXX This should go through some untainted cwd-fetching function, and not get untainted inline like this. 
3716     my $cwd = Cwd
::getcwd
(); 
3719     my @dirs = File
::Spec-
>splitdir( $cwd ); 
3721         my $ackrc = _check_for_ackrc
(@dirs); 
3722         if(defined $ackrc) { 
3723             push @config_files, { project 
=> 1, path 
=> $ackrc }; 
3729     # We only test for existence here, so if the file is deleted out from under us, this will fail later. 
3730     return _remove_redundancies
( @config_files ); 
3738     return unless defined $file && -e 
$file; 
3742     open( my $fh, '<', $file ) or App
::Ack
::die( "Unable to read $file: $!" ); 
3743     while ( my $line = <$fh> ) { 
3748         next if $line eq ''; 
3749         next if $line =~ /^\s*#/; 
3751         push( @lines, $line ); 
3753     close $fh or App
::Ack
::die( "Unable to close $file: $!" ); 
3759 package App
::Ack
::ConfigLoader
; 
3765 use Getopt
::Long 
2.35 (); 
3766 use Text
::ParseWords 
3.1 (); 
3769 my @INVALID_COMBINATIONS; 
3772     my @context  = qw( -A -B -C --after-context --before-context --context ); 
3773     my @pretty   = qw( --heading --group --break ); 
3774     my @filename = qw( -h -H --with-filename --no-filename ); 
3776     @INVALID_COMBINATIONS = ( 
3778         [qw(-l)]                 => [@context, @pretty, @filename, qw(-L -o --passthru --output --max-count --column -f -g --show-types)], 
3779         [qw(-L)]                 => [@context, @pretty, @filename, qw(-l -o --passthru --output --max-count --column -f -g --show-types -c --count)], 
3780         [qw(--line)]             => [@context, @pretty, @filename, qw(-l --files-with-matches --files-without-matches -L -o --passthru --match -m --max-count -1 -c --count --column --print0 -f -g --show-types)], 
3781         [qw(-o)]                 => [@context, qw(--output -c --count --column --column -f --show-types)], 
3782         [qw(--passthru)]         => [@context, qw(--output --column -m --max-count -1 -c --count -f -g)], 
3783         [qw(--output)]           => [@context, qw(-c --count -f -g)], 
3784         [qw(--match)]            => [qw(-f -g)], 
3785         [qw(-m --max-count)]     => [qw(-1 -f -g -c --count)], 
3786         [qw(-h --no-filename)]   => [qw(-H --with-filename -f -g --group --heading)], 
3787         [qw(-H --with-filename)] => [qw(-h --no-filename -f -g)], 
3788         [qw(-c --count)]         => [@context, @pretty, qw(--column -f -g)], 
3789         [qw(--column)]           => [qw(-f -g)], 
3790         [@context]               => [qw(-f -g)], 
3791         [qw(-f)]                 => [qw(-g), @pretty], 
3792         [qw(-g)]                 => [qw(-f), @pretty], 
3796 sub _generate_ignore_dir 
{ 
3797     my ( $option_name, $opt ) = @_; 
3799     my $is_inverted = $option_name =~ /^--no/; 
3802         my ( undef, $dir ) = @_; 
3804         $dir = App
::Ack
::remove_dir_sep
( $dir ); 
3805         if ( $dir !~ /:/ ) { 
3806             $dir = 'is:' . $dir; 
3809         my ( $filter_type, $args ) = split /:/, $dir, 2; 
3811         if ( $filter_type eq 'firstlinematch' ) { 
3812             Carp
::croak
( qq{Invalid filter specification "$filter_type" for option '$option_name'} ); 
3815         my $filter = App
::Ack
::Filter-
>create_filter($filter_type, split(/,/, $args)); 
3818         my $previous_inversion_matches = $opt->{idirs
} && !($is_inverted xor $opt->{idirs
}[-1]->is_inverted()); 
3820         if ( $previous_inversion_matches ) { 
3821             $collection = $opt->{idirs
}[-1]; 
3823             if ( $is_inverted ) { 
3824                 # XXX this relies on invert of an inverted filter 
3825                 #     to return the original 
3826                 $collection = $collection->invert() 
3830             $collection = App
::Ack
::Filter
::Collection-
>new(); 
3832             if ( $is_inverted ) { 
3833                 push @{ $opt->{idirs
} }, $collection->invert(); 
3836                 push @{ $opt->{idirs
} }, $collection; 
3840         $collection->add($filter); 
3842         if ( $filter_type eq 'is' ) { 
3843             $collection->add(App
::Ack
::Filter
::IsPath-
>new($args)); 
3848 sub process_filter_spec 
{ 
3851     if ( $spec =~ /^(\w+):(\w+):(.*)/ ) { 
3852         my ( $type_name, $ext_type, $arguments ) = ( $1, $2, $3 ); 
3854         return ( $type_name, 
3855             App
::Ack
::Filter-
>create_filter($ext_type, split(/,/, $arguments)) ); 
3857     elsif ( $spec =~ /^(\w+)=(.*)/ ) { # Check to see if we have ack1-style argument specification. 
3858         my ( $type_name, $extensions ) = ( $1, $2 ); 
3860         my @extensions = split(/,/, $extensions); 
3861         foreach my $extension ( @extensions ) { 
3862             $extension =~ s/^[.]//; 
3865         return ( $type_name, App
::Ack
::Filter-
>create_filter('ext', @extensions) ); 
3868         Carp
::croak 
"invalid filter specification '$spec'"; 
3873 sub uninvert_filter 
{ 
3874     my ( $opt, @filters ) = @_; 
3876     return unless defined $opt->{filters
} && @filters; 
3878     # Loop through all the registered filters.  If we hit one that 
3879     # matches this extension and it's inverted, we need to delete it from 
3881     for ( my $i = 0; $i < @{ $opt->{filters
} }; $i++ ) { 
3882         my $opt_filter = @{ $opt->{filters
} }[$i]; 
3884         # XXX Do a real list comparison? This just checks string equivalence. 
3885         if ( $opt_filter->is_inverted() && "$opt_filter->{filter}" eq "@filters" ) { 
3886             splice @{ $opt->{filters
} }, $i, 1; 
3893 sub process_filetypes 
{ 
3894     my ( $opt, $arg_sources ) = @_; 
3896     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); # start with default options, minus some annoying ones 
3897     Getopt
::Long
::Configure
( 
3902     my %additional_specs; 
3904     my $add_spec = sub { 
3905         my ( undef, $spec ) = @_; 
3907         my ( $name, $filter ) = process_filter_spec
($spec); 
3909         push @{ $App::Ack
::mappings
{$name} }, $filter; 
3911         $additional_specs{$name . '!'} = sub { 
3912             my ( undef, $value ) = @_; 
3914             my @filters = @{ $App::Ack
::mappings
{$name} }; 
3916                 @filters = map { $_->invert() } @filters; 
3919                 uninvert_filter
( $opt, @filters ); 
3922             push @{ $opt->{'filters'} }, @filters; 
3926     my $set_spec = sub { 
3927         my ( undef, $spec ) = @_; 
3929         my ( $name, $filter ) = process_filter_spec
($spec); 
3931         $App::Ack
::mappings
{$name} = [ $filter ]; 
3933         $additional_specs{$name . '!'} = sub { 
3934             my ( undef, $value ) = @_; 
3936             my @filters = @{ $App::Ack
::mappings
{$name} }; 
3938                 @filters = map { $_->invert() } @filters; 
3941             push @{ $opt->{'filters'} }, @filters; 
3945     my $delete_spec = sub { 
3946         my ( undef, $name ) = @_; 
3948         delete $App::Ack
::mappings
{$name}; 
3949         delete $additional_specs{$name . '!'}; 
3952     my %type_arg_specs = ( 
3953         'type-add=s' => $add_spec, 
3954         'type-set=s' => $set_spec, 
3955         'type-del=s' => $delete_spec, 
3958     foreach my $source (@{$arg_sources}) { 
3959         my ( $source_name, $args ) = @{$source}{qw
/name contents/}; 
3962             # $args are modified in place, so no need to munge $arg_sources 
3963             local @ARGV = @{$args}; 
3964             Getopt
::Long
::GetOptions
(%type_arg_specs); 
3968             ( undef, $source->{contents
} ) = 
3969                 Getopt
::Long
::GetOptionsFromString
($args, %type_arg_specs); 
3973     $additional_specs{'k|known-types'} = sub { 
3974         my ( undef, $value ) = @_; 
3976         my @filters = map { @{$_} } values(%App::Ack
::mappings
); 
3978         push @{ $opt->{'filters'} }, @filters; 
3981     return \
%additional_specs; 
3985 sub removed_option 
{ 
3986     my ( $option, $explanation ) = @_; 
3988     $explanation ||= ''; 
3990         warn "Option '$option' is not valid in ack 2\n$explanation"; 
3997     my ( $opt, $extra_specs ) = @_; 
3999     my $dash_a_explanation = <<'EOT'; 
4000 This is because we now have -k/--known-types which makes it only select files 
4001 of known types, rather than any text file (which is the behavior of ack 1.x). 
4002 You may have options in a .ackrc, or in the ACKRC_OPTIONS environment variable. 
4003 Try using the --dump flag. 
4008         1                   => sub { $opt->{1} = $opt->{m
} = 1 }, 
4009         'A|after-context=i' => \
$opt->{after_context
}, 
4010         'B|before-context=i' 
4011                             => \
$opt->{before_context
}, 
4012         'C|context:i'       => sub { shift; my $val = shift; $opt->{before_context
} = $opt->{after_context
} = ($val || 2) }, 
4013         'a'                 => removed_option
('-a', $dash_a_explanation), 
4014         'all'               => removed_option
('--all', $dash_a_explanation), 
4015         'break!'            => \
$opt->{break}, 
4016         c                   
=> \
$opt->{count
}, 
4017         'color|colour!'     => \
$opt->{color
}, 
4018         'color-match=s'     => \
$ENV{ACK_COLOR_MATCH
}, 
4019         'color-filename=s'  => \
$ENV{ACK_COLOR_FILENAME
}, 
4020         'color-lineno=s'    => \
$ENV{ACK_COLOR_LINENO
}, 
4021         'column!'           => \
$opt->{column
}, 
4022         count               
=> \
$opt->{count
}, 
4023         'create-ackrc'      => sub { print "$_\n" for ( '--ignore-ack-defaults', App
::Ack
::ConfigDefault
::options
() ); exit; }, 
4025             my ( undef, $value ) = @_; 
4028                 $opt->{noenv_seen
} = 1; 
4032         'files-from=s'      => \
$opt->{files_from
}, 
4033         'filter!'           => \
$App::Ack
::is_filter_mode
, 
4034         flush               
=> \
$opt->{flush
}, 
4035         'follow!'           => \
$opt->{follow
}, 
4037         G                   
=> removed_option
('-G'), 
4038         'group!'            => sub { shift; $opt->{heading
} = $opt->{break} = shift }, 
4039         'heading!'          => \
$opt->{heading
}, 
4040         'h|no-filename'     => \
$opt->{h
}, 
4041         'H|with-filename'   => \
$opt->{H
}, 
4042         'i|ignore-case'     => \
$opt->{i
}, 
4043         'ignore-directory|ignore-dir=s' => _generate_ignore_dir
('--ignore-dir', $opt), 
4044         'ignore-file=s'     => sub { 
4045                                     my ( undef, $file ) = @_; 
4047                                     my ( $filter_type, $args ) = split /:/, $file, 2; 
4049                                     my $filter = App
::Ack
::Filter-
>create_filter($filter_type, split(/,/, $args)); 
4051                                     if ( !$opt->{ifiles
} ) { 
4052                                         $opt->{ifiles
} = App
::Ack
::Filter
::Collection-
>new(); 
4054                                     $opt->{ifiles
}->add($filter); 
4056         'lines=s'           => sub { shift; my $val = shift; push @{$opt->{lines
}}, $val }, 
4057         'l|files-with-matches' 
4059         'L|files-without-matches' 
4061         'm|max-count=i'     => \
$opt->{m
}, 
4062         'match=s'           => \
$opt->{regex
}, 
4063         'n|no-recurse'      => \
$opt->{n
}, 
4064         o                   
=> sub { $opt->{output
} = '$&' }, 
4065         'output=s'          => \
$opt->{output
}, 
4067             my ( undef, $value ) = @_; 
4069             $opt->{pager
} = $value || $ENV{PAGER
}; 
4071         'noignore-directory|noignore-dir=s' => _generate_ignore_dir
('--noignore-dir', $opt), 
4072         'nopager'           => sub { $opt->{pager
} = undef }, 
4073         'passthru'          => \
$opt->{passthru
}, 
4074         'print0'            => \
$opt->{print0
}, 
4075         'Q|literal'         => \
$opt->{Q
}, 
4076         'r|R|recurse'       => sub { $opt->{n
} = 0 }, 
4077         's'                 => \
$opt->{dont_report_bad_filenames
}, 
4078         'show-types'        => \
$opt->{show_types
}, 
4079         'smart-case!'       => \
$opt->{smart_case
}, 
4080         'sort-files'        => \
$opt->{sort_files
}, 
4082             my ( $getopt, $value ) = @_; 
4085             if ( $value =~ s/^no// ) { 
4089             my $callback = $extra_specs->{ $value . '!' }; 
4092                 $callback->( $getopt, $cb_value ); 
4095                 Carp
::croak
( "Unknown type '$value'" ); 
4098         'u'                 => removed_option
('-u'), 
4099         'unrestricted'      => removed_option
('--unrestricted'), 
4100         'v|invert-match'    => \
$opt->{v
}, 
4101         'w|word-regexp'     => \
$opt->{w
}, 
4102         'x'                 => sub { $opt->{files_from
} = '-' }, 
4104         'version'           => sub { App
::Ack
::print_version_statement
(); exit; }, 
4105         'help|?:s'          => sub { shift; App
::Ack
::show_help
(@_); exit; }, 
4106         'help-types'        => sub { App
::Ack
::show_help_types
(); exit; }, 
4107         'man'               => sub { App
::Ack
::show_man
(); exit; }, 
4108         $extra_specs ? %{$extra_specs} : (), 
4114     my ( $opt, $extra_specs, $arg_sources ) = @_; 
4116     # Start with default options, minus some annoying ones. 
4117     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); 
4118     Getopt
::Long
::Configure
( 
4124     my $is_help_types_active; 
4126     foreach my $source (@{$arg_sources}) { 
4127         my ( $source_name, $args ) = @{$source}{qw
/name contents/}; 
4129         if ( $source_name eq 'ARGV' ) { 
4130             $argv_source = $args; 
4135     if ( $argv_source ) { # This *should* always be true, but you never know... 
4136         my @copy = @{$argv_source}; 
4137         local @ARGV = @copy; 
4139         Getopt
::Long
::Configure
('pass_through'); 
4141         Getopt
::Long
::GetOptions
( 
4142             'help-types' => \
$is_help_types_active, 
4145         Getopt
::Long
::Configure
('no_pass_through'); 
4148     my $arg_specs = get_arg_spec
($opt, $extra_specs); 
4150     foreach my $source (@{$arg_sources}) { 
4151         my ( $source_name, $args ) = @{$source}{qw
/name contents/}; 
4153         my $args_for_source = $arg_specs; 
4155         if ( $source->{project
} ) { 
4157                 die "Options --output, --pager and --match are forbidden in project .ackrc files.\n"; 
4160             $args_for_source = { %$args_for_source, 
4161                 'output=s' => $illegal, 
4162                 'pager:s'  => $illegal, 
4163                 'match=s'  => $illegal, 
4169             local @ARGV = @{$args}; 
4170             $ret = Getopt
::Long
::GetOptions
( %{$args_for_source} ); 
4174             ( $ret, $source->{contents
} ) = 
4175                 Getopt
::Long
::GetOptionsFromString
( $args, %{$args_for_source} ); 
4178             if ( !$is_help_types_active ) { 
4179                 my $where = $source_name eq 'ARGV' ? 'on command line' : "in $source_name"; 
4180                 App
::Ack
::die( "Invalid option $where" ); 
4183         if ( $opt->{noenv_seen
} ) { 
4184             App
::Ack
::die( "--noenv found in $source_name" ); 
4188     # XXX We need to check on a -- in the middle of a non-ARGV source 
4194 sub should_dump_options 
{ 
4195     my ( $sources ) = @_; 
4197     foreach my $source (@{$sources}) { 
4198         my ( $name, $options ) = @{$source}{qw
/name contents/}; 
4200         if($name eq 'ARGV') { 
4202             local @ARGV = @{$options}; 
4203             Getopt
::Long
::Configure
('default', 'pass_through', 'no_auto_help', 'no_auto_version'); 
4204             Getopt
::Long
::GetOptions
( 
4207             @{$options} = @ARGV; 
4215 sub explode_sources 
{ 
4216     my ( $sources ) = @_; 
4220     Getopt
::Long
::Configure
('default', 'pass_through', 'no_auto_help', 'no_auto_version'); 
4223     my $arg_spec = get_arg_spec
(\
%opt); 
4225     my $add_type = sub { 
4226         my ( undef, $arg ) = @_; 
4229         if ( $arg =~ /(\w+)=/) { 
4230             $arg_spec->{$1} = sub {}; 
4233             ( $arg ) = split /:/, $arg; 
4234             $arg_spec->{$arg} = sub {}; 
4238     my $del_type = sub { 
4239         my ( undef, $arg ) = @_; 
4241         delete $arg_spec->{$arg}; 
4244     foreach my $source (@{$sources}) { 
4245         my ( $name, $options ) = @{$source}{qw
/name contents/}; 
4246         if ( ref($options) ne 'ARRAY' ) { 
4247             $source->{contents
} = $options = 
4248                 [ Text
::ParseWords
::shellwords
($options) ]; 
4251         for my $j ( 0 .. @{$options}-1 ) { 
4252             next unless $options->[$j] =~ /^-/; 
4253             my @chunk = ( $options->[$j] ); 
4254             push @chunk, $options->[$j] while ++$j < @{$options} && $options->[$j] !~ /^-/; 
4258             local @ARGV = @chunk; 
4259             Getopt
::Long
::GetOptions
( 
4260                 'type-add=s' => $add_type, 
4261                 'type-set=s' => $add_type, 
4262                 'type-del=s' => $del_type, 
4264             Getopt
::Long
::GetOptions
( %{$arg_spec} ); 
4266             push @new_sources, { 
4273     return \
@new_sources; 
4280     my $first_a = $a->[0]; 
4281     my $first_b = $b->[0]; 
4283     $first_a =~ s/^--?//; 
4284     $first_b =~ s/^--?//; 
4286     return $first_a cmp $first_b; 
4291     my ( $sources ) = @_; 
4293     $sources = explode_sources
($sources); 
4298     foreach my $source (@{$sources}) { 
4299         my ( $name, $contents ) = @{$source}{qw
/name contents/}; 
4300         if ( not $opts_by_source{$name} ) { 
4301             $opts_by_source{$name} = []; 
4302             push @source_names, $name; 
4304         push @{$opts_by_source{$name}}, $contents; 
4307     foreach my $name (@source_names) { 
4308         my $contents = $opts_by_source{$name}; 
4311         print '=' x 
length($name), "\n"; 
4312         print '  ', join(' ', @{$_}), "\n" foreach sort { compare_opts
($a, $b) } @{$contents}; 
4319 sub remove_default_options_if_needed 
{ 
4320     my ( $sources ) = @_; 
4324     foreach my $index ( 0 .. $#{$sources} ) { 
4325         if ( $sources->[$index]{'name'} eq 'Defaults' ) { 
4326             $default_index = $index; 
4331     return $sources unless defined $default_index; 
4333     my $should_remove = 0; 
4335     # Start with default options, minus some annoying ones. 
4336     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); 
4337     Getopt
::Long
::Configure
( 
4343     foreach my $index ( $default_index + 1 .. $#{$sources} ) { 
4344         my ( $name, $args ) = @{$sources->[$index]}{qw
/name contents/}; 
4347             local @ARGV = @{$args}; 
4348             Getopt
::Long
::GetOptions
( 
4349                 'ignore-ack-defaults' => \
$should_remove, 
4354             ( undef, $sources->[$index]{contents
} ) = Getopt
::Long
::GetOptionsFromString
($args, 
4355                 'ignore-ack-defaults' => \
$should_remove, 
4360     Getopt
::Long
::Configure
('default'); 
4361     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); 
4363     return $sources unless $should_remove; 
4365     my @copy = @{$sources}; 
4366     splice @copy, $default_index, 1; 
4371 sub check_for_mutually_exclusive_options 
{ 
4372     my ( $arg_sources ) = @_; 
4374     my %mutually_exclusive_with; 
4375     my @copy = @{$arg_sources}; 
4377     for(my $i = 0; $i < @INVALID_COMBINATIONS; $i += 2) { 
4378         my ( $lhs, $rhs ) = @INVALID_COMBINATIONS[ $i, $i + 1 ]; 
4380         foreach my $l_opt ( @{$lhs} ) { 
4381             foreach my $r_opt ( @{$rhs} ) { 
4382                 push @{ $mutually_exclusive_with{ $l_opt } }, $r_opt; 
4383                 push @{ $mutually_exclusive_with{ $r_opt } }, $l_opt; 
4391         my $source = shift @copy; 
4392         my ( $source_name, $args ) = @{$source}{qw
/name contents/}; 
4393         $args = ref($args) ? [ @{$args} ] : [ Text
::ParseWords
::shellwords
($args) ]; 
4395         foreach my $opt ( @{$args} ) { 
4396             next unless $opt =~ /^[-+]/; 
4397             last if $opt eq '--'; 
4399             if( $opt =~ /^(.*)=/ ) { 
4402             elsif ( $opt =~ /^(-[^-]).+/ ) { 
4406             $set_opts{ $opt } = 1; 
4408             my $mutex_opts = $mutually_exclusive_with{ $opt }; 
4410             next unless $mutex_opts; 
4412             foreach my $mutex_opt ( @{$mutex_opts} ) { 
4413                 if($set_opts{ $mutex_opt }) { 
4414                     die "Options '$mutex_opt' and '$opt' are mutually exclusive\n"; 
4423     my $arg_sources = \
@_; 
4426         pager 
=> $ENV{ACK_PAGER_COLOR
} || $ENV{ACK_PAGER
}, 
4429     check_for_mutually_exclusive_options
($arg_sources); 
4431     $arg_sources = remove_default_options_if_needed
($arg_sources); 
4433     if ( should_dump_options
($arg_sources) ) { 
4434         dump_options
($arg_sources); 
4438     my $type_specs = process_filetypes
(\
%opt, $arg_sources); 
4439     process_other
(\
%opt, $type_specs, $arg_sources); 
4440     while ( @{$arg_sources} ) { 
4441         my $source = shift @{$arg_sources}; 
4442         my ( $source_name, $args ) = @{$source}{qw
/name contents/}; 
4444         # All of our sources should be transformed into an array ref 
4446             if ( $source_name eq 'ARGV' ) { 
4450                 Carp
::croak 
"source '$source_name' has extra arguments!"; 
4454             Carp
::croak 
'The impossible has occurred!'; 
4457     my $filters = ($opt{filters
} ||= []); 
4459     # Throw the default filter in if no others are selected. 
4460     if ( not grep { !$_->is_inverted() } @{$filters} ) { 
4461         push @{$filters}, App
::Ack
::Filter
::Default-
>new(); 
4467 sub retrieve_arg_sources 
{ 
4473     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); 
4474     Getopt
::Long
::Configure
('pass_through'); 
4475     Getopt
::Long
::Configure
('no_auto_abbrev'); 
4477     Getopt
::Long
::GetOptions
( 
4479         'ackrc=s' => \
$ackrc, 
4482     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); 
4487         my $finder = App
::Ack
::ConfigFinder-
>new; 
4488         @files  = $finder->find_config_files; 
4491         # We explicitly use open so we get a nice error message. 
4492         # XXX This is a potential race condition!. 
4493         if(open my $fh, '<', $ackrc) { 
4497             die "Unable to load ackrc '$ackrc': $!" 
4499         push( @files, { path 
=> $ackrc } ); 
4502     push @arg_sources, { 
4504         contents 
=> [ App
::Ack
::ConfigDefault
::options_clean
() ], 
4507     foreach my $file ( @files) { 
4508         my @lines = App
::Ack
::ConfigFinder
::read_rcfile
($file->{path
}); 
4511             push @arg_sources, { 
4512                 name     
=> $file->{path
}, 
4513                 contents 
=> \
@lines, 
4514                 project  
=> $file->{project
}, 
4519     if ( $ENV{ACK_OPTIONS
} && !$noenv ) { 
4520         push @arg_sources, { 
4521             name     
=> 'ACK_OPTIONS', 
4522             contents 
=> $ENV{ACK_OPTIONS
}, 
4526     push @arg_sources, { 
4528         contents 
=> [ @ARGV ], 
4531     return @arg_sources; 
4534 1; # End of App::Ack::ConfigLoader 
4535 package App
::Ack
::Filter
; 
4546     my ( undef, $type, @args ) = @_; 
4548     if ( my $package = $filter_types{$type} ) { 
4549         return $package->new(@args); 
4551     Carp
::croak 
"Unknown filter type '$type'"; 
4555 sub register_filter 
{ 
4556     my ( undef, $type, $package ) = @_; 
4558     $filter_types{$type} = $package; 
4567     return App
::Ack
::Filter
::Inverse-
>new( $self ); 
4579     return '(unimplemented to_string)'; 
4590 package App
::Ack
::Filter
::Extension
; 
4595     our @ISA = 'App::Ack::Filter'; 
4600     my ( $class, @extensions ) = @_; 
4602     my $exts = join('|', map { "\Q$_\E"} @extensions); 
4603     my $re   = qr/[.](?:$exts)$/i; 
4606         extensions 
=> \
@extensions, 
4608         groupname  
=> 'ExtensionGroup', 
4613     return App
::Ack
::Filter
::ExtensionGroup-
>new(); 
4617     my ( $self, $resource ) = @_; 
4619     my $re = $self->{'regex'}; 
4621     return $resource->name =~ /$re/; 
4627     my $re = $self->{'regex'}; 
4629     return ref($self) . " - $re"; 
4635     my $exts = $self->{'extensions'}; 
4637     return join(' ', map { ".$_" } @{$exts}); 
4641     App
::Ack
::Filter-
>register_filter(ext 
=> __PACKAGE__
); 
4645 package App
::Ack
::Filter
::FirstLineMatch
; 
4650     our @ISA = 'App::Ack::Filter'; 
4654     my ( $class, $re ) = @_; 
4656     $re =~ s{^/|/$}{}g; # XXX validate? 
4664 # This test reads the first 250 characters of a file, then just uses the 
4665 # first line found in that. This prevents reading something  like an entire 
4666 # .min.js file (which might be only one "line" long) into memory. 
4669     my ( $self, $resource ) = @_; 
4671     my $re = $self->{'regex'}; 
4673     my $line = $resource->firstliney; 
4675     return $line =~ /$re/; 
4681     my $re = $self->{'regex'}; 
4683     return ref($self) . " - $re"; 
4689     (my $re = $self->{regex
}) =~ s{\([^:]*:(.*)\)$}{$1}; 
4691     return "first line matches /$re/"; 
4695     App
::Ack
::Filter-
>register_filter(firstlinematch 
=> __PACKAGE__
); 
4699 package App
::Ack
::Filter
::Is
; 
4704     our @ISA = 'App::Ack::Filter'; 
4707 use File
::Spec 
3.00 (); 
4710     my ( $class, $filename ) = @_; 
4713         filename 
=> $filename, 
4714         groupname 
=> 'IsGroup', 
4719     return App
::Ack
::Filter
::IsGroup-
>new(); 
4723     my ( $self, $resource ) = @_; 
4725     my $filename = $self->{'filename'}; 
4726     my $base     = (File
::Spec-
>splitpath($resource->name))[2]; 
4728     return $base eq $filename; 
4734     my $filename = $self->{'filename'}; 
4736     return ref($self) . " - $filename"; 
4742     my $filename = $self->{'filename'}; 
4748     App
::Ack
::Filter-
>register_filter(is => __PACKAGE__
); 
4752 package App
::Ack
::Filter
::Match
; 
4757     our @ISA = 'App::Ack::Filter'; 
4760 use File
::Spec 
3.00; 
4763     my ( $class, $re ) = @_; 
4765     $re =~ s{^/|/$}{}g; # XXX validate? 
4770         groupname 
=> 'MatchGroup', 
4775     return App
::Ack
::Filter
::MatchGroup-
>new; 
4779     my ( $self, $resource ) = @_; 
4781     my $re = $self->{'regex'}; 
4783     return $resource->basename =~ /$re/; 
4789     my $re = $self->{'regex'}; 
4791     print ref($self) . " - $re"; 
4799     my $re = $self->{'regex'}; 
4801     return "filename matches $re"; 
4805     App
::Ack
::Filter-
>register_filter(match 
=> __PACKAGE__
); 
4809 package App
::Ack
::Filter
::Default
; 
4814     our @ISA = 'App::Ack::Filter'; 
4820     return bless {}, $class; 
4824     my ( $self, $resource ) = @_; 
4826     return -T 
$resource->name; 
4830 package App
::Ack
::Filter
::Inverse
; 
4835     our @ISA = 'App::Ack::Filter'; 
4839     my ( $class, $filter ) = @_; 
4847     my ( $self, $resource ) = @_; 
4849     my $filter = $self->{'filter'}; 
4850     return !$filter->filter( $resource ); 
4856     return $self->{'filter'}; 
4866     my $filter = $self->{'filter'}; 
4872 package App
::Ack
::Filter
::Collection
; 
4877     our @ISA = 'App::Ack::Filter'; 
4890     my ( $self, $resource ) = @_; 
4892     for my $group (values %{$self->{'groups'}}) { 
4893         if ($group->filter($resource)) { 
4898     for my $filter (@{$self->{'ungrouped'}}) { 
4899         if ($filter->filter($resource)) { 
4908     my ( $self, $filter ) = @_; 
4910     if (exists $filter->{'groupname'}) { 
4911         my $group = ($self->{groups
}->{$filter->{groupname
}} ||= $filter->create_group()); 
4912         $group->add($filter); 
4915         push @{$self->{'ungrouped'}}, $filter; 
4924     return ref($self) . " - $self"; 
4930     my $ungrouped = $self->{'ungrouped'}; 
4932     return join(', ', map { "($_)" } @{$ungrouped}); 
4936 package App
::Ack
::Filter
::IsGroup
; 
4941     our @ISA = 'App::Ack::Filter'; 
4944 use File
::Spec 
3.00 (); 
4955     my ( $self, $filter ) = @_; 
4957     $self->{data
}->{ $filter->{filename
} } = 1; 
4963     my ( $self, $resource ) = @_; 
4965     my $data = $self->{'data'}; 
4966     my $base = $resource->basename; 
4968     return exists $data->{$base}; 
4974     return ref($self) . " - $self"; 
4980     return join(' ', keys %{$self->{data
}}); 
4984 package App
::Ack
::Filter
::ExtensionGroup
; 
4989     our @ISA = 'App::Ack::Filter'; 
5001     my ( $self, $filter ) = @_; 
5003     foreach my $ext (@{$filter->{extensions
}}) { 
5004         $self->{data
}->{lc $ext} = 1; 
5011     my ( $self, $resource ) = @_; 
5013     if ($resource->name =~ /[.]([^.]*)$/) { 
5014         return exists $self->{'data'}->{lc $1}; 
5023     return ref($self) . " - $self"; 
5029     return join(' ', map { ".$_" } sort keys %{$self->{data
}}); 
5033 package App
::Ack
::Filter
::MatchGroup
; 
5038     our @ISA = 'App::Ack::Filter'; 
5051     my ( $self, $filter ) = @_; 
5053     push @{ $self->{matches
} }, $filter->{regex
}; 
5055     my $re = join('|', map { "(?:$_)" } @{ $self->{matches
} }); 
5056     $self->{big_re
} = qr/$re/; 
5062     my ( $self, $resource ) = @_; 
5064     my $re = $self->{big_re
}; 
5066     return $resource->basename =~ /$re/; 
5078 package App
::Ack
::Filter
::IsPath
; 
5083     our @ISA = 'App::Ack::Filter'; 
5088     my ( $class, $filename ) = @_; 
5091         filename 
=> $filename, 
5092         groupname 
=> 'IsPathGroup', 
5097     return App
::Ack
::Filter
::IsPathGroup-
>new(); 
5101     my ( $self, $resource ) = @_; 
5103     return $resource->name eq $self->{'filename'}; 
5109     my $filename = $self->{'filename'}; 
5111     return ref($self) . " - $filename"; 
5117     my $filename = $self->{'filename'}; 
5123 package App
::Ack
::Filter
::IsPathGroup
; 
5128     our @ISA = 'App::Ack::Filter'; 
5140     my ( $self, $filter ) = @_; 
5142     $self->{data
}->{ $filter->{filename
} } = 1; 
5148     my ( $self, $resource ) = @_; 
5150     my $data = $self->{'data'}; 
5152     return exists $data->{$resource->name}; 
5158     return ref($self) . " - $self"; 
5164     return join(' ', keys %{$self->{data
}}); 
5174 our $VERSION = '1.12'; 
5180 our $name; # name of the current file 
5181 our $dir;  # dir of the current file 
5183 our %files_defaults; 
5188         file_filter     
=> undef, 
5189         descend_filter  
=> undef, 
5190         error_handler   
=> sub { CORE
::die @_ }, 
5191         warning_handler 
=> sub { CORE
::warn @_ }, 
5192         sort_files      
=> undef, 
5193         follow_symlinks 
=> 1, 
5196     %skip_dirs = map {($_,1)} (File
::Spec-
>curdir, File
::Spec-
>updir); 
5201     die _bad_invocation
() if @_ && defined($_[0]) && ($_[0] eq __PACKAGE__
); 
5203     my ($parms,@queue) = _setup
( \
%files_defaults, @_ ); 
5204     my $filter = $parms->{file_filter
}; 
5208             my ($dirname,$file,$fullpath) = splice( @queue, 0, 3 ); 
5209             if ( -f 
$fullpath || -p 
$fullpath || $fullpath =~ m{^/dev/fd} ) { 
5212                     local $File::Next
::dir 
= $dirname; 
5213                     local $File::Next
::name 
= $fullpath; 
5214                     next if not $filter->(); 
5216                 return wantarray ? ($dirname,$file,$fullpath) : $fullpath; 
5219                 unshift( @queue, _candidate_files
( $parms, $fullpath ) ); 
5233     die _bad_invocation
() if @_ && defined($_[0]) && ($_[0] eq __PACKAGE__
); 
5235     my ($parms,@queue) = _setup
( \
%files_defaults, @_ ); 
5236     my $err  = $parms->{error_handler
}; 
5237     my $warn = $parms->{error_handler
}; 
5239     my $filename = $queue[1]; 
5241     if ( !defined($filename) ) { 
5242         $err->( 'Must pass a filename to from_file()' ); 
5247     if ( $filename eq '-' ) { 
5251         if ( !open( $fh, '<', $filename ) ) { 
5252             $err->( "Unable to open $filename: $!" ); 
5256     my $filter = $parms->{file_filter
}; 
5259         local $/ = $parms->{nul_separated
} ? "\x00" : $/; 
5260         while ( my $fullpath = <$fh> ) { 
5262             next unless $fullpath =~ /./; 
5263             if ( not ( -f 
$fullpath || -p _ 
) ) { 
5264                 $warn->( "$fullpath: No such file" ); 
5268             my ($volume,$dirname,$file) = File
::Spec-
>splitpath( $fullpath ); 
5271                 local $File::Next
::dir  
= $dirname; 
5272                 local $File::Next
::name 
= $fullpath; 
5273                 next if not $filter->(); 
5275             return wantarray ? ($dirname,$file,$fullpath) : $fullpath; 
5283 sub _bad_invocation 
{ 
5284     my $good = (caller(1))[3]; 
5286     $bad =~ s/(.+)::/$1->/; 
5287     return "$good must not be invoked as $bad"; 
5290 sub sort_standard
($$)   { return $_[0]->[1] cmp $_[1]->[1] } 
5291 sub sort_reverse
($$)    { return $_[1]->[1] cmp $_[0]->[1] } 
5296     my @parts = split( /\//, $path ); 
5298     return $path if @parts < 2; 
5300     return File
::Spec-
>catfile( @parts ); 
5306     my $defaults = shift; 
5307     my $passed_parms = ref $_[0] eq 'HASH' ? {%{+shift}} : {}; # copy parm hash 
5309     my %passed_parms = %{$passed_parms}; 
5312     for my $key ( keys %{$defaults} ) { 
5314             exists $passed_parms{$key} 
5315                 ? delete $passed_parms{$key} 
5316                 : $defaults->{$key}; 
5319     # Any leftover keys are bogus 
5320     for my $badkey ( keys %passed_parms ) { 
5321         my $sub = (caller(1))[3]; 
5322         $parms->{error_handler
}->( "Invalid option passed to $sub(): $badkey" ); 
5325     # If it's not a code ref, assume standard sort 
5326     if ( $parms->{sort_files
} && ( ref($parms->{sort_files
}) ne 'CODE' ) ) { 
5327         $parms->{sort_files
} = \
&sort_standard
; 
5332         my $start = reslash
( $_ ); 
5334             push @queue, ($start,undef,$start); 
5337             push @queue, (undef,$start,$start); 
5341     return ($parms,@queue); 
5345 sub _candidate_files 
{ 
5347     my $dirname = shift; 
5350     if ( !opendir $dh, $dirname ) { 
5351         $parms->{error_handler
}->( "$dirname: $!" ); 
5356     my $descend_filter = $parms->{descend_filter
}; 
5357     my $follow_symlinks = $parms->{follow_symlinks
}; 
5358     my $sort_sub = $parms->{sort_files
}; 
5360     for my $file ( grep { !exists $skip_dirs{$_} } readdir $dh ) { 
5363         # Only do directory checking if we have a descend_filter 
5364         my $fullpath = File
::Spec-
>catdir( $dirname, $file ); 
5365         if ( !$follow_symlinks ) { 
5366             next if -l 
$fullpath; 
5370         if ( $descend_filter ) { 
5371             if ( $has_stat ? (-d _
) : (-d 
$fullpath) ) { 
5372                 local $File::Next
::dir 
= $fullpath; 
5374                 next if not $descend_filter->(); 
5378             push( @newfiles, [ $dirname, $file, $fullpath ] ); 
5381             push( @newfiles, $dirname, $file, $fullpath ); 
5387         return map { @{$_} } sort $sort_sub @newfiles; 
5394 1; # End of File::Next