1 /*DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64
4 for INTEL64(R), AMD64(R)
6 Copyright(C) 2007-2009 Koine Yuusuke(koinec). All rights reserved.
8 Redistribution and use in source and binary forms, with or without
9 modification, are permitted provided that the following conditions are met:
11 1. Redistributions of source code must retain the above copyright notice,
12 this list of conditions and the following disclaimer.
13 2. Redistributions in binary form must reproduce the above copyright
14 notice, this list of conditions and the following disclaimer in the
15 documentation and/or other materials provided with the distribution.
17 THIS SOFTWARE IS PROVIDED BY Koine Yuusuke(koinec) ``AS IS'' AND ANY
18 EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
19 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
20 DISCLAIMED. IN NO EVENT SHALL Koine Yuusuke(koinec) OR CONTRIBUTORS BE
21 LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
22 CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23 SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24 INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
25 CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26 ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
27 OF THE POSSIBILITY OF SUCH DAMAGE.
29 DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64*/
31 /* File Info -----------------------------------------------------------
32 File: drd64_marshald_dispatch.c
33 Function: Marshald Command Dispatcher (Main Loop Routine)
35 ----------------------------------------------------------------------*/
37 #include"drd64_marshald.h"
39 static fd_set g_fds_orig;
42 /* for EXTERNAL Function */
44 Drd64_Marshald_Dispatch_SetFD(
47 FD_SET( i_fds, &g_fds_orig );
52 /* for EXTERNAL Function */
54 Drd64_Marshald_Dispatch_CloseSocket(
57 Drd64_Server_RecvStatus *p_recv;
58 Drd64_Marshald_ConnectInfo *p_cinfo;
60 p_recv = Drd64_Server_RecvStatus_GetRecvStatus( i_fds );
61 assert( NULL != p_recv );
63 if( NULL != p_recv->pv_cinfo_connection ) {
64 p_cinfo = (Drd64_Marshald_ConnectInfo *)p_recv->pv_cinfo_connection;
66 Drd64_Marshald_Cinfo_FreeConnectInfo( p_cinfo );
67 p_recv->pv_cinfo_connection = NULL;
69 DRD64_LOG_DEBUG(" [DEBUG] Free ConnectionInfo with Close");
73 FD_CLR( i_fds, &g_fds_orig );
74 Drd64_Server_RecvStatus_DeleteSocketsChain( p_recv );
75 Drd64_Server_RecvStatus_CloseRecvStatus( i_fds );
76 DRD64_DEBUG_PRINT("CloseSocket",i_fds,"FD",i_fds,"errono",errno);
83 Drd64_Marshald_Dispatch_OpenSocket(
87 Drd64_Server_RecvStatus *p_recv;
89 i_socket_new = accept( i_socket_server, NULL, NULL );
90 DRD64_DEBUG_SYSCALL("accept(New Comm.)",i_socket_new,errno);
92 if( -1 == i_socket_new ) {
96 FD_SET( i_socket_new, &g_fds_orig );
98 p_recv = Drd64_Server_RecvStatus_AllocRecvStatus(
99 i_socket_new, DRD64_MARSHALD_RECVSTATUS_UNITS );
101 if( NULL == p_recv ) {
105 Drd64_Server_RecvStatus_InitRecvStatus( p_recv, i_socket_new );
106 Drd64_Server_RecvStatus_AddSocketsChain( p_recv );
112 /*----------------------------------------------------------------------
113 ----------------------------------------------------------------------*/
115 Drd64_Marshald_Dispatch_ExecPacket(
117 Drd64_Server_RecvStatus *p_recv,
118 Drd64_Marshald_MasterInformation *p_marshald )
121 Drd64_PacketHeader *p_phead;
122 Drd64_Server_RecvStatus *p_recv_parent;
125 /* Phase 1 : Init. ================================*/
127 i_result = DRD64_MARSHALD_DISPATCH_RESULT_CLOSE; // XXX > error
129 p_phead = (Drd64_PacketHeader *)p_recv->pv_buf;
130 assert( NULL != p_phead );
132 if( 0 < p_phead->i_datalen )
133 { pv_data = DRD64_PacketData( p_recv->pv_buf ); }
136 /* Phase 2 : Exec. Command ========================*/
137 /* CMD: Connect -----------------------------------*/
138 if( DRD64_COMMAND_CONNECT == p_phead->dw_command ) {
139 i_result = Drd64_Marshald_Cmd_Connect(
140 i_recv_id, p_phead, pv_data );
142 /* CMD: Connect Count -----------------------------*/
143 else if( DRD64_COMMAND_CONNECT_COUNT == p_phead->dw_command ) {
144 i_result = Drd64_Marshald_Cmd_ConnectCount(
145 i_recv_id, p_phead, pv_data );
147 /* CMD: DisConnect --------------------------------*/
148 else if( DRD64_COMMAND_DISCONNECT == p_phead->dw_command ) {
149 i_result = Drd64_Marshald_Cmd_DisConnect( i_recv_id, p_phead, pv_data );
151 /* CMD: Attach Request ---------------------------*/
152 else if( DRD64_COMMAND_ATTACH_REQUEST == p_phead->dw_command ) {
153 i_result = Drd64_Marshald_Cmd_AttachRequest(
154 i_recv_id, p_phead, pv_data, p_marshald );
156 /* CMD: Attach Link ------------------------------*/
157 else if( DRD64_COMMAND_ATTACH_LINK == p_phead->dw_command ) {
158 i_result = Drd64_Marshald_Cmd_AttachLink(
159 i_recv_id, p_phead, pv_data, p_marshald );
161 /* CMD: Attach Report -----------------------------*/
162 else if( DRD64_COMMAND_ATTACH_REPORT == p_phead->dw_command ) {
163 i_result = Drd64_Marshald_Cmd_AttachReport(
164 i_recv_id, p_phead, pv_data, p_marshald );
166 else if( DRD64_COMMAND_DETACH == p_phead->dw_command ) {
167 i_result = Drd64_Marshald_Cmd_Detach(
168 i_recv_id, p_phead, pv_data, p_marshald );
170 else if( DRD64_COMMAND_EXIT == p_phead->dw_command ) {
172 else if( DRD64_COMMAND_DEBUGD_BOOTINFO == p_phead->dw_command ) {
173 i_result = Drd64_Marshald_Msg_DebugdBootInfo(
174 i_recv_id, p_phead, pv_data, p_marshald );
178 /* Phase 3 : Result Proc. =======================*/
179 if( DRD64_MARSHALD_DISPATCH_RESULT_RESTART == i_result ) {
180 if( -1 < p_phead->i_rid_resume ) {
181 p_recv_parent = Drd64_Server_RecvStatus_GetRecvStatus(
182 p_phead->i_rid_resume );
183 assert( NULL != p_recv_parent );
185 p_recv_parent->b_recv_status
186 = DRD64_SERVER_RECVSTATUS_STATUS_RESUME;
189 else if( DRD64_MARSHALD_DISPATCH_RESULT_POLL == i_result ) {
190 p_recv->b_recv_status = DRD64_SERVER_RECVSTATUS_STATUS_STOP;
194 if(( DRD64_MARSHALD_DISPATCH_RESULT_COMPLETE == i_result )
195 || ( DRD64_MARSHALD_DISPATCH_RESULT_RESTART == i_result )) {
196 Drd64_Server_RecvStatus_DeleteResumeChain( i_recv_id );
204 Drd64_Marshald_Dispatch_JudgePacket(
207 Drd64_Server_RecvStatus *p_recv,
208 Drd64_Marshald_MasterInformation *p_marshald )
212 Drd64_PacketHeader *p_phead;
213 Drd64_Server_RecvStatus *p_recv_new;
217 /* Judge 1: Receiving : Remain Bytes Receiving = 0x01 */
218 if( 0 < i_remainbytes )
219 { return DRD64_MARSHALD_DISPATCH_RESULT_RECEVING; }
220 /* Judge 2: Error: Connection Down or Close = 0x00 */
221 else if( 0 > i_remainbytes )
222 { return DRD64_MARSHALD_DISPATCH_RESULT_CLOSE; }
224 p_phead = (Drd64_PacketHeader *)p_recv->pv_buf;
225 assert( NULL != p_phead );
227 /* Check 1 : Header Check */
228 if( DRD64_PACKET_HEADER != p_phead->w_header )
229 { return DRD64_MARSHALD_DISPATCH_RESULT_CLOSE; }
231 /* Judge 3: Remain Packet Data? = 0x01 */
232 if(( DRD64_SERVER_RECVSTATUS_PHASE_HEADER == p_recv->i_read_phase ) &&
233 ( 0 < p_phead->i_datalen )) {
234 p_recv->i_read_phase = DRD64_SERVER_RECVSTATUS_PHASE_DATA;
236 /* Check BOF Attack */
237 if( DRD64_MAX_PACKET_DATA < p_phead->i_datalen )
238 { return DRD64_MARSHALD_DISPATCH_RESULT_CLOSE; }
239 p_recv->i_remain_bytes = p_phead->i_datalen;
241 return DRD64_MARSHALD_DISPATCH_RESULT_RECEVING;
244 /* Check 2: Standart Packet Header Check */
245 /* XXX : NO implement */
247 /* Check 4: Relay Debugd-Cmd Packet? */
249 /* Push Readed Command Packet for Resume Pool */
250 Drd64_Server_RecvStatus_DeleteSocketsChain( p_recv );
251 i_recv_id = Drd64_Server_RecvStatus_PushResumeChain(
252 i_fds, DRD64_MARSHALD_RECVSTATUS_UNITS );
254 { return DRD64_MARSHALD_DISPATCH_RESULT_CLOSE; } // XXX > error
256 p_recv_new = Drd64_Server_RecvStatus_GetRecvStatus( i_fds );
257 assert( NULL != p_recv_new );
259 Drd64_Server_RecvStatus_InitRecvStatus( p_recv_new, p_recv->i_fds_id );
260 Drd64_Server_RecvStatus_AddSocketsChain( p_recv_new );
261 Drd64_Server_RecvStatus_SetConnectionInfoPointer(
262 p_recv_new, p_recv->pv_cinfo_connection );
264 /* Exec Packet by Command-Code */
265 i_result = Drd64_Marshald_Dispatch_ExecPacket(
266 i_recv_id, p_recv, p_marshald );
273 Drd64_Marshald_Dispatch_ExecResumeRecvStatus(
274 Drd64_Marshald_MasterInformation *p_marshald )
277 Drd64_Server_RecvStatus *p_recv;
279 DRD64_LOG_DEBUG(" [DEBUG] Dispatch : Exec Resume RecvStatus Start");
281 p_recv = Drd64_Server_RecvStatus_GetResumeChainStart();
282 while( NULL != p_recv ) {
283 if( DRD64_SERVER_RECVSTATUS_STATUS_RESUME
284 == p_recv->b_recv_status ) {
286 DRD64_LOG_DEBUG(" [DEBUG] Dispatch : Do Resume RecvStatus");
287 i_result = Drd64_Marshald_Dispatch_ExecPacket(
288 p_recv->i_recvstatus_id, p_recv, p_marshald );
290 /* XXX : support for disconnect (CLOSE) */
291 /* 0x00 = Judge 1 : Disconnect ( Others Packet ) */
292 if( DRD64_MARSHALD_DISPATCH_RESULT_CLOSE == i_result ) {
293 Drd64_Marshald_Dispatch_CloseSocket( p_recv->i_fds_id );
295 else if( DRD64_MARSHALD_DISPATCH_RESULT_RESTART == i_result ) {
300 if( NULL != p_recv ) {
301 p_recv = (Drd64_Server_RecvStatus *)p_recv->pv_recv_next;
304 p_recv = Drd64_Server_RecvStatus_GetResumeChainStart();
308 DRD64_LOG_DEBUG(" [DEBUG] Dispatch : Exec Resume RecvStatus Ended");
314 Drd64_Marshald_Dispatch_Polling(
315 Drd64_Marshald_MasterInformation *p_marshald )
328 Drd64_Server_RecvStatus *p_recv;
329 struct timeval tmval;
331 FD_ZERO( &g_fds_orig );
332 FD_SET( p_marshald->i_socket_local, &g_fds_orig );
333 FD_SET( p_marshald->i_socket_inet, &g_fds_orig );
335 if( p_marshald->i_socket_local > p_marshald->i_socket_inet )
336 { i_selects_base = p_marshald->i_socket_local + 1; }
338 { i_selects_base = p_marshald->i_socket_inet + 1; }
339 i_selects_max = i_selects_base;
342 tmval.tv_usec = 5000;
345 /* Phase 1: Packet & Signal Polling */
346 memcpy( &fds_now, &g_fds_orig, sizeof( struct fd_set ) );
347 i_selects = select( i_selects_max, &fds_now, NULL, NULL, &tmval );
349 /* Phase 2: Receive Packet */
350 if( 0 < i_selects ) {
352 /* Server Socket from Local */
353 if( FD_ISSET( p_marshald->i_socket_local, &fds_now )) {
354 Drd64_Marshald_Dispatch_OpenSocket(
355 p_marshald->i_socket_local );
359 /* Server Socket from INet */
360 if( FD_ISSET( p_marshald->i_socket_inet, &fds_now )) {
361 Drd64_Marshald_Dispatch_OpenSocket(
362 p_marshald->i_socket_inet );
366 i_resume_flag = 0x00;
367 p_recv = Drd64_Server_RecvStatus_GetSocketsChainStart();
368 while(( NULL != p_recv ) && ( 0 < i_selects )) {
370 i_socket = p_recv->i_fds_id;
372 if( FD_ISSET( i_socket, &fds_now ) ) {
374 assert( DRD64_SERVER_RECVSTATUS_STATUS_READ
375 == p_recv->b_recv_status );
377 /*i_err = Drd64_Server_RecvSocket_SocketRead_Cert(
378 i_socket, &i_pid );*/
379 i_err = Drd64_Server_RecvSocket_SocketRead( i_socket );
380 DRD64_DEBUG_PRINT("SocketRead",i_err,"FD",i_socket,"DestPid",i_pid);
384 i_result = Drd64_Marshald_Dispatch_JudgePacket(
385 i_socket, i_err, p_recv, &drd64_marshald_info );
387 /* 0x00 = Judge 1 : Disconnect ( Others Packet ) */
388 if( DRD64_MARSHALD_DISPATCH_RESULT_CLOSE == i_result ) {
389 Drd64_Marshald_Dispatch_CloseSocket( i_socket );
391 else if( DRD64_MARSHALD_DISPATCH_RESULT_RESTART
393 { i_resume_flag = 0x01; }
394 /* 0x01 = Judge 1 : Reading Next */
398 p_recv = (Drd64_Server_RecvStatus *)p_recv->pv_recv_next;
401 /* Check Restart Packet (RecvStatus) */
402 if( 0x00 != i_resume_flag ) {
403 Drd64_Marshald_Dispatch_ExecResumeRecvStatus(
404 &drd64_marshald_info );
408 i_selects_last = Drd64_Server_RecvStatus_GetRecvStatMax();
409 if( i_selects_last > i_selects_base )
410 { i_selects_max = i_selects_last; }
412 { i_selects_max = i_selects_base; }
415 /* Phase 3: Check TimeOut Resume Packet */
417 /* Phase 4: Signal Check & Proc */
424 /* EOF of drd64_.c ----------------------------------- */