-/*
- * GPL HEADER START
- *
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 only,
- * as published by the Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful, but
- * WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * General Public License version 2 for more details (a copy is included
- * in the LICENSE file that accompanied this code).
- *
- * You should have received a copy of the GNU General Public License
- * version 2 along with this program; If not, see
- * http://www.gnu.org/licenses/gpl-2.0.html
- *
- * GPL HEADER END
- */
+// SPDX-License-Identifier: GPL-2.0
+
/*
* Copyright (c) 2020 Intel Corporation.
*/
+
/*
* Foreign symlink implementation.
*
{
struct ll_inode_info *lli = ll_i2info(inode);
struct ll_sb_info *sbi = ll_i2sbi(inode);
+ struct lmv_stripe_object *lsm_obj = NULL;
struct lov_foreign_md *lfm = NULL;
char *destname = NULL;
size_t lfm_size = 0;
* and LMV formats are identical, and then we also only need
* one set of parsing routines for both foreign files and dirs!
*/
- lfm = (struct lov_foreign_md *)(lli->lli_lsm_md);
- if (lfm != NULL) {
+ lsm_obj = lmv_stripe_object_get(lli->lli_lsm_obj);
+ up_read(&lli->lli_lsm_sem);
+
+ if (lsm_obj != NULL) {
+ lfm = (struct lov_foreign_md *)&lsm_obj->lso_lfm;
CDEBUG(D_INFO, "%s: inode "DFID": LMV cached found\n",
sbi->ll_fsname, PFID(ll_inode2fid(inode)));
} else {
failed:
if (S_ISDIR(inode->i_mode))
- up_read(&lli->lli_lsm_sem);
+ lmv_stripe_object_put(&lsm_obj);
if (S_ISREG(inode->i_mode) && lfm)
OBD_FREE(lfm, lfm_size);
static bool has_same_mount_namespace(struct ll_sb_info *sbi)
{
- int rc;
+ bool same;
- rc = (sbi->ll_mnt.mnt == current->fs->root.mnt);
- if (!rc)
+ same = (sbi->ll_mnt_ns == current->nsproxy->mnt_ns);
+ if (!same)
LCONSOLE_WARN("%s: client mount %s and '%s.%d' not in same mnt-namespace\n",
sbi->ll_fsname, sbi->ll_kset.kobj.name,
current->comm, current->pid);
- return rc;
+ return same;
}
ssize_t foreign_symlink_enable_show(struct kobject *kobj,
sbi->ll_foreign_symlink_prefix_size = new_len + 1;
up_write(&sbi->ll_foreign_symlink_sem);
- if (old)
- OBD_FREE(old, old_len);
+ OBD_FREE(old, old_len);
return new_len;
}
RETURN(rc == 0 ? count : rc);
}
+/* foreign fake-symlink version of ll_getattr() */
+#if defined(HAVE_USER_NAMESPACE_ARG)
+static int ll_foreign_symlink_getattr(struct mnt_idmap *map,
+ const struct path *path,
+ struct kstat *stat, u32 request_mask,
+ unsigned int flags)
+{
+ return ll_getattr_dentry(path->dentry, stat, request_mask, flags,
+ true);
+}
+#elif defined(HAVE_INODEOPS_ENHANCED_GETATTR)
+static int ll_foreign_symlink_getattr(const struct path *path,
+ struct kstat *stat, u32 request_mask,
+ unsigned int flags)
+{
+ return ll_getattr_dentry(path->dentry, stat, request_mask, flags,
+ true);
+}
+#else
+static int ll_foreign_symlink_getattr(struct vfsmount *mnt, struct dentry *de,
+ struct kstat *stat)
+{
+ return ll_getattr_dentry(de, stat, STATX_BASIC_STATS,
+ AT_STATX_SYNC_AS_STAT, true);
+}
+#endif
+
struct inode_operations ll_foreign_file_symlink_inode_operations = {
#ifdef HAVE_IOP_GENERIC_READLINK
.readlink = generic_readlink,
#endif
.listxattr = ll_listxattr,
};
-
-/* foreign fake-symlink version of ll_getattr() */
-#ifdef HAVE_INODEOPS_ENHANCED_GETATTR
-int ll_foreign_symlink_getattr(const struct path *path, struct kstat *stat,
- u32 request_mask, unsigned int flags)
-{
- return ll_getattr_dentry(path->dentry, stat, request_mask, flags,
- true);
-}
-#else
-int ll_foreign_symlink_getattr(struct vfsmount *mnt, struct dentry *de,
- struct kstat *stat)
-{
- return ll_getattr_dentry(de, stat, STATX_BASIC_STATS,
- AT_STATX_SYNC_AS_STAT, true);
-}
-#endif