2 * @file protocol_module_base.h
3 * @brief shared object protocol module abstract class
5 * L7VSD: Linux Virtual Server for Layer7 Load Balancing
6 * Copyright (C) 2009 NTT COMWARE Corporation.
8 * This program is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Lesser General Public
10 * License as published by the Free Software Foundation; either
11 * version 2.1 of the License, or (at your option) any later version.
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Lesser General Public License for more details.
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with this library; if not, write to the Free Software
20 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
23 **********************************************************************/
24 #ifndef PROTOCOL_MODULE_BASE_H
25 #define PROTOCOL_MODULE_BASE_H
27 #include <boost/thread.hpp>
28 #include <boost/asio.hpp>
29 #include <boost/function.hpp>
30 #include "logger_enum.h"
31 #include "module_base.h"
32 #include "realserver.h"
33 #include <boost/format.hpp>
35 #define VS_CONTACT_CLASS_NORMAL (0)
36 #define VS_CONTACT_CLASS_SSL (0x00000001)
40 //! @class protocol_module_base
41 //! @brief this class is base class of all protocol module classes.
42 class protocol_module_base : public module_base {
44 //! realserver list type
45 typedef std::list<realserver> realserverlist_type;
46 //! realserver iterator function object type
47 typedef boost::function< realserverlist_type::iterator( void ) >
48 rs_list_itr_func_type;
49 typedef boost::function< realserverlist_type::iterator( realserverlist_type::iterator ) >
50 rs_list_itr_next_func_type;
51 //! TCP/IP scheduler function object type.
52 typedef boost::function< void ( const boost::thread::id,
53 rs_list_itr_func_type,
54 rs_list_itr_func_type,
55 rs_list_itr_next_func_type,
56 boost::asio::ip::tcp::endpoint& ) >
57 tcp_schedule_func_type;
58 //! UDP scheduler function object type.
59 typedef boost::function< void ( const boost::thread::id,
60 rs_list_itr_func_type,
61 rs_list_itr_func_type,
62 rs_list_itr_next_func_type,
63 boost::asio::ip::udp::endpoint& ) >
64 udp_schedule_func_type;
67 //! @brief event tag is return to session.
69 //use in upstream_thread
70 INITIALIZE = 0, //!< Do Initialize
71 ACCEPT, //!< Accept to Client
72 CLIENT_RECV, //!< Receive from Client
73 REALSERVER_SELECT, //!< Select RealServer
74 REALSERVER_CONNECT, //!< Connect to RealServer
75 REALSERVER_SEND, //!< Send message to RealServer
76 SORRYSERVER_SELECT, //!< Select SorryServer
77 SORRYSERVER_CONNECT, //!< Connect to SorryServer
78 SORRYSERVER_SEND, //!< Send message to SorryServer
79 //use in downstream_thread
80 REALSERVER_RECV, //!< Receive from RealServer
81 SORRYSERVER_RECV, //!< Receive from SorryServer
82 CLIENT_SELECT, //!< Select Client
83 CLIENT_CONNECTION_CHECK, //!< Check ClientConnection available
84 CLIENT_SEND, //!< Send message to Client
86 CLIENT_RESPONSE_SEND, //!< Send UML7response message to Client
87 REALSERVER_DISCONNECT, //!< Disconnect RealServerConnection
88 SORRYSERVER_DISCONNECT, //!< Disconnect SorryServerConnection
89 CLIENT_DISCONNECT, //!< Disconnect ClientConnection
90 REALSERVER_CLOSE, //!< Close socket(RealServer side)
91 FINALIZE, //!< Do finalize
92 STOP //!< Stop SessionThread
95 //! @struct check_message_result
96 //! @brief this class is POD. this class used then return multi value
97 struct check_message_result{
98 bool flag; //! return flasg
99 std::string message; //! return message
101 //! @param[in] check_message_result& is equal check object.
102 //! @return true is equal
103 //! @return false is not equal
104 bool operator==( const check_message_result& in )
105 { return ( ( flag == in.flag ) && ( message == in.message ) ); }
106 //! @param[in] check_message_result& is not equal check object.
107 //! @return true is not equal
108 //! @return false is equal
109 bool operator!=( const check_message_result& in )
110 { return ( ( flag != in.flag ) || ( message != in.message ) ); }
112 check_message_result() : flag(false){}
115 //! realserver list iterator begin function object
116 rs_list_itr_func_type rs_list_begin;
117 //! realserver list iterator end function object
118 rs_list_itr_func_type rs_list_end;
119 //! realserver list iterator next function object
120 rs_list_itr_next_func_type
123 //! realserver list lock function object
124 boost::function< void( void ) > rs_list_lock;
125 //! realserver list unlock function object
126 boost::function< void( void ) > rs_list_unlock;
128 tcp_schedule_func_type schedule_tcp; //!< tcp_scheduler_function object
129 udp_schedule_func_type schedule_udp; //!< udp_scheduler function object
133 protocol_module_base( std::string in_modulename ) : module_base( in_modulename ){};
135 virtual ~protocol_module_base(){};
136 //! initialize function. called from module control. module loaded call
137 //! @param[in] realserver list iterator begin function object type
138 //! @param[in] realserver list iterator end function object type
139 //! @param[in] realserver list iterator next function object type
140 //! @param[in] realserver list mutex lock function object type.
141 //! @param[in] realserver list mutex unlock function object type
142 virtual void initialize(
143 rs_list_itr_func_type inlist_begin,
144 rs_list_itr_func_type inlist_end,
145 rs_list_itr_next_func_type inlist_next,
146 boost::function< void( void ) > inlist_lock,
147 boost::function< void( void ) > inlist_unlock ) = 0;
149 //! finalize called from module control. module unloaded call.
150 virtual void finalize() = 0;
152 //! sorry support check
153 //! @return true sorry mode is supported.
154 //! @return false sorry mode is unsupported.
155 virtual bool is_use_sorry() = 0;
157 //! realserver list update event
158 virtual void handle_rslist_update() = 0;
161 //! module parameter check.used by l7vsadm
162 //! @param[in] module paramter string list
163 //! @return result.flag true is parameter is noproblem.
164 //! @return result.flag false is paramter is problem.
165 virtual check_message_result check_parameter( const std::vector<std::string>& args ) = 0;
167 //! @param[in] module paramter string list
168 //! @return result.flag true is parameter is noproblem.
169 //! @return result.flag false is paramter is problem.
170 virtual check_message_result set_parameter( const std::vector<std::string>& args ) = 0;
172 //! @param[in] module paramter string list
173 //! @return result.flag true is parameter is noproblem.
174 //! @return result.flag false is paramter is problem.
175 virtual check_message_result add_parameter( const std::vector<std::string>& args ) = 0;
177 //! TCP/IP scheduled function registation.
178 //! @param[in] schedule module TCP/IP scheduled function object type
179 virtual void register_schedule( tcp_schedule_func_type inschedule ) = 0;
180 //! UDP scheduled function registation
181 //! @param[in] schedule module UDP scheduled funtion object type
182 virtual void register_schedule( udp_schedule_func_type inschedule ) = 0;
184 //! called from session initialzie use in upstream_thread
185 //! @param[in] upstream thread id.
186 //! @param[in] downstream thread id
187 //! @return session use EVENT mode.
188 virtual EVENT_TAG handle_session_initialize(
189 const boost::thread::id up_thread_id,
190 const boost::thread::id down_thread_id,
191 const boost::asio::ip::tcp::endpoint& client_endpoint_tcp,
192 const boost::asio::ip::udp::endpoint& client_endpoint_udp ) = 0;
194 //! called from session finalize use in upstream thread.
195 //! @param[in] upstream thread id.
196 //! @param[in] downstream thread id
197 //! @return session use EVENT mode.
198 virtual EVENT_TAG handle_session_finalize(
199 const boost::thread::id up_thread_id,
200 const boost::thread::id down_thread_id ) = 0;
202 //! called from after session accept.in client socket use in upstream thread.
203 //! @param[in] upstream thread id.
204 //! @return session use EVENT mode.
205 virtual EVENT_TAG handle_accept( const boost::thread::id thread_id ) = 0;
207 //! called from after session recv in client socket. use in upstream thread.
208 //! @param[in] upstream thread id
209 //! @param[in] recive buffer refarence.
210 //! @param[in] recive length
211 //! @return session use EVENT mode.
212 virtual EVENT_TAG handle_client_recv(
213 const boost::thread::id thread_id,
214 const boost::array<char,MAX_BUFFER_SIZE>& recvbuffer,
215 const size_t recvlen ) = 0;
217 //! called from after realserver select.use in upstream thread.
218 //! @param[in] upstream thread id
219 //! @param[out] realserver TCP endpoint
220 //! @return session use EVENT mode.
221 virtual EVENT_TAG handle_realserver_select(
222 const boost::thread::id thread_id,
223 boost::asio::ip::tcp::endpoint& rs_endpoint ) = 0;
225 //! called from after realserver select
226 //! @param[in] upstream thread id
227 //! @param[out] realserver UDP endpoint
228 //! @param[out] sendbudffer reference
229 //! @param[out] send data length
230 //! @return session use EVENT mode.
231 virtual EVENT_TAG handle_realserver_select(
232 const boost::thread::id thread_id,
233 boost::asio::ip::udp::endpoint& rs_endpoint,
234 boost::array<char,MAX_BUFFER_SIZE>& sendbuffer,
235 size_t& datalen ) = 0;
237 //! called from after realserver connect
238 //! @param[in] upstream thread id
239 //! @param[out] sendbuffer reference
240 //! @param[out] send data length
241 //! @return session use EVENT mode.
242 virtual EVENT_TAG handle_realserver_connect(
243 const boost::thread::id thread_id,
244 boost::array<char,MAX_BUFFER_SIZE>& sendbuffer,
245 size_t& datalen ) = 0;
247 //! called from after realserver connection fail
248 //! @param[in] upstream thread id
249 //! @param[in] fail realserver endpoint reference
250 //! @return session use EVENT mode.
251 virtual EVENT_TAG handle_realserver_connection_fail(
252 const boost::thread::id thread_id,
253 const boost::asio::ip::tcp::endpoint& rs_endpoint ) = 0;
255 //! called from after realserver send.
256 //! @param[in] upstream thread id
257 //! @return session use EVENT mode.
258 virtual EVENT_TAG handle_realserver_send(
259 const boost::thread::id thread_id ) = 0;
261 //! called from after sorryserver select
262 //! @param[in] upstream thread id
263 //! @param[in] sorryserver endppiont reference
264 //! @return session use EVENT mode.
265 virtual EVENT_TAG handle_sorryserver_select(
266 const boost::thread::id thread_id,
267 boost::asio::ip::tcp::endpoint& sorry_endpoint ) = 0;
269 //! called from after sorryserver connect
270 //! @param[in] upstream thread id
271 //! @param[out] send buffer reference.
272 //! @param[out] send length
273 //! @return session use EVENT mode.
274 virtual EVENT_TAG handle_sorryserver_connect(
275 const boost::thread::id thread_id,
276 boost::array<char,MAX_BUFFER_SIZE>& sendbuffer,
277 size_t& datalen ) = 0;
279 //! called from after sorryserver connection fail
280 //! @param[in] upstream thread id
281 //! @param[in] sorryserver endpoint reference.
282 //! @return session use EVENT mode.
283 virtual EVENT_TAG handle_sorryserver_connection_fail(
284 const boost::thread::id thread_id,
285 const boost::asio::ip::tcp::endpoint& sorry_endpoint ) = 0;
287 //! called from after sorryserver send
288 //! @param[in] upstream thread id
289 //! @return session use EVENT mode.
290 virtual EVENT_TAG handle_sorryserver_send( const boost::thread::id thread_id ) = 0;
292 //! called from after realserver recvive for TCP/IP
293 //! @param[in] downstream thread id
294 //! @param[in] realserver TCP/IP endpoint reference
295 //! @param[in] realserver recive buffer reference.
296 //! @param[in] recv data length
297 //! @return session use EVENT mode.
298 virtual EVENT_TAG handle_realserver_recv(
299 const boost::thread::id thread_id,
300 const boost::asio::ip::tcp::endpoint& rs_endpoint,
301 const boost::array<char,MAX_BUFFER_SIZE>& recvbuffer,
302 const size_t recvlen ) = 0;
303 //! called from after realserver recive.for UDP
304 //! @param[in] downstream thread id
305 //! @param[in] realserver UDP endpoint reference
306 //! @param[in] recive from realserver buffer reference
307 //! @param[in] recv data length
308 //! @return session use EVENT mode.
309 virtual EVENT_TAG handle_realserver_recv(
310 const boost::thread::id thread_id,
311 const boost::asio::ip::udp::endpoint& rs_endpoint,
312 const boost::array<char,MAX_BUFFER_SIZE>& recvbuffer,
313 const size_t recvlen ) = 0;
315 //! called from after sorryserver recive
316 //! @param[in] downstream thread id
317 //! @param[in] sorryserver endpoint reference
318 //! @param[in] recive from realserver buffer reference.
319 //! @param[in] recv data length
320 //! @return session use EVENT mode
321 virtual EVENT_TAG handle_sorryserver_recv(
322 const boost::thread::id thread_id,
323 const boost::asio::ip::tcp::endpoint& sorry_endpoint,
324 const boost::array<char,MAX_BUFFER_SIZE>& recvbuffer,
325 const size_t recvlen ) = 0;
327 //! called from UPSTEEARM thread. make module original message.
328 //! @param[in] downstream thread id.
329 //! @return session use EVENT mode
330 virtual EVENT_TAG handle_response_send_inform(
331 const boost::thread::id thread_id ) = 0;
333 //! called from after client connection check. use TCP/IP only. create client send message.
334 //! @param[in] downstream thread id
335 //! @param[out] send budffer reference
336 //! @param[out] send data length
337 //! @return session use EVENT mode
338 virtual EVENT_TAG handle_client_connection_check(
339 const boost::thread::id thread_id,
340 boost::array<char,MAX_BUFFER_SIZE>& sendbuffer,
341 size_t& datalen ) = 0;
343 //! called from after client select. use UDP only
344 //! @param[in] downstream thread id
345 //! @param[in] client udp endpoint
346 //! @param[out] send buffer reference
347 //! @param[out] send data length
348 //! @return session use EVENT mode
349 virtual EVENT_TAG handle_client_select(
350 const boost::thread::id thread_id,
351 boost::asio::ip::udp::endpoint& cl_endpoint,
352 boost::array<char,MAX_BUFFER_SIZE>& sendbuffer,
353 size_t& datalen ) = 0;
355 //! called from after client send
356 //! @param[in] downstream thread id
357 //! @return session use EVENT mode
358 virtual EVENT_TAG handle_client_send( const boost::thread::id thread_id ) = 0;
360 //! call from client disconnect event. use upstream thread and downstream thread.
361 //! @param[in] upstream and downstream thread id( check! one thread one event! )
362 //! @return session use EVENT mode
363 virtual EVENT_TAG handle_client_disconnect(
364 const boost::thread::id thread_id ) = 0;
366 //! call from sorry mode event. use upstream thread and downstream thread
367 //! @param[in] upstream and downstream thread id( check! one thread one event and first time call pattern )
368 //! @return session use EVENT mode
369 virtual EVENT_TAG handle_sorry_enable( const boost::thread::id thread_id ) = 0;
371 //! call from sorry mode disable. use upstream thread and downstream thread.
372 //! @param[in] upstream and downstream thread id( check! one thread one event )
373 //! @return session use EVENT mode
374 virtual EVENT_TAG handle_sorry_disable( const boost::thread::id thread_id ) = 0;
376 //! call from realserver disconnect. use upstream thread and downstream thread
377 //! @param[in] upstream and downstream thread id( check! one thread one event )
378 //! @param[in] disconnected realserver endpoint.
379 //! @return session use EVENT mode
380 virtual EVENT_TAG handle_realserver_disconnect(
381 const boost::thread::id thread_id,
382 const boost::asio::ip::tcp::endpoint& rs_endpoint ) = 0;
384 //! call from sorry server disconnect. use upstraem thread and downstream thread
385 //! @param[in] upstream and downstream thread id( check! one thread one event )
386 //! @param[in] disconnect sorryserver endpoint
387 //! @return session use EVENT mode
388 virtual EVENT_TAG handle_sorryserver_disconnect(
389 const boost::thread::id thread_id,
390 const boost::asio::ip::tcp::endpoint& sorry_endpoint ) = 0;
392 //! call from realserver disconnect. use upstream thread and downstream thread.
393 //! @param[in] upstream and downstream thread id( check! one thread one event )
394 //! @param[in] disconnect realserver endpoint
395 //! @return session use EVENT mode.
396 virtual EVENT_TAG handle_realserver_close(
397 const boost::thread::id thread_id,
398 const boost::asio::ip::udp::endpoint& rs_endpoint ) = 0;
400 virtual bool is_exec_OK(unsigned int vs_attr) {return true;}
401 //! format dump data.
402 //! @param[in] data want to format
403 //! @param[in] data size
404 //! @param[out] format string
406 static void dump_memory(
408 const size_t data_size,
409 std::string& data_dump)
411 if (data == NULL || data_size == 0)
416 boost::format formatter("%02X");
417 for (size_t i = 0; i < data_size; i++)
423 else if (i != 0 && i % 2 == 0)
428 formatter % static_cast<unsigned short>(static_cast<unsigned char>(data[i]));
429 data_dump += formatter.str();
437 #endif //PROTOCOL_MODULE_BASE_H