/* Retrieves the value for a corresponding key from the challenge string
* returns TRUE if the key could be found, FALSE if it does not exists
*/
-static bool auth_digest_get_key_value(const char *chlg,
- const char *key,
- char *value,
- size_t max_val_len,
- char end_char)
+static bool auth_digest_get_key_value(const char *chlg, const char *key,
+ char *buf, size_t buflen)
{
- char *find_pos;
- size_t i;
-
- find_pos = strstr(chlg, key);
- if(!find_pos)
- return FALSE;
-
- find_pos += strlen(key);
-
- for(i = 0; *find_pos && *find_pos != end_char && i < max_val_len - 1; ++i)
- value[i] = *find_pos++;
- value[i] = '\0';
+ /* keyword=[value],keyword2=[value]
+ The values may or may not be quoted.
+ */
+
+ do {
+ struct Curl_str data;
+ struct Curl_str name;
+ if(!curlx_str_until(&chlg, &name, 64, '=') &&
+ !curlx_str_single(&chlg, '=')) {
+ /* this is the key, get the value, possibly quoted */
+ int rc = curlx_str_quotedword(&chlg, &data, 256);
+ if(rc == STRE_BEGQUOTE)
+ /* try unquoted until comma */
+ rc = curlx_str_until(&chlg, &data, 256, ',');
+ if(rc)
+ return FALSE; /* weird */
+
+ if(curlx_str_cmp(&name, key)) {
+ /* if this is our key, return the value */
+ if(curlx_strlen(&data) >= buflen)
+ /* doesn't fit */
+ return FALSE;
+ memcpy(buf, curlx_str(&data), curlx_strlen(&data));
+ buf[curlx_strlen(&data)] = 0;
+ return TRUE;
+ }
+ if(curlx_str_single(&chlg, ','))
+ return FALSE;
+ }
+ else /* odd syntax */
+ break;
+ } while(1);
- return TRUE;
+ return FALSE;
}
static CURLcode auth_digest_get_qop_values(const char *options, int *value)
return CURLE_BAD_CONTENT_ENCODING;
/* Retrieve nonce string from the challenge */
- if(!auth_digest_get_key_value(chlg, "nonce=\"", nonce, nlen, '\"'))
+ if(!auth_digest_get_key_value(chlg, "nonce", nonce, nlen))
return CURLE_BAD_CONTENT_ENCODING;
/* Retrieve realm string from the challenge */
- if(!auth_digest_get_key_value(chlg, "realm=\"", realm, rlen, '\"')) {
+ if(!auth_digest_get_key_value(chlg, "realm", realm, rlen)) {
/* Challenge does not have a realm, set empty string [RFC2831] page 6 */
*realm = '\0';
}
/* Retrieve algorithm string from the challenge */
- if(!auth_digest_get_key_value(chlg, "algorithm=", alg, alen, ','))
+ if(!auth_digest_get_key_value(chlg, "algorithm", alg, alen))
return CURLE_BAD_CONTENT_ENCODING;
/* Retrieve qop-options string from the challenge */
- if(!auth_digest_get_key_value(chlg, "qop=\"", qop, qlen, '\"'))
+ if(!auth_digest_get_key_value(chlg, "qop", qop, qlen))
return CURLE_BAD_CONTENT_ENCODING;
return CURLE_OK;