source: Sophya/trunk/SophyaLib/SysTools/pdlmgr.cc@ 1284

Last change on this file since 1284 was 1277, checked in by ansari, 25 years ago

Correction dyn linker - compiler + Gestion TMPDIR , Reza 2/11/2000

File size: 6.9 KB
RevLine 
[219]1// Gestionnaire de lien dynamique - R. Ansari 12/98
2// LAL (Orsay) / IN2P3-CNRS DAPNIA/SPP (Saclay) / CEA
3
[913]4#include "pdlmgr.h"
[219]5#include <stdio.h>
6#include <stdlib.h>
7
8#include <iostream.h>
9
10
11// Extension de noms de fichiers Shared libs
12static const char* sofext = ".so";
13static const char* sofext_HPUX = ".sl";
14
15// Variables et methodes static
16int PDynLinkMgr::numSO = 0;
17string* PDynLinkMgr::tmpDir = NULL;
18
[895]19/*!
20 \class SOPHYA::PDynLinkMgr
[913]21 \ingroup SysTools
[895]22 This classes handles the run-time operations related to using shared
23 libraries. The present version has been adapted for different Unix
24 flavours (Linux, Compaq/Digital Unix, SGI IRIX, IBM AIX, Sun Solaris).
[1275]25 The example here shows the linking of shared library named "mylib.so"
[913]26 containing a function \c double \c myfunction(double x).
27 \code
28 #include "pdlmgr.h"
29 typedef double (* AFunctionOfX) (double x);
30 {
31 // ...
32 string soname = "mylib.so";
33 string funcname = "myfunction";
34 PDynLinkMgr dyl(son);
35 AFunctionOfX f = (AFunctionOfX)dyl.GetFunction(funcname);
36 double x = 3.1425;
37 if (f != NULL)
38 cout << " X= " << x << " myfunction(x)=" << f(x) << endl;
39 // ...
40 }
41 \endcode
[895]42*/
43
[219]44/* --Methode-Static-- */
[895]45/*! Sets the path for a temporary space where shared libraries are copied.
46 The path is appended to \b LD_LIBRARY_PATH
47*/
[219]48void PDynLinkMgr::SetTmpDir(string const & path)
49{
[1275]50if ( (path.length() > 0) && (path[path.length()-1] != '/') ) GetTmpDir() = path + '/';
[219]51else GetTmpDir() = path;
[1275]52#if defined(OSF1) || defined(Linux) || defined(SunOS) || defined(IRIX64)
53 char* varenv=NULL;
54#if !defined(IRIX64)
[480]55 string cmd = "LD_LIBRARY_PATH=";
56 varenv=getenv("LD_LIBRARY_PATH");
[1275]57#else
58#ifdef SGI_ARCH64
[480]59 string cmd = "LD_LIBRARYN32_PATH=";
60 varenv=getenv("LD_LIBRARYN32_PATH");
[1275]61#else
62 string cmd = "LD_LIBRARYN64_PATH=";
63 varenv=getenv("LD_LIBRARYN64_PATH");
64#endif
65#endif
[480]66
67 if (varenv == NULL) {
68 cmd += '.';
69 if (path.length() > 0) cmd += ':' + path;
70 }
71 else {
72 if (varenv[0] != '.') cmd += ".:";
73 if (path.length() > 0) cmd += path + ':';
74 cmd += varenv;
75 putenv(cmd.c_str());
76 }
77#elif defined(AIX)
78 string cmd = "LIBPATH=";
79 char* varenv=NULL;
80 varenv=getenv("LIBPATH");
81 if (varenv == NULL) {
82 cmd += '.';
83 if (path.length() > 0) cmd += ':' + path;
84 cmd += ":/usr/lib:/lib";
85 }
86 else {
87 if (varenv[0] != '.') cmd += ".:";
88 if (path.length() > 0) cmd += path + ':';
89 cmd += varenv;
90 putenv(const_cast<char *>(cmd.c_str()));
91 }
92
93#endif
[219]94return;
95}
96
97/* --Methode-Static-- */
[895]98/*! Returns the temporary space path */
[219]99string& PDynLinkMgr::GetTmpDir()
100{
101if (tmpDir == NULL) {
102 tmpDir = new string("");
103 char* varenv;
[1277]104 if ( (varenv=getenv("TMPDIR")) != NULL ) {
105 *tmpDir = varenv;
106 if ((*tmpDir)[tmpDir->length()-1] != '/') (*tmpDir) += '/';
[219]107 }
[1277]108}
[219]109return(*tmpDir);
110}
111
112/* --Methode-Static-- */
[895]113/*! Compiles the C source file named \b fname and creates the
114 corresponding shared library linking against the standard
115 C library (-lc) and the math library (-lm).
116 Returns a pointer to the created PDynLinkMgr object (by new).
117 Returns the NULL pointer in case of errors.
118*/
[219]119PDynLinkMgr* PDynLinkMgr::BuildFromCFile(string const & fname)
120{
121size_t l = fname.length();
122if (l < 1) return(NULL);
123string fnameobj = GetTmpDir()+"tmp_pdl.o";
124
125string cmd;
126int rc;
127
128// Compilation du fichier
[480]129#ifndef __mac__
[1249]130#ifdef SGI_ARCH64
131cmd = "cc -64 -c -o " + fnameobj + " " + fname;
132#else
[219]133cmd = "cc -c -o " + fnameobj + " " + fname;
[1249]134#endif
[480]135#else
136cmd = "Il faut compiler !!!" + fnameobj + " " + fname;
[219]137#endif
138rc = system(cmd.c_str());
139if (rc != 0) {
140 cerr << "PDynLinkMgr::BuildFromCFile() Error Rc(" << cmd <<")= "<< rc << endl;
141 return(NULL);
142 }
143
144char buff[32];
145numSO++;
146#ifndef HPUX
147sprintf(buff,"pdlmgr%d%s", numSO,sofext);
148#endif
149string fnameso = GetTmpDir()+buff;
150
151// Creation du shared-lib
152#if defined(OSF1)
153 cmd = "ld -shared -o " + fnameso + " -all " + fnameobj + " -none -lm -lc";
[480]154#elif defined(Linux)
[219]155 cmd = "ld -shared -o " + fnameso + " " + fnameobj + " -lm -lc";
[480]156#elif defined(SunOS)
157 cmd = "ld -G -o " + fnameso + " " + fnameobj + " -lm -lc";
158#elif defined(IRIX64)
[1249]159#ifdef SGI_ARCH64
160 cmd = "ld -64 -shared -o " + fnameso + " " + fnameobj + " -lm -lc";
161#else
[480]162 cmd = "ld -shared -o " + fnameso + " " + fnameobj + " -lm -lc";
[1249]163#endif
[480]164#elif defined(AIX)
165 cmd = "ld -G -bnogc -bexpall -bM:1L -o " + fnameso + " " + fnameobj;
166#elif defined(HPUX)
167 cmd = "ld -b -o " + fnameso + " " + fnameobj + " -lm -lc";
168#else
169 cmd = "ld -o " + fnameso + " " + fnameobj + " -lm -lc";
[219]170#endif
171rc = system(cmd.c_str());
172if (rc != 0) {
173 cerr << "PDynLinkMgr::BuildFromCFile() Error Rc(" << cmd <<")= "<< rc << endl;
174 return(NULL);
175 }
[296]176PDynLinkMgr* rdyn = new PDynLinkMgr(fnameso, false);
177rdyn->copy = true;
178return(rdyn);
[219]179
180}
181
182/* --Methode-- */
[895]183/*! The constructor.
184 \param soname : Name of the shared library. ".so" is appended
185 to the name if no dot "." is found in the name.
186 \param cp : if true, copies the shared library in the temporary space.
187*/
[219]188PDynLinkMgr::PDynLinkMgr(string& soname, bool cp)
189{
190dlhandle = NULL;
191soName = "";
192
193if (soname.find_last_of(".") > soname.length())
194#ifdef HPUX
195 soname += sofext_HPUX;
196#else
197 soname += sofext;
198#endif
199
200string fnameso;
201if (cp) {
202 numSO++;
203 char buff[32];
204#ifndef HPUX
205 sprintf(buff,"pdlmgr%d%s", numSO,sofext);
206#else
207 sprintf(buff,"pdlmgr%d%s", numSO,sofext_HPUX);
208#endif
209 fnameso = GetTmpDir()+buff;
210 string cmd = "cp " + soname + " " + fnameso;
211 int rc = system(cmd.c_str());
212 if (rc != 0) {
213 cerr << "PDynLinkMgr::PDynLinkMgr() Error Rc(" << cmd <<")= "<< rc << endl;
214 return;
215 }
216 }
217else fnameso = soname;
218copy = cp;
219soName = fnameso;
220
[480]221#if defined(HPUX)
222dlhandle = NULL;
223cerr << "PDynLinkMgr::PDynLinkMgr() Not yet available on HP-UX " << endl;
224return;
225#else
[219]226dlhandle = dlopen(fnameso.c_str(), RTLD_NOW);
227if (dlhandle == NULL) {
228 cerr << "PDynLinkMgr::PDynLinkMgr(): Error opening SO " << fnameso
229 << " (" << soname << ")" << endl;
230 string sn = dlerror();
231 cerr << "Loader Error (dlerror()) :" << sn << endl;
232 return;
233 }
234#endif
235}
236
237/* --Methode-- */
[895]238/*! Destructor. Closes the shared library. Removes the file if it had been
239 copied in the temporary space, or generated by \b BuildFromCFile */
[219]240PDynLinkMgr::~PDynLinkMgr()
241{
[480]242#if defined(HPUX)
243cerr << "PDynLinkMgr::~PDynLinkMgr() Not yet available on HP-UX " << endl;
244return;
245#else
[219]246if (dlhandle) dlclose(dlhandle); dlhandle = NULL;
247if (copy) {
[296]248 string cmd = "rm -f " + soName;
[219]249 system(cmd.c_str());
250 }
[480]251#endif
[219]252}
253
254/* --Methode-- */
[895]255/*! Returns a handle to the function named \b funcname.
256 Returns the NULL pointer in case of error */
[219]257DlFunction PDynLinkMgr::GetFunction(string const & funcname)
258{
259DlFunction f = NULL;
[480]260#if defined(HPUX)
261cerr << "PDynLinkMgr::GetFunction() Not yet available on HP-UX " << endl;
262return f;
263#else
[219]264if (dlhandle != NULL)
265 f = (DlFunction)dlsym(dlhandle, funcname.c_str());
[480]266if (f == NULL) cerr << "PDynLinkMgr::GetFunction(): Error linking " << funcname << endl;
267return(f);
[219]268#endif
269}
270
Note: See TracBrowser for help on using the repository browser.