Back to home page

EIC code displayed by LXR

 
 

    


Warning, file /jana2/src/python/modules/jana/jana_module.cc was not indexed or was modified since last indexation (in which case cross-reference links may be missing, inaccurate or erroneous).

0001 //
0002 // Copyright 2020, Jefferson Science Associates, LLC.
0003 // Subject to the terms in the LICENSE file found in the top-level directory.
0004 
0005 #include <janapy.h>
0006 #include <JANA/CLI/JMain.h>
0007 #include <JANA/JVersion.h>
0008 #include <dlfcn.h>
0009 
0010 // Something to throw that makes a nicer error message
0011 class PYTHON_MODULE_STARTUP_FAILED{public: PYTHON_MODULE_STARTUP_FAILED(){}};
0012 
0013 //================================================================================
0014 // Module definition
0015 // The arguments of this structure tell Python what to call the extension,
0016 // what it's methods are and where to look for it's method definitions.
0017 // The routines themselves are all defined in src/python/common/janapy.h
0018 // and src/python/common/janapy.cc.
0019 PYBIND11_MODULE(jana, m) {
0020 
0021     m.doc() = "JANA2 Python Interface";
0022 
0023     // (see src/python/common/janapy.h)
0024     JANA_MODULE_DEF
0025 
0026     // This is a bit tricky:
0027     // Python modules are open by the python executable using dlopen,
0028     // but without the RTLD_GLOBAL flag. This means the symbols in
0029     // the module itself are not available for linking to additional
0030     // shared objects opened with dlopen. Specifically, when the python
0031     // script is run and it tries to attach a plugin, the plugin will
0032     // need access to JANA library routines and they cannot come from
0033     // the python module itself. Thus, we explicitly dlopen libJANA.so
0034     // here using the RTLD_GLOBAL flag.
0035     //
0036     // Note that this will not work if the shared library is not created
0037     // (by virtue of the BUILD_SHARED_LIBS cmake variable being set to
0038     // Off).
0039 
0040     std::string suffix = ".so";
0041 #if __APPLE__
0042     suffix = ".dylib";
0043 #endif
0044 
0045     auto jana_install_dir = JVersion::GetInstallDir();
0046     auto shared_lib = jana_install_dir + "/lib/libJANA" + suffix;
0047     void* handle = dlopen(shared_lib.c_str(), RTLD_LAZY | RTLD_GLOBAL | RTLD_NODELETE);
0048     if (!handle) {
0049         LOG_ERROR(default_cerr_logger) << dlerror() << LOG_END;
0050         LOG_ERROR(default_cerr_logger) << "This may be due to building JANA with BUILD_SHARED_LIBS=Off." << LOG_END;
0051         LOG_ERROR(default_cerr_logger) << "You can try running with the embedded python interpreter like this:" << LOG_END;
0052         LOG_ERROR(default_cerr_logger) << LOG_END;
0053         LOG_ERROR(default_cerr_logger) << "    jana -Pplugins=janapy -PJANA_PYTHON_FILE=myfile.py" << LOG_END;
0054         LOG_ERROR(default_cerr_logger) << LOG_END;
0055         LOG_ERROR(default_cerr_logger) << "Alternatively, build JANA with BUILD_SHARED_LIBS=On" << LOG_END;
0056 
0057         throw PYTHON_MODULE_STARTUP_FAILED();
0058     }else{
0059         // LOG <<"Opened " << shared_lib << LOG_END;
0060     }
0061     auto options = jana::ParseCommandLineOptions(0, nullptr, false);
0062     pyjapp = jana::CreateJApplication(options);
0063 
0064     PY_MODULE_INSTANTIATED_JAPPLICATION = true;
0065 }