.. | .. |
---|
52 | 52 | #include "cifs_spnego.h" |
---|
53 | 53 | #include "fscache.h" |
---|
54 | 54 | #include "smb2pdu.h" |
---|
| 55 | +#ifdef CONFIG_CIFS_DFS_UPCALL |
---|
| 56 | +#include "dfs_cache.h" |
---|
| 57 | +#endif |
---|
| 58 | + |
---|
| 59 | +/* |
---|
| 60 | + * DOS dates from 1980/1/1 through 2107/12/31 |
---|
| 61 | + * Protocol specifications indicate the range should be to 119, which |
---|
| 62 | + * limits maximum year to 2099. But this range has not been checked. |
---|
| 63 | + */ |
---|
| 64 | +#define SMB_DATE_MAX (127<<9 | 12<<5 | 31) |
---|
| 65 | +#define SMB_DATE_MIN (0<<9 | 1<<5 | 1) |
---|
| 66 | +#define SMB_TIME_MAX (23<<11 | 59<<5 | 29) |
---|
55 | 67 | |
---|
56 | 68 | int cifsFYI = 0; |
---|
57 | 69 | bool traceSMB; |
---|
.. | .. |
---|
59 | 71 | bool linuxExtEnabled = true; |
---|
60 | 72 | bool lookupCacheEnabled = true; |
---|
61 | 73 | bool disable_legacy_dialects; /* false by default */ |
---|
| 74 | +bool enable_gcm_256; /* false by default, change when more servers support it */ |
---|
| 75 | +bool require_gcm_256; /* false by default */ |
---|
62 | 76 | unsigned int global_secflags = CIFSSEC_DEF; |
---|
63 | 77 | /* unsigned int ntlmv2_support = 0; */ |
---|
64 | 78 | unsigned int sign_CIFS_PDUs = 1; |
---|
.. | .. |
---|
81 | 95 | MODULE_PARM_DESC(cifs_max_pending, "Simultaneous requests to server for " |
---|
82 | 96 | "CIFS/SMB1 dialect (N/A for SMB3) " |
---|
83 | 97 | "Default: 32767 Range: 2 to 32767."); |
---|
| 98 | +#ifdef CONFIG_CIFS_STATS2 |
---|
| 99 | +unsigned int slow_rsp_threshold = 1; |
---|
| 100 | +module_param(slow_rsp_threshold, uint, 0644); |
---|
| 101 | +MODULE_PARM_DESC(slow_rsp_threshold, "Amount of time (in seconds) to wait " |
---|
| 102 | + "before logging that a response is delayed. " |
---|
| 103 | + "Default: 1 (if set to 0 disables msg)."); |
---|
| 104 | +#endif /* STATS2 */ |
---|
| 105 | + |
---|
84 | 106 | module_param(enable_oplocks, bool, 0644); |
---|
85 | 107 | MODULE_PARM_DESC(enable_oplocks, "Enable or disable oplocks. Default: y/Y/1"); |
---|
| 108 | + |
---|
| 109 | +module_param(enable_gcm_256, bool, 0644); |
---|
| 110 | +MODULE_PARM_DESC(enable_gcm_256, "Enable requesting strongest (256 bit) GCM encryption. Default: n/N/0"); |
---|
| 111 | + |
---|
| 112 | +module_param(require_gcm_256, bool, 0644); |
---|
| 113 | +MODULE_PARM_DESC(require_gcm_256, "Require strongest (256 bit) GCM encryption. Default: n/N/0"); |
---|
86 | 114 | |
---|
87 | 115 | module_param(disable_legacy_dialects, bool, 0644); |
---|
88 | 116 | MODULE_PARM_DESC(disable_legacy_dialects, "To improve security it may be " |
---|
.. | .. |
---|
98 | 126 | extern mempool_t *cifs_mid_poolp; |
---|
99 | 127 | |
---|
100 | 128 | struct workqueue_struct *cifsiod_wq; |
---|
| 129 | +struct workqueue_struct *decrypt_wq; |
---|
| 130 | +struct workqueue_struct *fileinfo_put_wq; |
---|
101 | 131 | struct workqueue_struct *cifsoplockd_wq; |
---|
102 | 132 | __u32 cifs_lock_secret; |
---|
103 | 133 | |
---|
.. | .. |
---|
131 | 161 | struct inode *inode; |
---|
132 | 162 | struct cifs_sb_info *cifs_sb; |
---|
133 | 163 | struct cifs_tcon *tcon; |
---|
| 164 | + struct timespec64 ts; |
---|
134 | 165 | int rc = 0; |
---|
135 | 166 | |
---|
136 | 167 | cifs_sb = CIFS_SB(sb); |
---|
.. | .. |
---|
147 | 178 | else |
---|
148 | 179 | sb->s_maxbytes = MAX_NON_LFS; |
---|
149 | 180 | |
---|
150 | | - /* BB FIXME fix time_gran to be larger for LANMAN sessions */ |
---|
151 | | - sb->s_time_gran = 100; |
---|
| 181 | + /* |
---|
| 182 | + * Some very old servers like DOS and OS/2 used 2 second granularity |
---|
| 183 | + * (while all current servers use 100ns granularity - see MS-DTYP) |
---|
| 184 | + * but 1 second is the maximum allowed granularity for the VFS |
---|
| 185 | + * so for old servers set time granularity to 1 second while for |
---|
| 186 | + * everything else (current servers) set it to 100ns. |
---|
| 187 | + */ |
---|
| 188 | + if ((tcon->ses->server->vals->protocol_id == SMB10_PROT_ID) && |
---|
| 189 | + ((tcon->ses->capabilities & |
---|
| 190 | + tcon->ses->server->vals->cap_nt_find) == 0) && |
---|
| 191 | + !tcon->unix_ext) { |
---|
| 192 | + sb->s_time_gran = 1000000000; /* 1 second is max allowed gran */ |
---|
| 193 | + ts = cnvrtDosUnixTm(cpu_to_le16(SMB_DATE_MIN), 0, 0); |
---|
| 194 | + sb->s_time_min = ts.tv_sec; |
---|
| 195 | + ts = cnvrtDosUnixTm(cpu_to_le16(SMB_DATE_MAX), |
---|
| 196 | + cpu_to_le16(SMB_TIME_MAX), 0); |
---|
| 197 | + sb->s_time_max = ts.tv_sec; |
---|
| 198 | + } else { |
---|
| 199 | + /* |
---|
| 200 | + * Almost every server, including all SMB2+, uses DCE TIME |
---|
| 201 | + * ie 100 nanosecond units, since 1601. See MS-DTYP and MS-FSCC |
---|
| 202 | + */ |
---|
| 203 | + sb->s_time_gran = 100; |
---|
| 204 | + ts = cifs_NTtimeToUnix(0); |
---|
| 205 | + sb->s_time_min = ts.tv_sec; |
---|
| 206 | + ts = cifs_NTtimeToUnix(cpu_to_le64(S64_MAX)); |
---|
| 207 | + sb->s_time_max = ts.tv_sec; |
---|
| 208 | + } |
---|
152 | 209 | |
---|
153 | 210 | sb->s_magic = CIFS_MAGIC_NUMBER; |
---|
154 | 211 | sb->s_op = &cifs_super_ops; |
---|
.. | .. |
---|
226 | 283 | buf->f_ffree = 0; /* unlimited */ |
---|
227 | 284 | |
---|
228 | 285 | if (server->ops->queryfs) |
---|
229 | | - rc = server->ops->queryfs(xid, tcon, buf); |
---|
| 286 | + rc = server->ops->queryfs(xid, tcon, cifs_sb, buf); |
---|
230 | 287 | |
---|
231 | 288 | free_xid(xid); |
---|
232 | 289 | return rc; |
---|
.. | .. |
---|
305 | 362 | return &cifs_inode->vfs_inode; |
---|
306 | 363 | } |
---|
307 | 364 | |
---|
308 | | -static void cifs_i_callback(struct rcu_head *head) |
---|
309 | | -{ |
---|
310 | | - struct inode *inode = container_of(head, struct inode, i_rcu); |
---|
311 | | - kmem_cache_free(cifs_inode_cachep, CIFS_I(inode)); |
---|
312 | | -} |
---|
313 | | - |
---|
314 | 365 | static void |
---|
315 | | -cifs_destroy_inode(struct inode *inode) |
---|
| 366 | +cifs_free_inode(struct inode *inode) |
---|
316 | 367 | { |
---|
317 | | - call_rcu(&inode->i_rcu, cifs_i_callback); |
---|
| 368 | + kmem_cache_free(cifs_inode_cachep, CIFS_I(inode)); |
---|
318 | 369 | } |
---|
319 | 370 | |
---|
320 | 371 | static void |
---|
.. | .. |
---|
384 | 435 | |
---|
385 | 436 | if (ses->sign) |
---|
386 | 437 | seq_puts(s, "i"); |
---|
| 438 | + |
---|
| 439 | + if (ses->sectype == Kerberos) |
---|
| 440 | + seq_printf(s, ",cruid=%u", |
---|
| 441 | + from_kuid_munged(&init_user_ns, ses->cred_uid)); |
---|
387 | 442 | } |
---|
388 | 443 | |
---|
389 | 444 | static void |
---|
.. | .. |
---|
395 | 450 | seq_puts(s, "strict"); |
---|
396 | 451 | else if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_DIRECT_IO) |
---|
397 | 452 | seq_puts(s, "none"); |
---|
| 453 | + else if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_RW_CACHE) |
---|
| 454 | + seq_puts(s, "singleclient"); /* assume only one client access */ |
---|
| 455 | + else if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_RO_CACHE) |
---|
| 456 | + seq_puts(s, "ro"); /* read only caching assumed */ |
---|
398 | 457 | else |
---|
399 | 458 | seq_puts(s, "loose"); |
---|
400 | 459 | } |
---|
.. | .. |
---|
479 | 538 | |
---|
480 | 539 | if (tcon->seal) |
---|
481 | 540 | seq_puts(s, ",seal"); |
---|
| 541 | + else if (tcon->ses->server->ignore_signature) |
---|
| 542 | + seq_puts(s, ",signloosely"); |
---|
482 | 543 | if (tcon->nocase) |
---|
483 | 544 | seq_puts(s, ",nocase"); |
---|
| 545 | + if (tcon->nodelete) |
---|
| 546 | + seq_puts(s, ",nodelete"); |
---|
| 547 | + if (tcon->local_lease) |
---|
| 548 | + seq_puts(s, ",locallease"); |
---|
484 | 549 | if (tcon->retry) |
---|
485 | 550 | seq_puts(s, ",hard"); |
---|
486 | 551 | else |
---|
.. | .. |
---|
495 | 560 | seq_puts(s, ",unix"); |
---|
496 | 561 | else |
---|
497 | 562 | seq_puts(s, ",nounix"); |
---|
| 563 | + if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_NO_DFS) |
---|
| 564 | + seq_puts(s, ",nodfs"); |
---|
498 | 565 | if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_POSIX_PATHS) |
---|
499 | 566 | seq_puts(s, ",posixpaths"); |
---|
500 | 567 | if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_SET_UID) |
---|
.. | .. |
---|
519 | 586 | seq_puts(s, ",nobrl"); |
---|
520 | 587 | if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_NO_HANDLE_CACHE) |
---|
521 | 588 | seq_puts(s, ",nohandlecache"); |
---|
| 589 | + if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_MODE_FROM_SID) |
---|
| 590 | + seq_puts(s, ",modefromsid"); |
---|
522 | 591 | if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_CIFS_ACL) |
---|
523 | 592 | seq_puts(s, ",cifsacl"); |
---|
524 | 593 | if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_DYNPERM) |
---|
.. | .. |
---|
544 | 613 | |
---|
545 | 614 | seq_printf(s, ",rsize=%u", cifs_sb->rsize); |
---|
546 | 615 | seq_printf(s, ",wsize=%u", cifs_sb->wsize); |
---|
| 616 | + seq_printf(s, ",bsize=%u", cifs_sb->bsize); |
---|
| 617 | + if (tcon->ses->server->min_offload) |
---|
| 618 | + seq_printf(s, ",esize=%u", tcon->ses->server->min_offload); |
---|
547 | 619 | seq_printf(s, ",echo_interval=%lu", |
---|
548 | 620 | tcon->ses->server->echo_interval / HZ); |
---|
| 621 | + |
---|
| 622 | + /* Only display the following if overridden on mount */ |
---|
| 623 | + if (tcon->ses->server->max_credits != SMB2_MAX_CREDITS_AVAILABLE) |
---|
| 624 | + seq_printf(s, ",max_credits=%u", tcon->ses->server->max_credits); |
---|
| 625 | + if (tcon->ses->server->tcp_nodelay) |
---|
| 626 | + seq_puts(s, ",tcpnodelay"); |
---|
| 627 | + if (tcon->ses->server->noautotune) |
---|
| 628 | + seq_puts(s, ",noautotune"); |
---|
| 629 | + if (tcon->ses->server->noblocksnd) |
---|
| 630 | + seq_puts(s, ",noblocksend"); |
---|
| 631 | + |
---|
549 | 632 | if (tcon->snapshot_time) |
---|
550 | 633 | seq_printf(s, ",snapshot=%llu", tcon->snapshot_time); |
---|
| 634 | + if (tcon->handle_timeout) |
---|
| 635 | + seq_printf(s, ",handletimeout=%u", tcon->handle_timeout); |
---|
551 | 636 | /* convert actimeo and display it in seconds */ |
---|
552 | 637 | seq_printf(s, ",actimeo=%lu", cifs_sb->actimeo / HZ); |
---|
| 638 | + |
---|
| 639 | + if (tcon->ses->chan_max > 1) |
---|
| 640 | + seq_printf(s, ",multichannel,max_channels=%zu", |
---|
| 641 | + tcon->ses->chan_max); |
---|
553 | 642 | |
---|
554 | 643 | return 0; |
---|
555 | 644 | } |
---|
.. | .. |
---|
617 | 706 | static const struct super_operations cifs_super_ops = { |
---|
618 | 707 | .statfs = cifs_statfs, |
---|
619 | 708 | .alloc_inode = cifs_alloc_inode, |
---|
620 | | - .destroy_inode = cifs_destroy_inode, |
---|
| 709 | + .free_inode = cifs_free_inode, |
---|
621 | 710 | .drop_inode = cifs_drop_inode, |
---|
622 | 711 | .evict_inode = cifs_evict_inode, |
---|
623 | 712 | /* .delete_inode = cifs_delete_inode, */ /* Do not need above |
---|
.. | .. |
---|
663 | 752 | struct inode *dir = d_inode(dentry); |
---|
664 | 753 | struct dentry *child; |
---|
665 | 754 | |
---|
666 | | - if (!dir) { |
---|
667 | | - dput(dentry); |
---|
668 | | - dentry = ERR_PTR(-ENOENT); |
---|
669 | | - break; |
---|
670 | | - } |
---|
671 | 755 | if (!S_ISDIR(dir->i_mode)) { |
---|
672 | 756 | dput(dentry); |
---|
673 | 757 | dentry = ERR_PTR(-ENOTDIR); |
---|
.. | .. |
---|
684 | 768 | while (*s && *s != sep) |
---|
685 | 769 | s++; |
---|
686 | 770 | |
---|
687 | | - child = lookup_one_len_unlocked(p, dentry, s - p); |
---|
| 771 | + child = lookup_positive_unlocked(p, dentry, s - p); |
---|
688 | 772 | dput(dentry); |
---|
689 | 773 | dentry = child; |
---|
690 | 774 | } while (!IS_ERR(dentry)); |
---|
.. | .. |
---|
710 | 794 | struct cifs_mnt_data mnt_data; |
---|
711 | 795 | struct dentry *root; |
---|
712 | 796 | |
---|
713 | | - cifs_dbg(FYI, "Devname: %s flags: %d\n", dev_name, flags); |
---|
| 797 | + /* |
---|
| 798 | + * Prints in Kernel / CIFS log the attempted mount operation |
---|
| 799 | + * If CIFS_DEBUG && cifs_FYI |
---|
| 800 | + */ |
---|
| 801 | + if (cifsFYI) |
---|
| 802 | + cifs_dbg(FYI, "Devname: %s flags: %d\n", dev_name, flags); |
---|
| 803 | + else |
---|
| 804 | + cifs_info("Attempting to mount %s\n", dev_name); |
---|
714 | 805 | |
---|
715 | 806 | volume_info = cifs_get_volume_info((char *)data, dev_name, is_smb3); |
---|
716 | 807 | if (IS_ERR(volume_info)) |
---|
.. | .. |
---|
779 | 870 | |
---|
780 | 871 | out_super: |
---|
781 | 872 | deactivate_locked_super(sb); |
---|
| 873 | + return root; |
---|
782 | 874 | out: |
---|
783 | 875 | cifs_cleanup_volume_info(volume_info); |
---|
784 | 876 | return root; |
---|
.. | .. |
---|
812 | 904 | ssize_t rc; |
---|
813 | 905 | struct inode *inode = file_inode(iocb->ki_filp); |
---|
814 | 906 | |
---|
815 | | - if (iocb->ki_filp->f_flags & O_DIRECT) |
---|
| 907 | + if (iocb->ki_flags & IOCB_DIRECT) |
---|
816 | 908 | return cifs_user_readv(iocb, iter); |
---|
817 | 909 | |
---|
818 | 910 | rc = cifs_revalidate_mapping(inode); |
---|
.. | .. |
---|
862 | 954 | |
---|
863 | 955 | static loff_t cifs_llseek(struct file *file, loff_t offset, int whence) |
---|
864 | 956 | { |
---|
| 957 | + struct cifsFileInfo *cfile = file->private_data; |
---|
| 958 | + struct cifs_tcon *tcon; |
---|
| 959 | + |
---|
865 | 960 | /* |
---|
866 | 961 | * whence == SEEK_END || SEEK_DATA || SEEK_HOLE => we must revalidate |
---|
867 | 962 | * the cached file length |
---|
.. | .. |
---|
892 | 987 | rc = cifs_revalidate_file_attr(file); |
---|
893 | 988 | if (rc < 0) |
---|
894 | 989 | return (loff_t)rc; |
---|
| 990 | + } |
---|
| 991 | + if (cfile && cfile->tlink) { |
---|
| 992 | + tcon = tlink_tcon(cfile->tlink); |
---|
| 993 | + if (tcon->ses->server->ops->llseek) |
---|
| 994 | + return tcon->ses->server->ops->llseek(file, tcon, |
---|
| 995 | + offset, whence); |
---|
895 | 996 | } |
---|
896 | 997 | return generic_file_llseek(file, offset, whence); |
---|
897 | 998 | } |
---|
.. | .. |
---|
934 | 1035 | .name = "cifs", |
---|
935 | 1036 | .mount = cifs_do_mount, |
---|
936 | 1037 | .kill_sb = cifs_kill_sb, |
---|
937 | | - /* .fs_flags */ |
---|
| 1038 | + .fs_flags = FS_RENAME_DOES_D_MOVE, |
---|
938 | 1039 | }; |
---|
939 | 1040 | MODULE_ALIAS_FS("cifs"); |
---|
940 | 1041 | |
---|
941 | | -static struct file_system_type smb3_fs_type = { |
---|
| 1042 | +struct file_system_type smb3_fs_type = { |
---|
942 | 1043 | .owner = THIS_MODULE, |
---|
943 | 1044 | .name = "smb3", |
---|
944 | 1045 | .mount = smb3_do_mount, |
---|
945 | 1046 | .kill_sb = cifs_kill_sb, |
---|
946 | | - /* .fs_flags */ |
---|
| 1047 | + .fs_flags = FS_RENAME_DOES_D_MOVE, |
---|
947 | 1048 | }; |
---|
948 | 1049 | MODULE_ALIAS_FS("smb3"); |
---|
949 | 1050 | MODULE_ALIAS("smb3"); |
---|
.. | .. |
---|
970 | 1071 | .getattr = cifs_getattr, |
---|
971 | 1072 | .permission = cifs_permission, |
---|
972 | 1073 | .listxattr = cifs_listxattr, |
---|
| 1074 | + .fiemap = cifs_fiemap, |
---|
973 | 1075 | }; |
---|
974 | 1076 | |
---|
975 | 1077 | const struct inode_operations cifs_symlink_inode_ops = { |
---|
.. | .. |
---|
978 | 1080 | .listxattr = cifs_listxattr, |
---|
979 | 1081 | }; |
---|
980 | 1082 | |
---|
981 | | -static int cifs_clone_file_range(struct file *src_file, loff_t off, |
---|
982 | | - struct file *dst_file, loff_t destoff, u64 len) |
---|
| 1083 | +static loff_t cifs_remap_file_range(struct file *src_file, loff_t off, |
---|
| 1084 | + struct file *dst_file, loff_t destoff, loff_t len, |
---|
| 1085 | + unsigned int remap_flags) |
---|
983 | 1086 | { |
---|
984 | 1087 | struct inode *src_inode = file_inode(src_file); |
---|
985 | 1088 | struct inode *target_inode = file_inode(dst_file); |
---|
.. | .. |
---|
988 | 1091 | struct cifs_tcon *target_tcon; |
---|
989 | 1092 | unsigned int xid; |
---|
990 | 1093 | int rc; |
---|
| 1094 | + |
---|
| 1095 | + if (remap_flags & ~(REMAP_FILE_DEDUP | REMAP_FILE_ADVISORY)) |
---|
| 1096 | + return -EINVAL; |
---|
991 | 1097 | |
---|
992 | 1098 | cifs_dbg(FYI, "clone range\n"); |
---|
993 | 1099 | |
---|
.. | .. |
---|
1031 | 1137 | unlock_two_nondirectories(src_inode, target_inode); |
---|
1032 | 1138 | out: |
---|
1033 | 1139 | free_xid(xid); |
---|
1034 | | - return rc; |
---|
| 1140 | + return rc < 0 ? rc : len; |
---|
1035 | 1141 | } |
---|
1036 | 1142 | |
---|
1037 | 1143 | ssize_t cifs_file_copychunk_range(unsigned int xid, |
---|
.. | .. |
---|
1048 | 1154 | ssize_t rc; |
---|
1049 | 1155 | |
---|
1050 | 1156 | cifs_dbg(FYI, "copychunk range\n"); |
---|
1051 | | - |
---|
1052 | | - if (src_inode == target_inode) { |
---|
1053 | | - rc = -EINVAL; |
---|
1054 | | - goto out; |
---|
1055 | | - } |
---|
1056 | 1157 | |
---|
1057 | 1158 | if (!src_file->private_data || !dst_file->private_data) { |
---|
1058 | 1159 | rc = -EBADF; |
---|
.. | .. |
---|
1071 | 1172 | goto out; |
---|
1072 | 1173 | } |
---|
1073 | 1174 | |
---|
| 1175 | + rc = -EOPNOTSUPP; |
---|
| 1176 | + if (!target_tcon->ses->server->ops->copychunk_range) |
---|
| 1177 | + goto out; |
---|
| 1178 | + |
---|
1074 | 1179 | /* |
---|
1075 | 1180 | * Note: cifs case is easier than btrfs since server responsible for |
---|
1076 | 1181 | * checks for proper open modes and file type and if it wants |
---|
.. | .. |
---|
1082 | 1187 | /* should we flush first and last page first */ |
---|
1083 | 1188 | truncate_inode_pages(&target_inode->i_data, 0); |
---|
1084 | 1189 | |
---|
1085 | | - if (target_tcon->ses->server->ops->copychunk_range) |
---|
| 1190 | + rc = file_modified(dst_file); |
---|
| 1191 | + if (!rc) |
---|
1086 | 1192 | rc = target_tcon->ses->server->ops->copychunk_range(xid, |
---|
1087 | 1193 | smb_file_src, smb_file_target, off, len, destoff); |
---|
1088 | | - else |
---|
1089 | | - rc = -EOPNOTSUPP; |
---|
| 1194 | + |
---|
| 1195 | + file_accessed(src_file); |
---|
1090 | 1196 | |
---|
1091 | 1197 | /* force revalidate of size and timestamps of target file now |
---|
1092 | 1198 | * that target is updated on the server |
---|
.. | .. |
---|
1119 | 1225 | { |
---|
1120 | 1226 | unsigned int xid = get_xid(); |
---|
1121 | 1227 | ssize_t rc; |
---|
| 1228 | + struct cifsFileInfo *cfile = dst_file->private_data; |
---|
| 1229 | + |
---|
| 1230 | + if (cfile->swapfile) { |
---|
| 1231 | + rc = -EOPNOTSUPP; |
---|
| 1232 | + free_xid(xid); |
---|
| 1233 | + return rc; |
---|
| 1234 | + } |
---|
1122 | 1235 | |
---|
1123 | 1236 | rc = cifs_file_copychunk_range(xid, src_file, off, dst_file, destoff, |
---|
1124 | 1237 | len, flags); |
---|
1125 | 1238 | free_xid(xid); |
---|
| 1239 | + |
---|
| 1240 | + if (rc == -EOPNOTSUPP || rc == -EXDEV) |
---|
| 1241 | + rc = generic_copy_file_range(src_file, off, dst_file, |
---|
| 1242 | + destoff, len, flags); |
---|
1126 | 1243 | return rc; |
---|
1127 | 1244 | } |
---|
1128 | 1245 | |
---|
.. | .. |
---|
1132 | 1249 | .open = cifs_open, |
---|
1133 | 1250 | .release = cifs_close, |
---|
1134 | 1251 | .lock = cifs_lock, |
---|
| 1252 | + .flock = cifs_flock, |
---|
1135 | 1253 | .fsync = cifs_fsync, |
---|
1136 | 1254 | .flush = cifs_flush, |
---|
1137 | 1255 | .mmap = cifs_file_mmap, |
---|
.. | .. |
---|
1140 | 1258 | .llseek = cifs_llseek, |
---|
1141 | 1259 | .unlocked_ioctl = cifs_ioctl, |
---|
1142 | 1260 | .copy_file_range = cifs_copy_file_range, |
---|
1143 | | - .clone_file_range = cifs_clone_file_range, |
---|
| 1261 | + .remap_file_range = cifs_remap_file_range, |
---|
1144 | 1262 | .setlease = cifs_setlease, |
---|
1145 | 1263 | .fallocate = cifs_fallocate, |
---|
1146 | 1264 | }; |
---|
.. | .. |
---|
1151 | 1269 | .open = cifs_open, |
---|
1152 | 1270 | .release = cifs_close, |
---|
1153 | 1271 | .lock = cifs_lock, |
---|
| 1272 | + .flock = cifs_flock, |
---|
1154 | 1273 | .fsync = cifs_strict_fsync, |
---|
1155 | 1274 | .flush = cifs_flush, |
---|
1156 | 1275 | .mmap = cifs_file_strict_mmap, |
---|
.. | .. |
---|
1159 | 1278 | .llseek = cifs_llseek, |
---|
1160 | 1279 | .unlocked_ioctl = cifs_ioctl, |
---|
1161 | 1280 | .copy_file_range = cifs_copy_file_range, |
---|
1162 | | - .clone_file_range = cifs_clone_file_range, |
---|
| 1281 | + .remap_file_range = cifs_remap_file_range, |
---|
1163 | 1282 | .setlease = cifs_setlease, |
---|
1164 | 1283 | .fallocate = cifs_fallocate, |
---|
1165 | 1284 | }; |
---|
1166 | 1285 | |
---|
1167 | 1286 | const struct file_operations cifs_file_direct_ops = { |
---|
1168 | | - /* BB reevaluate whether they can be done with directio, no cache */ |
---|
1169 | | - .read_iter = cifs_user_readv, |
---|
1170 | | - .write_iter = cifs_user_writev, |
---|
| 1287 | + .read_iter = cifs_direct_readv, |
---|
| 1288 | + .write_iter = cifs_direct_writev, |
---|
1171 | 1289 | .open = cifs_open, |
---|
1172 | 1290 | .release = cifs_close, |
---|
1173 | 1291 | .lock = cifs_lock, |
---|
| 1292 | + .flock = cifs_flock, |
---|
1174 | 1293 | .fsync = cifs_fsync, |
---|
1175 | 1294 | .flush = cifs_flush, |
---|
1176 | 1295 | .mmap = cifs_file_mmap, |
---|
.. | .. |
---|
1178 | 1297 | .splice_write = iter_file_splice_write, |
---|
1179 | 1298 | .unlocked_ioctl = cifs_ioctl, |
---|
1180 | 1299 | .copy_file_range = cifs_copy_file_range, |
---|
1181 | | - .clone_file_range = cifs_clone_file_range, |
---|
| 1300 | + .remap_file_range = cifs_remap_file_range, |
---|
1182 | 1301 | .llseek = cifs_llseek, |
---|
1183 | 1302 | .setlease = cifs_setlease, |
---|
1184 | 1303 | .fallocate = cifs_fallocate, |
---|
.. | .. |
---|
1197 | 1316 | .llseek = cifs_llseek, |
---|
1198 | 1317 | .unlocked_ioctl = cifs_ioctl, |
---|
1199 | 1318 | .copy_file_range = cifs_copy_file_range, |
---|
1200 | | - .clone_file_range = cifs_clone_file_range, |
---|
| 1319 | + .remap_file_range = cifs_remap_file_range, |
---|
1201 | 1320 | .setlease = cifs_setlease, |
---|
1202 | 1321 | .fallocate = cifs_fallocate, |
---|
1203 | 1322 | }; |
---|
.. | .. |
---|
1215 | 1334 | .llseek = cifs_llseek, |
---|
1216 | 1335 | .unlocked_ioctl = cifs_ioctl, |
---|
1217 | 1336 | .copy_file_range = cifs_copy_file_range, |
---|
1218 | | - .clone_file_range = cifs_clone_file_range, |
---|
| 1337 | + .remap_file_range = cifs_remap_file_range, |
---|
1219 | 1338 | .setlease = cifs_setlease, |
---|
1220 | 1339 | .fallocate = cifs_fallocate, |
---|
1221 | 1340 | }; |
---|
1222 | 1341 | |
---|
1223 | 1342 | const struct file_operations cifs_file_direct_nobrl_ops = { |
---|
1224 | | - /* BB reevaluate whether they can be done with directio, no cache */ |
---|
1225 | | - .read_iter = cifs_user_readv, |
---|
1226 | | - .write_iter = cifs_user_writev, |
---|
| 1343 | + .read_iter = cifs_direct_readv, |
---|
| 1344 | + .write_iter = cifs_direct_writev, |
---|
1227 | 1345 | .open = cifs_open, |
---|
1228 | 1346 | .release = cifs_close, |
---|
1229 | 1347 | .fsync = cifs_fsync, |
---|
.. | .. |
---|
1233 | 1351 | .splice_write = iter_file_splice_write, |
---|
1234 | 1352 | .unlocked_ioctl = cifs_ioctl, |
---|
1235 | 1353 | .copy_file_range = cifs_copy_file_range, |
---|
1236 | | - .clone_file_range = cifs_clone_file_range, |
---|
| 1354 | + .remap_file_range = cifs_remap_file_range, |
---|
1237 | 1355 | .llseek = cifs_llseek, |
---|
1238 | 1356 | .setlease = cifs_setlease, |
---|
1239 | 1357 | .fallocate = cifs_fallocate, |
---|
.. | .. |
---|
1245 | 1363 | .read = generic_read_dir, |
---|
1246 | 1364 | .unlocked_ioctl = cifs_ioctl, |
---|
1247 | 1365 | .copy_file_range = cifs_copy_file_range, |
---|
1248 | | - .clone_file_range = cifs_clone_file_range, |
---|
| 1366 | + .remap_file_range = cifs_remap_file_range, |
---|
1249 | 1367 | .llseek = generic_file_llseek, |
---|
1250 | 1368 | .fsync = cifs_dir_fsync, |
---|
1251 | 1369 | }; |
---|
.. | .. |
---|
1424 | 1542 | #ifdef CONFIG_CIFS_STATS2 |
---|
1425 | 1543 | atomic_set(&totBufAllocCount, 0); |
---|
1426 | 1544 | atomic_set(&totSmBufAllocCount, 0); |
---|
| 1545 | + if (slow_rsp_threshold < 1) |
---|
| 1546 | + cifs_dbg(FYI, "slow_response_threshold msgs disabled\n"); |
---|
| 1547 | + else if (slow_rsp_threshold > 32767) |
---|
| 1548 | + cifs_dbg(VFS, |
---|
| 1549 | + "slow response threshold set higher than recommended (0 to 32767)\n"); |
---|
1427 | 1550 | #endif /* CONFIG_CIFS_STATS2 */ |
---|
1428 | 1551 | |
---|
1429 | 1552 | atomic_set(&midCount, 0); |
---|
.. | .. |
---|
1450 | 1573 | goto out_clean_proc; |
---|
1451 | 1574 | } |
---|
1452 | 1575 | |
---|
| 1576 | + /* |
---|
| 1577 | + * Consider in future setting limit!=0 maybe to min(num_of_cores - 1, 3) |
---|
| 1578 | + * so that we don't launch too many worker threads but |
---|
| 1579 | + * Documentation/core-api/workqueue.rst recommends setting it to 0 |
---|
| 1580 | + */ |
---|
| 1581 | + |
---|
| 1582 | + /* WQ_UNBOUND allows decrypt tasks to run on any CPU */ |
---|
| 1583 | + decrypt_wq = alloc_workqueue("smb3decryptd", |
---|
| 1584 | + WQ_UNBOUND|WQ_FREEZABLE|WQ_MEM_RECLAIM, 0); |
---|
| 1585 | + if (!decrypt_wq) { |
---|
| 1586 | + rc = -ENOMEM; |
---|
| 1587 | + goto out_destroy_cifsiod_wq; |
---|
| 1588 | + } |
---|
| 1589 | + |
---|
| 1590 | + fileinfo_put_wq = alloc_workqueue("cifsfileinfoput", |
---|
| 1591 | + WQ_UNBOUND|WQ_FREEZABLE|WQ_MEM_RECLAIM, 0); |
---|
| 1592 | + if (!fileinfo_put_wq) { |
---|
| 1593 | + rc = -ENOMEM; |
---|
| 1594 | + goto out_destroy_decrypt_wq; |
---|
| 1595 | + } |
---|
| 1596 | + |
---|
1453 | 1597 | cifsoplockd_wq = alloc_workqueue("cifsoplockd", |
---|
1454 | 1598 | WQ_FREEZABLE|WQ_MEM_RECLAIM, 0); |
---|
1455 | 1599 | if (!cifsoplockd_wq) { |
---|
1456 | 1600 | rc = -ENOMEM; |
---|
1457 | | - goto out_destroy_cifsiod_wq; |
---|
| 1601 | + goto out_destroy_fileinfo_put_wq; |
---|
1458 | 1602 | } |
---|
1459 | 1603 | |
---|
1460 | 1604 | rc = cifs_fscache_register(); |
---|
.. | .. |
---|
1473 | 1617 | if (rc) |
---|
1474 | 1618 | goto out_destroy_mids; |
---|
1475 | 1619 | |
---|
| 1620 | +#ifdef CONFIG_CIFS_DFS_UPCALL |
---|
| 1621 | + rc = dfs_cache_init(); |
---|
| 1622 | + if (rc) |
---|
| 1623 | + goto out_destroy_request_bufs; |
---|
| 1624 | +#endif /* CONFIG_CIFS_DFS_UPCALL */ |
---|
1476 | 1625 | #ifdef CONFIG_CIFS_UPCALL |
---|
1477 | 1626 | rc = init_cifs_spnego(); |
---|
1478 | 1627 | if (rc) |
---|
1479 | | - goto out_destroy_request_bufs; |
---|
| 1628 | + goto out_destroy_dfs_cache; |
---|
1480 | 1629 | #endif /* CONFIG_CIFS_UPCALL */ |
---|
1481 | 1630 | |
---|
1482 | | -#ifdef CONFIG_CIFS_ACL |
---|
1483 | 1631 | rc = init_cifs_idmap(); |
---|
1484 | 1632 | if (rc) |
---|
1485 | 1633 | goto out_register_key_type; |
---|
1486 | | -#endif /* CONFIG_CIFS_ACL */ |
---|
1487 | 1634 | |
---|
1488 | 1635 | rc = register_filesystem(&cifs_fs_type); |
---|
1489 | 1636 | if (rc) |
---|
.. | .. |
---|
1498 | 1645 | return 0; |
---|
1499 | 1646 | |
---|
1500 | 1647 | out_init_cifs_idmap: |
---|
1501 | | -#ifdef CONFIG_CIFS_ACL |
---|
1502 | 1648 | exit_cifs_idmap(); |
---|
1503 | 1649 | out_register_key_type: |
---|
1504 | | -#endif |
---|
1505 | 1650 | #ifdef CONFIG_CIFS_UPCALL |
---|
1506 | 1651 | exit_cifs_spnego(); |
---|
| 1652 | +out_destroy_dfs_cache: |
---|
| 1653 | +#endif |
---|
| 1654 | +#ifdef CONFIG_CIFS_DFS_UPCALL |
---|
| 1655 | + dfs_cache_destroy(); |
---|
1507 | 1656 | out_destroy_request_bufs: |
---|
1508 | 1657 | #endif |
---|
1509 | 1658 | cifs_destroy_request_bufs(); |
---|
.. | .. |
---|
1515 | 1664 | cifs_fscache_unregister(); |
---|
1516 | 1665 | out_destroy_cifsoplockd_wq: |
---|
1517 | 1666 | destroy_workqueue(cifsoplockd_wq); |
---|
| 1667 | +out_destroy_fileinfo_put_wq: |
---|
| 1668 | + destroy_workqueue(fileinfo_put_wq); |
---|
| 1669 | +out_destroy_decrypt_wq: |
---|
| 1670 | + destroy_workqueue(decrypt_wq); |
---|
1518 | 1671 | out_destroy_cifsiod_wq: |
---|
1519 | 1672 | destroy_workqueue(cifsiod_wq); |
---|
1520 | 1673 | out_clean_proc: |
---|
.. | .. |
---|
1529 | 1682 | unregister_filesystem(&cifs_fs_type); |
---|
1530 | 1683 | unregister_filesystem(&smb3_fs_type); |
---|
1531 | 1684 | cifs_dfs_release_automount_timer(); |
---|
1532 | | -#ifdef CONFIG_CIFS_ACL |
---|
1533 | 1685 | exit_cifs_idmap(); |
---|
1534 | | -#endif |
---|
1535 | 1686 | #ifdef CONFIG_CIFS_UPCALL |
---|
1536 | 1687 | exit_cifs_spnego(); |
---|
| 1688 | +#endif |
---|
| 1689 | +#ifdef CONFIG_CIFS_DFS_UPCALL |
---|
| 1690 | + dfs_cache_destroy(); |
---|
1537 | 1691 | #endif |
---|
1538 | 1692 | cifs_destroy_request_bufs(); |
---|
1539 | 1693 | cifs_destroy_mids(); |
---|
1540 | 1694 | cifs_destroy_inodecache(); |
---|
1541 | 1695 | cifs_fscache_unregister(); |
---|
1542 | 1696 | destroy_workqueue(cifsoplockd_wq); |
---|
| 1697 | + destroy_workqueue(decrypt_wq); |
---|
| 1698 | + destroy_workqueue(fileinfo_put_wq); |
---|
1543 | 1699 | destroy_workqueue(cifsiod_wq); |
---|
1544 | 1700 | cifs_proc_clean(); |
---|
1545 | 1701 | } |
---|
1546 | 1702 | |
---|
1547 | | -MODULE_AUTHOR("Steve French <sfrench@us.ibm.com>"); |
---|
| 1703 | +MODULE_AUTHOR("Steve French"); |
---|
1548 | 1704 | MODULE_LICENSE("GPL"); /* combination of LGPL + GPL source behaves as GPL */ |
---|
| 1705 | +MODULE_IMPORT_NS(ANDROID_GKI_VFS_EXPORT_ONLY); |
---|
1549 | 1706 | MODULE_DESCRIPTION |
---|
1550 | | - ("VFS to access servers complying with the SNIA CIFS Specification " |
---|
1551 | | - "e.g. Samba and Windows"); |
---|
| 1707 | + ("VFS to access SMB3 servers e.g. Samba, Macs, Azure and Windows (and " |
---|
| 1708 | + "also older servers complying with the SNIA CIFS Specification)"); |
---|
1552 | 1709 | MODULE_VERSION(CIFS_VERSION); |
---|
1553 | | -MODULE_SOFTDEP("pre: arc4"); |
---|
1554 | | -MODULE_SOFTDEP("pre: des"); |
---|
1555 | | -MODULE_SOFTDEP("pre: ecb"); |
---|
1556 | | -MODULE_SOFTDEP("pre: hmac"); |
---|
1557 | | -MODULE_SOFTDEP("pre: md4"); |
---|
1558 | | -MODULE_SOFTDEP("pre: md5"); |
---|
1559 | | -MODULE_SOFTDEP("pre: nls"); |
---|
1560 | | -MODULE_SOFTDEP("pre: aes"); |
---|
1561 | | -MODULE_SOFTDEP("pre: cmac"); |
---|
1562 | | -MODULE_SOFTDEP("pre: sha256"); |
---|
1563 | | -MODULE_SOFTDEP("pre: sha512"); |
---|
1564 | | -MODULE_SOFTDEP("pre: aead2"); |
---|
1565 | | -MODULE_SOFTDEP("pre: ccm"); |
---|
| 1710 | +MODULE_SOFTDEP("ecb"); |
---|
| 1711 | +MODULE_SOFTDEP("hmac"); |
---|
| 1712 | +MODULE_SOFTDEP("md4"); |
---|
| 1713 | +MODULE_SOFTDEP("md5"); |
---|
| 1714 | +MODULE_SOFTDEP("nls"); |
---|
| 1715 | +MODULE_SOFTDEP("aes"); |
---|
| 1716 | +MODULE_SOFTDEP("cmac"); |
---|
| 1717 | +MODULE_SOFTDEP("sha256"); |
---|
| 1718 | +MODULE_SOFTDEP("sha512"); |
---|
| 1719 | +MODULE_SOFTDEP("aead2"); |
---|
| 1720 | +MODULE_SOFTDEP("ccm"); |
---|
| 1721 | +MODULE_SOFTDEP("gcm"); |
---|
1566 | 1722 | module_init(init_cifs) |
---|
1567 | 1723 | module_exit(exit_cifs) |
---|