00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028 #ifndef ROSCPP_XMLRPC_MANAGER_H
00029 #define ROSCPP_XMLRPC_MANAGER_H
00030
00031 #include <string>
00032 #include <set>
00033 #include <boost/function.hpp>
00034 #include <boost/thread/mutex.hpp>
00035 #include <boost/thread/thread.hpp>
00036 #include <boost/enable_shared_from_this.hpp>
00037
00038 #include "common.h"
00039 #include "XmlRpc.h"
00040
00041 #include <ros/time.h>
00042
00043
00044 namespace ros
00045 {
00046
00050 namespace xmlrpc
00051 {
00052 XmlRpc::XmlRpcValue responseStr(int code, const std::string& msg, const std::string& response);
00053 XmlRpc::XmlRpcValue responseInt(int code, const std::string& msg, int response);
00054 XmlRpc::XmlRpcValue responseBool(int code, const std::string& msg, bool response);
00055 }
00056
00057 class XMLRPCCallWrapper;
00058 typedef boost::shared_ptr<XMLRPCCallWrapper> XMLRPCCallWrapperPtr;
00059
00060 class ROSCPP_DECL ASyncXMLRPCConnection : public boost::enable_shared_from_this<ASyncXMLRPCConnection>
00061 {
00062 public:
00063 virtual ~ASyncXMLRPCConnection() {}
00064
00065 virtual void addToDispatch(XmlRpc::XmlRpcDispatch* disp) = 0;
00066 virtual void removeFromDispatch(XmlRpc::XmlRpcDispatch* disp) = 0;
00067
00068 virtual bool check() = 0;
00069 };
00070 typedef boost::shared_ptr<ASyncXMLRPCConnection> ASyncXMLRPCConnectionPtr;
00071 typedef std::set<ASyncXMLRPCConnectionPtr> S_ASyncXMLRPCConnection;
00072
00073 class ROSCPP_DECL CachedXmlRpcClient
00074 {
00075 public:
00076 CachedXmlRpcClient(XmlRpc::XmlRpcClient *c)
00077 : in_use_(false)
00078 , client_(c)
00079 {
00080 }
00081
00082 bool in_use_;
00083 ros::WallTime last_use_time_;
00084 XmlRpc::XmlRpcClient* client_;
00085
00086 static const ros::WallDuration s_zombie_time_;
00087 };
00088
00089 class XMLRPCManager;
00090 typedef boost::shared_ptr<XMLRPCManager> XMLRPCManagerPtr;
00091
00092 typedef boost::function<void(XmlRpc::XmlRpcValue&, XmlRpc::XmlRpcValue&)> XMLRPCFunc;
00093
00094 class ROSCPP_DECL XMLRPCManager
00095 {
00096 public:
00097 static const XMLRPCManagerPtr& instance();
00098
00099 XMLRPCManager();
00100 ~XMLRPCManager();
00101
00112 bool validateXmlrpcResponse(const std::string& method,
00113 XmlRpc::XmlRpcValue &response, XmlRpc::XmlRpcValue &payload);
00114
00118 inline const std::string& getServerURI() const { return uri_; }
00119 inline uint32_t getServerPort() const { return port_; }
00120
00121 XmlRpc::XmlRpcClient* getXMLRPCClient(const std::string& host, const int port, const std::string& uri);
00122 void releaseXMLRPCClient(XmlRpc::XmlRpcClient* c);
00123
00124 void addASyncConnection(const ASyncXMLRPCConnectionPtr& conn);
00125 void removeASyncConnection(const ASyncXMLRPCConnectionPtr& conn);
00126
00127 bool bind(const std::string& function_name, const XMLRPCFunc& cb);
00128 void unbind(const std::string& function_name);
00129
00130 void start();
00131 void shutdown();
00132
00133 bool isShuttingDown() { return shutting_down_; }
00134
00135 private:
00136 void serverThreadFunc();
00137
00138 std::string uri_;
00139 int port_;
00140 boost::thread server_thread_;
00141
00142 #if defined(__APPLE__)
00143
00144 boost::mutex xmlrpc_call_mutex_;
00145 #endif
00146 XmlRpc::XmlRpcServer server_;
00147 typedef std::vector<CachedXmlRpcClient> V_CachedXmlRpcClient;
00148 V_CachedXmlRpcClient clients_;
00149 boost::mutex clients_mutex_;
00150
00151 bool shutting_down_;
00152
00153 ros::WallDuration master_retry_timeout_;
00154
00155 S_ASyncXMLRPCConnection added_connections_;
00156 boost::mutex added_connections_mutex_;
00157 S_ASyncXMLRPCConnection removed_connections_;
00158 boost::mutex removed_connections_mutex_;
00159
00160 S_ASyncXMLRPCConnection connections_;
00161
00162
00163 struct FunctionInfo
00164 {
00165 std::string name;
00166 XMLRPCFunc function;
00167 XMLRPCCallWrapperPtr wrapper;
00168 };
00169 typedef std::map<std::string, FunctionInfo> M_StringToFuncInfo;
00170 boost::mutex functions_mutex_;
00171 M_StringToFuncInfo functions_;
00172
00173 volatile bool unbind_requested_;
00174 };
00175
00176 }
00177
00178 #endif