|
reSIProcate/stack
9694
|
00001 #ifndef digcalc_hxx 00002 #define digcalc_hxx 00003 00004 00005 #include "rutil/vmd5.hxx" 00006 #include <string.h> 00007 #include <iostream> 00008 #include "rutil/Data.hxx" 00009 00010 #define HASHLEN 16 00011 typedef char HASH[HASHLEN]; 00012 #define HASHHEXLEN 32 00013 typedef char HASHHEX[HASHHEXLEN+1]; 00014 #define IN const 00015 #define OUT 00016 00017 00018 using namespace std; 00019 00020 namespace resip 00021 { 00022 00023 typedef MD5Context MD5_CTX; 00024 00025 00026 void 00027 MD5_Update(struct MD5Context *ctx, char const *buf, unsigned len) 00028 { 00029 MD5Update(ctx, (unsigned char*)(buf), len); 00030 } 00031 00032 void 00033 MD5_Final(char digest[16], struct MD5Context *ctx) 00034 { 00035 MD5Final((unsigned char*)digest, ctx); 00036 } 00037 00038 /* calculate H(A1) as per HTTP Digest spec */ 00039 void DigestCalcHA1( 00040 IN char * pszAlg, 00041 IN char * pszUserName, 00042 IN char * pszRealm, 00043 IN char * pszPassword, 00044 IN char * pszNonce, 00045 IN char * pszCNonce, 00046 OUT HASHHEX SessionKey 00047 ); 00048 00049 /* calculate request-digest/response-digest as per HTTP Digest spec */ 00050 void DigestCalcResponse( 00051 IN HASHHEX HA1, /* H(A1) */ 00052 IN char * pszNonce, /* nonce from server */ 00053 IN char * pszNonceCount, /* 8 hex digits */ 00054 IN char * pszCNonce, /* client nonce */ 00055 IN char * pszQop, /* qop-value: "", "auth", "auth-int" */ 00056 IN char * pszMethod, /* method from the request */ 00057 IN char * pszDigestUri, /* requested URL */ 00058 IN HASHHEX HEntity, /* H(entity body) if qop="auth-int" */ 00059 OUT HASHHEX Response /* request-digest or response-digest */ 00060 ); 00061 00062 void CvtHex( 00063 IN HASH Bin, 00064 OUT HASHHEX Hex 00065 ) 00066 { 00067 unsigned short i; 00068 unsigned char j; 00069 00070 for (i = 0; i < HASHLEN; i++) { 00071 j = (Bin[i] >> 4) & 0xf; 00072 if (j <= 9) 00073 Hex[i*2] = (j + '0'); 00074 else 00075 Hex[i*2] = (j + 'a' - 10); 00076 j = Bin[i] & 0xf; 00077 if (j <= 9) 00078 Hex[i*2+1] = (j + '0'); 00079 else 00080 Hex[i*2+1] = (j + 'a' - 10); 00081 }; 00082 Hex[HASHHEXLEN] = '\0'; 00083 }; 00084 00085 /* calculate H(A1) as per spec */ 00086 void DigestCalcHA1( 00087 IN char * pszAlg, 00088 IN char * pszUserName, 00089 IN char * pszRealm, 00090 IN char * pszPassword, 00091 IN char * pszNonce, 00092 IN char * pszCNonce, 00093 OUT HASHHEX SessionKey 00094 ) 00095 { 00096 MD5_CTX Md5Ctx; 00097 HASH HA1; 00098 00099 MD5Init(&Md5Ctx); 00100 MD5_Update(&Md5Ctx, pszUserName, strlen(pszUserName)); 00101 MD5_Update(&Md5Ctx, ":", 1); 00102 MD5_Update(&Md5Ctx, pszRealm, strlen(pszRealm)); 00103 MD5_Update(&Md5Ctx, ":", 1); 00104 MD5_Update(&Md5Ctx, pszPassword, strlen(pszPassword)); 00105 MD5_Final(HA1, &Md5Ctx); 00106 if (strcasecmp(pszAlg, "md5-sess") == 0) { 00107 MD5Init(&Md5Ctx); 00108 MD5_Update(&Md5Ctx, HA1, HASHLEN); 00109 MD5_Update(&Md5Ctx, ":", 1); 00110 MD5_Update(&Md5Ctx, pszNonce, strlen(pszNonce)); 00111 MD5_Update(&Md5Ctx, ":", 1); 00112 MD5_Update(&Md5Ctx, pszCNonce, strlen(pszCNonce)); 00113 MD5_Final(HA1, &Md5Ctx); 00114 }; 00115 CvtHex(HA1, SessionKey); 00116 }; 00117 00118 /* calculate request-digest/response-digest as per HTTP Digest spec */ 00119 void DigestCalcResponse( 00120 IN HASHHEX HA1, /* H(A1) */ 00121 IN char * pszNonce, /* nonce from server */ 00122 IN char * pszNonceCount, /* 8 hex digits */ 00123 IN char * pszCNonce, /* client nonce */ 00124 IN char * pszQop, /* qop-value: "", "auth", "auth-int" */ 00125 IN char * pszMethod, /* method from the request */ 00126 IN char * pszDigestUri, /* requested URL */ 00127 IN HASHHEX HEntity, /* H(entity body) if qop="auth-int" */ 00128 OUT HASHHEX Response /* request-digest or response-digest */ 00129 ) 00130 { 00131 MD5_CTX Md5Ctx; 00132 HASH HA2; 00133 HASH RespHash; 00134 HASHHEX HA2Hex; 00135 00136 // calculate H(A2) 00137 MD5Init(&Md5Ctx); 00138 MD5_Update(&Md5Ctx, pszMethod, strlen(pszMethod)); 00139 MD5_Update(&Md5Ctx, ":", 1); 00140 MD5_Update(&Md5Ctx, pszDigestUri, strlen(pszDigestUri)); 00141 if (strcasecmp(pszQop, "auth-int") == 0) { 00142 MD5_Update(&Md5Ctx, ":", 1); 00143 MD5_Update(&Md5Ctx, HEntity, HASHHEXLEN); 00144 }; 00145 MD5_Final(HA2, &Md5Ctx); 00146 CvtHex(HA2, HA2Hex); 00147 00148 00149 // calculate response 00150 MD5Init(&Md5Ctx); 00151 MD5_Update(&Md5Ctx, HA1, HASHHEXLEN); 00152 MD5_Update(&Md5Ctx, ":", 1); 00153 MD5_Update(&Md5Ctx, pszNonce, strlen(pszNonce)); 00154 MD5_Update(&Md5Ctx, ":", 1); 00155 if (*pszQop) { 00156 MD5_Update(&Md5Ctx, pszNonceCount, strlen(pszNonceCount)); 00157 MD5_Update(&Md5Ctx, ":", 1); 00158 MD5_Update(&Md5Ctx, pszCNonce, strlen(pszCNonce)); 00159 MD5_Update(&Md5Ctx, ":", 1); 00160 MD5_Update(&Md5Ctx, pszQop, strlen(pszQop)); 00161 MD5_Update(&Md5Ctx, ":", 1); 00162 }; 00163 MD5_Update(&Md5Ctx, HA2Hex, HASHHEXLEN); 00164 MD5_Final(RespHash, &Md5Ctx); 00165 CvtHex(RespHash, Response); 00166 }; 00167 00168 00169 } 00170 00171 00172 #endif 00173 /* ==================================================================== 00174 * The Vovida Software License, Version 1.0 00175 * 00176 * Copyright (c) 2000 Vovida Networks, Inc. All rights reserved. 00177 * 00178 * Redistribution and use in source and binary forms, with or without 00179 * modification, are permitted provided that the following conditions 00180 * are met: 00181 * 00182 * 1. Redistributions of source code must retain the above copyright 00183 * notice, this list of conditions and the following disclaimer. 00184 * 00185 * 2. Redistributions in binary form must reproduce the above copyright 00186 * notice, this list of conditions and the following disclaimer in 00187 * the documentation and/or other materials provided with the 00188 * distribution. 00189 * 00190 * 3. The names "VOCAL", "Vovida Open Communication Application Library", 00191 * and "Vovida Open Communication Application Library (VOCAL)" must 00192 * not be used to endorse or promote products derived from this 00193 * software without prior written permission. For written 00194 * permission, please contact vocal@vovida.org. 00195 * 00196 * 4. Products derived from this software may not be called "VOCAL", nor 00197 * may "VOCAL" appear in their name, without prior written 00198 * permission of Vovida Networks, Inc. 00199 * 00200 * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESSED OR IMPLIED 00201 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 00202 * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, TITLE AND 00203 * NON-INFRINGEMENT ARE DISCLAIMED. IN NO EVENT SHALL VOVIDA 00204 * NETWORKS, INC. OR ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT DAMAGES 00205 * IN EXCESS OF $1,000, NOR FOR ANY INDIRECT, INCIDENTAL, SPECIAL, 00206 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 00207 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 00208 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY 00209 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 00210 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE 00211 * USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH 00212 * DAMAGE. 00213 * 00214 * ==================================================================== 00215 * 00216 * This software consists of voluntary contributions made by Vovida 00217 * Networks, Inc. and many individuals on behalf of Vovida Networks, 00218 * Inc. For more information on Vovida Networks, Inc., please see 00219 * <http://www.vovida.org/>. 00220 * 00221 */
1.7.5.1