1BEGIN { 2 if ($ENV{PERL_CORE}) { 3 chdir 't' if -d 't'; 4 @INC = ("../lib", "lib/compress"); 5 } 6} 7 8use lib qw(t t/compress); 9use strict; 10use warnings; 11use bytes; 12 13use Test::More ; 14use CompTestUtils; 15use Symbol; 16 17use constant ZLIB_1_2_12_0 => 0x12C0; 18 19BEGIN 20{ 21 # use Test::NoWarnings, if available 22 my $extra = 0 ; 23 $extra = 1 24 if eval { require Test::NoWarnings ; Test::NoWarnings->import; 1 }; 25 26 my $count = 0 ; 27 if ($] < 5.005) { 28 $count = 453 ; 29 } 30 else { 31 $count = 471 ; 32 } 33 34 35 plan tests => $count + $extra ; 36 37 use_ok('Compress::Zlib', qw(:ALL memGunzip memGzip zlib_version)); 38 use_ok('IO::Compress::Gzip::Constants') ; 39 40 use_ok('IO::Compress::Gzip', qw($GzipError)) ; 41} 42 43 44my $hello = <<EOM ; 45hello world 46this is a test 47EOM 48 49my $len = length $hello ; 50 51# Check zlib_version and ZLIB_VERSION are the same. 52SKIP: { 53 skip "TEST_SKIP_VERSION_CHECK is set", 1 54 if $ENV{TEST_SKIP_VERSION_CHECK}; 55 is Compress::Zlib::zlib_version, ZLIB_VERSION, 56 "ZLIB_VERSION matches Compress::Zlib::zlib_version" ; 57} 58 59# generate a long random string 60my $contents = '' ; 61foreach (1 .. 5000) 62 { $contents .= chr int rand 256 } 63 64my $x ; 65my $fil; 66 67# compress/uncompress tests 68# ========================= 69 70eval { compress([1]); }; 71ok $@ =~ m#not a scalar reference# 72 or print "# $@\n" ;; 73 74eval { uncompress([1]); }; 75ok $@ =~ m#not a scalar reference# 76 or print "# $@\n" ;; 77 78$hello = "hello mum" ; 79my $keep_hello = $hello ; 80 81my $compr = compress($hello) ; 82ok $compr ne "" ; 83 84my $keep_compr = $compr ; 85 86my $uncompr = uncompress ($compr) ; 87 88ok $hello eq $uncompr ; 89 90ok $hello eq $keep_hello ; 91ok $compr eq $keep_compr ; 92 93# compress a number 94$hello = 7890 ; 95$keep_hello = $hello ; 96 97$compr = compress($hello) ; 98ok $compr ne "" ; 99 100$keep_compr = $compr ; 101 102$uncompr = uncompress ($compr) ; 103 104ok $hello eq $uncompr ; 105 106ok $hello eq $keep_hello ; 107ok $compr eq $keep_compr ; 108 109# bigger compress 110 111$compr = compress ($contents) ; 112ok $compr ne "" ; 113 114$uncompr = uncompress ($compr) ; 115 116ok $contents eq $uncompr ; 117 118# buffer reference 119 120$compr = compress(\$hello) ; 121ok $compr ne "" ; 122 123 124$uncompr = uncompress (\$compr) ; 125ok $hello eq $uncompr ; 126 127# bad level 128$compr = compress($hello, 1000) ; 129ok ! defined $compr; 130 131# change level 132$compr = compress($hello, Z_BEST_COMPRESSION) ; 133ok defined $compr; 134$uncompr = uncompress (\$compr) ; 135ok $hello eq $uncompr ; 136 137# corrupt data 138$compr = compress(\$hello) ; 139ok $compr ne "" ; 140 141substr($compr,0, 1) = "\xFF"; 142ok !defined uncompress (\$compr) ; 143 144# deflate/inflate - small buffer 145# ============================== 146 147$hello = "I am a HAL 9000 computer" ; 148my @hello = split('', $hello) ; 149my ($err, $X, $status); 150 151ok (($x, $err) = deflateInit( {-Bufsize => 1} ) ) ; 152ok $x ; 153ok $err == Z_OK ; 154 155my $Answer = ''; 156foreach (@hello) 157{ 158 ($X, $status) = $x->deflate($_) ; 159 last unless $status == Z_OK ; 160 161 $Answer .= $X ; 162} 163 164ok $status == Z_OK ; 165 166ok ((($X, $status) = $x->flush())[1] == Z_OK ) ; 167$Answer .= $X ; 168 169 170my @Answer = split('', $Answer) ; 171 172my $k; 173ok (($k, $err) = inflateInit( {-Bufsize => 1}) ) ; 174ok $k ; 175ok $err == Z_OK ; 176 177my $GOT = ''; 178my $Z; 179foreach (@Answer) 180{ 181 ($Z, $status) = $k->inflate($_) ; 182 $GOT .= $Z ; 183 last if $status == Z_STREAM_END or $status != Z_OK ; 184 185} 186 187ok $status == Z_STREAM_END ; 188ok $GOT eq $hello ; 189 190 191title 'deflate/inflate - small buffer with a number'; 192# ============================== 193 194$hello = 6529 ; 195 196ok (($x, $err) = deflateInit( {-Bufsize => 1} ) ) ; 197ok $x ; 198ok $err == Z_OK ; 199 200ok !defined $x->msg() ; 201ok $x->total_in() == 0 ; 202ok $x->total_out() == 0 ; 203$Answer = ''; 204{ 205 ($X, $status) = $x->deflate($hello) ; 206 207 $Answer .= $X ; 208} 209 210ok $status == Z_OK ; 211 212ok ((($X, $status) = $x->flush())[1] == Z_OK ) ; 213$Answer .= $X ; 214 215ok !defined $x->msg() ; 216ok $x->total_in() == length $hello ; 217ok $x->total_out() == length $Answer ; 218 219 220@Answer = split('', $Answer) ; 221 222ok (($k, $err) = inflateInit( {-Bufsize => 1}) ) ; 223ok $k ; 224ok $err == Z_OK ; 225 226ok !defined $k->msg() ; 227ok $k->total_in() == 0 ; 228ok $k->total_out() == 0 ; 229 230$GOT = ''; 231foreach (@Answer) 232{ 233 ($Z, $status) = $k->inflate($_) ; 234 $GOT .= $Z ; 235 last if $status == Z_STREAM_END or $status != Z_OK ; 236 237} 238 239ok $status == Z_STREAM_END ; 240ok $GOT eq $hello ; 241 242ok !defined $k->msg() ; 243is $k->total_in(), length $Answer ; 244ok $k->total_out() == length $hello ; 245 246 247 248title 'deflate/inflate - larger buffer'; 249# ============================== 250 251 252ok $x = deflateInit() ; 253 254ok ((($X, $status) = $x->deflate($contents))[1] == Z_OK) ; 255 256my $Y = $X ; 257 258 259ok ((($X, $status) = $x->flush() )[1] == Z_OK ) ; 260$Y .= $X ; 261 262 263 264ok $k = inflateInit() ; 265 266($Z, $status) = $k->inflate($Y) ; 267 268ok $status == Z_STREAM_END ; 269ok $contents eq $Z ; 270 271title 'deflate/inflate - preset dictionary'; 272# =================================== 273 274my $dictionary = "hello" ; 275ok $x = deflateInit({-Level => Z_BEST_COMPRESSION, 276 -Dictionary => $dictionary}) ; 277 278my $dictID = $x->dict_adler() ; 279 280($X, $status) = $x->deflate($hello) ; 281ok $status == Z_OK ; 282($Y, $status) = $x->flush() ; 283ok $status == Z_OK ; 284$X .= $Y ; 285$x = 0 ; 286 287ok $k = inflateInit(-Dictionary => $dictionary) ; 288 289($Z, $status) = $k->inflate($X); 290ok $status == Z_STREAM_END ; 291ok $k->dict_adler() == $dictID; 292ok $hello eq $Z ; 293 294#$Z=''; 295#while (1) { 296# ($Z, $status) = $k->inflate($X) ; 297# last if $status == Z_STREAM_END or $status != Z_OK ; 298#print "status=[$status] hello=[$hello] Z=[$Z]\n"; 299#} 300#ok $status == Z_STREAM_END ; 301#ok $hello eq $Z 302# or print "status=[$status] hello=[$hello] Z=[$Z]\n"; 303 304 305 306 307 308 309title 'inflate - check remaining buffer after Z_STREAM_END'; 310# =================================================== 311 312{ 313 ok $x = deflateInit(-Level => Z_BEST_COMPRESSION ) ; 314 315 ($X, $status) = $x->deflate($hello) ; 316 ok $status == Z_OK ; 317 ($Y, $status) = $x->flush() ; 318 ok $status == Z_OK ; 319 $X .= $Y ; 320 $x = 0 ; 321 322 ok $k = inflateInit() ; 323 324 my $first = substr($X, 0, 2) ; 325 my $last = substr($X, 2) ; 326 ($Z, $status) = $k->inflate($first); 327 ok $status == Z_OK ; 328 ok $first eq "" ; 329 330 $last .= "appendage" ; 331 my $T; 332 ($T, $status) = $k->inflate($last); 333 ok $status == Z_STREAM_END ; 334 ok $hello eq $Z . $T ; 335 ok $last eq "appendage" ; 336 337} 338 339title 'memGzip & memGunzip'; 340{ 341 my ($name, $name1, $name2, $name3); 342 my $lex = LexFile->new( $name, $name1, $name2, $name3 ); 343 my $buffer = <<EOM; 344some sample 345text 346 347EOM 348 349 my $len = length $buffer ; 350 my ($x, $uncomp) ; 351 352 353 # create an in-memory gzip file 354 my $dest = memGzip($buffer) ; 355 ok length $dest ; 356 is $gzerrno, 0; 357 358 # write it to disk 359 ok open(FH, ">$name") ; 360 binmode(FH); 361 print FH $dest ; 362 close FH ; 363 364 # uncompress with gzopen 365 ok my $fil = gzopen($name, "rb") ; 366 367 is $fil->gzread($uncomp, 0), 0 ; 368 ok (($x = $fil->gzread($uncomp)) == $len) ; 369 370 ok ! $fil->gzclose ; 371 372 ok $uncomp eq $buffer ; 373 374 #1 while unlink $name ; 375 376 # now check that memGunzip can deal with it. 377 my $ungzip = memGunzip($dest) ; 378 ok defined $ungzip ; 379 ok $buffer eq $ungzip ; 380 is $gzerrno, 0; 381 382 # now do the same but use a reference 383 384 $dest = memGzip(\$buffer) ; 385 ok length $dest ; 386 is $gzerrno, 0; 387 388 # write it to disk 389 ok open(FH, ">$name1") ; 390 binmode(FH); 391 print FH $dest ; 392 close FH ; 393 394 # uncompress with gzopen 395 ok $fil = gzopen($name1, "rb") ; 396 397 ok (($x = $fil->gzread($uncomp)) == $len) ; 398 399 ok ! $fil->gzclose ; 400 401 ok $uncomp eq $buffer ; 402 403 # now check that memGunzip can deal with it. 404 my $keep = $dest; 405 $ungzip = memGunzip(\$dest) ; 406 is $gzerrno, 0; 407 ok defined $ungzip ; 408 ok $buffer eq $ungzip ; 409 410 # check memGunzip can cope with missing gzip trailer 411 my $minimal = substr($keep, 0, -1) ; 412 $ungzip = memGunzip(\$minimal) ; 413 ok defined $ungzip ; 414 ok $buffer eq $ungzip ; 415 is $gzerrno, 0; 416 417 $minimal = substr($keep, 0, -2) ; 418 $ungzip = memGunzip(\$minimal) ; 419 ok defined $ungzip ; 420 ok $buffer eq $ungzip ; 421 is $gzerrno, 0; 422 423 $minimal = substr($keep, 0, -3) ; 424 $ungzip = memGunzip(\$minimal) ; 425 ok defined $ungzip ; 426 ok $buffer eq $ungzip ; 427 is $gzerrno, 0; 428 429 $minimal = substr($keep, 0, -4) ; 430 $ungzip = memGunzip(\$minimal) ; 431 ok defined $ungzip ; 432 ok $buffer eq $ungzip ; 433 is $gzerrno, 0; 434 435 $minimal = substr($keep, 0, -5) ; 436 $ungzip = memGunzip(\$minimal) ; 437 ok defined $ungzip ; 438 ok $buffer eq $ungzip ; 439 is $gzerrno, 0; 440 441 $minimal = substr($keep, 0, -6) ; 442 $ungzip = memGunzip(\$minimal) ; 443 ok defined $ungzip ; 444 ok $buffer eq $ungzip ; 445 is $gzerrno, 0; 446 447 $minimal = substr($keep, 0, -7) ; 448 $ungzip = memGunzip(\$minimal) ; 449 ok defined $ungzip ; 450 ok $buffer eq $ungzip ; 451 is $gzerrno, 0; 452 453 $minimal = substr($keep, 0, -8) ; 454 $ungzip = memGunzip(\$minimal) ; 455 ok defined $ungzip ; 456 ok $buffer eq $ungzip ; 457 is $gzerrno, 0; 458 459 $minimal = substr($keep, 0, -9) ; 460 $ungzip = memGunzip(\$minimal) ; 461 ok ! defined $ungzip ; 462 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 463 464 465 #1 while unlink $name ; 466 467 # check corrupt header -- too short 468 $dest = "x" ; 469 my $result = memGunzip($dest) ; 470 ok !defined $result ; 471 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 472 473 # check corrupt header -- full of junk 474 $dest = "x" x 200 ; 475 $result = memGunzip($dest) ; 476 ok !defined $result ; 477 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 478 479 # corrupt header - 1st byte wrong 480 my $bad = $keep ; 481 substr($bad, 0, 1) = "\xFF" ; 482 $ungzip = memGunzip(\$bad) ; 483 ok ! defined $ungzip ; 484 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 485 486 # corrupt header - 2st byte wrong 487 $bad = $keep ; 488 substr($bad, 1, 1) = "\xFF" ; 489 $ungzip = memGunzip(\$bad) ; 490 ok ! defined $ungzip ; 491 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 492 493 # corrupt header - method not deflated 494 $bad = $keep ; 495 substr($bad, 2, 1) = "\xFF" ; 496 $ungzip = memGunzip(\$bad) ; 497 ok ! defined $ungzip ; 498 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 499 500 # corrupt header - reserved bits used 501 $bad = $keep ; 502 substr($bad, 3, 1) = "\xFF" ; 503 $ungzip = memGunzip(\$bad) ; 504 ok ! defined $ungzip ; 505 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 506 507 # corrupt trailer - length wrong 508 $bad = $keep ; 509 substr($bad, -8, 4) = "\xFF" x 4 ; 510 $ungzip = memGunzip(\$bad) ; 511 ok ! defined $ungzip ; 512 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 513 514 # corrupt trailer - CRC wrong 515 $bad = $keep ; 516 substr($bad, -4, 4) = "\xFF" x 4 ; 517 $ungzip = memGunzip(\$bad) ; 518 ok ! defined $ungzip ; 519 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 520} 521 522{ 523 title "Check all bytes can be handled"; 524 525 my $lex = LexFile->new( my $name ); 526 my $data = join '', map { chr } 0x00 .. 0xFF; 527 $data .= "\r\nabd\r\n"; 528 529 my $fil; 530 ok $fil = gzopen($name, "wb") ; 531 is $fil->gzwrite($data), length $data ; 532 ok ! $fil->gzclose(); 533 534 my $input; 535 ok $fil = gzopen($name, "rb") ; 536 is $fil->gzread($input), length $data ; 537 ok ! $fil->gzclose(); 538 ok $input eq $data; 539 540 title "Check all bytes can be handled - transparent mode"; 541 writeFile($name, $data); 542 ok $fil = gzopen($name, "rb") ; 543 is $fil->gzread($input), length $data ; 544 ok ! $fil->gzclose(); 545 ok $input eq $data; 546 547} 548 549title 'memGunzip with a gzopen created file'; 550{ 551 my $name = "test.gz" ; 552 my $buffer = <<EOM; 553some sample 554text 555 556EOM 557 558 ok $fil = gzopen($name, "wb") ; 559 560 ok $fil->gzwrite($buffer) == length $buffer ; 561 562 ok ! $fil->gzclose ; 563 564 my $compr = readFile($name); 565 ok length $compr ; 566 my $unc = memGunzip($compr) ; 567 is $gzerrno, 0; 568 ok defined $unc ; 569 ok $buffer eq $unc ; 570 1 while unlink $name ; 571} 572 573{ 574 575 # Check - MAX_WBITS 576 # ================= 577 578 $hello = "Test test test test test"; 579 @hello = split('', $hello) ; 580 581 ok (($x, $err) = deflateInit( -Bufsize => 1, -WindowBits => -MAX_WBITS() ) ) ; 582 ok $x ; 583 ok $err == Z_OK ; 584 585 $Answer = ''; 586 foreach (@hello) 587 { 588 ($X, $status) = $x->deflate($_) ; 589 last unless $status == Z_OK ; 590 591 $Answer .= $X ; 592 } 593 594 ok $status == Z_OK ; 595 596 ok ((($X, $status) = $x->flush())[1] == Z_OK ) ; 597 $Answer .= $X ; 598 599 600 @Answer = split('', $Answer) ; 601 # Undocumented corner -- extra byte needed to get inflate to return 602 # Z_STREAM_END when done. 603 push @Answer, " " ; 604 605 ok (($k, $err) = inflateInit(-Bufsize => 1, -WindowBits => -MAX_WBITS()) ) ; 606 ok $k ; 607 ok $err == Z_OK ; 608 609 $GOT = ''; 610 foreach (@Answer) 611 { 612 ($Z, $status) = $k->inflate($_) ; 613 $GOT .= $Z ; 614 last if $status == Z_STREAM_END or $status != Z_OK ; 615 616 } 617 618 ok $status == Z_STREAM_END ; 619 ok $GOT eq $hello ; 620 621} 622 623{ 624 # inflateSync 625 626 # create a deflate stream with flush points 627 628 my $hello = "I am a HAL 9000 computer" x 2001 ; 629 my $goodbye = "Will I dream?" x 2010; 630 my ($err, $answer, $X, $status, $Answer); 631 632 ok (($x, $err) = deflateInit() ) ; 633 ok $x ; 634 ok $err == Z_OK ; 635 636 ($Answer, $status) = $x->deflate($hello) ; 637 ok $status == Z_OK ; 638 639 # create a flush point 640 ok ((($X, $status) = $x->flush(Z_FULL_FLUSH))[1] == Z_OK ) ; 641 $Answer .= $X ; 642 643 ($X, $status) = $x->deflate($goodbye) ; 644 ok $status == Z_OK ; 645 $Answer .= $X ; 646 647 ok ((($X, $status) = $x->flush())[1] == Z_OK ) ; 648 $Answer .= $X ; 649 650 my ($first, @Answer) = split('', $Answer) ; 651 652 my $k; 653 ok (($k, $err) = inflateInit()) ; 654 ok $k ; 655 ok $err == Z_OK ; 656 657 ($Z, $status) = $k->inflate($first) ; 658 ok $status == Z_OK ; 659 660 # skip to the first flush point. 661 while (@Answer) 662 { 663 my $byte = shift @Answer; 664 $status = $k->inflateSync($byte) ; 665 last unless $status == Z_DATA_ERROR; 666 667 } 668 669 ok $status == Z_OK; 670 671 my $GOT = ''; 672 my $Z = ''; 673 foreach (@Answer) 674 { 675 my $Z = ''; 676 ($Z, $status) = $k->inflate($_) ; 677 $GOT .= $Z if defined $Z ; 678 # print "x $status\n"; 679 last if $status == Z_STREAM_END or $status != Z_OK ; 680 681 } 682 683 # zlib 1.0.9 returns Z_STREAM_END here, all others return Z_DATA_ERROR 684 ok $status == Z_DATA_ERROR || $status == Z_STREAM_END ; 685 ok $GOT eq $goodbye ; 686 687 688 # Check inflateSync leaves good data in buffer 689 $Answer =~ /^(.)(.*)$/ ; 690 my ($initial, $rest) = ($1, $2); 691 692 693 ok (($k, $err) = inflateInit()) ; 694 ok $k ; 695 ok $err == Z_OK ; 696 697 ($Z, $status) = $k->inflate($initial) ; 698 ok $status == Z_OK ; 699 700 $status = $k->inflateSync($rest) ; 701 ok $status == Z_OK; 702 703 ($GOT, $status) = $k->inflate($rest) ; 704 705 # Z_STREAM_END returned by 1.12.2, Z_DATA_ERROR for older zlib 706 # always Z_STREAM_ENDin zlib_ng 707 if (ZLIB_VERNUM >= ZLIB_1_2_12_0 || Compress::Raw::Zlib::is_zlibng) 708 { 709 cmp_ok $status, '==', Z_STREAM_END ; 710 } 711 else 712 { 713 cmp_ok $status, '==', Z_DATA_ERROR ; 714 } 715 716 ok $Z . $GOT eq $goodbye ; 717} 718 719{ 720 # deflateParams 721 722 my $hello = "I am a HAL 9000 computer" x 2001 ; 723 my $goodbye = "Will I dream?" x 2010; 724 my ($input, $err, $answer, $X, $status, $Answer); 725 726 ok (($x, $err) = deflateInit(-Level => Z_BEST_COMPRESSION, 727 -Strategy => Z_DEFAULT_STRATEGY) ) ; 728 ok $x ; 729 ok $err == Z_OK ; 730 731 ok $x->get_Level() == Z_BEST_COMPRESSION; 732 ok $x->get_Strategy() == Z_DEFAULT_STRATEGY; 733 734 ($Answer, $status) = $x->deflate($hello) ; 735 ok $status == Z_OK ; 736 $input .= $hello; 737 738 # error cases 739 eval { $x->deflateParams() }; 740 #like $@, mkErr("^Compress::Raw::Zlib::deflateParams needs Level and/or Strategy"); 741 like $@, "/^Compress::Raw::Zlib::deflateParams needs Level and/or Strategy/"; 742 743 eval { $x->deflateParams(-Joe => 3) }; 744 like $@, "/^Compress::Raw::Zlib::deflateStream::deflateParams: unknown key value/"; 745 #like $@, mkErr("^Compress::Raw::Zlib::deflateStream::deflateParams: unknown key value(s) Joe"); 746 #ok $@ =~ /^Compress::Zlib::deflateStream::deflateParams: unknown key value\(s\) Joe at/ 747 # or print "# $@\n" ; 748 749 ok $x->get_Level() == Z_BEST_COMPRESSION; 750 ok $x->get_Strategy() == Z_DEFAULT_STRATEGY; 751 752 # change both Level & Strategy 753 $status = $x->deflateParams(-Level => Z_BEST_SPEED, -Strategy => Z_HUFFMAN_ONLY) ; 754 ok $status == Z_OK ; 755 756 ok $x->get_Level() == Z_BEST_SPEED; 757 ok $x->get_Strategy() == Z_HUFFMAN_ONLY; 758 759 ($X, $status) = $x->deflate($goodbye) ; 760 ok $status == Z_OK ; 761 $Answer .= $X ; 762 $input .= $goodbye; 763 764 # change only Level 765 $status = $x->deflateParams(-Level => Z_NO_COMPRESSION) ; 766 ok $status == Z_OK ; 767 768 ok $x->get_Level() == Z_NO_COMPRESSION; 769 ok $x->get_Strategy() == Z_HUFFMAN_ONLY; 770 771 ($X, $status) = $x->deflate($goodbye) ; 772 ok $status == Z_OK ; 773 $Answer .= $X ; 774 $input .= $goodbye; 775 776 # change only Strategy 777 $status = $x->deflateParams(-Strategy => Z_FILTERED) ; 778 ok $status == Z_OK ; 779 780 ok $x->get_Level() == Z_NO_COMPRESSION; 781 ok $x->get_Strategy() == Z_FILTERED; 782 783 ($X, $status) = $x->deflate($goodbye) ; 784 ok $status == Z_OK ; 785 $Answer .= $X ; 786 $input .= $goodbye; 787 788 ok ((($X, $status) = $x->flush())[1] == Z_OK ) ; 789 $Answer .= $X ; 790 791 my ($first, @Answer) = split('', $Answer) ; 792 793 my $k; 794 ok (($k, $err) = inflateInit()) ; 795 ok $k ; 796 ok $err == Z_OK ; 797 798 ($Z, $status) = $k->inflate($Answer) ; 799 800 ok $status == Z_STREAM_END 801 or print "# status $status\n"; 802 ok $Z eq $input ; 803} 804 805{ 806 # error cases 807 808 eval { deflateInit(-Level) }; 809 like $@, '/^Compress::Zlib::deflateInit: Expected even number of parameters, got 1/'; 810 811 eval { inflateInit(-Level) }; 812 like $@, '/^Compress::Zlib::inflateInit: Expected even number of parameters, got 1/'; 813 814 eval { deflateInit(-Joe => 1) }; 815 ok $@ =~ /^Compress::Zlib::deflateInit: unknown key value\(s\) Joe at/; 816 817 eval { inflateInit(-Joe => 1) }; 818 ok $@ =~ /^Compress::Zlib::inflateInit: unknown key value\(s\) Joe at/; 819 820 eval { deflateInit(-Bufsize => 0) }; 821 ok $@ =~ /^.*?: Bufsize must be >= 1, you specified 0 at/; 822 823 eval { inflateInit(-Bufsize => 0) }; 824 ok $@ =~ /^.*?: Bufsize must be >= 1, you specified 0 at/; 825 826 eval { deflateInit(-Bufsize => -1) }; 827 #ok $@ =~ /^.*?: Bufsize must be >= 1, you specified -1 at/; 828 ok $@ =~ /^Compress::Zlib::deflateInit: Parameter 'Bufsize' must be an unsigned int, got '-1'/; 829 830 eval { inflateInit(-Bufsize => -1) }; 831 ok $@ =~ /^Compress::Zlib::inflateInit: Parameter 'Bufsize' must be an unsigned int, got '-1'/; 832 833 eval { deflateInit(-Bufsize => "xxx") }; 834 ok $@ =~ /^Compress::Zlib::deflateInit: Parameter 'Bufsize' must be an unsigned int, got 'xxx'/; 835 836 eval { inflateInit(-Bufsize => "xxx") }; 837 ok $@ =~ /^Compress::Zlib::inflateInit: Parameter 'Bufsize' must be an unsigned int, got 'xxx'/; 838 839 eval { gzopen([], 0) ; } ; 840 ok $@ =~ /^gzopen: file parameter is not a filehandle or filename at/ 841 or print "# $@\n" ; 842 843# my $x = Symbol::gensym() ; 844# eval { gzopen($x, 0) ; } ; 845# ok $@ =~ /^gzopen: file parameter is not a filehandle or filename at/ 846# or print "# $@\n" ; 847 848} 849 850if ($] >= 5.005) 851{ 852 # test inflate with a substr 853 854 ok my $x = deflateInit() ; 855 856 ok ((my ($X, $status) = $x->deflate($contents))[1] == Z_OK) ; 857 858 my $Y = $X ; 859 860 861 862 ok ((($X, $status) = $x->flush() )[1] == Z_OK ) ; 863 $Y .= $X ; 864 865 my $append = "Appended" ; 866 $Y .= $append ; 867 868 ok $k = inflateInit() ; 869 870 #($Z, $status) = $k->inflate(substr($Y, 0, -1)) ; 871 ($Z, $status) = $k->inflate(substr($Y, 0)) ; 872 873 ok $status == Z_STREAM_END ; 874 ok $contents eq $Z ; 875 is $Y, $append; 876 877} 878 879if ($] >= 5.005) 880{ 881 # deflate/inflate in scalar context 882 883 ok my $x = deflateInit() ; 884 885 my $X = $x->deflate($contents); 886 887 my $Y = $X ; 888 889 890 891 $X = $x->flush(); 892 $Y .= $X ; 893 894 my $append = "Appended" ; 895 $Y .= $append ; 896 897 ok $k = inflateInit() ; 898 899 $Z = $k->inflate(substr($Y, 0, -1)) ; 900 #$Z = $k->inflate(substr($Y, 0)) ; 901 902 ok $contents eq $Z ; 903 is $Y, $append; 904 905} 906 907{ 908 title 'CRC32' ; 909 910 # CRC32 of this data should have the high bit set 911 # value in ascii is ZgRNtjgSUW 912 my $data = "\x5a\x67\x52\x4e\x74\x6a\x67\x53\x55\x57"; 913 my $expected_crc = 0xCF707A2B ; # 3480255019 914 915 my $crc = crc32($data) ; 916 is $crc, $expected_crc; 917} 918 919{ 920 title 'Adler32' ; 921 922 # adler of this data should have the high bit set 923 # value in ascii is lpscOVsAJiUfNComkOfWYBcPhHZ[bT 924 my $data = "\x6c\x70\x73\x63\x4f\x56\x73\x41\x4a\x69\x55\x66" . 925 "\x4e\x43\x6f\x6d\x6b\x4f\x66\x57\x59\x42\x63\x50" . 926 "\x68\x48\x5a\x5b\x62\x54"; 927 my $expected_crc = 0xAAD60AC7 ; # 2866154183 928 my $crc = adler32($data) ; 929 is $crc, $expected_crc; 930} 931 932{ 933 # memGunzip - input > 4K 934 935 my $contents = '' ; 936 foreach (1 .. 20000) 937 { $contents .= chr int rand 256 } 938 939 ok my $compressed = memGzip(\$contents) ; 940 is $gzerrno, 0; 941 942 ok length $compressed > 4096 ; 943 ok my $out = memGunzip(\$compressed) ; 944 is $gzerrno, 0; 945 946 ok $contents eq $out ; 947 is length $out, length $contents ; 948 949 950} 951 952 953{ 954 # memGunzip Header Corruption Tests 955 956 my $string = <<EOM; 957some text 958EOM 959 960 my $good ; 961 ok my $x = IO::Compress::Gzip->new( \$good, Append => 1, -HeaderCRC => 1 ); 962 ok $x->write($string) ; 963 ok $x->close ; 964 965 { 966 title "Header Corruption - Fingerprint wrong 1st byte" ; 967 my $buffer = $good ; 968 substr($buffer, 0, 1) = 'x' ; 969 970 ok ! memGunzip(\$buffer) ; 971 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 972 } 973 974 { 975 title "Header Corruption - Fingerprint wrong 2nd byte" ; 976 my $buffer = $good ; 977 substr($buffer, 1, 1) = "\xFF" ; 978 979 ok ! memGunzip(\$buffer) ; 980 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 981 } 982 983 { 984 title "Header Corruption - CM not 8"; 985 my $buffer = $good ; 986 substr($buffer, 2, 1) = 'x' ; 987 988 ok ! memGunzip(\$buffer) ; 989 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 990 } 991 992 { 993 title "Header Corruption - Use of Reserved Flags"; 994 my $buffer = $good ; 995 substr($buffer, 3, 1) = "\xff"; 996 997 ok ! memGunzip(\$buffer) ; 998 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 999 } 1000 1001} 1002 1003for my $index ( GZIP_MIN_HEADER_SIZE + 1 .. GZIP_MIN_HEADER_SIZE + GZIP_FEXTRA_HEADER_SIZE + 1) 1004{ 1005 title "Header Corruption - Truncated in Extra"; 1006 my $string = <<EOM; 1007some text 1008EOM 1009 1010 my $truncated ; 1011 ok my $x = IO::Compress::Gzip->new( \$truncated, Append => 1, -HeaderCRC => 1, Strict => 0, 1012 -ExtraField => "hello" x 10 ); 1013 ok $x->write($string) ; 1014 ok $x->close ; 1015 1016 substr($truncated, $index) = '' ; 1017 1018 ok ! memGunzip(\$truncated) ; 1019 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 1020 1021 1022} 1023 1024my $Name = "fred" ; 1025for my $index ( GZIP_MIN_HEADER_SIZE .. GZIP_MIN_HEADER_SIZE + length($Name) -1) 1026{ 1027 title "Header Corruption - Truncated in Name"; 1028 my $string = <<EOM; 1029some text 1030EOM 1031 1032 my $truncated ; 1033 ok my $x = IO::Compress::Gzip->new( \$truncated, Append => 1, -Name => $Name ); 1034 ok $x->write($string) ; 1035 ok $x->close ; 1036 1037 substr($truncated, $index) = '' ; 1038 1039 ok ! memGunzip(\$truncated) ; 1040 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 1041} 1042 1043my $Comment = "comment" ; 1044for my $index ( GZIP_MIN_HEADER_SIZE .. GZIP_MIN_HEADER_SIZE + length($Comment) -1) 1045{ 1046 title "Header Corruption - Truncated in Comment"; 1047 my $string = <<EOM; 1048some text 1049EOM 1050 1051 my $truncated ; 1052 ok my $x = IO::Compress::Gzip->new( \$truncated, -Comment => $Comment ); 1053 ok $x->write($string) ; 1054 ok $x->close ; 1055 1056 substr($truncated, $index) = '' ; 1057 ok ! memGunzip(\$truncated) ; 1058 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 1059} 1060 1061for my $index ( GZIP_MIN_HEADER_SIZE .. GZIP_MIN_HEADER_SIZE + GZIP_FHCRC_SIZE -1) 1062{ 1063 title "Header Corruption - Truncated in CRC"; 1064 my $string = <<EOM; 1065some text 1066EOM 1067 1068 my $truncated ; 1069 ok my $x = IO::Compress::Gzip->new( \$truncated, -HeaderCRC => 1 ); 1070 ok $x->write($string) ; 1071 ok $x->close ; 1072 1073 substr($truncated, $index) = '' ; 1074 1075 ok ! memGunzip(\$truncated) ; 1076 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 1077} 1078 1079{ 1080 title "memGunzip can cope with a gzip header with all possible fields"; 1081 my $string = <<EOM; 1082some text 1083EOM 1084 1085 my $buffer ; 1086 ok my $x = IO::Compress::Gzip->new( \$buffer, 1087 -Append => 1, 1088 -Strict => 0, 1089 -HeaderCRC => 1, 1090 -Name => "Fred", 1091 -ExtraField => "Extra", 1092 -Comment => 'Comment' ); 1093 ok $x->write($string) ; 1094 ok $x->close ; 1095 1096 ok defined $buffer ; 1097 1098 ok my $got = memGunzip($buffer) 1099 or diag "gzerrno is $gzerrno" ; 1100 is $got, $string ; 1101 is $gzerrno, 0; 1102} 1103 1104 1105{ 1106 # Trailer Corruption tests 1107 1108 my $string = <<EOM; 1109some text 1110EOM 1111 1112 my $good ; 1113 ok my $x = IO::Compress::Gzip->new( \$good, Append => 1 ); 1114 ok $x->write($string) ; 1115 ok $x->close ; 1116 1117 foreach my $trim (-8 .. -1) 1118 { 1119 my $got = $trim + 8 ; 1120 title "Trailer Corruption - Trailer truncated to $got bytes" ; 1121 my $buffer = $good ; 1122 1123 substr($buffer, $trim) = ''; 1124 1125 ok my $u = memGunzip(\$buffer) ; 1126 is $gzerrno, 0; 1127 ok $u eq $string; 1128 1129 } 1130 1131 { 1132 title "Trailer Corruption - Length Wrong, CRC Correct" ; 1133 my $buffer = $good ; 1134 substr($buffer, -4, 4) = pack('V', 1234); 1135 1136 ok ! memGunzip(\$buffer) ; 1137 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 1138 } 1139 1140 { 1141 title "Trailer Corruption - Length Wrong, CRC Wrong" ; 1142 my $buffer = $good ; 1143 substr($buffer, -4, 4) = pack('V', 1234); 1144 substr($buffer, -8, 4) = pack('V', 1234); 1145 1146 ok ! memGunzip(\$buffer) ; 1147 cmp_ok $gzerrno, "==", Z_DATA_ERROR ; 1148 1149 } 1150} 1151 1152 1153sub slurp 1154{ 1155 my $name = shift ; 1156 1157 my $input; 1158 my $fil = gzopen($name, "rb") ; 1159 ok $fil , "opened $name"; 1160 cmp_ok $fil->gzread($input, 50000), ">", 0, "read more than zero bytes"; 1161 ok ! $fil->gzclose(), "closed ok"; 1162 1163 return $input; 1164} 1165 1166sub trickle 1167{ 1168 my $name = shift ; 1169 1170 my $got; 1171 my $input; 1172 $fil = gzopen($name, "rb") ; 1173 ok $fil, "opened ok"; 1174 while ($fil->gzread($input, 50000) > 0) 1175 { 1176 $got .= $input; 1177 $input = ''; 1178 } 1179 ok ! $fil->gzclose(), "closed ok"; 1180 1181 return $got; 1182 1183 return $input; 1184} 1185 1186{ 1187 1188 title "Append & MultiStream Tests"; 1189 # rt.24041 1190 1191 my $lex = LexFile->new( my $name ); 1192 my $data1 = "the is the first"; 1193 my $data2 = "and this is the second"; 1194 my $trailing = "some trailing data"; 1195 1196 my $fil; 1197 1198 title "One file"; 1199 $fil = gzopen($name, "wb") ; 1200 ok $fil, "opened first file"; 1201 is $fil->gzwrite($data1), length $data1, "write data1" ; 1202 ok ! $fil->gzclose(), "Closed"; 1203 1204 is slurp($name), $data1, "got expected data from slurp"; 1205 is trickle($name), $data1, "got expected data from trickle"; 1206 1207 title "Two files"; 1208 $fil = gzopen($name, "ab") ; 1209 ok $fil, "opened second file"; 1210 is $fil->gzwrite($data2), length $data2, "write data2" ; 1211 ok ! $fil->gzclose(), "Closed"; 1212 1213 is slurp($name), $data1 . $data2, "got expected data from slurp"; 1214 is trickle($name), $data1 . $data2, "got expected data from trickle"; 1215 1216 title "Trailing Data"; 1217 open F, ">>$name"; 1218 print F $trailing; 1219 close F; 1220 1221 is slurp($name), $data1 . $data2 . $trailing, "got expected data from slurp" ; 1222 is trickle($name), $data1 . $data2 . $trailing, "got expected data from trickle" ; 1223} 1224 1225{ 1226 title "gzclose & gzflush return codes"; 1227 # rt.29215 1228 1229 my $lex = LexFile->new( my $name ); 1230 my $data1 = "the is some text"; 1231 my $status; 1232 1233 $fil = gzopen($name, "wb") ; 1234 ok $fil, "opened first file"; 1235 is $fil->gzwrite($data1), length $data1, "write data1" ; 1236 $status = $fil->gzflush(0xfff); 1237 ok $status, "flush not ok" ; 1238 is $status, Z_STREAM_ERROR; 1239 ok ! $fil->gzflush(), "flush ok" ; 1240 ok ! $fil->gzclose(), "Closed"; 1241} 1242 1243 1244 1245{ 1246 title "repeated calls to flush - no compression"; 1247 1248 my ($err, $x, $X, $status, $data); 1249 1250 ok( ($x, $err) = deflateInit ( ), "Create deflate object" ); 1251 isa_ok $x, "Compress::Raw::Zlib::deflateStream" ; 1252 cmp_ok $err, '==', Z_OK, "status is Z_OK" ; 1253 1254 1255 ($data, $status) = $x->flush(Z_SYNC_FLUSH) ; 1256 cmp_ok $status, '==', Z_OK, "flush returned Z_OK" ; 1257 ($data, $status) = $x->flush(Z_SYNC_FLUSH) ; 1258 cmp_ok $status, '==', Z_OK, "second flush returned Z_OK" ; 1259 is $data, "", "no output from second flush"; 1260} 1261 1262{ 1263 title "repeated calls to flush - after compression"; 1264 1265 my $hello = "I am a HAL 9000 computer" ; 1266 my ($err, $x, $X, $status, $data); 1267 1268 ok( ($x, $err) = deflateInit ( ), "Create deflate object" ); 1269 isa_ok $x, "Compress::Raw::Zlib::deflateStream" ; 1270 cmp_ok $err, '==', Z_OK, "status is Z_OK" ; 1271 1272 ($data, $status) = $x->deflate($hello) ; 1273 cmp_ok $status, '==', Z_OK, "deflate returned Z_OK" ; 1274 1275 ($data, $status) = $x->flush(Z_SYNC_FLUSH) ; 1276 cmp_ok $status, '==', Z_OK, "flush returned Z_OK" ; 1277 ($data, $status) = $x->flush(Z_SYNC_FLUSH) ; 1278 cmp_ok $status, '==', Z_OK, "second flush returned Z_OK" ; 1279 is $data, "", "no output from second flush"; 1280} 1281