diff --git a/vtkm/opengl/testing/TestingWindow.h b/vtkm/opengl/testing/TestingWindow.h index 2dd7c0e14..26e7e60a3 100644 --- a/vtkm/opengl/testing/TestingWindow.h +++ b/vtkm/opengl/testing/TestingWindow.h @@ -22,6 +22,58 @@ #include #include + +#if defined(VTKM_GCC) && defined(VTKM_POSIX) && !defined(__APPLE__) +// +// 1. Some Linux distributions default linker implicitly enables the as-needed +// linking flag. This means that your shared library or executable will only +// link to libraries from which they use symbols. So if you explicitly link to +// pthread but don't use any symbols you wont have a 'DT_NEEDED' entry for +// pthread. +// +// 2. NVidia libGL (driver version 352 ) uses pthread but doesn't have +// a DT_NEEDED entry for the library. When you run ldd or readelf on the library +// you won't detect any reference to the pthread library. Aside this is odd +// since the mesa version does explicitly link to pthread. But if you run the +// following command: +// "strings /usr/lib/nvidia-352/libGL.so.1 | grep pthread | less" +// You will see the following: +// { pthread_create +// pthread_self +// pthread_equal +// pthread_key_crea +// ... +// libpthread.so.0 +// libpthread.so +// pthread_create +// } +// +// This is very strong evidence that this library is using pthread. +// +// +// 3. So what does this all mean? +// +// It means that on system that use the linking flag 'as-needed', are using +// the nvidia driver, and don't use pthread will generate binaries that crash +// on launch. The only way to work around this issue is to do either: +// +// +// A: Specify 'no-as-needed' to the linker potentially causing over-linking +// and a slow down in link time +// +// B: Use a method from pthread, making the linker realize that pthread is +// needed. +// +// +// So that is the explanation on why we have the following function which is +// never used and seems very crazy. +#include +#define VTKM_NVIDIA_PTHREAD_WORKAROUND 1 +int vtkm_force_linking_to_pthread_to_fix_nvidia_libgl_bug() + { return static_cast(pthread_self()); } +#endif + + namespace vtkm{ namespace opengl{ namespace testing{ @@ -34,6 +86,12 @@ namespace testing{ /// class TestingWindow : public vtkm::opengl::testing::WindowBase { + +#if defined(VTKM_NVIDIA_PTHREAD_WORKAROUND) + VTKM_CONT_EXPORT int vtkm_force_linking_to_pthread_to_fix_nvidia_libgl_bug() + { return vtkm_force_linking_to_pthread_to_fix_nvidia_libgl_bug(); } +#endif + public: VTKM_CONT_EXPORT TestingWindow(){};