📄 digestauth.cpp
字号:
if (pAuthBuf && !strncasecmp((char*)pAuthBuf->GetBuffer(), "Digest", 6)) { HX_RELEASE(m_pCredentials); HX_RELEASE(m_pPrincipalID); ParseCredentials(pAuthBuf, &m_pCredentials); m_pCredentials->GetPropertyCString("username", m_pPrincipalID); HX_RESULT Ret = HXR_OK; if (m_pAuthDBAccess) { Ret = m_pAuthDBAccess->GetCredentials(this, m_pPrincipalID); // Flow continues in GetCredentialsDone() } HX_RELEASE(pAuthBuf); return Ret; } else { // no Authorization header yet, we have to challenge for it HX_RELEASE(pAuthBuf); // just in case return SendChallengeResponse(); }}STDMETHODIMP CDigestAuthenticator::GetUserContext(REF(IUnknown*) pIUnknownUser){ pIUnknownUser = (IUnknown*)(IHXPlugin*)this; pIUnknownUser->AddRef(); return HXR_OK;}STDMETHODIMP_(BOOL) CDigestAuthenticator::IsAuthenticated(){ return m_bAuthenticated;}// IHXAuthenticationDBAccessResponseSTDMETHODIMP CDigestAuthenticator::ExistenceCheckDone(HX_RESULT hr, IHXBuffer* pBufPrincipalID){ return HXR_NOTIMPL;}STDMETHODIMP CDigestAuthenticator::GetCredentialsDone(HX_RESULT hr, IHXBuffer* pBufferPrincipalID,IHXBuffer* pBufferCredentials){ m_bAuthenticated = FALSE; // till we know better if (SUCCEEDED(hr) && pBufferCredentials) { IHXBuffer* pServerToken = NULL; IHXBuffer* pClientToken = NULL; // We run MD5 against password, nonce, etc. on server side, should // get same result as what client sent us. if (FAILED(ComputeServerToken(m_pCredentials, pBufferCredentials, &pServerToken))) m_pServerRespondee->ChallengeReady(HXR_UNEXPECTED, m_pServerRequest); m_pCredentials->GetPropertyCString("Response", pClientToken); if (pClientToken && pServerToken && !strcasecmp((char*) pServerToken->GetBuffer(), (char*) pClientToken->GetBuffer())) { m_bAuthenticated = TRUE; m_pRequestContext->SetUserContext((IUnknown*)(IHXPlugin*)this); } HX_RELEASE(pClientToken); HX_RELEASE(pServerToken); } if (!m_bAuthenticated) { HX_RELEASE(m_pPrincipalID); } SendChallengeResponse(); return HXR_OK;}HX_RESULTCDigestAuthenticator::SendChallengeResponse(){ if (!m_bAuthenticated && m_pRealm) { CHXString str; str = "Digest qop=\"auth\", algorith=MD5-sess, realm=\""; str += m_pRealm->GetBuffer(); str += "\""; str += ", nonce=\""; IHXScheduler* pSchedulerContext = NULL; m_pContext->QueryInterface(IID_IHXScheduler, (void**)&pSchedulerContext); if (pSchedulerContext) { HXTimeval TimeNow; TimeNow = pSchedulerContext->GetCurrentSchedulerTime(); str.AppendULONG(TimeNow.tv_sec); str.AppendULONG(TimeNow.tv_usec); } else { HX_ASSERT(0); str += "Crappy_Nonce"; } str += "\""; IHXValues* pChallengeHeaders = _GetResponseHeaders(); if (!pChallengeHeaders) { HX_ASSERT(0); return HXR_UNEXPECTED; } else { if (m_bIsProxyAuthentication) { _SetPropertyFromCharArray(pChallengeHeaders, "Proxy-Authenticate", (const char*) str); } else { _SetPropertyFromCharArray(pChallengeHeaders, "WWW-Authenticate", (const char*) str); } HX_RELEASE(pChallengeHeaders); } HX_RELEASE(pSchedulerContext); } m_pServerRespondee->ChallengeReady(HXR_OK, m_pServerRequest); HX_RELEASE(m_pServerRequest); HX_RELEASE(m_pRequestContext); HX_RELEASE(m_pServerRespondee); return HXR_OK;}HX_RESULT CDigestAuthenticator::ParseCredentials(IHXBuffer* pAuthHeader, IHXValues** ppCredentials){ char* szAuthHdr = (char*)pAuthHeader->GetBuffer(); szAuthHdr += 6; // Move past "Digest" (*ppCredentials) = new CHXHeader(); (*ppCredentials)->AddRef(); return _GetQuotedFields(szAuthHdr, *ppCredentials); }HX_RESULT CDigestAuthenticator::ComputeServerToken(IHXValues* pCredentials, IHXBuffer* pbufPassword, IHXBuffer** ppToken){ HX_RESULT hr = HXR_OK; IHXValues* pResponseHeaders = NULL; IHXBuffer* pbufHdr = NULL; IHXBuffer* pbufnonceval = NULL; IHXBuffer* pbufcnonceval = NULL; IHXBuffer* pbufurival = NULL; IHXBuffer* pbufnccount = NULL; IHXBuffer* pbufA1 = NULL; IHXBuffer* pbufA2 = NULL; char szresbuf[1024]; char* sToken = NULL; BOOL bQoPPresent = FALSE; // Calculate response //Calculate A1 if (SUCCEEDED(pCredentials->GetPropertyCString("algorithm", pbufHdr))) { if (!strncasecmp((const char*)pbufHdr->GetBuffer(), "MD5-sess", 8)) m_algorithm = MD5_SESS; else m_algorithm = MD5; HX_RELEASE(pbufHdr); } else { hr = HXR_FAIL; goto errorfound; } if (FAILED(pCredentials->GetPropertyCString("nonce", pbufnonceval))) { hr = HXR_FAIL; goto errorfound; } if (FAILED(pCredentials->GetPropertyCString("cnonce", pbufcnonceval))) { hr = HXR_FAIL; goto errorfound; } switch (m_algorithm) { case MD5: pbufA1 = pbufPassword; pbufA1->AddRef(); break; case MD5_SESS: sprintf(szresbuf, "%-.200s:%-.200s:%-.200s",pbufPassword->GetBuffer(), pbufnonceval->GetBuffer(), pbufcnonceval->GetBuffer()); pbufA1 = new CHXBuffer(); pbufA1->AddRef(); pbufA1->SetSize(64); sToken = (char*)pbufA1->GetBuffer(); MD5Data(sToken, (const UCHAR*)szresbuf, strlen(szresbuf)); break; case ALGO_UNKNOWN: hr = HXR_FAIL; goto errorfound; } m_pServerRequest->GetRequestHeaders(pResponseHeaders); if (FAILED(pResponseHeaders->GetPropertyCString("Method", pbufHdr))) { pbufHdr = new CHXBuffer(); pbufHdr->AddRef(); pbufHdr->SetSize(128); strcpy((char*)pbufHdr->GetBuffer(), "POST"); } if (FAILED(pCredentials->GetPropertyCString("uri", pbufurival))) { hr = HXR_FAIL; goto errorfound; } if (FAILED(pCredentials->GetPropertyCString("nc", pbufnccount))) { hr = HXR_FAIL; goto errorfound; } // We may need to add check for request-uri here. sprintf(szresbuf, "%-.200s:%-.200s", pbufHdr->GetBuffer(), pbufurival->GetBuffer()); pbufA2 = new CHXBuffer(); pbufA2->AddRef(); pbufA2->SetSize(64); sToken = (char*)pbufA2->GetBuffer(); MD5Data(sToken, (const UCHAR*)szresbuf, strlen(szresbuf)); HX_RELEASE(pbufHdr); if (SUCCEEDED(pCredentials->GetPropertyCString("qop", pbufHdr))) { if (strlen((char*)pbufHdr->GetBuffer()) > 4) { hr = HXR_FAIL; goto errorfound; } // Compute full string to be hashed sprintf(szresbuf, "%-.64s:%-.200s:%-.8s:%-.200s:%-.200s:%-.64s", pbufA1->GetBuffer(), pbufnonceval->GetBuffer(), pbufnccount->GetBuffer(), pbufcnonceval->GetBuffer(), pbufHdr->GetBuffer(), pbufA2->GetBuffer()); } else { sprintf(szresbuf, "%-.64s:%-.200s:%-.64s", pbufA1->GetBuffer(), pbufnonceval->GetBuffer(), pbufA2->GetBuffer()); } (*ppToken) = new CHXBuffer(); (*ppToken)->AddRef(); (*ppToken)->SetSize(64); sToken = (char*)(*ppToken)->GetBuffer(); MD5Data(sToken, (const UCHAR*)szresbuf, strlen(szresbuf)); errorfound: HX_RELEASE(pbufnonceval); HX_RELEASE(pbufcnonceval); HX_RELEASE(pbufHdr); HX_RELEASE(pResponseHeaders); HX_RELEASE(pbufurival); HX_RELEASE(pbufA1); HX_RELEASE(pbufA2); HX_RELEASE(pbufnccount); return hr;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -