RcppCore / Rcpp

Seamless R and C++ Integration
https://www.rcpp.org
GNU General Public License v2.0
740 stars 211 forks source link

Segfault with stop on gcc-8.3 on MacOS #961

Closed jackwasey closed 5 years ago

jackwasey commented 5 years ago
R -e 'Rcpp::cppFunction("void f() { Rcpp::stop(\"here\");}"); f()'

gives a segfault, both on my local setup (below) and travis, e.g., https://travis-ci.org/jackwasey/icd/jobs/516438592

gcc-8 --version
gcc-8 (Homebrew GCC 8.3.0) 8.3.0
R version 3.5.2 (2018-12-20) -- "Eggshell Igloo"
Copyright (C) 2018 The R Foundation for Statistical Computing
Platform: x86_64-apple-darwin15.6.0 (64-bit)

~/.R/Makevars of course has CXX=g++-8 and CC=gcc-8

MacOS 10.14.3 and FWIW xcode 10.2

You know how fun the macos toolchain is: I can't get a stack trace with debug symbols, but it seems to be in the Rcpp generated code for the function in question, hence minimal example. LLDB gives me assembly no matter what I do, and that is above my pay grade; I can't make GDB from brew work, due to code signing stuff. My package 'icd' wants openmp, which I suspected, but the above segfault happens without -fopenmp anywhere. Doesn't seem to be related to #347 or #736, but what do I know?

eddelbuettel commented 5 years ago

Is this is CRAN / R ordained compiler version for macOS? If not, I fear you very well be on your very own here.

Bugs happen. We just filed one against gfortran-8 as R Core sent me a reproducible 'this no longer works' example fortran file. Here we need to figure out if it is a g++ regression (likely) or an Rcpp issue (possible, though I am not where from; few changes in that area lately).

jackwasey commented 5 years ago

GCC 8 is mentioned in passing in WRE, but I don't see anything specific. It's really just vanilla GCC and vanilla MacOS Mojave, but I absolutely accept most Mac users are using binaries or xcode clang builds. Perhaps it originates in the brew gcc build. I don't know how the official binaries for CRAN are built for MacOS, but I'm guessing clang. If I get anywhere I'll let you know.

eddelbuettel commented 5 years ago

Using Rocker's r-base image, running apt-get update; apt-get install g++-8 gets us

> system("g++ --version")
g++ (Debian 8.3.0-5) 8.3.0
Copyright (C) 2018 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.  There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.

> Rcpp::cppFunction("void f() { Rcpp::stop(\"here\");}")
> f()
Error in f() : here
> 

So I feel inclined to close this. (My Ubuntu 18.10 box with g++ 8.2.* behaves the same way.)

jackwasey commented 5 years ago

If there is an r-hub config for macos gcc i'll try that, otherwise, please do close if you think this is outside Rcpp.

eddelbuettel commented 5 years ago

It doesn't say (on the hightest level) at rhub:

macOS macOS 10.9 Mavericks, R-oldrel (experimental) macOS 10.11 El Capitan, R-release (experimental)

eddelbuettel commented 5 years ago

I leave it open for a day or two (or longer if I forget to close...) so that other team members can comment. I am not too familar with the macOS toolchain, but to me it seems you tools are out of whack.

Just to confirm: you did, or did not, also rebuild R under that compiler?

jackwasey commented 5 years ago

I did not rebuild R - was not actually aware this was something I had to do as I've switched frequently between gcc and clang on linux without problems. I will add that to my homework before getting back to you.

I'm running an r-hub build now, so I can look in the session info to see the compiler. I will be able to let you know tomorrow.

jackwasey commented 5 years ago

R-hub is using an unspecified clang version from what i can see now.

eddelbuettel commented 5 years ago

Point takem about clang and gcc mixes. On the other hand when toolchains change (ie between major version of compilers) we sometimes recommend rebuilding as it frequently helps with these very "weird" behaviours.

And yes, clang is AFAIK the "ordained" tool for R on that platform.

kevinushey commented 5 years ago

Could this be another libstdc++ vs libc++ ABI compatibility issue?

jackwasey commented 5 years ago

How do I tell which is being used? I didn't configure anything regarding the standard libraries. The compiler call looks like:

/usr/local/bin/g++-8 -std=gnu++11 -dynamiclib -Wl,-headerpad_max_install_names -undefined dynamic_lookup -single_module -multiply_defined suppress -L/Library/Frameworks/R.framework/Resources/lib -L/usr/local/lib -o icd.so RcppExports.o appendMinor.o [.......] -F/Library/Frameworks/R.framework/.. -framework R -Wl,-framework -Wl,CoreFoundation

Is this therefore MacOS libc++?

coatless commented 5 years ago

I believe that the macOS version of R is compiled under libc++

You can determine the default standard with:

#include <Rcpp.h>

// [[Rcpp::export]]
void check_standard() {
#ifdef __GLIBCXX__
  Rcpp::Rcout << "Using libstdc++ standard (associated w/ gcc)"  << std::endl;
#endif

#ifdef _LIBCPP_VERSION
  Rcpp::Rcout << "Using libc++  standard (clang origins)" << std::endl;
#endif
}

/***R
check_standard()
*/

Running this with the clang6 build gives:

Using libc++  standard (clang origins)
eddelbuettel commented 5 years ago

I think that demonstrates the issue. Mixing these two, combined with edgier code (involving e.g. the belowed longjmp) goes boom. I am closing this as there is no structural Rcpp issue involved. One still needs to care in picking a consistent toolchain.

jackwasey commented 5 years ago

I also discovered that the bug does not exist if I compile R on MacOS with gcc-8. Thanks for all your thoughts.

eddelbuettel commented 5 years ago

That is the very library mix @kevinushey pointed out to you. These tools all work, but do not mix randomly. Ie don't drop your Chevy engine into your Ford.

jackwasey commented 5 years ago

I'm afraid I found the simple solution of just rebuilding Rcpp with the same compiler as my package. Apologies - I've read this requirement before, but didn't bring it to mind. For Travis users who might encounter this, I found that I could overcome the bug by using an Rcpp source install in the before_install stanza:

brew install gcc && echo 'CC=gcc-8' >> ~/.R/Makevars && echo 'CXX=g++-8' >> ~/.R/Makevars && echo 'CXX11=g++-8' >> ~/.R/Makevars && Rscript -e 'install.packages(\"Rcpp\", type = \"source\")'
eddelbuettel commented 5 years ago

It's really the same topic, albeit a different aspect of it :)

dcooley commented 5 years ago

If it's worth anything, I was also getting a segfault on Rcpp::stop() on Rcpp v1.0.2 (CRAN Release as of 20190927.

stop_crash

I didn't inspect this in any detail, I just upgraded to the latest github version (Rcpp * 1.0.2.1 2019-09-27 [1] Github (RcppCore/Rcpp@1789f09) and the issue has gone.

Full code

library(Rcpp)

devtools::session_info(pkgs = "Rcpp")

# ─ Session info ─────────────────────────────────────────────────────────────────────────────
# setting  value                       
# version  R version 3.6.1 (2019-07-05)
# os       macOS High Sierra 10.13.6   
# system   x86_64, darwin15.6.0        
# ui       RStudio                     
# language (EN)                        
# collate  en_AU.UTF-8                 
# ctype    en_AU.UTF-8                 
# tz       Australia/Melbourne         
# date     2019-09-27                  
# 
# ─ Packages ─────────────────────────────────────────────────────────────────────────────────
# package * version date       lib source                        
# Rcpp    * 1.0.2.1 2019-09-27 [1] Github (RcppCore/Rcpp@1789f09)
# 
# [1] /Library/Frameworks/R.framework/Versions/3.6/Resources/library

cppFunction(
  code = 'void stoptest(){
    Rcpp::stop("test");
  }'
)

stoptest()
kevinushey commented 5 years ago

I can't reproduce. I presume you're running into a similar issue (mixing of gcc + libstdc++ with clang + libc++).

Don't use gcc on macOS unless you're prepared to compile everything (including R) with gcc.

dcooley commented 5 years ago

I may have mixed compiler settings as I was exploring stuff, but now I've got everything back to how it was I can no longer reproduce it.