#!/usr/bin/perl -w # 2001.08.27 altblue # much code ripped off CDDB_get module by Armin Obersteiner # ####### use strict; use warnings; use Fcntl; my $CD_DEVICE = defined $ARGV[0] ? $ARGV[0] : '/dev/cdrom'; # cdrom IOCTL magic (from c headers) # /usr/include/linux/cdrom.h my $CDROMREADTOCHDR=0x5305; my $CDROMREADTOCENTRY=0x5306; my $CDROM_MSF=0x02; my @toc = read_toc($CD_DEVICE); my $id = cddb_discid($#toc,\@toc); my $dir = sprintf "%08X", $id; -d $dir or mkdir $dir, 0755; my $out = sprintf "%08X/info.txt", $id; print "$out\n"; open OUT,">$out"; my @tstart=(0); foreach (@toc) { push @tstart, $_->{min}*60+$_->{sec} } my $track = 1; my ($mins,$secs) = (0,0); foreach (@toc) { if (defined $tstart[$track+1]) { $mins = int (($tstart[$track+1]-($_->{min}*60+$_->{sec}))/60); $secs = ($tstart[$track+1]-($_->{min}*60+$_->{sec}))%60; printf OUT "%02d.%50s%02d:%02d\n", $track++,' ', $mins, $secs; } } close OUT; sub read_toc { my $device=shift; my $tochdr=""; sysopen (CD,$device, O_RDONLY | O_NONBLOCK) or die "cannot open cdrom"; ioctl(CD, $CDROMREADTOCHDR, $tochdr) or die "cannot read toc"; my ($start,$end)=unpack "CC",$tochdr; my @tracks=(); for (my $i=$start; $i<=$end;$i++) { push @tracks,$i; } push @tracks,0xAA; my @r=(); foreach my $i (@tracks) { my $tocentry=pack "CCC", $i,0,$CDROM_MSF; ioctl(CD, $CDROMREADTOCENTRY, $tocentry) or die "cannot read track $i info"; my ($min,$sec,$frame)=unpack "CCCC", substr($tocentry,4,4); my %cdtoc=(); $cdtoc{min}=$min; $cdtoc{sec}=$sec; $cdtoc{frame}=$frame; $cdtoc{frames}=$frame+$sec*75+$min*60*75; push @r,\%cdtoc; } close(CD); return @r; } sub cddb_sum { my $n=shift; my $ret=0; while ($n > 0) { $ret += ($n % 10); $n = int $n / 10; } return $ret; } sub cddb_discid { my $total=shift; my $toc=shift; my $i=0; my $t=0; my $n=0; while ($i < $total) { $n = $n + cddb_sum(($toc->[$i]->{min} * 60) + $toc->[$i]->{sec}); $i++; } $t = (($toc->[$total]->{min} * 60) + $toc->[$total]->{sec}) - (($toc->[0]->{min} * 60) + $toc->[0]->{sec}); return (($n % 0xff) << 24 | $t << 8 | $total); }