[PATCH libICE v2] Use getentropy() if arc4random_buf() is not available

Mark Kettenis mark.kettenis at xs4all.nl
Wed Apr 5 14:49:50 UTC 2017


> From: Benjamin Tissoires <benjamin.tissoires at gmail.com>
> Date: Tue,  4 Apr 2017 19:12:53 +0200
> 
> This allows to fix CVE-2017-2626 on Linux platforms without pulling in
> libbsd.
> The libc getentropy() is available since glibc 2.25 but also on OpenBSD.
> For Linux, we need at least a v3.17 kernel. If the recommended
> arc4random_buf() function is not available, emulate it by first trying
> to use getentropy() on a supported glibc and kernel. If the call fails,
> fall back to the current (partly vulnerable) code.
> 
> Signed-off-by: Benjamin Tissoires <benjamin.tissoires at gmail.com>

The emulate_getrandom_buf() name sounds a bit weird.  Perhaps call it
bad_getrandom_buf() or dangerous_getrandom_buf() or
insecure_getrandom_buf() to make it obvious that the fallback code
really isn't sufficient?

Reviewed-by: Mark Kettenis <kettenis at openbsd.org>

> ---
> 
> changes in v2:
> - use the getentropy() from glibc, not the plain syscall
> - make it clear that arc4random_buf() should be preferred and that we
>   are only adding band-aids on top of the missing function
> ---
>  configure.ac  |  2 +-
>  src/iceauth.c | 65 ++++++++++++++++++++++++++++++++++++++++++-----------------
>  2 files changed, 47 insertions(+), 20 deletions(-)
> 
> diff --git a/configure.ac b/configure.ac
> index 458882a..c971ab6 100644
> --- a/configure.ac
> +++ b/configure.ac
> @@ -38,7 +38,7 @@ AC_DEFINE(ICE_t, 1, [Xtrans transport type])
>  
>  # Checks for library functions.
>  AC_CHECK_LIB([bsd], [arc4random_buf])
> -AC_CHECK_FUNCS([asprintf arc4random_buf])
> +AC_CHECK_FUNCS([asprintf arc4random_buf getentropy])
>  
>  # Allow checking code with lint, sparse, etc.
>  XORG_WITH_LINT
> diff --git a/src/iceauth.c b/src/iceauth.c
> index ed31683..de4785b 100644
> --- a/src/iceauth.c
> +++ b/src/iceauth.c
> @@ -44,31 +44,19 @@ Author: Ralph Mor, X Consortium
>  
>  static int was_called_state;
>  
> -/*
> - * MIT-MAGIC-COOKIE-1 is a sample authentication method implemented by
> - * the SI.  It is not part of standard ICElib.
> - */
> +#ifndef HAVE_ARC4RANDOM_BUF
>  
> -
> -char *
> -IceGenerateMagicCookie (
> +static void
> +emulate_getrandom_buf (
> +	char *auth,
>  	int len
>  )
>  {
> -    char    *auth;
> -#ifndef HAVE_ARC4RANDOM_BUF
>      long    ldata[2];
>      int	    seed;
>      int	    value;
>      int	    i;
> -#endif
>  
> -    if ((auth = malloc (len + 1)) == NULL)
> -	return (NULL);
> -
> -#ifdef HAVE_ARC4RANDOM_BUF
> -    arc4random_buf(auth, len);
> -#else
>  #ifdef ITIMER_REAL
>      {
>  	struct timeval  now;
> @@ -76,13 +64,13 @@ IceGenerateMagicCookie (
>  	ldata[0] = now.tv_sec;
>  	ldata[1] = now.tv_usec;
>      }
> -#else
> +#else /* ITIMER_REAL */
>      {
>  	long    time ();
>  	ldata[0] = time ((long *) 0);
>  	ldata[1] = getpid ();
>      }
> -#endif
> +#endif /* ITIMER_REAL */
>      seed = (ldata[0]) + (ldata[1] << 16);
>      srand (seed);
>      for (i = 0; i < len; i++)
> @@ -90,7 +78,46 @@ IceGenerateMagicCookie (
>  	value = rand ();
>  	auth[i] = value & 0xff;
>      }
> -#endif
> +}
> +
> +static void
> +arc4random_buf (
> +	char *auth,
> +	int len
> +)
> +{
> +    int	    ret;
> +
> +#if HAVE_GETENTROPY
> +    /* weak emulation of arc4random through the entropy libc */
> +    ret = getentropy (auth, len);
> +    if (ret == 0)
> +	return;
> +#endif /* HAVE_GETENTROPY */
> +
> +    emulate_getrandom_buf (auth, len);
> +}
> +
> +#endif /* !defined(HAVE_ARC4RANDOM_BUF) */
> +
> +/*
> + * MIT-MAGIC-COOKIE-1 is a sample authentication method implemented by
> + * the SI.  It is not part of standard ICElib.
> + */
> +
> +
> +char *
> +IceGenerateMagicCookie (
> +	int len
> +)
> +{
> +    char    *auth;
> +
> +    if ((auth = malloc (len + 1)) == NULL)
> +	return (NULL);
> +
> +    arc4random_buf (auth, len);
> +
>      auth[len] = '\0';
>      return (auth);
>  }
> -- 
> 2.9.3
> 
> 


More information about the xorg-devel mailing list