OSDN Git Service

*** empty log message ***
[drdeamon64/drdeamon64.git] / deamon / drd64_server_recvstatus.c
1 /*DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64
2
3                          D r . D e a m o n  6 4
4                         for INTEL64(R), AMD64(R)
5         
6    Copyright(C) 2007-2009 Koine Yuusuke(koinec). All rights reserved.
7
8 Redistribution and use in source and binary forms, with or without
9 modification, are permitted provided that the following conditions are met:
10
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.
16
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.
28
29 DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64DrDeAmOn64*/
30
31 /* File Info -----------------------------------------------------------
32 File: drd64_.c
33 Function: 
34 Comment: 
35 ----------------------------------------------------------------------*/
36
37 #include"drd64_server.h"
38 #define DRD64_SRC_SERVER_RECVSTATUS
39 #include"drd64_server_recvstatus.h"
40
41 Drd64_Server_RecvStatus         **gpp_recvstat;
42 Drd64_Server_RecvStatus         *gp_recvalloc;
43 int                                                     gi_recvalloc_max;
44 int                                                     gi_recvalloc_now;
45 int                                                     gi_recvstat_max;
46 Drd64_Server_RecvStatus         *gp_recv_resume_start;
47 Drd64_Server_RecvStatus         *gp_recv_resume_end;
48 int                                                     gi_recv_resume_max;
49
50
51 int
52         Drd64_Server_RecvStatus_FreeRecvStatus_All(
53                 void )
54 {
55         int             i_cnt;
56
57         for( i_cnt = 0; i_cnt < gi_recvalloc_max; i_cnt++ )     {
58                         free( (gp_recvalloc + i_cnt)->pv_buf );
59                         (gp_recvalloc + i_cnt)->pv_buf  = NULL;
60         }
61
62         free( gp_recvalloc );
63         gi_recvalloc_max        = 0;
64         gi_recvalloc_now        = 0;
65         gp_recvalloc            = NULL;
66
67         free( gpp_recvstat );
68         gpp_recvstat            = NULL;
69
70         return;
71 }
72
73
74 Drd64_Server_RecvStatus *
75         Drd64_Server_RecvStatus_AllocRecvStatus_Unit(
76                 int             i_alloc_units )
77 {
78         int             i_cnt;
79         int             i_init_start_id;
80         int             i_init_end_id;
81         void    *pv_temp;
82         Drd64_Server_RecvStatus         *p_recvs;
83
84         p_recvs = NULL;
85
86         if( 0 == gi_recvalloc_max )     {
87                 p_recvs = (Drd64_Server_RecvStatus *)malloc(
88                                                 sizeof( Drd64_Server_RecvStatus )
89                                                         * i_alloc_units );
90
91                 i_init_start_id         = 0;
92                 i_init_end_id           = i_alloc_units;
93         }
94         else    {
95                 p_recvs = realloc( gp_recvalloc,
96                                         gi_recvalloc_max + i_alloc_units );
97
98                 i_init_start_id         = gi_recvalloc_max;
99                 i_init_end_id           = gi_recvalloc_max + i_alloc_units;
100         }
101         
102         if( NULL == p_recvs )   {
103                 return NULL;
104         }
105
106
107         for( i_cnt = i_init_start_id; i_cnt < i_init_end_id; i_cnt++ )  {
108                 memset( (p_recvs + i_cnt), 0x00, 
109                                         sizeof( Drd64_Server_RecvStatus ) );
110                 (p_recvs + i_cnt)->i_recvstatus_id      = -1;
111                 (p_recvs + i_cnt)->i_fds_id                     = -1;
112
113                 pv_temp = malloc( DRD64_MAX_PACKET_LENGTH );
114                 if( NULL == pv_temp )   { break; }
115                 (p_recvs + i_cnt)->pv_buf               = pv_temp;
116                 gi_recvalloc_max++;
117         }
118
119         if( gi_recvalloc_max == i_init_start_id )       {
120                 return NULL;
121         }
122
123         gp_recvalloc    = p_recvs;
124         return p_recvs;
125 }
126
127
128 EXTERN_SERVER_RECVSTATUS
129 int
130         Drd64_Server_RecvStatus_Init(
131                 int i_alloc_units )
132 {
133         Drd64_Server_RecvStatus *p_recvs;
134
135         /* Alloc RecvStatus Struct Management Area --- */
136         gpp_recvstat
137                 = (Drd64_Server_RecvStatus **)malloc(
138                                         sizeof( Drd64_Server_RecvStatus *)
139                                                 * FD_SETSIZE * DRD64_PACKET_MAX_MULTIPLE);
140         if( NULL == gpp_recvstat )      { return 0x01; }
141
142         memset( gpp_recvstat, 0x00, 
143                                         sizeof( Drd64_Server_RecvStatus *)
144                                                 * FD_SETSIZE * DRD64_PACKET_MAX_MULTIPLE );
145
146         gi_recvstat_max = 0;
147         
148         /* Alloc RecvStatus Area ( with Packet Data buffer ) ---*/
149         p_recvs = Drd64_Server_RecvStatus_AllocRecvStatus_Unit( i_alloc_units );
150         if( NULL == p_recvs )   {
151                 Drd64_Server_RecvStatus_FreeRecvStatus_All();
152                 return 0x02;
153         }
154
155         gp_recvalloc    = p_recvs;
156         gi_recvalloc_now        = 0;
157
158         gp_recv_resume_start    = NULL;
159         gi_recv_resume_max              = FD_SETSIZE;
160
161         return 0x00;
162 }
163
164
165 EXTERN_SERVER_RECVSTATUS
166 int
167         Drd64_Server_RecvStatus_Term(
168                 void )
169 {
170         Drd64_Server_RecvStatus_FreeRecvStatus_All();
171
172         return;
173 }
174
175
176 EXTERN_SERVER_RECVSTATUS
177 Drd64_Server_RecvStatus *
178         Drd64_Server_RecvStatus_AllocRecvStatus(
179                 int     i_fds,
180                 int     i_alloc_units )
181 {
182         int             i_cnt;
183         Drd64_Server_RecvStatus         *p_recv;
184         Drd64_Server_RecvStatus         *p_temp;
185
186         p_recv  = NULL;
187
188         /* Check No-Use RecvStatus --- */
189         if( gi_recvalloc_now >= gi_recvalloc_max )      {
190                 /* Search No-Use RecvStatus --- */
191                 for( i_cnt = 0; i_cnt < gi_recvalloc_max; i_cnt++ )             {
192                         if( -1 == (gp_recvalloc + i_cnt)->i_recvstatus_id )     {
193                                 p_recv  = (gp_recvalloc + i_cnt);
194                                 break;
195                         }
196                 }
197
198                 /* Realloc RecvStatus --- */
199                 if( NULL == p_recv )    {
200                         p_temp
201                                 = Drd64_Server_RecvStatus_AllocRecvStatus_Unit(
202                                                 i_alloc_units );
203                         if( NULL == p_temp )    { return NULL; }
204
205                         gp_recvalloc    = p_temp;
206                         p_recv  = gp_recvalloc + gi_recvalloc_now++;
207                 }
208         }
209         else    {
210                 p_recv  = gp_recvalloc + gi_recvalloc_now++;
211         }
212
213         /* Set RecvStatus Init. Param ---*/
214         p_recv->i_recvstatus_id = i_fds;
215         p_recv->i_fds_id                = i_fds;
216         *(gpp_recvstat + i_fds) = p_recv;
217
218
219
220         if( i_fds + 1 > gi_recvstat_max )
221                 { gi_recvstat_max       = i_fds + 1; }
222
223         return p_recv;
224 }
225
226
227 EXTERN_SERVER_RECVSTATUS
228 void
229         Drd64_Server_RecvStatus_FreeRecvStatus(
230                 int i_fds )
231 {
232         int             i_cnt;
233         Drd64_Server_RecvStatus *p_recv_now;
234         Drd64_Server_RecvStatus *p_recv_temp;
235
236         p_recv_now      = *(gpp_recvstat + i_fds);
237
238         if( NULL != p_recv_now )        {
239                 *(gpp_recvstat + i_fds) = NULL;
240
241                 if( i_fds + 1 == gi_recvstat_max )      {
242                         for( i_cnt = i_fds+1; i_cnt > 0; i_cnt-- )              {
243                                 p_recv_temp     = *(gpp_recvstat + i_cnt);
244                                 if( NULL != p_recv_temp )       {
245                                         gi_recvstat_max = i_cnt + 1;
246                                         break;
247                                 }
248                         }
249
250                         if( 0 == i_cnt ) { gi_recvstat_max      = 0; }
251                 }
252
253                 p_recv_now->i_recvstatus_id     = -1;
254                 p_recv_now->i_fds_id            = -1;
255         }
256         
257         return;
258 }
259
260
261 EXTERN_SERVER_RECVSTATUS
262 int
263         Drd64_Server_RecvStatus_PushResumeChain(
264                 int             i_fds,
265                 int             i_alloc_units )
266 {
267         int             i_cnt;
268         int             i_recv_id;
269         Drd64_Server_RecvStatus         *p_recv_self;
270         Drd64_Server_RecvStatus         *p_recv_new;
271         Drd64_Server_RecvStatus         *p_recv_before;
272
273         i_recv_id       = -1;
274
275         /* Get Self RecvStatus --- */
276         p_recv_self     = *(gpp_recvstat + i_fds);
277         if( NULL == p_recv_self )       {
278                 return -1;
279         }
280
281         /* Get New RecvStatus --- */
282         p_recv_new
283                 = Drd64_Server_RecvStatus_AllocRecvStatus(
284                                         i_fds, i_alloc_units );
285         if( NULL == p_recv_new )        {
286                 return -2;
287         }
288
289         /* Push & Chain RecvStatus ---*/
290         /* new */
291         if( NULL == gp_recv_resume_start )      {
292                 gp_recv_resume_start            = p_recv_self;
293                 gp_recv_resume_end                      = p_recv_self;
294                 p_recv_self->pv_recv_before     = NULL;
295                 p_recv_self->pv_recv_next       = NULL;
296                 i_cnt = gi_recv_resume_max;
297         }
298         else    {
299                 i_cnt   = FD_SETSIZE;
300                 while(( NULL != *(gpp_recvstat + i_cnt) )
301                                         && ( i_cnt < gi_recv_resume_max ))      { i_cnt++; }
302                 assert( NULL == *(gpp_recvstat + i_cnt) );
303                 
304                 p_recv_before   = gp_recv_resume_end;
305                 assert( NULL != p_recv_before );
306                 
307                 p_recv_self->pv_recv_before     = (void *)p_recv_before;
308                 p_recv_self->pv_recv_next       = (void *)p_recv_before->pv_recv_next;
309                 p_recv_before->pv_recv_next     = (void *)p_recv_self;
310                 gp_recv_resume_end                      = p_recv_self;
311
312         }
313
314         i_recv_id       = i_cnt;
315         p_recv_self->i_recvstatus_id    = i_cnt;
316         *(gpp_recvstat + p_recv_self->i_recvstatus_id)  = p_recv_self;
317         if( gi_recv_resume_max == i_cnt )       {
318                 gi_recv_resume_max++;
319         }
320         
321         return i_recv_id;
322 }
323
324
325 EXTERN_SERVER_RECVSTATUS
326 int
327         Drd64_Server_RecvStatus_DeleteResumeChain(
328                 int             i_recv_id )
329 {
330         Drd64_Server_RecvStatus *p_recv_self;
331         Drd64_Server_RecvStatus *p_recv_before;
332         Drd64_Server_RecvStatus *p_recv_next;
333
334         p_recv_self     = *(gpp_recvstat + i_recv_id);
335         if( NULL == p_recv_self )       {
336                 return 0x01;
337         }       
338
339         p_recv_before   = (Drd64_Server_RecvStatus *)p_recv_self->pv_recv_before;
340         p_recv_next             = (Drd64_Server_RecvStatus *)p_recv_self->pv_recv_next;
341
342         if( NULL != p_recv_before )     {
343                 p_recv_before->pv_recv_next     = (void *)p_recv_next;
344         }
345
346         if( NULL != p_recv_next )       {
347                 p_recv_next->pv_recv_before     = (void *)p_recv_before;
348         }
349
350         if( p_recv_self->i_recvstatus_id == (gi_recv_resume_max - 1) )  {
351                 gi_recv_resume_max--;
352         }
353
354         if( FD_SETSIZE == gi_recv_resume_max )  {
355                 gp_recv_resume_start    = NULL;
356                 gp_recv_resume_end              = NULL;
357         }
358
359         *(gpp_recvstat + i_recv_id)             = NULL;
360         p_recv_self->pv_recv_before             = NULL;
361         p_recv_self->pv_recv_next               = NULL;
362         
363         p_recv_self->i_recvstatus_id    = -1;
364         p_recv_self->i_fds_id                   = -1;
365
366         return 0x00;
367 }
368
369
370 EXTERN_SERVER_RECVSTATUS
371 void
372         Drd64_Server_RecvStatus_InitRecvStatus(
373                 Drd64_Server_RecvStatus *p_recv )
374 {
375         assert( NULL != p_recv );
376
377         p_recv->i_read_phase    = DRD64_SERVER_RECVSTATUS_PHASE_HEADER;
378         p_recv->b_recv_status   = DRD64_SERVER_RECVSTATUS_STATUS_READ;
379         p_recv->i_remain_bytes  = sizeof( Drd64_PacketHeader );
380         p_recv->pv_resume               = p_recv->pv_buf;
381
382         return;
383 }
384
385
386 EXTERN_SERVER_RECVSTATUS
387 Drd64_Server_RecvStatus *
388         Drd64_Server_RecvStatus_GetRecvStatus(
389                 int             i_recv_id )
390 {
391         return *(gpp_recvstat + i_recv_id);
392 }
393
394
395 EXTERN_SERVER_RECVSTATUS
396 int
397         Drd64_Server_RecvStatus_GetSocketID(
398                 int             i_recv_id )
399 {
400         Drd64_Server_RecvStatus         *p_recv;
401         p_recv  = *(gpp_recvstat + i_recv_id);
402         
403         if( NULL == p_recv )    { return -1; }
404
405         return p_recv->i_fds_id;
406 }
407
408
409 EXTERN_SERVER_RECVSTATUS
410 int
411         Drd64_Server_RecvStatus_GetPacketStatus(
412                 int             i_recv_id )
413 {
414         Drd64_Server_RecvStatus         *p_recv;
415         p_recv  = *(gpp_recvstat + i_recv_id);
416         
417         if( NULL == p_recv )    { return -1; }
418
419         return p_recv->b_recv_status;
420 }
421
422
423 EXTERN_SERVER_RECVSTATUS
424 int
425         Drd64_Server_RecvStatus_GetCmdStatus(
426                 int             i_recv_id )
427 {
428         Drd64_Server_RecvStatus         *p_recv;
429         p_recv  = *(gpp_recvstat + i_recv_id);
430         
431         if( NULL == p_recv )    { return -1; }
432
433         return p_recv->i_command_status;
434 }
435
436
437 EXTERN_SERVER_RECVSTATUS
438 int
439         Drd64_Server_RecvStatus_SetCmdStatus(
440                 int             i_recv_id,
441                 int             i_command_status )
442 {
443         Drd64_Server_RecvStatus         *p_recv;
444         p_recv  = *(gpp_recvstat + i_recv_id);
445         
446         if( NULL == p_recv )    { return -1; }
447
448         p_recv->i_command_status        = i_command_status;
449
450         return p_recv->i_command_status;
451 }
452
453
454 EXTERN_SERVER_RECVSTATUS
455 int
456         Drd64_Server_RecvStatus_GetRecvStatMax(
457                 void )
458 {
459         return gi_recvstat_max;
460 }
461
462
463 EXTERN_SERVER_RECVSTATUS
464 Drd64_Server_RecvStatus *
465         Drd64_Server_RecvStatus_GetResumeStart(
466                 void )
467 {
468         return gp_recv_resume_start;
469 }
470
471 /* EOF of drd64_.c ----------------------------------- */