]>
Tony Duckles's Git Repositories (git.nynim.org) - dotfiles.git/blob - bin/ack
   3 # This file, ack, is generated code. 
   4 # Please DO NOT EDIT or send patches for it. 
   6 # Please take a look at the source from 
   7 # https://github.com/petdance/ack 
   8 # and submit patches against the individual files 
  15 our $VERSION = '1.96'; 
  16 # Check http://betterthangrep.com/ for updates 
  18 # These are all our globals. 
  22     if ( $App::Ack
::VERSION 
ne $main::VERSION 
) { 
  23         App
::Ack
::die( "Program/library version mismatch\n\t$0 is $main::VERSION\n\t$INC{'App/Ack.pm'} is $App::Ack::VERSION" ); 
  26     # Do preliminary arg checking; 
  27     my $env_is_usable = 1; 
  29         last if ( $_ eq '--' ); 
  31         # Priorities! Get the --thpppt checking out of the way. 
  32         /^--th[pt]+t+$/ && App
::Ack
::_thpppt
($_); 
  34         # See if we want to ignore the environment. (Don't tell Al Gore.) 
  35         if ( /^--(no)?env$/ ) { 
  36             $env_is_usable = defined $1 ? 0 : 1; 
  39     if ( $env_is_usable ) { 
  40         unshift( @ARGV, App
::Ack
::read_ackrc
() ); 
  43         my @keys = ( 'ACKRC', grep { /^ACK_/ } keys %ENV ); 
  46     App
::Ack
::load_colors
(); 
  48     if ( exists $ENV{ACK_SWITCHES
} ) { 
  49         App
::Ack
::warn( 'ACK_SWITCHES is no longer supported.  Use ACK_OPTIONS.' ); 
  53         App
::Ack
::show_help
(); 
  61     my $opt = App
::Ack
::get_command_line_options
(); 
  63     $| = 1 if $opt->{flush
}; # Unbuffer the output if flush mode 
  65     if ( App
::Ack
::input_from_pipe
() ) { 
  66         # We're going into filter mode 
  68             $opt->{$_} and App
::Ack
::die( "Can't use -$_ when acting as a filter." ); 
  70         $opt->{show_filename
} = 0; 
  71         $opt->{regex
} = App
::Ack
::build_regex
( defined $opt->{regex
} ? $opt->{regex
} : shift @ARGV, $opt ); 
  72         if ( my $nargs = @ARGV ) { 
  73             my $s = $nargs == 1 ? '' : 's'; 
  74             App
::Ack
::warn( "Ignoring $nargs argument$s on the command-line while acting as a filter." ); 
  77         my $res = App
::Ack
::Resource
::Basic-
>new( '-' ); 
  79         if ( $opt->{count
} ) { 
  80             $nmatches = App
::Ack
::search_and_list
( $res, $opt ); 
  84             $nmatches = App
::Ack
::search_resource
( $res, $opt ); 
  87         App
::Ack
::exit_from_ack
( $nmatches ); 
  90     my $file_matching = $opt->{f
} || $opt->{lines
}; 
  91     if ( $file_matching ) { 
  92         App
::Ack
::die( "Can't specify both a regex ($opt->{regex}) and use one of --line, -f or -g." ) if $opt->{regex
}; 
  95         $opt->{regex
} = App
::Ack
::build_regex
( defined $opt->{regex
} ? $opt->{regex
} : shift @ARGV, $opt ); 
  98     # check that all regexes do compile fine 
  99     App
::Ack
::check_regex
( $_ ) for ( $opt->{regex
}, $opt->{G
} ); 
 101     my $what = App
::Ack
::get_starting_points
( \
@ARGV, $opt ); 
 102     my $iter = App
::Ack
::get_iterator
( $what, $opt ); 
 103     App
::Ack
::filetype_setup
(); 
 107     App
::Ack
::set_up_pager
( $opt->{pager
} ) if defined $opt->{pager
}; 
 109         $nmatches = App
::Ack
::print_files
( $iter, $opt ); 
 111     elsif ( $opt->{l
} || $opt->{count
} ) { 
 112         $nmatches = App
::Ack
::print_files_with_matches
( $iter, $opt ); 
 115         $nmatches = App
::Ack
::print_matches
( $iter, $opt ); 
 118     App
::Ack
::exit_from_ack
( $nmatches ); 
 123 ack - grep-like text finder 
 127     ack [options] PATTERN [FILE...] 
 128     ack -f [options] [DIRECTORY...] 
 132 Ack is designed as a replacement for 99% of the uses of F<grep>. 
 134 Ack searches the named input FILEs (or standard input if no files are 
 135 named, or the file name - is given) for lines containing a match to the 
 136 given PATTERN.  By default, ack prints the matching lines. 
 138 Ack can also list files that would be searched, without actually searching 
 139 them, to let you take advantage of ack's file-type filtering capabilities. 
 141 =head1 FILE SELECTION 
 143 I<ack> is intelligent about the files it searches.  It knows about 
 144 certain file types, based on both the extension on the file and, 
 145 in some cases, the contents of the file.  These selections can be 
 146 made with the B<--type> option. 
 148 With no file selections, I<ack> only searches files of types that 
 149 it recognizes.  If you have a file called F<foo.wango>, and I<ack> 
 150 doesn't know what a .wango file is, I<ack> won't search it. 
 152 The B<-a> option tells I<ack> to select all files, regardless of 
 155 Some files will never be selected by I<ack>, even with B<-a>, 
 160 =item * Backup files: Files matching F<#*#> or ending with F<~>. 
 162 =item * Coredumps: Files matching F<core.\d+> 
 166 However, I<ack> always searches the files given on the command line, 
 167 no matter what type. Furthermore, by specifying the B<-u> option all 
 168 files will be searched. 
 170 =head1 DIRECTORY SELECTION 
 172 I<ack> descends through the directory tree of the starting directories 
 173 specified.  However, it will ignore the shadow directories used by 
 174 many version control systems, and the build directories used by the 
 175 Perl MakeMaker system.  You may add or remove a directory from this 
 176 list with the B<--[no]ignore-dir> option. The option may be repeated 
 177 to add/remove multiple directories from the ignore list. 
 179 For a complete list of directories that do not get searched, run 
 182 =head1 WHEN TO USE GREP 
 184 I<ack> trumps I<grep> as an everyday tool 99% of the time, but don't 
 185 throw I<grep> away, because there are times you'll still need it. 
 187 E.g., searching through huge files looking for regexes that can be 
 188 expressed with I<grep> syntax should be quicker with I<grep>. 
 190 If your script or parent program uses I<grep> C<--quiet> or 
 191 C<--silent> or needs exit 2 on IO error, use I<grep>. 
 197 =item B<-a>, B<--all> 
 199 Operate on all files, regardless of type (but still skip directories 
 200 like F<blib>, F<CVS>, etc.) 
 202 =item B<-A I<NUM>>, B<--after-context=I<NUM>> 
 204 Print I<NUM> lines of trailing context after matching lines. 
 206 =item B<-B I<NUM>>, B<--before-context=I<NUM>> 
 208 Print I<NUM> lines of leading context before matching lines. 
 210 =item B<-C [I<NUM>]>, B<--context[=I<NUM>]> 
 212 Print I<NUM> lines (default 2) of context around matching lines. 
 214 =item B<-c>, B<--count> 
 216 Suppress normal output; instead print a count of matching lines for 
 217 each input file.  If B<-l> is in effect, it will only show the 
 218 number of lines for each file that has lines matching.  Without 
 219 B<-l>, some line counts may be zeroes. 
 221 If combined with B<-h> (B<--no-filename>) ack outputs only one total count. 
 223 =item B<--color>, B<--nocolor> 
 225 B<--color> highlights the matching text.  B<--nocolor> supresses 
 226 the color.  This is on by default unless the output is redirected. 
 228 On Windows, this option is off by default unless the 
 229 L<Win32::Console::ANSI> module is installed or the C<ACK_PAGER_COLOR> 
 230 environment variable is used. 
 232 =item B<--color-filename=I<color>> 
 234 Sets the color to be used for filenames. 
 236 =item B<--color-match=I<color>> 
 238 Sets the color to be used for matches. 
 240 =item B<--color-lineno=I<color>> 
 242 Sets the color to be used for line numbers. 
 246 Show the column number of the first match.  This is helpful for editors 
 247 that can place your cursor at a given position. 
 249 =item B<--env>, B<--noenv> 
 251 B<--noenv> disables all environment processing. No F<.ackrc> is read 
 252 and all environment variables are ignored. By default, F<ack> considers 
 253 F<.ackrc> and settings in the environment. 
 257 B<--flush> flushes output immediately.  This is off by default 
 258 unless ack is running interactively (when output goes to a pipe 
 263 Only print the files that would be searched, without actually doing 
 264 any searching.  PATTERN must not be specified, or it will be taken as 
 267 =item B<--follow>, B<--nofollow> 
 269 Follow or don't follow symlinks, other than whatever starting files 
 270 or directories were specified on the command line. 
 272 This is off by default. 
 276 Only paths matching I<REGEX> are included in the search.  The entire 
 277 path and filename are matched against I<REGEX>, and I<REGEX> is a 
 278 Perl regular expression, not a shell glob. 
 280 The options B<-i>, B<-w>, B<-v>, and B<-Q> do not apply to this I<REGEX>. 
 284 Print files where the relative path + filename matches I<REGEX>. This option is 
 285 a convenience shortcut for B<-f> B<-G I<REGEX>>. 
 287 The options B<-i>, B<-w>, B<-v>, and B<-Q> do not apply to this I<REGEX>. 
 289 =item B<--group>, B<--nogroup> 
 291 B<--group> groups matches by file name with.  This is the default when 
 294 B<--nogroup> prints one result per line, like grep.  This is the default 
 295 when output is redirected. 
 297 =item B<-H>, B<--with-filename> 
 299 Print the filename for each match. 
 301 =item B<-h>, B<--no-filename> 
 303 Suppress the prefixing of filenames on output when multiple files are 
 308 Print a short help statement. 
 310 =item B<-i>, B<--ignore-case> 
 312 Ignore case in the search strings. 
 314 This applies only to the PATTERN, not to the regexes given for the B<-g> 
 317 =item B<--[no]ignore-dir=I<DIRNAME>> 
 319 Ignore directory (as CVS, .svn, etc are ignored). May be used multiple times 
 320 to ignore multiple directories. For example, mason users may wish to include 
 321 B<--ignore-dir=data>. The B<--noignore-dir> option allows users to search 
 322 directories which would normally be ignored (perhaps to research the contents 
 323 of F<.svn/props> directories). 
 325 The I<DIRNAME> must always be a simple directory name. Nested directories like 
 326 F<foo/bar> are NOT supported. You would need to specify B<--ignore-dir=foo> and 
 327 then no files from any foo directory are taken into account by ack unless given 
 328 explicitly on the command line. 
 330 =item B<--line=I<NUM>> 
 332 Only print line I<NUM> of each file. Multiple lines can be given with multiple 
 333 B<--line> options or as a comma separated list (B<--line=3,5,7>). B<--line=4-7> 
 334 also works. The lines are always output in ascending order, no matter the 
 335 order given on the command line. 
 337 =item B<-l>, B<--files-with-matches> 
 339 Only print the filenames of matching files, instead of the matching text. 
 341 =item B<-L>, B<--files-without-matches> 
 343 Only print the filenames of files that do I<NOT> match. This is equivalent 
 344 to specifying B<-l> and B<-v>. 
 346 =item B<--match I<REGEX>> 
 348 Specify the I<REGEX> explicitly. This is helpful if you don't want to put the 
 349 regex as your first argument, e.g. when executing multiple searches over the 
 352     # search for foo and bar in given files 
 353     ack file1 t/file* --match foo 
 354     ack file1 t/file* --match bar 
 356 =item B<-m=I<NUM>>, B<--max-count=I<NUM>> 
 358 Stop reading a file after I<NUM> matches. 
 362 Print this manual page. 
 364 =item B<-n>, B<--no-recurse> 
 366 No descending into subdirectories. 
 370 Show only the part of each line matching PATTERN (turns off text 
 373 =item B<--output=I<expr>> 
 375 Output the evaluation of I<expr> for each line (turns off text 
 378 =item B<--pager=I<program>> 
 380 Direct ack's output through I<program>.  This can also be specified 
 381 via the C<ACK_PAGER> and C<ACK_PAGER_COLOR> environment variables. 
 383 Using --pager does not suppress grouping and coloring like piping 
 384 output on the command-line does. 
 388 Prints all lines, whether or not they match the expression.  Highlighting 
 389 will still work, though, so it can be used to highlight matches while 
 390 still seeing the entire file, as in: 
 392     # Watch a log file, and highlight a certain IP address 
 393     $ tail -f ~/access.log | ack --passthru 123.45.67.89 
 397 Only works in conjunction with -f, -g, -l or -c (filename output). The filenames 
 398 are output separated with a null byte instead of the usual newline. This is 
 399 helpful when dealing with filenames that contain whitespace, e.g. 
 401     # remove all files of type html 
 402     ack -f --html --print0 | xargs -0 rm -f 
 404 =item B<-Q>, B<--literal> 
 406 Quote all metacharacters in PATTERN, it is treated as a literal. 
 408 This applies only to the PATTERN, not to the regexes given for the B<-g> 
 411 =item B<-r>, B<-R>, B<--recurse> 
 413 Recurse into sub-directories. This is the default and just here for 
 414 compatibility with grep. You can also use it for turning B<--no-recurse> off. 
 416 =item B<--smart-case>, B<--no-smart-case> 
 418 Ignore case in the search strings if PATTERN contains no uppercase 
 419 characters. This is similar to C<smartcase> in vim. This option is 
 422 B<-i> always overrides this option. 
 424 This applies only to the PATTERN, not to the regexes given for the 
 425 B<-g> and B<-G> options. 
 427 =item B<--sort-files> 
 429 Sorts the found files lexically.  Use this if you want your file 
 430 listings to be deterministic between runs of I<ack>. 
 432 =item B<--show-types> 
 434 Outputs the filetypes that ack associates with each file. 
 436 Works with B<-f> and B<-g> options. 
 440 Display the all-important Bill The Cat logo.  Note that the exact 
 441 spelling of B<--thpppppt> is not important.  It's checked against 
 442 a regular expression. 
 444 =item B<--type=TYPE>, B<--type=noTYPE> 
 446 Specify the types of files to include or exclude from a search. 
 447 TYPE is a filetype, like I<perl> or I<xml>.  B<--type=perl> can 
 448 also be specified as B<--perl>, and B<--type=noperl> can be done 
 451 If a file is of both type "foo" and "bar", specifying --foo and 
 452 --nobar will exclude the file, because an exclusion takes precedence 
 455 Type specifications can be repeated and are ORed together. 
 457 See I<ack --help=types> for a list of valid types. 
 459 =item B<--type-add I<TYPE>=I<.EXTENSION>[,I<.EXT2>[,...]]> 
 461 Files with the given EXTENSION(s) are recognized as being of (the 
 462 existing) type TYPE. See also L</"Defining your own types">. 
 465 =item B<--type-set I<TYPE>=I<.EXTENSION>[,I<.EXT2>[,...]]> 
 467 Files with the given EXTENSION(s) are recognized as being of type 
 468 TYPE. This replaces an existing definition for type TYPE.  See also 
 469 L</"Defining your own types">. 
 471 =item B<-u>, B<--unrestricted> 
 473 All files and directories (including blib/, core.*, ...) are searched, 
 474 nothing is skipped. When both B<-u> and B<--ignore-dir> are used, the 
 475 B<--ignore-dir> option has no effect. 
 477 =item B<-v>, B<--invert-match> 
 479 Invert match: select non-matching lines 
 481 This applies only to the PATTERN, not to the regexes given for the B<-g> 
 486 Display version and copyright information. 
 488 =item B<-w>, B<--word-regexp> 
 490 Force PATTERN to match only whole words.  The PATTERN is wrapped with 
 491 C<\b> metacharacters. 
 493 This applies only to the PATTERN, not to the regexes given for the B<-g> 
 498 Stops after reporting first match of any kind.  This is different 
 499 from B<--max-count=1> or B<-m1>, where only one match per file is 
 500 shown.  Also, B<-1> works with B<-f> and B<-g>, where B<-m> does 
 505 =head1 THE .ackrc FILE 
 507 The F<.ackrc> file contains command-line options that are prepended 
 508 to the command line before processing.  Multiple options may live 
 509 on multiple lines.  Lines beginning with a # are ignored.  A F<.ackrc> 
 510 might look like this: 
 512     # Always sort the files 
 515     # Always color, even if piping to a another program 
 518     # Use "less -r" as my pager 
 521 Note that arguments with spaces in them do not need to be quoted, 
 522 as they are not interpreted by the shell. Basically, each I<line> 
 523 in the F<.ackrc> file is interpreted as one element of C<@ARGV>. 
 525 F<ack> looks in your home directory for the F<.ackrc>.  You can 
 526 specify another location with the F<ACKRC> variable, below. 
 528 If B<--noenv> is specified on the command line, the F<.ackrc> file 
 531 =head1 Defining your own types 
 533 ack allows you to define your own types in addition to the predefined 
 534 types. This is done with command line options that are best put into 
 535 an F<.ackrc> file - then you do not have to define your types over and 
 536 over again. In the following examples the options will always be shown 
 537 on one command line so that they can be easily copy & pasted. 
 539 I<ack --perl foo> searches for foo in all perl files. I<ack --help=types> 
 540 tells you, that perl files are files ending 
 541 in .pl, .pm, .pod or .t. So what if you would like to include .xs 
 542 files as well when searching for --perl files? I<ack --type-add perl=.xs --perl foo> 
 543 does this for you. B<--type-add> appends 
 544 additional extensions to an existing type. 
 546 If you want to define a new type, or completely redefine an existing 
 547 type, then use B<--type-set>. I<ack --type-set 
 548 eiffel=.e,.eiffel> defines the type I<eiffel> to include files with 
 549 the extensions .e or .eiffel. So to search for all eiffel files 
 550 containing the word Bertrand use I<ack --type-set eiffel=.e,.eiffel --eiffel Bertrand>. 
 551 As usual, you can also write B<--type=eiffel> 
 552 instead of B<--eiffel>. Negation also works, so B<--noeiffel> excludes 
 553 all eiffel files from a search. Redefining also works: I<ack --type-set cc=.c,.h> 
 554 and I<.xs> files no longer belong to the type I<cc>. 
 556 When defining your own types in the F<.ackrc> file you have to use 
 559   --type-set=eiffel=.e,.eiffel 
 561 or writing on separate lines 
 566 The following does B<NOT> work in the F<.ackrc> file: 
 568   --type-set eiffel=.e,.eiffel 
 571 In order to see all currently defined types, use I<--help types>, e.g. 
 572 I<ack --type-set backup=.bak --type-add perl=.perl --help types> 
 580 The types 'skipped', 'make', 'binary' and 'text' are considered "builtin" and 
 585 The shebang line recognition of the types 'perl', 'ruby', 'php', 'python', 
 586 'shell' and 'xml' cannot be redefined by I<--type-set>, it is always 
 587 active. However, the shebang line is only examined for files where the 
 588 extension is not recognised. Therefore it is possible to say 
 589 I<ack --type-set perl=.perl --type-set foo=.pl,.pm,.pod,.t --perl --nofoo> and 
 590 only find your shiny new I<.perl> files (and all files with unrecognized extension 
 591 and perl on the shebang line). 
 595 =head1 ENVIRONMENT VARIABLES 
 597 For commonly-used ack options, environment variables can make life much easier. 
 598 These variables are ignored if B<--noenv> is specified on the command line. 
 604 Specifies the location of the F<.ackrc> file.  If this file doesn't 
 605 exist, F<ack> looks in the default location. 
 609 This variable specifies default options to be placed in front of 
 610 any explicit options on the command line. 
 612 =item ACK_COLOR_FILENAME 
 614 Specifies the color of the filename when it's printed in B<--group> 
 615 mode.  By default, it's "bold green". 
 617 The recognized attributes are clear, reset, dark, bold, underline, 
 618 underscore, blink, reverse, concealed black, red, green, yellow, 
 619 blue, magenta, on_black, on_red, on_green, on_yellow, on_blue, 
 620 on_magenta, on_cyan, and on_white.  Case is not significant. 
 621 Underline and underscore are equivalent, as are clear and reset. 
 622 The color alone sets the foreground color, and on_color sets the 
 625 This option can also be set with B<--color-filename>. 
 627 =item ACK_COLOR_MATCH 
 629 Specifies the color of the matching text when printed in B<--color> 
 630 mode.  By default, it's "black on_yellow". 
 632 This option can also be set with B<--color-match>. 
 634 See B<ACK_COLOR_FILENAME> for the color specifications. 
 636 =item ACK_COLOR_LINENO 
 638 Specifies the color of the line number when printed in B<--color> 
 639 mode.  By default, it's "bold yellow". 
 641 This option can also be set with B<--color-lineno>. 
 643 See B<ACK_COLOR_FILENAME> for the color specifications. 
 647 Specifies a pager program, such as C<more>, C<less> or C<most>, to which 
 648 ack will send its output. 
 650 Using C<ACK_PAGER> does not suppress grouping and coloring like 
 651 piping output on the command-line does, except that on Windows 
 652 ack will assume that C<ACK_PAGER> does not support color. 
 654 C<ACK_PAGER_COLOR> overrides C<ACK_PAGER> if both are specified. 
 656 =item ACK_PAGER_COLOR 
 658 Specifies a pager program that understands ANSI color sequences. 
 659 Using C<ACK_PAGER_COLOR> does not suppress grouping and coloring 
 660 like piping output on the command-line does. 
 662 If you are not on Windows, you never need to use C<ACK_PAGER_COLOR>. 
 666 =head1 ACK & OTHER TOOLS 
 668 =head2 Vim integration 
 670 F<ack> integrates easily with the Vim text editor. Set this in your 
 671 F<.vimrc> to use F<ack> instead of F<grep>: 
 675 That examples uses C<-a> to search through all files, but you may 
 676 use other default flags. Now you can search with F<ack> and easily 
 677 step through the results in Vim: 
 681 =head2 Emacs integration 
 683 Phil Jackson put together an F<ack.el> extension that "provides a 
 684 simple compilation mode ... has the ability to guess what files you 
 685 want to search for based on the major-mode." 
 687 L<http://www.shellarchive.co.uk/content/emacs.html> 
 689 =head2 TextMate integration 
 691 Pedro Melo is a TextMate user who writes "I spend my day mostly 
 692 inside TextMate, and the built-in find-in-project sucks with large 
 693 projects.  So I hacked a TextMate command that was using find + 
 694 grep to use ack.  The result is the Search in Project with ack, and 
 695 you can find it here: 
 696 L<http://www.simplicidade.org/notes/archives/2008/03/search_in_proje.html>" 
 698 =head2 Shell and Return Code 
 700 For greater compatibility with I<grep>, I<ack> in normal use returns 
 701 shell return or exit code of 0 only if something is found and 1 if 
 704 (Shell exit code 1 is C<$?=256> in perl with C<system> or backticks.) 
 706 The I<grep> code 2 for errors is not used. 
 708 If C<-f> or C<-g> are specified, then 0 is returned if at least one 
 709 file is found.  If no files are found, then 1 is returned. 
 713 =head1 DEBUGGING ACK PROBLEMS 
 715 If ack gives you output you're not expecting, start with a few simple steps. 
 717 =head2 Use B<--noenv> 
 719 Your environment variables and F<.ackrc> may be doing things you're 
 720 not expecting, or forgotten you specified.  Use B<--noenv> to ignore 
 721 your environment and F<.ackrc>. 
 723 =head2 Use B<-f> to see what files you're scanning 
 725 The reason I created B<-f> in the first place was as a debugging 
 726 tool.  If ack is not finding matches you think it should find, run 
 727 F<ack -f> to see what files are being checked. 
 731 =head2 Use the F<.ackrc> file. 
 733 The F<.ackrc> is the place to put all your options you use most of 
 734 the time but don't want to remember.  Put all your --type-add and 
 735 --type-set definitions in it.  If you like --smart-case, set it 
 736 there, too.  I also set --sort-files there. 
 738 =head2 Use F<-f> for working with big codesets 
 740 Ack does more than search files.  C<ack -f --perl> will create a 
 741 list of all the Perl files in a tree, ideal for sending into F<xargs>. 
 744     # Change all "this" to "that" in all Perl files in a tree. 
 745     ack -f --perl | xargs perl -p -i -e's/this/that/g' 
 749     perl -p -i -e's/this/thatg/' $(ack -f --perl) 
 751 =head2 Use F<-Q> when in doubt about metacharacters 
 753 If you're searching for something with a regular expression 
 754 metacharacter, most often a period in a filename or IP address, add 
 755 the -Q to avoid false positives without all the backslashing.  See 
 756 the following example for more... 
 758 =head2 Use ack to watch log files 
 760 Here's one I used the other day to find trouble spots for a website 
 761 visitor.  The user had a problem loading F<troublesome.gif>, so I 
 762 took the access log and scanned it with ack twice. 
 764     ack -Q aa.bb.cc.dd /path/to/access.log | ack -Q -B5 troublesome.gif 
 766 The first ack finds only the lines in the Apache log for the given 
 767 IP.  The second finds the match on my troublesome GIF, and shows 
 768 the previous five lines from the log in each case. 
 770 =head2 Share your knowledge 
 772 Join the ack-users mailing list.  Send me your tips and I may add 
 777 =head2 Why isn't ack finding a match in (some file)? 
 779 Probably because it's of a type that ack doesn't recognize.  ack's 
 780 searching behavior is driven by filetype.  B<If ack doesn't know 
 781 what kind of file it is, ack ignores the file.> 
 783 Use the C<-f> switch to see a list of files that ack will search 
 786 If you want ack to search files that it doesn't recognize, use the 
 789 If you want ack to search every file, even ones that it always 
 790 ignores like coredumps and backup files, use the C<-u> switch. 
 792 =head2 Why does ack ignore unknown files by default? 
 794 ack is designed by a programmer, for programmers, for searching 
 795 large trees of code.  Most codebases have a lot files in them which 
 796 aren't source files (like compiled object files, source control 
 797 metadata, etc), and grep wastes a lot of time searching through all 
 798 of those as well and returning matches from those files. 
 800 That's why ack's behavior of not searching things it doesn't recognize 
 801 is one of its greatest strengths: the speed you get from only 
 802 searching the things that you want to be looking at. 
 804 =head2 Wouldn't it be great if F<ack> did search & replace? 
 806 No, ack will always be read-only.  Perl has a perfectly good way 
 807 to do search & replace in files, using the C<-i>, C<-p> and C<-n> 
 810 You can certainly use ack to select your files to update.  For 
 811 example, to change all "foo" to "bar" in all PHP files, you can do 
 812 this from the Unix shell: 
 814     $ perl -i -p -e's/foo/bar/g' $(ack -f --php) 
 816 =head2 Can you make ack recognize F<.xyz> files? 
 818 That's an enhancement.  Please see the section in the manual about 
 821 =head2 There's already a program/package called ack. 
 825 =head2 Why is it called ack if it's called ack-grep? 
 827 The name of the program is "ack".  Some packagers have called it 
 828 "ack-grep" when creating packages because there's already a package 
 829 out there called "ack" that has nothing to do with this ack. 
 831 I suggest you make a symlink named F<ack> that points to F<ack-grep> 
 832 because one of the crucial benefits of ack is having a name that's 
 833 so short and simple to type. 
 835 To do that, run this with F<sudo> or as root: 
 837    ln -s /usr/bin/ack-grep /usr/bin/ack 
 839 =head2 What does F<ack> mean? 
 841 Nothing.  I wanted a name that was easy to type and that you could 
 842 pronounce as a single syllable. 
 844 =head2 Can I do multi-line regexes? 
 846 No, ack does not support regexes that match multiple lines.  Doing 
 847 so would require reading in the entire file at a time. 
 849 If you want to see lines near your match, use the C<--A>, C<--B> 
 850 and C<--C> switches for displaying context. 
 854 Andy Lester, C<< <andy at petdance.com> >> 
 858 Please report any bugs or feature requests to the issues list at 
 859 Github: L<https://github.com/petdance/ack/issues> 
 863 All enhancement requests MUST first be posted to the ack-users 
 864 mailing list at L<http://groups.google.com/group/ack-users>.  I 
 865 will not consider a request without it first getting seen by other 
 866 ack users.  This includes requests for new filetypes. 
 868 There is a list of enhancements I want to make to F<ack> in the ack 
 869 issues list at Github: L<https://github.com/petdance/ack/issues> 
 871 Patches are always welcome, but patches with tests get the most 
 876 Support for and information about F<ack> can be found at: 
 880 =item * The ack homepage 
 882 L<http://betterthangrep.com/> 
 884 =item * The ack issues list at Github 
 886 L<https://github.com/petdance/ack/issues> 
 888 =item * AnnoCPAN: Annotated CPAN documentation 
 890 L<http://annocpan.org/dist/ack> 
 894 L<http://cpanratings.perl.org/d/ack> 
 898 L<http://search.cpan.org/dist/ack> 
 900 =item * Git source repository 
 902 L<https://github.com/petdance/ack> 
 906 =head1 ACKNOWLEDGEMENTS 
 908 How appropriate to have I<ack>nowledgements! 
 910 Thanks to everyone who has contributed to ack in any way, including 
 933 Christopher J. Madsen, 
 945 GE<aacute>bor SzabE<oacute>, 
 948 E<AElig>var ArnfjE<ouml>rE<eth> Bjarmason, 
 952 Mark Leighton Fisher, 
 963 Ask BjE<oslash>rn Hansen, 
 976 =head1 COPYRIGHT & LICENSE 
 978 Copyright 2005-2011 Andy Lester. 
 980 This program is free software; you can redistribute it and/or modify 
 981 it under the terms of the Artistic License v2.0. 
 990 our $VERSION = '1.06'; 
 997 our $name; # name of the current file 
 998 our $dir;  # dir of the current file 
1000 our %files_defaults; 
1005         file_filter     
=> undef, 
1006         descend_filter  
=> undef, 
1007         error_handler   
=> sub { CORE
::die @_ }, 
1008         sort_files      
=> undef, 
1009         follow_symlinks 
=> 1, 
1011     %skip_dirs = map {($_,1)} (File
::Spec-
>curdir, File
::Spec-
>updir); 
1016     ($_[0] eq __PACKAGE__
) && die 'File::Next::files must not be invoked as File::Next->files'; 
1018     my ($parms,@queue) = _setup
( \
%files_defaults, @_ ); 
1019     my $filter = $parms->{file_filter
}; 
1023             my ($dir,$file,$fullpath) = splice( @queue, 0, 3 ); 
1024             if ( -f 
$fullpath ) { 
1027                     local $File::Next
::dir 
= $dir; 
1028                     local $File::Next
::name 
= $fullpath; 
1029                     next if not $filter->(); 
1031                 return wantarray ? ($dir,$file,$fullpath) : $fullpath; 
1034                 unshift( @queue, _candidate_files
( $parms, $fullpath ) ); 
1048 sub sort_standard
($$)   { return $_[0]->[1] cmp $_[1]->[1] } 
1049 sub sort_reverse
($$)    { return $_[1]->[1] cmp $_[0]->[1] } 
1054     my @parts = split( /\//, $path ); 
1056     return $path if @parts < 2; 
1058     return File
::Spec-
>catfile( @parts ); 
1064     my $defaults = shift; 
1065     my $passed_parms = ref $_[0] eq 'HASH' ? {%{+shift}} : {}; # copy parm hash 
1067     my %passed_parms = %{$passed_parms}; 
1070     for my $key ( keys %{$defaults} ) { 
1072             exists $passed_parms{$key} 
1073                 ? delete $passed_parms{$key} 
1074                 : $defaults->{$key}; 
1077     # Any leftover keys are bogus 
1078     for my $badkey ( keys %passed_parms ) { 
1079         my $sub = (caller(1))[3]; 
1080         $parms->{error_handler
}->( "Invalid option passed to $sub(): $badkey" ); 
1083     # If it's not a code ref, assume standard sort 
1084     if ( $parms->{sort_files
} && ( ref($parms->{sort_files
}) ne 'CODE' ) ) { 
1085         $parms->{sort_files
} = \
&sort_standard
; 
1090         my $start = reslash
( $_ ); 
1092             push @queue, ($start,undef,$start); 
1095             push @queue, (undef,$start,$start); 
1099     return ($parms,@queue); 
1103 sub _candidate_files 
{ 
1108     if ( !opendir $dh, $dir ) { 
1109         $parms->{error_handler
}->( "$dir: $!" ); 
1114     my $descend_filter = $parms->{descend_filter
}; 
1115     my $follow_symlinks = $parms->{follow_symlinks
}; 
1116     my $sort_sub = $parms->{sort_files
}; 
1118     for my $file ( grep { !exists $skip_dirs{$_} } readdir $dh ) { 
1121         # Only do directory checking if we have a descend_filter 
1122         my $fullpath = File
::Spec-
>catdir( $dir, $file ); 
1123         if ( !$follow_symlinks ) { 
1124             next if -l 
$fullpath; 
1128         if ( $descend_filter ) { 
1129             if ( $has_stat ? (-d _
) : (-d 
$fullpath) ) { 
1130                 local $File::Next
::dir 
= $fullpath; 
1132                 next if not $descend_filter->(); 
1136             push( @newfiles, [ $dir, $file, $fullpath ] ); 
1139             push( @newfiles, $dir, $file, $fullpath ); 
1145         return map { @{$_} } sort $sort_sub @newfiles; 
1152 1; # End of File::Next 
1165     $COPYRIGHT = 'Copyright 2005-2011 Andy Lester.'; 
1180 our $input_from_pipe; 
1181 our $output_to_pipe; 
1188 use File
::Glob 
':glob'; 
1189 use Getopt
::Long 
(); 
1194         '.cdv'              => 'Codeville', 
1195         '~.dep'             => 'Interface Builder', 
1196         '~.dot'             => 'Interface Builder', 
1197         '~.nib'             => 'Interface Builder', 
1198         '~.plst'            => 'Interface Builder', 
1200         '.hg'               => 'Mercurial', 
1202         '.svn'              => 'Subversion', 
1204         blib                
=> 'Perl module building', 
1209         _sgbak              
=> 'Vault/Fortress', 
1210         'autom4te.cache'    => 'autoconf', 
1211         'cover_db'          => 'Devel::Cover', 
1212         _build              
=> 'Module::Build', 
1216         actionscript 
=> [qw( as mxml )], 
1217         ada         
=> [qw( ada adb ads )], 
1218         asm         
=> [qw( asm s )], 
1219         batch       
=> [qw( bat cmd )], 
1220         binary      
=> q{Binary files, as defined by Perl's -B op (default: off)}, 
1221         cc          
=> [qw( c h xs )], 
1222         cfmx        
=> [qw( cfc cfm cfml )], 
1223         clojure     
=> [qw( clj )], 
1224         cpp         
=> [qw( cpp cc cxx m hpp hh h hxx )], 
1225         csharp      
=> [qw( cs )], 
1227         delphi      
=> [qw( pas int dfm nfm dof dpk dproj groupproj bdsgroup bdsproj )], 
1228         elisp       
=> [qw( el )], 
1229         erlang      
=> [qw( erl hrl )], 
1230         fortran     
=> [qw( f f77 f90 f95 f03 for ftn fpp )], 
1232         groovy      
=> [qw( groovy gtmpl gpp grunit )], 
1233         haskell     
=> [qw( hs lhs )], 
1235         html        
=> [qw( htm html shtml xhtml )], 
1236         java        
=> [qw( java properties )], 
1238         jsp         
=> [qw( jsp jspx jhtm jhtml )], 
1239         lisp        
=> [qw( lisp lsp )], 
1241         make        
=> q{Makefiles (including *.mk and *.mak)}, 
1242         mason       
=> [qw( mas mhtml mpl mtxt )], 
1243         objc        
=> [qw( m h )], 
1244         objcpp      
=> [qw( mm h )], 
1245         ocaml       
=> [qw( ml mli )], 
1246         parrot      
=> [qw( pir pasm pmc ops pod pg tg )], 
1247         perl        
=> [qw( pl pm pm6 pod t )], 
1248         php         
=> [qw( php phpt php3 php4 php5 phtml)], 
1249         plone       
=> [qw( pt cpt metadata cpy py )], 
1250         python      
=> [qw( py )], 
1251         rake        
=> q{Rakefiles}, 
1252         ruby        
=> [qw( rb rhtml rjs rxml erb rake spec )], 
1253         scala       
=> [qw( scala )], 
1254         scheme      
=> [qw( scm ss )], 
1255         shell       
=> [qw( sh bash csh tcsh ksh zsh )], 
1256         skipped     
=> q{Files, but not directories, normally skipped by ack (default: off)}, 
1257         smalltalk   
=> [qw( st )], 
1258         sql         
=> [qw( sql ctl )], 
1259         tcl         
=> [qw( tcl itcl itk )], 
1260         tex         
=> [qw( tex cls sty )], 
1261         text        
=> q{Text files, as defined by Perl's -T op (default: off)}, 
1262         tt          
=> [qw( tt tt2 ttml )], 
1263         vb          
=> [qw( bas cls frm ctl vb resx )], 
1264         verilog     
=> [qw( v vh sv )], 
1265         vhdl        
=> [qw( vhd vhdl )], 
1267         yaml        
=> [qw( yaml yml )], 
1268         xml         
=> [qw( xml dtd xsl xslt ent )], 
1271     while ( my ($type,$exts) = each %mappings ) { 
1273             for my $ext ( @{$exts} ) { 
1274                 push( @{$types{$ext}}, $type ); 
1278     # add manually Makefile extensions 
1279     push @{$types{$_}}, 'make' for qw{ mk mak }; 
1281     # These have to be checked before any filehandle diddling. 
1282     $output_to_pipe  = not -t 
*STDOUT
; 
1283     $input_from_pipe = -p STDIN
; 
1285     $is_cygwin       = ($^O eq 'cygwin'); 
1286     $is_windows      = ($^O =~ /MSWin32/); 
1287     $dir_sep_chars   = $is_windows ? quotemeta( '\\/' ) : quotemeta( File
::Spec-
>catfile( '', '' ) ); 
1292     my @files = ( $ENV{ACKRC
} ); 
1295             ? ( $ENV{HOME
}, $ENV{USERPROFILE
} ) 
1296             : ( '~', $ENV{HOME
} ); 
1297     for my $dir ( grep { defined } @dirs ) { 
1298         for my $file ( '.ackrc', '_ackrc' ) { 
1299             push( @files, bsd_glob
( "$dir/$file", GLOB_TILDE 
) ); 
1302     for my $filename ( @files ) { 
1303         if ( defined $filename && -e 
$filename ) { 
1304             open( my $fh, '<', $filename ) or App
::Ack
::die( "$filename: $!\n" ); 
1305             my @lines = grep { /./ && !/^\s*#/ } <$fh>; 
1307             close $fh or App
::Ack
::die( "$filename: $!\n" ); 
1309             # get rid of leading and trailing whitespaces 
1323 sub get_command_line_options 
{ 
1325         pager 
=> $ENV{ACK_PAGER_COLOR
} || $ENV{ACK_PAGER
}, 
1328     my $getopt_specs = { 
1329         1                       => sub { $opt{1} = $opt{m
} = 1 }, 
1330         'A|after-context=i'     => \
$opt{after_context
}, 
1331         'B|before-context=i'    => \
$opt{before_context
}, 
1332         'C|context:i'           => sub { shift; my $val = shift; $opt{before_context
} = $opt{after_context
} = ($val || 2) }, 
1333         'a|all-types'           => \
$opt{all
}, 
1334         'break!'                => \
$opt{break}, 
1336         'color|colour!'         => \
$opt{color
}, 
1337         'color-match=s'         => \
$ENV{ACK_COLOR_MATCH
}, 
1338         'color-filename=s'      => \
$ENV{ACK_COLOR_FILENAME
}, 
1339         'color-lineno=s'        => \
$ENV{ACK_COLOR_LINENO
}, 
1340         'column!'               => \
$opt{column
}, 
1341         count                   
=> \
$opt{count
}, 
1342         'env!'                  => sub { }, # ignore this option, it is handled beforehand 
1344         flush                   
=> \
$opt{flush
}, 
1345         'follow!'               => \
$opt{follow
}, 
1346         'g=s'                   => sub { shift; $opt{G
} = shift; $opt{f
} = 1 }, 
1348         'group!'                => sub { shift; $opt{heading
} = $opt{break} = shift }, 
1349         'heading!'              => \
$opt{heading
}, 
1350         'h|no-filename'         => \
$opt{h
}, 
1351         'H|with-filename'       => \
$opt{H
}, 
1352         'i|ignore-case'         => \
$opt{i
}, 
1353         'invert-file-match'     => \
$opt{invert_file_match
}, 
1354         'lines=s'               => sub { shift; my $val = shift; push @{$opt{lines
}}, $val }, 
1355         'l|files-with-matches'  => \
$opt{l
}, 
1356         'L|files-without-matches' => sub { $opt{l
} = $opt{v
} = 1 }, 
1357         'm|max-count=i'         => \
$opt{m
}, 
1358         'match=s'               => \
$opt{regex
}, 
1359         'n|no-recurse'          => \
$opt{n
}, 
1360         o                       
=> sub { $opt{output
} = '$&' }, 
1361         'output=s'              => \
$opt{output
}, 
1362         'pager=s'               => \
$opt{pager
}, 
1363         'nopager'               => sub { $opt{pager
} = undef }, 
1364         'passthru'              => \
$opt{passthru
}, 
1365         'print0'                => \
$opt{print0
}, 
1366         'Q|literal'             => \
$opt{Q
}, 
1367         'r|R|recurse'           => sub { $opt{n
} = 0 }, 
1368         'show-types'            => \
$opt{show_types
}, 
1369         'smart-case!'           => \
$opt{smart_case
}, 
1370         'sort-files'            => \
$opt{sort_files
}, 
1371         'u|unrestricted'        => \
$opt{u
}, 
1372         'v|invert-match'        => \
$opt{v
}, 
1373         'w|word-regexp'         => \
$opt{w
}, 
1375         'ignore-dirs=s'         => sub { shift; my $dir = remove_dir_sep
( shift ); $ignore_dirs{$dir} = '--ignore-dirs' }, 
1376         'noignore-dirs=s'       => sub { shift; my $dir = remove_dir_sep
( shift ); delete $ignore_dirs{$dir} }, 
1378         'version'   => sub { print_version_statement
(); exit; }, 
1379         'help|?:s'  => sub { shift; show_help
(@_); exit; }, 
1380         'help-types'=> sub { show_help_types
(); exit; }, 
1383             Pod
::Usage
::pod2usage
({ 
1390             # Whatever --type=xxx they specify, set it manually in the hash 
1393             my $wanted = ($type =~ s/^no//) ? 0 : 1; # must not be undef later 
1395             if ( exists $type_wanted{ $type } ) { 
1396                 $type_wanted{ $type } = $wanted; 
1399                 App
::Ack
::die( qq{Unknown --type "$type"} ); 
1404     # Stick any default switches at the beginning, so they can be overridden 
1405     # by the command line switches. 
1406     unshift @ARGV, split( ' ', $ENV{ACK_OPTIONS
} ) if defined $ENV{ACK_OPTIONS
}; 
1408     # first pass through options, looking for type definitions 
1409     def_types_from_ARGV
(); 
1411     for my $i ( filetypes_supported
() ) { 
1412         $getopt_specs->{ "$i!" } = \
$type_wanted{ $i }; 
1416     my $parser = Getopt
::Long
::Parser-
>new(); 
1417     $parser->configure( 'bundling', 'no_ignore_case', ); 
1418     $parser->getoptions( %{$getopt_specs} ) or 
1419         App
::Ack
::die( 'See ack --help, ack --help-types or ack --man for options.' ); 
1421     my $to_screen = not output_to_pipe
(); 
1424         color          
=> $to_screen, 
1426         break          => $to_screen, 
1427         heading        
=> $to_screen, 
1428         before_context 
=> 0, 
1431     if ( $is_windows && $defaults{color
} && not $ENV{ACK_PAGER_COLOR
} ) { 
1432         if ( $ENV{ACK_PAGER
} || not eval { require Win32
::Console
::ANSI 
} ) { 
1433             $defaults{color
} = 0; 
1436     if ( $to_screen && $ENV{ACK_PAGER_COLOR
} ) { 
1437         $defaults{color
} = 1; 
1440     while ( my ($key,$value) = each %defaults ) { 
1441         if ( not defined $opt{$key} ) { 
1442             $opt{$key} = $value; 
1446     if ( defined $opt{m
} && $opt{m
} <= 0 ) { 
1447         App
::Ack
::die( '-m must be greater than zero' ); 
1450     for ( qw( before_context after_context ) ) { 
1451         if ( defined $opt{$_} && $opt{$_} < 0 ) { 
1452             App
::Ack
::die( "--$_ may not be negative" ); 
1456     if ( defined( my $val = $opt{output
} ) ) { 
1457         $opt{output
} = eval qq[ sub { "$val" } ]; 
1459     if ( defined( my $l = $opt{lines
} ) ) { 
1460         # --line=1 --line=5 is equivalent to --line=1,5 
1461         my @lines = split( /,/, join( ',', @{$l} ) ); 
1463         # --line=1-3 is equivalent to --line=1,2,3 
1467                 my ($from, $to) = split /-/, $_; 
1468                 if ( $from > $to ) { 
1469                     App
::Ack
::warn( "ignoring --line=$from-$to" ); 
1473                     @ret = ( $from .. $to ); 
1484             @uniq{ @lines } = (); 
1485             $opt{lines
} = [ sort { $a <=> $b } keys %uniq ];   # numerical sort and each line occurs only once! 
1488             # happens if there are only ignored --line directives 
1489             App
::Ack
::die( 'All --line options are invalid.' ); 
1497 sub def_types_from_ARGV 
{ 
1500     my $parser = Getopt
::Long
::Parser-
>new(); 
1501         # pass_through   => leave unrecognized command line arguments alone 
1502         # no_auto_abbrev => otherwise -c is expanded and not left alone 
1503     $parser->configure( 'no_ignore_case', 'pass_through', 'no_auto_abbrev' ); 
1504     $parser->getoptions( 
1505         'type-set=s' => sub { shift; push @typedef, ['c', shift] }, 
1506         'type-add=s' => sub { shift; push @typedef, ['a', shift] }, 
1507     ) or App
::Ack
::die( 'See ack --help or ack --man for options.' ); 
1509     for my $td (@typedef) { 
1510         my ($type, $ext) = split /=/, $td->[1]; 
1512         if ( $td->[0] eq 'c' ) { 
1514             if ( exists $mappings{$type} ) { 
1515                 # can't redefine types 'make', 'skipped', 'text' and 'binary' 
1516                 App
::Ack
::die( qq{--type-set: Builtin type "$type" cannot be changed.} ) 
1517                     if ref $mappings{$type} ne 'ARRAY'; 
1525             # can't append to types 'make', 'skipped', 'text' and 'binary' 
1526             App
::Ack
::die( qq{--type-add: Builtin type "$type" cannot be changed.} ) 
1527                 if exists $mappings{$type} && ref $mappings{$type} ne 'ARRAY'; 
1529             App
::Ack
::warn( qq{--type-add: Type "$type" does not exist, creating with "$ext" ...} ) 
1530                 unless exists $mappings{$type}; 
1533         my @exts = split /,/, $ext; 
1536         if ( !exists $mappings{$type} || ref($mappings{$type}) eq 'ARRAY' ) { 
1537             push @{$mappings{$type}}, @exts; 
1538             for my $e ( @exts ) { 
1539                 push @{$types{$e}}, $type; 
1543             App
::Ack
::die( qq{Cannot append to type "$type".} ); 
1554     App
::Ack
::die( qq{Internal error: Cannot delete builtin type "$type".} ) 
1555         unless ref $mappings{$type} eq 'ARRAY'; 
1557     delete $mappings{$type}; 
1558     delete $type_wanted{$type}; 
1559     for my $ext ( keys %types ) { 
1560         $types{$ext} = [ grep { $_ ne $type } @{$types{$ext}} ]; 
1565 sub ignoredir_filter 
{ 
1566     return !exists $ignore_dirs{$_} && !exists $ignore_dirs{$File::Next
::dir
}; 
1570 sub remove_dir_sep 
{ 
1572     $path =~ s/[$dir_sep_chars]$//; 
1578 use constant TEXT 
=> 'text'; 
1581     my $filename = shift; 
1583     my $basename = $filename; 
1584     $basename =~ s{.*[$dir_sep_chars]}{}; 
1586     return 'skipped' unless is_searchable
( $basename ); 
1588     my $lc_basename = lc $basename; 
1589     return ('make',TEXT
)        if $lc_basename eq 'makefile' || $lc_basename eq 'gnumakefile'; 
1590     return ('rake','ruby',TEXT
) if $lc_basename eq 'rakefile'; 
1592     # If there's an extension, look it up 
1593     if ( $filename =~ m{\.([^\.$dir_sep_chars]+)$}o ) { 
1594         my $ref = $types{lc $1}; 
1595         return (@{$ref},TEXT
) if $ref; 
1598     # At this point, we can't tell from just the name.  Now we have to 
1599     # open it and look inside. 
1601     return unless -e 
$filename; 
1602     # From Elliot Shank: 
1603     #     I can't see any reason that -r would fail on these-- the ACLs look 
1604     #     fine, and no program has any of them open, so the busted Windows 
1605     #     file locking model isn't getting in there.  If I comment the if 
1606     #     statement out, everything works fine 
1607     # So, for cygwin, don't bother trying to check for readability. 
1608     if ( !$is_cygwin ) { 
1609         if ( !-r 
$filename ) { 
1610             App
::Ack
::warn( "$filename: Permission denied" ); 
1615     return 'binary' if -B 
$filename; 
1617     # If there's no extension, or we don't recognize it, check the shebang line 
1619     if ( !open( $fh, '<', $filename ) ) { 
1620         App
::Ack
::warn( "$filename: $!" ); 
1626     if ( $header =~ /^#!/ ) { 
1627         return ($1,TEXT
)       if $header =~ /\b(ruby|lua|p(?:erl|hp|ython))-?(\d[\d.]*)?\b/; 
1628         return ('shell',TEXT
)  if $header =~ /\b(?:ba|t?c|k|z)?sh\b/; 
1631         return ('xml',TEXT
)    if $header =~ /\Q<?xml /i; 
1639     my $filename = shift; 
1641     # If these are updated, update the --help message 
1642     return if $filename =~ /[.]bak$/; 
1643     return if $filename =~ /~$/; 
1644     return if $filename =~ m{^#.*#$}o; 
1645     return if $filename =~ m{^core\.\d+$}o; 
1646     return if $filename =~ m{[._].*\.swp$}o; 
1647     return if $filename =~ /[.-]min\.js$/; 
1657     defined $str or App
::Ack
::die( 'No regular expression found.' ); 
1659     $str = quotemeta( $str ) if $opt->{Q
}; 
1661         $str = "\\b$str" if $str =~ /^\w/; 
1662         $str = "$str\\b" if $str =~ /\w$/; 
1665     my $regex_is_lc = $str eq lc $str; 
1666     if ( $opt->{i
} || ($opt->{smart_case
} && $regex_is_lc) ) { 
1677     return unless defined $regex; 
1679     eval { qr/$regex/ }; 
1681         (my $error = $@) =~ s/ at \S+ line \d+.*//; 
1683         App
::Ack
::die( "Invalid regex '$regex':\n  $error" ); 
1693     return CORE
::warn( _my_program
(), ': ', @_, "\n" ); 
1698     return CORE
::die( _my_program
(), ': ', @_, "\n" ); 
1702     require File
::Basename
; 
1703     return File
::Basename
::basename
( $0 ); 
1708 sub filetypes_supported 
{ 
1709     return keys %mappings; 
1713     my $y = q{_   /|,\\'!.x',=(www)=,   U   }; 
1714     $y =~ tr/,x!w/\nOo_/; 
1719     my $y = _get_thpppt
(); 
1720     App
::Ack
::print( "$y ack $_[0]!\n" ); 
1726     $str =~ s/[^a-z]//g; 
1733     my $help_arg = shift || 0; 
1735     return show_help_types
() if $help_arg =~ /^types?/; 
1737     my $ignore_dirs = _listify
( sort { _key
($a) cmp _key
($b) } keys %ignore_dirs ); 
1739     App
::Ack
::print( <<"END_OF_HELP" ); 
1740 Usage: ack [OPTION]... PATTERN [FILE] 
1742 Search for PATTERN in each source file in the tree from cwd on down. 
1743 If [FILES] is specified, then only those files/directories are checked. 
1744 ack may also search STDIN, but only if no FILE are specified, or if 
1745 one of FILES is "-". 
1747 Default switches may be specified in ACK_OPTIONS environment variable or 
1748 an .ackrc file. If you want no dependency on the environment, turn it 
1751 Example: ack -i select 
1754   -i, --ignore-case     Ignore case distinctions in PATTERN 
1755   --[no]smart-case      Ignore case distinctions in PATTERN, 
1756                         only if PATTERN contains no upper case 
1757                         Ignored if -i is specified 
1758   -v, --invert-match    Invert match: select non-matching lines 
1759   -w, --word-regexp     Force PATTERN to match only whole words 
1760   -Q, --literal         Quote all metacharacters; PATTERN is literal 
1763   --line=NUM            Only print line(s) NUM of each file 
1764   -l, --files-with-matches 
1765                         Only print filenames containing matches 
1766   -L, --files-without-matches 
1767                         Only print filenames with no matches 
1768   -o                    Show only the part of a line matching PATTERN 
1769                         (turns off text highlighting) 
1770   --passthru            Print all lines, whether matching or not 
1771   --output=expr         Output the evaluation of expr for each line 
1772                         (turns off text highlighting) 
1773   --match PATTERN       Specify PATTERN explicitly. 
1774   -m, --max-count=NUM   Stop searching in each file after NUM matches 
1775   -1                    Stop searching after one match of any kind 
1776   -H, --with-filename   Print the filename for each match 
1777   -h, --no-filename     Suppress the prefixing filename on output 
1778   -c, --count           Show number of lines matching per file 
1779   --column              Show the column number of the first match 
1781   -A NUM, --after-context=NUM 
1782                         Print NUM lines of trailing context after matching 
1784   -B NUM, --before-context=NUM 
1785                         Print NUM lines of leading context before matching 
1787   -C [NUM], --context[=NUM] 
1788                         Print NUM lines (default 2) of output context. 
1790   --print0              Print null byte as separator between filenames, 
1791                         only works with -f, -g, -l, -L or -c. 
1794   --pager=COMMAND       Pipes all ack output through COMMAND.  For example, 
1795                         --pager="less -R".  Ignored if output is redirected. 
1796   --nopager             Do not send output through a pager.  Cancels any 
1797                         setting in ~/.ackrc, ACK_PAGER or ACK_PAGER_COLOR. 
1798   --[no]heading         Print a filename heading above each file's results. 
1799                         (default: on when used interactively) 
1800   --[no]break           Print a break between results from different files. 
1801                         (default: on when used interactively) 
1802   --group               Same as --heading --break 
1803   --nogroup             Same as --noheading --nobreak 
1804   --[no]color           Highlight the matching text (default: on unless 
1805                         output is redirected, or on Windows) 
1806   --[no]colour          Same as --[no]color 
1807   --color-filename=COLOR 
1809   --color-lineno=COLOR  Set the color for filenames, matches, and line numbers. 
1810   --flush               Flush output immediately, even when ack is used 
1811                         non-interactively (when output goes to a pipe or 
1815   -f                    Only print the files found, without searching. 
1816                         The PATTERN must not be specified. 
1817   -g REGEX              Same as -f, but only print files matching REGEX. 
1818   --sort-files          Sort the found files lexically. 
1819   --invert-file-match   Print/search handle files that do not match -g/-G. 
1820   --show-types          Show which types each file has. 
1822 File inclusion/exclusion: 
1823   -a, --all-types       All file types searched; 
1824                         Ignores CVS, .svn and other ignored directories 
1825   -u, --unrestricted    All files and directories searched 
1826   --[no]ignore-dir=name Add/Remove directory from the list of ignored dirs 
1827   -r, -R, --recurse     Recurse into subdirectories (ack's default behavior) 
1828   -n, --no-recurse      No descending into subdirectories 
1829   -G REGEX              Only search files that match REGEX 
1831   --perl                Include only Perl files. 
1832   --type=perl           Include only Perl files. 
1833   --noperl              Exclude Perl files. 
1834   --type=noperl         Exclude Perl files. 
1835                         See "ack --help type" for supported filetypes. 
1837   --type-set TYPE=.EXTENSION[,.EXT2[,...]] 
1838                         Files with the given EXTENSION(s) are recognized as 
1839                         being of type TYPE. This replaces an existing 
1840                         definition for type TYPE. 
1841   --type-add TYPE=.EXTENSION[,.EXT2[,...]] 
1842                         Files with the given EXTENSION(s) are recognized as 
1843                         being of (the existing) type TYPE 
1845   --[no]follow          Follow symlinks.  Default is off. 
1847   Directories ignored by default: 
1850   Files not checked for type: 
1851     /~\$/            - Unix backup files 
1852     /#.+#\$/         - Emacs swap files 
1853     /[._].*\\.swp\$/ - Vi(m) swap files 
1854     /core\\.\\d+\$/  - core dumps 
1855     /[.-]min\\.js\$/  - Minified javascript files 
1858   --noenv               Ignore environment variables and ~/.ackrc 
1861   --version             Display version & copyright 
1862   --thpppt              Bill the Cat 
1864 Exit status is 0 if match, 1 if no match. 
1866 This is version $VERSION of ack. 
1874 sub show_help_types 
{ 
1875     App
::Ack
::print( <<'END_OF_HELP' ); 
1876 Usage: ack [OPTION]... PATTERN [FILES] 
1878 The following is the list of filetypes supported by ack.  You can 
1879 specify a file type with the --type=TYPE format, or the --TYPE 
1880 format.  For example, both --type=perl and --perl work. 
1882 Note that some extensions may appear in multiple types.  For example, 
1883 .pod files are both Perl and Parrot. 
1887     my @types = filetypes_supported
(); 
1890         $maxlen = length if $maxlen < length; 
1892     for my $type ( sort @types ) { 
1893         next if $type =~ /^-/; # Stuff to not show 
1894         my $ext_list = $mappings{$type}; 
1896         if ( ref $ext_list ) { 
1897             $ext_list = join( ' ', map { ".$_" } @{$ext_list} ); 
1899         App
::Ack
::print( sprintf( "    --[no]%-*.*s %s\n", $maxlen, $maxlen, $type, $ext_list ) ); 
1908     return '' if !@whats; 
1910     my $end = pop @whats; 
1911     my $str = @whats ? join( ', ', @whats ) . " and $end" : $end; 
1915     $Text::Wrap
::columns 
= 75; 
1916     return Text
::Wrap
::wrap
( '', '    ', $str ); 
1920 sub get_version_statement 
{ 
1923     my $copyright = get_copyright
(); 
1924     my $this_perl = $Config::Config
{perlpath
}; 
1926         my $ext = $Config::Config
{_exe
}; 
1927         $this_perl .= $ext unless $this_perl =~ m/$ext$/i; 
1929     my $ver = sprintf( '%vd', $^V ); 
1931     return <<"END_OF_VERSION"; 
1933 Running under Perl $ver at $this_perl 
1937 This program is free software.  You may modify or distribute it 
1938 under the terms of the Artistic License v2.0. 
1943 sub print_version_statement 
{ 
1944     App
::Ack
::print( get_version_statement
() ); 
1956     eval 'use Term::ANSIColor ()'; 
1958     $ENV{ACK_COLOR_MATCH
}    ||= 'black on_yellow'; 
1959     $ENV{ACK_COLOR_FILENAME
} ||= 'bold green'; 
1960     $ENV{ACK_COLOR_LINENO
}   ||= 'bold yellow'; 
1966 sub is_interesting 
{ 
1971     for my $type ( filetypes
( $File::Next
::name 
) ) { 
1972         if ( defined $type_wanted{$type} ) { 
1973             if ( $type_wanted{$type} ) { 
1987 # print subs added in order to make it easy for a third party 
1988 # module (such as App::Wack) to redefine the display methods 
1989 # and show the results in a different way. 
1990 sub print                   { print {$fh} @_ } 
1991 sub print_first_filename    
{ App
::Ack
::print( $_[0], "\n" ) } 
1992 sub print_blank_line        
{ App
::Ack
::print( "\n" ) } 
1993 sub print_separator         
{ App
::Ack
::print( "--\n" ) } 
1994 sub print_filename          
{ App
::Ack
::print( $_[0], $_[1] ) } 
1995 sub print_line_no           
{ App
::Ack
::print( $_[0], $_[1] ) } 
1996 sub print_column_no         
{ App
::Ack
::print( $_[0], $_[1] ) } 
1998     my $filename = shift; 
1999     my $nmatches = shift; 
2002     my $show_filename = shift; 
2004     if ($show_filename) { 
2005         App
::Ack
::print( $filename ); 
2006         App
::Ack
::print( ':', $nmatches ) if $count; 
2009         App
::Ack
::print( $nmatches ) if $count; 
2011     App
::Ack
::print( $ors ); 
2015     my $filename = shift; 
2017     my $show_filename = shift; 
2019     if ($show_filename) { 
2020         App
::Ack
::print( $filename, ':0', $ors ); 
2023         App
::Ack
::print( '0', $ors ); 
2032     my $display_filename; 
2036     my $last_output_line;             # number of the last line that has been output 
2037     my $any_output;                   # has there been any output for the current file yet 
2038     my $context_overall_output_count; # has there been any output at all 
2040 sub search_resource 
{ 
2044     $filename = $res->name(); 
2047     my $passthru = $opt->{passthru
}; 
2048     my $max = $opt->{m
}; 
2051     $display_filename = undef; 
2053     # for --line processing 
2056     if ( defined $opt->{lines
} ) { 
2058         @lines = ( @{$opt->{lines
}}, -1 ); 
2059         undef $regex; # Don't match when printing matching line 
2062         $regex = qr/$opt->{regex}/; 
2065     # for context processing 
2066     $last_output_line = -1; 
2068     my $before_context = $opt->{before_context
}; 
2069     my $after_context  = $opt->{after_context
}; 
2071     $keep_context = ($before_context || $after_context) && !$passthru; 
2074     my $before_starts_at_line; 
2075     my $after = 0; # number of lines still to print after a match 
2077     while ( $res->next_text ) { 
2078         # XXX Optimize away the case when there are no more @lines to find. 
2079         # XXX $has_lines, $passthru and $v never change.  Optimize. 
2081                ? $. != $lines[0]  # $lines[0] should be a scalar 
2082                : $v ? m/$regex/ : !m/$regex/ ) { 
2084                 App
::Ack
::print( $_ ); 
2088             if ( $keep_context ) { 
2090                     print_match_or_context
( $opt, 0, $., $-[0], $+[0], $_ ); 
2093                 elsif ( $before_context ) { 
2095                         if ( @before >= $before_context ) { 
2097                             ++$before_starts_at_line; 
2101                         $before_starts_at_line = $.; 
2105                 last if $max && ( $nmatches >= $max ) && !$after; 
2112         # print an empty line as a divider before first line in each file (not before the first file) 
2113         if ( !$any_output && $opt->{show_filename
} && $opt->{break} && defined( $context_overall_output_count ) ) { 
2114             App
::Ack
::print_blank_line
(); 
2117         shift @lines if $has_lines; 
2119         if ( $res->is_binary ) { 
2120             App
::Ack
::print( "Binary file $filename matches\n" ); 
2123         if ( $keep_context ) { 
2125                 print_match_or_context
( $opt, 0, $before_starts_at_line, $-[0], $+[0], @before ); 
2127                 $before_starts_at_line = 0; 
2129             if ( $max && $nmatches > $max ) { 
2133                 $after = $after_context; 
2136         print_match_or_context
( $opt, 1, $., $-[0], $+[0], $_ ); 
2138         last if $max && ( $nmatches >= $max ) && !$after; 
2142 }   # search_resource() 
2146 sub print_match_or_context 
{ 
2147     my $opt         = shift; # opts array 
2148     my $is_match    = shift; # is there a match on the line? 
2149     my $line_no     = shift; 
2150     my $match_start = shift; 
2151     my $match_end   = shift; 
2153     my $color         = $opt->{color
}; 
2154     my $heading       = $opt->{heading
}; 
2155     my $show_filename = $opt->{show_filename
}; 
2156     my $show_column   = $opt->{column
}; 
2158     if ( $show_filename ) { 
2159         if ( not defined $display_filename ) { 
2162                     ? Term
::ANSIColor
::colored
( $filename, $ENV{ACK_COLOR_FILENAME
} ) 
2164             if ( $heading && !$any_output ) { 
2165                 App
::Ack
::print_first_filename
($display_filename); 
2170     my $sep = $is_match ? ':' : '-'; 
2171     my $output_func = $opt->{output
}; 
2173         if ( $keep_context && !$output_func ) { 
2174             if ( ( $last_output_line != $line_no - 1 ) && 
2175                 ( $any_output || ( !$heading && defined( $context_overall_output_count ) ) ) ) { 
2176                 App
::Ack
::print_separator
(); 
2178             # to ensure separators between different files when --noheading 
2180             $last_output_line = $line_no; 
2183         if ( $show_filename ) { 
2184             App
::Ack
::print_filename
($display_filename, $sep) if not $heading; 
2185             my $display_line_no = 
2187                     ? Term
::ANSIColor
::colored
( $line_no, $ENV{ACK_COLOR_LINENO
} ) 
2189             App
::Ack
::print_line_no
($display_line_no, $sep); 
2192         if ( $output_func ) { 
2193             while ( /$regex/go ) { 
2194                 App
::Ack
::print( $output_func->() . "\n" ); 
2198             if ( $color && $is_match && $regex && 
2199                  s/$regex/Term::ANSIColor::colored( substr($_, $-[0], $+[0] - $-[0]), $ENV{ACK_COLOR_MATCH} )/eg ) { 
2200                 # At the end of the line reset the color and remove newline 
2201                 s/[\r\n]*\z/\e[0m\e[K/; 
2204                 # remove any kind of newline at the end of the line 
2207             if ( $show_column ) { 
2208                 App
::Ack
::print_column_no
( $match_start+1, $sep ); 
2210             App
::Ack
::print($_ . "\n"); 
2213         ++$context_overall_output_count; 
2218 } # print_match_or_context() 
2220 } # scope around search_resource() and print_match_or_context() 
2223 TOTAL_COUNT_SCOPE
: { 
2226 sub get_total_count 
{ 
2227     return $total_count; 
2230 sub reset_total_count 
{ 
2235 sub search_and_list 
{ 
2240     my $count = $opt->{count
}; 
2241     my $ors = $opt->{print0
} ? "\0" : "\n"; # output record separator 
2242     my $show_filename = $opt->{show_filename
}; 
2244     my $regex = qr/$opt->{regex}/; 
2247         while ( $res->next_text ) { 
2249                 return 0 unless $count; 
2257         while ( $res->next_text ) { 
2265     if ( $opt->{show_total
} ) { 
2266         $total_count += $nmatches; 
2270             App
::Ack
::print_count
( $res->name, $nmatches, $ors, $count, $show_filename ); 
2272         elsif ( $count && !$opt->{l
} ) { 
2273             App
::Ack
::print_count0
( $res->name, $ors, $show_filename ); 
2277     return $nmatches ? 1 : 0; 
2278 }   # search_and_list() 
2280 } # scope around $total_count 
2284 sub filetypes_supported_set 
{ 
2285     return grep { defined $type_wanted{$_} && ($type_wanted{$_} == 1) } filetypes_supported
(); 
2294     my $ors = $opt->{print0
} ? "\0" : "\n"; 
2297     while ( defined ( my $file = $iter->() ) ) { 
2298         App
::Ack
::print $file, $opt->{show_types
} ? " => " . join( ',', filetypes
( $file ) ) : (),  $ors; 
2307 sub print_files_with_matches 
{ 
2311     # if we have -l and only 1 file given on command line (this means 
2312     # show_filename is set to 0), we want to see the filename nevertheless 
2313     $opt->{show_filename
} = 1 if $opt->{l
}; 
2315     $opt->{show_filename
} = 0 if $opt->{h
}; 
2316     $opt->{show_filename
} = 1 if $opt->{H
}; 
2318     # abuse options to hand in the show_total parameter to search_and_list 
2319     $opt->{show_total
} = $opt->{count
} && !$opt->{show_filename
}; 
2320     reset_total_count
(); 
2323     while ( defined ( my $filename = $iter->() ) ) { 
2324         my $repo = App
::Ack
::Repository
::Basic-
>new( $filename ); 
2326         while ( $res = $repo->next_resource() ) { 
2327             $nmatches += search_and_list
( $res, $opt ); 
2329             last if $nmatches && $opt->{1}; 
2334     if ( $nmatches && $opt->{show_total
} ) { 
2335         App
::Ack
::print_count
('', get_total_count
(), "\n", 1, 0  ) 
2346     $opt->{show_filename
} = 0 if $opt->{h
}; 
2347     $opt->{show_filename
} = 1 if $opt->{H
}; 
2350     while ( defined ( my $filename = $iter->() ) ) { 
2352         my $tarballs_work = 0; 
2353         if ( $tarballs_work && $filename =~ /\.tar\.gz$/ ) { 
2354             App
::Ack
::die( 'Not working here yet' ); 
2355             require App
::Ack
::Repository
::Tar
; # XXX Error checking 
2356             $repo = App
::Ack
::Repository
::Tar-
>new( $filename ); 
2359             $repo = App
::Ack
::Repository
::Basic-
>new( $filename ); 
2363         while ( my $res = $repo->next_resource() ) { 
2364             my $needs_line_scan; 
2365             if ( $opt->{regex
} && !$opt->{passthru
} ) { 
2366                 $needs_line_scan = $res->needs_line_scan( $opt ); 
2367                 if ( $needs_line_scan ) { 
2372                 $needs_line_scan = 1; 
2374             if ( $needs_line_scan ) { 
2375                 $nmatches += search_resource
( $res, $opt ); 
2379         last if $nmatches && $opt->{1}; 
2386 sub filetype_setup 
{ 
2387     my $filetypes_supported_set = filetypes_supported_set
(); 
2388     # If anyone says --no-whatever, we assume all other types must be on. 
2389     if ( !$filetypes_supported_set ) { 
2390         for my $i ( keys %type_wanted ) { 
2391             $type_wanted{$i} = 1 unless ( defined( $type_wanted{$i} ) || $i eq 'binary' || $i eq 'text' || $i eq 'skipped' ); 
2398 EXPAND_FILENAMES_SCOPE
: { 
2401     sub expand_filenames 
{ 
2407         foreach my $pattern ( @{$argv} ) { 
2408             my @results = bsd_glob
( $pattern ); 
2410             if (@results == 0) { 
2411                 @results = $pattern; # Glob didn't match, pass it thru unchanged 
2413             elsif ( (@results > 1) or ($results[0] ne $pattern) ) { 
2414                 if (not defined $filter) { 
2415                     eval 'require Win32::File;'; 
2420                         $filter = Win32
::File
::HIDDEN
()|Win32
::File
::SYSTEM
(); 
2422                 } # end unless we've tried to load Win32::File 
2424                     # Filter out hidden and system files: 
2425                     @results = grep { not(Win32
::File
::GetAttributes
($_, $attr) and $attr & $filter) } @results; 
2426                     App
::Ack
::warn( "$pattern: Matched only hidden files" ) unless @results; 
2427                 } # end if we can filter by file attributes 
2428             } # end elsif this pattern got expanded 
2430             push @files, @results; 
2431         } # end foreach pattern 
2434     } # end expand_filenames 
2435 } # EXPAND_FILENAMES_SCOPE 
2439 sub get_starting_points 
{ 
2446         @what = @{ $is_windows ? expand_filenames
($argv) : $argv }; 
2447         $_ = File
::Next
::reslash
( $_ ) for @what; 
2449         # Show filenames unless we've specified one single file 
2450         $opt->{show_filename
} = (@what > 1) || (!-f 
$what[0]); 
2453         @what = '.'; # Assume current directory 
2454         $opt->{show_filename
} = 1; 
2457     for my $start_point (@what) { 
2458         App
::Ack
::warn( "$start_point: No such file or directory" ) unless -e 
$start_point; 
2464     my ( $target, $expression, $invert_flag ) = @_; 
2466     if ( $invert_flag ) { 
2467         return $target !~ $expression; 
2470         return $target =~ $expression; 
2479     # Starting points are always searched, no matter what 
2480     my %starting_point = map { ($_ => 1) } @{$what}; 
2482     my $g_regex = defined $opt->{G
} ? qr/$opt->{G}/ : undef; 
2487             = $opt->{u
}   ? sub { _match
( $File::Next
::name
, qr/$g_regex/, $opt->{invert_file_match
} ) }    # XXX Maybe this should be a 1, no? 
2488             : $opt->{all
} ? sub { $starting_point{ $File::Next
::name 
} || ( _match
( $File::Next
::name
, qr/$g_regex/, $opt->{invert_file_match
} ) && is_searchable
( $_ ) ) } 
2489             :               sub { $starting_point{ $File::Next
::name 
} || ( _match
( $File::Next
::name
, qr/$g_regex/, $opt->{invert_file_match
} ) && is_interesting
( @ _
) ) } 
2494             = $opt->{u
}   ? sub {1} 
2495             : $opt->{all
} ? sub { $starting_point{ $File::Next
::name 
} || is_searchable
( $_ ) } 
2496             :               sub { $starting_point{ $File::Next
::name 
} || is_interesting
( @_ ) } 
2501         = $opt->{n
} ? sub {0} 
2502         : $opt->{u
} ? sub {1} 
2503         : \
&ignoredir_filter
; 
2506         File
::Next
::files
( { 
2507             file_filter     
=> $file_filter, 
2508             descend_filter  
=> $descend_filter, 
2509             error_handler   
=> sub { my $msg = shift; App
::Ack
::warn( $msg ) }, 
2510             sort_files      
=> $opt->{sort_files
}, 
2511             follow_symlinks 
=> $opt->{follow
}, 
2518     my $command = shift; 
2520     return if App
::Ack
::output_to_pipe
(); 
2523     if ( not open( $pager, '|-', $command ) ) { 
2524         App
::Ack
::die( qq{Unable to pipe to pager "$command": $!} ); 
2532 sub input_from_pipe 
{ 
2533     return $input_from_pipe; 
2538 sub output_to_pipe 
{ 
2539     return $output_to_pipe; 
2544     my $nmatches = shift; 
2546     my $rc = $nmatches ? 0 : 1; 
2552 1; # End of App::Ack 
2553 package App
::Ack
::Repository
; 
2561     Carp
::confess
( 'Must be overloaded' ); 
2580 package App
::Ack
::Resource
; 
2588     Carp
::confess
( 'Must be overloaded' ); 
2608 sub needs_line_scan 
{ 
2628 package App
::Ack
::Plugin
::Basic
; 
2632 package App
::Ack
::Resource
::Basic
; 
2639 our @ISA = qw( App::Ack::Resource ); 
2644     my $filename = shift; 
2647         filename        
=> $filename, 
2649         could_be_binary 
=> undef, 
2654     if ( $self->{filename
} eq '-' ) { 
2655         $self->{fh
} = *STDIN
; 
2656         $self->{could_be_binary
} = 0; 
2659         if ( !open( $self->{fh
}, '<', $self->{filename
} ) ) { 
2660             App
::Ack
::warn( "$self->{filename}: $!" ); 
2663         $self->{could_be_binary
} = 1; 
2673     return $self->{filename
}; 
2680     if ( $self->{could_be_binary
} ) { 
2681         return -B 
$self->{filename
}; 
2689 sub needs_line_scan 
{ 
2693     return 1 if $opt->{v
}; 
2695     my $size = -s 
$self->{fh
}; 
2699     elsif ( $size > 100_000 ) { 
2704     my $rc = sysread( $self->{fh
}, $buffer, $size ); 
2705     if ( not defined $rc ) { 
2706         App
::Ack
::warn( "$self->{filename}: $!" ); 
2709     return 0 unless $rc && ( $rc == $size ); 
2711     my $regex = $opt->{regex
}; 
2712     return $buffer =~ /$regex/m; 
2719     seek( $self->{fh
}, 0, 0 ) 
2720         or App
::Ack
::warn( "$self->{filename}: $!" ); 
2727     if ( defined ($_ = readline $_[0]->{fh
}) ) { 
2728         $. = ++$_[0]->{line
}; 
2739     if ( not close $self->{fh
} ) { 
2740         App
::Ack
::warn( $self->name() . ": $!" ); 
2746 package App
::Ack
::Repository
::Basic
; 
2749 our @ISA = qw( App::Ack::Repository ); 
2757     my $filename = shift; 
2760         filename 
=> $filename, 
2771     return if $self->{nexted
}; 
2772     $self->{nexted
} = 1; 
2774     return App
::Ack
::Resource
::Basic-
>new( $self->{filename
} );