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 (sfrench@us.ibm.com)
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 "cifspdu.h"
18 #include "cifsglob.h"
19 #include "cifsproto.h"
20 #include "cifs_debug.h"
21 #include "cifs_fs_sb.h"
22 #include "cifs_unicode.h"
23 #include "fs_context.h"
24 #include "cifs_ioctl.h"
25 #include "fscache.h"
26 #include "cached_dir.h"
27
28 static void
renew_parental_timestamps(struct dentry * direntry)29 renew_parental_timestamps(struct dentry *direntry)
30 {
31 /* BB check if there is a way to get the kernel to do this or if we
32 really need this */
33 do {
34 cifs_set_time(direntry, jiffies);
35 direntry = direntry->d_parent;
36 } while (!IS_ROOT(direntry));
37 }
38
39 char *
cifs_build_path_to_root(struct smb3_fs_context * ctx,struct cifs_sb_info * cifs_sb,struct cifs_tcon * tcon,int add_treename)40 cifs_build_path_to_root(struct smb3_fs_context *ctx, struct cifs_sb_info *cifs_sb,
41 struct cifs_tcon *tcon, int add_treename)
42 {
43 int pplen = ctx->prepath ? strlen(ctx->prepath) + 1 : 0;
44 int dfsplen;
45 char *full_path = NULL;
46
47 /* if no prefix path, simply set path to the root of share to "" */
48 if (pplen == 0) {
49 full_path = kzalloc(1, GFP_KERNEL);
50 return full_path;
51 }
52
53 if (add_treename)
54 dfsplen = strnlen(tcon->tree_name, MAX_TREE_SIZE + 1);
55 else
56 dfsplen = 0;
57
58 full_path = kmalloc(dfsplen + pplen + 1, GFP_KERNEL);
59 if (full_path == NULL)
60 return full_path;
61
62 if (dfsplen)
63 memcpy(full_path, tcon->tree_name, dfsplen);
64 full_path[dfsplen] = CIFS_DIR_SEP(cifs_sb);
65 memcpy(full_path + dfsplen + 1, ctx->prepath, pplen);
66 convert_delimiter(full_path, CIFS_DIR_SEP(cifs_sb));
67 return full_path;
68 }
69
70 /* Note: caller must free return buffer */
71 const char *
build_path_from_dentry(struct dentry * direntry,void * page)72 build_path_from_dentry(struct dentry *direntry, void *page)
73 {
74 struct cifs_sb_info *cifs_sb = CIFS_SB(direntry->d_sb);
75 struct cifs_tcon *tcon = cifs_sb_master_tcon(cifs_sb);
76 bool prefix = tcon->Flags & SMB_SHARE_IS_IN_DFS;
77
78 return build_path_from_dentry_optional_prefix(direntry, page,
79 prefix);
80 }
81
__build_path_from_dentry_optional_prefix(struct dentry * direntry,void * page,const char * tree,int tree_len,bool prefix)82 char *__build_path_from_dentry_optional_prefix(struct dentry *direntry, void *page,
83 const char *tree, int tree_len,
84 bool prefix)
85 {
86 int dfsplen;
87 int pplen = 0;
88 struct cifs_sb_info *cifs_sb = CIFS_SB(direntry->d_sb);
89 char dirsep = CIFS_DIR_SEP(cifs_sb);
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 (cifs_sb->mnt_cifs_flags & 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 char *p;
119
120 for (p = s; *p; p++)
121 if (*p == '/')
122 *p = dirsep;
123 }
124 if (dfsplen) {
125 s -= dfsplen;
126 memcpy(s, tree, dfsplen);
127 if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_POSIX_PATHS) {
128 int i;
129 for (i = 0; i < dfsplen; i++) {
130 if (s[i] == '\\')
131 s[i] = '/';
132 }
133 }
134 }
135 return s;
136 }
137
build_path_from_dentry_optional_prefix(struct dentry * direntry,void * page,bool prefix)138 char *build_path_from_dentry_optional_prefix(struct dentry *direntry, void *page,
139 bool prefix)
140 {
141 struct cifs_sb_info *cifs_sb = CIFS_SB(direntry->d_sb);
142 struct cifs_tcon *tcon = cifs_sb_master_tcon(cifs_sb);
143
144 return __build_path_from_dentry_optional_prefix(direntry, page, tcon->tree_name,
145 MAX_TREE_SIZE, prefix);
146 }
147
148 /*
149 * Don't allow path components longer than the server max.
150 * Don't allow the separator character in a path component.
151 * The VFS will not allow "/", but "\" is allowed by posix.
152 */
153 static int
check_name(struct dentry * direntry,struct cifs_tcon * tcon)154 check_name(struct dentry *direntry, struct cifs_tcon *tcon)
155 {
156 struct cifs_sb_info *cifs_sb = CIFS_SB(direntry->d_sb);
157 int i;
158
159 if (unlikely(tcon->fsAttrInfo.MaxPathNameComponentLength &&
160 direntry->d_name.len >
161 le32_to_cpu(tcon->fsAttrInfo.MaxPathNameComponentLength)))
162 return -ENAMETOOLONG;
163
164 if (!(cifs_sb->mnt_cifs_flags & CIFS_MOUNT_POSIX_PATHS)) {
165 for (i = 0; i < direntry->d_name.len; i++) {
166 if (direntry->d_name.name[i] == '\\') {
167 cifs_dbg(FYI, "Invalid file name\n");
168 return -EINVAL;
169 }
170 }
171 }
172 return 0;
173 }
174
175
176 /* Inode operations in similar order to how they appear in Linux file fs.h */
177
cifs_do_create(struct inode * inode,struct dentry * direntry,unsigned int xid,struct tcon_link * tlink,unsigned int oflags,umode_t mode,__u32 * oplock,struct cifs_fid * fid,struct cifs_open_info_data * buf)178 static int cifs_do_create(struct inode *inode, struct dentry *direntry, unsigned int xid,
179 struct tcon_link *tlink, unsigned int oflags, umode_t mode, __u32 *oplock,
180 struct cifs_fid *fid, struct cifs_open_info_data *buf)
181 {
182 int rc = -ENOENT;
183 int create_options = CREATE_NOT_DIR;
184 int desired_access;
185 struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
186 struct cifs_tcon *tcon = tlink_tcon(tlink);
187 const char *full_path;
188 void *page = alloc_dentry_path();
189 struct inode *newinode = NULL;
190 int disposition;
191 struct TCP_Server_Info *server = tcon->ses->server;
192 struct cifs_open_parms oparms;
193 struct cached_fid *parent_cfid = NULL;
194 int rdwr_for_fscache = 0;
195 __le32 lease_flags = 0;
196
197 *oplock = 0;
198 if (tcon->ses->server->oplocks)
199 *oplock = REQ_OPLOCK;
200
201 full_path = build_path_from_dentry(direntry, page);
202 if (IS_ERR(full_path)) {
203 free_dentry_path(page);
204 return PTR_ERR(full_path);
205 }
206
207 /* If we're caching, we need to be able to fill in around partial writes. */
208 if (cifs_fscache_enabled(inode) && (oflags & O_ACCMODE) == O_WRONLY)
209 rdwr_for_fscache = 1;
210
211 #ifdef CONFIG_CIFS_ALLOW_INSECURE_LEGACY
212 if (tcon->unix_ext && cap_unix(tcon->ses) && !tcon->broken_posix_open &&
213 (CIFS_UNIX_POSIX_PATH_OPS_CAP &
214 le64_to_cpu(tcon->fsUnixInfo.Capability))) {
215 rc = cifs_posix_open(full_path, &newinode, inode->i_sb, mode,
216 oflags, oplock, &fid->netfid, xid);
217 switch (rc) {
218 case 0:
219 if (newinode == NULL) {
220 /* query inode info */
221 goto cifs_create_get_file_info;
222 }
223
224 if (S_ISDIR(newinode->i_mode)) {
225 CIFSSMBClose(xid, tcon, fid->netfid);
226 iput(newinode);
227 rc = -EISDIR;
228 goto out;
229 }
230
231 if (!S_ISREG(newinode->i_mode)) {
232 /*
233 * The server may allow us to open things like
234 * FIFOs, but the client isn't set up to deal
235 * with that. If it's not a regular file, just
236 * close it and proceed as if it were a normal
237 * lookup.
238 */
239 CIFSSMBClose(xid, tcon, fid->netfid);
240 goto cifs_create_get_file_info;
241 }
242 /* success, no need to query */
243 goto cifs_create_set_dentry;
244
245 case -ENOENT:
246 goto cifs_create_get_file_info;
247
248 case -EIO:
249 case -EINVAL:
250 /*
251 * EIO could indicate that (posix open) operation is not
252 * supported, despite what server claimed in capability
253 * negotiation.
254 *
255 * POSIX open in samba versions 3.3.1 and earlier could
256 * incorrectly fail with invalid parameter.
257 */
258 tcon->broken_posix_open = true;
259 break;
260
261 case -EREMOTE:
262 case -EOPNOTSUPP:
263 /*
264 * EREMOTE indicates DFS junction, which is not handled
265 * in posix open. If either that or op not supported
266 * returned, follow the normal lookup.
267 */
268 break;
269
270 default:
271 goto out;
272 }
273 /*
274 * fallthrough to retry, using older open call, this is case
275 * where server does not support this SMB level, and falsely
276 * claims capability (also get here for DFS case which should be
277 * rare for path not covered on files)
278 */
279 }
280 #endif /* CONFIG_CIFS_ALLOW_INSECURE_LEGACY */
281
282 desired_access = 0;
283 if (OPEN_FMODE(oflags) & FMODE_READ)
284 desired_access |= GENERIC_READ; /* is this too little? */
285 if (OPEN_FMODE(oflags) & FMODE_WRITE)
286 desired_access |= GENERIC_WRITE;
287 if (rdwr_for_fscache == 1)
288 desired_access |= GENERIC_READ;
289
290 disposition = FILE_OVERWRITE_IF;
291 if ((oflags & (O_CREAT | O_EXCL)) == (O_CREAT | O_EXCL))
292 disposition = FILE_CREATE;
293 else if ((oflags & (O_CREAT | O_TRUNC)) == (O_CREAT | O_TRUNC))
294 disposition = FILE_OVERWRITE_IF;
295 else if ((oflags & O_CREAT) == O_CREAT)
296 disposition = FILE_OPEN_IF;
297 else
298 cifs_dbg(FYI, "Create flag not set in create function\n");
299
300 /*
301 * BB add processing to set equivalent of mode - e.g. via CreateX with
302 * ACLs
303 */
304
305 if (!server->ops->open) {
306 rc = -ENOSYS;
307 goto out;
308 }
309
310 /*
311 * if we're not using unix extensions, see if we need to set
312 * ATTR_READONLY on the create call
313 */
314 if (!tcon->unix_ext && (mode & S_IWUGO) == 0)
315 create_options |= CREATE_OPTION_READONLY;
316
317
318 retry_open:
319 if (tcon->cfids && direntry->d_parent && server->dialect >= SMB30_PROT_ID) {
320 parent_cfid = NULL;
321 spin_lock(&tcon->cfids->cfid_list_lock);
322 list_for_each_entry(parent_cfid, &tcon->cfids->entries, entry) {
323 if (parent_cfid->dentry == direntry->d_parent) {
324 cifs_dbg(FYI, "found a parent cached file handle\n");
325 if (parent_cfid->has_lease && parent_cfid->time) {
326 lease_flags
327 |= SMB2_LEASE_FLAG_PARENT_LEASE_KEY_SET_LE;
328 memcpy(fid->parent_lease_key,
329 parent_cfid->fid.lease_key,
330 SMB2_LEASE_KEY_SIZE);
331 parent_cfid->dirents.is_valid = false;
332 }
333 break;
334 }
335 }
336 spin_unlock(&tcon->cfids->cfid_list_lock);
337 }
338
339 oparms = (struct cifs_open_parms) {
340 .tcon = tcon,
341 .cifs_sb = cifs_sb,
342 .desired_access = desired_access,
343 .create_options = cifs_create_options(cifs_sb, create_options),
344 .disposition = disposition,
345 .path = full_path,
346 .fid = fid,
347 .lease_flags = lease_flags,
348 .mode = mode,
349 };
350 rc = server->ops->open(xid, &oparms, oplock, buf);
351 if (rc) {
352 cifs_dbg(FYI, "cifs_create returned 0x%x\n", rc);
353 if (rc == -EACCES && rdwr_for_fscache == 1) {
354 desired_access &= ~GENERIC_READ;
355 rdwr_for_fscache = 2;
356 goto retry_open;
357 }
358 goto out;
359 }
360 if (rdwr_for_fscache == 2)
361 cifs_invalidate_cache(inode, FSCACHE_INVAL_DIO_WRITE);
362
363 #ifdef CONFIG_CIFS_ALLOW_INSECURE_LEGACY
364 /*
365 * If Open reported that we actually created a file then we now have to
366 * set the mode if possible.
367 */
368 if ((tcon->unix_ext) && (*oplock & CIFS_CREATE_ACTION)) {
369 struct cifs_unix_set_info_args args = {
370 .mode = mode,
371 .ctime = NO_CHANGE_64,
372 .atime = NO_CHANGE_64,
373 .mtime = NO_CHANGE_64,
374 .device = 0,
375 };
376
377 if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_SET_UID) {
378 args.uid = current_fsuid();
379 if (inode->i_mode & S_ISGID)
380 args.gid = inode->i_gid;
381 else
382 args.gid = current_fsgid();
383 } else {
384 args.uid = INVALID_UID; /* no change */
385 args.gid = INVALID_GID; /* no change */
386 }
387 CIFSSMBUnixSetFileInfo(xid, tcon, &args, fid->netfid,
388 current->tgid);
389 } else {
390 /*
391 * BB implement mode setting via Windows security
392 * descriptors e.g.
393 */
394 /* CIFSSMBWinSetPerms(xid,tcon,path,mode,-1,-1,nls);*/
395
396 /* Could set r/o dos attribute if mode & 0222 == 0 */
397 }
398
399 cifs_create_get_file_info:
400 /* server might mask mode so we have to query for it */
401 if (tcon->unix_ext)
402 rc = cifs_get_inode_info_unix(&newinode, full_path, inode->i_sb,
403 xid);
404 else {
405 #else
406 {
407 #endif /* CONFIG_CIFS_ALLOW_INSECURE_LEGACY */
408 /* TODO: Add support for calling POSIX query info here, but passing in fid */
409 rc = cifs_get_inode_info(&newinode, full_path, buf, inode->i_sb, xid, fid);
410 if (newinode) {
411 if (server->ops->set_lease_key)
412 server->ops->set_lease_key(newinode, fid);
413 if ((*oplock & CIFS_CREATE_ACTION) && S_ISREG(newinode->i_mode)) {
414 if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_DYNPERM)
415 newinode->i_mode = mode;
416 if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_SET_UID) {
417 newinode->i_uid = current_fsuid();
418 if (inode->i_mode & S_ISGID)
419 newinode->i_gid = inode->i_gid;
420 else
421 newinode->i_gid = current_fsgid();
422 }
423 }
424 }
425 }
426
427 #ifdef CONFIG_CIFS_ALLOW_INSECURE_LEGACY
428 cifs_create_set_dentry:
429 #endif /* CONFIG_CIFS_ALLOW_INSECURE_LEGACY */
430 if (rc != 0) {
431 cifs_dbg(FYI, "Create worked, get_inode_info failed rc = %d\n",
432 rc);
433 goto out_err;
434 }
435
436 if (newinode)
437 if (S_ISDIR(newinode->i_mode)) {
438 rc = -EISDIR;
439 goto out_err;
440 }
441
442 d_drop(direntry);
443 d_add(direntry, newinode);
444
445 out:
446 free_dentry_path(page);
447 return rc;
448
449 out_err:
450 if (server->ops->close)
451 server->ops->close(xid, tcon, fid);
452 if (newinode)
453 iput(newinode);
454 goto out;
455 }
456
457 int
458 cifs_atomic_open(struct inode *inode, struct dentry *direntry,
459 struct file *file, unsigned oflags, umode_t mode)
460 {
461 int rc;
462 unsigned int xid;
463 struct tcon_link *tlink;
464 struct cifs_tcon *tcon;
465 struct TCP_Server_Info *server;
466 struct cifs_fid fid = {};
467 struct cifs_pending_open open;
468 __u32 oplock;
469 struct cifsFileInfo *file_info;
470 struct cifs_open_info_data buf = {};
471
472 if (unlikely(cifs_forced_shutdown(CIFS_SB(inode->i_sb))))
473 return -EIO;
474
475 /*
476 * Posix open is only called (at lookup time) for file create now. For
477 * opens (rather than creates), because we do not know if it is a file
478 * or directory yet, and current Samba no longer allows us to do posix
479 * open on dirs, we could end up wasting an open call on what turns out
480 * to be a dir. For file opens, we wait to call posix open till
481 * cifs_open. It could be added to atomic_open in the future but the
482 * performance tradeoff of the extra network request when EISDIR or
483 * EACCES is returned would have to be weighed against the 50% reduction
484 * in network traffic in the other paths.
485 */
486 if (!(oflags & O_CREAT)) {
487 struct dentry *res;
488
489 /*
490 * Check for hashed negative dentry. We have already revalidated
491 * the dentry and it is fine. No need to perform another lookup.
492 */
493 if (!d_in_lookup(direntry))
494 return -ENOENT;
495
496 res = cifs_lookup(inode, direntry, 0);
497 if (IS_ERR(res))
498 return PTR_ERR(res);
499
500 return finish_no_open(file, res);
501 }
502
503 xid = get_xid();
504
505 cifs_dbg(FYI, "parent inode = 0x%p name is: %pd and dentry = 0x%p\n",
506 inode, direntry, direntry);
507
508 tlink = cifs_sb_tlink(CIFS_SB(inode->i_sb));
509 if (IS_ERR(tlink)) {
510 rc = PTR_ERR(tlink);
511 goto out_free_xid;
512 }
513
514 tcon = tlink_tcon(tlink);
515
516 rc = check_name(direntry, tcon);
517 if (rc)
518 goto out;
519
520 server = tcon->ses->server;
521
522 if (server->ops->new_lease_key)
523 server->ops->new_lease_key(&fid);
524
525 cifs_add_pending_open(&fid, tlink, &open);
526
527 rc = cifs_do_create(inode, direntry, xid, tlink, oflags, mode,
528 &oplock, &fid, &buf);
529 if (rc) {
530 cifs_del_pending_open(&open);
531 goto out;
532 }
533
534 if ((oflags & (O_CREAT | O_EXCL)) == (O_CREAT | O_EXCL))
535 file->f_mode |= FMODE_CREATED;
536
537 rc = finish_open(file, direntry, generic_file_open);
538 if (rc) {
539 if (server->ops->close)
540 server->ops->close(xid, tcon, &fid);
541 cifs_del_pending_open(&open);
542 goto out;
543 }
544
545 if (file->f_flags & O_DIRECT &&
546 CIFS_SB(inode->i_sb)->mnt_cifs_flags & CIFS_MOUNT_STRICT_IO) {
547 if (CIFS_SB(inode->i_sb)->mnt_cifs_flags & CIFS_MOUNT_NO_BRL)
548 file->f_op = &cifs_file_direct_nobrl_ops;
549 else
550 file->f_op = &cifs_file_direct_ops;
551 }
552
553 file_info = cifs_new_fileinfo(&fid, file, tlink, oplock, buf.symlink_target);
554 if (file_info == NULL) {
555 if (server->ops->close)
556 server->ops->close(xid, tcon, &fid);
557 cifs_del_pending_open(&open);
558 rc = -ENOMEM;
559 goto out;
560 }
561
562 fscache_use_cookie(cifs_inode_cookie(file_inode(file)),
563 file->f_mode & FMODE_WRITE);
564
565 out:
566 cifs_put_tlink(tlink);
567 out_free_xid:
568 free_xid(xid);
569 cifs_free_open_info(&buf);
570 return rc;
571 }
572
573 int cifs_create(struct mnt_idmap *idmap, struct inode *inode,
574 struct dentry *direntry, umode_t mode, bool excl)
575 {
576 int rc;
577 unsigned int xid = get_xid();
578 /*
579 * BB below access is probably too much for mknod to request
580 * but we have to do query and setpathinfo so requesting
581 * less could fail (unless we want to request getatr and setatr
582 * permissions (only). At least for POSIX we do not have to
583 * request so much.
584 */
585 unsigned oflags = O_EXCL | O_CREAT | O_RDWR;
586 struct tcon_link *tlink;
587 struct cifs_tcon *tcon;
588 struct TCP_Server_Info *server;
589 struct cifs_fid fid;
590 __u32 oplock;
591 struct cifs_open_info_data buf = {};
592
593 cifs_dbg(FYI, "cifs_create parent inode = 0x%p name is: %pd and dentry = 0x%p\n",
594 inode, direntry, direntry);
595
596 if (unlikely(cifs_forced_shutdown(CIFS_SB(inode->i_sb)))) {
597 rc = -EIO;
598 goto out_free_xid;
599 }
600
601 tlink = cifs_sb_tlink(CIFS_SB(inode->i_sb));
602 rc = PTR_ERR(tlink);
603 if (IS_ERR(tlink))
604 goto out_free_xid;
605
606 tcon = tlink_tcon(tlink);
607 server = tcon->ses->server;
608
609 if (server->ops->new_lease_key)
610 server->ops->new_lease_key(&fid);
611
612 rc = cifs_do_create(inode, direntry, xid, tlink, oflags, mode, &oplock, &fid, &buf);
613 if (!rc && server->ops->close)
614 server->ops->close(xid, tcon, &fid);
615
616 cifs_free_open_info(&buf);
617 cifs_put_tlink(tlink);
618 out_free_xid:
619 free_xid(xid);
620 return rc;
621 }
622
623 int cifs_mknod(struct mnt_idmap *idmap, struct inode *inode,
624 struct dentry *direntry, umode_t mode, dev_t device_number)
625 {
626 int rc = -EPERM;
627 unsigned int xid;
628 struct cifs_sb_info *cifs_sb;
629 struct tcon_link *tlink;
630 struct cifs_tcon *tcon;
631 const char *full_path;
632 void *page;
633
634 if (!old_valid_dev(device_number))
635 return -EINVAL;
636
637 cifs_sb = CIFS_SB(inode->i_sb);
638 if (unlikely(cifs_forced_shutdown(cifs_sb)))
639 return -EIO;
640
641 tlink = cifs_sb_tlink(cifs_sb);
642 if (IS_ERR(tlink))
643 return PTR_ERR(tlink);
644
645 page = alloc_dentry_path();
646 tcon = tlink_tcon(tlink);
647 xid = get_xid();
648
649 full_path = build_path_from_dentry(direntry, page);
650 if (IS_ERR(full_path)) {
651 rc = PTR_ERR(full_path);
652 goto mknod_out;
653 }
654
655 trace_smb3_mknod_enter(xid, tcon->tid, tcon->ses->Suid, full_path);
656
657 rc = tcon->ses->server->ops->make_node(xid, inode, direntry, tcon,
658 full_path, mode,
659 device_number);
660
661 mknod_out:
662 if (rc)
663 trace_smb3_mknod_err(xid, tcon->tid, tcon->ses->Suid, rc);
664 else
665 trace_smb3_mknod_done(xid, tcon->tid, tcon->ses->Suid);
666
667 free_dentry_path(page);
668 free_xid(xid);
669 cifs_put_tlink(tlink);
670 return rc;
671 }
672
673 struct dentry *
674 cifs_lookup(struct inode *parent_dir_inode, struct dentry *direntry,
675 unsigned int flags)
676 {
677 unsigned int xid;
678 int rc = 0; /* to get around spurious gcc warning, set to zero here */
679 struct cifs_sb_info *cifs_sb;
680 struct tcon_link *tlink;
681 struct cifs_tcon *pTcon;
682 struct inode *newInode = NULL;
683 const char *full_path;
684 void *page;
685 int retry_count = 0;
686
687 xid = get_xid();
688
689 cifs_dbg(FYI, "parent inode = 0x%p name is: %pd and dentry = 0x%p\n",
690 parent_dir_inode, direntry, direntry);
691
692 /* check whether path exists */
693
694 cifs_sb = CIFS_SB(parent_dir_inode->i_sb);
695 tlink = cifs_sb_tlink(cifs_sb);
696 if (IS_ERR(tlink)) {
697 free_xid(xid);
698 return ERR_CAST(tlink);
699 }
700 pTcon = tlink_tcon(tlink);
701
702 rc = check_name(direntry, pTcon);
703 if (unlikely(rc)) {
704 cifs_put_tlink(tlink);
705 free_xid(xid);
706 return ERR_PTR(rc);
707 }
708
709 /* can not grab the rename sem here since it would
710 deadlock in the cases (beginning of sys_rename itself)
711 in which we already have the sb rename sem */
712 page = alloc_dentry_path();
713 full_path = build_path_from_dentry(direntry, page);
714 if (IS_ERR(full_path)) {
715 cifs_put_tlink(tlink);
716 free_xid(xid);
717 free_dentry_path(page);
718 return ERR_CAST(full_path);
719 }
720
721 if (d_really_is_positive(direntry)) {
722 cifs_dbg(FYI, "non-NULL inode in lookup\n");
723 } else {
724 cifs_dbg(FYI, "NULL inode in lookup\n");
725 }
726 cifs_dbg(FYI, "Full path: %s inode = 0x%p\n",
727 full_path, d_inode(direntry));
728
729 again:
730 if (pTcon->posix_extensions) {
731 rc = smb311_posix_get_inode_info(&newInode, full_path, NULL,
732 parent_dir_inode->i_sb, xid);
733 } else if (pTcon->unix_ext) {
734 rc = cifs_get_inode_info_unix(&newInode, full_path,
735 parent_dir_inode->i_sb, xid);
736 } else {
737 rc = cifs_get_inode_info(&newInode, full_path, NULL,
738 parent_dir_inode->i_sb, xid, NULL);
739 }
740
741 if (rc == 0) {
742 /* since paths are not looked up by component - the parent
743 directories are presumed to be good here */
744 renew_parental_timestamps(direntry);
745 } else if (rc == -EAGAIN && retry_count++ < 10) {
746 goto again;
747 } else if (rc == -ENOENT) {
748 cifs_set_time(direntry, jiffies);
749 newInode = NULL;
750 } else {
751 if (rc != -EACCES) {
752 cifs_dbg(FYI, "Unexpected lookup error %d\n", rc);
753 /* We special case check for Access Denied - since that
754 is a common return code */
755 }
756 newInode = ERR_PTR(rc);
757 }
758 free_dentry_path(page);
759 cifs_put_tlink(tlink);
760 free_xid(xid);
761 return d_splice_alias(newInode, direntry);
762 }
763
764 static int
765 cifs_d_revalidate(struct inode *dir, const struct qstr *name,
766 struct dentry *direntry, unsigned int flags)
767 {
768 struct inode *inode;
769 int rc;
770
771 if (flags & LOOKUP_RCU)
772 return -ECHILD;
773
774 if (d_really_is_positive(direntry)) {
775 inode = d_inode(direntry);
776 if ((flags & LOOKUP_REVAL) && !CIFS_CACHE_READ(CIFS_I(inode)))
777 CIFS_I(inode)->time = 0; /* force reval */
778
779 rc = cifs_revalidate_dentry(direntry);
780 if (rc) {
781 cifs_dbg(FYI, "cifs_revalidate_dentry failed with rc=%d", rc);
782 switch (rc) {
783 case -ENOENT:
784 case -ESTALE:
785 /*
786 * Those errors mean the dentry is invalid
787 * (file was deleted or recreated)
788 */
789 return 0;
790 default:
791 /*
792 * Otherwise some unexpected error happened
793 * report it as-is to VFS layer
794 */
795 return rc;
796 }
797 }
798 else {
799 /*
800 * If the inode wasn't known to be a dfs entry when
801 * the dentry was instantiated, such as when created
802 * via ->readdir(), it needs to be set now since the
803 * attributes will have been updated by
804 * cifs_revalidate_dentry().
805 */
806 if (IS_AUTOMOUNT(inode) &&
807 !(direntry->d_flags & DCACHE_NEED_AUTOMOUNT)) {
808 spin_lock(&direntry->d_lock);
809 direntry->d_flags |= DCACHE_NEED_AUTOMOUNT;
810 spin_unlock(&direntry->d_lock);
811 }
812
813 return 1;
814 }
815 }
816
817 /*
818 * This may be nfsd (or something), anyway, we can't see the
819 * intent of this. So, since this can be for creation, drop it.
820 */
821 if (!flags)
822 return 0;
823
824 /*
825 * Drop the negative dentry, in order to make sure to use the
826 * case sensitive name which is specified by user if this is
827 * for creation.
828 */
829 if (flags & (LOOKUP_CREATE | LOOKUP_RENAME_TARGET))
830 return 0;
831
832 if (time_after(jiffies, cifs_get_time(direntry) + HZ) || !lookupCacheEnabled)
833 return 0;
834
835 return 1;
836 }
837
838 /* static int cifs_d_delete(struct dentry *direntry)
839 {
840 int rc = 0;
841
842 cifs_dbg(FYI, "In cifs d_delete, name = %pd\n", direntry);
843
844 return rc;
845 } */
846
847 const struct dentry_operations cifs_dentry_ops = {
848 .d_revalidate = cifs_d_revalidate,
849 .d_automount = cifs_d_automount,
850 /* d_delete: cifs_d_delete, */ /* not needed except for debugging */
851 };
852
853 static int cifs_ci_hash(const struct dentry *dentry, struct qstr *q)
854 {
855 struct nls_table *codepage = CIFS_SB(dentry->d_sb)->local_nls;
856 unsigned long hash;
857 wchar_t c;
858 int i, charlen;
859
860 hash = init_name_hash(dentry);
861 for (i = 0; i < q->len; i += charlen) {
862 charlen = codepage->char2uni(&q->name[i], q->len - i, &c);
863 /* error out if we can't convert the character */
864 if (unlikely(charlen < 0))
865 return charlen;
866 hash = partial_name_hash(cifs_toupper(c), hash);
867 }
868 q->hash = end_name_hash(hash);
869
870 return 0;
871 }
872
873 static int cifs_ci_compare(const struct dentry *dentry,
874 unsigned int len, const char *str, const struct qstr *name)
875 {
876 struct nls_table *codepage = CIFS_SB(dentry->d_sb)->local_nls;
877 wchar_t c1, c2;
878 int i, l1, l2;
879
880 /*
881 * We make the assumption here that uppercase characters in the local
882 * codepage are always the same length as their lowercase counterparts.
883 *
884 * If that's ever not the case, then this will fail to match it.
885 */
886 if (name->len != len)
887 return 1;
888
889 for (i = 0; i < len; i += l1) {
890 /* Convert characters in both strings to UTF-16. */
891 l1 = codepage->char2uni(&str[i], len - i, &c1);
892 l2 = codepage->char2uni(&name->name[i], name->len - i, &c2);
893
894 /*
895 * If we can't convert either character, just declare it to
896 * be 1 byte long and compare the original byte.
897 */
898 if (unlikely(l1 < 0 && l2 < 0)) {
899 if (str[i] != name->name[i])
900 return 1;
901 l1 = 1;
902 continue;
903 }
904
905 /*
906 * Here, we again ass|u|me that upper/lowercase versions of
907 * a character are the same length in the local NLS.
908 */
909 if (l1 != l2)
910 return 1;
911
912 /* Now compare uppercase versions of these characters */
913 if (cifs_toupper(c1) != cifs_toupper(c2))
914 return 1;
915 }
916
917 return 0;
918 }
919
920 const struct dentry_operations cifs_ci_dentry_ops = {
921 .d_revalidate = cifs_d_revalidate,
922 .d_hash = cifs_ci_hash,
923 .d_compare = cifs_ci_compare,
924 .d_automount = cifs_d_automount,
925 };
926