From patchwork Mon Oct 29 19:03:53 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Olga Kornievskaia X-Patchwork-Id: 990497 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=none (mailfrom) smtp.mailfrom=vger.kernel.org (client-ip=209.132.180.67; helo=vger.kernel.org; envelope-from=linux-cifs-owner@vger.kernel.org; receiver=) Authentication-Results: ozlabs.org; dmarc=pass (p=none dis=none) header.from=gmail.com Authentication-Results: ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=gmail.com header.i=@gmail.com header.b="JWfo1rDB"; dkim-atps=neutral Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id 42kPCm0jM5z9sBj for ; Tue, 30 Oct 2018 06:04:20 +1100 (AEDT) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1729479AbeJ3DyQ (ORCPT ); Mon, 29 Oct 2018 23:54:16 -0400 Received: from mail-qt1-f196.google.com ([209.85.160.196]:33339 "EHLO mail-qt1-f196.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1725969AbeJ3DyQ (ORCPT ); Mon, 29 Oct 2018 23:54:16 -0400 Received: by mail-qt1-f196.google.com with SMTP id i15-v6so10613557qtr.0; Mon, 29 Oct 2018 12:04:17 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=qWc4e/0MmfBIIgJWWnXm9U9/kkhvubDK4oN4lTXjqm4=; b=JWfo1rDBlJGsmP6/Tjb26ymRNA5Evw+upoKR9y/HE5cZAbv+tb8mipti6WheyXrv4Q A1lP9VJT8OyBMGWxxF309l5bAL6SEpEobMBSGQf9TaoFipcC3WWqiSh50KN+Yu81Yc/S wWFmhW1Z0X0jTE32lUXmr6YtFeGfD71BqKJ+HVOBP9XR73aQ+vFRidqqUHXm1bGkshlf qdsEs7OyAQu/gMwXAeoxCNSBiN9skp3tXZnzKLV9GBJEzyF1tryMtNXjWaz7w7vgx5r1 DjV/uJhjiGkkiLQa0VwaD1RpDuetWS1P4eo0yXrBXBQrDpdKh9leLwDLYEs9o7iTMCiH gEVA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=qWc4e/0MmfBIIgJWWnXm9U9/kkhvubDK4oN4lTXjqm4=; b=IwStD2faw4gd55RJ7jz5M96/lhpfQJlYAebr7H5vzrHIXLUaZebkWht3RQAtmMzP9w ewOzjv7l8HfVJF4EDb2ekXgs6TWqoKe/dhtbOQlFE9ZZzb89QlpVTHrhscXgAp3cYkXc it29xmbpYdv3NmrtQzKbHbdv0cvG+MPp71teQKJV2bAC7RM5a0FDRx6+eCX1IO57169M QXnE8zIYHCJnyK31M6sxwRATObBKmK4sdlMXveR3gdPy9iM0Li/TPsyZleVHS0/Tig5G Ko0Ltce1IYZegxuWe7WfPbqkE+KTrRK7acDB5QxRzpFqFvFF1E0sdIHb5/rq/xHf2sNB NYag== X-Gm-Message-State: AGRZ1gKSca0g5h6bUtuwiX3vxCYneE722PeletJNGTJDfApU6mQRR0dj BcnVUCIvP4phRE+TGmJUAG8= X-Google-Smtp-Source: AJdET5ehd7DBZWhx4fVBPXpQEABkROl9S7GceEwjqZNtLqZHjDWkpNCd5jKDDfBZOnVpJLdjxBlUkQ== X-Received: by 2002:a0c:8264:: with SMTP id h91mr7765457qva.116.1540839857155; Mon, 29 Oct 2018 12:04:17 -0700 (PDT) Received: from Olgas-MBP-195.attlocal.net (172-10-226-31.lightspeed.livnmi.sbcglobal.net. [172.10.226.31]) by smtp.gmail.com with ESMTPSA id c5-v6sm2714373qtj.55.2018.10.29.12.04.15 (version=TLS1 cipher=AES128-SHA bits=128/128); Mon, 29 Oct 2018 12:04:16 -0700 (PDT) From: Olga Kornievskaia To: trond.myklebust@hammerspace.com, anna.schumaker@netapp.com, viro@zeniv.linux.org.uk, smfrench@gmail.com, miklos@szeredi.hu Cc: linux-nfs@vger.kernel.org, linux-fsdevel@vger.kernel.org, linux-cifs@vger.kernel.org, linux-unionfs@vger.kernel.org, linux-man@vger.kernel.org Subject: [PATCH v6 08/12] NFS: inter ssc open Date: Mon, 29 Oct 2018 15:03:53 -0400 Message-Id: <20181029190357.38439-10-olga.kornievskaia@gmail.com> X-Mailer: git-send-email 2.10.1 (Apple Git-78) In-Reply-To: <20181029190357.38439-1-olga.kornievskaia@gmail.com> References: <20181029190357.38439-1-olga.kornievskaia@gmail.com> Sender: linux-cifs-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-cifs@vger.kernel.org From: Olga Kornievskaia NFSv4.2 inter server to server copy requires the destination server to READ the data from the source server using the provided stateid and file handle. Given an NFSv4 stateid and filehandle from the COPY operaion, provide the destination server with an NFS client function to create a struct file suitable for the destiniation server to READ the data to be copied. Signed-off-by: Olga Kornievskaia Signed-off-by: Andy Adamson --- fs/nfs/nfs4_fs.h | 7 +++++ fs/nfs/nfs4file.c | 94 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ fs/nfs/nfs4proc.c | 5 ++- 3 files changed, 103 insertions(+), 3 deletions(-) diff --git a/fs/nfs/nfs4_fs.h b/fs/nfs/nfs4_fs.h index 7d17b31..9c566a4 100644 --- a/fs/nfs/nfs4_fs.h +++ b/fs/nfs/nfs4_fs.h @@ -307,6 +307,13 @@ extern int nfs4_set_rw_stateid(nfs4_stateid *stateid, const struct nfs_open_context *ctx, const struct nfs_lock_context *l_ctx, fmode_t fmode); +extern int nfs4_proc_getattr(struct nfs_server *server, struct nfs_fh *fhandle, + struct nfs_fattr *fattr, struct nfs4_label *label, + struct inode *inode); +extern int update_open_stateid(struct nfs4_state *state, + const nfs4_stateid *open_stateid, + const nfs4_stateid *deleg_stateid, + fmode_t fmode); #if defined(CONFIG_NFS_V4_1) extern int nfs41_sequence_done(struct rpc_task *, struct nfs4_sequence_res *); diff --git a/fs/nfs/nfs4file.c b/fs/nfs/nfs4file.c index e5c1a68..0b1dcf9 100644 --- a/fs/nfs/nfs4file.c +++ b/fs/nfs/nfs4file.c @@ -8,6 +8,7 @@ #include #include #include +#include #include "delegation.h" #include "internal.h" #include "iostat.h" @@ -267,6 +268,99 @@ static int nfs42_clone_file_range(struct file *src_file, loff_t src_off, out: return ret; } + +static int read_name_gen = 1; +#define SSC_READ_NAME_BODY "ssc_read_%d" + +struct file * +nfs42_ssc_open(struct vfsmount *ss_mnt, struct nfs_fh *src_fh, + nfs4_stateid *stateid) +{ + struct nfs_fattr fattr; + struct file *filep, *res; + struct nfs_server *server; + struct inode *r_ino = NULL; + struct nfs_open_context *ctx; + struct nfs4_state_owner *sp; + char *read_name; + int len, status = 0; + + server = NFS_SERVER(ss_mnt->mnt_root->d_inode); + + nfs_fattr_init(&fattr); + + status = nfs4_proc_getattr(server, src_fh, &fattr, NULL, NULL); + if (status < 0) { + res = ERR_PTR(status); + goto out; + } + + res = ERR_PTR(-ENOMEM); + len = strlen(SSC_READ_NAME_BODY) + 16; + read_name = kzalloc(len, GFP_NOFS); + if (read_name == NULL) + goto out; + snprintf(read_name, len, SSC_READ_NAME_BODY, read_name_gen++); + + r_ino = nfs_fhget(ss_mnt->mnt_root->d_inode->i_sb, src_fh, &fattr, + NULL); + if (IS_ERR(r_ino)) { + res = ERR_CAST(r_ino); + goto out; + } + + filep = alloc_file_pseudo(r_ino, ss_mnt, read_name, FMODE_READ, + r_ino->i_fop); + if (IS_ERR(filep)) { + res = ERR_CAST(filep); + goto out; + } + filep->f_mode |= FMODE_READ; + + ctx = alloc_nfs_open_context(filep->f_path.dentry, filep->f_mode, + filep); + if (IS_ERR(ctx)) { + res = ERR_CAST(ctx); + goto out_filep; + } + + res = ERR_PTR(-EINVAL); + sp = nfs4_get_state_owner(server, ctx->cred, GFP_KERNEL); + if (sp == NULL) + goto out_ctx; + + ctx->state = nfs4_get_open_state(r_ino, sp); + if (ctx->state == NULL) + goto out_stateowner; + + set_bit(NFS_OPEN_STATE, &ctx->state->flags); + memcpy(&ctx->state->open_stateid.other, &stateid->other, + NFS4_STATEID_OTHER_SIZE); + update_open_stateid(ctx->state, stateid, NULL, filep->f_mode); + + nfs_file_set_open_context(filep, ctx); + put_nfs_open_context(ctx); + + file_ra_state_init(&filep->f_ra, filep->f_mapping->host->i_mapping); + res = filep; +out: + return res; +out_stateowner: + nfs4_put_state_owner(sp); +out_ctx: + put_nfs_open_context(ctx); +out_filep: + fput(filep); + goto out; +} +EXPORT_SYMBOL_GPL(nfs42_ssc_open); +void nfs42_ssc_close(struct file *filep) +{ + struct nfs_open_context *ctx = nfs_file_open_context(filep); + + ctx->state->flags = 0; +} +EXPORT_SYMBOL_GPL(nfs42_ssc_close); #endif /* CONFIG_NFS_V4_2 */ const struct file_operations nfs4_file_operations = { diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c index fec6e6b..e5178b2f 100644 --- a/fs/nfs/nfs4proc.c +++ b/fs/nfs/nfs4proc.c @@ -91,7 +91,6 @@ static int _nfs4_recover_proc_open(struct nfs4_opendata *data); static int nfs4_do_fsinfo(struct nfs_server *, struct nfs_fh *, struct nfs_fsinfo *); static void nfs_fixup_referral_attributes(struct nfs_fattr *fattr); -static int nfs4_proc_getattr(struct nfs_server *, struct nfs_fh *, struct nfs_fattr *, struct nfs4_label *label, struct inode *inode); static int _nfs4_proc_getattr(struct nfs_server *server, struct nfs_fh *fhandle, struct nfs_fattr *fattr, struct nfs4_label *label, struct inode *inode); static int nfs4_do_setattr(struct inode *inode, struct rpc_cred *cred, struct nfs_fattr *fattr, struct iattr *sattr, @@ -1653,7 +1652,7 @@ static void nfs_state_clear_delegation(struct nfs4_state *state) write_sequnlock(&state->seqlock); } -static int update_open_stateid(struct nfs4_state *state, +int update_open_stateid(struct nfs4_state *state, const nfs4_stateid *open_stateid, const nfs4_stateid *delegation, fmode_t fmode) @@ -3936,7 +3935,7 @@ static int _nfs4_proc_getattr(struct nfs_server *server, struct nfs_fh *fhandle, return nfs4_call_sync(server->client, server, &msg, &args.seq_args, &res.seq_res, 0); } -static int nfs4_proc_getattr(struct nfs_server *server, struct nfs_fh *fhandle, +int nfs4_proc_getattr(struct nfs_server *server, struct nfs_fh *fhandle, struct nfs_fattr *fattr, struct nfs4_label *label, struct inode *inode) {