summaryrefslogtreecommitdiff
path: root/drivers/base/dma-buf.c
diff options
context:
space:
mode:
authorEric Paris <eparis@redhat.com>2013-11-22 18:57:08 -0500
committerEric Paris <eparis@redhat.com>2013-11-22 18:57:54 -0500
commitfc582aef7dcc27a7120cf232c1e76c569c7b6eab (patch)
tree7d275dd4ceab6067b91e9a25a5f6338b425fbccd /drivers/base/dma-buf.c
parent9175c9d2aed528800175ef81c90569d00d23f9be (diff)
parent5e01dc7b26d9f24f39abace5da98ccbd6a5ceb52 (diff)
Merge tag 'v3.12'
Linux 3.12 Conflicts: fs/exec.c
Diffstat (limited to 'drivers/base/dma-buf.c')
-rw-r--r--drivers/base/dma-buf.c34
1 files changed, 33 insertions, 1 deletions
diff --git a/drivers/base/dma-buf.c b/drivers/base/dma-buf.c
index 6687ba741879..1e16cbd61da2 100644
--- a/drivers/base/dma-buf.c
+++ b/drivers/base/dma-buf.c
@@ -77,9 +77,36 @@ static int dma_buf_mmap_internal(struct file *file, struct vm_area_struct *vma)
return dmabuf->ops->mmap(dmabuf, vma);
}
+static loff_t dma_buf_llseek(struct file *file, loff_t offset, int whence)
+{
+ struct dma_buf *dmabuf;
+ loff_t base;
+
+ if (!is_dma_buf_file(file))
+ return -EBADF;
+
+ dmabuf = file->private_data;
+
+ /* only support discovering the end of the buffer,
+ but also allow SEEK_SET to maintain the idiomatic
+ SEEK_END(0), SEEK_CUR(0) pattern */
+ if (whence == SEEK_END)
+ base = dmabuf->size;
+ else if (whence == SEEK_SET)
+ base = 0;
+ else
+ return -EINVAL;
+
+ if (offset != 0)
+ return -EINVAL;
+
+ return base + offset;
+}
+
static const struct file_operations dma_buf_fops = {
.release = dma_buf_release,
.mmap = dma_buf_mmap_internal,
+ .llseek = dma_buf_llseek,
};
/*
@@ -133,7 +160,12 @@ struct dma_buf *dma_buf_export_named(void *priv, const struct dma_buf_ops *ops,
dmabuf->exp_name = exp_name;
file = anon_inode_getfile("dmabuf", &dma_buf_fops, dmabuf, flags);
+ if (IS_ERR(file)) {
+ kfree(dmabuf);
+ return ERR_CAST(file);
+ }
+ file->f_mode |= FMODE_LSEEK;
dmabuf->file = file;
mutex_init(&dmabuf->lock);
@@ -680,7 +712,7 @@ int dma_buf_debugfs_create_file(const char *name,
d = debugfs_create_file(name, S_IRUGO, dma_buf_debugfs_dir,
write, &dma_buf_debug_fops);
- return PTR_RET(d);
+ return PTR_ERR_OR_ZERO(d);
}
#else
static inline int dma_buf_init_debugfs(void)