/// <summary> /// An authentication response have been received from the web browser. /// Check if it's correct /// </summary> /// <param name="header">Contents from the Authorization header</param> /// <param name="realm">Realm that should be authenticated</param> /// <param name="httpVerb">GET/POST/PUT/DELETE etc.</param> /// <param name="options">First option: true if username/password is correct but not cnonce</param> /// <returns> /// Authentication object that is stored for the request. A user class or something like that. /// </returns> /// <exception cref="ArgumentException">if authenticationHeader is invalid</exception> /// <exception cref="ArgumentNullException">If any of the parameters is empty or null.</exception> public bool Authenticate(AuthorizationHeader header, string realm, string httpVerb, object[] options) { if (header == null) { throw new ArgumentNullException("header"); } lock (_nonces) { if (_timer == null) { _timer = new Timer(ManageNonces, null, 15000, 15000); } } if (!header.Scheme.Equals("digest", StringComparison.OrdinalIgnoreCase)) { return(false); } var parameters = HeaderParameterCollection.Parse(new StringReader(header.Data)); if (!IsValidNonce(parameters["nonce"]) && !DisableNonceCheck) { return(false); } // request authentication information string username = parameters["username"]; DigestContext context = new DigestContext(realm, username); if (!_authenticator(context)) { return(false); } // Encode authentication info string HA1; if (string.IsNullOrEmpty(context.HA1)) { string A1 = String.Format("{0}:{1}:{2}", username, realm, context.Password); HA1 = GetMD5HashBinHex2(A1); } else { HA1 = context.HA1; } // encode challenge info string A2 = String.Format("{0}:{1}", httpVerb, parameters["uri"]); string HA2 = GetMD5HashBinHex2(A2); string hashedDigest = Encrypt(HA1, HA2, parameters["qop"], parameters["nonce"], parameters["nc"], parameters["cnonce"]); //validate return(parameters["response"] == hashedDigest); }
/// <summary> /// An authentication response have been received from the web browser. /// Check if it's correct /// </summary> /// <param name="header">Contents from the Authorization header</param> /// <param name="realm">Realm that should be authenticated</param> /// <param name="httpVerb">GET/POST/PUT/DELETE etc.</param> /// <param name="options">First option: true if username/password is correct but not cnonce</param> /// <returns> /// Authentication object that is stored for the request. A user class or something like that. /// </returns> /// <exception cref="ArgumentException">if authenticationHeader is invalid</exception> /// <exception cref="ArgumentNullException">If any of the parameters is empty or null.</exception> public bool Authenticate(AuthorizationHeader header, string realm, string httpVerb, object[] options) { if (header == null) throw new ArgumentNullException("header"); lock (_nonces) { if (_timer == null) _timer = new Timer(ManageNonces, null, 15000, 15000); } if (!header.Scheme.Equals("digest", StringComparison.OrdinalIgnoreCase)) return false; var parameters = HeaderParameterCollection.Parse(new StringReader(header.Data)); if (!IsValidNonce(parameters["nonce"]) && !DisableNonceCheck) return false; // request authentication information string username = parameters["username"]; DigestContext context = new DigestContext(realm, username); if (!_authenticator(context)) return false; // Encode authentication info string HA1; if (string.IsNullOrEmpty(context.HA1)) { string A1 = String.Format("{0}:{1}:{2}", username, realm, context.Password); HA1 = GetMD5HashBinHex2(A1); } else HA1 = context.HA1; // encode challenge info string A2 = String.Format("{0}:{1}", httpVerb, parameters["uri"]); string HA2 = GetMD5HashBinHex2(A2); string hashedDigest = Encrypt(HA1, HA2, parameters["qop"], parameters["nonce"], parameters["nc"], parameters["cnonce"]); //validate return parameters["response"] == hashedDigest; }