Module: Mesa Branch: main Commit: 7e9b06f1c6031224935685a841d81aafcf5bedba URL: http://cgit.freedesktop.org/mesa/mesa/commit/?id=7e9b06f1c6031224935685a841d81aafcf5bedba
Author: Benjamin Lee <[email protected]> Date: Sat Jun 3 15:53:33 2023 -0700 intel: Fix stack overflow in intel_dump_gpu Previously, the call to ensure_device_info in the intercepted ioctl would eventually result in another call to ioctl, recursing until stack overflow: - ioctl (intercepted) - ensure_device_info - intel_get_device_info_from_fd - intel_device_info_i915_get_info_from_fd - getparam - intel_ioctl - ioctl (intercepted) Signed-off-by: Benjamin Lee <[email protected]> Reviewed-by: Lionel Landwerlin <[email protected]> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/23418> --- src/intel/tools/intel_dump_gpu.c | 30 ++++++++++++++++++++++++++++-- 1 file changed, 28 insertions(+), 2 deletions(-) diff --git a/src/intel/tools/intel_dump_gpu.c b/src/intel/tools/intel_dump_gpu.c index 71f29ed92fa..2e047cd2797 100644 --- a/src/intel/tools/intel_dump_gpu.c +++ b/src/intel/tools/intel_dump_gpu.c @@ -43,6 +43,7 @@ #include "intel_aub.h" #include "aub_write.h" +#include "c11/threads.h" #include "dev/intel_debug.h" #include "dev/intel_device_info.h" #include "common/intel_gem.h" @@ -488,8 +489,8 @@ maybe_init(int fd) output_filename, device, devinfo.ver); } -__attribute__ ((visibility ("default"))) int -ioctl(int fd, unsigned long request, ...) +static int +intercept_ioctl(int fd, unsigned long request, ...) { va_list args; void *argp; @@ -734,6 +735,31 @@ ioctl(int fd, unsigned long request, ...) } } +__attribute__ ((visibility ("default"))) int +ioctl(int fd, unsigned long request, ...) +{ + static thread_local bool entered = false; + va_list args; + void *argp; + int ret; + + va_start(args, request); + argp = va_arg(args, void *); + va_end(args); + + /* Some of the functions called by intercept_ioctl call ioctls of their + * own. These need to go to the libc ioctl instead of being passed back to + * intercept_ioctl to avoid a stack overflow. */ + if (entered) { + return libc_ioctl(fd, request, argp); + } else { + entered = true; + ret = intercept_ioctl(fd, request, argp); + entered = false; + return ret; + } +} + static void init(void) {
