@@ -21,27 +21,55 @@ uint32_t gssntlm_cli_auth(uint32_t *minor_status,
2121 struct ntlm_buffer auth_mic = { NULL , 16 };
2222 uint8_t micbuf [16 ];
2323 struct ntlm_buffer mic = { micbuf , 16 };
24+ char * username ;
25+ char * domain ;
26+ bool ext_sec ;
2427 bool add_mic = false;
2528 bool key_exch ;
2629 uint32_t retmaj ;
2730 uint32_t retmin ;
2831
32+ ext_sec = (in_flags & NTLMSSP_NEGOTIATE_EXTENDED_SESSIONSECURITY );
33+
2934 switch (cred -> type ) {
3035
36+ case GSSNTLM_CRED_EXTERNAL :
37+ retmin = external_cli_auth (ctx , cred , in_flags , input_chan_bindings );
38+ if (retmin ) {
39+ set_GSSERR (retmin );
40+ goto done ;
41+ }
42+ set_GSSERRS (0 , GSS_S_COMPLETE );
43+ return GSSERR ();
44+
45+ case GSSNTLM_CRED_ANON :
46+
47+ /* Anonymous auth, empty responses */
48+ if (!(ctx -> gss_flags & GSS_C_ANON_FLAG )) {
49+ set_GSSERR (EINVAL );
50+ goto done ;
51+ }
52+
53+ domain = NULL ;
54+ username = NULL ;
55+ memset (& nt_chal_resp , 0 , sizeof (nt_chal_resp ));
56+ lm_chal_resp .data = malloc (1 );
57+ if (!lm_chal_resp .data ) {
58+ set_GSSERR (ENOMEM );
59+ goto done ;
60+ }
61+ lm_chal_resp .data [0 ] = 0 ;
62+ lm_chal_resp .length = 1 ;
63+
64+ memset (key_exchange_key .data , 0 , 16 );
65+ break ;
66+
3167 case GSSNTLM_CRED_USER :
3268
33- if (ctx -> gss_flags & GSS_C_ANON_FLAG ) {
34- /* Anonymous auth, empty responses */
35- memset (& nt_chal_resp , 0 , sizeof (nt_chal_resp ));
36- lm_chal_resp .data = malloc (1 );
37- if (!lm_chal_resp .data ) {
38- set_GSSERR (ENOMEM );
39- goto done ;
40- }
41- lm_chal_resp .data [0 ] = 0 ;
42- lm_chal_resp .length = 1 ;
69+ domain = cred -> cred .user .user .data .user .domain ;
70+ username = cred -> cred .user .user .data .user .name ;
4371
44- } else if (gssntlm_sec_v2_ok (ctx )) {
72+ if (gssntlm_sec_v2_ok (ctx )) {
4573
4674 /* ### NTLMv2 ### */
4775 uint8_t client_chal [8 ];
@@ -111,9 +139,7 @@ uint32_t gssntlm_cli_auth(uint32_t *minor_status,
111139
112140 /* NTLMv2 Key */
113141 retmin = NTOWFv2 (ctx -> ntlm , & cred -> cred .user .nt_hash ,
114- cred -> cred .user .user .data .user .name ,
115- cred -> cred .user .user .data .user .domain ,
116- & ntlmv2_key );
142+ username , domain , & ntlmv2_key );
117143 if (retmin ) {
118144 set_GSSERR (retmin );
119145 goto done ;
@@ -160,7 +186,6 @@ uint32_t gssntlm_cli_auth(uint32_t *minor_status,
160186 struct ntlm_buffer cli_chal = { client_chal , 8 };
161187 struct ntlm_key session_base_key = { .length = 16 };
162188 bool NoLMResponseNTLMv1 = !gssntlm_sec_lm_ok (ctx );
163- bool ext_sec ;
164189
165190 nt_chal_resp .length = 24 ;
166191 nt_chal_resp .data = calloc (1 , nt_chal_resp .length );
@@ -178,8 +203,6 @@ uint32_t gssntlm_cli_auth(uint32_t *minor_status,
178203 goto done ;
179204 }
180205
181- ext_sec = (in_flags & NTLMSSP_NEGOTIATE_EXTENDED_SESSIONSECURITY );
182-
183206 retmin = ntlm_compute_nt_response (& cred -> cred .user .nt_hash ,
184207 ext_sec , ctx -> server_chal ,
185208 client_chal , & nt_chal_resp );
@@ -219,77 +242,69 @@ uint32_t gssntlm_cli_auth(uint32_t *minor_status,
219242 }
220243 }
221244
222- key_exch = (in_flags & NTLMSSP_NEGOTIATE_KEY_EXCH );
223-
224- retmin = ntlm_exported_session_key (& key_exchange_key , key_exch ,
225- & ctx -> exported_session_key );
226- if (retmin ) {
227- set_GSSERR (retmin );
228- goto done ;
229- }
245+ break ;
230246
231- if (key_exch ) {
232- retmin = ntlm_encrypted_session_key (& key_exchange_key ,
233- & ctx -> exported_session_key ,
234- & encrypted_random_session_key );
235- if (retmin ) {
236- set_GSSERR (retmin );
237- goto done ;
238- }
239- }
247+ default :
248+ set_GSSERR (ERR_NOUSRCRED );
249+ goto done ;
250+ }
240251
241- /* in_flags all verified, assign as current flags */
242- ctx -> neg_flags |= in_flags ;
252+ key_exch = (in_flags & NTLMSSP_NEGOTIATE_KEY_EXCH );
243253
244- enc_sess_key .data = encrypted_random_session_key .data ;
245- enc_sess_key .length = encrypted_random_session_key .length ;
254+ retmin = ntlm_exported_session_key (& key_exchange_key , key_exch ,
255+ & ctx -> exported_session_key );
256+ if (retmin ) {
257+ set_GSSERR (retmin );
258+ goto done ;
259+ }
246260
247- retmin = ntlm_encode_auth_msg (ctx -> ntlm , ctx -> neg_flags ,
248- & lm_chal_resp , & nt_chal_resp ,
249- cred -> cred .user .user .data .user .domain ,
250- cred -> cred .user .user .data .user .name ,
251- ctx -> workstation , & enc_sess_key ,
252- add_mic ? & auth_mic : NULL ,
253- & ctx -> auth_msg );
261+ if (key_exch ) {
262+ retmin = ntlm_encrypted_session_key (& key_exchange_key ,
263+ & ctx -> exported_session_key ,
264+ & encrypted_random_session_key );
254265 if (retmin ) {
255266 set_GSSERR (retmin );
256267 goto done ;
257268 }
269+ }
258270
259- /* Now we need to calculate the MIC, because the MIC is part of the
260- * message it protects, ntlm_encode_auth_msg() always add a zeroeth
261- * buffer, however it returns in data_mic the pointer to the actual
262- * area in the auth_msg that points at the mic, so we can backfill */
263- if (add_mic ) {
264- retmin = ntlm_mic (& ctx -> exported_session_key , & ctx -> nego_msg ,
265- & ctx -> chal_msg , & ctx -> auth_msg , & mic );
266- if (retmin ) {
267- set_GSSERR (retmin );
268- goto done ;
269- }
270- /* now that we have the mic, copy it into the auth message */
271- memcpy (auth_mic .data , mic .data , 16 );
271+ /* in_flags all verified, assign as current flags */
272+ ctx -> neg_flags |= in_flags ;
272273
273- /* Make sure SPNEGO gets to know it has to add mechlistMIC too */
274- ctx -> int_flags |= NTLMSSP_CTX_FLAG_AUTH_WITH_MIC ;
275- }
274+ enc_sess_key .data = encrypted_random_session_key .data ;
275+ enc_sess_key .length = encrypted_random_session_key .length ;
276276
277- set_GSSERRS (0 , GSS_S_COMPLETE );
278- break ;
277+ retmin = ntlm_encode_auth_msg (ctx -> ntlm , ctx -> neg_flags ,
278+ & lm_chal_resp , & nt_chal_resp ,
279+ domain , username ,
280+ ctx -> workstation , & enc_sess_key ,
281+ add_mic ? & auth_mic : NULL ,
282+ & ctx -> auth_msg );
283+ if (retmin ) {
284+ set_GSSERR (retmin );
285+ goto done ;
286+ }
279287
280- case GSSNTLM_CRED_EXTERNAL :
281- retmin = external_cli_auth (ctx , cred , in_flags , input_chan_bindings );
288+ /* Now we need to calculate the MIC, because the MIC is part of the
289+ * message it protects, ntlm_encode_auth_msg() always add a zeroeth
290+ * buffer, however it returns in data_mic the pointer to the actual
291+ * area in the auth_msg that points at the mic, so we can backfill */
292+ if (add_mic ) {
293+ retmin = ntlm_mic (& ctx -> exported_session_key , & ctx -> nego_msg ,
294+ & ctx -> chal_msg , & ctx -> auth_msg , & mic );
282295 if (retmin ) {
283296 set_GSSERR (retmin );
284297 goto done ;
285298 }
286- set_GSSERRS ( 0 , GSS_S_COMPLETE );
287- break ;
299+ /* now that we have the mic, copy it into the auth message */
300+ memcpy ( auth_mic . data , mic . data , 16 ) ;
288301
289- default :
290- set_GSSERR ( ERR_NOUSRCRED ) ;
302+ /* Make sure SPNEGO gets to know it has to add mechlistMIC too */
303+ ctx -> int_flags |= NTLMSSP_CTX_FLAG_AUTH_WITH_MIC ;
291304 }
292305
306+ set_GSSERRS (0 , GSS_S_COMPLETE );
307+
293308done :
294309 ntlm_free_buffer_data (& client_target_info );
295310 ntlm_free_buffer_data (& nt_chal_resp );
0 commit comments