aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog14
-rw-r--r--src/cyrsasl.erl14
-rw-r--r--src/cyrsasl_anonymous.erl4
-rw-r--r--src/cyrsasl_digest.erl20
-rw-r--r--src/cyrsasl_plain.erl4
-rw-r--r--src/ejabberd_auth.erl12
-rw-r--r--src/ejabberd_auth_anonymous.erl4
-rw-r--r--src/ejabberd_auth_external.erl2
-rw-r--r--src/ejabberd_auth_internal.erl4
-rw-r--r--src/ejabberd_auth_ldap.erl2
-rw-r--r--src/ejabberd_auth_odbc.erl6
-rw-r--r--src/ejabberd_auth_pam.erl2
-rw-r--r--src/ejabberd_c2s.erl9
13 files changed, 60 insertions, 37 deletions
diff --git a/ChangeLog b/ChangeLog
index 8cc8ecfd0..efc445b25 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,19 @@
2009-04-22 Badlop <badlop@process-one.net>
+ * src/cyrsasl.erl: Change API of check_password: pass a function
+ to generate the digest (thanks to Graham Whitted)(EJAB-863)
+ * src/cyrsasl_anonymous.erl: Likewise
+ * src/cyrsasl_digest.erl: Likewise
+ * src/cyrsasl_plain.erl: Likewise
+ * src/ejabberd_auth.erl: Likewise
+ * src/ejabberd_auth_anonymous.erl: Likewise
+ * src/ejabberd_auth_external.erl: Likewise
+ * src/ejabberd_auth_internal.erl: Likewise
+ * src/ejabberd_auth_ldap.erl: Likewise
+ * src/ejabberd_auth_odbc.erl: Likewise
+ * src/ejabberd_auth_pam.erl: Likewise
+ * src/ejabberd_c2s.erl: Likewise
+
* src/ejabberd_c2s.erl: Fix for SASL Anonymous connections not
stored or purged (thanks to Andy Skelton)(EJAB-912)
diff --git a/src/cyrsasl.erl b/src/cyrsasl.erl
index fb47b036b..f993b992a 100644
--- a/src/cyrsasl.erl
+++ b/src/cyrsasl.erl
@@ -30,19 +30,19 @@
-export([start/0,
register_mechanism/3,
listmech/1,
- server_new/6,
+ server_new/7,
server_start/3,
server_step/2]).
-record(sasl_mechanism, {mechanism, module, require_plain_password}).
-record(sasl_state, {service, myname, realm,
- get_password, check_password,
+ get_password, check_password, check_password_digest,
mech_mod, mech_state}).
-export([behaviour_info/1]).
behaviour_info(callbacks) ->
- [{mech_new, 3}, {mech_step, 2}];
+ [{mech_new, 4}, {mech_step, 2}];
behaviour_info(_Other) ->
undefined.
@@ -113,12 +113,13 @@ listmech(Host) ->
filter_anonymous(Host, Mechs).
server_new(Service, ServerFQDN, UserRealm, _SecFlags,
- GetPassword, CheckPassword) ->
+ GetPassword, CheckPassword, CheckPasswordDigest) ->
#sasl_state{service = Service,
myname = ServerFQDN,
realm = UserRealm,
get_password = GetPassword,
- check_password = CheckPassword}.
+ check_password = CheckPassword,
+ check_password_digest= CheckPasswordDigest}.
server_start(State, Mech, ClientIn) ->
case lists:member(Mech, listmech(State#sasl_state.myname)) of
@@ -128,7 +129,8 @@ server_start(State, Mech, ClientIn) ->
{ok, MechState} = Module:mech_new(
State#sasl_state.myname,
State#sasl_state.get_password,
- State#sasl_state.check_password),
+ State#sasl_state.check_password,
+ State#sasl_state.check_password_digest),
server_step(State#sasl_state{mech_mod = Module,
mech_state = MechState},
ClientIn);
diff --git a/src/cyrsasl_anonymous.erl b/src/cyrsasl_anonymous.erl
index 9fa51764c..19e65d6d8 100644
--- a/src/cyrsasl_anonymous.erl
+++ b/src/cyrsasl_anonymous.erl
@@ -27,7 +27,7 @@
-module(cyrsasl_anonymous).
--export([start/1, stop/0, mech_new/3, mech_step/2]).
+-export([start/1, stop/0, mech_new/4, mech_step/2]).
-behaviour(cyrsasl).
@@ -40,7 +40,7 @@ start(_Opts) ->
stop() ->
ok.
-mech_new(Host, _GetPassword, _CheckPassword) ->
+mech_new(Host, _GetPassword, _CheckPassword, _CheckPasswordDigest) ->
{ok, #state{server = Host}}.
mech_step(State, _ClientIn) ->
diff --git a/src/cyrsasl_digest.erl b/src/cyrsasl_digest.erl
index 0d27dbb68..49ea6a6d4 100644
--- a/src/cyrsasl_digest.erl
+++ b/src/cyrsasl_digest.erl
@@ -11,14 +11,14 @@
-export([start/1,
stop/0,
- mech_new/3,
+ mech_new/4,
mech_step/2]).
-include("ejabberd.hrl").
-behaviour(cyrsasl).
--record(state, {step, nonce, username, authzid, get_password, auth_module,
+-record(state, {step, nonce, username, authzid, get_password, check_password, auth_module,
host}).
start(_Opts) ->
@@ -27,11 +27,12 @@ start(_Opts) ->
stop() ->
ok.
-mech_new(Host, GetPassword, _CheckPassword) ->
+mech_new(Host, GetPassword, _CheckPassword, CheckPasswordDigest) ->
{ok, #state{step = 1,
nonce = randoms:get_string(),
host = Host,
- get_password = GetPassword}}.
+ get_password = GetPassword,
+ check_password = CheckPasswordDigest}}.
mech_step(#state{step = 1, nonce = Nonce} = State, _) ->
{continue,
@@ -56,10 +57,11 @@ mech_step(#state{step = 3, nonce = Nonce} = State, ClientIn) ->
{false, _} ->
{error, "not-authorized", UserName};
{Passwd, AuthModule} ->
- Response = response(KeyVals, UserName, Passwd,
- Nonce, AuthzId, "AUTHENTICATE"),
- case xml:get_attr_s("response", KeyVals) of
- Response ->
+ case (State#state.check_password)(UserName, Passwd,
+ xml:get_attr_s("response", KeyVals),
+ fun(PW) -> response(KeyVals, UserName, PW, Nonce, AuthzId,
+ "AUTHENTICATE") end) of
+ {true, _} ->
RspAuth = response(KeyVals,
UserName, Passwd,
Nonce, AuthzId, ""),
@@ -69,7 +71,7 @@ mech_step(#state{step = 3, nonce = Nonce} = State, ClientIn) ->
auth_module = AuthModule,
username = UserName,
authzid = AuthzId}};
- _ ->
+ {false, _} ->
{error, "not-authorized", UserName}
end
end
diff --git a/src/cyrsasl_plain.erl b/src/cyrsasl_plain.erl
index d9c7f1a50..4e69b06ba 100644
--- a/src/cyrsasl_plain.erl
+++ b/src/cyrsasl_plain.erl
@@ -27,7 +27,7 @@
-module(cyrsasl_plain).
-author('alexey@process-one.net').
--export([start/1, stop/0, mech_new/3, mech_step/2, parse/1]).
+-export([start/1, stop/0, mech_new/4, mech_step/2, parse/1]).
-behaviour(cyrsasl).
@@ -40,7 +40,7 @@ start(_Opts) ->
stop() ->
ok.
-mech_new(_Host, _GetPassword, CheckPassword) ->
+mech_new(_Host, _GetPassword, CheckPassword, _CheckPasswordDigest) ->
{ok, #state{check_password = CheckPassword}}.
mech_step(State, ClientIn) ->
diff --git a/src/ejabberd_auth.erl b/src/ejabberd_auth.erl
index 35b434f63..90bb34d17 100644
--- a/src/ejabberd_auth.erl
+++ b/src/ejabberd_auth.erl
@@ -84,12 +84,12 @@ check_password(User, Server, Password) ->
end.
%% @doc Check if the user and password can login in server.
-%% @spec (User::string(), Server::string(), Password::string(),
-%% StreamID::string(), Digest::string()) ->
+%% @spec (User::string(), Server::string(), Password::string()
+%% Digest::string(), DigestGen::function()) ->
%% true | false
-check_password(User, Server, Password, StreamID, Digest) ->
+check_password(User, Server, Password, Digest, DigestGen) ->
case check_password_with_authmodule(User, Server, Password,
- StreamID, Digest) of
+ Digest, DigestGen) of
{true, _AuthModule} -> true;
false -> false
end.
@@ -107,9 +107,9 @@ check_password(User, Server, Password, StreamID, Digest) ->
check_password_with_authmodule(User, Server, Password) ->
check_password_loop(auth_modules(Server), [User, Server, Password]).
-check_password_with_authmodule(User, Server, Password, StreamID, Digest) ->
+check_password_with_authmodule(User, Server, Password, Digest, DigestGen) ->
check_password_loop(auth_modules(Server), [User, Server, Password,
- StreamID, Digest]).
+ Digest, DigestGen]).
check_password_loop([], _Args) ->
false;
diff --git a/src/ejabberd_auth_anonymous.erl b/src/ejabberd_auth_anonymous.erl
index 9540e7c8c..05b9c98f5 100644
--- a/src/ejabberd_auth_anonymous.erl
+++ b/src/ejabberd_auth_anonymous.erl
@@ -173,7 +173,7 @@ purge_hook(true, LUser, LServer) ->
%% before allowing access
check_password(User, Server, Password) ->
check_password(User, Server, Password, undefined, undefined).
-check_password(User, Server, _Password, _StreamID, _Digest) ->
+check_password(User, Server, _Password, _Digest, _DigestGen) ->
%% We refuse login for registered accounts (They cannot logged but
%% they however are "reserved")
case ejabberd_auth:is_user_exists_in_other_modules(?MODULE,
@@ -226,7 +226,7 @@ get_password(User, Server) ->
get_password(User, Server, "").
get_password(User, Server, DefaultValue) ->
- case anonymous_user_exist(User, Server) of
+ case anonymous_user_exist(User, Server) or login(User, Server) of
%% We return the default value if the user is anonymous
true ->
DefaultValue;
diff --git a/src/ejabberd_auth_external.erl b/src/ejabberd_auth_external.erl
index d35d37f73..a5818a606 100644
--- a/src/ejabberd_auth_external.erl
+++ b/src/ejabberd_auth_external.erl
@@ -57,7 +57,7 @@ plain_password_required() ->
check_password(User, Server, Password) ->
extauth:check_password(User, Server, Password) andalso Password /= "".
-check_password(User, Server, Password, _StreamID, _Digest) ->
+check_password(User, Server, Password, _Digest, _DigestGen) ->
check_password(User, Server, Password).
set_password(User, Server, Password) ->
diff --git a/src/ejabberd_auth_internal.erl b/src/ejabberd_auth_internal.erl
index 2b8c62fd6..a3851b532 100644
--- a/src/ejabberd_auth_internal.erl
+++ b/src/ejabberd_auth_internal.erl
@@ -73,7 +73,7 @@ check_password(User, Server, Password) ->
false
end.
-check_password(User, Server, Password, StreamID, Digest) ->
+check_password(User, Server, Password, Digest, DigestGen) ->
LUser = jlib:nodeprep(User),
LServer = jlib:nameprep(Server),
US = {LUser, LServer},
@@ -81,7 +81,7 @@ check_password(User, Server, Password, StreamID, Digest) ->
[#passwd{password = Passwd}] ->
DigRes = if
Digest /= "" ->
- Digest == sha:sha(StreamID ++ Passwd);
+ Digest == DigestGen(Passwd);
true ->
false
end,
diff --git a/src/ejabberd_auth_ldap.erl b/src/ejabberd_auth_ldap.erl
index 1e57e0216..ea3de540a 100644
--- a/src/ejabberd_auth_ldap.erl
+++ b/src/ejabberd_auth_ldap.erl
@@ -147,7 +147,7 @@ check_password(User, Server, Password) ->
end
end.
-check_password(User, Server, Password, _StreamID, _Digest) ->
+check_password(User, Server, Password, _Digest, _DigestGen) ->
check_password(User, Server, Password).
set_password(_User, _Server, _Password) ->
diff --git a/src/ejabberd_auth_odbc.erl b/src/ejabberd_auth_odbc.erl
index edd493581..e06ebc560 100644
--- a/src/ejabberd_auth_odbc.erl
+++ b/src/ejabberd_auth_odbc.erl
@@ -80,8 +80,8 @@ check_password(User, Server, Password) ->
end
end.
-%% @spec (User, Server, Password, StreamID, Digest) -> true | false | {error, Error}
-check_password(User, Server, Password, StreamID, Digest) ->
+%% @spec (User, Server, Password, Digest, DigestGen) -> true | false | {error, Error}
+check_password(User, Server, Password, Digest, DigestGen) ->
case jlib:nodeprep(User) of
error ->
false;
@@ -93,7 +93,7 @@ check_password(User, Server, Password, StreamID, Digest) ->
{selected, ["password"], [{Passwd}]} ->
DigRes = if
Digest /= "" ->
- Digest == sha:sha(StreamID ++ Passwd);
+ Digest == DigestGen(Passwd);
true ->
false
end,
diff --git a/src/ejabberd_auth_pam.erl b/src/ejabberd_auth_pam.erl
index 72237282e..304f025ac 100644
--- a/src/ejabberd_auth_pam.erl
+++ b/src/ejabberd_auth_pam.erl
@@ -55,7 +55,7 @@ start(_Host) ->
set_password(_User, _Server, _Password) ->
{error, not_allowed}.
-check_password(User, Server, Password, _StreamID, _Digest) ->
+check_password(User, Server, Password, _Digest, _DigestGen) ->
check_password(User, Server, Password).
check_password(User, Host, Password) ->
diff --git a/src/ejabberd_c2s.erl b/src/ejabberd_c2s.erl
index 78fcd0761..df6144203 100644
--- a/src/ejabberd_c2s.erl
+++ b/src/ejabberd_c2s.erl
@@ -258,6 +258,10 @@ wait_for_stream({xmlstreamstart, _Name, Attrs}, StateData) ->
fun(U, P) ->
ejabberd_auth:check_password_with_authmodule(
U, Server, P)
+ end,
+ fun(U, P, D, DG) ->
+ ejabberd_auth:check_password_with_authmodule(
+ U, Server, P, D, DG)
end),
Mechs = lists:map(
fun(S) ->
@@ -444,9 +448,10 @@ wait_for_auth({xmlstreamelement, El}, StateData) ->
(acl:match_rule(StateData#state.server,
StateData#state.access, JID) == allow) of
true ->
+ DGen = fun(PW) ->
+ sha:sha(StateData#state.streamid ++ PW) end,
case ejabberd_auth:check_password_with_authmodule(
- U, StateData#state.server, P,
- StateData#state.streamid, D) of
+ U, StateData#state.server, P, D, DGen) of
{true, AuthModule} ->
?INFO_MSG(
"(~w) Accepted legacy authentication for ~s by ~p",