On Thu, Jun 19, 2003 at 01:42:29PM -0400 zentara wrote:

> On Thu, 19 Jun 2003 01:37:09 -0700 (PDT), [EMAIL PROTECTED] (Ben Crane)
> wrote:

> >Thanx, I hunting the info down now, seems quite
> >complex. I'm wondering whether it might not be better
> >to have a crack at this in C? Have you found perlXS to
> >be difficult to implement?
> 
> Inline::C and Swig  are easier to do than XS. I hav'nt been able
> to get Swig to work with 5.8 though.  
> 
> Here is a simple program to mess with the cdrom tray.
> USING Swig:
> Run these commands in succession:
> 
> swig -perl5 cdrom.i gcc -fpic -c cdrom.c cdrom_wrap.c 
>           -Dbool=char -I/usr/lib/perl5/5.6.0/i586-linux/CORE
> gcc -shared cdrom_wrap.o cdrom.o -o Cdrom.so

That however is a pretty optimistic case. It's not always that
straight-forward, especially not when you want to craft your own more
Perlish interface.

Also, one problem with Swig is the fact that it is not exclusively for
Perl. It covers other scripting languages as well. This becomes quickly
apparent when manipulating the files generated by it.

> USING Inline::C:
> 
> #!/usr/bin/perl -w
> use warnings;
> use Inline C;
> use strict;
> 
> my $cd = '/dev/cdrom';
> 
> cdlock($cd,0); #unlocks cdrom
> cdeject($cd);  #ejects cdrom
> cdclose($cd);  #closes cdrom
> cdlock($cd,1); #locks cdrom 
> 
> exit;
> __END__
> __C__
> #include <stdio.h>
> #include <sys/ioctl.h>
> #include <linux/cdrom.h>
> #include <fcntl.h>
> #include <unistd.h>
> #include <stdlib.h>
> 
> #define CDROM "/dev/cdrom" 
> /* In all functions 'device' means name of CD-ROM device,
> * for example /dev/cdrom
> */
> 
> /* Close CD-ROM tray */
> int cdclose(char *device)
> {
> int fd = open(device, O_RDONLY|O_NONBLOCK);
> if (fd == -1)
> return -1;
> if (ioctl(fd, CDROMCLOSETRAY) == -1)
> return -1;
> close(fd);
> return 0;
> }

[...]

And finally the same in XS. It's not the slightest bit harder than with
Inline::C. The only difference with the XS code below is that I changed
the return values in that the functions now return false when something
goes wrong and true otherwise.

This is CDROM.xs [untested]:

#include "EXTERN.h"
#include "perl.h"
#include "XSUB.h"

#include "ppport.h"

#include <stdio.h>
#include <sys/ioctl.h>
#include <linux/cdrom.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdlib.h>

MODULE = CDROM          PACKAGE = CDROM

INCLUDE: const-xs.inc

void
cdclose(device) 
        char* device;
    PROTOTYPE: $
    PREINIT:
        int fd;
    PPCODE:
        if ((fd = open(device, O_RDONLY|O_NONBLOCK)) == -1);
            XSRETURN_NO;
        if (ioctl(fd, CDROMCLOSETRAY) == -1)
            XSRETURN_NO;
        close(fd);
        XSRETURN_YES;
        
void
cdeject(device)
        char *device;
    PROTOTYPE: $
    PREINIT:
        int fd;
    PPCODE:
        if ((fd = open(device, O_RDONLY|O_NONBLOCK)) == -1)
            XSRETURN_NO;
        if (ioctl(fd, CDROMEJECT) == -1)
            XSRETURN_NO;
        close(fd);
        XSRETURN_YES;
       
void
cdlock(device, lock)
        char *device;
        int lock;
    PROTOTYPE: $$
    PREINIT:
        int fd;
    PPCODE:
        if ((fd = open(device, O_RDONLY|O_NONBLOCK)) == -1)
            XSRETURN_NO;
        if (ioctl(fd, CDROM_LOCKDOOR, lock) == -1)
            XSRETURN_NO;
        close(fd);
        XSRETURN_YES;
        
The corresponding CDROM.pm is autogenerated by h2xs and can be used
literally. In the above the -b switch would have been used (as can be
seen because ppport.h and const-xs.inc were included). That would make
the XS portion of the code backwards compatible up to the specified
version of Perl.

I never quite understood people's fondness for Inline::C. The Inline
modules don't make the hard things easier in any way (you still have to
write your own typemaps if you need them for example). I would even say
that XS allow better control when working with several namespaces and
inheritance. And it's quite convenient in that a very well working and
easily to be extended skeleton is automatically created. Finally, the
usual 'perl Makefile.PL PARAMS=...; make; make test; etc' cycle is more
transparent and in fact pretty fool-proof. What I hated about Inline::C
was the fact that it created a small directory hierarchy (without me
asking it to do so) where it created files that for instance contained
the error messages that happened during compilation. With XS I all have
them sent to stderr which resembles very much the familiar way of
working with C and C compilers.

Tassilo
-- 
$_=q#",}])!JAPH!qq(tsuJ[{@"tnirp}3..0}_$;//::niam/s~=)]3[))_$-3(rellac(=_$({
pam{rekcahbus})(rekcah{lrePbus})(lreP{rehtonabus})!JAPH!qq(rehtona{tsuJbus#;
$_=reverse,s+(?<=sub).+q#q!'"qq.\t$&."'!#+sexisexiixesixeseg;y~\n~~dddd;eval


-- 
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to