[Rcpp-devel] Passing a pointer to a class via modules

Ege Rubak rubak at math.aau.dk
Sun Feb 5 09:36:39 CET 2017


Hi,

I'm making an R interface to Google's s2 library for geometry on the 
sphere via Rcpp Modules. In general Modules is great for this since it 
allows me to expose a lot of classes and functions without much C++ 
experience.

Now I have encountered a problem which I would be grateful for help on.

Context: A S2Polygon is a region on the sphere consisting of one or more 
loops (of class S2Loop) which may represent e.g. landmass and lakes.

I have successfully exposed these classes using RCPP_EXPOSED_CLASS, and 
everything appears to work, but then at some later point when I try to 
access the loop in the polygon I suddenly get segfaults like:
  *** caught segfault ***
address 0x111, cause 'memory not mapped'
An irrecoverable exception occurred. R is aborting now ...

I think that this happens because the S2Polygon doesn't contain the 
loops that it is made up from but only pointers to these, and it appears 
that when I pass a S2Loop to the S2Polygon (through a S2PolygonBuilder) 
a new copy of the loop is made in C++ land and the S2Polygon points to 
this copy (and I guess eventually it is destroyed since it isn't 
protected by R).

I can construct a S2Loop from a data.frame of (lng,lat)s:
```r
library(s2) ## Version from github.com/spatstat/s2  -- not CRAN!
template <- data.frame(lng = c(1,-1,-1,1), lat = c(1,1,-1,-1))
s2loop <- S2Loop$new(template)
```

Then a S2Polygon can be constructed using a builder like this:
```r
pb <- S2PolygonBuilder$new(S2PolygonBuilderOptions$new())
pb$AddLoop(s2loop)
p <- S2Polygon$new()
unused_edges <- 0
pb$AssemblePolygon(p, unused_edges)
```

The polygon `p` now has a single loop, but this loop is not pointing to 
the one in R as I see output like:
```r
s2loop
## C++ object <0x23c9620> of class 'S2Loop' <0x27a80d0>
p$loop(0)
## C++ object <0xe8a9c0> of class 'S2Loop' <0x27a80d0>
```

In s2polygonbuilder.h the member function AddLoop(S2Loop const* loop) 
doesn't take ownership over the loop according to the source code comment:
https://github.com/spatstat/s2/blob/master/src/geometry/s2/s2polygonbuilder.h#L192-L193

Do you think I have the correct understanding of the problem?
And more importantly do you see a way to fix it? (Which is an 
non-intrusive as possible, since I try to modify the source code as 
little as possible.)

At the bottom of this email is a short script creating a bigger polygon 
from many loops and then accessing the loops, which consistently 
triggers the segfault for me in case it has any interest (probably not 
since it takes several minutes to just install the library from GitHub, 
so I don't expect anyone to waste time on this).

Kind regards,
Ege

############### segfault.R ###############

```r
library(s2) ## Version from github.com/spatstat/s2  -- not CRAN!

template <- data.frame(lng = c(1,-1,-1,1), lat = c(1,1,-1,-1))
looplist <- lapply(1:80, function(s) s*template)
s2loops <- lapply(looplist, S2Loop$new)

pb <- S2PolygonBuilder$new(S2PolygonBuilderOptions$new())
for(l in s2loops) pb$AddLoop(l)

p <- S2Polygon$new()
unused_edges <- 0
pb$AssemblePolygon(p, unused_edges)

p$loop(0)

for(i in 1:p$num_loops()){
   p$loop(i-1)
}
```

#############################################

-- 
Ege Rubak, Associate Professor,
Department of Mathematical Sciences, Aalborg University
Fredrik Bajers Vej 7G, 9220 Aalborg East, Denmark
Phone: (+45)99408861
Mobile: (+45)30230252
Email: rubak at math.aau.dk


More information about the Rcpp-devel mailing list