}
}
-static void freecookie(struct Cookie *co)
+static void freecookie(struct Cookie *co, bool maintoo)
{
curlx_free(co->domain);
curlx_free(co->path);
curlx_free(co->spath);
curlx_free(co->name);
curlx_free(co->value);
- curlx_free(co);
+ if(maintoo)
+ curlx_free(co);
}
static bool cookie_tailmatch(const char *cookie_domain,
if(co->expires) {
if(co->expires < now) {
Curl_node_remove(n);
- freecookie(co);
+ freecookie(co, TRUE);
ci->numcookies--;
}
else if(co->expires < ci->next_expiration)
Curl_node_remove(replace_n);
/* free the old cookie */
- freecookie(repl);
+ freecookie(repl, TRUE);
}
*replacep = replace_old;
return TRUE;
unless set */
bool secure) /* TRUE if connection is over secure origin */
{
+ struct Cookie comem;
struct Cookie *co;
size_t myhash;
CURLcode result;
if(data->req.setcookies >= MAX_SET_COOKIE_AMOUNT)
return CURLE_OK; /* silently ignore */
- /* First, alloc and init a new struct for it */
- co = curlx_calloc(1, sizeof(struct Cookie));
- if(!co)
- return CURLE_OUT_OF_MEMORY; /* bail out if we are this low on memory */
+ co = &comem;
+ memset(co, 0, sizeof(comem));
if(httpheader)
result = parse_cookie_header(data, co, ci, &okay,
if(!replace_existing(data, co, ci, secure, &replaces))
goto fail;
+ /* clone the stack struct into heap */
+ co = Curl_memdup(&comem, sizeof(comem));
+ if(!co) {
+ co = &comem;
+ goto fail; /* bail out if we are this low on memory */
+ }
+
/* add this cookie to the list */
myhash = cookiehash(co->domain);
Curl_llist_append(&ci->cookielist[myhash], co, &co->node);
return result;
fail:
- freecookie(co);
+ freecookie(co, FALSE);
return result;
}
struct Cookie *c = Curl_node_elem(n);
struct Curl_llist_node *e = Curl_node_next(n);
Curl_node_remove(n);
- freecookie(c);
+ freecookie(c, TRUE);
n = e;
}
}
e = Curl_node_next(n); /* in case the node is removed, get it early */
if(!curr->expires) {
Curl_node_remove(n);
- freecookie(curr);
+ freecookie(curr, TRUE);
ci->numcookies--;
}
}