comparison mod_sasl2_fast/mod_sasl2_fast.lua @ 5282:0566a71a7076

mod_sasl2_fast: Invalidate tokens issued prior to last password change
author Matthew Wild <mwild1@gmail.com>
date Tue, 28 Mar 2023 12:43:05 +0100
parents 471cbb583a1d
children 8e1f1eb00b58
comparison
equal deleted inserted replaced
5281:4ed65a6c2a6a 5282:0566a71a7076
1 local usermanager = require "core.usermanager";
2
1 local sasl = require "util.sasl"; 3 local sasl = require "util.sasl";
2 local dt = require "util.datetime"; 4 local dt = require "util.datetime";
3 local id = require "util.id"; 5 local id = require "util.id";
4 local jid = require "util.jid"; 6 local jid = require "util.jid";
5 local st = require "util.stanza"; 7 local st = require "util.stanza";
36 return token_info; 38 return token_info;
37 end 39 end
38 40
39 local function new_token_tester(hmac_f) 41 local function new_token_tester(hmac_f)
40 return function (mechanism, username, client_id, token_hash, cb_data, invalidate) 42 return function (mechanism, username, client_id, token_hash, cb_data, invalidate)
43 local account_info = usermanager.get_account_info(username, module.host);
44 local last_password_change = account_info and account_info.password_updated;
41 local tried_current_token = false; 45 local tried_current_token = false;
42 local key = hash.sha256(client_id, true).."-new"; 46 local key = hash.sha256(client_id, true).."-new";
43 local token; 47 local token;
44 repeat 48 repeat
45 log("debug", "Looking for %s token %s/%s", mechanism, username, key); 49 log("debug", "Looking for %s token %s/%s", mechanism, username, key);
48 local expected_hash = hmac_f(token.secret, "Initiator"..cb_data); 52 local expected_hash = hmac_f(token.secret, "Initiator"..cb_data);
49 if hash.equals(expected_hash, token_hash) then 53 if hash.equals(expected_hash, token_hash) then
50 local current_time = now(); 54 local current_time = now();
51 if token.expires_at < current_time then 55 if token.expires_at < current_time then
52 log("debug", "Token found, but it has expired (%ds ago). Cleaning up...", current_time - token.expires_at); 56 log("debug", "Token found, but it has expired (%ds ago). Cleaning up...", current_time - token.expires_at);
57 token_store:set(username, key, nil);
58 return nil, "credentials-expired";
59 elseif last_password_change and token.issued_at < last_password_change then
60 log("debug", "Token found, but issued prior to password change (%ds ago). Cleaning up...",
61 current_time - last_password_change
62 );
53 token_store:set(username, key, nil); 63 token_store:set(username, key, nil);
54 return nil, "credentials-expired"; 64 return nil, "credentials-expired";
55 end 65 end
56 if not tried_current_token and not invalidate then 66 if not tried_current_token and not invalidate then
57 -- The new token is becoming the current token 67 -- The new token is becoming the current token