[Mesa-dev] [PATCH] llvmpipe: Avoid deadlock when unloading opengl32.dll

Jose Fonseca jfonseca at vmware.com
Thu Nov 13 03:10:39 PST 2014


Hi Tom,

That's peculiar. It looks like pthreads got into a weird state somehow.  Don't precisely understand how though.  Maybe there's a race inside pipe_semaphore_signal() with the destruction of the semaphore.

I think the best thing for now is to revert to old behavior for non-windows platforms:

diff --git a/src/gallium/drivers/llvmpipe/lp_rast.c b/src/gallium/drivers/llvmpipe/lp_rast.c
index 6b54d43..e168766 100644
--- a/src/gallium/drivers/llvmpipe/lp_rast.c
+++ b/src/gallium/drivers/llvmpipe/lp_rast.c
@@ -800,7 +800,9 @@ static PIPE_THREAD_ROUTINE( thread_function, init_data )
       pipe_semaphore_signal(&task->work_done);
    }
 
+#ifdef _WIN32
    pipe_semaphore_signal(&task->work_done);
+#endif
 
    return 0;
 }
@@ -891,7 +893,11 @@ void lp_rast_destroy( struct lp_rasterizer *rast )
     * We don't actually call pipe_thread_wait to avoid dead lock on Windows
     * per https://bugs.freedesktop.org/show_bug.cgi?id=76252 */
    for (i = 0; i < rast->num_threads; i++) {
+#ifdef _WIN32
       pipe_semaphore_wait(&rast->tasks[i].work_done);
+#else
+      pipe_thread_wait(rast->threads[i]);
+#endif
    }
 
    /* Clean up per-thread data */


Because I don't think that the Windows deadlock ever happens on Linux.

Jose


________________________________________
From: Tom Stellard <tom at stellard.net>
Sent: 13 November 2014 01:45
To: Jose Fonseca
Cc: mesa-dev at lists.freedesktop.org; Roland Scheidegger
Subject: Re: [Mesa-dev] [PATCH] llvmpipe: Avoid deadlock when unloading opengl32.dll

On Fri, Nov 07, 2014 at 04:52:25PM +0000, jfonseca at vmware.com wrote:
> From: José Fonseca <jfonseca at vmware.com>
>

Hi Jose,

This patch is causing random segfaults with OpenCL programs on radeonsi.
I haven't been able to figure out exactly what is happening, so I was
hoping you could help.

I think the problem has something to do with the fact that when clover
probes the hardware for OpenCL devices, the pipe_loader creates an
llvmpipe screen, checks the value of PIPE_CAP_COMPUTE, and then destroys
the screen since PIPE_CAP_COMPUTE is 0.

The only way I can reproduce this bug is by running the piglit OpenCL
tests concurrently.  If it helps, here are the stack traces
from one of the core dumps I captured from a piglit run:

(gdb) thread 1
[Switching to thread 1 (Thread 0x7f6d53cdf700 (LWP 18653))]
#0  0x00007f6d53e56d2d in ?? ()
(gdb) bt
#0  0x00007f6d53e56d2d in ?? ()
#1  0x0000000000000000 in ?? ()
(gdb) thread 2
[Switching to thread 2 (Thread 0x7f6d5495f700 (LWP 18652))]
#0  0x00007f6d5aacd44c in pthread_cond_wait () from /lib64/libpthread.so.0
(gdb) bt
#0  0x00007f6d5aacd44c in pthread_cond_wait () from /lib64/libpthread.so.0
#1  0x00007f6d54c71dbb in mtx_init (mtx=0x7f6d54c71dbb <mtx_init+97>,type=0) at ../../../../../include/c11/threads_posix.h:182
#2  0x00007f6d54c72157 in radeon_set_fd_access (applier=0x61e828,owner=0x61e800, mutex=0x7f6d54c71dbb <mtx_init+97>, request=0,request_name=0x0, enable=238 '\356') at radeon_drm_winsys.c:70
#3  0x00007f6d54c7ad30 in radeon_drm_cs_emit_ioctl (param=0x61e4f0) at radeon_drm_winsys.c:598
#4  0x00007f6d54c71ce0 in cnd_wait (cond=0x61e4f0, mtx=0x7f6d54c7ad07 <radeon_drm_cs_emit_ioctl+168>) at ../../../../../include/c11/threads_posix.h:152
#5  0x00007f6d5aac91da in start_thread () from /lib64/libpthread.so.0
#6  0x00007f6d5afd5d7d in clone () from /lib64/libc.so.6
(gdb) thread 3
[Switching to thread 3 (Thread 0x7f6d5c20c740 (LWP 18649))]
#0  0x00007f6d5afae73e in re_node_set_insert_last () from /lib64/libc.so.6
(gdb) bt
#0  0x00007f6d5afae73e in re_node_set_insert_last () from /lib64/libc.so.6
#1  0x00007f6d5afae7fe in register_state () from /lib64/libc.so.6
#2  0x00007f6d5afb1d39 in re_acquire_state_context () from /lib64/libc.so.6
#3  0x00007f6d5afbaa95 in re_compile_internal () from /lib64/libc.so.6
#4  0x00007f6d5afbb603 in regcomp () from /lib64/libc.so.6
#5  0x0000000000403e9b in regex_get_matches (src=0x63e6c0 "float", pattern=0x40b940 "^ulong|ulong2|ulong3|ulong4|ulong8|ulong16$", pmatch=0x0, size=0, cflags=4) at /home/tstellar/piglit/tests/cl/program/program-tester.c:476
#6  0x00000000004040e2 in regex_match (src=0x63e6c0 "float", pattern=0x40b940 "^ulong|ulong2|ulong3|ulong4|ulong8|ulong16$") at /home/tstellar/piglit/tests/cl/program/program-tester.c:532
#7  0x00000000004059c6 in get_test_arg (src=0x63de70 "1 buffer float[7] 0.5 -0.5 0.0 -0.0 nan -3.99 1.5", test=0x645710, arg_in=true) at /home/tstellar/piglit/tests/cl/program/program-tester.c:1016
#8  0x0000000000406f4a in parse_config (     config_str=0x63fe30 "\n[config]\nname: Test float trunc built-in on CL 1.1\nclc_version_min: 10\ndimensions: 1\n\n[test]\nname: trunc float1\nkernel_name: test_1_trunc_float\nglobal_size: 7 0 0\n\narg_out: 0 buffer float[7] 0.0 -0.0"..., config=0x60e260 <config>) at /home/tstellar/piglit/tests/cl/program/program-tester.c:1410
#9  0x00000000004074a7 in init (argc=2, argv=0x7fff46612d88, config=0x60e260 <config>) at /home/tstellar/piglit/tests/cl/program/program-tester.c:1555
#10 0x00007f6d5be0232c in piglit_cl_program_test_init (argc=2, argv=0x7fff46612d88, void_config=0x60e260 <config>) at /home/tstellar/piglit/tests/util/piglit-framework-cl-program.c:60
#11 0x00007f6d5be00f33 in piglit_cl_framework_run (argc=2, argv=0x7fff46612d88) at /home/tstellar/piglit/tests/util/piglit-framework-cl.c:154
#12 0x0000000000403535 in main (argc=2, argv=0x7fff46612d88) at /home/tstellar/piglit/tests/cl/program/program-tester.c:164


Thanks,
Tom

> On Windows, DllMain calls and thread creation/destruction are
> serialized, so when llvmpipe is destroyed from DllMain waiting for the
> rasterizer threads to finish will deadlock.
>
> So, instead of waiting for rasterizer threads to have finished, simply wait for the
> rasterizer threads to notify they are just about to finish.
>
> Verified with this very simple program:
>
>    #include <windows.h>
>    int main() {
>       HMODULE hModule = LoadLibraryA("opengl32.dll");
>       FreeLibrary(hModule);
>    }
>
> Fixes https://urldefense.proofpoint.com/v2/url?u=https-3A__bugs.freedesktop.org_show-5Fbug.cgi-3Fid-3D76252&d=AAIFAw&c=Sqcl0Ez6M0X8aeM67LKIiDJAXVeAw-YihVMNtXt-uEs&r=zfmBZnnVGHeYde45pMKNnVyzeaZbdIqVLprmZCM2zzE&m=4Id8ETfWCgJJvW3xybyB1vrW9ODBP9N_-G0is9bVbcU&s=qfRGj0dAovk-hsV3gL4r54_d-vlULQMia4rgMFLdOs0&e=
>
> Cc: 10.2 10.3 <mesa-stable at lists.freedesktop.org>
> ---
>  src/gallium/drivers/llvmpipe/lp_rast.c | 8 ++++++--
>  1 file changed, 6 insertions(+), 2 deletions(-)
>
> diff --git a/src/gallium/drivers/llvmpipe/lp_rast.c b/src/gallium/drivers/llvmpipe/lp_rast.c
> index a3420a2..6b54d43 100644
> --- a/src/gallium/drivers/llvmpipe/lp_rast.c
> +++ b/src/gallium/drivers/llvmpipe/lp_rast.c
> @@ -800,6 +800,8 @@ static PIPE_THREAD_ROUTINE( thread_function, init_data )
>        pipe_semaphore_signal(&task->work_done);
>     }
>
> +   pipe_semaphore_signal(&task->work_done);
> +
>     return 0;
>  }
>
> @@ -885,9 +887,11 @@ void lp_rast_destroy( struct lp_rasterizer *rast )
>        pipe_semaphore_signal(&rast->tasks[i].work_ready);
>     }
>
> -   /* Wait for threads to terminate before cleaning up per-thread data */
> +   /* Wait for threads to terminate before cleaning up per-thread data.
> +    * We don't actually call pipe_thread_wait to avoid dead lock on Windows
> +    * per https://urldefense.proofpoint.com/v2/url?u=https-3A__bugs.freedesktop.org_show-5Fbug.cgi-3Fid-3D76252&d=AAIFAw&c=Sqcl0Ez6M0X8aeM67LKIiDJAXVeAw-YihVMNtXt-uEs&r=zfmBZnnVGHeYde45pMKNnVyzeaZbdIqVLprmZCM2zzE&m=4Id8ETfWCgJJvW3xybyB1vrW9ODBP9N_-G0is9bVbcU&s=qfRGj0dAovk-hsV3gL4r54_d-vlULQMia4rgMFLdOs0&e=  */
>     for (i = 0; i < rast->num_threads; i++) {
> -      pipe_thread_wait(rast->threads[i]);
> +      pipe_semaphore_wait(&rast->tasks[i].work_done);
>     }
>
>     /* Clean up per-thread data */
> --
> 1.9.1
>
> _______________________________________________
> mesa-dev mailing list
> mesa-dev at lists.freedesktop.org
> https://urldefense.proofpoint.com/v2/url?u=http-3A__lists.freedesktop.org_mailman_listinfo_mesa-2Ddev&d=AAIFAw&c=Sqcl0Ez6M0X8aeM67LKIiDJAXVeAw-YihVMNtXt-uEs&r=zfmBZnnVGHeYde45pMKNnVyzeaZbdIqVLprmZCM2zzE&m=4Id8ETfWCgJJvW3xybyB1vrW9ODBP9N_-G0is9bVbcU&s=-ewFLSojDiybFSLUfQiK9J6LQJf4z7Mm_jpcDXschKI&e=


More information about the mesa-dev mailing list