switch /dev/zero and /dev/full to ->read_iter()
authorAl Viro <viro@zeniv.linux.org.uk>
Mon, 18 Aug 2014 14:04:12 +0000 (10:04 -0400)
committerAl Viro <viro@zeniv.linux.org.uk>
Thu, 9 Oct 2014 06:39:08 +0000 (02:39 -0400)
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
drivers/char/mem.c

index 917403fe10da3eb62c0548bb29a2f0d898c8400a..524b707894ef14f43cf010bfd73c74928e811884 100644 (file)
@@ -622,53 +622,23 @@ static ssize_t splice_write_null(struct pipe_inode_info *pipe, struct file *out,
        return splice_from_pipe(pipe, out, ppos, len, flags, pipe_to_null);
 }
 
-static ssize_t read_zero(struct file *file, char __user *buf,
-                        size_t count, loff_t *ppos)
+static ssize_t read_iter_zero(struct kiocb *iocb, struct iov_iter *iter)
 {
-       size_t written;
-
-       if (!count)
-               return 0;
-
-       if (!access_ok(VERIFY_WRITE, buf, count))
-               return -EFAULT;
-
-       written = 0;
-       while (count) {
-               unsigned long unwritten;
-               size_t chunk = count;
+       size_t written = 0;
 
+       while (iov_iter_count(iter)) {
+               size_t chunk = iov_iter_count(iter), n;
                if (chunk > PAGE_SIZE)
                        chunk = PAGE_SIZE;      /* Just for latency reasons */
-               unwritten = __clear_user(buf, chunk);
-               written += chunk - unwritten;
-               if (unwritten)
-                       break;
+               n = iov_iter_zero(chunk, iter);
+               if (!n && iov_iter_count(iter))
+                       return written ? written : -EFAULT;
+               written += n;
                if (signal_pending(current))
                        return written ? written : -ERESTARTSYS;
-               buf += chunk;
-               count -= chunk;
                cond_resched();
        }
-       return written ? written : -EFAULT;
-}
-
-static ssize_t aio_read_zero(struct kiocb *iocb, const struct iovec *iov,
-                            unsigned long nr_segs, loff_t pos)
-{
-       size_t written = 0;
-       unsigned long i;
-       ssize_t ret;
-
-       for (i = 0; i < nr_segs; i++) {
-               ret = read_zero(iocb->ki_filp, iov[i].iov_base, iov[i].iov_len,
-                               &pos);
-               if (ret < 0)
-                       break;
-               written += ret;
-       }
-
-       return written ? written : -EFAULT;
+       return written;
 }
 
 static int mmap_zero(struct file *file, struct vm_area_struct *vma)
@@ -738,7 +708,6 @@ static int open_port(struct inode *inode, struct file *filp)
 #define zero_lseek     null_lseek
 #define full_lseek      null_lseek
 #define write_zero     write_null
-#define read_full       read_zero
 #define aio_write_zero aio_write_null
 #define open_mem       open_port
 #define open_kmem      open_mem
@@ -783,9 +752,9 @@ static const struct file_operations port_fops = {
 
 static const struct file_operations zero_fops = {
        .llseek         = zero_lseek,
-       .read           = read_zero,
+       .read           = new_sync_read,
        .write          = write_zero,
-       .aio_read       = aio_read_zero,
+       .read_iter      = read_iter_zero,
        .aio_write      = aio_write_zero,
        .mmap           = mmap_zero,
 };
@@ -802,7 +771,8 @@ static struct backing_dev_info zero_bdi = {
 
 static const struct file_operations full_fops = {
        .llseek         = full_lseek,
-       .read           = read_full,
+       .read           = new_sync_read,
+       .read_iter      = read_iter_zero,
        .write          = write_full,
 };