/// <summary>
        /// Calculates response value.
        /// </summary>
        /// <param name="userName">User name.</param>
        /// <param name="password">User password.</param>
        /// <returns>Returns calculated rsponse value.</returns>
        public string CalculateResponse(string userName, string password)
        {
            /*
             *  MD5
             *      A1 = username-value ":" realm-value ":" passwd
             *
             *  MD5-sess
             *      A1 = md5(username-value ":" realm-value ":" passwd) ":" nonce-value ":" cnonce-value
             *
             *  qop not peresent or auth
             *      A2 = Method ":" digest-uri-value
             *
             *  qop auth-int
             *      A2 = Method ":" digest-uri-value ":" md5h(entity-body)
             *
             *  qop present
             *      response = md5h(md5h(A1) ":" nonce-value ":" nc-value ":" cnonce-value ":" qop-value ":" md5h(A2))
             *
             *  qop not present
             *      response = md5h(md5h(A1) ":" nonce-value ":" md5h(A2))
             *
             */

            string a1 = "";
            string a2 = "";

            // Create A1
            if (Algorithm == "" || Algorithm.ToLower() == "md5")
            {
                a1 = userName + ":" + Realm + ":" + password;
            }
            else if (Algorithm.ToLower() == "md5-sess")
            {
                a1 = Core.ComputeMd5(userName + ":" + Realm + ":" + password, false) + ":" + Nonce + ":" +
                     CNonce;
            }
            else
            {
                throw new ArgumentException("Invalid Algorithm value '" + Algorithm + "' !");
            }
            // Create A2
            if (Qop == "" || Qop.ToLower() == "auth")
            {
                a2 = m_Method.ToUpper() + ":" + Uri;
            }
            else
            {
                throw new ArgumentException("Invalid qop value '" + Qop + "' !");
            }

            // Calculate response value.
            // qop present
            if (!string.IsNullOrEmpty(Qop))
            {
                return
                    (Core.ComputeMd5(
                         Core.ComputeMd5(a1, true) + ":" + Nonce + ":" + NonceCount.ToString("x8") + ":" +
                         CNonce + ":" + Qop + ":" + Core.ComputeMd5(a2, true),
                         true));
            }
            // qop not present
            else
            {
                return
                    (Core.ComputeMd5(
                         Core.ComputeMd5(a1, true) + ":" + Nonce + ":" + Core.ComputeMd5(a2, true), true));
            }
        }
Beispiel #2
0
        //	HEX( KD ( HEX(H(A1)),
        //	{
        //		nonce-value, ":" nc-value, ":",
        //		cnonce-value, ":", qop-value, ":", HEX(H(A2)) }))
        //
        //	If authzid is specified, then A1 is
        //
        //	A1 = { H( { username-value, ":", realm-value, ":", passwd } ),
        //	":", nonce-value, ":", cnonce-value, ":", authzid-value }
        //
        //	If authzid is not specified, then A1 is
        //
        //	A1 = { H( { username-value, ":", realm-value, ":", passwd } ),
        //	":", nonce-value, ":", cnonce-value }
        //
        //	where
        //
        //	passwd   = *OCTET
        public void GenerateResponse()
        {
            byte[] H1;
            byte[] H2;
            byte[] H3;
            //byte[] temp;
            string A1;
            string A2;
            string A3;
            string p1;
            string p2;

            var sb = new StringBuilder();

            sb.Append(Username);
            sb.Append(":");
            sb.Append(Realm);
            sb.Append(":");
            sb.Append(Password);

#if !CF
            H1 = new MD5CryptoServiceProvider().ComputeHash(Encoding.UTF8.GetBytes(sb.ToString()));
#else
            //H1 = Encoding.Default.GetBytes(util.Hash.MD5Hash(sb.ToString()));
            H1 = util.Hash.MD5Hash(Encoding.UTF8.GetBytes(sb.ToString()));
#endif

            sb.Remove(0, sb.Length);
            sb.Append(":");
            sb.Append(Nonce);
            sb.Append(":");
            sb.Append(Cnonce);

            if (Authzid != null)
            {
                sb.Append(":");
                sb.Append(Authzid);
            }
            A1 = sb.ToString();


//			sb.Remove(0, sb.Length);
//			sb.Append(Encoding.Default.GetChars(H1));
//			//sb.Append(Encoding.ASCII.GetChars(H1));
//
//			sb.Append(A1);
            var bA1   = Encoding.ASCII.GetBytes(A1);
            var bH1A1 = new byte[H1.Length + bA1.Length];

            //Array.Copy(H1, bH1A1, H1.Length);
            Array.Copy(H1, 0, bH1A1, 0, H1.Length);
            Array.Copy(bA1, 0, bH1A1, H1.Length, bA1.Length);
#if !CF
            H1 = new MD5CryptoServiceProvider().ComputeHash(bH1A1);
            //Console.WriteLine(util.Hash.HexToString(H1));
#else
            //H1 = Encoding.Default.GetBytes(util.Hash.MD5Hash(sb.ToString()));
            //H1 =util.Hash.MD5Hash(Encoding.Default.GetBytes(sb.ToString()));
            H1 = util.Hash.MD5Hash(bH1A1);
#endif
            sb.Remove(0, sb.Length);
            sb.Append("AUTHENTICATE:");
            sb.Append(DigestUri);
            if (Qop.CompareTo("auth") != 0)
            {
                sb.Append(":00000000000000000000000000000000");
            }
            A2 = sb.ToString();
            H2 = Encoding.ASCII.GetBytes(A2);

#if !CF
            H2 = new MD5CryptoServiceProvider().ComputeHash(H2);
#else
            //H2 = Encoding.Default.GetBytes(util.Hash.MD5Hash(H2));
            H2 = util.Hash.MD5Hash(H2);
#endif
            // create p1 and p2 as the hex representation of H1 and H2
            p1 = Hash.HexToString(H1).ToLower();
            p2 = Hash.HexToString(H2).ToLower();

            sb.Remove(0, sb.Length);
            sb.Append(p1);
            sb.Append(":");
            sb.Append(Nonce);
            sb.Append(":");
            sb.Append(Nc);
            sb.Append(":");
            sb.Append(Cnonce);
            sb.Append(":");
            sb.Append(Qop);
            sb.Append(":");
            sb.Append(p2);

            A3 = sb.ToString();
#if !CF
            H3 = new MD5CryptoServiceProvider().ComputeHash(Encoding.ASCII.GetBytes(A3));
#else
            //H3 = Encoding.Default.GetBytes(util.Hash.MD5Hash(A3));
            H3 = util.Hash.MD5Hash(Encoding.ASCII.GetBytes(A3));
#endif
            Response = Hash.HexToString(H3).ToLower();
        }
        /// <summary>
        /// Calculates 'rspauth' value.
        /// </summary>
        /// <param name="userName">User name.</param>
        /// <param name="password">Password.</param>
        /// <returns>Returns 'rspauth' value.</returns>
        public string CalculateRspAuth(string userName, string password)
        {
            /* RFC 2617 3.2.3.
             *  The optional response digest in the "response-auth" directive
             *  supports mutual authentication -- the server proves that it knows the
             *  user's secret, and with qop=auth-int also provides limited integrity
             *  protection of the response. The "response-digest" value is calculated
             *  as for the "request-digest" in the Authorization header, except that
             *  if "qop=auth" or is not specified in the Authorization header for the
             *  request, A2 is
             *
             *      A2 = ":" digest-uri-value
             *
             *  and if "qop=auth-int", then A2 is
             *
             *      A2 = ":" digest-uri-value ":" H(entity-body)
             *
             *  where "digest-uri-value" is the value of the "uri" directive on the
             *  Authorization header in the request. The "cnonce-value" and "nc-
             *  value" MUST be the ones for the client request to which this message
             *  is the response. The "response-auth", "cnonce", and "nonce-count"
             *  directives MUST BE present if "qop=auth" or "qop=auth-int" is
             *  specified.
             */

            string a1 = "";
            string a2 = "";

            // Create A1
            if (Algorithm == "" || Algorithm.ToLower() == "md5")
            {
                a1 = userName + ":" + Realm + ":" + password;
            }
            else if (Algorithm.ToLower() == "md5-sess")
            {
                a1 = Core.ComputeMd5(userName + ":" + Realm + ":" + password, false) + ":" + Nonce + ":" +
                     CNonce;
            }
            else
            {
                throw new ArgumentException("Invalid Algorithm value '" + Algorithm + "' !");
            }
            // Create A2
            if (Qop == "" || Qop.ToLower() == "auth")
            {
                a2 = ":" + Uri;
            }
            else
            {
                throw new ArgumentException("Invalid qop value '" + Qop + "' !");
            }

            // Calculate response value.
            // qop present
            if (!string.IsNullOrEmpty(Qop))
            {
                return
                    (Core.ComputeMd5(
                         Core.ComputeMd5(a1, true) + ":" + Nonce + ":" + NonceCount.ToString("x8") + ":" +
                         CNonce + ":" + Qop + ":" + Core.ComputeMd5(a2, true),
                         true));
            }
            // qop not present
            else
            {
                return
                    (Core.ComputeMd5(
                         Core.ComputeMd5(a1, true) + ":" + Nonce + ":" + Core.ComputeMd5(a2, true), true));
            }
        }