aboutsummaryrefslogtreecommitdiffstats
path: root/camel/camel-gpg-context.c
diff options
context:
space:
mode:
authorJeffrey Stedfast <fejj@ximian.com>2002-06-28 08:07:00 +0800
committerJeffrey Stedfast <fejj@src.gnome.org>2002-06-28 08:07:00 +0800
commit292847cc9694ae7041af1390f4d1956d23f20c6a (patch)
tree731344705172355707ab8e36884bfbc36be0ad9e /camel/camel-gpg-context.c
parent46bba132c7e353a3bba252ddf4f484b0c237ac46 (diff)
downloadgsoc2013-evolution-292847cc9694ae7041af1390f4d1956d23f20c6a.tar.gz
gsoc2013-evolution-292847cc9694ae7041af1390f4d1956d23f20c6a.tar.zst
gsoc2013-evolution-292847cc9694ae7041af1390f4d1956d23f20c6a.zip
Loop on our reads while errno is EINTR or EAGAIN. Also make sure to
2002-06-27 Jeffrey Stedfast <fejj@ximian.com> * camel-gpg-context.c (gpg_ctx_op_step): Loop on our reads while errno is EINTR or EAGAIN. Also make sure to completely read stdout and stderr by keeping better state. (gpg_ctx_parse_status): In the case of a NODATA response from gpg, try to use the diagnostics that gpg may have written to its stderr. (gpg_verify): Check that the gpg process has not exited. (gpg_ctx_op_wait): Make sure we haven't already exited (as by gpg_ctx_op_is_exited()) and if we have, retrieve the exit status from the gpg context. svn path=/trunk/; revision=17320
Diffstat (limited to 'camel/camel-gpg-context.c')
-rw-r--r--camel/camel-gpg-context.c70
1 files changed, 51 insertions, 19 deletions
diff --git a/camel/camel-gpg-context.c b/camel/camel-gpg-context.c
index 7d5f167d64..c847b9c66a 100644
--- a/camel/camel-gpg-context.c
+++ b/camel/camel-gpg-context.c
@@ -249,6 +249,9 @@ struct _GpgCtx {
GByteArray *diagnostics;
+ int exit_status;
+
+ unsigned int exited:1;
unsigned int complete:1;
unsigned int seen_eof1:1;
unsigned int seen_eof2:1;
@@ -262,7 +265,7 @@ struct _GpgCtx {
unsigned int validsig:1;
unsigned int trust:3;
- unsigned int padding:19;
+ unsigned int padding:18;
};
static struct _GpgCtx *
@@ -279,6 +282,8 @@ gpg_ctx_new (CamelSession *session, const char *path)
gpg->seen_eof1 = FALSE;
gpg->seen_eof2 = FALSE;
gpg->pid = (pid_t) -1;
+ gpg->exit_status = 0;
+ gpg->exited = FALSE;
gpg->path = g_strdup (path);
gpg->userid = NULL;
@@ -1100,16 +1105,38 @@ gpg_ctx_op_complete (struct _GpgCtx *gpg)
return gpg->complete && gpg->seen_eof1 && gpg->seen_eof2;
}
+static gboolean
+gpg_ctx_op_is_exited (struct _GpgCtx *gpg)
+{
+ pid_t retval;
+ int status;
+
+ if (gpg->exited)
+ return TRUE;
+
+ retval = waitpid (gpg->pid, &status, WNOHANG);
+ if (retval == gpg->pid) {
+ gpg->exit_status = status;
+ gpg->exited = TRUE;
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
static void
gpg_ctx_op_cancel (struct _GpgCtx *gpg)
{
pid_t retval;
int status;
+ if (gpg->exited)
+ return;
+
kill (gpg->pid, SIGTERM);
sleep (1);
retval = waitpid (gpg->pid, &status, WNOHANG);
- if (retval == 0) {
+ if (retval == (pid_t) 0) {
/* no more mr nice guy... */
kill (gpg->pid, SIGKILL);
sleep (1);
@@ -1124,25 +1151,30 @@ gpg_ctx_op_wait (struct _GpgCtx *gpg)
pid_t retval;
int status;
- sigemptyset (&mask);
- sigaddset (&mask, SIGALRM);
- sigprocmask (SIG_BLOCK, &mask, &omask);
- alarm (1);
- retval = waitpid (gpg->pid, &status, 0);
- alarm (0);
- sigprocmask (SIG_SETMASK, &omask, NULL);
-
- if (retval == (pid_t) -1 && errno == EINTR) {
- /* The child is hanging: send a friendly reminder. */
- kill (gpg->pid, SIGTERM);
- sleep (1);
- retval = waitpid (gpg->pid, &status, WNOHANG);
- if (retval == (pid_t) 0) {
- /* Still hanging; use brute force. */
- kill (gpg->pid, SIGKILL);
+ if (!gpg->exited) {
+ sigemptyset (&mask);
+ sigaddset (&mask, SIGALRM);
+ sigprocmask (SIG_BLOCK, &mask, &omask);
+ alarm (1);
+ retval = waitpid (gpg->pid, &status, 0);
+ alarm (0);
+ sigprocmask (SIG_SETMASK, &omask, NULL);
+
+ if (retval == (pid_t) -1 && errno == EINTR) {
+ /* The child is hanging: send a friendly reminder. */
+ kill (gpg->pid, SIGTERM);
sleep (1);
retval = waitpid (gpg->pid, &status, WNOHANG);
+ if (retval == (pid_t) 0) {
+ /* Still hanging; use brute force. */
+ kill (gpg->pid, SIGKILL);
+ sleep (1);
+ retval = waitpid (gpg->pid, &status, WNOHANG);
+ }
}
+ } else {
+ status = gpg->exit_status;
+ retval = gpg->pid;
}
if (retval != (pid_t) -1 && WIFEXITED (status))
@@ -1282,7 +1314,7 @@ gpg_verify (CamelCipherContext *context, CamelCipherHash hash,
goto exception;
}
- while (!gpg_ctx_op_complete (gpg)) {
+ while (!gpg_ctx_op_complete (gpg) && !gpg_ctx_op_is_exited (gpg)) {
if (camel_operation_cancel_check (NULL)) {
camel_exception_set (ex, CAMEL_EXCEPTION_USER_CANCEL,
_("Cancelled."));