diff options
author | Gerald Combs <gerald@wireshark.org> | 2018-03-02 09:11:31 -0800 |
---|---|---|
committer | Gerald Combs <gerald@wireshark.org> | 2018-03-02 18:07:58 +0000 |
commit | 80d652f06e205be070ba151158042c12adbb2d7e (patch) | |
tree | 937a17493e2c326a0716324d0770242d56dce4b0 /wsutil | |
parent | 184ef021110d52d123104c77863df92f7ecc5f6e (diff) |
More spawned process handling updates.
Document ws_pipe.h. Define invalid PIDs in one place.
Extcap didn't use stdin before 1a0987904f. Make sure we close it.
Change-Id: I7a69cd9b5137ae82435e64628a22e4d812d58f89
Reviewed-on: https://code.wireshark.org/review/26226
Petri-Dish: Gerald Combs <gerald@wireshark.org>
Tested-by: Petri Dish Buildbot
Reviewed-by: Gerald Combs <gerald@wireshark.org>
Diffstat (limited to 'wsutil')
-rw-r--r-- | wsutil/ws_pipe.c | 18 | ||||
-rw-r--r-- | wsutil/ws_pipe.h | 50 |
2 files changed, 58 insertions, 10 deletions
diff --git a/wsutil/ws_pipe.c b/wsutil/ws_pipe.c index 3649276864..7628a779eb 100644 --- a/wsutil/ws_pipe.c +++ b/wsutil/ws_pipe.c @@ -170,9 +170,16 @@ gboolean ws_pipe_spawn_sync(gchar *dirname, gchar *command, gint argc, gchar **a return result; } +void ws_pipe_init(ws_pipe_t *ws_pipe) +{ + if (!ws_pipe) return; + memset(ws_pipe, 0, sizeof(ws_pipe_t)); + ws_pipe->pid = WS_INVALID_PID; +} + GPid ws_pipe_spawn_async(ws_pipe_t *ws_pipe, GPtrArray *args) { - GPid pid = INVALID_EXTCAP_PID; + GPid pid = WS_INVALID_PID; #ifdef _WIN32 gint cnt = 0; @@ -256,9 +263,14 @@ GPid ws_pipe_spawn_async(ws_pipe_t *ws_pipe, GPtrArray *args) g_setenv("PATH", oldpath, TRUE); #else - g_spawn_async_with_pipes(NULL, (gchar **)args->pdata, NULL, + GError *error = NULL; + gboolean spawned = g_spawn_async_with_pipes(NULL, (gchar **)args->pdata, NULL, (GSpawnFlags) G_SPAWN_DO_NOT_REAP_CHILD, NULL, NULL, - &pid, &ws_pipe->stdin_fd, &ws_pipe->stdout_fd, &ws_pipe->stderr_fd, NULL); + &pid, &ws_pipe->stdin_fd, &ws_pipe->stdout_fd, &ws_pipe->stderr_fd, &error); + if (!spawned) { + g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "Error creating async pipe: %s", error->message); + g_free(error->message); + } #endif ws_pipe->pid = pid; diff --git a/wsutil/ws_pipe.h b/wsutil/ws_pipe.h index e69873c449..f0429d330d 100644 --- a/wsutil/ws_pipe.h +++ b/wsutil/ws_pipe.h @@ -12,17 +12,12 @@ #ifndef __WS_PIPE_H__ #define __WS_PIPE_H__ -#include "ws_symbol_export.h" +// ws_symbol_export and WS_INVALID_PID +#include "wsutil/processes.h" #include <glib.h> #ifdef _WIN32 -#define INVALID_EXTCAP_PID INVALID_HANDLE_VALUE -#else -#define INVALID_EXTCAP_PID (GPid)-1 -#endif - -#ifdef _WIN32 #include <windows.h> #include <io.h> #define ws_pipe_handle HANDLE @@ -44,16 +39,57 @@ typedef struct _ws_pipe_t { #endif } ws_pipe_t; +/** + * @brief Run a process using g_spawn_sync on UNIX and Linux, and + * CreateProcess on Windows. Wait for it to finish. + * @param [IN] dirname Initial working directory. + * @param [IN] command Command to run. + * @param [IN] argc Number of arguments for the command, not including the command itself. + * @param [IN] argv Arguments for the command, not including the command itself. + * @param [OUT] command_output If not NULL, receives a copy of the command output. Must be g_freed. + * @return TRUE on success or FALSE on failure. + */ WS_DLL_PUBLIC gboolean ws_pipe_spawn_sync ( gchar * dirname, gchar * command, gint argc, gchar ** argv, gchar ** command_output ); +/** + * @brief Initialize a ws_pipe_t struct. Sets .pid to WS_INVALID_PID and all other members to 0 or NULL. + * @param ws_pipe [IN] The pipe to initialize. + */ +WS_DLL_PUBLIC void ws_pipe_init(ws_pipe_t *ws_pipe); + +/** + * @brief Start a process using g_spawn_sync on UNIX and Linux, and CreateProcess on Windows. + * @param ws_pipe The process PID, stdio descriptors, etc. + * @param args The command to run along with its arguments. + * @return A valid PID on success, otherwise WS_INVALID_PID. + */ WS_DLL_PUBLIC GPid ws_pipe_spawn_async (ws_pipe_t * ws_pipe, GPtrArray * args ); +/** + * @brief Wait for a set of handles using WaitForMultipleObjects. Windows only. + * @param pipe_handles An array of handles + * @param num_pipe_handles The size of the array. + * @param pid Child process PID. + * @return TRUE on success or FALSE on failure. + */ #ifdef _WIN32 WS_DLL_PUBLIC gboolean ws_pipe_wait_for_pipe(HANDLE * pipe_handles, int num_pipe_handles, HANDLE pid); #endif +/** + * @brief Check to see if a file descriptor has data available. + * @param pipe_fd File descriptor, usually ws_pipe_t .stdout_fd or .stderr_fd. + * @return TRUE if data is available or FALSE otherwise. + */ WS_DLL_PUBLIC gboolean ws_pipe_data_available(int pipe_fd); +/** + * @brief Read up to buffer_size - 1 bytes from a pipe and append '\0' to the buffer. + * @param read_pipe File descriptor, usually ws_pipe_t .stdout_fd or .stderr_fd. + * @param buffer String buffer. + * @param buffer_size String buffer size. + * @return TRUE if zero or more bytes were read without error, FALSE otherwise. + */ WS_DLL_PUBLIC gboolean ws_read_string_from_pipe(ws_pipe_handle read_pipe, gchar *buffer, size_t buffer_size); |