diff --git a/docs/reference/glib/glib-sections.txt b/docs/reference/glib/glib-sections.txt index 340e29dfa..c563a0bcd 100644 --- a/docs/reference/glib/glib-sections.txt +++ b/docs/reference/glib/glib-sections.txt @@ -1389,7 +1389,9 @@ g_mem_gc_friendly g_alloca +g_alloca0 g_newa +g_newa0 g_memmove diff --git a/gio/gsocket.c b/gio/gsocket.c index 43eb98692..2569b76f0 100644 --- a/gio/gsocket.c +++ b/gio/gsocket.c @@ -4570,8 +4570,7 @@ G_STMT_START { \ _msg->msg_control = NULL; \ else \ { \ - _msg->msg_control = g_alloca (_msg->msg_controllen); \ - memset (_msg->msg_control, '\0', _msg->msg_controllen); \ + _msg->msg_control = g_alloca0 (_msg->msg_controllen); \ } \ \ cmsg = CMSG_FIRSTHDR (_msg); \ diff --git a/glib/galloca.h b/glib/galloca.h index 014a0efcb..86f0d7665 100644 --- a/glib/galloca.h +++ b/glib/galloca.h @@ -30,6 +30,7 @@ #endif #include +#include #if defined(__BIONIC__) && defined (GLIB_HAVE_ALLOCA_H) # include @@ -94,6 +95,22 @@ G_END_DECLS * Returns: space for @size bytes, allocated on the stack */ #define g_alloca(size) alloca (size) + +/** + * g_alloca0: + * @size: number of bytes to allocate. + * + * Wraps g_alloca() and initializes allocated memory to zeroes. + * If @size is `0` it returns %NULL. + * + * Note that the @size argument will be evaluated multiple times. + * + * Returns: (nullable) (transfer full): space for @size bytes, allocated on the stack + * + * Since: 2.72 + */ +#define g_alloca0(size) ((size) == 0 ? NULL : memset (g_alloca (size), 0, (size))) + /** * g_newa: * @struct_type: Type of memory chunks to be allocated @@ -111,4 +128,18 @@ G_END_DECLS */ #define g_newa(struct_type, n_structs) ((struct_type*) g_alloca (sizeof (struct_type) * (gsize) (n_structs))) +/** + * g_newa0: + * @struct_type: the type of the elements to allocate. + * @n_structs: the number of elements to allocate. + * + * Wraps g_alloca0() in a more typesafe manner. + * + * Returns: (nullable) (transfer full): Pointer to stack space for @n_structs + * chunks of type @struct_type + * + * Since: 2.72 + */ +#define g_newa0(struct_type, n_structs) ((struct_type*) g_alloca0 (sizeof (struct_type) * (gsize) (n_structs))) + #endif /* __G_ALLOCA_H__ */ diff --git a/glib/ghmac.c b/glib/ghmac.c index 49fd272f0..54da9f936 100644 --- a/glib/ghmac.c +++ b/glib/ghmac.c @@ -127,11 +127,9 @@ g_hmac_new (GChecksumType digest_type, hmac->digesti = checksum; hmac->digesto = g_checksum_new (digest_type); - buffer = g_alloca (block_size); + buffer = g_alloca0 (block_size); pad = g_alloca (block_size); - memset (buffer, 0, block_size); - /* If the key is too long, hash it */ if (key_len > block_size) { diff --git a/glib/goption.c b/glib/goption.c index 8cb72376c..50812ea35 100644 --- a/glib/goption.c +++ b/glib/goption.c @@ -2113,8 +2113,7 @@ g_option_context_parse (GOptionContext *context, gboolean has_h_entry = context_has_h_entry (context); arg = (*argv)[i] + 1; arg_length = strlen (arg); - nulled_out = g_newa (gboolean, arg_length); - memset (nulled_out, 0, arg_length * sizeof (gboolean)); + nulled_out = g_newa0 (gboolean, arg_length); for (j = 0; j < arg_length; j++) { if (context->help_enabled && (arg[j] == '?' || diff --git a/gobject/gobject.c b/gobject/gobject.c index 7499d2ec4..1c95e3d0d 100644 --- a/gobject/gobject.c +++ b/gobject/gobject.c @@ -2163,8 +2163,7 @@ g_object_new_with_properties (GType object_type, params[count].pspec = pspec; /* Init GValue */ - params[count].value = g_newa (GValue, 1); - memset (params[count].value, 0, sizeof (GValue)); + params[count].value = g_newa0 (GValue, 1); g_value_init (params[count].value, G_VALUE_TYPE (&values[i])); g_value_copy (&values[i], params[count].value); diff --git a/gobject/gsignal.c b/gobject/gsignal.c index a106bbeec..9cabacd15 100644 --- a/gobject/gsignal.c +++ b/gobject/gsignal.c @@ -2266,8 +2266,7 @@ g_signal_chain_from_overridden_handler (gpointer instance, va_start (var_args, instance); signal_return_type = node->return_type; - instance_and_params = g_alloca (sizeof (GValue) * (n_params + 1)); - memset (instance_and_params, 0, sizeof (GValue) * (n_params + 1)); + instance_and_params = g_newa0 (GValue, n_params + 1); param_values = instance_and_params + 1; for (i = 0; i < node->n_params; i++) @@ -3462,8 +3461,7 @@ g_signal_emit_valist (gpointer instance, n_params = node->n_params; signal_return_type = node->return_type; - instance_and_params = g_alloca (sizeof (GValue) * (n_params + 1)); - memset (instance_and_params, 0, sizeof (GValue) * (n_params + 1)); + instance_and_params = g_newa0 (GValue, n_params + 1); param_values = instance_and_params + 1; for (i = 0; i < node->n_params; i++) diff --git a/tests/slice-test.c b/tests/slice-test.c index 055adba5c..4b1b5f710 100644 --- a/tests/slice-test.c +++ b/tests/slice-test.c @@ -95,8 +95,7 @@ test_memchunk_thread (gpointer data) } /* prepare for memchunk creation */ - memchunks = g_alloca (sizeof (memchunks[0]) * prime_size); - memset (memchunks, 0, sizeof (memchunks[0]) * prime_size); + memchunks = g_newa0 (GMemChunk*, prime_size); ps = g_new (guint8*, number_of_blocks); ss = g_new (guint, number_of_blocks);