in src/SubprocessWin.cpp [28:108]
SEXP myDoSystem(SEXP call, SEXP op, SEXP args, SEXP) {
int argsCount = Rf_length(args);
int consignals = NA_INTEGER;
Rf_checkArityCall(op, args, call);
if (argsCount < 5 || argsCount > 7) {
Rf_error("RWrapper error: %d arguments passed to .Internal(system) which requires 5, 6 or 7", argsCount);
}
SEXP cmdExp = CAR(args);
if (!Rf_isString(cmdExp) || Rf_xlength(cmdExp) != 1)
Rf_errorcall(call, "character string expected as first argument");
const char* cmd = CHAR(STRING_ELT(cmdExp, 0));
args = CDR(args);
int flag = Rf_asInteger(CAR(args));
args = CDR(args);
if (flag >= 20) {
flag -= 20;
} else if (flag >= 10) {
flag -= 10;
}
SEXP Stdin = CAR(args);
if (!Rf_isString(Stdin)) Rf_errorcall(call, "character string expected as third argument");
const char* fin = CHAR(STRING_ELT(Stdin, 0));
args = CDR(args);
SEXP Stdout = CAR(args);
args = CDR(args);
SEXP Stderr = CAR(args);
args = CDR(args);
int timeout = args == R_NilValue ? 0 : Rf_asInteger(CAR(args));
if (timeout == NA_INTEGER || timeout < 0 || timeout > 2000000)
/* the limit could be increased, but not much as in milliseconds it
has to fit into a 32-bit unsigned integer */
Rf_errorcall(call, "invalid '%s' argument", "timeout");
if (timeout && !flag)
Rf_errorcall(call, "Timeout with background running processes is not supported.");
if (argsCount >= 7) {
consignals = Rf_asLogical(CADR(args));
if (consignals == NA_INTEGER) {
Rf_errorcall(call, "invalid '%s' argument", "receive.console.signals");
}
}
if (flag == 2) flag = 1; /* ignore std.output.on.console */
const char* fout = "";
const char* ferr = "";
SystemOutputType outType = IGNORE_OUTPUT;
SystemOutputType errType = IGNORE_OUTPUT;
if (TYPEOF(Stdout) == STRSXP) {
fout = CHAR(STRING_ELT(Stdout, 0));
outType = fout[0] ? TO_FILE : PRINT;
} else {
outType = Rf_asLogical(Stdout) ? COLLECT : IGNORE_OUTPUT;
}
if (TYPEOF(Stderr) == STRSXP) {
ferr = CHAR(STRING_ELT(Stderr, 0));
errType = ferr[0] ? TO_FILE : PRINT;
} else {
errType = Rf_asLogical(Stderr) ? COLLECT : IGNORE_OUTPUT;
}
CPP_BEGIN
std::string command = cmd;
DoSystemResult res = myDoSystemImpl(command.c_str(), timeout, outType, fout, errType, ferr, fin, flag == 0, consignals);
if (res.timedOut) Rf_warning("command '%s' timed out after %ds", cmd, timeout);
if (outType == COLLECT || errType == COLLECT) {
std::vector<std::string> lines;
std::istringstream stream(res.output);
std::string line;
while (std::getline(stream, line)) {
if (!line.empty() && line.back() == '\r') line.pop_back();
lines.push_back(line);
}
return makeCharacterVector(lines);
} else {
return toSEXP(res.exitCode);
}
CPP_END
}