aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDenys Vlasenko <vda.linux@googlemail.com>2012-02-01 02:42:54 +0100
committerDenys Vlasenko <vda.linux@googlemail.com>2012-02-01 02:42:54 +0100
commit35def51c9747895d38c11e3c41e62c3c68c92438 (patch)
tree7123ee794725e9d904a7d98865ad07f61e46cd6d
parent428bd2d4337dbd83feb3c7d1fc04d840f548003c (diff)
downloadbusybox-35def51c9747895d38c11e3c41e62c3c68c92438.tar.gz
httpd: fix MD5-encrypted-in-httpd.conf password logic
function old new delta check_user_passwd 467 492 +25 Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
-rw-r--r--networking/Config.src16
-rw-r--r--networking/httpd.c50
2 files changed, 39 insertions, 27 deletions
diff --git a/networking/Config.src b/networking/Config.src
index 8aeba0ef9..fb7dca7d4 100644
--- a/networking/Config.src
+++ b/networking/Config.src
@@ -199,14 +199,22 @@ config FEATURE_HTTPD_BASIC_AUTH
help
Utilizes password settings from /etc/httpd.conf for basic
authentication on a per url basis.
+ Example for httpd.conf file:
+ /adm:toor:PaSsWd
config FEATURE_HTTPD_AUTH_MD5
bool "Support MD5 crypted passwords for http Authentication"
default y
depends on FEATURE_HTTPD_BASIC_AUTH
help
- Enables basic per URL authentication from /etc/httpd.conf
- using md5 passwords.
+ Enables encrypted passwords, and wildcard user/passwords
+ in httpd.conf file.
+ User '*' means 'any system user name is ok',
+ password of '*' means 'use system password for this user'
+ Examples:
+ /adm:toor:$1$P/eKnWXS$aI1aPGxT.dJD5SzqAKWrF0
+ /adm:root:*
+ /wiki:*:*
config FEATURE_HTTPD_CGI
bool "Support Common Gateway Interface (CGI)"
@@ -223,8 +231,8 @@ config FEATURE_HTTPD_CONFIG_WITH_SCRIPT_INTERPR
help
This option enables support for running scripts through an
interpreter. Turn this on if you want PHP scripts to work
- properly. You need to supply an additional line in your httpd
- config file:
+ properly. You need to supply an additional line in your
+ httpd.conf file:
*.php:/path/to/your/php
config FEATURE_HTTPD_SET_REMOTE_PORT_TO_ENV
diff --git a/networking/httpd.c b/networking/httpd.c
index 3f4e6aab7..0e4c697f8 100644
--- a/networking/httpd.c
+++ b/networking/httpd.c
@@ -1776,6 +1776,16 @@ static int check_user_passwd(const char *path, char *user_and_passwd)
colon_after_user = strchr(user_and_passwd, ':');
if (!colon_after_user)
goto bad_input;
+
+ /* compare "user:" */
+ if (cur->after_colon[0] != '*'
+ && strncmp(cur->after_colon, user_and_passwd,
+ colon_after_user - user_and_passwd + 1) != 0
+ ) {
+ continue;
+ }
+ /* this cfg entry is '*' or matches username from peer */
+
passwd = strchr(cur->after_colon, ':');
if (!passwd)
goto bad_input;
@@ -1786,13 +1796,6 @@ static int check_user_passwd(const char *path, char *user_and_passwd)
struct pam_conv conv_info = { &pam_talker, (void *) &userinfo };
pam_handle_t *pamh;
- /* compare "user:" */
- if (cur->after_colon[0] != '*'
- && strncmp(cur->after_colon, user_and_passwd, colon_after_user - user_and_passwd + 1) != 0
- ) {
- continue;
- }
- /* this cfg entry is '*' or matches username from peer */
*colon_after_user = '\0';
userinfo.name = user_and_passwd;
userinfo.pw = colon_after_user + 1;
@@ -1828,31 +1831,32 @@ static int check_user_passwd(const char *path, char *user_and_passwd)
passwd = result->sp_pwdp;
}
# endif
+ /* In this case, passwd is ALWAYS encrypted:
+ * it came from /etc/passwd or /etc/shadow!
+ */
+ goto check_encrypted;
# endif /* ENABLE_PAM */
}
-
- /* compare "user:" */
- if (cur->after_colon[0] != '*'
- && strncmp(cur->after_colon, user_and_passwd, colon_after_user - user_and_passwd + 1) != 0
- ) {
- continue;
- }
- /* this cfg entry is '*' or matches username from peer */
-
- /* encrypt pwd from peer and check match with local one */
- {
- char *encrypted = pw_encrypt(
- /* pwd: */ colon_after_user + 1,
+ /* Else: passwd is from httpd.conf, it is either plaintext or encrypted */
+
+ if (passwd[0] == '$' && isdigit(passwd[1])) {
+ char *encrypted;
+ check_encrypted:
+ /* encrypt pwd from peer and check match with local one */
+ encrypted = pw_encrypt(
+ /* pwd (from peer): */ colon_after_user + 1,
/* salt: */ passwd,
/* cleanup: */ 0
);
r = strcmp(encrypted, passwd);
free(encrypted);
- goto end_check_passwd;
+ } else {
+ /* local passwd is from httpd.conf and it's plaintext */
+ r = strcmp(colon_after_user + 1, passwd);
}
- bad_input: ;
+ goto end_check_passwd;
}
-
+ bad_input:
/* Comparing plaintext "user:pass" in one go */
r = strcmp(cur->after_colon, user_and_passwd);
end_check_passwd: