[R] registration of C routines
Duncan Temple Lang
duncan at research.bell-labs.com
Fri Jul 20 13:36:08 CEST 2001
Interesting. I also run into this idea of specifying the name of a
routine rather than an R function. I haven't done much about
implementing anything yet, but here is my plan. When the user
specifies a "callback", if it is a function object, then we treat it
as a regular R function. If it is a string, then we lookup the
corresponding native symbol and return its address (and type) as an R
object. For example, suppose the user calls
lsoda(y, times, func = "foo")
then the lsoda() code would call
and get back an object such as
x <- list(address= numeric(1), pid="R session identifier", numArgs = ?, argTypes = c(argName=type, argName=type))
class(x) <- c("CRoutine", "NativeSymbolRef")
(The numArgs and argTypes would be available if the routine were registered.)
Now, this object (returned from NativeSymbol()) would get passed to
the C code that implements the lsoda() internals and contains the
address which can be cast to a C routine pointer and the routine
invoked that way.
If we have a collection of constructor functions such as
and the generic one
the user can specify which package to use, etc.
and be precise about which symbol they want.
This avoids any loading order issues, etc.
This approach would require a little bit of code in the base R that
would "reflect" information about the native symbols in one or more
DLLs/Shared libraries. This is very convenient for exactly your
purposes and doing general meta-computing on the system. But it keeps
users above the C-level internals of R which are potentially subject
One has to be very careful not to save one of these symbol reference
objects and restore it in a different session. But this is also
another recurring issue that we have to deal with.
Will this approach work for your problem? Is it too complex?
Setzer.Woodrow at epamail.epa.gov wrote:
> Thanks; I now have the documents you mentioned.
> I knew about R_FindSymbol, but I guess I was hoping to find it was really
> stable enough to be part of the API, even though it is not listed there. I
> was hoping to use it to extend my ODE package odesolve (on CRAN), to be
> able to directly handle systems of odes written directly in C or Fortran,
> and bypassing the R call-back mechanism. Odesolve uses callbacks into R,
> so that I use compiled Fortran code to solve a system of odes written in R.
> The idea was that, in R, I would dyn.load a shared library that contained
> the ode function, then call "lsoda()" (from odesolve), passing a string
> that gives the name of the function to be integrated. The string would be
> passed to the C wrapper I have around the actual ode solver, where
> R_FindSymbol would return a function pointer.
> R. Woodrow Setzer, Jr. Phone:
> (919) 541-0128
> Experimental Toxicology Division Fax: (919) 541-5394
> Pharmacokinetics Branch
> NHEERL MD-74; US EPA; RTP, NC 27711
> Duncan Temple Lang
> <duncan at research.bell To: Woodrow Setzer/RTP/USEPA/US at EPA
> -labs.com> cc: r-help at hypatia.math.ethz.ch
> Subject: Re: [R] registration of C routines
> 07/19/01 10:07 AM
> There are 3 different places you can find out more about the
> registration mechanism. The place to find code examples
> is in the libraries in the R distribution. For example, take a
> look at
> Also, I have collected the descriptions (drafts) I have written
> about this. They are available from
> The C routine R_FindSymbol() is the internal mechanism that finds a
> native symbol by name in a package. It is not in the official API, so
> is subject to change. Hence it is not a good idea to write your code
> to depend on it, but your mileage may vary depending on the context,
> Personally, I would think that it might be better to avoid this
> low-level dependency. You might be better off linking the DLL/.so from
> the secondary package with that in the first package. Alternatively,
> on some platforms, you can specify the value of the local argument as
> FALSE for dyn.load() and library.dynam() and that makes the symbols in
> that library visible to all the others. Then your C code can call the
> routine directly. This has potential danger based on how dlopen()
> works on each system and the order in which the libraries have been
> Setzer.Woodrow at epamail.epa.gov wrote:
> > Almost at the end of the News for R-1.3.0 is the following section:
> > o New mechanism for explicitly registering native routines in a
> > DLL/shared library accessible via .C(), .Call(), .Fortran() and
> > .External(). This is potentially more robust than the existing
> > dynamic lookup, since it checks the number of arguments, type of
> > the routine.
> > How do I learn how to use this mechanism? Also, is there a sanctioned
> > to find and use, in C-code loaded via dyn.load and executed using one of
> > the calls .C(), etc., functions defined in a separate DLL/shared library
> > and also loaded with dyn.load?
> > R. Woodrow Setzer, Jr. Phone:
> > (919) 541-0128
> > Experimental Toxicology Division Fax: (919)
> > Pharmacokinetics Branch
> > NHEERL MD-74; US EPA; RTP, NC 27711
> > -.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.
> > r-help mailing list -- Read
> > Send "info", "help", or "[un]subscribe"
> > (in the "body", not the subject !) To: r-help-request at stat.math.ethz.ch
> > _._._._._._._._._._._._._._._._._._._._._._._._._._._._._._._._._._._._.
> Duncan Temple Lang duncan at research.bell-labs.com
> Bell Labs, Lucent Technologies office: (908)582-3217
> 700 Mountain Avenue, Room 2C-259 fax: (908)582-3340
> Murray Hill, NJ 07974-2070
r-help mailing list -- Read http://www.ci.tuwien.ac.at/~hornik/R/R-FAQ.html
Send "info", "help", or "[un]subscribe"
(in the "body", not the subject !) To: r-help-request at stat.math.ethz.ch
More information about the R-help