diff options
author | Yusuke Sato <yusukes@google.com> | 2015-08-14 01:22:53 -0700 |
---|---|---|
committer | Yusuke Sato <yusukes@google.com> | 2015-08-19 11:00:37 -0700 |
commit | d81c3c6c45e572365127b73594c0ccf0b7f86f17 (patch) | |
tree | 2f0f5b12c2d37f58d57e9135295d9c7a3b8ca026 /logwrapper | |
parent | 1d44be87ffdc5e3bc074ab68200bff9d32c60d3a (diff) | |
download | core-d81c3c6c45e572365127b73594c0ccf0b7f86f17.tar.gz core-d81c3c6c45e572365127b73594c0ccf0b7f86f17.tar.bz2 core-d81c3c6c45e572365127b73594c0ccf0b7f86f17.zip |
Add |opts| argument to android_fork_execvp_ext
to allow the caller to send data to the child's stdin.
Bug: 21725996
Change-Id: I818f5cf61045286c8d64a91b6d50f05740329be1
Diffstat (limited to 'logwrapper')
-rw-r--r-- | logwrapper/include/logwrap/logwrap.h | 23 | ||||
-rw-r--r-- | logwrapper/logwrap.c | 28 | ||||
-rw-r--r-- | logwrapper/logwrapper.c | 2 |
3 files changed, 48 insertions, 5 deletions
diff --git a/logwrapper/include/logwrap/logwrap.h b/logwrapper/include/logwrap/logwrap.h index 4307a3055..449461f65 100644 --- a/logwrapper/include/logwrap/logwrap.h +++ b/logwrapper/include/logwrap/logwrap.h @@ -19,6 +19,7 @@ #define __LIBS_LOGWRAP_H #include <stdbool.h> +#include <stdint.h> __BEGIN_DECLS @@ -53,6 +54,9 @@ __BEGIN_DECLS * the specified log until the child has exited. * file_path: if log_target has the LOG_FILE bit set, then this parameter * must be set to the pathname of the file to log to. + * opts: set to non-NULL if you want to use one or more of the + * FORK_EXECVP_OPTION_* features. + * opts_len: the length of the opts array. When opts is NULL, pass 0. * * Return value: * 0 when logwrap successfully run the child process and captured its status @@ -68,8 +72,22 @@ __BEGIN_DECLS #define LOG_KLOG 2 #define LOG_FILE 4 +/* Write data to child's stdin. */ +#define FORK_EXECVP_OPTION_INPUT 0 + +struct AndroidForkExecvpOption { + int opt_type; + union { + struct { + const uint8_t* input; + size_t input_len; + } opt_input; + }; +}; + int android_fork_execvp_ext(int argc, char* argv[], int *status, bool ignore_int_quit, - int log_target, bool abbreviated, char *file_path); + int log_target, bool abbreviated, char *file_path, + const struct AndroidForkExecvpOption* opts, size_t opts_len); /* Similar to above, except abbreviated logging is not available, and if logwrap * is true, logging is to the Android system log, and if false, there is no @@ -79,7 +97,8 @@ static inline int android_fork_execvp(int argc, char* argv[], int *status, bool ignore_int_quit, bool logwrap) { return android_fork_execvp_ext(argc, argv, status, ignore_int_quit, - (logwrap ? LOG_ALOG : LOG_NONE), false, NULL); + (logwrap ? LOG_ALOG : LOG_NONE), false, NULL, + NULL, 0); } __END_DECLS diff --git a/logwrapper/logwrap.c b/logwrapper/logwrap.c index 777dafeff..c7b48358e 100644 --- a/logwrapper/logwrap.c +++ b/logwrapper/logwrap.c @@ -474,7 +474,8 @@ static void child(int argc, char* argv[]) { } int android_fork_execvp_ext(int argc, char* argv[], int *status, bool ignore_int_quit, - int log_target, bool abbreviated, char *file_path) { + int log_target, bool abbreviated, char *file_path, + const struct AndroidForkExecvpOption* opts, size_t opts_len) { pid_t pid; int parent_ptty; int child_ptty; @@ -483,6 +484,7 @@ int android_fork_execvp_ext(int argc, char* argv[], int *status, bool ignore_int sigset_t blockset; sigset_t oldset; int rc = 0; + size_t i; rc = pthread_mutex_lock(&fd_mutex); if (rc) { @@ -529,7 +531,13 @@ int android_fork_execvp_ext(int argc, char* argv[], int *status, bool ignore_int pthread_sigmask(SIG_SETMASK, &oldset, NULL); close(parent_ptty); - // redirect stdout and stderr + // redirect stdin, stdout and stderr + for (i = 0; i < opts_len; ++i) { + if (opts[i].opt_type == FORK_EXECVP_OPTION_INPUT) { + dup2(child_ptty, 0); + break; + } + } dup2(child_ptty, 1); dup2(child_ptty, 2); close(child_ptty); @@ -546,6 +554,22 @@ int android_fork_execvp_ext(int argc, char* argv[], int *status, bool ignore_int sigaction(SIGQUIT, &ignact, &quitact); } + for (i = 0; i < opts_len; ++i) { + if (opts[i].opt_type == FORK_EXECVP_OPTION_INPUT) { + size_t left = opts[i].opt_input.input_len; + const uint8_t* input = opts[i].opt_input.input; + while (left > 0) { + ssize_t res = + TEMP_FAILURE_RETRY(write(parent_ptty, input, left)); + if (res < 0) { + break; + } + left -= res; + input += res; + } + } + } + rc = parent(argv[0], parent_ptty, pid, status, log_target, abbreviated, file_path); } diff --git a/logwrapper/logwrapper.c b/logwrapper/logwrapper.c index 9e0385db2..55b71c708 100644 --- a/logwrapper/logwrapper.c +++ b/logwrapper/logwrapper.c @@ -81,7 +81,7 @@ int main(int argc, char* argv[]) { } rc = android_fork_execvp_ext(argc, &argv[0], &status, true, - log_target, abbreviated, NULL); + log_target, abbreviated, NULL, NULL, 0); if (!rc) { if (WIFEXITED(status)) rc = WEXITSTATUS(status); |