Implemented Util::Config::serveForkedSocket(), added Socket::Connection::drop() function for dropping unused sockets.

This commit is contained in:
Thulinma 2014-01-27 18:02:58 +01:00
parent 92b7a7534d
commit d81bc24155
4 changed files with 95 additions and 17 deletions

View file

@ -5,6 +5,7 @@
#include "defines.h"
#include "timing.h"
#include "tinythread.h"
#include "stream.h"
#include <string.h>
#include <signal.h>
@ -299,7 +300,7 @@ bool Util::Config::getBool(std::string optname){
struct callbackData{
Socket::Connection * sock;
void (*cb)(Socket::Connection &);
int (*cb)(Socket::Connection &);
};
static void callThreadCallback(void * cDataArg){
@ -312,8 +313,14 @@ static void callThreadCallback(void * cDataArg){
DEBUG_MSG(DLVL_INSANE, "Thread for %p ended", cDataArg);
}
int Util::Config::serveThreadedSocket(void (*callback)(Socket::Connection &)){
Socket::Server server_socket = Socket::Server(getInteger("listen_port"), getString("listen_interface"), false);
int Util::Config::serveThreadedSocket(int (*callback)(Socket::Connection &)){
Socket::Server server_socket;
if (vals.isMember("socket")){
server_socket = Socket::Server(Util::getTmpFolder() + getString("socket"));
}
if (vals.isMember("listen_port") && vals.isMember("listen_interface")){
server_socket = Socket::Server(getInteger("listen_port"), getString("listen_interface"), false);
}
if (!server_socket.connected()){return 1;}
DEBUG_MSG(DLVL_DEVEL, "Activating threaded server: %s", getString("cmd").c_str());
activate();
@ -337,6 +344,41 @@ int Util::Config::serveThreadedSocket(void (*callback)(Socket::Connection &)){
return 0;
}
int Util::Config::serveForkedSocket(int (*callback)(Socket::Connection & S)){
Socket::Server server_socket;
if (vals.isMember("socket")){
server_socket = Socket::Server(Util::getTmpFolder() + getString("socket"));
}
if (vals.isMember("listen_port") && vals.isMember("listen_interface")){
server_socket = Socket::Server(getInteger("listen_port"), getString("listen_interface"), false);
}
if (!server_socket.connected()){
DEBUG_MSG(DLVL_DEVEL, "Failure to open socket");
return 1;
}
DEBUG_MSG(DLVL_DEVEL, "Activating forked server: %s", getString("cmd").c_str());
activate();
while (is_active && server_socket.connected()){
Socket::Connection S = server_socket.accept();
if (S.connected()){ //check if the new connection is valid
pid_t myid = fork();
if (myid == 0){ //if new child, start MAINHANDLER
server_socket.drop();
return callback(S);
}else{ //otherwise, do nothing or output debugging text
DEBUG_MSG(DLVL_DEVEL, "Forked new process %i for socket %i", (int)myid, S.getSocket());
S.drop();
}
}else{
Util::sleep(10); //sleep 10ms
}
}//main loop
server_socket.close();
DEBUG_MSG(DLVL_DEVEL, "Forked server exiting: %s", getString("cmd").c_str());
return 0;
}
/// Activated the stored config. This will:
/// - Drop permissions to the stored "username", if any.
/// - Daemonize the process if "daemonize" exists and is true.
@ -425,7 +467,16 @@ void Util::Config::addBasicConnectorOptions(JSON::Value & capabilities){
capabilities["optional"]["username"]["help"] = "Username to drop privileges to - default if unprovided means do not drop privileges";
capabilities["optional"]["username"]["option"] = "--username";
capabilities["optional"]["username"]["type"] = "str";
if (capabilities.isMember("socket")){
option.null();
option["arg"] = "string";
option["help"] = "Socket name that can be connected to for this connector.";
option["value"].append(capabilities["socket"]);
addOption("socket", option);
}
option.null();
option["long"] = "daemon";
option["short"] = "d";