Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

832 lines
23 KiB

  1. /*++
  2. Copyright (c) 1998 Microsoft Corporation
  3. Module Name:
  4. cred.cxx
  5. Abstract:
  6. Shared memory data structures for digest sspi package.
  7. Author:
  8. Adriaan Canter (adriaanc) 01-Aug-1998
  9. --*/
  10. #include "include.hxx"
  11. //////////////////////////////////////////////////////////////////////
  12. //
  13. // CEntry Functions
  14. //
  15. //////////////////////////////////////////////////////////////////////
  16. //--------------------------------------------------------------------
  17. // CEntry::Free
  18. // BUGBUG - inline this.
  19. //--------------------------------------------------------------------
  20. DWORD CEntry::Free(CMMFile *pMMFile, CEntry *pEntry)
  21. {
  22. BOOL bFree = pMMFile->FreeEntry(pEntry);
  23. return (bFree ? ERROR_SUCCESS : ERROR_INTERNAL_ERROR);
  24. }
  25. //--------------------------------------------------------------------
  26. // CEntry::GetNext
  27. //--------------------------------------------------------------------
  28. CEntry* CEntry::GetNext(CEntry *pEntry)
  29. {
  30. if (pEntry->dwNext)
  31. return (CEntry*) OFFSET_TO_POINTER(g_pHeap, pEntry->dwNext);
  32. return NULL;
  33. }
  34. //--------------------------------------------------------------------
  35. // CEntry::GetPrev
  36. //--------------------------------------------------------------------
  37. CEntry* CEntry::GetPrev(CEntry *pEntry)
  38. {
  39. if (pEntry->dwPrev)
  40. return (CEntry*) OFFSET_TO_POINTER(g_pHeap, pEntry->dwPrev);
  41. return NULL;
  42. }
  43. //////////////////////////////////////////////////////////////////////
  44. //
  45. // CSess Functions
  46. //
  47. //////////////////////////////////////////////////////////////////////
  48. //--------------------------------------------------------------------
  49. // CSess::Create
  50. //--------------------------------------------------------------------
  51. CSess* CSess::Create(CMMFile *pMMFile,
  52. LPSTR szAppCtx, LPSTR szUserCtx, BOOL fHTTP)
  53. {
  54. DIGEST_ASSERT(pMMFile);
  55. // Unaligned Sess lengths.
  56. DWORD cbAppCtx = szAppCtx ? strlen(szAppCtx) + 1 : 0;
  57. DWORD cbUserCtx = szUserCtx ? strlen(szUserCtx) + 1 : 0;
  58. // Aligned Sess lengths.
  59. DWORD cbStructAligned = ROUNDUPDWORD(sizeof(CSess));
  60. DWORD cbAppCtxAligned = ROUNDUPDWORD(cbAppCtx);
  61. DWORD cbUserCtxAligned = ROUNDUPDWORD(cbUserCtx);
  62. // Total number of required bytes (aligned).
  63. DWORD cbEntryAligned = cbStructAligned
  64. + cbAppCtxAligned + cbUserCtxAligned;
  65. // Allocate from mem map.
  66. CSess *pSess = (CSess*) pMMFile->AllocateEntry(cbEntryAligned);
  67. if (!pSess)
  68. {
  69. DIGEST_ASSERT(FALSE);
  70. goto exit;
  71. }
  72. DWORD cbCurrentOffset;
  73. cbCurrentOffset = cbStructAligned;
  74. pSess->dwAppCtx = pSess->dwUserCtx = 0;
  75. // AppCtx
  76. if (szAppCtx)
  77. {
  78. memcpy(OFFSET_TO_POINTER(pSess, cbCurrentOffset), szAppCtx, cbAppCtx);
  79. pSess->dwAppCtx = cbCurrentOffset;
  80. cbCurrentOffset += cbAppCtxAligned;
  81. }
  82. // UserCtx
  83. if (szUserCtx)
  84. {
  85. memcpy(OFFSET_TO_POINTER(pSess, cbCurrentOffset), szUserCtx, cbUserCtx);
  86. pSess->dwUserCtx = cbCurrentOffset;
  87. }
  88. // No need to advance cbCurrentOffset.
  89. pSess->cbSess = cbEntryAligned;
  90. pSess->dwCred = 0;
  91. pSess->dwSig = SIG_SESS;
  92. pSess->fHTTP = fHTTP;
  93. pSess->dwPrev = 0;
  94. pSess->dwNext = 0;
  95. exit:
  96. return pSess;
  97. }
  98. //--------------------------------------------------------------------
  99. // CSess::GetAppCtx
  100. //--------------------------------------------------------------------
  101. LPSTR CSess::GetAppCtx(CSess *pSess)
  102. {
  103. if (pSess->dwAppCtx)
  104. return (LPSTR) OFFSET_TO_POINTER(pSess, pSess->dwAppCtx);
  105. else
  106. return NULL;
  107. }
  108. //--------------------------------------------------------------------
  109. // CSess::GetUserCtx
  110. //--------------------------------------------------------------------
  111. LPSTR CSess::GetUserCtx(CSess *pSess)
  112. {
  113. if (pSess->dwUserCtx)
  114. return (LPSTR) OFFSET_TO_POINTER(pSess, pSess->dwUserCtx);
  115. else
  116. return NULL;
  117. }
  118. //--------------------------------------------------------------------
  119. // CSess::GetCtx
  120. // Allocates a context string in local heap.
  121. //--------------------------------------------------------------------
  122. LPSTR CSess::GetCtx(CSess *pSess)
  123. {
  124. DIGEST_ASSERT(pSess);
  125. LPSTR szAppCtx, szUserCtx, szCtx;
  126. DWORD cbAppCtx, cbUserCtx, cbCtx;
  127. szAppCtx = GetAppCtx(pSess);
  128. szUserCtx = GetUserCtx(pSess);
  129. cbAppCtx = szAppCtx ? strlen(szAppCtx) : 0;
  130. cbUserCtx = szUserCtx ? strlen(szUserCtx) : 0;
  131. cbCtx = cbAppCtx + sizeof(':') + cbUserCtx + sizeof('\0');
  132. szCtx = new CHAR[cbCtx];
  133. if (!szCtx)
  134. {
  135. DIGEST_ASSERT(FALSE);
  136. return NULL;
  137. }
  138. // "appctx:userctx\0"
  139. // bugbug - macro for sizeof -1
  140. memcpy(szCtx, szAppCtx, cbAppCtx);
  141. memcpy(szCtx + cbAppCtx, ":", sizeof(":") - 1);
  142. memcpy(szCtx + cbAppCtx + sizeof(":") - 1, szUserCtx, cbUserCtx);
  143. memcpy(szCtx + cbAppCtx + sizeof(":") - 1 + cbUserCtx, "\0", sizeof("\0") - 1);
  144. return szCtx;
  145. }
  146. //--------------------------------------------------------------------
  147. // CSess::CtxMatch
  148. //--------------------------------------------------------------------
  149. BOOL CSess::CtxMatch(CSess *pSess1, CSess *pSess2)
  150. {
  151. DIGEST_ASSERT(pSess1 && pSess2);
  152. LPSTR szAppCtx1, szAppCtx2, szUserCtx1, szUserCtx2;
  153. szAppCtx1 = CSess::GetAppCtx(pSess1);
  154. szAppCtx2 = CSess::GetAppCtx(pSess2);
  155. szUserCtx1 = CSess::GetUserCtx(pSess1);
  156. szUserCtx2 = CSess::GetUserCtx(pSess2);
  157. // If both AppCtx values are NULL or
  158. // are equal to same string.
  159. if ((!szAppCtx1 && !szAppCtx2)
  160. || ((szAppCtx1 && szAppCtx2)
  161. && !strcmp(szAppCtx1, szAppCtx2)))
  162. {
  163. // And both UserCtx values are NULL or
  164. // are equal to same string.
  165. if ((!szUserCtx1 && !szUserCtx2)
  166. || ((szUserCtx1 && szUserCtx2)
  167. && !strcmp(szUserCtx1, szUserCtx2)))
  168. {
  169. // Credentials are shareable.
  170. return TRUE;
  171. }
  172. }
  173. // Otherwise creds are not shareable.
  174. return FALSE;
  175. }
  176. //--------------------------------------------------------------------
  177. // CSess::GetCred
  178. //--------------------------------------------------------------------
  179. CCred *CSess::GetCred(CSess* pSess)
  180. {
  181. if (!pSess->dwCred)
  182. return NULL;
  183. return (CCred*) OFFSET_TO_POINTER(g_pHeap, pSess->dwCred);
  184. }
  185. //--------------------------------------------------------------------
  186. // CSess::SetCred
  187. //--------------------------------------------------------------------
  188. CCred *CSess::SetCred(CSess* pSess, CCred* pCred)
  189. {
  190. if (!pCred)
  191. pSess->dwCred = 0;
  192. else
  193. pSess->dwCred = POINTER_TO_OFFSET(g_pHeap, pCred);
  194. return pCred;
  195. }
  196. //////////////////////////////////////////////////////////////////////
  197. //
  198. // CList Functions
  199. //
  200. //////////////////////////////////////////////////////////////////////
  201. //--------------------------------------------------------------------
  202. // CList::CList
  203. //--------------------------------------------------------------------
  204. CList::CList()
  205. {
  206. _pHead = NULL;
  207. _pCur = NULL;
  208. _pdwOffset = NULL;
  209. }
  210. //--------------------------------------------------------------------
  211. // CList::Init
  212. //--------------------------------------------------------------------
  213. CEntry* CList::Init(LPDWORD pdwOffset)
  214. {
  215. DIGEST_ASSERT(pdwOffset)
  216. _pdwOffset = pdwOffset;
  217. if (*pdwOffset)
  218. {
  219. _pHead = (CEntry*) OFFSET_TO_POINTER(g_pHeap, *pdwOffset);
  220. _pCur = _pHead;
  221. }
  222. return _pHead;
  223. }
  224. //--------------------------------------------------------------------
  225. // CList::Seek
  226. //--------------------------------------------------------------------
  227. CEntry* CList::Seek()
  228. {
  229. // DIGEST_ASSERT(_pHead);
  230. _pHead = (CEntry*) OFFSET_TO_POINTER(g_pHeap, *_pdwOffset);
  231. _pCur = _pHead;
  232. return _pCur;
  233. }
  234. //--------------------------------------------------------------------
  235. // CList::GetNext
  236. //--------------------------------------------------------------------
  237. CEntry* CList::GetNext()
  238. {
  239. if (! *_pdwOffset)
  240. return NULL;
  241. CEntry *pEntry = _pCur;
  242. if (_pCur)
  243. _pCur = _pCur->dwNext ?
  244. (CEntry*) OFFSET_TO_POINTER(g_pHeap, _pCur->dwNext) : NULL;
  245. return pEntry;
  246. }
  247. //--------------------------------------------------------------------
  248. // CList::GetPrev
  249. //--------------------------------------------------------------------
  250. CEntry* CList::GetPrev()
  251. {
  252. if (! *_pdwOffset)
  253. return NULL;
  254. CEntry *pEntry = _pCur;
  255. if (_pCur)
  256. _pCur = _pCur->dwPrev ?
  257. (CEntry*) OFFSET_TO_POINTER(g_pHeap, _pCur->dwPrev) : NULL;
  258. return pEntry;
  259. }
  260. //--------------------------------------------------------------------
  261. // CList::Insert
  262. //--------------------------------------------------------------------
  263. CEntry* CList::Insert(CEntry *pEntry)
  264. {
  265. // BUGBUG - assert pnext pprev are null
  266. DIGEST_ASSERT(pEntry
  267. && (pEntry->dwPrev == pEntry->dwNext == 0));
  268. if (!_pHead)
  269. {
  270. _pHead = pEntry;
  271. }
  272. else
  273. {
  274. pEntry->dwNext = POINTER_TO_OFFSET(g_pHeap, _pHead);
  275. _pHead->dwPrev = POINTER_TO_OFFSET(g_pHeap, pEntry);
  276. _pHead = pEntry;
  277. }
  278. *_pdwOffset = POINTER_TO_OFFSET(g_pHeap, pEntry);
  279. return pEntry;
  280. }
  281. //--------------------------------------------------------------------
  282. // CList::DeLink
  283. //--------------------------------------------------------------------
  284. CEntry* CList::DeLink(CEntry *pEntry)
  285. {
  286. DIGEST_ASSERT(pEntry);
  287. if (pEntry == _pHead)
  288. {
  289. _pHead = (CEntry*) OFFSET_TO_POINTER(g_pHeap, pEntry->dwNext);
  290. *_pdwOffset = POINTER_TO_OFFSET(g_pHeap, _pHead);
  291. }
  292. else
  293. {
  294. CEntry *pPrev;
  295. pPrev = (CEntry*) OFFSET_TO_POINTER(g_pHeap, pEntry->dwPrev);
  296. pPrev->dwNext = pEntry->dwNext;
  297. }
  298. if (pEntry->dwNext)
  299. {
  300. CEntry *pNext;
  301. pNext = (CEntry*) OFFSET_TO_POINTER(g_pHeap, pEntry->dwNext);
  302. pNext->dwPrev = pEntry->dwPrev;
  303. }
  304. if (_pCur == pEntry)
  305. {
  306. _pCur = (CEntry*) OFFSET_TO_POINTER(g_pHeap, pEntry->dwNext);
  307. }
  308. return pEntry;
  309. }
  310. //////////////////////////////////////////////////////////////////////
  311. //
  312. // CCred Functions
  313. //
  314. //////////////////////////////////////////////////////////////////////
  315. //--------------------------------------------------------------------
  316. // CCred::Create
  317. //--------------------------------------------------------------------
  318. CCred* CCred::Create(CMMFile *pMMFile,
  319. LPSTR szHost, LPSTR szRealm, LPSTR szUser,
  320. LPSTR szPass, LPSTR szNonce, LPSTR szCNonce)
  321. {
  322. // BUGBUG - assert strings non-null. Nonce can be NULL.
  323. DIGEST_ASSERT(pMMFile && szRealm && szUser && szPass);
  324. CSecureStr EncryptedPassword;
  325. if (szPass && !EncryptedPassword.SetData(szPass))
  326. return NULL;
  327. // Unaligned string sizes.
  328. DWORD cbRealm = szRealm ? strlen(szRealm) + 1 : 0;
  329. DWORD cbUser = szUser ? strlen(szUser) + 1 : 0;
  330. DWORD cbPass = szPass ? EncryptedPassword.GetStrLen() : 0;
  331. // Aligned string sizes.
  332. DWORD cbStructAligned = ROUNDUPDWORD(sizeof(CCred));
  333. DWORD cbRealmAligned = ROUNDUPDWORD(cbRealm);
  334. DWORD cbUserAligned = ROUNDUPDWORD(cbUser);
  335. DWORD cbPassAligned = ROUNDUPDWORD(cbPass);
  336. // Total number of required bytes (aligned).
  337. DWORD cbEntryAligned = cbStructAligned
  338. + cbRealmAligned
  339. + cbUserAligned
  340. + cbPassAligned;
  341. // Allocate cred and nonce from memmap
  342. // BUGBUG - MASKING PNONCE
  343. // BUGBUG - no, I'm not.
  344. CCred *pCred;
  345. CNonce *pNonce, *pCNonce;
  346. pNonce = pCNonce = NULL;
  347. // Allocate a credential.
  348. pCred = (CCred*) pMMFile->AllocateEntry(cbEntryAligned);
  349. if (!pCred)
  350. {
  351. DIGEST_ASSERT(FALSE);
  352. goto exit;
  353. }
  354. DWORD cbCurrentOffset;
  355. cbCurrentOffset = cbStructAligned;
  356. // Realm.
  357. memcpy(OFFSET_TO_POINTER(pCred, cbCurrentOffset), szRealm, cbRealm);
  358. pCred->dwRealm = cbCurrentOffset;
  359. cbCurrentOffset += cbRealmAligned;
  360. // User
  361. memcpy(OFFSET_TO_POINTER(pCred, cbCurrentOffset), szUser, cbUser);
  362. pCred->dwUser = cbCurrentOffset;
  363. cbCurrentOffset += cbUserAligned;
  364. // Pass
  365. memcpy(OFFSET_TO_POINTER(pCred, cbCurrentOffset), EncryptedPassword.GetPtr(), cbPass);
  366. pCred->dwPass = cbCurrentOffset;
  367. pCred->cbPass = cbPass;
  368. pCred->cbCred = cbEntryAligned;
  369. pCred->tStamp = GetTickCount();
  370. pCred->dwSig = SIG_CRED;
  371. pCred->dwPrev = NULL;
  372. pCred->dwNext = NULL;
  373. pCred->dwNonce = 0;
  374. pCred->dwCNonce = 0;
  375. // Allocate nonce and client nonce if specified.
  376. if (szNonce)
  377. CCred::SetNonce(pMMFile, pCred, szHost, szNonce, SERVER_NONCE);
  378. if (szCNonce)
  379. CCred::SetNonce(pMMFile, pCred, szHost, szCNonce, CLIENT_NONCE);
  380. exit:
  381. return pCred;
  382. }
  383. //--------------------------------------------------------------------
  384. // CCred::GetRealm
  385. //--------------------------------------------------------------------
  386. LPSTR CCred::GetRealm(CCred* pCred)
  387. {
  388. DIGEST_ASSERT(pCred);
  389. if (pCred->dwRealm)
  390. return (LPSTR) OFFSET_TO_POINTER(pCred, pCred->dwRealm);
  391. else
  392. return NULL;
  393. }
  394. //--------------------------------------------------------------------
  395. // CCred::GetUser
  396. //--------------------------------------------------------------------
  397. LPSTR CCred::GetUser(CCred* pCred)
  398. {
  399. DIGEST_ASSERT(pCred);
  400. if (pCred->dwUser)
  401. return (LPSTR) OFFSET_TO_POINTER(pCred, pCred->dwUser);
  402. else
  403. return NULL;
  404. }
  405. //--------------------------------------------------------------------
  406. // CCred::GetPass
  407. //--------------------------------------------------------------------
  408. LPSTR CCred::GetPass(CCred* pCred)
  409. {
  410. DIGEST_ASSERT(pCred);
  411. if (pCred->dwPass)
  412. {
  413. CSecureStr EncryptedPassword(
  414. (LPSTR) OFFSET_TO_POINTER(pCred, pCred->dwPass),
  415. pCred->cbPass,
  416. false);
  417. return EncryptedPassword.GetUnencryptedString();
  418. }
  419. else
  420. return NULL;
  421. }
  422. //--------------------------------------------------------------------
  423. // CCred::SetNonce
  424. //--------------------------------------------------------------------
  425. VOID CCred::SetNonce(CMMFile *pMMFile, CCred* pCred,
  426. LPSTR szHost, LPSTR szNonce, DWORD dwType)
  427. {
  428. DIGEST_ASSERT(pCred && szNonce);
  429. // First determine if a nonce for the specified host
  430. // already exists and delete it if it does.
  431. CList NonceList;
  432. NonceList.Init(dwType == SERVER_NONCE ?
  433. &pCred->dwNonce : &pCred->dwCNonce);
  434. CNonce *pNonce;
  435. while (pNonce = (CNonce*) NonceList.GetNext())
  436. {
  437. if (CNonce::IsHostMatch(pNonce, szHost))
  438. {
  439. NonceList.DeLink(pNonce);
  440. CEntry::Free(pMMFile, pNonce);
  441. break;
  442. }
  443. }
  444. // Create a CNonce object and insert it into the list.
  445. pNonce = CNonce::Create(pMMFile, szHost, szNonce);
  446. if (pNonce)
  447. {
  448. NonceList.Seek();
  449. NonceList.Insert(pNonce);
  450. }
  451. else
  452. {
  453. DIGEST_ASSERT(FALSE);
  454. }
  455. }
  456. //--------------------------------------------------------------------
  457. // CCred::GetNonce
  458. //--------------------------------------------------------------------
  459. CNonce *CCred::GetNonce(CCred* pCred, LPSTR szHost, DWORD dwType)
  460. {
  461. CNonce *pNonce;
  462. CList NonceList;
  463. NonceList.Init(dwType == SERVER_NONCE ?
  464. &pCred->dwNonce : &pCred->dwCNonce);
  465. while (pNonce = (CNonce*) NonceList.GetNext())
  466. {
  467. if (CNonce::IsHostMatch(pNonce, szHost))
  468. break;
  469. }
  470. return pNonce;
  471. }
  472. //--------------------------------------------------------------------
  473. // CCred::Free
  474. //--------------------------------------------------------------------
  475. VOID CCred::Free(CMMFile *pMMFile, CSess *pSess, CCred *pCred)
  476. {
  477. CNonce *pNonce;
  478. CList NonceList;
  479. // Free up server nonce.
  480. NonceList.Init(&pCred->dwNonce);
  481. while (pNonce = (CNonce*) NonceList.GetNext())
  482. {
  483. NonceList.DeLink(pNonce);
  484. CEntry::Free(pMMFile, pNonce);
  485. }
  486. // Free up client nonce.
  487. NonceList.Init(&pCred->dwCNonce);
  488. while (pNonce = (CNonce*) NonceList.GetNext())
  489. {
  490. NonceList.DeLink(pNonce);
  491. CEntry::Free(pMMFile, pNonce);
  492. }
  493. // Remove credential from session's list.
  494. CList CredList;
  495. CredList.Init(&pSess->dwCred);
  496. CredList.DeLink(pCred);
  497. CEntry::Free(pMMFile, pCred);
  498. }
  499. //////////////////////////////////////////////////////////////////////
  500. //
  501. // CNonce Functions
  502. //
  503. //////////////////////////////////////////////////////////////////////
  504. //--------------------------------------------------------------------
  505. // CNonce::Create
  506. //--------------------------------------------------------------------
  507. CNonce* CNonce::Create(CMMFile *pMMFile, LPSTR szHost, LPSTR szNonce)
  508. {
  509. DIGEST_ASSERT(pMMFile && szNonce);
  510. // Unaligned string sizes.
  511. DWORD cbNonce = szNonce ? strlen(szNonce) + 1 : 0;
  512. DWORD cbHost = szHost ? strlen(szHost) + 1 : 0;
  513. // Aligned string sizes.
  514. DWORD cbStructAligned = ROUNDUPDWORD(sizeof(CNonce));
  515. DWORD cbNonceAligned = ROUNDUPDWORD(cbNonce);
  516. DWORD cbHostAligned = ROUNDUPDWORD(cbHost);
  517. // Total number of required bytes (aligned).
  518. DWORD cbEntryAligned = cbStructAligned
  519. + cbHostAligned
  520. + cbNonceAligned;
  521. // Allocate from mem map.
  522. CNonce *pNonce = (CNonce*) pMMFile->AllocateEntry(cbEntryAligned);
  523. // Failed to allocate.
  524. if (!pNonce)
  525. {
  526. DIGEST_ASSERT(FALSE);
  527. goto exit;
  528. }
  529. DWORD cbCurrentOffset;
  530. cbCurrentOffset = cbStructAligned;
  531. // Host.
  532. if (szHost)
  533. {
  534. memcpy(OFFSET_TO_POINTER(pNonce, cbCurrentOffset), szHost, cbHost);
  535. pNonce->dwHost = cbCurrentOffset;
  536. cbCurrentOffset += cbHostAligned;
  537. }
  538. else
  539. {
  540. pNonce->dwHost = 0;
  541. }
  542. // Nonce.
  543. memcpy(OFFSET_TO_POINTER(pNonce, cbCurrentOffset), szNonce, cbNonce);
  544. pNonce->dwNonce = cbCurrentOffset;
  545. cbCurrentOffset += cbNonceAligned;
  546. pNonce->cbNonce = cbEntryAligned;
  547. pNonce->cCount = 0;
  548. pNonce->dwSig = SIG_NONC;
  549. pNonce->dwPrev = 0;
  550. pNonce->dwNext = 0;
  551. exit:
  552. return pNonce;
  553. }
  554. //--------------------------------------------------------------------
  555. // CNonce::GetNonce
  556. //--------------------------------------------------------------------
  557. LPSTR CNonce::GetNonce(CNonce* pNonce)
  558. {
  559. if (pNonce && pNonce->dwNonce)
  560. return (LPSTR) OFFSET_TO_POINTER(pNonce, pNonce->dwNonce);
  561. else
  562. return NULL;
  563. }
  564. //--------------------------------------------------------------------
  565. // CNonce::GetCount
  566. // bugbug - what if no nonce?
  567. //--------------------------------------------------------------------
  568. DWORD CNonce::GetCount(CNonce* pNonce)
  569. {
  570. DIGEST_ASSERT(pNonce);
  571. return pNonce->cCount;
  572. }
  573. //--------------------------------------------------------------------
  574. // CNonce::IsHostMatch
  575. //--------------------------------------------------------------------
  576. BOOL CNonce::IsHostMatch(CNonce *pNonce, LPSTR szHost)
  577. {
  578. if (szHost)
  579. {
  580. if (pNonce->dwHost
  581. && !strcmp(szHost, (LPSTR) OFFSET_TO_POINTER(pNonce, pNonce->dwHost)))
  582. return TRUE;
  583. return FALSE;
  584. }
  585. if (!pNonce->dwHost)
  586. return TRUE;
  587. return FALSE;
  588. }
  589. //////////////////////////////////////////////////////////////////////
  590. //
  591. // CCredInfo Functions
  592. //
  593. //////////////////////////////////////////////////////////////////////
  594. //--------------------------------------------------------------------
  595. // CCredInfo::CCredInfo
  596. //--------------------------------------------------------------------
  597. CCredInfo::CCredInfo(CCred* pCred, LPSTR szHost)
  598. {
  599. DIGEST_ASSERT(pCred
  600. && (pCred->dwPass > pCred->dwUser)
  601. && (pCred->dwUser > pCred->dwRealm));
  602. CCredInfo::szHost = NewString(szHost);
  603. szRealm = NewString(CCred::GetRealm(pCred));
  604. szUser = NewString(CCred::GetUser(pCred));
  605. LPSTR szPass = CCred::GetPass(pCred);
  606. if (szPass)
  607. {
  608. BOOL fSetDataSuccess = Password.SetData(szPass);
  609. SecureZeroMemory(szPass, strlen(szPass));
  610. delete [] szPass;
  611. if (!fSetDataSuccess)
  612. {
  613. dwStatus = ERROR_NOT_ENOUGH_MEMORY;
  614. return;
  615. }
  616. }
  617. // Get server nonce. This is always required.
  618. // BUGBUG - what about pre-loading?
  619. CNonce *pNonce;
  620. pNonce = CCred::GetNonce(pCred, szHost, SERVER_NONCE);
  621. if (!pNonce)
  622. {
  623. dwStatus = ERROR_INVALID_PARAMETER;
  624. return;
  625. }
  626. szNonce = NewString(CNonce::GetNonce(pNonce));
  627. cCount = pNonce->cCount;
  628. pNonce = CCred::GetNonce(pCred, szHost, CLIENT_NONCE);
  629. if (pNonce)
  630. szCNonce = NewString(CNonce::GetNonce(pNonce));
  631. else
  632. szCNonce = NULL;
  633. tStamp = pCred->tStamp;
  634. pPrev = NULL;
  635. pNext = NULL;
  636. dwStatus = ERROR_SUCCESS;
  637. }
  638. //--------------------------------------------------------------------
  639. // CCredInfo::CCredInfo
  640. // BUGBUG - special casing for NULLs, especially szNonce.
  641. //--------------------------------------------------------------------
  642. CCredInfo::CCredInfo(LPSTR szHost, LPSTR szRealm, LPSTR szUser,
  643. LPSTR szPass, LPSTR szNonce, LPSTR szCNonce)
  644. {
  645. CCredInfo::szHost = NewString(szHost);
  646. CCredInfo::szRealm = NewString(szRealm);
  647. CCredInfo::szUser = NewString(szUser);
  648. CCredInfo::Password.SetData(szPass);
  649. CCredInfo::szNonce = NewString(szNonce);
  650. CCredInfo::szCNonce = NewString(szCNonce);
  651. cCount = 0;
  652. tStamp = 0;
  653. pPrev = NULL;
  654. pNext = NULL;
  655. dwStatus = ERROR_SUCCESS;
  656. }
  657. //--------------------------------------------------------------------
  658. // CCredInfo::~CCredInfo
  659. //--------------------------------------------------------------------
  660. CCredInfo::~CCredInfo()
  661. {
  662. if (szHost)
  663. delete [] szHost;
  664. if (szRealm)
  665. delete [] szRealm;
  666. if (szUser)
  667. delete [] szUser;
  668. Password.Free();
  669. if (szNonce)
  670. delete [] szNonce;
  671. if (szCNonce)
  672. delete [] szCNonce;
  673. }