[PATCH 1/4] aarch64: Optimise AdvSIMD log1pf

Adhemerval Zanella Netto adhemerval.zanella@linaro.org
Thu Dec 4 11:28:56 GMT 2025



On 19/11/25 11:11, James Chesterman wrote:
> Optimise AdvSIMD log1pf by vectorising the special case and by
> reducing the range of values passed to the special case.
> Previously, high values such as 0x1.1p127 where treated as special
> cases, but now the special cases are for when the input is:
> Less than or equal to -1
> +/- INFINITY
> +/- NaN
> ---
> OK for master? If so, please commit for me as I don't have commit rights.
> Thanks,
> James

LGTM, thanks.

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

>  sysdeps/aarch64/fpu/log1pf_advsimd.c | 48 ++++++++++++++++++++--------
>  1 file changed, 35 insertions(+), 13 deletions(-)
> 
> diff --git a/sysdeps/aarch64/fpu/log1pf_advsimd.c b/sysdeps/aarch64/fpu/log1pf_advsimd.c
> index 79e33e4aae..537de5d511 100644
> --- a/sysdeps/aarch64/fpu/log1pf_advsimd.c
> +++ b/sysdeps/aarch64/fpu/log1pf_advsimd.c
> @@ -20,28 +20,50 @@
>  #include "v_math.h"
>  #include "v_log1pf_inline.h"
>  
> -const static struct v_log1pf_data data = V_LOG1PF_CONSTANTS_TABLE;
> +static const struct data
> +{
> +  struct v_log1pf_data d;
> +  float32x4_t nan, pinf, minf;
> +} data = {
> +  .d = V_LOG1PF_CONSTANTS_TABLE,
> +  .nan = V4 (NAN),
> +  .pinf = V4 (INFINITY),
> +  .minf = V4 (-INFINITY),
> +};
>  
> -static float32x4_t NOINLINE VPCS_ATTR
> -special_case (float32x4_t x, uint32x4_t cmp)
> +static inline float32x4_t
> +special_case (float32x4_t x, uint32x4_t cmp, const struct data *d)
>  {
> -  return v_call_f32 (log1pf, x, log1pf_inline (x, ptr_barrier (&data)), cmp);
> +  float32x4_t y = log1pf_inline (x, ptr_barrier (&d->d));
> +  y = vbslq_f32 (cmp, d->nan, y);
> +  uint32x4_t ret_pinf = vceqq_f32 (x, d->pinf);
> +  uint32x4_t ret_minf = vceqq_f32 (x, v_f32 (-1.0));
> +
> +  y = vbslq_f32 (ret_pinf, d->pinf, y);
> +  return vbslq_f32 (ret_minf, d->minf, y);
>  }
>  
> -/* Vector log1pf approximation using polynomial on reduced interval. Worst-case
> -   error is 1.63 ULP:
> -   _ZGVnN4v_log1pf(0x1.216d12p-2) got 0x1.fdcb12p-3
> -				 want 0x1.fdcb16p-3.  */
> +/* Single-precision implementation of vector log1pf(x).
> +  Maximum observed error: 1.20 + 0.5
> +  _ZGVnN4v_log1pf(0x1.04418ap-2) got 0x1.cfcbd8p-3
> +				want 0x1.cfcbdcp-3.  */
>  float32x4_t VPCS_ATTR NOINLINE V_NAME_F1 (log1p) (float32x4_t x)
>  {
> -  uint32x4_t special_cases = vornq_u32 (vcleq_f32 (x, v_f32 (-1)),
> -					vcaleq_f32 (x, v_f32 (0x1p127f)));
> +  const struct data *d = ptr_barrier (&data);
>  
> -  if (__glibc_unlikely (v_any_u32 (special_cases)))
> -    return special_case (x, special_cases);
> +  /* Use signed integers here to ensure that negative numbers between 0 and -1
> +    don't make this expression true.  */
> +  uint32x4_t is_infnan
> +      = vcgeq_s32 (vreinterpretq_s32_f32 (x), vreinterpretq_s32_f32 (d->pinf));
> +  /* The OR-NOT is needed to catch -NaN.  */
> +  uint32x4_t special = vornq_u32 (is_infnan, vcgtq_f32 (x, v_f32 (-1)));
>  
> -  return log1pf_inline (x, ptr_barrier (&data));
> +  if (__glibc_unlikely (v_any_u32 (special)))
> +    return special_case (x, special, d);
> +
> +  return log1pf_inline (x, &d->d);
>  }
> +
>  libmvec_hidden_def (V_NAME_F1 (log1p))
>  HALF_WIDTH_ALIAS_F1 (log1p)
>  strong_alias (V_NAME_F1 (log1p), V_NAME_F1 (logp1))



More information about the Libc-alpha mailing list