194f9cce5d832e045e495b0b54938cb8e5492208
[platform/adaptation/renesas_rcar/renesas_kernel.git] / fs / cifs / cifsencrypt.c
1 /*
2  *   fs/cifs/cifsencrypt.c
3  *
4  *   Copyright (C) International Business Machines  Corp., 2005,2013
5  *   Author(s): Steve French (sfrench@us.ibm.com)
6  *
7  *   This library is free software; you can redistribute it and/or modify
8  *   it under the terms of the GNU Lesser General Public License as published
9  *   by the Free Software Foundation; either version 2.1 of the License, or
10  *   (at your option) any later version.
11  *
12  *   This library is distributed in the hope that it will be useful,
13  *   but WITHOUT ANY WARRANTY; without even the implied warranty of
14  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See
15  *   the GNU Lesser General Public License for more details.
16  *
17  *   You should have received a copy of the GNU Lesser General Public License
18  *   along with this library; if not, write to the Free Software
19  *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20  */
21
22 #include <linux/fs.h>
23 #include <linux/slab.h>
24 #include "cifspdu.h"
25 #include "cifsglob.h"
26 #include "cifs_debug.h"
27 #include "cifs_unicode.h"
28 #include "cifsproto.h"
29 #include "ntlmssp.h"
30 #include <linux/ctype.h>
31 #include <linux/random.h>
32 #include <linux/highmem.h>
33
34 static int
35 cifs_crypto_shash_md5_allocate(struct TCP_Server_Info *server)
36 {
37         int rc;
38         unsigned int size;
39
40         if (server->secmech.sdescmd5 != NULL)
41                 return 0; /* already allocated */
42
43         server->secmech.md5 = crypto_alloc_shash("md5", 0, 0);
44         if (IS_ERR(server->secmech.md5)) {
45                 cifs_dbg(VFS, "could not allocate crypto md5\n");
46                 return PTR_ERR(server->secmech.md5);
47         }
48
49         size = sizeof(struct shash_desc) +
50                         crypto_shash_descsize(server->secmech.md5);
51         server->secmech.sdescmd5 = kmalloc(size, GFP_KERNEL);
52         if (!server->secmech.sdescmd5) {
53                 rc = -ENOMEM;
54                 crypto_free_shash(server->secmech.md5);
55                 server->secmech.md5 = NULL;
56                 return rc;
57         }
58         server->secmech.sdescmd5->shash.tfm = server->secmech.md5;
59         server->secmech.sdescmd5->shash.flags = 0x0;
60
61         return 0;
62 }
63
64 /*
65  * Calculate and return the CIFS signature based on the mac key and SMB PDU.
66  * The 16 byte signature must be allocated by the caller. Note we only use the
67  * 1st eight bytes and that the smb header signature field on input contains
68  * the sequence number before this function is called. Also, this function
69  * should be called with the server->srv_mutex held.
70  */
71 static int cifs_calc_signature(struct smb_rqst *rqst,
72                         struct TCP_Server_Info *server, char *signature)
73 {
74         int i;
75         int rc;
76         struct kvec *iov = rqst->rq_iov;
77         int n_vec = rqst->rq_nvec;
78
79         if (iov == NULL || signature == NULL || server == NULL)
80                 return -EINVAL;
81
82         if (!server->secmech.sdescmd5) {
83                 rc = cifs_crypto_shash_md5_allocate(server);
84                 if (rc) {
85                         cifs_dbg(VFS, "%s: Can't alloc md5 crypto\n", __func__);
86                         return -1;
87                 }
88         }
89
90         rc = crypto_shash_init(&server->secmech.sdescmd5->shash);
91         if (rc) {
92                 cifs_dbg(VFS, "%s: Could not init md5\n", __func__);
93                 return rc;
94         }
95
96         rc = crypto_shash_update(&server->secmech.sdescmd5->shash,
97                 server->session_key.response, server->session_key.len);
98         if (rc) {
99                 cifs_dbg(VFS, "%s: Could not update with response\n", __func__);
100                 return rc;
101         }
102
103         for (i = 0; i < n_vec; i++) {
104                 if (iov[i].iov_len == 0)
105                         continue;
106                 if (iov[i].iov_base == NULL) {
107                         cifs_dbg(VFS, "null iovec entry\n");
108                         return -EIO;
109                 }
110                 /* The first entry includes a length field (which does not get
111                    signed that occupies the first 4 bytes before the header */
112                 if (i == 0) {
113                         if (iov[0].iov_len <= 8) /* cmd field at offset 9 */
114                                 break; /* nothing to sign or corrupt header */
115                         rc =
116                         crypto_shash_update(&server->secmech.sdescmd5->shash,
117                                 iov[i].iov_base + 4, iov[i].iov_len - 4);
118                 } else {
119                         rc =
120                         crypto_shash_update(&server->secmech.sdescmd5->shash,
121                                 iov[i].iov_base, iov[i].iov_len);
122                 }
123                 if (rc) {
124                         cifs_dbg(VFS, "%s: Could not update with payload\n",
125                                  __func__);
126                         return rc;
127                 }
128         }
129
130         /* now hash over the rq_pages array */
131         for (i = 0; i < rqst->rq_npages; i++) {
132                 struct kvec p_iov;
133
134                 cifs_rqst_page_to_kvec(rqst, i, &p_iov);
135                 crypto_shash_update(&server->secmech.sdescmd5->shash,
136                                         p_iov.iov_base, p_iov.iov_len);
137                 kunmap(rqst->rq_pages[i]);
138         }
139
140         rc = crypto_shash_final(&server->secmech.sdescmd5->shash, signature);
141         if (rc)
142                 cifs_dbg(VFS, "%s: Could not generate md5 hash\n", __func__);
143
144         return rc;
145 }
146
147 /* must be called with server->srv_mutex held */
148 int cifs_sign_rqst(struct smb_rqst *rqst, struct TCP_Server_Info *server,
149                    __u32 *pexpected_response_sequence_number)
150 {
151         int rc = 0;
152         char smb_signature[20];
153         struct smb_hdr *cifs_pdu = (struct smb_hdr *)rqst->rq_iov[0].iov_base;
154
155         if ((cifs_pdu == NULL) || (server == NULL))
156                 return -EINVAL;
157
158         if (!(cifs_pdu->Flags2 & SMBFLG2_SECURITY_SIGNATURE) ||
159             server->tcpStatus == CifsNeedNegotiate)
160                 return rc;
161
162         if (!server->session_estab) {
163                 memcpy(cifs_pdu->Signature.SecuritySignature, "BSRSPYL", 8);
164                 return rc;
165         }
166
167         cifs_pdu->Signature.Sequence.SequenceNumber =
168                                 cpu_to_le32(server->sequence_number);
169         cifs_pdu->Signature.Sequence.Reserved = 0;
170
171         *pexpected_response_sequence_number = ++server->sequence_number;
172         ++server->sequence_number;
173
174         rc = cifs_calc_signature(rqst, server, smb_signature);
175         if (rc)
176                 memset(cifs_pdu->Signature.SecuritySignature, 0, 8);
177         else
178                 memcpy(cifs_pdu->Signature.SecuritySignature, smb_signature, 8);
179
180         return rc;
181 }
182
183 int cifs_sign_smbv(struct kvec *iov, int n_vec, struct TCP_Server_Info *server,
184                    __u32 *pexpected_response_sequence)
185 {
186         struct smb_rqst rqst = { .rq_iov = iov,
187                                  .rq_nvec = n_vec };
188
189         return cifs_sign_rqst(&rqst, server, pexpected_response_sequence);
190 }
191
192 /* must be called with server->srv_mutex held */
193 int cifs_sign_smb(struct smb_hdr *cifs_pdu, struct TCP_Server_Info *server,
194                   __u32 *pexpected_response_sequence_number)
195 {
196         struct kvec iov;
197
198         iov.iov_base = cifs_pdu;
199         iov.iov_len = be32_to_cpu(cifs_pdu->smb_buf_length) + 4;
200
201         return cifs_sign_smbv(&iov, 1, server,
202                               pexpected_response_sequence_number);
203 }
204
205 int cifs_verify_signature(struct smb_rqst *rqst,
206                           struct TCP_Server_Info *server,
207                           __u32 expected_sequence_number)
208 {
209         unsigned int rc;
210         char server_response_sig[8];
211         char what_we_think_sig_should_be[20];
212         struct smb_hdr *cifs_pdu = (struct smb_hdr *)rqst->rq_iov[0].iov_base;
213
214         if (cifs_pdu == NULL || server == NULL)
215                 return -EINVAL;
216
217         if (!server->session_estab)
218                 return 0;
219
220         if (cifs_pdu->Command == SMB_COM_LOCKING_ANDX) {
221                 struct smb_com_lock_req *pSMB =
222                         (struct smb_com_lock_req *)cifs_pdu;
223             if (pSMB->LockType & LOCKING_ANDX_OPLOCK_RELEASE)
224                         return 0;
225         }
226
227         /* BB what if signatures are supposed to be on for session but
228            server does not send one? BB */
229
230         /* Do not need to verify session setups with signature "BSRSPYL "  */
231         if (memcmp(cifs_pdu->Signature.SecuritySignature, "BSRSPYL ", 8) == 0)
232                 cifs_dbg(FYI, "dummy signature received for smb command 0x%x\n",
233                          cifs_pdu->Command);
234
235         /* save off the origiginal signature so we can modify the smb and check
236                 its signature against what the server sent */
237         memcpy(server_response_sig, cifs_pdu->Signature.SecuritySignature, 8);
238
239         cifs_pdu->Signature.Sequence.SequenceNumber =
240                                         cpu_to_le32(expected_sequence_number);
241         cifs_pdu->Signature.Sequence.Reserved = 0;
242
243         mutex_lock(&server->srv_mutex);
244         rc = cifs_calc_signature(rqst, server, what_we_think_sig_should_be);
245         mutex_unlock(&server->srv_mutex);
246
247         if (rc)
248                 return rc;
249
250 /*      cifs_dump_mem("what we think it should be: ",
251                       what_we_think_sig_should_be, 16); */
252
253         if (memcmp(server_response_sig, what_we_think_sig_should_be, 8))
254                 return -EACCES;
255         else
256                 return 0;
257
258 }
259
260 /* first calculate 24 bytes ntlm response and then 16 byte session key */
261 int setup_ntlm_response(struct cifs_ses *ses, const struct nls_table *nls_cp)
262 {
263         int rc = 0;
264         unsigned int temp_len = CIFS_SESS_KEY_SIZE + CIFS_AUTH_RESP_SIZE;
265         char temp_key[CIFS_SESS_KEY_SIZE];
266
267         if (!ses)
268                 return -EINVAL;
269
270         ses->auth_key.response = kmalloc(temp_len, GFP_KERNEL);
271         if (!ses->auth_key.response)
272                 return -ENOMEM;
273
274         ses->auth_key.len = temp_len;
275
276         rc = SMBNTencrypt(ses->password, ses->server->cryptkey,
277                         ses->auth_key.response + CIFS_SESS_KEY_SIZE, nls_cp);
278         if (rc) {
279                 cifs_dbg(FYI, "%s Can't generate NTLM response, error: %d\n",
280                          __func__, rc);
281                 return rc;
282         }
283
284         rc = E_md4hash(ses->password, temp_key, nls_cp);
285         if (rc) {
286                 cifs_dbg(FYI, "%s Can't generate NT hash, error: %d\n",
287                          __func__, rc);
288                 return rc;
289         }
290
291         rc = mdfour(ses->auth_key.response, temp_key, CIFS_SESS_KEY_SIZE);
292         if (rc)
293                 cifs_dbg(FYI, "%s Can't generate NTLM session key, error: %d\n",
294                          __func__, rc);
295
296         return rc;
297 }
298
299 #ifdef CONFIG_CIFS_WEAK_PW_HASH
300 int calc_lanman_hash(const char *password, const char *cryptkey, bool encrypt,
301                         char *lnm_session_key)
302 {
303         int i;
304         int rc;
305         char password_with_pad[CIFS_ENCPWD_SIZE];
306
307         memset(password_with_pad, 0, CIFS_ENCPWD_SIZE);
308         if (password)
309                 strncpy(password_with_pad, password, CIFS_ENCPWD_SIZE);
310
311         if (!encrypt && global_secflags & CIFSSEC_MAY_PLNTXT) {
312                 memcpy(lnm_session_key, password_with_pad,
313                         CIFS_ENCPWD_SIZE);
314                 return 0;
315         }
316
317         /* calculate old style session key */
318         /* calling toupper is less broken than repeatedly
319         calling nls_toupper would be since that will never
320         work for UTF8, but neither handles multibyte code pages
321         but the only alternative would be converting to UCS-16 (Unicode)
322         (using a routine something like UniStrupr) then
323         uppercasing and then converting back from Unicode - which
324         would only worth doing it if we knew it were utf8. Basically
325         utf8 and other multibyte codepages each need their own strupper
326         function since a byte at a time will ont work. */
327
328         for (i = 0; i < CIFS_ENCPWD_SIZE; i++)
329                 password_with_pad[i] = toupper(password_with_pad[i]);
330
331         rc = SMBencrypt(password_with_pad, cryptkey, lnm_session_key);
332
333         return rc;
334 }
335 #endif /* CIFS_WEAK_PW_HASH */
336
337 /* Build a proper attribute value/target info pairs blob.
338  * Fill in netbios and dns domain name and workstation name
339  * and client time (total five av pairs and + one end of fields indicator.
340  * Allocate domain name which gets freed when session struct is deallocated.
341  */
342 static int
343 build_avpair_blob(struct cifs_ses *ses, const struct nls_table *nls_cp)
344 {
345         unsigned int dlen;
346         unsigned int size = 2 * sizeof(struct ntlmssp2_name);
347         char *defdmname = "WORKGROUP";
348         unsigned char *blobptr;
349         struct ntlmssp2_name *attrptr;
350
351         if (!ses->domainName) {
352                 ses->domainName = kstrdup(defdmname, GFP_KERNEL);
353                 if (!ses->domainName)
354                         return -ENOMEM;
355         }
356
357         dlen = strlen(ses->domainName);
358
359         /*
360          * The length of this blob is two times the size of a
361          * structure (av pair) which holds name/size
362          * ( for NTLMSSP_AV_NB_DOMAIN_NAME followed by NTLMSSP_AV_EOL ) +
363          * unicode length of a netbios domain name
364          */
365         ses->auth_key.len = size + 2 * dlen;
366         ses->auth_key.response = kzalloc(ses->auth_key.len, GFP_KERNEL);
367         if (!ses->auth_key.response) {
368                 ses->auth_key.len = 0;
369                 return -ENOMEM;
370         }
371
372         blobptr = ses->auth_key.response;
373         attrptr = (struct ntlmssp2_name *) blobptr;
374
375         /*
376          * As defined in MS-NTLM 3.3.2, just this av pair field
377          * is sufficient as part of the temp
378          */
379         attrptr->type = cpu_to_le16(NTLMSSP_AV_NB_DOMAIN_NAME);
380         attrptr->length = cpu_to_le16(2 * dlen);
381         blobptr = (unsigned char *)attrptr + sizeof(struct ntlmssp2_name);
382         cifs_strtoUTF16((__le16 *)blobptr, ses->domainName, dlen, nls_cp);
383
384         return 0;
385 }
386
387 /* Server has provided av pairs/target info in the type 2 challenge
388  * packet and we have plucked it and stored within smb session.
389  * We parse that blob here to find netbios domain name to be used
390  * as part of ntlmv2 authentication (in Target String), if not already
391  * specified on the command line.
392  * If this function returns without any error but without fetching
393  * domain name, authentication may fail against some server but
394  * may not fail against other (those who are not very particular
395  * about target string i.e. for some, just user name might suffice.
396  */
397 static int
398 find_domain_name(struct cifs_ses *ses, const struct nls_table *nls_cp)
399 {
400         unsigned int attrsize;
401         unsigned int type;
402         unsigned int onesize = sizeof(struct ntlmssp2_name);
403         unsigned char *blobptr;
404         unsigned char *blobend;
405         struct ntlmssp2_name *attrptr;
406
407         if (!ses->auth_key.len || !ses->auth_key.response)
408                 return 0;
409
410         blobptr = ses->auth_key.response;
411         blobend = blobptr + ses->auth_key.len;
412
413         while (blobptr + onesize < blobend) {
414                 attrptr = (struct ntlmssp2_name *) blobptr;
415                 type = le16_to_cpu(attrptr->type);
416                 if (type == NTLMSSP_AV_EOL)
417                         break;
418                 blobptr += 2; /* advance attr type */
419                 attrsize = le16_to_cpu(attrptr->length);
420                 blobptr += 2; /* advance attr size */
421                 if (blobptr + attrsize > blobend)
422                         break;
423                 if (type == NTLMSSP_AV_NB_DOMAIN_NAME) {
424                         if (!attrsize || attrsize >= CIFS_MAX_DOMAINNAME_LEN)
425                                 break;
426                         if (!ses->domainName) {
427                                 ses->domainName =
428                                         kmalloc(attrsize + 1, GFP_KERNEL);
429                                 if (!ses->domainName)
430                                                 return -ENOMEM;
431                                 cifs_from_utf16(ses->domainName,
432                                         (__le16 *)blobptr, attrsize, attrsize,
433                                         nls_cp, false);
434                                 break;
435                         }
436                 }
437                 blobptr += attrsize; /* advance attr  value */
438         }
439
440         return 0;
441 }
442
443 static int calc_ntlmv2_hash(struct cifs_ses *ses, char *ntlmv2_hash,
444                             const struct nls_table *nls_cp)
445 {
446         int rc = 0;
447         int len;
448         char nt_hash[CIFS_NTHASH_SIZE];
449         __le16 *user;
450         wchar_t *domain;
451         wchar_t *server;
452
453         if (!ses->server->secmech.sdeschmacmd5) {
454                 cifs_dbg(VFS, "%s: can't generate ntlmv2 hash\n", __func__);
455                 return -1;
456         }
457
458         /* calculate md4 hash of password */
459         E_md4hash(ses->password, nt_hash, nls_cp);
460
461         rc = crypto_shash_setkey(ses->server->secmech.hmacmd5, nt_hash,
462                                 CIFS_NTHASH_SIZE);
463         if (rc) {
464                 cifs_dbg(VFS, "%s: Could not set NT Hash as a key\n", __func__);
465                 return rc;
466         }
467
468         rc = crypto_shash_init(&ses->server->secmech.sdeschmacmd5->shash);
469         if (rc) {
470                 cifs_dbg(VFS, "%s: could not init hmacmd5\n", __func__);
471                 return rc;
472         }
473
474         /* convert ses->user_name to unicode */
475         len = ses->user_name ? strlen(ses->user_name) : 0;
476         user = kmalloc(2 + (len * 2), GFP_KERNEL);
477         if (user == NULL) {
478                 rc = -ENOMEM;
479                 return rc;
480         }
481
482         if (len) {
483                 len = cifs_strtoUTF16(user, ses->user_name, len, nls_cp);
484                 UniStrupr(user);
485         } else {
486                 memset(user, '\0', 2);
487         }
488
489         rc = crypto_shash_update(&ses->server->secmech.sdeschmacmd5->shash,
490                                 (char *)user, 2 * len);
491         kfree(user);
492         if (rc) {
493                 cifs_dbg(VFS, "%s: Could not update with user\n", __func__);
494                 return rc;
495         }
496
497         /* convert ses->domainName to unicode and uppercase */
498         if (ses->domainName) {
499                 len = strlen(ses->domainName);
500
501                 domain = kmalloc(2 + (len * 2), GFP_KERNEL);
502                 if (domain == NULL) {
503                         rc = -ENOMEM;
504                         return rc;
505                 }
506                 len = cifs_strtoUTF16((__le16 *)domain, ses->domainName, len,
507                                       nls_cp);
508                 rc =
509                 crypto_shash_update(&ses->server->secmech.sdeschmacmd5->shash,
510                                         (char *)domain, 2 * len);
511                 kfree(domain);
512                 if (rc) {
513                         cifs_dbg(VFS, "%s: Could not update with domain\n",
514                                  __func__);
515                         return rc;
516                 }
517         } else if (ses->serverName) {
518                 len = strlen(ses->serverName);
519
520                 server = kmalloc(2 + (len * 2), GFP_KERNEL);
521                 if (server == NULL) {
522                         rc = -ENOMEM;
523                         return rc;
524                 }
525                 len = cifs_strtoUTF16((__le16 *)server, ses->serverName, len,
526                                         nls_cp);
527                 rc =
528                 crypto_shash_update(&ses->server->secmech.sdeschmacmd5->shash,
529                                         (char *)server, 2 * len);
530                 kfree(server);
531                 if (rc) {
532                         cifs_dbg(VFS, "%s: Could not update with server\n",
533                                  __func__);
534                         return rc;
535                 }
536         }
537
538         rc = crypto_shash_final(&ses->server->secmech.sdeschmacmd5->shash,
539                                         ntlmv2_hash);
540         if (rc)
541                 cifs_dbg(VFS, "%s: Could not generate md5 hash\n", __func__);
542
543         return rc;
544 }
545
546 static int
547 CalcNTLMv2_response(const struct cifs_ses *ses, char *ntlmv2_hash)
548 {
549         int rc;
550         unsigned int offset = CIFS_SESS_KEY_SIZE + 8;
551
552         if (!ses->server->secmech.sdeschmacmd5) {
553                 cifs_dbg(VFS, "%s: can't generate ntlmv2 hash\n", __func__);
554                 return -1;
555         }
556
557         rc = crypto_shash_setkey(ses->server->secmech.hmacmd5,
558                                 ntlmv2_hash, CIFS_HMAC_MD5_HASH_SIZE);
559         if (rc) {
560                 cifs_dbg(VFS, "%s: Could not set NTLMV2 Hash as a key\n",
561                          __func__);
562                 return rc;
563         }
564
565         rc = crypto_shash_init(&ses->server->secmech.sdeschmacmd5->shash);
566         if (rc) {
567                 cifs_dbg(VFS, "%s: could not init hmacmd5\n", __func__);
568                 return rc;
569         }
570
571         if (ses->server->negflavor == CIFS_NEGFLAVOR_EXTENDED)
572                 memcpy(ses->auth_key.response + offset,
573                         ses->ntlmssp->cryptkey, CIFS_SERVER_CHALLENGE_SIZE);
574         else
575                 memcpy(ses->auth_key.response + offset,
576                         ses->server->cryptkey, CIFS_SERVER_CHALLENGE_SIZE);
577         rc = crypto_shash_update(&ses->server->secmech.sdeschmacmd5->shash,
578                 ses->auth_key.response + offset, ses->auth_key.len - offset);
579         if (rc) {
580                 cifs_dbg(VFS, "%s: Could not update with response\n", __func__);
581                 return rc;
582         }
583
584         rc = crypto_shash_final(&ses->server->secmech.sdeschmacmd5->shash,
585                 ses->auth_key.response + CIFS_SESS_KEY_SIZE);
586         if (rc)
587                 cifs_dbg(VFS, "%s: Could not generate md5 hash\n", __func__);
588
589         return rc;
590 }
591
592 static int crypto_hmacmd5_alloc(struct TCP_Server_Info *server)
593 {
594         unsigned int size;
595
596         /* check if already allocated */
597         if (server->secmech.sdeschmacmd5)
598                 return 0;
599
600         server->secmech.hmacmd5 = crypto_alloc_shash("hmac(md5)", 0, 0);
601         if (IS_ERR(server->secmech.hmacmd5)) {
602                 cifs_dbg(VFS, "could not allocate crypto hmacmd5\n");
603                 return PTR_ERR(server->secmech.hmacmd5);
604         }
605
606         size = sizeof(struct shash_desc) +
607                         crypto_shash_descsize(server->secmech.hmacmd5);
608         server->secmech.sdeschmacmd5 = kmalloc(size, GFP_KERNEL);
609         if (!server->secmech.sdeschmacmd5) {
610                 crypto_free_shash(server->secmech.hmacmd5);
611                 server->secmech.hmacmd5 = NULL;
612                 return -ENOMEM;
613         }
614         server->secmech.sdeschmacmd5->shash.tfm = server->secmech.hmacmd5;
615         server->secmech.sdeschmacmd5->shash.flags = 0x0;
616
617         return 0;
618 }
619
620 int
621 setup_ntlmv2_rsp(struct cifs_ses *ses, const struct nls_table *nls_cp)
622 {
623         int rc;
624         int baselen;
625         unsigned int tilen;
626         struct ntlmv2_resp *buf;
627         char ntlmv2_hash[16];
628         unsigned char *tiblob = NULL; /* target info blob */
629
630         if (ses->server->negflavor == CIFS_NEGFLAVOR_EXTENDED) {
631                 if (!ses->domainName) {
632                         rc = find_domain_name(ses, nls_cp);
633                         if (rc) {
634                                 cifs_dbg(VFS, "error %d finding domain name\n",
635                                          rc);
636                                 goto setup_ntlmv2_rsp_ret;
637                         }
638                 }
639         } else {
640                 rc = build_avpair_blob(ses, nls_cp);
641                 if (rc) {
642                         cifs_dbg(VFS, "error %d building av pair blob\n", rc);
643                         goto setup_ntlmv2_rsp_ret;
644                 }
645         }
646
647         baselen = CIFS_SESS_KEY_SIZE + sizeof(struct ntlmv2_resp);
648         tilen = ses->auth_key.len;
649         tiblob = ses->auth_key.response;
650
651         ses->auth_key.response = kmalloc(baselen + tilen, GFP_KERNEL);
652         if (!ses->auth_key.response) {
653                 rc = ENOMEM;
654                 ses->auth_key.len = 0;
655                 goto setup_ntlmv2_rsp_ret;
656         }
657         ses->auth_key.len += baselen;
658
659         buf = (struct ntlmv2_resp *)
660                         (ses->auth_key.response + CIFS_SESS_KEY_SIZE);
661         buf->blob_signature = cpu_to_le32(0x00000101);
662         buf->reserved = 0;
663         buf->time = cpu_to_le64(cifs_UnixTimeToNT(CURRENT_TIME));
664         get_random_bytes(&buf->client_chal, sizeof(buf->client_chal));
665         buf->reserved2 = 0;
666
667         memcpy(ses->auth_key.response + baselen, tiblob, tilen);
668
669         rc = crypto_hmacmd5_alloc(ses->server);
670         if (rc) {
671                 cifs_dbg(VFS, "could not crypto alloc hmacmd5 rc %d\n", rc);
672                 goto setup_ntlmv2_rsp_ret;
673         }
674
675         /* calculate ntlmv2_hash */
676         rc = calc_ntlmv2_hash(ses, ntlmv2_hash, nls_cp);
677         if (rc) {
678                 cifs_dbg(VFS, "could not get v2 hash rc %d\n", rc);
679                 goto setup_ntlmv2_rsp_ret;
680         }
681
682         /* calculate first part of the client response (CR1) */
683         rc = CalcNTLMv2_response(ses, ntlmv2_hash);
684         if (rc) {
685                 cifs_dbg(VFS, "Could not calculate CR1 rc: %d\n", rc);
686                 goto setup_ntlmv2_rsp_ret;
687         }
688
689         /* now calculate the session key for NTLMv2 */
690         rc = crypto_shash_setkey(ses->server->secmech.hmacmd5,
691                 ntlmv2_hash, CIFS_HMAC_MD5_HASH_SIZE);
692         if (rc) {
693                 cifs_dbg(VFS, "%s: Could not set NTLMV2 Hash as a key\n",
694                          __func__);
695                 goto setup_ntlmv2_rsp_ret;
696         }
697
698         rc = crypto_shash_init(&ses->server->secmech.sdeschmacmd5->shash);
699         if (rc) {
700                 cifs_dbg(VFS, "%s: Could not init hmacmd5\n", __func__);
701                 goto setup_ntlmv2_rsp_ret;
702         }
703
704         rc = crypto_shash_update(&ses->server->secmech.sdeschmacmd5->shash,
705                 ses->auth_key.response + CIFS_SESS_KEY_SIZE,
706                 CIFS_HMAC_MD5_HASH_SIZE);
707         if (rc) {
708                 cifs_dbg(VFS, "%s: Could not update with response\n", __func__);
709                 goto setup_ntlmv2_rsp_ret;
710         }
711
712         rc = crypto_shash_final(&ses->server->secmech.sdeschmacmd5->shash,
713                 ses->auth_key.response);
714         if (rc)
715                 cifs_dbg(VFS, "%s: Could not generate md5 hash\n", __func__);
716
717 setup_ntlmv2_rsp_ret:
718         kfree(tiblob);
719
720         return rc;
721 }
722
723 int
724 calc_seckey(struct cifs_ses *ses)
725 {
726         int rc;
727         struct crypto_blkcipher *tfm_arc4;
728         struct scatterlist sgin, sgout;
729         struct blkcipher_desc desc;
730         unsigned char sec_key[CIFS_SESS_KEY_SIZE]; /* a nonce */
731
732         get_random_bytes(sec_key, CIFS_SESS_KEY_SIZE);
733
734         tfm_arc4 = crypto_alloc_blkcipher("ecb(arc4)", 0, CRYPTO_ALG_ASYNC);
735         if (IS_ERR(tfm_arc4)) {
736                 rc = PTR_ERR(tfm_arc4);
737                 cifs_dbg(VFS, "could not allocate crypto API arc4\n");
738                 return rc;
739         }
740
741         desc.tfm = tfm_arc4;
742
743         rc = crypto_blkcipher_setkey(tfm_arc4, ses->auth_key.response,
744                                         CIFS_SESS_KEY_SIZE);
745         if (rc) {
746                 cifs_dbg(VFS, "%s: Could not set response as a key\n",
747                          __func__);
748                 return rc;
749         }
750
751         sg_init_one(&sgin, sec_key, CIFS_SESS_KEY_SIZE);
752         sg_init_one(&sgout, ses->ntlmssp->ciphertext, CIFS_CPHTXT_SIZE);
753
754         rc = crypto_blkcipher_encrypt(&desc, &sgout, &sgin, CIFS_CPHTXT_SIZE);
755         if (rc) {
756                 cifs_dbg(VFS, "could not encrypt session key rc: %d\n", rc);
757                 crypto_free_blkcipher(tfm_arc4);
758                 return rc;
759         }
760
761         /* make secondary_key/nonce as session key */
762         memcpy(ses->auth_key.response, sec_key, CIFS_SESS_KEY_SIZE);
763         /* and make len as that of session key only */
764         ses->auth_key.len = CIFS_SESS_KEY_SIZE;
765
766         crypto_free_blkcipher(tfm_arc4);
767
768         return rc;
769 }
770
771 void
772 cifs_crypto_shash_release(struct TCP_Server_Info *server)
773 {
774         if (server->secmech.cmacaes) {
775                 crypto_free_shash(server->secmech.cmacaes);
776                 server->secmech.cmacaes = NULL;
777         }
778
779         if (server->secmech.hmacsha256) {
780                 crypto_free_shash(server->secmech.hmacsha256);
781                 server->secmech.hmacsha256 = NULL;
782         }
783
784         if (server->secmech.md5) {
785                 crypto_free_shash(server->secmech.md5);
786                 server->secmech.md5 = NULL;
787         }
788
789         if (server->secmech.hmacmd5) {
790                 crypto_free_shash(server->secmech.hmacmd5);
791                 server->secmech.hmacmd5 = NULL;
792         }
793
794         kfree(server->secmech.sdesccmacaes);
795         server->secmech.sdesccmacaes = NULL;
796         kfree(server->secmech.sdeschmacsha256);
797         server->secmech.sdeschmacsha256 = NULL;
798         kfree(server->secmech.sdeschmacmd5);
799         server->secmech.sdeschmacmd5 = NULL;
800         kfree(server->secmech.sdescmd5);
801         server->secmech.sdescmd5 = NULL;
802 }