summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRichard Yao <ryao@gentoo.org>2012-11-19 15:48:48 -0500
committerRichard Yao <ryao@cs.stonybrook.edu>2012-11-22 22:53:32 -0500
commit9b996818cb6eacaaecaaa9bae8d0377fa1fdb803 (patch)
tree64985a4a9d926aa4ca69623416256e61798e4362
parent8a72e9e927f7d3fea2696e5c71a420d3638985e0 (diff)
Introduce execute_command
This is useful in situations where we do not have builtins avaiable. Signed-off-by: Richard Yao <ryao@gentoo.org>
-rw-r--r--src/udev/util.c40
-rw-r--r--src/udev/util.h1
2 files changed, 41 insertions, 0 deletions
diff --git a/src/udev/util.c b/src/udev/util.c
index 6d826b6f5e..d8c5bb2e1e 100644
--- a/src/udev/util.c
+++ b/src/udev/util.c
@@ -4296,6 +4296,46 @@ bool dirent_is_file_with_suffix(const struct dirent *de, const char *suffix) {
return endswith(de->d_name, suffix);
}
+int execute_command(const char *command, char *const argv[])
+{
+
+ pid_t pid;
+ int status;
+
+ if ((status = access(command, X_OK)) != 0)
+ return status;
+
+ if ((pid = fork()) < 0) {
+ log_error("Failed to fork: %m");
+ return pid;
+ }
+
+ if (pid == 0) {
+
+ execv(command, argv);
+
+ log_error("Failed to execute %s: %m", command);
+ _exit(EXIT_FAILURE);
+ }
+ else while (1)
+ {
+ siginfo_t si;
+
+ int r = waitid(P_PID, pid, &si, WEXITED);
+
+ if (!is_clean_exit(si.si_code, si.si_status, NULL)) {
+ if (si.si_code == CLD_EXITED)
+ log_error("%s exited with exit status %i.", command, si.si_status);
+ else
+ log_error("%s terminated by signal %s.", command, signal_to_string(si.si_status));
+ } else
+ log_debug("%s exited successfully.", command);
+
+ return si.si_status;
+
+ }
+}
+
void execute_directory(const char *directory, DIR *d, char *argv[]) {
DIR *_d = NULL;
struct dirent *de;
diff --git a/src/udev/util.h b/src/udev/util.h
index a148ebbc58..b9230e38bc 100644
--- a/src/udev/util.h
+++ b/src/udev/util.h
@@ -453,6 +453,7 @@ bool tty_is_console(const char *tty);
int vtnr_from_tty(const char *tty);
const char *default_term_for_tty(const char *tty);
+int execute_command(const char *command, char *const argv[]);
void execute_directory(const char *directory, DIR *_d, char *argv[]);
int kill_and_sigcont(pid_t pid, int sig);