Merge waqas with Tobias. Eww.
authorMatthew Wild <mwild1@gmail.com>
Tue, 18 Aug 2009 12:03:35 +0000 (13:03 +0100)
committerMatthew Wild <mwild1@gmail.com>
Tue, 18 Aug 2009 12:03:35 +0000 (13:03 +0100)
core/s2smanager.lua
core/sessionmanager.lua
net/server.lua
net/xmppclient_listener.lua
net/xmppserver_listener.lua
plugins/mod_compression.lua [new file with mode: 0644]
plugins/mod_posix.lua
plugins/mod_roster.lua
plugins/mod_tls.lua

index 0589e024ca26f4054a9b01e93d72d0ac7070fa55..ab2e4a5c83d2bd27d09eccbf63bce22d64a9c4d6 100644 (file)
@@ -126,6 +126,7 @@ function new_incoming(conn)
        end
        open_sessions = open_sessions + 1;
        local w, log = conn.write, logger_init("s2sin"..tostring(conn):match("[a-f0-9]+$"));
+       session.log = log;
        session.sends2s = function (t) log("debug", "sending: %s", tostring(t)); w(tostring(t)); end
        incoming_s2s[session] = true;
        return session;
index 1b1b36df9c8ccaaa4002511d519c77f27974c6d5..59f0eadf8087910294dad2feb31b21d11641bb5c 100644 (file)
@@ -19,7 +19,8 @@ local full_sessions = full_sessions;
 local bare_sessions = bare_sessions;
 
 local modulemanager = require "core.modulemanager";
-local log = require "util.logger".init("sessionmanager");
+local logger = require "util.logger";
+local log = logger.init("sessionmanager");
 local error = error;
 local uuid_generate = require "util.uuid".generate;
 local rm_load_roster = require "core.rostermanager".load_roster;
@@ -50,6 +51,9 @@ function new_session(conn)
        local w = conn.write;
        session.send = function (t) w(tostring(t)); end
        session.ip = conn.ip();
+       local conn_name = "c2s"..tostring(conn):match("[a-f0-9]+$");
+       session.log = logger.init(conn_name);
+               
        return session;
 end
 
index 966006c17350aeafdaf03f217da6254d6926f81a..069db50f5dc0b17e4dd34c6b08a3a790b91335c1 100644 (file)
@@ -246,7 +246,7 @@ wrapserver = function( listeners, socket, ip, serverport, pattern, sslctx, maxco
         _socketlist[ socket ] = nil\r
         handler = nil\r
         socket = nil\r
-        mem_free( )\r
+        --mem_free( )\r
         out_put "server.lua: closed server handler and removed sockets from list"\r
     end\r
     handler.ip = function( )\r
@@ -373,7 +373,7 @@ wrapconnection = function( server, listeners, socket, ip, serverport, clientport
             handler = nil\r
         end\r
         socket = nil\r
-        mem_free( )\r
+        --mem_free( )\r
        if server then\r
                server.remove( )\r
        end\r
@@ -559,7 +559,7 @@ wrapconnection = function( server, listeners, socket, ip, serverport, clientport
             socket, err = ssl_wrap( socket, sslctx )    -- wrap socket\r
             if err then\r
                 out_put( "server.lua: ssl error: ", tostring(err) )\r
-                mem_free( )\r
+                --mem_free( )\r
                 return nil, nil, err    -- fatal error\r
             end\r
             socket:settimeout( 0 )\r
@@ -664,7 +664,7 @@ closesocket = function( socket )
     _readlistlen = removesocket( _readlist, socket, _readlistlen )\r
     _socketlist[ socket ] = nil\r
     socket:close( )\r
-    mem_free( )\r
+    --mem_free( )\r
 end\r
 \r
 ----------------------------------// PUBLIC //--\r
@@ -733,7 +733,7 @@ closeall = function( )
     _sendlist = { }\r
     _timerlist = { }\r
     _socketlist = { }\r
-    mem_free( )\r
+    --mem_free( )\r
 end\r
 \r
 getsettings = function( )\r
index dcc561f373dd844af220b04382a3d472b7dc06b6..6cea43f2ecd7c75226f66b16dc3c54b7493e5da5 100644 (file)
@@ -114,11 +114,6 @@ function xmppclient.listener(conn, data)
                session = sm_new_session(conn);
                sessions[conn] = session;
 
-               -- Logging functions --
-
-               local conn_name = "c2s"..tostring(conn):match("[a-f0-9]+$");
-               session.log = logger.init(conn_name);
-               
                session.log("info", "Client connected");
                
                -- Client is using legacy SSL (otherwise mod_tls sets this flag)
index 1f27d841721cd4b6a1f5b5fabb18c1cb14405d20..6a196446d44e8b35d8db0a1c834e045ff2d1f233 100644 (file)
@@ -114,12 +114,6 @@ function xmppserver.listener(conn, data)
                session = s2s_new_incoming(conn);
                sessions[conn] = session;
 
-               -- Logging functions --
-
-               
-               local conn_name = "s2sin"..tostring(conn):match("[a-f0-9]+$");
-               session.log = logger.init(conn_name);
-               
                session.log("info", "Incoming s2s connection");
                
                session.reset_stream = session_reset_stream;
diff --git a/plugins/mod_compression.lua b/plugins/mod_compression.lua
new file mode 100644 (file)
index 0000000..4ff10d5
--- /dev/null
@@ -0,0 +1,115 @@
+-- Prosody IM
+-- Copyright (C) 2009 Tobias Markmann
+-- 
+-- This project is MIT/X11 licensed. Please see the
+-- COPYING file in the source package for more information.
+--
+
+local st = require "util.stanza";
+local zlib = require "zlib";
+local pcall = pcall;
+
+local xmlns_compression_feature = "http://jabber.org/features/compress"
+local xmlns_compression_protocol = "http://jabber.org/protocol/compress"
+local compression_stream_feature = st.stanza("compression", {xmlns=xmlns_compression_feature}):tag("method"):text("zlib"):up();
+
+local compression_level = module:get_option("compression_level");
+
+-- if not defined assume admin wants best compression
+if compression_level == nil then compression_level = 9 end;
+
+compression_level = tonumber(compression_level);
+if not compression_level or compression_level < 1 or compression_level > 9 then
+       module:log("warn", "Invalid compression level in config: %s", tostring(compression_level));
+       module:log("warn", "Module loading aborted. Compression won't be available.");
+       return;
+end
+
+module:add_event_hook("stream-features",
+               function (session, features)
+                       if not session.compressed then
+                               -- FIXME only advertise compression support when TLS layer has no compression enabled
+                               features:add_child(compression_stream_feature);
+                       end
+               end
+);
+
+-- TODO Support compression on S2S level too.
+module:add_handler("c2s_unauthed", "compress", xmlns_compression_protocol,
+               function(session, stanza)
+                       -- checking if the compression method is supported
+                       local method = stanza:child_with_name("method")[1];
+                       if method == "zlib" then
+                               session.log("info", method.." compression selected.");
+                               session.send(st.stanza("compressed", {xmlns=xmlns_compression_protocol}));
+                               session:reset_stream();
+                               
+                               -- create deflate and inflate streams
+                               local status, deflate_stream = pcall(zlib.deflate, compression_level);
+                               if status == false then
+                                       local error_st = st.stanza("failure", {xmlns=xmlns_compression_protocol}):tag("setup-failed");
+                                       session.send(error_st);
+                                       session:log("error", "Failed to create zlib.deflate filter.");
+                                       module:log("error", inflate_stream);
+                                       return
+                               end
+                               
+                               local status, inflate_stream = pcall(zlib.inflate);
+                               if status == false then
+                                       local error_st = st.stanza("failure", {xmlns=xmlns_compression_protocol}):tag("setup-failed");
+                                       session.send(error_st);
+                                       session:log("error", "Failed to create zlib.deflate filter.");
+                                       module:log("error", inflate_stream);
+                                       return
+                               end
+                               
+                               -- setup compression for session.w
+                               local old_send = session.send;
+                               
+                               session.send = function(t)
+                                               local status, compressed, eof = pcall(deflate_stream, tostring(t), 'sync');
+                                               if status == false then
+                                                       session:close({
+                                                         condition = "undefined-condition";
+                                                         text = compressed;
+                                                         extra = st.stanza("failure", {xmlns="http://jabber.org/protocol/compress"}):tag("processing-failed");
+                                                       });
+                                                       module:log("error", compressed);
+                                                       return;
+                                               end
+                                               old_send(compressed);
+                                       end;
+                                       
+                               -- setup decompression for session.data
+                               local function setup_decompression(session)
+                                       local old_data = session.data
+                                       session.data = function(conn, data)
+                                                       local status, decompressed, eof = pcall(inflate_stream, data);
+                                                       if status == false then
+                                                               session:close({
+                                                                 condition = "undefined-condition";
+                                                                 text = compressed;
+                                                                 extra = st.stanza("failure", {xmlns="http://jabber.org/protocol/compress"}):tag("processing-failed");
+                                                               });
+                                                               module:log("error", compressed);
+                                                               return;
+                                                       end
+                                                       old_data(conn, decompressed);
+                                               end;
+                               end
+                               setup_decompression(session);
+                               
+                               local session_reset_stream = session.reset_stream;
+                               session.reset_stream = function(session)
+                                               session_reset_stream(session);
+                                               setup_decompression(session);
+                                               return true;
+                                       end;
+                               session.compressed = true;
+                       else
+                               session.log("info", method.." compression selected. But we don't support it.");
+                               local error_st = st.stanza("failure", {xmlns=xmlns_compression_protocol}):tag("unsupported-method");
+                               session.send(error_st);
+                       end
+               end
+);
index 83b8122e839834980444d836bc1978944c2a8451..5f7dfc5b1884e9c8b857b851c1aa43764b936c4f 100644 (file)
@@ -23,12 +23,39 @@ local prosody = _G.prosody;
 
 module.host = "*"; -- we're a global module
 
+-- Allow switching away from root, some people like strange ports.
+module:add_event_hook("server-started", function ()
+               local uid = module:get_option("setuid");
+               local gid = module:get_option("setgid");
+               if gid then
+                       local success, msg = pposix.setgid(gid);
+                       if success then
+                               module:log("debug", "Changed group to "..gid.." successfully.");
+                       else
+                               module:log("error", "Failed to change group to "..gid..". Error: "..msg);
+                               prosody.shutdown("Failed to change group to "..gid);
+                       end
+               end
+               if uid then
+                       local success, msg = pposix.setuid(uid);
+                       if success then
+                               module:log("debug", "Changed user to "..uid.." successfully.");
+                       else
+                               module:log("error", "Failed to change user to "..uid..". Error: "..msg);
+                               prosody.shutdown("Failed to change user to "..uid);
+                       end
+               end
+       end);
+
 -- Don't even think about it!
 module:add_event_hook("server-starting", function ()
-               if pposix.getuid() == 0 and not module:get_option("run_as_root") then
-                       module:log("error", "Danger, Will Robinson! Prosody doesn't need to be run as root, so don't do it!");
-                       module:log("error", "For more information on running Prosody as root, see http://prosody.im/doc/root");
-                       prosody.shutdown("Refusing to run as root");
+               local suid = module:get_option("setuid");
+               if not suid or suid == 0 or suid == "root" then
+                       if pposix.getuid() == 0 and not module:get_option("run_as_root") then
+                               module:log("error", "Danger, Will Robinson! Prosody doesn't need to be run as root, so don't do it!");
+                               module:log("error", "For more information on running Prosody as root, see http://prosody.im/doc/root");
+                               prosody.shutdown("Refusing to run as root");
+                       end
                end
        end);
 
index 8f25ed64169fefcdc742b3c9e466008701a8365e..7ca22aa1aa9f2b3c6f3c20ce6f71e352ae1ffdde 100644 (file)
@@ -24,7 +24,7 @@ module:add_feature("jabber:iq:roster");
 
 local rosterver_stream_feature = st.stanza("ver", {xmlns="urn:xmpp:features:rosterver"}):tag("optional"):up();
 module:add_event_hook("stream-features", 
-               function (session, features)                                                                                            
+               function (session, features)
                        if session.username then
                                features:add_child(rosterver_stream_feature);
                        end
index 158285f61bc275630fa53013b0e4f87a2707ec87..10455559dd600dabb593bb75ff31dc5dccc5eac1 100644 (file)
@@ -28,7 +28,7 @@ module:add_handler("c2s_unauthed", "starttls", xmlns_starttls,
                
 local starttls_attr = { xmlns = xmlns_starttls };
 module:add_event_hook("stream-features", 
-               function (session, features)                                                                                            
+               function (session, features)
                        if session.conn.starttls then
                                features:tag("starttls", starttls_attr);
                                if secure_auth_only then