Index: util-linux-2.12r/mount/lomount.c =================================================================== --- util-linux-2.12r.orig/mount/lomount.c +++ util-linux-2.12r/mount/lomount.c @@ -46,24 +46,24 @@ #include "rmd160.h" #include "aes.h" +#define LO_PASS_OK EXIT_SUCCESS +#define LO_PASS_ERR EXIT_FAILURE +#define LO_PASS_EMPTY 5 +#define LO_PASS_SHORT 6 + extern int verbose; extern char *xstrdup (const char *s); /* not: #include "sundries.h" */ extern void error (const char *fmt, ...); /* idem */ extern void show_all_loops(void); extern int read_options_from_fstab(char *, char **); +volatile int timeout=0; int passphrase_timeout=0; struct sigaction alrmact; static void alrmhandler() { - /* let the SIGINT handler do the work: */ - kill(getpid(),SIGINT); - usleep(1000000); - kill(getpid(),SIGTERM); - usleep(1000000); - /* stubborn... */ - exit(0); + timeout = 1; } @@ -473,11 +473,14 @@ static char *do_GPG_pipe(char *pass) return multiKeyPass[0]; } -static char *sGetPass(int minLen, int warnLen) +static int sGetPass(char **pass, int minLen, int warnLen) { char *p, *s, *seed; int i, ask2; + *pass = NULL; + timeout = 0; + if(!passFDnumber) { if(passphrase_timeout) { @@ -489,6 +492,9 @@ static char *sGetPass(int minLen, int wa } p = getpass(_("Password: ")); + alarm(0); + if (timeout) + return LO_PASS_EMPTY; ask2 = passAskTwice ? 1 : 0; } else { i = atoi(passFDnumber); @@ -504,11 +510,13 @@ static char *sGetPass(int minLen, int wa } if(x == 65) { multiKeyMode = 65; - return multiKeyPass[0]; + *pass = multiKeyPass[0]; + return LO_PASS_OK; } if(x == 64) { multiKeyMode = 64; - return multiKeyPass[0]; + *pass = multiKeyPass[0]; + return LO_PASS_OK; } p = multiKeyPass[0]; } @@ -531,6 +539,9 @@ static char *sGetPass(int minLen, int wa } p = getpass(_("Retype password: ")); + alarm(0); + if (timeout) + return LO_PASS_EMPTY; if(!p) goto nomem; if(strcmp(s, p)) goto compareErr; memset(s, 0, i); @@ -538,17 +549,25 @@ static char *sGetPass(int minLen, int wa ask2 = 0; } p = do_GPG_pipe(p); - if(!p) return(NULL); + if(!p) + return LO_PASS_ERR; if(!p[0]) { fprintf(stderr, _("Error: gpg key file decryption failed\n")); - return(NULL); + return LO_PASS_ERR; + } + if(multiKeyMode) { + *pass = p; + return LO_PASS_OK; } - if(multiKeyMode) return(p); } i = strlen(p); + if(i == 0) { + fprintf(stderr, _("Error: Empty password\n")); + return LO_PASS_EMPTY; + } if(i < minLen) { fprintf(stderr, _("Error: Password must be at least %d characters.\n"), minLen); - return(NULL); + return LO_PASS_SHORT; } seed = passSeedString; if(!seed) seed = ""; @@ -556,7 +575,7 @@ static char *sGetPass(int minLen, int wa if(!s) { nomem: fprintf(stderr, _("Error: Unable to allocate memory\n")); - return(NULL); + return LO_PASS_ERR; } strcpy(s, p); memset(p, 0, i); @@ -571,11 +590,14 @@ static char *sGetPass(int minLen, int wa } p = getpass(_("Retype password: ")); + alarm(0); + if (timeout) + return LO_PASS_EMPTY; if(!p) goto nomem; if(strcmp(s, p)) { compareErr: fprintf(stderr, _("Error: Passwords are not identical\n")); - return(NULL); + return LO_PASS_ERR; } memset(p, 0, i); } @@ -583,7 +605,8 @@ static char *sGetPass(int minLen, int wa fprintf(stderr, _("WARNING - Please use longer password (%d or more characters)\n"), SUSE_PASSWORD_MIN_LENGTH); } strcat(s, seed); - return(s); + *pass = s; + return LO_PASS_OK; } /* this is for compatibility with historic loop-AES version */ @@ -788,6 +811,7 @@ set_loop(const char *device, const char unsigned char multiKeyBits[65][32]; int minPassLen = SUSE_PASSWORD_MIN_LENGTH; int run_mkfs_command = 0; + int ret; loopFileName = (char *)file; multiKeyMode = 0; @@ -848,8 +872,8 @@ set_loop(const char *device, const char loopinfo.lo_encrypt_key_size = 0; break; case LO_CRYPT_XOR: - pass = sGetPass (1, 0); - if(!pass) goto close_fd_ffd_return1; + ret = sGetPass (&pass, 1, 0); + if(ret) goto close_fd_ffd_return1; xstrncpy (loopinfo.lo_encrypt_key, pass, LO_KEY_SIZE); loopinfo.lo_encrypt_key_size = strlen(loopinfo.lo_encrypt_key); break; @@ -886,6 +910,7 @@ set_loop(const char *device, const char /* This is not compatible with gpgkey= mount option */ if(rd_wr_retry(atoi(passFDnumber), (char *)&loopinfo.lo_encrypt_key[0], LO_KEY_SIZE, 0) < 1) { fprintf(stderr, _("Error: couldn't read binary key\n")); + ret = 1; goto close_fd_ffd_return1; } break; /* out of switch(loopinfo.lo_encrypt_type) */ @@ -894,6 +919,7 @@ set_loop(const char *device, const char /* WARNING! DO NOT USE RANDOM HASH TYPE ON PARTITION WITH EXISTING */ /* IMPORTANT DATA ON IT. RANDOM HASH TYPE WILL DESTROY YOUR DATA. */ if(loop_create_random_keys((char*)file, *loopro, &multiKeyBits[0][0])) { + ret = 1; goto close_fd_ffd_return1; } memcpy(&loopinfo.lo_encrypt_key[0], &multiKeyBits[0][0], sizeof(loopinfo.lo_encrypt_key)); @@ -901,8 +927,8 @@ set_loop(const char *device, const char break; /* out of switch(loopinfo.lo_encrypt_type) */ } } - pass = sGetPass (minPassLen, SUSE_PASSWORD_MIN_LENGTH); - if(!pass) goto close_fd_ffd_return1; + ret = sGetPass (&pass, minPassLen, SUSE_PASSWORD_MIN_LENGTH); + if(ret) goto close_fd_ffd_return1; i = strlen(pass); if(hashFunc == unhashed1_key_setup) { /* this is for compatibility with historic loop-AES version */ @@ -966,6 +992,7 @@ set_loop(const char *device, const char break; default: fprintf (stderr, _("Error: don't know how to get key for encryption system %d\n"), loopinfo.lo_encrypt_type); + ret = 1; goto close_fd_ffd_return1; } @@ -985,7 +1012,7 @@ close_fd_ffd_return1: close (fd); close_ffd_return1: close (ffd); - return 1; + return ret; } /* type 18 == LO_CRYPT_CRYPTOAPI */ Index: util-linux-2.12r/mount/losetup.8 =================================================================== --- util-linux-2.12r.orig/mount/losetup.8 +++ util-linux-2.12r/mount/losetup.8 @@ -143,6 +143,10 @@ displays the status of a loop device, it is not configured and 2 if an error occurred which prevented .B losetup from determining the status of the device. +When using encryption +.B losetup +returns 5 if the passphrase is empty or a timeout occurred and 6 if +the passphrase is too short. .SH FILES .nf