annotate mod_sasl2/mod_sasl2.lua @ 5383:df11a2cbc7b7

mod_http_oauth2: Implement RFC 7628 Proof Key for Code Exchange Likely to become mandatory in OAuth 2.1. Backwards compatible since the default 'plain' verifier would compare nil with nil if the relevant parameters are left out.
author Kim Alvefur <zash@zash.se>
date Sat, 29 Apr 2023 13:09:46 +0200
parents 6526b670e66d
children 2597e2113561
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
1 -- Prosody IM
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
2 -- Copyright (C) 2019 Kim Alvefur
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
3 --
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
4 -- This project is MIT/X11 licensed. Please see the
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
5 -- COPYING file in the source package for more information.
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
6 --
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
7 -- XEP-0388: Extensible SASL Profile
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
8 --
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
9
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
10 local st = require "util.stanza";
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
11 local errors = require "util.error";
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
12 local base64 = require "util.encodings".base64;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
13 local jid_join = require "util.jid".join;
5038
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
14 local set = require "util.set";
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
15
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
16 local usermanager_get_sasl_handler = require "core.usermanager".get_sasl_handler;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
17 local sm_make_authenticated = require "core.sessionmanager".make_authenticated;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
18
5039
c0d243b27e64 mod_sasl2, mod_sasl_bind2, mod_sasl2_sm: Bump XEP-0388 namespace
Matthew Wild <mwild1@gmail.com>
parents: 5038
diff changeset
19 local xmlns_sasl2 = "urn:xmpp:sasl:2";
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
20
5088
e9cf361982d5 mod_sasl2: Honour (c2s_)require_encryption config option
Matthew Wild <mwild1@gmail.com>
parents: 5067
diff changeset
21 local secure_auth_only = module:get_option_boolean("c2s_require_encryption", module:get_option_boolean("require_encryption", true));
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
22 local allow_unencrypted_plain_auth = module:get_option_boolean("allow_unencrypted_plain_auth", false)
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
23 local insecure_mechanisms = module:get_option_set("insecure_sasl_mechanisms", allow_unencrypted_plain_auth and {} or {"PLAIN", "LOGIN"});
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
24 local disabled_mechanisms = module:get_option_set("disable_sasl_mechanisms", { "DIGEST-MD5" });
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
25
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
26 local host = module.host;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
27
5038
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
28 local function tls_unique(self)
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
29 return self.userdata["tls-unique"]:ssl_peerfinished();
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
30 end
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
31
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
32 local function tls_exporter(conn)
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
33 if not conn.ssl_exportkeyingmaterial then return end
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
34 return conn:ssl_exportkeyingmaterial("EXPORTER-Channel-Binding", 32, "");
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
35 end
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
36
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
37 local function sasl_tls_exporter(self)
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
38 return tls_exporter(self.userdata["tls-exporter"]);
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
39 end
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
40
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
41 module:hook("stream-features", function(event)
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
42 local origin, features = event.origin, event.features;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
43 local log = origin.log or module._log;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
44
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
45 if origin.type ~= "c2s_unauthed" then
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
46 log("debug", "Already authenticated");
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
47 return
5088
e9cf361982d5 mod_sasl2: Honour (c2s_)require_encryption config option
Matthew Wild <mwild1@gmail.com>
parents: 5067
diff changeset
48 elseif secure_auth_only and not origin.secure then
e9cf361982d5 mod_sasl2: Honour (c2s_)require_encryption config option
Matthew Wild <mwild1@gmail.com>
parents: 5067
diff changeset
49 log("debug", "Not offering authentication on insecure connection");
e9cf361982d5 mod_sasl2: Honour (c2s_)require_encryption config option
Matthew Wild <mwild1@gmail.com>
parents: 5067
diff changeset
50 return;
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
51 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
52
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
53 local sasl_handler = usermanager_get_sasl_handler(host, origin)
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
54 origin.sasl_handler = sasl_handler;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
55
5038
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
56 local channel_bindings = set.new()
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
57 if origin.encrypted then
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
58 -- check whether LuaSec has the nifty binding to the function needed for tls-unique
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
59 -- FIXME: would be nice to have this check only once and not for every socket
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
60 if sasl_handler.add_cb_handler then
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
61 local info = origin.conn:ssl_info();
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
62 if info and info.protocol == "TLSv1.3" then
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
63 log("debug", "Channel binding 'tls-unique' undefined in context of TLS 1.3");
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
64 if tls_exporter(origin.conn) then
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
65 log("debug", "Channel binding 'tls-exporter' supported");
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
66 sasl_handler:add_cb_handler("tls-exporter", sasl_tls_exporter);
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
67 channel_bindings:add("tls-exporter");
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
68 end
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
69 elseif origin.conn.ssl_peerfinished and origin.conn:ssl_peerfinished() then
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
70 log("debug", "Channel binding 'tls-unique' supported");
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
71 sasl_handler:add_cb_handler("tls-unique", tls_unique);
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
72 channel_bindings:add("tls-unique");
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
73 else
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
74 log("debug", "Channel binding 'tls-unique' not supported (by LuaSec?)");
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
75 end
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
76 sasl_handler["userdata"] = {
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
77 ["tls-unique"] = origin.conn;
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
78 ["tls-exporter"] = origin.conn;
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
79 };
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
80 else
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
81 log("debug", "Channel binding not supported by SASL handler");
88980b2dd986 mod_sasl2: Hacky support for channel binding
Matthew Wild <mwild1@gmail.com>
parents: 5028
diff changeset
82 end
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
83 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
84
5039
c0d243b27e64 mod_sasl2, mod_sasl_bind2, mod_sasl2_sm: Bump XEP-0388 namespace
Matthew Wild <mwild1@gmail.com>
parents: 5038
diff changeset
85 local mechanisms = st.stanza("authentication", { xmlns = xmlns_sasl2 });
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
86
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
87 local available_mechanisms = sasl_handler:mechanisms()
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
88 for mechanism in pairs(available_mechanisms) do
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
89 if disabled_mechanisms:contains(mechanism) then
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
90 log("debug", "Not offering disabled mechanism %s", mechanism);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
91 elseif not origin.secure and insecure_mechanisms:contains(mechanism) then
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
92 log("debug", "Not offering mechanism %s on insecure connection", mechanism);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
93 else
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
94 log("debug", "Offering mechanism %s", mechanism);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
95 mechanisms:text_tag("mechanism", mechanism);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
96 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
97 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
98
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
99 features:add_direct_child(mechanisms);
5028
1f2d2bfd29dd mod_sasl2: Add event for other modules to advertise inline features
Matthew Wild <mwild1@gmail.com>
parents: 5025
diff changeset
100
5042
166fd192f39c mod_sasl2: Move <inline/> into <authentication>
Matthew Wild <mwild1@gmail.com>
parents: 5041
diff changeset
101 local inline = st.stanza("inline");
5067
54c6b4595f86 mod_sasl2: Forward stream attributes into sub-event
Matthew Wild <mwild1@gmail.com>
parents: 5063
diff changeset
102 module:fire_event("advertise-sasl-features", { origin = origin, features = inline, stream = event.stream });
5042
166fd192f39c mod_sasl2: Move <inline/> into <authentication>
Matthew Wild <mwild1@gmail.com>
parents: 5041
diff changeset
103 mechanisms:add_direct_child(inline);
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
104 end, 1);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
105
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
106 local function handle_status(session, status, ret, err_msg)
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
107 local err = nil;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
108 if status == "error" then
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
109 ret, err = nil, ret;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
110 if not errors.is_err(err) then
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
111 err = errors.new({ condition = err, text = err_msg }, { session = session });
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
112 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
113 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
114
5018
ed2a9a4c4f01 mod_sasl2: Return status from event handlers
Matthew Wild <mwild1@gmail.com>
parents: 4796
diff changeset
115 return module:fire_event("sasl2/"..session.base_type.."/"..status, {
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
116 session = session,
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
117 message = ret;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
118 error = err;
5025
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
119 error_text = err_msg;
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
120 });
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
121 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
122
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
123 module:hook("sasl2/c2s/failure", function (event)
5249
828e5e443613 mod_sasl2: Fire authentication-{success,failure} events like mod_saslauth
Matthew Wild <mwild1@gmail.com>
parents: 5088
diff changeset
124 module:fire_event("authentication-failure", event);
5025
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
125 local session, condition, text = event.session, event.message, event.error_text;
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
126 local failure = st.stanza("failure", { xmlns = xmlns_sasl2 })
5041
afa09e069afb mod_sasl2: Fix missing namespace on failure condition (thanks tmolitor)
Matthew Wild <mwild1@gmail.com>
parents: 5039
diff changeset
127 :tag(condition, { xmlns = "urn:ietf:params:xml:ns:xmpp-sasl" }):up();
5025
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
128 if text then
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
129 failure:text_tag("text", text);
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
130 end
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
131 session.send(failure);
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
132 return true;
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
133 end);
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
134
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
135 module:hook("sasl2/c2s/error", function (event)
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
136 local session = event.session
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
137 session.send(st.stanza("failure", { xmlns = xmlns_sasl2 })
5025
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
138 :tag(event.error and event.error.condition));
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
139 return true;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
140 end);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
141
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
142 module:hook("sasl2/c2s/challenge", function (event)
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
143 local session = event.session;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
144 session.send(st.stanza("challenge", { xmlns = xmlns_sasl2 })
5019
c83ce822f105 mod_sasl2: Fix <challenge> generation
Matthew Wild <mwild1@gmail.com>
parents: 5018
diff changeset
145 :text(base64.encode(event.message)));
5020
6a36dae4a88d mod_sasl2: Return true to indicate challenge was handled successfully
Matthew Wild <mwild1@gmail.com>
parents: 5019
diff changeset
146 return true;
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
147 end);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
148
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
149 module:hook("sasl2/c2s/success", function (event)
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
150 local session = event.session
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
151 local ok, err = sm_make_authenticated(session, session.sasl_handler.username);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
152 if not ok then
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
153 handle_status(session, "failure", err);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
154 return true;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
155 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
156 event.success = st.stanza("success", { xmlns = xmlns_sasl2 });
5023
90772a9c92a0 mod_sasl2: Include additional-data in SASL success response
Matthew Wild <mwild1@gmail.com>
parents: 5021
diff changeset
157 if event.message then
90772a9c92a0 mod_sasl2: Include additional-data in SASL success response
Matthew Wild <mwild1@gmail.com>
parents: 5021
diff changeset
158 event.success:text_tag("additional-data", base64.encode(event.message));
90772a9c92a0 mod_sasl2: Include additional-data in SASL success response
Matthew Wild <mwild1@gmail.com>
parents: 5021
diff changeset
159 end
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
160 end, 1000);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
161
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
162 module:hook("sasl2/c2s/success", function (event)
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
163 local session = event.session
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
164 event.success:text_tag("authorization-identifier", jid_join(session.username, session.host, session.resource));
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
165 session.send(event.success);
5049
e89aad13a52a mod_sasl2: Further break up success handling, into pre/post stream:features
Matthew Wild <mwild1@gmail.com>
parents: 5048
diff changeset
166 end, -1000);
e89aad13a52a mod_sasl2: Further break up success handling, into pre/post stream:features
Matthew Wild <mwild1@gmail.com>
parents: 5048
diff changeset
167
e89aad13a52a mod_sasl2: Further break up success handling, into pre/post stream:features
Matthew Wild <mwild1@gmail.com>
parents: 5048
diff changeset
168 module:hook("sasl2/c2s/success", function (event)
5249
828e5e443613 mod_sasl2: Fire authentication-{success,failure} events like mod_saslauth
Matthew Wild <mwild1@gmail.com>
parents: 5088
diff changeset
169 module:fire_event("authentication-success", event);
5049
e89aad13a52a mod_sasl2: Further break up success handling, into pre/post stream:features
Matthew Wild <mwild1@gmail.com>
parents: 5048
diff changeset
170 local session = event.session;
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
171 local features = st.stanza("stream:features");
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
172 module:fire_event("stream-features", { origin = session, features = features });
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
173 session.send(features);
5049
e89aad13a52a mod_sasl2: Further break up success handling, into pre/post stream:features
Matthew Wild <mwild1@gmail.com>
parents: 5048
diff changeset
174 end, -1500);
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
175
5021
f62b091b1c81 mod_sasl2: Eventually return true from success handler
Matthew Wild <mwild1@gmail.com>
parents: 5020
diff changeset
176 -- The gap here is to allow modules to do stuff to the stream after the stanza
f62b091b1c81 mod_sasl2: Eventually return true from success handler
Matthew Wild <mwild1@gmail.com>
parents: 5020
diff changeset
177 -- is sent, but before we proceed with anything else. This is expected to be
f62b091b1c81 mod_sasl2: Eventually return true from success handler
Matthew Wild <mwild1@gmail.com>
parents: 5020
diff changeset
178 -- a common pattern with SASL2, which allows atomic negotiation of a bunch of
f62b091b1c81 mod_sasl2: Eventually return true from success handler
Matthew Wild <mwild1@gmail.com>
parents: 5020
diff changeset
179 -- stream features.
f62b091b1c81 mod_sasl2: Eventually return true from success handler
Matthew Wild <mwild1@gmail.com>
parents: 5020
diff changeset
180 module:hook("sasl2/c2s/success", function (event) --luacheck: ignore 212/event
5063
53145c6b6b0b mod_sasl2: Clear sasl_handler on final success
Matthew Wild <mwild1@gmail.com>
parents: 5049
diff changeset
181 event.session.sasl_handler = nil;
5021
f62b091b1c81 mod_sasl2: Eventually return true from success handler
Matthew Wild <mwild1@gmail.com>
parents: 5020
diff changeset
182 return true;
f62b091b1c81 mod_sasl2: Eventually return true from success handler
Matthew Wild <mwild1@gmail.com>
parents: 5020
diff changeset
183 end, -2000);
f62b091b1c81 mod_sasl2: Eventually return true from success handler
Matthew Wild <mwild1@gmail.com>
parents: 5020
diff changeset
184
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
185 local function process_cdata(session, cdata)
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
186 if cdata then
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
187 cdata = base64.decode(cdata);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
188 if not cdata then
5025
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
189 return handle_status(session, "failure", "incorrect-encoding");
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
190 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
191 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
192 return handle_status(session, session.sasl_handler:process(cdata));
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
193 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
194
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
195 module:hook_tag(xmlns_sasl2, "authenticate", function (session, auth)
5088
e9cf361982d5 mod_sasl2: Honour (c2s_)require_encryption config option
Matthew Wild <mwild1@gmail.com>
parents: 5067
diff changeset
196 if secure_auth_only and not session.secure then
e9cf361982d5 mod_sasl2: Honour (c2s_)require_encryption config option
Matthew Wild <mwild1@gmail.com>
parents: 5067
diff changeset
197 return handle_status(session, "failure", "encryption-required");
e9cf361982d5 mod_sasl2: Honour (c2s_)require_encryption config option
Matthew Wild <mwild1@gmail.com>
parents: 5067
diff changeset
198 end
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
199 local sasl_handler = session.sasl_handler;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
200 if not sasl_handler then
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
201 sasl_handler = usermanager_get_sasl_handler(host, session);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
202 session.sasl_handler = sasl_handler;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
203 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
204 local mechanism = assert(auth.attr.mechanism);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
205 if not sasl_handler:select(mechanism) then
5025
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
206 return handle_status(session, "failure", "invalid-mechanism");
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
207 end
5048
3697d19d5fd9 mod_sasl2: Store client id if provided
Matthew Wild <mwild1@gmail.com>
parents: 5044
diff changeset
208 local user_agent = auth:get_child("user-agent");
3697d19d5fd9 mod_sasl2: Store client id if provided
Matthew Wild <mwild1@gmail.com>
parents: 5044
diff changeset
209 if user_agent then
3697d19d5fd9 mod_sasl2: Store client id if provided
Matthew Wild <mwild1@gmail.com>
parents: 5044
diff changeset
210 session.client_id = user_agent.attr.id;
5261
6526b670e66d mod_sasl2: Pull user-agent info into sasl_handler for later reference
Matthew Wild <mwild1@gmail.com>
parents: 5249
diff changeset
211 sasl_handler.user_agent = {
6526b670e66d mod_sasl2: Pull user-agent info into sasl_handler for later reference
Matthew Wild <mwild1@gmail.com>
parents: 5249
diff changeset
212 software = user_agent:get_child_text("software");
6526b670e66d mod_sasl2: Pull user-agent info into sasl_handler for later reference
Matthew Wild <mwild1@gmail.com>
parents: 5249
diff changeset
213 device = user_agent:get_child_text("device");
6526b670e66d mod_sasl2: Pull user-agent info into sasl_handler for later reference
Matthew Wild <mwild1@gmail.com>
parents: 5249
diff changeset
214 };
5048
3697d19d5fd9 mod_sasl2: Store client id if provided
Matthew Wild <mwild1@gmail.com>
parents: 5044
diff changeset
215 end
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
216 local initial = auth:get_child_text("initial-response");
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
217 return process_cdata(session, initial);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
218 end);
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
219
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
220 module:hook_tag(xmlns_sasl2, "response", function (session, response)
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
221 local sasl_handler = session.sasl_handler;
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
222 if not sasl_handler or not sasl_handler.selected then
5025
fd154db7c8fc mod_sasl2: Fix handling of various failure/error cases
Matthew Wild <mwild1@gmail.com>
parents: 5023
diff changeset
223 return handle_status(session, "failure", "invalid-mechanism");
3905
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
224 end
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
225 return process_cdata(session, response:get_text());
5ae2e865eea0 mod_sasl2: Experimental implementation of XEP-0388
Kim Alvefur <zash@zash.se>
parents:
diff changeset
226 end);