[PATCH v3] malloc: Improve performance of __libc_malloc

DJ Delorie dj@redhat.com
Thu Mar 27 21:40:54 GMT 2025


This looks OK to me although I added some food for thought about
tcache_try_malloc().

Reviewed-by: DJ Delorie <dj@redhat.com>

Wilco Dijkstra <Wilco.Dijkstra@arm.com> writes:
> diff --git a/malloc/malloc.c b/malloc/malloc.c
> index 7e4c1399385051b1989cbc0ac14266d2138695af..a0bc733482532ce34684d0357cb9076b03ac8a52 100644
> --- a/malloc/malloc.c
> +++ b/malloc/malloc.c
> @@ -1325,6 +1325,9 @@ nextchunk-> +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
>  static __always_inline size_t
>  checked_request2size (size_t req) __nonnull (1)
>  {
> +  _Static_assert (PTRDIFF_MAX <= SIZE_MAX / 2,
> +                  "PTRDIFF_MAX is not more than half of SIZE_MAX");
> +

Ok.

>  
>  #if IS_IN (libc)
> -void *
> -__libc_malloc (size_t bytes)
> +
> +static void * __attribute_noinline__
> +__libc_malloc2 (size_t bytes)
>  {

Ok.

>    void *victim;
>  
> -  _Static_assert (PTRDIFF_MAX <= SIZE_MAX / 2,
> -                  "PTRDIFF_MAX is not more than half of SIZE_MAX");
> -

Not sure why this needs to move, but ok.

>    if (!__malloc_initialized)
>      ptmalloc_init ();
> -#if USE_TCACHE
> -  bool err = tcache_try_malloc (bytes, &victim);
> -
> -  if (err)
> -      return NULL;
>  
> -  if (victim)
> -      return tag_new_usable (victim);
> -#endif
> +  MAYBE_INIT_TCACHE ();

Ok.  Note that tcache_try_malloc() is only called once now (from calloc)
but it will be inlined there so no point manually inlining it
unless/until we wanted to do the same to calloc.

>            ar_ptr == arena_for_chunk (mem2chunk (victim)));
>    return victim;
>  }
> +
> +void *
> +__libc_malloc (size_t bytes)
> +{
> +#if USE_TCACHE
> +  size_t tc_idx = csize2tidx (checked_request2size (bytes));

checked_request2size could return zero (bad request) which we don't
check for here, but csize2tidx would compute a negative number and cast
to size_t, yielding a very large tcache idx, which would be checked for
in the usual max-bins check.  I think this is OK.

> +
> +  if (tcache_available (tc_idx))

This checks for too-large requests along with tcache present, so should
be ok.

> +    return tag_new_usable (tcache_get (tc_idx));

These can't fail, so ok.

> +#endif
> +
> +  return __libc_malloc2 (bytes);
> +}
>  libc_hidden_def (__libc_malloc)

Ok.



More information about the Libc-alpha mailing list