diotalevi has asked for the wisdom of the Perl Monks concerning the following question:
I'm working with a data format where the file consists of contiguous binary records. The first two bytes are a packed integer and contain the record length inclusive of the packed integer. This means that for 142 bytes of data the record length is 144 (to include the leading two bytes as well).
I figured out that I could use the single unpack format '(n/a)*' if the record length didn't include those two bytes. I tried modifying that format to read '(n/a XX)*' to get unpack to step back two bytes so as to align correctly. That doesn't parse as valid perl. I ended up writing a while() loop to get the job done but I'm left wondering if there was a way to word that unpack format so it would work correctly. Any ideas?
# Sample working while() loop $sourceMetacodeLen = length $sourceMetacode; $sourceMetacodePos = 0; while ($sourceMetacodePos < $sourceMetacodeLen) { $recordLen = unpack( 'n', substr $sourceMetacode, $sourceMetacodePos, 2); $record = substr( $sourceMetacode, $sourceMetacodePos + 2, $recordLen - 2); # not relevant to the example # $parse .= ${translate_record(\$record, $sourceMetacodePos, \@ +fonts)}; $sourceMetacodePos += $recordLen; }
And here is an example of what the data looks like (after adding some newlines)
$ dd if=3012034-1.met bs=1 count=144|vis \^@\M^P\^@\^@+$DJDE$ FONTS=(UN104B,HE18BP,HE06NP,HE08OP,HE08NP,HE09BP, HE10BP,HE14BP,HE10VP,HE12NP,BLANKP,FORMSX,C395L ,HE12BP,HE36SP,HE08BP,HE 10NP),; \^A $ od -x 3012034-1.met | head 0000000 9000 0000 242b 4a44 4544 2024 2020 4f46 0000020 544e 3d53 5528 314e 3430 2c42 4548 3831 0000040 5042 482c 3045 4e36 2c50 4548 3830 504f 0000060 482c 3045 4e38 2c50 4548 3930 5042 482c 0000100 3145 4230 2c50 4548 3431 5042 482c 3145 0000120 5630 2c50 4548 3231 504e 422c 414c 4b4e 0000140 2c50 4f46 4d52 5853 432c 3933 4c35 2c20 0000160 4548 3231 5042 482c 3345 5336 2c50 4548 0000200 3830 5042 482c 3145 4e30 2950 3b2c 0120 $
__SIG__
printf "You are here %08x\n", unpack "L!", unpack "P4", pack "L!", B::svref_2object(sub{})->OUTSIDE
|
|---|
| Replies are listed 'Best First'. | |
|---|---|
|
Re: Unpacking fixed length records
by shenme (Priest) on Oct 06, 2002 at 22:46 UTC | |
by diotalevi (Canon) on Oct 07, 2002 at 00:15 UTC | |
by shenme (Priest) on Oct 07, 2002 at 04:43 UTC | |
by diotalevi (Canon) on Oct 07, 2002 at 14:29 UTC | |
|
Re: Unpacking fixed length records
by runrig (Abbot) on Oct 06, 2002 at 22:34 UTC | |
|
Re: Unpacking fixed length records
by Anonymous Monk on Oct 07, 2002 at 21:57 UTC | |
by diotalevi (Canon) on Oct 07, 2002 at 22:10 UTC | |
by Aristotle (Chancellor) on Oct 09, 2002 at 20:07 UTC |