[PATCH v6 1/1] malloc: aarch64: Add ifuncs for malloc functions

Adhemerval Zanella Netto adhemerval.zanella@linaro.org
Mon Jun 15 12:37:54 GMT 2026



On 10/06/26 09:45, Yury Khrustalev wrote:
> Introduce ifuncs and resolvers for functions pertinent to the
> malloc interface on the AArch64 target: malloc, calloc, free,
> realloc, memalign, valloc, pvalloc, posix_memalign, aligned_alloc,
> free_sized, free_aligned_sized, malloc_usable_size.
> 
> A target can define the USE_MULTIARCH_MALLOC macro. In this case
> it must provide alternative aliases for the malloc functions that
> point to the ifuncs.
> 
> This implementation respects the --disable-multi-arch configure
> flag. If multi-arch support is disabled, the generic aliases
> are used on aarch64.
> 
> This patch contains aarch64-specific resolvers. At this moment they
> return core implementations but in the future they can be changed
> to support for features, e.g. to handle memory tagging.

LGTM, thanks.

Reviewed-by: Adhemerval Zanella  <adhemerval.zanella@linaro.org>

> ---
>  malloc/malloc-internal.h                  |   2 +
>  malloc/malloc.c                           | 155 +++------------------
>  sysdeps/aarch64/multiarch/Makefile        |  10 +-
>  sysdeps/aarch64/multiarch/malloc-ifuncs.c |  77 +++++++++++
>  sysdeps/aarch64/multiarch/malloc-ifuncs.h |  24 ++++
>  sysdeps/generic/malloc-api.h              | 161 ++++++++++++++++++++++
>  sysdeps/generic/malloc-ifuncs.h           |  36 +++++
>  7 files changed, 330 insertions(+), 135 deletions(-)
>  create mode 100644 sysdeps/aarch64/multiarch/malloc-ifuncs.c
>  create mode 100644 sysdeps/aarch64/multiarch/malloc-ifuncs.h
>  create mode 100644 sysdeps/generic/malloc-api.h
>  create mode 100644 sysdeps/generic/malloc-ifuncs.h
> 
> diff --git a/malloc/malloc-internal.h b/malloc/malloc-internal.h
> index a6340bfd88..29bc3734c6 100644
> --- a/malloc/malloc-internal.h
> +++ b/malloc/malloc-internal.h
> @@ -24,6 +24,8 @@
>  #include <malloc-size.h>
>  #include <hugepages.h>
>  #include <calloc-clear-memory.h>
> +#include <malloc-api.h>
> +#include <malloc-ifuncs.h>
>  
>  /* Called in the parent process before a fork.  */
>  void __malloc_fork_lock_parent (void) attribute_hidden;
> diff --git a/malloc/malloc.c b/malloc/malloc.c
> index 297e365627..a354576aca 100644
> --- a/malloc/malloc.c
> +++ b/malloc/malloc.c
> @@ -459,101 +459,10 @@ static int extra_mmap_prot = 0;
>  /* ---------- description of public routines ------------ */
>  
>  #if IS_IN (libc)
> -/*
> -  malloc(size_t n)
> -  Returns a pointer to a newly allocated chunk of at least n bytes, or null
> -  if no space is available. Additionally, on failure, errno is
> -  set to ENOMEM on ANSI C systems.
> -
> -  If n is zero, malloc returns a minimum-sized chunk. (The minimum
> -  size is 16 bytes on most 32bit systems, and 24 or 32 bytes on 64bit
> -  systems.)  On most systems, size_t is an unsigned type, so calls
> -  with negative arguments are interpreted as requests for huge amounts
> -  of space, which will often fail. The maximum supported value of n
> -  differs across systems, but is in all cases less than the maximum
> -  representable value of a size_t.
> -*/
> -void *__libc_malloc (size_t);
> -libc_hidden_proto (__libc_malloc)
>  
>  static void *__libc_calloc2 (size_t);
>  static void *__libc_malloc2 (size_t);
>  
> -/*
> -  free(void* p)
> -  Releases the chunk of memory pointed to by p, that had been previously
> -  allocated using malloc or a related routine such as realloc.
> -  It has no effect if p is null. It can have arbitrary (i.e., bad!)
> -  effects if p has already been freed.
> -
> -  Unless disabled (using mallopt), freeing very large spaces will
> -  when possible, automatically trigger operations that give
> -  back unused memory to the system, thus reducing program footprint.
> -*/
> -void     __libc_free(void*);
> -libc_hidden_proto (__libc_free)
> -
> -/*
> -  calloc(size_t n_elements, size_t element_size);
> -  Returns a pointer to n_elements * element_size bytes, with all locations
> -  set to zero.
> -*/
> -void*  __libc_calloc(size_t, size_t);
> -
> -/*
> -  realloc(void* p, size_t n)
> -  Returns a pointer to a chunk of size n that contains the same data
> -  as does chunk p up to the minimum of (n, p's size) bytes, or null
> -  if no space is available.
> -
> -  The returned pointer may or may not be the same as p. The algorithm
> -  prefers extending p when possible, otherwise it employs the
> -  equivalent of a malloc-copy-free sequence.
> -
> -  If p is null, realloc is equivalent to malloc.
> -
> -  If space is not available, realloc returns null, errno is set (if on
> -  ANSI) and p is NOT freed.
> -
> -  if n is for fewer bytes than already held by p, the newly unused
> -  space is lopped off and freed if possible.  Unless the #define
> -  REALLOC_ZERO_BYTES_FREES is set, realloc with a size argument of
> -  zero (re)allocates a minimum-sized chunk.
> -
> -  Large chunks that were internally obtained via mmap will always be
> -  grown using malloc-copy-free sequences unless the system supports
> -  MREMAP (currently only linux).
> -
> -  The old unix realloc convention of allowing the last-free'd chunk
> -  to be used as an argument to realloc is not supported.
> -*/
> -void*  __libc_realloc(void*, size_t);
> -libc_hidden_proto (__libc_realloc)
> -
> -/*
> -  memalign(size_t alignment, size_t n);
> -  Returns a pointer to a newly allocated chunk of n bytes, aligned
> -  in accord with the alignment argument.
> -
> -  The alignment argument should be a power of two. If the argument is
> -  not a power of two, the nearest greater power is used.
> -  8-byte alignment is guaranteed by normal malloc calls, so don't
> -  bother calling memalign with an argument of 8 or less.
> -
> -  Overreliance on memalign is a sure way to fragment space.
> -*/
> -void*  __libc_memalign(size_t, size_t);
> -libc_hidden_proto (__libc_memalign)
> -
> -/*
> -  valloc(size_t n);
> -  Equivalent to memalign(pagesize, n), where pagesize is the page
> -  size of the system. If the pagesize is unknown, 4096 is used.
> -*/
> -void*  __libc_valloc(size_t);
> -
> -
> -
>  /*
>    mallinfo()
>    Returns (by copy) a struct containing various summary statistics:
> @@ -578,14 +487,6 @@ libc_hidden_proto (__libc_mallinfo2)
>  
>  struct mallinfo __libc_mallinfo(void);
>  
> -
> -/*
> -  pvalloc(size_t n);
> -  Equivalent to valloc(minimum-page-that-holds(n)), that is,
> -  round up n to nearest pagesize.
> - */
> -void*  __libc_pvalloc(size_t);
> -
>  /*
>    malloc_trim(size_t pad);
>  
> @@ -612,23 +513,6 @@ void*  __libc_pvalloc(size_t);
>  */
>  int      __malloc_trim(size_t);
>  
> -/*
> -  malloc_usable_size(void* p);
> -
> -  Returns the number of bytes you can actually use in
> -  an allocated chunk, which may be more than you requested (although
> -  often not) due to alignment and minimum size constraints.
> -  You can use this many bytes without worrying about
> -  overwriting other allocated objects. This is not a particularly great
> -  programming practice. malloc_usable_size can be more useful in
> -  debugging and assertions, for example:
> -
> -  p = malloc(n);
> -  assert(malloc_usable_size(p) >= 256);
> -
> -*/
> -size_t   __malloc_usable_size(void*);
> -
>  /*
>    malloc_stats();
>    Prints on stderr the amount of space obtained from the system (both
> @@ -651,12 +535,6 @@ size_t   __malloc_usable_size(void*);
>  */
>  void     __malloc_stats(void);
>  
> -/*
> -  posix_memalign(void **memptr, size_t alignment, size_t size);
> -
> -  POSIX wrapper like memalign(), checking for validity of size.
> -*/
> -int      __posix_memalign(void **, size_t, size_t);
>  #endif /* IS_IN (libc) */
>  
>  /*
> @@ -3312,10 +3190,8 @@ __libc_memalign (size_t alignment, size_t bytes)
>  }
>  libc_hidden_def (__libc_memalign)
>  
> -/* For ISO C17.  */
>  void *
> -weak_function
> -aligned_alloc (size_t alignment, size_t bytes)
> +__aligned_alloc (size_t alignment, size_t bytes)
>  {
>  /* Starting with ISO C17 the standard requires an error for alignments
>     that are not supported.  Only integral powers of 2 are valid.  */
> @@ -3327,11 +3203,10 @@ aligned_alloc (size_t alignment, size_t bytes)
>  
>    return _mid_memalign (alignment, bytes);
>  }
> +libc_hidden_def (__aligned_alloc)
>  
> -/* For ISO C23.  */
>  void
> -weak_function
> -free_sized (void *ptr, __attribute_maybe_unused__ size_t size)
> +__free_sized (void *ptr, __attribute_maybe_unused__ size_t size)
>  {
>    /* We do not perform validation that size is the same as the original
>       requested size at this time. We leave that to the sanitizers.  We
> @@ -3340,11 +3215,10 @@ free_sized (void *ptr, __attribute_maybe_unused__ size_t size)
>  
>    free (ptr);
>  }
> +libc_hidden_def (__free_sized)
>  
> -/* For ISO C23.  */
>  void
> -weak_function
> -free_aligned_sized (void *ptr, __attribute_maybe_unused__ size_t alignment,
> +__free_aligned_sized (void *ptr, __attribute_maybe_unused__ size_t alignment,
>                      __attribute_maybe_unused__ size_t size)
>  {
>    /* We do not perform validation that size and alignment is the same as
> @@ -3354,6 +3228,7 @@ free_aligned_sized (void *ptr, __attribute_maybe_unused__ size_t alignment,
>  
>    free (ptr);
>  }
> +libc_hidden_def (__free_aligned_sized)
>  
>  static void *
>  _mid_memalign (size_t alignment, size_t bytes)
> @@ -3402,6 +3277,7 @@ __libc_valloc (size_t bytes)
>  {
>    return _mid_memalign (GLRO (dl_pagesize), bytes);
>  }
> +libc_hidden_def (__libc_valloc)
>  
>  void *
>  __libc_pvalloc (size_t bytes)
> @@ -3419,6 +3295,7 @@ __libc_pvalloc (size_t bytes)
>  
>    return _mid_memalign (pagesize, rounded_bytes & -pagesize);
>  }
> +libc_hidden_def (__libc_pvalloc)
>  
>  static void * __attribute_noinline__
>  __libc_calloc2 (size_t sz)
> @@ -3540,6 +3417,7 @@ __libc_calloc (size_t n, size_t elem_size)
>  #endif
>    return __libc_calloc2 (bytes);
>  }
> +libc_hidden_def (__libc_calloc)
>  #endif /* IS_IN (libc) */
>  
>  /*
> @@ -4532,6 +4410,7 @@ __malloc_usable_size (void *m)
>      return 0;
>    return musable (m);
>  }
> +libc_hidden_def (__malloc_usable_size)
>  #endif /* IS_IN (libc) */
>  
>  /*
> @@ -5059,6 +4938,7 @@ __posix_memalign (void **memptr, size_t alignment, size_t size)
>    *memptr = mem;
>    return 0;
>  }
> +libc_hidden_def (__posix_memalign)
>  #endif /* IS_IN (libc) */
>  
>  
> @@ -5221,6 +5101,9 @@ __malloc_info (int options, FILE *fp)
>  }
>  
>  #if IS_IN (libc)
> +
> +/* See sysdeps/generic/malloc-ifuncs.h for details.  */
> +# if !USE_MULTIARCH_MALLOC
>  strong_alias (__libc_malloc, malloc)
>  strong_alias (__libc_realloc, realloc)
>  strong_alias (__libc_free, free)
> @@ -5230,6 +5113,10 @@ weak_alias (__posix_memalign, posix_memalign)
>  weak_alias (__libc_valloc, valloc)
>  weak_alias (__libc_pvalloc, pvalloc)
>  weak_alias (__malloc_usable_size, malloc_usable_size)
> +weak_alias (__aligned_alloc, aligned_alloc)
> +weak_alias (__free_sized, free_sized)
> +weak_alias (__free_aligned_sized, free_aligned_sized)
> +#endif /* !USE_MULTIARCH_MALLOC */
>  
>  weak_alias (__malloc_info, malloc_info)
>  weak_alias (__libc_mallinfo, mallinfo)
> @@ -5239,9 +5126,11 @@ weak_alias (__malloc_stats, malloc_stats)
>  weak_alias (__malloc_trim, malloc_trim)
>  #endif /* IS_IN (libc) */
>  
> -#if SHLIB_COMPAT (libc, GLIBC_2_0, GLIBC_2_26)
> +#if !USE_MULTIARCH_MALLOC
> +# if SHLIB_COMPAT (libc, GLIBC_2_0, GLIBC_2_26)
>  compat_symbol (libc, __libc_free, cfree, GLIBC_2_0);
> -#endif
> +# endif
> +#endif /* !USE_MULTIARCH_MALLOC */
>  
>  /* ------------------------------------------------------------
>     History:
> diff --git a/sysdeps/aarch64/multiarch/Makefile b/sysdeps/aarch64/multiarch/Makefile
> index 38952655b1..a8a03a0491 100644
> --- a/sysdeps/aarch64/multiarch/Makefile
> +++ b/sysdeps/aarch64/multiarch/Makefile
> @@ -18,5 +18,11 @@ sysdep_routines += \
>    memset_zva64 \
>    strlen_asimd \
>    strlen_generic \
> -# sysdep_routines
> -endif
> +  # sysdep_routines
> +endif # ifeq ($(subdir),string)
> +
> +ifeq ($(subdir),malloc)
> +sysdep_routines += \
> +  malloc-ifuncs \
> +  # sysdep_routines
> +endif # ifeq ($(subdir),malloc)
> diff --git a/sysdeps/aarch64/multiarch/malloc-ifuncs.c b/sysdeps/aarch64/multiarch/malloc-ifuncs.c
> new file mode 100644
> index 0000000000..648fb617de
> --- /dev/null
> +++ b/sysdeps/aarch64/multiarch/malloc-ifuncs.c
> @@ -0,0 +1,77 @@
> +/* Code for ifunc resolvers for malloc: aarch64 version.
> +   Copyright (C) 2026 Free Software Foundation, Inc.
> +   This file is part of the GNU C Library.
> +
> +   The GNU C Library is free software; you can redistribute it and/or
> +   modify it under the terms of the GNU Lesser General Public
> +   License as published by the Free Software Foundation; either
> +   version 2.1 of the License, or (at your option) any later version.
> +
> +   The GNU C Library is distributed in the hope that it will be useful,
> +   but WITHOUT ANY WARRANTY; without even the implied warranty of
> +   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
> +   Lesser General Public License for more details.
> +
> +   You should have received a copy of the GNU Lesser General Public
> +   License along with the GNU C Library; if not, see
> +   <https://www.gnu.org/licenses/>.  */
> +
> +#if IS_IN (libc)
> +
> +#include <init-arch.h>
> +#include <malloc-api.h>
> +#include <shlib-compat.h>
> +
> +libc_ifunc_hidden (__libc_malloc, __libc_malloc_redirect,
> +		   __libc_malloc)
> +strong_alias (__libc_malloc_redirect, malloc)
> +
> +libc_ifunc_hidden (__libc_calloc, __libc_calloc_redirect,
> +		   __libc_calloc)
> +weak_alias (__libc_calloc_redirect, calloc)
> +
> +libc_ifunc_hidden (__libc_memalign, __libc_memalign_redirect,
> +		   __libc_memalign)
> +weak_alias (__libc_memalign_redirect, memalign)
> +
> +libc_ifunc_hidden (__libc_valloc, __libc_valloc_redirect,
> +		   __libc_valloc)
> +weak_alias (__libc_valloc_redirect, valloc)
> +
> +libc_ifunc_hidden (__libc_pvalloc, __libc_pvalloc_redirect,
> +		   __libc_pvalloc)
> +weak_alias (__libc_pvalloc_redirect, pvalloc)
> +
> +libc_ifunc_hidden (__libc_realloc, __libc_realloc_redirect,
> +		   __libc_realloc)
> +strong_alias (__libc_realloc_redirect, realloc)
> +
> +libc_ifunc_hidden (__libc_free, __libc_free_redirect,
> +		   __libc_free)
> +strong_alias (__libc_free_redirect, free)
> +
> +libc_ifunc_hidden (__malloc_usable_size, __malloc_usable_size_redirect,
> +		   __malloc_usable_size)
> +weak_alias (__malloc_usable_size_redirect, malloc_usable_size)
> +
> +libc_ifunc_hidden (__posix_memalign, __posix_memalign_redirect,
> +		   __posix_memalign)
> +weak_alias (__posix_memalign_redirect, posix_memalign)
> +
> +libc_ifunc_hidden (__aligned_alloc, __aligned_alloc_redirect,
> +		   __aligned_alloc)
> +weak_alias (__aligned_alloc_redirect, aligned_alloc)
> +
> +libc_ifunc_hidden (__free_sized, __free_sized_redirect,
> +		   __free_sized)
> +weak_alias (__free_sized_redirect, free_sized)
> +
> +libc_ifunc_hidden (__free_aligned_sized, __free_aligned_sized_redirect,
> +		   __free_aligned_sized)
> +weak_alias (__free_aligned_sized_redirect, free_aligned_sized)
> +
> +#endif /* IS_IN (libc) */
> +
> +#if SHLIB_COMPAT (libc, GLIBC_2_0, GLIBC_2_26)
> +compat_symbol (libc, __libc_free_redirect, cfree, GLIBC_2_0);
> +#endif
> diff --git a/sysdeps/aarch64/multiarch/malloc-ifuncs.h b/sysdeps/aarch64/multiarch/malloc-ifuncs.h
> new file mode 100644
> index 0000000000..572c2f229e
> --- /dev/null
> +++ b/sysdeps/aarch64/multiarch/malloc-ifuncs.h
> @@ -0,0 +1,24 @@
> +/* Definitions for ifunc resolvers for malloc: aarch64 version.
> +   Copyright (C) 2026 Free Software Foundation, Inc.
> +   This file is part of the GNU C Library.
> +
> +   The GNU C Library is free software; you can redistribute it and/or
> +   modify it under the terms of the GNU Lesser General Public
> +   License as published by the Free Software Foundation; either
> +   version 2.1 of the License, or (at your option) any later version.
> +
> +   The GNU C Library is distributed in the hope that it will be useful,
> +   but WITHOUT ANY WARRANTY; without even the implied warranty of
> +   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
> +   Lesser General Public License for more details.
> +
> +   You should have received a copy of the GNU Lesser General Public
> +   License along with the GNU C Library; if not, see
> +   <https://www.gnu.org/licenses/>.  */
> +
> +#ifndef _AARCH64_MALLOC_IFUNCS_H
> +#define _AARCH64_MALLOC_IFUNCS_H
> +
> +#define USE_MULTIARCH_MALLOC 1
> +
> +#endif /* _AARCH64_MALLOC_IFUNCS_H */
> diff --git a/sysdeps/generic/malloc-api.h b/sysdeps/generic/malloc-api.h
> new file mode 100644
> index 0000000000..2a243cc4af
> --- /dev/null
> +++ b/sysdeps/generic/malloc-api.h
> @@ -0,0 +1,161 @@
> +/* Malloc API functions.
> +   Copyright (C) 2026 Free Software Foundation, Inc.
> +   This file is part of the GNU C Library.
> +
> +   The GNU C Library is free software; you can redistribute it and/or
> +   modify it under the terms of the GNU Lesser General Public License as
> +   published by the Free Software Foundation; either version 2.1 of the
> +   License, or (at your option) any later version.
> +
> +   The GNU C Library is distributed in the hope that it will be useful,
> +   but WITHOUT ANY WARRANTY; without even the implied warranty of
> +   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
> +   Lesser General Public License for more details.
> +
> +   You should have received a copy of the GNU Lesser General Public
> +   License along with the GNU C Library; see the file COPYING.LIB.  If
> +   not, see <https://www.gnu.org/licenses/>.  */
> +
> +#ifndef _MALLOC_API_H
> +#define _MALLOC_API_H
> +
> +#include <stddef.h>
> +#include <libc-symbols.h>
> +
> +/*
> +  malloc(size_t n)
> +  Returns a pointer to a newly allocated chunk of at least n bytes, or null
> +  if no space is available. Additionally, on failure, errno is
> +  set to ENOMEM on ANSI C systems.
> +
> +  If n is zero, malloc returns a minimum-sized chunk. (The minimum
> +  size is 16 bytes on most 32bit systems, and 24 or 32 bytes on 64bit
> +  systems.)  On most systems, size_t is an unsigned type, so calls
> +  with negative arguments are interpreted as requests for huge amounts
> +  of space, which will often fail. The maximum supported value of n
> +  differs across systems, but is in all cases less than the maximum
> +  representable value of a size_t.
> +*/
> +void *__libc_malloc (size_t);
> +libc_hidden_proto (__libc_malloc)
> +
> +/*
> +  calloc(size_t n_elements, size_t element_size);
> +  Returns a pointer to n_elements * element_size bytes, with all locations
> +  set to zero.
> +*/
> +void *__libc_calloc (size_t, size_t);
> +libc_hidden_proto (__libc_calloc)
> +
> +/*
> +  memalign(size_t alignment, size_t n);
> +  Returns a pointer to a newly allocated chunk of n bytes, aligned
> +  in accord with the alignment argument.
> +
> +  The alignment argument should be a power of two. If the argument is
> +  not a power of two, the nearest greater power is used.
> +  8-byte alignment is guaranteed by normal malloc calls, so don't
> +  bother calling memalign with an argument of 8 or less.
> +
> +  Overreliance on memalign is a sure way to fragment space.
> +*/
> +void *__libc_memalign (size_t, size_t);
> +libc_hidden_proto (__libc_memalign)
> +
> +/*
> +  valloc(size_t n);
> +  Equivalent to memalign(pagesize, n), where pagesize is the page
> +  size of the system. If the pagesize is unknown, 4096 is used.
> +*/
> +void *__libc_valloc (size_t);
> +libc_hidden_proto (__libc_valloc)
> +
> +/*
> +  pvalloc(size_t n);
> +  Equivalent to valloc(minimum-page-that-holds(n)), that is,
> +  round up n to nearest pagesize.
> + */
> +void *__libc_pvalloc (size_t);
> +libc_hidden_proto (__libc_pvalloc)
> +
> +/*
> +  realloc(void* p, size_t n)
> +  Returns a pointer to a chunk of size n that contains the same data
> +  as does chunk p up to the minimum of (n, p's size) bytes, or null
> +  if no space is available.
> +
> +  The returned pointer may or may not be the same as p. The algorithm
> +  prefers extending p when possible, otherwise it employs the
> +  equivalent of a malloc-copy-free sequence.
> +
> +  If p is null, realloc is equivalent to malloc.
> +
> +  If space is not available, realloc returns null, errno is set (if on
> +  ANSI) and p is NOT freed.
> +
> +  if n is for fewer bytes than already held by p, the newly unused
> +  space is lopped off and freed if possible.  Unless the #define
> +  REALLOC_ZERO_BYTES_FREES is set, realloc with a size argument of
> +  zero (re)allocates a minimum-sized chunk.
> +
> +  Large chunks that were internally obtained via mmap will always be
> +  grown using malloc-copy-free sequences unless the system supports
> +  MREMAP (currently only linux).
> +
> +  The old unix realloc convention of allowing the last-free'd chunk
> +  to be used as an argument to realloc is not supported.
> +*/
> +void *__libc_realloc (void *, size_t);
> +libc_hidden_proto (__libc_realloc)
> +
> +/*
> +  free(void* p)
> +  Releases the chunk of memory pointed to by p, that had been previously
> +  allocated using malloc or a related routine such as realloc.
> +  It has no effect if p is null. It can have arbitrary (i.e., bad!)
> +  effects if p has already been freed.
> +
> +  Unless disabled (using mallopt), freeing very large spaces will
> +  when possible, automatically trigger operations that give
> +  back unused memory to the system, thus reducing program footprint.
> +*/
> +void __libc_free (void *);
> +libc_hidden_proto (__libc_free)
> +
> +/*
> +  malloc_usable_size(void* p);
> +
> +  Returns the number of bytes you can actually use in
> +  an allocated chunk, which may be more than you requested (although
> +  often not) due to alignment and minimum size constraints.
> +  You can use this many bytes without worrying about
> +  overwriting other allocated objects. This is not a particularly great
> +  programming practice. malloc_usable_size can be more useful in
> +  debugging and assertions, for example:
> +
> +  p = malloc(n);
> +  assert(malloc_usable_size(p) >= 256);
> +
> +*/
> +size_t __malloc_usable_size (void *);
> +libc_hidden_proto (__malloc_usable_size)
> +
> +/*
> +  posix_memalign(void **memptr, size_t alignment, size_t size);
> +
> +  POSIX wrapper like memalign(), checking for validity of size.
> +*/
> +int __posix_memalign (void **, size_t, size_t);
> +libc_hidden_proto (__posix_memalign)
> +
> +/* For ISO C17.  */
> +void *__aligned_alloc (size_t, size_t);
> +libc_hidden_proto (__aligned_alloc)
> +
> +/* For ISO C23.  */
> +void __free_sized (void *, size_t);
> +libc_hidden_proto (__free_sized)
> +void __free_aligned_sized (void *, size_t, size_t);
> +libc_hidden_proto (__free_aligned_sized)
> +
> +#endif /* _MALLOC_API_H */
> diff --git a/sysdeps/generic/malloc-ifuncs.h b/sysdeps/generic/malloc-ifuncs.h
> new file mode 100644
> index 0000000000..8fe88af95e
> --- /dev/null
> +++ b/sysdeps/generic/malloc-ifuncs.h
> @@ -0,0 +1,36 @@
> +/* Definitions for ifunc resolvers for malloc: generic version.
> +   Copyright (C) 2026 Free Software Foundation, Inc.
> +   This file is part of the GNU C Library.
> +
> +   The GNU C Library is free software; you can redistribute it and/or
> +   modify it under the terms of the GNU Lesser General Public
> +   License as published by the Free Software Foundation; either
> +   version 2.1 of the License, or (at your option) any later version.
> +
> +   The GNU C Library is distributed in the hope that it will be useful,
> +   but WITHOUT ANY WARRANTY; without even the implied warranty of
> +   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
> +   Lesser General Public License for more details.
> +
> +   You should have received a copy of the GNU Lesser General Public
> +   License along with the GNU C Library; if not, see
> +   <https://www.gnu.org/licenses/>.  */
> +
> +#ifndef _GENERIC_MALLOC_IFUNCS_H
> +#define _GENERIC_MALLOC_IFUNCS_H
> +
> +/* Targets that support GNU ifuncs should define this macro
> +   if they provide ifuncs for malloc functions.
> +
> +   When USE_MULTIARCH_MALLOC is defined as 1, the following
> +   functions should be implemented via ifuncs:
> +
> +     malloc, calloc, free, realloc
> +     memalign, valloc, pvalloc
> +     posix_memalign
> +     malloc_usable_size
> +     aligned_alloc, free_sized, free_aligned_sized
> +*/
> +#define USE_MULTIARCH_MALLOC 0
> +
> +#endif /* _GENERIC_MALLOC_IFUNCS_H */



More information about the Libc-alpha mailing list