diff options
Diffstat (limited to 'src/util/service.c')
-rw-r--r-- | src/util/service.c | 856 |
1 files changed, 306 insertions, 550 deletions
diff --git a/src/util/service.c b/src/util/service.c index 73a73cbea..fba5a2f20 100644 --- a/src/util/service.c +++ b/src/util/service.c | |||
@@ -37,14 +37,13 @@ | |||
37 | #endif | 37 | #endif |
38 | 38 | ||
39 | 39 | ||
40 | #define LOG(kind,...) GNUNET_log_from (kind, "util-service", __VA_ARGS__) | 40 | #define LOG(kind, ...) GNUNET_log_from (kind, "util-service", __VA_ARGS__) |
41 | 41 | ||
42 | #define LOG_STRERROR(kind,syscall) GNUNET_log_from_strerror (kind, \ | 42 | #define LOG_STRERROR(kind, syscall) \ |
43 | "util-service", \ | 43 | GNUNET_log_from_strerror (kind, "util-service", syscall) |
44 | syscall) | ||
45 | 44 | ||
46 | #define LOG_STRERROR_FILE(kind,syscall,filename) GNUNET_log_from_strerror_file ( \ | 45 | #define LOG_STRERROR_FILE(kind, syscall, filename) \ |
47 | kind, "util-service", syscall, filename) | 46 | GNUNET_log_from_strerror_file (kind, "util-service", syscall, filename) |
48 | 47 | ||
49 | 48 | ||
50 | /** | 49 | /** |
@@ -77,7 +76,6 @@ struct ServiceListenContext | |||
77 | * Task scheduled to do the listening. | 76 | * Task scheduled to do the listening. |
78 | */ | 77 | */ |
79 | struct GNUNET_SCHEDULER_Task *listen_task; | 78 | struct GNUNET_SCHEDULER_Task *listen_task; |
80 | |||
81 | }; | 79 | }; |
82 | 80 | ||
83 | 81 | ||
@@ -363,8 +361,7 @@ struct GNUNET_SERVICE_Client | |||
363 | static int | 361 | static int |
364 | have_non_monitor_clients (struct GNUNET_SERVICE_Handle *sh) | 362 | have_non_monitor_clients (struct GNUNET_SERVICE_Handle *sh) |
365 | { | 363 | { |
366 | for (struct GNUNET_SERVICE_Client *client = sh->clients_head; | 364 | for (struct GNUNET_SERVICE_Client *client = sh->clients_head; NULL != client; |
367 | NULL != client; | ||
368 | client = client->next) | 365 | client = client->next) |
369 | { | 366 | { |
370 | if (client->is_monitor) | 367 | if (client->is_monitor) |
@@ -383,8 +380,7 @@ have_non_monitor_clients (struct GNUNET_SERVICE_Handle *sh) | |||
383 | * @param sr reason for suspending accepting connections | 380 | * @param sr reason for suspending accepting connections |
384 | */ | 381 | */ |
385 | static void | 382 | static void |
386 | do_suspend (struct GNUNET_SERVICE_Handle *sh, | 383 | do_suspend (struct GNUNET_SERVICE_Handle *sh, enum SuspendReason sr) |
387 | enum SuspendReason sr) | ||
388 | { | 384 | { |
389 | struct ServiceListenContext *slc; | 385 | struct ServiceListenContext *slc; |
390 | 386 | ||
@@ -426,8 +422,7 @@ service_shutdown (void *cls) | |||
426 | break; | 422 | break; |
427 | case GNUNET_SERVICE_OPTION_SOFT_SHUTDOWN: | 423 | case GNUNET_SERVICE_OPTION_SOFT_SHUTDOWN: |
428 | if (0 == (sh->suspend_state & SUSPEND_STATE_SHUTDOWN)) | 424 | if (0 == (sh->suspend_state & SUSPEND_STATE_SHUTDOWN)) |
429 | do_suspend (sh, | 425 | do_suspend (sh, SUSPEND_STATE_SHUTDOWN); |
430 | SUSPEND_STATE_SHUTDOWN); | ||
431 | if (GNUNET_NO == have_non_monitor_clients (sh)) | 426 | if (GNUNET_NO == have_non_monitor_clients (sh)) |
432 | GNUNET_SERVICE_shutdown (sh); | 427 | GNUNET_SERVICE_shutdown (sh); |
433 | break; | 428 | break; |
@@ -451,8 +446,7 @@ check_ipv4_listed (const struct GNUNET_STRINGS_IPv4NetworkPolicy *list, | |||
451 | if (NULL == list) | 446 | if (NULL == list) |
452 | return GNUNET_NO; | 447 | return GNUNET_NO; |
453 | i = 0; | 448 | i = 0; |
454 | while ( (0 != list[i].network.s_addr) || | 449 | while ((0 != list[i].network.s_addr) || (0 != list[i].netmask.s_addr)) |
455 | (0 != list[i].netmask.s_addr) ) | ||
456 | { | 450 | { |
457 | if ((add->s_addr & list[i].netmask.s_addr) == | 451 | if ((add->s_addr & list[i].netmask.s_addr) == |
458 | (list[i].network.s_addr & list[i].netmask.s_addr)) | 452 | (list[i].network.s_addr & list[i].netmask.s_addr)) |
@@ -480,7 +474,7 @@ check_ipv6_listed (const struct GNUNET_STRINGS_IPv6NetworkPolicy *list, | |||
480 | if (NULL == list) | 474 | if (NULL == list) |
481 | return GNUNET_NO; | 475 | return GNUNET_NO; |
482 | i = 0; | 476 | i = 0; |
483 | NEXT: | 477 | NEXT: |
484 | while (0 != GNUNET_is_zero (&list[i].network)) | 478 | while (0 != GNUNET_is_zero (&list[i].network)) |
485 | { | 479 | { |
486 | for (j = 0; j < sizeof (struct in6_addr) / sizeof (int); j++) | 480 | for (j = 0; j < sizeof (struct in6_addr) / sizeof (int); j++) |
@@ -518,22 +512,17 @@ do_send (void *cls) | |||
518 | client->send_task = NULL; | 512 | client->send_task = NULL; |
519 | buf = (const char *) client->msg; | 513 | buf = (const char *) client->msg; |
520 | left = ntohs (client->msg->size) - client->msg_pos; | 514 | left = ntohs (client->msg->size) - client->msg_pos; |
521 | ret = GNUNET_NETWORK_socket_send (client->sock, | 515 | ret = GNUNET_NETWORK_socket_send (client->sock, &buf[client->msg_pos], left); |
522 | &buf[client->msg_pos], | ||
523 | left); | ||
524 | GNUNET_assert (ret <= (ssize_t) left); | 516 | GNUNET_assert (ret <= (ssize_t) left); |
525 | if (0 == ret) | 517 | if (0 == ret) |
526 | { | 518 | { |
527 | LOG (GNUNET_ERROR_TYPE_DEBUG, | 519 | LOG (GNUNET_ERROR_TYPE_DEBUG, "no data send"); |
528 | "no data send"); | 520 | GNUNET_MQ_inject_error (client->mq, GNUNET_MQ_ERROR_WRITE); |
529 | GNUNET_MQ_inject_error (client->mq, | ||
530 | GNUNET_MQ_ERROR_WRITE); | ||
531 | return; | 521 | return; |
532 | } | 522 | } |
533 | if (-1 == ret) | 523 | if (-1 == ret) |
534 | { | 524 | { |
535 | if ( (EAGAIN == errno) || | 525 | if ((EAGAIN == errno) || (EINTR == errno)) |
536 | (EINTR == errno) ) | ||
537 | { | 526 | { |
538 | /* ignore */ | 527 | /* ignore */ |
539 | ret = 0; | 528 | ret = 0; |
@@ -541,13 +530,11 @@ do_send (void *cls) | |||
541 | else | 530 | else |
542 | { | 531 | { |
543 | if (EPIPE != errno) | 532 | if (EPIPE != errno) |
544 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, | 533 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "send"); |
545 | "send"); | ||
546 | LOG (GNUNET_ERROR_TYPE_DEBUG, | 534 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
547 | "socket send returned with error code %i", | 535 | "socket send returned with error code %i", |
548 | errno); | 536 | errno); |
549 | GNUNET_MQ_inject_error (client->mq, | 537 | GNUNET_MQ_inject_error (client->mq, GNUNET_MQ_ERROR_WRITE); |
550 | GNUNET_MQ_ERROR_WRITE); | ||
551 | return; | 538 | return; |
552 | } | 539 | } |
553 | } | 540 | } |
@@ -559,11 +546,11 @@ do_send (void *cls) | |||
559 | if (left > (size_t) ret) | 546 | if (left > (size_t) ret) |
560 | { | 547 | { |
561 | GNUNET_assert (NULL == client->drop_task); | 548 | GNUNET_assert (NULL == client->drop_task); |
562 | client->send_task | 549 | client->send_task = |
563 | = GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, | 550 | GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, |
564 | client->sock, | 551 | client->sock, |
565 | &do_send, | 552 | &do_send, |
566 | client); | 553 | client); |
567 | return; | 554 | return; |
568 | } | 555 | } |
569 | GNUNET_MQ_impl_send_continue (client->mq); | 556 | GNUNET_MQ_impl_send_continue (client->mq); |
@@ -595,11 +582,11 @@ service_mq_send (struct GNUNET_MQ_Handle *mq, | |||
595 | ntohs (msg->size)); | 582 | ntohs (msg->size)); |
596 | client->msg = msg; | 583 | client->msg = msg; |
597 | client->msg_pos = 0; | 584 | client->msg_pos = 0; |
598 | client->send_task | 585 | client->send_task = |
599 | = GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, | 586 | GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, |
600 | client->sock, | 587 | client->sock, |
601 | &do_send, | 588 | &do_send, |
602 | client); | 589 | client); |
603 | } | 590 | } |
604 | 591 | ||
605 | 592 | ||
@@ -610,8 +597,7 @@ service_mq_send (struct GNUNET_MQ_Handle *mq, | |||
610 | * @param impl_state state specific to the implementation | 597 | * @param impl_state state specific to the implementation |
611 | */ | 598 | */ |
612 | static void | 599 | static void |
613 | service_mq_cancel (struct GNUNET_MQ_Handle *mq, | 600 | service_mq_cancel (struct GNUNET_MQ_Handle *mq, void *impl_state) |
614 | void *impl_state) | ||
615 | { | 601 | { |
616 | struct GNUNET_SERVICE_Client *client = impl_state; | 602 | struct GNUNET_SERVICE_Client *client = impl_state; |
617 | 603 | ||
@@ -633,14 +619,12 @@ service_mq_cancel (struct GNUNET_MQ_Handle *mq, | |||
633 | * @param error error code | 619 | * @param error error code |
634 | */ | 620 | */ |
635 | static void | 621 | static void |
636 | service_mq_error_handler (void *cls, | 622 | service_mq_error_handler (void *cls, enum GNUNET_MQ_Error error) |
637 | enum GNUNET_MQ_Error error) | ||
638 | { | 623 | { |
639 | struct GNUNET_SERVICE_Client *client = cls; | 624 | struct GNUNET_SERVICE_Client *client = cls; |
640 | struct GNUNET_SERVICE_Handle *sh = client->sh; | 625 | struct GNUNET_SERVICE_Handle *sh = client->sh; |
641 | 626 | ||
642 | if ( (GNUNET_MQ_ERROR_NO_MATCH == error) && | 627 | if ((GNUNET_MQ_ERROR_NO_MATCH == error) && (GNUNET_NO == sh->require_found)) |
643 | (GNUNET_NO == sh->require_found) ) | ||
644 | { | 628 | { |
645 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 629 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
646 | "No handler for message of type %u found\n", | 630 | "No handler for message of type %u found\n", |
@@ -662,18 +646,20 @@ warn_no_client_continue (void *cls) | |||
662 | { | 646 | { |
663 | struct GNUNET_SERVICE_Client *client = cls; | 647 | struct GNUNET_SERVICE_Client *client = cls; |
664 | 648 | ||
665 | GNUNET_break (0 != client->warn_type); /* type should never be 0 here, as we don't use 0 */ | 649 | GNUNET_break ( |
666 | client->warn_task | 650 | 0 != |
667 | = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MINUTES, | 651 | client->warn_type); /* type should never be 0 here, as we don't use 0 */ |
668 | &warn_no_client_continue, | 652 | client->warn_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MINUTES, |
669 | client); | 653 | &warn_no_client_continue, |
670 | LOG (GNUNET_ERROR_TYPE_WARNING, | 654 | client); |
671 | _ ( | 655 | LOG ( |
672 | "Processing code for message of type %u did not call `GNUNET_SERVICE_client_continue' after %s\n"), | 656 | GNUNET_ERROR_TYPE_WARNING, |
673 | (unsigned int) client->warn_type, | 657 | _ ( |
674 | GNUNET_STRINGS_relative_time_to_string ( | 658 | "Processing code for message of type %u did not call `GNUNET_SERVICE_client_continue' after %s\n"), |
675 | GNUNET_TIME_absolute_get_duration (client->warn_start), | 659 | (unsigned int) client->warn_type, |
676 | GNUNET_YES)); | 660 | GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration ( |
661 | client->warn_start), | ||
662 | GNUNET_YES)); | ||
677 | } | 663 | } |
678 | 664 | ||
679 | 665 | ||
@@ -689,8 +675,7 @@ warn_no_client_continue (void *cls) | |||
689 | * @return #GNUNET_OK on success, #GNUNET_SYSERR if the client was dropped | 675 | * @return #GNUNET_OK on success, #GNUNET_SYSERR if the client was dropped |
690 | */ | 676 | */ |
691 | static int | 677 | static int |
692 | service_client_mst_cb (void *cls, | 678 | service_client_mst_cb (void *cls, const struct GNUNET_MessageHeader *message) |
693 | const struct GNUNET_MessageHeader *message) | ||
694 | { | 679 | { |
695 | struct GNUNET_SERVICE_Client *client = cls; | 680 | struct GNUNET_SERVICE_Client *client = cls; |
696 | 681 | ||
@@ -703,12 +688,10 @@ service_client_mst_cb (void *cls, | |||
703 | client->warn_type = ntohs (message->type); | 688 | client->warn_type = ntohs (message->type); |
704 | client->warn_start = GNUNET_TIME_absolute_get (); | 689 | client->warn_start = GNUNET_TIME_absolute_get (); |
705 | GNUNET_assert (NULL == client->warn_task); | 690 | GNUNET_assert (NULL == client->warn_task); |
706 | client->warn_task | 691 | client->warn_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MINUTES, |
707 | = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MINUTES, | 692 | &warn_no_client_continue, |
708 | &warn_no_client_continue, | 693 | client); |
709 | client); | 694 | GNUNET_MQ_inject_message (client->mq, message); |
710 | GNUNET_MQ_inject_message (client->mq, | ||
711 | message); | ||
712 | if (NULL != client->drop_task) | 695 | if (NULL != client->drop_task) |
713 | return GNUNET_SYSERR; | 696 | return GNUNET_SYSERR; |
714 | return GNUNET_OK; | 697 | return GNUNET_OK; |
@@ -728,10 +711,7 @@ service_client_recv (void *cls) | |||
728 | int ret; | 711 | int ret; |
729 | 712 | ||
730 | client->recv_task = NULL; | 713 | client->recv_task = NULL; |
731 | ret = GNUNET_MST_read (client->mst, | 714 | ret = GNUNET_MST_read (client->mst, client->sock, GNUNET_NO, GNUNET_YES); |
732 | client->sock, | ||
733 | GNUNET_NO, | ||
734 | GNUNET_YES); | ||
735 | if (GNUNET_SYSERR == ret) | 715 | if (GNUNET_SYSERR == ret) |
736 | { | 716 | { |
737 | /* client closed connection (or IO error) */ | 717 | /* client closed connection (or IO error) */ |
@@ -751,11 +731,11 @@ service_client_recv (void *cls) | |||
751 | if (NULL != client->recv_task) | 731 | if (NULL != client->recv_task) |
752 | return; | 732 | return; |
753 | /* MST needs more data, re-schedule read job */ | 733 | /* MST needs more data, re-schedule read job */ |
754 | client->recv_task | 734 | client->recv_task = |
755 | = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, | 735 | GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, |
756 | client->sock, | 736 | client->sock, |
757 | &service_client_recv, | 737 | &service_client_recv, |
758 | client); | 738 | client); |
759 | } | 739 | } |
760 | 740 | ||
761 | 741 | ||
@@ -773,9 +753,7 @@ start_client (struct GNUNET_SERVICE_Handle *sh, | |||
773 | struct GNUNET_SERVICE_Client *client; | 753 | struct GNUNET_SERVICE_Client *client; |
774 | 754 | ||
775 | client = GNUNET_new (struct GNUNET_SERVICE_Client); | 755 | client = GNUNET_new (struct GNUNET_SERVICE_Client); |
776 | GNUNET_CONTAINER_DLL_insert (sh->clients_head, | 756 | GNUNET_CONTAINER_DLL_insert (sh->clients_head, sh->clients_tail, client); |
777 | sh->clients_tail, | ||
778 | client); | ||
779 | client->sh = sh; | 757 | client->sh = sh; |
780 | client->sock = csock; | 758 | client->sock = csock; |
781 | client->mq = GNUNET_MQ_queue_for_callbacks (&service_mq_send, | 759 | client->mq = GNUNET_MQ_queue_for_callbacks (&service_mq_send, |
@@ -785,19 +763,15 @@ start_client (struct GNUNET_SERVICE_Handle *sh, | |||
785 | sh->handlers, | 763 | sh->handlers, |
786 | &service_mq_error_handler, | 764 | &service_mq_error_handler, |
787 | client); | 765 | client); |
788 | client->mst = GNUNET_MST_create (&service_client_mst_cb, | 766 | client->mst = GNUNET_MST_create (&service_client_mst_cb, client); |
789 | client); | ||
790 | if (NULL != sh->connect_cb) | 767 | if (NULL != sh->connect_cb) |
791 | client->user_context = sh->connect_cb (sh->cb_cls, | 768 | client->user_context = sh->connect_cb (sh->cb_cls, client, client->mq); |
792 | client, | 769 | GNUNET_MQ_set_handlers_closure (client->mq, client->user_context); |
793 | client->mq); | 770 | client->recv_task = |
794 | GNUNET_MQ_set_handlers_closure (client->mq, | 771 | GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, |
795 | client->user_context); | 772 | client->sock, |
796 | client->recv_task | 773 | &service_client_recv, |
797 | = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, | 774 | client); |
798 | client->sock, | ||
799 | &service_client_recv, | ||
800 | client); | ||
801 | } | 775 | } |
802 | 776 | ||
803 | 777 | ||
@@ -830,11 +804,9 @@ accept_client (void *cls) | |||
830 | if (NULL == sock) | 804 | if (NULL == sock) |
831 | { | 805 | { |
832 | if (EMFILE == errno) | 806 | if (EMFILE == errno) |
833 | do_suspend (sh, | 807 | do_suspend (sh, SUSPEND_STATE_EMFILE); |
834 | SUSPEND_STATE_EMFILE); | ||
835 | else if (EAGAIN != errno) | 808 | else if (EAGAIN != errno) |
836 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, | 809 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "accept"); |
837 | "accept"); | ||
838 | break; | 810 | break; |
839 | } | 811 | } |
840 | switch (sa.ss_family) | 812 | switch (sa.ss_family) |
@@ -842,26 +814,22 @@ accept_client (void *cls) | |||
842 | case AF_INET: | 814 | case AF_INET: |
843 | GNUNET_assert (addrlen == sizeof (struct sockaddr_in)); | 815 | GNUNET_assert (addrlen == sizeof (struct sockaddr_in)); |
844 | v4 = (const struct sockaddr_in *) &sa; | 816 | v4 = (const struct sockaddr_in *) &sa; |
845 | ok = ( ( (NULL == sh->v4_allowed) || | 817 | ok = (((NULL == sh->v4_allowed) || |
846 | (check_ipv4_listed (sh->v4_allowed, | 818 | (check_ipv4_listed (sh->v4_allowed, &v4->sin_addr))) && |
847 | &v4->sin_addr))) && | 819 | ((NULL == sh->v4_denied) || |
848 | ( (NULL == sh->v4_denied) || | 820 | (! check_ipv4_listed (sh->v4_denied, &v4->sin_addr)))); |
849 | (! check_ipv4_listed (sh->v4_denied, | ||
850 | &v4->sin_addr)) ) ); | ||
851 | break; | 821 | break; |
852 | case AF_INET6: | 822 | case AF_INET6: |
853 | GNUNET_assert (addrlen == sizeof (struct sockaddr_in6)); | 823 | GNUNET_assert (addrlen == sizeof (struct sockaddr_in6)); |
854 | v6 = (const struct sockaddr_in6 *) &sa; | 824 | v6 = (const struct sockaddr_in6 *) &sa; |
855 | ok = ( ( (NULL == sh->v6_allowed) || | 825 | ok = (((NULL == sh->v6_allowed) || |
856 | (check_ipv6_listed (sh->v6_allowed, | 826 | (check_ipv6_listed (sh->v6_allowed, &v6->sin6_addr))) && |
857 | &v6->sin6_addr))) && | 827 | ((NULL == sh->v6_denied) || |
858 | ( (NULL == sh->v6_denied) || | 828 | (! check_ipv6_listed (sh->v6_denied, &v6->sin6_addr)))); |
859 | (! check_ipv6_listed (sh->v6_denied, | ||
860 | &v6->sin6_addr)) ) ); | ||
861 | break; | 829 | break; |
862 | #ifndef WINDOWS | 830 | #ifndef WINDOWS |
863 | case AF_UNIX: | 831 | case AF_UNIX: |
864 | ok = GNUNET_OK; /* controlled using file-system ACL now */ | 832 | ok = GNUNET_OK; /* controlled using file-system ACL now */ |
865 | break; | 833 | break; |
866 | #endif | 834 | #endif |
867 | default: | 835 | default: |
@@ -874,26 +842,22 @@ accept_client (void *cls) | |||
874 | { | 842 | { |
875 | LOG (GNUNET_ERROR_TYPE_DEBUG, | 843 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
876 | "Service rejected incoming connection from %s due to policy.\n", | 844 | "Service rejected incoming connection from %s due to policy.\n", |
877 | GNUNET_a2s ((const struct sockaddr *) &sa, | 845 | GNUNET_a2s ((const struct sockaddr *) &sa, addrlen)); |
878 | addrlen)); | 846 | GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (sock)); |
879 | GNUNET_break (GNUNET_OK == | ||
880 | GNUNET_NETWORK_socket_close (sock)); | ||
881 | continue; | 847 | continue; |
882 | } | 848 | } |
883 | LOG (GNUNET_ERROR_TYPE_DEBUG, | 849 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
884 | "Service accepted incoming connection from %s.\n", | 850 | "Service accepted incoming connection from %s.\n", |
885 | GNUNET_a2s ((const struct sockaddr *) &sa, | 851 | GNUNET_a2s ((const struct sockaddr *) &sa, addrlen)); |
886 | addrlen)); | 852 | start_client (slc->sh, sock); |
887 | start_client (slc->sh, | ||
888 | sock); | ||
889 | } | 853 | } |
890 | if (0 != sh->suspend_state) | 854 | if (0 != sh->suspend_state) |
891 | return; | 855 | return; |
892 | slc->listen_task | 856 | slc->listen_task = |
893 | = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, | 857 | GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, |
894 | slc->listen_socket, | 858 | slc->listen_socket, |
895 | &accept_client, | 859 | &accept_client, |
896 | slc); | 860 | slc); |
897 | } | 861 | } |
898 | 862 | ||
899 | 863 | ||
@@ -905,24 +869,22 @@ accept_client (void *cls) | |||
905 | * or #SUSPEND_STATE_NONE on first startup | 869 | * or #SUSPEND_STATE_NONE on first startup |
906 | */ | 870 | */ |
907 | static void | 871 | static void |
908 | do_resume (struct GNUNET_SERVICE_Handle *sh, | 872 | do_resume (struct GNUNET_SERVICE_Handle *sh, enum SuspendReason sr) |
909 | enum SuspendReason sr) | ||
910 | { | 873 | { |
911 | struct ServiceListenContext *slc; | 874 | struct ServiceListenContext *slc; |
912 | 875 | ||
913 | GNUNET_assert ( (SUSPEND_STATE_NONE == sr) || | 876 | GNUNET_assert ((SUSPEND_STATE_NONE == sr) || (0 != (sh->suspend_state & sr))); |
914 | (0 != (sh->suspend_state & sr)) ); | ||
915 | sh->suspend_state -= sr; | 877 | sh->suspend_state -= sr; |
916 | if (SUSPEND_STATE_NONE != sh->suspend_state) | 878 | if (SUSPEND_STATE_NONE != sh->suspend_state) |
917 | return; | 879 | return; |
918 | for (slc = sh->slc_head; NULL != slc; slc = slc->next) | 880 | for (slc = sh->slc_head; NULL != slc; slc = slc->next) |
919 | { | 881 | { |
920 | GNUNET_assert (NULL == slc->listen_task); | 882 | GNUNET_assert (NULL == slc->listen_task); |
921 | slc->listen_task | 883 | slc->listen_task = |
922 | = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, | 884 | GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, |
923 | slc->listen_socket, | 885 | slc->listen_socket, |
924 | &accept_client, | 886 | &accept_client, |
925 | slc); | 887 | slc); |
926 | } | 888 | } |
927 | } | 889 | } |
928 | 890 | ||
@@ -940,22 +902,18 @@ service_main (void *cls) | |||
940 | struct GNUNET_SERVICE_Handle *sh = cls; | 902 | struct GNUNET_SERVICE_Handle *sh = cls; |
941 | 903 | ||
942 | if (GNUNET_SERVICE_OPTION_MANUAL_SHUTDOWN != sh->options) | 904 | if (GNUNET_SERVICE_OPTION_MANUAL_SHUTDOWN != sh->options) |
943 | GNUNET_SCHEDULER_add_shutdown (&service_shutdown, | 905 | GNUNET_SCHEDULER_add_shutdown (&service_shutdown, sh); |
944 | sh); | 906 | do_resume (sh, SUSPEND_STATE_NONE); |
945 | do_resume (sh, | ||
946 | SUSPEND_STATE_NONE); | ||
947 | 907 | ||
948 | if (-1 != sh->ready_confirm_fd) | 908 | if (-1 != sh->ready_confirm_fd) |
949 | { | 909 | { |
950 | GNUNET_break (1 == WRITE (sh->ready_confirm_fd, ".", 1)); | 910 | GNUNET_break (1 == write (sh->ready_confirm_fd, ".", 1)); |
951 | GNUNET_break (0 == CLOSE (sh->ready_confirm_fd)); | 911 | GNUNET_break (0 == close (sh->ready_confirm_fd)); |
952 | sh->ready_confirm_fd = -1; | 912 | sh->ready_confirm_fd = -1; |
953 | } | 913 | } |
954 | 914 | ||
955 | if (NULL != sh->service_init_cb) | 915 | if (NULL != sh->service_init_cb) |
956 | sh->service_init_cb (sh->cb_cls, | 916 | sh->service_init_cb (sh->cb_cls, sh->cfg, sh); |
957 | sh->cfg, | ||
958 | sh); | ||
959 | } | 917 | } |
960 | 918 | ||
961 | 919 | ||
@@ -975,9 +933,7 @@ process_acl4 (struct GNUNET_STRINGS_IPv4NetworkPolicy **ret, | |||
975 | { | 933 | { |
976 | char *opt; | 934 | char *opt; |
977 | 935 | ||
978 | if (! GNUNET_CONFIGURATION_have_value (sh->cfg, | 936 | if (! GNUNET_CONFIGURATION_have_value (sh->cfg, sh->service_name, option)) |
979 | sh->service_name, | ||
980 | option)) | ||
981 | { | 937 | { |
982 | *ret = NULL; | 938 | *ret = NULL; |
983 | return GNUNET_OK; | 939 | return GNUNET_OK; |
@@ -1018,9 +974,7 @@ process_acl6 (struct GNUNET_STRINGS_IPv6NetworkPolicy **ret, | |||
1018 | { | 974 | { |
1019 | char *opt; | 975 | char *opt; |
1020 | 976 | ||
1021 | if (! GNUNET_CONFIGURATION_have_value (sh->cfg, | 977 | if (! GNUNET_CONFIGURATION_have_value (sh->cfg, sh->service_name, option)) |
1022 | sh->service_name, | ||
1023 | option)) | ||
1024 | { | 978 | { |
1025 | *ret = NULL; | 979 | *ret = NULL; |
1026 | return GNUNET_OK; | 980 | return GNUNET_OK; |
@@ -1066,9 +1020,7 @@ add_unixpath (struct sockaddr **saddrs, | |||
1066 | 1020 | ||
1067 | un = GNUNET_new (struct sockaddr_un); | 1021 | un = GNUNET_new (struct sockaddr_un); |
1068 | un->sun_family = AF_UNIX; | 1022 | un->sun_family = AF_UNIX; |
1069 | GNUNET_strlcpy (un->sun_path, | 1023 | GNUNET_strlcpy (un->sun_path, unixpath, sizeof (un->sun_path)); |
1070 | unixpath, | ||
1071 | sizeof (un->sun_path)); | ||
1072 | #ifdef LINUX | 1024 | #ifdef LINUX |
1073 | if (GNUNET_YES == abstract) | 1025 | if (GNUNET_YES == abstract) |
1074 | un->sun_path[0] = '\0'; | 1026 | un->sun_path[0] = '\0'; |
@@ -1132,24 +1084,18 @@ get_server_addresses (const char *service_name, | |||
1132 | *addr_lens = NULL; | 1084 | *addr_lens = NULL; |
1133 | desc = NULL; | 1085 | desc = NULL; |
1134 | disablev6 = GNUNET_NO; | 1086 | disablev6 = GNUNET_NO; |
1135 | if ( (GNUNET_NO == | 1087 | if ((GNUNET_NO == GNUNET_NETWORK_test_pf (PF_INET6)) || |
1136 | GNUNET_NETWORK_test_pf (PF_INET6)) || | 1088 | (GNUNET_YES == |
1137 | (GNUNET_YES == | 1089 | GNUNET_CONFIGURATION_get_value_yesno (cfg, service_name, "DISABLEV6"))) |
1138 | GNUNET_CONFIGURATION_get_value_yesno (cfg, | ||
1139 | service_name, | ||
1140 | "DISABLEV6") ) ) | ||
1141 | disablev6 = GNUNET_YES; | 1090 | disablev6 = GNUNET_YES; |
1142 | 1091 | ||
1143 | port = 0; | 1092 | port = 0; |
1144 | if (GNUNET_CONFIGURATION_have_value (cfg, | 1093 | if (GNUNET_CONFIGURATION_have_value (cfg, service_name, "PORT")) |
1145 | service_name, | ||
1146 | "PORT")) | ||
1147 | { | 1094 | { |
1148 | if (GNUNET_OK != | 1095 | if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (cfg, |
1149 | GNUNET_CONFIGURATION_get_value_number (cfg, | 1096 | service_name, |
1150 | service_name, | 1097 | "PORT", |
1151 | "PORT", | 1098 | &port)) |
1152 | &port)) | ||
1153 | { | 1099 | { |
1154 | LOG (GNUNET_ERROR_TYPE_ERROR, | 1100 | LOG (GNUNET_ERROR_TYPE_ERROR, |
1155 | _ ("Require valid port number for service `%s' in configuration!\n"), | 1101 | _ ("Require valid port number for service `%s' in configuration!\n"), |
@@ -1164,9 +1110,7 @@ get_server_addresses (const char *service_name, | |||
1164 | } | 1110 | } |
1165 | } | 1111 | } |
1166 | 1112 | ||
1167 | if (GNUNET_CONFIGURATION_have_value (cfg, | 1113 | if (GNUNET_CONFIGURATION_have_value (cfg, service_name, "BINDTO")) |
1168 | service_name, | ||
1169 | "BINDTO")) | ||
1170 | { | 1114 | { |
1171 | GNUNET_break (GNUNET_OK == | 1115 | GNUNET_break (GNUNET_OK == |
1172 | GNUNET_CONFIGURATION_get_value_string (cfg, | 1116 | GNUNET_CONFIGURATION_get_value_string (cfg, |
@@ -1181,14 +1125,11 @@ get_server_addresses (const char *service_name, | |||
1181 | abstract = GNUNET_NO; | 1125 | abstract = GNUNET_NO; |
1182 | #ifdef AF_UNIX | 1126 | #ifdef AF_UNIX |
1183 | if ((GNUNET_YES == | 1127 | if ((GNUNET_YES == |
1184 | GNUNET_CONFIGURATION_have_value (cfg, | 1128 | GNUNET_CONFIGURATION_have_value (cfg, service_name, "UNIXPATH")) && |
1185 | service_name, | 1129 | (GNUNET_OK == GNUNET_CONFIGURATION_get_value_filename (cfg, |
1186 | "UNIXPATH")) && | 1130 | service_name, |
1187 | (GNUNET_OK == | 1131 | "UNIXPATH", |
1188 | GNUNET_CONFIGURATION_get_value_filename (cfg, | 1132 | &unixpath)) && |
1189 | service_name, | ||
1190 | "UNIXPATH", | ||
1191 | &unixpath)) && | ||
1192 | (0 < strlen (unixpath))) | 1133 | (0 < strlen (unixpath))) |
1193 | { | 1134 | { |
1194 | /* probe UNIX support */ | 1135 | /* probe UNIX support */ |
@@ -1201,9 +1142,7 @@ get_server_addresses (const char *service_name, | |||
1201 | unixpath, | 1142 | unixpath, |
1202 | (unsigned long long) sizeof (s_un.sun_path)); | 1143 | (unsigned long long) sizeof (s_un.sun_path)); |
1203 | unixpath = GNUNET_NETWORK_shorten_unixpath (unixpath); | 1144 | unixpath = GNUNET_NETWORK_shorten_unixpath (unixpath); |
1204 | LOG (GNUNET_ERROR_TYPE_INFO, | 1145 | LOG (GNUNET_ERROR_TYPE_INFO, _ ("Using `%s' instead\n"), unixpath); |
1205 | _ ("Using `%s' instead\n"), | ||
1206 | unixpath); | ||
1207 | } | 1146 | } |
1208 | #ifdef LINUX | 1147 | #ifdef LINUX |
1209 | abstract = GNUNET_CONFIGURATION_get_value_yesno (cfg, | 1148 | abstract = GNUNET_CONFIGURATION_get_value_yesno (cfg, |
@@ -1212,27 +1151,19 @@ get_server_addresses (const char *service_name, | |||
1212 | if (GNUNET_SYSERR == abstract) | 1151 | if (GNUNET_SYSERR == abstract) |
1213 | abstract = GNUNET_NO; | 1152 | abstract = GNUNET_NO; |
1214 | #endif | 1153 | #endif |
1215 | if ( (GNUNET_YES != abstract) && | 1154 | if ((GNUNET_YES != abstract) && |
1216 | (GNUNET_OK != | 1155 | (GNUNET_OK != GNUNET_DISK_directory_create_for_file (unixpath))) |
1217 | GNUNET_DISK_directory_create_for_file (unixpath)) ) | 1156 | GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, "mkdir", unixpath); |
1218 | GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, | ||
1219 | "mkdir", | ||
1220 | unixpath); | ||
1221 | } | 1157 | } |
1222 | if (NULL != unixpath) | 1158 | if (NULL != unixpath) |
1223 | { | 1159 | { |
1224 | desc = GNUNET_NETWORK_socket_create (AF_UNIX, | 1160 | desc = GNUNET_NETWORK_socket_create (AF_UNIX, SOCK_STREAM, 0); |
1225 | SOCK_STREAM, | ||
1226 | 0); | ||
1227 | if (NULL == desc) | 1161 | if (NULL == desc) |
1228 | { | 1162 | { |
1229 | if ((ENOBUFS == errno) || | 1163 | if ((ENOBUFS == errno) || (ENOMEM == errno) || (ENFILE == errno) || |
1230 | (ENOMEM == errno) || | ||
1231 | (ENFILE == errno) || | ||
1232 | (EACCES == errno)) | 1164 | (EACCES == errno)) |
1233 | { | 1165 | { |
1234 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, | 1166 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "socket"); |
1235 | "socket"); | ||
1236 | GNUNET_free_non_null (hostname); | 1167 | GNUNET_free_non_null (hostname); |
1237 | GNUNET_free (unixpath); | 1168 | GNUNET_free (unixpath); |
1238 | return GNUNET_SYSERR; | 1169 | return GNUNET_SYSERR; |
@@ -1241,14 +1172,13 @@ get_server_addresses (const char *service_name, | |||
1241 | _ ( | 1172 | _ ( |
1242 | "Disabling UNIX domain socket support for service `%s', failed to create UNIX domain socket: %s\n"), | 1173 | "Disabling UNIX domain socket support for service `%s', failed to create UNIX domain socket: %s\n"), |
1243 | service_name, | 1174 | service_name, |
1244 | STRERROR (errno)); | 1175 | strerror (errno)); |
1245 | GNUNET_free (unixpath); | 1176 | GNUNET_free (unixpath); |
1246 | unixpath = NULL; | 1177 | unixpath = NULL; |
1247 | } | 1178 | } |
1248 | else | 1179 | else |
1249 | { | 1180 | { |
1250 | GNUNET_break (GNUNET_OK == | 1181 | GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (desc)); |
1251 | GNUNET_NETWORK_socket_close (desc)); | ||
1252 | desc = NULL; | 1182 | desc = NULL; |
1253 | } | 1183 | } |
1254 | } | 1184 | } |
@@ -1265,14 +1195,9 @@ get_server_addresses (const char *service_name, | |||
1265 | } | 1195 | } |
1266 | if (0 == port) | 1196 | if (0 == port) |
1267 | { | 1197 | { |
1268 | saddrs = GNUNET_new_array (2, | 1198 | saddrs = GNUNET_new_array (2, struct sockaddr *); |
1269 | struct sockaddr *); | 1199 | saddrlens = GNUNET_new_array (2, socklen_t); |
1270 | saddrlens = GNUNET_new_array (2, | 1200 | add_unixpath (saddrs, saddrlens, unixpath, abstract); |
1271 | socklen_t); | ||
1272 | add_unixpath (saddrs, | ||
1273 | saddrlens, | ||
1274 | unixpath, | ||
1275 | abstract); | ||
1276 | GNUNET_free_non_null (unixpath); | 1201 | GNUNET_free_non_null (unixpath); |
1277 | GNUNET_free_non_null (hostname); | 1202 | GNUNET_free_non_null (hostname); |
1278 | *addrs = saddrs; | 1203 | *addrs = saddrs; |
@@ -1286,16 +1211,11 @@ get_server_addresses (const char *service_name, | |||
1286 | "Resolving `%s' since that is where `%s' will bind to.\n", | 1211 | "Resolving `%s' since that is where `%s' will bind to.\n", |
1287 | hostname, | 1212 | hostname, |
1288 | service_name); | 1213 | service_name); |
1289 | memset (&hints, | 1214 | memset (&hints, 0, sizeof (struct addrinfo)); |
1290 | 0, | ||
1291 | sizeof (struct addrinfo)); | ||
1292 | if (disablev6) | 1215 | if (disablev6) |
1293 | hints.ai_family = AF_INET; | 1216 | hints.ai_family = AF_INET; |
1294 | hints.ai_protocol = IPPROTO_TCP; | 1217 | hints.ai_protocol = IPPROTO_TCP; |
1295 | if ((0 != (ret = getaddrinfo (hostname, | 1218 | if ((0 != (ret = getaddrinfo (hostname, NULL, &hints, &res))) || |
1296 | NULL, | ||
1297 | &hints, | ||
1298 | &res))) || | ||
1299 | (NULL == res)) | 1219 | (NULL == res)) |
1300 | { | 1220 | { |
1301 | LOG (GNUNET_ERROR_TYPE_ERROR, | 1221 | LOG (GNUNET_ERROR_TYPE_ERROR, |
@@ -1311,8 +1231,7 @@ get_server_addresses (const char *service_name, | |||
1311 | while (NULL != (pos = next)) | 1231 | while (NULL != (pos = next)) |
1312 | { | 1232 | { |
1313 | next = pos->ai_next; | 1233 | next = pos->ai_next; |
1314 | if ( (disablev6) && | 1234 | if ((disablev6) && (pos->ai_family == AF_INET6)) |
1315 | (pos->ai_family == AF_INET6) ) | ||
1316 | continue; | 1235 | continue; |
1317 | i++; | 1236 | i++; |
1318 | } | 1237 | } |
@@ -1330,45 +1249,34 @@ get_server_addresses (const char *service_name, | |||
1330 | resi = i; | 1249 | resi = i; |
1331 | if (NULL != unixpath) | 1250 | if (NULL != unixpath) |
1332 | resi++; | 1251 | resi++; |
1333 | saddrs = GNUNET_new_array (resi + 1, | 1252 | saddrs = GNUNET_new_array (resi + 1, struct sockaddr *); |
1334 | struct sockaddr *); | 1253 | saddrlens = GNUNET_new_array (resi + 1, socklen_t); |
1335 | saddrlens = GNUNET_new_array (resi + 1, | ||
1336 | socklen_t); | ||
1337 | i = 0; | 1254 | i = 0; |
1338 | if (NULL != unixpath) | 1255 | if (NULL != unixpath) |
1339 | { | 1256 | { |
1340 | add_unixpath (saddrs, | 1257 | add_unixpath (saddrs, saddrlens, unixpath, abstract); |
1341 | saddrlens, | ||
1342 | unixpath, | ||
1343 | abstract); | ||
1344 | i++; | 1258 | i++; |
1345 | } | 1259 | } |
1346 | next = res; | 1260 | next = res; |
1347 | while (NULL != (pos = next)) | 1261 | while (NULL != (pos = next)) |
1348 | { | 1262 | { |
1349 | next = pos->ai_next; | 1263 | next = pos->ai_next; |
1350 | if ( (disablev6) && | 1264 | if ((disablev6) && (AF_INET6 == pos->ai_family)) |
1351 | (AF_INET6 == pos->ai_family) ) | ||
1352 | continue; | 1265 | continue; |
1353 | if ( (IPPROTO_TCP != pos->ai_protocol) && | 1266 | if ((IPPROTO_TCP != pos->ai_protocol) && (0 != pos->ai_protocol)) |
1354 | (0 != pos->ai_protocol) ) | 1267 | continue; /* not TCP */ |
1355 | continue; /* not TCP */ | 1268 | if ((SOCK_STREAM != pos->ai_socktype) && (0 != pos->ai_socktype)) |
1356 | if ( (SOCK_STREAM != pos->ai_socktype) && | 1269 | continue; /* huh? */ |
1357 | (0 != pos->ai_socktype) ) | ||
1358 | continue; /* huh? */ | ||
1359 | LOG (GNUNET_ERROR_TYPE_DEBUG, | 1270 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
1360 | "Service `%s' will bind to `%s'\n", | 1271 | "Service `%s' will bind to `%s'\n", |
1361 | service_name, | 1272 | service_name, |
1362 | GNUNET_a2s (pos->ai_addr, | 1273 | GNUNET_a2s (pos->ai_addr, pos->ai_addrlen)); |
1363 | pos->ai_addrlen)); | ||
1364 | if (AF_INET == pos->ai_family) | 1274 | if (AF_INET == pos->ai_family) |
1365 | { | 1275 | { |
1366 | GNUNET_assert (sizeof (struct sockaddr_in) == pos->ai_addrlen); | 1276 | GNUNET_assert (sizeof (struct sockaddr_in) == pos->ai_addrlen); |
1367 | saddrlens[i] = pos->ai_addrlen; | 1277 | saddrlens[i] = pos->ai_addrlen; |
1368 | saddrs[i] = GNUNET_malloc (saddrlens[i]); | 1278 | saddrs[i] = GNUNET_malloc (saddrlens[i]); |
1369 | GNUNET_memcpy (saddrs[i], | 1279 | GNUNET_memcpy (saddrs[i], pos->ai_addr, saddrlens[i]); |
1370 | pos->ai_addr, | ||
1371 | saddrlens[i]); | ||
1372 | ((struct sockaddr_in *) saddrs[i])->sin_port = htons (port); | 1280 | ((struct sockaddr_in *) saddrs[i])->sin_port = htons (port); |
1373 | } | 1281 | } |
1374 | else | 1282 | else |
@@ -1377,9 +1285,7 @@ get_server_addresses (const char *service_name, | |||
1377 | GNUNET_assert (sizeof (struct sockaddr_in6) == pos->ai_addrlen); | 1285 | GNUNET_assert (sizeof (struct sockaddr_in6) == pos->ai_addrlen); |
1378 | saddrlens[i] = pos->ai_addrlen; | 1286 | saddrlens[i] = pos->ai_addrlen; |
1379 | saddrs[i] = GNUNET_malloc (saddrlens[i]); | 1287 | saddrs[i] = GNUNET_malloc (saddrlens[i]); |
1380 | GNUNET_memcpy (saddrs[i], | 1288 | GNUNET_memcpy (saddrs[i], pos->ai_addr, saddrlens[i]); |
1381 | pos->ai_addr, | ||
1382 | saddrlens[i]); | ||
1383 | ((struct sockaddr_in6 *) saddrs[i])->sin6_port = htons (port); | 1289 | ((struct sockaddr_in6 *) saddrs[i])->sin6_port = htons (port); |
1384 | } | 1290 | } |
1385 | i++; | 1291 | i++; |
@@ -1398,16 +1304,11 @@ get_server_addresses (const char *service_name, | |||
1398 | if (NULL != unixpath) | 1304 | if (NULL != unixpath) |
1399 | resi++; | 1305 | resi++; |
1400 | i = 0; | 1306 | i = 0; |
1401 | saddrs = GNUNET_new_array (resi + 1, | 1307 | saddrs = GNUNET_new_array (resi + 1, struct sockaddr *); |
1402 | struct sockaddr *); | 1308 | saddrlens = GNUNET_new_array (resi + 1, socklen_t); |
1403 | saddrlens = GNUNET_new_array (resi + 1, | ||
1404 | socklen_t); | ||
1405 | if (NULL != unixpath) | 1309 | if (NULL != unixpath) |
1406 | { | 1310 | { |
1407 | add_unixpath (saddrs, | 1311 | add_unixpath (saddrs, saddrlens, unixpath, abstract); |
1408 | saddrlens, | ||
1409 | unixpath, | ||
1410 | abstract); | ||
1411 | i++; | 1312 | i++; |
1412 | } | 1313 | } |
1413 | saddrlens[i] = sizeof (struct sockaddr_in); | 1314 | saddrlens[i] = sizeof (struct sockaddr_in); |
@@ -1424,17 +1325,12 @@ get_server_addresses (const char *service_name, | |||
1424 | resi = 2; | 1325 | resi = 2; |
1425 | if (NULL != unixpath) | 1326 | if (NULL != unixpath) |
1426 | resi++; | 1327 | resi++; |
1427 | saddrs = GNUNET_new_array (resi + 1, | 1328 | saddrs = GNUNET_new_array (resi + 1, struct sockaddr *); |
1428 | struct sockaddr *); | 1329 | saddrlens = GNUNET_new_array (resi + 1, socklen_t); |
1429 | saddrlens = GNUNET_new_array (resi + 1, | ||
1430 | socklen_t); | ||
1431 | i = 0; | 1330 | i = 0; |
1432 | if (NULL != unixpath) | 1331 | if (NULL != unixpath) |
1433 | { | 1332 | { |
1434 | add_unixpath (saddrs, | 1333 | add_unixpath (saddrs, saddrlens, unixpath, abstract); |
1435 | saddrlens, | ||
1436 | unixpath, | ||
1437 | abstract); | ||
1438 | i++; | 1334 | i++; |
1439 | } | 1335 | } |
1440 | saddrlens[i] = sizeof (struct sockaddr_in6); | 1336 | saddrlens[i] = sizeof (struct sockaddr_in6); |
@@ -1480,18 +1376,14 @@ receive_sockets_from_parent (struct GNUNET_SERVICE_Handle *sh) | |||
1480 | HANDLE lsocks_pipe; | 1376 | HANDLE lsocks_pipe; |
1481 | 1377 | ||
1482 | env_buf = getenv ("GNUNET_OS_READ_LSOCKS"); | 1378 | env_buf = getenv ("GNUNET_OS_READ_LSOCKS"); |
1483 | if ( (NULL == env_buf) || | 1379 | if ((NULL == env_buf) || (strlen (env_buf) <= 0)) |
1484 | (strlen (env_buf) <= 0) ) | ||
1485 | return NULL; | 1380 | return NULL; |
1486 | /* Using W32 API directly here, because this pipe will | 1381 | /* Using W32 API directly here, because this pipe will |
1487 | * never be used outside of this function, and it's just too much of a bother | 1382 | * never be used outside of this function, and it's just too much of a bother |
1488 | * to create a GNUnet API that boxes a HANDLE (the way it is done with socks) | 1383 | * to create a GNUnet API that boxes a HANDLE (the way it is done with socks) |
1489 | */ | 1384 | */ |
1490 | lsocks_pipe = (HANDLE) strtoul (env_buf, | 1385 | lsocks_pipe = (HANDLE) strtoul (env_buf, NULL, 10); |
1491 | NULL, | 1386 | if ((0 == lsocks_pipe) || (INVALID_HANDLE_VALUE == lsocks_pipe)) |
1492 | 10); | ||
1493 | if ( (0 == lsocks_pipe) || | ||
1494 | (INVALID_HANDLE_VALUE == lsocks_pipe)) | ||
1495 | return NULL; | 1387 | return NULL; |
1496 | fail = 1; | 1388 | fail = 1; |
1497 | do | 1389 | do |
@@ -1500,17 +1392,10 @@ receive_sockets_from_parent (struct GNUNET_SERVICE_Handle *sh) | |||
1500 | int fail2; | 1392 | int fail2; |
1501 | DWORD rd; | 1393 | DWORD rd; |
1502 | 1394 | ||
1503 | ret = ReadFile (lsocks_pipe, | 1395 | ret = ReadFile (lsocks_pipe, &count, sizeof (count), &rd, NULL); |
1504 | &count, | 1396 | if ((0 == ret) || (sizeof (count) != rd) || (0 == count)) |
1505 | sizeof (count), | ||
1506 | &rd, | ||
1507 | NULL); | ||
1508 | if ( (0 == ret) || | ||
1509 | (sizeof (count) != rd) || | ||
1510 | (0 == count) ) | ||
1511 | break; | 1397 | break; |
1512 | lsocks = GNUNET_new_array (count + 1, | 1398 | lsocks = GNUNET_new_array (count + 1, struct GNUNET_NETWORK_Handle *); |
1513 | struct GNUNET_NETWORK_Handle *); | ||
1514 | 1399 | ||
1515 | fail2 = 1; | 1400 | fail2 = 1; |
1516 | for (i = 0; i < count; i++) | 1401 | for (i = 0; i < count; i++) |
@@ -1519,22 +1404,11 @@ receive_sockets_from_parent (struct GNUNET_SERVICE_Handle *sh) | |||
1519 | uint64_t size; | 1404 | uint64_t size; |
1520 | SOCKET s; | 1405 | SOCKET s; |
1521 | 1406 | ||
1522 | ret = ReadFile (lsocks_pipe, | 1407 | ret = ReadFile (lsocks_pipe, &size, sizeof (size), &rd, NULL); |
1523 | &size, | 1408 | if ((0 == ret) || (sizeof (size) != rd) || (sizeof (pi) != size)) |
1524 | sizeof (size), | ||
1525 | &rd, | ||
1526 | NULL); | ||
1527 | if ( (0 == ret) || | ||
1528 | (sizeof (size) != rd) || | ||
1529 | (sizeof (pi) != size) ) | ||
1530 | break; | 1409 | break; |
1531 | ret = ReadFile (lsocks_pipe, | 1410 | ret = ReadFile (lsocks_pipe, &pi, sizeof (pi), &rd, NULL); |
1532 | &pi, | 1411 | if ((0 == ret) || (sizeof (pi) != rd)) |
1533 | sizeof (pi), | ||
1534 | &rd, | ||
1535 | NULL); | ||
1536 | if ( (0 == ret) || | ||
1537 | (sizeof (pi) != rd)) | ||
1538 | break; | 1412 | break; |
1539 | s = WSASocketA (pi.iAddressFamily, | 1413 | s = WSASocketA (pi.iAddressFamily, |
1540 | pi.iSocketType, | 1414 | pi.iSocketType, |
@@ -1552,8 +1426,7 @@ receive_sockets_from_parent (struct GNUNET_SERVICE_Handle *sh) | |||
1552 | break; | 1426 | break; |
1553 | lsocks[count] = NULL; | 1427 | lsocks[count] = NULL; |
1554 | fail = 0; | 1428 | fail = 0; |
1555 | } | 1429 | } while (fail); |
1556 | while (fail); | ||
1557 | CloseHandle (lsocks_pipe); | 1430 | CloseHandle (lsocks_pipe); |
1558 | 1431 | ||
1559 | if (fail) | 1432 | if (fail) |
@@ -1561,8 +1434,7 @@ receive_sockets_from_parent (struct GNUNET_SERVICE_Handle *sh) | |||
1561 | LOG (GNUNET_ERROR_TYPE_ERROR, | 1434 | LOG (GNUNET_ERROR_TYPE_ERROR, |
1562 | _ ("Could not access a pre-bound socket, will try to bind myself\n")); | 1435 | _ ("Could not access a pre-bound socket, will try to bind myself\n")); |
1563 | for (i = 0; (i < count) && (NULL != lsocks[i]); i++) | 1436 | for (i = 0; (i < count) && (NULL != lsocks[i]); i++) |
1564 | GNUNET_break (GNUNET_OK == | 1437 | GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (lsocks[i])); |
1565 | GNUNET_NETWORK_socket_close (lsocks[i])); | ||
1566 | GNUNET_free (lsocks); | 1438 | GNUNET_free (lsocks); |
1567 | return NULL; | 1439 | return NULL; |
1568 | } | 1440 | } |
@@ -1579,8 +1451,7 @@ receive_sockets_from_parent (struct GNUNET_SERVICE_Handle *sh) | |||
1579 | * @return NULL on error, otherwise the listen socket | 1451 | * @return NULL on error, otherwise the listen socket |
1580 | */ | 1452 | */ |
1581 | static struct GNUNET_NETWORK_Handle * | 1453 | static struct GNUNET_NETWORK_Handle * |
1582 | open_listen_socket (const struct sockaddr *server_addr, | 1454 | open_listen_socket (const struct sockaddr *server_addr, socklen_t socklen) |
1583 | socklen_t socklen) | ||
1584 | { | 1455 | { |
1585 | struct GNUNET_NETWORK_Handle *sock; | 1456 | struct GNUNET_NETWORK_Handle *sock; |
1586 | uint16_t port; | 1457 | uint16_t port; |
@@ -1602,20 +1473,15 @@ open_listen_socket (const struct sockaddr *server_addr, | |||
1602 | port = 0; | 1473 | port = 0; |
1603 | break; | 1474 | break; |
1604 | } | 1475 | } |
1605 | sock = GNUNET_NETWORK_socket_create (server_addr->sa_family, | 1476 | sock = GNUNET_NETWORK_socket_create (server_addr->sa_family, SOCK_STREAM, 0); |
1606 | SOCK_STREAM, | ||
1607 | 0); | ||
1608 | if (NULL == sock) | 1477 | if (NULL == sock) |
1609 | { | 1478 | { |
1610 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, | 1479 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "socket"); |
1611 | "socket"); | ||
1612 | errno = 0; | 1480 | errno = 0; |
1613 | return NULL; | 1481 | return NULL; |
1614 | } | 1482 | } |
1615 | /* bind the socket */ | 1483 | /* bind the socket */ |
1616 | if (GNUNET_OK != GNUNET_NETWORK_socket_bind (sock, | 1484 | if (GNUNET_OK != GNUNET_NETWORK_socket_bind (sock, server_addr, socklen)) |
1617 | server_addr, | ||
1618 | socklen)) | ||
1619 | { | 1485 | { |
1620 | eno = errno; | 1486 | eno = errno; |
1621 | if (EADDRINUSE != errno) | 1487 | if (EADDRINUSE != errno) |
@@ -1631,8 +1497,7 @@ open_listen_socket (const struct sockaddr *server_addr, | |||
1631 | port, | 1497 | port, |
1632 | (AF_INET == server_addr->sa_family) ? "IPv4" : "IPv6"); | 1498 | (AF_INET == server_addr->sa_family) ? "IPv4" : "IPv6"); |
1633 | else | 1499 | else |
1634 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, | 1500 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "bind"); |
1635 | "bind"); | ||
1636 | eno = 0; | 1501 | eno = 0; |
1637 | } | 1502 | } |
1638 | else | 1503 | else |
@@ -1640,7 +1505,8 @@ open_listen_socket (const struct sockaddr *server_addr, | |||
1640 | if (0 != port) | 1505 | if (0 != port) |
1641 | LOG (GNUNET_ERROR_TYPE_WARNING, | 1506 | LOG (GNUNET_ERROR_TYPE_WARNING, |
1642 | _ ("`%s' failed for port %d (%s): address already in use\n"), | 1507 | _ ("`%s' failed for port %d (%s): address already in use\n"), |
1643 | "bind", port, | 1508 | "bind", |
1509 | port, | ||
1644 | (AF_INET == server_addr->sa_family) ? "IPv4" : "IPv6"); | 1510 | (AF_INET == server_addr->sa_family) ? "IPv4" : "IPv6"); |
1645 | else if (AF_UNIX == server_addr->sa_family) | 1511 | else if (AF_UNIX == server_addr->sa_family) |
1646 | { | 1512 | { |
@@ -1650,18 +1516,14 @@ open_listen_socket (const struct sockaddr *server_addr, | |||
1650 | GNUNET_a2s (server_addr, socklen)); | 1516 | GNUNET_a2s (server_addr, socklen)); |
1651 | } | 1517 | } |
1652 | } | 1518 | } |
1653 | GNUNET_break (GNUNET_OK == | 1519 | GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (sock)); |
1654 | GNUNET_NETWORK_socket_close (sock)); | ||
1655 | errno = eno; | 1520 | errno = eno; |
1656 | return NULL; | 1521 | return NULL; |
1657 | } | 1522 | } |
1658 | if (GNUNET_OK != GNUNET_NETWORK_socket_listen (sock, | 1523 | if (GNUNET_OK != GNUNET_NETWORK_socket_listen (sock, 5)) |
1659 | 5)) | ||
1660 | { | 1524 | { |
1661 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, | 1525 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "listen"); |
1662 | "listen"); | 1526 | GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (sock)); |
1663 | GNUNET_break (GNUNET_OK == | ||
1664 | GNUNET_NETWORK_socket_close (sock)); | ||
1665 | errno = 0; | 1527 | errno = 0; |
1666 | return NULL; | 1528 | return NULL; |
1667 | } | 1529 | } |
@@ -1701,16 +1563,12 @@ setup_service (struct GNUNET_SERVICE_Handle *sh) | |||
1701 | char dummy[2]; | 1563 | char dummy[2]; |
1702 | #endif | 1564 | #endif |
1703 | 1565 | ||
1704 | if (GNUNET_CONFIGURATION_have_value | 1566 | if (GNUNET_CONFIGURATION_have_value (sh->cfg, sh->service_name, "TOLERANT")) |
1705 | (sh->cfg, | ||
1706 | sh->service_name, | ||
1707 | "TOLERANT")) | ||
1708 | { | 1567 | { |
1709 | if (GNUNET_SYSERR == | 1568 | if (GNUNET_SYSERR == |
1710 | (tolerant = | 1569 | (tolerant = GNUNET_CONFIGURATION_get_value_yesno (sh->cfg, |
1711 | GNUNET_CONFIGURATION_get_value_yesno (sh->cfg, | 1570 | sh->service_name, |
1712 | sh->service_name, | 1571 | "TOLERANT"))) |
1713 | "TOLERANT"))) | ||
1714 | { | 1572 | { |
1715 | LOG (GNUNET_ERROR_TYPE_ERROR, | 1573 | LOG (GNUNET_ERROR_TYPE_ERROR, |
1716 | _ ("Specified value for `%s' of service `%s' is invalid\n"), | 1574 | _ ("Specified value for `%s' of service `%s' is invalid\n"), |
@@ -1725,25 +1583,16 @@ setup_service (struct GNUNET_SERVICE_Handle *sh) | |||
1725 | lsocks = NULL; | 1583 | lsocks = NULL; |
1726 | #ifndef MINGW | 1584 | #ifndef MINGW |
1727 | errno = 0; | 1585 | errno = 0; |
1728 | if ( (NULL != (nfds = getenv ("LISTEN_FDS"))) && | 1586 | if ((NULL != (nfds = getenv ("LISTEN_FDS"))) && |
1729 | (1 == SSCANF (nfds, | 1587 | (1 == sscanf (nfds, "%u%1s", &cnt, dummy)) && (cnt > 0) && |
1730 | "%u%1s", | 1588 | (cnt < FD_SETSIZE) && (cnt + 4 < FD_SETSIZE)) |
1731 | &cnt, | ||
1732 | dummy)) && | ||
1733 | (cnt > 0) && | ||
1734 | (cnt < FD_SETSIZE) && | ||
1735 | (cnt + 4 < FD_SETSIZE) ) | ||
1736 | { | 1589 | { |
1737 | lsocks = GNUNET_new_array (cnt + 1, | 1590 | lsocks = GNUNET_new_array (cnt + 1, struct GNUNET_NETWORK_Handle *); |
1738 | struct GNUNET_NETWORK_Handle *); | ||
1739 | while (0 < cnt--) | 1591 | while (0 < cnt--) |
1740 | { | 1592 | { |
1741 | flags = fcntl (3 + cnt, | 1593 | flags = fcntl (3 + cnt, F_GETFD); |
1742 | F_GETFD); | 1594 | if ((flags < 0) || (0 != (flags & FD_CLOEXEC)) || |
1743 | if ( (flags < 0) || | 1595 | (NULL == (lsocks[cnt] = GNUNET_NETWORK_socket_box_native (3 + cnt)))) |
1744 | (0 != (flags & FD_CLOEXEC)) || | ||
1745 | (NULL == | ||
1746 | (lsocks[cnt] = GNUNET_NETWORK_socket_box_native (3 + cnt)))) | ||
1747 | { | 1596 | { |
1748 | LOG (GNUNET_ERROR_TYPE_ERROR, | 1597 | LOG (GNUNET_ERROR_TYPE_ERROR, |
1749 | _ ( | 1598 | _ ( |
@@ -1780,9 +1629,7 @@ setup_service (struct GNUNET_SERVICE_Handle *sh) | |||
1780 | slc = GNUNET_new (struct ServiceListenContext); | 1629 | slc = GNUNET_new (struct ServiceListenContext); |
1781 | slc->sh = sh; | 1630 | slc->sh = sh; |
1782 | slc->listen_socket = *ls; | 1631 | slc->listen_socket = *ls; |
1783 | GNUNET_CONTAINER_DLL_insert (sh->slc_head, | 1632 | GNUNET_CONTAINER_DLL_insert (sh->slc_head, sh->slc_tail, slc); |
1784 | sh->slc_tail, | ||
1785 | slc); | ||
1786 | } | 1633 | } |
1787 | GNUNET_free (lsocks); | 1634 | GNUNET_free (lsocks); |
1788 | } | 1635 | } |
@@ -1792,10 +1639,7 @@ setup_service (struct GNUNET_SERVICE_Handle *sh) | |||
1792 | socklen_t *addrlens; | 1639 | socklen_t *addrlens; |
1793 | int num; | 1640 | int num; |
1794 | 1641 | ||
1795 | num = get_server_addresses (sh->service_name, | 1642 | num = get_server_addresses (sh->service_name, sh->cfg, &addrs, &addrlens); |
1796 | sh->cfg, | ||
1797 | &addrs, | ||
1798 | &addrlens); | ||
1799 | if (GNUNET_SYSERR == num) | 1643 | if (GNUNET_SYSERR == num) |
1800 | return GNUNET_SYSERR; | 1644 | return GNUNET_SYSERR; |
1801 | 1645 | ||
@@ -1805,54 +1649,40 @@ setup_service (struct GNUNET_SERVICE_Handle *sh) | |||
1805 | 1649 | ||
1806 | slc = GNUNET_new (struct ServiceListenContext); | 1650 | slc = GNUNET_new (struct ServiceListenContext); |
1807 | slc->sh = sh; | 1651 | slc->sh = sh; |
1808 | slc->listen_socket = open_listen_socket (addrs[i], | 1652 | slc->listen_socket = open_listen_socket (addrs[i], addrlens[i]); |
1809 | addrlens[i]); | ||
1810 | GNUNET_free (addrs[i]); | 1653 | GNUNET_free (addrs[i]); |
1811 | if (NULL == slc->listen_socket) | 1654 | if (NULL == slc->listen_socket) |
1812 | { | 1655 | { |
1813 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, | 1656 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "bind"); |
1814 | "bind"); | ||
1815 | GNUNET_free (slc); | 1657 | GNUNET_free (slc); |
1816 | continue; | 1658 | continue; |
1817 | } | 1659 | } |
1818 | GNUNET_CONTAINER_DLL_insert (sh->slc_head, | 1660 | GNUNET_CONTAINER_DLL_insert (sh->slc_head, sh->slc_tail, slc); |
1819 | sh->slc_tail, | ||
1820 | slc); | ||
1821 | } | 1661 | } |
1822 | GNUNET_free_non_null (addrlens); | 1662 | GNUNET_free_non_null (addrlens); |
1823 | GNUNET_free_non_null (addrs); | 1663 | GNUNET_free_non_null (addrs); |
1824 | if ( (0 != num) && | 1664 | if ((0 != num) && (NULL == sh->slc_head)) |
1825 | (NULL == sh->slc_head) ) | ||
1826 | { | 1665 | { |
1827 | /* All attempts to bind failed, hard failure */ | 1666 | /* All attempts to bind failed, hard failure */ |
1828 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | 1667 | GNUNET_log ( |
1829 | _ ( | 1668 | GNUNET_ERROR_TYPE_ERROR, |
1830 | "Could not bind to any of the ports I was supposed to, refusing to run!\n")); | 1669 | _ ( |
1670 | "Could not bind to any of the ports I was supposed to, refusing to run!\n")); | ||
1831 | return GNUNET_SYSERR; | 1671 | return GNUNET_SYSERR; |
1832 | } | 1672 | } |
1833 | } | 1673 | } |
1834 | 1674 | ||
1835 | sh->require_found = tolerant ? GNUNET_NO : GNUNET_YES; | 1675 | sh->require_found = tolerant ? GNUNET_NO : GNUNET_YES; |
1836 | sh->match_uid | 1676 | sh->match_uid = GNUNET_CONFIGURATION_get_value_yesno (sh->cfg, |
1837 | = GNUNET_CONFIGURATION_get_value_yesno (sh->cfg, | 1677 | sh->service_name, |
1838 | sh->service_name, | 1678 | "UNIX_MATCH_UID"); |
1839 | "UNIX_MATCH_UID"); | 1679 | sh->match_gid = GNUNET_CONFIGURATION_get_value_yesno (sh->cfg, |
1840 | sh->match_gid | 1680 | sh->service_name, |
1841 | = GNUNET_CONFIGURATION_get_value_yesno (sh->cfg, | 1681 | "UNIX_MATCH_GID"); |
1842 | sh->service_name, | 1682 | process_acl4 (&sh->v4_denied, sh, "REJECT_FROM"); |
1843 | "UNIX_MATCH_GID"); | 1683 | process_acl4 (&sh->v4_allowed, sh, "ACCEPT_FROM"); |
1844 | process_acl4 (&sh->v4_denied, | 1684 | process_acl6 (&sh->v6_denied, sh, "REJECT_FROM6"); |
1845 | sh, | 1685 | process_acl6 (&sh->v6_allowed, sh, "ACCEPT_FROM6"); |
1846 | "REJECT_FROM"); | ||
1847 | process_acl4 (&sh->v4_allowed, | ||
1848 | sh, | ||
1849 | "ACCEPT_FROM"); | ||
1850 | process_acl6 (&sh->v6_denied, | ||
1851 | sh, | ||
1852 | "REJECT_FROM6"); | ||
1853 | process_acl6 (&sh->v6_allowed, | ||
1854 | sh, | ||
1855 | "ACCEPT_FROM6"); | ||
1856 | return GNUNET_OK; | 1686 | return GNUNET_OK; |
1857 | } | 1687 | } |
1858 | 1688 | ||
@@ -1869,11 +1699,10 @@ get_user_name (struct GNUNET_SERVICE_Handle *sh) | |||
1869 | { | 1699 | { |
1870 | char *un; | 1700 | char *un; |
1871 | 1701 | ||
1872 | if (GNUNET_OK != | 1702 | if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (sh->cfg, |
1873 | GNUNET_CONFIGURATION_get_value_filename (sh->cfg, | 1703 | sh->service_name, |
1874 | sh->service_name, | 1704 | "USERNAME", |
1875 | "USERNAME", | 1705 | &un)) |
1876 | &un)) | ||
1877 | return NULL; | 1706 | return NULL; |
1878 | return un; | 1707 | return un; |
1879 | } | 1708 | } |
@@ -1891,7 +1720,7 @@ set_user_id (struct GNUNET_SERVICE_Handle *sh) | |||
1891 | char *user; | 1720 | char *user; |
1892 | 1721 | ||
1893 | if (NULL == (user = get_user_name (sh))) | 1722 | if (NULL == (user = get_user_name (sh))) |
1894 | return GNUNET_OK; /* keep */ | 1723 | return GNUNET_OK; /* keep */ |
1895 | #ifndef MINGW | 1724 | #ifndef MINGW |
1896 | struct passwd *pws; | 1725 | struct passwd *pws; |
1897 | 1726 | ||
@@ -1902,28 +1731,23 @@ set_user_id (struct GNUNET_SERVICE_Handle *sh) | |||
1902 | LOG (GNUNET_ERROR_TYPE_ERROR, | 1731 | LOG (GNUNET_ERROR_TYPE_ERROR, |
1903 | _ ("Cannot obtain information about user `%s': %s\n"), | 1732 | _ ("Cannot obtain information about user `%s': %s\n"), |
1904 | user, | 1733 | user, |
1905 | errno == 0 ? _ ("No such user") : STRERROR (errno)); | 1734 | errno == 0 ? _ ("No such user") : strerror (errno)); |
1906 | GNUNET_free (user); | 1735 | GNUNET_free (user); |
1907 | return GNUNET_SYSERR; | 1736 | return GNUNET_SYSERR; |
1908 | } | 1737 | } |
1909 | if ( (0 != setgid (pws->pw_gid)) || | 1738 | if ((0 != setgid (pws->pw_gid)) || (0 != setegid (pws->pw_gid)) || |
1910 | (0 != setegid (pws->pw_gid)) || | ||
1911 | #if HAVE_INITGROUPS | 1739 | #if HAVE_INITGROUPS |
1912 | (0 != initgroups (user, | 1740 | (0 != initgroups (user, pws->pw_gid)) || |
1913 | pws->pw_gid)) || | ||
1914 | #endif | 1741 | #endif |
1915 | (0 != setuid (pws->pw_uid)) || | 1742 | (0 != setuid (pws->pw_uid)) || (0 != seteuid (pws->pw_uid))) |
1916 | (0 != seteuid (pws->pw_uid))) | ||
1917 | { | 1743 | { |
1918 | if ((0 != setregid (pws->pw_gid, | 1744 | if ((0 != setregid (pws->pw_gid, pws->pw_gid)) || |
1919 | pws->pw_gid)) || | 1745 | (0 != setreuid (pws->pw_uid, pws->pw_uid))) |
1920 | (0 != setreuid (pws->pw_uid, | ||
1921 | pws->pw_uid))) | ||
1922 | { | 1746 | { |
1923 | LOG (GNUNET_ERROR_TYPE_ERROR, | 1747 | LOG (GNUNET_ERROR_TYPE_ERROR, |
1924 | _ ("Cannot change user/group to `%s': %s\n"), | 1748 | _ ("Cannot change user/group to `%s': %s\n"), |
1925 | user, | 1749 | user, |
1926 | STRERROR (errno)); | 1750 | strerror (errno)); |
1927 | GNUNET_free (user); | 1751 | GNUNET_free (user); |
1928 | return GNUNET_SYSERR; | 1752 | return GNUNET_SYSERR; |
1929 | } | 1753 | } |
@@ -1946,11 +1770,10 @@ get_pid_file_name (struct GNUNET_SERVICE_Handle *sh) | |||
1946 | { | 1770 | { |
1947 | char *pif; | 1771 | char *pif; |
1948 | 1772 | ||
1949 | if (GNUNET_OK != | 1773 | if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (sh->cfg, |
1950 | GNUNET_CONFIGURATION_get_value_filename (sh->cfg, | 1774 | sh->service_name, |
1951 | sh->service_name, | 1775 | "PIDFILE", |
1952 | "PIDFILE", | 1776 | &pif)) |
1953 | &pif)) | ||
1954 | return NULL; | 1777 | return NULL; |
1955 | return pif; | 1778 | return pif; |
1956 | } | 1779 | } |
@@ -1967,11 +1790,9 @@ pid_file_delete (struct GNUNET_SERVICE_Handle *sh) | |||
1967 | char *pif = get_pid_file_name (sh); | 1790 | char *pif = get_pid_file_name (sh); |
1968 | 1791 | ||
1969 | if (NULL == pif) | 1792 | if (NULL == pif) |
1970 | return; /* no PID file */ | 1793 | return; /* no PID file */ |
1971 | if (0 != UNLINK (pif)) | 1794 | if (0 != unlink (pif)) |
1972 | LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, | 1795 | LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "unlink", pif); |
1973 | "unlink", | ||
1974 | pif); | ||
1975 | GNUNET_free (pif); | 1796 | GNUNET_free (pif); |
1976 | } | 1797 | } |
1977 | 1798 | ||
@@ -1990,17 +1811,15 @@ detach_terminal (struct GNUNET_SERVICE_Handle *sh) | |||
1990 | int nullfd; | 1811 | int nullfd; |
1991 | int filedes[2]; | 1812 | int filedes[2]; |
1992 | 1813 | ||
1993 | if (0 != PIPE (filedes)) | 1814 | if (0 != pipe (filedes)) |
1994 | { | 1815 | { |
1995 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, | 1816 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "pipe"); |
1996 | "pipe"); | ||
1997 | return GNUNET_SYSERR; | 1817 | return GNUNET_SYSERR; |
1998 | } | 1818 | } |
1999 | pid = fork (); | 1819 | pid = fork (); |
2000 | if (pid < 0) | 1820 | if (pid < 0) |
2001 | { | 1821 | { |
2002 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, | 1822 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "fork"); |
2003 | "fork"); | ||
2004 | return GNUNET_SYSERR; | 1823 | return GNUNET_SYSERR; |
2005 | } | 1824 | } |
2006 | if (0 != pid) | 1825 | if (0 != pid) |
@@ -2008,13 +1827,10 @@ detach_terminal (struct GNUNET_SERVICE_Handle *sh) | |||
2008 | /* Parent */ | 1827 | /* Parent */ |
2009 | char c; | 1828 | char c; |
2010 | 1829 | ||
2011 | GNUNET_break (0 == CLOSE (filedes[1])); | 1830 | GNUNET_break (0 == close (filedes[1])); |
2012 | c = 'X'; | 1831 | c = 'X'; |
2013 | if (1 != READ (filedes[0], | 1832 | if (1 != read (filedes[0], &c, sizeof (char))) |
2014 | &c, | 1833 | LOG_STRERROR (GNUNET_ERROR_TYPE_WARNING, "read"); |
2015 | sizeof (char))) | ||
2016 | LOG_STRERROR (GNUNET_ERROR_TYPE_WARNING, | ||
2017 | "read"); | ||
2018 | fflush (stdout); | 1834 | fflush (stdout); |
2019 | switch (c) | 1835 | switch (c) |
2020 | { | 1836 | { |
@@ -2033,30 +1849,26 @@ detach_terminal (struct GNUNET_SERVICE_Handle *sh) | |||
2033 | _ ("Service process failed to report status\n")); | 1849 | _ ("Service process failed to report status\n")); |
2034 | break; | 1850 | break; |
2035 | } | 1851 | } |
2036 | exit (1); /* child reported error */ | 1852 | exit (1); /* child reported error */ |
2037 | } | 1853 | } |
2038 | GNUNET_break (0 == CLOSE (0)); | 1854 | GNUNET_break (0 == close (0)); |
2039 | GNUNET_break (0 == CLOSE (1)); | 1855 | GNUNET_break (0 == close (1)); |
2040 | GNUNET_break (0 == CLOSE (filedes[0])); | 1856 | GNUNET_break (0 == close (filedes[0])); |
2041 | nullfd = OPEN ("/dev/null", | 1857 | nullfd = open ("/dev/null", O_RDWR | O_APPEND); |
2042 | O_RDWR | O_APPEND); | ||
2043 | if (nullfd < 0) | 1858 | if (nullfd < 0) |
2044 | return GNUNET_SYSERR; | 1859 | return GNUNET_SYSERR; |
2045 | /* set stdin/stdout to /dev/null */ | 1860 | /* set stdin/stdout to /dev/null */ |
2046 | if ( (dup2 (nullfd, 0) < 0) || | 1861 | if ((dup2 (nullfd, 0) < 0) || (dup2 (nullfd, 1) < 0)) |
2047 | (dup2 (nullfd, 1) < 0) ) | ||
2048 | { | 1862 | { |
2049 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, | 1863 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "dup2"); |
2050 | "dup2"); | 1864 | (void) close (nullfd); |
2051 | (void) CLOSE (nullfd); | ||
2052 | return GNUNET_SYSERR; | 1865 | return GNUNET_SYSERR; |
2053 | } | 1866 | } |
2054 | (void) CLOSE (nullfd); | 1867 | (void) close (nullfd); |
2055 | /* Detach from controlling terminal */ | 1868 | /* Detach from controlling terminal */ |
2056 | pid = setsid (); | 1869 | pid = setsid (); |
2057 | if (-1 == pid) | 1870 | if (-1 == pid) |
2058 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, | 1871 | LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "setsid"); |
2059 | "setsid"); | ||
2060 | sh->ready_confirm_fd = filedes[1]; | 1872 | sh->ready_confirm_fd = filedes[1]; |
2061 | #else | 1873 | #else |
2062 | /* FIXME: we probably need to do something else | 1874 | /* FIXME: we probably need to do something else |
@@ -2084,9 +1896,7 @@ teardown_service (struct GNUNET_SERVICE_Handle *sh) | |||
2084 | GNUNET_free_non_null (sh->v6_allowed); | 1896 | GNUNET_free_non_null (sh->v6_allowed); |
2085 | while (NULL != (slc = sh->slc_head)) | 1897 | while (NULL != (slc = sh->slc_head)) |
2086 | { | 1898 | { |
2087 | GNUNET_CONTAINER_DLL_remove (sh->slc_head, | 1899 | GNUNET_CONTAINER_DLL_remove (sh->slc_head, sh->slc_tail, slc); |
2088 | sh->slc_tail, | ||
2089 | slc); | ||
2090 | if (NULL != slc->listen_task) | 1900 | if (NULL != slc->listen_task) |
2091 | GNUNET_SCHEDULER_cancel (slc->listen_task); | 1901 | GNUNET_SCHEDULER_cancel (slc->listen_task); |
2092 | GNUNET_break (GNUNET_OK == | 1902 | GNUNET_break (GNUNET_OK == |
@@ -2103,8 +1913,7 @@ teardown_service (struct GNUNET_SERVICE_Handle *sh) | |||
2103 | * @param msg AGPL request | 1913 | * @param msg AGPL request |
2104 | */ | 1914 | */ |
2105 | static void | 1915 | static void |
2106 | return_agpl (void *cls, | 1916 | return_agpl (void *cls, const struct GNUNET_MessageHeader *msg) |
2107 | const struct GNUNET_MessageHeader *msg) | ||
2108 | { | 1917 | { |
2109 | struct GNUNET_SERVICE_Client *client = cls; | 1918 | struct GNUNET_SERVICE_Client *client = cls; |
2110 | struct GNUNET_MQ_Handle *mq; | 1919 | struct GNUNET_MQ_Handle *mq; |
@@ -2114,15 +1923,10 @@ return_agpl (void *cls, | |||
2114 | 1923 | ||
2115 | (void) msg; | 1924 | (void) msg; |
2116 | slen = strlen (GNUNET_AGPL_URL) + 1; | 1925 | slen = strlen (GNUNET_AGPL_URL) + 1; |
2117 | env = GNUNET_MQ_msg_extra (res, | 1926 | env = GNUNET_MQ_msg_extra (res, GNUNET_MESSAGE_TYPE_RESPONSE_AGPL, slen); |
2118 | GNUNET_MESSAGE_TYPE_RESPONSE_AGPL, | 1927 | memcpy (&res[1], GNUNET_AGPL_URL, slen); |
2119 | slen); | ||
2120 | memcpy (&res[1], | ||
2121 | GNUNET_AGPL_URL, | ||
2122 | slen); | ||
2123 | mq = GNUNET_SERVICE_client_get_mq (client); | 1928 | mq = GNUNET_SERVICE_client_get_mq (client); |
2124 | GNUNET_MQ_send (mq, | 1929 | GNUNET_MQ_send (mq, env); |
2125 | env); | ||
2126 | GNUNET_SERVICE_client_continue (client); | 1930 | GNUNET_SERVICE_client_continue (client); |
2127 | } | 1931 | } |
2128 | 1932 | ||
@@ -2179,17 +1983,14 @@ GNUNET_SERVICE_start (const char *service_name, | |||
2179 | sh->connect_cb = connect_cb; | 1983 | sh->connect_cb = connect_cb; |
2180 | sh->disconnect_cb = disconnect_cb; | 1984 | sh->disconnect_cb = disconnect_cb; |
2181 | sh->cb_cls = cls; | 1985 | sh->cb_cls = cls; |
2182 | sh->handlers = GNUNET_MQ_copy_handlers2 (handlers, | 1986 | sh->handlers = GNUNET_MQ_copy_handlers2 (handlers, &return_agpl, NULL); |
2183 | &return_agpl, | ||
2184 | NULL); | ||
2185 | if (GNUNET_OK != setup_service (sh)) | 1987 | if (GNUNET_OK != setup_service (sh)) |
2186 | { | 1988 | { |
2187 | GNUNET_free_non_null (sh->handlers); | 1989 | GNUNET_free_non_null (sh->handlers); |
2188 | GNUNET_free (sh); | 1990 | GNUNET_free (sh); |
2189 | return NULL; | 1991 | return NULL; |
2190 | } | 1992 | } |
2191 | do_resume (sh, | 1993 | do_resume (sh, SUSPEND_STATE_NONE); |
2192 | SUSPEND_STATE_NONE); | ||
2193 | return sh; | 1994 | return sh; |
2194 | } | 1995 | } |
2195 | 1996 | ||
@@ -2279,24 +2080,21 @@ GNUNET_SERVICE_run_ (int argc, | |||
2279 | int ret; | 2080 | int ret; |
2280 | int err; | 2081 | int err; |
2281 | 2082 | ||
2282 | struct GNUNET_GETOPT_CommandLineOption service_options[] = { | 2083 | struct GNUNET_GETOPT_CommandLineOption service_options[] = |
2283 | GNUNET_GETOPT_option_cfgfile (&opt_cfg_filename), | 2084 | {GNUNET_GETOPT_option_cfgfile (&opt_cfg_filename), |
2284 | GNUNET_GETOPT_option_flag ('d', | 2085 | GNUNET_GETOPT_option_flag ('d', |
2285 | "daemonize", | 2086 | "daemonize", |
2286 | gettext_noop ( | 2087 | gettext_noop ( |
2287 | "do daemonize (detach from terminal)"), | 2088 | "do daemonize (detach from terminal)"), |
2288 | &do_daemonize), | 2089 | &do_daemonize), |
2289 | GNUNET_GETOPT_option_help (NULL), | 2090 | GNUNET_GETOPT_option_help (NULL), |
2290 | GNUNET_GETOPT_option_loglevel (&loglev), | 2091 | GNUNET_GETOPT_option_loglevel (&loglev), |
2291 | GNUNET_GETOPT_option_logfile (&logfile), | 2092 | GNUNET_GETOPT_option_logfile (&logfile), |
2292 | GNUNET_GETOPT_option_version (PACKAGE_VERSION " " VCS_VERSION), | 2093 | GNUNET_GETOPT_option_version (PACKAGE_VERSION " " VCS_VERSION), |
2293 | GNUNET_GETOPT_OPTION_END | 2094 | GNUNET_GETOPT_OPTION_END}; |
2294 | }; | ||
2295 | 2095 | ||
2296 | err = 1; | 2096 | err = 1; |
2297 | memset (&sh, | 2097 | memset (&sh, 0, sizeof (sh)); |
2298 | 0, | ||
2299 | sizeof (sh)); | ||
2300 | xdg = getenv ("XDG_CONFIG_HOME"); | 2098 | xdg = getenv ("XDG_CONFIG_HOME"); |
2301 | if (NULL != xdg) | 2099 | if (NULL != xdg) |
2302 | GNUNET_asprintf (&cfg_filename, | 2100 | GNUNET_asprintf (&cfg_filename, |
@@ -2305,8 +2103,8 @@ GNUNET_SERVICE_run_ (int argc, | |||
2305 | DIR_SEPARATOR_STR, | 2103 | DIR_SEPARATOR_STR, |
2306 | GNUNET_OS_project_data_get ()->config_file); | 2104 | GNUNET_OS_project_data_get ()->config_file); |
2307 | else | 2105 | else |
2308 | cfg_filename = GNUNET_strdup ( | 2106 | cfg_filename = |
2309 | GNUNET_OS_project_data_get ()->user_config_file); | 2107 | GNUNET_strdup (GNUNET_OS_project_data_get ()->user_config_file); |
2310 | sh.ready_confirm_fd = -1; | 2108 | sh.ready_confirm_fd = -1; |
2311 | sh.options = options; | 2109 | sh.options = options; |
2312 | sh.cfg = cfg = GNUNET_CONFIGURATION_create (); | 2110 | sh.cfg = cfg = GNUNET_CONFIGURATION_create (); |
@@ -2322,10 +2120,7 @@ GNUNET_SERVICE_run_ (int argc, | |||
2322 | logfile = NULL; | 2120 | logfile = NULL; |
2323 | opt_cfg_filename = NULL; | 2121 | opt_cfg_filename = NULL; |
2324 | do_daemonize = 0; | 2122 | do_daemonize = 0; |
2325 | ret = GNUNET_GETOPT_run (service_name, | 2123 | ret = GNUNET_GETOPT_run (service_name, service_options, argc, argv); |
2326 | service_options, | ||
2327 | argc, | ||
2328 | argv); | ||
2329 | if (GNUNET_SYSERR == ret) | 2124 | if (GNUNET_SYSERR == ret) |
2330 | goto shutdown; | 2125 | goto shutdown; |
2331 | if (GNUNET_NO == ret) | 2126 | if (GNUNET_NO == ret) |
@@ -2333,20 +2128,15 @@ GNUNET_SERVICE_run_ (int argc, | |||
2333 | err = 0; | 2128 | err = 0; |
2334 | goto shutdown; | 2129 | goto shutdown; |
2335 | } | 2130 | } |
2336 | if (GNUNET_OK != GNUNET_log_setup (service_name, | 2131 | if (GNUNET_OK != GNUNET_log_setup (service_name, loglev, logfile)) |
2337 | loglev, | ||
2338 | logfile)) | ||
2339 | { | 2132 | { |
2340 | GNUNET_break (0); | 2133 | GNUNET_break (0); |
2341 | goto shutdown; | 2134 | goto shutdown; |
2342 | } | 2135 | } |
2343 | if (NULL != opt_cfg_filename) | 2136 | if (NULL != opt_cfg_filename) |
2344 | { | 2137 | { |
2345 | if ( (GNUNET_YES != | 2138 | if ((GNUNET_YES != GNUNET_DISK_file_test (opt_cfg_filename)) || |
2346 | GNUNET_DISK_file_test (opt_cfg_filename)) || | 2139 | (GNUNET_SYSERR == GNUNET_CONFIGURATION_load (cfg, opt_cfg_filename))) |
2347 | (GNUNET_SYSERR == | ||
2348 | GNUNET_CONFIGURATION_load (cfg, | ||
2349 | opt_cfg_filename)) ) | ||
2350 | { | 2140 | { |
2351 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | 2141 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
2352 | _ ("Malformed configuration file `%s', exit ...\n"), | 2142 | _ ("Malformed configuration file `%s', exit ...\n"), |
@@ -2356,12 +2146,9 @@ GNUNET_SERVICE_run_ (int argc, | |||
2356 | } | 2146 | } |
2357 | else | 2147 | else |
2358 | { | 2148 | { |
2359 | if (GNUNET_YES == | 2149 | if (GNUNET_YES == GNUNET_DISK_file_test (cfg_filename)) |
2360 | GNUNET_DISK_file_test (cfg_filename)) | ||
2361 | { | 2150 | { |
2362 | if (GNUNET_SYSERR == | 2151 | if (GNUNET_SYSERR == GNUNET_CONFIGURATION_load (cfg, cfg_filename)) |
2363 | GNUNET_CONFIGURATION_load (cfg, | ||
2364 | cfg_filename)) | ||
2365 | { | 2152 | { |
2366 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | 2153 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
2367 | _ ("Malformed configuration file `%s', exit ...\n"), | 2154 | _ ("Malformed configuration file `%s', exit ...\n"), |
@@ -2371,9 +2158,7 @@ GNUNET_SERVICE_run_ (int argc, | |||
2371 | } | 2158 | } |
2372 | else | 2159 | else |
2373 | { | 2160 | { |
2374 | if (GNUNET_SYSERR == | 2161 | if (GNUNET_SYSERR == GNUNET_CONFIGURATION_load (cfg, NULL)) |
2375 | GNUNET_CONFIGURATION_load (cfg, | ||
2376 | NULL)) | ||
2377 | { | 2162 | { |
2378 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | 2163 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
2379 | _ ("Malformed configuration, exit ...\n")); | 2164 | _ ("Malformed configuration, exit ...\n")); |
@@ -2383,8 +2168,7 @@ GNUNET_SERVICE_run_ (int argc, | |||
2383 | } | 2168 | } |
2384 | if (GNUNET_OK != setup_service (&sh)) | 2169 | if (GNUNET_OK != setup_service (&sh)) |
2385 | goto shutdown; | 2170 | goto shutdown; |
2386 | if ( (1 == do_daemonize) && | 2171 | if ((1 == do_daemonize) && (GNUNET_OK != detach_terminal (&sh))) |
2387 | (GNUNET_OK != detach_terminal (&sh)) ) | ||
2388 | { | 2172 | { |
2389 | GNUNET_break (0); | 2173 | GNUNET_break (0); |
2390 | goto shutdown; | 2174 | goto shutdown; |
@@ -2395,64 +2179,51 @@ GNUNET_SERVICE_run_ (int argc, | |||
2395 | "Service `%s' runs with configuration from `%s'\n", | 2179 | "Service `%s' runs with configuration from `%s'\n", |
2396 | service_name, | 2180 | service_name, |
2397 | (NULL != opt_cfg_filename) ? opt_cfg_filename : cfg_filename); | 2181 | (NULL != opt_cfg_filename) ? opt_cfg_filename : cfg_filename); |
2398 | if ((GNUNET_OK == | 2182 | if ((GNUNET_OK == GNUNET_CONFIGURATION_get_value_number (sh.cfg, |
2399 | GNUNET_CONFIGURATION_get_value_number (sh.cfg, | 2183 | "TESTING", |
2400 | "TESTING", | 2184 | "SKEW_OFFSET", |
2401 | "SKEW_OFFSET", | 2185 | &skew_offset)) && |
2402 | &skew_offset)) && | 2186 | (GNUNET_OK == GNUNET_CONFIGURATION_get_value_number (sh.cfg, |
2403 | (GNUNET_OK == | 2187 | "TESTING", |
2404 | GNUNET_CONFIGURATION_get_value_number (sh.cfg, | 2188 | "SKEW_VARIANCE", |
2405 | "TESTING", | 2189 | &skew_variance))) |
2406 | "SKEW_VARIANCE", | ||
2407 | &skew_variance))) | ||
2408 | { | 2190 | { |
2409 | clock_offset = skew_offset - skew_variance; | 2191 | clock_offset = skew_offset - skew_variance; |
2410 | GNUNET_TIME_set_offset (clock_offset); | 2192 | GNUNET_TIME_set_offset (clock_offset); |
2411 | LOG (GNUNET_ERROR_TYPE_DEBUG, | 2193 | LOG (GNUNET_ERROR_TYPE_DEBUG, "Skewing clock by %dll ms\n", clock_offset); |
2412 | "Skewing clock by %dll ms\n", | ||
2413 | clock_offset); | ||
2414 | } | 2194 | } |
2415 | GNUNET_RESOLVER_connect (sh.cfg); | 2195 | GNUNET_RESOLVER_connect (sh.cfg); |
2416 | 2196 | ||
2417 | /* actually run service */ | 2197 | /* actually run service */ |
2418 | err = 0; | 2198 | err = 0; |
2419 | GNUNET_SCHEDULER_run (&service_main, | 2199 | GNUNET_SCHEDULER_run (&service_main, &sh); |
2420 | &sh); | ||
2421 | /* shutdown */ | 2200 | /* shutdown */ |
2422 | if (1 == do_daemonize) | 2201 | if (1 == do_daemonize) |
2423 | pid_file_delete (&sh); | 2202 | pid_file_delete (&sh); |
2424 | 2203 | ||
2425 | shutdown: | 2204 | shutdown: |
2426 | if (-1 != sh.ready_confirm_fd) | 2205 | if (-1 != sh.ready_confirm_fd) |
2427 | { | 2206 | { |
2428 | if (1 != WRITE (sh.ready_confirm_fd, | 2207 | if (1 != write (sh.ready_confirm_fd, err ? "I" : "S", 1)) |
2429 | err ? "I" : "S", | 2208 | LOG_STRERROR (GNUNET_ERROR_TYPE_WARNING, "write"); |
2430 | 1)) | 2209 | GNUNET_break (0 == close (sh.ready_confirm_fd)); |
2431 | LOG_STRERROR (GNUNET_ERROR_TYPE_WARNING, | ||
2432 | "write"); | ||
2433 | GNUNET_break (0 == CLOSE (sh.ready_confirm_fd)); | ||
2434 | } | 2210 | } |
2435 | #if HAVE_MALLINFO | 2211 | #if HAVE_MALLINFO |
2436 | { | 2212 | { |
2437 | char *counter; | 2213 | char *counter; |
2438 | 2214 | ||
2439 | if ( (GNUNET_YES == | 2215 | if ((GNUNET_YES == GNUNET_CONFIGURATION_have_value (sh.cfg, |
2440 | GNUNET_CONFIGURATION_have_value (sh.cfg, | 2216 | service_name, |
2441 | service_name, | 2217 | "GAUGER_HEAP")) && |
2442 | "GAUGER_HEAP")) && | 2218 | (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string (sh.cfg, |
2443 | (GNUNET_OK == | 2219 | service_name, |
2444 | GNUNET_CONFIGURATION_get_value_string (sh.cfg, | 2220 | "GAUGER_HEAP", |
2445 | service_name, | 2221 | &counter))) |
2446 | "GAUGER_HEAP", | ||
2447 | &counter)) ) | ||
2448 | { | 2222 | { |
2449 | struct mallinfo mi; | 2223 | struct mallinfo mi; |
2450 | 2224 | ||
2451 | mi = mallinfo (); | 2225 | mi = mallinfo (); |
2452 | GAUGER (service_name, | 2226 | GAUGER (service_name, counter, mi.usmblks, "blocks"); |
2453 | counter, | ||
2454 | mi.usmblks, | ||
2455 | "blocks"); | ||
2456 | GNUNET_free (counter); | 2227 | GNUNET_free (counter); |
2457 | } | 2228 | } |
2458 | } | 2229 | } |
@@ -2479,8 +2250,7 @@ GNUNET_SERVICE_run_ (int argc, | |||
2479 | void | 2250 | void |
2480 | GNUNET_SERVICE_suspend (struct GNUNET_SERVICE_Handle *sh) | 2251 | GNUNET_SERVICE_suspend (struct GNUNET_SERVICE_Handle *sh) |
2481 | { | 2252 | { |
2482 | do_suspend (sh, | 2253 | do_suspend (sh, SUSPEND_STATE_APP); |
2483 | SUSPEND_STATE_APP); | ||
2484 | } | 2254 | } |
2485 | 2255 | ||
2486 | 2256 | ||
@@ -2492,8 +2262,7 @@ GNUNET_SERVICE_suspend (struct GNUNET_SERVICE_Handle *sh) | |||
2492 | void | 2262 | void |
2493 | GNUNET_SERVICE_resume (struct GNUNET_SERVICE_Handle *sh) | 2263 | GNUNET_SERVICE_resume (struct GNUNET_SERVICE_Handle *sh) |
2494 | { | 2264 | { |
2495 | do_resume (sh, | 2265 | do_resume (sh, SUSPEND_STATE_APP); |
2496 | SUSPEND_STATE_APP); | ||
2497 | } | 2266 | } |
2498 | 2267 | ||
2499 | 2268 | ||
@@ -2511,8 +2280,7 @@ resume_client_receive (void *cls) | |||
2511 | 2280 | ||
2512 | c->recv_task = NULL; | 2281 | c->recv_task = NULL; |
2513 | /* first, check if there is still something in the buffer */ | 2282 | /* first, check if there is still something in the buffer */ |
2514 | ret = GNUNET_MST_next (c->mst, | 2283 | ret = GNUNET_MST_next (c->mst, GNUNET_YES); |
2515 | GNUNET_YES); | ||
2516 | if (GNUNET_SYSERR == ret) | 2284 | if (GNUNET_SYSERR == ret) |
2517 | { | 2285 | { |
2518 | if (NULL == c->drop_task) | 2286 | if (NULL == c->drop_task) |
@@ -2527,11 +2295,10 @@ resume_client_receive (void *cls) | |||
2527 | /* need to receive more data from the network first */ | 2295 | /* need to receive more data from the network first */ |
2528 | if (NULL != c->recv_task) | 2296 | if (NULL != c->recv_task) |
2529 | return; | 2297 | return; |
2530 | c->recv_task | 2298 | c->recv_task = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, |
2531 | = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, | 2299 | c->sock, |
2532 | c->sock, | 2300 | &service_client_recv, |
2533 | &service_client_recv, | 2301 | c); |
2534 | c); | ||
2535 | } | 2302 | } |
2536 | 2303 | ||
2537 | 2304 | ||
@@ -2553,9 +2320,7 @@ GNUNET_SERVICE_client_continue (struct GNUNET_SERVICE_Client *c) | |||
2553 | GNUNET_SCHEDULER_cancel (c->warn_task); | 2320 | GNUNET_SCHEDULER_cancel (c->warn_task); |
2554 | c->warn_task = NULL; | 2321 | c->warn_task = NULL; |
2555 | } | 2322 | } |
2556 | c->recv_task | 2323 | c->recv_task = GNUNET_SCHEDULER_add_now (&resume_client_receive, c); |
2557 | = GNUNET_SCHEDULER_add_now (&resume_client_receive, | ||
2558 | c); | ||
2559 | } | 2324 | } |
2560 | 2325 | ||
2561 | 2326 | ||
@@ -2598,20 +2363,18 @@ finish_client_drop (void *cls) | |||
2598 | GNUNET_MQ_destroy (c->mq); | 2363 | GNUNET_MQ_destroy (c->mq); |
2599 | if (GNUNET_NO == c->persist) | 2364 | if (GNUNET_NO == c->persist) |
2600 | { | 2365 | { |
2601 | GNUNET_break (GNUNET_OK == | 2366 | GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (c->sock)); |
2602 | GNUNET_NETWORK_socket_close (c->sock)); | 2367 | if ((0 != (SUSPEND_STATE_EMFILE & sh->suspend_state)) && |
2603 | if ( (0 != (SUSPEND_STATE_EMFILE & sh->suspend_state)) && | 2368 | (0 == (SUSPEND_STATE_SHUTDOWN & sh->suspend_state))) |
2604 | (0 == (SUSPEND_STATE_SHUTDOWN & sh->suspend_state)) ) | 2369 | do_resume (sh, SUSPEND_STATE_EMFILE); |
2605 | do_resume (sh, | ||
2606 | SUSPEND_STATE_EMFILE); | ||
2607 | } | 2370 | } |
2608 | else | 2371 | else |
2609 | { | 2372 | { |
2610 | GNUNET_NETWORK_socket_free_memory_only_ (c->sock); | 2373 | GNUNET_NETWORK_socket_free_memory_only_ (c->sock); |
2611 | } | 2374 | } |
2612 | GNUNET_free (c); | 2375 | GNUNET_free (c); |
2613 | if ( (0 != (SUSPEND_STATE_SHUTDOWN & sh->suspend_state)) && | 2376 | if ((0 != (SUSPEND_STATE_SHUTDOWN & sh->suspend_state)) && |
2614 | (GNUNET_NO == have_non_monitor_clients (sh)) ) | 2377 | (GNUNET_NO == have_non_monitor_clients (sh))) |
2615 | GNUNET_SERVICE_shutdown (sh); | 2378 | GNUNET_SERVICE_shutdown (sh); |
2616 | } | 2379 | } |
2617 | 2380 | ||
@@ -2640,8 +2403,7 @@ GNUNET_SERVICE_client_drop (struct GNUNET_SERVICE_Client *c) | |||
2640 | void *backtrace_array[MAX_TRACE_DEPTH]; | 2403 | void *backtrace_array[MAX_TRACE_DEPTH]; |
2641 | int num_backtrace_strings = backtrace (backtrace_array, MAX_TRACE_DEPTH); | 2404 | int num_backtrace_strings = backtrace (backtrace_array, MAX_TRACE_DEPTH); |
2642 | char **backtrace_strings = | 2405 | char **backtrace_strings = |
2643 | backtrace_symbols (backtrace_array, | 2406 | backtrace_symbols (backtrace_array, t->num_backtrace_strings); |
2644 | t->num_backtrace_strings); | ||
2645 | for (unsigned int i = 0; i < num_backtrace_strings; i++) | 2407 | for (unsigned int i = 0; i < num_backtrace_strings; i++) |
2646 | LOG (GNUNET_ERROR_TYPE_DEBUG, | 2408 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
2647 | "client drop trace %u: %s\n", | 2409 | "client drop trace %u: %s\n", |
@@ -2655,13 +2417,9 @@ GNUNET_SERVICE_client_drop (struct GNUNET_SERVICE_Client *c) | |||
2655 | GNUNET_assert (0); | 2417 | GNUNET_assert (0); |
2656 | return; | 2418 | return; |
2657 | } | 2419 | } |
2658 | GNUNET_CONTAINER_DLL_remove (sh->clients_head, | 2420 | GNUNET_CONTAINER_DLL_remove (sh->clients_head, sh->clients_tail, c); |
2659 | sh->clients_tail, | ||
2660 | c); | ||
2661 | if (NULL != sh->disconnect_cb) | 2421 | if (NULL != sh->disconnect_cb) |
2662 | sh->disconnect_cb (sh->cb_cls, | 2422 | sh->disconnect_cb (sh->cb_cls, c, c->user_context); |
2663 | c, | ||
2664 | c->user_context); | ||
2665 | if (NULL != c->warn_task) | 2423 | if (NULL != c->warn_task) |
2666 | { | 2424 | { |
2667 | GNUNET_SCHEDULER_cancel (c->warn_task); | 2425 | GNUNET_SCHEDULER_cancel (c->warn_task); |
@@ -2677,8 +2435,7 @@ GNUNET_SERVICE_client_drop (struct GNUNET_SERVICE_Client *c) | |||
2677 | GNUNET_SCHEDULER_cancel (c->send_task); | 2435 | GNUNET_SCHEDULER_cancel (c->send_task); |
2678 | c->send_task = NULL; | 2436 | c->send_task = NULL; |
2679 | } | 2437 | } |
2680 | c->drop_task = GNUNET_SCHEDULER_add_now (&finish_client_drop, | 2438 | c->drop_task = GNUNET_SCHEDULER_add_now (&finish_client_drop, c); |
2681 | c); | ||
2682 | } | 2439 | } |
2683 | 2440 | ||
2684 | 2441 | ||
@@ -2693,8 +2450,7 @@ GNUNET_SERVICE_shutdown (struct GNUNET_SERVICE_Handle *sh) | |||
2693 | struct GNUNET_SERVICE_Client *client; | 2450 | struct GNUNET_SERVICE_Client *client; |
2694 | 2451 | ||
2695 | if (0 == (sh->suspend_state & SUSPEND_STATE_SHUTDOWN)) | 2452 | if (0 == (sh->suspend_state & SUSPEND_STATE_SHUTDOWN)) |
2696 | do_suspend (sh, | 2453 | do_suspend (sh, SUSPEND_STATE_SHUTDOWN); |
2697 | SUSPEND_STATE_SHUTDOWN); | ||
2698 | while (NULL != (client = sh->clients_head)) | 2454 | while (NULL != (client = sh->clients_head)) |
2699 | GNUNET_SERVICE_client_drop (client); | 2455 | GNUNET_SERVICE_client_drop (client); |
2700 | } | 2456 | } |
@@ -2716,8 +2472,8 @@ void | |||
2716 | GNUNET_SERVICE_client_mark_monitor (struct GNUNET_SERVICE_Client *c) | 2472 | GNUNET_SERVICE_client_mark_monitor (struct GNUNET_SERVICE_Client *c) |
2717 | { | 2473 | { |
2718 | c->is_monitor = GNUNET_YES; | 2474 | c->is_monitor = GNUNET_YES; |
2719 | if ( ((0 != (SUSPEND_STATE_SHUTDOWN & c->sh->suspend_state))&& | 2475 | if (((0 != (SUSPEND_STATE_SHUTDOWN & c->sh->suspend_state)) && |
2720 | (GNUNET_NO == have_non_monitor_clients (c->sh)) ) ) | 2476 | (GNUNET_NO == have_non_monitor_clients (c->sh)))) |
2721 | GNUNET_SERVICE_shutdown (c->sh); | 2477 | GNUNET_SERVICE_shutdown (c->sh); |
2722 | } | 2478 | } |
2723 | 2479 | ||