diff options
author | Daniel P. Berrange <berrange@redhat.com> | 2015-05-12 17:09:19 +0100 |
---|---|---|
committer | Kevin Wolf <kwolf@redhat.com> | 2015-05-22 17:08:01 +0200 |
commit | d57e4e482e3997b1382625c84149ad0b69155fc0 (patch) | |
tree | 3ce7f69edf3c4e628e464f3c0d846a23a7c74cba /util/oslib-posix.c | |
parent | 8336aafae1451d54c81dd2b187b45f7c45d2428e (diff) |
util: move read_password method out of qemu-img into osdep/oslib
The qemu-img.c file has a read_password() method impl that is
used to prompt for passwords on the console, with impls for
POSIX and Windows. This will be needed by qemu-io.c too, so
move it into the QEMU osdep/oslib files where it can be shared
without code duplication
Signed-off-by: Daniel P. Berrange <berrange@redhat.com>
Reviewed-by: Eric Blake <eblake@redhat.com>
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
Diffstat (limited to 'util/oslib-posix.c')
-rw-r--r-- | util/oslib-posix.c | 66 |
1 files changed, 66 insertions, 0 deletions
diff --git a/util/oslib-posix.c b/util/oslib-posix.c index 37ffd96245..1c23fd2132 100644 --- a/util/oslib-posix.c +++ b/util/oslib-posix.c @@ -50,6 +50,7 @@ extern int daemon(int, int); #include <termios.h> #include <unistd.h> +#include <termios.h> #include <glib/gprintf.h> @@ -415,3 +416,68 @@ void os_mem_prealloc(int fd, char *area, size_t memory) pthread_sigmask(SIG_SETMASK, &oldset, NULL); } } + + +static struct termios oldtty; + +static void term_exit(void) +{ + tcsetattr(0, TCSANOW, &oldtty); +} + +static void term_init(void) +{ + struct termios tty; + + tcgetattr(0, &tty); + oldtty = tty; + + tty.c_iflag &= ~(IGNBRK|BRKINT|PARMRK|ISTRIP + |INLCR|IGNCR|ICRNL|IXON); + tty.c_oflag |= OPOST; + tty.c_lflag &= ~(ECHO|ECHONL|ICANON|IEXTEN); + tty.c_cflag &= ~(CSIZE|PARENB); + tty.c_cflag |= CS8; + tty.c_cc[VMIN] = 1; + tty.c_cc[VTIME] = 0; + + tcsetattr(0, TCSANOW, &tty); + + atexit(term_exit); +} + +int qemu_read_password(char *buf, int buf_size) +{ + uint8_t ch; + int i, ret; + + printf("password: "); + fflush(stdout); + term_init(); + i = 0; + for (;;) { + ret = read(0, &ch, 1); + if (ret == -1) { + if (errno == EAGAIN || errno == EINTR) { + continue; + } else { + break; + } + } else if (ret == 0) { + ret = -1; + break; + } else { + if (ch == '\r') { + ret = 0; + break; + } + if (i < (buf_size - 1)) { + buf[i++] = ch; + } + } + } + term_exit(); + buf[i] = '\0'; + printf("\n"); + return ret; +} |