diff options
Diffstat (limited to 'rsCppUtils.cpp')
-rw-r--r-- | rsCppUtils.cpp | 44 |
1 files changed, 44 insertions, 0 deletions
diff --git a/rsCppUtils.cpp b/rsCppUtils.cpp index c9a19c23..b55f9e6a 100644 --- a/rsCppUtils.cpp +++ b/rsCppUtils.cpp @@ -21,6 +21,10 @@ #include <string.h> +#ifndef RS_COMPATIBILITY_LIB +#include <sys/wait.h> +#endif + namespace android { namespace renderscript { @@ -46,5 +50,45 @@ const char* rsuJoinStrings(int n, const char* const* strs) { return strndup(tmp.c_str(), tmp.size()); } +#ifndef RS_COMPATIBILITY_LIB +bool rsuExecuteCommand(const char *exe, int nArgs, const char * const *args) { + std::unique_ptr<const char> joined(rsuJoinStrings(nArgs, args)); + + pid_t pid = fork(); + + switch (pid) { + case -1: { // Error occurred (we attempt no recovery) + ALOGE("Fork of \"%s\" failed with error %s", exe, strerror(errno)); + return false; + } + case 0: { // Child process + ALOGV("Invoking %s with args '%s'", exe, joined.get()); + execv(exe, (char * const *)args); + + ALOGE("execv() failed: %s", strerror(errno)); + abort(); + return false; + } + default: { // Parent process (actual driver) + // Wait on child process to finish execution. + int status = 0; + pid_t w = TEMP_FAILURE_RETRY(waitpid(pid, &status, 0)); + if (w == -1) { + ALOGE("Waitpid of \"%s\" failed with error %s", exe, + strerror(errno)); + return false; + } + + if (WIFEXITED(status) && WEXITSTATUS(status) == 0) { + return true; + } + + ALOGE("Child process \"%s\" terminated with status %d", exe, status); + return false; + } + } +} +#endif // RS_COMPATIBILITY_LIB + } } |