Apparently GNU mv is fond of extended attributes, and keeps breaking
9pfuse when I try to move a file between directories. This is the
culprit:
src/cmd/9pfuse/fuse.c:175:        case FUSE_SETXATTR:
src/cmd/9pfuse/fuse.c:176:                /* struct and two strings */

 In fact, SETXATTR comes with one string (the name of the attribute),
and one blob of arbitrary data (the length of which is given in the
fuse_setxattr_in struct). So:

src/cmd/9pfuse/fuse.c:179:                || ((char*)m->tx)[m->hdr->len-1] != 0

 the last byte of a well-formed message is not guaranteed to be NUL,
and this check is not sensible. Suggested fix (which works locally):

--- fuse.c      7 Nov 2007 22:31:22 -0000       1.11
+++ fuse.c      4 Jul 2008 04:57:15 -0000
@@ -173,10 +173,9 @@
                        goto bad;
                break;
        case FUSE_SETXATTR:
-               /* struct and two strings */
+               /* struct, one string and one binary blob */
                if(m->hdr->len <= sizeof(struct fuse_setxattr_in)
-               || ((char*)m->tx)[m->hdr->len-1] != 0
-               || memchr((uchar*)m->tx+sizeof(struct
fuse_setxattr_in), 0, m->hdr->len-sizeof(struct fuse_setxattr_in)-1)
== 0)
+               || ((char*)m->tx)[m->hdr->len-1-((struct
fuse_setxattr_in*)m->tx)->size] != 0)
                        goto bad;
                break;

 Dropped the memchr as it is clearly satisfied by the previous condition.
-sqweek

Reply via email to