From simon.urbanek at r-project.org  Tue Jan  1 19:33:55 2008
From: simon.urbanek at r-project.org (Simon Urbanek)
Date: Tue, 1 Jan 2008 13:33:55 -0500
Subject: [Rd] Problem with dyn.load'ed code
In-Reply-To: <1199207329.17113.67.camel@calder-linux>
References: <1199072630.17113.54.camel@calder-linux>
	<20071231203010.GA72526@piskorski.com>
	<1199207329.17113.67.camel@calder-linux>
Message-ID: <95DF88BB-C703-4B87-BDC3-439D6D57AF50@r-project.org>

Matt,

On Jan 1, 2008, at 12:08 PM, Matt Calder wrote:

> Andrew,
> 	Thanks! The version script worked like a charm. Specifically I now
> build using:
>
> g++ -shared -Wl,--version-script=ver.map to_dyn_load.cc -o  
> to_dyn_load.so -larpack
>

just a word of warning - this is in no way portable. It is probably ok  
for your private compilation, but it won't work in general. In any  
case, I'd strongly recommend enabling this hack only if you know that  
the target system supports it for the sake of portability. However, if  
you are concerned about the latter, you should probably have a look at  
libtool and --export-symbols - it allows you to control the visibility  
on most systems that support it.
Note that there are systems that don't support it at all.

Cheers,
Simon


> where ver.map is the file:
>
> {
>     global: R_func_*;
>     local:*;
> };
>
> and any function I want exported to R is named R_func_*. This is going
> to be my new SOP.
> 	Thanks again Andrew, and also Simon. I greatly appreciate you taking
> your time to solve this problem for me.
>
> 	Matt
>
> 	
> On Mon, 2007-12-31 at 15:30 -0500, Andrew Piskorski wrote:
>> On Sun, Dec 30, 2007 at 10:43:50PM -0500, Matt Calder wrote:
>>> Simon,
>>> 	Thanks for the reply. Indeed, declaring the function static fixes  
>>> the
>>> example. Unfortunately, the real problem that gave rise to the  
>>> example
>>> arises in a large Fortran library that is not under my control  
>>> (ARPACK).
>>> The author is providing BLAS and LAPACK functionality intentionally.
>>> That may or may not be good practice, but it is a given in this  
>>> case.
>>
>> Ok, so R is calling its one "dnrm2_" function, let's call this "A",
>> while ARPACK defines a second, different "dnrm2_", which we'll call
>> "B".  You want to call function A from your own C code, while R keeps
>> calling function A as before without any change or interference.  And
>> of course, A and B are two C-coded functions with different behaviors
>> but the exact same name.  You can make that work, it just requires
>> some tricks.
>>
>>> 	I still feel like the linker ought to be able to solve this  
>>> problem for
>>> me. My impression was that the static keyword passed to the linker
>>
>> It can, you just need to tell it exactly what you want.  I assume you
>> are building your own custom C code into a shared library, which you
>> then load into R.
>>
>> Thus, one solution is to statically link the ARPACK library into your
>> own shared library, and then carefully tell the linker which symbols
>> to export and which to keep private inside your shared library.  As
>> long as the symbol ARPACK's "B" dnrm2_ function is kept private  
>> inside
>> your own shared library (not exported), R will never see it and will
>> happily keep using dnrm2_ "A" as before.
>>
>> That's how I've solved this sort of name collision problem in the
>> past.  In your "src/Makevars", you may want something like to this:
>>
>>  PKG_LIBS = -Wl,--version-script=vis.map -Wl,-Bstatic -L/usr/local/ 
>> lib/ARPACK -lARPACK -Wl,-Bdynamic
>>
>> You may also need a PG_PKG_LIBS with the same stuff, but I don't
>> remember why.  The '--version-script=' and related matters were also
>> disccussed here back in February:
>>
>>  https://stat.ethz.ch/pipermail/r-devel/2007-February/044531.html
>>
>
> ______________________________________________
> R-devel at r-project.org mailing list
> https://stat.ethz.ch/mailman/listinfo/r-devel
>
>



[Rd] Problem with dyn.load'ed code
Simon Urbanek