summaryrefslogtreecommitdiff
path: root/crypto/dso/dso_dlfcn.c
diff options
context:
space:
mode:
authorGeoff Thorpe <geoff@openssl.org>2000-04-19 21:45:17 +0000
committerGeoff Thorpe <geoff@openssl.org>2000-04-19 21:45:17 +0000
commitb9e6391582c1a2c8ff6ebc96d7a2abb7483def2a (patch)
tree9255d75e5070366a465d52bed9c3a473446b10cd /crypto/dso/dso_dlfcn.c
parent2c8c4ce2e0e4c3ccc7f43993e0fed1542e20e11f (diff)
downloadopenssl-new-b9e6391582c1a2c8ff6ebc96d7a2abb7483def2a.tar.gz
This change facilitates name translation for shared libraries. The
technique used is far from perfect and alternatives are welcome. Basically if the translation flag is set, the string is not too long, and there appears to be no path information in the string, then it is converted to whatever the standard should be for the DSO_METHOD in question, eg; blah --> libblah.so on *nix, and blah --> blah.dll on win32. This change also introduces the DSO_ctrl() function that is used by the name translation stuff.
Diffstat (limited to 'crypto/dso/dso_dlfcn.c')
-rw-r--r--crypto/dso/dso_dlfcn.c48
1 files changed, 47 insertions, 1 deletions
diff --git a/crypto/dso/dso_dlfcn.c b/crypto/dso/dso_dlfcn.c
index c5db28f356..cad1aedd4e 100644
--- a/crypto/dso/dso_dlfcn.c
+++ b/crypto/dso/dso_dlfcn.c
@@ -71,6 +71,9 @@ DSO_METHOD *DSO_METHOD_dlfcn(void)
#include <dlfcn.h>
#endif
+/* Part of the hack in "dlfcn_load" ... */
+#define DSO_MAX_TRANSLATED_SIZE 256
+
static int dlfcn_load(DSO *dso, const char *filename);
static int dlfcn_unload(DSO *dso);
static int dlfcn_bind(DSO *dso, const char *symname, void **symptr);
@@ -79,6 +82,7 @@ static int dlfcn_unbind(DSO *dso, char *symname, void *symptr);
static int dlfcn_init(DSO *dso);
static int dlfcn_finish(DSO *dso);
#endif
+static long dlfcn_ctrl(DSO *dso, int cmd, long larg, void *parg);
static DSO_METHOD dso_meth_dlfcn = {
"OpenSSL 'dlfcn' shared library method",
@@ -89,6 +93,7 @@ static DSO_METHOD dso_meth_dlfcn = {
#if 0
NULL, /* unbind */
#endif
+ dlfcn_ctrl,
NULL, /* init */
NULL /* finish */
};
@@ -105,8 +110,25 @@ DSO_METHOD *DSO_METHOD_dlfcn(void)
static int dlfcn_load(DSO *dso, const char *filename)
{
void *ptr;
+ char translated[DSO_MAX_TRANSLATED_SIZE];
+ int len;
- ptr = dlopen(filename, RTLD_NOW);
+ /* NB: This is a hideous hack, but I'm not yet sure what
+ * to replace it with. This attempts to convert any filename,
+ * that looks like it has no path information, into a
+ * translated form, e. "blah" -> "libblah.so" */
+ len = strlen(filename);
+ if((dso->flags & DSO_FLAG_NAME_TRANSLATION) &&
+ (len + 6 < DSO_MAX_TRANSLATED_SIZE) &&
+ (strstr(filename, "/") == NULL))
+ {
+ sprintf(translated, "lib%s.so", filename);
+ ptr = dlopen(translated, RTLD_NOW);
+ }
+ else
+ {
+ ptr = dlopen(filename, RTLD_NOW);
+ }
if(ptr == NULL)
{
DSOerr(DSO_F_DLFCN_LOAD,DSO_R_LOAD_FAILED);
@@ -178,4 +200,28 @@ static int dlfcn_bind(DSO *dso, const char *symname, void **symptr)
return(1);
}
+static long dlfcn_ctrl(DSO *dso, int cmd, long larg, void *parg)
+ {
+ if(dso == NULL)
+ {
+ DSOerr(DSO_F_DLFCN_CTRL,ERR_R_PASSED_NULL_PARAMETER);
+ return(-1);
+ }
+ switch(cmd)
+ {
+ case DSO_CTRL_GET_FLAGS:
+ return dso->flags;
+ case DSO_CTRL_SET_FLAGS:
+ dso->flags = (int)larg;
+ return(0);
+ case DSO_CTRL_OR_FLAGS:
+ dso->flags |= (int)larg;
+ return(0);
+ default:
+ break;
+ }
+ DSOerr(DSO_F_DLFCN_CTRL,DSO_R_UNKNOWN_COMMAND);
+ return(-1);
+ }
+
#endif /* DSO_DLFCN */