Stack Exchange
Evaluating R command from C is not working
I'm trying to make simple R command evaluator.
I have the following code:
Evaluator.h
void evaluate(const std::string &command);

extern "C" SEXP run_eval() {
  evaluate("grDevices:::png(\"snapshot.png\")");

  return R_NilValue;
}

Evaluator.cpp
SEXP createSexp(const std::string &str, ScopeProtector *protector) {
  SEXP result = Rf_allocVector(STRSXP, 1);

  protector->add(result);

  SET_STRING_ELT(result, 0, Rf_mkChar(str.c_str()));

  return result;
}

SEXP createExpressionSexp(SEXP strSexp, ScopeProtector *protector) {
  ParseStatus status;

  SEXP result = R_ParseVector(strSexp, 1, &status, R_NilValue);

  protector->add(result);

  return result;
}

SEXP createExpressionSexp(const std::string &str, ScopeProtector *protector) {
  return createExpressionSexp(createSexp(str, protector), protector);
}

SEXP evaluateExpression(SEXP exprSexp, ScopeProtector *protector) {
  SEXP result = Rf_eval(exprSexp, R_GlobalEnv);

  protector->add(result);

  return result;
}

void evaluate(const std::string &command) {
  ScopeProtector protector;

  evaluateExpression(createExpressionSexp(command, &protector), &protector);
}

ScopeProtector.h
class ScopeProtector: boost::noncopyable {
 public:
  ScopeProtector();

  virtual ~ScopeProtector();

  void add(SEXP sexp);

 private:
  class Impl;

  const std::unique_ptr<Impl> pImpl;
};

ScopeProtector.cpp
class ScopeProtector::Impl {
 public:
  Impl() : count(0) {
  }

  virtual ~Impl() {
    if (count > 0) {
      UNPROTECT(count);
    }
  }

  void add(SEXP sexp) {
    PROTECT(sexp);
    count++;
  }

 private:
  int count;
};

ScopeProtector::ScopeProtector() : pImpl(new Impl) {
}

ScopeProtector::~ScopeProtector() = default;

void ScopeProtector::add(SEXP sexp) {
  pImpl->add(sexp);
}

CMakeLists.txt
cmake_minimum_required(VERSION 3.3)
project(REvaluator)

set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11 -Wall -Werror")

include_directories("/usr/share/R/include")

set(
        SOURCE_FILES
        Evaluator.cpp Evaluator.h
        ScopeProtector.cpp ScopeProtector.h
)

add_library(revaluator SHARED ${SOURCE_FILES})

I'm trying to check my evaluator by executing the following commands:
> dyn.load("librevaluator.so")
> .Call("run_eval")
NULL
> dev.list()
NULL

As you can see there is no any png devices. Could you tell what is the problem?

I've found the solution. Just replace
SEXP result = Rf_eval(exprSexp, R_GlobalEnv);

with
SEXP result = Rf_eval(VECTOR_ELT(exprSexp, 0), R_GlobalEnv);


Have you looked at Rcpp and its Rcpp::Function() ?
R> library(Rcpp)
R> dev.list()
NULL
R> cppFunction('void newDev(std::string filename) { 
        Rcpp::Function dn = Rcpp::Function("png"); 
        dn(filename); }')
R> newDev("/tmp/foo.png")
R> dev.list()
png 
  2 
R> 

We generally do not recommend to call lots of R functions from 'down low in C++' but for the occassional set-up issue like creating a graphics device it is perfectly fine.
(Note that I indented the code to fit for the display here. The cppFunction() is one line; it creates a shared library with the function defined in the argument and assigns it -- so that the new R caller newDev we just created can then be used to create the png device.)

Is Rcpp included into std R distribution or it should be installed manually?

@user2235698 you can always check if something is already installed by using installed.packages()

@Tim I'd like to write evaluator which should work with any R installation

@user2235698 Rcpp is the most simple and recommended (e.g. http://adv-r.had.co.nz/Rcpp.html) way to do it. If you want, you can always use pure C++ but why would you like to bother with reinventing the wheel..? Many major packages link to Rcpp so most users would it have installed already.
