Loading fs/cifs/connect.c +28 −13 Original line number Original line Diff line number Diff line Loading @@ -2630,12 +2630,18 @@ cifs_get_smb_ses(struct TCP_Server_Info *server, struct smb_vol *volume_info) return ERR_PTR(rc); return ERR_PTR(rc); } } static int match_tcon(struct cifs_tcon *tcon, const char *unc) static int match_tcon(struct cifs_tcon *tcon, struct smb_vol *volume_info) { { if (tcon->tidStatus == CifsExiting) if (tcon->tidStatus == CifsExiting) return 0; return 0; if (strncmp(tcon->treeName, unc, MAX_TREE_SIZE)) if (strncmp(tcon->treeName, volume_info->UNC, MAX_TREE_SIZE)) return 0; return 0; if (tcon->seal != volume_info->seal) return 0; #ifdef CONFIG_CIFS_SMB2 if (tcon->snapshot_time != volume_info->snapshot_time) return 0; #endif /* CONFIG_CIFS_SMB2 */ return 1; return 1; } } Loading @@ -2648,14 +2654,8 @@ cifs_find_tcon(struct cifs_ses *ses, struct smb_vol *volume_info) spin_lock(&cifs_tcp_ses_lock); spin_lock(&cifs_tcp_ses_lock); list_for_each(tmp, &ses->tcon_list) { list_for_each(tmp, &ses->tcon_list) { tcon = list_entry(tmp, struct cifs_tcon, tcon_list); tcon = list_entry(tmp, struct cifs_tcon, tcon_list); if (!match_tcon(tcon, volume_info->UNC)) if (!match_tcon(tcon, volume_info)) continue; continue; #ifdef CONFIG_CIFS_SMB2 if (tcon->snapshot_time != volume_info->snapshot_time) continue; #endif /* CONFIG_CIFS_SMB2 */ ++tcon->tc_count; ++tcon->tc_count; spin_unlock(&cifs_tcp_ses_lock); spin_unlock(&cifs_tcp_ses_lock); return tcon; return tcon; Loading Loading @@ -2701,8 +2701,6 @@ cifs_get_tcon(struct cifs_ses *ses, struct smb_vol *volume_info) cifs_dbg(FYI, "Found match on UNC path\n"); cifs_dbg(FYI, "Found match on UNC path\n"); /* existing tcon already has a reference */ /* existing tcon already has a reference */ cifs_put_smb_ses(ses); cifs_put_smb_ses(ses); if (tcon->seal != volume_info->seal) cifs_dbg(VFS, "transport encryption setting conflicts with existing tid\n"); return tcon; return tcon; } } Loading Loading @@ -2758,7 +2756,6 @@ cifs_get_tcon(struct cifs_ses *ses, struct smb_vol *volume_info) tcon->Flags &= ~SMB_SHARE_IS_IN_DFS; tcon->Flags &= ~SMB_SHARE_IS_IN_DFS; cifs_dbg(FYI, "DFS disabled (%d)\n", tcon->Flags); cifs_dbg(FYI, "DFS disabled (%d)\n", tcon->Flags); } } tcon->seal = volume_info->seal; tcon->use_persistent = false; tcon->use_persistent = false; /* check if SMB2 or later, CIFS does not support persistent handles */ /* check if SMB2 or later, CIFS does not support persistent handles */ if (volume_info->persistent) { if (volume_info->persistent) { Loading Loading @@ -2795,6 +2792,24 @@ cifs_get_tcon(struct cifs_ses *ses, struct smb_vol *volume_info) tcon->use_resilient = true; tcon->use_resilient = true; } } if (volume_info->seal) { if (ses->server->vals->protocol_id == 0) { cifs_dbg(VFS, "SMB3 or later required for encryption\n"); rc = -EOPNOTSUPP; goto out_fail; #ifdef CONFIG_CIFS_SMB2 } else if (tcon->ses->server->capabilities & SMB2_GLOBAL_CAP_ENCRYPTION) tcon->seal = true; else { cifs_dbg(VFS, "Encryption is not supported on share\n"); rc = -EOPNOTSUPP; goto out_fail; #endif /* CONFIG_CIFS_SMB2 */ } } /* /* * We can have only one retry value for a connection to a share so for * We can have only one retry value for a connection to a share so for * resources mounted more than once to the same server share the last * resources mounted more than once to the same server share the last Loading Loading @@ -2926,7 +2941,7 @@ cifs_match_super(struct super_block *sb, void *data) if (!match_server(tcp_srv, volume_info) || if (!match_server(tcp_srv, volume_info) || !match_session(ses, volume_info) || !match_session(ses, volume_info) || !match_tcon(tcon, volume_info->UNC) || !match_tcon(tcon, volume_info) || !match_prepath(sb, mnt_data)) { !match_prepath(sb, mnt_data)) { rc = 0; rc = 0; goto out; goto out; Loading fs/cifs/smb2pdu.c +15 −18 Original line number Original line Diff line number Diff line Loading @@ -79,9 +79,14 @@ static const int smb2_req_struct_sizes[NUMBER_OF_SMB2_COMMANDS] = { static int encryption_required(const struct cifs_tcon *tcon) static int encryption_required(const struct cifs_tcon *tcon) { { if (!tcon) return 0; if ((tcon->ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) || if ((tcon->ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) || (tcon->share_flags & SHI1005_FLAGS_ENCRYPT_DATA)) (tcon->share_flags & SHI1005_FLAGS_ENCRYPT_DATA)) return 1; return 1; if (tcon->seal && (tcon->ses->server->capabilities & SMB2_GLOBAL_CAP_ENCRYPTION)) return 1; return 0; return 0; } } Loading Loading @@ -835,8 +840,6 @@ SMB2_auth_kerberos(struct SMB2_sess_data *sess_data) ses->Suid = rsp->hdr.sync_hdr.SessionId; ses->Suid = rsp->hdr.sync_hdr.SessionId; ses->session_flags = le16_to_cpu(rsp->SessionFlags); ses->session_flags = le16_to_cpu(rsp->SessionFlags); if (ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) cifs_dbg(VFS, "SMB3 encryption not supported yet\n"); rc = SMB2_sess_establish_session(sess_data); rc = SMB2_sess_establish_session(sess_data); out_put_spnego_key: out_put_spnego_key: Loading Loading @@ -933,8 +936,6 @@ SMB2_sess_auth_rawntlmssp_negotiate(struct SMB2_sess_data *sess_data) ses->Suid = rsp->hdr.sync_hdr.SessionId; ses->Suid = rsp->hdr.sync_hdr.SessionId; ses->session_flags = le16_to_cpu(rsp->SessionFlags); ses->session_flags = le16_to_cpu(rsp->SessionFlags); if (ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) cifs_dbg(VFS, "SMB3 encryption not supported yet\n"); out: out: kfree(ntlmssp_blob); kfree(ntlmssp_blob); Loading Loading @@ -993,8 +994,6 @@ SMB2_sess_auth_rawntlmssp_authenticate(struct SMB2_sess_data *sess_data) ses->Suid = rsp->hdr.sync_hdr.SessionId; ses->Suid = rsp->hdr.sync_hdr.SessionId; ses->session_flags = le16_to_cpu(rsp->SessionFlags); ses->session_flags = le16_to_cpu(rsp->SessionFlags); if (ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) cifs_dbg(VFS, "SMB3 encryption not supported yet\n"); rc = SMB2_sess_establish_session(sess_data); rc = SMB2_sess_establish_session(sess_data); out: out: Loading Loading @@ -1145,12 +1144,6 @@ SMB2_tcon(const unsigned int xid, struct cifs_ses *ses, const char *tree, if (tcon && tcon->bad_network_name) if (tcon && tcon->bad_network_name) return -ENOENT; return -ENOENT; if ((tcon && tcon->seal) && ((ses->server->capabilities & SMB2_GLOBAL_CAP_ENCRYPTION) == 0)) { cifs_dbg(VFS, "encryption requested but no server support"); return -EOPNOTSUPP; } unc_path = kmalloc(MAX_SHARENAME_LENGTH * 2, GFP_KERNEL); unc_path = kmalloc(MAX_SHARENAME_LENGTH * 2, GFP_KERNEL); if (unc_path == NULL) if (unc_path == NULL) return -ENOMEM; return -ENOMEM; Loading @@ -1168,15 +1161,16 @@ SMB2_tcon(const unsigned int xid, struct cifs_ses *ses, const char *tree, return rc; return rc; } } if (ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) if (tcon == NULL) { if ((ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA)) flags |= CIFS_TRANSFORM_REQ; flags |= CIFS_TRANSFORM_REQ; if (tcon == NULL) { /* since no tcon, smb2_init can not do this, so do here */ /* since no tcon, smb2_init can not do this, so do here */ req->hdr.sync_hdr.SessionId = ses->Suid; req->hdr.sync_hdr.SessionId = ses->Suid; /* if (ses->server->sec_mode & SECMODE_SIGN_REQUIRED) /* if (ses->server->sec_mode & SECMODE_SIGN_REQUIRED) req->hdr.Flags |= SMB2_FLAGS_SIGNED; */ req->hdr.Flags |= SMB2_FLAGS_SIGNED; */ } } else if (encryption_required(tcon)) flags |= CIFS_TRANSFORM_REQ; iov[0].iov_base = (char *)req; iov[0].iov_base = (char *)req; /* 4 for rfc1002 length field and 1 for pad */ /* 4 for rfc1002 length field and 1 for pad */ Loading Loading @@ -1233,9 +1227,12 @@ SMB2_tcon(const unsigned int xid, struct cifs_ses *ses, const char *tree, if ((rsp->Capabilities & SMB2_SHARE_CAP_DFS) && if ((rsp->Capabilities & SMB2_SHARE_CAP_DFS) && ((tcon->share_flags & SHI1005_FLAGS_DFS) == 0)) ((tcon->share_flags & SHI1005_FLAGS_DFS) == 0)) cifs_dbg(VFS, "DFS capability contradicts DFS flag\n"); cifs_dbg(VFS, "DFS capability contradicts DFS flag\n"); if (tcon->seal && !(tcon->ses->server->capabilities & SMB2_GLOBAL_CAP_ENCRYPTION)) cifs_dbg(VFS, "Encryption is requested but not supported\n"); init_copy_chunk_defaults(tcon); init_copy_chunk_defaults(tcon); if (tcon->share_flags & SHI1005_FLAGS_ENCRYPT_DATA) cifs_dbg(VFS, "Encrypted shares not supported"); if (tcon->ses->server->ops->validate_negotiate) if (tcon->ses->server->ops->validate_negotiate) rc = tcon->ses->server->ops->validate_negotiate(xid, tcon); rc = tcon->ses->server->ops->validate_negotiate(xid, tcon); tcon_exit: tcon_exit: Loading Loading
fs/cifs/connect.c +28 −13 Original line number Original line Diff line number Diff line Loading @@ -2630,12 +2630,18 @@ cifs_get_smb_ses(struct TCP_Server_Info *server, struct smb_vol *volume_info) return ERR_PTR(rc); return ERR_PTR(rc); } } static int match_tcon(struct cifs_tcon *tcon, const char *unc) static int match_tcon(struct cifs_tcon *tcon, struct smb_vol *volume_info) { { if (tcon->tidStatus == CifsExiting) if (tcon->tidStatus == CifsExiting) return 0; return 0; if (strncmp(tcon->treeName, unc, MAX_TREE_SIZE)) if (strncmp(tcon->treeName, volume_info->UNC, MAX_TREE_SIZE)) return 0; return 0; if (tcon->seal != volume_info->seal) return 0; #ifdef CONFIG_CIFS_SMB2 if (tcon->snapshot_time != volume_info->snapshot_time) return 0; #endif /* CONFIG_CIFS_SMB2 */ return 1; return 1; } } Loading @@ -2648,14 +2654,8 @@ cifs_find_tcon(struct cifs_ses *ses, struct smb_vol *volume_info) spin_lock(&cifs_tcp_ses_lock); spin_lock(&cifs_tcp_ses_lock); list_for_each(tmp, &ses->tcon_list) { list_for_each(tmp, &ses->tcon_list) { tcon = list_entry(tmp, struct cifs_tcon, tcon_list); tcon = list_entry(tmp, struct cifs_tcon, tcon_list); if (!match_tcon(tcon, volume_info->UNC)) if (!match_tcon(tcon, volume_info)) continue; continue; #ifdef CONFIG_CIFS_SMB2 if (tcon->snapshot_time != volume_info->snapshot_time) continue; #endif /* CONFIG_CIFS_SMB2 */ ++tcon->tc_count; ++tcon->tc_count; spin_unlock(&cifs_tcp_ses_lock); spin_unlock(&cifs_tcp_ses_lock); return tcon; return tcon; Loading Loading @@ -2701,8 +2701,6 @@ cifs_get_tcon(struct cifs_ses *ses, struct smb_vol *volume_info) cifs_dbg(FYI, "Found match on UNC path\n"); cifs_dbg(FYI, "Found match on UNC path\n"); /* existing tcon already has a reference */ /* existing tcon already has a reference */ cifs_put_smb_ses(ses); cifs_put_smb_ses(ses); if (tcon->seal != volume_info->seal) cifs_dbg(VFS, "transport encryption setting conflicts with existing tid\n"); return tcon; return tcon; } } Loading Loading @@ -2758,7 +2756,6 @@ cifs_get_tcon(struct cifs_ses *ses, struct smb_vol *volume_info) tcon->Flags &= ~SMB_SHARE_IS_IN_DFS; tcon->Flags &= ~SMB_SHARE_IS_IN_DFS; cifs_dbg(FYI, "DFS disabled (%d)\n", tcon->Flags); cifs_dbg(FYI, "DFS disabled (%d)\n", tcon->Flags); } } tcon->seal = volume_info->seal; tcon->use_persistent = false; tcon->use_persistent = false; /* check if SMB2 or later, CIFS does not support persistent handles */ /* check if SMB2 or later, CIFS does not support persistent handles */ if (volume_info->persistent) { if (volume_info->persistent) { Loading Loading @@ -2795,6 +2792,24 @@ cifs_get_tcon(struct cifs_ses *ses, struct smb_vol *volume_info) tcon->use_resilient = true; tcon->use_resilient = true; } } if (volume_info->seal) { if (ses->server->vals->protocol_id == 0) { cifs_dbg(VFS, "SMB3 or later required for encryption\n"); rc = -EOPNOTSUPP; goto out_fail; #ifdef CONFIG_CIFS_SMB2 } else if (tcon->ses->server->capabilities & SMB2_GLOBAL_CAP_ENCRYPTION) tcon->seal = true; else { cifs_dbg(VFS, "Encryption is not supported on share\n"); rc = -EOPNOTSUPP; goto out_fail; #endif /* CONFIG_CIFS_SMB2 */ } } /* /* * We can have only one retry value for a connection to a share so for * We can have only one retry value for a connection to a share so for * resources mounted more than once to the same server share the last * resources mounted more than once to the same server share the last Loading Loading @@ -2926,7 +2941,7 @@ cifs_match_super(struct super_block *sb, void *data) if (!match_server(tcp_srv, volume_info) || if (!match_server(tcp_srv, volume_info) || !match_session(ses, volume_info) || !match_session(ses, volume_info) || !match_tcon(tcon, volume_info->UNC) || !match_tcon(tcon, volume_info) || !match_prepath(sb, mnt_data)) { !match_prepath(sb, mnt_data)) { rc = 0; rc = 0; goto out; goto out; Loading
fs/cifs/smb2pdu.c +15 −18 Original line number Original line Diff line number Diff line Loading @@ -79,9 +79,14 @@ static const int smb2_req_struct_sizes[NUMBER_OF_SMB2_COMMANDS] = { static int encryption_required(const struct cifs_tcon *tcon) static int encryption_required(const struct cifs_tcon *tcon) { { if (!tcon) return 0; if ((tcon->ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) || if ((tcon->ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) || (tcon->share_flags & SHI1005_FLAGS_ENCRYPT_DATA)) (tcon->share_flags & SHI1005_FLAGS_ENCRYPT_DATA)) return 1; return 1; if (tcon->seal && (tcon->ses->server->capabilities & SMB2_GLOBAL_CAP_ENCRYPTION)) return 1; return 0; return 0; } } Loading Loading @@ -835,8 +840,6 @@ SMB2_auth_kerberos(struct SMB2_sess_data *sess_data) ses->Suid = rsp->hdr.sync_hdr.SessionId; ses->Suid = rsp->hdr.sync_hdr.SessionId; ses->session_flags = le16_to_cpu(rsp->SessionFlags); ses->session_flags = le16_to_cpu(rsp->SessionFlags); if (ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) cifs_dbg(VFS, "SMB3 encryption not supported yet\n"); rc = SMB2_sess_establish_session(sess_data); rc = SMB2_sess_establish_session(sess_data); out_put_spnego_key: out_put_spnego_key: Loading Loading @@ -933,8 +936,6 @@ SMB2_sess_auth_rawntlmssp_negotiate(struct SMB2_sess_data *sess_data) ses->Suid = rsp->hdr.sync_hdr.SessionId; ses->Suid = rsp->hdr.sync_hdr.SessionId; ses->session_flags = le16_to_cpu(rsp->SessionFlags); ses->session_flags = le16_to_cpu(rsp->SessionFlags); if (ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) cifs_dbg(VFS, "SMB3 encryption not supported yet\n"); out: out: kfree(ntlmssp_blob); kfree(ntlmssp_blob); Loading Loading @@ -993,8 +994,6 @@ SMB2_sess_auth_rawntlmssp_authenticate(struct SMB2_sess_data *sess_data) ses->Suid = rsp->hdr.sync_hdr.SessionId; ses->Suid = rsp->hdr.sync_hdr.SessionId; ses->session_flags = le16_to_cpu(rsp->SessionFlags); ses->session_flags = le16_to_cpu(rsp->SessionFlags); if (ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) cifs_dbg(VFS, "SMB3 encryption not supported yet\n"); rc = SMB2_sess_establish_session(sess_data); rc = SMB2_sess_establish_session(sess_data); out: out: Loading Loading @@ -1145,12 +1144,6 @@ SMB2_tcon(const unsigned int xid, struct cifs_ses *ses, const char *tree, if (tcon && tcon->bad_network_name) if (tcon && tcon->bad_network_name) return -ENOENT; return -ENOENT; if ((tcon && tcon->seal) && ((ses->server->capabilities & SMB2_GLOBAL_CAP_ENCRYPTION) == 0)) { cifs_dbg(VFS, "encryption requested but no server support"); return -EOPNOTSUPP; } unc_path = kmalloc(MAX_SHARENAME_LENGTH * 2, GFP_KERNEL); unc_path = kmalloc(MAX_SHARENAME_LENGTH * 2, GFP_KERNEL); if (unc_path == NULL) if (unc_path == NULL) return -ENOMEM; return -ENOMEM; Loading @@ -1168,15 +1161,16 @@ SMB2_tcon(const unsigned int xid, struct cifs_ses *ses, const char *tree, return rc; return rc; } } if (ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) if (tcon == NULL) { if ((ses->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA)) flags |= CIFS_TRANSFORM_REQ; flags |= CIFS_TRANSFORM_REQ; if (tcon == NULL) { /* since no tcon, smb2_init can not do this, so do here */ /* since no tcon, smb2_init can not do this, so do here */ req->hdr.sync_hdr.SessionId = ses->Suid; req->hdr.sync_hdr.SessionId = ses->Suid; /* if (ses->server->sec_mode & SECMODE_SIGN_REQUIRED) /* if (ses->server->sec_mode & SECMODE_SIGN_REQUIRED) req->hdr.Flags |= SMB2_FLAGS_SIGNED; */ req->hdr.Flags |= SMB2_FLAGS_SIGNED; */ } } else if (encryption_required(tcon)) flags |= CIFS_TRANSFORM_REQ; iov[0].iov_base = (char *)req; iov[0].iov_base = (char *)req; /* 4 for rfc1002 length field and 1 for pad */ /* 4 for rfc1002 length field and 1 for pad */ Loading Loading @@ -1233,9 +1227,12 @@ SMB2_tcon(const unsigned int xid, struct cifs_ses *ses, const char *tree, if ((rsp->Capabilities & SMB2_SHARE_CAP_DFS) && if ((rsp->Capabilities & SMB2_SHARE_CAP_DFS) && ((tcon->share_flags & SHI1005_FLAGS_DFS) == 0)) ((tcon->share_flags & SHI1005_FLAGS_DFS) == 0)) cifs_dbg(VFS, "DFS capability contradicts DFS flag\n"); cifs_dbg(VFS, "DFS capability contradicts DFS flag\n"); if (tcon->seal && !(tcon->ses->server->capabilities & SMB2_GLOBAL_CAP_ENCRYPTION)) cifs_dbg(VFS, "Encryption is requested but not supported\n"); init_copy_chunk_defaults(tcon); init_copy_chunk_defaults(tcon); if (tcon->share_flags & SHI1005_FLAGS_ENCRYPT_DATA) cifs_dbg(VFS, "Encrypted shares not supported"); if (tcon->ses->server->ops->validate_negotiate) if (tcon->ses->server->ops->validate_negotiate) rc = tcon->ses->server->ops->validate_negotiate(xid, tcon); rc = tcon->ses->server->ops->validate_negotiate(xid, tcon); tcon_exit: tcon_exit: Loading