From d04ef5406b9e6517c80f82f430665fedc86725b4 Mon Sep 17 00:00:00 2001 From: rakshasa Date: Fri, 6 Jul 2007 21:33:26 +0000 Subject: [PATCH] * Removed the FastCGI code. * Cleaned up XmlRpc and fixed some compile errors. git-svn-id: svn://rakshasa.no/libtorrent/trunk/rtorrent@930 e378c898-3ddf-0310-93e7-cc216c733640 --- configure.ac | 1 - src/command_network.cc | 32 ++----- src/control.cc | 7 +- src/control.h | 8 -- src/rpc/Makefile.am | 2 - src/rpc/fast_cgi.cc | 185 -------------------------------------- src/rpc/fast_cgi.h | 77 ---------------- src/rpc/parse_commands.cc | 1 + src/rpc/parse_commands.h | 8 +- src/rpc/xmlrpc.cc | 52 ++++++----- src/rpc/xmlrpc.h | 22 ++--- 11 files changed, 49 insertions(+), 346 deletions(-) delete mode 100644 src/rpc/fast_cgi.cc delete mode 100644 src/rpc/fast_cgi.h diff --git a/configure.ac b/configure.ac index 1e40670f..2c857cad 100644 --- a/configure.ac +++ b/configure.ac @@ -30,7 +30,6 @@ PKG_CHECK_MODULES(STUFF, sigc++-2.0 libcurl >= 7.12.0 libtorrent >= 0.11.5, LIBS="$LIBS $STUFF_LIBS") AC_LANG_PUSH(C++) -TORRENT_WITH_FASTCGI TORRENT_WITH_XMLRPC_C AC_LANG_POP(C++) diff --git a/src/command_network.cc b/src/command_network.cc index c6188a70..6b7b705a 100644 --- a/src/command_network.cc +++ b/src/command_network.cc @@ -47,9 +47,7 @@ #include "core/download.h" #include "core/manager.h" -#include "rpc/fast_cgi.h" #include "rpc/scgi.h" -#include "rpc/xmlrpc.h" #include "ui/root.h" #include "rpc/command_slot.h" #include "rpc/command_variable.h" @@ -145,8 +143,8 @@ apply_enable_trackers(int64_t arg) { void initialize_xmlrpc() { - control->set_xmlrpc(new rpc::XmlRpc); - rpc::XmlRpc::set_slot_find_download(rak::mem_fn(control->core()->download_list(), &core::DownloadList::find_hex_ptr)); + rpc::xmlrpc.initialize(); + rpc::xmlrpc.set_slot_find_download(rak::mem_fn(control->core()->download_list(), &core::DownloadList::find_hex_ptr)); unsigned int count = 0; @@ -155,9 +153,9 @@ initialize_xmlrpc() { continue; if (itr->second.m_genericSlot != NULL) - control->xmlrpc()->insert_command(itr->first, itr->second.m_parm, itr->second.m_doc, false); + rpc::xmlrpc.insert_command(itr->first, itr->second.m_parm, itr->second.m_doc, false); else if (itr->second.m_downloadSlot != NULL) - control->xmlrpc()->insert_command(itr->first, itr->second.m_parm, itr->second.m_doc, true); + rpc::xmlrpc.insert_command(itr->first, itr->second.m_parm, itr->second.m_doc, true); else throw torrent::internal_error("XMLRPC: Bad entry."); @@ -170,24 +168,12 @@ initialize_xmlrpc() { control->core()->push_log(buffer); } -void -apply_fast_cgi(const std::string& arg) { - if (control->fast_cgi() != NULL) - throw torrent::input_error("FastCGI already enabled."); - - if (control->xmlrpc() == NULL) - initialize_xmlrpc(); - - control->set_fast_cgi(new rpc::FastCgi(arg)); - control->fast_cgi()->set_slot_process(rak::mem_fn(control->xmlrpc(), &rpc::XmlRpc::process)); -} - void apply_scgi(const std::string& arg, int type) { if (control->scgi() != NULL) throw torrent::input_error("SCGI already enabled."); - if (control->xmlrpc() == NULL) + if (!rpc::xmlrpc.is_valid()) initialize_xmlrpc(); // Fix this... @@ -240,14 +226,11 @@ apply_scgi(const std::string& arg, int type) { throw torrent::input_error(e.what()); } - control->scgi()->set_slot_process(rak::mem_fn(control->xmlrpc(), &rpc::XmlRpc::process)); + control->scgi()->set_slot_process(rak::mem_fn(&rpc::xmlrpc, &rpc::XmlRpc::process)); } void apply_xmlrpc_dialect(const std::string& arg) { - if (control->xmlrpc() == NULL) - initialize_xmlrpc(); - int value; if (arg == "i8") @@ -259,7 +242,7 @@ apply_xmlrpc_dialect(const std::string& arg) { else value = -1; - control->xmlrpc()->set_dialect(value); + rpc::xmlrpc.set_dialect(value); } void @@ -314,7 +297,6 @@ initialize_command_network() { ADD_COMMAND_VALUE_TRI("max_open_sockets", rak::make_mem_fun(cm, &torrent::ConnectionManager::set_max_size), rak::make_mem_fun(cm, &torrent::ConnectionManager::max_size)); ADD_COMMAND_VALUE_TRI("max_open_http", rak::make_mem_fun(httpStack, &core::CurlStack::set_max_active), rak::make_mem_fun(httpStack, &core::CurlStack::max_active)); - ADD_COMMAND_STRING_UN("fast_cgi", std::ptr_fun(&apply_fast_cgi)); ADD_COMMAND_STRING_UN("scgi_port", rak::bind2nd(std::ptr_fun(&apply_scgi), 1)); ADD_COMMAND_STRING_UN("scgi_local", rak::bind2nd(std::ptr_fun(&apply_scgi), 2)); ADD_VARIABLE_BOOL("scgi_dont_route", false); diff --git a/src/control.cc b/src/control.cc index 51bfbcef..1bc7fb8b 100644 --- a/src/control.cc +++ b/src/control.cc @@ -51,10 +51,8 @@ #include "input/manager.h" #include "input/input_event.h" #include "rpc/command_scheduler.h" -#include "rpc/fast_cgi.h" #include "rpc/parse_commands.h" #include "rpc/scgi.h" -#include "rpc/xmlrpc.h" #include "ui/root.h" #include "control.h" @@ -70,9 +68,7 @@ Control::Control() : m_commandScheduler(new rpc::CommandScheduler()), - m_fastCgi(NULL), m_scgi(NULL), - m_xmlrpc(NULL), m_tick(0) { @@ -124,9 +120,8 @@ Control::initialize() { void Control::cleanup() { - delete m_fastCgi; m_fastCgi = NULL; delete m_scgi; m_scgi = NULL; - delete m_xmlrpc; m_xmlrpc = NULL; + rpc::xmlrpc.cleanup(); priority_queue_erase(&taskScheduler, &m_taskShutdown); diff --git a/src/control.h b/src/control.h index 8e965e0f..e306d0be 100644 --- a/src/control.h +++ b/src/control.h @@ -99,15 +99,9 @@ public: rpc::CommandScheduler* command_scheduler() { return m_commandScheduler; } - rpc::FastCgi* fast_cgi() { return m_fastCgi; } - void set_fast_cgi(rpc::FastCgi* f) { m_fastCgi = f; } - rpc::SCgi* scgi() { return m_scgi; } void set_scgi(rpc::SCgi* f) { m_scgi = f; } - rpc::XmlRpc* xmlrpc() { return m_xmlrpc; } - void set_xmlrpc(rpc::XmlRpc* f) { m_xmlrpc = f; } - uint64_t tick() const { return m_tick; } void inc_tick() { m_tick++; } @@ -135,9 +129,7 @@ private: rpc::CommandScheduler* m_commandScheduler; - rpc::FastCgi* m_fastCgi; rpc::SCgi* m_scgi; - rpc::XmlRpc* m_xmlrpc; uint64_t m_tick; diff --git a/src/rpc/Makefile.am b/src/rpc/Makefile.am index 772c66ca..961613c5 100644 --- a/src/rpc/Makefile.am +++ b/src/rpc/Makefile.am @@ -14,8 +14,6 @@ libsub_rpc_a_SOURCES = \ command_slot.h \ command_variable.cc \ command_variable.h \ - fast_cgi.cc \ - fast_cgi.h \ parse.cc \ parse.h \ parse_commands.cc \ diff --git a/src/rpc/fast_cgi.cc b/src/rpc/fast_cgi.cc deleted file mode 100644 index 4cd0f179..00000000 --- a/src/rpc/fast_cgi.cc +++ /dev/null @@ -1,185 +0,0 @@ -// rTorrent - BitTorrent client -// Copyright (C) 2005-2006, Jari Sundell -// -// This program is free software; you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation; either version 2 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// You should have received a copy of the GNU General Public License -// along with this program; if not, write to the Free Software -// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -// -// In addition, as a special exception, the copyright holders give -// permission to link the code of portions of this program with the -// OpenSSL library under certain conditions as described in each -// individual source file, and distribute linked combinations -// including the two. -// -// You must obey the GNU General Public License in all respects for -// all of the code used other than OpenSSL. If you modify file(s) -// with this exception, you may extend this exception to your version -// of the file(s), but you are not obligated to do so. If you do not -// wish to do so, delete this exception statement from your version. -// If you delete this exception statement from all source files in the -// program, then also delete it here. -// -// Contact: Jari Sundell -// -// Skomakerveien 33 -// 3185 Skoppum, NORWAY - -#include "config.h" - -#ifdef HAVE_FASTCGI -#include -#include - -#include -#include -#include - -#include "globals.h" -#include "control.h" -#include "core/manager.h" -#endif - -#include - -#include "fast_cgi.h" - -namespace rpc { - -bool FastCgi::m_initialized = false; - -#ifdef HAVE_FASTCGI - -FastCgi::FastCgi(const std::string& path) : m_path(path) { - if (!m_initialized) - if (FCGX_Init() != 0) - throw torrent::resource_error("Could not initialize FastCGI library."); - - // Register the fd with torrent::ConnectionManager. - - // Set non-blocking as per - // http://www.fastcgi.com/archives/fastcgi-developers/2004-January/003136.html? - if ((m_fileDesc = FCGX_OpenSocket(m_path.c_str(), 5)) == -1) - throw torrent::resource_error("FastCGI could not open socket."); - - m_request = new FCGX_Request; - - // Need FCGI_FAIL_ON_INTR flag? - if (fcntl(m_fileDesc, F_SETFL, O_NONBLOCK) != 0 || - FCGX_InitRequest(m_request, m_fileDesc, 0) != 0) { - ::close(m_fileDesc); - delete m_request; - - throw torrent::resource_error("FastCGI could not initialize request."); - } - - // Meh. - control->core()->get_poll_manager()->get_torrent_poll()->open(this); - control->core()->get_poll_manager()->get_torrent_poll()->insert_read(this); -} - -FastCgi::~FastCgi() { - if (m_request == NULL) - return; - - control->core()->get_poll_manager()->get_torrent_poll()->remove_read(this); - control->core()->get_poll_manager()->get_torrent_poll()->close(this); - - FCGX_Free(m_request, true); - - m_fileDesc = 0; - m_request = NULL; - - // Also unlink the socket file. -} - -// This is fundementally wrong as it blocks. We can live with it as -// the http server will usually buffer the whole requests before -// opening the connection. - -void -FastCgi::event_read() { - if (FCGX_Accept_r(m_request) != 0) { - control->core()->push_log("FastCGI accept failed."); - return; - } - -// int flags = fcntl(((FCGX_Request*)m_request)->ipcFd, F_GETFL); - -// if (fcntl(((FCGX_Request*)m_request)->ipcFd, F_SETFL, flags & ~O_NONBLOCK) != 0) -// throw torrent::internal_error("FastCgi::event_read() could not set socket flags."); - - int length; - char* endPtr; - char* buffer = NULL; - slot_write slotWrite; - - const char* contentLength = FCGX_GetParam("CONTENT_LENGTH", m_request->envp); - - if (contentLength == NULL || (length = strtol(contentLength, &endPtr, 10)) < 0 || *endPtr != '\0') { - control->core()->push_log("FastCGI invalid content length."); - goto event_read_exit; - } - - buffer = new char[length]; - - if (FCGX_GetStr(buffer, length, m_request->in) != length) { - control->core()->push_log("FastCGI could not read sufficient data."); - goto event_read_exit; - } - - slotWrite.set(rak::mem_fn(this, &FastCgi::receive_write)); - - if (!m_slotProcess(buffer, length, slotWrite) || - FCGX_FFlush(m_request->out) == -1) { - control->core()->push_log("FastCGI could not write data."); - goto event_read_exit; - } - - control->core()->push_log("Processed an XMLRPC call."); - -event_read_exit: - FCGX_Finish_r(m_request); - delete buffer; -} - -void -FastCgi::event_write() { -} - -void -FastCgi::event_error() { - throw torrent::internal_error("FastCgi::event_error()."); -} - -bool -FastCgi::receive_write(const char* buffer, uint32_t length) { - return - FCGX_FPrintF(m_request->out, - "Content-type: text/plain\r\n" - "Content-length: %i\r\n\r\n", length) != -1 && - FCGX_PutStr(buffer, length, m_request->out) != -1; -} - -#else - -FastCgi::FastCgi(const std::string& path) { throw torrent::resource_error("FastCGI not supported."); } -FastCgi::~FastCgi() {} -void FastCgi::event_read() {} -void FastCgi::event_write() {} -void FastCgi::event_error() {} - -bool FastCgi::receive_write(const char* buffer, uint32_t length) { return false; } - -#endif - -} diff --git a/src/rpc/fast_cgi.h b/src/rpc/fast_cgi.h deleted file mode 100644 index 115545a3..00000000 --- a/src/rpc/fast_cgi.h +++ /dev/null @@ -1,77 +0,0 @@ -// rTorrent - BitTorrent client -// Copyright (C) 2005-2006, Jari Sundell -// -// This program is free software; you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation; either version 2 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// You should have received a copy of the GNU General Public License -// along with this program; if not, write to the Free Software -// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -// -// In addition, as a special exception, the copyright holders give -// permission to link the code of portions of this program with the -// OpenSSL library under certain conditions as described in each -// individual source file, and distribute linked combinations -// including the two. -// -// You must obey the GNU General Public License in all respects for -// all of the code used other than OpenSSL. If you modify file(s) -// with this exception, you may extend this exception to your version -// of the file(s), but you are not obligated to do so. If you do not -// wish to do so, delete this exception statement from your version. -// If you delete this exception statement from all source files in the -// program, then also delete it here. -// -// Contact: Jari Sundell -// -// Skomakerveien 33 -// 3185 Skoppum, NORWAY - -#ifndef RTORRENT_RPC_FAST_CGI_H -#define RTORRENT_RPC_FAST_CGI_H - -#include -#include -#include - -struct FCGX_Request; - -namespace rpc { - -class FastCgi : public torrent::Event { -public: - typedef rak::function2 slot_write; - typedef rak::function3 slot_process; - - FastCgi(const std::string& path); - virtual ~FastCgi(); - - const std::string path() const { return m_path; } - - void set_slot_process(slot_process::base_type* s) { m_slotProcess.set(s); } - - virtual void event_read(); - virtual void event_write(); - virtual void event_error(); - - bool receive_write(const char* buffer, uint32_t length); - -private: - static bool m_initialized; - - FCGX_Request* m_request; - std::string m_path; - - slot_process m_slotProcess; -}; - -} - -#endif diff --git a/src/rpc/parse_commands.cc b/src/rpc/parse_commands.cc index b2c4c555..d3e31621 100644 --- a/src/rpc/parse_commands.cc +++ b/src/rpc/parse_commands.cc @@ -49,6 +49,7 @@ namespace rpc { CommandMap commands; +XmlRpc xmlrpc; struct command_map_is_space : std::unary_function { bool operator () (char c) const { diff --git a/src/rpc/parse_commands.h b/src/rpc/parse_commands.h index 24d9a262..c277ec6e 100644 --- a/src/rpc/parse_commands.h +++ b/src/rpc/parse_commands.h @@ -40,6 +40,7 @@ #include #include "command_map.h" +#include "xmlrpc.h" namespace core { class Download; @@ -47,7 +48,9 @@ namespace core { namespace rpc { -// class CommandMap; +// Move to another file? +extern CommandMap commands; +extern XmlRpc xmlrpc; const char* parse_command_name(const char* first, const char* last, std::string* dest); @@ -69,9 +72,6 @@ parse_command_d_single_std(core::Download* download, const std::string& cmd) { parse_command_d_single(download, cmd.c_str(), cmd.c_str() + cmd.size()); } -// Move to anoher file? -extern CommandMap commands; - inline torrent::Object call_command(const char* key, const torrent::Object& obj) { return commands.call_command(key, obj); } inline torrent::Object call_command_void(const char* key) { return commands.call_command(key, torrent::Object()); } inline std::string call_command_string(const char* key) { return commands.call_command(key, torrent::Object()).as_string(); } diff --git a/src/rpc/xmlrpc.cc b/src/rpc/xmlrpc.cc index 4d36ae6d..7a48bd8e 100644 --- a/src/rpc/xmlrpc.cc +++ b/src/rpc/xmlrpc.cc @@ -49,15 +49,6 @@ namespace rpc { -// Ugly... -#ifdef XMLRPC_HAVE_I8 -int XmlRpc::m_dialect = dialect_i8; -#else -int XmlRpc::m_dialect = dialect_generic; -#endif - -XmlRpc::slot_find_download XmlRpc::m_slotFindDownload; - #ifdef HAVE_XMLRPC_C xmlrpc_value* xmlrpc_call_command(xmlrpc_env* env, xmlrpc_value* args, void* voidServerInfo); @@ -152,7 +143,7 @@ xmlrpc_to_download(xmlrpc_env* env, xmlrpc_value* value) { return NULL; if (std::strlen(valueString) != 40 || - (download = XmlRpc::get_slot_find_download()(valueString)) == NULL) + (download = xmlrpc.get_slot_find_download()(valueString)) == NULL) xmlrpc_env_set_fault(env, XMLRPC_TYPE_ERROR, "Could not find info-hash."); // Urgh, seriously? @@ -248,7 +239,7 @@ object_to_xmlrpc(xmlrpc_env* env, const torrent::Object& object) { case torrent::Object::TYPE_VALUE: #ifdef XMLRPC_HAVE_I8 - if (XmlRpc::dialect() != XmlRpc::dialect_generic) + if (xmlrpc::dialect() != XmlRpc::dialect_generic) return xmlrpc_i8_new(env, object.as_value()); #else return xmlrpc_int_new(env, object.as_value()); @@ -258,13 +249,14 @@ object_to_xmlrpc(xmlrpc_env* env, const torrent::Object& object) { return xmlrpc_string_new(env, object.as_string().c_str()); case torrent::Object::TYPE_LIST: + { xmlrpc_value* result = xmlrpc_array_new(env); for (torrent::Object::list_type::const_iterator itr = object.as_list().begin(), last = object.as_list().end(); itr != last; itr++) xmlrpc_array_append_item(env, result, object_to_xmlrpc(env, *itr)); return result; - + } default: return xmlrpc_int_new(env, 0); } @@ -303,20 +295,23 @@ xmlrpc_call_command_d(xmlrpc_env* env, xmlrpc_value* args, void* voidServerInfo) } } -XmlRpc::XmlRpc() : - m_env(new xmlrpc_env) { - -// #ifdef XMLRPC_HAVE_I8 -// m_dialect(dialect_i8) { -// #else -// m_dialect(dialect_generic) { -// #endif +void +XmlRpc::initialize() { +#ifndef XMLRPC_HAVE_I8 + m_dialect = dialect_generic; +#endif + m_env = new xmlrpc_env; + xmlrpc_env_init((xmlrpc_env*)m_env); m_registry = xmlrpc_registry_new((xmlrpc_env*)m_env); } -XmlRpc::~XmlRpc() { +void +XmlRpc::cleanup() { + if (!is_valid()) + return; + xmlrpc_registry_free((xmlrpc_registry*)m_registry); xmlrpc_env_clean((xmlrpc_env*)m_env); delete (xmlrpc_env*)m_env; @@ -354,6 +349,9 @@ XmlRpc::insert_command(const char* name, const char* parm, const char* doc, bool void XmlRpc::set_dialect(int dialect) { + if (!is_valid()) + throw torrent::input_error("Cannot select XMLRPC dialect before it is initialized."); + xmlrpc_env localEnv; xmlrpc_env_init(&localEnv); @@ -376,8 +374,10 @@ XmlRpc::set_dialect(int dialect) { throw torrent::input_error("Unsupported XMLRPC dialect selected."); } - if (localEnv.fault_occurred) + if (localEnv.fault_occurred) { + xmlrpc_env_clean(&localEnv); throw torrent::input_error("Unsupported XMLRPC dialect selected."); + } xmlrpc_env_clean(&localEnv); m_dialect = dialect; @@ -385,16 +385,14 @@ XmlRpc::set_dialect(int dialect) { #else -XmlRpc::XmlRpc() : m_dialect(dialect_generic) { throw torrent::resource_error("XMLRPC not supported."); } -XmlRpc::~XmlRpc() {} +void XmlRpc::initialize() { throw torrent::resource_error("XMLRPC not supported."); } +void XmlRpc::cleanup() {} void XmlRpc::insert_command(const char* name, const char* parm, const char* doc, bool onDownload) {} +void XmlRpc::set_dialect(__UNUSED int dialect) {} bool XmlRpc::process(const char* inBuffer, uint32_t length, slot_write slotWrite) { return false; } -xmlrpc_value* XmlRpc::call_command(xmlrpc_env* env, xmlrpc_value* args, void* voidServerInfo) { return NULL; } -xmlrpc_value* call_command_d(xmlrpc_env* env, xmlrpc_value* args, void* voidServerInfo) { return NULL; } - #endif } diff --git a/src/rpc/xmlrpc.h b/src/rpc/xmlrpc.h index 2ded36f6..7d2ba569 100644 --- a/src/rpc/xmlrpc.h +++ b/src/rpc/xmlrpc.h @@ -58,30 +58,30 @@ public: static const int dialect_i8 = 1; static const int dialect_apache = 2; - XmlRpc(); - ~XmlRpc(); + XmlRpc() : m_env(NULL), m_registry(NULL), m_dialect(dialect_i8) {} + + bool is_valid() const { return m_env != NULL; } + + void initialize(); + void cleanup(); bool process(const char* inBuffer, uint32_t length, slot_write slotWrite); void insert_command(const char* name, const char* parm, const char* doc, bool onDownload); - static int dialect() { return m_dialect; } + int dialect() { return m_dialect; } void set_dialect(int dialect); - static slot_find_download& get_slot_find_download() { return m_slotFindDownload; } - static void set_slot_find_download(slot_find_download::base_type* slot) { m_slotFindDownload.set(slot); } + slot_find_download& get_slot_find_download() { return m_slotFindDownload; } + void set_slot_find_download(slot_find_download::base_type* slot) { m_slotFindDownload.set(slot); } private: -// xmlrpc_env* m_env; -// xmlrpc_registry* m_registry; - void* m_env; void* m_registry; - // Meh. - static int m_dialect; + int m_dialect; - static slot_find_download m_slotFindDownload; + slot_find_download m_slotFindDownload; }; }