Arcane  v3.14.10.0
Documentation développeur
Chargement...
Recherche...
Aucune correspondance
GlibDynamicLibraryLoader.cc
1// -*- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature -*-
2//-----------------------------------------------------------------------------
3// Copyright 2000-2022 CEA (www.cea.fr) IFPEN (www.ifpenergiesnouvelles.com)
4// See the top-level COPYRIGHT file for details.
5// SPDX-License-Identifier: Apache-2.0
6//-----------------------------------------------------------------------------
7/*---------------------------------------------------------------------------*/
8/* GlibDynamicLibraryLoader.cc (C) 2000-2019 */
9/* */
10/* Chargeur dynamique de bibliothèque avec Glib (utiliser gmodule). */
11/*---------------------------------------------------------------------------*/
12/*---------------------------------------------------------------------------*/
13
14#include "arcane/utils/String.h"
15#include "arcane/utils/PlatformUtils.h"
16#include "arcane/utils/ArrayView.h"
17#include "arcane/utils/IDynamicLibraryLoader.h"
18
19#include "gmodule.h"
20
21#include <iostream>
22#include <set>
23#include <vector>
24
25/*---------------------------------------------------------------------------*/
26/*---------------------------------------------------------------------------*/
27
28namespace Arcane
29{
30
31class GlibDynamicLibraryLoader;
32
33/*---------------------------------------------------------------------------*/
34/*---------------------------------------------------------------------------*/
35
36class ARCANE_IMPL_EXPORT GlibDynamicLibrary
37: public IDynamicLibrary
38{
39 public:
41 : m_manager(mng), m_gmodule(gmodule){}
42 public:
43 void close() override;
44 void* getSymbolAddress(const String& symbol_name,bool* is_found) override;
45 private:
46 GlibDynamicLibraryLoader* m_manager;
47 GModule* m_gmodule;
48};
49
50/*---------------------------------------------------------------------------*/
51/*---------------------------------------------------------------------------*/
55class ARCANE_IMPL_EXPORT GlibDynamicLibraryLoader
57{
58 public:
59 GlibDynamicLibraryLoader() : m_is_verbose(false){}
61
62 public:
63
64 void build() override
65 {
66 String s = platform::getEnvironmentVariable("ARCANE_VERBOSE_DYNAMICLIBRARY");
67 if (s=="1" || s=="true")
68 m_is_verbose = true;
69 }
70
71 IDynamicLibrary* open(const String& directory,const String& name) override
72 {
73 IDynamicLibrary* dl = _tryOpen(directory, name);
74 if (!dl){
75 // Si on ne trouve pas, essaie avec l'extension '.dll' car sous windows
76 // certaines version de la GLIB prefixent automatiquement le
77 // nom de la bibliothèque par 'lib' si elle ne finit pas par '.dll'.
78 dl = _tryOpen(directory, name + ".dll");
79 }
80 if (!dl){
81 // Si on ne trouve pas, essaie en cherchant à côté du binaire
82 dl = _tryOpen(".", name);
83 }
84 if (!dl){
85 // Si on ne trouve pas, essaie en cherchant à côté du binaire
86 // et avec l'extension dll
87 dl = _tryOpen(".", name + ".dll");
88 }
89 return dl;
90 }
91
92 IDynamicLibrary* _tryOpen(const String& directory, const String& name)
93 {
94 const gchar* gdirectory = reinterpret_cast<const gchar*>(directory.utf8().data());
95 const gchar* gname = reinterpret_cast<const gchar*>(name.utf8().data());
97 if (m_is_verbose) {
98 std::cout << "** Load Dynamic Library '" << full_path << "'...";
99 }
100 GModule* gmodule = g_module_open(full_path, GModuleFlags());
101 g_free(full_path);
102 if (m_is_verbose) {
103 if (!gmodule){
104 std::cout << " NOT FOUND\n";
105 } else {
106 std::cout << " OK\n";
107 }
108 }
109 if (!gmodule)
110 return nullptr;
111 auto lib = new GlibDynamicLibrary(this,gmodule);
112 m_opened_libraries.insert(lib);
113 return lib;
114 }
115
116 void closeLibraries() override
117 {
118 // Cette méthode va modifier m opened libraries donc il faut le copier avant.
119 std::vector<GlibDynamicLibrary*> libs(m_opened_libraries.begin(),m_opened_libraries.end());
120 for( auto lib : libs ){
121 lib->close();
122 delete lib;
123 }
124 }
125
126 void removeInstance(GlibDynamicLibrary* lib)
127 {
128 auto iter = m_opened_libraries.find(lib);
129 if (iter!=m_opened_libraries.end())
130 m_opened_libraries.erase(iter);
131 }
132
133 private:
134
135 bool m_is_verbose;
136 std::set<GlibDynamicLibrary*> m_opened_libraries;
137};
138
139/*---------------------------------------------------------------------------*/
140/*---------------------------------------------------------------------------*/
141
143close()
144{
145 if (!m_gmodule)
146 return;
147 bool is_ok = g_module_close(m_gmodule);
148 m_gmodule = 0;
149 if (!is_ok)
150 std::cerr << "WARNING: can not unload module\n";
151 m_manager->removeInstance(this);
152}
153
154/*---------------------------------------------------------------------------*/
155/*---------------------------------------------------------------------------*/
156
159{
160 if (is_found)
161 *is_found = false;
162 if (!m_gmodule)
163 return nullptr;
164 const gchar* gname = reinterpret_cast<const gchar*>(symbol_name.utf8().data());
165 void* symbol_addr = nullptr;
166 bool r = ::g_module_symbol(m_gmodule,gname,&symbol_addr);
167 if (is_found)
168 (*is_found) = r;
169 return symbol_addr;
170}
171
172/*---------------------------------------------------------------------------*/
173/*---------------------------------------------------------------------------*/
174
175extern "C++" ARCANE_IMPL_EXPORT IDynamicLibraryLoader*
176createGlibDynamicLibraryLoader()
177{
179 idll->build();
180 return idll;
181}
182
183/*---------------------------------------------------------------------------*/
184/*---------------------------------------------------------------------------*/
185
186} // End namespace Arcane
187
188/*---------------------------------------------------------------------------*/
189/*---------------------------------------------------------------------------*/
190
Interface d'une chargeur dynamique de bibliothèque.
IDynamicLibrary * open(const String &directory, const String &name) override
Charge une bibliothèque dynamique.
virtual ~GlibDynamicLibraryLoader()
Libère les ressources.
void closeLibraries() override
Ferme toutes les bibliothèques ouvertes via open()
void close() override
Ferme la bibliothèque dynamique.
void * getSymbolAddress(const String &symbol_name, bool *is_found) override
Retourne l'adresse du symbol de nom symbol_name.
Interface d'une chargeur dynamique de bibliothèque.
Interface d'une bibliothèque dynamique.
Lecteur des fichiers de maillage via la bibliothèque LIMA.
Definition Lima.cc:120
constexpr const_pointer data() const noexcept
Pointeur sur la mémoire allouée.
Chaîne de caractères unicode.
ByteConstArrayView utf8() const
Retourne la conversion de l'instance dans l'encodage UTF-8.
Definition String.cc:275
-*- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature -*-