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 # http://github.com/petdance/ack2 
   8 # and submit patches against the individual files 
  18 # XXX Don't make this so brute force 
  19 # See also: https://github.com/petdance/ack2/issues/89 
  21 use Getopt
::Long 
2.36 (); 
  25 our $VERSION = '2.00b06'; 
  26 # Check http://betterthangrep.com/ for updates 
  28 # These are all our globals. 
  31     $App::Ack
::orig_program_name 
= $0; 
  32     $0 = join(' ', 'ack', $0); 
  33     if ( $App::Ack
::VERSION 
ne $main::VERSION 
) { 
  34         App
::Ack
::die( "Program/library version mismatch\n\t$0 is $main::VERSION\n\t$INC{'App/Ack.pm'} is $App::Ack::VERSION" ); 
  37     # Do preliminary arg checking; 
  38     my $env_is_usable = 1; 
  40         last if ( $_ eq '--' ); 
  42         # Get the --thpppt and --bar checking out of the way. 
  43         /^--th[pt]+t+$/ && App
::Ack
::_thpppt
($_); 
  44         /^--bar$/ && App
::Ack
::_bar
(); 
  46         # See if we want to ignore the environment. (Don't tell Al Gore.) 
  47         if ( /^--(no)?env$/ ) { 
  48             $env_is_usable = defined $1 ? 0 : 1; 
  51     if ( !$env_is_usable ) { 
  52         my @keys = ( 'ACKRC', grep { /^ACK_/ } keys %ENV ); 
  55     App
::Ack
::load_colors
(); 
  57     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); 
  58     Getopt
::Long
::Configure
('pass_through', 'no_auto_abbrev'); 
  59     Getopt
::Long
::GetOptions
( 
  60         'help'       => sub { App
::Ack
::show_help
(); exit; }, 
  61         'version'    => sub { App
::Ack
::print_version_statement
(); exit; }, 
  62         'man'        => sub { App
::Ack
::show_man
(); exit; }, 
  64     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); 
  67         App
::Ack
::show_help
(); 
  74 sub _compile_descend_filter 
{ 
  77     my $idirs = $opt->{idirs
}; 
  78     return unless $idirs && @{$idirs}; 
  82     foreach my $idir (@{$idirs}) { 
  83         if ( $idir =~ /^(\w+):(.*)/ ) { 
  88                 Carp
::croak
( 'Non-is filters are not yet supported for --ignore-dir' ); 
  92             Carp
::croak
( qq{Invalid filter specification "$_"} ); 
  97         return !exists $ignore_dirs{$_} && !exists $ignore_dirs{$File::Next
::dir
}; 
 101 sub _compile_file_filter 
{ 
 102     my ( $opt, $start ) = @_; 
 104     my $ifiles = $opt->{ifiles
}; 
 107     my @ifiles_filters = map { 
 110         if ( /^(\w+):(.+)/ ) { 
 111             my ($how,$what) = ($1,$2); 
 112             $filter = App
::Ack
::Filter-
>create_filter($how, split(/,/, $what)); 
 115             Carp
::croak
( qq{Invalid filter specification "$_"} ); 
 120     my $filters         = $opt->{'filters'} || []; 
 121     my $inverse_filters = [ grep {  $_->is_inverted() } @{$filters} ]; 
 122     @{$filters}         =   grep { !$_->is_inverted() } @{$filters}; 
 124     my %is_member_of_starting_set = map { (App
::Ack
::get_file_id
($_) => 1) } @{$start}; 
 127         # ack always selects files that are specified on the command 
 128         # line, regardless of filetype.  If you want to ack a JPEG, 
 129         # and say "ack foo whatever.jpg" it will do it for you. 
 130         return 1 if $is_member_of_starting_set{ App
::Ack
::get_file_id
($File::Next
::name
) }; 
 132         # Ignore named pipes found in directory searching.  Named 
 133         # pipes created by subprocesses get specified on the command 
 134         # line, so the rule of "always select whatever is on the 
 135         # command line" wins. 
 136         return 0 if -p 
$File::Next
::name
; 
 138         foreach my $filter (@ifiles_filters) { 
 139             my $resource = App
::Ack
::Resource
::Basic-
>new($File::Next
::name
); 
 140             return 0 if ! $resource || $filter->filter($resource); 
 146             foreach my $filter (@{$filters}) { 
 147                 my $resource = App
::Ack
::Resource
::Basic-
>new($File::Next
::name
); 
 148                 return 0 if ! $resource; 
 149                 if ($filter->filter($resource)) { 
 155         # Don't bother invoking inverse filters unless we consider the current resource a match 
 156         if ( $match_found && @{$inverse_filters} ) { 
 157             foreach my $filter ( @{$inverse_filters} ) { 
 158                 my $resource = App
::Ack
::Resource
::Basic-
>new($File::Next
::name
); 
 159                 return 0 if ! $resource; 
 160                 if ( not $filter->filter( $resource ) ) { 
 171     my $resource = shift; 
 174     my @types = App
::Ack
::filetypes
( $resource ); 
 175     my $types = join( ',', @types ); 
 176     my $arrow = @types ? ' => ' : ' =>'; 
 177     App
::Ack
::print( $resource->name, $arrow, join( ',', @types ), $ors ); 
 183     my @arg_sources = App
::Ack
::retrieve_arg_sources
(); 
 185     my $opt = App
::Ack
::ConfigLoader
::process_args
( @arg_sources ); 
 187     $App::Ack
::report_bad_filenames 
= !$opt->{dont_report_bad_filenames
}; 
 189     if ( $opt->{flush
} ) { 
 193     if ( not defined $opt->{color
} ) { 
 194         $opt->{color
} = !App
::Ack
::output_to_pipe
() && !$App::Ack
::is_windows
; 
 196     if ( not defined $opt->{heading
} and not defined $opt->{break}  ) { 
 197         $opt->{heading
} = $opt->{break} = !App
::Ack
::output_to_pipe
(); 
 200     if ( defined($opt->{H
}) || defined($opt->{h
}) ) { 
 201         $opt->{show_filename
}= $opt->{H
} && !$opt->{h
}; 
 204     if ( my $output = $opt->{output
} ) { 
 205         $output        =~ s{\\}{\\\\}g; 
 206         $output        =~ s{"}{\\"}g; 
 207         $opt->{output
} = qq{"$output"}; 
 211     if ( $App::Ack
::is_filter_mode 
&& !$opt->{files_from
} ) { # probably -x 
 212         $resources    = App
::Ack
::Resources-
>from_stdin( $opt ); 
 213         my $regex = $opt->{regex
}; 
 214         $regex = shift @ARGV if not defined $regex; 
 215         $opt->{regex
} = App
::Ack
::build_regex
( $regex, $opt ); 
 218         if ( $opt->{f
} || $opt->{lines
} ) { 
 219             if ( $opt->{regex
} ) { 
 220                 App
::Ack
::warn( "regex ($opt->{regex}) specified with -f or --lines" ); 
 221                 App
::Ack
::exit_from_ack
( 0 ); # XXX the 0 is misleading 
 225             my $regex = $opt->{regex
}; 
 226             $regex = shift @ARGV if not defined $regex; 
 227             $opt->{regex
} = App
::Ack
::build_regex
( $regex, $opt ); 
 230         if ( not defined $opt->{files_from
} ) { 
 233         if ( !exists($opt->{show_filename
}) ) { 
 234             unless(@start == 1 && !(-d 
$start[0])) { 
 235                 $opt->{show_filename
} = 1; 
 239         if ( defined $opt->{files_from
} ) { 
 240             $resources = App
::Ack
::Resources-
>from_file( $opt, $opt->{files_from
} ); 
 241             exit 1 unless $resources; 
 244             @start = ('.') unless @start; 
 245             foreach my $target (@start) { 
 246                 if ( !-e 
$target && $App::Ack
::report_bad_filenames
) { 
 247                     App
::Ack
::warn( "$target: No such file or directory" ); 
 251             $opt->{file_filter
}    = _compile_file_filter
($opt, \
@start); 
 252             $opt->{descend_filter
} = _compile_descend_filter
($opt); 
 254             $resources = App
::Ack
::Resources-
>from_argv( $opt, \
@start ); 
 257     App
::Ack
::set_up_pager
( $opt->{pager
} ) if defined $opt->{pager
}; 
 259     my $print_filenames = $opt->{show_filename
}; 
 260     my $max_count       = $opt->{m
}; 
 261     my $ors             = $opt->{print0
} ? "\0" : "\n"; 
 262     my $only_first      = $opt->{1}; 
 267     while ( my $resource = $resources->next ) { 
 268         # XXX this variable name combined with what we're trying 
 269         # to do makes no sense. 
 271         # XXX Combine the -f and -g functions 
 273             # XXX printing should probably happen inside of App::Ack 
 274             if ( $opt->{show_types
} ) { 
 275                 show_types
( $resource, $ors ); 
 278                 App
::Ack
::print( $resource->name, $ors ); 
 281             last RESOURCES 
if defined($max_count) && $nmatches >= $max_count; 
 283         elsif ( $opt->{g
} ) { 
 284             my $is_match = ( $resource->name =~ /$opt->{regex}/o ); 
 285             if ( $opt->{v
} ? !$is_match : $is_match ) { 
 286                 if ( $opt->{show_types
} ) { 
 287                     show_types
( $resource, $ors ); 
 290                     App
::Ack
::print( $resource->name, $ors ); 
 293                 last RESOURCES 
if defined($max_count) && $nmatches >= $max_count; 
 296         elsif ( $opt->{lines
} ) { 
 297             my $print_filename = $opt->{show_filename
}; 
 298             my $passthru       = $opt->{passthru
}; 
 301             foreach my $line ( @{ $opt->{lines
} } ) { 
 302                 my @lines             = split /,/, $line; 
 308                 @line_numbers{@lines} = (1) x 
@lines; 
 311             my $filename = $resource->name; 
 313             local $opt->{color
} = 0; 
 315             App
::Ack
::iterate
($resource, $opt, sub { 
 318                 if ( $line_numbers{$.} ) { 
 319                     App
::Ack
::print_line_with_context
($opt, $filename, $_, $.); 
 321                 elsif ( $passthru ) { 
 322                     App
::Ack
::print_line_with_options
($opt, $filename, $_, $., ':'); 
 327         elsif ( $opt->{count
} ) { 
 328             my $matches_for_this_file = App
::Ack
::count_matches_in_resource
( $resource, $opt ); 
 330             unless ( $opt->{show_filename
} ) { 
 331                 $total_count += $matches_for_this_file; 
 335             if ( !$opt->{l
} || $matches_for_this_file > 0) { 
 336                 if ( $print_filenames ) { 
 337                     App
::Ack
::print( $resource->name, ':', $matches_for_this_file, $ors ); 
 340                     App
::Ack
::print( $matches_for_this_file, $ors ); 
 344         elsif ( $opt->{l
} || $opt->{L
} ) { 
 345             my $is_match = App
::Ack
::resource_has_match
( $resource, $opt ); 
 347             if ( $opt->{L
} ? !$is_match : $is_match ) { 
 348                 App
::Ack
::print( $resource->name, $ors ); 
 351                 last RESOURCES 
if $only_first; 
 352                 last RESOURCES 
if defined($max_count) && $nmatches >= $max_count; 
 356             $nmatches += App
::Ack
::print_matches_in_resource
( $resource, $opt ); 
 357             if ( $nmatches && $only_first ) { 
 363     if ( $opt->{count
} && !$opt->{show_filename
} ) { 
 364         App
::Ack
::print( $total_count, "\n" ); 
 368     App
::Ack
::exit_from_ack
( $nmatches ); 
 374 ack - grep-like text finder 
 378     ack [options] PATTERN [FILE...] 
 379     ack -f [options] [DIRECTORY...] 
 383 Ack is designed as a replacement for 99% of the uses of F<grep>. 
 385 Ack searches the named input FILEs (or standard input if no files 
 386 are named, or the file name - is given) for lines containing a match 
 387 to the given PATTERN.  By default, ack prints the matching lines. 
 389 PATTERN is a Perl regular expression.  Perl regular expressions 
 390 are commonly found in other programming languages, but for the particulars 
 391 of their behavior, please consult 
 392 L<http://perldoc.perl.org/perlreref.html|perlreref>.  If you don't know 
 393 how to use regular expression but are interested in learning, you may 
 394 consult L<http://perldoc.perl.org/perlretut.html|perlretut>.  If you do not 
 395 need or want ack to use regular expressions, please see the 
 396 C<-Q>/C<--literal> option. 
 398 Ack can also list files that would be searched, without actually 
 399 searching them, to let you take advantage of ack's file-type filtering 
 402 =head1 FILE SELECTION 
 404 If files are not specified for searching, either on the command 
 405 line or piped in with the C<-x> option, I<ack> delves into 
 406 subdirectories selecting files for searching. 
 408 I<ack> is intelligent about the files it searches.  It knows about 
 409 certain file types, based on both the extension on the file and, 
 410 in some cases, the contents of the file.  These selections can be 
 411 made with the B<--type> option. 
 413 With no file selection, I<ack> searches through regular files that 
 414 are not explicitly excluded by B<--ignore-dir> and B<--ignore-file> 
 415 options, either present in F<ackrc> files or on the command line. 
 417 The default options for I<ack> ignore certain files and directories.  These 
 422 =item * Backup files: Files matching F<#*#> or ending with F<~>. 
 424 =item * Coredumps: Files matching F<core.\d+> 
 426 =item * Version control directories like F<.svn> and F<.git>. 
 430 Run I<ack> with the C<--dump> option to see what settings are set. 
 432 However, I<ack> always searches the files given on the command line, 
 433 no matter what type.  If you tell I<ack> to search in a coredump, 
 434 it will search in a coredump. 
 436 =head1 DIRECTORY SELECTION 
 438 I<ack> descends through the directory tree of the starting directories 
 439 specified.  If no directories are specified, the current working directory is 
 440 used.  However, it will ignore the shadow directories used by 
 441 many version control systems, and the build directories used by the 
 442 Perl MakeMaker system.  You may add or remove a directory from this 
 443 list with the B<--[no]ignore-dir> option. The option may be repeated 
 444 to add/remove multiple directories from the ignore list. 
 446 For a complete list of directories that do not get searched, run 
 449 =head1 WHEN TO USE GREP 
 451 I<ack> trumps I<grep> as an everyday tool 99% of the time, but don't 
 452 throw I<grep> away, because there are times you'll still need it. 
 454 E.g., searching through huge files looking for regexes that can be 
 455 expressed with I<grep> syntax should be quicker with I<grep>. 
 457 If your script or parent program uses I<grep> C<--quiet> or C<--silent> 
 458 or needs exit 2 on IO error, use I<grep>. 
 464 =item B<-A I<NUM>>, B<--after-context=I<NUM>> 
 466 Print I<NUM> lines of trailing context after matching lines. 
 468 =item B<-B I<NUM>>, B<--before-context=I<NUM>> 
 470 Print I<NUM> lines of leading context before matching lines. 
 474 Print a break between results from different files. On by default 
 475 when used interactively. 
 477 =item B<-C [I<NUM>]>, B<--context[=I<NUM>]> 
 479 Print I<NUM> lines (default 2) of context around matching lines. 
 481 =item B<-c>, B<--count> 
 483 Suppress normal output; instead print a count of matching lines for 
 484 each input file.  If B<-l> is in effect, it will only show the 
 485 number of lines for each file that has lines matching.  Without 
 486 B<-l>, some line counts may be zeroes. 
 488 If combined with B<-h> (B<--no-filename>) ack outputs only one total 
 491 =item B<--color>, B<--nocolor>, B<--colour>, B<--nocolour> 
 493 B<--color> highlights the matching text.  B<--nocolor> supresses 
 494 the color.  This is on by default unless the output is redirected. 
 496 On Windows, this option is off by default unless the 
 497 L<Win32::Console::ANSI> module is installed or the C<ACK_PAGER_COLOR> 
 498 environment variable is used. 
 500 =item B<--color-filename=I<color>> 
 502 Sets the color to be used for filenames. 
 504 =item B<--color-match=I<color>> 
 506 Sets the color to be used for matches. 
 508 =item B<--color-lineno=I<color>> 
 510 Sets the color to be used for line numbers. 
 512 =item B<--[no]column> 
 514 Show the column number of the first match.  This is helpful for 
 515 editors that can place your cursor at a given position. 
 517 =item B<--create-ackrc> 
 519 Dumps the default ack options to standard output.  This is useful for 
 520 when you want to customize the defaults. 
 524 Writes the list of options loaded and where they came from to standard 
 525 output.  Handy for debugging. 
 527 =item B<--env>, B<--noenv> 
 529 B<--noenv> disables all environment processing. No F<.ackrc> is 
 530 read and all environment variables are ignored. By default, F<ack> 
 531 considers F<.ackrc> and settings in the environment. 
 535 B<--flush> flushes output immediately.  This is off by default 
 536 unless ack is running interactively (when output goes to a pipe or 
 541 Only print the files that would be searched, without actually doing 
 542 any searching.  PATTERN must not be specified, or it will be taken 
 545 =item B<--files-from=I<FILE>> 
 547 The list of files to be searched is specified in I<FILE>.  The list of 
 548 files are seperated by newlines.  If I<FILE> is C<->, the list is loaded 
 551 =item B<--[no]filter> 
 553 Forces ack to act as if it were recieving input via a pipe. 
 555 =item B<--follow>, B<--nofollow> 
 557 Follow or don't follow symlinks, other than whatever starting files 
 558 or directories were specified on the command line. 
 560 This is off by default. 
 564 Print files where the relative path + filename matches I<REGEX>. 
 566 =item B<--group>, B<--nogroup> 
 568 B<--group> groups matches by file name.  This is the default 
 569 when used interactively. 
 571 B<--nogroup> prints one result per line, like grep.  This is the 
 572 default when output is redirected. 
 574 =item B<-H>, B<--with-filename> 
 576 Print the filename for each match. 
 578 =item B<-h>, B<--no-filename> 
 580 Suppress the prefixing of filenames on output when multiple files are 
 583 =item B<--[no]heading> 
 585 Print a filename heading above each file's results.  This is the default 
 586 when used interactively. 
 588 =item B<--help>, B<-?> 
 590 Print a short help statement. 
 592 =item B<--help-types>, B<--help=types> 
 594 Print all known types. 
 596 =item B<-i>, B<--ignore-case> 
 598 Ignore case in the search strings. 
 600 =item B<--ignore-ack-defaults> 
 602 Tells ack to completely ignore the default definitions provided with ack. 
 603 This is useful in combination with B<--create-ackrc> if you I<really> want 
 606 =item B<--[no]ignore-dir=I<DIRNAME>>, B<--[no]ignore-directory=I<DIRNAME>> 
 608 Ignore directory (as CVS, .svn, etc are ignored). May be used 
 609 multiple times to ignore multiple directories. For example, mason 
 610 users may wish to include B<--ignore-dir=data>. The B<--noignore-dir> 
 611 option allows users to search directories which would normally be 
 612 ignored (perhaps to research the contents of F<.svn/props> directories). 
 614 The I<DIRNAME> must always be a simple directory name. Nested 
 615 directories like F<foo/bar> are NOT supported. You would need to 
 616 specify B<--ignore-dir=foo> and then no files from any foo directory 
 617 are taken into account by ack unless given explicitly on the command 
 620 =item B<--ignore-file=I<FILTERTYPE:FILTERARGS>> 
 622 Ignore files matching I<FILTERTYPE:FILTERARGS>.  The filters are specified 
 623 identically to file type filters as seen in L</"Defining your own types">. 
 625 =item B<-k>, B<--known-types> 
 627 Limit selected files to those with types that ack knows about.  This is 
 628 equivalent to the default behavior found in ack 1. 
 630 =item B<--lines=I<NUM>> 
 632 Only print line I<NUM> of each file. Multiple lines can be given with multiple 
 633 B<--lines> options or as a comma separated list (B<--lines=3,5,7>). B<--lines=4-7> 
 634 also works. The lines are always output in ascending order, no matter the 
 635 order given on the command line. 
 637 =item B<-l>, B<--files-with-matches> 
 639 Only print the filenames of matching files, instead of the matching text. 
 641 =item B<-L>, B<--files-without-matches> 
 643 Only print the filenames of files that do I<NOT> match. 
 645 =item B<--match I<REGEX>> 
 647 Specify the I<REGEX> explicitly. This is helpful if you don't want to put the 
 648 regex as your first argument, e.g. when executing multiple searches over the 
 651     # search for foo and bar in given files 
 652     ack file1 t/file* --match foo 
 653     ack file1 t/file* --match bar 
 655 =item B<-m=I<NUM>>, B<--max-count=I<NUM>> 
 657 Stop reading a file after I<NUM> matches. 
 661 Print this manual page. 
 663 =item B<-n>, B<--no-recurse> 
 665 No descending into subdirectories. 
 669 Show only the part of each line matching PATTERN (turns off text 
 672 =item B<--output=I<expr>> 
 674 Output the evaluation of I<expr> for each line (turns off text 
 676 If PATTERN matches more than once then a line is output for each non-overlapping match. 
 677 For more information please see the section L</"Examples of F<--output>">. 
 679 =item B<--pager=I<program>>, B<--nopager> 
 681 B<--pager> directs ack's output through I<program>.  This can also be specified 
 682 via the C<ACK_PAGER> and C<ACK_PAGER_COLOR> environment variables. 
 684 Using --pager does not suppress grouping and coloring like piping 
 685 output on the command-line does. 
 687 B<--nopager> cancels any setting in ~/.ackrc, C<ACK_PAGER> or C<ACK_PAGER_COLOR>. 
 688 No output will be sent through a pager. 
 692 Prints all lines, whether or not they match the expression.  Highlighting 
 693 will still work, though, so it can be used to highlight matches while 
 694 still seeing the entire file, as in: 
 696     # Watch a log file, and highlight a certain IP address 
 697     $ tail -f ~/access.log | ack --passthru 123.45.67.89 
 701 Only works in conjunction with -f, -g, -l or -c (filename output). The filenames 
 702 are output separated with a null byte instead of the usual newline. This is 
 703 helpful when dealing with filenames that contain whitespace, e.g. 
 705     # remove all files of type html 
 706     ack -f --html --print0 | xargs -0 rm -f 
 708 =item B<-Q>, B<--literal> 
 710 Quote all metacharacters in PATTERN, it is treated as a literal. 
 712 =item B<-r>, B<-R>, B<--recurse> 
 714 Recurse into sub-directories. This is the default and just here for 
 715 compatibility with grep. You can also use it for turning B<--no-recurse> off. 
 719 Suppress error messages about nonexistent or unreadable files.  This is taken 
 722 =item B<--[no]smart-case>, B<--no-smart-case> 
 724 Ignore case in the search strings if PATTERN contains no uppercase 
 725 characters. This is similar to C<smartcase> in vim. This option is 
 728 B<-i> always overrides this option. 
 730 =item B<--sort-files> 
 732 Sorts the found files lexicographically.  Use this if you want your file 
 733 listings to be deterministic between runs of I<ack>. 
 735 =item B<--show-types> 
 737 Outputs the filetypes that ack associates with each file. 
 739 Works with B<-f> and B<-g> options. 
 741 =item B<--type=TYPE>, B<--type=noTYPE> 
 743 Specify the types of files to include or exclude from a search. 
 744 TYPE is a filetype, like I<perl> or I<xml>.  B<--type=perl> can 
 745 also be specified as B<--perl>, and B<--type=noperl> can be done 
 748 If a file is of both type "foo" and "bar", specifying --foo and 
 749 --nobar will exclude the file, because an exclusion takes precedence 
 752 Type specifications can be repeated and are ORed together. 
 754 See I<ack --help=types> for a list of valid types. 
 756 =item B<--type-add I<TYPE>:I<FILTER>:I<FILTERARGS>> 
 758 Files with the given FILTERARGS applied to the given FILTER 
 759 are recognized as being of (the existing) type TYPE. 
 760 See also L</"Defining your own types">. 
 763 =item B<--type-set I<TYPE>:I<FILTER>:I<FILTERARGS>> 
 765 Files with the given FILTERARGS applied to the given FILTER are recognized as 
 766 being of type TYPE. This replaces an existing definition for type TYPE.  See 
 767 also L</"Defining your own types">. 
 769 =item B<--type-del I<TYPE>> 
 771 The filters associated with TYPE are removed from Ack, and are no longer considered 
 774 =item B<-v>, B<--invert-match> 
 776 Invert match: select non-matching lines 
 780 Display version and copyright information. 
 782 =item B<-w>, B<--word-regexp> 
 784 Force PATTERN to match only whole words.  The PATTERN is wrapped with 
 785 C<\b> metacharacters. 
 789 An abbreviation for B<--files-from=->; the list of files to search are read 
 790 from standard input, with one line per file. 
 794 Stops after reporting first match of any kind.  This is different 
 795 from B<--max-count=1> or B<-m1>, where only one match per file is 
 796 shown.  Also, B<-1> works with B<-f> and B<-g>, where B<-m> does 
 801 Display the all-important Bill The Cat logo.  Note that the exact 
 802 spelling of B<--thpppppt> is not important.  It's checked against 
 803 a regular expression. 
 807 Check with the admiral for traps. 
 811 =head1 THE .ackrc FILE 
 813 The F<.ackrc> file contains command-line options that are prepended 
 814 to the command line before processing.  Multiple options may live 
 815 on multiple lines.  Lines beginning with a # are ignored.  A F<.ackrc> 
 816 might look like this: 
 818     # Always sort the files 
 821     # Always color, even if piping to a another program 
 824     # Use "less -r" as my pager 
 827 Note that arguments with spaces in them do not need to be quoted, 
 828 as they are not interpreted by the shell. Basically, each I<line> 
 829 in the F<.ackrc> file is interpreted as one element of C<@ARGV>. 
 831 F<ack> looks in several locations for F<.ackrc> files; the searching 
 832 process is detailed in L</"ACKRC LOCATION SEMANTICS">.  These 
 833 files are not considered if B<--noenv> is specified on the command line. 
 835 =head1 Defining your own types 
 837 ack allows you to define your own types in addition to the predefined 
 838 types. This is done with command line options that are best put into 
 839 an F<.ackrc> file - then you do not have to define your types over and 
 840 over again. In the following examples the options will always be shown 
 841 on one command line so that they can be easily copy & pasted. 
 843 I<ack --perl foo> searches for foo in all perl files. I<ack --help=types> 
 844 tells you, that perl files are files ending 
 845 in .pl, .pm, .pod or .t. So what if you would like to include .xs 
 846 files as well when searching for --perl files? I<ack --type-add perl:ext:xs --perl foo> 
 847 does this for you. B<--type-add> appends 
 848 additional extensions to an existing type. 
 850 If you want to define a new type, or completely redefine an existing 
 851 type, then use B<--type-set>. I<ack --type-set eiffel:ext:e,eiffel> defines 
 852 the type I<eiffel> to include files with 
 853 the extensions .e or .eiffel. So to search for all eiffel files 
 854 containing the word Bertrand use I<ack --type-set eiffel:ext:e,eiffel --eiffel Bertrand>. 
 855 As usual, you can also write B<--type=eiffel> 
 856 instead of B<--eiffel>. Negation also works, so B<--noeiffel> excludes 
 857 all eiffel files from a search. Redefining also works: I<ack --type-set cc:ext:c,h> 
 858 and I<.xs> files no longer belong to the type I<cc>. 
 860 When defining your own types in the F<.ackrc> file you have to use 
 863   --type-set=eiffel:ext:e,eiffel 
 865 or writing on separate lines 
 870 The following does B<NOT> work in the F<.ackrc> file: 
 872   --type-set eiffel:ext:e,eiffel 
 875 In order to see all currently defined types, use I<--help-types>, e.g. 
 876 I<ack --type-set backup:ext:bak --type-add perl:ext:perl --help-types> 
 878 In addition to filtering based on extension (like ack 1.x allowed), ack 2 
 879 offers additional filter types.  The generic syntax is 
 880 I<--type-set TYPE:FILTER:FILTERARGS>; I<FILTERARGS> depends on the value 
 887 I<is> filters match the target filename exactly.  It takes exactly one 
 888 argument, which is the name of the file to match. 
 892     --type-set make:is:Makefile 
 894 =item ext:I<EXTENSION>[,I<EXTENSION2>[,...]] 
 896 I<ext> filters match the extension of the target file against a list 
 897 of extensions.  No leading dot is needed for the extensions. 
 901     --type-set perl:ext:pl,pm,t 
 905 I<match> filters match the target filename against a regular expression. 
 906 The regular expression is made case insensitive for the search. 
 910     --type-set make:match:/(gnu)?makefile/ 
 912 =item firstlinematch:I<REGEX> 
 914 I<firstlinematch> matches the first line of the target file against a 
 915 regular expression.  Like I<match>, the regular expression is made 
 920     --type-add perl:firstlinematch:/perl/ 
 924 More filter types may be made available in the future. 
 926 =head1 ENVIRONMENT VARIABLES 
 928 For commonly-used ack options, environment variables can make life 
 929 much easier.  These variables are ignored if B<--noenv> is specified 
 936 Specifies the location of the user's F<.ackrc> file.  If this file doesn't 
 937 exist, F<ack> looks in the default location. 
 941 This variable specifies default options to be placed in front of 
 942 any explicit options on the command line. 
 944 =item ACK_COLOR_FILENAME 
 946 Specifies the color of the filename when it's printed in B<--group> 
 947 mode.  By default, it's "bold green". 
 949 The recognized attributes are clear, reset, dark, bold, underline, 
 950 underscore, blink, reverse, concealed black, red, green, yellow, 
 951 blue, magenta, on_black, on_red, on_green, on_yellow, on_blue, 
 952 on_magenta, on_cyan, and on_white.  Case is not significant. 
 953 Underline and underscore are equivalent, as are clear and reset. 
 954 The color alone sets the foreground color, and on_color sets the 
 957 This option can also be set with B<--color-filename>. 
 959 =item ACK_COLOR_MATCH 
 961 Specifies the color of the matching text when printed in B<--color> 
 962 mode.  By default, it's "black on_yellow". 
 964 This option can also be set with B<--color-match>. 
 966 See B<ACK_COLOR_FILENAME> for the color specifications. 
 968 =item ACK_COLOR_LINENO 
 970 Specifies the color of the line number when printed in B<--color> 
 971 mode.  By default, it's "bold yellow". 
 973 This option can also be set with B<--color-lineno>. 
 975 See B<ACK_COLOR_FILENAME> for the color specifications. 
 979 Specifies a pager program, such as C<more>, C<less> or C<most>, to which 
 980 ack will send its output. 
 982 Using C<ACK_PAGER> does not suppress grouping and coloring like 
 983 piping output on the command-line does, except that on Windows 
 984 ack will assume that C<ACK_PAGER> does not support color. 
 986 C<ACK_PAGER_COLOR> overrides C<ACK_PAGER> if both are specified. 
 988 =item ACK_PAGER_COLOR 
 990 Specifies a pager program that understands ANSI color sequences. 
 991 Using C<ACK_PAGER_COLOR> does not suppress grouping and coloring 
 992 like piping output on the command-line does. 
 994 If you are not on Windows, you never need to use C<ACK_PAGER_COLOR>. 
 998 =head1 ACK & OTHER TOOLS 
1000 =head2 Vim integration 
1002 F<ack> integrates easily with the Vim text editor. Set this in your 
1003 F<.vimrc> to use F<ack> instead of F<grep>: 
1007 That example uses C<-k> to search through only files of the types ack 
1008 knows about, but you may use other default flags. Now you can search 
1009 with F<ack> and easily step through the results in Vim: 
1011   :grep Dumper perllib 
1013 =head2 Emacs integration 
1015 Phil Jackson put together an F<ack.el> extension that "provides a 
1016 simple compilation mode ... has the ability to guess what files you 
1017 want to search for based on the major-mode." 
1019 L<http://www.shellarchive.co.uk/content/emacs.html> 
1021 =head2 TextMate integration 
1023 Pedro Melo is a TextMate user who writes "I spend my day mostly 
1024 inside TextMate, and the built-in find-in-project sucks with large 
1025 projects.  So I hacked a TextMate command that was using find + 
1026 grep to use ack.  The result is the Search in Project with ack, and 
1027 you can find it here: 
1028 L<http://www.simplicidade.org/notes/archives/2008/03/search_in_proje.html>" 
1030 =head2 Shell and Return Code 
1032 For greater compatibility with I<grep>, I<ack> in normal use returns 
1033 shell return or exit code of 0 only if something is found and 1 if 
1036 (Shell exit code 1 is C<$?=256> in perl with C<system> or backticks.) 
1038 The I<grep> code 2 for errors is not used. 
1040 If C<-f> or C<-g> are specified, then 0 is returned if at least one 
1041 file is found.  If no files are found, then 1 is returned. 
1045 =head1 DEBUGGING ACK PROBLEMS 
1047 If ack gives you output you're not expecting, start with a few simple steps. 
1049 =head2 Use B<--noenv> 
1051 Your environment variables and F<.ackrc> may be doing things you're 
1052 not expecting, or forgotten you specified.  Use B<--noenv> to ignore 
1053 your environment and F<.ackrc>. 
1055 =head2 Use B<-f> to see what files have been selected 
1057 Ack's B<-f> was originally added as a debugging tool.  If ack is 
1058 not finding matches you think it should find, run F<ack -f> to see 
1059 what files have been selected.  You can also add the C<--show-types> 
1060 options to show the type of each file selected. 
1062 =head2 Use B<--dump> 
1064 This lists the ackrc files that are loaded and the options loaded 
1066 So for example you can find a list of directories that do not get searched or where filetypes are defined. 
1070 =head2 Use the F<.ackrc> file. 
1072 The F<.ackrc> is the place to put all your options you use most of 
1073 the time but don't want to remember.  Put all your --type-add and 
1074 --type-set definitions in it.  If you like --smart-case, set it 
1075 there, too.  I also set --sort-files there. 
1077 =head2 Use F<-f> for working with big codesets 
1079 Ack does more than search files.  C<ack -f --perl> will create a 
1080 list of all the Perl files in a tree, ideal for sending into F<xargs>. 
1083     # Change all "this" to "that" in all Perl files in a tree. 
1084     ack -f --perl | xargs perl -p -i -e's/this/that/g' 
1088     perl -p -i -e's/this/that/g' $(ack -f --perl) 
1090 =head2 Use F<-Q> when in doubt about metacharacters 
1092 If you're searching for something with a regular expression 
1093 metacharacter, most often a period in a filename or IP address, add 
1094 the -Q to avoid false positives without all the backslashing.  See 
1095 the following example for more... 
1097 =head2 Use ack to watch log files 
1099 Here's one I used the other day to find trouble spots for a website 
1100 visitor.  The user had a problem loading F<troublesome.gif>, so I 
1101 took the access log and scanned it with ack twice. 
1103     ack -Q aa.bb.cc.dd /path/to/access.log | ack -Q -B5 troublesome.gif 
1105 The first ack finds only the lines in the Apache log for the given 
1106 IP.  The second finds the match on my troublesome GIF, and shows 
1107 the previous five lines from the log in each case. 
1109 =head2 Examples of F<--output> 
1111 Following variables are useful in the expansion string: 
1117 The whole string matched by PATTERN. 
1119 =item C<$1>, C<$2>, ... 
1121 The contents of the 1st, 2nd ... bracketed group in PATTERN. 
1125 The string before the match. 
1129 The string after the match. 
1133 For more details and other variables see 
1134 L<http://perldoc.perl.org/perlvar.html#Variables-related-to-regular-expressions|perlvar>. 
1136 This example shows how to add text around a particular pattern 
1137 (in this case adding _ around word with "e") 
1139     ack2.pl "\w*e\w*" quick.txt --output="$`_$&_$'" 
1140     _The_ quick brown fox jumps over the lazy dog 
1141     The quick brown fox jumps _over_ the lazy dog 
1142     The quick brown fox jumps over _the_ lazy dog 
1144 This shows how to pick out particular parts of a match using ( ) within regular expression. 
1146   ack '=head(\d+)\s+(.*)' --output=' $1 : $2' 
1147   input file contains "=head1 NAME" 
1150 =head2 Share your knowledge 
1152 Join the ack-users mailing list.  Send me your tips and I may add 
1157 =head2 Why isn't ack finding a match in (some file)? 
1159 Probably because it's of a type that ack doesn't recognize.  ack's 
1160 searching behavior is driven by filetype.  B<If ack doesn't know 
1161 what kind of file it is, ack ignores the file.> 
1163 Use the C<-f> switch to see a list of files that ack will search 
1166 If you want ack to search files that it doesn't recognize, use the 
1169 If you want ack to search every file, even ones that it always 
1170 ignores like coredumps and backup files, use the C<-u> switch. 
1172 =head2 Why does ack ignore unknown files by default? 
1174 ack is designed by a programmer, for programmers, for searching 
1175 large trees of code.  Most codebases have a lot files in them which 
1176 aren't source files (like compiled object files, source control 
1177 metadata, etc), and grep wastes a lot of time searching through all 
1178 of those as well and returning matches from those files. 
1180 That's why ack's behavior of not searching things it doesn't recognize 
1181 is one of its greatest strengths: the speed you get from only 
1182 searching the things that you want to be looking at. 
1184 =head2 Wouldn't it be great if F<ack> did search & replace? 
1186 No, ack will always be read-only.  Perl has a perfectly good way 
1187 to do search & replace in files, using the C<-i>, C<-p> and C<-n> 
1190 You can certainly use ack to select your files to update.  For 
1191 example, to change all "foo" to "bar" in all PHP files, you can do 
1192 this from the Unix shell: 
1194     $ perl -i -p -e's/foo/bar/g' $(ack -f --php) 
1196 =head2 Can you make ack recognize F<.xyz> files? 
1198 Yes!  Please see L</"Defining your own types">.  If you think 
1199 that F<ack> should recognize a type by default, please see 
1202 =head2 There's already a program/package called ack. 
1206 =head2 Why is it called ack if it's called ack-grep? 
1208 The name of the program is "ack".  Some packagers have called it 
1209 "ack-grep" when creating packages because there's already a package 
1210 out there called "ack" that has nothing to do with this ack. 
1212 I suggest you make a symlink named F<ack> that points to F<ack-grep> 
1213 because one of the crucial benefits of ack is having a name that's 
1214 so short and simple to type. 
1216 To do that, run this with F<sudo> or as root: 
1218    ln -s /usr/bin/ack-grep /usr/bin/ack 
1220 Alternatively, you could use a shell alias: 
1228 =head2 What does F<ack> mean? 
1230 Nothing.  I wanted a name that was easy to type and that you could 
1231 pronounce as a single syllable. 
1233 =head2 Can I do multi-line regexes? 
1235 No, ack does not support regexes that match multiple lines.  Doing 
1236 so would require reading in the entire file at a time. 
1238 If you want to see lines near your match, use the C<--A>, C<--B> 
1239 and C<--C> switches for displaying context. 
1241 =head2 Why is ack telling me I have an invalid option when searching for C<+foo>? 
1243 ack treats command line options beginning with C<+> or C<-> as options; if you 
1244 would like to search for these, you may prefix your search term with C<--> or 
1245 use the C<--match> option.  (However, don't forget that C<+> is a regular 
1246 expression metacharacter!) 
1248 =head1 ACKRC LOCATION SEMANTICS 
1250 Ack can load its configuration from many sources.  This list 
1251 specifies the sources Ack looks for configuration; each one 
1252 that is found is loaded in the order specified here, and 
1253 each one overrides options set in any of the sources preceding 
1254 it.  (For example, if I set --sort-files in my user ackrc, and 
1255 --nosort-files on the command line, the command line takes 
1262 Defaults are loaded from App::Ack::ConfigDefaults.  This can be omitted 
1263 using C<--ignore-ack-defaults>. 
1265 =item * Global ackrc 
1267 Options are then loaded from the global ackrc.  This is located at 
1268 C</etc/ackrc> on Unix-like systems, and 
1269 C<C:\Documents and Settings\All Users\Application Data> on Windows. 
1270 This can be omitted using C<--noenv>. 
1274 Options are then loaded from the user's ackrc.  This is located at 
1275 C<$HOME/.ackrc> on Unix-like systems, and 
1276 C<C:\Documents and Settings\$USER\Application Data>.  If a different 
1277 ackrc is desired, it may be overriden with the C<$ACKRC> environment 
1279 This can be omitted using C<--noenv>. 
1281 =item * Project ackrc 
1283 Options are then loaded from the project ackrc.  The project ackrc is 
1284 the first ackrc file with the name C<.ackrc> or C<_ackrc>, first searching 
1285 in the current directory, then the parent directory, then the grandparent 
1286 directory, etc.  This can be omitted using C<--noenv>. 
1290 Options are then loaded from the enviroment variable C<ACK_OPTIONS>.  This can 
1291 be omitted using C<--noenv>. 
1293 =item * Command line 
1295 Options are then loaded from the command line. 
1299 =head1 DIFFERENCES BETWEEN ACK 1.X AND ACK 2.X 
1301 A lot of changes were made for ack 2; here is a list of them. 
1303 =head2 GENERAL CHANGES 
1309 When no selectors are specified, ack 1.x only searches through files that 
1310 it can map to a file type.  ack 2.x, by constrast, will search through 
1311 every regular, non-binary file that is not explicitly ignored via 
1312 B<--ignore-file> or B<--ignore-dir>.  This is similar to the behavior of the 
1313 B<-a/--all> option in ack 1.x. 
1317 A more flexible filter system has been added, so that more powerful file types 
1318 may be created by the user.  For details, please consult 
1319 L</"Defining your own types">. 
1323 ack now loads multiple ackrc files; see L</"ACKRC LOCATION SEMANTICS"> for 
1328 ack's default filter definitions aren't special; you may tell ack to 
1329 completely disregard them if you don't like them. 
1333 =head2 REMOVED OPTIONS 
1339 Because of the change in default search behavior, the B<-a/--all> and 
1340 B<-u/--unrestricted> options have been removed.  In addition, the 
1341 B<-k/--known-types> option was added to cause ack to behave with 
1342 the default search behavior of ack 1.x. 
1346 The B<-G> option has been removed.  Two regular expressions on the 
1347 command line was considered too confusing; to simulate B<-G>'s functionality, 
1348 you may use the new B<-x> option to pipe filenames from one invocation of 
1353 The B<--binary> option has been removed. 
1357 The B<--skipped> option has been removed. 
1361 The B<--text> option has been removed. 
1365 The B<--invert-file-match> option has been removed.  Instead, you may 
1366 use B<-v> with B<-g>. 
1370 =head2 CHANGED OPTIONS 
1376 The options that modify the regular expression's behavior (B<-i>, B<-w>, 
1377 B<-Q>, and B<-v>) may now be used with B<-g>. 
1381 =head2 ADDED OPTIONS 
1387 B<--files-from> was added so that a user may submit a list of filenames as 
1388 a list of files to search. 
1392 B<-x> was added to tell ack to accept a list of filenames via standard input; 
1393 this list is the list of filenames that will be used for the search. 
1397 B<-s> was added to tell ack to suppress error messages about non-existent or 
1402 B<--ignore-directory> and B<--noignore-directory> were added as aliases for 
1403 B<--ignore-dir> and B<--noignore-dir> respectively. 
1407 B<--ignore-file> was added so that users may specify patterns of files to 
1408 ignore (ex. /.*~$/). 
1412 B<--dump> was added to allow users to easily find out which options are 
1417 B<--create-ackrc> was added so that users may create custom ackrc files based 
1418 on the default settings loaded by ack, and so that users may easily view those 
1423 B<--type-del> was added to selectively remove file type definitions. 
1427 B<--ignore-ack-defaults> was added so that users may ignore ack's default 
1428 options in favor of their own. 
1432 B<--bar> was added so ack users may consult Admiral Ackbar. 
1438 Andy Lester, C<< <andy at petdance.com> >> 
1442 Please report any bugs or feature requests to the issues list at 
1443 Github: L<https://github.com/petdance/ack2/issues> 
1447 All enhancement requests MUST first be posted to the ack-users 
1448 mailing list at L<http://groups.google.com/group/ack-users>.  I 
1449 will not consider a request without it first getting seen by other 
1450 ack users.  This includes requests for new filetypes. 
1452 There is a list of enhancements I want to make to F<ack> in the ack 
1453 issues list at Github: L<https://github.com/petdance/ack2/issues> 
1455 Patches are always welcome, but patches with tests get the most 
1460 Support for and information about F<ack> can be found at: 
1464 =item * The ack homepage 
1466 L<http://betterthangrep.com/> 
1468 =item * The ack-users mailing list 
1470 L<http://groups.google.com/group/ack-users> 
1472 =item * The ack issues list at Github 
1474 L<https://github.com/petdance/ack2/issues> 
1476 =item * AnnoCPAN: Annotated CPAN documentation 
1478 L<http://annocpan.org/dist/ack> 
1480 =item * CPAN Ratings 
1482 L<http://cpanratings.perl.org/d/ack> 
1486 L<http://search.cpan.org/dist/ack> 
1488 =item * Git source repository 
1490 L<https://github.com/petdance/ack2> 
1494 =head1 ACKNOWLEDGEMENTS 
1496 How appropriate to have I<ack>nowledgements! 
1498 Thanks to everyone who has contributed to ack in any way, including 
1519 Eric Van Dewoestine, 
1528 Christopher J. Madsen, 
1540 GE<aacute>bor SzabE<oacute>, 
1543 E<AElig>var ArnfjE<ouml>rE<eth> Bjarmason, 
1547 Mark Leighton Fisher, 
1553 Nilson Santos F. Jr, 
1558 Ask BjE<oslash>rn Hansen, 
1562 Slaven ReziE<0x107>, 
1572 =head1 COPYRIGHT & LICENSE 
1574 Copyright 2005-2013 Andy Lester. 
1576 This program is free software; you can redistribute it and/or modify 
1577 it under the terms of the Artistic License v2.0. 
1579 See http://www.perlfoundation.org/artistic_license_2_0 or the LICENSE.md 
1580 file that comes with the ack distribution. 
1589 our $VERSION = '1.12'; 
1595 our $name; # name of the current file 
1596 our $dir;  # dir of the current file 
1598 our %files_defaults; 
1603         file_filter     
=> undef, 
1604         descend_filter  
=> undef, 
1605         error_handler   
=> sub { CORE
::die @_ }, 
1606         warning_handler 
=> sub { CORE
::warn @_ }, 
1607         sort_files      
=> undef, 
1608         follow_symlinks 
=> 1, 
1611     %skip_dirs = map {($_,1)} (File
::Spec-
>curdir, File
::Spec-
>updir); 
1616     die _bad_invocation
() if @_ && defined($_[0]) && ($_[0] eq __PACKAGE__
); 
1618     my ($parms,@queue) = _setup
( \
%files_defaults, @_ ); 
1619     my $filter = $parms->{file_filter
}; 
1623             my ($dirname,$file,$fullpath) = splice( @queue, 0, 3 ); 
1624             if ( -f 
$fullpath || -p 
$fullpath || $fullpath =~ m{^/dev/fd} ) { 
1627                     local $File::Next
::dir 
= $dirname; 
1628                     local $File::Next
::name 
= $fullpath; 
1629                     next if not $filter->(); 
1631                 return wantarray ? ($dirname,$file,$fullpath) : $fullpath; 
1634                 unshift( @queue, _candidate_files
( $parms, $fullpath ) ); 
1648     die _bad_invocation
() if @_ && defined($_[0]) && ($_[0] eq __PACKAGE__
); 
1650     my ($parms,@queue) = _setup
( \
%files_defaults, @_ ); 
1651     my $err  = $parms->{error_handler
}; 
1652     my $warn = $parms->{error_handler
}; 
1654     my $filename = $queue[1]; 
1656     if ( !defined($filename) ) { 
1657         $err->( 'Must pass a filename to from_file()' ); 
1662     if ( $filename eq '-' ) { 
1666         if ( !open( $fh, '<', $filename ) ) { 
1667             $err->( "Unable to open $filename: $!" ); 
1671     my $filter = $parms->{file_filter
}; 
1674         local $/ = $parms->{nul_separated
} ? "\x00" : $/; 
1675         while ( my $fullpath = <$fh> ) { 
1677             next unless $fullpath =~ /./; 
1678             if ( not ( -f 
$fullpath || -p _ 
) ) { 
1679                 $warn->( "$fullpath: No such file" ); 
1683             my ($volume,$dirname,$file) = File
::Spec-
>splitpath( $fullpath ); 
1686                 local $File::Next
::dir  
= $dirname; 
1687                 local $File::Next
::name 
= $fullpath; 
1688                 next if not $filter->(); 
1690             return wantarray ? ($dirname,$file,$fullpath) : $fullpath; 
1698 sub _bad_invocation 
{ 
1699     my $good = (caller(1))[3]; 
1701     $bad =~ s/(.+)::/$1->/; 
1702     return "$good must not be invoked as $bad"; 
1705 sub sort_standard
($$)   { return $_[0]->[1] cmp $_[1]->[1] } 
1706 sub sort_reverse
($$)    { return $_[1]->[1] cmp $_[0]->[1] } 
1711     my @parts = split( /\//, $path ); 
1713     return $path if @parts < 2; 
1715     return File
::Spec-
>catfile( @parts ); 
1721     my $defaults = shift; 
1722     my $passed_parms = ref $_[0] eq 'HASH' ? {%{+shift}} : {}; # copy parm hash 
1724     my %passed_parms = %{$passed_parms}; 
1727     for my $key ( keys %{$defaults} ) { 
1729             exists $passed_parms{$key} 
1730                 ? delete $passed_parms{$key} 
1731                 : $defaults->{$key}; 
1734     # Any leftover keys are bogus 
1735     for my $badkey ( keys %passed_parms ) { 
1736         my $sub = (caller(1))[3]; 
1737         $parms->{error_handler
}->( "Invalid option passed to $sub(): $badkey" ); 
1740     # If it's not a code ref, assume standard sort 
1741     if ( $parms->{sort_files
} && ( ref($parms->{sort_files
}) ne 'CODE' ) ) { 
1742         $parms->{sort_files
} = \
&sort_standard
; 
1747         my $start = reslash
( $_ ); 
1749             push @queue, ($start,undef,$start); 
1752             push @queue, (undef,$start,$start); 
1756     return ($parms,@queue); 
1760 sub _candidate_files 
{ 
1762     my $dirname = shift; 
1765     if ( !opendir $dh, $dirname ) { 
1766         $parms->{error_handler
}->( "$dirname: $!" ); 
1771     my $descend_filter = $parms->{descend_filter
}; 
1772     my $follow_symlinks = $parms->{follow_symlinks
}; 
1773     my $sort_sub = $parms->{sort_files
}; 
1775     for my $file ( grep { !exists $skip_dirs{$_} } readdir $dh ) { 
1778         # Only do directory checking if we have a descend_filter 
1779         my $fullpath = File
::Spec-
>catdir( $dirname, $file ); 
1780         if ( !$follow_symlinks ) { 
1781             next if -l 
$fullpath; 
1785         if ( $descend_filter ) { 
1786             if ( $has_stat ? (-d _
) : (-d 
$fullpath) ) { 
1787                 local $File::Next
::dir 
= $fullpath; 
1789                 next if not $descend_filter->(); 
1793             push( @newfiles, [ $dirname, $file, $fullpath ] ); 
1796             push( @newfiles, $dirname, $file, $fullpath ); 
1802         return map { @{$_} } sort $sort_sub @newfiles; 
1809 1; # End of File::Next 
1815 use Getopt
::Long 
2.36 (); 
1822     $VERSION = '2.00b06'; 
1823     $COPYRIGHT = 'Copyright 2005-2013 Andy Lester.'; 
1824     $GIT_REVISION = q{04e8986}; 
1839 our $is_filter_mode; 
1840 our $output_to_pipe; 
1846 use File
::Spec 
1.00015 (); 
1847 use File
::Glob 
1.00015 ':glob'; 
1850     # These have to be checked before any filehandle diddling. 
1851     $output_to_pipe  = not -t 
*STDOUT
; 
1852     $is_filter_mode = -p STDIN
; 
1854     $is_cygwin       = ($^O eq 'cygwin'); 
1855     $is_windows      = ($^O =~ /MSWin32/); 
1856     $dir_sep_chars   = $is_windows ? quotemeta( '\\/' ) : quotemeta( File
::Spec-
>catfile( '', '' ) ); 
1860 sub retrieve_arg_sources 
{ 
1866     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); 
1867     Getopt
::Long
::Configure
('pass_through'); 
1868     Getopt
::Long
::Configure
('no_auto_abbrev'); 
1870     Getopt
::Long
::GetOptions
( 
1872         'ackrc=s' => \
$ackrc, 
1875     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); 
1880         my $finder = App
::Ack
::ConfigFinder-
>new; 
1881         @files  = $finder->find_config_files; 
1884         # we explicitly use open so we get a nice error message 
1885         # XXX this is a potential race condition! 
1886         if(open my $fh, '<', $ackrc) { 
1890             die "Unable to load ackrc '$ackrc': $!" 
1892         push( @files, $ackrc ); 
1895     push @arg_sources, Defaults 
=> [ App
::Ack
::ConfigDefault
::options
() ]; 
1897     foreach my $file ( @files) { 
1898         my @lines = read_rcfile
($file); 
1899         push ( @arg_sources, $file, \
@lines ) if @lines; 
1902     if ( $ENV{ACK_OPTIONS
} && !$noenv ) { 
1903         push( @arg_sources, 'ACK_OPTIONS' => $ENV{ACK_OPTIONS
} ); 
1906     push( @arg_sources, 'ARGV' => [ @ARGV ] ); 
1908     return @arg_sources; 
1914     return unless defined $file && -e 
$file; 
1918     open( my $fh, '<', $file ) or App
::Ack
::die( "Unable to read $file: $!" ); 
1919     while ( my $line = <$fh> ) { 
1924         next if $line eq ''; 
1925         next if $line =~ /^#/; 
1927         push( @lines, $line ); 
1935 sub create_ignore_rules 
{ 
1940     my @opts = @{$opts}; 
1944     for my $opt ( @opts ) { 
1945         if ( $opt =~ /^(is|ext|regex),(.+)$/ ) { 
1948             if ( $method eq 'regex' ) { 
1949                 push( @{$rules{regex
}}, qr/$arg/ ); 
1952                 ++$rules{$method}{$arg}; 
1956             App
::Ack
::die( "Invalid argument for --$what: $opt" ); 
1964 sub remove_dir_sep 
{ 
1966     $path =~ s/[$dir_sep_chars]$//; 
1976     defined $str or App
::Ack
::die( 'No regular expression found.' ); 
1978     $str = quotemeta( $str ) if $opt->{Q
}; 
1980         $str = "\\b$str" if $str =~ /^\w/; 
1981         $str = "$str\\b" if $str =~ /\w$/; 
1984     my $regex_is_lc = $str eq lc $str; 
1985     if ( $opt->{i
} || ($opt->{smart_case
} && $regex_is_lc) ) { 
1996         die "Invalid regex '$str':\n  $error"; 
2006     return unless defined $regex; 
2008     eval { qr/$regex/ }; 
2010         (my $error = $@) =~ s/ at \S+ line \d+.*//; 
2012         App
::Ack
::die( "Invalid regex '$regex':\n  $error" ); 
2022     return CORE
::warn( _my_program
(), ': ', @_, "\n" ); 
2027     return CORE
::die( _my_program
(), ': ', @_, "\n" ); 
2031     require File
::Basename
; 
2032     return File
::Basename
::basename
( $0 ); 
2037 sub filetypes_supported 
{ 
2038     return keys %mappings; 
2042     my $y = q{_   /|,\\'!.x',=(www)=,   U   }; 
2043     $y =~ tr/,x!w/\nOo_/; 
2048     my $y = _get_thpppt
(); 
2049     App
::Ack
::print( "$y ack $_[0]!\n" ); 
2057  3~!I#7#I"7#I!?!+!="+"="+!:! 
2058  2?#I!7!I!?#I!7!I"+"=%+"=# 
2059  1?"+!?*+!=#~"=!+#?"="+! 
2060  0?"+!?"I"?&+!="~!=!~"=!+%="+" 
2061  /I!+!?)+!?!+!=$~!=!~!="+!="+"?!="?! 
2063  ,,!?%I"?(+$=$~!=#:"~$:!~! 
2064  ,I!?!I!?"I"?!+#?"+!?!+#="~$:!~!:!~!:!,!:!,":#~! 
2065  +I!?&+!="+!?#+$=!~":!~!:!~!:!,!:#,!:!,%:" 
2066  *+!I!?!+$=!+!=!+!?$+#=!~":!~":#,$:",#:!,!:! 
2067  *I!?"+!?!+!=$+!?#+#=#~":$,!:",!:!,&:" 
2068  )I!?$=!~!=#+"?!+!=!+!=!~!="~!:!~":!,'.!,%:!~! 
2069  (=!?"+!?!=!~$?"+!?!+!=#~"=",!="~$,$.",#.!:!=! 
2070  (I"+"="~"=!+&=!~"=!~!,!~!+!=!?!+!?!=!I!?!+"=!.",!.!,":! 
2071  %I$?!+!?!=%+!~!+#~!=!~#:#=!~!+!~!=#:!,%.!,!.!:" 
2072  $I!?!=!?!I!+!?"+!=!~!=!~!?!I!?!=!+!=!~#:",!~"=!~!:"~!=!:",&:" '-/ 
2073  $?!+!I!?"+"=!+"~!,!:"+#~#:#,"=!~"=!,!~!,!.",!:".!:! */! !I!t!'!s! !a! !g!r!e!p!!! !/! 
2074  $+"=!+!?!+"~!=!:!~!:"I!+!,!~!=!:!~!,!:!,$:!~".&:"~!,# (-/ 
2075  %~!=!~!=!:!.!+"~!:!,!.!,!~!=!:$.!,":!,!.!:!~!,!:!=!.#="~!,!:" ./! 
2076  %=!~!?!+"?"+!=!~",!.!:!?!~!.!:!,!:!,#.!,!:","~!:!=!~!=!:",!~! ./! 
2077  %+"~":!~!=#~!:!~!,!.!~!:",!~!=!~!.!:!,!.",!:!,":!=":!.!,!:!7! -/! 
2078  %~",!:".#:!=!:!,!:"+!:!~!:!.!,!~!,!.#,!.!,$:"~!,":"~!=! */! 
2079  &=!~!=#+!=!~",!.!:",#:#,!.",+:!,!.",!=!+!?! 
2080  &~!=!~!=!~!:"~#:",!.!,#~!:!.!+!,!.",$.",$.#,!+!I!?! 
2081  &~!="~!:!~":!~",!~!=!~":!,!:!~!,!:!,&.$,#."+!?!I!?!I! 
2082  &~!=!~!=!+!,!:!~!:!=!,!:!~&:$,!.!,".!,".!,#."~!+!?$I! 
2083  &~!=!~!="~!=!:!~":!,!~%:#,!:",!.!,#.",#I!7"I!?!+!?"I" 
2084  &+!I!7!:#~"=!~!:!,!:"~$.!=!.!,!~!,$.#,!~!7!I#?!+!?"I"7! 
2085  %7#?!+!~!:!=!~!=!~":!,!:"~":#.!,)7#I"?"I!7& 
2086  %7#I!=":!=!~!:"~$:"~!:#,!:!,!:!~!:#,!7#I!?#7) 
2087  $7$+!,!~!=#~!:!~!:!~$:#,!.!~!:!=!,":!7#I"?#7+=!?! 
2088  $7#I!~!,!~#=!~!:"~!:!,!:!,#:!=!~",":!7$I!?#I!7*+!=!+" 
2089  "I!7$I!,":!,!.!=":$,!:!,$:$7$I!+!?"I!7+?"I!7!I!7!,! 
2090  !,!7%I!:",!."~":!,&.!,!:!~!I!7$I!+!?"I!7,?!I!7',! 
2091  !7(,!.#~":!,%.!,!7%I!7!?#I"7,+!?!7* 
2092 7+:!,!~#,"=!7'I!?#I"7/+!7+ 
2093 77I!+!7!?!7!I"71+!7, 
2096     $x =~ s/(.)(.)/$1x(ord($2)-32)/eg; 
2097     App
::Ack
::print( $x ); 
2103     my $help_arg = shift || 0; 
2105     return show_help_types
() if $help_arg =~ /^types?/; 
2107     App
::Ack
::print( <<"END_OF_HELP" ); 
2108 Usage: ack [OPTION]... PATTERN [FILES OR DIRECTORIES] 
2110 Search for PATTERN in each source file in the tree from the current 
2111 directory on down.  If any files or directories are specified, then 
2112 only those files and directories are checked.  ack may also search 
2113 STDIN, but only if no file or directory arguments are specified, 
2114 or if one of them is "-". 
2116 Default switches may be specified in ACK_OPTIONS environment variable or 
2117 an .ackrc file. If you want no dependency on the environment, turn it 
2120 Example: ack -i select 
2123   -i, --ignore-case             Ignore case distinctions in PATTERN 
2124   --[no]smart-case              Ignore case distinctions in PATTERN, 
2125                                 only if PATTERN contains no upper case. 
2126                                 Ignored if -i is specified 
2127   -v, --invert-match            Invert match: select non-matching lines 
2128   -w, --word-regexp             Force PATTERN to match only whole words 
2129   -Q, --literal                 Quote all metacharacters; PATTERN is literal 
2132   --lines=NUM                   Only print line(s) NUM of each file 
2133   -l, --files-with-matches      Only print filenames containing matches 
2134   -L, --files-without-matches   Only print filenames with no matches 
2135   --output=expr                 Output the evaluation of expr for each line 
2136                                 (turns off text highlighting) 
2137   -o                            Show only the part of a line matching PATTERN 
2138                                 Same as --output='\$&' 
2139   --passthru                    Print all lines, whether matching or not 
2140   --match PATTERN               Specify PATTERN explicitly. 
2141   -m, --max-count=NUM           Stop searching in each file after NUM matches 
2142   -1                            Stop searching after one match of any kind 
2143   -H, --with-filename           Print the filename for each match 
2144   -h, --no-filename             Suppress the prefixing filename on output 
2145   -c, --count                   Show number of lines matching per file 
2146   --[no]column                  Show the column number of the first match 
2148   -A NUM, --after-context=NUM   Print NUM lines of trailing context after matching 
2150   -B NUM, --before-context=NUM  Print NUM lines of leading context before matching 
2152   -C [NUM], --context[=NUM]     Print NUM lines (default 2) of output context. 
2154   --print0                      Print null byte as separator between filenames, 
2155                                 only works with -f, -g, -l, -L or -c. 
2157   -s                            Suppress error messages about nonexistent or 
2162   --pager=COMMAND               Pipes all ack output through COMMAND.  For example, 
2163                                 --pager="less -R".  Ignored if output is redirected. 
2164   --nopager                     Do not send output through a pager.  Cancels any 
2165                                 setting in ~/.ackrc, ACK_PAGER or ACK_PAGER_COLOR. 
2166   --[no]heading                 Print a filename heading above each file's results. 
2167                                 (default: on when used interactively) 
2168   --[no]break                   Print a break between results from different files. 
2169                                 (default: on when used interactively) 
2170   --group                       Same as --heading --break 
2171   --nogroup                     Same as --noheading --nobreak 
2172   --[no]color                   Highlight the matching text (default: on unless 
2173                                 output is redirected, or on Windows) 
2174   --[no]colour                  Same as --[no]color 
2175   --color-filename=COLOR 
2177   --color-lineno=COLOR          Set the color for filenames, matches, and line numbers. 
2178   --flush                       Flush output immediately, even when ack is used 
2179                                 non-interactively (when output goes to a pipe or 
2184   -f                            Only print the files selected, without searching. 
2185                                 The PATTERN must not be specified. 
2186   -g                            Same as -f, but only select files matching PATTERN. 
2187   --sort-files                  Sort the found files lexically. 
2188   --show-types                  Show which types each file has. 
2189   --files-from=FILE             Read the list of files to search from FILE. 
2190   -x                            Read the list of files to search from STDIN. 
2192 File inclusion/exclusion: 
2193   --[no]ignore-dir=name         Add/Remove directory from the list of ignored dirs 
2194   --[no]ignore-directory=name   Synonym for ignore-dir 
2195   --ignore-file=filter          Add filter for ignoring files 
2196   -r, -R, --recurse             Recurse into subdirectories (ack's default behavior) 
2197   -n, --no-recurse              No descending into subdirectories 
2198   --[no]follow                  Follow symlinks.  Default is off. 
2199   -k, --known-types             Include only files with types that ack recognizes. 
2201   --type=X                      Include only X files, where X is a recognized filetype. 
2202   --type=noX                    Exclude X files. 
2203                                 See "ack --help-types" for supported filetypes. 
2205 File type specification: 
2206   --type-set TYPE:FILTER:FILTERARGS 
2207                                 Files with the given FILTERARGS applied to the given 
2208                                 FILTER are recognized as being of type TYPE. This 
2209                                 replaces an existing definition for type TYPE. 
2210   --type-add TYPE:FILTER:FILTERARGS 
2211                                 Files with the given FILTERARGS applied to the given 
2212                                 FILTER are recognized as being of type TYPE. 
2213   --type-del TYPE               Removes all filters associated with TYPE. 
2217   --[no]env                     Ignore environment variables and global ackrc files.  --env is legal but redundant. 
2218   --ackrc=filename              Specify an ackrc file to use 
2219   --ignore-ack-defaults         Ignore the default definitions that ack includes. 
2220   --create-ackrc                Outputs a default ackrc for your customization to standard output. 
2221   --help, -?                    This help 
2222   --help-types                  Display all known types 
2223   --dump                        Dump information on which options are loaded from which RC files 
2224   --[no]filter                  Force ack to treat standard input as a pipe (--filter) or tty (--nofilter) 
2226   --version                     Display version & copyright 
2227   --thpppt                      Bill the Cat 
2228   --bar                         The warning admiral 
2230 Exit status is 0 if match, 1 if no match. 
2232 This is version $VERSION of ack. 
2240 sub show_help_types 
{ 
2241     App
::Ack
::print( <<'END_OF_HELP' ); 
2242 Usage: ack [OPTION]... PATTERN [FILES OR DIRECTORIES] 
2244 The following is the list of filetypes supported by ack.  You can 
2245 specify a file type with the --type=TYPE format, or the --TYPE 
2246 format.  For example, both --type=perl and --perl work. 
2248 Note that some extensions may appear in multiple types.  For example, 
2249 .pod files are both Perl and Parrot. 
2253     my @types = filetypes_supported
(); 
2256         $maxlen = length if $maxlen < length; 
2258     for my $type ( sort @types ) { 
2259         next if $type =~ /^-/; # Stuff to not show 
2260         my $ext_list = $mappings{$type}; 
2262         if ( ref $ext_list ) { 
2263             $ext_list = join( ' ', map { $_->to_string } @{$ext_list} ); 
2265         App
::Ack
::print( sprintf( "    --[no]%-*.*s %s\n", $maxlen, $maxlen, $type, $ext_list ) ); 
2274     Pod
::Usage
::pod2usage
({ 
2275         -input   
=> $App::Ack
::orig_program_name
, 
2284 sub get_version_statement 
{ 
2287     my $copyright = get_copyright
(); 
2288     my $this_perl = $Config::Config
{perlpath
}; 
2290         my $ext = $Config::Config
{_exe
}; 
2291         $this_perl .= $ext unless $this_perl =~ m/$ext$/i; 
2293     my $ver = sprintf( '%vd', $^V ); 
2295     my $git_revision = $GIT_REVISION ? " (git commit $GIT_REVISION)" : ''; 
2297     return <<"END_OF_VERSION"; 
2298 ack ${VERSION}${git_revision} 
2299 Running under Perl $ver at $this_perl 
2303 This program is free software.  You may modify or distribute it 
2304 under the terms of the Artistic License v2.0. 
2309 sub print_version_statement 
{ 
2310     App
::Ack
::print( get_version_statement
() ); 
2322     eval 'use Term::ANSIColor 1.12 ()'; 
2324     $ENV{ACK_COLOR_MATCH
}    ||= 'black on_yellow'; 
2325     $ENV{ACK_COLOR_FILENAME
} ||= 'bold green'; 
2326     $ENV{ACK_COLOR_LINENO
}   ||= 'bold yellow'; 
2332 # print subs added in order to make it easy for a third party 
2333 # module (such as App::Wack) to redefine the display methods 
2334 # and show the results in a different way. 
2335 sub print                   { print {$fh} @_; return; } 
2336 sub print_first_filename    
{ App
::Ack
::print( $_[0], "\n" ); return; } 
2337 sub print_blank_line        
{ App
::Ack
::print( "\n" ); return; } 
2338 sub print_separator         
{ App
::Ack
::print( "--\n" ); return; } 
2339 sub print_filename          
{ App
::Ack
::print( $_[0], $_[1] ); return; } 
2340 sub print_line_no           
{ App
::Ack
::print( $_[0], $_[1] ); return; } 
2341 sub print_column_no         
{ App
::Ack
::print( $_[0], $_[1] ); return; } 
2343     my $filename = shift; 
2344     my $nmatches = shift; 
2347     my $show_filename = shift; 
2349     if ($show_filename) { 
2350         App
::Ack
::print( $filename ); 
2351         App
::Ack
::print( ':', $nmatches ) if $count; 
2354         App
::Ack
::print( $nmatches ) if $count; 
2356     App
::Ack
::print( $ors ); 
2362     my $filename = shift; 
2364     my $show_filename = shift; 
2366     if ($show_filename) { 
2367         App
::Ack
::print( $filename, ':0', $ors ); 
2370         App
::Ack
::print( '0', $ors ); 
2377     my $command = shift; 
2379     return if App
::Ack
::output_to_pipe
(); 
2382     if ( not open( $pager, '|-', $command ) ) { 
2383         App
::Ack
::die( qq{Unable to pipe to pager "$command": $!} ); 
2391 sub output_to_pipe 
{ 
2392     return $output_to_pipe; 
2397     my $nmatches = shift; 
2399     my $rc = $nmatches ? 0 : 1; 
2405 my @capture_indices; 
2406 my $match_column_number; 
2409     my ( $opt, $line ) = @_; 
2411     my $re     = $opt->{regex
}; 
2412     my $invert = $opt->{v
}; 
2416     $match_column_number = undef; 
2417     @capture_indices     = (); 
2419     if ( $invert ? $line !~ /$re/ : $line =~ /$re/ ) { 
2420         if ( not $invert ) { 
2421             # @- = @LAST_MATCH_START 
2422             # @+ = @LAST_MATCH_END 
2423             $match_column_number = $-[0] + 1; 
2426                 @capture_indices = map { 
2438 sub get_capture_indices 
{ 
2439     return @capture_indices; 
2442 sub get_match_column 
{ 
2443     return $match_column_number; 
2448 sub print_matches_in_resource 
{ 
2449     my ( $resource, $opt ) = @_; 
2451     my $passthru       = $opt->{passthru
}; 
2452     my $max_count      = $opt->{m
} || -1; 
2454     my $filename       = $resource->name; 
2455     my $break          = $opt->{break}; 
2456     my $heading        = $opt->{heading
}; 
2457     my $ors            = $opt->{print0
} ? "\0" : "\n"; 
2458     my $color          = $opt->{color
}; 
2459     my $print_filename = $opt->{show_filename
}; 
2461     my $has_printed_for_this_resource = 0; 
2463     App
::Ack
::iterate
($resource, $opt, sub { 
2464         if ( App
::Ack
::does_match
($opt, $_) ) { 
2465             if( !$has_printed_for_this_resource ) { 
2466                 if( $break && has_printed_something
() ) { 
2467                     App
::Ack
::print_blank_line
(); 
2469                 if( $print_filename) { 
2471                         my $filename = $resource->name; 
2473                             $filename = Term
::ANSIColor
::colored
($filename, 
2474                                 $ENV{ACK_COLOR_FILENAME
}); 
2476                         App
::Ack
::print_filename
( $filename, $ors ); 
2480             App
::Ack
::print_line_with_context
($opt, $filename, $_, $.); 
2481             $has_printed_for_this_resource = 1; 
2485         elsif ( $passthru ) { 
2487             if( $break && !$has_printed_for_this_resource && has_printed_something
() ) { 
2488                 App
::Ack
::print_blank_line
(); 
2490             App
::Ack
::print_line_with_options
($opt, $filename, $_, $., ':'); 
2491             $has_printed_for_this_resource = 1; 
2493         return $max_count != 0; 
2499 sub count_matches_in_resource 
{ 
2500     my ( $resource, $opt ) = @_; 
2504     App
::Ack
::iterate
( $resource, $opt, sub { 
2505         ++$nmatches if App
::Ack
::does_match
($opt, $_); 
2512 sub resource_has_match 
{ 
2513     my ( $resource, $opt ) = @_; 
2515     return count_matches_in_resource
($resource, $opt) > 0; 
2520 my @before_ctx_lines; 
2521 my @after_ctx_lines; 
2525     if ( not $is_iterating ) { 
2526         Carp
::croak
( 'get_context() called outside of iterate()' ); 
2530         scalar(@before_ctx_lines) ? \
@before_ctx_lines : undef, 
2531         scalar(@after_ctx_lines)  ? \
@after_ctx_lines  : undef, 
2536     my ( $resource, $opt, $cb ) = @_; 
2540     local $opt->{before_context
} = $opt->{output
} ? 0 : $opt->{before_context
}; 
2541     local $opt->{after_context
}  = $opt->{output
} ? 0 : $opt->{after_context
}; 
2543     my $n_before_ctx_lines = $opt->{before_context
} || 0; 
2544     my $n_after_ctx_lines  = $opt->{after_context
}  || 0; 
2547     @after_ctx_lines = @before_ctx_lines = (); 
2549     if ( $resource->next_text() ) { 
2550         $current_line = $_; # prime the first line of input 
2553     while ( defined $current_line ) { 
2554         while ( (@after_ctx_lines < $n_after_ctx_lines) && $resource->next_text() ) { 
2555             push @after_ctx_lines, $_; 
2558         local $_ = $current_line; 
2559         my $former_dot_period = $.; 
2560         $. = $. - @after_ctx_lines; 
2562         last unless $cb->(); 
2564         # I tried doing this with local(), but for some reason, 
2565         # $. continued to have its new value after the exit of the 
2566         # enclosing block.  I'm guessing that $. has some extra 
2567         # magic associated with it or something.  If someone can 
2568         # tell me why this happened, I would love to know! 
2569         $. = $former_dot_period; # XXX this won't happen on an exception 
2571         push @before_ctx_lines, $current_line; 
2572 if($n_after_ctx_lines) { 
2573             $current_line = shift @after_ctx_lines; 
2575         elsif($resource->next_text()) { 
2579             undef $current_line; 
2581         shift @before_ctx_lines while @before_ctx_lines > $n_before_ctx_lines; 
2584     $is_iterating = 0; # XXX this won't happen on an exception 
2585                        #     then again, do we care? ack doesn't really 
2586                        #     handle exceptions anyway. 
2593 my $has_printed_something; 
2596     $has_printed_something = 0; 
2599 sub has_printed_something 
{ 
2600     return $has_printed_something; 
2603 sub print_line_with_options 
{ 
2604     my ( $opt, $filename, $line, $line_no, $separator ) = @_; 
2606     $has_printed_something = 1; 
2608     my $print_filename = $opt->{show_filename
}; 
2609     my $print_column   = $opt->{column
}; 
2610     my $ors            = $opt->{print0
} ? "\0" : "\n"; 
2611     my $heading        = $opt->{heading
}; 
2612     my $output_expr    = $opt->{output
}; 
2613     my $re             = $opt->{regex
}; 
2614     my $color          = $opt->{color
}; 
2619         $filename = Term
::ANSIColor
::colored
($filename, 
2620             $ENV{ACK_COLOR_FILENAME
}); 
2621         $line_no  = Term
::ANSIColor
::colored
($line_no, 
2622             $ENV{ACK_COLOR_LINENO
}); 
2625     if($print_filename) { 
2627             push @line_parts, $line_no; 
2630             push @line_parts, $filename, $line_no; 
2633         if( $print_column ) { 
2634             push @line_parts, get_match_column
(); 
2637     if( $output_expr ) { 
2638         # XXX avoid re-evaluation if we can 
2639         while( $line =~ /$re/g ) { 
2640             my $output = eval $output_expr; 
2641             App
::Ack
::print( join( $separator, @line_parts, $output ), $ors ); 
2645         my @capture_indices = get_capture_indices
(); 
2646         if( @capture_indices ) { 
2647             my $offset = 0; # additional offset for when we add stuff 
2649             foreach my $index_pair ( @capture_indices ) { 
2650                 my ( $match_start, $match_end ) = @{$index_pair}; 
2652                 my $substring = substr( $line, 
2653                     $offset + $match_start, $match_end - $match_start ); 
2654                 my $substitution = Term
::ANSIColor
::colored
( $substring, 
2655                     $ENV{ACK_COLOR_MATCH
} ); 
2657                 substr( $line, $offset + $match_start, 
2658                     $match_end - $match_start, $substitution ); 
2660                 $offset += length( $substitution ) - length( $substring ); 
2664             # XXX I know $& is a no-no; fix it later 
2665             if($line  =~ s/$re/Term::ANSIColor::colored($&, $ENV{ACK_COLOR_MATCH})/ge) { 
2666                 $line .= "\033[0m\033[K"; 
2670         push @line_parts, $line; 
2671         App
::Ack
::print( join( $separator, @line_parts ), $ors ); 
2680 my $previous_file_processed; 
2681 my $previous_line_printed; 
2684     $is_first_match        = 1; 
2685     $previous_line_printed = -1; 
2688 sub print_line_with_context 
{ 
2689     my ( $opt, $filename, $matching_line, $line_no ) = @_; 
2691     my $heading = $opt->{heading
}; 
2693     if( !defined($previous_file_processed) || 
2694       $previous_file_processed ne $filename ) { 
2695         $previous_file_processed = $filename; 
2696         $previous_line_printed   = -1; 
2699             $is_first_match = 1; 
2703     my $ors                 = $opt->{print0
} ? "\0" : "\n"; 
2704     my $match_word          = $opt->{w
}; 
2705     my $re                  = $opt->{regex
}; 
2706     my $is_tracking_context = $opt->{after_context
} || $opt->{before_context
}; 
2707     my $output_expr         = $opt->{output
}; 
2709     chomp $matching_line; 
2711     my ( $before_context, $after_context ) = get_context
(); 
2713     if ( $before_context ) { 
2714         my $first_line = $. - @{$before_context}; 
2716         if ( $first_line <= $previous_line_printed ) { 
2717             splice @{$before_context}, 0, $previous_line_printed - $first_line + 1; 
2718             $first_line = $. - @{$before_context}; 
2720         if ( @{$before_context} ) { 
2721             my $offset = @{$before_context}; 
2723             if( !$is_first_match && $previous_line_printed != $first_line - 1 ) { 
2724                 App
::Ack
::print('--', $ors); 
2726             foreach my $line (@{$before_context}) { 
2727                 my $context_line_no = $. - $offset; 
2728                 if ( $context_line_no <= $previous_line_printed ) { 
2733                 App
::Ack
::print_line_with_options
($opt, $filename, $line, $context_line_no, '-'); 
2734                 $previous_line_printed = $context_line_no; 
2740     if ( $. > $previous_line_printed ) { 
2741         if( $is_tracking_context && !$is_first_match && $previous_line_printed != $. - 1 ) { 
2742             App
::Ack
::print('--', $ors); 
2745         App
::Ack
::print_line_with_options
($opt, $filename, $matching_line, $line_no, ':'); 
2746         $previous_line_printed = $.; 
2749     if($after_context) { 
2751         foreach my $line (@{$after_context}) { 
2753             if ( $previous_line_printed >= $. + $offset ) { 
2758             my $separator = App
::Ack
::does_match
( $opt, $line ) ? ':' : '-'; 
2759             App
::Ack
::print_line_with_options
($opt, $filename, $line, $. + $offset, $separator); 
2760             $previous_line_printed = $. + $offset; 
2765     $is_first_match = 0; 
2772 # inefficient, but functional 
2774     my ( $resource ) = @_; 
2778     foreach my $k (keys %mappings) { 
2779         my $filters = $mappings{$k}; 
2781         foreach my $filter (@{$filters}) { 
2782             # clone the resource 
2783             my $clone = $resource->clone; 
2784             if ( $filter->filter($clone) ) { 
2791     return sort @matches; 
2794 # returns a (fairly) unique identifier for a file 
2795 # use this function to compare two files to see if they're 
2796 # equal (ie. the same file, but with a different path/links/etc) 
2798     my ( $filename ) = @_; 
2800     if ( $is_windows ) { 
2801         return File
::Next
::reslash
( $filename ); 
2804         # XXX is this the best method? it always hits the FS 
2805         if( my ( $dev, $inode ) = (stat($filename))[0, 1] ) { 
2806             return join(':', $dev, $inode); 
2809             # XXX this could be better 
2816     my @lines = App
::Ack
::ConfigDefault
::options
(); 
2818     print join("\n", '--ignore-ack-defaults', @lines); 
2823 1; # End of App::Ack 
2824 package App
::Ack
::Resource
; 
2834     Carp
::confess
( 'Must be overloaded' ); 
2854 sub needs_line_scan 
{ 
2879 package App
::Ack
::Resources
; 
2892     my $self = bless {}, $class; 
2894     my $file_filter    = undef; 
2895     my $descend_filter = $opt->{descend_filter
}; 
2898         $descend_filter = sub { 
2904         File
::Next
::files
( { 
2905             file_filter     
=> $opt->{file_filter
}, 
2906             descend_filter  
=> $descend_filter, 
2907             error_handler   
=> sub { my $msg = shift; App
::Ack
::warn( $msg ) }, 
2908             sort_files      
=> $opt->{sort_files
}, 
2909             follow_symlinks 
=> $opt->{follow
}, 
2922         File
::Next
::from_file
( { 
2923             error_handler   
=> sub { my $msg = shift; App
::Ack
::warn( $msg ) }, 
2924             warning_handler 
=> sub { my $msg = shift; App
::Ack
::warn( $msg ) }, 
2925             sort_files      
=> $opt->{sort_files
}, 
2926         }, $file ) or return undef; 
2933 # This is for reading input lines from STDIN, not the list of files from STDIN 
2938     my $self  = bless {}, $class; 
2940     my $has_been_called = 0; 
2942     $self->{iter
} = sub { 
2943         if ( !$has_been_called ) { 
2944             $has_been_called = 1; 
2956     my $file = $self->{iter
}->() or return; 
2958     return App
::Ack
::Resource
::Basic-
>new( $file ); 
2962 package App
::Ack
::Resource
::Basic
; 
2969     our @ISA = 'App::Ack::Resource'; 
2975     my $filename = shift; 
2978         filename 
=> $filename, 
2983     if ( $self->{filename
} eq '-' ) { 
2984         $self->{fh
} = *STDIN
; 
2987         if ( !open( $self->{fh
}, '<', $self->{filename
} ) && $App::Ack
::report_bad_filenames 
) { 
2988             App
::Ack
::warn( "$self->{filename}: $!" ); 
3000     return $self->{filename
}; 
3005 sub needs_line_scan 
{ 
3009     return 1 if $opt->{v
}; 
3011     my $size = -s 
$self->{fh
}; 
3015     elsif ( $size > 100_000 ) { 
3020     my $rc = sysread( $self->{fh
}, $buffer, $size ); 
3021     if ( !defined($rc) && $App::Ack
::report_bad_filenames 
) { 
3022         App
::Ack
::warn( "$self->{filename}: $!" ); 
3025     return 0 unless $rc && ( $rc == $size ); 
3027     my $regex = $opt->{regex
}; 
3028     return $buffer =~ /$regex/m; 
3035     if( !seek( $self->{fh
}, 0, 0 ) && $App::Ack
::report_bad_filenames 
) { 
3036         App
::Ack
::warn( "$self->{filename}: $!" ); 
3044     if ( defined ($_ = readline $_[0]->{fh
}) ) { 
3045         $. = ++$_[0]->{line
}; 
3046         s/[\r\n]+$//; # chomp may not handle this 
3047         $_ .= "\n"; # add back newline (XXX make it native) 
3058     if ( !close($self->{fh
}) && $App::Ack
::report_bad_filenames 
) { 
3059         App
::Ack
::warn( $self->name() . ": $!" ); 
3069     return __PACKAGE__-
>new($self->name); 
3074 package App
::Ack
::Filter
; 
3079     '""' => 'to_string'; 
3087     my ( undef, $type, @args ) = @_; 
3089     if ( my $package = $filter_types{$type} ) { 
3090         return $package->new(@args); 
3092     Carp
::croak 
"Unknown filter type '$type'"; 
3096 sub register_filter 
{ 
3097     my ( undef, $type, $package ) = @_; 
3099     $filter_types{$type} = $package; 
3108     return App
::Ack
::Filter
::Inverse-
>new( $self ); 
3120     return '(unimplemented to_string)'; 
3131 package App
::Ack
::Filter
::Extension
; 
3136     our @ISA = 'App::Ack::Filter'; 
3140     my ( $class, @extensions ) = @_; 
3142     my $exts = join('|', map { "\Q$_\E"} @extensions); 
3143     my $re   = qr/[.](?:$exts)$/i; 
3146         extensions 
=> \
@extensions, 
3152     my ( $self, $resource ) = @_; 
3154     my $re = $self->{'regex'}; 
3156     return $resource->name =~ /$re/; 
3162     my $re = $self->{'regex'}; 
3164     return ref($self) . " - $re"; 
3170     my $exts = $self->{'extensions'}; 
3172     return join(' ', map { ".$_" } @{$exts}); 
3176     App
::Ack
::Filter-
>register_filter(ext 
=> __PACKAGE__
); 
3180 package App
::Ack
::Filter
::FirstLineMatch
; 
3185     our @ISA = 'App::Ack::Filter'; 
3189     my ( $class, $re ) = @_; 
3191     $re =~ s{^/|/$}{}g; # XXX validate? 
3199 # XXX This test checks the first "line" of the file, but we need 
3200 # it to be less piggy.  If it's something like a .min.js file, then 
3201 # the "line" could be the entire file.  Instead, it should read the 
3202 # first, say, 100 characters of the first line. 
3205     my ( $self, $resource ) = @_; 
3207     my $re = $self->{'regex'}; 
3210     return unless $resource->next_text; 
3218     my $re = $self->{'regex'}; 
3220     return ref($self) . " - $re"; 
3226     my $re = $self->{'regex'}; 
3228     return "first line matches $re"; 
3232     App
::Ack
::Filter-
>register_filter(firstlinematch 
=> __PACKAGE__
); 
3236 package App
::Ack
::Filter
::Is
; 
3241     our @ISA = 'App::Ack::Filter'; 
3244 use File
::Spec 
3.00 (); 
3247     my ( $class, $filename ) = @_; 
3250         filename 
=> $filename, 
3255     my ( $self, $resource ) = @_; 
3257     my $filename = $self->{'filename'}; 
3258     my $base     = (File
::Spec-
>splitpath($resource->name))[2]; 
3260     return $base eq $filename; 
3266     my $filename = $self->{'filename'}; 
3268     return ref($self) . " - $filename"; 
3274     my $filename = $self->{'filename'}; 
3278     App
::Ack
::Filter-
>register_filter(is => __PACKAGE__
); 
3282 package App
::Ack
::Filter
::Match
; 
3287     our @ISA = 'App::Ack::Filter'; 
3290 use File
::Spec 
3.00; 
3293     my ( $class, $re ) = @_; 
3295     $re =~ s{^/|/$}{}g; # XXX validate? 
3304     my ( $self, $resource ) = @_; 
3306     my $re   = $self->{'regex'}; 
3307     my $base = (File
::Spec-
>splitpath($resource->name))[2]; 
3309     return $base =~ /$re/; 
3315     my $re = $self->{'regex'}; 
3317     print ref($self) . " - $re"; 
3323     my $re = $self->{'regex'}; 
3325     return "filename matches $re"; 
3329     App
::Ack
::Filter-
>register_filter(match 
=> __PACKAGE__
); 
3333 package App
::Ack
::Filter
::Default
; 
3338     our @ISA = 'App::Ack::Filter'; 
3344     return bless {}, $class; 
3348     my ( $self, $resource ) = @_; 
3350     return -T 
$resource->name; 
3354 package App
::Ack
::Filter
::Inverse
; 
3359     our @ISA = 'App::Ack::Filter'; 
3363     my ( $class, $filter ) = @_; 
3371     my ( $self, $resource ) = @_; 
3373     my $filter = $self->{'filter'}; 
3374     return !$filter->filter( $resource ); 
3380     return $self->{'filter'}; 
3390     my $filter = $self->{'filter'}; 
3396 package App
::Ack
::ConfigFinder
; 
3403 use File
::Spec 
3.00; 
3406     if ($App::Ack
::is_windows
) { 
3415     return bless {}, $class; 
3418 sub _remove_redundancies 
{ 
3419     my ( @configs ) = @_; 
3421     my %dev_and_inode_seen; 
3423     foreach my $path ( @configs ) { 
3424         my ( $dev, $inode ) = (stat $path)[0, 1]; 
3426         if( defined($dev) ) { 
3427             if( $dev_and_inode_seen{"$dev:$inode"} ) { 
3431                 $dev_and_inode_seen{"$dev:$inode"} = 1; 
3435     return grep { defined() } @configs; 
3438 sub _check_for_ackrc 
{ 
3439     return unless defined $_[0]; 
3441     my @files = grep { -f 
} 
3442                 map { File
::Spec-
>catfile(@_, $_) } 
3445     die File
::Spec-
>catdir(@_) . " contains both .ackrc and _ackrc.\n" . 
3446         "Please remove one of those files.\n" 
3449     return wantarray ? @files : $files[0]; 
3450 } # end _check_for_ackrc 
3453 sub find_config_files 
{ 
3456     if($App::Ack
::is_windows
) { 
3457         push @config_files, map { File
::Spec-
>catfile($_, 'ackrc') } ( 
3458             Win32
::GetFolderPath
(Win32
::CSIDL_COMMON_APPDATA
()), 
3459             Win32
::GetFolderPath
(Win32
::CSIDL_APPDATA
()), 
3463         push @config_files, '/etc/ackrc'; 
3466     if ( $ENV{'ACKRC'} && -f 
$ENV{'ACKRC'} ) { 
3467         push @config_files, $ENV{'ACKRC'}; 
3470         push @config_files, _check_for_ackrc
($ENV{'HOME'}); 
3473     my @dirs = File
::Spec-
>splitdir(Cwd
::getcwd
()); 
3475         my $ackrc = _check_for_ackrc
(@dirs); 
3476         if(defined $ackrc) { 
3477             push @config_files, $ackrc; 
3483     # XXX we only test for existence here, so if the file is 
3484     #     deleted out from under us, this will fail later. =( 
3485     return _remove_redundancies
( @config_files ); 
3489 package App
::Ack
::ConfigLoader
; 
3495 use Getopt
::Long 
2.36 (); 
3496 use Text
::ParseWords 
3.1 (); 
3499 my @INVALID_COMBINATIONS; 
3502     my @context  = qw( -A -B -C --after-context --before-context --context ); 
3503     my @pretty   = qw( --heading --group --break ); 
3504     my @filename = qw( -h -H --with-filename --no-filename ); 
3506     @INVALID_COMBINATIONS = ( 
3508         [qw(-l)]                 => [@context, @pretty, @filename, qw(-L -o --passthru --output --max-count --column -f -g --show-types)], 
3509         [qw(-L)]                 => [@context, @pretty, @filename, qw(-l -o --passthru --output --max-count --column -f -g --show-types -c --count)], 
3510         [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)], 
3511         [qw(-o)]                 => [@context, qw(--output -c --count --column --column -f --show-types)], 
3512         [qw(--passthru)]         => [@context, qw(--output --column -m --max-count -1 -c --count -f -g)], 
3513         [qw(--output)]           => [@context, qw(-c --count -f -g)], 
3514         [qw(--match)]            => [qw(-f -g)], 
3515         [qw(-m --max-count)]     => [qw(-1 -f -g -c --count)], 
3516         [qw(-h --no-filename)]   => [qw(-H --with-filename -f -g --group --heading)], 
3517         [qw(-H --with-filename)] => [qw(-h --no-filename -f -g)], 
3518         [qw(-c --count)]         => [@context, @pretty, qw(--column -f -g)], 
3519         [qw(--column)]           => [qw(-f -g)], 
3520         [@context]               => [qw(-f -g)], 
3521         [qw(-f)]                 => [qw(-g), @pretty], 
3522         [qw(-g)]                 => [qw(-f), @pretty], 
3526 sub process_filter_spec 
{ 
3529     if ( $spec =~ /^(\w+):(\w+):(.*)/ ) { 
3530         my ( $type_name, $ext_type, $arguments ) = ( $1, $2, $3 ); 
3532         return ( $type_name, 
3533             App
::Ack
::Filter-
>create_filter($ext_type, split(/,/, $arguments)) ); 
3535     elsif ( $spec =~ /^(\w+)=(.*)/ ) { # Check to see if we have ack1-style argument specification. 
3536         my ( $type_name, $extensions ) = ( $1, $2 ); 
3538         my @extensions = split(/,/, $extensions); 
3539         foreach my $extension ( @extensions ) { 
3540             $extension =~ s/^[.]//; 
3543         return ( $type_name, App
::Ack
::Filter-
>create_filter('ext', @extensions) ); 
3546         Carp
::croak 
"invalid filter specification '$spec'"; 
3550 sub process_filetypes 
{ 
3551     my ( $opt, $arg_sources ) = @_; 
3553     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); # start with default options, minus some annoying ones 
3554     Getopt
::Long
::Configure
( 
3559     my %additional_specs; 
3561     my $add_spec = sub { 
3562         my ( undef, $spec ) = @_; 
3564         my ( $name, $filter ) = process_filter_spec
($spec); 
3566         push @{ $App::Ack
::mappings
{$name} }, $filter; 
3568         $additional_specs{$name . '!'} = sub { 
3569             my ( undef, $value ) = @_; 
3571             my @filters = @{ $App::Ack
::mappings
{$name} }; 
3573                 @filters = map { $_->invert() } @filters; 
3576             push @{ $opt->{'filters'} }, @filters; 
3580     my $set_spec = sub { 
3581         my ( undef, $spec ) = @_; 
3583         my ( $name, $filter ) = process_filter_spec
($spec); 
3585         $App::Ack
::mappings
{$name} = [ $filter ]; 
3587         $additional_specs{$name . '!'} = sub { 
3588             my ( undef, $value ) = @_; 
3590             my @filters = @{ $App::Ack
::mappings
{$name} }; 
3592                 @filters = map { $_->invert() } @filters; 
3595             push @{ $opt->{'filters'} }, @filters; 
3599     my $delete_spec = sub { 
3600         my ( undef, $name ) = @_; 
3602         delete $App::Ack
::mappings
{$name}; 
3603         delete $additional_specs{$name . '!'}; 
3606     my %type_arg_specs = ( 
3607         'type-add=s' => $add_spec, 
3608         'type-set=s' => $set_spec, 
3609         'type-del=s' => $delete_spec, 
3612     for ( my $i = 0; $i < @{$arg_sources}; $i += 2) { 
3613         my ( $source_name, $args ) = @{$arg_sources}[ $i, $i + 1]; 
3616             # $args are modified in place, so no need to munge $arg_sources 
3617             Getopt
::Long
::GetOptionsFromArray
($args, %type_arg_specs); 
3620             ( undef, $arg_sources->[$i + 1] ) = 
3621                 Getopt
::Long
::GetOptionsFromString
($args, %type_arg_specs); 
3625     $additional_specs{'k|known-types'} = sub { 
3626         my ( undef, $value ) = @_; 
3628         my @filters = map { @{$_} } values(%App::Ack
::mappings
); 
3630         push @{ $opt->{'filters'} }, @filters; 
3633     return \
%additional_specs; 
3636 sub removed_option 
{ 
3637     my ( $option, $explanation ) = @_; 
3639     $explanation ||= ''; 
3641         warn "Option '$option' is not valid in ack 2\n$explanation"; 
3647     my ( $opt, $extra_specs ) = @_; 
3649     my $dash_a_explanation = <<EOT; 
3650 This is because we now have -k/--known-types which makes it only select files 
3651 of known types, rather than any text file (which is the behavior of ack 1.x). 
3655         1                   => sub { $opt->{1} = $opt->{m
} = 1 }, 
3656         'A|after-context=i' => \
$opt->{after_context
}, 
3657         'B|before-context=i' 
3658                             => \
$opt->{before_context
}, 
3659         'C|context:i'       => sub { shift; my $val = shift; $opt->{before_context
} = $opt->{after_context
} = ($val || 2) }, 
3660         'a'                 => removed_option
('-a', $dash_a_explanation), 
3661         'all'               => removed_option
('--all', $dash_a_explanation), 
3662         'break!'            => \
$opt->{break}, 
3663         c                   
=> \
$opt->{count
}, 
3664         'color|colour!'     => \
$opt->{color
}, 
3665         'color-match=s'     => \
$ENV{ACK_COLOR_MATCH
}, 
3666         'color-filename=s'  => \
$ENV{ACK_COLOR_FILENAME
}, 
3667         'color-lineno=s'    => \
$ENV{ACK_COLOR_LINENO
}, 
3668         'column!'           => \
$opt->{column
}, 
3669         count               
=> \
$opt->{count
}, 
3670         'create-ackrc'      => sub { App
::Ack
::create_ackrc
(); exit; }, 
3672             my ( undef, $value ) = @_; 
3675                 $opt->{noenv_seen
} = 1; 
3679         'files-from=s'      => \
$opt->{files_from
}, 
3680         'filter!'           => \
$App::Ack
::is_filter_mode
, 
3681         flush               
=> \
$opt->{flush
}, 
3682         'follow!'           => \
$opt->{follow
}, 
3684         G                   
=> removed_option
('-G'), 
3685         'group!'            => sub { shift; $opt->{heading
} = $opt->{break} = shift }, 
3686         'heading!'          => \
$opt->{heading
}, 
3687         'h|no-filename'     => \
$opt->{h
}, 
3688         'H|with-filename'   => \
$opt->{H
}, 
3689         'i|ignore-case'     => \
$opt->{i
}, 
3690         'ignore-directory|ignore-dir=s' # XXX Combine this version with the negated version below 
3692                                 my ( undef, $dir ) = @_; 
3694                                 $dir = App
::Ack
::remove_dir_sep
( $dir ); 
3695                                 if ( $dir !~ /^(?:is|match):/ ) { 
3696                                     $dir = 'is:' . $dir; 
3698                                 push @{ $opt->{idirs
} }, $dir; 
3700         'ignore-file=s'    => sub { 
3701                                     my ( undef, $file ) = @_; 
3702                                     push @{ $opt->{ifiles
} }, $file; 
3704         'lines=s'           => sub { shift; my $val = shift; push @{$opt->{lines
}}, $val }, 
3705         'l|files-with-matches' 
3707         'L|files-without-matches' 
3709         'm|max-count=i'     => \
$opt->{m
}, 
3710         'match=s'           => \
$opt->{regex
}, 
3711         'n|no-recurse'      => \
$opt->{n
}, 
3712         o                   
=> sub { $opt->{output
} = '$&' }, 
3713         'output=s'          => \
$opt->{output
}, 
3714         'pager=s'           => \
$opt->{pager
}, 
3715         'noignore-directory|noignore-dir=s' 
3717                                 my ( undef, $dir ) = @_; 
3719                                 # XXX can you do --noignore-dir=match,...? 
3720                                 $dir = App
::Ack
::remove_dir_sep
( $dir ); 
3721                                 if ( $dir !~ /^(?:is|match):/ ) { 
3722                                     $dir = 'is:' . $dir; 
3724                                 if ( $dir !~ /^(?:is|match):/ ) { 
3725                                     Carp
::croak
("invalid noignore-directory argument: '$dir'"); 
3728                                 @{ $opt->{idirs
} } = grep { 
3730                                 } @{ $opt->{idirs
} }; 
3732         'nopager'           => sub { $opt->{pager
} = undef }, 
3733         'passthru'          => \
$opt->{passthru
}, 
3734         'print0'            => \
$opt->{print0
}, 
3735         'Q|literal'         => \
$opt->{Q
}, 
3736         'r|R|recurse'       => sub { $opt->{n
} = 0 }, 
3737         's'                 => \
$opt->{dont_report_bad_filenames
}, 
3738         'show-types'        => \
$opt->{show_types
}, 
3739         'smart-case!'       => \
$opt->{smart_case
}, 
3740         'sort-files'        => \
$opt->{sort_files
}, 
3742             my ( $getopt, $value ) = @_; 
3745             if ( $value =~ s/^no// ) { 
3749             my $callback = $extra_specs->{ $value . '!' }; 
3752                 $callback->( $getopt, $cb_value ); 
3755                 Carp
::croak
( "Unknown type '$value'" ); 
3758         'u'                 => removed_option
('-u'), 
3759         'unrestricted'      => removed_option
('--unrestricted'), 
3760         'v|invert-match'    => \
$opt->{v
}, 
3761         'w|word-regexp'     => \
$opt->{w
}, 
3762         'x'                 => sub { $opt->{files_from
} = '-' }, 
3764         'version'           => sub { App
::Ack
::print_version_statement
(); exit; }, 
3765         'help|?:s'          => sub { shift; App
::Ack
::show_help
(@_); exit; }, 
3766         'help-types'        => sub { App
::Ack
::show_help_types
(); exit; }, 
3767         'man'               => sub { App
::Ack
::show_man
(); exit; }, 
3768         $extra_specs ? %{$extra_specs} : (), 
3773     my ( $opt, $extra_specs, $arg_sources ) = @_; 
3775     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); # start with default options, minus some annoying ones 
3776     Getopt
::Long
::Configure
( 
3782     my $is_help_types_active; 
3784     for ( my $i = 0; $i < @{$arg_sources}; $i += 2 ) { 
3785         my ( $source_name, $args ) = @{$arg_sources}[ $i, $i + 1 ]; 
3787         if ( $source_name eq 'ARGV' ) { 
3788             $argv_source = $args; 
3793     if ( $argv_source ) { # this *should* always be true, but you never know... 
3794         my @copy = @{$argv_source}; 
3796         Getopt
::Long
::Configure
('pass_through'); 
3798         Getopt
::Long
::GetOptionsFromArray
( \
@copy, 
3799             'help-types' => \
$is_help_types_active, 
3802         Getopt
::Long
::Configure
('no_pass_through'); 
3805     my $arg_specs = get_arg_spec
($opt, $extra_specs); 
3807     for ( my $i = 0; $i < @{$arg_sources}; $i += 2) { 
3808         my ($source_name, $args) = @{$arg_sources}[$i, $i + 1]; 
3812             $ret = Getopt
::Long
::GetOptionsFromArray
( $args, %{$arg_specs} ); 
3815             ( $ret, $arg_sources->[$i + 1] ) = 
3816                 Getopt
::Long
::GetOptionsFromString
( $args, %{$arg_specs} ); 
3819             if ( !$is_help_types_active ) { 
3820                 my $where = $source_name eq 'ARGV' ? 'on command line' : "in $source_name"; 
3821                 App
::Ack
::die( "Invalid option $where" ); 
3824         if ( $opt->{noenv_seen
} ) { 
3825             App
::Ack
::die( "--noenv found in $source_name" ); 
3829     # XXX We need to check on a -- in the middle of a non-ARGV source 
3834 sub should_dump_options 
{ 
3835     my ( $sources ) = @_; 
3837     for(my $i = 0; $i < @{$sources}; $i += 2) { 
3838         my ( $name, $options ) = @{$sources}[$i, $i + 1]; 
3839         if($name eq 'ARGV') { 
3841             Getopt
::Long
::Configure
('default', 'pass_through', 'no_auto_help', 'no_auto_version'); 
3842             Getopt
::Long
::GetOptionsFromArray
($options, 
3851 sub explode_sources 
{ 
3852     my ( $sources ) = @_; 
3856     Getopt
::Long
::Configure
('default', 'pass_through', 'no_auto_help', 'no_auto_version'); 
3859     my $arg_spec = get_arg_spec
(\
%opt); 
3861     my $add_type = sub { 
3862         my ( undef, $arg ) = @_; 
3865         if ( $arg =~ /(\w+)=/) { 
3866             $arg_spec->{$1} = sub {}; 
3869             ( $arg ) = split /:/, $arg; 
3870             $arg_spec->{$arg} = sub {}; 
3874     my $del_type = sub { 
3875         my ( undef, $arg ) = @_; 
3877         delete $arg_spec->{$arg}; 
3880     for(my $i = 0; $i < @{$sources}; $i += 2) { 
3881         my ( $name, $options ) = @{$sources}[$i, $i + 1]; 
3882         if ( ref($options) ne 'ARRAY' ) { 
3883             $sources->[$i + 1] = $options = 
3884                 [ Text
::ParseWords
::shellwords
($options) ]; 
3886         for ( my $j = 0; $j < @{$options}; $j++ ) { 
3887             next unless $options->[$j] =~ /^-/; 
3888             my @chunk = ( $options->[$j] ); 
3889             push @chunk, $options->[$j] while ++$j < @{$options} && $options->[$j] !~ /^-/; 
3893             Getopt
::Long
::GetOptionsFromArray
(\
@chunk, 
3894                 'type-add=s' => $add_type, 
3895                 'type-set=s' => $add_type, 
3896                 'type-del=s' => $del_type, 
3898             Getopt
::Long
::GetOptionsFromArray
(\
@chunk, %{$arg_spec}); 
3900             splice @copy, -1 * @chunk if @chunk; # XXX explain this 
3901             push @new_sources, $name, \
@copy; 
3905     return \
@new_sources; 
3911     my $first_a = $a->[0]; 
3912     my $first_b = $b->[0]; 
3914     $first_a =~ s/^--?//; 
3915     $first_b =~ s/^--?//; 
3917     return $first_a cmp $first_b; 
3921     my ( $sources ) = @_; 
3923     $sources = explode_sources
($sources); 
3928     for(my $i = 0; $i < @{$sources}; $i += 2) { 
3929         my ( $name, $contents ) = @{$sources}[$i, $i + 1]; 
3930         if ( not $opts_by_source{$name} ) { 
3931             $opts_by_source{$name} = []; 
3932             push @source_names, $name; 
3934         push @{$opts_by_source{$name}}, $contents; 
3937     foreach my $name (@source_names) { 
3938         my $contents = $opts_by_source{$name}; 
3941         print '=' x 
length($name), "\n"; 
3942         print '  ', join(' ', @{$_}), "\n" foreach sort { compare_opts
($a, $b) } @{$contents}; 
3948 sub remove_default_options_if_needed 
{ 
3949     my ( $sources ) = @_; 
3953     foreach my $index ( 0 .. $#$sources ) { 
3954         if ( $sources->[$index] eq 'Defaults' ) { 
3955             $default_index = $index; 
3960     return $sources unless defined $default_index; 
3962     my $should_remove = 0; 
3964     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); # start with default options, minus some annoying ones 
3965     Getopt
::Long
::Configure
( 
3971     foreach my $index ( $default_index + 2 .. $#$sources ) { 
3972         next if $index % 2 != 0; 
3974         my ( $name, $args ) = @{$sources}[ $index, $index + 1 ]; 
3977             Getopt
::Long
::GetOptionsFromArray
($args, 
3978                 'ignore-ack-defaults' => \
$should_remove, 
3982             ( undef, $sources->[$index + 1] ) = Getopt
::Long
::GetOptionsFromString
($args, 
3983                 'ignore-ack-defaults' => \
$should_remove, 
3988     Getopt
::Long
::Configure
('default'); 
3989     Getopt
::Long
::Configure
('default', 'no_auto_help', 'no_auto_version'); 
3991     return $sources unless $should_remove; 
3993     my @copy = @{$sources}; 
3994     splice @copy, $default_index, 2; 
3998 sub check_for_mutually_exclusive_options 
{ 
3999     my ( $arg_sources ) = @_; 
4001     my %mutually_exclusive_with; 
4002     my @copy = @{$arg_sources}; 
4004     for(my $i = 0; $i < @INVALID_COMBINATIONS; $i += 2) { 
4005         my ( $lhs, $rhs ) = @INVALID_COMBINATIONS[ $i, $i + 1 ]; 
4007         foreach my $l_opt ( @{$lhs} ) { 
4008             foreach my $r_opt ( @{$rhs} ) { 
4009                 push @{ $mutually_exclusive_with{ $l_opt } }, $r_opt; 
4010                 push @{ $mutually_exclusive_with{ $r_opt } }, $l_opt; 
4018         my ( $source_name, $args ) = splice @copy, 0, 2; 
4019         $args = ref($args) ? [ @{$args} ] : [ Text
::ParseWords
::shellwords
($args) ]; 
4021         foreach my $opt ( @{$args} ) { 
4022             next unless $opt =~ /^[-+]/; 
4023             last if $opt eq '--'; 
4025             if( $opt =~ /^(.*)=/ ) { 
4028             elsif ( $opt =~ /^(-[^-]).+/ ) { 
4032             $set_opts{ $opt } = 1; 
4034             my $mutex_opts = $mutually_exclusive_with{ $opt }; 
4036             next unless $mutex_opts; 
4038             foreach my $mutex_opt ( @{$mutex_opts} ) { 
4039                 if($set_opts{ $mutex_opt }) { 
4040                     die "Options '$mutex_opt' and '$opt' are mutually exclusive\n"; 
4048     my $arg_sources = \
@_; 
4052     check_for_mutually_exclusive_options
($arg_sources); 
4054     $arg_sources = remove_default_options_if_needed
($arg_sources); 
4056     if ( should_dump_options
($arg_sources) ) { 
4057         dump_options
($arg_sources); 
4061     my $type_specs = process_filetypes
(\
%opt, $arg_sources); 
4062     process_other
(\
%opt, $type_specs, $arg_sources); 
4063     while ( @{$arg_sources} ) { 
4064         my ( $source_name, $args ) = splice( @{$arg_sources}, 0, 2 ); 
4066         # All of our sources should be transformed into an array ref 
4068             if ( $source_name eq 'ARGV' ) { 
4072                 Carp
::croak 
"source '$source_name' has extra arguments!"; 
4076             Carp
::croak 
'The impossible has occurred!'; 
4079     my $filters = ($opt{filters
} ||= []); 
4081     # throw the default filter in if no others are selected 
4082     if ( not grep { !$_->is_inverted() } @{$filters} ) { 
4083         push @{$filters}, App
::Ack
::Filter
::Default-
>new(); 
4088 1; # End of App::Ack::ConfigLoader 
4089 package App
::Ack
::ConfigDefault
; 
4095     my @options = split( /\n/, _options_block
() ); 
4096     @options = grep { /./ && !/^#/ } @options; 
4101 sub _options_block 
{ 
4103 # This is the default ackrc for ack 2.0 
4105 # There are four different ways to match 
4106 # is:  Match the filename exactly 
4107 # ext: Match the extension of the filename exactly 
4108 # match: Match the filename against a Perl regular expression 
4109 # firstlinematch: Match the first 80 characters of the first line 
4110 #   of text against a Perl regular expression.  This is only for 
4111 #   the --type-add option. 
4114 # Directories to ignore 
4116 --ignore-directory=is:.bzr 
4119 --ignore-directory=is:.cdv 
4122 --ignore-directory=is:~.dep 
4123 --ignore-directory=is:~.dot 
4124 --ignore-directory=is:~.nib 
4125 --ignore-directory=is:~.plst 
4128 --ignore-directory=is:.git 
4131 --ignore-directory=is:.hg 
4134 --ignore-directory=is:.pc 
4137 --ignore-directory=is:.svn 
4140 --ignore-directory=is:_MTN 
4143 --ignore-directory=is:CVS 
4146 --ignore-directory=is:RCS 
4149 --ignore-directory=is:SCCS 
4152 --ignore-directory=is:_darcs 
4155 --ignore-directory=is:_sgbak 
4158 --ignore-directory=is:autom4te.cache 
4160 # Perl module building 
4161 --ignore-directory=is:blib 
4162 --ignore-directory=is:_build 
4164 # Perl Devel::Cover module's output directory 
4165 --ignore-directory=is:cover_db 
4171 --ignore-file=ext:bak 
4172 --ignore-file=match:/~$/ 
4175 --ignore-file=match:/^#.+#$/ 
4178 --ignore-file=match:/[._].*\.swp$/ 
4181 --ignore-file=match:/core\.\d+$/ 
4183 # minified Javascript 
4184 --ignore-file=match:/[.]min[.]js$/ 
4189 # Perl http://perl.org/ 
4190 --type-add=perl:ext:pl,pm,pod,t 
4191 --type-add=perl:firstlinematch:/#!.*\bperl/ 
4193 # Makefiles http://www.gnu.org/s/make/ 
4194 --type-add=make:ext:mk 
4195 --type-add=make:ext:mak 
4196 --type-add=make:is:makefile 
4197 --type-add=make:is:Makefile 
4198 --type-add=make:is:GNUmakefile 
4200 # Rakefiles http://rake.rubyforge.org/ 
4201 --type-add=rake:is:Rakefile 
4203 # CMake http://www.cmake.org/ 
4204 --type-add=cmake:is:CMakeLists.txt 
4205 --type-add=cmake:ext:cmake 
4208 --type-add=actionscript:ext:as,mxml 
4210 # Ada http://www.adaic.org/ 
4211 --type-add=ada:ext:ada,adb,ads 
4213 # ASP http://msdn.microsoft.com/en-us/library/aa286483.aspx 
4214 --type-add=asp:ext:asp 
4216 # ASP.Net http://www.asp.net/ 
4217 --type-add=aspx:ext:master,ascx,asmx,aspx,svc 
4220 --type-add=asm:ext:asm,s 
4223 --type-add=batch:ext:bat,cmd 
4225 # ColdFusion http://en.wikipedia.org/wiki/ColdFusion 
4226 --type-add=cfmx:ext:cfc,cfm,cfml 
4228 # Clojure http://clojure.org/ 
4229 --type-add=clojure:ext:clj 
4232 # .xs are Perl C files 
4233 --type-add=cc:ext:c,h,xs 
4239 --type-add=cpp:ext:cpp,cc,cxx,m,hpp,hh,h,hxx 
4242 --type-add=csharp:ext:cs 
4244 # CSS http://www.w3.org/Style/CSS/ 
4245 --type-add=css:ext:css 
4247 # Delphi http://en.wikipedia.org/wiki/Embarcadero_Delphi 
4248 --type-add=delphi:ext:pas,int,dfm,nfm,dof,dpk,dproj,groupproj,bdsgroup,bdsproj 
4250 # Emacs Lisp http://www.gnu.org/software/emacs 
4251 --type-add=elisp:ext:el 
4253 # Erlang http://www.erlang.org/ 
4254 --type-add=erlang:ext:erl,hrl 
4256 # Fortran http://en.wikipedia.org/wiki/Fortran 
4257 --type-add=fortran:ext:f,f77,f90,f95,f03,for,ftn,fpp 
4259 # Google Go http://golang.org/ 
4260 --type-add=go:ext:go 
4262 # Groovy http://groovy.codehaus.org/ 
4263 --type-add=groovy:ext:groovy,gtmpl,gpp,grunit,gradle 
4265 # Haskell http://www.haskell.org/ 
4266 --type-add=haskell:ext:hs,lhs 
4269 --type-add=html:ext:htm,html 
4271 # Java http://www.oracle.com/technetwork/java/index.html 
4272 --type-add=java:ext:java,properties 
4275 --type-add=js:ext:js 
4277 # JSP http://www.oracle.com/technetwork/java/javaee/jsp/index.html 
4278 --type-add=jsp:ext:jsp,jspx,jhtm,jhtml 
4280 # Common Lisp http://common-lisp.net/ 
4281 --type-add=lisp:ext:lisp,lsp 
4283 # Lua http://www.lua.org/ 
4284 --type-add=lua:ext:lua 
4287 --type-add=objc:ext:m,h 
4290 --type-add=objcpp:ext:mm,h 
4292 # OCaml http://caml.inria.fr/ 
4293 --type-add=ocaml:ext:ml,mli 
4295 # Parrot http://www.parrot.org/ 
4296 --type-add=parrot:ext:pir,pasm,pmc,ops,pod,pg,tg 
4298 # PHP http://www.php.net/ 
4299 --type-add=php:ext:php,phpt,php3,php4,php5,phtml 
4300 --type-add=php:firstlinematch:/#!.*\bphp/ 
4302 # Plone http://plone.org/ 
4303 --type-add=plone:ext:pt,cpt,metadata,cpy,py 
4305 # Python http://www.python.org/ 
4306 --type-add=python:ext:py 
4307 --type-add=python:firstlinematch:/#!.*\bpython/ 
4309 # R http://www.r-project.org/ 
4312 # Ruby http://www.ruby-lang.org/ 
4313 --type-add=ruby:ext:rb,rhtml,rjs,rxml,erb,rake,spec 
4314 --type-add=ruby:is:Rakefile 
4315 --type-add=ruby:firstlinematch:/#!.*\bruby/ 
4317 # Scala http://www.scala-lang.org/ 
4318 --type-add=scala:ext:scala 
4320 # Scheme http://groups.csail.mit.edu/mac/projects/scheme/ 
4321 --type-add=scheme:ext:scm,ss 
4324 --type-add=shell:ext:sh,bash,csh,tcsh,ksh,zsh 
4325 --type-add=shell:firstlinematch:/(?:ba|t?c|k|z)?sh\b/ 
4327 # Smalltalk http://www.smalltalk.org/ 
4328 --type-add=smalltalk:ext:st 
4330 # SQL http://www.iso.org/iso/catalogue_detail.htm?csnumber=45498 
4331 --type-add=sql:ext:sql,ctl 
4333 # Tcl http://www.tcl.tk/ 
4334 --type-add=tcl:ext:tcl,itcl,itk 
4336 # LaTeX http://www.latex-project.org/ 
4337 --type-add=tex:ext:tex,cls,sty 
4339 # Template Toolkit http://template-toolkit.org/ 
4340 --type-add=tt:ext:tt,tt2,ttml 
4343 --type-add=vb:ext:bas,cls,frm,ctl,vb,resx 
4346 --type-add=verilog:ext:v,vh,sv 
4348 # VHDL http://www.eda.org/twiki/bin/view.cgi/P1076/WebHome 
4349 --type-add=vhdl:ext:vhd,vhdl 
4351 # Vim http://www.vim.org/ 
4352 --type-add=vim:ext:vim 
4354 # XML http://www.w3.org/TR/REC-xml/ 
4355 --type-add=xml:ext:xml,dtd,xsl,xslt,ent 
4356 --type-add=xml:firstlinematch:/<[?]xml/ 
4358 # YAML http://yaml.org/ 
4359 --type-add=yaml:ext:yaml,yml