4370 lines · c
1// SPDX-License-Identifier: LGPL-2.12/*3 *4 * Copyright (C) International Business Machines Corp., 2002,20115 * Author(s): Steve French (sfrench@us.ibm.com)6 *7 */8#include <linux/fs.h>9#include <linux/net.h>10#include <linux/string.h>11#include <linux/sched/mm.h>12#include <linux/sched/signal.h>13#include <linux/list.h>14#include <linux/wait.h>15#include <linux/slab.h>16#include <linux/pagemap.h>17#include <linux/ctype.h>18#include <linux/utsname.h>19#include <linux/mempool.h>20#include <linux/delay.h>21#include <linux/completion.h>22#include <linux/kthread.h>23#include <linux/pagevec.h>24#include <linux/freezer.h>25#include <linux/namei.h>26#include <linux/uuid.h>27#include <linux/uaccess.h>28#include <asm/processor.h>29#include <linux/inet.h>30#include <linux/module.h>31#include <keys/user-type.h>32#include <net/ipv6.h>33#include <linux/parser.h>34#include <linux/bvec.h>35#include "cifspdu.h"36#include "cifsglob.h"37#include "cifsproto.h"38#include "cifs_unicode.h"39#include "cifs_debug.h"40#include "cifs_fs_sb.h"41#include "ntlmssp.h"42#include "nterr.h"43#include "rfc1002pdu.h"44#include "fscache.h"45#include "smb2proto.h"46#include "smbdirect.h"47#include "dns_resolve.h"48#ifdef CONFIG_CIFS_DFS_UPCALL49#include "dfs.h"50#include "dfs_cache.h"51#endif52#include "fs_context.h"53#include "cifs_swn.h"54 55/* FIXME: should these be tunable? */56#define TLINK_ERROR_EXPIRE (1 * HZ)57#define TLINK_IDLE_EXPIRE (600 * HZ)58 59/* Drop the connection to not overload the server */60#define MAX_STATUS_IO_TIMEOUT 561 62static int ip_connect(struct TCP_Server_Info *server);63static int generic_ip_connect(struct TCP_Server_Info *server);64static void tlink_rb_insert(struct rb_root *root, struct tcon_link *new_tlink);65static void cifs_prune_tlinks(struct work_struct *work);66 67/*68 * Resolve hostname and set ip addr in tcp ses. Useful for hostnames that may69 * get their ip addresses changed at some point.70 *71 * This should be called with server->srv_mutex held.72 */73static int reconn_set_ipaddr_from_hostname(struct TCP_Server_Info *server)74{75 int rc;76 int len;77 char *unc;78 struct sockaddr_storage ss;79 80 if (!server->hostname)81 return -EINVAL;82 83 /* if server hostname isn't populated, there's nothing to do here */84 if (server->hostname[0] == '\0')85 return 0;86 87 len = strlen(server->hostname) + 3;88 89 unc = kmalloc(len, GFP_KERNEL);90 if (!unc) {91 cifs_dbg(FYI, "%s: failed to create UNC path\n", __func__);92 return -ENOMEM;93 }94 scnprintf(unc, len, "\\\\%s", server->hostname);95 96 spin_lock(&server->srv_lock);97 ss = server->dstaddr;98 spin_unlock(&server->srv_lock);99 100 rc = dns_resolve_server_name_to_ip(unc, (struct sockaddr *)&ss, NULL);101 kfree(unc);102 103 if (rc < 0) {104 cifs_dbg(FYI, "%s: failed to resolve server part of %s to IP: %d\n",105 __func__, server->hostname, rc);106 } else {107 spin_lock(&server->srv_lock);108 memcpy(&server->dstaddr, &ss, sizeof(server->dstaddr));109 spin_unlock(&server->srv_lock);110 rc = 0;111 }112 113 return rc;114}115 116static void smb2_query_server_interfaces(struct work_struct *work)117{118 int rc;119 int xid;120 struct cifs_tcon *tcon = container_of(work,121 struct cifs_tcon,122 query_interfaces.work);123 struct TCP_Server_Info *server = tcon->ses->server;124 125 /*126 * query server network interfaces, in case they change127 */128 if (!server->ops->query_server_interfaces)129 return;130 131 xid = get_xid();132 rc = server->ops->query_server_interfaces(xid, tcon, false);133 free_xid(xid);134 135 if (rc) {136 if (rc == -EOPNOTSUPP)137 return;138 139 cifs_dbg(FYI, "%s: failed to query server interfaces: %d\n",140 __func__, rc);141 }142 143 queue_delayed_work(cifsiod_wq, &tcon->query_interfaces,144 (SMB_INTERFACE_POLL_INTERVAL * HZ));145}146 147/*148 * Update the tcpStatus for the server.149 * This is used to signal the cifsd thread to call cifs_reconnect150 * ONLY cifsd thread should call cifs_reconnect. For any other151 * thread, use this function152 *153 * @server: the tcp ses for which reconnect is needed154 * @all_channels: if this needs to be done for all channels155 */156void157cifs_signal_cifsd_for_reconnect(struct TCP_Server_Info *server,158 bool all_channels)159{160 struct TCP_Server_Info *pserver;161 struct cifs_ses *ses;162 int i;163 164 /* If server is a channel, select the primary channel */165 pserver = SERVER_IS_CHAN(server) ? server->primary_server : server;166 167 /* if we need to signal just this channel */168 if (!all_channels) {169 spin_lock(&server->srv_lock);170 if (server->tcpStatus != CifsExiting)171 server->tcpStatus = CifsNeedReconnect;172 spin_unlock(&server->srv_lock);173 return;174 }175 176 spin_lock(&cifs_tcp_ses_lock);177 list_for_each_entry(ses, &pserver->smb_ses_list, smb_ses_list) {178 if (cifs_ses_exiting(ses))179 continue;180 spin_lock(&ses->chan_lock);181 for (i = 0; i < ses->chan_count; i++) {182 if (!ses->chans[i].server)183 continue;184 185 spin_lock(&ses->chans[i].server->srv_lock);186 if (ses->chans[i].server->tcpStatus != CifsExiting)187 ses->chans[i].server->tcpStatus = CifsNeedReconnect;188 spin_unlock(&ses->chans[i].server->srv_lock);189 }190 spin_unlock(&ses->chan_lock);191 }192 spin_unlock(&cifs_tcp_ses_lock);193}194 195/*196 * Mark all sessions and tcons for reconnect.197 * IMPORTANT: make sure that this gets called only from198 * cifsd thread. For any other thread, use199 * cifs_signal_cifsd_for_reconnect200 *201 * @server: the tcp ses for which reconnect is needed202 * @server needs to be previously set to CifsNeedReconnect.203 * @mark_smb_session: whether even sessions need to be marked204 */205void206cifs_mark_tcp_ses_conns_for_reconnect(struct TCP_Server_Info *server,207 bool mark_smb_session)208{209 struct TCP_Server_Info *pserver;210 struct cifs_ses *ses, *nses;211 struct cifs_tcon *tcon;212 213 /*214 * before reconnecting the tcp session, mark the smb session (uid) and the tid bad so they215 * are not used until reconnected.216 */217 cifs_dbg(FYI, "%s: marking necessary sessions and tcons for reconnect\n", __func__);218 219 /* If server is a channel, select the primary channel */220 pserver = SERVER_IS_CHAN(server) ? server->primary_server : server;221 222 /*223 * if the server has been marked for termination, there is a224 * chance that the remaining channels all need reconnect. To be225 * on the safer side, mark the session and trees for reconnect226 * for this scenario. This might cause a few redundant session227 * setup and tree connect requests, but it is better than not doing228 * a tree connect when needed, and all following requests failing229 */230 if (server->terminate) {231 mark_smb_session = true;232 server = pserver;233 }234 235 spin_lock(&cifs_tcp_ses_lock);236 list_for_each_entry_safe(ses, nses, &pserver->smb_ses_list, smb_ses_list) {237 spin_lock(&ses->ses_lock);238 if (ses->ses_status == SES_EXITING) {239 spin_unlock(&ses->ses_lock);240 continue;241 }242 spin_unlock(&ses->ses_lock);243 244 spin_lock(&ses->chan_lock);245 if (cifs_ses_get_chan_index(ses, server) ==246 CIFS_INVAL_CHAN_INDEX) {247 spin_unlock(&ses->chan_lock);248 continue;249 }250 251 if (!cifs_chan_is_iface_active(ses, server)) {252 spin_unlock(&ses->chan_lock);253 cifs_chan_update_iface(ses, server);254 spin_lock(&ses->chan_lock);255 }256 257 if (!mark_smb_session && cifs_chan_needs_reconnect(ses, server)) {258 spin_unlock(&ses->chan_lock);259 continue;260 }261 262 if (mark_smb_session)263 CIFS_SET_ALL_CHANS_NEED_RECONNECT(ses);264 else265 cifs_chan_set_need_reconnect(ses, server);266 267 cifs_dbg(FYI, "%s: channel connect bitmap: 0x%lx\n",268 __func__, ses->chans_need_reconnect);269 270 /* If all channels need reconnect, then tcon needs reconnect */271 if (!mark_smb_session && !CIFS_ALL_CHANS_NEED_RECONNECT(ses)) {272 spin_unlock(&ses->chan_lock);273 continue;274 }275 spin_unlock(&ses->chan_lock);276 277 spin_lock(&ses->ses_lock);278 ses->ses_status = SES_NEED_RECON;279 spin_unlock(&ses->ses_lock);280 281 list_for_each_entry(tcon, &ses->tcon_list, tcon_list) {282 tcon->need_reconnect = true;283 spin_lock(&tcon->tc_lock);284 tcon->status = TID_NEED_RECON;285 spin_unlock(&tcon->tc_lock);286 287 cancel_delayed_work(&tcon->query_interfaces);288 }289 if (ses->tcon_ipc) {290 ses->tcon_ipc->need_reconnect = true;291 spin_lock(&ses->tcon_ipc->tc_lock);292 ses->tcon_ipc->status = TID_NEED_RECON;293 spin_unlock(&ses->tcon_ipc->tc_lock);294 }295 }296 spin_unlock(&cifs_tcp_ses_lock);297}298 299static void300cifs_abort_connection(struct TCP_Server_Info *server)301{302 struct mid_q_entry *mid, *nmid;303 struct list_head retry_list;304 305 server->maxBuf = 0;306 server->max_read = 0;307 308 /* do not want to be sending data on a socket we are freeing */309 cifs_dbg(FYI, "%s: tearing down socket\n", __func__);310 cifs_server_lock(server);311 if (server->ssocket) {312 cifs_dbg(FYI, "State: 0x%x Flags: 0x%lx\n", server->ssocket->state,313 server->ssocket->flags);314 kernel_sock_shutdown(server->ssocket, SHUT_WR);315 cifs_dbg(FYI, "Post shutdown state: 0x%x Flags: 0x%lx\n", server->ssocket->state,316 server->ssocket->flags);317 sock_release(server->ssocket);318 server->ssocket = NULL;319 }320 server->sequence_number = 0;321 server->session_estab = false;322 kfree_sensitive(server->session_key.response);323 server->session_key.response = NULL;324 server->session_key.len = 0;325 server->lstrp = jiffies;326 327 /* mark submitted MIDs for retry and issue callback */328 INIT_LIST_HEAD(&retry_list);329 cifs_dbg(FYI, "%s: moving mids to private list\n", __func__);330 spin_lock(&server->mid_lock);331 list_for_each_entry_safe(mid, nmid, &server->pending_mid_q, qhead) {332 kref_get(&mid->refcount);333 if (mid->mid_state == MID_REQUEST_SUBMITTED)334 mid->mid_state = MID_RETRY_NEEDED;335 list_move(&mid->qhead, &retry_list);336 mid->mid_flags |= MID_DELETED;337 }338 spin_unlock(&server->mid_lock);339 cifs_server_unlock(server);340 341 cifs_dbg(FYI, "%s: issuing mid callbacks\n", __func__);342 list_for_each_entry_safe(mid, nmid, &retry_list, qhead) {343 list_del_init(&mid->qhead);344 mid->callback(mid);345 release_mid(mid);346 }347 348 if (cifs_rdma_enabled(server)) {349 cifs_server_lock(server);350 smbd_destroy(server);351 cifs_server_unlock(server);352 }353}354 355static bool cifs_tcp_ses_needs_reconnect(struct TCP_Server_Info *server, int num_targets)356{357 spin_lock(&server->srv_lock);358 server->nr_targets = num_targets;359 if (server->tcpStatus == CifsExiting) {360 /* the demux thread will exit normally next time through the loop */361 spin_unlock(&server->srv_lock);362 wake_up(&server->response_q);363 return false;364 }365 366 cifs_dbg(FYI, "Mark tcp session as need reconnect\n");367 trace_smb3_reconnect(server->CurrentMid, server->conn_id,368 server->hostname);369 server->tcpStatus = CifsNeedReconnect;370 371 spin_unlock(&server->srv_lock);372 return true;373}374 375/*376 * cifs tcp session reconnection377 *378 * mark tcp session as reconnecting so temporarily locked379 * mark all smb sessions as reconnecting for tcp session380 * reconnect tcp session381 * wake up waiters on reconnection? - (not needed currently)382 *383 * if mark_smb_session is passed as true, unconditionally mark384 * the smb session (and tcon) for reconnect as well. This value385 * doesn't really matter for non-multichannel scenario.386 *387 */388static int __cifs_reconnect(struct TCP_Server_Info *server,389 bool mark_smb_session)390{391 int rc = 0;392 393 if (!cifs_tcp_ses_needs_reconnect(server, 1))394 return 0;395 396 cifs_mark_tcp_ses_conns_for_reconnect(server, mark_smb_session);397 398 cifs_abort_connection(server);399 400 do {401 try_to_freeze();402 cifs_server_lock(server);403 404 if (!cifs_swn_set_server_dstaddr(server)) {405 /* resolve the hostname again to make sure that IP address is up-to-date */406 rc = reconn_set_ipaddr_from_hostname(server);407 cifs_dbg(FYI, "%s: reconn_set_ipaddr_from_hostname: rc=%d\n", __func__, rc);408 }409 410 if (cifs_rdma_enabled(server))411 rc = smbd_reconnect(server);412 else413 rc = generic_ip_connect(server);414 if (rc) {415 cifs_server_unlock(server);416 cifs_dbg(FYI, "%s: reconnect error %d\n", __func__, rc);417 msleep(3000);418 } else {419 atomic_inc(&tcpSesReconnectCount);420 set_credits(server, 1);421 spin_lock(&server->srv_lock);422 if (server->tcpStatus != CifsExiting)423 server->tcpStatus = CifsNeedNegotiate;424 spin_unlock(&server->srv_lock);425 cifs_swn_reset_server_dstaddr(server);426 cifs_server_unlock(server);427 mod_delayed_work(cifsiod_wq, &server->reconnect, 0);428 }429 } while (server->tcpStatus == CifsNeedReconnect);430 431 spin_lock(&server->srv_lock);432 if (server->tcpStatus == CifsNeedNegotiate)433 mod_delayed_work(cifsiod_wq, &server->echo, 0);434 spin_unlock(&server->srv_lock);435 436 wake_up(&server->response_q);437 return rc;438}439 440#ifdef CONFIG_CIFS_DFS_UPCALL441static int __reconnect_target_unlocked(struct TCP_Server_Info *server, const char *target)442{443 int rc;444 char *hostname;445 446 if (!cifs_swn_set_server_dstaddr(server)) {447 if (server->hostname != target) {448 hostname = extract_hostname(target);449 if (!IS_ERR(hostname)) {450 spin_lock(&server->srv_lock);451 kfree(server->hostname);452 server->hostname = hostname;453 spin_unlock(&server->srv_lock);454 } else {455 cifs_dbg(FYI, "%s: couldn't extract hostname or address from dfs target: %ld\n",456 __func__, PTR_ERR(hostname));457 cifs_dbg(FYI, "%s: default to last target server: %s\n", __func__,458 server->hostname);459 }460 }461 /* resolve the hostname again to make sure that IP address is up-to-date. */462 rc = reconn_set_ipaddr_from_hostname(server);463 cifs_dbg(FYI, "%s: reconn_set_ipaddr_from_hostname: rc=%d\n", __func__, rc);464 }465 /* Reconnect the socket */466 if (cifs_rdma_enabled(server))467 rc = smbd_reconnect(server);468 else469 rc = generic_ip_connect(server);470 471 return rc;472}473 474static int reconnect_target_unlocked(struct TCP_Server_Info *server, struct dfs_cache_tgt_list *tl,475 struct dfs_cache_tgt_iterator **target_hint)476{477 int rc;478 struct dfs_cache_tgt_iterator *tit;479 480 *target_hint = NULL;481 482 /* If dfs target list is empty, then reconnect to last server */483 tit = dfs_cache_get_tgt_iterator(tl);484 if (!tit)485 return __reconnect_target_unlocked(server, server->hostname);486 487 /* Otherwise, try every dfs target in @tl */488 for (; tit; tit = dfs_cache_get_next_tgt(tl, tit)) {489 rc = __reconnect_target_unlocked(server, dfs_cache_get_tgt_name(tit));490 if (!rc) {491 *target_hint = tit;492 break;493 }494 }495 return rc;496}497 498static int reconnect_dfs_server(struct TCP_Server_Info *server)499{500 struct dfs_cache_tgt_iterator *target_hint = NULL;501 502 DFS_CACHE_TGT_LIST(tl);503 int num_targets = 0;504 int rc = 0;505 506 /*507 * Determine the number of dfs targets the referral path in @cifs_sb resolves to.508 *509 * smb2_reconnect() needs to know how long it should wait based upon the number of dfs510 * targets (server->nr_targets). It's also possible that the cached referral was cleared511 * through /proc/fs/cifs/dfscache or the target list is empty due to server settings after512 * refreshing the referral, so, in this case, default it to 1.513 */514 mutex_lock(&server->refpath_lock);515 if (!dfs_cache_noreq_find(server->leaf_fullpath + 1, NULL, &tl))516 num_targets = dfs_cache_get_nr_tgts(&tl);517 mutex_unlock(&server->refpath_lock);518 if (!num_targets)519 num_targets = 1;520 521 if (!cifs_tcp_ses_needs_reconnect(server, num_targets))522 return 0;523 524 /*525 * Unconditionally mark all sessions & tcons for reconnect as we might be connecting to a526 * different server or share during failover. It could be improved by adding some logic to527 * only do that in case it connects to a different server or share, though.528 */529 cifs_mark_tcp_ses_conns_for_reconnect(server, true);530 531 cifs_abort_connection(server);532 533 do {534 try_to_freeze();535 cifs_server_lock(server);536 537 rc = reconnect_target_unlocked(server, &tl, &target_hint);538 if (rc) {539 /* Failed to reconnect socket */540 cifs_server_unlock(server);541 cifs_dbg(FYI, "%s: reconnect error %d\n", __func__, rc);542 msleep(3000);543 continue;544 }545 /*546 * Socket was created. Update tcp session status to CifsNeedNegotiate so that a547 * process waiting for reconnect will know it needs to re-establish session and tcon548 * through the reconnected target server.549 */550 atomic_inc(&tcpSesReconnectCount);551 set_credits(server, 1);552 spin_lock(&server->srv_lock);553 if (server->tcpStatus != CifsExiting)554 server->tcpStatus = CifsNeedNegotiate;555 spin_unlock(&server->srv_lock);556 cifs_swn_reset_server_dstaddr(server);557 cifs_server_unlock(server);558 mod_delayed_work(cifsiod_wq, &server->reconnect, 0);559 } while (server->tcpStatus == CifsNeedReconnect);560 561 mutex_lock(&server->refpath_lock);562 dfs_cache_noreq_update_tgthint(server->leaf_fullpath + 1, target_hint);563 mutex_unlock(&server->refpath_lock);564 dfs_cache_free_tgts(&tl);565 566 /* Need to set up echo worker again once connection has been established */567 spin_lock(&server->srv_lock);568 if (server->tcpStatus == CifsNeedNegotiate)569 mod_delayed_work(cifsiod_wq, &server->echo, 0);570 spin_unlock(&server->srv_lock);571 572 wake_up(&server->response_q);573 return rc;574}575 576int cifs_reconnect(struct TCP_Server_Info *server, bool mark_smb_session)577{578 mutex_lock(&server->refpath_lock);579 if (!server->leaf_fullpath) {580 mutex_unlock(&server->refpath_lock);581 return __cifs_reconnect(server, mark_smb_session);582 }583 mutex_unlock(&server->refpath_lock);584 585 return reconnect_dfs_server(server);586}587#else588int cifs_reconnect(struct TCP_Server_Info *server, bool mark_smb_session)589{590 return __cifs_reconnect(server, mark_smb_session);591}592#endif593 594static void595cifs_echo_request(struct work_struct *work)596{597 int rc;598 struct TCP_Server_Info *server = container_of(work,599 struct TCP_Server_Info, echo.work);600 601 /*602 * We cannot send an echo if it is disabled.603 * Also, no need to ping if we got a response recently.604 */605 606 if (server->tcpStatus == CifsNeedReconnect ||607 server->tcpStatus == CifsExiting ||608 server->tcpStatus == CifsNew ||609 (server->ops->can_echo && !server->ops->can_echo(server)) ||610 time_before(jiffies, server->lstrp + server->echo_interval - HZ))611 goto requeue_echo;612 613 rc = server->ops->echo ? server->ops->echo(server) : -ENOSYS;614 cifs_server_dbg(FYI, "send echo request: rc = %d\n", rc);615 616 /* Check witness registrations */617 cifs_swn_check();618 619requeue_echo:620 queue_delayed_work(cifsiod_wq, &server->echo, server->echo_interval);621}622 623static bool624allocate_buffers(struct TCP_Server_Info *server)625{626 if (!server->bigbuf) {627 server->bigbuf = (char *)cifs_buf_get();628 if (!server->bigbuf) {629 cifs_server_dbg(VFS, "No memory for large SMB response\n");630 msleep(3000);631 /* retry will check if exiting */632 return false;633 }634 } else if (server->large_buf) {635 /* we are reusing a dirty large buf, clear its start */636 memset(server->bigbuf, 0, HEADER_SIZE(server));637 }638 639 if (!server->smallbuf) {640 server->smallbuf = (char *)cifs_small_buf_get();641 if (!server->smallbuf) {642 cifs_server_dbg(VFS, "No memory for SMB response\n");643 msleep(1000);644 /* retry will check if exiting */645 return false;646 }647 /* beginning of smb buffer is cleared in our buf_get */648 } else {649 /* if existing small buf clear beginning */650 memset(server->smallbuf, 0, HEADER_SIZE(server));651 }652 653 return true;654}655 656static bool657server_unresponsive(struct TCP_Server_Info *server)658{659 /*660 * If we're in the process of mounting a share or reconnecting a session661 * and the server abruptly shut down (e.g. socket wasn't closed, packet662 * had been ACK'ed but no SMB response), don't wait longer than 20s to663 * negotiate protocol.664 */665 spin_lock(&server->srv_lock);666 if (server->tcpStatus == CifsInNegotiate &&667 time_after(jiffies, server->lstrp + 20 * HZ)) {668 spin_unlock(&server->srv_lock);669 cifs_reconnect(server, false);670 return true;671 }672 /*673 * We need to wait 3 echo intervals to make sure we handle such674 * situations right:675 * 1s client sends a normal SMB request676 * 2s client gets a response677 * 30s echo workqueue job pops, and decides we got a response recently678 * and don't need to send another679 * ...680 * 65s kernel_recvmsg times out, and we see that we haven't gotten681 * a response in >60s.682 */683 if ((server->tcpStatus == CifsGood ||684 server->tcpStatus == CifsNeedNegotiate) &&685 (!server->ops->can_echo || server->ops->can_echo(server)) &&686 time_after(jiffies, server->lstrp + 3 * server->echo_interval)) {687 spin_unlock(&server->srv_lock);688 cifs_server_dbg(VFS, "has not responded in %lu seconds. Reconnecting...\n",689 (3 * server->echo_interval) / HZ);690 cifs_reconnect(server, false);691 return true;692 }693 spin_unlock(&server->srv_lock);694 695 return false;696}697 698static inline bool699zero_credits(struct TCP_Server_Info *server)700{701 int val;702 703 spin_lock(&server->req_lock);704 val = server->credits + server->echo_credits + server->oplock_credits;705 if (server->in_flight == 0 && val == 0) {706 spin_unlock(&server->req_lock);707 return true;708 }709 spin_unlock(&server->req_lock);710 return false;711}712 713static int714cifs_readv_from_socket(struct TCP_Server_Info *server, struct msghdr *smb_msg)715{716 int length = 0;717 int total_read;718 719 for (total_read = 0; msg_data_left(smb_msg); total_read += length) {720 try_to_freeze();721 722 /* reconnect if no credits and no requests in flight */723 if (zero_credits(server)) {724 cifs_reconnect(server, false);725 return -ECONNABORTED;726 }727 728 if (server_unresponsive(server))729 return -ECONNABORTED;730 if (cifs_rdma_enabled(server) && server->smbd_conn)731 length = smbd_recv(server->smbd_conn, smb_msg);732 else733 length = sock_recvmsg(server->ssocket, smb_msg, 0);734 735 spin_lock(&server->srv_lock);736 if (server->tcpStatus == CifsExiting) {737 spin_unlock(&server->srv_lock);738 return -ESHUTDOWN;739 }740 741 if (server->tcpStatus == CifsNeedReconnect) {742 spin_unlock(&server->srv_lock);743 cifs_reconnect(server, false);744 return -ECONNABORTED;745 }746 spin_unlock(&server->srv_lock);747 748 if (length == -ERESTARTSYS ||749 length == -EAGAIN ||750 length == -EINTR) {751 /*752 * Minimum sleep to prevent looping, allowing socket753 * to clear and app threads to set tcpStatus754 * CifsNeedReconnect if server hung.755 */756 usleep_range(1000, 2000);757 length = 0;758 continue;759 }760 761 if (length <= 0) {762 cifs_dbg(FYI, "Received no data or error: %d\n", length);763 cifs_reconnect(server, false);764 return -ECONNABORTED;765 }766 }767 return total_read;768}769 770int771cifs_read_from_socket(struct TCP_Server_Info *server, char *buf,772 unsigned int to_read)773{774 struct msghdr smb_msg = {};775 struct kvec iov = {.iov_base = buf, .iov_len = to_read};776 777 iov_iter_kvec(&smb_msg.msg_iter, ITER_DEST, &iov, 1, to_read);778 779 return cifs_readv_from_socket(server, &smb_msg);780}781 782ssize_t783cifs_discard_from_socket(struct TCP_Server_Info *server, size_t to_read)784{785 struct msghdr smb_msg = {};786 787 /*788 * iov_iter_discard already sets smb_msg.type and count and iov_offset789 * and cifs_readv_from_socket sets msg_control and msg_controllen790 * so little to initialize in struct msghdr791 */792 iov_iter_discard(&smb_msg.msg_iter, ITER_DEST, to_read);793 794 return cifs_readv_from_socket(server, &smb_msg);795}796 797int798cifs_read_iter_from_socket(struct TCP_Server_Info *server, struct iov_iter *iter,799 unsigned int to_read)800{801 struct msghdr smb_msg = { .msg_iter = *iter };802 803 iov_iter_truncate(&smb_msg.msg_iter, to_read);804 return cifs_readv_from_socket(server, &smb_msg);805}806 807static bool808is_smb_response(struct TCP_Server_Info *server, unsigned char type)809{810 /*811 * The first byte big endian of the length field,812 * is actually not part of the length but the type813 * with the most common, zero, as regular data.814 */815 switch (type) {816 case RFC1002_SESSION_MESSAGE:817 /* Regular SMB response */818 return true;819 case RFC1002_SESSION_KEEP_ALIVE:820 cifs_dbg(FYI, "RFC 1002 session keep alive\n");821 break;822 case RFC1002_POSITIVE_SESSION_RESPONSE:823 cifs_dbg(FYI, "RFC 1002 positive session response\n");824 break;825 case RFC1002_NEGATIVE_SESSION_RESPONSE:826 /*827 * We get this from Windows 98 instead of an error on828 * SMB negprot response.829 */830 cifs_dbg(FYI, "RFC 1002 negative session response\n");831 /* give server a second to clean up */832 msleep(1000);833 /*834 * Always try 445 first on reconnect since we get NACK835 * on some if we ever connected to port 139 (the NACK836 * is since we do not begin with RFC1001 session837 * initialize frame).838 */839 cifs_set_port((struct sockaddr *)&server->dstaddr, CIFS_PORT);840 cifs_reconnect(server, true);841 break;842 default:843 cifs_server_dbg(VFS, "RFC 1002 unknown response type 0x%x\n", type);844 cifs_reconnect(server, true);845 }846 847 return false;848}849 850void851dequeue_mid(struct mid_q_entry *mid, bool malformed)852{853#ifdef CONFIG_CIFS_STATS2854 mid->when_received = jiffies;855#endif856 spin_lock(&mid->server->mid_lock);857 if (!malformed)858 mid->mid_state = MID_RESPONSE_RECEIVED;859 else860 mid->mid_state = MID_RESPONSE_MALFORMED;861 /*862 * Trying to handle/dequeue a mid after the send_recv()863 * function has finished processing it is a bug.864 */865 if (mid->mid_flags & MID_DELETED) {866 spin_unlock(&mid->server->mid_lock);867 pr_warn_once("trying to dequeue a deleted mid\n");868 } else {869 list_del_init(&mid->qhead);870 mid->mid_flags |= MID_DELETED;871 spin_unlock(&mid->server->mid_lock);872 }873}874 875static unsigned int876smb2_get_credits_from_hdr(char *buffer, struct TCP_Server_Info *server)877{878 struct smb2_hdr *shdr = (struct smb2_hdr *)buffer;879 880 /*881 * SMB1 does not use credits.882 */883 if (is_smb1(server))884 return 0;885 886 return le16_to_cpu(shdr->CreditRequest);887}888 889static void890handle_mid(struct mid_q_entry *mid, struct TCP_Server_Info *server,891 char *buf, int malformed)892{893 if (server->ops->check_trans2 &&894 server->ops->check_trans2(mid, server, buf, malformed))895 return;896 mid->credits_received = smb2_get_credits_from_hdr(buf, server);897 mid->resp_buf = buf;898 mid->large_buf = server->large_buf;899 /* Was previous buf put in mpx struct for multi-rsp? */900 if (!mid->multiRsp) {901 /* smb buffer will be freed by user thread */902 if (server->large_buf)903 server->bigbuf = NULL;904 else905 server->smallbuf = NULL;906 }907 dequeue_mid(mid, malformed);908}909 910int911cifs_enable_signing(struct TCP_Server_Info *server, bool mnt_sign_required)912{913 bool srv_sign_required = server->sec_mode & server->vals->signing_required;914 bool srv_sign_enabled = server->sec_mode & server->vals->signing_enabled;915 bool mnt_sign_enabled;916 917 /*918 * Is signing required by mnt options? If not then check919 * global_secflags to see if it is there.920 */921 if (!mnt_sign_required)922 mnt_sign_required = ((global_secflags & CIFSSEC_MUST_SIGN) ==923 CIFSSEC_MUST_SIGN);924 925 /*926 * If signing is required then it's automatically enabled too,927 * otherwise, check to see if the secflags allow it.928 */929 mnt_sign_enabled = mnt_sign_required ? mnt_sign_required :930 (global_secflags & CIFSSEC_MAY_SIGN);931 932 /* If server requires signing, does client allow it? */933 if (srv_sign_required) {934 if (!mnt_sign_enabled) {935 cifs_dbg(VFS, "Server requires signing, but it's disabled in SecurityFlags!\n");936 return -EOPNOTSUPP;937 }938 server->sign = true;939 }940 941 /* If client requires signing, does server allow it? */942 if (mnt_sign_required) {943 if (!srv_sign_enabled) {944 cifs_dbg(VFS, "Server does not support signing!\n");945 return -EOPNOTSUPP;946 }947 server->sign = true;948 }949 950 if (cifs_rdma_enabled(server) && server->sign)951 cifs_dbg(VFS, "Signing is enabled, and RDMA read/write will be disabled\n");952 953 return 0;954}955 956static noinline_for_stack void957clean_demultiplex_info(struct TCP_Server_Info *server)958{959 int length;960 961 /* take it off the list, if it's not already */962 spin_lock(&server->srv_lock);963 list_del_init(&server->tcp_ses_list);964 spin_unlock(&server->srv_lock);965 966 cancel_delayed_work_sync(&server->echo);967 968 spin_lock(&server->srv_lock);969 server->tcpStatus = CifsExiting;970 spin_unlock(&server->srv_lock);971 wake_up_all(&server->response_q);972 973 /* check if we have blocked requests that need to free */974 spin_lock(&server->req_lock);975 if (server->credits <= 0)976 server->credits = 1;977 spin_unlock(&server->req_lock);978 /*979 * Although there should not be any requests blocked on this queue it980 * can not hurt to be paranoid and try to wake up requests that may981 * haven been blocked when more than 50 at time were on the wire to the982 * same server - they now will see the session is in exit state and get983 * out of SendReceive.984 */985 wake_up_all(&server->request_q);986 /* give those requests time to exit */987 msleep(125);988 if (cifs_rdma_enabled(server))989 smbd_destroy(server);990 if (server->ssocket) {991 sock_release(server->ssocket);992 server->ssocket = NULL;993 }994 995 if (!list_empty(&server->pending_mid_q)) {996 struct mid_q_entry *mid_entry;997 struct list_head *tmp, *tmp2;998 LIST_HEAD(dispose_list);999 1000 spin_lock(&server->mid_lock);1001 list_for_each_safe(tmp, tmp2, &server->pending_mid_q) {1002 mid_entry = list_entry(tmp, struct mid_q_entry, qhead);1003 cifs_dbg(FYI, "Clearing mid %llu\n", mid_entry->mid);1004 kref_get(&mid_entry->refcount);1005 mid_entry->mid_state = MID_SHUTDOWN;1006 list_move(&mid_entry->qhead, &dispose_list);1007 mid_entry->mid_flags |= MID_DELETED;1008 }1009 spin_unlock(&server->mid_lock);1010 1011 /* now walk dispose list and issue callbacks */1012 list_for_each_safe(tmp, tmp2, &dispose_list) {1013 mid_entry = list_entry(tmp, struct mid_q_entry, qhead);1014 cifs_dbg(FYI, "Callback mid %llu\n", mid_entry->mid);1015 list_del_init(&mid_entry->qhead);1016 mid_entry->callback(mid_entry);1017 release_mid(mid_entry);1018 }1019 /* 1/8th of sec is more than enough time for them to exit */1020 msleep(125);1021 }1022 1023 if (!list_empty(&server->pending_mid_q)) {1024 /*1025 * mpx threads have not exited yet give them at least the smb1026 * send timeout time for long ops.1027 *1028 * Due to delays on oplock break requests, we need to wait at1029 * least 45 seconds before giving up on a request getting a1030 * response and going ahead and killing cifsd.1031 */1032 cifs_dbg(FYI, "Wait for exit from demultiplex thread\n");1033 msleep(46000);1034 /*1035 * If threads still have not exited they are probably never1036 * coming home not much else we can do but free the memory.1037 */1038 }1039 1040 put_net(cifs_net_ns(server));1041 kfree(server->leaf_fullpath);1042 kfree(server);1043 1044 length = atomic_dec_return(&tcpSesAllocCount);1045 if (length > 0)1046 mempool_resize(cifs_req_poolp, length + cifs_min_rcv);1047}1048 1049static int1050standard_receive3(struct TCP_Server_Info *server, struct mid_q_entry *mid)1051{1052 int length;1053 char *buf = server->smallbuf;1054 unsigned int pdu_length = server->pdu_size;1055 1056 /* make sure this will fit in a large buffer */1057 if (pdu_length > CIFSMaxBufSize + MAX_HEADER_SIZE(server) -1058 HEADER_PREAMBLE_SIZE(server)) {1059 cifs_server_dbg(VFS, "SMB response too long (%u bytes)\n", pdu_length);1060 cifs_reconnect(server, true);1061 return -ECONNABORTED;1062 }1063 1064 /* switch to large buffer if too big for a small one */1065 if (pdu_length > MAX_CIFS_SMALL_BUFFER_SIZE - 4) {1066 server->large_buf = true;1067 memcpy(server->bigbuf, buf, server->total_read);1068 buf = server->bigbuf;1069 }1070 1071 /* now read the rest */1072 length = cifs_read_from_socket(server, buf + HEADER_SIZE(server) - 1,1073 pdu_length - MID_HEADER_SIZE(server));1074 1075 if (length < 0)1076 return length;1077 server->total_read += length;1078 1079 dump_smb(buf, server->total_read);1080 1081 return cifs_handle_standard(server, mid);1082}1083 1084int1085cifs_handle_standard(struct TCP_Server_Info *server, struct mid_q_entry *mid)1086{1087 char *buf = server->large_buf ? server->bigbuf : server->smallbuf;1088 int rc;1089 1090 /*1091 * We know that we received enough to get to the MID as we1092 * checked the pdu_length earlier. Now check to see1093 * if the rest of the header is OK.1094 *1095 * 48 bytes is enough to display the header and a little bit1096 * into the payload for debugging purposes.1097 */1098 rc = server->ops->check_message(buf, server->total_read, server);1099 if (rc)1100 cifs_dump_mem("Bad SMB: ", buf,1101 min_t(unsigned int, server->total_read, 48));1102 1103 if (server->ops->is_session_expired &&1104 server->ops->is_session_expired(buf)) {1105 cifs_reconnect(server, true);1106 return -1;1107 }1108 1109 if (server->ops->is_status_pending &&1110 server->ops->is_status_pending(buf, server))1111 return -1;1112 1113 if (!mid)1114 return rc;1115 1116 handle_mid(mid, server, buf, rc);1117 return 0;1118}1119 1120static void1121smb2_add_credits_from_hdr(char *buffer, struct TCP_Server_Info *server)1122{1123 struct smb2_hdr *shdr = (struct smb2_hdr *)buffer;1124 int scredits, in_flight;1125 1126 /*1127 * SMB1 does not use credits.1128 */1129 if (is_smb1(server))1130 return;1131 1132 if (shdr->CreditRequest) {1133 spin_lock(&server->req_lock);1134 server->credits += le16_to_cpu(shdr->CreditRequest);1135 scredits = server->credits;1136 in_flight = server->in_flight;1137 spin_unlock(&server->req_lock);1138 wake_up(&server->request_q);1139 1140 trace_smb3_hdr_credits(server->CurrentMid,1141 server->conn_id, server->hostname, scredits,1142 le16_to_cpu(shdr->CreditRequest), in_flight);1143 cifs_server_dbg(FYI, "%s: added %u credits total=%d\n",1144 __func__, le16_to_cpu(shdr->CreditRequest),1145 scredits);1146 }1147}1148 1149 1150static int1151cifs_demultiplex_thread(void *p)1152{1153 int i, num_mids, length;1154 struct TCP_Server_Info *server = p;1155 unsigned int pdu_length;1156 unsigned int next_offset;1157 char *buf = NULL;1158 struct task_struct *task_to_wake = NULL;1159 struct mid_q_entry *mids[MAX_COMPOUND];1160 char *bufs[MAX_COMPOUND];1161 unsigned int noreclaim_flag, num_io_timeout = 0;1162 bool pending_reconnect = false;1163 1164 noreclaim_flag = memalloc_noreclaim_save();1165 cifs_dbg(FYI, "Demultiplex PID: %d\n", task_pid_nr(current));1166 1167 length = atomic_inc_return(&tcpSesAllocCount);1168 if (length > 1)1169 mempool_resize(cifs_req_poolp, length + cifs_min_rcv);1170 1171 set_freezable();1172 allow_kernel_signal(SIGKILL);1173 while (server->tcpStatus != CifsExiting) {1174 if (try_to_freeze())1175 continue;1176 1177 if (!allocate_buffers(server))1178 continue;1179 1180 server->large_buf = false;1181 buf = server->smallbuf;1182 pdu_length = 4; /* enough to get RFC1001 header */1183 1184 length = cifs_read_from_socket(server, buf, pdu_length);1185 if (length < 0)1186 continue;1187 1188 if (is_smb1(server))1189 server->total_read = length;1190 else1191 server->total_read = 0;1192 1193 /*1194 * The right amount was read from socket - 4 bytes,1195 * so we can now interpret the length field.1196 */1197 pdu_length = get_rfc1002_length(buf);1198 1199 cifs_dbg(FYI, "RFC1002 header 0x%x\n", pdu_length);1200 if (!is_smb_response(server, buf[0]))1201 continue;1202 1203 pending_reconnect = false;1204next_pdu:1205 server->pdu_size = pdu_length;1206 1207 /* make sure we have enough to get to the MID */1208 if (server->pdu_size < MID_HEADER_SIZE(server)) {1209 cifs_server_dbg(VFS, "SMB response too short (%u bytes)\n",1210 server->pdu_size);1211 cifs_reconnect(server, true);1212 continue;1213 }1214 1215 /* read down to the MID */1216 length = cifs_read_from_socket(server,1217 buf + HEADER_PREAMBLE_SIZE(server),1218 MID_HEADER_SIZE(server));1219 if (length < 0)1220 continue;1221 server->total_read += length;1222 1223 if (server->ops->next_header) {1224 if (server->ops->next_header(server, buf, &next_offset)) {1225 cifs_dbg(VFS, "%s: malformed response (next_offset=%u)\n",1226 __func__, next_offset);1227 cifs_reconnect(server, true);1228 continue;1229 }1230 if (next_offset)1231 server->pdu_size = next_offset;1232 }1233 1234 memset(mids, 0, sizeof(mids));1235 memset(bufs, 0, sizeof(bufs));1236 num_mids = 0;1237 1238 if (server->ops->is_transform_hdr &&1239 server->ops->receive_transform &&1240 server->ops->is_transform_hdr(buf)) {1241 length = server->ops->receive_transform(server,1242 mids,1243 bufs,1244 &num_mids);1245 } else {1246 mids[0] = server->ops->find_mid(server, buf);1247 bufs[0] = buf;1248 num_mids = 1;1249 1250 if (!mids[0] || !mids[0]->receive)1251 length = standard_receive3(server, mids[0]);1252 else1253 length = mids[0]->receive(server, mids[0]);1254 }1255 1256 if (length < 0) {1257 for (i = 0; i < num_mids; i++)1258 if (mids[i])1259 release_mid(mids[i]);1260 continue;1261 }1262 1263 if (server->ops->is_status_io_timeout &&1264 server->ops->is_status_io_timeout(buf)) {1265 num_io_timeout++;1266 if (num_io_timeout > MAX_STATUS_IO_TIMEOUT) {1267 cifs_server_dbg(VFS,1268 "Number of request timeouts exceeded %d. Reconnecting",1269 MAX_STATUS_IO_TIMEOUT);1270 1271 pending_reconnect = true;1272 num_io_timeout = 0;1273 }1274 }1275 1276 server->lstrp = jiffies;1277 1278 for (i = 0; i < num_mids; i++) {1279 if (mids[i] != NULL) {1280 mids[i]->resp_buf_size = server->pdu_size;1281 1282 if (bufs[i] != NULL) {1283 if (server->ops->is_network_name_deleted &&1284 server->ops->is_network_name_deleted(bufs[i],1285 server)) {1286 cifs_server_dbg(FYI,1287 "Share deleted. Reconnect needed");1288 }1289 }1290 1291 if (!mids[i]->multiRsp || mids[i]->multiEnd)1292 mids[i]->callback(mids[i]);1293 1294 release_mid(mids[i]);1295 } else if (server->ops->is_oplock_break &&1296 server->ops->is_oplock_break(bufs[i],1297 server)) {1298 smb2_add_credits_from_hdr(bufs[i], server);1299 cifs_dbg(FYI, "Received oplock break\n");1300 } else {1301 cifs_server_dbg(VFS, "No task to wake, unknown frame received! NumMids %d\n",1302 atomic_read(&mid_count));1303 cifs_dump_mem("Received Data is: ", bufs[i],1304 HEADER_SIZE(server));1305 smb2_add_credits_from_hdr(bufs[i], server);1306#ifdef CONFIG_CIFS_DEBUG21307 if (server->ops->dump_detail)1308 server->ops->dump_detail(bufs[i],1309 server);1310 cifs_dump_mids(server);1311#endif /* CIFS_DEBUG2 */1312 }1313 }1314 1315 if (pdu_length > server->pdu_size) {1316 if (!allocate_buffers(server))1317 continue;1318 pdu_length -= server->pdu_size;1319 server->total_read = 0;1320 server->large_buf = false;1321 buf = server->smallbuf;1322 goto next_pdu;1323 }1324 1325 /* do this reconnect at the very end after processing all MIDs */1326 if (pending_reconnect)1327 cifs_reconnect(server, true);1328 1329 } /* end while !EXITING */1330 1331 /* buffer usually freed in free_mid - need to free it here on exit */1332 cifs_buf_release(server->bigbuf);1333 if (server->smallbuf) /* no sense logging a debug message if NULL */1334 cifs_small_buf_release(server->smallbuf);1335 1336 task_to_wake = xchg(&server->tsk, NULL);1337 clean_demultiplex_info(server);1338 1339 /* if server->tsk was NULL then wait for a signal before exiting */1340 if (!task_to_wake) {1341 set_current_state(TASK_INTERRUPTIBLE);1342 while (!signal_pending(current)) {1343 schedule();1344 set_current_state(TASK_INTERRUPTIBLE);1345 }1346 set_current_state(TASK_RUNNING);1347 }1348 1349 memalloc_noreclaim_restore(noreclaim_flag);1350 module_put_and_kthread_exit(0);1351}1352 1353int1354cifs_ipaddr_cmp(struct sockaddr *srcaddr, struct sockaddr *rhs)1355{1356 struct sockaddr_in *saddr4 = (struct sockaddr_in *)srcaddr;1357 struct sockaddr_in *vaddr4 = (struct sockaddr_in *)rhs;1358 struct sockaddr_in6 *saddr6 = (struct sockaddr_in6 *)srcaddr;1359 struct sockaddr_in6 *vaddr6 = (struct sockaddr_in6 *)rhs;1360 1361 switch (srcaddr->sa_family) {1362 case AF_UNSPEC:1363 switch (rhs->sa_family) {1364 case AF_UNSPEC:1365 return 0;1366 case AF_INET:1367 case AF_INET6:1368 return 1;1369 default:1370 return -1;1371 }1372 case AF_INET: {1373 switch (rhs->sa_family) {1374 case AF_UNSPEC:1375 return -1;1376 case AF_INET:1377 return memcmp(saddr4, vaddr4,1378 sizeof(struct sockaddr_in));1379 case AF_INET6:1380 return 1;1381 default:1382 return -1;1383 }1384 }1385 case AF_INET6: {1386 switch (rhs->sa_family) {1387 case AF_UNSPEC:1388 case AF_INET:1389 return -1;1390 case AF_INET6:1391 return memcmp(saddr6,1392 vaddr6,1393 sizeof(struct sockaddr_in6));1394 default:1395 return -1;1396 }1397 }1398 default:1399 return -1; /* don't expect to be here */1400 }1401}1402 1403/*1404 * Returns true if srcaddr isn't specified and rhs isn't specified, or1405 * if srcaddr is specified and matches the IP address of the rhs argument1406 */1407bool1408cifs_match_ipaddr(struct sockaddr *srcaddr, struct sockaddr *rhs)1409{1410 switch (srcaddr->sa_family) {1411 case AF_UNSPEC:1412 return (rhs->sa_family == AF_UNSPEC);1413 case AF_INET: {1414 struct sockaddr_in *saddr4 = (struct sockaddr_in *)srcaddr;1415 struct sockaddr_in *vaddr4 = (struct sockaddr_in *)rhs;1416 1417 return (saddr4->sin_addr.s_addr == vaddr4->sin_addr.s_addr);1418 }1419 case AF_INET6: {1420 struct sockaddr_in6 *saddr6 = (struct sockaddr_in6 *)srcaddr;1421 struct sockaddr_in6 *vaddr6 = (struct sockaddr_in6 *)rhs;1422 1423 return (ipv6_addr_equal(&saddr6->sin6_addr, &vaddr6->sin6_addr)1424 && saddr6->sin6_scope_id == vaddr6->sin6_scope_id);1425 }1426 default:1427 WARN_ON(1);1428 return false; /* don't expect to be here */1429 }1430}1431 1432/*1433 * If no port is specified in addr structure, we try to match with 445 port1434 * and if it fails - with 139 ports. It should be called only if address1435 * families of server and addr are equal.1436 */1437static bool1438match_port(struct TCP_Server_Info *server, struct sockaddr *addr)1439{1440 __be16 port, *sport;1441 1442 /* SMBDirect manages its own ports, don't match it here */1443 if (server->rdma)1444 return true;1445 1446 switch (addr->sa_family) {1447 case AF_INET:1448 sport = &((struct sockaddr_in *) &server->dstaddr)->sin_port;1449 port = ((struct sockaddr_in *) addr)->sin_port;1450 break;1451 case AF_INET6:1452 sport = &((struct sockaddr_in6 *) &server->dstaddr)->sin6_port;1453 port = ((struct sockaddr_in6 *) addr)->sin6_port;1454 break;1455 default:1456 WARN_ON(1);1457 return false;1458 }1459 1460 if (!port) {1461 port = htons(CIFS_PORT);1462 if (port == *sport)1463 return true;1464 1465 port = htons(RFC1001_PORT);1466 }1467 1468 return port == *sport;1469}1470 1471static bool match_server_address(struct TCP_Server_Info *server, struct sockaddr *addr)1472{1473 if (!cifs_match_ipaddr(addr, (struct sockaddr *)&server->dstaddr))1474 return false;1475 1476 return true;1477}1478 1479static bool1480match_security(struct TCP_Server_Info *server, struct smb3_fs_context *ctx)1481{1482 /*1483 * The select_sectype function should either return the ctx->sectype1484 * that was specified, or "Unspecified" if that sectype was not1485 * compatible with the given NEGOTIATE request.1486 */1487 if (server->ops->select_sectype(server, ctx->sectype)1488 == Unspecified)1489 return false;1490 1491 /*1492 * Now check if signing mode is acceptable. No need to check1493 * global_secflags at this point since if MUST_SIGN is set then1494 * the server->sign had better be too.1495 */1496 if (ctx->sign && !server->sign)1497 return false;1498 1499 return true;1500}1501 1502/* this function must be called with srv_lock held */1503static int match_server(struct TCP_Server_Info *server,1504 struct smb3_fs_context *ctx,1505 bool match_super)1506{1507 struct sockaddr *addr = (struct sockaddr *)&ctx->dstaddr;1508 1509 lockdep_assert_held(&server->srv_lock);1510 1511 if (ctx->nosharesock)1512 return 0;1513 1514 /* this server does not share socket */1515 if (server->nosharesock)1516 return 0;1517 1518 if (!match_super && (ctx->dfs_conn || server->dfs_conn))1519 return 0;1520 1521 /* If multidialect negotiation see if existing sessions match one */1522 if (strcmp(ctx->vals->version_string, SMB3ANY_VERSION_STRING) == 0) {1523 if (server->vals->protocol_id < SMB30_PROT_ID)1524 return 0;1525 } else if (strcmp(ctx->vals->version_string,1526 SMBDEFAULT_VERSION_STRING) == 0) {1527 if (server->vals->protocol_id < SMB21_PROT_ID)1528 return 0;1529 } else if ((server->vals != ctx->vals) || (server->ops != ctx->ops))1530 return 0;1531 1532 if (!net_eq(cifs_net_ns(server), current->nsproxy->net_ns))1533 return 0;1534 1535 if (!cifs_match_ipaddr((struct sockaddr *)&ctx->srcaddr,1536 (struct sockaddr *)&server->srcaddr))1537 return 0;1538 /*1539 * When matching cifs.ko superblocks (@match_super == true), we can't1540 * really match either @server->leaf_fullpath or @server->dstaddr1541 * directly since this @server might belong to a completely different1542 * server -- in case of domain-based DFS referrals or DFS links -- as1543 * provided earlier by mount(2) through 'source' and 'ip' options.1544 *1545 * Otherwise, match the DFS referral in @server->leaf_fullpath or the1546 * destination address in @server->dstaddr.1547 *1548 * When using 'nodfs' mount option, we avoid sharing it with DFS1549 * connections as they might failover.1550 */1551 if (!match_super) {1552 if (!ctx->nodfs) {1553 if (server->leaf_fullpath) {1554 if (!ctx->leaf_fullpath ||1555 strcasecmp(server->leaf_fullpath,1556 ctx->leaf_fullpath))1557 return 0;1558 } else if (ctx->leaf_fullpath) {1559 return 0;1560 }1561 } else if (server->leaf_fullpath) {1562 return 0;1563 }1564 }1565 1566 /*1567 * Match for a regular connection (address/hostname/port) which has no1568 * DFS referrals set.1569 */1570 if (!server->leaf_fullpath &&1571 (strcasecmp(server->hostname, ctx->server_hostname) ||1572 !match_server_address(server, addr) ||1573 !match_port(server, addr)))1574 return 0;1575 1576 if (!match_security(server, ctx))1577 return 0;1578 1579 if (server->echo_interval != ctx->echo_interval * HZ)1580 return 0;1581 1582 if (server->rdma != ctx->rdma)1583 return 0;1584 1585 if (server->ignore_signature != ctx->ignore_signature)1586 return 0;1587 1588 if (server->min_offload != ctx->min_offload)1589 return 0;1590 1591 if (server->retrans != ctx->retrans)1592 return 0;1593 1594 return 1;1595}1596 1597struct TCP_Server_Info *1598cifs_find_tcp_session(struct smb3_fs_context *ctx)1599{1600 struct TCP_Server_Info *server;1601 1602 spin_lock(&cifs_tcp_ses_lock);1603 list_for_each_entry(server, &cifs_tcp_ses_list, tcp_ses_list) {1604 spin_lock(&server->srv_lock);1605 /*1606 * Skip ses channels since they're only handled in lower layers1607 * (e.g. cifs_send_recv).1608 */1609 if (SERVER_IS_CHAN(server) ||1610 !match_server(server, ctx, false)) {1611 spin_unlock(&server->srv_lock);1612 continue;1613 }1614 spin_unlock(&server->srv_lock);1615 1616 ++server->srv_count;1617 spin_unlock(&cifs_tcp_ses_lock);1618 cifs_dbg(FYI, "Existing tcp session with server found\n");1619 return server;1620 }1621 spin_unlock(&cifs_tcp_ses_lock);1622 return NULL;1623}1624 1625void1626cifs_put_tcp_session(struct TCP_Server_Info *server, int from_reconnect)1627{1628 struct task_struct *task;1629 1630 spin_lock(&cifs_tcp_ses_lock);1631 if (--server->srv_count > 0) {1632 spin_unlock(&cifs_tcp_ses_lock);1633 return;1634 }1635 1636 /* srv_count can never go negative */1637 WARN_ON(server->srv_count < 0);1638 1639 list_del_init(&server->tcp_ses_list);1640 spin_unlock(&cifs_tcp_ses_lock);1641 1642 cancel_delayed_work_sync(&server->echo);1643 1644 if (from_reconnect)1645 /*1646 * Avoid deadlock here: reconnect work calls1647 * cifs_put_tcp_session() at its end. Need to be sure1648 * that reconnect work does nothing with server pointer after1649 * that step.1650 */1651 cancel_delayed_work(&server->reconnect);1652 else1653 cancel_delayed_work_sync(&server->reconnect);1654 1655 /* For secondary channels, we pick up ref-count on the primary server */1656 if (SERVER_IS_CHAN(server))1657 cifs_put_tcp_session(server->primary_server, from_reconnect);1658 1659 spin_lock(&server->srv_lock);1660 server->tcpStatus = CifsExiting;1661 spin_unlock(&server->srv_lock);1662 1663 cifs_crypto_secmech_release(server);1664 1665 kfree_sensitive(server->session_key.response);1666 server->session_key.response = NULL;1667 server->session_key.len = 0;1668 kfree(server->hostname);1669 server->hostname = NULL;1670 1671 task = xchg(&server->tsk, NULL);1672 if (task)1673 send_sig(SIGKILL, task, 1);1674}1675 1676struct TCP_Server_Info *1677cifs_get_tcp_session(struct smb3_fs_context *ctx,1678 struct TCP_Server_Info *primary_server)1679{1680 struct TCP_Server_Info *tcp_ses = NULL;1681 int rc;1682 1683 cifs_dbg(FYI, "UNC: %s\n", ctx->UNC);1684 1685 /* see if we already have a matching tcp_ses */1686 tcp_ses = cifs_find_tcp_session(ctx);1687 if (tcp_ses)1688 return tcp_ses;1689 1690 tcp_ses = kzalloc(sizeof(struct TCP_Server_Info), GFP_KERNEL);1691 if (!tcp_ses) {1692 rc = -ENOMEM;1693 goto out_err;1694 }1695 1696 tcp_ses->hostname = kstrdup(ctx->server_hostname, GFP_KERNEL);1697 if (!tcp_ses->hostname) {1698 rc = -ENOMEM;1699 goto out_err;1700 }1701 1702 if (ctx->leaf_fullpath) {1703 tcp_ses->leaf_fullpath = kstrdup(ctx->leaf_fullpath, GFP_KERNEL);1704 if (!tcp_ses->leaf_fullpath) {1705 rc = -ENOMEM;1706 goto out_err;1707 }1708 }1709 1710 if (ctx->nosharesock)1711 tcp_ses->nosharesock = true;1712 tcp_ses->dfs_conn = ctx->dfs_conn;1713 1714 tcp_ses->ops = ctx->ops;1715 tcp_ses->vals = ctx->vals;1716 cifs_set_net_ns(tcp_ses, get_net(current->nsproxy->net_ns));1717 1718 tcp_ses->conn_id = atomic_inc_return(&tcpSesNextId);1719 tcp_ses->noblockcnt = ctx->rootfs;1720 tcp_ses->noblocksnd = ctx->noblocksnd || ctx->rootfs;1721 tcp_ses->noautotune = ctx->noautotune;1722 tcp_ses->tcp_nodelay = ctx->sockopt_tcp_nodelay;1723 tcp_ses->rdma = ctx->rdma;1724 tcp_ses->in_flight = 0;1725 tcp_ses->max_in_flight = 0;1726 tcp_ses->credits = 1;1727 if (primary_server) {1728 spin_lock(&cifs_tcp_ses_lock);1729 ++primary_server->srv_count;1730 spin_unlock(&cifs_tcp_ses_lock);1731 tcp_ses->primary_server = primary_server;1732 }1733 init_waitqueue_head(&tcp_ses->response_q);1734 init_waitqueue_head(&tcp_ses->request_q);1735 INIT_LIST_HEAD(&tcp_ses->pending_mid_q);1736 mutex_init(&tcp_ses->_srv_mutex);1737 memcpy(tcp_ses->workstation_RFC1001_name,1738 ctx->source_rfc1001_name, RFC1001_NAME_LEN_WITH_NULL);1739 memcpy(tcp_ses->server_RFC1001_name,1740 ctx->target_rfc1001_name, RFC1001_NAME_LEN_WITH_NULL);1741 tcp_ses->session_estab = false;1742 tcp_ses->sequence_number = 0;1743 tcp_ses->channel_sequence_num = 0; /* only tracked for primary channel */1744 tcp_ses->reconnect_instance = 1;1745 tcp_ses->lstrp = jiffies;1746 tcp_ses->compression.requested = ctx->compress;1747 spin_lock_init(&tcp_ses->req_lock);1748 spin_lock_init(&tcp_ses->srv_lock);1749 spin_lock_init(&tcp_ses->mid_lock);1750 INIT_LIST_HEAD(&tcp_ses->tcp_ses_list);1751 INIT_LIST_HEAD(&tcp_ses->smb_ses_list);1752 INIT_DELAYED_WORK(&tcp_ses->echo, cifs_echo_request);1753 INIT_DELAYED_WORK(&tcp_ses->reconnect, smb2_reconnect_server);1754 mutex_init(&tcp_ses->reconnect_mutex);1755#ifdef CONFIG_CIFS_DFS_UPCALL1756 mutex_init(&tcp_ses->refpath_lock);1757#endif1758 memcpy(&tcp_ses->srcaddr, &ctx->srcaddr,1759 sizeof(tcp_ses->srcaddr));1760 memcpy(&tcp_ses->dstaddr, &ctx->dstaddr,1761 sizeof(tcp_ses->dstaddr));1762 if (ctx->use_client_guid)1763 memcpy(tcp_ses->client_guid, ctx->client_guid,1764 SMB2_CLIENT_GUID_SIZE);1765 else1766 generate_random_uuid(tcp_ses->client_guid);1767 /*1768 * at this point we are the only ones with the pointer1769 * to the struct since the kernel thread not created yet1770 * no need to spinlock this init of tcpStatus or srv_count1771 */1772 tcp_ses->tcpStatus = CifsNew;1773 ++tcp_ses->srv_count;1774 1775 if (ctx->echo_interval >= SMB_ECHO_INTERVAL_MIN &&1776 ctx->echo_interval <= SMB_ECHO_INTERVAL_MAX)1777 tcp_ses->echo_interval = ctx->echo_interval * HZ;1778 else1779 tcp_ses->echo_interval = SMB_ECHO_INTERVAL_DEFAULT * HZ;1780 if (tcp_ses->rdma) {1781#ifndef CONFIG_CIFS_SMB_DIRECT1782 cifs_dbg(VFS, "CONFIG_CIFS_SMB_DIRECT is not enabled\n");1783 rc = -ENOENT;1784 goto out_err_crypto_release;1785#endif1786 tcp_ses->smbd_conn = smbd_get_connection(1787 tcp_ses, (struct sockaddr *)&ctx->dstaddr);1788 if (tcp_ses->smbd_conn) {1789 cifs_dbg(VFS, "RDMA transport established\n");1790 rc = 0;1791 goto smbd_connected;1792 } else {1793 rc = -ENOENT;1794 goto out_err_crypto_release;1795 }1796 }1797 rc = ip_connect(tcp_ses);1798 if (rc < 0) {1799 cifs_dbg(VFS, "Error connecting to socket. Aborting operation.\n");1800 goto out_err_crypto_release;1801 }1802smbd_connected:1803 /*1804 * since we're in a cifs function already, we know that1805 * this will succeed. No need for try_module_get().1806 */1807 __module_get(THIS_MODULE);1808 tcp_ses->tsk = kthread_run(cifs_demultiplex_thread,1809 tcp_ses, "cifsd");1810 if (IS_ERR(tcp_ses->tsk)) {1811 rc = PTR_ERR(tcp_ses->tsk);1812 cifs_dbg(VFS, "error %d create cifsd thread\n", rc);1813 module_put(THIS_MODULE);1814 goto out_err_crypto_release;1815 }1816 tcp_ses->min_offload = ctx->min_offload;1817 tcp_ses->retrans = ctx->retrans;1818 /*1819 * at this point we are the only ones with the pointer1820 * to the struct since the kernel thread not created yet1821 * no need to spinlock this update of tcpStatus1822 */1823 spin_lock(&tcp_ses->srv_lock);1824 tcp_ses->tcpStatus = CifsNeedNegotiate;1825 spin_unlock(&tcp_ses->srv_lock);1826 1827 if ((ctx->max_credits < 20) || (ctx->max_credits > 60000))1828 tcp_ses->max_credits = SMB2_MAX_CREDITS_AVAILABLE;1829 else1830 tcp_ses->max_credits = ctx->max_credits;1831 1832 tcp_ses->nr_targets = 1;1833 tcp_ses->ignore_signature = ctx->ignore_signature;1834 /* thread spawned, put it on the list */1835 spin_lock(&cifs_tcp_ses_lock);1836 list_add(&tcp_ses->tcp_ses_list, &cifs_tcp_ses_list);1837 spin_unlock(&cifs_tcp_ses_lock);1838 1839 /* queue echo request delayed work */1840 queue_delayed_work(cifsiod_wq, &tcp_ses->echo, tcp_ses->echo_interval);1841 1842 return tcp_ses;1843 1844out_err_crypto_release:1845 cifs_crypto_secmech_release(tcp_ses);1846 1847 put_net(cifs_net_ns(tcp_ses));1848 1849out_err:1850 if (tcp_ses) {1851 if (SERVER_IS_CHAN(tcp_ses))1852 cifs_put_tcp_session(tcp_ses->primary_server, false);1853 kfree(tcp_ses->hostname);1854 kfree(tcp_ses->leaf_fullpath);1855 if (tcp_ses->ssocket)1856 sock_release(tcp_ses->ssocket);1857 kfree(tcp_ses);1858 }1859 return ERR_PTR(rc);1860}1861 1862/* this function must be called with ses_lock and chan_lock held */1863static int match_session(struct cifs_ses *ses,1864 struct smb3_fs_context *ctx,1865 bool match_super)1866{1867 if (ctx->sectype != Unspecified &&1868 ctx->sectype != ses->sectype)1869 return 0;1870 1871 if (!match_super && ctx->dfs_root_ses != ses->dfs_root_ses)1872 return 0;1873 1874 /*1875 * If an existing session is limited to less channels than1876 * requested, it should not be reused1877 */1878 if (ses->chan_max < ctx->max_channels)1879 return 0;1880 1881 switch (ses->sectype) {1882 case Kerberos:1883 if (!uid_eq(ctx->cred_uid, ses->cred_uid))1884 return 0;1885 break;1886 default:1887 /* NULL username means anonymous session */1888 if (ses->user_name == NULL) {1889 if (!ctx->nullauth)1890 return 0;1891 break;1892 }1893 1894 /* anything else takes username/password */1895 if (strncmp(ses->user_name,1896 ctx->username ? ctx->username : "",1897 CIFS_MAX_USERNAME_LEN))1898 return 0;1899 if ((ctx->username && strlen(ctx->username) != 0) &&1900 ses->password != NULL &&1901 strncmp(ses->password,1902 ctx->password ? ctx->password : "",1903 CIFS_MAX_PASSWORD_LEN))1904 return 0;1905 }1906 1907 if (strcmp(ctx->local_nls->charset, ses->local_nls->charset))1908 return 0;1909 1910 return 1;1911}1912 1913/**1914 * cifs_setup_ipc - helper to setup the IPC tcon for the session1915 * @ses: smb session to issue the request on1916 * @ctx: the superblock configuration context to use for building the1917 * new tree connection for the IPC (interprocess communication RPC)1918 *1919 * A new IPC connection is made and stored in the session1920 * tcon_ipc. The IPC tcon has the same lifetime as the session.1921 */1922static int1923cifs_setup_ipc(struct cifs_ses *ses, struct smb3_fs_context *ctx)1924{1925 int rc = 0, xid;1926 struct cifs_tcon *tcon;1927 char unc[SERVER_NAME_LENGTH + sizeof("//x/IPC$")] = {0};1928 bool seal = false;1929 struct TCP_Server_Info *server = ses->server;1930 1931 /*1932 * If the mount request that resulted in the creation of the1933 * session requires encryption, force IPC to be encrypted too.1934 */1935 if (ctx->seal) {1936 if (server->capabilities & SMB2_GLOBAL_CAP_ENCRYPTION)1937 seal = true;1938 else {1939 cifs_server_dbg(VFS,1940 "IPC: server doesn't support encryption\n");1941 return -EOPNOTSUPP;1942 }1943 }1944 1945 /* no need to setup directory caching on IPC share, so pass in false */1946 tcon = tcon_info_alloc(false, netfs_trace_tcon_ref_new_ipc);1947 if (tcon == NULL)1948 return -ENOMEM;1949 1950 spin_lock(&server->srv_lock);1951 scnprintf(unc, sizeof(unc), "\\\\%s\\IPC$", server->hostname);1952 spin_unlock(&server->srv_lock);1953 1954 xid = get_xid();1955 tcon->ses = ses;1956 tcon->ipc = true;1957 tcon->seal = seal;1958 rc = server->ops->tree_connect(xid, ses, unc, tcon, ctx->local_nls);1959 free_xid(xid);1960 1961 if (rc) {1962 cifs_server_dbg(VFS, "failed to connect to IPC (rc=%d)\n", rc);1963 tconInfoFree(tcon, netfs_trace_tcon_ref_free_ipc_fail);1964 goto out;1965 }1966 1967 cifs_dbg(FYI, "IPC tcon rc=%d ipc tid=0x%x\n", rc, tcon->tid);1968 1969 spin_lock(&tcon->tc_lock);1970 tcon->status = TID_GOOD;1971 spin_unlock(&tcon->tc_lock);1972 ses->tcon_ipc = tcon;1973out:1974 return rc;1975}1976 1977static struct cifs_ses *1978cifs_find_smb_ses(struct TCP_Server_Info *server, struct smb3_fs_context *ctx)1979{1980 struct cifs_ses *ses, *ret = NULL;1981 1982 spin_lock(&cifs_tcp_ses_lock);1983 list_for_each_entry(ses, &server->smb_ses_list, smb_ses_list) {1984 spin_lock(&ses->ses_lock);1985 if (ses->ses_status == SES_EXITING) {1986 spin_unlock(&ses->ses_lock);1987 continue;1988 }1989 spin_lock(&ses->chan_lock);1990 if (match_session(ses, ctx, false)) {1991 spin_unlock(&ses->chan_lock);1992 spin_unlock(&ses->ses_lock);1993 ret = ses;1994 break;1995 }1996 spin_unlock(&ses->chan_lock);1997 spin_unlock(&ses->ses_lock);1998 }1999 if (ret)2000 cifs_smb_ses_inc_refcount(ret);2001 spin_unlock(&cifs_tcp_ses_lock);2002 return ret;2003}2004 2005void __cifs_put_smb_ses(struct cifs_ses *ses)2006{2007 struct TCP_Server_Info *server = ses->server;2008 struct cifs_tcon *tcon;2009 unsigned int xid;2010 size_t i;2011 bool do_logoff;2012 int rc;2013 2014 spin_lock(&cifs_tcp_ses_lock);2015 spin_lock(&ses->ses_lock);2016 cifs_dbg(FYI, "%s: id=0x%llx ses_count=%d ses_status=%u ipc=%s\n",2017 __func__, ses->Suid, ses->ses_count, ses->ses_status,2018 ses->tcon_ipc ? ses->tcon_ipc->tree_name : "none");2019 if (ses->ses_status == SES_EXITING || --ses->ses_count > 0) {2020 spin_unlock(&ses->ses_lock);2021 spin_unlock(&cifs_tcp_ses_lock);2022 return;2023 }2024 /* ses_count can never go negative */2025 WARN_ON(ses->ses_count < 0);2026 2027 spin_lock(&ses->chan_lock);2028 cifs_chan_clear_need_reconnect(ses, server);2029 spin_unlock(&ses->chan_lock);2030 2031 do_logoff = ses->ses_status == SES_GOOD && server->ops->logoff;2032 ses->ses_status = SES_EXITING;2033 tcon = ses->tcon_ipc;2034 ses->tcon_ipc = NULL;2035 spin_unlock(&ses->ses_lock);2036 spin_unlock(&cifs_tcp_ses_lock);2037 2038 /*2039 * On session close, the IPC is closed and the server must release all2040 * tcons of the session. No need to send a tree disconnect here.2041 *2042 * Besides, it will make the server to not close durable and resilient2043 * files on session close, as specified in MS-SMB2 3.3.5.6 Receiving an2044 * SMB2 LOGOFF Request.2045 */2046 tconInfoFree(tcon, netfs_trace_tcon_ref_free_ipc);2047 if (do_logoff) {2048 xid = get_xid();2049 rc = server->ops->logoff(xid, ses);2050 cifs_server_dbg(FYI, "%s: Session Logoff: rc=%d\n",2051 __func__, rc);2052 _free_xid(xid);2053 }2054 2055 spin_lock(&cifs_tcp_ses_lock);2056 list_del_init(&ses->smb_ses_list);2057 spin_unlock(&cifs_tcp_ses_lock);2058 2059 /* close any extra channels */2060 for (i = 1; i < ses->chan_count; i++) {2061 if (ses->chans[i].iface) {2062 kref_put(&ses->chans[i].iface->refcount, release_iface);2063 ses->chans[i].iface = NULL;2064 }2065 cifs_put_tcp_session(ses->chans[i].server, 0);2066 ses->chans[i].server = NULL;2067 }2068 2069 /* we now account for primary channel in iface->refcount */2070 if (ses->chans[0].iface) {2071 kref_put(&ses->chans[0].iface->refcount, release_iface);2072 ses->chans[0].server = NULL;2073 }2074 2075 sesInfoFree(ses);2076 cifs_put_tcp_session(server, 0);2077}2078 2079#ifdef CONFIG_KEYS2080 2081/* strlen("cifs:a:") + CIFS_MAX_DOMAINNAME_LEN + 1 */2082#define CIFSCREDS_DESC_SIZE (7 + CIFS_MAX_DOMAINNAME_LEN + 1)2083 2084/* Populate username and pw fields from keyring if possible */2085static int2086cifs_set_cifscreds(struct smb3_fs_context *ctx, struct cifs_ses *ses)2087{2088 int rc = 0;2089 int is_domain = 0;2090 const char *delim, *payload;2091 char *desc;2092 ssize_t len;2093 struct key *key;2094 struct TCP_Server_Info *server = ses->server;2095 struct sockaddr_in *sa;2096 struct sockaddr_in6 *sa6;2097 const struct user_key_payload *upayload;2098 2099 desc = kmalloc(CIFSCREDS_DESC_SIZE, GFP_KERNEL);2100 if (!desc)2101 return -ENOMEM;2102 2103 /* try to find an address key first */2104 switch (server->dstaddr.ss_family) {2105 case AF_INET:2106 sa = (struct sockaddr_in *)&server->dstaddr;2107 sprintf(desc, "cifs:a:%pI4", &sa->sin_addr.s_addr);2108 break;2109 case AF_INET6:2110 sa6 = (struct sockaddr_in6 *)&server->dstaddr;2111 sprintf(desc, "cifs:a:%pI6c", &sa6->sin6_addr.s6_addr);2112 break;2113 default:2114 cifs_dbg(FYI, "Bad ss_family (%hu)\n",2115 server->dstaddr.ss_family);2116 rc = -EINVAL;2117 goto out_err;2118 }2119 2120 cifs_dbg(FYI, "%s: desc=%s\n", __func__, desc);2121 key = request_key(&key_type_logon, desc, "");2122 if (IS_ERR(key)) {2123 if (!ses->domainName) {2124 cifs_dbg(FYI, "domainName is NULL\n");2125 rc = PTR_ERR(key);2126 goto out_err;2127 }2128 2129 /* didn't work, try to find a domain key */2130 sprintf(desc, "cifs:d:%s", ses->domainName);2131 cifs_dbg(FYI, "%s: desc=%s\n", __func__, desc);2132 key = request_key(&key_type_logon, desc, "");2133 if (IS_ERR(key)) {2134 rc = PTR_ERR(key);2135 goto out_err;2136 }2137 is_domain = 1;2138 }2139 2140 down_read(&key->sem);2141 upayload = user_key_payload_locked(key);2142 if (IS_ERR_OR_NULL(upayload)) {2143 rc = upayload ? PTR_ERR(upayload) : -EINVAL;2144 goto out_key_put;2145 }2146 2147 /* find first : in payload */2148 payload = upayload->data;2149 delim = strnchr(payload, upayload->datalen, ':');2150 cifs_dbg(FYI, "payload=%s\n", payload);2151 if (!delim) {2152 cifs_dbg(FYI, "Unable to find ':' in payload (datalen=%d)\n",2153 upayload->datalen);2154 rc = -EINVAL;2155 goto out_key_put;2156 }2157 2158 len = delim - payload;2159 if (len > CIFS_MAX_USERNAME_LEN || len <= 0) {2160 cifs_dbg(FYI, "Bad value from username search (len=%zd)\n",2161 len);2162 rc = -EINVAL;2163 goto out_key_put;2164 }2165 2166 ctx->username = kstrndup(payload, len, GFP_KERNEL);2167 if (!ctx->username) {2168 cifs_dbg(FYI, "Unable to allocate %zd bytes for username\n",2169 len);2170 rc = -ENOMEM;2171 goto out_key_put;2172 }2173 cifs_dbg(FYI, "%s: username=%s\n", __func__, ctx->username);2174 2175 len = key->datalen - (len + 1);2176 if (len > CIFS_MAX_PASSWORD_LEN || len <= 0) {2177 cifs_dbg(FYI, "Bad len for password search (len=%zd)\n", len);2178 rc = -EINVAL;2179 kfree(ctx->username);2180 ctx->username = NULL;2181 goto out_key_put;2182 }2183 2184 ++delim;2185 /* BB consider adding support for password2 (Key Rotation) for multiuser in future */2186 ctx->password = kstrndup(delim, len, GFP_KERNEL);2187 if (!ctx->password) {2188 cifs_dbg(FYI, "Unable to allocate %zd bytes for password\n",2189 len);2190 rc = -ENOMEM;2191 kfree(ctx->username);2192 ctx->username = NULL;2193 goto out_key_put;2194 }2195 2196 /*2197 * If we have a domain key then we must set the domainName in the2198 * for the request.2199 */2200 if (is_domain && ses->domainName) {2201 ctx->domainname = kstrdup(ses->domainName, GFP_KERNEL);2202 if (!ctx->domainname) {2203 cifs_dbg(FYI, "Unable to allocate %zd bytes for domain\n",2204 len);2205 rc = -ENOMEM;2206 kfree(ctx->username);2207 ctx->username = NULL;2208 kfree_sensitive(ctx->password);2209 /* no need to free ctx->password2 since not allocated in this path */2210 ctx->password = NULL;2211 goto out_key_put;2212 }2213 }2214 2215 strscpy(ctx->workstation_name, ses->workstation_name, sizeof(ctx->workstation_name));2216 2217out_key_put:2218 up_read(&key->sem);2219 key_put(key);2220out_err:2221 kfree(desc);2222 cifs_dbg(FYI, "%s: returning %d\n", __func__, rc);2223 return rc;2224}2225#else /* ! CONFIG_KEYS */2226static inline int2227cifs_set_cifscreds(struct smb3_fs_context *ctx __attribute__((unused)),2228 struct cifs_ses *ses __attribute__((unused)))2229{2230 return -ENOSYS;2231}2232#endif /* CONFIG_KEYS */2233 2234/**2235 * cifs_get_smb_ses - get a session matching @ctx data from @server2236 * @server: server to setup the session to2237 * @ctx: superblock configuration context to use to setup the session2238 *2239 * This function assumes it is being called from cifs_mount() where we2240 * already got a server reference (server refcount +1). See2241 * cifs_get_tcon() for refcount explanations.2242 */2243struct cifs_ses *2244cifs_get_smb_ses(struct TCP_Server_Info *server, struct smb3_fs_context *ctx)2245{2246 int rc = 0;2247 unsigned int xid;2248 struct cifs_ses *ses;2249 struct sockaddr_in *addr = (struct sockaddr_in *)&server->dstaddr;2250 struct sockaddr_in6 *addr6 = (struct sockaddr_in6 *)&server->dstaddr;2251 2252 xid = get_xid();2253 2254 ses = cifs_find_smb_ses(server, ctx);2255 if (ses) {2256 cifs_dbg(FYI, "Existing smb sess found (status=%d)\n",2257 ses->ses_status);2258 2259 spin_lock(&ses->chan_lock);2260 if (cifs_chan_needs_reconnect(ses, server)) {2261 spin_unlock(&ses->chan_lock);2262 cifs_dbg(FYI, "Session needs reconnect\n");2263 2264 mutex_lock(&ses->session_mutex);2265 rc = cifs_negotiate_protocol(xid, ses, server);2266 if (rc) {2267 mutex_unlock(&ses->session_mutex);2268 /* problem -- put our ses reference */2269 cifs_put_smb_ses(ses);2270 free_xid(xid);2271 return ERR_PTR(rc);2272 }2273 2274 rc = cifs_setup_session(xid, ses, server,2275 ctx->local_nls);2276 if (rc) {2277 mutex_unlock(&ses->session_mutex);2278 /* problem -- put our reference */2279 cifs_put_smb_ses(ses);2280 free_xid(xid);2281 return ERR_PTR(rc);2282 }2283 mutex_unlock(&ses->session_mutex);2284 2285 spin_lock(&ses->chan_lock);2286 }2287 spin_unlock(&ses->chan_lock);2288 2289 /* existing SMB ses has a server reference already */2290 cifs_put_tcp_session(server, 0);2291 free_xid(xid);2292 return ses;2293 }2294 2295 rc = -ENOMEM;2296 2297 cifs_dbg(FYI, "Existing smb sess not found\n");2298 ses = sesInfoAlloc();2299 if (ses == NULL)2300 goto get_ses_fail;2301 2302 /* new SMB session uses our server ref */2303 ses->server = server;2304 if (server->dstaddr.ss_family == AF_INET6)2305 sprintf(ses->ip_addr, "%pI6", &addr6->sin6_addr);2306 else2307 sprintf(ses->ip_addr, "%pI4", &addr->sin_addr);2308 2309 if (ctx->username) {2310 ses->user_name = kstrdup(ctx->username, GFP_KERNEL);2311 if (!ses->user_name)2312 goto get_ses_fail;2313 }2314 2315 /* ctx->password freed at unmount */2316 if (ctx->password) {2317 ses->password = kstrdup(ctx->password, GFP_KERNEL);2318 if (!ses->password)2319 goto get_ses_fail;2320 }2321 /* ctx->password freed at unmount */2322 if (ctx->password2) {2323 ses->password2 = kstrdup(ctx->password2, GFP_KERNEL);2324 if (!ses->password2)2325 goto get_ses_fail;2326 }2327 if (ctx->domainname) {2328 ses->domainName = kstrdup(ctx->domainname, GFP_KERNEL);2329 if (!ses->domainName)2330 goto get_ses_fail;2331 }2332 2333 strscpy(ses->workstation_name, ctx->workstation_name, sizeof(ses->workstation_name));2334 2335 if (ctx->domainauto)2336 ses->domainAuto = ctx->domainauto;2337 ses->cred_uid = ctx->cred_uid;2338 ses->linux_uid = ctx->linux_uid;2339 2340 ses->sectype = ctx->sectype;2341 ses->sign = ctx->sign;2342 ses->local_nls = load_nls(ctx->local_nls->charset);2343 2344 /* add server as first channel */2345 spin_lock(&ses->chan_lock);2346 ses->chans[0].server = server;2347 ses->chan_count = 1;2348 ses->chan_max = ctx->multichannel ? ctx->max_channels:1;2349 ses->chans_need_reconnect = 1;2350 spin_unlock(&ses->chan_lock);2351 2352 mutex_lock(&ses->session_mutex);2353 rc = cifs_negotiate_protocol(xid, ses, server);2354 if (!rc)2355 rc = cifs_setup_session(xid, ses, server, ctx->local_nls);2356 mutex_unlock(&ses->session_mutex);2357 2358 /* each channel uses a different signing key */2359 spin_lock(&ses->chan_lock);2360 memcpy(ses->chans[0].signkey, ses->smb3signingkey,2361 sizeof(ses->smb3signingkey));2362 spin_unlock(&ses->chan_lock);2363 2364 if (rc)2365 goto get_ses_fail;2366 2367 /*2368 * success, put it on the list and add it as first channel2369 * note: the session becomes active soon after this. So you'll2370 * need to lock before changing something in the session.2371 */2372 spin_lock(&cifs_tcp_ses_lock);2373 ses->dfs_root_ses = ctx->dfs_root_ses;2374 list_add(&ses->smb_ses_list, &server->smb_ses_list);2375 spin_unlock(&cifs_tcp_ses_lock);2376 2377 cifs_setup_ipc(ses, ctx);2378 2379 free_xid(xid);2380 2381 return ses;2382 2383get_ses_fail:2384 sesInfoFree(ses);2385 free_xid(xid);2386 return ERR_PTR(rc);2387}2388 2389/* this function must be called with tc_lock held */2390static int match_tcon(struct cifs_tcon *tcon, struct smb3_fs_context *ctx)2391{2392 struct TCP_Server_Info *server = tcon->ses->server;2393 2394 if (tcon->status == TID_EXITING)2395 return 0;2396 2397 if (tcon->origin_fullpath) {2398 if (!ctx->source ||2399 !dfs_src_pathname_equal(ctx->source,2400 tcon->origin_fullpath))2401 return 0;2402 } else if (!server->leaf_fullpath &&2403 strncmp(tcon->tree_name, ctx->UNC, MAX_TREE_SIZE)) {2404 return 0;2405 }2406 if (tcon->seal != ctx->seal)2407 return 0;2408 if (tcon->snapshot_time != ctx->snapshot_time)2409 return 0;2410 if (tcon->handle_timeout != ctx->handle_timeout)2411 return 0;2412 if (tcon->no_lease != ctx->no_lease)2413 return 0;2414 if (tcon->nodelete != ctx->nodelete)2415 return 0;2416 return 1;2417}2418 2419static struct cifs_tcon *2420cifs_find_tcon(struct cifs_ses *ses, struct smb3_fs_context *ctx)2421{2422 struct cifs_tcon *tcon;2423 2424 spin_lock(&cifs_tcp_ses_lock);2425 list_for_each_entry(tcon, &ses->tcon_list, tcon_list) {2426 spin_lock(&tcon->tc_lock);2427 if (!match_tcon(tcon, ctx)) {2428 spin_unlock(&tcon->tc_lock);2429 continue;2430 }2431 ++tcon->tc_count;2432 trace_smb3_tcon_ref(tcon->debug_id, tcon->tc_count,2433 netfs_trace_tcon_ref_get_find);2434 spin_unlock(&tcon->tc_lock);2435 spin_unlock(&cifs_tcp_ses_lock);2436 return tcon;2437 }2438 spin_unlock(&cifs_tcp_ses_lock);2439 return NULL;2440}2441 2442void2443cifs_put_tcon(struct cifs_tcon *tcon, enum smb3_tcon_ref_trace trace)2444{2445 unsigned int xid;2446 struct cifs_ses *ses;2447 LIST_HEAD(ses_list);2448 2449 /*2450 * IPC tcon share the lifetime of their session and are2451 * destroyed in the session put function2452 */2453 if (tcon == NULL || tcon->ipc)2454 return;2455 2456 ses = tcon->ses;2457 cifs_dbg(FYI, "%s: tc_count=%d\n", __func__, tcon->tc_count);2458 spin_lock(&cifs_tcp_ses_lock);2459 spin_lock(&tcon->tc_lock);2460 trace_smb3_tcon_ref(tcon->debug_id, tcon->tc_count - 1, trace);2461 if (--tcon->tc_count > 0) {2462 spin_unlock(&tcon->tc_lock);2463 spin_unlock(&cifs_tcp_ses_lock);2464 return;2465 }2466 2467 /* tc_count can never go negative */2468 WARN_ON(tcon->tc_count < 0);2469 2470 list_del_init(&tcon->tcon_list);2471 tcon->status = TID_EXITING;2472#ifdef CONFIG_CIFS_DFS_UPCALL2473 list_replace_init(&tcon->dfs_ses_list, &ses_list);2474#endif2475 spin_unlock(&tcon->tc_lock);2476 spin_unlock(&cifs_tcp_ses_lock);2477 2478 /* cancel polling of interfaces */2479 cancel_delayed_work_sync(&tcon->query_interfaces);2480#ifdef CONFIG_CIFS_DFS_UPCALL2481 cancel_delayed_work_sync(&tcon->dfs_cache_work);2482#endif2483 2484 if (tcon->use_witness) {2485 int rc;2486 2487 rc = cifs_swn_unregister(tcon);2488 if (rc < 0) {2489 cifs_dbg(VFS, "%s: Failed to unregister for witness notifications: %d\n",2490 __func__, rc);2491 }2492 }2493 2494 xid = get_xid();2495 if (ses->server->ops->tree_disconnect)2496 ses->server->ops->tree_disconnect(xid, tcon);2497 _free_xid(xid);2498 2499 cifs_fscache_release_super_cookie(tcon);2500 tconInfoFree(tcon, netfs_trace_tcon_ref_free);2501 cifs_put_smb_ses(ses);2502#ifdef CONFIG_CIFS_DFS_UPCALL2503 dfs_put_root_smb_sessions(&ses_list);2504#endif2505}2506 2507/**2508 * cifs_get_tcon - get a tcon matching @ctx data from @ses2509 * @ses: smb session to issue the request on2510 * @ctx: the superblock configuration context to use for building the2511 *2512 * - tcon refcount is the number of mount points using the tcon.2513 * - ses refcount is the number of tcon using the session.2514 *2515 * 1. This function assumes it is being called from cifs_mount() where2516 * we already got a session reference (ses refcount +1).2517 *2518 * 2. Since we're in the context of adding a mount point, the end2519 * result should be either:2520 *2521 * a) a new tcon already allocated with refcount=1 (1 mount point) and2522 * its session refcount incremented (1 new tcon). This +1 was2523 * already done in (1).2524 *2525 * b) an existing tcon with refcount+1 (add a mount point to it) and2526 * identical ses refcount (no new tcon). Because of (1) we need to2527 * decrement the ses refcount.2528 */2529static struct cifs_tcon *2530cifs_get_tcon(struct cifs_ses *ses, struct smb3_fs_context *ctx)2531{2532 struct cifs_tcon *tcon;2533 bool nohandlecache;2534 int rc, xid;2535 2536 tcon = cifs_find_tcon(ses, ctx);2537 if (tcon) {2538 /*2539 * tcon has refcount already incremented but we need to2540 * decrement extra ses reference gotten by caller (case b)2541 */2542 cifs_dbg(FYI, "Found match on UNC path\n");2543 cifs_put_smb_ses(ses);2544 return tcon;2545 }2546 2547 if (!ses->server->ops->tree_connect) {2548 rc = -ENOSYS;2549 goto out_fail;2550 }2551 2552 if (ses->server->dialect >= SMB20_PROT_ID &&2553 (ses->server->capabilities & SMB2_GLOBAL_CAP_DIRECTORY_LEASING))2554 nohandlecache = ctx->nohandlecache;2555 else2556 nohandlecache = true;2557 tcon = tcon_info_alloc(!nohandlecache, netfs_trace_tcon_ref_new);2558 if (tcon == NULL) {2559 rc = -ENOMEM;2560 goto out_fail;2561 }2562 tcon->nohandlecache = nohandlecache;2563 2564 if (ctx->snapshot_time) {2565 if (ses->server->vals->protocol_id == 0) {2566 cifs_dbg(VFS,2567 "Use SMB2 or later for snapshot mount option\n");2568 rc = -EOPNOTSUPP;2569 goto out_fail;2570 } else2571 tcon->snapshot_time = ctx->snapshot_time;2572 }2573 2574 if (ctx->handle_timeout) {2575 if (ses->server->vals->protocol_id == 0) {2576 cifs_dbg(VFS,2577 "Use SMB2.1 or later for handle timeout option\n");2578 rc = -EOPNOTSUPP;2579 goto out_fail;2580 } else2581 tcon->handle_timeout = ctx->handle_timeout;2582 }2583 2584 tcon->ses = ses;2585 if (ctx->password) {2586 tcon->password = kstrdup(ctx->password, GFP_KERNEL);2587 if (!tcon->password) {2588 rc = -ENOMEM;2589 goto out_fail;2590 }2591 }2592 2593 if (ctx->seal) {2594 if (ses->server->vals->protocol_id == 0) {2595 cifs_dbg(VFS,2596 "SMB3 or later required for encryption\n");2597 rc = -EOPNOTSUPP;2598 goto out_fail;2599 } else if (tcon->ses->server->capabilities &2600 SMB2_GLOBAL_CAP_ENCRYPTION)2601 tcon->seal = true;2602 else {2603 cifs_dbg(VFS, "Encryption is not supported on share\n");2604 rc = -EOPNOTSUPP;2605 goto out_fail;2606 }2607 }2608 2609 if (ctx->linux_ext) {2610 if (ses->server->posix_ext_supported) {2611 tcon->posix_extensions = true;2612 pr_warn_once("SMB3.11 POSIX Extensions are experimental\n");2613 } else if ((ses->server->vals->protocol_id == SMB311_PROT_ID) ||2614 (strcmp(ses->server->vals->version_string,2615 SMB3ANY_VERSION_STRING) == 0) ||2616 (strcmp(ses->server->vals->version_string,2617 SMBDEFAULT_VERSION_STRING) == 0)) {2618 cifs_dbg(VFS, "Server does not support mounting with posix SMB3.11 extensions\n");2619 rc = -EOPNOTSUPP;2620 goto out_fail;2621 } else if (ses->server->vals->protocol_id == SMB10_PROT_ID)2622 if (cap_unix(ses))2623 cifs_dbg(FYI, "Unix Extensions requested on SMB1 mount\n");2624 else {2625 cifs_dbg(VFS, "SMB1 Unix Extensions not supported by server\n");2626 rc = -EOPNOTSUPP;2627 goto out_fail;2628 } else {2629 cifs_dbg(VFS,2630 "Check vers= mount option. SMB3.11 disabled but required for POSIX extensions\n");2631 rc = -EOPNOTSUPP;2632 goto out_fail;2633 }2634 }2635 2636 xid = get_xid();2637 rc = ses->server->ops->tree_connect(xid, ses, ctx->UNC, tcon,2638 ctx->local_nls);2639 free_xid(xid);2640 cifs_dbg(FYI, "Tcon rc = %d\n", rc);2641 if (rc)2642 goto out_fail;2643 2644 tcon->use_persistent = false;2645 /* check if SMB2 or later, CIFS does not support persistent handles */2646 if (ctx->persistent) {2647 if (ses->server->vals->protocol_id == 0) {2648 cifs_dbg(VFS,2649 "SMB3 or later required for persistent handles\n");2650 rc = -EOPNOTSUPP;2651 goto out_fail;2652 } else if (ses->server->capabilities &2653 SMB2_GLOBAL_CAP_PERSISTENT_HANDLES)2654 tcon->use_persistent = true;2655 else /* persistent handles requested but not supported */ {2656 cifs_dbg(VFS,2657 "Persistent handles not supported on share\n");2658 rc = -EOPNOTSUPP;2659 goto out_fail;2660 }2661 } else if ((tcon->capabilities & SMB2_SHARE_CAP_CONTINUOUS_AVAILABILITY)2662 && (ses->server->capabilities & SMB2_GLOBAL_CAP_PERSISTENT_HANDLES)2663 && (ctx->nopersistent == false)) {2664 cifs_dbg(FYI, "enabling persistent handles\n");2665 tcon->use_persistent = true;2666 } else if (ctx->resilient) {2667 if (ses->server->vals->protocol_id == 0) {2668 cifs_dbg(VFS,2669 "SMB2.1 or later required for resilient handles\n");2670 rc = -EOPNOTSUPP;2671 goto out_fail;2672 }2673 tcon->use_resilient = true;2674 }2675 2676 tcon->use_witness = false;2677 if (IS_ENABLED(CONFIG_CIFS_SWN_UPCALL) && ctx->witness) {2678 if (ses->server->vals->protocol_id >= SMB30_PROT_ID) {2679 if (tcon->capabilities & SMB2_SHARE_CAP_CLUSTER) {2680 /*2681 * Set witness in use flag in first place2682 * to retry registration in the echo task2683 */2684 tcon->use_witness = true;2685 /* And try to register immediately */2686 rc = cifs_swn_register(tcon);2687 if (rc < 0) {2688 cifs_dbg(VFS, "Failed to register for witness notifications: %d\n", rc);2689 goto out_fail;2690 }2691 } else {2692 /* TODO: try to extend for non-cluster uses (eg multichannel) */2693 cifs_dbg(VFS, "witness requested on mount but no CLUSTER capability on share\n");2694 rc = -EOPNOTSUPP;2695 goto out_fail;2696 }2697 } else {2698 cifs_dbg(VFS, "SMB3 or later required for witness option\n");2699 rc = -EOPNOTSUPP;2700 goto out_fail;2701 }2702 }2703 2704 /* If the user really knows what they are doing they can override */2705 if (tcon->share_flags & SMB2_SHAREFLAG_NO_CACHING) {2706 if (ctx->cache_ro)2707 cifs_dbg(VFS, "cache=ro requested on mount but NO_CACHING flag set on share\n");2708 else if (ctx->cache_rw)2709 cifs_dbg(VFS, "cache=singleclient requested on mount but NO_CACHING flag set on share\n");2710 }2711 2712 if (ctx->no_lease) {2713 if (ses->server->vals->protocol_id == 0) {2714 cifs_dbg(VFS,2715 "SMB2 or later required for nolease option\n");2716 rc = -EOPNOTSUPP;2717 goto out_fail;2718 } else2719 tcon->no_lease = ctx->no_lease;2720 }2721 2722 /*2723 * We can have only one retry value for a connection to a share so for2724 * resources mounted more than once to the same server share the last2725 * value passed in for the retry flag is used.2726 */2727 tcon->retry = ctx->retry;2728 tcon->nocase = ctx->nocase;2729 tcon->broken_sparse_sup = ctx->no_sparse;2730 tcon->max_cached_dirs = ctx->max_cached_dirs;2731 tcon->nodelete = ctx->nodelete;2732 tcon->local_lease = ctx->local_lease;2733 INIT_LIST_HEAD(&tcon->pending_opens);2734 tcon->status = TID_GOOD;2735 2736 INIT_DELAYED_WORK(&tcon->query_interfaces,2737 smb2_query_server_interfaces);2738 if (ses->server->dialect >= SMB30_PROT_ID &&2739 (ses->server->capabilities & SMB2_GLOBAL_CAP_MULTI_CHANNEL)) {2740 /* schedule query interfaces poll */2741 queue_delayed_work(cifsiod_wq, &tcon->query_interfaces,2742 (SMB_INTERFACE_POLL_INTERVAL * HZ));2743 }2744#ifdef CONFIG_CIFS_DFS_UPCALL2745 INIT_DELAYED_WORK(&tcon->dfs_cache_work, dfs_cache_refresh);2746#endif2747 spin_lock(&cifs_tcp_ses_lock);2748 list_add(&tcon->tcon_list, &ses->tcon_list);2749 spin_unlock(&cifs_tcp_ses_lock);2750 2751 return tcon;2752 2753out_fail:2754 tconInfoFree(tcon, netfs_trace_tcon_ref_free_fail);2755 return ERR_PTR(rc);2756}2757 2758void2759cifs_put_tlink(struct tcon_link *tlink)2760{2761 if (!tlink || IS_ERR(tlink))2762 return;2763 2764 if (!atomic_dec_and_test(&tlink->tl_count) ||2765 test_bit(TCON_LINK_IN_TREE, &tlink->tl_flags)) {2766 tlink->tl_time = jiffies;2767 return;2768 }2769 2770 if (!IS_ERR(tlink_tcon(tlink)))2771 cifs_put_tcon(tlink_tcon(tlink), netfs_trace_tcon_ref_put_tlink);2772 kfree(tlink);2773}2774 2775static int2776compare_mount_options(struct super_block *sb, struct cifs_mnt_data *mnt_data)2777{2778 struct cifs_sb_info *old = CIFS_SB(sb);2779 struct cifs_sb_info *new = mnt_data->cifs_sb;2780 unsigned int oldflags = old->mnt_cifs_flags & CIFS_MOUNT_MASK;2781 unsigned int newflags = new->mnt_cifs_flags & CIFS_MOUNT_MASK;2782 2783 if ((sb->s_flags & CIFS_MS_MASK) != (mnt_data->flags & CIFS_MS_MASK))2784 return 0;2785 2786 if (old->mnt_cifs_serverino_autodisabled)2787 newflags &= ~CIFS_MOUNT_SERVER_INUM;2788 2789 if (oldflags != newflags)2790 return 0;2791 2792 /*2793 * We want to share sb only if we don't specify an r/wsize or2794 * specified r/wsize is greater than or equal to existing one.2795 */2796 if (new->ctx->wsize && new->ctx->wsize < old->ctx->wsize)2797 return 0;2798 2799 if (new->ctx->rsize && new->ctx->rsize < old->ctx->rsize)2800 return 0;2801 2802 if (!uid_eq(old->ctx->linux_uid, new->ctx->linux_uid) ||2803 !gid_eq(old->ctx->linux_gid, new->ctx->linux_gid))2804 return 0;2805 2806 if (old->ctx->file_mode != new->ctx->file_mode ||2807 old->ctx->dir_mode != new->ctx->dir_mode)2808 return 0;2809 2810 if (strcmp(old->local_nls->charset, new->local_nls->charset))2811 return 0;2812 2813 if (old->ctx->acregmax != new->ctx->acregmax)2814 return 0;2815 if (old->ctx->acdirmax != new->ctx->acdirmax)2816 return 0;2817 if (old->ctx->closetimeo != new->ctx->closetimeo)2818 return 0;2819 if (old->ctx->reparse_type != new->ctx->reparse_type)2820 return 0;2821 2822 return 1;2823}2824 2825static int match_prepath(struct super_block *sb,2826 struct cifs_tcon *tcon,2827 struct cifs_mnt_data *mnt_data)2828{2829 struct smb3_fs_context *ctx = mnt_data->ctx;2830 struct cifs_sb_info *old = CIFS_SB(sb);2831 struct cifs_sb_info *new = mnt_data->cifs_sb;2832 bool old_set = (old->mnt_cifs_flags & CIFS_MOUNT_USE_PREFIX_PATH) &&2833 old->prepath;2834 bool new_set = (new->mnt_cifs_flags & CIFS_MOUNT_USE_PREFIX_PATH) &&2835 new->prepath;2836 2837 if (tcon->origin_fullpath &&2838 dfs_src_pathname_equal(tcon->origin_fullpath, ctx->source))2839 return 1;2840 2841 if (old_set && new_set && !strcmp(new->prepath, old->prepath))2842 return 1;2843 else if (!old_set && !new_set)2844 return 1;2845 2846 return 0;2847}2848 2849int2850cifs_match_super(struct super_block *sb, void *data)2851{2852 struct cifs_mnt_data *mnt_data = data;2853 struct smb3_fs_context *ctx;2854 struct cifs_sb_info *cifs_sb;2855 struct TCP_Server_Info *tcp_srv;2856 struct cifs_ses *ses;2857 struct cifs_tcon *tcon;2858 struct tcon_link *tlink;2859 int rc = 0;2860 2861 spin_lock(&cifs_tcp_ses_lock);2862 cifs_sb = CIFS_SB(sb);2863 2864 /* We do not want to use a superblock that has been shutdown */2865 if (CIFS_MOUNT_SHUTDOWN & cifs_sb->mnt_cifs_flags) {2866 spin_unlock(&cifs_tcp_ses_lock);2867 return 0;2868 }2869 2870 tlink = cifs_get_tlink(cifs_sb_master_tlink(cifs_sb));2871 if (IS_ERR_OR_NULL(tlink)) {2872 pr_warn_once("%s: skip super matching due to bad tlink(%p)\n",2873 __func__, tlink);2874 spin_unlock(&cifs_tcp_ses_lock);2875 return 0;2876 }2877 tcon = tlink_tcon(tlink);2878 ses = tcon->ses;2879 tcp_srv = ses->server;2880 2881 ctx = mnt_data->ctx;2882 2883 spin_lock(&tcp_srv->srv_lock);2884 spin_lock(&ses->ses_lock);2885 spin_lock(&ses->chan_lock);2886 spin_lock(&tcon->tc_lock);2887 if (!match_server(tcp_srv, ctx, true) ||2888 !match_session(ses, ctx, true) ||2889 !match_tcon(tcon, ctx) ||2890 !match_prepath(sb, tcon, mnt_data)) {2891 rc = 0;2892 goto out;2893 }2894 2895 rc = compare_mount_options(sb, mnt_data);2896out:2897 spin_unlock(&tcon->tc_lock);2898 spin_unlock(&ses->chan_lock);2899 spin_unlock(&ses->ses_lock);2900 spin_unlock(&tcp_srv->srv_lock);2901 2902 spin_unlock(&cifs_tcp_ses_lock);2903 cifs_put_tlink(tlink);2904 return rc;2905}2906 2907#ifdef CONFIG_DEBUG_LOCK_ALLOC2908static struct lock_class_key cifs_key[2];2909static struct lock_class_key cifs_slock_key[2];2910 2911static inline void2912cifs_reclassify_socket4(struct socket *sock)2913{2914 struct sock *sk = sock->sk;2915 2916 BUG_ON(!sock_allow_reclassification(sk));2917 sock_lock_init_class_and_name(sk, "slock-AF_INET-CIFS",2918 &cifs_slock_key[0], "sk_lock-AF_INET-CIFS", &cifs_key[0]);2919}2920 2921static inline void2922cifs_reclassify_socket6(struct socket *sock)2923{2924 struct sock *sk = sock->sk;2925 2926 BUG_ON(!sock_allow_reclassification(sk));2927 sock_lock_init_class_and_name(sk, "slock-AF_INET6-CIFS",2928 &cifs_slock_key[1], "sk_lock-AF_INET6-CIFS", &cifs_key[1]);2929}2930#else2931static inline void2932cifs_reclassify_socket4(struct socket *sock)2933{2934}2935 2936static inline void2937cifs_reclassify_socket6(struct socket *sock)2938{2939}2940#endif2941 2942/* See RFC1001 section 14 on representation of Netbios names */2943static void rfc1002mangle(char *target, char *source, unsigned int length)2944{2945 unsigned int i, j;2946 2947 for (i = 0, j = 0; i < (length); i++) {2948 /* mask a nibble at a time and encode */2949 target[j] = 'A' + (0x0F & (source[i] >> 4));2950 target[j+1] = 'A' + (0x0F & source[i]);2951 j += 2;2952 }2953 2954}2955 2956static int2957bind_socket(struct TCP_Server_Info *server)2958{2959 int rc = 0;2960 2961 if (server->srcaddr.ss_family != AF_UNSPEC) {2962 /* Bind to the specified local IP address */2963 struct socket *socket = server->ssocket;2964 2965 rc = kernel_bind(socket,2966 (struct sockaddr *) &server->srcaddr,2967 sizeof(server->srcaddr));2968 if (rc < 0) {2969 struct sockaddr_in *saddr4;2970 struct sockaddr_in6 *saddr6;2971 2972 saddr4 = (struct sockaddr_in *)&server->srcaddr;2973 saddr6 = (struct sockaddr_in6 *)&server->srcaddr;2974 if (saddr6->sin6_family == AF_INET6)2975 cifs_server_dbg(VFS, "Failed to bind to: %pI6c, error: %d\n",2976 &saddr6->sin6_addr, rc);2977 else2978 cifs_server_dbg(VFS, "Failed to bind to: %pI4, error: %d\n",2979 &saddr4->sin_addr.s_addr, rc);2980 }2981 }2982 return rc;2983}2984 2985static int2986ip_rfc1001_connect(struct TCP_Server_Info *server)2987{2988 int rc = 0;2989 /*2990 * some servers require RFC1001 sessinit before sending2991 * negprot - BB check reconnection in case where second2992 * sessinit is sent but no second negprot2993 */2994 struct rfc1002_session_packet req = {};2995 struct smb_hdr *smb_buf = (struct smb_hdr *)&req;2996 unsigned int len;2997 2998 req.trailer.session_req.called_len = sizeof(req.trailer.session_req.called_name);2999 3000 if (server->server_RFC1001_name[0] != 0)3001 rfc1002mangle(req.trailer.session_req.called_name,3002 server->server_RFC1001_name,3003 RFC1001_NAME_LEN_WITH_NULL);3004 else3005 rfc1002mangle(req.trailer.session_req.called_name,3006 DEFAULT_CIFS_CALLED_NAME,3007 RFC1001_NAME_LEN_WITH_NULL);3008 3009 req.trailer.session_req.calling_len = sizeof(req.trailer.session_req.calling_name);3010 3011 /* calling name ends in null (byte 16) from old smb convention */3012 if (server->workstation_RFC1001_name[0] != 0)3013 rfc1002mangle(req.trailer.session_req.calling_name,3014 server->workstation_RFC1001_name,3015 RFC1001_NAME_LEN_WITH_NULL);3016 else3017 rfc1002mangle(req.trailer.session_req.calling_name,3018 "LINUX_CIFS_CLNT",3019 RFC1001_NAME_LEN_WITH_NULL);3020 3021 /*3022 * As per rfc1002, @len must be the number of bytes that follows the3023 * length field of a rfc1002 session request payload.3024 */3025 len = sizeof(req) - offsetof(struct rfc1002_session_packet, trailer.session_req);3026 3027 smb_buf->smb_buf_length = cpu_to_be32((RFC1002_SESSION_REQUEST << 24) | len);3028 rc = smb_send(server, smb_buf, len);3029 /*3030 * RFC1001 layer in at least one server requires very short break before3031 * negprot presumably because not expecting negprot to follow so fast.3032 * This is a simple solution that works without complicating the code3033 * and causes no significant slowing down on mount for everyone else3034 */3035 usleep_range(1000, 2000);3036 3037 return rc;3038}3039 3040static int3041generic_ip_connect(struct TCP_Server_Info *server)3042{3043 struct sockaddr *saddr;3044 struct socket *socket;3045 int slen, sfamily;3046 __be16 sport;3047 int rc = 0;3048 3049 saddr = (struct sockaddr *) &server->dstaddr;3050 3051 if (server->dstaddr.ss_family == AF_INET6) {3052 struct sockaddr_in6 *ipv6 = (struct sockaddr_in6 *)&server->dstaddr;3053 3054 sport = ipv6->sin6_port;3055 slen = sizeof(struct sockaddr_in6);3056 sfamily = AF_INET6;3057 cifs_dbg(FYI, "%s: connecting to [%pI6]:%d\n", __func__, &ipv6->sin6_addr,3058 ntohs(sport));3059 } else {3060 struct sockaddr_in *ipv4 = (struct sockaddr_in *)&server->dstaddr;3061 3062 sport = ipv4->sin_port;3063 slen = sizeof(struct sockaddr_in);3064 sfamily = AF_INET;3065 cifs_dbg(FYI, "%s: connecting to %pI4:%d\n", __func__, &ipv4->sin_addr,3066 ntohs(sport));3067 }3068 3069 if (server->ssocket) {3070 socket = server->ssocket;3071 } else {3072 struct net *net = cifs_net_ns(server);3073 struct sock *sk;3074 3075 rc = __sock_create(net, sfamily, SOCK_STREAM,3076 IPPROTO_TCP, &server->ssocket, 1);3077 if (rc < 0) {3078 cifs_server_dbg(VFS, "Error %d creating socket\n", rc);3079 return rc;3080 }3081 3082 sk = server->ssocket->sk;3083 __netns_tracker_free(net, &sk->ns_tracker, false);3084 sk->sk_net_refcnt = 1;3085 get_net_track(net, &sk->ns_tracker, GFP_KERNEL);3086 sock_inuse_add(net, 1);3087 3088 /* BB other socket options to set KEEPALIVE, NODELAY? */3089 cifs_dbg(FYI, "Socket created\n");3090 socket = server->ssocket;3091 socket->sk->sk_allocation = GFP_NOFS;3092 socket->sk->sk_use_task_frag = false;3093 if (sfamily == AF_INET6)3094 cifs_reclassify_socket6(socket);3095 else3096 cifs_reclassify_socket4(socket);3097 }3098 3099 rc = bind_socket(server);3100 if (rc < 0)3101 return rc;3102 3103 /*3104 * Eventually check for other socket options to change from3105 * the default. sock_setsockopt not used because it expects3106 * user space buffer3107 */3108 socket->sk->sk_rcvtimeo = 7 * HZ;3109 socket->sk->sk_sndtimeo = 5 * HZ;3110 3111 /* make the bufsizes depend on wsize/rsize and max requests */3112 if (server->noautotune) {3113 if (socket->sk->sk_sndbuf < (200 * 1024))3114 socket->sk->sk_sndbuf = 200 * 1024;3115 if (socket->sk->sk_rcvbuf < (140 * 1024))3116 socket->sk->sk_rcvbuf = 140 * 1024;3117 }3118 3119 if (server->tcp_nodelay)3120 tcp_sock_set_nodelay(socket->sk);3121 3122 cifs_dbg(FYI, "sndbuf %d rcvbuf %d rcvtimeo 0x%lx\n",3123 socket->sk->sk_sndbuf,3124 socket->sk->sk_rcvbuf, socket->sk->sk_rcvtimeo);3125 3126 rc = kernel_connect(socket, saddr, slen,3127 server->noblockcnt ? O_NONBLOCK : 0);3128 /*3129 * When mounting SMB root file systems, we do not want to block in3130 * connect. Otherwise bail out and then let cifs_reconnect() perform3131 * reconnect failover - if possible.3132 */3133 if (server->noblockcnt && rc == -EINPROGRESS)3134 rc = 0;3135 if (rc < 0) {3136 cifs_dbg(FYI, "Error %d connecting to server\n", rc);3137 trace_smb3_connect_err(server->hostname, server->conn_id, &server->dstaddr, rc);3138 sock_release(socket);3139 server->ssocket = NULL;3140 return rc;3141 }3142 trace_smb3_connect_done(server->hostname, server->conn_id, &server->dstaddr);3143 if (sport == htons(RFC1001_PORT))3144 rc = ip_rfc1001_connect(server);3145 3146 return rc;3147}3148 3149static int3150ip_connect(struct TCP_Server_Info *server)3151{3152 __be16 *sport;3153 struct sockaddr_in6 *addr6 = (struct sockaddr_in6 *)&server->dstaddr;3154 struct sockaddr_in *addr = (struct sockaddr_in *)&server->dstaddr;3155 3156 if (server->dstaddr.ss_family == AF_INET6)3157 sport = &addr6->sin6_port;3158 else3159 sport = &addr->sin_port;3160 3161 if (*sport == 0) {3162 int rc;3163 3164 /* try with 445 port at first */3165 *sport = htons(CIFS_PORT);3166 3167 rc = generic_ip_connect(server);3168 if (rc >= 0)3169 return rc;3170 3171 /* if it failed, try with 139 port */3172 *sport = htons(RFC1001_PORT);3173 }3174 3175 return generic_ip_connect(server);3176}3177 3178#ifdef CONFIG_CIFS_ALLOW_INSECURE_LEGACY3179void reset_cifs_unix_caps(unsigned int xid, struct cifs_tcon *tcon,3180 struct cifs_sb_info *cifs_sb, struct smb3_fs_context *ctx)3181{3182 /*3183 * If we are reconnecting then should we check to see if3184 * any requested capabilities changed locally e.g. via3185 * remount but we can not do much about it here3186 * if they have (even if we could detect it by the following)3187 * Perhaps we could add a backpointer to array of sb from tcon3188 * or if we change to make all sb to same share the same3189 * sb as NFS - then we only have one backpointer to sb.3190 * What if we wanted to mount the server share twice once with3191 * and once without posixacls or posix paths?3192 */3193 __u64 saved_cap = le64_to_cpu(tcon->fsUnixInfo.Capability);3194 3195 if (ctx && ctx->no_linux_ext) {3196 tcon->fsUnixInfo.Capability = 0;3197 tcon->unix_ext = 0; /* Unix Extensions disabled */3198 cifs_dbg(FYI, "Linux protocol extensions disabled\n");3199 return;3200 } else if (ctx)3201 tcon->unix_ext = 1; /* Unix Extensions supported */3202 3203 if (!tcon->unix_ext) {3204 cifs_dbg(FYI, "Unix extensions disabled so not set on reconnect\n");3205 return;3206 }3207 3208 if (!CIFSSMBQFSUnixInfo(xid, tcon)) {3209 __u64 cap = le64_to_cpu(tcon->fsUnixInfo.Capability);3210 3211 cifs_dbg(FYI, "unix caps which server supports %lld\n", cap);3212 /*3213 * check for reconnect case in which we do not3214 * want to change the mount behavior if we can avoid it3215 */3216 if (ctx == NULL) {3217 /*3218 * turn off POSIX ACL and PATHNAMES if not set3219 * originally at mount time3220 */3221 if ((saved_cap & CIFS_UNIX_POSIX_ACL_CAP) == 0)3222 cap &= ~CIFS_UNIX_POSIX_ACL_CAP;3223 if ((saved_cap & CIFS_UNIX_POSIX_PATHNAMES_CAP) == 0) {3224 if (cap & CIFS_UNIX_POSIX_PATHNAMES_CAP)3225 cifs_dbg(VFS, "POSIXPATH support change\n");3226 cap &= ~CIFS_UNIX_POSIX_PATHNAMES_CAP;3227 } else if ((cap & CIFS_UNIX_POSIX_PATHNAMES_CAP) == 0) {3228 cifs_dbg(VFS, "possible reconnect error\n");3229 cifs_dbg(VFS, "server disabled POSIX path support\n");3230 }3231 }3232 3233 if (cap & CIFS_UNIX_TRANSPORT_ENCRYPTION_MANDATORY_CAP)3234 cifs_dbg(VFS, "per-share encryption not supported yet\n");3235 3236 cap &= CIFS_UNIX_CAP_MASK;3237 if (ctx && ctx->no_psx_acl)3238 cap &= ~CIFS_UNIX_POSIX_ACL_CAP;3239 else if (CIFS_UNIX_POSIX_ACL_CAP & cap) {3240 cifs_dbg(FYI, "negotiated posix acl support\n");3241 if (cifs_sb)3242 cifs_sb->mnt_cifs_flags |=3243 CIFS_MOUNT_POSIXACL;3244 }3245 3246 if (ctx && ctx->posix_paths == 0)3247 cap &= ~CIFS_UNIX_POSIX_PATHNAMES_CAP;3248 else if (cap & CIFS_UNIX_POSIX_PATHNAMES_CAP) {3249 cifs_dbg(FYI, "negotiate posix pathnames\n");3250 if (cifs_sb)3251 cifs_sb->mnt_cifs_flags |=3252 CIFS_MOUNT_POSIX_PATHS;3253 }3254 3255 cifs_dbg(FYI, "Negotiate caps 0x%x\n", (int)cap);3256#ifdef CONFIG_CIFS_DEBUG23257 if (cap & CIFS_UNIX_FCNTL_CAP)3258 cifs_dbg(FYI, "FCNTL cap\n");3259 if (cap & CIFS_UNIX_EXTATTR_CAP)3260 cifs_dbg(FYI, "EXTATTR cap\n");3261 if (cap & CIFS_UNIX_POSIX_PATHNAMES_CAP)3262 cifs_dbg(FYI, "POSIX path cap\n");3263 if (cap & CIFS_UNIX_XATTR_CAP)3264 cifs_dbg(FYI, "XATTR cap\n");3265 if (cap & CIFS_UNIX_POSIX_ACL_CAP)3266 cifs_dbg(FYI, "POSIX ACL cap\n");3267 if (cap & CIFS_UNIX_LARGE_READ_CAP)3268 cifs_dbg(FYI, "very large read cap\n");3269 if (cap & CIFS_UNIX_LARGE_WRITE_CAP)3270 cifs_dbg(FYI, "very large write cap\n");3271 if (cap & CIFS_UNIX_TRANSPORT_ENCRYPTION_CAP)3272 cifs_dbg(FYI, "transport encryption cap\n");3273 if (cap & CIFS_UNIX_TRANSPORT_ENCRYPTION_MANDATORY_CAP)3274 cifs_dbg(FYI, "mandatory transport encryption cap\n");3275#endif /* CIFS_DEBUG2 */3276 if (CIFSSMBSetFSUnixInfo(xid, tcon, cap)) {3277 if (ctx == NULL)3278 cifs_dbg(FYI, "resetting capabilities failed\n");3279 else3280 cifs_dbg(VFS, "Negotiating Unix capabilities with the server failed. Consider mounting with the Unix Extensions disabled if problems are found by specifying the nounix mount option.\n");3281 3282 }3283 }3284}3285#endif /* CONFIG_CIFS_ALLOW_INSECURE_LEGACY */3286 3287int cifs_setup_cifs_sb(struct cifs_sb_info *cifs_sb)3288{3289 struct smb3_fs_context *ctx = cifs_sb->ctx;3290 3291 INIT_DELAYED_WORK(&cifs_sb->prune_tlinks, cifs_prune_tlinks);3292 3293 spin_lock_init(&cifs_sb->tlink_tree_lock);3294 cifs_sb->tlink_tree = RB_ROOT;3295 3296 cifs_dbg(FYI, "file mode: %04ho dir mode: %04ho\n",3297 ctx->file_mode, ctx->dir_mode);3298 3299 /* this is needed for ASCII cp to Unicode converts */3300 if (ctx->iocharset == NULL) {3301 /* load_nls_default cannot return null */3302 cifs_sb->local_nls = load_nls_default();3303 } else {3304 cifs_sb->local_nls = load_nls(ctx->iocharset);3305 if (cifs_sb->local_nls == NULL) {3306 cifs_dbg(VFS, "CIFS mount error: iocharset %s not found\n",3307 ctx->iocharset);3308 return -ELIBACC;3309 }3310 }3311 ctx->local_nls = cifs_sb->local_nls;3312 3313 smb3_update_mnt_flags(cifs_sb);3314 3315 if (ctx->direct_io)3316 cifs_dbg(FYI, "mounting share using direct i/o\n");3317 if (ctx->cache_ro) {3318 cifs_dbg(VFS, "mounting share with read only caching. Ensure that the share will not be modified while in use.\n");3319 cifs_sb->mnt_cifs_flags |= CIFS_MOUNT_RO_CACHE;3320 } else if (ctx->cache_rw) {3321 cifs_dbg(VFS, "mounting share in single client RW caching mode. Ensure that no other systems will be accessing the share.\n");3322 cifs_sb->mnt_cifs_flags |= (CIFS_MOUNT_RO_CACHE |3323 CIFS_MOUNT_RW_CACHE);3324 }3325 3326 if ((ctx->cifs_acl) && (ctx->dynperm))3327 cifs_dbg(VFS, "mount option dynperm ignored if cifsacl mount option supported\n");3328 3329 if (ctx->prepath) {3330 cifs_sb->prepath = kstrdup(ctx->prepath, GFP_KERNEL);3331 if (cifs_sb->prepath == NULL)3332 return -ENOMEM;3333 cifs_sb->mnt_cifs_flags |= CIFS_MOUNT_USE_PREFIX_PATH;3334 }3335 3336 return 0;3337}3338 3339/* Release all succeed connections */3340void cifs_mount_put_conns(struct cifs_mount_ctx *mnt_ctx)3341{3342 int rc = 0;3343 3344 if (mnt_ctx->tcon)3345 cifs_put_tcon(mnt_ctx->tcon, netfs_trace_tcon_ref_put_mnt_ctx);3346 else if (mnt_ctx->ses)3347 cifs_put_smb_ses(mnt_ctx->ses);3348 else if (mnt_ctx->server)3349 cifs_put_tcp_session(mnt_ctx->server, 0);3350 mnt_ctx->ses = NULL;3351 mnt_ctx->tcon = NULL;3352 mnt_ctx->server = NULL;3353 mnt_ctx->cifs_sb->mnt_cifs_flags &= ~CIFS_MOUNT_POSIX_PATHS;3354 free_xid(mnt_ctx->xid);3355}3356 3357int cifs_mount_get_session(struct cifs_mount_ctx *mnt_ctx)3358{3359 struct TCP_Server_Info *server = NULL;3360 struct smb3_fs_context *ctx;3361 struct cifs_ses *ses = NULL;3362 unsigned int xid;3363 int rc = 0;3364 3365 xid = get_xid();3366 3367 if (WARN_ON_ONCE(!mnt_ctx || !mnt_ctx->fs_ctx)) {3368 rc = -EINVAL;3369 goto out;3370 }3371 ctx = mnt_ctx->fs_ctx;3372 3373 /* get a reference to a tcp session */3374 server = cifs_get_tcp_session(ctx, NULL);3375 if (IS_ERR(server)) {3376 rc = PTR_ERR(server);3377 server = NULL;3378 goto out;3379 }3380 3381 /* get a reference to a SMB session */3382 ses = cifs_get_smb_ses(server, ctx);3383 if (IS_ERR(ses)) {3384 rc = PTR_ERR(ses);3385 ses = NULL;3386 goto out;3387 }3388 3389 if ((ctx->persistent == true) && (!(ses->server->capabilities &3390 SMB2_GLOBAL_CAP_PERSISTENT_HANDLES))) {3391 cifs_server_dbg(VFS, "persistent handles not supported by server\n");3392 rc = -EOPNOTSUPP;3393 }3394 3395out:3396 mnt_ctx->xid = xid;3397 mnt_ctx->server = server;3398 mnt_ctx->ses = ses;3399 mnt_ctx->tcon = NULL;3400 3401 return rc;3402}3403 3404int cifs_mount_get_tcon(struct cifs_mount_ctx *mnt_ctx)3405{3406 struct TCP_Server_Info *server;3407 struct cifs_sb_info *cifs_sb;3408 struct smb3_fs_context *ctx;3409 struct cifs_tcon *tcon = NULL;3410 int rc = 0;3411 3412 if (WARN_ON_ONCE(!mnt_ctx || !mnt_ctx->server || !mnt_ctx->ses || !mnt_ctx->fs_ctx ||3413 !mnt_ctx->cifs_sb)) {3414 rc = -EINVAL;3415 goto out;3416 }3417 server = mnt_ctx->server;3418 ctx = mnt_ctx->fs_ctx;3419 cifs_sb = mnt_ctx->cifs_sb;3420 3421 /* search for existing tcon to this server share */3422 tcon = cifs_get_tcon(mnt_ctx->ses, ctx);3423 if (IS_ERR(tcon)) {3424 rc = PTR_ERR(tcon);3425 tcon = NULL;3426 goto out;3427 }3428 3429 /* if new SMB3.11 POSIX extensions are supported do not remap / and \ */3430 if (tcon->posix_extensions)3431 cifs_sb->mnt_cifs_flags |= CIFS_MOUNT_POSIX_PATHS;3432 3433#ifdef CONFIG_CIFS_ALLOW_INSECURE_LEGACY3434 /* tell server which Unix caps we support */3435 if (cap_unix(tcon->ses)) {3436 /*3437 * reset of caps checks mount to see if unix extensions disabled3438 * for just this mount.3439 */3440 reset_cifs_unix_caps(mnt_ctx->xid, tcon, cifs_sb, ctx);3441 spin_lock(&tcon->ses->server->srv_lock);3442 if ((tcon->ses->server->tcpStatus == CifsNeedReconnect) &&3443 (le64_to_cpu(tcon->fsUnixInfo.Capability) &3444 CIFS_UNIX_TRANSPORT_ENCRYPTION_MANDATORY_CAP)) {3445 spin_unlock(&tcon->ses->server->srv_lock);3446 rc = -EACCES;3447 goto out;3448 }3449 spin_unlock(&tcon->ses->server->srv_lock);3450 } else3451#endif /* CONFIG_CIFS_ALLOW_INSECURE_LEGACY */3452 tcon->unix_ext = 0; /* server does not support them */3453 3454 /* do not care if a following call succeed - informational */3455 if (!tcon->pipe && server->ops->qfs_tcon) {3456 server->ops->qfs_tcon(mnt_ctx->xid, tcon, cifs_sb);3457 if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_RO_CACHE) {3458 if (tcon->fsDevInfo.DeviceCharacteristics &3459 cpu_to_le32(FILE_READ_ONLY_DEVICE))3460 cifs_dbg(VFS, "mounted to read only share\n");3461 else if ((cifs_sb->mnt_cifs_flags &3462 CIFS_MOUNT_RW_CACHE) == 0)3463 cifs_dbg(VFS, "read only mount of RW share\n");3464 /* no need to log a RW mount of a typical RW share */3465 }3466 }3467 3468 /*3469 * Clamp the rsize/wsize mount arguments if they are too big for the server3470 * and set the rsize/wsize to the negotiated values if not passed in by3471 * the user on mount3472 */3473 if ((cifs_sb->ctx->wsize == 0) ||3474 (cifs_sb->ctx->wsize > server->ops->negotiate_wsize(tcon, ctx))) {3475 cifs_sb->ctx->wsize =3476 round_down(server->ops->negotiate_wsize(tcon, ctx), PAGE_SIZE);3477 /*3478 * in the very unlikely event that the server sent a max write size under PAGE_SIZE,3479 * (which would get rounded down to 0) then reset wsize to absolute minimum eg 40963480 */3481 if (cifs_sb->ctx->wsize == 0) {3482 cifs_sb->ctx->wsize = PAGE_SIZE;3483 cifs_dbg(VFS, "wsize too small, reset to minimum ie PAGE_SIZE, usually 4096\n");3484 }3485 }3486 if ((cifs_sb->ctx->rsize == 0) ||3487 (cifs_sb->ctx->rsize > server->ops->negotiate_rsize(tcon, ctx)))3488 cifs_sb->ctx->rsize = server->ops->negotiate_rsize(tcon, ctx);3489 3490 /*3491 * The cookie is initialized from volume info returned above.3492 * Inside cifs_fscache_get_super_cookie it checks3493 * that we do not get super cookie twice.3494 */3495 if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_FSCACHE)3496 cifs_fscache_get_super_cookie(tcon);3497 3498out:3499 mnt_ctx->tcon = tcon;3500 return rc;3501}3502 3503static int mount_setup_tlink(struct cifs_sb_info *cifs_sb, struct cifs_ses *ses,3504 struct cifs_tcon *tcon)3505{3506 struct tcon_link *tlink;3507 3508 /* hang the tcon off of the superblock */3509 tlink = kzalloc(sizeof(*tlink), GFP_KERNEL);3510 if (tlink == NULL)3511 return -ENOMEM;3512 3513 tlink->tl_uid = ses->linux_uid;3514 tlink->tl_tcon = tcon;3515 tlink->tl_time = jiffies;3516 set_bit(TCON_LINK_MASTER, &tlink->tl_flags);3517 set_bit(TCON_LINK_IN_TREE, &tlink->tl_flags);3518 3519 cifs_sb->master_tlink = tlink;3520 spin_lock(&cifs_sb->tlink_tree_lock);3521 tlink_rb_insert(&cifs_sb->tlink_tree, tlink);3522 spin_unlock(&cifs_sb->tlink_tree_lock);3523 3524 queue_delayed_work(cifsiod_wq, &cifs_sb->prune_tlinks,3525 TLINK_IDLE_EXPIRE);3526 return 0;3527}3528 3529static int3530cifs_are_all_path_components_accessible(struct TCP_Server_Info *server,3531 unsigned int xid,3532 struct cifs_tcon *tcon,3533 struct cifs_sb_info *cifs_sb,3534 char *full_path,3535 int added_treename)3536{3537 int rc;3538 char *s;3539 char sep, tmp;3540 int skip = added_treename ? 1 : 0;3541 3542 sep = CIFS_DIR_SEP(cifs_sb);3543 s = full_path;3544 3545 rc = server->ops->is_path_accessible(xid, tcon, cifs_sb, "");3546 while (rc == 0) {3547 /* skip separators */3548 while (*s == sep)3549 s++;3550 if (!*s)3551 break;3552 /* next separator */3553 while (*s && *s != sep)3554 s++;3555 /*3556 * if the treename is added, we then have to skip the first3557 * part within the separators3558 */3559 if (skip) {3560 skip = 0;3561 continue;3562 }3563 /*3564 * temporarily null-terminate the path at the end of3565 * the current component3566 */3567 tmp = *s;3568 *s = 0;3569 rc = server->ops->is_path_accessible(xid, tcon, cifs_sb,3570 full_path);3571 *s = tmp;3572 }3573 return rc;3574}3575 3576/*3577 * Check if path is remote (i.e. a DFS share).3578 *3579 * Return -EREMOTE if it is, otherwise 0 or -errno.3580 */3581int cifs_is_path_remote(struct cifs_mount_ctx *mnt_ctx)3582{3583 int rc;3584 struct cifs_sb_info *cifs_sb = mnt_ctx->cifs_sb;3585 struct TCP_Server_Info *server = mnt_ctx->server;3586 unsigned int xid = mnt_ctx->xid;3587 struct cifs_tcon *tcon = mnt_ctx->tcon;3588 struct smb3_fs_context *ctx = mnt_ctx->fs_ctx;3589 char *full_path;3590 3591 if (!server->ops->is_path_accessible)3592 return -EOPNOTSUPP;3593 3594 /*3595 * cifs_build_path_to_root works only when we have a valid tcon3596 */3597 full_path = cifs_build_path_to_root(ctx, cifs_sb, tcon,3598 tcon->Flags & SMB_SHARE_IS_IN_DFS);3599 if (full_path == NULL)3600 return -ENOMEM;3601 3602 cifs_dbg(FYI, "%s: full_path: %s\n", __func__, full_path);3603 3604 rc = server->ops->is_path_accessible(xid, tcon, cifs_sb,3605 full_path);3606 if (rc != 0 && rc != -EREMOTE)3607 goto out;3608 3609 if (rc != -EREMOTE) {3610 rc = cifs_are_all_path_components_accessible(server, xid, tcon,3611 cifs_sb, full_path, tcon->Flags & SMB_SHARE_IS_IN_DFS);3612 if (rc != 0) {3613 cifs_server_dbg(VFS, "cannot query dirs between root and final path, enabling CIFS_MOUNT_USE_PREFIX_PATH\n");3614 cifs_sb->mnt_cifs_flags |= CIFS_MOUNT_USE_PREFIX_PATH;3615 rc = 0;3616 }3617 }3618 3619out:3620 kfree(full_path);3621 return rc;3622}3623 3624#ifdef CONFIG_CIFS_DFS_UPCALL3625int cifs_mount(struct cifs_sb_info *cifs_sb, struct smb3_fs_context *ctx)3626{3627 struct cifs_mount_ctx mnt_ctx = { .cifs_sb = cifs_sb, .fs_ctx = ctx, };3628 int rc;3629 3630 rc = dfs_mount_share(&mnt_ctx);3631 if (rc)3632 goto error;3633 if (!ctx->dfs_conn)3634 goto out;3635 3636 /*3637 * After reconnecting to a different server, unique ids won't match anymore, so we disable3638 * serverino. This prevents dentry revalidation to think the dentry are stale (ESTALE).3639 */3640 cifs_autodisable_serverino(cifs_sb);3641 /*3642 * Force the use of prefix path to support failover on DFS paths that resolve to targets3643 * that have different prefix paths.3644 */3645 cifs_sb->mnt_cifs_flags |= CIFS_MOUNT_USE_PREFIX_PATH;3646 kfree(cifs_sb->prepath);3647 cifs_sb->prepath = ctx->prepath;3648 ctx->prepath = NULL;3649 3650out:3651 cifs_try_adding_channels(mnt_ctx.ses);3652 rc = mount_setup_tlink(cifs_sb, mnt_ctx.ses, mnt_ctx.tcon);3653 if (rc)3654 goto error;3655 3656 free_xid(mnt_ctx.xid);3657 return rc;3658 3659error:3660 cifs_mount_put_conns(&mnt_ctx);3661 return rc;3662}3663#else3664int cifs_mount(struct cifs_sb_info *cifs_sb, struct smb3_fs_context *ctx)3665{3666 int rc = 0;3667 struct cifs_mount_ctx mnt_ctx = { .cifs_sb = cifs_sb, .fs_ctx = ctx, };3668 3669 rc = cifs_mount_get_session(&mnt_ctx);3670 if (rc)3671 goto error;3672 3673 rc = cifs_mount_get_tcon(&mnt_ctx);3674 if (!rc) {3675 /*3676 * Prevent superblock from being created with any missing3677 * connections.3678 */3679 if (WARN_ON(!mnt_ctx.server))3680 rc = -EHOSTDOWN;3681 else if (WARN_ON(!mnt_ctx.ses))3682 rc = -EACCES;3683 else if (WARN_ON(!mnt_ctx.tcon))3684 rc = -ENOENT;3685 }3686 if (rc)3687 goto error;3688 3689 rc = cifs_is_path_remote(&mnt_ctx);3690 if (rc == -EREMOTE)3691 rc = -EOPNOTSUPP;3692 if (rc)3693 goto error;3694 3695 rc = mount_setup_tlink(cifs_sb, mnt_ctx.ses, mnt_ctx.tcon);3696 if (rc)3697 goto error;3698 3699 free_xid(mnt_ctx.xid);3700 return rc;3701 3702error:3703 cifs_mount_put_conns(&mnt_ctx);3704 return rc;3705}3706#endif3707 3708#ifdef CONFIG_CIFS_ALLOW_INSECURE_LEGACY3709/*3710 * Issue a TREE_CONNECT request.3711 */3712int3713CIFSTCon(const unsigned int xid, struct cifs_ses *ses,3714 const char *tree, struct cifs_tcon *tcon,3715 const struct nls_table *nls_codepage)3716{3717 struct smb_hdr *smb_buffer;3718 struct smb_hdr *smb_buffer_response;3719 TCONX_REQ *pSMB;3720 TCONX_RSP *pSMBr;3721 unsigned char *bcc_ptr;3722 int rc = 0;3723 int length;3724 __u16 bytes_left, count;3725 3726 if (ses == NULL)3727 return -EIO;3728 3729 smb_buffer = cifs_buf_get();3730 if (smb_buffer == NULL)3731 return -ENOMEM;3732 3733 smb_buffer_response = smb_buffer;3734 3735 header_assemble(smb_buffer, SMB_COM_TREE_CONNECT_ANDX,3736 NULL /*no tid */, 4 /*wct */);3737 3738 smb_buffer->Mid = get_next_mid(ses->server);3739 smb_buffer->Uid = ses->Suid;3740 pSMB = (TCONX_REQ *) smb_buffer;3741 pSMBr = (TCONX_RSP *) smb_buffer_response;3742 3743 pSMB->AndXCommand = 0xFF;3744 pSMB->Flags = cpu_to_le16(TCON_EXTENDED_SECINFO);3745 bcc_ptr = &pSMB->Password[0];3746 3747 pSMB->PasswordLength = cpu_to_le16(1); /* minimum */3748 *bcc_ptr = 0; /* password is null byte */3749 bcc_ptr++; /* skip password */3750 /* already aligned so no need to do it below */3751 3752 if (ses->server->sign)3753 smb_buffer->Flags2 |= SMBFLG2_SECURITY_SIGNATURE;3754 3755 if (ses->capabilities & CAP_STATUS32)3756 smb_buffer->Flags2 |= SMBFLG2_ERR_STATUS;3757 3758 if (ses->capabilities & CAP_DFS)3759 smb_buffer->Flags2 |= SMBFLG2_DFS;3760 3761 if (ses->capabilities & CAP_UNICODE) {3762 smb_buffer->Flags2 |= SMBFLG2_UNICODE;3763 length =3764 cifs_strtoUTF16((__le16 *) bcc_ptr, tree,3765 6 /* max utf8 char length in bytes */ *3766 (/* server len*/ + 256 /* share len */), nls_codepage);3767 bcc_ptr += 2 * length; /* convert num 16 bit words to bytes */3768 bcc_ptr += 2; /* skip trailing null */3769 } else { /* ASCII */3770 strcpy(bcc_ptr, tree);3771 bcc_ptr += strlen(tree) + 1;3772 }3773 strcpy(bcc_ptr, "?????");3774 bcc_ptr += strlen("?????");3775 bcc_ptr += 1;3776 count = bcc_ptr - &pSMB->Password[0];3777 be32_add_cpu(&pSMB->hdr.smb_buf_length, count);3778 pSMB->ByteCount = cpu_to_le16(count);3779 3780 rc = SendReceive(xid, ses, smb_buffer, smb_buffer_response, &length,3781 0);3782 3783 /* above now done in SendReceive */3784 if (rc == 0) {3785 bool is_unicode;3786 3787 tcon->tid = smb_buffer_response->Tid;3788 bcc_ptr = pByteArea(smb_buffer_response);3789 bytes_left = get_bcc(smb_buffer_response);3790 length = strnlen(bcc_ptr, bytes_left - 2);3791 if (smb_buffer->Flags2 & SMBFLG2_UNICODE)3792 is_unicode = true;3793 else3794 is_unicode = false;3795 3796 3797 /* skip service field (NB: this field is always ASCII) */3798 if (length == 3) {3799 if ((bcc_ptr[0] == 'I') && (bcc_ptr[1] == 'P') &&3800 (bcc_ptr[2] == 'C')) {3801 cifs_dbg(FYI, "IPC connection\n");3802 tcon->ipc = true;3803 tcon->pipe = true;3804 }3805 } else if (length == 2) {3806 if ((bcc_ptr[0] == 'A') && (bcc_ptr[1] == ':')) {3807 /* the most common case */3808 cifs_dbg(FYI, "disk share connection\n");3809 }3810 }3811 bcc_ptr += length + 1;3812 bytes_left -= (length + 1);3813 strscpy(tcon->tree_name, tree, sizeof(tcon->tree_name));3814 3815 /* mostly informational -- no need to fail on error here */3816 kfree(tcon->nativeFileSystem);3817 tcon->nativeFileSystem = cifs_strndup_from_utf16(bcc_ptr,3818 bytes_left, is_unicode,3819 nls_codepage);3820 3821 cifs_dbg(FYI, "nativeFileSystem=%s\n", tcon->nativeFileSystem);3822 3823 if ((smb_buffer_response->WordCount == 3) ||3824 (smb_buffer_response->WordCount == 7))3825 /* field is in same location */3826 tcon->Flags = le16_to_cpu(pSMBr->OptionalSupport);3827 else3828 tcon->Flags = 0;3829 cifs_dbg(FYI, "Tcon flags: 0x%x\n", tcon->Flags);3830 3831 /*3832 * reset_cifs_unix_caps calls QFSInfo which requires3833 * need_reconnect to be false, but we would not need to call3834 * reset_caps if this were not a reconnect case so must check3835 * need_reconnect flag here. The caller will also clear3836 * need_reconnect when tcon was successful but needed to be3837 * cleared earlier in the case of unix extensions reconnect3838 */3839 if (tcon->need_reconnect && tcon->unix_ext) {3840 cifs_dbg(FYI, "resetting caps for %s\n", tcon->tree_name);3841 tcon->need_reconnect = false;3842 reset_cifs_unix_caps(xid, tcon, NULL, NULL);3843 }3844 }3845 cifs_buf_release(smb_buffer);3846 return rc;3847}3848#endif /* CONFIG_CIFS_ALLOW_INSECURE_LEGACY */3849 3850static void delayed_free(struct rcu_head *p)3851{3852 struct cifs_sb_info *cifs_sb = container_of(p, struct cifs_sb_info, rcu);3853 3854 unload_nls(cifs_sb->local_nls);3855 smb3_cleanup_fs_context(cifs_sb->ctx);3856 kfree(cifs_sb);3857}3858 3859void3860cifs_umount(struct cifs_sb_info *cifs_sb)3861{3862 struct rb_root *root = &cifs_sb->tlink_tree;3863 struct rb_node *node;3864 struct tcon_link *tlink;3865 3866 cancel_delayed_work_sync(&cifs_sb->prune_tlinks);3867 3868 spin_lock(&cifs_sb->tlink_tree_lock);3869 while ((node = rb_first(root))) {3870 tlink = rb_entry(node, struct tcon_link, tl_rbnode);3871 cifs_get_tlink(tlink);3872 clear_bit(TCON_LINK_IN_TREE, &tlink->tl_flags);3873 rb_erase(node, root);3874 3875 spin_unlock(&cifs_sb->tlink_tree_lock);3876 cifs_put_tlink(tlink);3877 spin_lock(&cifs_sb->tlink_tree_lock);3878 }3879 spin_unlock(&cifs_sb->tlink_tree_lock);3880 3881 kfree(cifs_sb->prepath);3882 call_rcu(&cifs_sb->rcu, delayed_free);3883}3884 3885int3886cifs_negotiate_protocol(const unsigned int xid, struct cifs_ses *ses,3887 struct TCP_Server_Info *server)3888{3889 int rc = 0;3890 3891 if (!server->ops->need_neg || !server->ops->negotiate)3892 return -ENOSYS;3893 3894 /* only send once per connect */3895 spin_lock(&server->srv_lock);3896 if (server->tcpStatus != CifsGood &&3897 server->tcpStatus != CifsNew &&3898 server->tcpStatus != CifsNeedNegotiate) {3899 spin_unlock(&server->srv_lock);3900 return -EHOSTDOWN;3901 }3902 3903 if (!server->ops->need_neg(server) &&3904 server->tcpStatus == CifsGood) {3905 spin_unlock(&server->srv_lock);3906 return 0;3907 }3908 3909 server->tcpStatus = CifsInNegotiate;3910 spin_unlock(&server->srv_lock);3911 3912 rc = server->ops->negotiate(xid, ses, server);3913 if (rc == 0) {3914 spin_lock(&server->srv_lock);3915 if (server->tcpStatus == CifsInNegotiate)3916 server->tcpStatus = CifsGood;3917 else3918 rc = -EHOSTDOWN;3919 spin_unlock(&server->srv_lock);3920 } else {3921 spin_lock(&server->srv_lock);3922 if (server->tcpStatus == CifsInNegotiate)3923 server->tcpStatus = CifsNeedNegotiate;3924 spin_unlock(&server->srv_lock);3925 }3926 3927 return rc;3928}3929 3930int3931cifs_setup_session(const unsigned int xid, struct cifs_ses *ses,3932 struct TCP_Server_Info *server,3933 struct nls_table *nls_info)3934{3935 int rc = -ENOSYS;3936 struct TCP_Server_Info *pserver = SERVER_IS_CHAN(server) ? server->primary_server : server;3937 struct sockaddr_in6 *addr6 = (struct sockaddr_in6 *)&pserver->dstaddr;3938 struct sockaddr_in *addr = (struct sockaddr_in *)&pserver->dstaddr;3939 bool is_binding = false;3940 3941 spin_lock(&ses->ses_lock);3942 cifs_dbg(FYI, "%s: channel connect bitmap: 0x%lx\n",3943 __func__, ses->chans_need_reconnect);3944 3945 if (ses->ses_status != SES_GOOD &&3946 ses->ses_status != SES_NEW &&3947 ses->ses_status != SES_NEED_RECON) {3948 spin_unlock(&ses->ses_lock);3949 return -EHOSTDOWN;3950 }3951 3952 /* only send once per connect */3953 spin_lock(&ses->chan_lock);3954 if (CIFS_ALL_CHANS_GOOD(ses)) {3955 if (ses->ses_status == SES_NEED_RECON)3956 ses->ses_status = SES_GOOD;3957 spin_unlock(&ses->chan_lock);3958 spin_unlock(&ses->ses_lock);3959 return 0;3960 }3961 3962 cifs_chan_set_in_reconnect(ses, server);3963 is_binding = !CIFS_ALL_CHANS_NEED_RECONNECT(ses);3964 spin_unlock(&ses->chan_lock);3965 3966 if (!is_binding) {3967 ses->ses_status = SES_IN_SETUP;3968 3969 /* force iface_list refresh */3970 ses->iface_last_update = 0;3971 }3972 spin_unlock(&ses->ses_lock);3973 3974 /* update ses ip_addr only for primary chan */3975 if (server == pserver) {3976 if (server->dstaddr.ss_family == AF_INET6)3977 scnprintf(ses->ip_addr, sizeof(ses->ip_addr), "%pI6", &addr6->sin6_addr);3978 else3979 scnprintf(ses->ip_addr, sizeof(ses->ip_addr), "%pI4", &addr->sin_addr);3980 }3981 3982 if (!is_binding) {3983 ses->capabilities = server->capabilities;3984 if (!linuxExtEnabled)3985 ses->capabilities &= (~server->vals->cap_unix);3986 3987 if (ses->auth_key.response) {3988 cifs_dbg(FYI, "Free previous auth_key.response = %p\n",3989 ses->auth_key.response);3990 kfree_sensitive(ses->auth_key.response);3991 ses->auth_key.response = NULL;3992 ses->auth_key.len = 0;3993 }3994 }3995 3996 cifs_dbg(FYI, "Security Mode: 0x%x Capabilities: 0x%x TimeAdjust: %d\n",3997 server->sec_mode, server->capabilities, server->timeAdj);3998 3999 if (server->ops->sess_setup)4000 rc = server->ops->sess_setup(xid, ses, server, nls_info);4001 4002 if (rc) {4003 cifs_server_dbg(VFS, "Send error in SessSetup = %d\n", rc);4004 spin_lock(&ses->ses_lock);4005 if (ses->ses_status == SES_IN_SETUP)4006 ses->ses_status = SES_NEED_RECON;4007 spin_lock(&ses->chan_lock);4008 cifs_chan_clear_in_reconnect(ses, server);4009 spin_unlock(&ses->chan_lock);4010 spin_unlock(&ses->ses_lock);4011 } else {4012 spin_lock(&ses->ses_lock);4013 if (ses->ses_status == SES_IN_SETUP)4014 ses->ses_status = SES_GOOD;4015 spin_lock(&ses->chan_lock);4016 cifs_chan_clear_in_reconnect(ses, server);4017 cifs_chan_clear_need_reconnect(ses, server);4018 spin_unlock(&ses->chan_lock);4019 spin_unlock(&ses->ses_lock);4020 }4021 4022 return rc;4023}4024 4025static int4026cifs_set_vol_auth(struct smb3_fs_context *ctx, struct cifs_ses *ses)4027{4028 ctx->sectype = ses->sectype;4029 4030 /* krb5 is special, since we don't need username or pw */4031 if (ctx->sectype == Kerberos)4032 return 0;4033 4034 return cifs_set_cifscreds(ctx, ses);4035}4036 4037static struct cifs_tcon *4038cifs_construct_tcon(struct cifs_sb_info *cifs_sb, kuid_t fsuid)4039{4040 int rc;4041 struct cifs_tcon *master_tcon = cifs_sb_master_tcon(cifs_sb);4042 struct cifs_ses *ses;4043 struct cifs_tcon *tcon = NULL;4044 struct smb3_fs_context *ctx;4045 char *origin_fullpath = NULL;4046 4047 ctx = kzalloc(sizeof(*ctx), GFP_KERNEL);4048 if (ctx == NULL)4049 return ERR_PTR(-ENOMEM);4050 4051 ctx->local_nls = cifs_sb->local_nls;4052 ctx->linux_uid = fsuid;4053 ctx->cred_uid = fsuid;4054 ctx->UNC = master_tcon->tree_name;4055 ctx->retry = master_tcon->retry;4056 ctx->nocase = master_tcon->nocase;4057 ctx->nohandlecache = master_tcon->nohandlecache;4058 ctx->local_lease = master_tcon->local_lease;4059 ctx->no_lease = master_tcon->no_lease;4060 ctx->resilient = master_tcon->use_resilient;4061 ctx->persistent = master_tcon->use_persistent;4062 ctx->handle_timeout = master_tcon->handle_timeout;4063 ctx->no_linux_ext = !master_tcon->unix_ext;4064 ctx->linux_ext = master_tcon->posix_extensions;4065 ctx->sectype = master_tcon->ses->sectype;4066 ctx->sign = master_tcon->ses->sign;4067 ctx->seal = master_tcon->seal;4068 ctx->witness = master_tcon->use_witness;4069 ctx->dfs_root_ses = master_tcon->ses->dfs_root_ses;4070 4071 rc = cifs_set_vol_auth(ctx, master_tcon->ses);4072 if (rc) {4073 tcon = ERR_PTR(rc);4074 goto out;4075 }4076 4077 /* get a reference for the same TCP session */4078 spin_lock(&cifs_tcp_ses_lock);4079 ++master_tcon->ses->server->srv_count;4080 spin_unlock(&cifs_tcp_ses_lock);4081 4082 ses = cifs_get_smb_ses(master_tcon->ses->server, ctx);4083 if (IS_ERR(ses)) {4084 tcon = ERR_CAST(ses);4085 cifs_put_tcp_session(master_tcon->ses->server, 0);4086 goto out;4087 }4088 4089#ifdef CONFIG_CIFS_DFS_UPCALL4090 spin_lock(&master_tcon->tc_lock);4091 if (master_tcon->origin_fullpath) {4092 spin_unlock(&master_tcon->tc_lock);4093 origin_fullpath = dfs_get_path(cifs_sb, cifs_sb->ctx->source);4094 if (IS_ERR(origin_fullpath)) {4095 tcon = ERR_CAST(origin_fullpath);4096 origin_fullpath = NULL;4097 cifs_put_smb_ses(ses);4098 goto out;4099 }4100 } else {4101 spin_unlock(&master_tcon->tc_lock);4102 }4103#endif4104 4105 tcon = cifs_get_tcon(ses, ctx);4106 if (IS_ERR(tcon)) {4107 cifs_put_smb_ses(ses);4108 goto out;4109 }4110 4111#ifdef CONFIG_CIFS_DFS_UPCALL4112 if (origin_fullpath) {4113 spin_lock(&tcon->tc_lock);4114 tcon->origin_fullpath = origin_fullpath;4115 spin_unlock(&tcon->tc_lock);4116 origin_fullpath = NULL;4117 queue_delayed_work(dfscache_wq, &tcon->dfs_cache_work,4118 dfs_cache_get_ttl() * HZ);4119 }4120#endif4121 4122#ifdef CONFIG_CIFS_ALLOW_INSECURE_LEGACY4123 if (cap_unix(ses))4124 reset_cifs_unix_caps(0, tcon, NULL, ctx);4125#endif /* CONFIG_CIFS_ALLOW_INSECURE_LEGACY */4126 4127out:4128 kfree(ctx->username);4129 kfree_sensitive(ctx->password);4130 kfree(origin_fullpath);4131 kfree(ctx);4132 4133 return tcon;4134}4135 4136struct cifs_tcon *4137cifs_sb_master_tcon(struct cifs_sb_info *cifs_sb)4138{4139 return tlink_tcon(cifs_sb_master_tlink(cifs_sb));4140}4141 4142/* find and return a tlink with given uid */4143static struct tcon_link *4144tlink_rb_search(struct rb_root *root, kuid_t uid)4145{4146 struct rb_node *node = root->rb_node;4147 struct tcon_link *tlink;4148 4149 while (node) {4150 tlink = rb_entry(node, struct tcon_link, tl_rbnode);4151 4152 if (uid_gt(tlink->tl_uid, uid))4153 node = node->rb_left;4154 else if (uid_lt(tlink->tl_uid, uid))4155 node = node->rb_right;4156 else4157 return tlink;4158 }4159 return NULL;4160}4161 4162/* insert a tcon_link into the tree */4163static void4164tlink_rb_insert(struct rb_root *root, struct tcon_link *new_tlink)4165{4166 struct rb_node **new = &(root->rb_node), *parent = NULL;4167 struct tcon_link *tlink;4168 4169 while (*new) {4170 tlink = rb_entry(*new, struct tcon_link, tl_rbnode);4171 parent = *new;4172 4173 if (uid_gt(tlink->tl_uid, new_tlink->tl_uid))4174 new = &((*new)->rb_left);4175 else4176 new = &((*new)->rb_right);4177 }4178 4179 rb_link_node(&new_tlink->tl_rbnode, parent, new);4180 rb_insert_color(&new_tlink->tl_rbnode, root);4181}4182 4183/*4184 * Find or construct an appropriate tcon given a cifs_sb and the fsuid of the4185 * current task.4186 *4187 * If the superblock doesn't refer to a multiuser mount, then just return4188 * the master tcon for the mount.4189 *4190 * First, search the rbtree for an existing tcon for this fsuid. If one4191 * exists, then check to see if it's pending construction. If it is then wait4192 * for construction to complete. Once it's no longer pending, check to see if4193 * it failed and either return an error or retry construction, depending on4194 * the timeout.4195 *4196 * If one doesn't exist then insert a new tcon_link struct into the tree and4197 * try to construct a new one.4198 *4199 * REMEMBER to call cifs_put_tlink() after successful calls to cifs_sb_tlink,4200 * to avoid refcount issues4201 */4202struct tcon_link *4203cifs_sb_tlink(struct cifs_sb_info *cifs_sb)4204{4205 struct tcon_link *tlink, *newtlink;4206 kuid_t fsuid = current_fsuid();4207 int err;4208 4209 if (!(cifs_sb->mnt_cifs_flags & CIFS_MOUNT_MULTIUSER))4210 return cifs_get_tlink(cifs_sb_master_tlink(cifs_sb));4211 4212 spin_lock(&cifs_sb->tlink_tree_lock);4213 tlink = tlink_rb_search(&cifs_sb->tlink_tree, fsuid);4214 if (tlink)4215 cifs_get_tlink(tlink);4216 spin_unlock(&cifs_sb->tlink_tree_lock);4217 4218 if (tlink == NULL) {4219 newtlink = kzalloc(sizeof(*tlink), GFP_KERNEL);4220 if (newtlink == NULL)4221 return ERR_PTR(-ENOMEM);4222 newtlink->tl_uid = fsuid;4223 newtlink->tl_tcon = ERR_PTR(-EACCES);4224 set_bit(TCON_LINK_PENDING, &newtlink->tl_flags);4225 set_bit(TCON_LINK_IN_TREE, &newtlink->tl_flags);4226 cifs_get_tlink(newtlink);4227 4228 spin_lock(&cifs_sb->tlink_tree_lock);4229 /* was one inserted after previous search? */4230 tlink = tlink_rb_search(&cifs_sb->tlink_tree, fsuid);4231 if (tlink) {4232 cifs_get_tlink(tlink);4233 spin_unlock(&cifs_sb->tlink_tree_lock);4234 kfree(newtlink);4235 goto wait_for_construction;4236 }4237 tlink = newtlink;4238 tlink_rb_insert(&cifs_sb->tlink_tree, tlink);4239 spin_unlock(&cifs_sb->tlink_tree_lock);4240 } else {4241wait_for_construction:4242 err = wait_on_bit(&tlink->tl_flags, TCON_LINK_PENDING,4243 TASK_INTERRUPTIBLE);4244 if (err) {4245 cifs_put_tlink(tlink);4246 return ERR_PTR(-ERESTARTSYS);4247 }4248 4249 /* if it's good, return it */4250 if (!IS_ERR(tlink->tl_tcon))4251 return tlink;4252 4253 /* return error if we tried this already recently */4254 if (time_before(jiffies, tlink->tl_time + TLINK_ERROR_EXPIRE)) {4255 err = PTR_ERR(tlink->tl_tcon);4256 cifs_put_tlink(tlink);4257 return ERR_PTR(err);4258 }4259 4260 if (test_and_set_bit(TCON_LINK_PENDING, &tlink->tl_flags))4261 goto wait_for_construction;4262 }4263 4264 tlink->tl_tcon = cifs_construct_tcon(cifs_sb, fsuid);4265 clear_bit(TCON_LINK_PENDING, &tlink->tl_flags);4266 wake_up_bit(&tlink->tl_flags, TCON_LINK_PENDING);4267 4268 if (IS_ERR(tlink->tl_tcon)) {4269 err = PTR_ERR(tlink->tl_tcon);4270 if (err == -ENOKEY)4271 err = -EACCES;4272 cifs_put_tlink(tlink);4273 return ERR_PTR(err);4274 }4275 4276 return tlink;4277}4278 4279/*4280 * periodic workqueue job that scans tcon_tree for a superblock and closes4281 * out tcons.4282 */4283static void4284cifs_prune_tlinks(struct work_struct *work)4285{4286 struct cifs_sb_info *cifs_sb = container_of(work, struct cifs_sb_info,4287 prune_tlinks.work);4288 struct rb_root *root = &cifs_sb->tlink_tree;4289 struct rb_node *node;4290 struct rb_node *tmp;4291 struct tcon_link *tlink;4292 4293 /*4294 * Because we drop the spinlock in the loop in order to put the tlink4295 * it's not guarded against removal of links from the tree. The only4296 * places that remove entries from the tree are this function and4297 * umounts. Because this function is non-reentrant and is canceled4298 * before umount can proceed, this is safe.4299 */4300 spin_lock(&cifs_sb->tlink_tree_lock);4301 node = rb_first(root);4302 while (node != NULL) {4303 tmp = node;4304 node = rb_next(tmp);4305 tlink = rb_entry(tmp, struct tcon_link, tl_rbnode);4306 4307 if (test_bit(TCON_LINK_MASTER, &tlink->tl_flags) ||4308 atomic_read(&tlink->tl_count) != 0 ||4309 time_after(tlink->tl_time + TLINK_IDLE_EXPIRE, jiffies))4310 continue;4311 4312 cifs_get_tlink(tlink);4313 clear_bit(TCON_LINK_IN_TREE, &tlink->tl_flags);4314 rb_erase(tmp, root);4315 4316 spin_unlock(&cifs_sb->tlink_tree_lock);4317 cifs_put_tlink(tlink);4318 spin_lock(&cifs_sb->tlink_tree_lock);4319 }4320 spin_unlock(&cifs_sb->tlink_tree_lock);4321 4322 queue_delayed_work(cifsiod_wq, &cifs_sb->prune_tlinks,4323 TLINK_IDLE_EXPIRE);4324}4325 4326#ifndef CONFIG_CIFS_DFS_UPCALL4327int cifs_tree_connect(const unsigned int xid, struct cifs_tcon *tcon, const struct nls_table *nlsc)4328{4329 int rc;4330 const struct smb_version_operations *ops = tcon->ses->server->ops;4331 4332 /* only send once per connect */4333 spin_lock(&tcon->tc_lock);4334 4335 /* if tcon is marked for needing reconnect, update state */4336 if (tcon->need_reconnect)4337 tcon->status = TID_NEED_TCON;4338 4339 if (tcon->status == TID_GOOD) {4340 spin_unlock(&tcon->tc_lock);4341 return 0;4342 }4343 4344 if (tcon->status != TID_NEW &&4345 tcon->status != TID_NEED_TCON) {4346 spin_unlock(&tcon->tc_lock);4347 return -EHOSTDOWN;4348 }4349 4350 tcon->status = TID_IN_TCON;4351 spin_unlock(&tcon->tc_lock);4352 4353 rc = ops->tree_connect(xid, tcon->ses, tcon->tree_name, tcon, nlsc);4354 if (rc) {4355 spin_lock(&tcon->tc_lock);4356 if (tcon->status == TID_IN_TCON)4357 tcon->status = TID_NEED_TCON;4358 spin_unlock(&tcon->tc_lock);4359 } else {4360 spin_lock(&tcon->tc_lock);4361 if (tcon->status == TID_IN_TCON)4362 tcon->status = TID_GOOD;4363 tcon->need_reconnect = false;4364 spin_unlock(&tcon->tc_lock);4365 }4366 4367 return rc;4368}4369#endif4370