14 Evaluation
Evaluating R code from C is how you call back into R: apply a function, access a method, or run user-supplied expressions. There is no public “apply this closure to these arguments” entry point (Rf_applyClosure() is internal); instead you build a call — a LANGSXP pairlist, see Pairlists, calls, and ... — and evaluate it with Rf_eval().
Evaluation can do anything R code can do: allocate, signal errors, and longjmp. Treat every Rf_eval() as a potential non-local return and protect accordingly.
14.1 Evaluation
Follows WRE §5.11, Evaluating R expressions from C closely.
A typical use looks up a function and calls it with C-constructed arguments:
SEXP call = PROTECT(Rf_lang2(Rf_install("sqrt"), x));
SEXP result = PROTECT(Rf_eval(call, R_GlobalEnv));
/* ... */
UNPROTECT(2);For more than a couple of arguments, build the call with Rf_allocList() + SET_TYPEOF(..., LANGSXP) or Rf_cons() rather than deeply nesting Rf_lang*() calls. Evaluate in the environment that gives the call the right scope: R_GlobalEnv for user-visible semantics, a namespace environment for calling a package’s internals, or R_BaseEnv/R_BaseNamespace for base functions.
14.1.1 Rf_eval()
needs protect throws
Header: Rinternals.h
R equivalent: eval()
Evaluate an expression in an environment.
SEXP Rf_eval(SEXP expression, SEXP environment);Returns: The result of evaluating expression in environment; may be R_NilValue.
Expression can be anything - non-language objects are returned as is.
14.1.2 R_forceAndCall()
experimental needs protect throws
Header: Rinternals.h
Force promises in an expression and then call it.
SEXP R_forceAndCall(SEXP expression, int n, SEXP environment);n: The number of arguments to force.
Returns: The result of the call after forcing the first n arguments.
n is the number of leading arguments in the call to force before evaluating.
See also: Rf_eval()
14.1.3 Rf_substitute()
needs protect throws
Header: Rinternals.h
R equivalent: substitute()
Substitute values for variables in an expression.
SEXP Rf_substitute(SEXP,SEXP);Returns: The expression with variables replaced by their values.
14.2 Protected evaluation
Rf_eval() longjmps on error, abandoning your C function mid-flight. If you need to keep control after a failure — to report the error yourself, retry, or clean up and continue — evaluate in a context that catches the error instead. These functions ignore all existing condition handlers, so R-level tryCatch() and suppressWarnings() have no effect on the protected evaluation.
For richer control — running cleanup code on unwind, or installing condition handlers — see Errors and conditions.
14.2.1 R_tryEval(), R_tryEvalSilent()
needs protect
Header: Rinternals.h
R equivalent: try()
Evaluate an R expression in a stand-alone context so errors don’t longjmp.
SEXP R_tryEval(SEXP expression, SEXP environment, int* pOutError);
SEXP R_tryEvalSilent(SEXP expression, SEXP environment, int* pOutError);pOutError: On error, the function returns NULL and sets the contents ofpOutErrorto 1.
Returns: The result of evaluating expression, or NULL on error (with *pOutError set to 1).
R_tryEvalSilent() behaves like R_tryEval() but suppresses printing of error messages. Both ignore existing condition handlers, so R-level tryCatch() and suppressWarnings() have no effect on the evaluation.
See also: R_ToplevelExec()
14.2.2 R_ToplevelExec()
Header: Rinternals.h
Execute a C function in a top-level context, catching any errors.
Rboolean R_ToplevelExec(void (*fun)(void *), void *data);fun: C function to call after context setup. Passed*data.
Returns: TRUE if fun ran to completion, FALSE if an error occurred.
Both R_tryEval() and R_tryEvalSilent() call R_ToplevelExec under the hood.
See also: R_tryEval()
14.2.3 R_curErrorBuf()
experimental
Header: Rinternals.h
R equivalent: geterrmessage()
Access the text of the current error.
const char *R_curErrorBuf();Returns: The text of the current error message.
14.3 Parsing
Parsing turns text into an expression vector (EXPRSXP) without evaluating it; evaluate the result element by element with Rf_eval(). Always check the returned ParseStatus before evaluating.
14.3.1 R_ParseVector(), R_ParseString(), R_ParseEvalString()
needs protect throws
Header: R_ext/Parse.h
Parse R code from a character vector or C string.
SEXP R_ParseVector(SEXP text, int n, ParseStatus *status, SEXP srcfile);
SEXP R_ParseString(const char *str);
SEXP R_ParseEvalString(const char *str, SEXP env);text: a character vector of lines of R code.n: number of elements to parse, or -1 for all.status: set toPARSE_OK,PARSE_INCOMPLETE,PARSE_ERROR, orPARSE_EOF; may beNULL.srcfile: a source reference environment, usuallyR_NilValue.
Returns: R_ParseVector() and R_ParseString() return an EXPRSXP vector of parsed expressions; R_ParseEvalString() returns the result of evaluating the parsed code in env.
Returns an EXPRSXP of parsed expressions. R_ParseString() (R 4.4.0) parses a single C string; R_ParseEvalString() parses and evaluates in one step. Check status before evaluating the result.
See also: Rf_eval()