in reply to CRC Error on ZIP Files

Solved !

SearchigPerl, are you still there? The updated snippet is not entirely correct; in particular, this chomp is a disaster waiting to happen:

while (read($peunter,$bytes,1024)) { unless (eof()) { chomp($bytes); } print $bytes; }

$bytes is a binary string, and it might just happen to have a trailing newline that chomp would happily remove, giving you a corrupted ZIP again. And the eof() check is entirely wrong (see the docs, particularly that bit about eof() being a special case).

There is nothing fundamentally wrong with your original loop:

while (read($peunter,$bytes,1024)) { print $bytes; }
So I'd just go with that.

Replies are listed 'Best First'.
Re^2: CRC Error on ZIP Files
by SearchigPerl (Acolyte) on Mar 05, 2014 at 18:31 UTC
    Hi hazylife,

    yes, I am still there - meaning here, just had to deal with some other major problem on my machine.
    Thanks for your hint, I digged into the documentation regarding the eol subject.
    I am not quite sure whether or not I really got the point. What I learned is, that obviously
    eol is far away from being reliable to determine the last buffer of the file to be transported.
    Yet what I had to realize is that if I go with the original version of the code, I end up
    with a downloaded file showing some more bytes than the original file is showing.
    If I chomp all buffers I end up with a file showing exactly 1 byte less than the original file.
    I tried to determine the last buffer to be transported by it's length. But the result is kind of erratic.
    2 out of three files end up corrupted ... The current version seems to be the only one working fine.
    (on various kinds of files (such as excel files, jpegs, mp4)
    Do have any idea, what I am doing wrong ?

    Cheers
      I'm out of ideas, sorry. If the eof()/chomp construct does actually help, then it would probably be best to leave it be it's a clear sign that some other part of the code is broken. Could you maybe post your whole script somewhere (e.g. pastebin.com, pastie.org, your public scratchpad etc.)?
        Hi Hazylife !

        sorry for answering late ! Yes, sure, below you find the complete script.
        It gets called with two parameters, the path and the name of the file to be downloaded

        I left all the commented sections inside, they result from different approaches
        to the function or they were meant to provide information
        of what the script was receiving and doing with it.

        Having downloaded the file, the source directory gets removed.
        Finally the script calls a defined URL to return to

        Thanks for your efforts !

        Cheers
        Uli

        #!/usr/bin/perl #use warnings; # open (datei, "<liste.txt"); # $verzeichnis=<datei>; # close datei; $Datten = $ENV{'QUERY_STRING'}; @Daten=split(/&/, $Datten); @dateien=split(/=/, @Daten[0]); @verz=split(/=/, @Daten[1]); $verzeichnis = @verz[1]; # print "Content-type: text/html\n\n"; # # print $Datten."<br>\n"; # print @Daten."<br>\n"; # print @dateien."<br>\n"; # print @verz."<br>\n"; # print $verzeichnis."<br>\n"; # print @dateien[1]."<br>\n"; # exit; download($verzeichnis, @dateien[1]); # $url = $verzeichnis.@dateien[1]; # print "Location: $url\n\n"; wait(); use File::Path qw( rmtree ); rmtree( $verzeichnis ); # Verzeichnisse in downloads, ‰lter as 1 Tag lˆschen # opendir(zeig,'../downloads/./'); # @entries = readdir(zeig); # close zeig; opendir zeig, '../downloads/./'; while ($entry = readdir zeig){ push (@entries, $entry); } #$index=-1; open (file, ">", "aktion.txt"); print file @entries; foreach $entry (@entries) { #$index++; print file $entry."\n"; if ($entry ne '.' && $entry ne '..' && $entry ne "index.html") { if(-d "../downloads/$entry") { if ((-M "../downloads/$entry") >1 ) { rmtree( "../downloads/$entry" ); print file " wurde gelöscht\n"; } } } } close (file); open (datei,">","fertig.txt"); print datei "Nachhause.pl !"; close datei; # $status=""; # $status=system("../cgi-bin/nachhause.pl","../donwloads/index.html"); # # wiederwarten: # unless ($status ne "") { # goto wiederwarten; # } heimat(); exit; sub download { use CGI; $html=new CGI; #print $html->header(-type => 'application/octet-stream', -attachment +=> $_[1]); print $html->header(-type => 'application/zip', -attachment => $_[1]); + open($peunter, "<", $_[0].$_[1]); binmode($peunter); binmode STDOUT; while (read($peunter,$bytes,1024)) { unless (eof()) { #unless (length($bytes)<1024) { chomp($bytes); } print $bytes; } #@data = <$peunter>; close($peunter); #print "@data"; } sub heimat { # use CGI; # # $htm=new CGI; # print $htm->header(-type =>'text/html', -expires => 'now'); # print $htm->system("../cgi-bin/nachhause.pl","../donwloads/index.htm +l"); $- =0; system("../cgi-bin/nachhause.pl","../donwloads/index.html"); }