SQLAPI ++ possède une fonction inhabituelle dans laquelle vous définissez une chaîne pour indiquer où trouver la bibliothèque partagée ODBC. Dans mon cas c'est libtdsodbc.so
, et mon application lie réellement cette bibliothèque au moment de la construction, mais au moment de l'exécution ce n'est pas suffisant pour que SQLAPI ++ fonctionne.SQLAPI ++: Récupère le chemin d'accès à la bibliothèque partagée chargée par l'exécutable
Mon code est:
SAConnection conn;
conn.setOption("ODBC.LIBS") = "libtdsodbc.so";
conn.Connect("SERVER=...", "", "", SA_ODBC_Client);
ODBC.LIBS
est documented comme ceci:
Forces SQLAPI ++ Bibliothèque pour utiliser la bibliothèque de gestionnaire ODBC spécifié.
Le code ci-dessus fonctionne si vous définissez LD_LIBRARY_PATH
dans un répertoire contenant libtdsodbc.so
. Mais si vous ne le faites pas, Connect()
échoue:
libtdsodbc.so: cannot open shared object file: No such file or directory
DBMS API Library 'libtdsodbc.so' loading fails
This library is a part of DBMS client installation, not SQLAPI++
Make sure DBMS client is installed and
this required library is available for dynamic loading
Linux/Unix:
1) The directories in the user's LD_LIBRARY_PATH environment variable
2) The list of libraries cached in /etc/ld.so.cache
3) /usr/lib, followed by /lib
Il fonctionne à nouveau si vous définissez ODBC.LIBS
à un chemin complet plutôt que juste un nom de fichier. Mais comment l'application peut-elle savoir quel chemin?
Mon application (en dehors de SQLAPI ++) trouve libtdsodbc.so
via son RUNPATH
qui est défini au moment de la construction. Ce chemin n'est pas un chemin système comme /usr/lib
. Je voudrais que SQLAPI ++ utilise la même bibliothèque qui est chargée dans l'application lors de l'exécution.
Une idée est pour l'application à inspect its own RUNPATH
, recherchez libtdsobc.so
et utilisez ce chemin. Mais cela nécessite un peu de code fiddly pour réimplémenter fondamentalement ce que fait déjà ld.so
.
Je ne veux pas faire le chemin dans l'exécutable au moment de la construction séparément de RUNPATH
, parce que je modifie parfois RUNPATH
avant le déploiement (et puis j'ai besoin de modifier deux choses).
Idéalement, je voudrais dire à SQLAPI ++ d'utiliser simplement la bibliothèque qui est déjà chargée. Je peux comprendre ce chemin en exécutant lsof -p PID | grep libtdsodbc.so
mais exécuter des commandes shell à partir de l'exécutable n'est pas une bonne solution (et encore une fois je préfèrerais ne pas réimplémenter lsof
).