aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristian Grothoff <christian@grothoff.org>2011-08-15 12:30:49 +0000
committerChristian Grothoff <christian@grothoff.org>2011-08-15 12:30:49 +0000
commit35430039ae033e8f4ef5d29feb132c1195114aa4 (patch)
treec440174afae8ad1e23f843810714712cf7f2ecb7
parent7cc66758e12f3e6809dec47e4a9119db4d7cb10f (diff)
downloadgnunet-gtk-35430039ae033e8f4ef5d29feb132c1195114aa4.tar.gz
gnunet-gtk-35430039ae033e8f4ef5d29feb132c1195114aa4.zip
some code cleanup
-rw-r--r--src/lib/eventloop.c133
1 files changed, 72 insertions, 61 deletions
diff --git a/src/lib/eventloop.c b/src/lib/eventloop.c
index 24e8cba3..19e0647c 100644
--- a/src/lib/eventloop.c
+++ b/src/lib/eventloop.c
@@ -26,6 +26,14 @@
26#include "gnunet_gtk.h" 26#include "gnunet_gtk.h"
27 27
28 28
29/**
30 * Initial size of our poll array cache.
31 *
32 * TODO: get some statistics, find the maximum number of fds ever
33 * polled during normal gnunet-gtk operation, and set this to that number.
34 */
35#define INITIAL_POLL_ARRAY_SIZE 30
36
29/** 37/**
30 * Main context for our event loop. 38 * Main context for our event loop.
31 */ 39 */
@@ -92,7 +100,6 @@ struct GNUNET_GTK_MainLoop
92 */ 100 */
93 gint max_priority; 101 gint max_priority;
94 102
95
96#if WINDOWS 103#if WINDOWS
97 /** 104 /**
98 * Array to hold pipe handles during a select() call 105 * Array to hold pipe handles during a select() call
@@ -206,6 +213,21 @@ gnunet_gtk_dispatch_task (void *cls,
206} 213}
207 214
208 215
216/**
217 * Change the size of the cached poll array to the given value.
218 *
219 * @param ml main loop context with the cached poll array
220 * @param new_size desired size of the cached poll array
221 */
222static void
223resize_cached_poll_array (struct GNUNET_GTK_MainLoop *ml,
224 guint new_size)
225{
226 ml->cached_poll_array = g_new (GPollFD, new_size);
227 ml->cached_poll_array_size = new_size;
228}
229
230
209#ifndef FD_COPY 231#ifndef FD_COPY
210#define FD_COPY(s, d) (memcpy ((d), (s), sizeof (fd_set))) 232#define FD_COPY(s, d) (memcpy ((d), (s), sizeof (fd_set)))
211#endif 233#endif
@@ -234,11 +256,9 @@ gnunet_gtk_select (void *cls,
234 struct GNUNET_GTK_MainLoop *ml = cls; 256 struct GNUNET_GTK_MainLoop *ml = cls;
235 int max_nfds; 257 int max_nfds;
236 gint poll_result; 258 gint poll_result;
237 GPollFD *gfds;
238 gint delay; 259 gint delay;
239 guint i; 260 guint i;
240 guint fd_counter = 0; 261 guint fd_counter = 0;
241 guint allocated_nfds;
242 guint need_gfds; 262 guint need_gfds;
243 fd_set aread; 263 fd_set aread;
244 fd_set awrite; 264 fd_set awrite;
@@ -292,24 +312,17 @@ gnunet_gtk_select (void *cls,
292 if (efds != NULL) 312 if (efds != NULL)
293 max_nfds = GNUNET_MAX (max_nfds, efds->nsds); 313 max_nfds = GNUNET_MAX (max_nfds, efds->nsds);
294 314
295 allocated_nfds = ml->cached_poll_array_size; 315 ml->cached_poll_array_size = ml->cached_poll_array_size;
296 gfds = ml->cached_poll_array; 316 if (ml->cached_poll_array_size == 0)
297 if (allocated_nfds == 0) 317 resize_cached_poll_array (ml, INITIAL_POLL_ARRAY_SIZE);
298 {
299 /* TODO: get some statistics, find the maximum number of fds ever
300 * polled during normal gnunet-gtk operation, and set this to that number.
301 */
302 ml->cached_poll_array = gfds = g_new (GPollFD, 30);
303 ml->cached_poll_array_size = allocated_nfds = 30;
304 }
305 318
306 while (1) 319 while (1)
307 {
308 fd_counter = 0;
309#if !WINDOWS
310 gboolean need_realloc = FALSE;
311 for (i = 0; !need_realloc && i < max_nfds; i += 1)
312 { 320 {
321 fd_counter = 0;
322#if !WINDOWS
323 gboolean need_realloc = FALSE;
324 for (i = 0; !need_realloc && i < max_nfds; i += 1)
325 {
313 int isset[3]; 326 int isset[3];
314 327
315 isset[0] = (rfds == NULL) ? 0 : FD_ISSET (i, &rfds->sds); 328 isset[0] = (rfds == NULL) ? 0 : FD_ISSET (i, &rfds->sds);
@@ -317,23 +330,22 @@ gnunet_gtk_select (void *cls,
317 isset[2] = (efds == NULL) ? 0 : FD_ISSET (i, &efds->sds); 330 isset[2] = (efds == NULL) ? 0 : FD_ISSET (i, &efds->sds);
318 if (!isset[0] && !isset[1] && !isset[2]) 331 if (!isset[0] && !isset[1] && !isset[2])
319 continue; 332 continue;
320 if (fd_counter >= allocated_nfds) 333 if (fd_counter >= ml->cached_poll_array_size)
321 { 334 {
322 need_realloc = TRUE; 335 need_realloc = TRUE;
323 break; 336 break;
324 } 337 }
325 gfds[fd_counter].fd = i; 338 ml->cached_poll_array[fd_counter].fd = i;
326 gfds[fd_counter].events = (isset[0] ? G_IO_IN | G_IO_HUP | G_IO_ERR : 0) 339 ml->cached_poll_array[fd_counter].events = (isset[0] ? G_IO_IN | G_IO_HUP | G_IO_ERR : 0)
327 | (isset[1] ? G_IO_OUT | G_IO_ERR : 0) | (isset[2] ? G_IO_ERR : 0); 340 | (isset[1] ? G_IO_OUT | G_IO_ERR : 0) | (isset[2] ? G_IO_ERR : 0);
328 fd_counter += 1; 341 fd_counter += 1;
329 } 342 }
330 if (need_realloc) 343 if (need_realloc)
331 { 344 {
332 ml->cached_poll_array = gfds = g_renew (GPollFD, gfds, ml->cached_poll_array_size * 2); 345 resize_cached_poll_array (ml, ml->cached_poll_array_size * 2);
333 ml->cached_poll_array_size = allocated_nfds = ml->cached_poll_array_size * 2; 346 fd_counter = 0;
334 fd_counter = 0; 347 need_realloc = FALSE;
335 need_realloc = FALSE; 348 }
336 }
337 else 349 else
338 break; 350 break;
339#else 351#else
@@ -343,13 +355,13 @@ gnunet_gtk_select (void *cls,
343 + (rfds == NULL ? 0 : GNUNET_CONTAINER_slist_count (rfds->handles)) 355 + (rfds == NULL ? 0 : GNUNET_CONTAINER_slist_count (rfds->handles))
344 + (wfds == NULL ? 0 : 1) 356 + (wfds == NULL ? 0 : 1)
345 + 1; 357 + 1;
346 if (need_nfds >= allocated_nfds) 358 if (need_nfds >= ml->cached_poll_array_size)
347 { 359 {
348 /* Since there are also gmainloop's own fds, just need_nfds won't be 360 /* Since there are also gmainloop's own fds, just need_nfds won't be
349 * enough, so make it twice as long. 361 * enough, so make it twice as long.
350 */ 362 */
351 ml->cached_poll_array = gfds = g_renew (GPollFD, gfds, need_nfds * 2); 363 ml->cached_poll_array = ml->cached_poll_array = g_renew (GPollFD, ml->cached_poll_array, need_nfds * 2);
352 ml->cached_poll_array_size = allocated_nfds = need_nfds * 2; 364 ml->cached_poll_array_size = ml->cached_poll_array_size = need_nfds * 2;
353 } 365 }
354 if (ml->read_array_length < GNUNET_CONTAINER_slist_count (rfds->handles)) 366 if (ml->read_array_length < GNUNET_CONTAINER_slist_count (rfds->handles))
355 { 367 {
@@ -374,20 +386,20 @@ gnunet_gtk_select (void *cls,
374#if DEBUG_NETWORK 386#if DEBUG_NETWORK
375 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Adding the pipe's 0x%x overlapped event to the array as %d\n", fh->h, nhandles); 387 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Adding the pipe's 0x%x overlapped event to the array as %d\n", fh->h, nhandles);
376#endif 388#endif
377 gfds[fd_counter].fd = (intptr_t) fh->oOverlapRead->hEvent; 389 ml->cached_poll_array[fd_counter].fd = (intptr_t) fh->oOverlapRead->hEvent;
378 /* On W32 .events makes no sense - g_poll will just OR its 390 /* On W32 .events makes no sense - g_poll will just OR its
379 * contents into .revents when the .fd event fires. 391 * contents into .revents when the .fd event fires.
380 * So we'll use it in the way that suits us the best. 392 * So we'll use it in the way that suits us the best.
381 */ 393 */
382 gfds[fd_counter].events = G_IO_IN; 394 ml->cached_poll_array[fd_counter].events = G_IO_IN;
383 fd_counter += 1; 395 fd_counter += 1;
384 ml->read_array[read_handles] = fh; 396 ml->read_array[read_handles] = fh;
385 read_handles += 1; 397 read_handles += 1;
386 } 398 }
387 else 399 else
388 { 400 {
389 gfds[fd_counter].fd = (intptr_t) ml->hEventReadReady; 401 ml->cached_poll_array[fd_counter].fd = (intptr_t) ml->hEventReadReady;
390 gfds[fd_counter].events = G_IO_HUP; 402 ml->cached_poll_array[fd_counter].events = G_IO_HUP;
391 fd_counter += 1; 403 fd_counter += 1;
392 ml->read_array[read_handles] = fh; 404 ml->read_array[read_handles] = fh;
393 read_handles += 1; 405 read_handles += 1;
@@ -398,8 +410,8 @@ gnunet_gtk_select (void *cls,
398#if DEBUG_NETWORK 410#if DEBUG_NETWORK
399 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Adding the read ready event to the array as %d\n", nhandles); 411 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Adding the read ready event to the array as %d\n", nhandles);
400#endif 412#endif
401 gfds[fd_counter].fd = (intptr_t) ml->hEventReadReady; 413 ml->cached_poll_array[fd_counter].fd = (intptr_t) ml->hEventReadReady;
402 gfds[fd_counter].events = G_IO_IN; 414 ml->cached_poll_array[fd_counter].events = G_IO_IN;
403 fd_counter += 1; 415 fd_counter += 1;
404 ml->read_array[read_handles] = fh; 416 ml->read_array[read_handles] = fh;
405 read_handles += 1; 417 read_handles += 1;
@@ -416,8 +428,8 @@ gnunet_gtk_select (void *cls,
416 } 428 }
417 if (wfds != NULL && GNUNET_CONTAINER_slist_count (wfds->handles) > 0) 429 if (wfds != NULL && GNUNET_CONTAINER_slist_count (wfds->handles) > 0)
418 { 430 {
419 gfds[fd_counter].fd = (intptr_t) ml->hEventPipeWrite; 431 ml->cached_poll_array[fd_counter].fd = (intptr_t) ml->hEventPipeWrite;
420 gfds[fd_counter].events = G_IO_OUT; 432 ml->cached_poll_array[fd_counter].events = G_IO_OUT;
421 always_ready_write_fd = fd_counter; 433 always_ready_write_fd = fd_counter;
422 fd_counter += 1; 434 fd_counter += 1;
423 } 435 }
@@ -449,8 +461,8 @@ gnunet_gtk_select (void *cls,
449#if DEBUG_NETWORK 461#if DEBUG_NETWORK
450 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Adding the socket read event to the array as %d\n", fd_counter); 462 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Adding the socket read event to the array as %d\n", fd_counter);
451#endif 463#endif
452 gfds[fd_counter].fd = (intptr_t) ml->hEventRead; 464 ml->cached_poll_array[fd_counter].fd = (intptr_t) ml->hEventRead;
453 gfds[fd_counter].events = G_IO_IN; 465 ml->cached_poll_array[fd_counter].events = G_IO_IN;
454 for (i = 0; i < rfds->sds.fd_count; i++) 466 for (i = 0; i < rfds->sds.fd_count; i++)
455 WSAEventSelect (rfds->sds.fd_array[i], ml->hEventRead, FD_ACCEPT | FD_READ | FD_CLOSE); 467 WSAEventSelect (rfds->sds.fd_array[i], ml->hEventRead, FD_ACCEPT | FD_READ | FD_CLOSE);
456 fd_counter += 1; 468 fd_counter += 1;
@@ -462,8 +474,8 @@ gnunet_gtk_select (void *cls,
462#if DEBUG_NETWORK 474#if DEBUG_NETWORK
463 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Adding the socket write event to the array as %d\n", fd_counter); 475 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Adding the socket write event to the array as %d\n", fd_counter);
464#endif 476#endif
465 gfds[fd_counter].fd = (intptr_t) ml->hEventWrite; 477 ml->cached_poll_array[fd_counter].fd = (intptr_t) ml->hEventWrite;
466 gfds[fd_counter].events = G_IO_OUT; 478 ml->cached_poll_array[fd_counter].events = G_IO_OUT;
467 for (i = 0; i < wfds->sds.fd_count; i++) 479 for (i = 0; i < wfds->sds.fd_count; i++)
468 { 480 {
469 DWORD error; 481 DWORD error;
@@ -487,8 +499,8 @@ gnunet_gtk_select (void *cls,
487#if DEBUG_NETWORK 499#if DEBUG_NETWORK
488 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Adding the socket error event to the array as %d\n", fd_counter); 500 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Adding the socket error event to the array as %d\n", fd_counter);
489#endif 501#endif
490 gfds[fd_counter].fd = (intptr_t) ml->hEventException; 502 ml->cached_poll_array[fd_counter].fd = (intptr_t) ml->hEventException;
491 gfds[fd_counter].events = G_IO_ERR; 503 ml->cached_poll_array[fd_counter].events = G_IO_ERR;
492 for (i = 0; i < efds->sds.fd_count; i++) 504 for (i = 0; i < efds->sds.fd_count; i++)
493 WSAEventSelect (efds->sds.fd_array[i], ml->hEventException, FD_OOB | FD_CLOSE); 505 WSAEventSelect (efds->sds.fd_array[i], ml->hEventException, FD_OOB | FD_CLOSE);
494 fd_counter += 1; 506 fd_counter += 1;
@@ -500,12 +512,11 @@ gnunet_gtk_select (void *cls,
500 socks = sock_read + sock_write + sock_err; 512 socks = sock_read + sock_write + sock_err;
501 513
502 g_main_context_prepare (ml->gmc, &ml->max_priority); 514 g_main_context_prepare (ml->gmc, &ml->max_priority);
503 while (allocated_nfds < (need_gfds = g_main_context_query (ml->gmc, 515 while (ml->cached_poll_array_size < (need_gfds = g_main_context_query (ml->gmc,
504 ml->max_priority, &delay, &gfds[fd_counter], allocated_nfds - fd_counter))) 516 ml->max_priority, &delay, &ml->cached_poll_array[fd_counter], ml->cached_poll_array_size - fd_counter)))
505 { 517 resize_cached_poll_array (ml,
506 ml->cached_poll_array = gfds = g_renew (GPollFD, gfds, allocated_nfds - fd_counter + need_gfds); 518 ml->cached_poll_array_size - fd_counter + need_gfds);
507 ml->cached_poll_array_size = allocated_nfds = allocated_nfds - fd_counter + need_gfds; 519
508 }
509 ml->poll_array_active = fd_counter + need_gfds; 520 ml->poll_array_active = fd_counter + need_gfds;
510 521
511 if (timeout.rel_value != GNUNET_TIME_UNIT_FOREVER_REL.rel_value) 522 if (timeout.rel_value != GNUNET_TIME_UNIT_FOREVER_REL.rel_value)
@@ -528,7 +539,7 @@ gnunet_gtk_select (void *cls,
528 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "We have %d of our FDs and %d of GMC ones, going to wait %6dms\n", fd_counter, need_gfds, delay); 539 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "We have %d of our FDs and %d of GMC ones, going to wait %6dms\n", fd_counter, need_gfds, delay);
529#endif 540#endif
530 541
531 poll_result = g_poll (gfds, fd_counter + need_gfds, delay); 542 poll_result = g_poll (ml->cached_poll_array, fd_counter + need_gfds, delay);
532 543
533#if DEBUG_NETWORK 544#if DEBUG_NETWORK
534 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "g_poll returned : %d\n", poll_result); 545 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "g_poll returned : %d\n", poll_result);
@@ -539,7 +550,7 @@ gnunet_gtk_select (void *cls,
539 * from within a task (currently we're not in a task, but in a select() call, remember) 550 * from within a task (currently we're not in a task, but in a select() call, remember)
540 * Startup reason is used to pass the scheduler sanity check. 551 * Startup reason is used to pass the scheduler sanity check.
541 */ 552 */
542 if (TRUE == g_main_context_check (ml->gmc, ml->max_priority, &gfds[fd_counter], need_gfds)) 553 if (TRUE == g_main_context_check (ml->gmc, ml->max_priority, &ml->cached_poll_array[fd_counter], need_gfds))
543 GNUNET_SCHEDULER_add_continuation (gnunet_gtk_dispatch_task, ml, 554 GNUNET_SCHEDULER_add_continuation (gnunet_gtk_dispatch_task, ml,
544 GNUNET_SCHEDULER_REASON_STARTUP); 555 GNUNET_SCHEDULER_REASON_STARTUP);
545 556
@@ -553,12 +564,12 @@ gnunet_gtk_select (void *cls,
553 for (i = 0; i < fd_counter; i++) 564 for (i = 0; i < fd_counter; i++)
554 { 565 {
555 int set[3]; 566 int set[3];
556 if ((set[0] = FD_ISSET (gfds[i].fd, &aread))) 567 if ((set[0] = FD_ISSET (ml->cached_poll_array[i].fd, &aread)))
557 FD_SET (gfds[i].fd, &rfds->sds); 568 FD_SET (ml->cached_poll_array[i].fd, &rfds->sds);
558 if ((set[1] = FD_ISSET (gfds[i].fd, &awrite))) 569 if ((set[1] = FD_ISSET (ml->cached_poll_array[i].fd, &awrite)))
559 FD_SET (gfds[i].fd, &wfds->sds); 570 FD_SET (ml->cached_poll_array[i].fd, &wfds->sds);
560 if ((set[2] = FD_ISSET (gfds[i].fd, &aexcept))) 571 if ((set[2] = FD_ISSET (ml->cached_poll_array[i].fd, &aexcept)))
561 FD_SET (gfds[i].fd, &efds->sds); 572 FD_SET (ml->cached_poll_array[i].fd, &efds->sds);
562 if (set[0] || set[1] || set[2]) 573 if (set[0] || set[1] || set[2])
563 result += 1; 574 result += 1;
564 } 575 }
@@ -575,7 +586,7 @@ gnunet_gtk_select (void *cls,
575 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "select() returned %d\n", select_ret); 586 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "select() returned %d\n", select_ret);
576#endif 587#endif
577 } 588 }
578 if (always_ready_write_fd >= 0 && gfds[always_ready_write_fd].revents & G_IO_OUT) 589 if (always_ready_write_fd >= 0 && ml->cached_poll_array[always_ready_write_fd].revents & G_IO_OUT)
579 { 590 {
580 GNUNET_CONTAINER_slist_append (ml->handles_write, wfds->handles); 591 GNUNET_CONTAINER_slist_append (ml->handles_write, wfds->handles);
581 result += GNUNET_CONTAINER_slist_count (ml->handles_write); 592 result += GNUNET_CONTAINER_slist_count (ml->handles_write);
@@ -587,7 +598,7 @@ gnunet_gtk_select (void *cls,
587 { 598 {
588 DWORD error; 599 DWORD error;
589 BOOL bret; 600 BOOL bret;
590 if (!(gfds[i].revents & (G_IO_IN | G_IO_HUP | G_IO_ERR))) 601 if (!(ml->cached_poll_array[i].revents & (G_IO_IN | G_IO_HUP | G_IO_ERR)))
591 continue; 602 continue;
592 SetLastError (0); 603 SetLastError (0);
593 waitstatus = 0; 604 waitstatus = 0;
@@ -596,7 +607,7 @@ gnunet_gtk_select (void *cls,
596#if DEBUG_NETWORK 607#if DEBUG_NETWORK
597 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peek at read pipe %d (0x%x) returned %d (%d bytes available) GLE %u\n", i, ml->read_array[i]->h, bret, waitstatus, error); 608 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peek at read pipe %d (0x%x) returned %d (%d bytes available) GLE %u\n", i, ml->read_array[i]->h, bret, waitstatus, error);
598#endif 609#endif
599 if (bret == 0 || (gfds[i].revents & G_IO_ERR)) 610 if (bret == 0 || (ml->cached_poll_array[i].revents & G_IO_ERR))
600 { 611 {
601 if (efds != NULL) 612 if (efds != NULL)
602 { 613 {