From patchwork Sat Oct 24 23:17:11 2015 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peng Tao X-Patchwork-Id: 7480621 Return-Path: X-Original-To: patchwork-linux-nfs@patchwork.kernel.org Delivered-To: patchwork-parsemail@patchwork1.web.kernel.org Received: from mail.kernel.org (mail.kernel.org [198.145.29.136]) by patchwork1.web.kernel.org (Postfix) with ESMTP id 1EA579F36A for ; Sat, 24 Oct 2015 15:30:12 +0000 (UTC) Received: from mail.kernel.org (localhost [127.0.0.1]) by mail.kernel.org (Postfix) with ESMTP id 365E4206EF for ; Sat, 24 Oct 2015 15:30:11 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.kernel.org (Postfix) with ESMTP id 3CE5F207DB for ; Sat, 24 Oct 2015 15:30:10 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1752706AbbJXP31 (ORCPT ); Sat, 24 Oct 2015 11:29:27 -0400 Received: from mail-pa0-f51.google.com ([209.85.220.51]:34855 "EHLO mail-pa0-f51.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1752620AbbJXP3P (ORCPT ); Sat, 24 Oct 2015 11:29:15 -0400 Received: by pasz6 with SMTP id z6so144431897pas.2 for ; Sat, 24 Oct 2015 08:29:14 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=primarydata_com.20150623.gappssmtp.com; s=20150623; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=NiKL1iNygeKkEKzcJ8O95jrh4ghcBRT1GXG6jokAJh8=; b=RFStMY1on1I++ZcG4TYFetG2QtVV9ZNfmTt/KuOjiYD54aoF1OndRJI0F/gcdHJuK+ OE/FuKRIF7ajkq2MXRAAWMnddlb5SWqFH88PUpyQkeq5DrkBRt/zgJPDd52xpcGSwqY6 dav04idEQ4buN+BD2fkk5kbg9FAKlS+kQL8NxdQm+zlk6SvMMNi4XDddd18e/rMy+ocI cKYQU9hujAtrK6wrQ9Do0MJ1jCGBAi79nzyizf8SfTHlnXr9aymUz/wElCdvzqqe17oj hhcsVK7/NdGgXekOaqCHUn5JaL3Hq8BsuOxpSh3+/c3lKH9QWVLOjwwvcZ+/WJc6M7So Zn+w== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20130820; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=NiKL1iNygeKkEKzcJ8O95jrh4ghcBRT1GXG6jokAJh8=; b=IaNMUiQ5/1owg9Jxc2btNbk7qbyek5Nz7GLZlPzr4LwJr7Za1sLDkh0WuGse5TB5Jy /F08zRPNoVHf1MTpDcN7P41RaJR2bHQe04By2a5sgWhWtkEsyy11NncjoeRwQbfuAkmF D/9va5T+avmqPLDoqJ8TmrL4aBCjb9AyEOSZpG3tXpdmpqbftIDNtdF77cpUtVLz+ogz gJKPzIdh+u92J9Tkzy35QbkJluCRgeBYOOx8+JI0+bQbN7IizRFDlXFf95uQFASfyd5z yX1kVrlL1kKpqgbx1uUFeWUjCBtPGTF6Sj2oDGCuj4SgUK7ssDd2guHjjxdX89tydEF9 kY4g== X-Gm-Message-State: ALoCoQlxYlx7352tL6Wx0H6DLi6QLgYnDg6vwq4HhzOVUWVAT5tQkgfkNno82oEie+gFipukRhJp X-Received: by 10.68.163.195 with SMTP id yk3mr11766779pbb.120.1445700554645; Sat, 24 Oct 2015 08:29:14 -0700 (PDT) Received: from lear.localdomain (ec2-54-65-164-9.ap-northeast-1.compute.amazonaws.com. [54.65.164.9]) by smtp.gmail.com with ESMTPSA id nj1sm24764918pbc.2.2015.10.24.08.29.08 (version=TLSv1.2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Sat, 24 Oct 2015 08:29:14 -0700 (PDT) From: Peng Tao To: linux-fsdevel@vger.kernel.org Cc: Trond Myklebust , Anna Schumaker , Christoph Hellwig , Zach Brown , Darren Hart , Jeff Layton , bfields@fieldses.org, "Darrick J. Wong" , viro@zeniv.linux.org.uk, linux-nfs@vger.kernel.org, linux-btrfs@vger.kernel.org, linux-cifs@vger.kernel.org, Steve French , Peng Tao Subject: [PATCH 4/9] vfs: pull btrfs clone API to vfs layer Date: Sun, 25 Oct 2015 07:17:11 +0800 Message-Id: <1445728636-10109-5-git-send-email-tao.peng@primarydata.com> X-Mailer: git-send-email 1.8.3.1 In-Reply-To: <1445728636-10109-1-git-send-email-tao.peng@primarydata.com> References: <1445728636-10109-1-git-send-email-tao.peng@primarydata.com> Sender: linux-nfs-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org X-Spam-Status: No, score=-4.8 required=5.0 tests=BAYES_00, DATE_IN_FUTURE_06_12, DKIM_SIGNED, RCVD_IN_DNSWL_HI, RP_MATCHES_RCVD, T_DKIM_INVALID, UNPARSEABLE_RELAY autolearn=unavailable version=3.3.1 X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on mail.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Now that a few file systems are adding clone functionality, namingly btrfs, CIFS, NFS (in another series) and XFS (ttp://oss.sgi.com/archives/xfs/2015-06/msg00407.html), it makes sense to pull the ioctl to common code. Signed-off-by: Peng Tao --- fs/ioctl.c | 40 ++++++++++++++++++++++++++++++++++++++++ include/uapi/linux/fs.h | 9 +++++++++ 2 files changed, 49 insertions(+) diff --git a/fs/ioctl.c b/fs/ioctl.c index 5d01d26..9a78426 100644 --- a/fs/ioctl.c +++ b/fs/ioctl.c @@ -215,6 +215,40 @@ static int ioctl_fiemap(struct file *filp, unsigned long arg) return error; } +static long ioctl_file_clone(struct file *dst_file, unsigned long srcfd, + u64 off, u64 olen, u64 destoff) +{ + struct fd src_file = fdget(srcfd); + struct inode *src_inode; + int ret; + + if (!src_file.file) + return -EBADF; + /* olen == 0 means src off to eof */ + if (olen == 0) { + src_inode = file_inode(src_file.file); + olen = i_size_read(src_inode) - off; + } + ret = vfs_copy_file_range(src_file.file, off, dst_file, + destoff, olen, COPY_FILE_CLONE_ONLY); + /* vfs_copy_file_range returns bytes copied */ + if (ret > 0) + ret = 0; + + fdput(src_file); + return ret; +} + +static long ioctl_file_clone_range(struct file *file, void __user *argp) +{ + struct file_clone_range args; + + if (copy_from_user(&args, argp, sizeof(args))) + return -EFAULT; + return ioctl_file_clone(file, args.src_fd, args.src_offset, + args.src_length, args.dest_offset); +} + #ifdef CONFIG_BLOCK static inline sector_t logical_to_blk(struct inode *inode, loff_t offset) @@ -600,6 +634,12 @@ int do_vfs_ioctl(struct file *filp, unsigned int fd, unsigned int cmd, case FIGETBSZ: return put_user(inode->i_sb->s_blocksize, argp); + case FICLONE: + return ioctl_file_clone(filp, arg, 0, 0, 0); + + case FICLONERANGE: + return ioctl_file_clone_range(filp, argp); + default: if (S_ISREG(inode->i_mode)) error = file_ioctl(filp, cmd, arg); diff --git a/include/uapi/linux/fs.h b/include/uapi/linux/fs.h index 9b964a5..ac7f1c5 100644 --- a/include/uapi/linux/fs.h +++ b/include/uapi/linux/fs.h @@ -39,6 +39,13 @@ #define RENAME_EXCHANGE (1 << 1) /* Exchange source and dest */ #define RENAME_WHITEOUT (1 << 2) /* Whiteout source */ +struct file_clone_range { + __s64 src_fd; + __u64 src_offset; + __u64 src_length; + __u64 dest_offset; +}; + struct fstrim_range { __u64 start; __u64 len; @@ -159,6 +166,8 @@ struct inodes_stat_t { #define FIFREEZE _IOWR('X', 119, int) /* Freeze */ #define FITHAW _IOWR('X', 120, int) /* Thaw */ #define FITRIM _IOWR('X', 121, struct fstrim_range) /* Trim */ +#define FICLONE _IOW(0x94, 9, int) /* Clone */ +#define FICLONERANGE _IOW(0x94, 13, struct file_clone_range) /* Clone range */ #define FS_IOC_GETFLAGS _IOR('f', 1, long) #define FS_IOC_SETFLAGS _IOW('f', 2, long)