1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
|
-- Prosody IM
-- Copyright (C) 2008-2010 Matthew Wild
-- Copyright (C) 2008-2010 Waqas Hussain
--
-- This project is MIT/X11 licensed. Please see the
-- COPYING file in the source package for more information.
--
local hosts = prosody.hosts;
local pairs, setmetatable = pairs, setmetatable;
local logger_init = require "util.logger".init;
local sessionlib = require "util.session";
local log = logger_init("s2smanager");
local prosody = _G.prosody;
local incoming_s2s = {};
_G.incoming_s2s = incoming_s2s;
prosody.incoming_s2s = incoming_s2s;
local fire_event = prosody.events.fire_event;
local _ENV = nil;
-- luacheck: std none
local function new_incoming(conn)
local host_session = sessionlib.new("s2sin");
sessionlib.set_id(host_session);
sessionlib.set_logger(host_session);
sessionlib.set_conn(host_session, conn);
host_session.direction = "incoming";
host_session.hosts = {};
incoming_s2s[host_session] = true;
return host_session;
end
local function new_outgoing(from_host, to_host)
local host_session = sessionlib.new("s2sout");
sessionlib.set_id(host_session);
sessionlib.set_logger(host_session);
host_session.to_host = to_host;
host_session.from_host = from_host;
host_session.host = from_host;
host_session.notopen = true;
host_session.direction = "outgoing";
hosts[from_host].s2sout[to_host] = host_session;
return host_session;
end
local resting_session = { -- Resting, not dead
destroyed = true;
type = "s2s_destroyed";
open_stream = function (session)
session.log("debug", "Attempt to open stream on resting session");
end;
close = function (session)
session.log("debug", "Attempt to close already-closed session");
end;
reset_stream = function (session)
session.log("debug", "Attempt to reset stream of already-closed session");
end;
filter = function (type, data) return data; end; --luacheck: ignore 212/type
}; resting_session.__index = resting_session;
local function retire_session(session, reason)
local log = session.log or log; --luacheck: ignore 431/log
for k in pairs(session) do
if k ~= "log" and k ~= "id" and k ~= "conn" then
session[k] = nil;
end
end
session.destruction_reason = reason;
function session.send(data) log("debug", "Discarding data sent to resting session: %s", data); end
function session.data(data) log("debug", "Discarding data received from resting session: %s", data); end
session.thread = { run = function (_, data) return session.data(data) end };
session.sends2s = session.send;
return setmetatable(session, resting_session);
end
local function destroy_session(session, reason)
if session.destroyed then return; end
local log = session.log or log;
log("debug", "Destroying %s session %s->%s%s%s", session.direction, session.from_host, session.to_host, reason and ": " or "", reason or "");
if session.direction == "outgoing" then
hosts[session.from_host].s2sout[session.to_host] = nil;
session:bounce_sendq(reason);
elseif session.direction == "incoming" then
incoming_s2s[session] = nil;
end
local event_data = { session = session, reason = reason };
if session.type == "s2sout" then
fire_event("s2sout-destroyed", event_data);
if hosts[session.from_host] then
hosts[session.from_host].events.fire_event("s2sout-destroyed", event_data);
end
elseif session.type == "s2sin" then
fire_event("s2sin-destroyed", event_data);
if hosts[session.to_host] then
hosts[session.to_host].events.fire_event("s2sin-destroyed", event_data);
end
end
retire_session(session, reason); -- Clean session until it is GC'd
return true;
end
return {
incoming_s2s = incoming_s2s;
new_incoming = new_incoming;
new_outgoing = new_outgoing;
retire_session = retire_session;
destroy_session = destroy_session;
};
|