Comparison

plugins/mod_smacks.lua @ 12136:6366240d2edb

mod_smacks: Limit "old" session resumption counters Doing this when creating a whole new session seems reasonable because it is already expensive and this is when it may be adding to the old session store, while a successful resumption should be plus-minus zero.
author Kim Alvefur <zash@zash.se>
date Fri, 31 Dec 2021 00:48:38 +0100
parent 12135:fa804c2db747
child 12137:4e61aaa4e9b2
comparison
equal deleted inserted replaced
12135:fa804c2db747 12136:6366240d2edb
50 local smqueue = require "util.smqueue"; 50 local smqueue = require "util.smqueue";
51 local st = require "util.stanza"; 51 local st = require "util.stanza";
52 local timer = require "util.timer"; 52 local timer = require "util.timer";
53 local new_id = require "util.id".short; 53 local new_id = require "util.id".short;
54 local watchdog = require "util.watchdog"; 54 local watchdog = require "util.watchdog";
55 local it = require"util.iterators";
55 56
56 local sessionmanager = require "core.sessionmanager"; 57 local sessionmanager = require "core.sessionmanager";
57 local core_process_stanza = prosody.core_process_stanza; 58 local core_process_stanza = prosody.core_process_stanza;
58 59
59 local xmlns_errors = "urn:ietf:params:xml:ns:xmpp-stanzas"; 60 local xmlns_errors = "urn:ietf:params:xml:ns:xmpp-stanzas";
70 local s2s_smacks = module:get_option_boolean("smacks_enabled_s2s", true); 71 local s2s_smacks = module:get_option_boolean("smacks_enabled_s2s", true);
71 local s2s_resend = module:get_option_boolean("smacks_s2s_resend", false); 72 local s2s_resend = module:get_option_boolean("smacks_s2s_resend", false);
72 local max_unacked_stanzas = module:get_option_number("smacks_max_unacked_stanzas", 0); 73 local max_unacked_stanzas = module:get_option_number("smacks_max_unacked_stanzas", 0);
73 local max_inactive_unacked_stanzas = module:get_option_number("smacks_max_inactive_unacked_stanzas", 256); 74 local max_inactive_unacked_stanzas = module:get_option_number("smacks_max_inactive_unacked_stanzas", 256);
74 local delayed_ack_timeout = module:get_option_number("smacks_max_ack_delay", 30); 75 local delayed_ack_timeout = module:get_option_number("smacks_max_ack_delay", 30);
76 local max_old_sessions = module:get_option_number("smacks_max_old_sessions", 10);
75 77
76 local c2s_sessions = module:shared("/*/c2s/sessions"); 78 local c2s_sessions = module:shared("/*/c2s/sessions");
77 local local_sessions = prosody.hosts[module.host].sessions; 79 local local_sessions = prosody.hosts[module.host].sessions;
78 80
79 local function format_h(h) if h then return string.format("%d", h) end end 81 local function format_h(h) if h then return string.format("%d", h) end end
80 82
83 local all_old_sessions = module:open_store("smacks_h");
81 local old_session_registry = module:open_store("smacks_h", "map"); 84 local old_session_registry = module:open_store("smacks_h", "map");
82 local session_registry = module:shared "/*/smacks/resumption-tokens"; -- > user@host/resumption-token --> resource 85 local session_registry = module:shared "/*/smacks/resumption-tokens"; -- > user@host/resumption-token --> resource
83 86
84 local ack_errors = require"util.error".init("mod_smacks", xmlns_sm3, { 87 local ack_errors = require"util.error".init("mod_smacks", xmlns_sm3, {
85 head = { condition = "undefined-condition"; text = "Client acknowledged more stanzas than sent by server" }; 88 head = { condition = "undefined-condition"; text = "Client acknowledged more stanzas than sent by server" };
277 local ok, err, err_text = can_do_smacks(session); 280 local ok, err, err_text = can_do_smacks(session);
278 if not ok then 281 if not ok then
279 session.log("warn", "Failed to enable smacks: %s", err_text); -- TODO: XEP doesn't say we can send error text, should it? 282 session.log("warn", "Failed to enable smacks: %s", err_text); -- TODO: XEP doesn't say we can send error text, should it?
280 (session.sends2s or session.send)(st.stanza("failed", { xmlns = xmlns_sm }):tag(err, { xmlns = xmlns_errors})); 283 (session.sends2s or session.send)(st.stanza("failed", { xmlns = xmlns_sm }):tag(err, { xmlns = xmlns_errors}));
281 return true; 284 return true;
285 end
286
287 if session.username then
288 local old_sessions, err = all_old_sessions:get(session.username);
289 module:log("debug", "Old sessions: %q", old_sessions)
290 if old_sessions then
291 local keep, count = {}, 0;
292 for token, info in it.sorted_pairs(old_sessions, function(a, b)
293 return (old_sessions[a].t or 0) > (old_sessions[b].t or 0);
294 end) do
295 count = count + 1;
296 if count > max_old_sessions then break end
297 keep[token] = info;
298 end
299 all_old_sessions:set(session.username, keep);
300 end
282 end 301 end
283 302
284 module:log("debug", "Enabling stream management"); 303 module:log("debug", "Enabling stream management");
285 session.smacks = xmlns_sm; 304 session.smacks = xmlns_sm;
286 305