]> git.karo-electronics.de Git - karo-tx-linux.git/commitdiff
cifs: Set client guid on per connection basis
authorSachin Prabhu <sprabhu@redhat.com>
Mon, 12 May 2014 23:48:12 +0000 (00:48 +0100)
committerSteve French <smfrench@gmail.com>
Wed, 21 May 2014 17:18:05 +0000 (10:18 -0700)
When mounting from a Windows 2012R2 server, we hit the following
problem:
1) Mount with any of the following versions - 2.0, 2.1 or 3.0
2) unmount
3) Attempt a mount again using a different SMB version >= 2.0.

You end up with the following failure:
Status code returned 0xc0000203 STATUS_USER_SESSION_DELETED
CIFS VFS: Send error in SessSetup = -5
CIFS VFS: cifs_mount failed w/return code = -5

I cannot reproduce this issue using a Windows 2008 R2 server.

This appears to be caused because we use the same client guid for the
connection on first mount which we then disconnect and attempt to mount
again using a different protocol version. By generating a new guid each
time a new connection is Negotiated, we avoid hitting this problem.

Signed-off-by: Sachin Prabhu <sprabhu@redhat.com>
Signed-off-by: Steve French <smfrench@gmail.com>
fs/cifs/cifsfs.c
fs/cifs/cifsglob.h
fs/cifs/connect.c
fs/cifs/smb2pdu.c
fs/cifs/smb2pdu.h

index be66533c0f58d178e1acce1c4762879c048250b9..6aaa8112c538a73c82b15eaf8dd733abd21f39f0 100644 (file)
@@ -87,10 +87,6 @@ extern mempool_t *cifs_mid_poolp;
 
 struct workqueue_struct        *cifsiod_wq;
 
-#ifdef CONFIG_CIFS_SMB2
-__u8 cifs_client_guid[SMB2_CLIENT_GUID_SIZE];
-#endif
-
 /*
  * Bumps refcount for cifs super block.
  * Note that it should be only called if a referece to VFS super block is
@@ -1188,10 +1184,6 @@ init_cifs(void)
        spin_lock_init(&cifs_file_list_lock);
        spin_lock_init(&GlobalMid_Lock);
 
-#ifdef CONFIG_CIFS_SMB2
-       get_random_bytes(cifs_client_guid, SMB2_CLIENT_GUID_SIZE);
-#endif
-
        if (cifs_max_pending < 2) {
                cifs_max_pending = 2;
                cifs_dbg(FYI, "cifs_max_pending set to min of 2\n");
index 630e0f4b2c6600e9df7aecf41a842ab64861165d..de6aed8c78e562e468f015a02a71a8a75e3ff36a 100644 (file)
@@ -559,6 +559,7 @@ struct TCP_Server_Info {
        int echo_credits;  /* echo reserved slots */
        int oplock_credits;  /* oplock break reserved slots */
        bool echoes:1; /* enable echoes */
+       __u8 client_guid[SMB2_CLIENT_GUID_SIZE]; /* Client GUID */
 #endif
        u16 dialect; /* dialect index that server chose */
        bool oplocks:1; /* enable oplocks */
index 8813ff776ba3a988e2773147f86406e5013d9047..8b8fe9b373f214ab2f83eed8f585fc712a50b113 100644 (file)
@@ -2144,6 +2144,9 @@ cifs_get_tcp_session(struct smb_vol *volume_info)
               sizeof(tcp_ses->srcaddr));
        memcpy(&tcp_ses->dstaddr, &volume_info->dstaddr,
                sizeof(tcp_ses->dstaddr));
+#ifdef CONFIG_CIFS_SMB2
+       get_random_bytes(tcp_ses->client_guid, SMB2_CLIENT_GUID_SIZE);
+#endif
        /*
         * at this point we are the only ones with the pointer
         * to the struct since the kernel thread not created yet
index 3802f8c94accdba8e9d62622155a523a2c39b4d4..dc44610fdc0d722f70eaeeabbbd0f9ee462a698d 100644 (file)
@@ -375,7 +375,7 @@ SMB2_negotiate(const unsigned int xid, struct cifs_ses *ses)
 
        req->Capabilities = cpu_to_le32(ses->server->vals->req_capabilities);
 
-       memcpy(req->ClientGUID, cifs_client_guid, SMB2_CLIENT_GUID_SIZE);
+       memcpy(req->ClientGUID, server->client_guid, SMB2_CLIENT_GUID_SIZE);
 
        iov[0].iov_base = (char *)req;
        /* 4 for rfc1002 length field */
@@ -478,7 +478,8 @@ int smb3_validate_negotiate(const unsigned int xid, struct cifs_tcon *tcon)
 
        vneg_inbuf.Capabilities =
                        cpu_to_le32(tcon->ses->server->vals->req_capabilities);
-       memcpy(vneg_inbuf.Guid, cifs_client_guid, SMB2_CLIENT_GUID_SIZE);
+       memcpy(vneg_inbuf.Guid, tcon->ses->server->client_guid,
+                                       SMB2_CLIENT_GUID_SIZE);
 
        if (tcon->ses->sign)
                vneg_inbuf.SecurityMode =
index 2022c542ea3aa65ddf15cf511ee652d3040b73a2..743e11e20c5cba2a55e05c4bc27c3dd95fbf0dca 100644 (file)
@@ -183,8 +183,6 @@ struct smb2_symlink_err_rsp {
 
 #define SMB2_CLIENT_GUID_SIZE 16
 
-extern __u8 cifs_client_guid[SMB2_CLIENT_GUID_SIZE];
-
 struct smb2_negotiate_req {
        struct smb2_hdr hdr;
        __le16 StructureSize; /* Must be 36 */