pull: Fix use-after-free in async fetcher
Refcount the pending data structure.
This commit is contained in:
parent
31b439b84c
commit
a98ca05676
|
|
@ -32,6 +32,7 @@ typedef enum {
|
||||||
} OstreeFetcherState;
|
} OstreeFetcherState;
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
|
guint refcount;
|
||||||
OstreeFetcher *self;
|
OstreeFetcher *self;
|
||||||
SoupURI *uri;
|
SoupURI *uri;
|
||||||
|
|
||||||
|
|
@ -52,6 +53,11 @@ typedef struct {
|
||||||
static void
|
static void
|
||||||
pending_uri_free (OstreeFetcherPendingURI *pending)
|
pending_uri_free (OstreeFetcherPendingURI *pending)
|
||||||
{
|
{
|
||||||
|
g_assert (pending->refcount > 0);
|
||||||
|
pending->refcount--;
|
||||||
|
if (pending->refcount > 0)
|
||||||
|
return;
|
||||||
|
|
||||||
g_clear_object (&pending->self);
|
g_clear_object (&pending->self);
|
||||||
g_clear_object (&pending->tmpfile);
|
g_clear_object (&pending->tmpfile);
|
||||||
g_clear_object (&pending->request);
|
g_clear_object (&pending->request);
|
||||||
|
|
@ -116,10 +122,8 @@ on_request_unqueued (SoupSession *session,
|
||||||
{
|
{
|
||||||
OstreeFetcher *self = user_data;
|
OstreeFetcher *self = user_data;
|
||||||
if (msg == self->sending_message)
|
if (msg == self->sending_message)
|
||||||
{
|
self->sending_message = NULL;
|
||||||
self->sending_message = NULL;
|
g_hash_table_remove (self->message_to_request, msg);
|
||||||
g_hash_table_remove (self->message_to_request, msg);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
|
@ -136,7 +140,8 @@ ostree_fetcher_init (OstreeFetcher *self)
|
||||||
g_signal_connect (self->session, "request-unqueued",
|
g_signal_connect (self->session, "request-unqueued",
|
||||||
G_CALLBACK (on_request_unqueued), self);
|
G_CALLBACK (on_request_unqueued), self);
|
||||||
|
|
||||||
self->message_to_request = g_hash_table_new_full (NULL, NULL, (GDestroyNotify)g_object_unref, NULL);
|
self->message_to_request = g_hash_table_new_full (NULL, NULL, (GDestroyNotify)g_object_unref,
|
||||||
|
(GDestroyNotify)pending_uri_free);
|
||||||
}
|
}
|
||||||
|
|
||||||
OstreeFetcher *
|
OstreeFetcher *
|
||||||
|
|
@ -222,12 +227,14 @@ ostree_fetcher_request_uri_async (OstreeFetcher *self,
|
||||||
GError *local_error = NULL;
|
GError *local_error = NULL;
|
||||||
|
|
||||||
pending = g_new0 (OstreeFetcherPendingURI, 1);
|
pending = g_new0 (OstreeFetcherPendingURI, 1);
|
||||||
|
pending->refcount = 1;
|
||||||
pending->self = g_object_ref (self);
|
pending->self = g_object_ref (self);
|
||||||
pending->uri = soup_uri_copy (uri);
|
pending->uri = soup_uri_copy (uri);
|
||||||
pending->cancellable = cancellable ? g_object_ref (cancellable) : NULL;
|
pending->cancellable = cancellable ? g_object_ref (cancellable) : NULL;
|
||||||
pending->request = soup_requester_request_uri (self->requester, uri, &local_error);
|
pending->request = soup_requester_request_uri (self->requester, uri, &local_error);
|
||||||
g_assert_no_error (local_error);
|
g_assert_no_error (local_error);
|
||||||
|
|
||||||
|
pending->refcount++;
|
||||||
g_hash_table_insert (self->message_to_request,
|
g_hash_table_insert (self->message_to_request,
|
||||||
soup_request_http_get_message ((SoupRequestHTTP*)pending->request),
|
soup_request_http_get_message ((SoupRequestHTTP*)pending->request),
|
||||||
pending);
|
pending);
|
||||||
|
|
@ -240,7 +247,6 @@ ostree_fetcher_request_uri_async (OstreeFetcher *self,
|
||||||
|
|
||||||
soup_request_send_async (pending->request, cancellable,
|
soup_request_send_async (pending->request, cancellable,
|
||||||
on_request_sent, pending);
|
on_request_sent, pending);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
GFile *
|
GFile *
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue