[PATCH] correct_password: Handle NULL from crypt
Tito
farmatito at tiscali.it
Mon Feb 3 21:25:44 UTC 2014
On Monday 03 February 2014 17:50:00 Lauri Kasanen wrote:
> Hi,
>
> As with many other software, busybox was also broken by the glibc >=
> 2.17 behavior change. Now crypt() returns NULL if either salt or
> password is invalid.
>
> This causes busybox 1.21, 1.22, and git su to segfault, when you just
> press enter at the password prompt (configured to use system crypt() of
> course).
>
> Program terminated with signal 11, Segmentation fault.
> #0 0xb760cb84 in strcmp () from /lib/libc.so.6
> (gdb) bt full
> #0 0xb760cb84 in strcmp () from /lib/libc.so.6
> No symbol table info available.
> #1 0x080493d3 in ask_and_check_password_extended ()
> No symbol table info available.
>
> The attached patch fixes su. You may want to check every other call to
> crypt() in busybox.
>
> - Lauri
>
>
Hi,
other users of crypt():
1) call pw_encrypt directly:
busybox/loginutils/chpasswd.c
busybox/loginutils/cryptpw.c
busybox/loginutils/passwd.c
these 3 could be fixed by adding a new pw_encrypt_or_die() function like:
char* FAST_FUNC pw_encrypt_or_die(const char *clear, const char *salt, int cleanup)
{
char * s = crypt(clear, salt);
if (! s)
bb_simple_perror_msg_and_die("crypt");
return xstrdup(s);
}
in case we use bb internal crypt function erroring out maybe is not
needed so in this case we could define pw_encrypt_or_die = pw_encrypt.
2) using ask_and_check_password or ask_and_check_password_extended fixed by Lauri's patch
busybox/loginutils/login.c
busybox/loginutils/su.c
busybox/loginutils/sulogin.c
busybox/loginutils/vlock.c
3) needs separate fix (as daemon could not be killed) (untested):
busybox/networking/httpd.c at line 1874
if (passwd[0] == '$' && isdigit(passwd[1])) {
char *encrypted;
# if !ENABLE_PAM
check_encrypted:
# endif
/* encrypt pwd from peer and check match with local one */
encrypted = pw_encrypt(
/* pwd (from peer): */ colon_after_user + 1,
/* salt: */ passwd,
/* cleanup: */ 0
);
+ if (!encrypted)
+ r = 1;
+ else {
r = strcmp(encrypted, passwd);
free(encrypted);
+ }
} else {
/* local passwd is from httpd.conf and it's plaintext */
r = strcmp(colon_after_user + 1, passwd);
}
goto end_check_passwd;
}
Hope this helps.
Ciao,
Tito
More information about the busybox
mailing list