OSDN Git Service

DHAソースコード、UT項目票(20091127)の登録
[ultramonkey-l7/ultramonkey-l7-v3.git] / include / protocol_module_base.h
1 /*
2  *      @file   protocol_module_base.h
3  *      @brief  shared object protocol module abstract class
4  *
5  * L7VSD: Linux Virtual Server for Layer7 Load Balancing
6  * Copyright (C) 2009  NTT COMWARE Corporation.
7  *
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.
12  *
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.
17  *
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
21  * 02110-1301 USA
22  *
23  **********************************************************************/
24 #ifndef PROTOCOL_MODULE_BASE_H
25 #define PROTOCOL_MODULE_BASE_H
26
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>
34
35 #define VS_CONTACT_CLASS_NORMAL (0)
36 #define VS_CONTACT_CLASS_SSL (0x00000001)
37
38 namespace l7vs{
39
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 {
43 public:
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;
65
66         //! @enum       EVENT_TAG
67         //! @brief      event tag is return to session.
68         enum    EVENT_TAG{
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
85                 //COMMON Status
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
93         };
94
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
100                 //!     == operator
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 ) ); }
111                 //! constractor
112                 check_message_result() : flag(false){}
113         };
114 protected:
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
121                                                         rs_list_next;
122
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;
127
128         tcp_schedule_func_type          schedule_tcp;   //!< tcp_scheduler_function object
129         udp_schedule_func_type          schedule_udp;   //!< udp_scheduler function object
130
131 public:
132         //! constractor
133         protocol_module_base( std::string in_modulename ) : module_base( in_modulename ){};
134         //! destractor
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;
148
149         //! finalize called from module control. module unloaded call.
150         virtual void    finalize() = 0;
151
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;
156
157         //! realserver list update event
158         virtual void    handle_rslist_update() = 0;
159
160
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;
166         //! parameter set
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;
171         //! parameter add
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;
176
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;
183
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;
193
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;
201
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;
206
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;
216
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;
224
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;
236
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;
246
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;
254
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;
260
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;
268
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;
278
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;
286
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;
291
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;
314
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;
326
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;
332
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;
342
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;
354
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;
359
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;
365
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;
370
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;
375
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;
383
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;
391
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;
399         //! call from 
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
405         //! @return
406         static void  dump_memory(
407                                                                         const char* data,
408                                                                         const size_t data_size,
409                                                                         std::string& data_dump)
410         {
411             if (data == NULL || data_size == 0)
412             {
413                 return;
414             }
415
416                 boost::format formatter("%02X");
417                 for (size_t i = 0; i < data_size; i++)
418                 {
419                         if (i % 32 == 0)
420                         {
421                                 data_dump += "\n";
422                         }
423                         else if (i != 0 && i % 2 == 0)
424                         {
425                                 data_dump += " ";
426                         }
427
428                         formatter % static_cast<unsigned short>(static_cast<unsigned char>(data[i]));
429                         data_dump += formatter.str();
430                 }
431                 data_dump += "\n";
432         }
433 };
434
435 } // namespace l7vsd
436
437 #endif  //PROTOCOL_MODULE_BASE_H