diff options
author | Mattias Andrée <maandree@operamail.com> | 2015-12-05 00:22:34 +0100 |
---|---|---|
committer | Mattias Andrée <maandree@operamail.com> | 2015-12-05 00:22:34 +0100 |
commit | 18894103fcf337dfa672481ffc6b4906f340adff (patch) | |
tree | d703c56133818df28a6714db9128c647da1c1bc9 /src | |
parent | m (diff) | |
download | libpassphrase-18894103fcf337dfa672481ffc6b4906f340adff.tar.gz libpassphrase-18894103fcf337dfa672481ffc6b4906f340adff.tar.bz2 libpassphrase-18894103fcf337dfa672481ffc6b4906f340adff.tar.xz |
accept input from any fd
Signed-off-by: Mattias Andrée <maandree@operamail.com>
Diffstat (limited to 'src')
-rw-r--r-- | src/passphrase.c | 84 | ||||
-rw-r--r-- | src/passphrase.h | 46 | ||||
-rw-r--r-- | src/test.c | 6 |
3 files changed, 112 insertions, 24 deletions
diff --git a/src/passphrase.c b/src/passphrase.c index b44542f..ec21aad 100644 --- a/src/passphrase.c +++ b/src/passphrase.c @@ -22,6 +22,7 @@ #include <unistd.h> #include <signal.h> +#define PASSPHRASE_USE_DEPRECATED #include "passphrase.h" #include "passphrase_helper.h" @@ -57,23 +58,31 @@ static char* xrealloc(char* array, size_t cur_size, size_t new_size) #endif /* !PASSPHRASE_REALLOC */ +static int fdgetc(int fd) +{ + unsigned char c; + if (read(fd, &c, sizeof(c)) <= 0) + return -1; + return (int)c; +} + #if defined(PASSPHRASE_DEDICATED) && defined(PASSPHRASE_MOVE) -static int get_dedicated_control_key(void) +static int get_dedicated_control_key(int fdin) { - int c = getchar(); + int c = fdgetc(fdin); if (c == 'O') { - c = getchar(); + c = fdgetc(fdin); if (c == 'H') return KEY_HOME; if (c == 'F') return KEY_END; } else if (c == '[') { - c = getchar(); + c = fdgetc(fdin); if (c == 'C') return KEY_RIGHT; if (c == 'D') return KEY_LEFT; - if (('1' <= c) && (c <= '4') && (getchar() == '~')) + if (('1' <= c) && (c <= '4') && (fdgetc(fdin) == '~')) return -(c - '0'); } return 0; @@ -83,13 +92,15 @@ static int get_dedicated_control_key(void) #ifdef PASSPHRASE_MOVE -static int get_key(int c) +static int get_key(int c, int fdin) { # ifdef PASSPHRASE_DEDICATED - if (c == '\033') return get_dedicated_control_key(); + if (c == '\033') return get_dedicated_control_key(fdin); +# else /* PASSPHRASE_DEDICATED */ + (void) fdin; # endif /* PASSPHRASE_DEDICATED */ if ((c == 8) || (c == 127)) return KEY_ERASE; - if ((c < 0) || (c >= ' ')) return ((int)c) & 255; + if ((c < 0) || (c >= ' ')) return c & 255; # ifdef PASSPHRASE_CONTROL if (c == 'A' - '@') return KEY_HOME; if (c == 'B' - '@') return KEY_LEFT; @@ -106,10 +117,23 @@ static int get_key(int c) /** * Reads the passphrase from stdin * - * @return The passphrase, should be wiped `free`:ed, `NULL` on error + * @return The passphrase, should be wiped and `free`:ed, `NULL` on error */ char* passphrase_read(void) { + return passphrase_read2(STDIN_FILENO, 0); +} + + +/** + * Reads the passphrase from stdin + * + * @param fdin File descriptor for input + * @param flags Settings + * @return The passphrase, should be wiped and `free`:ed, `NULL` on error + */ +char* passphrase_read2(int fdin, int flags) +{ char* rc = malloc(START_PASSPHRASE_LIMIT * sizeof(char)); size_t size = START_PASSPHRASE_LIMIT; size_t len = 0; @@ -127,6 +151,7 @@ char* passphrase_read(void) #ifdef PASSPHRASE_MOVE int cc; #endif + (void) flags; if (rc == NULL) return NULL; @@ -142,12 +167,12 @@ char* passphrase_read(void) that in X.org) and can be echoed into stdin by the kernel. */ for (;;) { - c = getchar(); + c = fdgetc(fdin); if ((c < 0) || (c == '\n')) break; if (c == 0) continue; #if defined(PASSPHRASE_MOVE) - cc = get_key(c); + cc = get_key(c, fdin); if (cc > 0) { c = (char)cc; @@ -266,35 +291,62 @@ void passphrase_wipe(volatile char* ptr, size_t n) *(ptr + i) = 0; } + /** * Disable echoing and do anything else to the terminal settnings `passphrase_read` requires */ void passphrase_disable_echo(void) { + passphrase_disable_echo1(STDIN_FILENO); +} + + +/** + * Undo the actions of `passphrase_disable_echo` + */ +void passphrase_reenable_echo(void) +{ + passphrase_reenable_echo1(STDIN_FILENO); +} + +/** + * Disable echoing and do anything else to the terminal settnings `passphrase_read2` requires + * + * @param fdin File descriptor for input + */ +void passphrase_disable_echo1(int fdin) +{ #if !defined(PASSPHRASE_ECHO) || defined(PASSPHRASE_MOVE) struct termios stty; - tcgetattr(STDIN_FILENO, &stty); + tcgetattr(fdin, &stty); saved_stty = stty; stty.c_lflag &= (tcflag_t)~ECHO; # if defined(PASSPHRASE_STAR) || defined(PASSPHRASE_TEXT) || defined(PASSPHRASE_MOVE) stty.c_lflag &= (tcflag_t)~ICANON; # endif /* PASSPHRASE_STAR || PASSPHRASE_TEXT || PASSPHRASE_MOVE */ - tcsetattr(STDIN_FILENO, TCSAFLUSH, &stty); + tcsetattr(fdin, TCSAFLUSH, &stty); +#else /* !PASSPHRASE_ECHO || PASSPHRASE_MOVE */ + (void) fdin; #endif /* !PASSPHRASE_ECHO || PASSPHRASE_MOVE */ } /** - * Undo the actions of `passphrase_disable_echo` + * Undo the actions of `passphrase_disable_echo1` + * + * @param fdin File descriptor for input */ -void passphrase_reenable_echo(void) +void passphrase_reenable_echo1(int fdin) { #if !defined(PASSPHRASE_ECHO) || defined(PASSPHRASE_MOVE) - tcsetattr(STDIN_FILENO, TCSAFLUSH, &saved_stty); + tcsetattr(fdin, TCSAFLUSH, &saved_stty); +#else /* !PASSPHRASE_ECHO || !PASSPHRASE_MOVE */ + (void) fdin; #endif /* !PASSPHRASE_ECHO || !PASSPHRASE_MOVE */ } + #ifdef __GNUC__ # pragma GCC diagnostic pop #endif diff --git a/src/passphrase.h b/src/passphrase.h index 85faffd..24d4aa4 100644 --- a/src/passphrase.h +++ b/src/passphrase.h @@ -19,13 +19,30 @@ #ifndef PASSPHRASE_H #define PASSPHRASE_H +#if defined(__GNUC__) && !defined(PASSPHRASE_USE_DEPRECATED) +# define PASSPHRASE_DEPRECATED(MSG) __attribute__((__deprecated__(MSG))) +#else +# define PASSPHRASE_DEPRECATED(MSG) /* ignore */ +#endif + + /** * Reads the passphrase from stdin * - * @return The passphrase, should be wiped `free`:ed, `NULL` on error + * @return The passphrase, should be wiped and `free`:ed, `NULL` on error */ -extern char* passphrase_read(void); +PASSPHRASE_DEPRECATED("Please use 'passphrase_read2' instead.") +char* passphrase_read(void); + +/** + * Reads the passphrase + * + * @param fdin File descriptor for input + * @param flags Settings + * @return The passphrase, should be wiped and `free`:ed, `NULL` on error + */ +char* passphrase_read2(int, int); /** * Forcable write NUL characters to a passphrase @@ -33,18 +50,37 @@ extern char* passphrase_read(void); * @param ptr The password to wipe * @param n The number of characters to wipe */ -extern void passphrase_wipe(volatile char*, size_t); +void passphrase_wipe(volatile char*, size_t); /** * Disable echoing and do anything else to the terminal settnings `passphrase_read` requires */ -extern void passphrase_disable_echo(void); +PASSPHRASE_DEPRECATED("Please use 'passphrase_disable_echo1' instead.") +void passphrase_disable_echo(void); /** * Undo the actions of `passphrase_disable_echo` */ -extern void passphrase_reenable_echo(void); +PASSPHRASE_DEPRECATED("Please use 'passphrase_reenable_echo1' instead.") +void passphrase_reenable_echo(void); + +/** + * Disable echoing and do anything else to the terminal settnings `passphrase_read2` requires + * + * @param fdin File descriptor for input + */ +void passphrase_disable_echo1(int); + +/** + * Undo the actions of `passphrase_disable_echo1` + * + * @param fdin File descriptor for input + */ +void passphrase_reenable_echo1(int); + + +#undef PASSPHRASE_DEPRECATED #endif @@ -33,14 +33,14 @@ int main(int argc, char** argv) char* passphrase_; /* Hide the passphrase */ - passphrase_disable_echo(); + passphrase_disable_echo1(0); /* Do things needed before reading the passphrase */ printf("Passphrase: "); fflush(stdout); /* Read the passphrase */ - passphrase = passphrase_read(); + passphrase = passphrase_read2(0, 0); if (passphrase == NULL) { /* Something went wrong, print what and exit */ @@ -58,7 +58,7 @@ int main(int argc, char** argv) free(passphrase_); /* Stop hiding user input */ - passphrase_reenable_echo(); + passphrase_reenable_echo1(0); /* End of program */ return 0; |