diff --git a/config/ie/options b/config/ie/options index 986f5caedf..6904e7b3f7 100644 --- a/config/ie/options +++ b/config/ie/options @@ -389,7 +389,9 @@ envVarsToImport = ["PATH", "CORTEX_POINTDISTRIBUTION_TILESET", "OCIO", "IECORE_DEBUG_WAIT", - "CORTEX_PERFORMANCE_TEST"] + "CORTEX_PERFORMANCE_TEST", + "IECORE_FORCE_GLOBAL_SYMBOLS", +] ENV_VARS_TO_IMPORT= " ".join(envVarsToImport) diff --git a/python/IECore/__init__.py b/python/IECore/__init__.py index 6b7b9f65d6..b5c46bb5fe 100644 --- a/python/IECore/__init__.py +++ b/python/IECore/__init__.py @@ -38,22 +38,37 @@ # # Some parts of the IECore library are defined purely in Python. These are shown below. -# Turn on RTLD_GLOBAL to avoid the dreaded cross module RTTI -# errors on Linux. This causes libIECore etc to be loaded into -# the global symbol table and those symbols to be shared between -# modules. Without it, different python modules and/or libraries -# can end up with their own copies of symbols, which breaks a -# great many things. +# Set IECORE_FORCE_GLOBAL_SYMBOLS = 1 to turn on RTLD_GLOBAL to +# avoid the dreaded cross module RTTI errors on Linux. +# This causes libIECore etc to be loaded into the global symbol +# table and those symbols to be shared between modules. Without +# it, different python modules and/or libraries can end up with +# their own copies of symbols, which breaks a great many things. # # We use the awkward "__import__" approach to avoid importing sys # and ctypes into the IECore namespace. -if __import__( "os" ).name == 'posix': +if __import__( "os" ).name == 'posix' and __import__( "os" ).environ.get( "IECORE_FORCE_GLOBAL_SYMBOLS" ) == "1" : __import__( "sys" ).setdlopenflags( __import__( "sys" ).getdlopenflags() | __import__( "ctypes" ).RTLD_GLOBAL ) -__import__( "imath" ) +try : + + # Make sure we import imath _with_ RTLD_GLOBAL. This avoids + # boost to_python (by-value) converter issues for imath types. + + import sys + import ctypes + originalDLOpenFlags = sys.getdlopenflags() + sys.setdlopenflags( originalDLOpenFlags | ctypes.RTLD_GLOBAL ) + + __import__( "imath" ) + +finally : + + sys.setdlopenflags( originalDLOpenFlags ) + del sys, ctypes, originalDLOpenFlags from _IECore import * diff --git a/src/IECoreHoudini/plugin/Plugin.cpp b/src/IECoreHoudini/plugin/Plugin.cpp index 10e99ab90a..98931e732c 100644 --- a/src/IECoreHoudini/plugin/Plugin.cpp +++ b/src/IECoreHoudini/plugin/Plugin.cpp @@ -86,7 +86,11 @@ extern "C" { SYS_VISIBILITY_EXPORT void HoudiniDSOInit( UT_DSOInfo &dsoinfo ) { - dsoinfo.loadGlobal = true; + const char *forceGlobals = std::getenv( "IECORE_FORCE_GLOBAL_SYMBOLS" ); + if( forceGlobals && !strcmp( forceGlobals, "1" ) ) + { + dsoinfo.loadGlobal = true; + } } } diff --git a/src/IECoreMaya/plugin/Loader.cpp b/src/IECoreMaya/plugin/Loader.cpp index 04dbd55866..922c4a601b 100644 --- a/src/IECoreMaya/plugin/Loader.cpp +++ b/src/IECoreMaya/plugin/Loader.cpp @@ -51,7 +51,15 @@ IECORE_EXPORT MStatus initializePlugin( MObject obj ) std::string implName = pluginPath + "/impl/" + pluginName + ".so"; - g_libraryHandle = dlopen( implName.c_str(), RTLD_NOW | RTLD_GLOBAL ); + const char *forceGlobals = std::getenv( "IECORE_FORCE_GLOBAL_SYMBOLS" ); + if( forceGlobals && !strcmp( forceGlobals, "1" ) ) + { + g_libraryHandle = dlopen( implName.c_str(), RTLD_NOW | RTLD_GLOBAL ); + } + else + { + g_libraryHandle = dlopen( implName.c_str(), RTLD_NOW ); + } if (! g_libraryHandle ) {