From: Corey Hickey <chickey@xxxxxxxxxx> When ssh-add is used in a script like: if ! KEY_LISTING=$(ssh-add -l 2>&1) ; then echo "SSH agent error" >&2 exit 2 fi ...the operation fails when there is an agent but there are no keys in the agent. This is because ssh-add exits with status of 1. If the intent is to examine the keys in the agent, then this behavior is undesired and not easily distinguishable from an error (e.g. no agent running). To address this, add a new option -p to make ssh-add behavior more friendly to parsing. --- ssh-add.1 | 4 ++++ ssh-add.c | 13 +++++++++---- 2 files changed, 13 insertions(+), 4 deletions(-) diff --git a/ssh-add.1 b/ssh-add.1 index c31de4dd9..80fdfcbcc 100644 --- a/ssh-add.1 +++ b/ssh-add.1 @@ -223,6 +223,10 @@ Lists public key parameters of all identities currently represented by the agent. .It Fl l Lists fingerprints of all identities currently represented by the agent. +.It Fl p +Behave in a more parsing-friendly fashion: when listing public keys or +fingerprints, and there are none in the agent, print nothing and exit with a +status of 0. .It Fl q Be quiet after a successful operation. .It Fl S Ar provider diff --git a/ssh-add.c b/ssh-add.c index 0035cb84a..889decc0d 100644 --- a/ssh-add.c +++ b/ssh-add.c @@ -529,7 +529,7 @@ test_key(int agent_fd, const char *filename) } static int -list_identities(int agent_fd, int do_fp) +list_identities(int agent_fd, int do_fp, int parse_friendly) { char *fp; int r; @@ -541,6 +541,8 @@ list_identities(int agent_fd, int do_fp) if (r != SSH_ERR_AGENT_NO_IDENTITIES) fprintf(stderr, "error fetching identities: %s\n", ssh_err(r)); + else if (parse_friendly) + return 0; /* no identities; nothing to do */ else printf("The agent has no identities.\n"); return -1; @@ -814,7 +816,7 @@ main(int argc, char **argv) char **dest_constraint_strings = NULL, **hostkey_files = NULL; int r, i, ch, deleting = 0, ret = 0, key_only = 0, cert_only = 0; int do_download = 0, xflag = 0, lflag = 0, Dflag = 0; - int qflag = 0, Tflag = 0; + int pflag = 0, qflag = 0, Tflag = 0; SyslogFacility log_facility = SYSLOG_FACILITY_AUTH; LogLevel log_level = SYSLOG_LEVEL_INFO; struct sshkey *k, **certs = NULL; @@ -846,7 +848,7 @@ main(int argc, char **argv) skprovider = getenv("SSH_SK_PROVIDER"); - while ((ch = getopt(argc, argv, "vkKlLCcdDTxXE:e:h:H:M:m:qs:S:t:")) != -1) { + while ((ch = getopt(argc, argv, "vkKlLCcdDTxXE:e:h:H:M:m:pqs:S:t:")) != -1) { switch (ch) { case 'v': if (log_level == SYSLOG_LEVEL_INFO) @@ -935,6 +937,9 @@ main(int argc, char **argv) case 'T': Tflag = 1; break; + case 'p': + pflag = 1; + break; default: usage(); ret = 1; @@ -950,7 +955,7 @@ main(int argc, char **argv) ret = 1; goto done; } else if (lflag) { - if (list_identities(agent_fd, lflag == 'l' ? 1 : 0) == -1) + if (list_identities(agent_fd, lflag == 'l' ? 1 : 0, pflag) == -1) ret = 1; goto done; } else if (Dflag) { -- 2.47.1 _______________________________________________ openssh-unix-dev mailing list openssh-unix-dev@xxxxxxxxxxx https://lists.mindrot.org/mailman/listinfo/openssh-unix-dev