From: Dan Winship Date: Fri, 1 Feb 2008 18:15:18 +0000 (+0000) Subject: Use GObject properties. (soup_address_new, soup_address_new_from_sockaddr) X-Git-Tag: LIBSOUP_2_3_2~16 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=87dff5a5be45fd038f2ec4e0b19599ef734ef5e2;p=platform%2Fupstream%2Flibsoup.git Use GObject properties. (soup_address_new, soup_address_new_from_sockaddr) * libsoup/soup-address.c: Use GObject properties. (soup_address_new, soup_address_new_from_sockaddr) (soup_address_new_any): Make these just wrappers around g_object_new. * libsoup/soup-message-body.c (soup_message_body_get_type): * libsoup/soup-message-headers.c (soup_message_headers_get_type): * libsoup/soup-server.c (soup_client_context_get_type): Register these as boxed types, for language bindings. * libsoup/soup-date.c (soup_date_get_type): * libsoup/soup-message-body.c (soup_buffer_get_type): * libsoup/soup-value-utils.c (soup_byte_array_get_type): * libsoup/soup-uri.c (soup_uri_get_type): Upgrade to the latest yummiest type-registering idiom. svn path=/trunk/; revision=1067 --- diff --git a/ChangeLog b/ChangeLog index 0a30792..033bde7 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,23 @@ 2008-02-01 Dan Winship + * libsoup/soup-address.c: Use GObject properties. + (soup_address_new, soup_address_new_from_sockaddr) + (soup_address_new_any): Make these just wrappers around + g_object_new. + + * libsoup/soup-message-body.c (soup_message_body_get_type): + * libsoup/soup-message-headers.c (soup_message_headers_get_type): + * libsoup/soup-server.c (soup_client_context_get_type): + Register these as boxed types, for language bindings. + + * libsoup/soup-date.c (soup_date_get_type): + * libsoup/soup-message-body.c (soup_buffer_get_type): + * libsoup/soup-value-utils.c (soup_byte_array_get_type): + * libsoup/soup-uri.c (soup_uri_get_type): Upgrade to the latest + yummiest type-registering idiom. + +2008-02-01 Dan Winship + * libsoup/soup-connection.c (soup_connection_disconnect): Reorganize this; emitting DISCONNECTED may cause the session to unref the connection, causing it to be destroyed, so do everything diff --git a/libsoup/soup-address.c b/libsoup/soup-address.c index 628f4ba..4c5178c 100644 --- a/libsoup/soup-address.c +++ b/libsoup/soup-address.c @@ -18,6 +18,7 @@ #include "soup-address.h" #include "soup-dns.h" +#include "soup-enum-types.h" #include "soup-marshal.h" #include "soup-misc.h" @@ -42,6 +43,18 @@ * both IPv4 and IPv6 addresses. **/ +enum { + PROP_0, + + PROP_NAME, + PROP_FAMILY, + PROP_PORT, + PROP_PHYSICAL, + PROP_SOCKADDR, + + LAST_PROP +}; + typedef struct { struct sockaddr *sockaddr; @@ -110,6 +123,14 @@ typedef struct { memcpy (SOUP_ADDRESS_GET_DATA (priv), data, length) +static GObject *constructor (GType type, + guint n_construct_properties, + GObjectConstructParam *construct_properties); +static void set_property (GObject *object, guint prop_id, + const GValue *value, GParamSpec *pspec); +static void get_property (GObject *object, guint prop_id, + GValue *value, GParamSpec *pspec); + G_DEFINE_TYPE (SoupAddress, soup_address, G_TYPE_OBJECT) static void @@ -148,7 +169,47 @@ soup_address_class_init (SoupAddressClass *address_class) g_type_class_add_private (address_class, sizeof (SoupAddressPrivate)); /* virtual method override */ + object_class->constructor = constructor; object_class->finalize = finalize; + object_class->set_property = set_property; + object_class->get_property = get_property; + + /* properties */ + g_object_class_install_property ( + object_class, PROP_NAME, + g_param_spec_string (SOUP_ADDRESS_NAME, + "Name", + "Hostname for this address", + NULL, + G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY)); + g_object_class_install_property ( + object_class, PROP_FAMILY, + g_param_spec_enum (SOUP_ADDRESS_FAMILY, + "Family", + "Address family for this address", + SOUP_TYPE_ADDRESS_FAMILY, + SOUP_ADDRESS_FAMILY_INVALID, + G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY)); + g_object_class_install_property ( + object_class, PROP_PORT, + g_param_spec_int (SOUP_ADDRESS_PORT, + "Port", + "Port for this address", + -1, 65535, -1, + G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY)); + g_object_class_install_property ( + object_class, PROP_PHYSICAL, + g_param_spec_string (SOUP_ADDRESS_PHYSICAL, + "Physical address", + "IP address for this address", + NULL, + G_PARAM_READABLE)); + g_object_class_install_property ( + object_class, PROP_SOCKADDR, + g_param_spec_pointer (SOUP_ADDRESS_SOCKADDR, + "sockaddr", + "struct sockaddr for this address", + G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY)); #ifdef G_OS_WIN32 /* This hopefully is a good place to call WSAStartup */ @@ -160,6 +221,119 @@ soup_address_class_init (SoupAddressClass *address_class) #endif } +static GObject * +constructor (GType type, + guint n_construct_properties, + GObjectConstructParam *construct_properties) +{ + GObject *addr; + SoupAddressPrivate *priv; + + addr = G_OBJECT_CLASS (soup_address_parent_class)->constructor ( + type, n_construct_properties, construct_properties); + if (!addr) + return NULL; + priv = SOUP_ADDRESS_GET_PRIVATE (addr); + + if (priv->name) { + if (!priv->sockaddr) + priv->lookup = soup_dns_lookup_name (priv->name); + } else if (priv->sockaddr) + priv->lookup = soup_dns_lookup_address (priv->sockaddr); + else { + g_object_unref (addr); + return NULL; + } + + return addr; +} + +static void +set_property (GObject *object, guint prop_id, + const GValue *value, GParamSpec *pspec) +{ + SoupAddressPrivate *priv = SOUP_ADDRESS_GET_PRIVATE (object); + SoupAddressFamily family; + struct sockaddr *sa; + int len, port; + + /* This is a mess because the properties are mostly orthogonal, + * but g_object_constructor wants to set a default value for each + * of them. + */ + + switch (prop_id) { + case PROP_NAME: + priv->name = g_value_dup_string (value); + break; + + case PROP_FAMILY: + family = g_value_get_enum (value); + if (family == SOUP_ADDRESS_FAMILY_INVALID) + return; + g_return_if_fail (SOUP_ADDRESS_FAMILY_IS_VALID (family)); + g_return_if_fail (priv->sockaddr == NULL); + + priv->sockaddr = g_malloc0 (SOUP_ADDRESS_FAMILY_SOCKADDR_SIZE (family)); + SOUP_ADDRESS_SET_FAMILY (priv, family); + SOUP_ADDRESS_SET_PORT (priv, htons (priv->port)); + break; + + case PROP_PORT: + port = g_value_get_int (value); + if (port == -1) + return; + g_return_if_fail (SOUP_ADDRESS_PORT_IS_VALID (port)); + + priv->port = port; + if (priv->sockaddr) + SOUP_ADDRESS_SET_PORT (priv, htons (port)); + break; + + case PROP_SOCKADDR: + sa = g_value_get_pointer (value); + if (!sa) + return; + g_return_if_fail (priv->sockaddr == NULL); + + len = SOUP_ADDRESS_FAMILY_SOCKADDR_SIZE (sa->sa_family); + priv->sockaddr = g_memdup (sa, len); + priv->port = ntohs (SOUP_ADDRESS_GET_PORT (priv)); + break; + default: + break; + } +} + +static void +get_property (GObject *object, guint prop_id, + GValue *value, GParamSpec *pspec) +{ + SoupAddressPrivate *priv = SOUP_ADDRESS_GET_PRIVATE (object); + + switch (prop_id) { + case PROP_NAME: + g_value_set_string (value, priv->name); + break; + case PROP_FAMILY: + if (priv->sockaddr) + g_value_set_enum (value, SOUP_ADDRESS_GET_FAMILY (priv)); + else + g_value_set_enum (value, 0); + break; + case PROP_PORT: + g_value_set_int (value, priv->port); + break; + case PROP_PHYSICAL: + g_value_set_string (value, soup_address_get_physical (SOUP_ADDRESS (object))); + break; + case PROP_SOCKADDR: + g_value_set_pointer (value, priv->sockaddr); + break; + default: + break; + } +} /** * soup_address_new: @@ -176,19 +350,13 @@ soup_address_class_init (SoupAddressClass *address_class) SoupAddress * soup_address_new (const char *name, guint port) { - SoupAddress *addr; - SoupAddressPrivate *priv; - g_return_val_if_fail (name != NULL, NULL); g_return_val_if_fail (SOUP_ADDRESS_PORT_IS_VALID (port), NULL); - addr = g_object_new (SOUP_TYPE_ADDRESS, NULL); - priv = SOUP_ADDRESS_GET_PRIVATE (addr); - priv->name = g_strdup (name); - priv->port = port; - priv->lookup = soup_dns_lookup_name (priv->name); - - return addr; + return g_object_new (SOUP_TYPE_ADDRESS, + SOUP_ADDRESS_NAME, name, + SOUP_ADDRESS_PORT, port, + NULL); } /** @@ -204,20 +372,13 @@ soup_address_new (const char *name, guint port) SoupAddress * soup_address_new_from_sockaddr (struct sockaddr *sa, int len) { - SoupAddress *addr; - SoupAddressPrivate *priv; - g_return_val_if_fail (sa != NULL, NULL); g_return_val_if_fail (SOUP_ADDRESS_FAMILY_IS_VALID (sa->sa_family), NULL); g_return_val_if_fail (len == SOUP_ADDRESS_FAMILY_SOCKADDR_SIZE (sa->sa_family), NULL); - addr = g_object_new (SOUP_TYPE_ADDRESS, NULL); - priv = SOUP_ADDRESS_GET_PRIVATE (addr); - priv->sockaddr = g_memdup (sa, len); - priv->port = ntohs (SOUP_ADDRESS_GET_PORT (priv)); - priv->lookup = soup_dns_lookup_address (priv->sockaddr); - - return addr; + return g_object_new (SOUP_TYPE_ADDRESS, + SOUP_ADDRESS_SOCKADDR, sa, + NULL); } /** @@ -252,22 +413,13 @@ soup_address_new_from_sockaddr (struct sockaddr *sa, int len) SoupAddress * soup_address_new_any (SoupAddressFamily family, guint port) { - SoupAddress *addr; - SoupAddressPrivate *priv; - g_return_val_if_fail (SOUP_ADDRESS_FAMILY_IS_VALID (family), NULL); g_return_val_if_fail (SOUP_ADDRESS_PORT_IS_VALID (port), NULL); - addr = g_object_new (SOUP_TYPE_ADDRESS, NULL); - priv = SOUP_ADDRESS_GET_PRIVATE (addr); - priv->port = port; - - priv->sockaddr = g_malloc0 (SOUP_ADDRESS_FAMILY_SOCKADDR_SIZE (family)); - SOUP_ADDRESS_SET_FAMILY (priv, family); - SOUP_ADDRESS_SET_PORT (priv, htons (port)); - priv->lookup = soup_dns_lookup_address (priv->sockaddr); - - return addr; + return g_object_new (SOUP_TYPE_ADDRESS, + SOUP_ADDRESS_FAMILY, family, + SOUP_ADDRESS_PORT, port, + NULL); } /** diff --git a/libsoup/soup-address.h b/libsoup/soup-address.h index 92e71fe..54f8b67 100644 --- a/libsoup/soup-address.h +++ b/libsoup/soup-address.h @@ -37,12 +37,20 @@ typedef struct { void (*_libsoup_reserved4) (void); } SoupAddressClass; +#define SOUP_ADDRESS_NAME "name" +#define SOUP_ADDRESS_FAMILY "family" +#define SOUP_ADDRESS_PORT "port" +#define SOUP_ADDRESS_PHYSICAL "physical" +#define SOUP_ADDRESS_SOCKADDR "sockaddr" + /* gtk-doc gets confused if there's an #ifdef inside the typedef */ #ifndef AF_INET6 #define AF_INET6 -1 #endif typedef enum { + SOUP_ADDRESS_FAMILY_INVALID = -1, + SOUP_ADDRESS_FAMILY_IPV4 = AF_INET, SOUP_ADDRESS_FAMILY_IPV6 = AF_INET6 } SoupAddressFamily; diff --git a/libsoup/soup-date.c b/libsoup/soup-date.c index 02a26ec..52fcbd4 100644 --- a/libsoup/soup-date.c +++ b/libsoup/soup-date.c @@ -54,15 +54,16 @@ static const int days_before[] = { GType soup_date_get_type (void) { - static GType type = 0; + static volatile gsize type_volatile = 0; - if (type == 0) { - type = g_boxed_type_register_static ( + if (g_once_init_enter (&type_volatile)) { + GType type = g_boxed_type_register_static ( g_intern_static_string ("SoupDate"), - (GBoxedCopyFunc)soup_date_copy, - (GBoxedFreeFunc)soup_date_free); + (GBoxedCopyFunc) soup_date_copy, + (GBoxedFreeFunc) soup_date_free); + g_once_init_leave (&type_volatile, type); } - return type; + return type_volatile; } /** diff --git a/libsoup/soup-message-body.c b/libsoup/soup-message-body.c index 20b8980..60e1271 100644 --- a/libsoup/soup-message-body.c +++ b/libsoup/soup-message-body.c @@ -186,15 +186,16 @@ soup_buffer_free (SoupBuffer *buffer) GType soup_buffer_get_type (void) { - static GType type = 0; + static volatile gsize type_volatile = 0; - if (type == 0) { - type = g_boxed_type_register_static ( + if (g_once_init_enter (&type_volatile)) { + GType type = g_boxed_type_register_static ( g_intern_static_string ("SoupBuffer"), - (GBoxedCopyFunc)soup_buffer_copy, - (GBoxedFreeFunc)soup_buffer_free); + (GBoxedCopyFunc) soup_buffer_copy, + (GBoxedFreeFunc) soup_buffer_free); + g_once_init_leave (&type_volatile, type); } - return type; + return type_volatile; } @@ -222,6 +223,7 @@ typedef struct { SoupMessageBody body; GSList *chunks, *last; SoupBuffer *flattened; + int ref_count; } SoupMessageBodyPrivate; /** @@ -235,7 +237,12 @@ typedef struct { SoupMessageBody * soup_message_body_new (void) { - return (SoupMessageBody *)g_slice_new0 (SoupMessageBodyPrivate); + SoupMessageBodyPrivate *priv; + + priv = g_slice_new0 (SoupMessageBodyPrivate); + priv->ref_count = 1; + + return (SoupMessageBody *)priv; } static void @@ -421,11 +428,37 @@ soup_message_body_get_chunk (SoupMessageBody *body, goffset offset) } } +static SoupMessageBody * +soup_message_body_copy (SoupMessageBody *body) +{ + SoupMessageBodyPrivate *priv = (SoupMessageBodyPrivate *)body; + + priv->ref_count++; + return body; +} + void soup_message_body_free (SoupMessageBody *body) { SoupMessageBodyPrivate *priv = (SoupMessageBodyPrivate *)body; - soup_message_body_truncate (body); - g_slice_free (SoupMessageBodyPrivate, priv); + if (--priv->ref_count == 0) { + soup_message_body_truncate (body); + g_slice_free (SoupMessageBodyPrivate, priv); + } +} + +GType +soup_message_body_get_type (void) +{ + static volatile gsize type_volatile = 0; + + if (g_once_init_enter (&type_volatile)) { + GType type = g_boxed_type_register_static ( + g_intern_static_string ("SoupMessageBody"), + (GBoxedCopyFunc) soup_message_body_copy, + (GBoxedFreeFunc) soup_message_body_free); + g_once_init_leave (&type_volatile, type); + } + return type_volatile; } diff --git a/libsoup/soup-message-body.h b/libsoup/soup-message-body.h index 329c773..cbb9c6f 100644 --- a/libsoup/soup-message-body.h +++ b/libsoup/soup-message-body.h @@ -40,6 +40,9 @@ typedef struct { goffset length; } SoupMessageBody; +GType soup_message_body_get_type (void); +#define SOUP_TYPE_MESSAGE_BODY (soup_message_body_get_type ()) + SoupMessageBody *soup_message_body_new (void); void soup_message_body_append (SoupMessageBody *body, diff --git a/libsoup/soup-message-headers.c b/libsoup/soup-message-headers.c index bd827c1..6a9eb21 100644 --- a/libsoup/soup-message-headers.c +++ b/libsoup/soup-message-headers.c @@ -35,6 +35,8 @@ struct SoupMessageHeaders { SoupEncoding encoding; goffset content_length; SoupExpectation expectations; + + int ref_count; }; /** @@ -57,7 +59,15 @@ soup_message_headers_new (SoupMessageHeadersType type) hdrs->array = g_array_sized_new (TRUE, FALSE, sizeof (SoupHeader), 5); hdrs->type = type; hdrs->encoding = -1; + hdrs->ref_count = 1; + + return hdrs; +} +static SoupMessageHeaders * +soup_message_headers_copy (SoupMessageHeaders *hdrs) +{ + hdrs->ref_count++; return hdrs; } @@ -70,11 +80,28 @@ soup_message_headers_new (SoupMessageHeadersType type) void soup_message_headers_free (SoupMessageHeaders *hdrs) { - soup_message_headers_clear (hdrs); - g_array_free (hdrs->array, TRUE); - if (hdrs->concat) - g_hash_table_destroy (hdrs->concat); - g_slice_free (SoupMessageHeaders, hdrs); + if (--hdrs->ref_count == 0) { + soup_message_headers_clear (hdrs); + g_array_free (hdrs->array, TRUE); + if (hdrs->concat) + g_hash_table_destroy (hdrs->concat); + g_slice_free (SoupMessageHeaders, hdrs); + } +} + +GType +soup_message_headers_get_type (void) +{ + static volatile gsize type_volatile = 0; + + if (g_once_init_enter (&type_volatile)) { + GType type = g_boxed_type_register_static ( + g_intern_static_string ("SoupMessageHeaders"), + (GBoxedCopyFunc) soup_message_headers_copy, + (GBoxedFreeFunc) soup_message_headers_free); + g_once_init_leave (&type_volatile, type); + } + return type_volatile; } /** diff --git a/libsoup/soup-message-headers.h b/libsoup/soup-message-headers.h index b6eb94e..68baf52 100644 --- a/libsoup/soup-message-headers.h +++ b/libsoup/soup-message-headers.h @@ -9,6 +9,9 @@ #include typedef struct SoupMessageHeaders SoupMessageHeaders; +GType soup_message_headers_get_type (void); +#define SOUP_TYPE_MESSAGE_HEADERS (soup_message_headers_get_type ()) + typedef enum { SOUP_MESSAGE_HEADERS_REQUEST, SOUP_MESSAGE_HEADERS_RESPONSE diff --git a/libsoup/soup-server.c b/libsoup/soup-server.c index b8bf3bd..d3b0be4 100644 --- a/libsoup/soup-server.c +++ b/libsoup/soup-server.c @@ -76,6 +76,8 @@ struct SoupClientContext { SoupSocket *sock; SoupAuthDomain *auth_domain; char *auth_user; + + int ref_count; }; typedef struct { @@ -552,6 +554,18 @@ soup_server_get_listener (SoupServer *server) static void start_request (SoupServer *, SoupClientContext *); +static SoupClientContext * +soup_client_context_new (SoupServer *server, SoupSocket *sock) +{ + SoupClientContext *client = g_slice_new0 (SoupClientContext); + + client->server = server; + client->sock = sock; + client->ref_count = 1; + + return client; +} + static void soup_client_context_cleanup (SoupClientContext *client) { @@ -565,6 +579,22 @@ soup_client_context_cleanup (SoupClientContext *client) } } +static SoupClientContext * +soup_client_context_ref (SoupClientContext *client) +{ + client->ref_count++; + return client; +} + +static void +soup_client_context_unref (SoupClientContext *client) +{ + if (--client->ref_count == 0) { + soup_client_context_cleanup (client); + g_slice_free (SoupClientContext, client); + } +} + static void request_finished (SoupMessage *msg, SoupClientContext *client) { @@ -582,7 +612,7 @@ request_finished (SoupMessage *msg, SoupClientContext *client) start_request (server, client); } else { soup_socket_disconnect (sock); - g_slice_free (SoupClientContext, client); + soup_client_context_unref (client); } g_object_unref (msg); g_object_unref (sock); @@ -740,10 +770,9 @@ new_connection (SoupSocket *listner, SoupSocket *sock, gpointer user_data) { SoupServer *server = user_data; SoupServerPrivate *priv = SOUP_SERVER_GET_PRIVATE (server); - SoupClientContext *client = g_slice_new0 (SoupClientContext); + SoupClientContext *client; - client->server = server; - client->sock = g_object_ref (sock); + client = soup_client_context_new (server, g_object_ref (sock)); priv->client_socks = g_slist_prepend (priv->client_socks, sock); g_signal_connect (sock, "disconnected", G_CALLBACK (socket_disconnected), server); @@ -876,11 +905,16 @@ soup_server_get_async_context (SoupServer *server) GType soup_client_context_get_type (void) { - static GType type = 0; - - if (type == 0) - type = g_pointer_type_register_static ("SoupClientContext"); - return type; + static volatile gsize type_volatile = 0; + + if (g_once_init_enter (&type_volatile)) { + GType type = g_boxed_type_register_static ( + g_intern_static_string ("SoupClientContext"), + (GBoxedCopyFunc) soup_client_context_ref, + (GBoxedFreeFunc) soup_client_context_unref); + g_once_init_leave (&type_volatile, type); + } + return type_volatile; } /** diff --git a/libsoup/soup-server.h b/libsoup/soup-server.h index bfa0f2e..e9e426c 100644 --- a/libsoup/soup-server.h +++ b/libsoup/soup-server.h @@ -31,10 +31,14 @@ typedef struct { GObjectClass parent_class; /* signals */ - void (*request_started) (SoupServer *, SoupMessage *, SoupClientContext *); - void (*request_read) (SoupServer *, SoupMessage *, SoupClientContext *); - void (*request_finished) (SoupServer *, SoupMessage *, SoupClientContext *); - void (*request_aborted) (SoupServer *, SoupMessage *, SoupClientContext *); + void (*request_started) (SoupServer *server, SoupMessage *msg, + SoupClientContext *client); + void (*request_read) (SoupServer *server, SoupMessage *msg, + SoupClientContext *client); + void (*request_finished) (SoupServer *server, SoupMessage *msg, + SoupClientContext *client); + void (*request_aborted) (SoupServer *server, SoupMessage *msg, + SoupClientContext *client); /* Padding for future expansion */ void (*_libsoup_reserved1) (void); diff --git a/libsoup/soup-session.h b/libsoup/soup-session.h index cc63dcf..e4c05ae 100644 --- a/libsoup/soup-session.h +++ b/libsoup/soup-session.h @@ -31,9 +31,10 @@ typedef struct { GObjectClass parent_class; /* signals */ - void (*request_started) (SoupSession *, SoupMessage *, SoupSocket *); - void (*authenticate) (SoupSession *, SoupMessage *, - SoupAuth *, gboolean); + void (*request_started) (SoupSession *session, SoupMessage *msg, + SoupSocket *socket); + void (*authenticate) (SoupSession *session, SoupMessage *msg, + SoupAuth *auth, gboolean retrying); /* methods */ void (*queue_message) (SoupSession *session, SoupMessage *msg, diff --git a/libsoup/soup-uri.c b/libsoup/soup-uri.c index 63bf93e..deeb4d5 100644 --- a/libsoup/soup-uri.c +++ b/libsoup/soup-uri.c @@ -934,13 +934,14 @@ soup_uri_set_fragment (SoupURI *uri, const char *fragment) GType soup_uri_get_type (void) { - static GType type = 0; + static volatile gsize type_volatile = 0; - if (G_UNLIKELY (type == 0)) { - type = g_boxed_type_register_static ( + if (g_once_init_enter (&type_volatile)) { + GType type = g_boxed_type_register_static ( g_intern_static_string ("SoupURI"), - (GBoxedCopyFunc)soup_uri_copy, - (GBoxedFreeFunc)soup_uri_free); + (GBoxedCopyFunc) soup_uri_copy, + (GBoxedFreeFunc) soup_uri_free); + g_once_init_leave (&type_volatile, type); } - return type; + return type_volatile; } diff --git a/libsoup/soup-value-utils.c b/libsoup/soup-value-utils.c index ce0b7d4..34f2133 100644 --- a/libsoup/soup-value-utils.c +++ b/libsoup/soup-value-utils.c @@ -463,13 +463,14 @@ soup_byte_array_free (GByteArray *ba) GType soup_byte_array_get_type (void) { - static GType type = 0; + static volatile gsize type_volatile = 0; - if (type == 0) { - type = g_boxed_type_register_static ( + if (g_once_init_enter (&type_volatile)) { + GType type = g_boxed_type_register_static ( g_intern_static_string ("GByteArray"), - (GBoxedCopyFunc)soup_byte_array_copy, - (GBoxedFreeFunc)soup_byte_array_free); + (GBoxedCopyFunc) soup_byte_array_copy, + (GBoxedFreeFunc) soup_byte_array_free); + g_once_init_leave (&type_volatile, type); } - return type; + return type_volatile; }