23Auth::Digest::UserRequest::UserRequest() :
35 memset(nc, 0,
sizeof(nc));
36 memset(&flags, 0,
sizeof(flags));
43Auth::Digest::UserRequest::~UserRequest()
62Auth::Digest::UserRequest::credentialsStr()
77 if (user() ==
nullptr || user()->credentials() ==
Auth::Failed) {
83 Auth::Digest::User *digest_user =
dynamic_cast<Auth::Digest::User*
>(auth_user.
getRaw());
84 assert(digest_user !=
nullptr);
86 Auth::Digest::UserRequest *digest_request =
this;
89 if (!digest_user->HA1created) {
94 if (digest_request->nonce ==
nullptr) {
100 DigestCalcHA1(digest_request->algorithm,
nullptr,
nullptr,
nullptr,
102 digest_request->cnonce,
103 digest_user->HA1, SESSIONKEY);
106 digest_request->nc, digest_request->cnonce, digest_request->qop,
107 sTmp.
c_str(), digest_request->uri, HA2, Response);
109 debugs(29, 9,
"\nResponse = '" << digest_request->response <<
"'\nsquid is = '" << Response <<
"'");
111 if (strcasecmp(digest_request->response, Response) != 0) {
112 if (!digest_request->flags.helper_queried) {
114 digest_request->flags.helper_queried =
true;
128 digest_request->nc, digest_request->cnonce, digest_request->qop,
129 sTmp.
c_str(), digest_request->uri, HA2, Response);
131 if (strcasecmp(digest_request->response, Response)) {
133 digest_request->flags.invalid_password =
true;
134 digest_request->setDenyMessage(
"Incorrect password");
140 static int seen_broken_client = 0;
142 if (!seen_broken_client) {
144 seen_broken_client = 1;
148 debugs(29,
DBG_IMPORTANT,
"ERROR: User agent Digest Authentication POST bug detected from " <<
150 (useragent ? useragent :
"-") <<
151 "'. Please upgrade browser. See Bug #630 for details.");
158 digest_request->flags.invalid_password =
true;
159 digest_request->setDenyMessage(
"Incorrect password");
168 debugs(29, 3, auth_user->username() <<
"' validated OK but nonce stale: " << digest_request->noncehex);
171 nonce->flags.valid =
false;
179 debugs(29, 4,
"user '" << auth_user->username() <<
"' validated OK");
183Auth::Digest::UserRequest::module_direction()
188 switch (user()->credentials()) {
208Auth::Digest::UserRequest::addAuthenticationInfoHeader(
HttpReply * rep,
int accel)
226 flags.authinfo_sent =
true;
227 Auth::Digest::User *digest_user =
dynamic_cast<Auth::Digest::User *
>(user().getRaw());
231 digest_nonce_h *nextnonce = digest_user->currentNonce();
243Auth::Digest::UserRequest::addAuthenticationInfoTrailer(
HttpReply * rep,
int accel)
247 if (!auth_user_request)
251 if (flags.authinfo_sent)
262 Auth::Digest::User *digest_user =
dynamic_cast<Auth::Digest::User *
>(auth_user_request->
user().
getRaw());
263 nonce = digest_user->currentNonce();
281 debugs(29, 9,
"'\"" << user()->username() <<
"\":\"" << realm <<
"\"'");
289 const char *keyExtras = helperRequestKeyExtras(request, al);
291 snprintf(buf, 8192,
"\"%s\":\"%s\" %s\n", user()->username(), realm, keyExtras);
293 snprintf(buf, 8192,
"\"%s\":\"%s\"\n", user()->username(), realm);
300Auth::Digest::UserRequest::HandleReply(
void *data,
const Helper::Reply &reply)
303 debugs(29, 9,
"reply=" << reply);
311 auth_user_request->
user()->notes.replaceOrAddOrAppend(&reply.
notes, appendables);
313 auth_user_request->
user()->notes.remove(
"ha1");
315 static bool oldHelperWarningDone =
false;
320 if (!oldHelperWarningDone) {
321 debugs(29,
DBG_IMPORTANT,
"WARNING: Digest auth helper returned old format HA1 response. It needs to be upgraded.");
322 oldHelperWarningDone=
true;
326 Auth::Digest::User *digest_user =
dynamic_cast<Auth::Digest::User *
>(auth_user_request->
user().
getRaw());
327 assert(digest_user !=
nullptr);
330 digest_user->HA1created = 1;
336 Auth::Digest::User *digest_user =
dynamic_cast<Auth::Digest::User *
>(auth_user_request->
user().
getRaw());
337 assert(digest_user !=
nullptr);
340 CvtBin(ha1Note, digest_user->HA1);
341 digest_user->HA1created = 1;
343 debugs(29,
DBG_IMPORTANT,
"ERROR: Digest auth helper did not produce a HA1. Using the wrong helper program? received: " << reply);
349 debugs(29,
DBG_IMPORTANT,
"ERROR: Digest auth does not support the result code received. Using the wrong helper program? received: " << reply);
359 Auth::Digest::UserRequest *digest_request =
dynamic_cast<Auth::Digest::UserRequest *
>(auth_user_request.
getRaw());
363 digest_request->flags.invalid_password =
true;
365 if (
auto msgNote = reply.
notes.
find(
"message")) {
366 digest_request->setDenyMessage(msgNote->c_str());
370 digest_request->setDenyMessage(reply.
other().
content());
371 if (!oldHelperWarningDone) {
372 debugs(29,
DBG_IMPORTANT,
"WARNING: Digest auth helper returned old format ERR response. It needs to be upgraded.");
373 oldHelperWarningDone=
true;
Helper::ClientPointer digestauthenticators
void authDigestUserLinkNonce(Auth::Digest::User *user, digest_nonce_h *nonce)
void authDigestNonceUnlink(digest_nonce_h *nonce)
int authDigestNonceIsValid(digest_nonce_h *nonce, char nc[9])
const char * authenticateDigestNonceNonceHex(const digest_nonce_h *nonce)
int authDigestNonceLastRequest(digest_nonce_h *nonce)
void authDigestNoncePurge(digest_nonce_h *nonce)
digest_nonce_h * authenticateDigestNonceNew(void)
static void authenticate(int socket_fd, const char *username, const char *passwd)
#define cbdataReferenceValidDone(var, ptr)
static SchemeConfig * Find(const char *proxy_auth)
UserRequest::Pointer auth_user_request
virtual User::Pointer user()
Helper::ResultCode result
The helper response 'result' field.
const MemBuf & other() const
const SBuf & image() const
Http::StatusCode status() const
retrieve the status code for this status line
char * content()
start of the added data
std::vector< SBuf > Names
std::optional< SBuf > find(const char *noteKey, const char *sep=",") const
const char * findFirst(const char *noteKey) const
#define debugs(SECTION, LEVEL, CONTENT)
void helperSubmit(const Helper::Client::Pointer &hlp, const char *const buf, HLPCB *const callback, void *const data)
@ CRED_ERROR
ERROR in the auth module. Cannot determine the state of this request.
@ CRED_CHALLENGE
Client needs to be challenged. secure token.
@ CRED_LOOKUP
Credentials need to be validated with the backend helper.
@ CRED_VALID
Credentials are valid and a up to date. The OK/Failed state is accurate.
@ scProxyAuthenticationRequired
@ PROXY_AUTHENTICATION_INFO
void DigestCalcHA1(const char *pszAlg, const char *pszUserName, const char *pszRealm, const char *pszPassword, const char *pszNonce, const char *pszCNonce, HASH HA1, HASHHEX SessionKey)
void CvtBin(const HASHHEX Hex, HASH Bin)
char HASHHEX[HASHHEXLEN+1]
void DigestCalcResponse(const HASHHEX HA1, const char *pszNonce, const char *pszNonceCount, const char *pszCNonce, const char *pszQop, const char *pszMethod, const char *pszDigestUri, const HASHHEX HEntity, HASHHEX Response)
static Auth::Config * getConfig(char const *type_str)