Beefy Boxes and Bandwidth Generously Provided by pair Networks
Perl-Sensitive Sunglasses
 
PerlMonks  

More on hex pack/unpack

by BBQ (Curate)
on Jun 26, 2000 at 19:14 UTC ( [id://19856]=perlquestion: print w/replies, xml ) Need Help??

BBQ has asked for the wisdom of the Perl Monks concerning the following question:

OK, a follow up on this pack/unpack idea... After having embeded the image hex value into my script, the output seems somewhat garbled. Check it out for yourselves:

original image embeded image
The code generating the image for the embeded version is as follows:
#!/usr/bin/perl print "Content-type: image/gif\n\n"; print Image(); sub Image { my $image; $image = '4749463839610f001000a2ff00848684' . 'dfe0dfc6c7c6c0c0c000000000000000' . '000000000021f90401000003002c0000' . '00000f00100040034048baacf3608049' . 'a98824ca0aae78d9b375a4164a92470e' . '016a8dde10721c48dfc029ee528b0ac0' . 'e0671712'; return(pack("H*",$image)); }
The hex was just copied and pasted into the code from the unpack script that generated it. I can't see a reason why it should look any different than the original. Mdillon was kind enough to a round-trip integrity check on pack/unpack, and nothing seems to be wrong on that part. I have exausted my ideas. Anyone care to take a stab at this one?

TIA

Replies are listed 'Best First'.
Re: More on hex pack/unpack
by httptech (Chaplain) on Jun 26, 2000 at 20:20 UTC
    Ok, I took the good image and looked at it in a hex editor... Looks like your data is truncated, because the following works for me:
    print "Content-type: image/gif\n\n"; print Image(); sub Image { my $image = '4749463839610f001000a2ff00848684' . 'dfe0dfc6c7c6c0c0c000000000000000' . '000000000021f90401000003002c0000' . '00000f00100040034048baacf3608049' . 'a98824ca0aae78d9b375a4164a92470e' . '016a8dde10721c48dfc029ee528b0ac0' . 'e06717121a8132cd6729b4ed8cc4c891' . '97a45a09b286569100003b00'; return(pack("H*",$image)); }
    So the problem must lie in the unpack code.
      I have come to the source of my problem... STAY AWAY FROM ACTIVESTATE! I have 5.005_03 installed on both of my test machines, one running linux the other running NT 4.0. Guess what?

      The unpack code only truncates under the NT 4.0 machine. Same image source, same everything. #*$%^@ ActiveState distro! I'm going to install DynamicPerl now! Thanks for the helping hand, httptech!

      Code for unpacking (thanks mdillon) here:
      #!/usr/bin/perl open IMG, "foo.gif" or die "Couldn't open image: $!\n"; undef $/; $image = <IMG>; $hex = unpack("H*", $image); close IMG; while ($txt = substr($hex,0,32,'')) { print "'$txt'\n"; }


      #!/home/bbq/bin/perl
      # Trust no1!
        It's too late to help you, but I just got an advisory warning that the latest versions of ActiveState Perl are seriously broken.

        So, yeah, it looks like avoiding them for a while might be a very good thing.

        - Ozymandias

        Update: Here's the text; not an official advisory, but a warning from someone I know and trust:

        Activestate Perl 5.6 build 613. Stop! If you haven't downloaded this version of Perl for Windows. DON'T! The Perl Package Manager (PPM) section is fatally broken. If you don't need the ability to install or update modules I guess you can go ahead and download this. But otherwise. DON'T. Yes, they have a "Hotfix" that updates PPM to version 1.1.4. But it doesn't work. The PPM commands install, verify, update, search, and query do not work both before and after installing the "fix". What's worse is that Activestate has known of these problems for at least two months but is not saying a thing about it on their website (except for what is displayed on the bug tracking server). If I were them, I would immediately pull this distribution and wait until all of the problems were resolved rather than letting people blindly download this thinking it is a stable release. An extreme WTF experience.

        Since I got the warning, I've heard again from him that other things are broken; although he didn't mention pack or unpack, it wouldn't surprise me a bit if there's even more screwed up than he mentioned.

        i've only used Perl under Windows a couple times, but i believe this can be fixed by calling binmode on IMG before anything reads from it.
Re: More on hex pack/unpack
by Corion (Patriarch) on Jun 26, 2000 at 20:29 UTC

    Egads - httptech is right - BBQs file is truncated at the first 0x1A character. Maybe using binmode() would be a good idea. I always use binmode whenever I open binary files, even on operating systems that don't claim to need it...

    (0x1A is ^Z (EOF) under DOS, Win32 and the like and messes up reading from binary files, that's why you need binmode() for those files.)

      Corion, ^Z does more than just mess up reading from binary files. Consider the following code (I know it's nonsense, but bear with me):
      #/usr/bin/perl use CGI; my $query = new CGI; print "Where did this line go?\n";
      That code will work fine on linux, but in Active State Perl on my Windows box, that last line will never appear if I run it from the command line (admittedly, this might happen in all WinPerl versions). You can imagine my fun in debugging that.

      What's going on is that when I instantiate a new CGI object, I have to enter name=value pairs in offline mode. Then I press ^Z to stop that. Nothing else prints until I print a newline! (I've tried $| = 1 to no avail).

      Needless to say, this has made my life hell when I've debugged CGI scripts and forgotten about this little "feature".

      Update: To make matters worse, this feature appears to be intermittant. Every once in a while, with no code changes, "Where did this line go?" will appear.

RE: More on hex pack/unpack
by gnat (Beadle) on Jun 27, 2000 at 18:09 UTC
    Welcome to the world of Windows, where nothing works right. The problem here is that Windows has two modes for reading files: one is text mode, the other binary mode.

    Windows needs this because the standard I/O library, as it is supposed to, translates your machine's line endings into a \n for the C programs that manipulate data. Perl is written in C and uses the standard I/O library, so it happens. And we want it to--otherwise any program that wanted to print or read a line would have to know about all the different systems' line endings.

    Text mode is where line ending conversion happens. Binary mode is where it doesn't. If you're not reading a text file, but instead a binary file that happens to have a pair of characters in it that are the Windows line ending set, you don't want the stdio library rewriting your binary data! Binary mode good.

    However, that text/binary distinction also affects end of file. Windows has this stupid half-assed file system that keeps the length of the file in the directory entry, but also will return end of file when you're reading the file in text mode and have read a Ctrl-Z byte. So even though it knows full well by the directory entry that you haven't read all the data in the file, it's happy to pretend you have when you encounter the Ctrl-Z. The only reason I can think of for this is that on the console you have to be able to indicate EOF, and they use Ctrl-Z for this, so perhaps a naive implementation of it carried the Ctrl-Z bug over to non-terminal files as well? Who knows.

    So that's what you're running into. Your binary image data happens to have a Ctrl-Z byte in it, and that's prematurely ending your read. The solution is to say

    binmode(IMG);
    after you open the IMG filehandle. It doesn't change the behaviour on Unix, but makes it work right on Windows. sigh.
Re: More on hex pack/unpack
by httptech (Chaplain) on Jun 26, 2000 at 19:47 UTC
    Neither one of the images you supplied appear to work from your server. I tried your code on my own server and it shows as a 15x16 transparent GIF for me.
      Terribly sorry! My connection hasn't been very reliable these days. I just moved the samples to a new server:

      original image embeded image


      #!/home/bbq/bin/perl
      # Trust no1!

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://19856]
Approved by root
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others romping around the Monastery: (3)
As of 2025-02-18 18:44 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found