Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

loading shared libraries with same function names

49 views
Skip to first unread message

Michele

unread,
May 14, 2008, 2:58:52 PM5/14/08
to
I'm loading a couple of shared libraries into my tcl script (using the
"load" command rather than the "package require")
Both libraries have identical function names: Version
Is there a way that I can specify which library's "Version" call to
use? I don't own the library source code.

wiede...@googlemail.com

unread,
May 15, 2008, 4:43:19 AM5/15/08
to

try this: ( no guarantee )
load lib_a.so
rename Version A::Version
load lib_b.so
rename Version B::Version

uwe

George Peter Staplin

unread,
May 15, 2008, 8:31:20 AM5/15/08
to


If Version is a C function in both .dll or .so, then here's an example
of one way of solving that. I don't think you can use Tcl's load in
this situation. But you could duplicate some of its functionality.

$ cat symbols.c
#include <stdio.h>
#include <stdlib.h>
#include <dlfcn.h>

int (*version) (void);
int (*version2) (void);

int main() {
void *l, *l2;
char *err;

l = dlopen("./version.so", RTLD_NOW);
if(NULL == l) {
fprintf(stderr, "%s\n", dlerror());
return EXIT_FAILURE;
}

dlerror();
version = dlsym(l, "version");
err = dlerror();
if (err) {
fprintf(stderr, "%s\n", err);
return EXIT_FAILURE;
}

l2 = dlopen("./version2.so", RTLD_NOW);
if(NULL == l2) {
fprintf(stderr, "%s\n", dlerror());
return EXIT_FAILURE;
}


dlerror();
version2 = dlsym(l2, "version");
err = dlerror();
if (err) {
fprintf(stderr, "%s\n", err);
return EXIT_FAILURE;
}

printf("version %d\n", version());
printf("version2 %d\n", version2());

return EXIT_SUCCESS;
}


$ cat version.c
int version (void) {
return 123;
}

$ cat version2.c
int version (void) {
return 456;
}


$ gcc symbols.c -ldl
$ gcc -shared version.c -o version.so
$ gcc -shared version2.c -o version2.so

$ ./a.out
version 123
version2 456


To do what Tcl does:

int (*theext_init) (Tcl_Interp *interp);
char *err;

dlerror();
theext_init = dlsym(somelibhandle, "Theext_Init");
err = dlerror();
if (err) {
/* handle missing Theext_Init() */
}

if (TCL_OK != theext_init(interp)) {
/* print an error or return one to Tcl. Tcl_GetStringResult(interp)
is one way of getting a char * for the error message. */
return TCL_ERROR;
}


For Windows you would need LoadLibrary() and friends. You can probably
gather a lot of the patterns from the Tcl sources.

George

0 new messages