xref: /freebsd/sys/contrib/openzfs/include/os/linux/kernel/linux/vfs_compat.h (revision 7a7741af18d6c8a804cc643cb7ecda9d730c6aa6)
1 /*
2  * CDDL HEADER START
3  *
4  * The contents of this file are subject to the terms of the
5  * Common Development and Distribution License (the "License").
6  * You may not use this file except in compliance with the License.
7  *
8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9  * or https://opensource.org/licenses/CDDL-1.0.
10  * See the License for the specific language governing permissions
11  * and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL HEADER in each
14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15  * If applicable, add the following below this CDDL HEADER, with the
16  * fields enclosed by brackets "[]" replaced with your own identifying
17  * information: Portions Copyright [yyyy] [name of copyright owner]
18  *
19  * CDDL HEADER END
20  */
21 
22 /*
23  * Copyright (C) 2011 Lawrence Livermore National Security, LLC.
24  * Copyright (C) 2015 Jörg Thalheim.
25  */
26 
27 #ifndef _ZFS_VFS_H
28 #define	_ZFS_VFS_H
29 
30 #include <sys/taskq.h>
31 #include <sys/cred.h>
32 #include <linux/backing-dev.h>
33 #include <linux/compat.h>
34 
35 /*
36  * 4.14 adds SB_* flag definitions, define them to MS_* equivalents
37  * if not set.
38  */
39 #ifndef	SB_RDONLY
40 #define	SB_RDONLY	MS_RDONLY
41 #endif
42 
43 #ifndef	SB_SILENT
44 #define	SB_SILENT	MS_SILENT
45 #endif
46 
47 #ifndef	SB_ACTIVE
48 #define	SB_ACTIVE	MS_ACTIVE
49 #endif
50 
51 #ifndef	SB_POSIXACL
52 #define	SB_POSIXACL	MS_POSIXACL
53 #endif
54 
55 #ifndef	SB_MANDLOCK
56 #define	SB_MANDLOCK	MS_MANDLOCK
57 #endif
58 
59 #ifndef	SB_NOATIME
60 #define	SB_NOATIME	MS_NOATIME
61 #endif
62 
63 #if defined(SEEK_HOLE) && defined(SEEK_DATA)
64 static inline loff_t
lseek_execute(struct file * filp,struct inode * inode,loff_t offset,loff_t maxsize)65 lseek_execute(
66 	struct file *filp,
67 	struct inode *inode,
68 	loff_t offset,
69 	loff_t maxsize)
70 {
71 #ifdef FMODE_UNSIGNED_OFFSET
72 	if (offset < 0 && !(filp->f_mode & FMODE_UNSIGNED_OFFSET))
73 #else
74 	if (offset < 0 && !(filp->f_op->fop_flags & FOP_UNSIGNED_OFFSET))
75 #endif
76 		return (-EINVAL);
77 
78 	if (offset > maxsize)
79 		return (-EINVAL);
80 
81 	if (offset != filp->f_pos) {
82 		spin_lock(&filp->f_lock);
83 		filp->f_pos = offset;
84 #ifdef HAVE_FILE_F_VERSION
85 		filp->f_version = 0;
86 #endif
87 		spin_unlock(&filp->f_lock);
88 	}
89 
90 	return (offset);
91 }
92 #endif /* SEEK_HOLE && SEEK_DATA */
93 
94 #if defined(CONFIG_FS_POSIX_ACL)
95 /*
96  * These functions safely approximates the behavior of posix_acl_release()
97  * which cannot be used because it calls the GPL-only symbol kfree_rcu().
98  * The in-kernel version, which can access the RCU, frees the ACLs after
99  * the grace period expires.  Because we're unsure how long that grace
100  * period may be this implementation conservatively delays for 60 seconds.
101  * This is several orders of magnitude larger than expected grace period.
102  * At 60 seconds the kernel will also begin issuing RCU stall warnings.
103  */
104 
105 #include <linux/posix_acl.h>
106 
107 void zpl_posix_acl_release_impl(struct posix_acl *);
108 
109 static inline void
zpl_posix_acl_release(struct posix_acl * acl)110 zpl_posix_acl_release(struct posix_acl *acl)
111 {
112 	if ((acl == NULL) || (acl == ACL_NOT_CACHED))
113 		return;
114 	if (refcount_dec_and_test(&acl->a_refcount))
115 		zpl_posix_acl_release_impl(acl);
116 }
117 #endif /* CONFIG_FS_POSIX_ACL */
118 
zfs_uid_read_impl(struct inode * ip)119 static inline uid_t zfs_uid_read_impl(struct inode *ip)
120 {
121 	return (from_kuid(kcred->user_ns, ip->i_uid));
122 }
123 
zfs_uid_read(struct inode * ip)124 static inline uid_t zfs_uid_read(struct inode *ip)
125 {
126 	return (zfs_uid_read_impl(ip));
127 }
128 
zfs_gid_read_impl(struct inode * ip)129 static inline gid_t zfs_gid_read_impl(struct inode *ip)
130 {
131 	return (from_kgid(kcred->user_ns, ip->i_gid));
132 }
133 
zfs_gid_read(struct inode * ip)134 static inline gid_t zfs_gid_read(struct inode *ip)
135 {
136 	return (zfs_gid_read_impl(ip));
137 }
138 
zfs_uid_write(struct inode * ip,uid_t uid)139 static inline void zfs_uid_write(struct inode *ip, uid_t uid)
140 {
141 	ip->i_uid = make_kuid(kcred->user_ns, uid);
142 }
143 
zfs_gid_write(struct inode * ip,gid_t gid)144 static inline void zfs_gid_write(struct inode *ip, gid_t gid)
145 {
146 	ip->i_gid = make_kgid(kcred->user_ns, gid);
147 }
148 
149 /*
150  * 3.15 API change
151  */
152 #ifndef RENAME_NOREPLACE
153 #define	RENAME_NOREPLACE	(1 << 0) /* Don't overwrite target */
154 #endif
155 #ifndef RENAME_EXCHANGE
156 #define	RENAME_EXCHANGE		(1 << 1) /* Exchange source and dest */
157 #endif
158 #ifndef RENAME_WHITEOUT
159 #define	RENAME_WHITEOUT		(1 << 2) /* Whiteout source */
160 #endif
161 
162 /*
163  * 4.9 API change
164  */
165 #if !(defined(HAVE_SETATTR_PREPARE_NO_USERNS) || \
166     defined(HAVE_SETATTR_PREPARE_USERNS) || \
167     defined(HAVE_SETATTR_PREPARE_IDMAP))
168 static inline int
setattr_prepare(struct dentry * dentry,struct iattr * ia)169 setattr_prepare(struct dentry *dentry, struct iattr *ia)
170 {
171 	return (inode_change_ok(dentry->d_inode, ia));
172 }
173 #endif
174 
175 /*
176  * 4.11 API change
177  * These macros are defined by kernel 4.11.  We define them so that the same
178  * code builds under kernels < 4.11 and >= 4.11.  The macros are set to 0 so
179  * that it will create obvious failures if they are accidentally used when built
180  * against a kernel >= 4.11.
181  */
182 
183 #ifndef STATX_BASIC_STATS
184 #define	STATX_BASIC_STATS	0
185 #endif
186 
187 #ifndef AT_STATX_SYNC_AS_STAT
188 #define	AT_STATX_SYNC_AS_STAT	0
189 #endif
190 
191 /*
192  * 4.11 API change
193  * 4.11 takes struct path *, < 4.11 takes vfsmount *
194  */
195 
196 #if defined(HAVE_PATH_IOPS_GETATTR)
197 #define	ZPL_GETATTR_WRAPPER(func)					\
198 static int								\
199 func(const struct path *path, struct kstat *stat, u32 request_mask,	\
200     unsigned int query_flags)						\
201 {									\
202 	return (func##_impl(path, stat, request_mask, query_flags));	\
203 }
204 #elif defined(HAVE_USERNS_IOPS_GETATTR)
205 #define	ZPL_GETATTR_WRAPPER(func)					\
206 static int								\
207 func(struct user_namespace *user_ns, const struct path *path,	\
208     struct kstat *stat, u32 request_mask, unsigned int query_flags)	\
209 {									\
210 	return (func##_impl(user_ns, path, stat, request_mask, \
211 	    query_flags));	\
212 }
213 #elif defined(HAVE_IDMAP_IOPS_GETATTR)
214 #define	ZPL_GETATTR_WRAPPER(func)					\
215 static int								\
216 func(struct mnt_idmap *user_ns, const struct path *path,	\
217     struct kstat *stat, u32 request_mask, unsigned int query_flags)	\
218 {									\
219 	return (func##_impl(user_ns, path, stat, request_mask,	\
220 	    query_flags));	\
221 }
222 #else
223 #error
224 #endif
225 
226 /*
227  * Returns true when called in the context of a 32-bit system call.
228  */
229 static inline int
zpl_is_32bit_api(void)230 zpl_is_32bit_api(void)
231 {
232 #ifdef CONFIG_COMPAT
233 	return (in_compat_syscall());
234 #else
235 	return (BITS_PER_LONG == 32);
236 #endif
237 }
238 
239 /*
240  * 5.12 API change
241  * To support id-mapped mounts, generic_fillattr() was modified to
242  * accept a new struct user_namespace* as its first arg.
243  *
244  * 6.3 API change
245  * generic_fillattr() first arg is changed to struct mnt_idmap *
246  *
247  * 6.6 API change
248  * generic_fillattr() gets new second arg request_mask, a u32 type
249  *
250  */
251 #ifdef HAVE_GENERIC_FILLATTR_IDMAP
252 #define	zpl_generic_fillattr(idmap, ip, sp)	\
253     generic_fillattr(idmap, ip, sp)
254 #elif defined(HAVE_GENERIC_FILLATTR_IDMAP_REQMASK)
255 #define	zpl_generic_fillattr(idmap, rqm, ip, sp)	\
256     generic_fillattr(idmap, rqm, ip, sp)
257 #elif defined(HAVE_GENERIC_FILLATTR_USERNS)
258 #define	zpl_generic_fillattr(user_ns, ip, sp)	\
259     generic_fillattr(user_ns, ip, sp)
260 #else
261 #define	zpl_generic_fillattr(user_ns, ip, sp)	generic_fillattr(ip, sp)
262 #endif
263 
264 #endif /* _ZFS_VFS_H */
265