From f7f5435f252a53bcd74428446a00f1bcd1fbae70 Mon Sep 17 00:00:00 2001 From: Ben Kibbey Date: Wed, 25 Mar 2009 20:36:24 -0400 Subject: [PATCH] Removed pwmd_open_nb(), pwmd_save_nb(), pwmd_open_nb_finalize() and pwmd_save_nb_finalize(). These have been replaced with pwmd_open_async2() and pwmd_save_async2() which are asynchronous commands that should call pwmd_process() but still have the same functionality as the old functions. --- src/libpwmd.c | 321 +++++++++++++++++++++++++------------------------------ src/libpwmd.h.in | 47 +------- src/pwmc.c | 75 ++----------- src/types.h | 8 ++ 4 files changed, 168 insertions(+), 283 deletions(-) diff --git a/src/libpwmd.c b/src/libpwmd.c index 4012a1c8..b43ddb7c 100644 --- a/src/libpwmd.c +++ b/src/libpwmd.c @@ -947,35 +947,6 @@ static int _inquire_cb(void *data, const char *keyword) return rc; } -gpg_error_t pwmd_finalize(pwm_t *pwm) -{ - if (!pwm) - return GPG_ERR_INV_ARG; - - if (pwm->cmd == ASYNC_CMD_NONE || pwm->state != ASYNC_DONE) - return GPG_ERR_INV_STATE; - - pwm->state = ASYNC_INIT; - pwm->cmd = ASYNC_CMD_NONE; - -#ifdef WITH_TCP - if (pwm->cmd == ASYNC_CMD_CONNECT || pwm->cmd == ASYNC_CMD_DNS) { - gpg_error_t rc = pwm->tcp_conn->rc; - - /* pwm is no longer a valid handle. */ - if (rc) - pwmd_close(pwm); - - return 0; - } -#endif - - if (pwm->fd < 0) - return GPG_ERR_INV_ARG; - - return 0; -} - static gpg_error_t do_nb_command(pwm_t *pwm, const char *cmd, const char *arg) { char *buf; @@ -1078,13 +1049,18 @@ gpg_error_t pwmd_pending_line(pwm_t *pwm) return assuan_pending_line(pwm->ctx) ? 0 : GPG_ERR_NO_DATA; } -static void reset_async(pwm_t *pwm) +static pwmd_async_t reset_async(pwm_t *pwm) { pwm->state = ASYNC_INIT; pwm->cmd = ASYNC_CMD_NONE; pwm->ntries = 0; #ifdef WITH_PINENTRY pwm->is_open_cmd = 0; + + if (pwm->nb_fd != -1) { + close(pwm->nb_fd); + pwm->nb_fd = -1; + } #endif #ifdef WITH_TCP if (pwm->tcp_conn && pwm->tcp_conn->fd != -1) { @@ -1092,6 +1068,8 @@ static void reset_async(pwm_t *pwm) pwm->tcp_conn->fd = -1; } #endif + + return ASYNC_DONE; }; pwmd_async_t pwmd_process(pwm_t *pwm, gpg_error_t *rc, char **result) @@ -1117,6 +1095,12 @@ pwmd_async_t pwmd_process(pwm_t *pwm, gpg_error_t *rc, char **result) return pwm->state; } + /* Fixes pwmd_open/save_async2() when there is a cached or new file. */ + if (pwm->state == ASYNC_DONE) { + reset_async(pwm); + return ASYNC_DONE; + } + if (pwm->state != ASYNC_PROCESS) { *rc = GPG_ERR_INV_STATE; return ASYNC_DONE; @@ -1193,20 +1177,49 @@ pwmd_async_t pwmd_process(pwm_t *pwm, gpg_error_t *rc, char **result) case ASYNC_CMD_HOSTKEY: if (!*rc) *result = pwm->result; - - reset_async(pwm); break; default: break; } + return reset_async(pwm); + } +#endif + +#ifdef WITH_PINENTRY + if (pwm->cmd == ASYNC_CMD_OPEN2 || pwm->cmd == ASYNC_CMD_SAVE2) { + if (pwm->nb_fd == -1) { + *rc = GPG_ERR_INV_STATE; + return reset_async(pwm); + } + + FD_ZERO(&fds); + FD_SET(pwm->nb_fd, &fds); +#ifdef WITH_LIBPTH + n = pth_select(pwm->nb_fd+1, &fds, NULL, NULL, &tv); +#else + n = select(pwm->nb_fd+1, &fds, NULL, NULL, &tv); +#endif + if (n == -1) { + *rc = gpg_error_from_syserror(); + return reset_async(pwm); + } + + if (n > 0) { + pwmd_nb_status_t nb; + size_t len = read(pwm->nb_fd, &nb, sizeof(nb)); + + *rc = nb.error; + return reset_async(pwm); + } + return pwm->state; } #endif if (pwm->fd < 0) { *rc = GPG_ERR_INV_STATE; - return ASYNC_DONE; + return reset_async(pwm); } /* This is for the non-blocking OPEN and SAVE commands. */ @@ -1218,14 +1231,26 @@ pwmd_async_t pwmd_process(pwm_t *pwm, gpg_error_t *rc, char **result) n = select(pwm->fd+1, &fds, NULL, NULL, &tv); #endif + if (n == -1) { + *rc = gpg_error_from_syserror(); + return reset_async(pwm); + } + if (n > 0) { - if (FD_ISSET(pwm->fd, &fds)) + if (FD_ISSET(pwm->fd, &fds)) { *rc = parse_assuan_line(pwm); + + if (*rc) + return reset_async(pwm); + } } while (!*rc && assuan_pending_line(pwm->ctx)) *rc = parse_assuan_line(pwm); + if (*rc) + return reset_async(pwm); + /* For pinentry retries. */ if (pwm->is_open_cmd && gpg_err_code(*rc) == EPWMD_BADKEY && ++pwm->ntries < pwm->pinentry_tries) { @@ -1233,6 +1258,9 @@ pwmd_async_t pwmd_process(pwm_t *pwm, gpg_error_t *rc, char **result) *rc = pwmd_open_async(pwm, pwm->filename); } + if (*rc) + return reset_async(pwm); + if (pwm->state == ASYNC_DONE) { reset_async(pwm); return ASYNC_DONE; @@ -1668,36 +1696,6 @@ getpin_again: } #endif -gpg_error_t pwmd_open_nb_finalize(pwm_t *pwm, pwmd_nb_status_t *pw) -{ - gpg_error_t error; - -#ifndef WITH_PINENTRY - return GPG_ERR_NOT_IMPLEMENTED; -#endif - - if (!pwm || !pw || !pw->filename[0]) - return GPG_ERR_INV_ARG; - - close(pw->fd); - - if (pw->error) { - error = pw->error; - goto fail; - } - - if (pwm->filename) - pwmd_free(pwm->filename); - - pwm->filename = pwmd_strdup(pw->filename); - memset(pw, 0, sizeof(pwmd_nb_status_t)); - return 0; - -fail: - memset(pw, 0, sizeof(pwmd_nb_status_t)); - return error; -} - static gpg_error_t do_open_command(pwm_t *pwm, const char *filename, char *password) { char buf[ASSUAN_LINELENGTH]; @@ -1714,8 +1712,7 @@ static gpg_error_t do_open_command(pwm_t *pwm, const char *filename, char *passw return error; } -static int do_pwmd_open(pwm_t *pwm, gpg_error_t *error, const char *filename, - int nb) +static gpg_error_t do_pwmd_open(pwm_t *pwm, const char *filename, int nb) { char *result = NULL; char *password = NULL; @@ -1723,11 +1720,10 @@ static int do_pwmd_open(pwm_t *pwm, gpg_error_t *error, const char *filename, #ifdef WITH_PINENTRY int pin_try; #endif + gpg_error_t rc; - if (!pwm || !filename || !*filename) { - *error = GPG_ERR_INV_ARG; - return nb ? -1 : 1; - } + if (!pwm || !filename || !*filename) + return GPG_ERR_INV_ARG; #ifdef WITH_PINENTRY pin_try = pwm->pinentry_tries - 1; @@ -1737,10 +1733,10 @@ static int do_pwmd_open(pwm_t *pwm, gpg_error_t *error, const char *filename, * Avoid calling pinentry if the password is cached on the server or if * this is a new file. */ - *error = pwmd_command(pwm, &result, "GETCONFIG data_directory"); + rc = pwmd_command(pwm, &result, "GETCONFIG data_directory"); - if (*error) - return nb ? -1 : 1; + if (rc) + return rc; snprintf(path, sizeof(path), "%s/%s", result, filename); pwmd_free(result); @@ -1750,9 +1746,9 @@ static int do_pwmd_open(pwm_t *pwm, gpg_error_t *error, const char *filename, goto gotpassword; } - *error = pwmd_command(pwm, &result, "ISCACHED %s", filename); + rc = pwmd_command(pwm, &result, "ISCACHED %s", filename); - if (*error == EPWMD_CACHE_NOT_FOUND) { + if (rc == EPWMD_CACHE_NOT_FOUND) { if (pwm->passfunc) { password = (char *)pwm->passfunc(pwm->passdata); goto gotpassword; @@ -1772,10 +1768,8 @@ static int do_pwmd_open(pwm_t *pwm, gpg_error_t *error, const char *filename, pid_t pid; pwmd_nb_status_t pw; - if (pipe(p) == -1) { - *error = gpg_error_from_syserror(); - return -1; - } + if (pipe(p) == -1) + return gpg_error_from_syserror(); #ifdef WITH_LIBPTH pid = pth_fork(); @@ -1786,8 +1780,6 @@ static int do_pwmd_open(pwm_t *pwm, gpg_error_t *error, const char *filename, switch (pid) { case 0: close(p[0]); - strncpy(pw.filename, filename, sizeof(pw.filename)); - pw.filename[sizeof(pw.filename)-1] = 0; pw.fd = p[0]; if (pwm->pinentry_timeout > 0) { @@ -1797,17 +1789,17 @@ static int do_pwmd_open(pwm_t *pwm, gpg_error_t *error, const char *filename, } getpin_nb_again: - *error = getpin(pwm, &password, &pin_try, 0); + rc = getpin(pwm, &password, &pin_try, 0); - if (*error) { + if (rc) { getpin_nb_fail: if (pwm->pctx) pinentry_disconnect(pwm); if (gtimeout && gelapsed >= gtimeout) - *error = GPG_ERR_TIMEOUT; + rc = GPG_ERR_TIMEOUT; - pw.error = *error; + pw.error = rc; #ifdef WITH_LIBPTH pth_write(p[1], &pw, sizeof(pw)); #else @@ -1822,12 +1814,12 @@ getpin_nb_fail: * which may have many iterations. */ signal(SIGALRM, SIG_DFL); - *error = do_open_command(pwm, filename, password); + rc = do_open_command(pwm, filename, password); if (pwm->pinentry_timeout) signal(SIGALRM, catchsig); - if (pwm->pctx && *error == EPWMD_BADKEY) { + if (pwm->pctx && rc == EPWMD_BADKEY) { if (pin_try-- > 0) goto getpin_nb_again; @@ -1845,17 +1837,17 @@ getpin_nb_fail: _exit(0); break; case -1: - *error = gpg_error_from_syserror(); + rc = gpg_error_from_syserror(); close(p[0]); close(p[1]); - return -1; + return rc; default: break; } close(p[1]); - *error = 0; - return p[0]; + pwm->nb_fd = p[0]; + return 0; } } else { @@ -1869,11 +1861,11 @@ getpin_nb_fail: } #endif } - else if (*error) - return nb ? -1 : 1; + else if (rc) + return rc; gotpassword: - *error = do_open_command(pwm, filename, password); + rc = do_open_command(pwm, filename, password); /* * Keep the user defined password set with pwmd_setopt(). The password may @@ -1883,13 +1875,13 @@ gotpassword: pwmd_free(password); #ifdef WITH_PINENTRY - if (*error == EPWMD_BADKEY) { + if (rc == EPWMD_BADKEY) { if (pin_try-- > 0 && !nb) { - *error = pwmd_command(pwm, &result, "OPTION TITLE=%s", + rc = pwmd_command(pwm, &result, "OPTION TITLE=%s", N_("Invalid passphrase, please try again.")); - if (*error) - return 1; + if (rc) + return rc; goto gotpassword; } @@ -1897,41 +1889,40 @@ gotpassword: if (nb) pinentry_disconnect(pwm); - return nb ? -1 : 1; + return rc; } #endif - if (!*error) { + if (!rc) { if (pwm->filename) pwmd_free(pwm->filename); pwm->filename = pwmd_strdup(filename); } - /* - * The file is cached or the file is a new file. - */ - if (nb) - return *error ? -1 : -2; - - return *error ? 1 : 0; + return rc; } gpg_error_t pwmd_open(pwm_t *pwm, const char *filename) { - gpg_error_t error; - - do_pwmd_open(pwm, &error, filename, 0); - return error; + return do_pwmd_open(pwm, filename, 0); } -int pwmd_open_nb(pwm_t *pwm, gpg_error_t *error, const char *filename) +gpg_error_t pwmd_open_async2(pwm_t *pwm, const char *filename) { #ifndef WITH_PINENTRY - *error = GPG_ERR_NOT_IMPLEMENTED; - return -1; + return GPG_ERR_NOT_IMPLEMENTED; #else - return do_pwmd_open(pwm, error, filename, 1); + gpg_error_t rc; + + pwm->cmd = ASYNC_CMD_OPEN2; + pwm->state = ASYNC_PROCESS; + rc = do_pwmd_open(pwm, filename, 1); + + if (rc) + reset_async(pwm); + + return rc; #endif } @@ -1991,37 +1982,19 @@ static gpg_error_t do_save_command(pwm_t *pwm, char *password) return error; } -gpg_error_t pwmd_save_nb_finalize(pwm_t *pwm, pwmd_nb_status_t *pw) -{ - gpg_error_t rc; - -#ifndef WITH_PINENTRY - return GPG_ERR_NOT_IMPLEMENTED; -#endif - - if (!pwm || !pw || !pw->filename[0]) - return GPG_ERR_INV_ARG; - - close(pw->fd); - rc = pw->error; - memset(pw, 0, sizeof(pwmd_nb_status_t)); - return rc; -} - -static int do_pwmd_save(pwm_t *pwm, gpg_error_t *error, int nb) +static gpg_error_t do_pwmd_save(pwm_t *pwm, int nb) { char *result = NULL; char *password = NULL; + gpg_error_t rc; - if (!pwm) { - *error = GPG_ERR_INV_ARG; - return nb ? -1 : 1; - } + if (!pwm) + return GPG_ERR_INV_ARG; if (pwm->use_pinentry || pwm->passfunc) { - *error = pwmd_command(pwm, &result, "ISCACHED %s", pwm->filename); + rc = pwmd_command(pwm, &result, "ISCACHED %s", pwm->filename); - if (*error == EPWMD_CACHE_NOT_FOUND) { + if (rc == EPWMD_CACHE_NOT_FOUND) { if (pwm->passfunc) password = (char *)(*pwm->passfunc)(pwm->passdata); #ifdef WITH_PINENTRY @@ -2031,10 +2004,8 @@ static int do_pwmd_save(pwm_t *pwm, gpg_error_t *error, int nb) pid_t pid; pwmd_nb_status_t pw; - if (pipe(p) == -1) { - *error = gpg_error_from_syserror(); - return -1; - } + if (pipe(p) == -1) + return gpg_error_from_syserror(); #ifdef WITH_LIBPTH pid = pth_fork(); @@ -2045,20 +2016,18 @@ static int do_pwmd_save(pwm_t *pwm, gpg_error_t *error, int nb) switch (pid) { case 0: close(p[0]); - strncpy(pw.filename, pwm->filename, sizeof(pw.filename)); - pw.filename[sizeof(pw.filename)-1] = 0; pw.fd = p[0]; do { password = NULL; - *error = do_save_getpin(pwm, &password); - } while (*error == EPWMD_BADKEY); + rc = do_save_getpin(pwm, &password); + } while (rc == EPWMD_BADKEY); - if (*error) { + if (rc) { if (pwm->pctx) pinentry_disconnect(pwm); - pw.error = *error; + pw.error = rc; #ifdef WITH_LIBPTH pth_write(p[1], &pw, sizeof(pw)); #else @@ -2068,9 +2037,9 @@ static int do_pwmd_save(pwm_t *pwm, gpg_error_t *error, int nb) _exit(1); } - *error = do_save_command(pwm, password); + rc = do_save_command(pwm, password); pinentry_disconnect(pwm); - pw.error = *error; + pw.error = rc; #ifdef WITH_LIBPTH pth_write(p[1], &pw, sizeof(pw)); #else @@ -2080,61 +2049,63 @@ static int do_pwmd_save(pwm_t *pwm, gpg_error_t *error, int nb) _exit(0); break; case -1: - *error = gpg_error_from_syserror(); + rc = gpg_error_from_syserror(); close(p[0]); close(p[1]); - return -1; + return rc; default: break; } close(p[1]); - *error = 0; - return p[0]; + pwm->nb_fd = p[0]; + return 0; } - *error = do_save_getpin(pwm, &password); + rc = do_save_getpin(pwm, &password); - if (*error) - return 1; + if (rc) + return rc; } #endif } else { - if (*error) - return nb ? -1 : 1; + if (rc) + return rc; } } else password = pwm->password; - *error = do_save_command(pwm, password); + rc = do_save_command(pwm, password); if (!pwm->passfunc && password && password != pwm->password) pwmd_free(password); - if (nb) - return *error ? -1 : -2; - - return *error ? 1 : 0; + return rc; } -int pwmd_save_nb(pwm_t *pwm, gpg_error_t *error) +gpg_error_t pwmd_save_async2(pwm_t *pwm) { #ifndef WITH_PINENTRY - *error = GPG_ERR_NOT_IMPLEMENTED; - return -1; + return GPG_ERR_NOT_IMPLEMENTED; #else - return do_pwmd_save(pwm, error, 1); + gpg_error_t rc; + + pwm->cmd = ASYNC_CMD_SAVE2; + pwm->state = ASYNC_PROCESS; + rc = do_pwmd_save(pwm, 1); + + if (rc) + reset_async(pwm); + + return rc; #endif } gpg_error_t pwmd_save(pwm_t *pwm) { - gpg_error_t error; - - do_pwmd_save(pwm, &error, 0); - return error; + return do_pwmd_save(pwm, 0); } gpg_error_t pwmd_setopt(pwm_t *pwm, pwmd_option_t opt, ...) @@ -2337,6 +2308,10 @@ pwm_t *pwmd_new(const char *name) } } + h->fd = -1; +#ifdef WITH_PINENTRY + h->nb_fd = -1; +#endif return h; } diff --git a/src/libpwmd.h.in b/src/libpwmd.h.in index f0f3f118..7b420eec 100644 --- a/src/libpwmd.h.in +++ b/src/libpwmd.h.in @@ -35,29 +35,6 @@ struct pwm_s; typedef struct pwm_s pwm_t; /* - * Used with pwmd_open_nb() and pwmd_save_nb(). Both are non-blocking - * functions for pin retrieval with pinentry. The pwmd_open_nb_finalize() and - * pwmd_save_nb_finalize() functions use this type after a successful read() - * from the returned file descriptor of those functions. - * - * Although version 1.4 and later of pwmd has it's own support for pinentry, - * commands that uses pinentry will block and as a result block the client. So - * these non-blocking functions may be used to retrieve the key before sending - * the command that requires a key. - * - * Update: You can use pwmd_open_async() and pwmd_save_async() for - * non-blocking pin retrieval. These will have pwmd use it's pinentry method - * rather than have libpwmd fork(). pwmd_open_nb() and pwmd_save_nb() will be - * kept (both were previously flagged as deprecated) in case pin retrieval - * isn't possible with pwmd. - */ -typedef struct { - char filename[FILENAME_MAX]; - int fd; /* Closed after the finalize function. */ - gpg_error_t error; /* Returned from the NB function. */ -} pwmd_nb_status_t; - -/* * For use with pwmd_process(). pwmd_open_async() and pwmd_save_async() use * this data type. */ @@ -330,17 +307,7 @@ gpg_error_t pwmd_open(pwm_t *pwm, const char *filename) __attribute__ ((warn_unu * * Be sure to set PWMD_OPTION_PINENTRY. */ -int pwmd_open_nb(pwm_t *pwm, gpg_error_t *error, const char *filename) __attribute__ ((warn_unused_result)); - -/* - * When a file descriptor has been returned from pwmd_open_nb() and after a - * successful read(), you should call pwmd_open_nb_finalize() to update the - * 'pwm' handle. If there was a pinentry or protocol error - * pwmd_open_nb_finalize() will return an error code or 0 on success. Note - * that pwmd_open_nb_finalize() will close the file descriptor returned from - * pwmd_open_nb(). - */ -gpg_error_t pwmd_open_nb_finalize(pwm_t *pwm, pwmd_nb_status_t *status) __attribute__ ((warn_unused_result)); +gpg_error_t pwmd_open_async2(pwm_t *pwm, const char *filename) __attribute__ ((warn_unused_result)); /* * This is the preferred way to do a non-blocking open. The difference from @@ -391,17 +358,7 @@ gpg_error_t pwmd_save(pwm_t *pwm) __attribute__ ((warn_unused_result)); * * Be sure to set PWMD_OPTION_PINENTRY. */ -int pwmd_save_nb(pwm_t *pwm, gpg_error_t *error) __attribute__ ((warn_unused_result)); - -/* - * When a file descriptor has been returned from pwmd_save_nb() and after a - * successful read(), you should call pwmd_save_nb_finalize() to update the - * 'pwm' handle. If there was a pinentry or protocol error - * pwmd_save_nb_finalize() will return an error code or 0 on success. Note - * that pwmd_save_nb_finalize() will close the file descriptor returned from - * pwmd_save_nb(). - */ -gpg_error_t pwmd_save_nb_finalize(pwm_t *pwm, pwmd_nb_status_t *status) __attribute__ ((warn_unused_result)); +gpg_error_t pwmd_save_async2(pwm_t *pwm) __attribute__ ((warn_unused_result)); /* * Like pwmd_save_nb() but uses pwmd to launch pinentry rather than having diff --git a/src/pwmc.c b/src/pwmc.c index 713a8fb1..e415db39 100644 --- a/src/pwmc.c +++ b/src/pwmc.c @@ -159,51 +159,6 @@ static int status_msg_cb(void *data, const char *line) return 0; } -#ifdef DEBUG -static gpg_error_t do_nb_command(int fd, int which) -{ - int n; - gpg_error_t error = 0; - - fcntl(fd, F_SETFL, O_NONBLOCK); - - do { - fd_set fds; - struct timeval tv = {0, 50000}; - - FD_ZERO(&fds); - FD_SET(fd, &fds); - n = select(fd+1, &fds, NULL, NULL, &tv); - - if (n > 0) { - if (FD_ISSET(fd, &fds)) { - pwmd_nb_status_t status; - - n = read(fd, &status, sizeof(status)); - - if (n == -1) { - error = gpg_error_from_errno(errno); - goto done; - } - - if (!which) - error = pwmd_open_nb_finalize(pwm, &status); - else - error = pwmd_save_nb_finalize(pwm, &status); - - if (error) - goto done; - } - } - else - fputc('.', stderr); - } while (n == 0); - -done: - return error; -} -#endif - int main(int argc, char *argv[]) { int opt; @@ -561,8 +516,11 @@ int main(int argc, char *argv[]) if (filename) { #ifdef DEBUG /* This method doesn't support PWMD_OPTION_PINENTRY_TRIES. */ - if (method == 1) { - error = pwmd_open_async(pwm, filename); + if (method) { + if (method == 1) + error = pwmd_open_async(pwm, filename); + else + error = pwmd_open_async2(pwm, filename); if (!error) { do { @@ -572,14 +530,6 @@ int main(int argc, char *argv[]) } while (s == ASYNC_PROCESS); } } - else if (method == 2) { - int fd = pwmd_open_nb(pwm, &error, filename); - - if (fd == -1) - goto done; - else if (fd >= 0) - error = do_nb_command(fd, 0); - } else error = pwmd_open(pwm, filename); #else @@ -703,8 +653,11 @@ done: } #ifdef DEBUG - if (method == 1) { - error = pwmd_save_async(pwm); + if (method) { + if (method == 1) + error = pwmd_save_async(pwm); + else + error = pwmd_save_async2(pwm); if (!error) { do { @@ -714,14 +667,6 @@ done: } while (s == ASYNC_PROCESS); } } - else if (method == 3) { - int fd = pwmd_save_nb(pwm, &error); - - if (fd == -1) - goto done; - else if (fd >= 0) - error = do_nb_command(fd, 1); - } else error = pwmd_save(pwm); #else diff --git a/src/types.h b/src/types.h index 0094329e..c08d81a9 100644 --- a/src/types.h +++ b/src/types.h @@ -35,7 +35,9 @@ typedef enum { ASYNC_CMD_HOSTKEY, #endif ASYNC_CMD_OPEN, + ASYNC_CMD_OPEN2, ASYNC_CMD_SAVE, + ASYNC_CMD_SAVE2, } pwmd_async_cmd_t; #ifdef WITH_TCP @@ -72,6 +74,7 @@ struct pwm_s { pid_t pid; assuan_context_t pctx; gpg_error_t pin_error; + int nb_fd; /* for pwmd_open/save_async2(). */ #endif int is_open_cmd; int use_pinentry; // this is for a local pinentry, not pwmd pinentry. @@ -103,6 +106,11 @@ typedef struct { void *buf; } membuf_t; +typedef struct { + int fd; + gpg_error_t error; +} pwmd_nb_status_t; + static gpg_error_t assuan_command(pwm_t *pwm, assuan_context_t ctx, char **result, const char *cmd); -- 2.11.4.GIT