MPEG-Audio-Frame

 view release on metacpan or  search on metacpan

lib/MPEG/Audio/Frame.pm  view on Meta::CPAN

		return $self->{broken} = 0 unless (($self->{header}[LAYER] & 0x02) == 0x00); # can't sum

		my $bits = $protbits[$layer[$self->{header}[LAYER]]][$self->{header}[CHANMODE] == 0x03 ? 0 : 1 ];
		my $i;
			
		my $c = 0xffff;
			
		$c = ($c << 8) ^ $crc_table[(($c >> 8) ^ ord((substr($self->{binhead},2,1)))) & 0xff];
		$c = ($c << 8) ^ $crc_table[(($c >> 8) ^ ord((substr($self->{binhead},3,1)))) & 0xff];

		for ($i = 0; $bits >= 32; do { $bits-=32; $i+=4 }){
			my $data = unpack("N",substr($self->{content},$i,4));
				
			$c = ($c << 8) ^ $crc_table[(($c >> 8) ^ ($data >> 24)) & 0xff];
			$c = ($c << 8) ^ $crc_table[(($c >> 8) ^ ($data >> 16)) & 0xff];
			$c = ($c << 8) ^ $crc_table[(($c >> 8) ^ ($data >>  8)) & 0xff];
			$c = ($c << 8) ^ $crc_table[(($c >> 8) ^ ($data >>  0)) & 0xff];
				
		}
		while ($bits >= 8){
			$c = ($c << 8) ^ $crc_table[(($c >> 8) ^ (ord(substr($self->{content},$i++,1)))) & 0xff];
		} continue { $bits -= 8 }
		$self->{broken} = (( $c & 0xffff ) != unpack("n",$self->{crc_sum})) ? 1 : 0;
	}

	return $self->{broken};
}


# tie hack

sub TIEHANDLE { bless \$_[1],$_[0] } # encapsulate the handle to save on unblessing and stuff
sub READLINE { (ref $_[0])->read(${$_[0]}) } # read from the encapsulated handle

1; # keep your mother happy

__END__

=pod

=head1 NAME

MPEG::Audio::Frame - a class for weeding out MPEG audio frames out of a file
handle.

=head1 SYNOPSIS

	use MPEG::Audio::Frame;

	open FILE,"file.mp3";

	while(my $frame = MPEG::Audio::Frame->read(\*FILE)){
		print $frame->offset(), ": ", $frame->bitrate(), "Kbps/", $frame->sample()/1000, "KHz\n"; # or something.
	}

=head1 DESCRIPTION

A very simple, pure Perl module which allows parsing out data from mp3 files,
or streams, and chunking them up into different frames. You can use this to
accurately determine the length of an mp3, filter nonaudio data, or chunk up
the file for streaming via datagram. Virtually anything is possible.

=head1 MPEG FORMAT SUPPORT

L<MPEG::Audio::Frame> supports various types of MPEG data.

=over 4

=item MPEG-1

Any type of MPEG1 audio is supported, including the backwards compatible
multichannel extensions to MPEG-1. See F<t/20-mpeg1-*.t>.

=item MPEG-2 Multichannel

MPEG 2 has a variation on the multichannel extension, which is not backwards
compatible. It still structurally resembles MPEG 1, but there is no publically
documented method for telling apart MPEG-2 MC from MPEG-2 LSF.

=item MPEG-2 LSF

There is another type of MPEG 2, which is more similar to MPEG 2.5, called
MPEG-2 low sampling frequency. It the only type of MPEG-2 supported. See
F<t/20-mpeg2-22050>.

=item MPEG-2.5

This unofficial standard is also supported. Since it is unofficial, and
sometimes causes problems when streams contain garbage between frames, it can be disabled.

There is a test, F<t/20-mpeg2-test30.t>, which fails if MPEG 2.5 is allowed. It
is not included in the distribution because MPEG-2 multichannel is not
supported and those tests are just failing bloat. Ask me about darcs access if
you're curious.

=back

=head1 METHODS

There are two types of methods in this module, aside from the constructor
C<read>.

The first kind are accessors, which return the value of a certain header field,
like C<version>, which will return the actual integer value of the bits of that
field.

The second kind is sorts of queries on the accessible data. For example,
C<is_mono> checks to see of the C<channels> accessor returns the value for
mono.

=over 4

=item read GLOB

This is the constructor method. It receives a reference to a filehandle, and
reads the next (hopefully) valid frame it can find on the stream. Please make
sure use binmode if you're on a funny platform - the module doesn't know the
difference, and shouldn't change stuff, IMHO.

=item offset



( run in 2.049 seconds using v1.01-cache-2.11-cpan-6aa56a78535 )