SQLAPI++ 有一个不寻常的功能,您可以设置一个字符串来告诉它在哪里可以找到 ODBC 共享库。就我而言,这是libtdsodbc.so
,我的应用程序实际上在构建时链接了该库,但在运行时这还不足以让 SQLAPI++ 工作。
我的代码是:
SAConnection conn;
conn.setOption("ODBC.LIBS") = "libtdsodbc.so";
conn.Connect("SERVER=...", "", "", SA_ODBC_Client);
ODBC.LIBS
记录如下:
强制 SQLAPI++ 库使用指定的 ODBC 管理器库。
如果您设置LD_LIBRARY_PATH
为包含libtdsodbc.so
. 但如果你不这样做,Connect()
失败:
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
如果您设置ODBC.LIBS
为完整路径而不仅仅是文件名,它会再次起作用。但是应用程序怎么知道是哪条路径呢?
我的应用程序(在 SQLAPI++ 之外)是libtdsodbc.so
通过它RUNPATH
在构建时设置的。此路径不是系统路径,如/usr/lib
. 我想让 SQLAPI++ 使用在运行时加载到应用程序中的相同库。
一种想法是让应用程序检查自己的RUNPATH
、搜索libtdsobc.so
和使用该路径。但这需要相当多的繁琐代码才能从根本上重新实现ld.so
已经完成的工作。
我不想在构建时将路径与可执行文件分开烘焙RUNPATH
,因为我有时会RUNPATH
在部署之前进行编辑(然后我需要编辑两件事)。
理想情况下,我想告诉 SQLAPI++ 只使用已经加载的库。我可以通过运行来找出这条路径,lsof -p PID | grep libtdsodbc.so
但从可执行文件中运行 shell 命令不是一个好的解决方案(我也不想重新实现lsof
)。