Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

143 lines
3.0 KiB

  1. package File::Compare;
  2. use strict;
  3. use vars qw($VERSION @ISA @EXPORT @EXPORT_OK $Too_Big *FROM *TO);
  4. require Exporter;
  5. use Carp;
  6. $VERSION = '1.1001';
  7. @ISA = qw(Exporter);
  8. @EXPORT = qw(compare);
  9. @EXPORT_OK = qw(cmp);
  10. $Too_Big = 1024 * 1024 * 2;
  11. sub VERSION {
  12. # Version of File::Compare
  13. return $File::Compare::VERSION;
  14. }
  15. sub compare {
  16. croak("Usage: compare( file1, file2 [, buffersize]) ")
  17. unless(@_ == 2 || @_ == 3);
  18. my $from = shift;
  19. my $to = shift;
  20. my $closefrom=0;
  21. my $closeto=0;
  22. my ($size, $fromsize, $status, $fr, $tr, $fbuf, $tbuf);
  23. local(*FROM, *TO);
  24. local($\) = '';
  25. croak("from undefined") unless (defined $from);
  26. croak("to undefined") unless (defined $to);
  27. if (ref($from) &&
  28. (UNIVERSAL::isa($from,'GLOB') || UNIVERSAL::isa($from,'IO::Handle'))) {
  29. *FROM = *$from;
  30. } elsif (ref(\$from) eq 'GLOB') {
  31. *FROM = $from;
  32. } else {
  33. open(FROM,"<$from") or goto fail_open1;
  34. binmode FROM;
  35. $closefrom = 1;
  36. $fromsize = -s FROM;
  37. }
  38. if (ref($to) &&
  39. (UNIVERSAL::isa($to,'GLOB') || UNIVERSAL::isa($to,'IO::Handle'))) {
  40. *TO = *$to;
  41. } elsif (ref(\$to) eq 'GLOB') {
  42. *TO = $to;
  43. } else {
  44. open(TO,"<$to") or goto fail_open2;
  45. binmode TO;
  46. $closeto = 1;
  47. }
  48. if ($closefrom && $closeto) {
  49. # If both are opened files we know they differ if their size differ
  50. goto fail_inner if $fromsize != -s TO;
  51. }
  52. if (@_) {
  53. $size = shift(@_) + 0;
  54. croak("Bad buffer size for compare: $size\n") unless ($size > 0);
  55. } else {
  56. $size = $fromsize;
  57. $size = 1024 if ($size < 512);
  58. $size = $Too_Big if ($size > $Too_Big);
  59. }
  60. $fbuf = '';
  61. $tbuf = '';
  62. while(defined($fr = read(FROM,$fbuf,$size)) && $fr > 0) {
  63. unless (defined($tr = read(TO,$tbuf,$fr)) and $tbuf eq $fbuf) {
  64. goto fail_inner;
  65. }
  66. }
  67. goto fail_inner if (defined($tr = read(TO,$tbuf,$size)) && $tr > 0);
  68. close(TO) || goto fail_open2 if $closeto;
  69. close(FROM) || goto fail_open1 if $closefrom;
  70. return 0;
  71. # All of these contortions try to preserve error messages...
  72. fail_inner:
  73. close(TO) || goto fail_open2 if $closeto;
  74. close(FROM) || goto fail_open1 if $closefrom;
  75. return 1;
  76. fail_open2:
  77. if ($closefrom) {
  78. $status = $!;
  79. $! = 0;
  80. close FROM;
  81. $! = $status unless $!;
  82. }
  83. fail_open1:
  84. return -1;
  85. }
  86. *cmp = \&compare;
  87. 1;
  88. __END__
  89. =head1 NAME
  90. File::Compare - Compare files or filehandles
  91. =head1 SYNOPSIS
  92. use File::Compare;
  93. if (compare("file1","file2") == 0) {
  94. print "They're equal\n";
  95. }
  96. =head1 DESCRIPTION
  97. The File::Compare::compare function compares the contents of two
  98. sources, each of which can be a file or a file handle. It is exported
  99. from File::Compare by default.
  100. File::Compare::cmp is a synonym for File::Compare::compare. It is
  101. exported from File::Compare only by request.
  102. =head1 RETURN
  103. File::Compare::compare return 0 if the files are equal, 1 if the
  104. files are unequal, or -1 if an error was encountered.
  105. =head1 AUTHOR
  106. File::Compare was written by Nick Ing-Simmons.
  107. Its original documentation was written by Chip Salzenberg.
  108. =cut