Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(59)

Side by Side Diff: net/http/http_auth_handler_ntlm_portable.cc

Issue 2904043002: Remove insecure code paths in portable NTLM. (Closed)
Patch Set: Created 3 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "net/http/http_auth_handler_ntlm.h" 5 #include "net/http/http_auth_handler_ntlm.h"
6 6
7 #include <stdlib.h> 7 #include <stdlib.h>
8 // For gethostname 8 // For gethostname
9 #if defined(OS_POSIX) 9 #if defined(OS_POSIX)
10 #include <unistd.h> 10 #include <unistd.h>
(...skipping 132 matching lines...) Expand 10 before | Expand all | Expand 10 after
143 143
144 LM_HASH_LEN = 16, 144 LM_HASH_LEN = 16,
145 LM_RESP_LEN = 24, 145 LM_RESP_LEN = 24,
146 146
147 NTLM_HASH_LEN = 16, 147 NTLM_HASH_LEN = 16,
148 NTLM_RESP_LEN = 24 148 NTLM_RESP_LEN = 24
149 }; 149 };
150 150
151 //----------------------------------------------------------------------------- 151 //-----------------------------------------------------------------------------
152 152
153 // The return value of this function controls whether or not the LM hash will
154 // be included in response to a NTLM challenge.
155 //
156 // In Mozilla, this function returns the value of the boolean preference
157 // "network.ntlm.send-lm-response". By default, the preference is disabled
158 // since servers should almost never need the LM hash, and the LM hash is what
159 // makes NTLM authentication less secure. See
160 // https://bugzilla.mozilla.org/show_bug.cgi?id=250691 for further details.
161 //
162 // We just return a hardcoded false.
163 static bool SendLM() {
164 return false;
165 }
166
167 //-----------------------------------------------------------------------------
168
169 #define LogFlags(x) ((void)0) 153 #define LogFlags(x) ((void)0)
170 #define LogBuf(a, b, c) ((void)0) 154 #define LogBuf(a, b, c) ((void)0)
171 #define LogToken(a, b, c) ((void)0) 155 #define LogToken(a, b, c) ((void)0)
172 156
173 //----------------------------------------------------------------------------- 157 //-----------------------------------------------------------------------------
174 158
175 // Byte order swapping. 159 // Byte order swapping.
176 #define SWAP16(x) ((((x)&0xff) << 8) | (((x) >> 8) & 0xff)) 160 #define SWAP16(x) ((((x)&0xff) << 8) | (((x) >> 8) & 0xff))
177 #define SWAP32(x) ((SWAP16((x)&0xffff) << 16) | (SWAP16((x) >> 16))) 161 #define SWAP32(x) ((SWAP16((x)&0xffff) << 16) | (SWAP16((x) >> 16)))
178 162
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after
239 uint32_t x = (static_cast<uint32_t>(buf[0])) | 223 uint32_t x = (static_cast<uint32_t>(buf[0])) |
240 (static_cast<uint32_t>(buf[1]) << 8) | 224 (static_cast<uint32_t>(buf[1]) << 8) |
241 (static_cast<uint32_t>(buf[2]) << 16) | 225 (static_cast<uint32_t>(buf[2]) << 16) |
242 (static_cast<uint32_t>(buf[3]) << 24); 226 (static_cast<uint32_t>(buf[3]) << 24);
243 buf += sizeof(x); 227 buf += sizeof(x);
244 return x; 228 return x;
245 } 229 }
246 230
247 //----------------------------------------------------------------------------- 231 //-----------------------------------------------------------------------------
248 232
249 // LM_Hash computes the LM hash of the given password.
250 //
251 // param password
252 // unicode password.
253 // param hash
254 // 16-byte result buffer
255 //
256 // Note: This function is not being used because our SendLM() function always
257 // returns false.
258 static void LM_Hash(const base::string16& password, uint8_t* hash) {
259 static const uint8_t LM_MAGIC[] = "KGS!@#$%";
260
261 // Convert password to OEM character set. We'll just use the native
262 // filesystem charset.
263 std::string passbuf = base::SysWideToNativeMB(base::UTF16ToWide(password));
264 passbuf = base::ToUpperASCII(passbuf);
265 passbuf.resize(14, '\0');
266
267 uint8_t k1[8], k2[8];
268 DESMakeKey(reinterpret_cast<const uint8_t*>(passbuf.data()), k1);
269 DESMakeKey(reinterpret_cast<const uint8_t*>(passbuf.data()) + 7, k2);
270 ZapString(&passbuf);
271
272 // Use password keys to hash LM magic string twice.
273 DESEncrypt(k1, LM_MAGIC, hash);
274 DESEncrypt(k2, LM_MAGIC, hash + 8);
275 }
276
277 // NTLM_Hash computes the NTLM hash of the given password. 233 // NTLM_Hash computes the NTLM hash of the given password.
278 // 234 //
279 // param password 235 // param password
280 // null-terminated unicode password. 236 // null-terminated unicode password.
281 // param hash 237 // param hash
282 // 16-byte result buffer 238 // 16-byte result buffer
283 static void NTLM_Hash(const base::string16& password, uint8_t* hash) { 239 static void NTLM_Hash(const base::string16& password, uint8_t* hash) {
284 #ifdef IS_BIG_ENDIAN 240 #ifdef IS_BIG_ENDIAN
285 uint32_t len = password.length(); 241 uint32_t len = password.length();
286 uint8_t* passbuf; 242 uint8_t* passbuf;
(...skipping 253 matching lines...) Expand 10 before | Expand all | Expand 10 after
540 *out_buf = malloc(*out_len); 496 *out_buf = malloc(*out_len);
541 if (!*out_buf) 497 if (!*out_buf)
542 return ERR_OUT_OF_MEMORY; 498 return ERR_OUT_OF_MEMORY;
543 499
544 // 500 //
545 // Next, we compute the LM and NTLM responses. 501 // Next, we compute the LM and NTLM responses.
546 // 502 //
547 uint8_t lm_resp[LM_RESP_LEN]; 503 uint8_t lm_resp[LM_RESP_LEN];
548 uint8_t ntlm_resp[NTLM_RESP_LEN]; 504 uint8_t ntlm_resp[NTLM_RESP_LEN];
549 uint8_t ntlm_hash[NTLM_HASH_LEN]; 505 uint8_t ntlm_hash[NTLM_HASH_LEN];
550 if (msg.flags & NTLM_NegotiateNTLM2Key) {
551 // compute NTLM2 session response
552 base::MD5Digest session_hash;
553 uint8_t temp[16];
554 506
555 memcpy(lm_resp, rand_8_bytes, 8); 507 // compute NTLM2 session response
556 memset(lm_resp + 8, 0, LM_RESP_LEN - 8); 508 base::MD5Digest session_hash;
509 uint8_t temp[16];
557 510
558 memcpy(temp, msg.challenge, 8); 511 memcpy(lm_resp, rand_8_bytes, 8);
559 memcpy(temp + 8, lm_resp, 8); 512 memset(lm_resp + 8, 0, LM_RESP_LEN - 8);
560 base::MD5Sum(temp, 16, &session_hash);
561 513
562 NTLM_Hash(password, ntlm_hash); 514 memcpy(temp, msg.challenge, 8);
563 LM_Response(ntlm_hash, session_hash.a, ntlm_resp); 515 memcpy(temp + 8, lm_resp, 8);
564 } else { 516 base::MD5Sum(temp, 16, &session_hash);
565 NTLM_Hash(password, ntlm_hash);
566 LM_Response(ntlm_hash, msg.challenge, ntlm_resp);
567 517
568 if (SendLM()) { 518 NTLM_Hash(password, ntlm_hash);
569 uint8_t lm_hash[LM_HASH_LEN]; 519 LM_Response(ntlm_hash, session_hash.a, ntlm_resp);
570 LM_Hash(password, lm_hash);
571 LM_Response(lm_hash, msg.challenge, lm_resp);
572 } else {
573 // According to http://davenport.sourceforge.net/ntlm.html#ntlmVersion2,
574 // the correct way to not send the LM hash is to send the NTLM hash twice
575 // in both the LM and NTLM response fields.
576 LM_Response(ntlm_hash, msg.challenge, lm_resp);
577 }
578 }
579 520
580 // 521 //
581 // Finally, we assemble the Type-3 msg :-) 522 // Finally, we assemble the Type-3 msg :-)
582 // 523 //
583 void* cursor = *out_buf; 524 void* cursor = *out_buf;
584 uint32_t offset; 525 uint32_t offset;
585 526
586 // 0 : signature 527 // 0 : signature
587 cursor = WriteBytes(cursor, NTLM_SIGNATURE, sizeof(NTLM_SIGNATURE)); 528 cursor = WriteBytes(cursor, NTLM_SIGNATURE, sizeof(NTLM_SIGNATURE));
588 529
(...skipping 132 matching lines...) Expand 10 before | Expand all | Expand 10 after
721 // of NTLM. 662 // of NTLM.
722 std::unique_ptr<HttpAuthHandler> tmp_handler(new HttpAuthHandlerNTLM); 663 std::unique_ptr<HttpAuthHandler> tmp_handler(new HttpAuthHandlerNTLM);
723 if (!tmp_handler->InitFromChallenge(challenge, target, ssl_info, origin, 664 if (!tmp_handler->InitFromChallenge(challenge, target, ssl_info, origin,
724 net_log)) 665 net_log))
725 return ERR_INVALID_RESPONSE; 666 return ERR_INVALID_RESPONSE;
726 handler->swap(tmp_handler); 667 handler->swap(tmp_handler);
727 return OK; 668 return OK;
728 } 669 }
729 670
730 } // namespace net 671 } // namespace net
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698