I am (or was) attempting to reimplement the discid.c program that can be downloaded from freedb.org. I know I could use Inline, but want to see if I can do the full thing in perl. I got it to import some constants from some header files and I got it to read the toc header using ioctl. However, to read individual entries, I have to read information into a more complex structure using ioctl (the header was easy as it took the first two bytes from the returned scalar).

So, my question is, how do I read into a more complex structure. My C isn't as good as it could be but I have attempted to come up with a pack structure that mimics the struct but ioctl doesn't like it.

I have included the beginning of my script with some of the calling C code and the structs from linux/cdrom.h. Again, I know I could use Inline to do this and will do that if no answer works, but I would rather see if there is an answer for reading a complex structure via ioctl.

Note: it is the second ioctl call that fails.

#!/usr/bin/perl -w use strict; use vars qw(); use Fatal qw(open close ioctl); ### try to load some cdrom constants if( ! eval { require "linux/cdrom.ph" } ){ my $error; if( $@ =~ /^(Can\'t locate .+? in \@INC)/ ){ $error = $1 ."\n You may need to run h2ph.\n"; }else{ $error = $@; } print $error; print "Continuing with hard coded constants...\n"; ### copy from linux/cdrom.ph eval 'sub CDROMREADTOCHDR () {0x5305;}' unless defined(&CDROMREADTOC +HDR); eval 'sub CDROMREADTOCENTRY () {0x5306;}' unless defined(&CDROMREADT +OCENTRY); eval 'sub CDROM_MSF () {0x02;}' unless defined(&CDROM_MSF); } ### open the cdrom device print "Opening cd device...\n"; my $device = "/dev/hdc"; # not portable...yet open(_DEV,"<$device"); ### read the toc range print "Reading toc header...\n"; my $str = ''; ioctl(_DEV, CDROMREADTOCHDR(), $str); my $track0 = ord( substr($str,0,1) ); my $trackn = ord( substr($str,1,1) ); print "Track range: [$track0][$trackn]\n"; ### read the entries print "Reading toc entries...\n"; for(my $i = $track0; $i <= $trackn; $i ++){ my $track = $i; my $format = CDROM_MSF(); my $struct = "CC4C4CCCCiC"; my $str = pack($struct,$track,0,0,$format); ioctl(_DEV, CDROMREADTOCENTRY(), $str); my($_track,$adr,$ctrl,$_format, $min,$sec,$frame, $lba, $datamode) = unpack($struct,$str); print "$_track $adr $_format $min $sec $frame\n"; } print "Done\n"; __END__ # Sample calling code and structs # struct cdrom_tocentry tocentry; # tocentry.cdte_track = i; # tocentry.cdte_format = CDROM_MSF; # ioctl(drive, CDROMREADTOCENTRY, &tocentry); # # struct cdrom_msf0 # { # __u8 minute; # __u8 second; # __u8 frame; # }; # # /* Address in either MSF or logical format */ # union cdrom_addr # { # struct cdrom_msf0 msf; # int lba; # }; # # struct cdrom_tocentry # { # __u8 cdte_track; # __u8 cdte_adr :4; # __u8 cdte_ctrl :4; # __u8 cdte_format; # union cdrom_addr cdte_addr; # __u8 cdte_datamode; # };

my @a=qw(random brilliant braindead); print $a[rand(@a)];


In reply to ioctl into or from perl structs by Rhandom

Title:
Use:  <p> text here (a paragraph) </p>
and:  <code> code here </code>
to format your post, it's "PerlMonks-approved HTML":



  • Posts are HTML formatted. Put <p> </p> tags around your paragraphs. Put <code> </code> tags around your code and data!
  • Titles consisting of a single word are discouraged, and in most cases are disallowed outright.
  • Read Where should I post X? if you're not absolutely sure you're posting in the right place.
  • Please read these before you post! —
  • Posts may use any of the Perl Monks Approved HTML tags:
    a, abbr, b, big, blockquote, br, caption, center, col, colgroup, dd, del, details, div, dl, dt, em, font, h1, h2, h3, h4, h5, h6, hr, i, ins, li, ol, p, pre, readmore, small, span, spoiler, strike, strong, sub, summary, sup, table, tbody, td, tfoot, th, thead, tr, tt, u, ul, wbr
  • You may need to use entities for some characters, as follows. (Exception: Within code tags, you can put the characters literally.)
            For:     Use:
    & &amp;
    < &lt;
    > &gt;
    [ &#91;
    ] &#93;
  • Link using PerlMonks shortcuts! What shortcuts can I use for linking?
  • See Writeup Formatting Tips and other pages linked from there for more info.