in reply to yet another "reading binary data" question

We can't do much to polish code we can't see. Perhaps you need to show us a sample of what you have got?


Perl is environmentally friendly - it saves trees
  • Comment on Re: yet another "reading binary data" question

Replies are listed 'Best First'.
Re^2: yet another "reading binary data" question
by dwalin (Monk) on May 08, 2008 at 07:46 UTC
    ok, it's kludgy and non-perlish but here it goes:
    # # ECHI R11 (standard). # $ECHI_R11_LEN = 323; @ECHI_R11_FMT = ( ['CALLID', 'V', 0, 4], ['ACWTIME', 'V', 4, 4], ['ANSHOLDTIME', 'V', 8, 4], ['CONSULTTIME', 'V', 12, 4], ['DISPTIME', 'V', 16, 4], ['DURATION', 'V', 20, 4], ['SEGSTART', 'D', 24, 4], ['SEGSTOP', 'D', 28, 4], ['TALKTIME', 'V', 32, 4], ['NETINTIME', 'V', 36, 4], ['ORIGHOLDTIME', 'V', 40, 4], ['DISPIVECTOR', 'v', 44, 2], ['DISPSPLIT', 'v', 46, 2], ['FIRSTVECTOR', 'v', 48, 2], ['SPLIT1', 'v', 50, 2], ['SPLIT2', 'v', 52, 2], ['SPLIT3', 'v', 54, 2], ['TKGRP', 'v', 56, 2], ['EQ_LOCID', 'v', 58, 2], ['ORIG_LOCID', 'v', 60, 2], ['ANS_LOCID', 'v', 62, 2], ['OBS_LOCID', 'v', 64, 2], ['ASSIST', 'b', 66, 1, 0], ['AUDIO', 'b', 66, 1, 1], ['CONFERENCE', 'b', 66, 1, 2], ['DA_QUEUED', 'b', 66, 1, 3], ['HOLDABN', 'b', 66, 1, 4], ['MALICIOUS', 'b', 66, 1, 5], ['OBSERVINGCALL', 'b', 66, 1, 6], ['TRANSFERRED', 'b', 66, 1, 7], ['AGT_RELEASED', 'b', 67, 1, 0], ['ACD', 'V', 68, 1], ['DISPOSITION', 'V', 69, 1], ['DISPPRIORITY', 'V', 70, 1], ['HELD', 'V', 71, 1], ['SEGMENT', 'V', 72, 1], ['ANSREASON', 'V', 73, 1], ['ORIGREASON', 'V', 74, 1], ['DISPSKLEVEL', 'V', 75, 1], ['EVENT1', 'V', 76, 1], ['EVENT2', 'V', 77, 1], ['EVENT3', 'V', 78, 1], ['EVENT4', 'V', 79, 1], ['EVENT5', 'V', 80, 1], ['EVENT6', 'V', 81, 1], ['EVENT7', 'V', 82, 1], ['EVENT8', 'V', 83, 1], ['EVENT9', 'V', 84, 1], ['UCID', 'Z', 85, 21], ['DISPVDN', 'Z', 106, 8], ['EQLOC', 'Z', 114, 10], ['FIRSTVDN', 'Z', 124, 8], ['ORIGLOGIN', 'Z', 132, 10], ['ANSLOGIN', 'Z', 142, 10], ['LASTOBSERVER', 'Z', 152, 10], ['DIALED_NUM', 'Z', 162, 25], ['CALLING_PTY', 'Z', 187, 13], ['LASTDIGITS', 'Z', 200, 17], ['LASTCWC', 'Z', 217, 17], ['CALLING_II', 'Z', 234, 3], ['CWC1', 'Z', 237, 17], ['CWC2', 'Z', 254, 17], ['CWC3', 'Z', 271, 17], ['CWC4', 'Z', 288, 17], ['CWC5', 'Z', 305, 17] ); # # ECHI R12 (expanded). # $ECHI_R12_LEN = 493; @ECHI_R12_FMT = ( ['CALLID', 'V', 0, 4], ['ACWTIME', 'V', 4, 4], ['ANSHOLDTIME', 'V', 8, 4], ['CONSULTTIME', 'V', 12, 4], ['DISPTIME', 'V', 16, 4], ['DURATION', 'V', 20, 4], ['SEGSTART', 'V', 24, 4], ['SEGSTOP', 'V', 28, 4], ['TALKTIME', 'V', 32, 4], ['NETINTIME', 'V', 36, 4], ['ORIGHOLDTIME', 'V', 40, 4], # # Extended ECHI R12 fields # ['QUEUETIME', 'V', 44, 4], ['RINGTIME', 'V', 48, 4], # # End of Extended ECHI R12 fields # ['DISPIVECTOR', 'v', 52, 2], ['DISPSPLIT', 'v', 54, 2], ['FIRSTVECTOR', 'v', 56, 2], ['SPLIT1', 'v', 58, 2], ['SPLIT2', 'v', 60, 2], ['SPLIT3', 'v', 62, 2], ['TKGRP', 'v', 64, 2], ['EQ_LOCID', 'v', 66, 2], ['ORIG_LOCID', 'v', 68, 2], ['ANS_LOCID', 'v', 70, 2], ['OBS_LOCID', 'v', 72, 2], # # Extended ECHI R12 field # ['UUI_LEN', 'v', 74, 2], # # End of Extended ECHI R12 field # ['ASSIST', 'b', 76, 1, 0], ['AUDIO', 'b', 76, 1, 1], ['CONFERENCE', 'b', 76, 1, 2], ['DA_QUEUED', 'b', 76, 1, 3], ['HOLDABN', 'b', 76, 1, 4], ['MALICIOUS', 'b', 76, 1, 5], ['OBSERVINGCALL', 'b', 76, 1, 6], ['TRANSFERRED', 'b', 76, 1, 7], ['AGT_RELEASED', 'b', 77, 1, 0], ['ACD', 'C', 78, 1], ['DISPOSITION', 'C', 79, 1], ['DISPPRIORITY', 'C', 80, 1], ['HELD', 'C', 81, 1], ['SEGMENT', 'C', 82, 1], ['ANSREASON', 'C', 83, 1], ['ORIGREASON', 'C', 84, 1], ['DISPSKLEVEL', 'C', 85, 1], ['EVENT1', 'C', 86, 1], ['EVENT2', 'C', 87, 1], ['EVENT3', 'C', 88, 1], ['EVENT4', 'C', 89, 1], ['EVENT5', 'C', 90, 1], ['EVENT6', 'C', 91, 1], ['EVENT7', 'C', 92, 1], ['EVENT8', 'C', 93, 1], ['EVENT9', 'C', 94, 1], ['UCID', 'Z*', 95, 21], ['DISPVDN', 'Z*', 116, 8], ['EQLOC', 'Z*', 124, 10], ['FIRSTVDN', 'Z*', 134, 8], ['ORIGLOGIN', 'Z*', 142, 10], ['ANSLOGIN', 'Z*', 152, 10], ['LASTOBSERVER', 'Z*', 162, 10], ['DIALED_NUM', 'Z*', 172, 25], ['CALLING_PTY', 'Z*', 197, 13], ['LASTDIGITS', 'Z*', 210, 17], ['LASTCWC', 'Z*', 227, 17], ['CALLING_II', 'Z*', 244, 3], ['CWC1', 'Z*', 247, 17], ['CWC2', 'Z*', 264, 17], ['CWC3', 'Z*', 281, 17], ['CWC4', 'Z*', 298, 17], ['CWC5', 'Z*', 315, 17], # # Extended ECHI R12 fields # ['VDN2', 'Z*', 332, 8], ['VDN3', 'Z*', 340, 8], ['VDN4', 'Z*', 348, 8], ['VDN5', 'Z*', 356, 8], ['VDN6', 'Z*', 364, 8], ['VDN7', 'Z*', 372, 8], ['VDN8', 'Z*', 380, 8], ['VDN9', 'Z*', 388, 8], ['ASAI_UUI', 'Z*', 396, 96] ); [...skipped...] read(INFILE, $buf, 4); $version = unpack("V", $buf); read(INFILE, $buf, 4); $sequence = unpack("V", $buf); if ($version == 12 || $version == 11) { print localtime() . " Processing file $ARGV[0], version $version, se +quence $sequence\n"; } else { die localtime() . " Unsupported file version $version, can't process +!\n" }; undef $buf; my $rec_len = $version == 12 ? $ECHI_R12_LEN : $ECHI_R11_LEN; my $echi_fmt = $version == 12 ? \@ECHI_R12_FMT : \@ECHI_R11_FMT; my $processed = 0; print_header(OUTFILE, $echi_fmt) unless !$PRINT_HEADER; while(read(INFILE, $buf, $rec_len)) { my %record = unpack_record($buf, $echi_fmt); print localtime() . " Processing record $processed, Call ID " . $rec +ord{'CALLID'} . ", Segment " . $record{'SEGMENT'} . "\n"; print_record(OUTFILE, \%record, $echi_fmt); $processed++; }; [...skipped...] sub unpack_record { my $buf = shift; my $echi_format = shift; my $echi_rec = undef; my %record; my $str = undef; my $val = undef; foreach $echi_field (@$echi_format) { my $echi_name = @$echi_field[0]; my $echi_type = @$echi_field[1]; my $echi_offset = @$echi_field[2]; my $echi_len = @$echi_field[3]; my $echi_bitoffset = @$echi_field[4]; my $str = undef; $str = substr($buf, $echi_offset, $echi_len); if ($echi_type ne 'b') { $val = unpack($echi_type, $str); } else { $val = vec($str, $echi_bitoffset, 8); }; if ($echi_name =~ /SEG(START|STOP)/) { $val = strftime($DATE_FORMAT, localtime($val)) unless !$DATE_FORMA +T; }; if ($echi_name =~ /SPLIT[1-3]/) { $val -= 65536 if ($val > 32767); + }; if ($echi_type =~ /Z/) { $record{$echi_name} = "\"" . $val . "\""; } else { $record{$echi_name} = $val; }; }; return %record; }; sub print_header { my $file = shift; my $echi_format = shift; my $line = ""; foreach $echi_field (@$echi_format) { $line .= @$echi_field[0] . ","; }; $line =~ s/,$//; print $file "$line\n"; }; sub print_record { my $file = shift; my $record = shift; my $echi_format = shift; my $line = ""; foreach $echi_field (@$echi_format) { $name = @$echi_field[0]; $line .= $record->{$name} . ","; }; $line =~ s/,$//; print $file "$line\n"; };

    *blush* i guess my old pascal habits stick out... but at least it works. :) now, i was always told to optimize lately so now that i got working script i would like to optimize the hell out of it. that's the real fun. :)
Re^2: yet another "reading binary data" question
by Anonymous Monk on Jun 25, 2014 at 13:00 UTC
    Does anyone have an Perl Code for Echi Cms 16.2 Release ?