From 0a3452520fe4cd6871ae8b7c4199c6d5d4efe912 Mon Sep 17 00:00:00 2001 From: Pauli Date: Wed, 26 Jul 2017 10:04:05 +1000 Subject: [PATCH] Fix potential use-after-free and memory leak In function wait_for_async(), allocated async fds is freed if `SSL_get_all_async_fds` fails, but later `fds` is used. Interestingly, it is not freed when everything succeeds. Rewrite the FD set loop to make it more readable and to not modify the allocated pointer so it can be freed. Reviewed-by: Andy Polyakov Reviewed-by: Paul Dale (Merged from https://github.com/openssl/openssl/pull/3992) --- apps/apps.c | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/apps/apps.c b/apps/apps.c index 4459be9c9b..ad386a116a 100644 --- a/apps/apps.c +++ b/apps/apps.c @@ -2614,6 +2614,7 @@ void wait_for_async(SSL *s) fd_set asyncfds; OSSL_ASYNC_FD *fds; size_t numfds; + size_t i; if (!SSL_get_all_async_fds(s, NULL, &numfds)) return; @@ -2622,17 +2623,17 @@ void wait_for_async(SSL *s) fds = app_malloc(sizeof(OSSL_ASYNC_FD) * numfds, "allocate async fds"); if (!SSL_get_all_async_fds(s, fds, &numfds)) { OPENSSL_free(fds); + return; } FD_ZERO(&asyncfds); - while (numfds > 0) { - if (width <= (int)*fds) - width = (int)*fds + 1; - openssl_fdset((int)*fds, &asyncfds); - numfds--; - fds++; + for (i = 0; i < numfds; i++) { + if (width <= (int)fds[i]) + width = (int)fds[i] + 1; + openssl_fdset((int)fds[i], &asyncfds); } select(width, (void *)&asyncfds, NULL, NULL, NULL); + OPENSSL_free(fds); #endif } -- 2.25.1