X-Git-Url: http://git.rot13.org/?a=blobdiff_plain;f=Fuse.xs;h=893f1a0fd83615cfa07c25115cbaac253290bfb1;hb=7f982ef01e7f172d79086ef68ddfd5591397f541;hp=fb73a12794c0dac95e3534e397231e57d9fad634;hpb=4de2d39279b7cfcab70112b0986ee554a0c859ee;p=perl-fuse.git diff --git a/Fuse.xs b/Fuse.xs index fb73a12..893f1a0 100755 --- a/Fuse.xs +++ b/Fuse.xs @@ -5,7 +5,7 @@ #include -#if defined(__FreeBSD__) || defined(__NetBSD__) +#if (defined(__FreeBSD__) && __FreeBSD__ < 10) || defined(__NetBSD__) # define XATTR_CREATE 1 # define XATTR_REPLACE 2 #else @@ -1423,16 +1423,19 @@ int _PLfuse_bmap(const char *file, size_t blocksize, uint64_t *idx) { int _PLfuse_ioctl(const char *file, int cmd, void *arg, struct fuse_file_info *fi, unsigned int flags, void *data) { int rv; + SV *sv = NULL; FUSE_CONTEXT_PRE; DEBUGf("ioctl begin\n"); ENTER; SAVETMPS; PUSHMARK(SP); XPUSHs(sv_2mortal(newSVpv(file,0))); - XPUSHs(sv_2mortal(newSViv(cmd))); - XPUSHs(sv_2mortal(newSViv((uintptr_t)arg))); + /* I don't know why cmd is a signed int in the first place; + * casting as unsigned so stupid tricks don't have to be done on + * the perl side */ + XPUSHs(sv_2mortal(newSViv((unsigned int)cmd))); XPUSHs(sv_2mortal(newSViv(flags))); - if (_IOC_DIR(cmd) & _IOC_READ) + if (_IOC_DIR(cmd) & _IOC_WRITE) XPUSHs(sv_2mortal(newSVpvn(data, _IOC_SIZE(cmd)))); else XPUSHs(&PL_sv_undef); @@ -1440,12 +1443,18 @@ int _PLfuse_ioctl(const char *file, int cmd, void *arg, PUTBACK; rv = call_sv(MY_CXT.callback[39],G_ARRAY); SPAGAIN; - if (_IOC_DIR(cmd) & _IOC_WRITE) { - if (rv == 2) { - SV *sv = POPs; + if ((_IOC_DIR(cmd) & _IOC_READ) && (rv == 2)) { + sv = POPs; + rv--; + } + + if (rv > 0) + rv = POPi; + + if ((_IOC_DIR(cmd) & _IOC_READ) && !rv) { + if (sv) { size_t len; char *rdata = SvPV(sv, len); - rv--; if (len > _IOC_SIZE(cmd)) { fprintf(stderr, "ioctl(): returned data was too large for data area\n"); @@ -1457,12 +1466,10 @@ int _PLfuse_ioctl(const char *file, int cmd, void *arg, } } else { - fprintf(stderr, "ioctl(): ioctl was a write op, but no data was returned from call?\n"); + fprintf(stderr, "ioctl(): ioctl was a read op, but no data was returned from call?\n"); rv = -EFAULT; } } - if (rv > 0) - rv = POPi; FREETMPS; LEAVE; PUTBACK; @@ -1613,7 +1620,6 @@ fuse_version() OUTPUT: RETVAL -#ifndef __FreeBSD__ SV * XATTR_CREATE() CODE: @@ -1628,8 +1634,6 @@ XATTR_REPLACE() OUTPUT: RETVAL -#endif - void perl_fuse_main(...) PREINIT: