projects/linux·blob master · refs

1235 lines · 31.4 KiB

1// SPDX-License-Identifier: LGPL-2.1
2/*
3 *
4 * vfs operations that deal with dentries
5 *
6 * Copyright (C) International Business Machines Corp., 2002,2009
7 * Author(s): Steve French ([email protected])
8 *
9 */
10#include <linux/fs.h>
11#include <linux/stat.h>
12#include <linux/slab.h>
13#include <linux/namei.h>
14#include <linux/mount.h>
15#include <linux/file.h>
16#include "cifsfs.h"
17#include "cifsglob.h"
18#include "cifsproto.h"
19#include "cifs_debug.h"
20#include "cifs_fs_sb.h"
21#include "cifs_unicode.h"
22#include "fs_context.h"
23#include "cifs_ioctl.h"
24#include "fscache.h"
25#include "cached_dir.h"
26
27static void
28renew_parental_timestamps(struct dentry *direntry)
29{
30 /* BB check if there is a way to get the kernel to do this or if we
31 really need this */
32 do {
33 cifs_set_time(direntry, jiffies);
34 direntry = direntry->d_parent;
35 } while (!IS_ROOT(direntry));
36}
37
38char *
39cifs_build_path_to_root(struct smb3_fs_context *ctx, struct cifs_sb_info *cifs_sb,
40 struct cifs_tcon *tcon, int add_treename)
41{
42 int pplen = ctx->prepath ? strlen(ctx->prepath) + 1 : 0;
43 int dfsplen;
44 char *full_path = NULL;
45
46 /* if no prefix path, simply set path to the root of share to "" */
47 if (pplen == 0) {
48 full_path = kzalloc(1, GFP_KERNEL);
49 return full_path;
50 }
51
52 if (add_treename)
53 dfsplen = strnlen(tcon->tree_name, MAX_TREE_SIZE + 1);
54 else
55 dfsplen = 0;
56
57 full_path = kmalloc(dfsplen + pplen + 1, GFP_KERNEL);
58 if (full_path == NULL)
59 return full_path;
60
61 if (dfsplen)
62 memcpy(full_path, tcon->tree_name, dfsplen);
63 full_path[dfsplen] = CIFS_DIR_SEP(cifs_sb);
64 memcpy(full_path + dfsplen + 1, ctx->prepath, pplen);
65 convert_delimiter(full_path, CIFS_DIR_SEP(cifs_sb));
66 return full_path;
67}
68
69/* Note: caller must free return buffer */
70const char *
71build_path_from_dentry(struct dentry *direntry, void *page)
72{
73 struct cifs_sb_info *cifs_sb = CIFS_SB(direntry->d_sb);
74 struct cifs_tcon *tcon = cifs_sb_master_tcon(cifs_sb);
75 bool prefix = tcon->Flags & SMB_SHARE_IS_IN_DFS;
76
77 return build_path_from_dentry_optional_prefix(direntry, page,
78 prefix);
79}
80
81char *__build_path_from_dentry_optional_prefix(struct dentry *direntry, void *page,
82 const char *tree, int tree_len,
83 bool prefix)
84{
85 struct cifs_sb_info *cifs_sb = CIFS_SB(direntry);
86 unsigned int sbflags = cifs_sb_flags(cifs_sb);
87 char dirsep = CIFS_DIR_SEP(cifs_sb);
88 int pplen = 0;
89 int dfsplen;
90 char *s;
91
92 if (unlikely(!page))
93 return ERR_PTR(-ENOMEM);
94
95 if (prefix)
96 dfsplen = strnlen(tree, tree_len + 1);
97 else
98 dfsplen = 0;
99
100 if (sbflags & CIFS_MOUNT_USE_PREFIX_PATH)
101 pplen = cifs_sb->prepath ? strlen(cifs_sb->prepath) + 1 : 0;
102
103 s = dentry_path_raw(direntry, page, PATH_MAX);
104 if (IS_ERR(s))
105 return s;
106 if (!s[1]) // for root we want "", not "/"
107 s++;
108 if (s < (char *)page + pplen + dfsplen)
109 return ERR_PTR(-ENAMETOOLONG);
110 if (pplen) {
111 cifs_dbg(FYI, "using cifs_sb prepath <%s>\n", cifs_sb->prepath);
112 s -= pplen;
113 memcpy(s + 1, cifs_sb->prepath, pplen - 1);
114 *s = '/';
115 }
116 if (dirsep != '/') {
117 /* BB test paths to Windows with '/' in the midst of prepath */
118 strreplace(s, '/', dirsep);
119 }
120 if (dfsplen) {
121 s -= dfsplen;
122 memcpy(s, tree, dfsplen);
123 if (sbflags & CIFS_MOUNT_POSIX_PATHS) {
124 int i;
125 for (i = 0; i < dfsplen; i++) {
126 if (s[i] == '\\')
127 s[i] = '/';
128 }
129 }
130 }
131 return s;
132}
133
134char *build_path_from_dentry_optional_prefix(struct dentry *direntry, void *page,
135 bool prefix)
136{
137 struct cifs_sb_info *cifs_sb = CIFS_SB(direntry->d_sb);
138 struct cifs_tcon *tcon = cifs_sb_master_tcon(cifs_sb);
139
140 return __build_path_from_dentry_optional_prefix(direntry, page, tcon->tree_name,
141 MAX_TREE_SIZE, prefix);
142}
143
144/*
145 * Don't allow path components longer than the server max.
146 * Don't allow the separator character in a path component.
147 * The VFS will not allow "/", but "\" is allowed by posix.
148 */
149static int
150check_name(struct dentry *direntry, struct cifs_tcon *tcon)
151{
152 struct cifs_sb_info *cifs_sb = CIFS_SB(direntry);
153 int i;
154
155 if (unlikely(tcon->fsAttrInfo.MaxPathNameComponentLength &&
156 direntry->d_name.len >
157 le32_to_cpu(tcon->fsAttrInfo.MaxPathNameComponentLength)))
158 return -ENAMETOOLONG;
159
160 if (!(cifs_sb_flags(cifs_sb) & CIFS_MOUNT_POSIX_PATHS)) {
161 for (i = 0; i < direntry->d_name.len; i++) {
162 if (direntry->d_name.name[i] == '\\') {
163 cifs_dbg(FYI, "Invalid file name\n");
164 return -EINVAL;
165 }
166 }
167 }
168 return 0;
169}
170
171static char *alloc_parent_path(struct dentry *dentry, size_t namelen)
172{
173 struct cifs_sb_info *cifs_sb = CIFS_SB(dentry);
174 void *page = alloc_dentry_path();
175 const char *path;
176 size_t size;
177 char *npath;
178
179 path = build_path_from_dentry(dentry->d_parent, page);
180 if (IS_ERR(path)) {
181 npath = ERR_CAST(path);
182 goto out;
183 }
184
185 size = strlen(path) + namelen + 2;
186 npath = kmalloc(size, GFP_KERNEL);
187 if (!npath)
188 npath = ERR_PTR(-ENOMEM);
189 else
190 scnprintf(npath, size, "%s%c", path, CIFS_DIR_SEP(cifs_sb));
191out:
192 free_dentry_path(page);
193 return npath;
194}
195
196/* Inode operations in similar order to how they appear in Linux file fs.h */
197static int __cifs_do_create(struct inode *dir, struct dentry *direntry,
198 const char *full_path, unsigned int xid,
199 struct tcon_link *tlink, unsigned int oflags,
200 umode_t mode, __u32 *oplock, struct cifs_fid *fid,
201 struct cifs_open_info_data *buf,
202 struct inode **inode, bool *opened)
203{
204 int rc = -ENOENT;
205 int create_options = CREATE_NOT_DIR;
206 int desired_access;
207 struct cifs_sb_info *cifs_sb = CIFS_SB(dir);
208 struct cifs_tcon *tcon = tlink_tcon(tlink);
209 struct inode *newinode = NULL;
210 unsigned int sbflags = cifs_sb_flags(cifs_sb);
211 int disposition;
212 struct TCP_Server_Info *server = tcon->ses->server;
213 struct cifs_open_parms oparms;
214 struct cached_fid *parent_cfid = NULL;
215 int rdwr_for_fscache = 0;
216 __le32 lease_flags = 0;
217
218 *inode = NULL;
219 *opened = false;
220 *oplock = 0;
221 if (tcon->ses->server->oplocks)
222 *oplock = REQ_OPLOCK;
223
224 /* If we're caching, we need to be able to fill in around partial writes. */
225 if (cifs_fscache_enabled(dir) && (oflags & O_ACCMODE) == O_WRONLY)
226 rdwr_for_fscache = 1;
227
228#ifdef CONFIG_CIFS_ALLOW_INSECURE_LEGACY
229 if (tcon->unix_ext && cap_unix(tcon->ses) && !tcon->broken_posix_open &&
230 (CIFS_UNIX_POSIX_PATH_OPS_CAP &
231 le64_to_cpu(tcon->fsUnixInfo.Capability))) {
232 rc = cifs_posix_open(full_path, &newinode, dir->i_sb, mode,
233 oflags, oplock, &fid->netfid, xid);
234 switch (rc) {
235 case 0:
236 *opened = true;
237 if (newinode == NULL) {
238 /* query inode info */
239 goto cifs_create_get_file_info;
240 }
241
242 if ((oflags & __O_REGULAR) && !S_ISREG(newinode->i_mode)) {
243 CIFSSMBClose(xid, tcon, fid->netfid);
244 iput(newinode);
245 return -EFTYPE;
246 }
247
248 if (S_ISDIR(newinode->i_mode)) {
249 CIFSSMBClose(xid, tcon, fid->netfid);
250 iput(newinode);
251 return -EISDIR;
252 }
253
254 if (!S_ISREG(newinode->i_mode)) {
255 /*
256 * The server may allow us to open things like
257 * FIFOs, but the client isn't set up to deal
258 * with that. Keep the handle until the caller
259 * can finish the lookup.
260 */
261 goto cifs_create_get_file_info;
262 }
263 /* success, no need to query */
264 goto cifs_create_set_dentry;
265
266 case -ENOENT:
267 goto cifs_create_get_file_info;
268
269 case -EIO:
270 case -EINVAL:
271 /*
272 * EIO could indicate that (posix open) operation is not
273 * supported, despite what server claimed in capability
274 * negotiation.
275 *
276 * POSIX open in samba versions 3.3.1 and earlier could
277 * incorrectly fail with invalid parameter.
278 */
279 tcon->broken_posix_open = true;
280 break;
281
282 case -EREMOTE:
283 case -EOPNOTSUPP:
284 /*
285 * EREMOTE indicates DFS junction, which is not handled
286 * in posix open. If either that or op not supported
287 * returned, follow the normal lookup.
288 */
289 break;
290
291 default:
292 return rc;
293 }
294 /*
295 * fallthrough to retry, using older open call, this is case
296 * where server does not support this SMB level, and falsely
297 * claims capability (also get here for DFS case which should be
298 * rare for path not covered on files)
299 */
300 }
301#endif /* CONFIG_CIFS_ALLOW_INSECURE_LEGACY */
302
303 desired_access = 0;
304 if (OPEN_FMODE(oflags) & FMODE_READ)
305 desired_access |= GENERIC_READ; /* is this too little? */
306 if (OPEN_FMODE(oflags) & FMODE_WRITE)
307 desired_access |= GENERIC_WRITE;
308 if (rdwr_for_fscache == 1)
309 desired_access |= GENERIC_READ;
310 if (oflags & O_TMPFILE)
311 desired_access |= DELETE;
312
313 disposition = FILE_OVERWRITE_IF;
314 if (oflags & O_CREAT) {
315 if (oflags & O_EXCL)
316 disposition = FILE_CREATE;
317 else if (oflags & O_TRUNC)
318 disposition = FILE_OVERWRITE_IF;
319 else
320 disposition = FILE_OPEN_IF;
321 } else if (oflags & O_TMPFILE) {
322 disposition = FILE_CREATE;
323 } else {
324 cifs_dbg(FYI, "Create flag not set in create function\n");
325 }
326
327 /*
328 * BB add processing to set equivalent of mode - e.g. via CreateX with
329 * ACLs
330 */
331
332 if (!server->ops->open)
333 return -EOPNOTSUPP;
334
335 create_options |= cifs_open_create_options(oflags, create_options);
336 /*
337 * if we're not using unix extensions, see if we need to set
338 * ATTR_READONLY on the create call
339 */
340 if (!tcon->unix_ext && (mode & S_IWUGO) == 0)
341 create_options |= CREATE_OPTION_READONLY;
342
343
344retry_open:
345 if (tcon->cfids && direntry->d_parent && server->dialect >= SMB30_PROT_ID) {
346 parent_cfid = NULL;
347 spin_lock(&tcon->cfids->cfid_list_lock);
348 list_for_each_entry(parent_cfid, &tcon->cfids->entries, entry) {
349 if (parent_cfid->dentry == direntry->d_parent) {
350 cifs_dbg(FYI, "found a parent cached file handle\n");
351 if (is_valid_cached_dir(parent_cfid)) {
352 lease_flags
353 |= SMB2_LEASE_FLAG_PARENT_LEASE_KEY_SET_LE;
354 memcpy(fid->parent_lease_key,
355 parent_cfid->fid.lease_key,
356 SMB2_LEASE_KEY_SIZE);
357 parent_cfid->dirents.is_valid = false;
358 parent_cfid->dirents.is_failed = true;
359 }
360 break;
361 }
362 }
363 spin_unlock(&tcon->cfids->cfid_list_lock);
364 }
365
366 oparms = (struct cifs_open_parms) {
367 .tcon = tcon,
368 .cifs_sb = cifs_sb,
369 .desired_access = desired_access,
370 .create_options = cifs_create_options(cifs_sb, create_options),
371 .disposition = disposition,
372 .path = full_path,
373 .fid = fid,
374 .lease_flags = lease_flags,
375 .mode = mode,
376 };
377 rc = server->ops->open(xid, &oparms, oplock, buf);
378 if (rc) {
379 cifs_dbg(FYI, "cifs_create returned 0x%x\n", rc);
380 if (rc == -EACCES && rdwr_for_fscache == 1) {
381 desired_access &= ~GENERIC_READ;
382 rdwr_for_fscache = 2;
383 goto retry_open;
384 }
385 return rc;
386 }
387 *opened = true;
388 if (rdwr_for_fscache == 2)
389 cifs_invalidate_cache(dir, FSCACHE_INVAL_DIO_WRITE);
390
391#ifdef CONFIG_CIFS_ALLOW_INSECURE_LEGACY
392 /*
393 * If Open reported that we actually created a file then we now have to
394 * set the mode if possible.
395 */
396 if ((tcon->unix_ext) && (*oplock & CIFS_CREATE_ACTION)) {
397 struct cifs_unix_set_info_args args = {
398 .mode = mode,
399 .ctime = NO_CHANGE_64,
400 .atime = NO_CHANGE_64,
401 .mtime = NO_CHANGE_64,
402 .device = 0,
403 };
404
405 if (sbflags & CIFS_MOUNT_SET_UID) {
406 args.uid = current_fsuid();
407 if (dir->i_mode & S_ISGID)
408 args.gid = dir->i_gid;
409 else
410 args.gid = current_fsgid();
411 } else {
412 args.uid = INVALID_UID; /* no change */
413 args.gid = INVALID_GID; /* no change */
414 }
415 CIFSSMBUnixSetFileInfo(xid, tcon, &args, fid->netfid,
416 current->tgid);
417 } else {
418 /*
419 * BB implement mode setting via Windows security
420 * descriptors e.g.
421 */
422
423 /* Could set r/o dos attribute if mode & 0222 == 0 */
424 }
425
426cifs_create_get_file_info:
427 /* server might mask mode so we have to query for it */
428 if (tcon->unix_ext)
429 rc = cifs_get_inode_info_unix(&newinode, full_path, dir->i_sb,
430 xid);
431 else {
432#else
433 {
434#endif /* CONFIG_CIFS_ALLOW_INSECURE_LEGACY */
435 /* TODO: Add support for calling POSIX query info here, but passing in fid */
436 rc = cifs_get_inode_info(&newinode, full_path, buf, dir->i_sb, xid, fid);
437 if (newinode) {
438 if (server->ops->set_lease_key)
439 server->ops->set_lease_key(newinode, fid);
440 if ((*oplock & CIFS_CREATE_ACTION) && S_ISREG(newinode->i_mode)) {
441 if (sbflags & CIFS_MOUNT_DYNPERM)
442 newinode->i_mode = mode;
443 if (sbflags & CIFS_MOUNT_SET_UID) {
444 newinode->i_uid = current_fsuid();
445 if (dir->i_mode & S_ISGID)
446 newinode->i_gid = dir->i_gid;
447 else
448 newinode->i_gid = current_fsgid();
449 }
450 }
451 }
452 }
453
454#ifdef CONFIG_CIFS_ALLOW_INSECURE_LEGACY
455cifs_create_set_dentry:
456#endif /* CONFIG_CIFS_ALLOW_INSECURE_LEGACY */
457 if (rc != 0) {
458 cifs_dbg(FYI, "Create worked, get_inode_info failed rc = %d\n",
459 rc);
460 goto out_err;
461 }
462
463 if (newinode) {
464 if ((oflags & __O_REGULAR) && !S_ISREG(newinode->i_mode)) {
465 rc = -EFTYPE;
466 goto out_err;
467 }
468 if (S_ISDIR(newinode->i_mode)) {
469 rc = -EISDIR;
470 goto out_err;
471 }
472 }
473
474 *inode = newinode;
475 return rc;
476
477out_err:
478 if (*opened && server->ops->close)
479 server->ops->close(xid, tcon, fid);
480 if (newinode)
481 iput(newinode);
482 return rc;
483}
484
485static int cifs_do_create(struct inode *dir, struct dentry *direntry,
486 unsigned int xid, struct tcon_link *tlink,
487 unsigned int oflags, umode_t mode,
488 __u32 *oplock, struct cifs_fid *fid,
489 struct cifs_open_info_data *buf,
490 struct inode **inode, bool *opened)
491{
492 void *page = alloc_dentry_path();
493 const char *full_path;
494 int rc;
495
496 full_path = build_path_from_dentry(direntry, page);
497 if (IS_ERR(full_path)) {
498 rc = PTR_ERR(full_path);
499 *opened = false;
500 } else {
501 rc = __cifs_do_create(dir, direntry, full_path, xid,
502 tlink, oflags, mode, oplock,
503 fid, buf, inode, opened);
504 }
505 free_dentry_path(page);
506 return rc;
507}
508
509
510/*
511 * Look up, create and open a CIFS file.
512 *
513 * The initial dentry state is in-lookup or hashed-negative. On success, dentry
514 * will become hashed-positive by calling d_splice_alias() if in-lookup,
515 * otherwise d_instantiate().
516 */
517int cifs_atomic_open(struct inode *dir, struct dentry *direntry,
518 struct file *file, unsigned int oflags, umode_t mode)
519{
520 struct cifs_sb_info *cifs_sb = CIFS_SB(dir);
521 struct cifs_open_info_data buf = {};
522 struct TCP_Server_Info *server;
523 struct cifsFileInfo *file_info;
524 struct cifs_pending_open open;
525 struct cifs_fid fid = {};
526 struct tcon_link *tlink;
527 struct cifs_tcon *tcon;
528 unsigned int sbflags;
529 struct dentry *alias;
530 struct inode *inode;
531 unsigned int xid;
532 __u32 oplock;
533 bool is_regular;
534 bool opened;
535 int rc;
536
537 if (unlikely(cifs_forced_shutdown(cifs_sb)))
538 return smb_EIO(smb_eio_trace_forced_shutdown);
539
540 /*
541 * Posix open is only called (at lookup time) for file create now. For
542 * opens (rather than creates), because we do not know if it is a file
543 * or directory yet, and current Samba no longer allows us to do posix
544 * open on dirs, we could end up wasting an open call on what turns out
545 * to be a dir. For file opens, we wait to call posix open till
546 * cifs_open. It could be added to atomic_open in the future but the
547 * performance tradeoff of the extra network request when EISDIR or
548 * EACCES is returned would have to be weighed against the 50% reduction
549 * in network traffic in the other paths.
550 */
551 if (!(oflags & O_CREAT)) {
552 /*
553 * Check for hashed negative dentry. We have already revalidated
554 * the dentry and it is fine. No need to perform another lookup.
555 */
556 if (!d_in_lookup(direntry))
557 return -ENOENT;
558
559 return finish_no_open(file, cifs_lookup(dir, direntry, 0));
560 }
561
562 xid = get_xid();
563
564 cifs_dbg(FYI, "parent inode = 0x%p name is: %pd and dentry = 0x%p\n",
565 dir, direntry, direntry);
566
567 tlink = cifs_sb_tlink(cifs_sb);
568 if (IS_ERR(tlink)) {
569 rc = PTR_ERR(tlink);
570 goto out_free_xid;
571 }
572
573 tcon = tlink_tcon(tlink);
574
575 rc = check_name(direntry, tcon);
576 if (rc)
577 goto out;
578
579 server = tcon->ses->server;
580
581 if (server->ops->new_lease_key)
582 server->ops->new_lease_key(&fid);
583
584 cifs_add_pending_open(&fid, tlink, &open);
585
586 rc = cifs_do_create(dir, direntry, xid, tlink, oflags, mode,
587 &oplock, &fid, &buf, &inode, &opened);
588 if (rc) {
589 cifs_del_pending_open(&open);
590 goto out;
591 }
592
593 is_regular = S_ISREG(inode->i_mode);
594 if (!is_regular || !opened) {
595 if (opened && server->ops->close)
596 server->ops->close(xid, tcon, &fid);
597 cifs_del_pending_open(&open);
598 if (S_ISLNK(inode->i_mode) &&
599 (oflags & (O_NOFOLLOW | __O_REGULAR)) ==
600 (O_NOFOLLOW | __O_REGULAR) && !(oflags & O_EXCL)) {
601 iput(inode);
602 rc = -ELOOP;
603 goto out;
604 }
605 }
606
607 if (d_in_lookup(direntry)) {
608 alias = d_splice_alias(inode, direntry);
609 if (!IS_ERR_OR_NULL(alias))
610 direntry = alias;
611 } else {
612 d_instantiate(direntry, inode);
613 }
614
615 if (is_regular && opened &&
616 (oflags & (O_CREAT | O_EXCL)) == (O_CREAT | O_EXCL))
617 file->f_mode |= FMODE_CREATED;
618
619 if (!is_regular || !opened) {
620 rc = finish_no_open(file, NULL);
621 goto out;
622 }
623
624 rc = finish_open(file, direntry, generic_file_open);
625 if (rc) {
626 if (server->ops->close)
627 server->ops->close(xid, tcon, &fid);
628 cifs_del_pending_open(&open);
629 goto out;
630 }
631
632 sbflags = cifs_sb_flags(cifs_sb);
633 if ((file->f_flags & O_DIRECT) && (sbflags & CIFS_MOUNT_STRICT_IO)) {
634 if (sbflags & CIFS_MOUNT_NO_BRL)
635 file->f_op = &cifs_file_direct_nobrl_ops;
636 else
637 file->f_op = &cifs_file_direct_ops;
638 }
639
640 file_info = cifs_new_fileinfo(&fid, file, tlink, oplock, buf.symlink_target);
641 if (file_info == NULL) {
642 if (server->ops->close)
643 server->ops->close(xid, tcon, &fid);
644 cifs_del_pending_open(&open);
645 rc = -ENOMEM;
646 goto out;
647 }
648
649 fscache_use_cookie(cifs_inode_cookie(file_inode(file)),
650 file->f_mode & FMODE_WRITE);
651
652out:
653 cifs_put_tlink(tlink);
654out_free_xid:
655 free_xid(xid);
656 cifs_free_open_info(&buf);
657 return rc;
658}
659
660/*
661 * Create a CIFS file.
662 *
663 * The initial dentry state is hashed-negative. On success, dentry will become
664 * hashed-positive by calling d_instantiate().
665 */
666int cifs_create(const struct mnt_idmap *idmap, struct inode *dir,
667 struct dentry *direntry, umode_t mode)
668{
669 struct cifs_sb_info *cifs_sb = CIFS_SB(dir);
670 int rc;
671 unsigned int xid = get_xid();
672 /*
673 * BB below access is probably too much for mknod to request
674 * but we have to do query and setpathinfo so requesting
675 * less could fail (unless we want to request getatr and setatr
676 * permissions (only). At least for POSIX we do not have to
677 * request so much.
678 */
679 unsigned oflags = O_EXCL | O_CREAT | O_RDWR;
680 struct tcon_link *tlink;
681 struct cifs_tcon *tcon;
682 struct TCP_Server_Info *server;
683 struct inode *inode;
684 struct cifs_fid fid;
685 __u32 oplock;
686 bool opened;
687 struct cifs_open_info_data buf = {};
688
689 cifs_dbg(FYI, "cifs_create parent inode = 0x%p name is: %pd and dentry = 0x%p\n",
690 dir, direntry, direntry);
691
692 if (unlikely(cifs_forced_shutdown(cifs_sb))) {
693 rc = smb_EIO(smb_eio_trace_forced_shutdown);
694 goto out_free_xid;
695 }
696
697 tlink = cifs_sb_tlink(cifs_sb);
698 rc = PTR_ERR(tlink);
699 if (IS_ERR(tlink))
700 goto out_free_xid;
701
702 tcon = tlink_tcon(tlink);
703 server = tcon->ses->server;
704
705 if (server->ops->new_lease_key)
706 server->ops->new_lease_key(&fid);
707
708 rc = cifs_do_create(dir, direntry, xid, tlink, oflags,
709 mode, &oplock, &fid, &buf, &inode, &opened);
710 if (!rc) {
711 d_instantiate(direntry, inode);
712 if (opened && server->ops->close)
713 server->ops->close(xid, tcon, &fid);
714 }
715
716 cifs_free_open_info(&buf);
717 cifs_put_tlink(tlink);
718out_free_xid:
719 free_xid(xid);
720 return rc;
721}
722
723int cifs_mknod(const struct mnt_idmap *idmap, struct inode *inode,
724 struct dentry *direntry, umode_t mode, dev_t device_number)
725{
726 int rc = -EPERM;
727 unsigned int xid;
728 struct cifs_sb_info *cifs_sb;
729 struct tcon_link *tlink;
730 struct cifs_tcon *tcon;
731 const char *full_path;
732 void *page;
733
734 if (!old_valid_dev(device_number))
735 return -EINVAL;
736
737 cifs_sb = CIFS_SB(inode->i_sb);
738 if (unlikely(cifs_forced_shutdown(cifs_sb)))
739 return smb_EIO(smb_eio_trace_forced_shutdown);
740
741 tlink = cifs_sb_tlink(cifs_sb);
742 if (IS_ERR(tlink))
743 return PTR_ERR(tlink);
744
745 page = alloc_dentry_path();
746 tcon = tlink_tcon(tlink);
747 xid = get_xid();
748
749 full_path = build_path_from_dentry(direntry, page);
750 if (IS_ERR(full_path)) {
751 rc = PTR_ERR(full_path);
752 goto mknod_out;
753 }
754
755 trace_smb3_mknod_enter(xid, tcon->tid, tcon->ses->Suid, full_path);
756
757 rc = tcon->ses->server->ops->make_node(xid, inode, direntry, tcon,
758 full_path, mode,
759 device_number);
760
761mknod_out:
762 if (rc)
763 trace_smb3_mknod_err(xid, tcon->tid, tcon->ses->Suid, rc);
764 else
765 trace_smb3_mknod_done(xid, tcon->tid, tcon->ses->Suid);
766
767 free_dentry_path(page);
768 free_xid(xid);
769 cifs_put_tlink(tlink);
770 return rc;
771}
772
773struct dentry *
774cifs_lookup(struct inode *parent_dir_inode, struct dentry *direntry,
775 unsigned int flags)
776{
777 unsigned int xid;
778 int rc = 0; /* to get around spurious gcc warning, set to zero here */
779 struct cifs_sb_info *cifs_sb;
780 struct tcon_link *tlink;
781 struct cifs_tcon *pTcon;
782 struct inode *newInode = NULL;
783 const char *full_path;
784 void *page;
785 int retry_count = 0;
786 struct dentry *de;
787
788 xid = get_xid();
789
790 cifs_dbg(FYI, "parent inode = 0x%p name is: %pd and dentry = 0x%p\n",
791 parent_dir_inode, direntry, direntry);
792
793 /* check whether path exists */
794
795 cifs_sb = CIFS_SB(parent_dir_inode->i_sb);
796 tlink = cifs_sb_tlink(cifs_sb);
797 if (IS_ERR(tlink)) {
798 de = ERR_CAST(tlink);
799 goto free_xid;
800 }
801 pTcon = tlink_tcon(tlink);
802
803 rc = check_name(direntry, pTcon);
804 if (unlikely(rc)) {
805 de = ERR_PTR(rc);
806 goto put_tlink;
807 }
808
809 /* can not grab the rename sem here since it would
810 deadlock in the cases (beginning of sys_rename itself)
811 in which we already have the sb rename sem */
812 page = alloc_dentry_path();
813 full_path = build_path_from_dentry(direntry, page);
814 if (IS_ERR(full_path)) {
815 de = ERR_CAST(full_path);
816 goto free_dentry_path;
817 }
818
819 if (d_really_is_positive(direntry)) {
820 cifs_dbg(FYI, "non-NULL inode in lookup\n");
821 } else {
822 struct cached_fid *cfid = NULL;
823
824 cifs_dbg(FYI, "NULL inode in lookup\n");
825
826 /*
827 * We can only rely on negative dentries having the same
828 * spelling as the cached dirent if case insensitivity is
829 * forced on mount.
830 *
831 * XXX: if servers correctly announce Case Sensitivity Search
832 * on GetInfo of FileFSAttributeInformation, then we can take
833 * correct action even if case insensitive is not forced on
834 * mount.
835 */
836 if (pTcon->nocase && !open_cached_dir_by_dentry(pTcon, direntry->d_parent, &cfid)) {
837 /*
838 * dentry is negative and parent is fully cached:
839 * we can assume file does not exist
840 */
841 if (cfid->dirents.is_valid) {
842 close_cached_dir(cfid);
843 goto out;
844 }
845 close_cached_dir(cfid);
846 }
847 }
848 cifs_dbg(FYI, "Full path: %s inode = 0x%p\n",
849 full_path, d_inode(direntry));
850
851again:
852 if (pTcon->posix_extensions) {
853 rc = smb311_posix_get_inode_info(&newInode, full_path, NULL,
854 parent_dir_inode->i_sb, xid);
855 } else if (pTcon->unix_ext) {
856 rc = cifs_get_inode_info_unix(&newInode, full_path,
857 parent_dir_inode->i_sb, xid);
858 } else {
859 rc = cifs_get_inode_info(&newInode, full_path, NULL,
860 parent_dir_inode->i_sb, xid, NULL);
861 }
862
863 if (rc == 0) {
864 /* since paths are not looked up by component - the parent
865 directories are presumed to be good here */
866 renew_parental_timestamps(direntry);
867 } else if (rc == -EAGAIN && retry_count++ < 10) {
868 goto again;
869 } else if (rc == -ENOENT) {
870 cifs_set_time(direntry, jiffies);
871 newInode = NULL;
872 } else {
873 if (rc != -EACCES) {
874 cifs_dbg(FYI, "Unexpected lookup error %d\n", rc);
875 /* We special case check for Access Denied - since that
876 is a common return code */
877 }
878 newInode = ERR_PTR(rc);
879 }
880
881out:
882 de = d_splice_alias(newInode, direntry);
883free_dentry_path:
884 free_dentry_path(page);
885put_tlink:
886 cifs_put_tlink(tlink);
887free_xid:
888 free_xid(xid);
889 return de;
890}
891
892static int
893cifs_d_revalidate(struct inode *dir, const struct qstr *name,
894 struct dentry *direntry, unsigned int flags)
895{
896 if (flags & LOOKUP_RCU)
897 return -ECHILD;
898
899 if (d_really_is_positive(direntry)) {
900 int rc;
901 struct inode *inode = d_inode(direntry);
902
903 if ((flags & LOOKUP_REVAL) && !CIFS_CACHE_READ(CIFS_I(inode)))
904 CIFS_I(inode)->time = 0; /* force reval */
905
906 rc = cifs_revalidate_dentry(direntry);
907 if (rc) {
908 cifs_dbg(FYI, "cifs_revalidate_dentry failed with rc=%d", rc);
909 switch (rc) {
910 case -ENOENT:
911 case -ESTALE:
912 /*
913 * Those errors mean the dentry is invalid
914 * (file was deleted or recreated)
915 */
916 return 0;
917 default:
918 /*
919 * Otherwise some unexpected error happened
920 * report it as-is to VFS layer
921 */
922 return rc;
923 }
924 }
925 else {
926 /*
927 * If the inode wasn't known to be a dfs entry when
928 * the dentry was instantiated, such as when created
929 * via ->readdir(), it needs to be set now since the
930 * attributes will have been updated by
931 * cifs_revalidate_dentry().
932 */
933 if (IS_AUTOMOUNT(inode) &&
934 !(direntry->d_flags & DCACHE_NEED_AUTOMOUNT)) {
935 spin_lock(&direntry->d_lock);
936 direntry->d_flags |= DCACHE_NEED_AUTOMOUNT;
937 spin_unlock(&direntry->d_lock);
938 }
939
940 return 1;
941 }
942 } else {
943 struct cifs_sb_info *cifs_sb = CIFS_SB(dir->i_sb);
944 struct cifs_tcon *tcon = cifs_sb_master_tcon(cifs_sb);
945 struct cached_fid *cfid;
946
947 if (!open_cached_dir_by_dentry(tcon, direntry->d_parent, &cfid)) {
948 /*
949 * dentry is negative and parent is fully cached:
950 * we can assume file does not exist
951 */
952 if (cfid->dirents.is_valid) {
953 close_cached_dir(cfid);
954 return 1;
955 }
956 close_cached_dir(cfid);
957 }
958 }
959
960 /*
961 * This may be nfsd (or something), anyway, we can't see the
962 * intent of this. So, since this can be for creation, drop it.
963 */
964 if (!flags)
965 return 0;
966
967 /*
968 * Drop the negative dentry, in order to make sure to use the
969 * case sensitive name which is specified by user if this is
970 * for creation.
971 */
972 if (flags & (LOOKUP_CREATE | LOOKUP_RENAME_TARGET))
973 return 0;
974
975 if (time_after(jiffies, cifs_get_time(direntry) + HZ) || !lookupCacheEnabled)
976 return 0;
977
978 return 1;
979}
980
981/* static int cifs_d_delete(struct dentry *direntry)
982{
983 int rc = 0;
984
985 cifs_dbg(FYI, "In cifs d_delete, name = %pd\n", direntry);
986
987 return rc;
988} */
989
990const struct dentry_operations cifs_dentry_ops = {
991 .d_revalidate = cifs_d_revalidate,
992 .d_automount = cifs_d_automount,
993/* d_delete: cifs_d_delete, */ /* not needed except for debugging */
994};
995
996static int cifs_ci_hash(const struct dentry *dentry, struct qstr *q)
997{
998 struct nls_table *codepage = CIFS_SB(dentry->d_sb)->local_nls;
999 unsigned long hash;
1000 wchar_t c;
1001 int i, charlen;
1002
1003 hash = init_name_hash(dentry);
1004 for (i = 0; i < q->len; i += charlen) {
1005 charlen = codepage->char2uni(&q->name[i], q->len - i, &c);
1006 /* error out if we can't convert the character */
1007 if (unlikely(charlen < 0))
1008 return charlen;
1009 hash = partial_name_hash(cifs_toupper(c), hash);
1010 }
1011 q->hash = end_name_hash(hash);
1012
1013 return 0;
1014}
1015
1016static int cifs_ci_compare(const struct dentry *dentry,
1017 unsigned int len, const char *str, const struct qstr *name)
1018{
1019 struct nls_table *codepage = CIFS_SB(dentry->d_sb)->local_nls;
1020 wchar_t c1, c2;
1021 int i, l1, l2;
1022
1023 /*
1024 * We make the assumption here that uppercase characters in the local
1025 * codepage are always the same length as their lowercase counterparts.
1026 *
1027 * If that's ever not the case, then this will fail to match it.
1028 */
1029 if (name->len != len)
1030 return 1;
1031
1032 for (i = 0; i < len; i += l1) {
1033 /* Convert characters in both strings to UTF-16. */
1034 l1 = codepage->char2uni(&str[i], len - i, &c1);
1035 l2 = codepage->char2uni(&name->name[i], name->len - i, &c2);
1036
1037 /*
1038 * If we can't convert either character, just declare it to
1039 * be 1 byte long and compare the original byte.
1040 */
1041 if (unlikely(l1 < 0 && l2 < 0)) {
1042 if (str[i] != name->name[i])
1043 return 1;
1044 l1 = 1;
1045 continue;
1046 }
1047
1048 /*
1049 * Here, we again ass|u|me that upper/lowercase versions of
1050 * a character are the same length in the local NLS.
1051 */
1052 if (l1 != l2)
1053 return 1;
1054
1055 /* Now compare uppercase versions of these characters */
1056 if (cifs_toupper(c1) != cifs_toupper(c2))
1057 return 1;
1058 }
1059
1060 return 0;
1061}
1062
1063static int set_tmpfile_attr(const unsigned int xid, unsigned int oflags,
1064 struct inode *inode, const char *full_path,
1065 struct TCP_Server_Info *server)
1066{
1067 struct cifsInodeInfo *cinode = CIFS_I(inode);
1068 FILE_BASIC_INFO fi;
1069
1070 cinode->cifsAttrs |= ATTR_HIDDEN;
1071 if (oflags & O_EXCL)
1072 cinode->cifsAttrs |= ATTR_TEMPORARY;
1073
1074 fi = (FILE_BASIC_INFO) {
1075 .Attributes = cpu_to_le32(cinode->cifsAttrs),
1076 };
1077 return server->ops->set_file_info(inode, full_path, &fi, xid);
1078}
1079
1080/*
1081 * Create a hidden temporary CIFS file with delete-on-close bit set.
1082 *
1083 * The initial dentry state is unhashed-negative. On success, dentry will
1084 * become unhashed-positive by calling d_instantiate().
1085 */
1086int cifs_tmpfile(const struct mnt_idmap *idmap, struct inode *dir,
1087 struct file *file, umode_t mode)
1088{
1089 struct dentry *dentry = file->f_path.dentry;
1090 struct cifs_sb_info *cifs_sb = CIFS_SB(dir);
1091 size_t namesize = CIFS_TMPNAME_LEN + 1;
1092 char *path __free(kfree) = NULL, *name;
1093 unsigned int oflags = file->f_flags;
1094 int retries = 0, max_retries = 16;
1095 struct TCP_Server_Info *server;
1096 struct cifs_pending_open open;
1097 struct cifsFileInfo *cfile;
1098 struct cifs_fid fid = {};
1099 struct tcon_link *tlink;
1100 struct cifs_tcon *tcon;
1101 unsigned int sbflags;
1102 struct inode *inode;
1103 unsigned int xid;
1104 __u32 oplock;
1105 bool opened;
1106 int namelen;
1107 int rc;
1108
1109 if (unlikely(cifs_forced_shutdown(cifs_sb)))
1110 return smb_EIO(smb_eio_trace_forced_shutdown);
1111
1112 tlink = cifs_sb_tlink(cifs_sb);
1113 if (IS_ERR(tlink))
1114 return PTR_ERR(tlink);
1115 tcon = tlink_tcon(tlink);
1116 server = tcon->ses->server;
1117
1118 xid = get_xid();
1119
1120 if (server->vals->protocol_id < SMB20_PROT_ID) {
1121 cifs_dbg(VFS | ONCE, "O_TMPFILE is supported only in SMB2+\n");
1122 rc = -EOPNOTSUPP;
1123 goto out;
1124 }
1125
1126 if (server->ops->new_lease_key)
1127 server->ops->new_lease_key(&fid);
1128 cifs_add_pending_open(&fid, tlink, &open);
1129
1130 path = alloc_parent_path(dentry, namesize - 1);
1131 if (IS_ERR(path)) {
1132 cifs_del_pending_open(&open);
1133 rc = PTR_ERR(path);
1134 path = NULL;
1135 goto out;
1136 }
1137
1138 name = path + strlen(path);
1139 do {
1140 /* Append tmpfile name to @path */
1141 namelen = scnprintf(name, namesize, CIFS_TMPNAME_PREFIX "%x",
1142 atomic_inc_return(&cifs_tmpcounter));
1143 rc = __cifs_do_create(dir, dentry, path, xid, tlink, oflags,
1144 mode, &oplock, &fid, NULL, &inode, &opened);
1145 if (!rc) {
1146 rc = d_mark_tmpfile_name(file, &QSTR_LEN(name, namelen));
1147 if (rc) {
1148 cifs_dbg(VFS | ONCE, "%s: failed to set filename in dentry: %d\n",
1149 __func__, rc);
1150 rc = -EISDIR;
1151 iput(inode);
1152 goto err_open;
1153 }
1154 set_nlink(inode, 0);
1155 mark_inode_dirty(inode);
1156 d_instantiate(dentry, inode);
1157 break;
1158 }
1159 } while (unlikely(rc == -EEXIST) && ++retries < max_retries);
1160
1161 if (rc) {
1162 if (rc == -ENOENT)
1163 rc = -EOPNOTSUPP;
1164 cifs_del_pending_open(&open);
1165 goto out;
1166 }
1167
1168 rc = finish_open(file, dentry, generic_file_open);
1169 if (rc)
1170 goto err_open;
1171
1172 sbflags = cifs_sb_flags(cifs_sb);
1173 if ((file->f_flags & O_DIRECT) && (sbflags & CIFS_MOUNT_STRICT_IO)) {
1174 if (sbflags & CIFS_MOUNT_NO_BRL)
1175 file->f_op = &cifs_file_direct_nobrl_ops;
1176 else
1177 file->f_op = &cifs_file_direct_ops;
1178 }
1179
1180 cfile = cifs_new_fileinfo(&fid, file, tlink, oplock, NULL);
1181 if (!cfile) {
1182 rc = -ENOMEM;
1183 goto err_open;
1184 }
1185
1186 rc = set_tmpfile_attr(xid, oflags, inode, path, server);
1187 if (rc)
1188 goto out;
1189
1190 fscache_use_cookie(cifs_inode_cookie(file_inode(file)),
1191 file->f_mode & FMODE_WRITE);
1192out:
1193 cifs_put_tlink(tlink);
1194 free_xid(xid);
1195 return rc;
1196err_open:
1197 cifs_del_pending_open(&open);
1198 if (server->ops->close)
1199 server->ops->close(xid, tcon, &fid);
1200 goto out;
1201}
1202
1203char *cifs_silly_fullpath(struct dentry *dentry)
1204{
1205 unsigned char name[CIFS_SILLYNAME_LEN + 1];
1206 int retries = 0, max_retries = 16;
1207 size_t namesize = sizeof(name);
1208 struct dentry *sdentry = NULL;
1209 char *path;
1210
1211 do {
1212 dput(sdentry);
1213 scnprintf(name, namesize, CIFS_SILLYNAME_PREFIX "%x",
1214 atomic_inc_return(&cifs_sillycounter));
1215 sdentry = lookup_noperm(&QSTR(name), dentry->d_parent);
1216 if (IS_ERR(sdentry))
1217 return ERR_CAST(sdentry);
1218 if (d_is_negative(sdentry)) {
1219 dput(sdentry);
1220 path = alloc_parent_path(dentry, CIFS_SILLYNAME_LEN);
1221 if (!IS_ERR(path))
1222 strcat(path, name);
1223 return path;
1224 }
1225 } while (++retries < max_retries);
1226 dput(sdentry);
1227 return ERR_PTR(-EBUSY);
1228}
1229
1230const struct dentry_operations cifs_ci_dentry_ops = {
1231 .d_revalidate = cifs_d_revalidate,
1232 .d_hash = cifs_ci_hash,
1233 .d_compare = cifs_ci_compare,
1234 .d_automount = cifs_d_automount,
1235};