diff mbox

[V9fs-developer,PATCH-V5,09/10] virtio-9p: Implement Security model for mknod

Message ID 1275700132-22823-10-git-send-email-jvrao@linux.vnet.ibm.com (mailing list archive)
State Not Applicable, archived
Headers show

Commit Message

jvrao June 5, 2010, 1:08 a.m. UTC
None
diff mbox

Patch

diff --git a/hw/file-op-9p.h b/hw/file-op-9p.h
index 0808630..5bc61b5 100644
--- a/hw/file-op-9p.h
+++ b/hw/file-op-9p.h
@@ -51,7 +51,7 @@  typedef struct FileOperations
     ssize_t (*readlink)(FsContext *, const char *, char *, size_t);
     int (*chmod)(FsContext *, const char *, FsCred *);
     int (*chown)(FsContext *, const char *, FsCred *);
-    int (*mknod)(FsContext *, const char *, mode_t, dev_t);
+    int (*mknod)(FsContext *, const char *, FsCred *);
     int (*mksock)(FsContext *, const char *);
     int (*utime)(FsContext *, const char *, const struct utimbuf *);
     int (*remove)(FsContext *, const char *);
diff --git a/hw/virtio-9p-local.c b/hw/virtio-9p-local.c
index fcc2250..b54624c 100644
--- a/hw/virtio-9p-local.c
+++ b/hw/virtio-9p-local.c
@@ -195,9 +195,39 @@  static int local_chmod(FsContext *fs_ctx, const char *path, FsCred *credp)
     return -1;
 }
 
-static int local_mknod(FsContext *ctx, const char *path, mode_t mode, dev_t dev)
+static int local_mknod(FsContext *fs_ctx, const char *path, FsCred *credp)
 {
-    return mknod(rpath(ctx, path), mode, dev);
+    int err = -1;
+    int serrno = 0;
+
+    /* Determine the security model */
+    if (fs_ctx->fs_sm == SM_MAPPED) {
+        err = mknod(rpath(fs_ctx, path), SM_LOCAL_MODE_BITS|S_IFREG, 0);
+        if (err == -1) {
+            return err;
+        }
+        local_set_xattr(rpath(fs_ctx, path), credp);
+        if (err == -1) {
+            serrno = errno;
+            goto err_end;
+        }
+    } else if (fs_ctx->fs_sm == SM_PASSTHROUGH) {
+        err = mknod(rpath(fs_ctx, path), credp->fc_mode, credp->fc_rdev);
+        if (err == -1) {
+            return err;
+        }
+        err = local_post_create_passthrough(fs_ctx, path, credp);
+        if (err == -1) {
+            serrno = errno;
+            goto err_end;
+        }
+    }
+    return err;
+
+err_end:
+    remove(rpath(fs_ctx, path));
+    errno = serrno;
+    return err;
 }
 
 static int local_mksock(FsContext *ctx2, const char *path)
diff --git a/hw/virtio-9p.c b/hw/virtio-9p.c
index 1a25e96..d276db3 100644
--- a/hw/virtio-9p.c
+++ b/hw/virtio-9p.c
@@ -160,9 +160,15 @@  static int v9fs_do_chmod(V9fsState *s, V9fsString *path, mode_t mode)
     return s->ops->chmod(&s->ctx, path->data, &cred);
 }
 
-static int v9fs_do_mknod(V9fsState *s, V9fsString *path, mode_t mode, dev_t dev)
+static int v9fs_do_mknod(V9fsState *s, V9fsCreateState *vs, mode_t mode,
+        dev_t dev)
 {
-    return s->ops->mknod(&s->ctx, path->data, mode, dev);
+    FsCred cred;
+    cred_init(&cred);
+    cred.fc_uid = vs->fidp->uid;
+    cred.fc_mode = mode;
+    cred.fc_rdev = dev;
+    return s->ops->mknod(&s->ctx, vs->fullname.data, &cred);
 }
 
 static int v9fs_do_mksock(V9fsState *s, V9fsString *path)
@@ -1825,10 +1831,10 @@  static void v9fs_create_post_lstat(V9fsState *s, V9fsCreateState *vs, int err)
         }
 
         nmode |= vs->perm & 0777;
-        err = v9fs_do_mknod(s, &vs->fullname, nmode, makedev(major, minor));
+        err = v9fs_do_mknod(s, vs, nmode, makedev(major, minor));
         v9fs_create_post_perms(s, vs, err);
     } else if (vs->perm & P9_STAT_MODE_NAMED_PIPE) {
-        err = v9fs_do_mknod(s, &vs->fullname, S_IFIFO | (vs->mode & 0777), 0);
+        err = v9fs_do_mknod(s, vs, S_IFIFO | (vs->perm & 0777), 0);
         v9fs_post_create(s, vs, err);
     } else if (vs->perm & P9_STAT_MODE_SOCKET) {
         err = v9fs_do_mksock(s, &vs->fullname);