s3:ntlmssp: remove unused ntlmssp_stored_response()
[ira/wip.git] / source3 / libsmb / ntlmssp.c
1 /*
2    Unix SMB/Netbios implementation.
3    Version 3.0
4    handle NLTMSSP, server side
5
6    Copyright (C) Andrew Tridgell      2001
7    Copyright (C) Andrew Bartlett 2001-2003
8    Copyright (C) Andrew Bartlett 2005 (Updated from gensec).
9
10    This program is free software; you can redistribute it and/or modify
11    it under the terms of the GNU General Public License as published by
12    the Free Software Foundation; either version 3 of the License, or
13    (at your option) any later version.
14
15    This program is distributed in the hope that it will be useful,
16    but WITHOUT ANY WARRANTY; without even the implied warranty of
17    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18    GNU General Public License for more details.
19
20    You should have received a copy of the GNU General Public License
21    along with this program.  If not, see <http://www.gnu.org/licenses/>.
22 */
23
24 #include "includes.h"
25 #include "ntlmssp.h"
26 #include "../libcli/auth/libcli_auth.h"
27 #include "../librpc/gen_ndr/ndr_ntlmssp.h"
28 #include "../libcli/auth/ntlmssp_ndr.h"
29
30 static NTSTATUS ntlmssp_client_initial(struct ntlmssp_state *ntlmssp_state,
31                                        DATA_BLOB reply, DATA_BLOB *next_request);
32 static NTSTATUS ntlmssp_server_negotiate(struct ntlmssp_state *ntlmssp_state,
33                                          const DATA_BLOB in, DATA_BLOB *out);
34 static NTSTATUS ntlmssp_client_challenge(struct ntlmssp_state *ntlmssp_state,
35                                          const DATA_BLOB reply, DATA_BLOB *next_request);
36 static NTSTATUS ntlmssp_server_auth(struct ntlmssp_state *ntlmssp_state,
37                                     const DATA_BLOB request, DATA_BLOB *reply);
38
39 /**
40  * Callbacks for NTLMSSP - for both client and server operating modes
41  *
42  */
43
44 static const struct ntlmssp_callbacks {
45         enum ntlmssp_role role;
46         enum ntlmssp_message_type ntlmssp_command;
47         NTSTATUS (*fn)(struct ntlmssp_state *ntlmssp_state,
48                        DATA_BLOB in, DATA_BLOB *out);
49 } ntlmssp_callbacks[] = {
50         {NTLMSSP_CLIENT, NTLMSSP_INITIAL, ntlmssp_client_initial},
51         {NTLMSSP_SERVER, NTLMSSP_NEGOTIATE, ntlmssp_server_negotiate},
52         {NTLMSSP_CLIENT, NTLMSSP_CHALLENGE, ntlmssp_client_challenge},
53         {NTLMSSP_SERVER, NTLMSSP_AUTH, ntlmssp_server_auth},
54         {NTLMSSP_CLIENT, NTLMSSP_UNKNOWN, NULL},
55         {NTLMSSP_SERVER, NTLMSSP_UNKNOWN, NULL}
56 };
57
58
59 /**
60  * Print out the NTLMSSP flags for debugging
61  * @param neg_flags The flags from the packet
62  */
63
64 void debug_ntlmssp_flags(uint32 neg_flags)
65 {
66         DEBUG(3,("Got NTLMSSP neg_flags=0x%08x\n", neg_flags));
67
68         if (neg_flags & NTLMSSP_NEGOTIATE_UNICODE)
69                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_UNICODE\n"));
70         if (neg_flags & NTLMSSP_NEGOTIATE_OEM)
71                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_OEM\n"));
72         if (neg_flags & NTLMSSP_REQUEST_TARGET)
73                 DEBUGADD(4, ("  NTLMSSP_REQUEST_TARGET\n"));
74         if (neg_flags & NTLMSSP_NEGOTIATE_SIGN)
75                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_SIGN\n"));
76         if (neg_flags & NTLMSSP_NEGOTIATE_SEAL)
77                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_SEAL\n"));
78         if (neg_flags & NTLMSSP_NEGOTIATE_DATAGRAM)
79                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_DATAGRAM\n"));
80         if (neg_flags & NTLMSSP_NEGOTIATE_LM_KEY)
81                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_LM_KEY\n"));
82         if (neg_flags & NTLMSSP_NEGOTIATE_NETWARE)
83                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_NETWARE\n"));
84         if (neg_flags & NTLMSSP_NEGOTIATE_NTLM)
85                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_NTLM\n"));
86         if (neg_flags & NTLMSSP_NEGOTIATE_OEM_DOMAIN_SUPPLIED)
87                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_OEM_DOMAIN_SUPPLIED\n"));
88         if (neg_flags & NTLMSSP_NEGOTIATE_OEM_WORKSTATION_SUPPLIED)
89                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_OEM_WORKSTATION_SUPPLIED\n"));
90         if (neg_flags & NTLMSSP_NEGOTIATE_THIS_IS_LOCAL_CALL)
91                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_THIS_IS_LOCAL_CALL\n"));
92         if (neg_flags & NTLMSSP_NEGOTIATE_ALWAYS_SIGN)
93                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_ALWAYS_SIGN\n"));
94         if (neg_flags & NTLMSSP_REQUEST_NON_NT_SESSION_KEY)
95                 DEBUGADD(4, ("  NTLMSSP_REQUEST_NON_NT_SESSION_KEY\n"));
96         if (neg_flags & NTLMSSP_NEGOTIATE_NTLM2)
97                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_NTLM2\n"));
98         if (neg_flags & NTLMSSP_NEGOTIATE_TARGET_INFO)
99                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_TARGET_INFO\n"));
100         if (neg_flags & NTLMSSP_NEGOTIATE_VERSION)
101                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_VERSION\n"));
102         if (neg_flags & NTLMSSP_NEGOTIATE_128)
103                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_128\n"));
104         if (neg_flags & NTLMSSP_NEGOTIATE_KEY_EXCH)
105                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_KEY_EXCH\n"));
106         if (neg_flags & NTLMSSP_NEGOTIATE_56)
107                 DEBUGADD(4, ("  NTLMSSP_NEGOTIATE_56\n"));
108 }
109
110 /**
111  * Default challenge generation code.
112  *
113  */
114
115 static void get_challenge(const struct ntlmssp_state *ntlmssp_state,
116                           uint8_t chal[8])
117 {
118         generate_random_buffer(chal, 8);
119 }
120
121 /**
122  * Default 'we can set the challenge to anything we like' implementation
123  *
124  */
125
126 static bool may_set_challenge(const struct ntlmssp_state *ntlmssp_state)
127 {
128         return True;
129 }
130
131 /**
132  * Default 'we can set the challenge to anything we like' implementation
133  *
134  * Does not actually do anything, as the value is always in the structure anyway.
135  *
136  */
137
138 static NTSTATUS set_challenge(struct ntlmssp_state *ntlmssp_state, DATA_BLOB *challenge)
139 {
140         SMB_ASSERT(challenge->length == 8);
141         return NT_STATUS_OK;
142 }
143
144 /**
145  * Set a username on an NTLMSSP context - ensures it is talloc()ed
146  *
147  */
148
149 NTSTATUS ntlmssp_set_username(struct ntlmssp_state *ntlmssp_state, const char *user)
150 {
151         ntlmssp_state->user = talloc_strdup(ntlmssp_state, user ? user : "" );
152         if (!ntlmssp_state->user) {
153                 return NT_STATUS_NO_MEMORY;
154         }
155         return NT_STATUS_OK;
156 }
157
158 /**
159  * Store NT and LM hashes on an NTLMSSP context - ensures they are talloc()ed
160  *
161  */
162 NTSTATUS ntlmssp_set_hashes(struct ntlmssp_state *ntlmssp_state,
163                 const unsigned char lm_hash[16],
164                 const unsigned char nt_hash[16])
165 {
166         ntlmssp_state->lm_hash = (unsigned char *)
167                 TALLOC_MEMDUP(ntlmssp_state, lm_hash, 16);
168         ntlmssp_state->nt_hash = (unsigned char *)
169                 TALLOC_MEMDUP(ntlmssp_state, nt_hash, 16);
170         if (!ntlmssp_state->lm_hash || !ntlmssp_state->nt_hash) {
171                 TALLOC_FREE(ntlmssp_state->lm_hash);
172                 TALLOC_FREE(ntlmssp_state->nt_hash);
173                 return NT_STATUS_NO_MEMORY;
174         }
175         return NT_STATUS_OK;
176 }
177
178 /**
179  * Converts a password to the hashes on an NTLMSSP context.
180  *
181  */
182 NTSTATUS ntlmssp_set_password(struct ntlmssp_state *ntlmssp_state, const char *password)
183 {
184         if (!password) {
185                 ntlmssp_state->lm_hash = NULL;
186                 ntlmssp_state->nt_hash = NULL;
187         } else {
188                 unsigned char lm_hash[16];
189                 unsigned char nt_hash[16];
190
191                 E_deshash(password, lm_hash);
192                 E_md4hash(password, nt_hash);
193                 return ntlmssp_set_hashes(ntlmssp_state, lm_hash, nt_hash);
194         }
195         return NT_STATUS_OK;
196 }
197
198 /**
199  * Set a domain on an NTLMSSP context - ensures it is talloc()ed
200  *
201  */
202 NTSTATUS ntlmssp_set_domain(struct ntlmssp_state *ntlmssp_state, const char *domain)
203 {
204         ntlmssp_state->domain = talloc_strdup(ntlmssp_state,
205                                               domain ? domain : "" );
206         if (!ntlmssp_state->domain) {
207                 return NT_STATUS_NO_MEMORY;
208         }
209         return NT_STATUS_OK;
210 }
211
212 /**
213  * Set a workstation on an NTLMSSP context - ensures it is talloc()ed
214  *
215  */
216 NTSTATUS ntlmssp_set_workstation(struct ntlmssp_state *ntlmssp_state, const char *workstation)
217 {
218         ntlmssp_state->workstation = talloc_strdup(ntlmssp_state, workstation);
219         if (!ntlmssp_state->workstation) {
220                 return NT_STATUS_NO_MEMORY;
221         }
222         return NT_STATUS_OK;
223 }
224
225 /**
226  * Request features for the NTLMSSP negotiation
227  *
228  * @param ntlmssp_state NTLMSSP state
229  * @param feature_list List of space seperated features requested from NTLMSSP.
230  */
231 void ntlmssp_want_feature_list(struct ntlmssp_state *ntlmssp_state, char *feature_list)
232 {
233         /*
234          * We need to set this to allow a later SetPassword
235          * via the SAMR pipe to succeed. Strange.... We could
236          * also add  NTLMSSP_NEGOTIATE_SEAL here. JRA.
237          */
238         if (in_list("NTLMSSP_FEATURE_SESSION_KEY", feature_list, True)) {
239                 ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_SIGN;
240         }
241         if (in_list("NTLMSSP_FEATURE_SIGN", feature_list, True)) {
242                 ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_SIGN;
243         }
244         if(in_list("NTLMSSP_FEATURE_SEAL", feature_list, True)) {
245                 ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_SEAL;
246         }
247 }
248
249 /**
250  * Request a feature for the NTLMSSP negotiation
251  *
252  * @param ntlmssp_state NTLMSSP state
253  * @param feature Bit flag specifying the requested feature
254  */
255 void ntlmssp_want_feature(struct ntlmssp_state *ntlmssp_state, uint32 feature)
256 {
257         /* As per JRA's comment above */
258         if (feature & NTLMSSP_FEATURE_SESSION_KEY) {
259                 ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_SIGN;
260         }
261         if (feature & NTLMSSP_FEATURE_SIGN) {
262                 ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_SIGN;
263         }
264         if (feature & NTLMSSP_FEATURE_SEAL) {
265                 ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_SEAL;
266         }
267 }
268
269 /**
270  * Next state function for the NTLMSSP state machine
271  *
272  * @param ntlmssp_state NTLMSSP State
273  * @param in The packet in from the NTLMSSP partner, as a DATA_BLOB
274  * @param out The reply, as an allocated DATA_BLOB, caller to free.
275  * @return Errors, NT_STATUS_MORE_PROCESSING_REQUIRED or NT_STATUS_OK.
276  */
277
278 NTSTATUS ntlmssp_update(struct ntlmssp_state *ntlmssp_state,
279                         const DATA_BLOB input, DATA_BLOB *out)
280 {
281         uint32 ntlmssp_command;
282         int i;
283
284         if (ntlmssp_state->expected_state == NTLMSSP_DONE) {
285                 /* Called update after negotiations finished. */
286                 DEBUG(1, ("Called NTLMSSP after state machine was 'done'\n"));
287                 return NT_STATUS_INVALID_PARAMETER;
288         }
289
290         *out = data_blob_null;
291
292         if (!input.length) {
293                 switch (ntlmssp_state->role) {
294                 case NTLMSSP_CLIENT:
295                         ntlmssp_command = NTLMSSP_INITIAL;
296                         break;
297                 case NTLMSSP_SERVER:
298                         /* 'datagram' mode - no neg packet */
299                         ntlmssp_command = NTLMSSP_NEGOTIATE;
300                         break;
301                 }
302         } else {
303                 if (!msrpc_parse(ntlmssp_state, &input, "Cd",
304                                  "NTLMSSP",
305                                  &ntlmssp_command)) {
306                         DEBUG(1, ("Failed to parse NTLMSSP packet, could not extract NTLMSSP command\n"));
307                         dump_data(2, input.data, input.length);
308                         return NT_STATUS_INVALID_PARAMETER;
309                 }
310         }
311
312         if (ntlmssp_command != ntlmssp_state->expected_state) {
313                 DEBUG(1, ("got NTLMSSP command %u, expected %u\n", ntlmssp_command, ntlmssp_state->expected_state));
314                 return NT_STATUS_INVALID_PARAMETER;
315         }
316
317         for (i=0; ntlmssp_callbacks[i].fn; i++) {
318                 if (ntlmssp_callbacks[i].role == ntlmssp_state->role
319                     && ntlmssp_callbacks[i].ntlmssp_command == ntlmssp_command) {
320                         return ntlmssp_callbacks[i].fn(ntlmssp_state, input, out);
321                 }
322         }
323
324         DEBUG(1, ("failed to find NTLMSSP callback for NTLMSSP mode %u, command %u\n",
325                   ntlmssp_state->role, ntlmssp_command));
326
327         return NT_STATUS_INVALID_PARAMETER;
328 }
329
330 /**
331  * End an NTLMSSP state machine
332  *
333  * @param ntlmssp_state NTLMSSP State, free()ed by this function
334  */
335
336 void ntlmssp_end(struct ntlmssp_state **ntlmssp_state)
337 {
338         data_blob_free(&(*ntlmssp_state)->chal);
339         data_blob_free(&(*ntlmssp_state)->lm_resp);
340         data_blob_free(&(*ntlmssp_state)->nt_resp);
341         TALLOC_FREE(*ntlmssp_state);
342
343         *ntlmssp_state = NULL;
344         return;
345 }
346
347 /**
348  * Determine correct target name flags for reply, given server role
349  * and negotiated flags
350  *
351  * @param ntlmssp_state NTLMSSP State
352  * @param neg_flags The flags from the packet
353  * @param chal_flags The flags to be set in the reply packet
354  * @return The 'target name' string.
355  */
356
357 static const char *ntlmssp_target_name(struct ntlmssp_state *ntlmssp_state,
358                                        uint32 neg_flags, uint32 *chal_flags)
359 {
360         if (neg_flags & NTLMSSP_REQUEST_TARGET) {
361                 *chal_flags |= NTLMSSP_NEGOTIATE_TARGET_INFO;
362                 *chal_flags |= NTLMSSP_REQUEST_TARGET;
363                 if (ntlmssp_state->server_role == ROLE_STANDALONE) {
364                         *chal_flags |= NTLMSSP_TARGET_TYPE_SERVER;
365                         return ntlmssp_state->get_global_myname();
366                 } else {
367                         *chal_flags |= NTLMSSP_TARGET_TYPE_DOMAIN;
368                         return ntlmssp_state->get_domain();
369                 };
370         } else {
371                 return "";
372         }
373 }
374
375 static void ntlmssp_handle_neg_flags(struct ntlmssp_state *ntlmssp_state,
376                                       uint32 neg_flags, bool allow_lm) {
377         if (neg_flags & NTLMSSP_NEGOTIATE_UNICODE) {
378                 ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_UNICODE;
379                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_OEM;
380                 ntlmssp_state->unicode = True;
381         } else {
382                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_UNICODE;
383                 ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_OEM;
384                 ntlmssp_state->unicode = False;
385         }
386
387         if ((neg_flags & NTLMSSP_NEGOTIATE_LM_KEY) && allow_lm) {
388                 /* other end forcing us to use LM */
389                 ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_LM_KEY;
390                 ntlmssp_state->use_ntlmv2 = False;
391         } else {
392                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_LM_KEY;
393         }
394
395         if (!(neg_flags & NTLMSSP_NEGOTIATE_ALWAYS_SIGN)) {
396                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_ALWAYS_SIGN;
397         }
398
399         if (!(neg_flags & NTLMSSP_NEGOTIATE_NTLM2)) {
400                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_NTLM2;
401         }
402
403         if (!(neg_flags & NTLMSSP_NEGOTIATE_128)) {
404                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_128;
405         }
406
407         if (!(neg_flags & NTLMSSP_NEGOTIATE_56)) {
408                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_56;
409         }
410
411         if (!(neg_flags & NTLMSSP_NEGOTIATE_KEY_EXCH)) {
412                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_KEY_EXCH;
413         }
414
415         if (!(neg_flags & NTLMSSP_NEGOTIATE_SIGN)) {
416                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_SIGN;
417         }
418
419         if (!(neg_flags & NTLMSSP_NEGOTIATE_SEAL)) {
420                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_SEAL;
421         }
422
423         /* Woop Woop - unknown flag for Windows compatibility...
424            What does this really do ? JRA. */
425         if (!(neg_flags & NTLMSSP_NEGOTIATE_VERSION)) {
426                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_VERSION;
427         }
428
429         if ((neg_flags & NTLMSSP_REQUEST_TARGET)) {
430                 ntlmssp_state->neg_flags |= NTLMSSP_REQUEST_TARGET;
431         }
432 }
433
434 /**
435  Weaken NTLMSSP keys to cope with down-level clients and servers.
436
437  We probably should have some parameters to control this, but as
438  it only occours for LM_KEY connections, and this is controlled
439  by the client lanman auth/lanman auth parameters, it isn't too bad.
440 */
441
442 DATA_BLOB ntlmssp_weaken_keys(struct ntlmssp_state *ntlmssp_state, TALLOC_CTX *mem_ctx)
443 {
444         DATA_BLOB weakened_key = data_blob_talloc(mem_ctx,
445                                         ntlmssp_state->session_key.data,
446                                         ntlmssp_state->session_key.length);
447
448         /* Nothing to weaken.  We certainly don't want to 'extend' the length... */
449         if (weakened_key.length < 16) {
450                 /* perhaps there was no key? */
451                 return weakened_key;
452         }
453
454         /* Key weakening not performed on the master key for NTLM2
455            and does not occour for NTLM1.  Therefore we only need
456            to do this for the LM_KEY.
457         */
458
459         if (ntlmssp_state->neg_flags & NTLMSSP_NEGOTIATE_LM_KEY) {
460                 /* LM key doesn't support 128 bit crypto, so this is
461                  * the best we can do.  If you negotiate 128 bit, but
462                  * not 56, you end up with 40 bit... */
463                 if (ntlmssp_state->neg_flags & NTLMSSP_NEGOTIATE_56) {
464                         weakened_key.data[7] = 0xa0;
465                 } else { /* forty bits */
466                         weakened_key.data[5] = 0xe5;
467                         weakened_key.data[6] = 0x38;
468                         weakened_key.data[7] = 0xb0;
469                 }
470                 weakened_key.length = 8;
471         }
472         return weakened_key;
473 }
474
475 /**
476  * Next state function for the Negotiate packet
477  *
478  * @param ntlmssp_state NTLMSSP State
479  * @param request The request, as a DATA_BLOB
480  * @param request The reply, as an allocated DATA_BLOB, caller to free.
481  * @return Errors or MORE_PROCESSING_REQUIRED if a reply is sent.
482  */
483
484 static NTSTATUS ntlmssp_server_negotiate(struct ntlmssp_state *ntlmssp_state,
485                                          const DATA_BLOB request, DATA_BLOB *reply)
486 {
487         DATA_BLOB struct_blob;
488         const char *dnsname;
489         char *dnsdomname = NULL;
490         uint32 neg_flags = 0;
491         uint32 ntlmssp_command, chal_flags;
492         uint8_t cryptkey[8];
493         const char *target_name;
494         struct NEGOTIATE_MESSAGE negotiate;
495         struct CHALLENGE_MESSAGE challenge;
496
497         /* parse the NTLMSSP packet */
498 #if 0
499         file_save("ntlmssp_negotiate.dat", request.data, request.length);
500 #endif
501
502         if (request.length) {
503                 if ((request.length < 16) || !msrpc_parse(ntlmssp_state, &request, "Cdd",
504                                                           "NTLMSSP",
505                                                           &ntlmssp_command,
506                                                           &neg_flags)) {
507                         DEBUG(1, ("ntlmssp_server_negotiate: failed to parse NTLMSSP Negotiate of length %u\n",
508                                 (unsigned int)request.length));
509                         dump_data(2, request.data, request.length);
510                         return NT_STATUS_INVALID_PARAMETER;
511                 }
512                 debug_ntlmssp_flags(neg_flags);
513
514                 if (DEBUGLEVEL >= 10) {
515                         if (NT_STATUS_IS_OK(ntlmssp_pull_NEGOTIATE_MESSAGE(&request,
516                                                        ntlmssp_state,
517                                                        NULL,
518                                                        &negotiate)))
519                         {
520                                 NDR_PRINT_DEBUG(NEGOTIATE_MESSAGE, &negotiate);
521                         }
522                 }
523         }
524
525         ntlmssp_handle_neg_flags(ntlmssp_state, neg_flags, lp_lanman_auth());
526
527         /* Ask our caller what challenge they would like in the packet */
528         ntlmssp_state->get_challenge(ntlmssp_state, cryptkey);
529
530         /* Check if we may set the challenge */
531         if (!ntlmssp_state->may_set_challenge(ntlmssp_state)) {
532                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_NTLM2;
533         }
534
535         /* The flags we send back are not just the negotiated flags,
536          * they are also 'what is in this packet'.  Therfore, we
537          * operate on 'chal_flags' from here on
538          */
539
540         chal_flags = ntlmssp_state->neg_flags;
541
542         /* get the right name to fill in as 'target' */
543         target_name = ntlmssp_target_name(ntlmssp_state,
544                                           neg_flags, &chal_flags);
545         if (target_name == NULL)
546                 return NT_STATUS_INVALID_PARAMETER;
547
548         ntlmssp_state->chal = data_blob_talloc(ntlmssp_state, cryptkey, 8);
549         ntlmssp_state->internal_chal = data_blob_talloc(ntlmssp_state,
550                                                         cryptkey, 8);
551
552         /* This should be a 'netbios domain -> DNS domain' mapping */
553         dnsdomname = get_mydnsdomname(ntlmssp_state);
554         if (!dnsdomname) {
555                 dnsdomname = talloc_strdup(ntlmssp_state, "");
556         }
557         if (!dnsdomname) {
558                 return NT_STATUS_NO_MEMORY;
559         }
560         strlower_m(dnsdomname);
561
562         dnsname = get_mydnsfullname();
563         if (!dnsname) {
564                 dnsname = "";
565         }
566
567         /* This creates the 'blob' of names that appears at the end of the packet */
568         if (chal_flags & NTLMSSP_NEGOTIATE_TARGET_INFO)
569         {
570                 msrpc_gen(ntlmssp_state, &struct_blob, "aaaaa",
571                           MsvAvNbDomainName, target_name,
572                           MsvAvNbComputerName, ntlmssp_state->get_global_myname(),
573                           MsvAvDnsDomainName, dnsdomname,
574                           MsvAvDnsComputerName, dnsname,
575                           MsvAvEOL, "");
576         } else {
577                 struct_blob = data_blob_null;
578         }
579
580         {
581                 /* Marshel the packet in the right format, be it unicode or ASCII */
582                 const char *gen_string;
583                 if (ntlmssp_state->unicode) {
584                         gen_string = "CdUdbddB";
585                 } else {
586                         gen_string = "CdAdbddB";
587                 }
588
589                 msrpc_gen(ntlmssp_state, reply, gen_string,
590                           "NTLMSSP",
591                           NTLMSSP_CHALLENGE,
592                           target_name,
593                           chal_flags,
594                           cryptkey, 8,
595                           0, 0,
596                           struct_blob.data, struct_blob.length);
597
598                 if (DEBUGLEVEL >= 10) {
599                         if (NT_STATUS_IS_OK(ntlmssp_pull_CHALLENGE_MESSAGE(reply,
600                                                        ntlmssp_state,
601                                                        NULL,
602                                                        &challenge)))
603                         {
604                                 NDR_PRINT_DEBUG(CHALLENGE_MESSAGE, &challenge);
605                         }
606                 }
607         }
608
609         data_blob_free(&struct_blob);
610
611         ntlmssp_state->expected_state = NTLMSSP_AUTH;
612
613         return NT_STATUS_MORE_PROCESSING_REQUIRED;
614 }
615
616 /**
617  * Next state function for the Authenticate packet
618  *
619  * @param ntlmssp_state NTLMSSP State
620  * @param request The request, as a DATA_BLOB
621  * @param request The reply, as an allocated DATA_BLOB, caller to free.
622  * @return Errors or NT_STATUS_OK.
623  */
624
625 static NTSTATUS ntlmssp_server_auth(struct ntlmssp_state *ntlmssp_state,
626                                     const DATA_BLOB request, DATA_BLOB *reply)
627 {
628         DATA_BLOB encrypted_session_key = data_blob_null;
629         DATA_BLOB user_session_key = data_blob_null;
630         DATA_BLOB lm_session_key = data_blob_null;
631         DATA_BLOB session_key = data_blob_null;
632         uint32 ntlmssp_command, auth_flags;
633         NTSTATUS nt_status = NT_STATUS_OK;
634         struct AUTHENTICATE_MESSAGE authenticate;
635
636         /* used by NTLM2 */
637         bool doing_ntlm2 = False;
638
639         uchar session_nonce[16];
640         uchar session_nonce_hash[16];
641
642         const char *parse_string;
643
644         /* parse the NTLMSSP packet */
645         *reply = data_blob_null;
646
647 #if 0
648         file_save("ntlmssp_auth.dat", request.data, request.length);
649 #endif
650
651         if (ntlmssp_state->unicode) {
652                 parse_string = "CdBBUUUBd";
653         } else {
654                 parse_string = "CdBBAAABd";
655         }
656
657         data_blob_free(&ntlmssp_state->lm_resp);
658         data_blob_free(&ntlmssp_state->nt_resp);
659
660         ntlmssp_state->user = NULL;
661         ntlmssp_state->domain = NULL;
662         ntlmssp_state->workstation = NULL;
663
664         /* now the NTLMSSP encoded auth hashes */
665         if (!msrpc_parse(ntlmssp_state, &request, parse_string,
666                          "NTLMSSP",
667                          &ntlmssp_command,
668                          &ntlmssp_state->lm_resp,
669                          &ntlmssp_state->nt_resp,
670                          &ntlmssp_state->domain,
671                          &ntlmssp_state->user,
672                          &ntlmssp_state->workstation,
673                          &encrypted_session_key,
674                          &auth_flags)) {
675                 auth_flags = 0;
676
677                 /* Try again with a shorter string (Win9X truncates this packet) */
678                 if (ntlmssp_state->unicode) {
679                         parse_string = "CdBBUUU";
680                 } else {
681                         parse_string = "CdBBAAA";
682                 }
683
684                 /* now the NTLMSSP encoded auth hashes */
685                 if (!msrpc_parse(ntlmssp_state, &request, parse_string,
686                                  "NTLMSSP",
687                                  &ntlmssp_command,
688                                  &ntlmssp_state->lm_resp,
689                                  &ntlmssp_state->nt_resp,
690                                  &ntlmssp_state->domain,
691                                  &ntlmssp_state->user,
692                                  &ntlmssp_state->workstation)) {
693                         DEBUG(1, ("ntlmssp_server_auth: failed to parse NTLMSSP (tried both formats):\n"));
694                         dump_data(2, request.data, request.length);
695
696                         return NT_STATUS_INVALID_PARAMETER;
697                 }
698         }
699
700         if (auth_flags)
701                 ntlmssp_handle_neg_flags(ntlmssp_state, auth_flags, lp_lanman_auth());
702
703         if (DEBUGLEVEL >= 10) {
704                 if (NT_STATUS_IS_OK(ntlmssp_pull_AUTHENTICATE_MESSAGE(&request,
705                                                   ntlmssp_state,
706                                                   NULL,
707                                                   &authenticate)))
708                 {
709                         NDR_PRINT_DEBUG(AUTHENTICATE_MESSAGE, &authenticate);
710                 }
711         }
712
713         DEBUG(3,("Got user=[%s] domain=[%s] workstation=[%s] len1=%lu len2=%lu\n",
714                  ntlmssp_state->user, ntlmssp_state->domain, ntlmssp_state->workstation, (unsigned long)ntlmssp_state->lm_resp.length, (unsigned long)ntlmssp_state->nt_resp.length));
715
716 #if 0
717         file_save("nthash1.dat",  &ntlmssp_state->nt_resp.data,  &ntlmssp_state->nt_resp.length);
718         file_save("lmhash1.dat",  &ntlmssp_state->lm_resp.data,  &ntlmssp_state->lm_resp.length);
719 #endif
720
721         /* NTLM2 uses a 'challenge' that is made of up both the server challenge, and a
722            client challenge
723
724            However, the NTLM2 flag may still be set for the real NTLMv2 logins, be careful.
725         */
726         if (ntlmssp_state->neg_flags & NTLMSSP_NEGOTIATE_NTLM2) {
727                 if (ntlmssp_state->nt_resp.length == 24 && ntlmssp_state->lm_resp.length == 24) {
728                         struct MD5Context md5_session_nonce_ctx;
729                         SMB_ASSERT(ntlmssp_state->internal_chal.data && ntlmssp_state->internal_chal.length == 8);
730
731                         doing_ntlm2 = True;
732
733                         memcpy(session_nonce, ntlmssp_state->internal_chal.data, 8);
734                         memcpy(&session_nonce[8], ntlmssp_state->lm_resp.data, 8);
735
736                         MD5Init(&md5_session_nonce_ctx);
737                         MD5Update(&md5_session_nonce_ctx, session_nonce, 16);
738                         MD5Final(session_nonce_hash, &md5_session_nonce_ctx);
739
740                         ntlmssp_state->chal = data_blob_talloc(
741                                 ntlmssp_state, session_nonce_hash, 8);
742
743                         /* LM response is no longer useful */
744                         data_blob_free(&ntlmssp_state->lm_resp);
745
746                         /* We changed the effective challenge - set it */
747                         if (!NT_STATUS_IS_OK(nt_status = ntlmssp_state->set_challenge(ntlmssp_state, &ntlmssp_state->chal))) {
748                                 data_blob_free(&encrypted_session_key);
749                                 return nt_status;
750                         }
751
752                         /* LM Key is incompatible. */
753                         ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_LM_KEY;
754                 }
755         }
756
757         /*
758          * Note we don't check here for NTLMv2 auth settings. If NTLMv2 auth
759          * is required (by "ntlm auth = no" and "lm auth = no" being set in the
760          * smb.conf file) and no NTLMv2 response was sent then the password check
761          * will fail here. JRA.
762          */
763
764         /* Finally, actually ask if the password is OK */
765
766         if (!NT_STATUS_IS_OK(nt_status = ntlmssp_state->check_password(ntlmssp_state,
767                                                                        &user_session_key, &lm_session_key))) {
768                 data_blob_free(&encrypted_session_key);
769                 return nt_status;
770         }
771
772         dump_data_pw("NT session key:\n", user_session_key.data, user_session_key.length);
773         dump_data_pw("LM first-8:\n", lm_session_key.data, lm_session_key.length);
774
775         /* Handle the different session key derivation for NTLM2 */
776         if (doing_ntlm2) {
777                 if (user_session_key.data && user_session_key.length == 16) {
778                         session_key = data_blob_talloc(ntlmssp_state,
779                                                        NULL, 16);
780                         hmac_md5(user_session_key.data, session_nonce,
781                                  sizeof(session_nonce), session_key.data);
782                         DEBUG(10,("ntlmssp_server_auth: Created NTLM2 session key.\n"));
783                         dump_data_pw("NTLM2 session key:\n", session_key.data, session_key.length);
784
785                 } else {
786                         DEBUG(10,("ntlmssp_server_auth: Failed to create NTLM2 session key.\n"));
787                         session_key = data_blob_null;
788                 }
789         } else if (ntlmssp_state->neg_flags & NTLMSSP_NEGOTIATE_LM_KEY) {
790                 if (lm_session_key.data && lm_session_key.length >= 8) {
791                         if (ntlmssp_state->lm_resp.data && ntlmssp_state->lm_resp.length == 24) {
792                                 session_key = data_blob_talloc(ntlmssp_state,
793                                                                NULL, 16);
794                                 if (session_key.data == NULL) {
795                                         return NT_STATUS_NO_MEMORY;
796                                 }
797                                 SMBsesskeygen_lm_sess_key(lm_session_key.data, ntlmssp_state->lm_resp.data,
798                                                           session_key.data);
799                                 DEBUG(10,("ntlmssp_server_auth: Created NTLM session key.\n"));
800                         } else {
801                                 uint8 zeros[24];
802                                 ZERO_STRUCT(zeros);
803                                 session_key = data_blob_talloc(
804                                         ntlmssp_state, NULL, 16);
805                                 if (session_key.data == NULL) {
806                                         return NT_STATUS_NO_MEMORY;
807                                 }
808                                 SMBsesskeygen_lm_sess_key(
809                                         lm_session_key.data, zeros,
810                                         session_key.data);
811                         }
812                         dump_data_pw("LM session key:\n", session_key.data,
813                                      session_key.length);
814                 } else {
815                         DEBUG(10,("ntlmssp_server_auth: Failed to create NTLM session key.\n"));
816                         session_key = data_blob_null;
817                 }
818         } else if (user_session_key.data) {
819                 session_key = user_session_key;
820                 DEBUG(10,("ntlmssp_server_auth: Using unmodified nt session key.\n"));
821                 dump_data_pw("unmodified session key:\n", session_key.data, session_key.length);
822         } else if (lm_session_key.data) {
823                 session_key = lm_session_key;
824                 DEBUG(10,("ntlmssp_server_auth: Using unmodified lm session key.\n"));
825                 dump_data_pw("unmodified session key:\n", session_key.data, session_key.length);
826         } else {
827                 DEBUG(10,("ntlmssp_server_auth: Failed to create unmodified session key.\n"));
828                 session_key = data_blob_null;
829         }
830
831         /* With KEY_EXCH, the client supplies the proposed session key,
832            but encrypts it with the long-term key */
833         if (ntlmssp_state->neg_flags & NTLMSSP_NEGOTIATE_KEY_EXCH) {
834                 if (!encrypted_session_key.data || encrypted_session_key.length != 16) {
835                         data_blob_free(&encrypted_session_key);
836                         DEBUG(1, ("Client-supplied KEY_EXCH session key was of invalid length (%u)!\n",
837                                   (unsigned int)encrypted_session_key.length));
838                         return NT_STATUS_INVALID_PARAMETER;
839                 } else if (!session_key.data || session_key.length != 16) {
840                         DEBUG(5, ("server session key is invalid (len == %u), cannot do KEY_EXCH!\n",
841                                   (unsigned int)session_key.length));
842                         ntlmssp_state->session_key = session_key;
843                 } else {
844                         dump_data_pw("KEY_EXCH session key (enc):\n", encrypted_session_key.data, encrypted_session_key.length);
845                         arcfour_crypt_blob(encrypted_session_key.data,
846                                            encrypted_session_key.length,
847                                            &session_key);
848                         ntlmssp_state->session_key = data_blob_talloc(
849                                 ntlmssp_state, encrypted_session_key.data,
850                                 encrypted_session_key.length);
851                         dump_data_pw("KEY_EXCH session key:\n", encrypted_session_key.data,
852                                      encrypted_session_key.length);
853                 }
854         } else {
855                 ntlmssp_state->session_key = session_key;
856         }
857
858         if (!NT_STATUS_IS_OK(nt_status)) {
859                 ntlmssp_state->session_key = data_blob_null;
860         } else if (ntlmssp_state->session_key.length) {
861                 nt_status = ntlmssp_sign_init(ntlmssp_state);
862         }
863
864         data_blob_free(&encrypted_session_key);
865
866         /* Only one authentication allowed per server state. */
867         ntlmssp_state->expected_state = NTLMSSP_DONE;
868
869         return nt_status;
870 }
871
872 /**
873  * Create an NTLMSSP state machine
874  *
875  * @param ntlmssp_state NTLMSSP State, allocated by this function
876  */
877
878 NTSTATUS ntlmssp_server_start(struct ntlmssp_state **ntlmssp_state)
879 {
880         *ntlmssp_state = TALLOC_ZERO_P(NULL, struct ntlmssp_state);
881         if (!*ntlmssp_state) {
882                 DEBUG(0,("ntlmssp_server_start: talloc failed!\n"));
883                 talloc_destroy(*ntlmssp_state);
884                 return NT_STATUS_NO_MEMORY;
885         }
886
887         (*ntlmssp_state)->role = NTLMSSP_SERVER;
888
889         (*ntlmssp_state)->get_challenge = get_challenge;
890         (*ntlmssp_state)->set_challenge = set_challenge;
891         (*ntlmssp_state)->may_set_challenge = may_set_challenge;
892
893         (*ntlmssp_state)->get_global_myname = global_myname;
894         (*ntlmssp_state)->get_domain = lp_workgroup;
895         (*ntlmssp_state)->server_role = ROLE_DOMAIN_MEMBER; /* a good default */
896
897         (*ntlmssp_state)->expected_state = NTLMSSP_NEGOTIATE;
898
899         (*ntlmssp_state)->neg_flags =
900                 NTLMSSP_NEGOTIATE_128 |
901                 NTLMSSP_NEGOTIATE_56 |
902                 NTLMSSP_NEGOTIATE_VERSION |
903                 NTLMSSP_NEGOTIATE_ALWAYS_SIGN |
904                 NTLMSSP_NEGOTIATE_NTLM |
905                 NTLMSSP_NEGOTIATE_NTLM2 |
906                 NTLMSSP_NEGOTIATE_KEY_EXCH |
907                 NTLMSSP_NEGOTIATE_SIGN |
908                 NTLMSSP_NEGOTIATE_SEAL;
909
910         return NT_STATUS_OK;
911 }
912
913 /*********************************************************************
914  Client side NTLMSSP
915 *********************************************************************/
916
917 /**
918  * Next state function for the Initial packet
919  *
920  * @param ntlmssp_state NTLMSSP State
921  * @param request The request, as a DATA_BLOB.  reply.data must be NULL
922  * @param request The reply, as an allocated DATA_BLOB, caller to free.
923  * @return Errors or NT_STATUS_OK.
924  */
925
926 static NTSTATUS ntlmssp_client_initial(struct ntlmssp_state *ntlmssp_state,
927                                   DATA_BLOB reply, DATA_BLOB *next_request)
928 {
929         struct NEGOTIATE_MESSAGE negotiate;
930
931         if (ntlmssp_state->unicode) {
932                 ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_UNICODE;
933         } else {
934                 ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_OEM;
935         }
936
937         if (ntlmssp_state->use_ntlmv2) {
938                 ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_NTLM2;
939         }
940
941         /* generate the ntlmssp negotiate packet */
942         msrpc_gen(ntlmssp_state, next_request, "CddAA",
943                   "NTLMSSP",
944                   NTLMSSP_NEGOTIATE,
945                   ntlmssp_state->neg_flags,
946                   ntlmssp_state->get_domain(),
947                   ntlmssp_state->get_global_myname());
948
949         if (DEBUGLEVEL >= 10) {
950                 if (NT_STATUS_IS_OK(ntlmssp_pull_NEGOTIATE_MESSAGE(next_request,
951                                                ntlmssp_state,
952                                                NULL,
953                                                &negotiate)))
954                 {
955                         NDR_PRINT_DEBUG(NEGOTIATE_MESSAGE, &negotiate);
956                 }
957         }
958
959         ntlmssp_state->expected_state = NTLMSSP_CHALLENGE;
960
961         return NT_STATUS_MORE_PROCESSING_REQUIRED;
962 }
963
964 /**
965  * Next state function for the Challenge Packet.  Generate an auth packet.
966  *
967  * @param ntlmssp_state NTLMSSP State
968  * @param request The request, as a DATA_BLOB.  reply.data must be NULL
969  * @param request The reply, as an allocated DATA_BLOB, caller to free.
970  * @return Errors or NT_STATUS_OK.
971  */
972
973 static NTSTATUS ntlmssp_client_challenge(struct ntlmssp_state *ntlmssp_state,
974                                          const DATA_BLOB reply, DATA_BLOB *next_request)
975 {
976         uint32 chal_flags, ntlmssp_command, unkn1, unkn2;
977         DATA_BLOB server_domain_blob;
978         DATA_BLOB challenge_blob;
979         DATA_BLOB struct_blob = data_blob_null;
980         char *server_domain;
981         const char *chal_parse_string;
982         const char *auth_gen_string;
983         DATA_BLOB lm_response = data_blob_null;
984         DATA_BLOB nt_response = data_blob_null;
985         DATA_BLOB session_key = data_blob_null;
986         DATA_BLOB encrypted_session_key = data_blob_null;
987         NTSTATUS nt_status = NT_STATUS_OK;
988         struct CHALLENGE_MESSAGE challenge;
989         struct AUTHENTICATE_MESSAGE authenticate;
990
991         if (!msrpc_parse(ntlmssp_state, &reply, "CdBd",
992                          "NTLMSSP",
993                          &ntlmssp_command,
994                          &server_domain_blob,
995                          &chal_flags)) {
996                 DEBUG(1, ("Failed to parse the NTLMSSP Challenge: (#1)\n"));
997                 dump_data(2, reply.data, reply.length);
998
999                 return NT_STATUS_INVALID_PARAMETER;
1000         }
1001
1002         if (DEBUGLEVEL >= 10) {
1003                 if (NT_STATUS_IS_OK(ntlmssp_pull_CHALLENGE_MESSAGE(&reply,
1004                                                ntlmssp_state,
1005                                                NULL,
1006                                                &challenge)))
1007                 {
1008                         NDR_PRINT_DEBUG(CHALLENGE_MESSAGE, &challenge);
1009                 }
1010         }
1011
1012         data_blob_free(&server_domain_blob);
1013
1014         DEBUG(3, ("Got challenge flags:\n"));
1015         debug_ntlmssp_flags(chal_flags);
1016
1017         ntlmssp_handle_neg_flags(ntlmssp_state, chal_flags, lp_client_lanman_auth());
1018
1019         if (ntlmssp_state->unicode) {
1020                 if (chal_flags & NTLMSSP_NEGOTIATE_TARGET_INFO) {
1021                         chal_parse_string = "CdUdbddB";
1022                 } else {
1023                         chal_parse_string = "CdUdbdd";
1024                 }
1025                 auth_gen_string = "CdBBUUUBd";
1026         } else {
1027                 if (chal_flags & NTLMSSP_NEGOTIATE_TARGET_INFO) {
1028                         chal_parse_string = "CdAdbddB";
1029                 } else {
1030                         chal_parse_string = "CdAdbdd";
1031                 }
1032
1033                 auth_gen_string = "CdBBAAABd";
1034         }
1035
1036         DEBUG(3, ("NTLMSSP: Set final flags:\n"));
1037         debug_ntlmssp_flags(ntlmssp_state->neg_flags);
1038
1039         if (!msrpc_parse(ntlmssp_state, &reply, chal_parse_string,
1040                          "NTLMSSP",
1041                          &ntlmssp_command,
1042                          &server_domain,
1043                          &chal_flags,
1044                          &challenge_blob, 8,
1045                          &unkn1, &unkn2,
1046                          &struct_blob)) {
1047                 DEBUG(1, ("Failed to parse the NTLMSSP Challenge: (#2)\n"));
1048                 dump_data(2, reply.data, reply.length);
1049                 return NT_STATUS_INVALID_PARAMETER;
1050         }
1051
1052         ntlmssp_state->server_domain = server_domain;
1053
1054         if (challenge_blob.length != 8) {
1055                 data_blob_free(&struct_blob);
1056                 return NT_STATUS_INVALID_PARAMETER;
1057         }
1058
1059         if (!ntlmssp_state->nt_hash || !ntlmssp_state->lm_hash) {
1060                 uchar zeros[16];
1061                 /* do nothing - blobs are zero length */
1062
1063                 ZERO_STRUCT(zeros);
1064
1065                 /* session key is all zeros */
1066                 session_key = data_blob_talloc(ntlmssp_state, zeros, 16);
1067
1068                 /* not doing NLTM2 without a password */
1069                 ntlmssp_state->neg_flags &= ~NTLMSSP_NEGOTIATE_NTLM2;
1070         } else if (ntlmssp_state->use_ntlmv2) {
1071                 if (!struct_blob.length) {
1072                         /* be lazy, match win2k - we can't do NTLMv2 without it */
1073                         DEBUG(1, ("Server did not provide 'target information', required for NTLMv2\n"));
1074                         return NT_STATUS_INVALID_PARAMETER;
1075                 }
1076
1077                 /* TODO: if the remote server is standalone, then we should replace 'domain'
1078                    with the server name as supplied above */
1079
1080                 if (!SMBNTLMv2encrypt_hash(ntlmssp_state,
1081                                            ntlmssp_state->user,
1082                                            ntlmssp_state->domain,
1083                                            ntlmssp_state->nt_hash, &challenge_blob,
1084                                            &struct_blob,
1085                                            &lm_response, &nt_response, NULL,
1086                                            &session_key)) {
1087                         data_blob_free(&challenge_blob);
1088                         data_blob_free(&struct_blob);
1089                         return NT_STATUS_NO_MEMORY;
1090                 }
1091         } else if (ntlmssp_state->neg_flags & NTLMSSP_NEGOTIATE_NTLM2) {
1092                 struct MD5Context md5_session_nonce_ctx;
1093                 uchar session_nonce[16];
1094                 uchar session_nonce_hash[16];
1095                 uchar user_session_key[16];
1096
1097                 lm_response = data_blob_talloc(ntlmssp_state, NULL, 24);
1098                 generate_random_buffer(lm_response.data, 8);
1099                 memset(lm_response.data+8, 0, 16);
1100
1101                 memcpy(session_nonce, challenge_blob.data, 8);
1102                 memcpy(&session_nonce[8], lm_response.data, 8);
1103
1104                 MD5Init(&md5_session_nonce_ctx);
1105                 MD5Update(&md5_session_nonce_ctx, challenge_blob.data, 8);
1106                 MD5Update(&md5_session_nonce_ctx, lm_response.data, 8);
1107                 MD5Final(session_nonce_hash, &md5_session_nonce_ctx);
1108
1109                 DEBUG(5, ("NTLMSSP challenge set by NTLM2\n"));
1110                 DEBUG(5, ("challenge is: \n"));
1111                 dump_data(5, session_nonce_hash, 8);
1112
1113                 nt_response = data_blob_talloc(ntlmssp_state, NULL, 24);
1114                 SMBNTencrypt_hash(ntlmssp_state->nt_hash,
1115                                   session_nonce_hash,
1116                                   nt_response.data);
1117
1118                 session_key = data_blob_talloc(ntlmssp_state, NULL, 16);
1119
1120                 SMBsesskeygen_ntv1(ntlmssp_state->nt_hash, user_session_key);
1121                 hmac_md5(user_session_key, session_nonce, sizeof(session_nonce), session_key.data);
1122                 dump_data_pw("NTLM2 session key:\n", session_key.data, session_key.length);
1123         } else {
1124                 /* lanman auth is insecure, it may be disabled */
1125                 if (lp_client_lanman_auth()) {
1126                         lm_response = data_blob_talloc(ntlmssp_state,
1127                                                        NULL, 24);
1128                         SMBencrypt_hash(ntlmssp_state->lm_hash,challenge_blob.data,
1129                                    lm_response.data);
1130                 }
1131
1132                 nt_response = data_blob_talloc(ntlmssp_state, NULL, 24);
1133                 SMBNTencrypt_hash(ntlmssp_state->nt_hash,challenge_blob.data,
1134                              nt_response.data);
1135
1136                 session_key = data_blob_talloc(ntlmssp_state, NULL, 16);
1137                 if ((ntlmssp_state->neg_flags & NTLMSSP_NEGOTIATE_LM_KEY)
1138                     && lp_client_lanman_auth()) {
1139                         SMBsesskeygen_lm_sess_key(ntlmssp_state->lm_hash, lm_response.data,
1140                                         session_key.data);
1141                         dump_data_pw("LM session key\n", session_key.data, session_key.length);
1142                 } else {
1143                         SMBsesskeygen_ntv1(ntlmssp_state->nt_hash, session_key.data);
1144                         dump_data_pw("NT session key:\n", session_key.data, session_key.length);
1145                 }
1146         }
1147         data_blob_free(&struct_blob);
1148
1149         /* Key exchange encryptes a new client-generated session key with
1150            the password-derived key */
1151         if (ntlmssp_state->neg_flags & NTLMSSP_NEGOTIATE_KEY_EXCH) {
1152                 /* Make up a new session key */
1153                 uint8 client_session_key[16];
1154                 generate_random_buffer(client_session_key, sizeof(client_session_key));
1155
1156                 /* Encrypt the new session key with the old one */
1157                 encrypted_session_key = data_blob(client_session_key, sizeof(client_session_key));
1158                 dump_data_pw("KEY_EXCH session key:\n", encrypted_session_key.data, encrypted_session_key.length);
1159                 arcfour_crypt_blob(encrypted_session_key.data, encrypted_session_key.length, &session_key);
1160                 dump_data_pw("KEY_EXCH session key (enc):\n", encrypted_session_key.data, encrypted_session_key.length);
1161
1162                 /* Mark the new session key as the 'real' session key */
1163                 data_blob_free(&session_key);
1164                 session_key = data_blob_talloc(ntlmssp_state,
1165                                                client_session_key,
1166                                                sizeof(client_session_key));
1167         }
1168
1169         /* this generates the actual auth packet */
1170         if (!msrpc_gen(ntlmssp_state, next_request, auth_gen_string,
1171                        "NTLMSSP",
1172                        NTLMSSP_AUTH,
1173                        lm_response.data, lm_response.length,
1174                        nt_response.data, nt_response.length,
1175                        ntlmssp_state->domain,
1176                        ntlmssp_state->user,
1177                        ntlmssp_state->get_global_myname(),
1178                        encrypted_session_key.data, encrypted_session_key.length,
1179                        ntlmssp_state->neg_flags)) {
1180
1181                 return NT_STATUS_NO_MEMORY;
1182         }
1183
1184         if (DEBUGLEVEL >= 10) {
1185                 if (NT_STATUS_IS_OK(ntlmssp_pull_AUTHENTICATE_MESSAGE(next_request,
1186                                                   ntlmssp_state,
1187                                                   NULL,
1188                                                   &authenticate)))
1189                 {
1190                         NDR_PRINT_DEBUG(AUTHENTICATE_MESSAGE, &authenticate);
1191                 }
1192         }
1193
1194         data_blob_free(&encrypted_session_key);
1195
1196         data_blob_free(&ntlmssp_state->chal);
1197
1198         ntlmssp_state->session_key = session_key;
1199
1200         ntlmssp_state->chal = challenge_blob;
1201         ntlmssp_state->lm_resp = lm_response;
1202         ntlmssp_state->nt_resp = nt_response;
1203
1204         ntlmssp_state->expected_state = NTLMSSP_DONE;
1205
1206         if (!NT_STATUS_IS_OK(nt_status = ntlmssp_sign_init(ntlmssp_state))) {
1207                 DEBUG(1, ("Could not setup NTLMSSP signing/sealing system (error was: %s)\n", nt_errstr(nt_status)));
1208         }
1209
1210         return nt_status;
1211 }
1212
1213 NTSTATUS ntlmssp_client_start(struct ntlmssp_state **ntlmssp_state)
1214 {
1215         *ntlmssp_state = TALLOC_ZERO_P(NULL, struct ntlmssp_state);
1216         if (!*ntlmssp_state) {
1217                 DEBUG(0,("ntlmssp_client_start: talloc failed!\n"));
1218                 talloc_destroy(*ntlmssp_state);
1219                 return NT_STATUS_NO_MEMORY;
1220         }
1221
1222         (*ntlmssp_state)->role = NTLMSSP_CLIENT;
1223
1224         (*ntlmssp_state)->get_global_myname = global_myname;
1225         (*ntlmssp_state)->get_domain = lp_workgroup;
1226
1227         (*ntlmssp_state)->unicode = True;
1228
1229         (*ntlmssp_state)->use_ntlmv2 = lp_client_ntlmv2_auth();
1230
1231         (*ntlmssp_state)->expected_state = NTLMSSP_INITIAL;
1232
1233         (*ntlmssp_state)->neg_flags =
1234                 NTLMSSP_NEGOTIATE_128 |
1235                 NTLMSSP_NEGOTIATE_ALWAYS_SIGN |
1236                 NTLMSSP_NEGOTIATE_NTLM |
1237                 NTLMSSP_NEGOTIATE_NTLM2 |
1238                 NTLMSSP_NEGOTIATE_KEY_EXCH |
1239                 NTLMSSP_REQUEST_TARGET;
1240
1241         return NT_STATUS_OK;
1242 }