Make it possible to interrupt password prompts

* Fri Oct  8 2010 Miloslav Trmač <mitr@redhat.com> - 0.3.4-3
- Make it possible to interrupt password prompts
  Resolves: #641111
This commit is contained in:
Miloslav Trmač 2010-10-08 19:30:21 +02:00
parent 2e6d0e53e8
commit f93fc197bb
2 changed files with 169 additions and 1 deletions

View File

@ -0,0 +1,161 @@
Subject: [PATCH] Don't use getpass (), it is difficult to interrupt
2010-10-08 Miloslav Trmač <mitr@redhat.com>
* src/volume_key.c (get_password): New function.
(nss_password_fn, generic_ui_cb, passphrase_ui_cb): Use get_password ()
instead of getpass ().
diff --git a/src/volume_key.c b/src/volume_key.c
index abdd838..7f9f391 100644
--- a/src/volume_key.c
+++ b/src/volume_key.c
@@ -24,6 +24,7 @@ Author: Miloslav Trmač <mitr@redhat.com> */
#include <stdio.h>
#include <string.h>
#include <sys/stat.h>
+#include <termios.h>
#include <unistd.h>
#include <glib.h>
@@ -391,36 +392,93 @@ read_batch_string (void)
return res;
}
+/* Read a password (from /dev/tty if possible).
+ Return a password for g_free (), or NULL on error.
+ Unlike getpass(), does not block SIGINT and other signals. (We rely on the
+ shell to re-enable ECHO on SIGINT.) */
+static char *
+get_password (const char *prompt)
+{
+ FILE *tty, *in_file, *out_file;
+ char buf[LINE_MAX], *p;
+ struct termios otermios;
+ gboolean echo_disabled;
+
+ tty = fopen ("/dev/tty", "r+");
+ if (tty != NULL)
+ {
+ in_file = tty;
+ out_file = tty;
+ }
+ else
+ {
+ in_file = stdin;
+ out_file = stderr;
+ }
+
+ fputs (prompt, out_file);
+ fflush (out_file);
+
+ if (tcgetattr (fileno (in_file), &otermios) != 0)
+ echo_disabled = FALSE;
+ else
+ {
+ struct termios ntermios;
+
+ ntermios = otermios;
+ ntermios.c_lflag &= ~ECHO;
+ echo_disabled = tcsetattr (fileno (in_file), TCSAFLUSH, &ntermios) == 0;
+ }
+
+ p = fgets(buf, sizeof(buf), in_file);
+
+ if (echo_disabled)
+ {
+ (void)tcsetattr (fileno (in_file), TCSAFLUSH, &otermios);
+ putc ('\n', out_file);
+ }
+
+ if (tty != NULL)
+ fclose (tty);
+
+ if (p == NULL)
+ return NULL;
+
+ p = strchr(buf, '\r');
+ if (p != NULL)
+ *p = '\0';
+ p = strchr(buf, '\n');
+ if (p != NULL)
+ *p = '\0';
+
+ return g_strdup (buf);
+}
+
/* A PK11_SetPaswordFunc handler */
static char *
nss_password_fn (PK11SlotInfo *slot, PRBool retry, void *arg)
{
+ char *s, *res;
+
+ (void)arg;
if (batch_mode == 0)
{
- char *prompt, *s;
+ char *prompt;
- (void)arg;
if (retry)
fprintf (stderr, _("Error, try again.\n"));
prompt = g_strdup_printf (_("Enter password for `%s': "),
PK11_GetTokenName (slot));
- s = getpass (prompt);
+ s = get_password (prompt);
g_free (prompt);
- if (s == NULL)
- return NULL;
- return PL_strdup (s);
}
else
- {
- char *s, *res;
-
- s = read_batch_string ();
- if (s == NULL)
- return NULL;
- res = PL_strdup (s);
- g_free (s);
- return res;
- }
+ s = read_batch_string ();
+ if (s == NULL)
+ return NULL;
+ res = PL_strdup (s);
+ g_free (s);
+ return res;
}
/* A "generic" struct libvk_ui callback. */
@@ -435,10 +493,11 @@ generic_ui_cb (void *id, const char *prompt, int echo)
char *s, *res;
s = g_strdup_printf (_("%s: "), prompt);
- res = getpass (s);
+ res = get_password (s);
g_free (s);
if (res != NULL && res[0] != '\0')
- return g_strdup (res);
+ return res;
+ g_free (res);
return NULL;
}
else
@@ -487,10 +546,11 @@ passphrase_ui_cb (void *data, const char *prompt, unsigned failed_attempts)
return read_batch_string ();
}
s = g_strdup_printf (_("%s: "), prompt);
- res = getpass (s);
+ res = get_password (s);
g_free (s);
if (res != NULL && res[0] != '\0')
- return g_strdup (res);
+ return res;
+ g_free (res);
return NULL;
}
--
1.7.2.3

View File

@ -3,7 +3,7 @@
Summary: An utility for manipulating storage encryption keys and passphrases
Name: volume_key
Version: 0.3.4
Release: 2%{?dist}
Release: 3%{?dist}
License: GPLv2
Group: Applications/System
URL: https://fedorahosted.org/volume_key/
@ -14,6 +14,8 @@ Source0: https://fedorahosted.org/releases/v/o/volume_key/volume_key-%{version}.
Patch0: volume_key-0.3.4-volume-doc.patch
# Upstream commit a2ab2a3546f3ee5937bb4272f4f26650f31f42bb
Patch1: volume_key-0.3.4-ssl-errors.patch
# Upstream commit 82f476f614ff8492231e730b6ceffaa7242481cc
Patch2: volume_key-0.3.4-getpass.patch
BuildRequires: cryptsetup-luks-devel, gettext-devel, glib2-devel, gnupg
BuildRequires: gpgme-devel, libblkid-devel, nss-devel, python-devel
@ -79,6 +81,7 @@ for other formats is possible, some formats are planned for future releases.
%setup -q
%patch0 -p1 -b .volume-doc
%patch1 -p1 -b .ssl-errors
%patch2 -p1 -b .getpass
%build
%configure
@ -119,6 +122,10 @@ rm -rf $RPM_BUILD_ROOT
%{python_sitearch}/volume_key.py*
%changelog
* Fri Oct 8 2010 Miloslav Trmač <mitr@redhat.com> - 0.3.4-3
- Make it possible to interrupt password prompts
Resolves: #641111
* Wed Sep 29 2010 Miloslav Trmač <mitr@redhat.com> - 0.3.4-2
- Clarify which block device should be passed as an argument
Resolves: #636541