Alexander Sobolev
Alexander Sobolev

Reputation: 789

Error calling C++ function from R - library loads, but function is not on the table

Here is the C code:

// a.cpp
void double_me(int* x) {
  // takes a numeric input and doubles it
  *x = *x + *x;
}

I compile the code with

>R CMD SHLIB a.cpp

After that i run R and type following commands:

 dinfo <- dyn.load("a.so")
 .C("double_me",x=2)

This end with error: "double_me" is not on the list.

Now the question: dyn.load works fine, dinfo contains:

DLL name: a Filename: /Users/myusername/a.so Dynamic lookup: TRUE

But the function is not on the table:

is.loaded("double_me") [1] FALSE

How could it happen? This happens on macOS.

Upvotes: 2

Views: 71

Answers (1)

duckmayr
duckmayr

Reputation: 16930

This is because you are using a.cpp; C++ function names are "mangled" by the compiler. You can use your same code with the filename a.c, compiling it just as you did, and get the following from R:

> dinfo <- dyn.load("a.so")
>  .C("double_me",x=2)
$x
[1] 2

Or, alternatively, you can add this line to the top of a.cpp:

extern "C" void double_me(int* x);

and get the following from R:

> dinfo <- dyn.load("a.so")
>  .C("double_me",x=2)
$x
[1] 2

Update: Why was the result above 2?

If you do not coerce the argument to the proper type, a copy may be made, such that your original value is not altered; if we coerce the value to be an integer as we should when using .C(), we get the expected result:

> dyn.load("a.so")
> .C("double_me", x = as.integer(2))
$x
[1] 4

Upvotes: 3

Related Questions