aboutsummaryrefslogtreecommitdiff
path: root/src/dht/gnunet-dht-driver.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/dht/gnunet-dht-driver.c')
-rw-r--r--src/dht/gnunet-dht-driver.c3415
1 files changed, 1696 insertions, 1719 deletions
diff --git a/src/dht/gnunet-dht-driver.c b/src/dht/gnunet-dht-driver.c
index 6039e196b..a5158fba5 100644
--- a/src/dht/gnunet-dht-driver.c
+++ b/src/dht/gnunet-dht-driver.c
@@ -778,11 +778,9 @@ static char *blacklist_transports;
778 778
779static enum GNUNET_TESTING_Topology topology; 779static enum GNUNET_TESTING_Topology topology;
780 780
781static enum GNUNET_TESTING_Topology blacklist_topology = 781static enum GNUNET_TESTING_Topology blacklist_topology = GNUNET_TESTING_TOPOLOGY_NONE; /* Don't do any blacklisting */
782 GNUNET_TESTING_TOPOLOGY_NONE; /* Don't do any blacklisting */
783 782
784static enum GNUNET_TESTING_Topology connect_topology = 783static enum GNUNET_TESTING_Topology connect_topology = GNUNET_TESTING_TOPOLOGY_NONE; /* NONE actually means connect all allowed peers */
785 GNUNET_TESTING_TOPOLOGY_NONE; /* NONE actually means connect all allowed peers */
786 784
787static enum GNUNET_TESTING_TopologyOption connect_topology_option = 785static enum GNUNET_TESTING_TopologyOption connect_topology_option =
788 GNUNET_TESTING_TOPOLOGY_OPTION_ALL; 786 GNUNET_TESTING_TOPOLOGY_OPTION_ALL;
@@ -815,18 +813,19 @@ static int ok;
815 * @return the progress meter 813 * @return the progress meter
816 */ 814 */
817static struct ProgressMeter * 815static struct ProgressMeter *
818create_meter(unsigned int total, char * start_string, int print) 816create_meter (unsigned int total, char *start_string, int print)
819{ 817{
820 struct ProgressMeter *ret; 818 struct ProgressMeter *ret;
821 ret = GNUNET_malloc(sizeof(struct ProgressMeter)); 819
820 ret = GNUNET_malloc (sizeof (struct ProgressMeter));
822 ret->print = print; 821 ret->print = print;
823 ret->total = total; 822 ret->total = total;
824 ret->modnum = total / 4; 823 ret->modnum = total / 4;
825 ret->dotnum = (total / 50) + 1; 824 ret->dotnum = (total / 50) + 1;
826 if (start_string != NULL) 825 if (start_string != NULL)
827 ret->startup_string = GNUNET_strdup(start_string); 826 ret->startup_string = GNUNET_strdup (start_string);
828 else 827 else
829 ret->startup_string = GNUNET_strdup(""); 828 ret->startup_string = GNUNET_strdup ("");
830 829
831 return ret; 830 return ret;
832} 831}
@@ -840,27 +839,27 @@ create_meter(unsigned int total, char * start_string, int print)
840 * GNUNET_NO if more items expected 839 * GNUNET_NO if more items expected
841 */ 840 */
842static int 841static int
843update_meter(struct ProgressMeter *meter) 842update_meter (struct ProgressMeter *meter)
844{ 843{
845 if (meter->print == GNUNET_YES) 844 if (meter->print == GNUNET_YES)
845 {
846 if (meter->completed % meter->modnum == 0)
846 { 847 {
847 if (meter->completed % meter->modnum == 0) 848 if (meter->completed == 0)
848 { 849 {
849 if (meter->completed == 0) 850 fprintf (stdout, "%sProgress: [0%%", meter->startup_string);
850 { 851 }
851 fprintf (stdout, "%sProgress: [0%%", meter->startup_string); 852 else
852 } 853 fprintf (stdout, "%d%%", (int) (((float) meter->completed
853 else 854 / meter->total) * 100));
854 fprintf (stdout, "%d%%", (int) (((float) meter->completed
855 / meter->total) * 100));
856 }
857 else if (meter->completed % meter->dotnum == 0)
858 fprintf (stdout, ".");
859
860 if (meter->completed + 1 == meter->total)
861 fprintf (stdout, "%d%%]\n", 100);
862 fflush (stdout);
863 } 855 }
856 else if (meter->completed % meter->dotnum == 0)
857 fprintf (stdout, ".");
858
859 if (meter->completed + 1 == meter->total)
860 fprintf (stdout, "%d%%]\n", 100);
861 fflush (stdout);
862 }
864 meter->completed++; 863 meter->completed++;
865 864
866 if (meter->completed == meter->total) 865 if (meter->completed == meter->total)
@@ -877,7 +876,7 @@ update_meter(struct ProgressMeter *meter)
877 * GNUNET_SYSERR on error 876 * GNUNET_SYSERR on error
878 */ 877 */
879static int 878static int
880reset_meter(struct ProgressMeter *meter) 879reset_meter (struct ProgressMeter *meter)
881{ 880{
882 if (meter == NULL) 881 if (meter == NULL)
883 return GNUNET_SYSERR; 882 return GNUNET_SYSERR;
@@ -892,7 +891,7 @@ reset_meter(struct ProgressMeter *meter)
892 * @param meter the meter to free 891 * @param meter the meter to free
893 */ 892 */
894static void 893static void
895free_meter(struct ProgressMeter *meter) 894free_meter (struct ProgressMeter *meter)
896{ 895{
897 GNUNET_free_non_null (meter->startup_string); 896 GNUNET_free_non_null (meter->startup_string);
898 GNUNET_free (meter); 897 GNUNET_free (meter);
@@ -902,32 +901,31 @@ free_meter(struct ProgressMeter *meter)
902 * Check whether peers successfully shut down. 901 * Check whether peers successfully shut down.
903 */ 902 */
904static void 903static void
905shutdown_callback(void *cls, const char *emsg) 904shutdown_callback (void *cls, const char *emsg)
906{ 905{
907 if (emsg != NULL) 906 if (emsg != NULL)
908 { 907 {
909 if (ok == 0) 908 if (ok == 0)
910 ok = 2; 909 ok = 2;
911 } 910 }
912} 911}
913 912
914/** 913/**
915 * Task to release DHT handles for PUT 914 * Task to release DHT handles for PUT
916 */ 915 */
917static void 916static void
918put_disconnect_task(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 917put_disconnect_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
919{ 918{
920 struct TestPutContext *test_put = cls; 919 struct TestPutContext *test_put = cls;
920
921 test_put->disconnect_task = GNUNET_SCHEDULER_NO_TASK; 921 test_put->disconnect_task = GNUNET_SCHEDULER_NO_TASK;
922 GNUNET_DHT_disconnect (test_put->dht_handle); 922 GNUNET_DHT_disconnect (test_put->dht_handle);
923 test_put->dht_handle = NULL; 923 test_put->dht_handle = NULL;
924 if (replicate_same == GNUNET_NO) 924 if (replicate_same == GNUNET_NO)
925 test_put->daemon 925 test_put->daemon
926 = GNUNET_TESTING_daemon_get ( 926 = GNUNET_TESTING_daemon_get (pg,
927 pg, 927 GNUNET_CRYPTO_random_u32
928 GNUNET_CRYPTO_random_u32 ( 928 (GNUNET_CRYPTO_QUALITY_WEAK, num_peers));
929 GNUNET_CRYPTO_QUALITY_WEAK,
930 num_peers));
931} 929}
932 930
933/** 931/**
@@ -935,7 +933,7 @@ put_disconnect_task(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
935 * testcase. 933 * testcase.
936 */ 934 */
937static void 935static void
938finish_testing(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 936finish_testing (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
939{ 937{
940 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Ending test normally!\n", 938 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Ending test normally!\n",
941 (char *) cls); 939 (char *) cls);
@@ -946,34 +944,34 @@ finish_testing(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
946 char *revision_str; 944 char *revision_str;
947 945
948 while (test_put != NULL) 946 while (test_put != NULL)
949 { 947 {
950 if (test_put->disconnect_task != GNUNET_SCHEDULER_NO_TASK) 948 if (test_put->disconnect_task != GNUNET_SCHEDULER_NO_TASK)
951 GNUNET_SCHEDULER_cancel (test_put->disconnect_task); 949 GNUNET_SCHEDULER_cancel (test_put->disconnect_task);
952 if (test_put->dht_handle != NULL) 950 if (test_put->dht_handle != NULL)
953 GNUNET_DHT_disconnect (test_put->dht_handle); 951 GNUNET_DHT_disconnect (test_put->dht_handle);
954 test_put = test_put->next; 952 test_put = test_put->next;
955 } 953 }
956 954
957 while (test_get != NULL) 955 while (test_get != NULL)
958 { 956 {
959 if (test_get->disconnect_task != GNUNET_SCHEDULER_NO_TASK) 957 if (test_get->disconnect_task != GNUNET_SCHEDULER_NO_TASK)
960 GNUNET_SCHEDULER_cancel (test_get->disconnect_task); 958 GNUNET_SCHEDULER_cancel (test_get->disconnect_task);
961 if (test_get->get_handle != NULL) 959 if (test_get->get_handle != NULL)
962 GNUNET_DHT_get_stop (test_get->get_handle); 960 GNUNET_DHT_get_stop (test_get->get_handle);
963 if (test_get->dht_handle != NULL) 961 if (test_get->dht_handle != NULL)
964 GNUNET_DHT_disconnect (test_get->dht_handle); 962 GNUNET_DHT_disconnect (test_get->dht_handle);
965 test_get = test_get->next; 963 test_get = test_get->next;
966 } 964 }
967 965
968 GNUNET_TESTING_daemons_stop (pg, DEFAULT_TIMEOUT, &shutdown_callback, NULL); 966 GNUNET_TESTING_daemons_stop (pg, DEFAULT_TIMEOUT, &shutdown_callback, NULL);
969 967
970 if (dhtlog_handle != NULL) 968 if (dhtlog_handle != NULL)
971 { 969 {
972 fprintf (stderr, "Update trial endtime\n"); 970 fprintf (stderr, "Update trial endtime\n");
973 dhtlog_handle->update_trial (cumulative_successful_gets); 971 dhtlog_handle->update_trial (cumulative_successful_gets);
974 GNUNET_DHTLOG_disconnect (dhtlog_handle); 972 GNUNET_DHTLOG_disconnect (dhtlog_handle);
975 dhtlog_handle = NULL; 973 dhtlog_handle = NULL;
976 } 974 }
977 975
978 if (hostkey_meter != NULL) 976 if (hostkey_meter != NULL)
979 free_meter (hostkey_meter); 977 free_meter (hostkey_meter);
@@ -989,13 +987,14 @@ finish_testing(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
989 GNUNET_asprintf (&temp_get_string, "DHT Successful GETs", trial_to_run); 987 GNUNET_asprintf (&temp_get_string, "DHT Successful GETs", trial_to_run);
990 GNUNET_asprintf (&revision_str, "%llu", revision); 988 GNUNET_asprintf (&revision_str, "%llu", revision);
991 if (GNUNET_YES == insert_gauger_data) 989 if (GNUNET_YES == insert_gauger_data)
992 GAUGER_ID("DHT_TESTING", temp_get_string, cumulative_successful_gets / (double)cumulative_num_gets, "percent successful", revision_str); 990 GAUGER_ID ("DHT_TESTING", temp_get_string,
993 fprintf ( 991 cumulative_successful_gets / (double) cumulative_num_gets,
994 stderr, 992 "percent successful", revision_str);
993 fprintf (stderr,
995 "Finished trial, had %llu successful gets out of %llu total, %.2f percent succeeded\n", 994 "Finished trial, had %llu successful gets out of %llu total, %.2f percent succeeded\n",
996 cumulative_successful_gets, cumulative_num_gets, 995 cumulative_successful_gets, cumulative_num_gets,
997 cumulative_successful_gets / (double) cumulative_num_gets); 996 cumulative_successful_gets / (double) cumulative_num_gets);
998 GNUNET_free(temp_get_string); 997 GNUNET_free (temp_get_string);
999 998
1000 ok = 0; 999 ok = 0;
1001} 1000}
@@ -1004,40 +1003,42 @@ finish_testing(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
1004 * Callback for iterating over all the peer connections of a peer group. 1003 * Callback for iterating over all the peer connections of a peer group.
1005 */ 1004 */
1006static void 1005static void
1007log_topology_cb(void *cls, const struct GNUNET_PeerIdentity *first, 1006log_topology_cb (void *cls, const struct GNUNET_PeerIdentity *first,
1008 const struct GNUNET_PeerIdentity *second, const char *emsg) 1007 const struct GNUNET_PeerIdentity *second, const char *emsg)
1009{ 1008{
1010 struct TopologyIteratorContext *topo_ctx = cls; 1009 struct TopologyIteratorContext *topo_ctx = cls;
1010
1011 if ((first != NULL) && (second != NULL)) 1011 if ((first != NULL) && (second != NULL))
1012 {
1013 if ((topo_ctx->peers_seen != NULL) && (GNUNET_NO
1014 ==
1015 GNUNET_CONTAINER_multihashmap_contains
1016 (topo_ctx->peers_seen,
1017 &first->hashPubKey)))
1012 { 1018 {
1013 if ((topo_ctx->peers_seen != NULL) && (GNUNET_NO 1019 GNUNET_CONTAINER_multihashmap_put (topo_ctx->peers_seen,
1014 == GNUNET_CONTAINER_multihashmap_contains (topo_ctx->peers_seen, 1020 &first->hashPubKey, NULL,
1015 &first->hashPubKey))) 1021 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY);
1016 { 1022 topo_ctx->total_peers++;
1017 GNUNET_CONTAINER_multihashmap_put (topo_ctx->peers_seen,
1018 &first->hashPubKey, NULL,
1019 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY);
1020 topo_ctx->total_peers++;
1021 }
1022 topo_ctx->total_connections++;
1023 if ((GNUNET_NO == dhtlog_minimal) && (dhtlog_handle != NULL))
1024 dhtlog_handle->insert_extended_topology (first, second);
1025 } 1023 }
1024 topo_ctx->total_connections++;
1025 if ((GNUNET_NO == dhtlog_minimal) && (dhtlog_handle != NULL))
1026 dhtlog_handle->insert_extended_topology (first, second);
1027 }
1026 else 1028 else
1027 { 1029 {
1028 GNUNET_assert(dhtlog_handle != NULL); 1030 GNUNET_assert (dhtlog_handle != NULL);
1029 GNUNET_log ( 1031 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1030 GNUNET_ERROR_TYPE_WARNING, 1032 "Topology iteration (%u/%u) finished (%u connections, %u peers)\n",
1031 "Topology iteration (%u/%u) finished (%u connections, %u peers)\n", 1033 topo_ctx->current_iteration, topo_ctx->total_iterations,
1032 topo_ctx->current_iteration, topo_ctx->total_iterations, 1034 topo_ctx->total_connections, topo_ctx->total_peers);
1033 topo_ctx->total_connections, topo_ctx->total_peers); 1035 dhtlog_handle->update_topology (topo_ctx->total_connections);
1034 dhtlog_handle->update_topology (topo_ctx->total_connections); 1036 if (topo_ctx->cont != NULL)
1035 if (topo_ctx->cont != NULL) 1037 GNUNET_SCHEDULER_add_now (topo_ctx->cont, topo_ctx->cls);
1036 GNUNET_SCHEDULER_add_now (topo_ctx->cont, topo_ctx->cls); 1038 if (topo_ctx->peers_seen != NULL)
1037 if (topo_ctx->peers_seen != NULL) 1039 GNUNET_CONTAINER_multihashmap_destroy (topo_ctx->peers_seen);
1038 GNUNET_CONTAINER_multihashmap_destroy (topo_ctx->peers_seen); 1040 GNUNET_free (topo_ctx);
1039 GNUNET_free(topo_ctx); 1041 }
1040 }
1041} 1042}
1042 1043
1043/** 1044/**
@@ -1051,9 +1052,10 @@ log_topology_cb(void *cls, const struct GNUNET_PeerIdentity *first,
1051 * GNUNET_NO if not. 1052 * GNUNET_NO if not.
1052 */ 1053 */
1053static int 1054static int
1054stats_iterate(void *cls, const GNUNET_HashCode * key, void *value) 1055stats_iterate (void *cls, const GNUNET_HashCode * key, void *value)
1055{ 1056{
1056 struct StatisticsIteratorContext *stats_ctx; 1057 struct StatisticsIteratorContext *stats_ctx;
1058
1057 if (value == NULL) 1059 if (value == NULL)
1058 return GNUNET_NO; 1060 return GNUNET_NO;
1059 stats_ctx = value; 1061 stats_ctx = value;
@@ -1072,12 +1074,12 @@ stats_iterate(void *cls, const GNUNET_HashCode * key, void *value)
1072 stats_ctx->stat_get_reply, 1074 stats_ctx->stat_get_reply,
1073 stats_ctx->stat_find_peer_answer, 1075 stats_ctx->stat_find_peer_answer,
1074 stats_ctx->stat_get_response_start); 1076 stats_ctx->stat_get_response_start);
1075 GNUNET_free(stats_ctx); 1077 GNUNET_free (stats_ctx);
1076 return GNUNET_YES; 1078 return GNUNET_YES;
1077} 1079}
1078 1080
1079static void 1081static void
1080stats_finished(void *cls, int result) 1082stats_finished (void *cls, int result)
1081{ 1083{
1082 fprintf (stderr, "Finished getting all peers statistics, iterating!\n"); 1084 fprintf (stderr, "Finished getting all peers statistics, iterating!\n");
1083 GNUNET_CONTAINER_multihashmap_iterate (stats_map, &stats_iterate, NULL); 1085 GNUNET_CONTAINER_multihashmap_iterate (stats_map, &stats_iterate, NULL);
@@ -1097,28 +1099,28 @@ stats_finished(void *cls, int result)
1097 * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration 1099 * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration
1098 */ 1100 */
1099static int 1101static int
1100stats_handle(void *cls, const struct GNUNET_PeerIdentity *peer, 1102stats_handle (void *cls, const struct GNUNET_PeerIdentity *peer,
1101 const char *subsystem, const char *name, uint64_t value, 1103 const char *subsystem, const char *name, uint64_t value,
1102 int is_persistent) 1104 int is_persistent)
1103{ 1105{
1104 struct StatisticsIteratorContext *stats_ctx; 1106 struct StatisticsIteratorContext *stats_ctx;
1105 1107
1106 if (dhtlog_handle != NULL) 1108 if (dhtlog_handle != NULL)
1107 dhtlog_handle->add_generic_stat (peer, name, subsystem, value); 1109 dhtlog_handle->add_generic_stat (peer, name, subsystem, value);
1108 if (GNUNET_CONTAINER_multihashmap_contains (stats_map, &peer->hashPubKey)) 1110 if (GNUNET_CONTAINER_multihashmap_contains (stats_map, &peer->hashPubKey))
1109 { 1111 {
1110 stats_ctx = GNUNET_CONTAINER_multihashmap_get (stats_map, 1112 stats_ctx = GNUNET_CONTAINER_multihashmap_get (stats_map,
1111 &peer->hashPubKey); 1113 &peer->hashPubKey);
1112 } 1114 }
1113 else 1115 else
1114 { 1116 {
1115 stats_ctx = GNUNET_malloc(sizeof(struct StatisticsIteratorContext)); 1117 stats_ctx = GNUNET_malloc (sizeof (struct StatisticsIteratorContext));
1116 stats_ctx->peer = peer; 1118 stats_ctx->peer = peer;
1117 GNUNET_CONTAINER_multihashmap_put (stats_map, &peer->hashPubKey, 1119 GNUNET_CONTAINER_multihashmap_put (stats_map, &peer->hashPubKey,
1118 stats_ctx, 1120 stats_ctx,
1119 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); 1121 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY);
1120 } 1122 }
1121 GNUNET_assert(stats_ctx != NULL); 1123 GNUNET_assert (stats_ctx != NULL);
1122 1124
1123 if (strcmp (name, STAT_ROUTES) == 0) 1125 if (strcmp (name, STAT_ROUTES) == 0)
1124 stats_ctx->stat_routes = value; 1126 stats_ctx->stat_routes = value;
@@ -1161,7 +1163,7 @@ stats_handle(void *cls, const struct GNUNET_PeerIdentity *peer,
1161 * dht statistics for safe keeping. 1163 * dht statistics for safe keeping.
1162 */ 1164 */
1163static void 1165static void
1164log_dht_statistics(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 1166log_dht_statistics (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
1165{ 1167{
1166 stats_map = GNUNET_CONTAINER_multihashmap_create (num_peers); 1168 stats_map = GNUNET_CONTAINER_multihashmap_create (num_peers);
1167 fprintf (stderr, "Starting statistics logging\n"); 1169 fprintf (stderr, "Starting statistics logging\n");
@@ -1173,10 +1175,11 @@ log_dht_statistics(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
1173 * connections. 1175 * connections.
1174 */ 1176 */
1175static void 1177static void
1176capture_current_topology(void *cls, 1178capture_current_topology (void *cls,
1177 const struct GNUNET_SCHEDULER_TaskContext * tc) 1179 const struct GNUNET_SCHEDULER_TaskContext *tc)
1178{ 1180{
1179 struct TopologyIteratorContext *topo_ctx = cls; 1181 struct TopologyIteratorContext *topo_ctx = cls;
1182
1180 dhtlog_handle->insert_topology (0); 1183 dhtlog_handle->insert_topology (0);
1181 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Called capture_current_topology\n"); 1184 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Called capture_current_topology\n");
1182 GNUNET_TESTING_get_topology (pg, &log_topology_cb, topo_ctx); 1185 GNUNET_TESTING_get_topology (pg, &log_topology_cb, topo_ctx);
@@ -1188,7 +1191,7 @@ capture_current_topology(void *cls,
1188 * test. 1191 * test.
1189 */ 1192 */
1190static void 1193static void
1191end_badly(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 1194end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
1192{ 1195{
1193 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Failing test with error: `%s'!\n", 1196 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Failing test with error: `%s'!\n",
1194 (char *) cls); 1197 (char *) cls);
@@ -1197,34 +1200,34 @@ end_badly(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
1197 struct TestGetContext *test_get = all_gets; 1200 struct TestGetContext *test_get = all_gets;
1198 1201
1199 while (test_put != NULL) 1202 while (test_put != NULL)
1200 { 1203 {
1201 if (test_put->disconnect_task != GNUNET_SCHEDULER_NO_TASK) 1204 if (test_put->disconnect_task != GNUNET_SCHEDULER_NO_TASK)
1202 GNUNET_SCHEDULER_cancel (test_put->disconnect_task); 1205 GNUNET_SCHEDULER_cancel (test_put->disconnect_task);
1203 if (test_put->dht_handle != NULL) 1206 if (test_put->dht_handle != NULL)
1204 GNUNET_DHT_disconnect (test_put->dht_handle); 1207 GNUNET_DHT_disconnect (test_put->dht_handle);
1205 test_put = test_put->next; 1208 test_put = test_put->next;
1206 } 1209 }
1207 1210
1208 while (test_get != NULL) 1211 while (test_get != NULL)
1209 { 1212 {
1210 if (test_get->disconnect_task != GNUNET_SCHEDULER_NO_TASK) 1213 if (test_get->disconnect_task != GNUNET_SCHEDULER_NO_TASK)
1211 GNUNET_SCHEDULER_cancel (test_get->disconnect_task); 1214 GNUNET_SCHEDULER_cancel (test_get->disconnect_task);
1212 if (test_get->get_handle != NULL) 1215 if (test_get->get_handle != NULL)
1213 GNUNET_DHT_get_stop (test_get->get_handle); 1216 GNUNET_DHT_get_stop (test_get->get_handle);
1214 if (test_get->dht_handle != NULL) 1217 if (test_get->dht_handle != NULL)
1215 GNUNET_DHT_disconnect (test_get->dht_handle); 1218 GNUNET_DHT_disconnect (test_get->dht_handle);
1216 test_get = test_get->next; 1219 test_get = test_get->next;
1217 } 1220 }
1218 1221
1219 GNUNET_TESTING_daemons_stop (pg, DEFAULT_TIMEOUT, &shutdown_callback, NULL); 1222 GNUNET_TESTING_daemons_stop (pg, DEFAULT_TIMEOUT, &shutdown_callback, NULL);
1220 1223
1221 if (dhtlog_handle != NULL) 1224 if (dhtlog_handle != NULL)
1222 { 1225 {
1223 fprintf (stderr, "Update trial endtime\n"); 1226 fprintf (stderr, "Update trial endtime\n");
1224 dhtlog_handle->update_trial (gets_completed); 1227 dhtlog_handle->update_trial (gets_completed);
1225 GNUNET_DHTLOG_disconnect (dhtlog_handle); 1228 GNUNET_DHTLOG_disconnect (dhtlog_handle);
1226 dhtlog_handle = NULL; 1229 dhtlog_handle = NULL;
1227 } 1230 }
1228 1231
1229 if (hostkey_meter != NULL) 1232 if (hostkey_meter != NULL)
1230 free_meter (hostkey_meter); 1233 free_meter (hostkey_meter);
@@ -1243,14 +1246,12 @@ end_badly(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
1243/** 1246/**
1244 * Forward declaration. 1247 * Forward declaration.
1245 */ 1248 */
1246static void 1249static void do_put (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc);
1247do_put(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc);
1248 1250
1249/** 1251/**
1250 * Forward declaration. 1252 * Forward declaration.
1251 */ 1253 */
1252static void 1254static void do_get (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc);
1253do_get(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc);
1254 1255
1255/** 1256/**
1256 * Iterator over hash map entries. 1257 * Iterator over hash map entries.
@@ -1263,11 +1264,12 @@ do_get(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc);
1263 * GNUNET_NO if not. 1264 * GNUNET_NO if not.
1264 */ 1265 */
1265static int 1266static int
1266remove_peer_count(void *cls, const GNUNET_HashCode * key, void *value) 1267remove_peer_count (void *cls, const GNUNET_HashCode * key, void *value)
1267{ 1268{
1268 struct PeerCount *peer_count = value; 1269 struct PeerCount *peer_count = value;
1270
1269 GNUNET_CONTAINER_heap_remove_node (peer_count->heap_node); 1271 GNUNET_CONTAINER_heap_remove_node (peer_count->heap_node);
1270 GNUNET_free(peer_count); 1272 GNUNET_free (peer_count);
1271 1273
1272 return GNUNET_YES; 1274 return GNUNET_YES;
1273} 1275}
@@ -1277,9 +1279,10 @@ remove_peer_count(void *cls, const GNUNET_HashCode * key, void *value)
1277 * connections. 1279 * connections.
1278 */ 1280 */
1279static void 1281static void
1280count_new_peers(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 1282count_new_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
1281{ 1283{
1282 struct FindPeerContext *find_peer_context = cls; 1284 struct FindPeerContext *find_peer_context = cls;
1285
1283 find_peer_context->previous_peers = find_peer_context->current_peers; 1286 find_peer_context->previous_peers = find_peer_context->current_peers;
1284 find_peer_context->current_peers = 0; 1287 find_peer_context->current_peers = 0;
1285 GNUNET_TESTING_get_topology (pg, find_peer_context->count_peers_cb, 1288 GNUNET_TESTING_get_topology (pg, find_peer_context->count_peers_cb,
@@ -1287,18 +1290,19 @@ count_new_peers(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
1287} 1290}
1288 1291
1289static void 1292static void
1290decrement_find_peers(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 1293decrement_find_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
1291{ 1294{
1292 struct TestFindPeer *test_find_peer = cls; 1295 struct TestFindPeer *test_find_peer = cls;
1293 GNUNET_assert(test_find_peer->find_peer_context->outstanding > 0); 1296
1297 GNUNET_assert (test_find_peer->find_peer_context->outstanding > 0);
1294 test_find_peer->find_peer_context->outstanding--; 1298 test_find_peer->find_peer_context->outstanding--;
1295 test_find_peer->find_peer_context->total--; 1299 test_find_peer->find_peer_context->total--;
1296 if (0 == test_find_peer->find_peer_context->total) 1300 if (0 == test_find_peer->find_peer_context->total)
1297 { 1301 {
1298 GNUNET_SCHEDULER_add_now (&count_new_peers, 1302 GNUNET_SCHEDULER_add_now (&count_new_peers,
1299 test_find_peer->find_peer_context); 1303 test_find_peer->find_peer_context);
1300 } 1304 }
1301 GNUNET_free(test_find_peer); 1305 GNUNET_free (test_find_peer);
1302} 1306}
1303 1307
1304/** 1308/**
@@ -1309,42 +1313,41 @@ decrement_find_peers(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
1309 * @param tc context the task is being called with 1313 * @param tc context the task is being called with
1310 */ 1314 */
1311static void 1315static void
1312handle_find_peer_sent(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 1316handle_find_peer_sent (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
1313{ 1317{
1314 struct TestFindPeer *test_find_peer = cls; 1318 struct TestFindPeer *test_find_peer = cls;
1315 1319
1316 GNUNET_DHT_disconnect (test_find_peer->dht_handle); 1320 GNUNET_DHT_disconnect (test_find_peer->dht_handle);
1317 GNUNET_SCHEDULER_add_delayed ( 1321 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_divide
1318 GNUNET_TIME_relative_divide (find_peer_delay, 2), 1322 (find_peer_delay, 2), &decrement_find_peers,
1319 &decrement_find_peers, test_find_peer); 1323 test_find_peer);
1320} 1324}
1321 1325
1322static void 1326static void
1323send_find_peer_request(void *cls, 1327send_find_peer_request (void *cls,
1324 const struct GNUNET_SCHEDULER_TaskContext * tc) 1328 const struct GNUNET_SCHEDULER_TaskContext *tc)
1325{ 1329{
1326 struct TestFindPeer *test_find_peer = cls; 1330 struct TestFindPeer *test_find_peer = cls;
1327 1331
1328 if (test_find_peer->find_peer_context->outstanding 1332 if (test_find_peer->find_peer_context->outstanding
1329 > max_outstanding_find_peers) 1333 > max_outstanding_find_peers)
1330 { 1334 {
1331 GNUNET_SCHEDULER_add_delayed (find_peer_offset, &send_find_peer_request, 1335 GNUNET_SCHEDULER_add_delayed (find_peer_offset, &send_find_peer_request,
1332 test_find_peer); 1336 test_find_peer);
1333 return; 1337 return;
1334 } 1338 }
1335 1339
1336 test_find_peer->find_peer_context->outstanding++; 1340 test_find_peer->find_peer_context->outstanding++;
1337 if (GNUNET_TIME_absolute_get_remaining ( 1341 if (GNUNET_TIME_absolute_get_remaining
1338 test_find_peer->find_peer_context->endtime).rel_value 1342 (test_find_peer->find_peer_context->endtime).rel_value == 0)
1339 == 0) 1343 {
1340 { 1344 GNUNET_SCHEDULER_add_now (&decrement_find_peers, test_find_peer);
1341 GNUNET_SCHEDULER_add_now (&decrement_find_peers, test_find_peer); 1345 return;
1342 return; 1346 }
1343 }
1344 1347
1345 test_find_peer->dht_handle = GNUNET_DHT_connect (test_find_peer->daemon->cfg, 1348 test_find_peer->dht_handle = GNUNET_DHT_connect (test_find_peer->daemon->cfg,
1346 1); 1349 1);
1347 GNUNET_assert(test_find_peer->dht_handle != NULL); 1350 GNUNET_assert (test_find_peer->dht_handle != NULL);
1348 GNUNET_DHT_find_peers (test_find_peer->dht_handle, &handle_find_peer_sent, 1351 GNUNET_DHT_find_peers (test_find_peer->dht_handle, &handle_find_peer_sent,
1349 test_find_peer); 1352 test_find_peer);
1350} 1353}
@@ -1355,63 +1358,63 @@ send_find_peer_request(void *cls,
1355 * the least connections to initiate find peer requests from. 1358 * the least connections to initiate find peer requests from.
1356 */ 1359 */
1357static void 1360static void
1358add_new_connection(struct FindPeerContext *find_peer_context, 1361add_new_connection (struct FindPeerContext *find_peer_context,
1359 const struct GNUNET_PeerIdentity *first, 1362 const struct GNUNET_PeerIdentity *first,
1360 const struct GNUNET_PeerIdentity *second) 1363 const struct GNUNET_PeerIdentity *second)
1361{ 1364{
1362 struct PeerCount *first_count; 1365 struct PeerCount *first_count;
1363 struct PeerCount *second_count; 1366 struct PeerCount *second_count;
1364 1367
1365 if (GNUNET_CONTAINER_multihashmap_contains (find_peer_context->peer_hash, 1368 if (GNUNET_CONTAINER_multihashmap_contains (find_peer_context->peer_hash,
1366 &first->hashPubKey)) 1369 &first->hashPubKey))
1367 { 1370 {
1368 first_count 1371 first_count
1369 = GNUNET_CONTAINER_multihashmap_get (find_peer_context->peer_hash, 1372 = GNUNET_CONTAINER_multihashmap_get (find_peer_context->peer_hash,
1370 &first->hashPubKey); 1373 &first->hashPubKey);
1371 GNUNET_assert(first_count != NULL); 1374 GNUNET_assert (first_count != NULL);
1372 first_count->count++; 1375 first_count->count++;
1373 GNUNET_CONTAINER_heap_update_cost (find_peer_context->peer_min_heap, 1376 GNUNET_CONTAINER_heap_update_cost (find_peer_context->peer_min_heap,
1374 first_count->heap_node, 1377 first_count->heap_node,
1375 first_count->count); 1378 first_count->count);
1376 } 1379 }
1377 else 1380 else
1378 { 1381 {
1379 first_count = GNUNET_malloc(sizeof(struct PeerCount)); 1382 first_count = GNUNET_malloc (sizeof (struct PeerCount));
1380 first_count->count = 1; 1383 first_count->count = 1;
1381 memcpy (&first_count->peer_id, first, sizeof(struct GNUNET_PeerIdentity)); 1384 memcpy (&first_count->peer_id, first, sizeof (struct GNUNET_PeerIdentity));
1382 first_count->heap_node 1385 first_count->heap_node
1383 = GNUNET_CONTAINER_heap_insert (find_peer_context->peer_min_heap, 1386 = GNUNET_CONTAINER_heap_insert (find_peer_context->peer_min_heap,
1384 first_count, first_count->count); 1387 first_count, first_count->count);
1385 GNUNET_CONTAINER_multihashmap_put (find_peer_context->peer_hash, 1388 GNUNET_CONTAINER_multihashmap_put (find_peer_context->peer_hash,
1386 &first->hashPubKey, first_count, 1389 &first->hashPubKey, first_count,
1387 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); 1390 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY);
1388 } 1391 }
1389 1392
1390 if (GNUNET_CONTAINER_multihashmap_contains (find_peer_context->peer_hash, 1393 if (GNUNET_CONTAINER_multihashmap_contains (find_peer_context->peer_hash,
1391 &second->hashPubKey)) 1394 &second->hashPubKey))
1392 { 1395 {
1393 second_count 1396 second_count
1394 = GNUNET_CONTAINER_multihashmap_get (find_peer_context->peer_hash, 1397 = GNUNET_CONTAINER_multihashmap_get (find_peer_context->peer_hash,
1395 &second->hashPubKey); 1398 &second->hashPubKey);
1396 GNUNET_assert(second_count != NULL); 1399 GNUNET_assert (second_count != NULL);
1397 second_count->count++; 1400 second_count->count++;
1398 GNUNET_CONTAINER_heap_update_cost (find_peer_context->peer_min_heap, 1401 GNUNET_CONTAINER_heap_update_cost (find_peer_context->peer_min_heap,
1399 second_count->heap_node, 1402 second_count->heap_node,
1400 second_count->count); 1403 second_count->count);
1401 } 1404 }
1402 else 1405 else
1403 { 1406 {
1404 second_count = GNUNET_malloc(sizeof(struct PeerCount)); 1407 second_count = GNUNET_malloc (sizeof (struct PeerCount));
1405 second_count->count = 1; 1408 second_count->count = 1;
1406 memcpy (&second_count->peer_id, second, 1409 memcpy (&second_count->peer_id, second,
1407 sizeof(struct GNUNET_PeerIdentity)); 1410 sizeof (struct GNUNET_PeerIdentity));
1408 second_count->heap_node 1411 second_count->heap_node
1409 = GNUNET_CONTAINER_heap_insert (find_peer_context->peer_min_heap, 1412 = GNUNET_CONTAINER_heap_insert (find_peer_context->peer_min_heap,
1410 second_count, second_count->count); 1413 second_count, second_count->count);
1411 GNUNET_CONTAINER_multihashmap_put (find_peer_context->peer_hash, 1414 GNUNET_CONTAINER_multihashmap_put (find_peer_context->peer_hash,
1412 &second->hashPubKey, second_count, 1415 &second->hashPubKey, second_count,
1413 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); 1416 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY);
1414 } 1417 }
1415} 1418}
1416 1419
1417/** 1420/**
@@ -1427,46 +1430,43 @@ add_new_connection(struct FindPeerContext *find_peer_context,
1427 * GNUNET_NO if not. 1430 * GNUNET_NO if not.
1428 */ 1431 */
1429static int 1432static int
1430iterate_min_heap_peers(void *cls, struct GNUNET_CONTAINER_HeapNode *node, 1433iterate_min_heap_peers (void *cls, struct GNUNET_CONTAINER_HeapNode *node,
1431 void *element, GNUNET_CONTAINER_HeapCostType cost) 1434 void *element, GNUNET_CONTAINER_HeapCostType cost)
1432{ 1435{
1433 struct FindPeerContext *find_peer_context = cls; 1436 struct FindPeerContext *find_peer_context = cls;
1434 struct PeerCount *peer_count = element; 1437 struct PeerCount *peer_count = element;
1435 struct GNUNET_TESTING_Daemon *d1; 1438 struct GNUNET_TESTING_Daemon *d1;
1436 struct GNUNET_TESTING_Daemon *d2; 1439 struct GNUNET_TESTING_Daemon *d2;
1437 struct GNUNET_TIME_Relative timeout; 1440 struct GNUNET_TIME_Relative timeout;
1441
1438 if (cost == 0) 1442 if (cost == 0)
1443 {
1444 d1 = GNUNET_TESTING_daemon_get_by_id (pg, &peer_count->peer_id);
1445 GNUNET_assert (d1 != NULL);
1446 d2 = d1;
1447 while ((d2 == d1) || (GNUNET_YES != GNUNET_TESTING_daemon_running (d2)))
1439 { 1448 {
1440 d1 = GNUNET_TESTING_daemon_get_by_id (pg, &peer_count->peer_id); 1449 d2 = GNUNET_TESTING_daemon_get (pg,
1441 GNUNET_assert(d1 != NULL); 1450 GNUNET_CRYPTO_random_u32
1442 d2 = d1; 1451 (GNUNET_CRYPTO_QUALITY_WEAK, num_peers));
1443 while ((d2 == d1) || (GNUNET_YES != GNUNET_TESTING_daemon_running (d2))) 1452 GNUNET_assert (d2 != NULL);
1444 { 1453 }
1445 d2
1446 = GNUNET_TESTING_daemon_get (
1447 pg,
1448 GNUNET_CRYPTO_random_u32 (
1449 GNUNET_CRYPTO_QUALITY_WEAK,
1450 num_peers));
1451 GNUNET_assert(d2 != NULL);
1452 }
1453 1454
1454 /** Just try to connect the peers, don't worry about callbacks, etc. **/ 1455 /** Just try to connect the peers, don't worry about callbacks, etc. **/
1455 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 1456 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1456 "Peer %s has 0 connections. Trying to connect to %s...\n", 1457 "Peer %s has 0 connections. Trying to connect to %s...\n",
1457 GNUNET_i2s (&peer_count->peer_id), d2->shortname); 1458 GNUNET_i2s (&peer_count->peer_id), d2->shortname);
1458 timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 1459 timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS,
1459 DEFAULT_CONNECT_TIMEOUT); 1460 DEFAULT_CONNECT_TIMEOUT);
1460 if (GNUNET_TIME_relative_to_absolute (timeout).abs_value 1461 if (GNUNET_TIME_relative_to_absolute (timeout).abs_value
1461 > find_peer_context->endtime.abs_value) 1462 > find_peer_context->endtime.abs_value)
1462 { 1463 {
1463 timeout 1464 timeout = GNUNET_TIME_absolute_get_remaining (find_peer_context->endtime);
1464 = GNUNET_TIME_absolute_get_remaining (find_peer_context->endtime);
1465 }
1466 GNUNET_TESTING_daemons_connect (d1, d2, timeout,
1467 DEFAULT_RECONNECT_ATTEMPTS, GNUNET_YES,
1468 NULL, NULL);
1469 } 1465 }
1466 GNUNET_TESTING_daemons_connect (d1, d2, timeout,
1467 DEFAULT_RECONNECT_ATTEMPTS, GNUNET_YES,
1468 NULL, NULL);
1469 }
1470 if (GNUNET_TIME_absolute_get_remaining (find_peer_context->endtime).rel_value 1470 if (GNUNET_TIME_absolute_get_remaining (find_peer_context->endtime).rel_value
1471 > 0) 1471 > 0)
1472 return GNUNET_YES; 1472 return GNUNET_YES;
@@ -1478,9 +1478,9 @@ iterate_min_heap_peers(void *cls, struct GNUNET_CONTAINER_HeapNode *node,
1478 * Forward declaration. 1478 * Forward declaration.
1479 */ 1479 */
1480static void 1480static void
1481 schedule_churn_find_peer_requests( 1481schedule_churn_find_peer_requests (void *cls,
1482 void *cls, 1482 const struct GNUNET_SCHEDULER_TaskContext
1483 const struct GNUNET_SCHEDULER_TaskContext * tc); 1483 *tc);
1484 1484
1485/** 1485/**
1486 * Callback for iterating over all the peer connections of a peer group. 1486 * Callback for iterating over all the peer connections of a peer group.
@@ -1488,39 +1488,39 @@ static void
1488 * connections so we can make them issue find peer requests. 1488 * connections so we can make them issue find peer requests.
1489 */ 1489 */
1490static void 1490static void
1491count_peers_churn_cb(void *cls, const struct GNUNET_PeerIdentity *first, 1491count_peers_churn_cb (void *cls, const struct GNUNET_PeerIdentity *first,
1492 const struct GNUNET_PeerIdentity *second, const char *emsg) 1492 const struct GNUNET_PeerIdentity *second,
1493 const char *emsg)
1493{ 1494{
1494 struct FindPeerContext *find_peer_context = cls; 1495 struct FindPeerContext *find_peer_context = cls;
1495 struct TopologyIteratorContext *topo_ctx; 1496 struct TopologyIteratorContext *topo_ctx;
1496 struct PeerCount *peer_count; 1497 struct PeerCount *peer_count;
1497 1498
1498 if ((first != NULL) && (second != NULL)) 1499 if ((first != NULL) && (second != NULL))
1499 { 1500 {
1500 add_new_connection (find_peer_context, first, second); 1501 add_new_connection (find_peer_context, first, second);
1501 find_peer_context->current_peers++; 1502 find_peer_context->current_peers++;
1502 } 1503 }
1503 else 1504 else
1504 { 1505 {
1505 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 1506 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1506 "Peer count finished (%u connections)\n", 1507 "Peer count finished (%u connections)\n",
1507 find_peer_context->current_peers); 1508 find_peer_context->current_peers);
1508 peer_count 1509 peer_count = GNUNET_CONTAINER_heap_peek (find_peer_context->peer_min_heap);
1509 = GNUNET_CONTAINER_heap_peek (find_peer_context->peer_min_heap); 1510 GNUNET_assert (peer_count != NULL);
1510 GNUNET_assert(peer_count != NULL); 1511 /* WAIT. When peers are churned they will come back with their peers (at least in peerinfo), because the HOSTS file doesn't likely get removed. CRAP. */
1511 /* WAIT. When peers are churned they will come back with their peers (at least in peerinfo), because the HOSTS file doesn't likely get removed. CRAP. */ 1512 /* NO they won't, because we have disabled peerinfo writing to disk (remember?) so we WILL have to give them new connections */
1512 /* NO they won't, because we have disabled peerinfo writing to disk (remember?) so we WILL have to give them new connections */ 1513 /* Best course of action: have DHT automatically try to add peers from peerinfo on startup. This way IF peerinfo writes to file
1513 /* Best course of action: have DHT automatically try to add peers from peerinfo on startup. This way IF peerinfo writes to file 1514 * then some peers will end up connected.
1514 * then some peers will end up connected. 1515 *
1515 * 1516 * Also, find any peers that have zero connections here and set up a task to choose at random another peer in the network to
1516 * Also, find any peers that have zero connections here and set up a task to choose at random another peer in the network to 1517 * connect to. Of course, if they are blacklisted from that peer they won't be able to connect, so we will have to keep trying
1517 * connect to. Of course, if they are blacklisted from that peer they won't be able to connect, so we will have to keep trying 1518 * until they get a peer.
1518 * until they get a peer. 1519 */
1519 */ 1520 /* However, they won't automatically be connected to any of their previous peers... How can we handle that? */
1520 /* However, they won't automatically be connected to any of their previous peers... How can we handle that? */ 1521 /* So now we have choices: do we want them to come back with all their connections? Probably not, but it solves this mess. */
1521 /* So now we have choices: do we want them to come back with all their connections? Probably not, but it solves this mess. */ 1522
1522 1523 /* Second problem, which is still a problem, is that a FIND_PEER request won't work when a peer has no connections */
1523 /* Second problem, which is still a problem, is that a FIND_PEER request won't work when a peer has no connections */
1524 1524
1525 /** 1525 /**
1526 * Okay, so here's how this *should* work now. 1526 * Okay, so here's how this *should* work now.
@@ -1555,77 +1555,73 @@ count_peers_churn_cb(void *cls, const struct GNUNET_PeerIdentity *first,
1555 * into the general testing churn options seems like overkill because 1555 * into the general testing churn options seems like overkill because
1556 * these are very specialized cases. 1556 * these are very specialized cases.
1557 */ 1557 */
1558 GNUNET_log ( 1558 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1559 GNUNET_ERROR_TYPE_WARNING, 1559 "Out of %u peers, fewest connections is %d\n",
1560 "Out of %u peers, fewest connections is %d\n", 1560 GNUNET_CONTAINER_heap_get_size
1561 GNUNET_CONTAINER_heap_get_size ( 1561 (find_peer_context->peer_min_heap), peer_count->count);
1562 find_peer_context->peer_min_heap), 1562 if ((peer_count->count == 0) &&
1563 peer_count->count); 1563 (GNUNET_TIME_absolute_get_remaining
1564 if ((peer_count->count == 0) 1564 (find_peer_context->endtime).rel_value > 0))
1565 && (GNUNET_TIME_absolute_get_remaining (find_peer_context->endtime).rel_value 1565 {
1566 > 0)) 1566 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1567 { 1567 "Found peer with no connections, will choose some peer(s) at random to connect to!\n");
1568 GNUNET_log ( 1568 GNUNET_CONTAINER_heap_iterate (find_peer_context->peer_min_heap,
1569 GNUNET_ERROR_TYPE_WARNING, 1569 &iterate_min_heap_peers,
1570 "Found peer with no connections, will choose some peer(s) at random to connect to!\n"); 1570 find_peer_context);
1571 GNUNET_CONTAINER_heap_iterate (find_peer_context->peer_min_heap, 1571 GNUNET_SCHEDULER_add_now (&schedule_churn_find_peer_requests,
1572 &iterate_min_heap_peers, 1572 find_peer_context);
1573 find_peer_context); 1573 }
1574 GNUNET_SCHEDULER_add_now (&schedule_churn_find_peer_requests, 1574 else if ((GNUNET_TIME_absolute_get_remaining
1575 find_peer_context); 1575 (find_peer_context->endtime).rel_value > 0) &&
1576 } 1576 (find_peer_context->last_sent != 0))
1577 else if ((GNUNET_TIME_absolute_get_remaining (find_peer_context->endtime).rel_value 1577 {
1578 > 0) && (find_peer_context->last_sent != 0)) 1578 GNUNET_SCHEDULER_add_now (&schedule_churn_find_peer_requests,
1579 { 1579 find_peer_context);
1580 GNUNET_SCHEDULER_add_now (&schedule_churn_find_peer_requests, 1580 }
1581 find_peer_context); 1581 else
1582 } 1582 {
1583 GNUNET_CONTAINER_multihashmap_iterate (find_peer_context->peer_hash,
1584 &remove_peer_count,
1585 find_peer_context);
1586 GNUNET_CONTAINER_multihashmap_destroy (find_peer_context->peer_hash);
1587 GNUNET_CONTAINER_heap_destroy (find_peer_context->peer_min_heap);
1588 GNUNET_free (find_peer_context);
1589 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1590 "Churn round %u of %llu finished, scheduling next GET round.\n",
1591 current_churn_round, churn_rounds);
1592 if (dhtlog_handle != NULL)
1593 {
1594 topo_ctx = GNUNET_malloc (sizeof (struct TopologyIteratorContext));
1595 topo_ctx->cont = &do_get;
1596 topo_ctx->cls = all_gets;
1597 topo_ctx->timeout = DEFAULT_GET_TIMEOUT;
1598 topo_ctx->peers_seen = GNUNET_CONTAINER_multihashmap_create (num_peers);
1599 die_task
1600 =
1601 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_add
1602 (GNUNET_TIME_relative_add
1603 (DEFAULT_GET_TIMEOUT,
1604 all_get_timeout),
1605 DEFAULT_TOPOLOGY_CAPTURE_TIMEOUT),
1606 &end_badly,
1607 "from do gets (count_peers_churn_cb)");
1608 GNUNET_SCHEDULER_add_now (&capture_current_topology, topo_ctx);
1609 }
1583 else 1610 else
1584 { 1611 {
1585 GNUNET_CONTAINER_multihashmap_iterate (find_peer_context->peer_hash, 1612 die_task
1586 &remove_peer_count, 1613 =
1587 find_peer_context); 1614 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_add
1588 GNUNET_CONTAINER_multihashmap_destroy (find_peer_context->peer_hash); 1615 (GNUNET_TIME_relative_add
1589 GNUNET_CONTAINER_heap_destroy (find_peer_context->peer_min_heap); 1616 (DEFAULT_GET_TIMEOUT,
1590 GNUNET_free(find_peer_context); 1617 all_get_timeout),
1591 GNUNET_log ( 1618 DEFAULT_TOPOLOGY_CAPTURE_TIMEOUT),
1592 GNUNET_ERROR_TYPE_WARNING, 1619 &end_badly,
1593 "Churn round %u of %llu finished, scheduling next GET round.\n", 1620 "from do gets (count_peers_churn_cb)");
1594 current_churn_round, churn_rounds); 1621 GNUNET_SCHEDULER_add_now (&do_get, all_gets);
1595 if (dhtlog_handle != NULL) 1622 }
1596 {
1597 topo_ctx = GNUNET_malloc(sizeof(struct TopologyIteratorContext));
1598 topo_ctx->cont = &do_get;
1599 topo_ctx->cls = all_gets;
1600 topo_ctx->timeout = DEFAULT_GET_TIMEOUT;
1601 topo_ctx->peers_seen
1602 = GNUNET_CONTAINER_multihashmap_create (num_peers);
1603 die_task
1604 = GNUNET_SCHEDULER_add_delayed (
1605 GNUNET_TIME_relative_add (
1606 GNUNET_TIME_relative_add (
1607 DEFAULT_GET_TIMEOUT,
1608 all_get_timeout),
1609 DEFAULT_TOPOLOGY_CAPTURE_TIMEOUT),
1610 &end_badly,
1611 "from do gets (count_peers_churn_cb)");
1612 GNUNET_SCHEDULER_add_now (&capture_current_topology, topo_ctx);
1613 }
1614 else
1615 {
1616 die_task
1617 = GNUNET_SCHEDULER_add_delayed (
1618 GNUNET_TIME_relative_add (
1619 GNUNET_TIME_relative_add (
1620 DEFAULT_GET_TIMEOUT,
1621 all_get_timeout),
1622 DEFAULT_TOPOLOGY_CAPTURE_TIMEOUT),
1623 &end_badly,
1624 "from do gets (count_peers_churn_cb)");
1625 GNUNET_SCHEDULER_add_now (&do_get, all_gets);
1626 }
1627 }
1628 } 1623 }
1624 }
1629} 1625}
1630 1626
1631/** 1627/**
@@ -1634,24 +1630,23 @@ count_peers_churn_cb(void *cls, const struct GNUNET_PeerIdentity *first,
1634 * and the time allowed for each one! 1630 * and the time allowed for each one!
1635 */ 1631 */
1636static void 1632static void
1637schedule_churn_find_peer_requests( 1633schedule_churn_find_peer_requests (void *cls,
1638 void *cls, 1634 const struct GNUNET_SCHEDULER_TaskContext
1639 const struct GNUNET_SCHEDULER_TaskContext * tc) 1635 *tc)
1640{ 1636{
1641 struct FindPeerContext *find_peer_ctx = cls; 1637 struct FindPeerContext *find_peer_ctx = cls;
1642 struct TestFindPeer *test_find_peer; 1638 struct TestFindPeer *test_find_peer;
1643 struct PeerCount *peer_count; 1639 struct PeerCount *peer_count;
1644 uint32_t i; 1640 uint32_t i;
1645 1641
1646 if (find_peer_ctx->previous_peers == 0) /* First time, go slowly */ 1642 if (find_peer_ctx->previous_peers == 0) /* First time, go slowly */
1647 find_peer_ctx->total = 1; 1643 find_peer_ctx->total = 1;
1648 else if (find_peer_ctx->current_peers - find_peer_ctx->previous_peers 1644 else if (find_peer_ctx->current_peers - find_peer_ctx->previous_peers
1649 < MIN_FIND_PEER_CUTOFF) 1645 < MIN_FIND_PEER_CUTOFF)
1650 find_peer_ctx->total = find_peer_ctx->total / 2; 1646 find_peer_ctx->total = find_peer_ctx->total / 2;
1651 else if (find_peer_ctx->current_peers - find_peer_ctx->previous_peers 1647 else if (find_peer_ctx->current_peers - find_peer_ctx->previous_peers > MAX_FIND_PEER_CUTOFF) /* Found LOTS of peers, still go slowly */
1652 > MAX_FIND_PEER_CUTOFF) /* Found LOTS of peers, still go slowly */
1653 find_peer_ctx->total = find_peer_ctx->last_sent - (find_peer_ctx->last_sent 1648 find_peer_ctx->total = find_peer_ctx->last_sent - (find_peer_ctx->last_sent
1654 / 4); 1649 / 4);
1655 else 1650 else
1656 find_peer_ctx->total = find_peer_ctx->last_sent * 4; 1651 find_peer_ctx->total = find_peer_ctx->last_sent * 4;
1657 1652
@@ -1667,62 +1662,61 @@ schedule_churn_find_peer_requests(
1667 find_peer_offset = GNUNET_TIME_relative_divide (find_peer_delay, 1662 find_peer_offset = GNUNET_TIME_relative_divide (find_peer_delay,
1668 find_peer_ctx->total); 1663 find_peer_ctx->total);
1669 else 1664 else
1670 { 1665 {
1671 find_peer_ctx->previous_peers = find_peer_ctx->current_peers; 1666 find_peer_ctx->previous_peers = find_peer_ctx->current_peers;
1672 find_peer_ctx->current_peers = 0; 1667 find_peer_ctx->current_peers = 0;
1673 GNUNET_TESTING_get_topology (pg, &count_peers_churn_cb, find_peer_ctx); 1668 GNUNET_TESTING_get_topology (pg, &count_peers_churn_cb, find_peer_ctx);
1674 } 1669 }
1675 1670
1676 for (i = 0; i < find_peer_ctx->total; i++) 1671 for (i = 0; i < find_peer_ctx->total; i++)
1677 { 1672 {
1678 test_find_peer = GNUNET_malloc(sizeof(struct TestFindPeer)); 1673 test_find_peer = GNUNET_malloc (sizeof (struct TestFindPeer));
1679 /* If we have sent requests, choose peers with a low number of connections to send requests from */ 1674 /* If we have sent requests, choose peers with a low number of connections to send requests from */
1680 peer_count 1675 peer_count
1681 = GNUNET_CONTAINER_heap_remove_root (find_peer_ctx->peer_min_heap); 1676 = GNUNET_CONTAINER_heap_remove_root (find_peer_ctx->peer_min_heap);
1682 GNUNET_assert(peer_count != NULL); 1677 GNUNET_assert (peer_count != NULL);
1683 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 1678 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1684 "Sending find peer request from peer with %u connections\n", 1679 "Sending find peer request from peer with %u connections\n",
1685 peer_count->count); 1680 peer_count->count);
1686 GNUNET_CONTAINER_multihashmap_remove (find_peer_ctx->peer_hash, 1681 GNUNET_CONTAINER_multihashmap_remove (find_peer_ctx->peer_hash,
1687 &peer_count->peer_id.hashPubKey, 1682 &peer_count->peer_id.hashPubKey,
1688 peer_count); 1683 peer_count);
1689 test_find_peer->daemon 1684 test_find_peer->daemon
1690 = GNUNET_TESTING_daemon_get_by_id (pg, &peer_count->peer_id); 1685 = GNUNET_TESTING_daemon_get_by_id (pg, &peer_count->peer_id);
1691 GNUNET_assert(test_find_peer->daemon != NULL); 1686 GNUNET_assert (test_find_peer->daemon != NULL);
1692 test_find_peer->find_peer_context = find_peer_ctx; 1687 test_find_peer->find_peer_context = find_peer_ctx;
1693 GNUNET_SCHEDULER_add_delayed ( 1688 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
1694 GNUNET_TIME_relative_multiply ( 1689 (find_peer_offset, i),
1695 find_peer_offset, 1690 &send_find_peer_request, test_find_peer);
1696 i), 1691 }
1697 &send_find_peer_request, test_find_peer);
1698 }
1699 1692
1700 if ((find_peer_ctx->peer_hash == NULL) && (find_peer_ctx->peer_min_heap 1693 if ((find_peer_ctx->peer_hash == NULL) && (find_peer_ctx->peer_min_heap
1701 == NULL)) 1694 == NULL))
1702 { 1695 {
1703 find_peer_ctx->peer_hash 1696 find_peer_ctx->peer_hash = GNUNET_CONTAINER_multihashmap_create (num_peers);
1704 = GNUNET_CONTAINER_multihashmap_create (num_peers); 1697 find_peer_ctx->peer_min_heap
1705 find_peer_ctx->peer_min_heap 1698 = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN);
1706 = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); 1699 }
1707 }
1708 else 1700 else
1709 { 1701 {
1710 GNUNET_CONTAINER_multihashmap_iterate (find_peer_ctx->peer_hash, 1702 GNUNET_CONTAINER_multihashmap_iterate (find_peer_ctx->peer_hash,
1711 &remove_peer_count, find_peer_ctx); 1703 &remove_peer_count, find_peer_ctx);
1712 GNUNET_CONTAINER_multihashmap_destroy (find_peer_ctx->peer_hash); 1704 GNUNET_CONTAINER_multihashmap_destroy (find_peer_ctx->peer_hash);
1713 find_peer_ctx->peer_hash 1705 find_peer_ctx->peer_hash = GNUNET_CONTAINER_multihashmap_create (num_peers);
1714 = GNUNET_CONTAINER_multihashmap_create (num_peers); 1706 }
1715 }
1716 1707
1717 GNUNET_assert(0 == GNUNET_CONTAINER_multihashmap_size(find_peer_ctx->peer_hash)); 1708 GNUNET_assert (0 ==
1718 GNUNET_assert(0 == GNUNET_CONTAINER_heap_get_size(find_peer_ctx->peer_min_heap)); 1709 GNUNET_CONTAINER_multihashmap_size (find_peer_ctx->peer_hash));
1710 GNUNET_assert (0 ==
1711 GNUNET_CONTAINER_heap_get_size (find_peer_ctx->peer_min_heap));
1719} 1712}
1720 1713
1721static void 1714static void
1722schedule_churn_get_topology(void *cls, 1715schedule_churn_get_topology (void *cls,
1723 const struct GNUNET_SCHEDULER_TaskContext * tc) 1716 const struct GNUNET_SCHEDULER_TaskContext *tc)
1724{ 1717{
1725 struct FindPeerContext *find_peer_context = cls; 1718 struct FindPeerContext *find_peer_context = cls;
1719
1726 GNUNET_TESTING_get_topology (pg, &count_peers_churn_cb, find_peer_context); 1720 GNUNET_TESTING_get_topology (pg, &count_peers_churn_cb, find_peer_context);
1727} 1721}
1728 1722
@@ -1733,7 +1727,7 @@ schedule_churn_get_topology(void *cls,
1733 * @param emsg NULL on success, or a printable error on failure 1727 * @param emsg NULL on success, or a printable error on failure
1734 */ 1728 */
1735static void 1729static void
1736churn_complete(void *cls, const char *emsg) 1730churn_complete (void *cls, const char *emsg)
1737{ 1731{
1738 struct FindPeerContext *find_peer_context = cls; 1732 struct FindPeerContext *find_peer_context = cls;
1739 struct PeerCount *peer_count; 1733 struct PeerCount *peer_count;
@@ -1744,12 +1738,12 @@ churn_complete(void *cls, const char *emsg)
1744 int count_added; 1738 int count_added;
1745 1739
1746 if (emsg != NULL) 1740 if (emsg != NULL)
1747 { 1741 {
1748 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 1742 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1749 "Ending test, churning of peers failed with error `%s'", emsg); 1743 "Ending test, churning of peers failed with error `%s'", emsg);
1750 GNUNET_SCHEDULER_add_now (&end_badly, (void *) emsg); 1744 GNUNET_SCHEDULER_add_now (&end_badly, (void *) emsg);
1751 return; 1745 return;
1752 } 1746 }
1753 1747
1754 /** 1748 /**
1755 * If we switched any peers on, we have to somehow force connect the new peer to 1749 * If we switched any peers on, we have to somehow force connect the new peer to
@@ -1757,83 +1751,78 @@ churn_complete(void *cls, const char *emsg)
1757 * with no connections, then choose a random peer for each and connect them. 1751 * with no connections, then choose a random peer for each and connect them.
1758 */ 1752 */
1759 if (find_peer_context != NULL) 1753 if (find_peer_context != NULL)
1754 {
1755 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1756 "We have churned on some peers, so we must schedule find peer requests for them!\n");
1757 count_added = 0;
1758 for (i = 0; i < num_peers; i++)
1760 { 1759 {
1761 GNUNET_log ( 1760 temp_daemon = GNUNET_TESTING_daemon_get (pg, i);
1762 GNUNET_ERROR_TYPE_WARNING, 1761 if (GNUNET_YES == GNUNET_TESTING_daemon_running (temp_daemon))
1763 "We have churned on some peers, so we must schedule find peer requests for them!\n"); 1762 {
1764 count_added = 0; 1763 peer_count = GNUNET_malloc (sizeof (struct PeerCount));
1765 for (i = 0; i < num_peers; i++) 1764 memcpy (&peer_count->peer_id, &temp_daemon->id,
1766 { 1765 sizeof (struct GNUNET_PeerIdentity));
1767 temp_daemon = GNUNET_TESTING_daemon_get (pg, i); 1766 GNUNET_assert (peer_count->count == 0);
1768 if (GNUNET_YES == GNUNET_TESTING_daemon_running (temp_daemon)) 1767 peer_count->heap_node
1769 { 1768 = GNUNET_CONTAINER_heap_insert (find_peer_context->peer_min_heap,
1770 peer_count = GNUNET_malloc (sizeof(struct PeerCount)); 1769 peer_count, peer_count->count);
1771 memcpy (&peer_count->peer_id, &temp_daemon->id, 1770 GNUNET_CONTAINER_multihashmap_put (find_peer_context->peer_hash,
1772 sizeof(struct GNUNET_PeerIdentity)); 1771 &temp_daemon->id.hashPubKey,
1773 GNUNET_assert(peer_count->count == 0); 1772 peer_count,
1774 peer_count->heap_node 1773 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY);
1775 = GNUNET_CONTAINER_heap_insert ( 1774 count_added++;
1776 find_peer_context->peer_min_heap, 1775 }
1777 peer_count, peer_count->count);
1778 GNUNET_CONTAINER_multihashmap_put (find_peer_context->peer_hash,
1779 &temp_daemon->id.hashPubKey,
1780 peer_count,
1781 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY);
1782 count_added++;
1783 }
1784 }
1785 GNUNET_log (
1786 GNUNET_ERROR_TYPE_WARNING,
1787 "Added %d peers to heap, total size %d\n",
1788 count_added,
1789 GNUNET_CONTAINER_heap_get_size (
1790 find_peer_context->peer_min_heap));
1791 GNUNET_SCHEDULER_add_delayed (DEFAULT_PEER_DISCONNECT_TIMEOUT,
1792 &schedule_churn_get_topology,
1793 find_peer_context);
1794 } 1776 }
1777 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1778 "Added %d peers to heap, total size %d\n",
1779 count_added,
1780 GNUNET_CONTAINER_heap_get_size
1781 (find_peer_context->peer_min_heap));
1782 GNUNET_SCHEDULER_add_delayed (DEFAULT_PEER_DISCONNECT_TIMEOUT,
1783 &schedule_churn_get_topology,
1784 find_peer_context);
1785 }
1795 else 1786 else
1787 {
1788 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1789 "Only churned off peers, no find peer requests, scheduling more gets (after allowing time for peers to disconnect properly!)...\n");
1790 if (dhtlog_handle != NULL)
1796 { 1791 {
1797 GNUNET_log ( 1792 topo_ctx = GNUNET_malloc (sizeof (struct TopologyIteratorContext));
1798 GNUNET_ERROR_TYPE_WARNING, 1793 topo_ctx->cont = &do_get;
1799 "Only churned off peers, no find peer requests, scheduling more gets (after allowing time for peers to disconnect properly!)...\n"); 1794 topo_ctx->cls = all_gets;
1800 if (dhtlog_handle != NULL) 1795 topo_ctx->timeout = DEFAULT_GET_TIMEOUT;
1801 { 1796 topo_ctx->peers_seen = GNUNET_CONTAINER_multihashmap_create (num_peers);
1802 topo_ctx = GNUNET_malloc(sizeof(struct TopologyIteratorContext)); 1797 calc_timeout = GNUNET_TIME_relative_add (DEFAULT_GET_TIMEOUT,
1803 topo_ctx->cont = &do_get; 1798 all_get_timeout);
1804 topo_ctx->cls = all_gets; 1799 calc_timeout
1805 topo_ctx->timeout = DEFAULT_GET_TIMEOUT; 1800 = GNUNET_TIME_relative_add (calc_timeout,
1806 topo_ctx->peers_seen 1801 DEFAULT_TOPOLOGY_CAPTURE_TIMEOUT);
1807 = GNUNET_CONTAINER_multihashmap_create (num_peers); 1802 calc_timeout
1808 calc_timeout = GNUNET_TIME_relative_add (DEFAULT_GET_TIMEOUT, 1803 = GNUNET_TIME_relative_add (calc_timeout,
1809 all_get_timeout); 1804 DEFAULT_PEER_DISCONNECT_TIMEOUT);
1810 calc_timeout 1805 die_task
1811 = GNUNET_TIME_relative_add (calc_timeout, 1806 = GNUNET_SCHEDULER_add_delayed (calc_timeout, &end_badly,
1812 DEFAULT_TOPOLOGY_CAPTURE_TIMEOUT); 1807 "from do gets (churn_complete)");
1813 calc_timeout 1808 GNUNET_SCHEDULER_add_delayed (DEFAULT_PEER_DISCONNECT_TIMEOUT,
1814 = GNUNET_TIME_relative_add (calc_timeout, 1809 &capture_current_topology, topo_ctx);
1815 DEFAULT_PEER_DISCONNECT_TIMEOUT); 1810 dhtlog_handle->insert_round (DHT_ROUND_GET, rounds_finished);
1816 die_task 1811 }
1817 = GNUNET_SCHEDULER_add_delayed (calc_timeout, &end_badly, 1812 else
1818 "from do gets (churn_complete)"); 1813 {
1819 GNUNET_SCHEDULER_add_delayed (DEFAULT_PEER_DISCONNECT_TIMEOUT, 1814 calc_timeout = GNUNET_TIME_relative_add (DEFAULT_GET_TIMEOUT,
1820 &capture_current_topology, topo_ctx); 1815 all_get_timeout);
1821 dhtlog_handle->insert_round (DHT_ROUND_GET, rounds_finished); 1816 calc_timeout
1822 } 1817 = GNUNET_TIME_relative_add (calc_timeout,
1823 else 1818 DEFAULT_PEER_DISCONNECT_TIMEOUT);
1824 { 1819 die_task
1825 calc_timeout = GNUNET_TIME_relative_add (DEFAULT_GET_TIMEOUT, 1820 = GNUNET_SCHEDULER_add_delayed (calc_timeout, &end_badly,
1826 all_get_timeout); 1821 "from do gets (churn_complete)");
1827 calc_timeout 1822 GNUNET_SCHEDULER_add_delayed (DEFAULT_PEER_DISCONNECT_TIMEOUT,
1828 = GNUNET_TIME_relative_add (calc_timeout, 1823 &do_get, all_gets);
1829 DEFAULT_PEER_DISCONNECT_TIMEOUT);
1830 die_task
1831 = GNUNET_SCHEDULER_add_delayed (calc_timeout, &end_badly,
1832 "from do gets (churn_complete)");
1833 GNUNET_SCHEDULER_add_delayed (DEFAULT_PEER_DISCONNECT_TIMEOUT,
1834 &do_get, all_gets);
1835 }
1836 } 1824 }
1825 }
1837} 1826}
1838 1827
1839/** 1828/**
@@ -1846,7 +1835,7 @@ churn_complete(void *cls, const char *emsg)
1846 * @param tc task context (unused) 1835 * @param tc task context (unused)
1847 */ 1836 */
1848static void 1837static void
1849churn_peers(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 1838churn_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
1850{ 1839{
1851 unsigned int count_running; 1840 unsigned int count_running;
1852 unsigned int churn_up; 1841 unsigned int churn_up;
@@ -1865,39 +1854,38 @@ churn_peers(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
1865 "Not churning any peers, topology unchanged.\n"); 1854 "Not churning any peers, topology unchanged.\n");
1866 1855
1867 if (churn_up > num_peers - count_running) 1856 if (churn_up > num_peers - count_running)
1868 { 1857 {
1869 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 1858 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1870 "Churn file specified %u peers (up); only have %u!", 1859 "Churn file specified %u peers (up); only have %u!",
1871 churn_array[current_churn_round], num_peers); 1860 churn_array[current_churn_round], num_peers);
1872 churn_up = num_peers - count_running; 1861 churn_up = num_peers - count_running;
1873 } 1862 }
1874 else if (churn_down > count_running) 1863 else if (churn_down > count_running)
1875 { 1864 {
1876 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 1865 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1877 "Churn file specified %u peers (down); only have %u!", 1866 "Churn file specified %u peers (down); only have %u!",
1878 churn_array[current_churn_round], count_running); 1867 churn_array[current_churn_round], count_running);
1879 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 1868 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1880 "This will leave NO peers running (mistake in churn configuration?)!"); 1869 "This will leave NO peers running (mistake in churn configuration?)!");
1881 churn_down = count_running; 1870 churn_down = count_running;
1882 } 1871 }
1883 //timeout = GNUNET_TIME_relative_multiply(seconds_per_peer_start, churn_up > 0 ? churn_up : churn_down); 1872 //timeout = GNUNET_TIME_relative_multiply(seconds_per_peer_start, churn_up > 0 ? churn_up : churn_down);
1884 //timeout = GNUNET_TIME_relative_multiply (seconds_per_peer_start, churn_up > 0 ? churn_up : churn_down); 1873 //timeout = GNUNET_TIME_relative_multiply (seconds_per_peer_start, churn_up > 0 ? churn_up : churn_down);
1885 timeout = GNUNET_TIME_relative_multiply (DEFAULT_TIMEOUT, 2); /* FIXME: Lack of intelligent choice here */ 1874 timeout = GNUNET_TIME_relative_multiply (DEFAULT_TIMEOUT, 2); /* FIXME: Lack of intelligent choice here */
1886 find_peer_context = NULL; 1875 find_peer_context = NULL;
1887 if (churn_up > 0) /* Only need to do find peer requests if we turned new peers on */ 1876 if (churn_up > 0) /* Only need to do find peer requests if we turned new peers on */
1888 { 1877 {
1889 find_peer_context = GNUNET_malloc(sizeof(struct FindPeerContext)); 1878 find_peer_context = GNUNET_malloc (sizeof (struct FindPeerContext));
1890 find_peer_context->count_peers_cb = &count_peers_churn_cb; 1879 find_peer_context->count_peers_cb = &count_peers_churn_cb;
1891 find_peer_context->previous_peers = 0; 1880 find_peer_context->previous_peers = 0;
1892 find_peer_context->current_peers = 0; 1881 find_peer_context->current_peers = 0;
1893 find_peer_context->endtime = GNUNET_TIME_relative_to_absolute (timeout); 1882 find_peer_context->endtime = GNUNET_TIME_relative_to_absolute (timeout);
1894 find_peer_context->peer_hash 1883 find_peer_context->peer_hash
1895 = GNUNET_CONTAINER_multihashmap_create (num_peers); 1884 = GNUNET_CONTAINER_multihashmap_create (num_peers);
1896 find_peer_context->peer_min_heap 1885 find_peer_context->peer_min_heap
1897 = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); 1886 = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN);
1898 } 1887 }
1899 GNUNET_log ( 1888 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1900 GNUNET_ERROR_TYPE_WARNING,
1901 "churn_peers: want %u total, %u running, starting %u, stopping %u\n", 1889 "churn_peers: want %u total, %u running, starting %u, stopping %u\n",
1902 churn_array[current_churn_round], count_running, churn_up, 1890 churn_array[current_churn_round], count_running, churn_up,
1903 churn_down); 1891 churn_down);
@@ -1910,147 +1898,135 @@ churn_peers(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
1910 * Task to release DHT handle associated with GET request. 1898 * Task to release DHT handle associated with GET request.
1911 */ 1899 */
1912static void 1900static void
1913get_stop_finished(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 1901get_stop_finished (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
1914{ 1902{
1915 struct TestGetContext *test_get = cls; 1903 struct TestGetContext *test_get = cls;
1916 struct TopologyIteratorContext *topo_ctx; 1904 struct TopologyIteratorContext *topo_ctx;
1917 1905
1918 /* The dht_handle may be null if this get was scheduled from a down peer */ 1906 /* The dht_handle may be null if this get was scheduled from a down peer */
1919 if (test_get->dht_handle != NULL) 1907 if (test_get->dht_handle != NULL)
1920 { 1908 {
1921 GNUNET_DHT_disconnect (test_get->dht_handle); 1909 GNUNET_DHT_disconnect (test_get->dht_handle);
1922 outstanding_gets--; /* GET is really finished */ 1910 outstanding_gets--; /* GET is really finished */
1923 test_get->dht_handle = NULL; 1911 test_get->dht_handle = NULL;
1924 } 1912 }
1925 1913
1926 /* Reset the uid (which item to search for) and the daemon (which peer to search from) for later get request iterations */ 1914 /* Reset the uid (which item to search for) and the daemon (which peer to search from) for later get request iterations */
1927 if (get_from_same == GNUNET_NO) 1915 if (get_from_same == GNUNET_NO)
1928 { 1916 {
1929 test_get->uid = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 1917 test_get->uid = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK,
1930 num_puts); 1918 num_puts);
1931 test_get->daemon 1919 test_get->daemon
1932 = GNUNET_TESTING_daemon_get ( 1920 = GNUNET_TESTING_daemon_get (pg,
1933 pg, 1921 GNUNET_CRYPTO_random_u32
1934 GNUNET_CRYPTO_random_u32 ( 1922 (GNUNET_CRYPTO_QUALITY_WEAK, num_peers));
1935 GNUNET_CRYPTO_QUALITY_WEAK, 1923 }
1936 num_peers));
1937 }
1938 1924
1939#if VERBOSE > 1 1925#if VERBOSE > 1
1940 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "%d gets succeeded, %d gets failed!\n", gets_completed, gets_failed); 1926 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "%d gets succeeded, %d gets failed!\n",
1927 gets_completed, gets_failed);
1941#endif 1928#endif
1942 update_meter (get_meter); 1929 update_meter (get_meter);
1943 if ((gets_completed + gets_failed == num_gets) && (outstanding_gets == 0)) 1930 if ((gets_completed + gets_failed == num_gets) && (outstanding_gets == 0))
1944 { 1931 {
1945 fprintf ( 1932 fprintf (stderr,
1946 stderr, 1933 "Canceling die task (get_stop_finished) %llu gets completed, %llu gets failed\n",
1947 "Canceling die task (get_stop_finished) %llu gets completed, %llu gets failed\n", 1934 gets_completed, gets_failed);
1948 gets_completed, gets_failed); 1935 if ((GNUNET_YES == dhtlog_minimal) && (NULL != dhtlog_handle))
1949 if ((GNUNET_YES == dhtlog_minimal) && (NULL != dhtlog_handle)) 1936 dhtlog_handle->insert_round_details (DHT_ROUND_GET, rounds_finished,
1950 dhtlog_handle->insert_round_details (DHT_ROUND_GET, rounds_finished, 1937 num_gets, gets_completed);
1951 num_gets, gets_completed); 1938 GNUNET_SCHEDULER_cancel (die_task);
1952 GNUNET_SCHEDULER_cancel (die_task); 1939 reset_meter (put_meter);
1953 reset_meter (put_meter); 1940 reset_meter (get_meter);
1954 reset_meter (get_meter); 1941 if ((target_completions > 0) && (gets_completed > target_completions))
1955 if ((target_completions > 0) 1942 fprintf (stderr, "Ending test early due to GET success!\n");
1956 && (gets_completed > target_completions))
1957 fprintf(stderr, "Ending test early due to GET success!\n");
1958 /** 1943 /**
1959 * Handle all cases: 1944 * Handle all cases:
1960 * 1) Testing is completely finished, call the topology iteration dealy and die 1945 * 1) Testing is completely finished, call the topology iteration dealy and die
1961 * 2) Testing is not finished, churn the network and do gets again (current_churn_round < churn_rounds) 1946 * 2) Testing is not finished, churn the network and do gets again (current_churn_round < churn_rounds)
1962 * 3) Testing is not finished, reschedule all the PUTS *and* GETS again (num_rounds > 1) 1947 * 3) Testing is not finished, reschedule all the PUTS *and* GETS again (num_rounds > 1)
1963 */ 1948 */
1964 if ((rounds_finished == total_rounds - 1) || ((target_completions > 0) 1949 if ((rounds_finished == total_rounds - 1) || ((target_completions > 0) && (gets_completed > target_completions))) /* Everything is finished, end testing */
1965 && (gets_completed > target_completions))) /* Everything is finished, end testing */ 1950 {
1966 { 1951 if ((dhtlog_handle != NULL) && (GNUNET_NO == dhtlog_minimal))
1967 if ((dhtlog_handle != NULL) && (GNUNET_NO == dhtlog_minimal)) 1952 {
1968 { 1953 topo_ctx = GNUNET_malloc (sizeof (struct TopologyIteratorContext));
1969 topo_ctx = GNUNET_malloc(sizeof(struct TopologyIteratorContext)); 1954 topo_ctx->cont = &log_dht_statistics;
1970 topo_ctx->cont = &log_dht_statistics; 1955 topo_ctx->peers_seen = GNUNET_CONTAINER_multihashmap_create (num_peers);
1971 topo_ctx->peers_seen 1956 GNUNET_SCHEDULER_add_now (&capture_current_topology, topo_ctx);
1972 = GNUNET_CONTAINER_multihashmap_create (num_peers); 1957 }
1973 GNUNET_SCHEDULER_add_now (&capture_current_topology, topo_ctx); 1958 else
1974 } 1959 GNUNET_SCHEDULER_add_now (&finish_testing, NULL);
1975 else 1960 }
1976 GNUNET_SCHEDULER_add_now (&finish_testing, NULL); 1961 else if (current_churn_round < churns_per_round * (rounds_finished + 1)) /* Do next round of churn */
1977 } 1962 {
1978 else if (current_churn_round < churns_per_round * (rounds_finished + 1)) /* Do next round of churn */ 1963 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1979 { 1964 "Current churn round %u, real round %u, scheduling next round of churn.\n",
1980 GNUNET_log ( 1965 current_churn_round, rounds_finished + 1);
1981 GNUNET_ERROR_TYPE_WARNING, 1966 gets_completed = 0;
1982 "Current churn round %u, real round %u, scheduling next round of churn.\n", 1967 gets_failed = 0;
1983 current_churn_round, rounds_finished + 1);
1984 gets_completed = 0;
1985 gets_failed = 0;
1986 1968
1987 if (dhtlog_handle != NULL) 1969 if (dhtlog_handle != NULL)
1988 dhtlog_handle->insert_round (DHT_ROUND_CHURN, rounds_finished); 1970 dhtlog_handle->insert_round (DHT_ROUND_CHURN, rounds_finished);
1989 1971
1990 GNUNET_SCHEDULER_add_now (&churn_peers, NULL); 1972 GNUNET_SCHEDULER_add_now (&churn_peers, NULL);
1991 } 1973 }
1992 else if (rounds_finished < total_rounds - 1) /* Start a new complete round */ 1974 else if (rounds_finished < total_rounds - 1) /* Start a new complete round */
1993 { 1975 {
1994 rounds_finished++; 1976 rounds_finished++;
1995 gets_completed = 0; 1977 gets_completed = 0;
1996 gets_failed = 0; 1978 gets_failed = 0;
1997 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 1979 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
1998 "Round %u of %llu finished, scheduling next round.\n", 1980 "Round %u of %llu finished, scheduling next round.\n",
1999 rounds_finished, total_rounds); 1981 rounds_finished, total_rounds);
2000 1982
2001 /** We reset the peer daemon for puts and gets on each disconnect, so all we need to do is start another round! */ 1983 /** We reset the peer daemon for puts and gets on each disconnect, so all we need to do is start another round! */
2002 if (GNUNET_YES == in_dht_replication) /* Replication done in DHT, don't redo puts! */ 1984 if (GNUNET_YES == in_dht_replication) /* Replication done in DHT, don't redo puts! */
2003 { 1985 {
2004 if (dhtlog_handle != NULL) 1986 if (dhtlog_handle != NULL)
2005 dhtlog_handle->insert_round (DHT_ROUND_GET, rounds_finished); 1987 dhtlog_handle->insert_round (DHT_ROUND_GET, rounds_finished);
2006 1988
2007 die_task 1989 die_task
2008 = GNUNET_SCHEDULER_add_delayed ( 1990 =
2009 GNUNET_TIME_relative_add ( 1991 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_add
2010 GNUNET_TIME_relative_add ( 1992 (GNUNET_TIME_relative_add
2011 GNUNET_TIME_relative_multiply ( 1993 (GNUNET_TIME_relative_multiply
2012 GNUNET_TIME_UNIT_SECONDS, 1994 (GNUNET_TIME_UNIT_SECONDS,
2013 round_delay), 1995 round_delay), all_get_timeout),
2014 all_get_timeout), 1996 DEFAULT_TOPOLOGY_CAPTURE_TIMEOUT),
2015 DEFAULT_TOPOLOGY_CAPTURE_TIMEOUT), 1997 &end_badly,
2016 &end_badly, 1998 "from do gets (next round)");
2017 "from do gets (next round)"); 1999 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
2018 GNUNET_SCHEDULER_add_delayed ( 2000 (GNUNET_TIME_UNIT_SECONDS, round_delay),
2019 GNUNET_TIME_relative_multiply ( 2001 &do_get, all_gets);
2020 GNUNET_TIME_UNIT_SECONDS, 2002 }
2021 round_delay), 2003 else
2022 &do_get, all_gets); 2004 {
2023 } 2005 if (dhtlog_handle != NULL)
2024 else 2006 dhtlog_handle->insert_round (DHT_ROUND_NORMAL, rounds_finished);
2025 { 2007 die_task
2026 if (dhtlog_handle != NULL) 2008 =
2027 dhtlog_handle->insert_round (DHT_ROUND_NORMAL, rounds_finished); 2009 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_add
2028 die_task 2010 (GNUNET_TIME_relative_multiply
2029 = GNUNET_SCHEDULER_add_delayed ( 2011 (GNUNET_TIME_UNIT_SECONDS,
2030 GNUNET_TIME_relative_add ( 2012 round_delay),
2031 GNUNET_TIME_relative_multiply ( 2013 GNUNET_TIME_relative_multiply
2032 GNUNET_TIME_UNIT_SECONDS, 2014 (GNUNET_TIME_UNIT_SECONDS,
2033 round_delay), 2015 num_puts * 2)), &end_badly,
2034 GNUNET_TIME_relative_multiply ( 2016 "from do puts");
2035 GNUNET_TIME_UNIT_SECONDS, 2017 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
2036 num_puts 2018 (GNUNET_TIME_UNIT_SECONDS, round_delay),
2037 * 2)), 2019 &do_put, all_puts);
2038 &end_badly, "from do puts"); 2020 }
2039 GNUNET_SCHEDULER_add_delayed (
2040 GNUNET_TIME_relative_multiply (
2041 GNUNET_TIME_UNIT_SECONDS,
2042 round_delay),
2043 &do_put, all_puts);
2044 }
2045 }
2046 } 2021 }
2022 }
2047} 2023}
2048 2024
2049/** 2025/**
2050 * Task to release get handle. 2026 * Task to release get handle.
2051 */ 2027 */
2052static void 2028static void
2053get_stop_task(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 2029get_stop_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
2054{ 2030{
2055 struct TestGetContext *test_get = cls; 2031 struct TestGetContext *test_get = cls;
2056 2032
@@ -2059,7 +2035,7 @@ get_stop_task(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
2059 else 2035 else
2060 cumulative_successful_gets++; 2036 cumulative_successful_gets++;
2061 2037
2062 GNUNET_assert(test_get->get_handle != NULL); 2038 GNUNET_assert (test_get->get_handle != NULL);
2063 GNUNET_DHT_get_stop (test_get->get_handle); 2039 GNUNET_DHT_get_stop (test_get->get_handle);
2064 test_get->get_handle = NULL; 2040 test_get->get_handle = NULL;
2065 test_get->disconnect_task = GNUNET_SCHEDULER_NO_TASK; 2041 test_get->disconnect_task = GNUNET_SCHEDULER_NO_TASK;
@@ -2081,28 +2057,28 @@ get_stop_task(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
2081 * @param data pointer to the result data 2057 * @param data pointer to the result data
2082 */ 2058 */
2083static void 2059static void
2084get_result_iterator(void *cls, struct GNUNET_TIME_Absolute exp, 2060get_result_iterator (void *cls, struct GNUNET_TIME_Absolute exp,
2085 const GNUNET_HashCode * key, 2061 const GNUNET_HashCode * key,
2086 const struct GNUNET_PeerIdentity * const *get_path, 2062 const struct GNUNET_PeerIdentity *const *get_path,
2087 const struct GNUNET_PeerIdentity * const *put_path, 2063 const struct GNUNET_PeerIdentity *const *put_path,
2088 enum GNUNET_BLOCK_Type type, size_t size, const void *data) 2064 enum GNUNET_BLOCK_Type type, size_t size, const void *data)
2089{ 2065{
2090 struct TestGetContext *test_get = cls; 2066 struct TestGetContext *test_get = cls;
2091 2067
2092 if (test_get->succeeded == GNUNET_YES) 2068 if (test_get->succeeded == GNUNET_YES)
2093 return; /* Get has already been successful, probably ending now */ 2069 return; /* Get has already been successful, probably ending now */
2094 2070
2095 if (0 != memcmp (&known_keys[test_get->uid], key, sizeof(GNUNET_HashCode))) /* || (0 != memcmp(original_data, data, sizeof(original_data))))*/ 2071 if (0 != memcmp (&known_keys[test_get->uid], key, sizeof (GNUNET_HashCode))) /* || (0 != memcmp(original_data, data, sizeof(original_data)))) */
2096 { 2072 {
2097 gets_completed++; 2073 gets_completed++;
2098 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 2074 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
2099 "Key or data is not the same as was inserted!\n"); 2075 "Key or data is not the same as was inserted!\n");
2100 } 2076 }
2101 else 2077 else
2102 { 2078 {
2103 gets_completed++; 2079 gets_completed++;
2104 test_get->succeeded = GNUNET_YES; 2080 test_get->succeeded = GNUNET_YES;
2105 } 2081 }
2106#if VERBOSE > 1 2082#if VERBOSE > 1
2107 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received correct GET response!\n"); 2083 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received correct GET response!\n");
2108#endif 2084#endif
@@ -2115,46 +2091,44 @@ get_result_iterator(void *cls, struct GNUNET_TIME_Absolute exp,
2115 * Set up some data, and call API PUT function 2091 * Set up some data, and call API PUT function
2116 */ 2092 */
2117static void 2093static void
2118do_get(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 2094do_get (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
2119{ 2095{
2120 struct TestGetContext *test_get = cls; 2096 struct TestGetContext *test_get = cls;
2121 2097
2122 if (num_gets == 0) 2098 if (num_gets == 0)
2123 { 2099 {
2124 GNUNET_SCHEDULER_cancel (die_task); 2100 GNUNET_SCHEDULER_cancel (die_task);
2125 GNUNET_SCHEDULER_add_now (&finish_testing, NULL); 2101 GNUNET_SCHEDULER_add_now (&finish_testing, NULL);
2126 } 2102 }
2127 2103
2128 if (test_get == NULL) 2104 if (test_get == NULL)
2129 return; /* End of the list */ 2105 return; /* End of the list */
2130 2106
2131 /* Set this here in case we are re-running gets */ 2107 /* Set this here in case we are re-running gets */
2132 test_get->succeeded = GNUNET_NO; 2108 test_get->succeeded = GNUNET_NO;
2133 2109
2134 if (GNUNET_YES != GNUNET_TESTING_daemon_running (test_get->daemon)) /* If the peer has been churned off, don't try issuing request from it! */ 2110 if (GNUNET_YES != GNUNET_TESTING_daemon_running (test_get->daemon)) /* If the peer has been churned off, don't try issuing request from it! */
2135 { 2111 {
2136 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 2112 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
2137 "Peer we should issue get request from is down, skipping.\n"); 2113 "Peer we should issue get request from is down, skipping.\n");
2138 gets_failed++; 2114 gets_failed++;
2139 GNUNET_SCHEDULER_add_now (&get_stop_finished, test_get); 2115 GNUNET_SCHEDULER_add_now (&get_stop_finished, test_get);
2140 GNUNET_SCHEDULER_add_now (&do_get, test_get->next); 2116 GNUNET_SCHEDULER_add_now (&do_get, test_get->next);
2141 return; 2117 return;
2142 } 2118 }
2143 2119
2144 /* Check if more gets are outstanding than should be */ 2120 /* Check if more gets are outstanding than should be */
2145 if (outstanding_gets > max_outstanding_gets) 2121 if (outstanding_gets > max_outstanding_gets)
2146 { 2122 {
2147 GNUNET_SCHEDULER_add_delayed ( 2123 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
2148 GNUNET_TIME_relative_multiply ( 2124 (GNUNET_TIME_UNIT_MILLISECONDS, 200), &do_get,
2149 GNUNET_TIME_UNIT_MILLISECONDS, 2125 test_get);
2150 200), 2126 return;
2151 &do_get, test_get); 2127 }
2152 return;
2153 }
2154 2128
2155 /* Connect to the first peer's DHT */ 2129 /* Connect to the first peer's DHT */
2156 test_get->dht_handle = GNUNET_DHT_connect (test_get->daemon->cfg, 10); 2130 test_get->dht_handle = GNUNET_DHT_connect (test_get->daemon->cfg, 10);
2157 GNUNET_assert(test_get->dht_handle != NULL); 2131 GNUNET_assert (test_get->dht_handle != NULL);
2158 outstanding_gets++; 2132 outstanding_gets++;
2159 2133
2160 cumulative_num_gets++; 2134 cumulative_num_gets++;
@@ -2169,8 +2143,7 @@ do_get(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
2169 2143
2170#if VERBOSE > 1 2144#if VERBOSE > 1
2171 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting get for uid %u from peer %s\n", 2145 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting get for uid %u from peer %s\n",
2172 test_get->uid, 2146 test_get->uid, test_get->daemon->shortname);
2173 test_get->daemon->shortname);
2174#endif 2147#endif
2175 test_get->disconnect_task = GNUNET_SCHEDULER_add_delayed (get_timeout, 2148 test_get->disconnect_task = GNUNET_SCHEDULER_add_delayed (get_timeout,
2176 &get_stop_task, 2149 &get_stop_task,
@@ -2185,10 +2158,11 @@ do_get(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
2185 * Schedule the GET request for some time in the future. 2158 * Schedule the GET request for some time in the future.
2186 */ 2159 */
2187static void 2160static void
2188put_finished(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 2161put_finished (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
2189{ 2162{
2190 struct TestPutContext *test_put = cls; 2163 struct TestPutContext *test_put = cls;
2191 struct TopologyIteratorContext *topo_ctx; 2164 struct TopologyIteratorContext *topo_ctx;
2165
2192 outstanding_puts--; 2166 outstanding_puts--;
2193 puts_completed++; 2167 puts_completed++;
2194 2168
@@ -2198,125 +2172,115 @@ put_finished(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
2198 /* Reset the daemon (which peer to insert at) for later put request iterations */ 2172 /* Reset the daemon (which peer to insert at) for later put request iterations */
2199 if (replicate_same == GNUNET_NO) 2173 if (replicate_same == GNUNET_NO)
2200 test_put->daemon 2174 test_put->daemon
2201 = GNUNET_TESTING_daemon_get ( 2175 = GNUNET_TESTING_daemon_get (pg,
2202 pg, 2176 GNUNET_CRYPTO_random_u32
2203 GNUNET_CRYPTO_random_u32 ( 2177 (GNUNET_CRYPTO_QUALITY_WEAK, num_peers));
2204 GNUNET_CRYPTO_QUALITY_WEAK,
2205 num_peers));
2206 2178
2207 GNUNET_SCHEDULER_cancel (test_put->disconnect_task); 2179 GNUNET_SCHEDULER_cancel (test_put->disconnect_task);
2208 test_put->disconnect_task = GNUNET_SCHEDULER_add_now (&put_disconnect_task, 2180 test_put->disconnect_task = GNUNET_SCHEDULER_add_now (&put_disconnect_task,
2209 test_put); 2181 test_put);
2210 if (GNUNET_YES == update_meter (put_meter)) 2182 if (GNUNET_YES == update_meter (put_meter))
2183 {
2184 GNUNET_assert (outstanding_puts == 0);
2185 GNUNET_SCHEDULER_cancel (die_task);
2186 if ((dhtlog_handle != NULL) && (GNUNET_NO == dhtlog_minimal))
2211 { 2187 {
2212 GNUNET_assert(outstanding_puts == 0); 2188 topo_ctx = GNUNET_malloc (sizeof (struct TopologyIteratorContext));
2213 GNUNET_SCHEDULER_cancel (die_task); 2189 topo_ctx->cont = &do_get;
2214 if ((dhtlog_handle != NULL) && (GNUNET_NO == dhtlog_minimal)) 2190 topo_ctx->cls = all_gets;
2215 { 2191 topo_ctx->timeout = DEFAULT_GET_TIMEOUT;
2216 topo_ctx = GNUNET_malloc(sizeof(struct TopologyIteratorContext)); 2192 topo_ctx->peers_seen = GNUNET_CONTAINER_multihashmap_create (num_peers);
2217 topo_ctx->cont = &do_get; 2193 die_task
2218 topo_ctx->cls = all_gets; 2194 =
2219 topo_ctx->timeout = DEFAULT_GET_TIMEOUT; 2195 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_add
2220 topo_ctx->peers_seen 2196 (GNUNET_TIME_relative_add
2221 = GNUNET_CONTAINER_multihashmap_create (num_peers); 2197 (DEFAULT_GET_TIMEOUT, all_get_timeout),
2222 die_task 2198 DEFAULT_TOPOLOGY_CAPTURE_TIMEOUT),
2223 = GNUNET_SCHEDULER_add_delayed ( 2199 &end_badly,
2224 GNUNET_TIME_relative_add ( 2200 "from do gets (put finished)");
2225 GNUNET_TIME_relative_add ( 2201 GNUNET_SCHEDULER_add_now (&capture_current_topology, topo_ctx);
2226 DEFAULT_GET_TIMEOUT, 2202 }
2227 all_get_timeout), 2203 else
2228 DEFAULT_TOPOLOGY_CAPTURE_TIMEOUT), 2204 {
2229 &end_badly, 2205 fprintf (stderr, "Scheduling die task (put finished)\n");
2230 "from do gets (put finished)"); 2206 die_task
2231 GNUNET_SCHEDULER_add_now (&capture_current_topology, topo_ctx); 2207 =
2232 } 2208 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_add
2233 else 2209 (DEFAULT_GET_TIMEOUT, all_get_timeout),
2234 { 2210 &end_badly,
2235 fprintf (stderr, "Scheduling die task (put finished)\n"); 2211 "from do gets (put finished)");
2236 die_task 2212 GNUNET_SCHEDULER_add_delayed (DEFAULT_GET_TIMEOUT, &do_get, all_gets);
2237 = GNUNET_SCHEDULER_add_delayed (
2238 GNUNET_TIME_relative_add (
2239 DEFAULT_GET_TIMEOUT,
2240 all_get_timeout),
2241 &end_badly,
2242 "from do gets (put finished)");
2243 GNUNET_SCHEDULER_add_delayed (DEFAULT_GET_TIMEOUT, &do_get, all_gets);
2244 }
2245 return;
2246 } 2213 }
2214 return;
2215 }
2247} 2216}
2248 2217
2249/** 2218/**
2250 * Set up some data, and call API PUT function 2219 * Set up some data, and call API PUT function
2251 */ 2220 */
2252static void 2221static void
2253do_put(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 2222do_put (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
2254{ 2223{
2255 struct TestPutContext *test_put = cls; 2224 struct TestPutContext *test_put = cls;
2256 char data[test_data_size]; /* Made up data to store */ 2225 char data[test_data_size]; /* Made up data to store */
2257 uint32_t rand; 2226 uint32_t rand;
2258 int i; 2227 int i;
2259 2228
2260 if (test_put == NULL) 2229 if (test_put == NULL)
2261 return; /* End of list */ 2230 return; /* End of list */
2262 2231
2263 if (GNUNET_YES != GNUNET_TESTING_daemon_running (test_put->daemon)) /* If the peer has been churned off, don't try issuing request from it! */ 2232 if (GNUNET_YES != GNUNET_TESTING_daemon_running (test_put->daemon)) /* If the peer has been churned off, don't try issuing request from it! */
2264 { 2233 {
2265 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 2234 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
2266 "Peer we should issue put request at is down, skipping.\n"); 2235 "Peer we should issue put request at is down, skipping.\n");
2267 update_meter (put_meter); 2236 update_meter (put_meter);
2268 GNUNET_SCHEDULER_add_now (&do_put, test_put->next); 2237 GNUNET_SCHEDULER_add_now (&do_put, test_put->next);
2269 return; 2238 return;
2270 } 2239 }
2271 2240
2272 for (i = 0; i < sizeof(data); i++) 2241 for (i = 0; i < sizeof (data); i++)
2273 { 2242 {
2274 memset (&data[i], GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 2243 memset (&data[i], GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK,
2275 UINT32_MAX), 1); 2244 UINT32_MAX), 1);
2276 } 2245 }
2277 2246
2278 if (outstanding_puts > max_outstanding_puts) 2247 if (outstanding_puts > max_outstanding_puts)
2279 { 2248 {
2280 GNUNET_SCHEDULER_add_delayed ( 2249 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
2281 GNUNET_TIME_relative_multiply ( 2250 (GNUNET_TIME_UNIT_MILLISECONDS, 200), &do_put,
2282 GNUNET_TIME_UNIT_MILLISECONDS, 2251 test_put);
2283 200), 2252 return;
2284 &do_put, test_put); 2253 }
2285 return;
2286 }
2287 2254
2288#if VERBOSE > 1 2255#if VERBOSE > 1
2289 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting put for uid %u from peer %s\n", 2256 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting put for uid %u from peer %s\n",
2290 test_put->uid, 2257 test_put->uid, test_put->daemon->shortname);
2291 test_put->daemon->shortname);
2292#endif 2258#endif
2293 test_put->dht_handle = GNUNET_DHT_connect (test_put->daemon->cfg, 10); 2259 test_put->dht_handle = GNUNET_DHT_connect (test_put->daemon->cfg, 10);
2294 2260
2295 GNUNET_assert(test_put->dht_handle != NULL); 2261 GNUNET_assert (test_put->dht_handle != NULL);
2296 outstanding_puts++; 2262 outstanding_puts++;
2297 GNUNET_DHT_put (test_put->dht_handle, &known_keys[test_put->uid], 2263 GNUNET_DHT_put (test_put->dht_handle, &known_keys[test_put->uid],
2298 put_replication, GNUNET_DHT_RO_NONE, GNUNET_BLOCK_TYPE_TEST, 2264 put_replication, GNUNET_DHT_RO_NONE, GNUNET_BLOCK_TYPE_TEST,
2299 sizeof(data), data, GNUNET_TIME_UNIT_FOREVER_ABS, put_delay, 2265 sizeof (data), data, GNUNET_TIME_UNIT_FOREVER_ABS, put_delay,
2300 &put_finished, test_put); 2266 &put_finished, test_put);
2301 test_put->disconnect_task 2267 test_put->disconnect_task
2302 = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_get_forever (), 2268 = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_get_forever (),
2303 &put_disconnect_task, test_put); 2269 &put_disconnect_task, test_put);
2304 rand = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 2); 2270 rand = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 2);
2305 GNUNET_SCHEDULER_add_delayed ( 2271 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
2306 GNUNET_TIME_relative_multiply ( 2272 (GNUNET_TIME_UNIT_SECONDS, rand), &do_put,
2307 GNUNET_TIME_UNIT_SECONDS,
2308 rand), &do_put,
2309 test_put->next); 2273 test_put->next);
2310} 2274}
2311 2275
2312static void 2276static void
2313schedule_find_peer_requests(void *cls, 2277schedule_find_peer_requests (void *cls,
2314 const struct GNUNET_SCHEDULER_TaskContext * tc); 2278 const struct GNUNET_SCHEDULER_TaskContext *tc);
2315 2279
2316#if HAVE_MALICIOUS 2280#if HAVE_MALICIOUS
2317static void 2281static void
2318setup_malicious_peers(void *cls, 2282setup_malicious_peers (void *cls,
2319 const struct GNUNET_SCHEDULER_TaskContext * tc); 2283 const struct GNUNET_SCHEDULER_TaskContext *tc);
2320#endif 2284#endif
2321 2285
2322/** 2286/**
@@ -2324,19 +2288,20 @@ setup_malicious_peers(void *cls,
2324 * connections in a perfect kademlia topology. 2288 * connections in a perfect kademlia topology.
2325 */ 2289 */
2326static unsigned int 2290static unsigned int
2327connection_estimate(unsigned int peer_count, unsigned int bucket_size) 2291connection_estimate (unsigned int peer_count, unsigned int bucket_size)
2328{ 2292{
2329 unsigned int i; 2293 unsigned int i;
2330 unsigned int filled; 2294 unsigned int filled;
2295
2331 i = num_peers; 2296 i = num_peers;
2332 2297
2333 filled = 0; 2298 filled = 0;
2334 while (i >= bucket_size) 2299 while (i >= bucket_size)
2335 { 2300 {
2336 filled++; 2301 filled++;
2337 i = i / 2; 2302 i = i / 2;
2338 } 2303 }
2339 filled++; /* Add one filled bucket to account for one "half full" and some miscellaneous */ 2304 filled++; /* Add one filled bucket to account for one "half full" and some miscellaneous */
2340 return filled * bucket_size * peer_count; 2305 return filled * bucket_size * peer_count;
2341 2306
2342} 2307}
@@ -2345,56 +2310,57 @@ connection_estimate(unsigned int peer_count, unsigned int bucket_size)
2345 * Callback for iterating over all the peer connections of a peer group. 2310 * Callback for iterating over all the peer connections of a peer group.
2346 */ 2311 */
2347static void 2312static void
2348count_peers_cb(void *cls, const struct GNUNET_PeerIdentity *first, 2313count_peers_cb (void *cls, const struct GNUNET_PeerIdentity *first,
2349 const struct GNUNET_PeerIdentity *second, const char *emsg) 2314 const struct GNUNET_PeerIdentity *second, const char *emsg)
2350{ 2315{
2351 struct FindPeerContext *find_peer_context = cls; 2316 struct FindPeerContext *find_peer_context = cls;
2317
2352 if ((first != NULL) && (second != NULL)) 2318 if ((first != NULL) && (second != NULL))
2319 {
2320 add_new_connection (find_peer_context, first, second);
2321 find_peer_context->current_peers++;
2322 }
2323 else
2324 {
2325 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
2326 "Peer count finished (%u connections), %u new peers, connection estimate %u (target %u)\n",
2327 find_peer_context->current_peers,
2328 find_peer_context->current_peers
2329 - find_peer_context->previous_peers,
2330 connection_estimate (num_peers, DEFAULT_BUCKET_SIZE),
2331 target_total_connections);
2332
2333 if ((find_peer_context->last_sent < 8)
2334 || ((find_peer_context->current_peers < 2
2335 * connection_estimate (num_peers, DEFAULT_BUCKET_SIZE))
2336 &&
2337 (GNUNET_TIME_absolute_get_remaining
2338 (find_peer_context->endtime).rel_value > 0) &&
2339 (find_peer_context->current_peers < target_total_connections)))
2353 { 2340 {
2354 add_new_connection (find_peer_context, first, second); 2341 GNUNET_SCHEDULER_add_now (&schedule_find_peer_requests,
2355 find_peer_context->current_peers++; 2342 find_peer_context);
2356 } 2343 }
2357 else 2344 else
2358 { 2345 {
2359 GNUNET_log ( 2346 GNUNET_CONTAINER_multihashmap_iterate (find_peer_context->peer_hash,
2360 GNUNET_ERROR_TYPE_WARNING, 2347 &remove_peer_count,
2361 "Peer count finished (%u connections), %u new peers, connection estimate %u (target %u)\n", 2348 find_peer_context);
2362 find_peer_context->current_peers, 2349 GNUNET_CONTAINER_multihashmap_destroy (find_peer_context->peer_hash);
2363 find_peer_context->current_peers 2350 GNUNET_CONTAINER_heap_destroy (find_peer_context->peer_min_heap);
2364 - find_peer_context->previous_peers, 2351 GNUNET_free (find_peer_context);
2365 connection_estimate (num_peers, DEFAULT_BUCKET_SIZE), 2352 fprintf (stderr, "Not sending any more find peer requests.\n");
2366 target_total_connections);
2367
2368 if ((find_peer_context->last_sent < 8)
2369 || ((find_peer_context->current_peers < 2
2370 * connection_estimate (num_peers, DEFAULT_BUCKET_SIZE))
2371 && (GNUNET_TIME_absolute_get_remaining (
2372 find_peer_context->endtime).rel_value
2373 > 0) && (find_peer_context->current_peers
2374 < target_total_connections)))
2375 {
2376 GNUNET_SCHEDULER_add_now (&schedule_find_peer_requests,
2377 find_peer_context);
2378 }
2379 else
2380 {
2381 GNUNET_CONTAINER_multihashmap_iterate (find_peer_context->peer_hash,
2382 &remove_peer_count,
2383 find_peer_context);
2384 GNUNET_CONTAINER_multihashmap_destroy (find_peer_context->peer_hash);
2385 GNUNET_CONTAINER_heap_destroy (find_peer_context->peer_min_heap);
2386 GNUNET_free(find_peer_context);
2387 fprintf (stderr, "Not sending any more find peer requests.\n");
2388 2353
2389#if HAVE_MALICIOUS 2354#if HAVE_MALICIOUS
2390 if (GNUNET_YES == malicious_after_settle) 2355 if (GNUNET_YES == malicious_after_settle)
2391 { 2356 {
2392 GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "calling setup_malicious_peers\n"); 2357 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
2393 GNUNET_SCHEDULER_add_now(&setup_malicious_peers, NULL); 2358 "calling setup_malicious_peers\n");
2394 } 2359 GNUNET_SCHEDULER_add_now (&setup_malicious_peers, NULL);
2360 }
2395#endif 2361#endif
2396 }
2397 } 2362 }
2363 }
2398} 2364}
2399 2365
2400/** 2366/**
@@ -2403,8 +2369,8 @@ count_peers_cb(void *cls, const struct GNUNET_PeerIdentity *first,
2403 * and the time allowed for each one! 2369 * and the time allowed for each one!
2404 */ 2370 */
2405static void 2371static void
2406schedule_find_peer_requests(void *cls, 2372schedule_find_peer_requests (void *cls,
2407 const struct GNUNET_SCHEDULER_TaskContext * tc) 2373 const struct GNUNET_SCHEDULER_TaskContext *tc)
2408{ 2374{
2409 struct FindPeerContext *find_peer_ctx = cls; 2375 struct FindPeerContext *find_peer_ctx = cls;
2410 struct TestFindPeer *test_find_peer; 2376 struct TestFindPeer *test_find_peer;
@@ -2412,12 +2378,11 @@ schedule_find_peer_requests(void *cls,
2412 uint32_t i; 2378 uint32_t i;
2413 uint32_t random; 2379 uint32_t random;
2414 2380
2415 if (find_peer_ctx->previous_peers == 0) /* First time, go slowly */ 2381 if (find_peer_ctx->previous_peers == 0) /* First time, go slowly */
2416 find_peer_ctx->total = 1; 2382 find_peer_ctx->total = 1;
2417 else if (find_peer_ctx->current_peers - find_peer_ctx->previous_peers 2383 else if (find_peer_ctx->current_peers - find_peer_ctx->previous_peers > MAX_FIND_PEER_CUTOFF) /* Found LOTS of peers, still go slowly */
2418 > MAX_FIND_PEER_CUTOFF) /* Found LOTS of peers, still go slowly */
2419 find_peer_ctx->total = find_peer_ctx->last_sent - (find_peer_ctx->last_sent 2384 find_peer_ctx->total = find_peer_ctx->last_sent - (find_peer_ctx->last_sent
2420 / 8); 2385 / 8);
2421 else 2386 else
2422 find_peer_ctx->total = find_peer_ctx->last_sent * 2; 2387 find_peer_ctx->total = find_peer_ctx->last_sent * 2;
2423 2388
@@ -2435,15 +2400,15 @@ schedule_find_peer_requests(void *cls,
2435 find_peer_offset = GNUNET_TIME_relative_divide (find_peer_delay, 2400 find_peer_offset = GNUNET_TIME_relative_divide (find_peer_delay,
2436 find_peer_ctx->total); 2401 find_peer_ctx->total);
2437 for (i = 0; i < find_peer_ctx->total; i++) 2402 for (i = 0; i < find_peer_ctx->total; i++)
2403 {
2404 test_find_peer = GNUNET_malloc (sizeof (struct TestFindPeer));
2405 /* If we haven't sent any requests yet, choose random peers */
2406 /* Also choose random in _half_ of all cases, so we don't
2407 * get stuck choosing topologically restricted peers with
2408 * few connections that will never be able to find any new
2409 * peers! */
2410 if ((find_peer_ctx->previous_peers == 0) || (i % 2 == 0))
2438 { 2411 {
2439 test_find_peer = GNUNET_malloc(sizeof(struct TestFindPeer));
2440 /* If we haven't sent any requests yet, choose random peers */
2441 /* Also choose random in _half_ of all cases, so we don't
2442 * get stuck choosing topologically restricted peers with
2443 * few connections that will never be able to find any new
2444 * peers! */
2445 if ((find_peer_ctx->previous_peers == 0) || (i % 2 == 0))
2446 {
2447 /** 2412 /**
2448 * Attempt to spread find peer requests across even sections of the peer address 2413 * Attempt to spread find peer requests across even sections of the peer address
2449 * space. Choose basically 1 peer in every num_peers / max_outstanding_requests 2414 * space. Choose basically 1 peer in every num_peers / max_outstanding_requests
@@ -2452,56 +2417,57 @@ schedule_find_peer_requests(void *cls,
2452 * For instance, if num_peers is 100 and max_outstanding is 10, first chosen peer 2417 * For instance, if num_peers is 100 and max_outstanding is 10, first chosen peer
2453 * will be between 0 - 10, second between 10 - 20, etc. 2418 * will be between 0 - 10, second between 10 - 20, etc.
2454 */ 2419 */
2455 random = (num_peers / find_peer_ctx->total) * i; 2420 random = (num_peers / find_peer_ctx->total) * i;
2456 random = random 2421 random = random
2457 + GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 2422 + GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK,
2458 (num_peers / find_peer_ctx->total)); 2423 (num_peers / find_peer_ctx->total));
2459 if (random >= num_peers) 2424 if (random >= num_peers)
2460 { 2425 {
2461 random = random - num_peers; 2426 random = random - num_peers;
2462 } 2427 }
2463#if REAL_RANDOM 2428#if REAL_RANDOM
2464 random = GNUNET_CRYPTO_random_u32(GNUNET_CRYPTO_QUALITY_WEAK, num_peers); 2429 random = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, num_peers);
2465#endif 2430#endif
2466 test_find_peer->daemon = GNUNET_TESTING_daemon_get (pg, random); 2431 test_find_peer->daemon = GNUNET_TESTING_daemon_get (pg, random);
2467 }
2468 else /* If we have sent requests, choose peers with a low number of connections to send requests from */
2469 {
2470 peer_count
2471 = GNUNET_CONTAINER_heap_remove_root (find_peer_ctx->peer_min_heap);
2472 GNUNET_assert(GNUNET_YES == GNUNET_CONTAINER_multihashmap_remove(find_peer_ctx->peer_hash, &peer_count->peer_id.hashPubKey, peer_count));
2473 test_find_peer->daemon
2474 = GNUNET_TESTING_daemon_get_by_id (pg, &peer_count->peer_id);
2475 GNUNET_assert(test_find_peer->daemon != NULL);
2476 }
2477
2478 test_find_peer->find_peer_context = find_peer_ctx;
2479 GNUNET_SCHEDULER_add_delayed (
2480 GNUNET_TIME_relative_multiply (
2481 find_peer_offset,
2482 i),
2483 &send_find_peer_request, test_find_peer);
2484 } 2432 }
2485 2433 else /* If we have sent requests, choose peers with a low number of connections to send requests from */
2486 if ((find_peer_ctx->peer_hash == NULL) && (find_peer_ctx->peer_min_heap
2487 == NULL))
2488 { 2434 {
2489 find_peer_ctx->peer_hash 2435 peer_count
2490 = GNUNET_CONTAINER_multihashmap_create (num_peers); 2436 = GNUNET_CONTAINER_heap_remove_root (find_peer_ctx->peer_min_heap);
2491 find_peer_ctx->peer_min_heap 2437 GNUNET_assert (GNUNET_YES ==
2492 = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); 2438 GNUNET_CONTAINER_multihashmap_remove
2439 (find_peer_ctx->peer_hash, &peer_count->peer_id.hashPubKey,
2440 peer_count));
2441 test_find_peer->daemon =
2442 GNUNET_TESTING_daemon_get_by_id (pg, &peer_count->peer_id);
2443 GNUNET_assert (test_find_peer->daemon != NULL);
2493 } 2444 }
2445
2446 test_find_peer->find_peer_context = find_peer_ctx;
2447 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
2448 (find_peer_offset, i),
2449 &send_find_peer_request, test_find_peer);
2450 }
2451
2452 if ((find_peer_ctx->peer_hash == NULL) && (find_peer_ctx->peer_min_heap
2453 == NULL))
2454 {
2455 find_peer_ctx->peer_hash = GNUNET_CONTAINER_multihashmap_create (num_peers);
2456 find_peer_ctx->peer_min_heap
2457 = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN);
2458 }
2494 else 2459 else
2495 { 2460 {
2496 GNUNET_CONTAINER_multihashmap_iterate (find_peer_ctx->peer_hash, 2461 GNUNET_CONTAINER_multihashmap_iterate (find_peer_ctx->peer_hash,
2497 &remove_peer_count, find_peer_ctx); 2462 &remove_peer_count, find_peer_ctx);
2498 GNUNET_CONTAINER_multihashmap_destroy (find_peer_ctx->peer_hash); 2463 GNUNET_CONTAINER_multihashmap_destroy (find_peer_ctx->peer_hash);
2499 find_peer_ctx->peer_hash 2464 find_peer_ctx->peer_hash = GNUNET_CONTAINER_multihashmap_create (num_peers);
2500 = GNUNET_CONTAINER_multihashmap_create (num_peers); 2465 }
2501 }
2502 2466
2503 GNUNET_assert(0 == GNUNET_CONTAINER_multihashmap_size(find_peer_ctx->peer_hash)); 2467 GNUNET_assert (0 ==
2504 GNUNET_assert(0 == GNUNET_CONTAINER_heap_get_size(find_peer_ctx->peer_min_heap)); 2468 GNUNET_CONTAINER_multihashmap_size (find_peer_ctx->peer_hash));
2469 GNUNET_assert (0 ==
2470 GNUNET_CONTAINER_heap_get_size (find_peer_ctx->peer_min_heap));
2505 2471
2506} 2472}
2507 2473
@@ -2512,9 +2478,9 @@ schedule_find_peer_requests(void *cls,
2512 * @param hash set to uid (extended with zeros) 2478 * @param hash set to uid (extended with zeros)
2513 */ 2479 */
2514static void 2480static void
2515hash_from_uid(uint32_t uid, GNUNET_HashCode *hash) 2481hash_from_uid (uint32_t uid, GNUNET_HashCode * hash)
2516{ 2482{
2517 memset (hash, 0, sizeof(GNUNET_HashCode)); 2483 memset (hash, 0, sizeof (GNUNET_HashCode));
2518 *((uint32_t *) hash) = uid; 2484 *((uint32_t *) hash) = uid;
2519} 2485}
2520 2486
@@ -2524,7 +2490,7 @@ hash_from_uid(uint32_t uid, GNUNET_HashCode *hash)
2524 * add to list, then schedule the actual PUT operations. 2490 * add to list, then schedule the actual PUT operations.
2525 */ 2491 */
2526static void 2492static void
2527setup_puts_and_gets(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 2493setup_puts_and_gets (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
2528{ 2494{
2529 int i; 2495 int i;
2530 struct TestPutContext *test_put; 2496 struct TestPutContext *test_put;
@@ -2532,98 +2498,99 @@ setup_puts_and_gets(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
2532 uint32_t temp_peer; 2498 uint32_t temp_peer;
2533 GNUNET_HashCode uid_hash; 2499 GNUNET_HashCode uid_hash;
2534 int count; 2500 int count;
2501
2535#if REMEMBER 2502#if REMEMBER
2536 int remember[num_puts][num_peers]; 2503 int remember[num_puts][num_peers];
2537 memset(&remember, 0, sizeof(int) * num_puts * num_peers); 2504
2505 memset (&remember, 0, sizeof (int) * num_puts * num_peers);
2538#endif 2506#endif
2539 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "in setup_puts_and_gets\n"); 2507 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "in setup_puts_and_gets\n");
2540 known_keys = GNUNET_malloc(sizeof(GNUNET_HashCode) * num_puts); 2508 known_keys = GNUNET_malloc (sizeof (GNUNET_HashCode) * num_puts);
2541 for (i = 0; i < num_puts; i++) 2509 for (i = 0; i < num_puts; i++)
2510 {
2511 test_put = GNUNET_malloc (sizeof (struct TestPutContext));
2512 test_put->uid = i;
2513 GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK,
2514 &known_keys[i]);
2515 /* Set first X bits to match the chosen sybil location if we want to do the sybil attack! */
2516 if (GNUNET_YES == malicious_sybil)
2542 { 2517 {
2543 test_put = GNUNET_malloc(sizeof(struct TestPutContext)); 2518 memcpy (&known_keys[i], &sybil_target, sizeof (GNUNET_HashCode) / 2);
2544 test_put->uid = i; 2519 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
2545 GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, 2520 "Distance between sybil location and key is %d\n",
2546 &known_keys[i]); 2521 GNUNET_CRYPTO_hash_matching_bits (&known_keys[i],
2547 /* Set first X bits to match the chosen sybil location if we want to do the sybil attack! */ 2522 &sybil_target));
2548 if (GNUNET_YES == malicious_sybil) 2523 }
2549 { 2524 temp_peer = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK,
2550 memcpy (&known_keys[i], &sybil_target, sizeof(GNUNET_HashCode) / 2); 2525 num_peers);
2551 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 2526 test_put->daemon = GNUNET_TESTING_daemon_get (pg, temp_peer);
2552 "Distance between sybil location and key is %d\n", 2527 /* Don't start PUTs at malicious peers! */
2553 GNUNET_CRYPTO_hash_matching_bits (&known_keys[i], 2528 if (malicious_bloom != NULL)
2554 &sybil_target)); 2529 {
2555 } 2530 count = 0;
2556 temp_peer = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 2531 hash_from_uid (temp_peer, &uid_hash);
2557 num_peers); 2532 while ((GNUNET_YES
2558 test_put->daemon = GNUNET_TESTING_daemon_get (pg, temp_peer);
2559 /* Don't start PUTs at malicious peers! */
2560 if (malicious_bloom != NULL)
2561 {
2562 count = 0;
2563 hash_from_uid (temp_peer, &uid_hash);
2564 while ((GNUNET_YES
2565 == GNUNET_CONTAINER_bloomfilter_test (malicious_bloom, &uid_hash)) 2533 == GNUNET_CONTAINER_bloomfilter_test (malicious_bloom, &uid_hash))
2566 && (count < num_peers)) 2534 && (count < num_peers))
2567 { 2535 {
2568 temp_peer = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 2536 temp_peer = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK,
2569 num_peers); 2537 num_peers);
2570 hash_from_uid (temp_peer, &uid_hash); 2538 hash_from_uid (temp_peer, &uid_hash);
2571 test_put->daemon = GNUNET_TESTING_daemon_get (pg, temp_peer); 2539 test_put->daemon = GNUNET_TESTING_daemon_get (pg, temp_peer);
2572 count++; 2540 count++;
2573 } 2541 }
2574 if (count == num_peers) 2542 if (count == num_peers)
2575 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 2543 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
2576 "Couldn't find peer not in malicious bloom to select!\n"); 2544 "Couldn't find peer not in malicious bloom to select!\n");
2577 }
2578
2579 test_put->next = all_puts;
2580 all_puts = test_put;
2581 } 2545 }
2582 2546
2547 test_put->next = all_puts;
2548 all_puts = test_put;
2549 }
2550
2583 for (i = 0; i < num_gets; i++) 2551 for (i = 0; i < num_gets; i++)
2584 { 2552 {
2585 test_get = GNUNET_malloc(sizeof(struct TestGetContext)); 2553 test_get = GNUNET_malloc (sizeof (struct TestGetContext));
2586 test_get->uid = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 2554 test_get->uid = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK,
2587 num_puts); 2555 num_puts);
2588#if REMEMBER 2556#if REMEMBER
2589 while (remember[test_get->uid][temp_daemon] == 1) 2557 while (remember[test_get->uid][temp_daemon] == 1)
2590 temp_daemon = GNUNET_CRYPTO_random_u32(GNUNET_CRYPTO_QUALITY_WEAK, num_peers); 2558 temp_daemon =
2591 remember[test_get->uid][temp_daemon] = 1; 2559 GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, num_peers);
2560 remember[test_get->uid][temp_daemon] = 1;
2592#endif 2561#endif
2593 temp_peer = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 2562 temp_peer = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK,
2594 num_peers); 2563 num_peers);
2595 test_get->daemon = GNUNET_TESTING_daemon_get (pg, temp_peer); 2564 test_get->daemon = GNUNET_TESTING_daemon_get (pg, temp_peer);
2596 /* Don't start GETs at malicious peers! */ 2565 /* Don't start GETs at malicious peers! */
2597 if (malicious_bloom != NULL) 2566 if (malicious_bloom != NULL)
2598 { 2567 {
2599 hash_from_uid (temp_peer, &uid_hash); 2568 hash_from_uid (temp_peer, &uid_hash);
2600 count = 0; 2569 count = 0;
2601 while ((GNUNET_YES 2570 while ((GNUNET_YES
2602 == GNUNET_CONTAINER_bloomfilter_test (malicious_bloom, &uid_hash)) 2571 == GNUNET_CONTAINER_bloomfilter_test (malicious_bloom, &uid_hash))
2603 && (count < num_peers)) 2572 && (count < num_peers))
2604 { 2573 {
2605 temp_peer = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 2574 temp_peer = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK,
2606 num_peers); 2575 num_peers);
2607 hash_from_uid (temp_peer, &uid_hash); 2576 hash_from_uid (temp_peer, &uid_hash);
2608 test_get->daemon = GNUNET_TESTING_daemon_get (pg, temp_peer); 2577 test_get->daemon = GNUNET_TESTING_daemon_get (pg, temp_peer);
2609 count++; 2578 count++;
2610 } 2579 }
2611 if (count == num_peers) 2580 if (count == num_peers)
2612 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 2581 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
2613 "Couldn't find peer not in malicious bloom to select!\n"); 2582 "Couldn't find peer not in malicious bloom to select!\n");
2614 }
2615 test_get->next = all_gets;
2616 all_gets = test_get;
2617 } 2583 }
2584 test_get->next = all_gets;
2585 all_gets = test_get;
2586 }
2618 2587
2619 /*GNUNET_SCHEDULER_cancel (die_task);*/ 2588 /*GNUNET_SCHEDULER_cancel (die_task); */
2620 die_task 2589 die_task
2621 = GNUNET_SCHEDULER_add_delayed ( 2590 =
2622 GNUNET_TIME_relative_multiply ( 2591 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
2623 GNUNET_TIME_UNIT_SECONDS, 2592 (GNUNET_TIME_UNIT_SECONDS, num_puts * 2),
2624 num_puts 2593 &end_badly, "from do puts");
2625 * 2),
2626 &end_badly, "from do puts");
2627 GNUNET_SCHEDULER_add_now (&do_put, all_puts); 2594 GNUNET_SCHEDULER_add_now (&do_put, all_puts);
2628 2595
2629} 2596}
@@ -2634,105 +2601,100 @@ setup_puts_and_gets(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
2634 * then call actual insert functions. 2601 * then call actual insert functions.
2635 */ 2602 */
2636static void 2603static void
2637continue_puts_and_gets(void *cls, 2604continue_puts_and_gets (void *cls,
2638 const struct GNUNET_SCHEDULER_TaskContext * tc) 2605 const struct GNUNET_SCHEDULER_TaskContext *tc)
2639{ 2606{
2640 int i; 2607 int i;
2641 int max; 2608 int max;
2642 struct TopologyIteratorContext *topo_ctx; 2609 struct TopologyIteratorContext *topo_ctx;
2643 struct FindPeerContext *find_peer_context; 2610 struct FindPeerContext *find_peer_context;
2611
2644 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "In continue_puts_and_gets\n"); 2612 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "In continue_puts_and_gets\n");
2645 if ((dhtlog_handle != NULL) && (GNUNET_NO == dhtlog_minimal)) 2613 if ((dhtlog_handle != NULL) && (GNUNET_NO == dhtlog_minimal))
2614 {
2615 if (settle_time >= 180 * 2)
2616 max = (settle_time / 180) - 2;
2617 else
2618 max = 1;
2619 for (i = 1; i < max; i++)
2646 { 2620 {
2647 if (settle_time >= 180 * 2) 2621 topo_ctx = GNUNET_malloc (sizeof (struct TopologyIteratorContext));
2648 max = (settle_time / 180) - 2; 2622 topo_ctx->current_iteration = i;
2649 else 2623 topo_ctx->total_iterations = max;
2650 max = 1;
2651 for (i = 1; i < max; i++)
2652 {
2653 topo_ctx = GNUNET_malloc(sizeof(struct TopologyIteratorContext));
2654 topo_ctx->current_iteration = i;
2655 topo_ctx->total_iterations = max;
2656 topo_ctx->peers_seen
2657 = GNUNET_CONTAINER_multihashmap_create (num_peers);
2658 //fprintf(stderr, "scheduled topology iteration in %d minutes\n", i);
2659 GNUNET_SCHEDULER_add_delayed (
2660 GNUNET_TIME_relative_multiply (
2661 GNUNET_TIME_UNIT_MINUTES,
2662 i * 3),
2663 &capture_current_topology, topo_ctx);
2664 }
2665 topo_ctx = GNUNET_malloc(sizeof(struct TopologyIteratorContext));
2666 topo_ctx->cont = &setup_puts_and_gets;
2667 topo_ctx->peers_seen = GNUNET_CONTAINER_multihashmap_create (num_peers); 2624 topo_ctx->peers_seen = GNUNET_CONTAINER_multihashmap_create (num_peers);
2668 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 2625 //fprintf(stderr, "scheduled topology iteration in %d minutes\n", i);
2669 "setting setup_puts_and_gets for %d seconds in the future\n", 2626 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
2670 settle_time + 10); 2627 (GNUNET_TIME_UNIT_MINUTES, i * 3),
2671 GNUNET_SCHEDULER_add_delayed (
2672 GNUNET_TIME_relative_multiply (
2673 GNUNET_TIME_UNIT_SECONDS,
2674 (settle_time
2675 + 10)),
2676 &capture_current_topology, topo_ctx); 2628 &capture_current_topology, topo_ctx);
2677 } 2629 }
2630 topo_ctx = GNUNET_malloc (sizeof (struct TopologyIteratorContext));
2631 topo_ctx->cont = &setup_puts_and_gets;
2632 topo_ctx->peers_seen = GNUNET_CONTAINER_multihashmap_create (num_peers);
2633 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
2634 "setting setup_puts_and_gets for %d seconds in the future\n",
2635 settle_time + 10);
2636 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
2637 (GNUNET_TIME_UNIT_SECONDS,
2638 (settle_time + 10)),
2639 &capture_current_topology, topo_ctx);
2640 }
2678 else 2641 else
2679 GNUNET_SCHEDULER_add_delayed ( 2642 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
2680 GNUNET_TIME_relative_multiply ( 2643 (GNUNET_TIME_UNIT_SECONDS,
2681 GNUNET_TIME_UNIT_SECONDS, 2644 (settle_time + 10)), &setup_puts_and_gets,
2682 (settle_time 2645 NULL);
2683 + 10)),
2684 &setup_puts_and_gets, NULL);
2685 2646
2686 if (dhtlog_handle != NULL) 2647 if (dhtlog_handle != NULL)
2687 dhtlog_handle->insert_round (DHT_ROUND_NORMAL, rounds_finished); 2648 dhtlog_handle->insert_round (DHT_ROUND_NORMAL, rounds_finished);
2688 2649
2689#if HAVE_MALICIOUS 2650#if HAVE_MALICIOUS
2690 if ((GNUNET_YES != malicious_after_settle) || (settle_time == 0)) 2651 if ((GNUNET_YES != malicious_after_settle) || (settle_time == 0))
2691 { 2652 {
2692 GNUNET_SCHEDULER_add_now(&setup_malicious_peers, NULL); 2653 GNUNET_SCHEDULER_add_now (&setup_malicious_peers, NULL);
2693 } 2654 }
2694#endif 2655#endif
2695 2656
2696 if ((GNUNET_YES == do_find_peer) && (settle_time > 0)) 2657 if ((GNUNET_YES == do_find_peer) && (settle_time > 0))
2697 { 2658 {
2698 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 2659 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
2699 "Scheduling find peer requests during \"settle\" time.\n"); 2660 "Scheduling find peer requests during \"settle\" time.\n");
2700 find_peer_context = GNUNET_malloc(sizeof(struct FindPeerContext)); 2661 find_peer_context = GNUNET_malloc (sizeof (struct FindPeerContext));
2701 find_peer_context->count_peers_cb = &count_peers_cb; 2662 find_peer_context->count_peers_cb = &count_peers_cb;
2702 find_peer_context->endtime 2663 find_peer_context->endtime
2703 = GNUNET_TIME_relative_to_absolute ( 2664 =
2704 GNUNET_TIME_relative_multiply ( 2665 GNUNET_TIME_relative_to_absolute (GNUNET_TIME_relative_multiply
2705 GNUNET_TIME_UNIT_SECONDS, 2666 (GNUNET_TIME_UNIT_SECONDS,
2706 settle_time)); 2667 settle_time));
2707 GNUNET_SCHEDULER_add_now (&schedule_find_peer_requests, find_peer_context); 2668 GNUNET_SCHEDULER_add_now (&schedule_find_peer_requests, find_peer_context);
2708 } 2669 }
2709 else 2670 else
2710 { 2671 {
2711 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 2672 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
2712 "Assuming automatic DHT find peer requests.\n"); 2673 "Assuming automatic DHT find peer requests.\n");
2713 } 2674 }
2714} 2675}
2715 2676
2716/** 2677/**
2717 * Task to release DHT handles 2678 * Task to release DHT handles
2718 */ 2679 */
2719static void 2680static void
2720malicious_disconnect_task(void *cls, 2681malicious_disconnect_task (void *cls,
2721 const struct GNUNET_SCHEDULER_TaskContext * tc) 2682 const struct GNUNET_SCHEDULER_TaskContext *tc)
2722{ 2683{
2723 struct MaliciousContext *ctx = cls; 2684 struct MaliciousContext *ctx = cls;
2685
2724 outstanding_malicious--; 2686 outstanding_malicious--;
2725 malicious_completed++; 2687 malicious_completed++;
2726 ctx->disconnect_task = GNUNET_SCHEDULER_NO_TASK; 2688 ctx->disconnect_task = GNUNET_SCHEDULER_NO_TASK;
2727 GNUNET_DHT_disconnect (ctx->dht_handle); 2689 GNUNET_DHT_disconnect (ctx->dht_handle);
2728 ctx->dht_handle = NULL; 2690 ctx->dht_handle = NULL;
2729 GNUNET_free(ctx); 2691 GNUNET_free (ctx);
2730 2692
2731 if (malicious_completed == malicious_getters + malicious_putters 2693 if (malicious_completed == malicious_getters + malicious_putters
2732 + malicious_droppers) 2694 + malicious_droppers)
2733 { 2695 {
2734 fprintf (stderr, "Finished setting all malicious peers up!\n"); 2696 fprintf (stderr, "Finished setting all malicious peers up!\n");
2735 } 2697 }
2736} 2698}
2737 2699
2738#if HAVE_MALICIOUS 2700#if HAVE_MALICIOUS
@@ -2740,64 +2702,66 @@ malicious_disconnect_task(void *cls,
2740 * Task to release DHT handles 2702 * Task to release DHT handles
2741 */ 2703 */
2742static void 2704static void
2743malicious_done_task(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 2705malicious_done_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
2744 { 2706{
2745 struct MaliciousContext *ctx = cls; 2707 struct MaliciousContext *ctx = cls;
2746 GNUNET_SCHEDULER_cancel (ctx->disconnect_task); 2708
2747 GNUNET_SCHEDULER_add_now (&malicious_disconnect_task, ctx); 2709 GNUNET_SCHEDULER_cancel (ctx->disconnect_task);
2748 } 2710 GNUNET_SCHEDULER_add_now (&malicious_disconnect_task, ctx);
2711}
2749 2712
2750/** 2713/**
2751 * Set up some data, and call API PUT function 2714 * Set up some data, and call API PUT function
2752 */ 2715 */
2753static void 2716static void
2754set_malicious(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 2717set_malicious (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
2755 { 2718{
2756 struct MaliciousContext *ctx = cls; 2719 struct MaliciousContext *ctx = cls;
2757 2720
2758 if (outstanding_malicious > DEFAULT_MAX_OUTSTANDING_GETS) 2721 if (outstanding_malicious > DEFAULT_MAX_OUTSTANDING_GETS)
2759 { 2722 {
2760 GNUNET_SCHEDULER_add_delayed ( 2723 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
2761 GNUNET_TIME_relative_multiply ( 2724 (GNUNET_TIME_UNIT_MILLISECONDS, 100),
2762 GNUNET_TIME_UNIT_MILLISECONDS, 2725 &set_malicious, ctx);
2763 100), 2726 return;
2764 &set_malicious, ctx); 2727 }
2765 return;
2766 }
2767 2728
2768 if (ctx->dht_handle == NULL) 2729 if (ctx->dht_handle == NULL)
2769 { 2730 {
2770 ctx->dht_handle = GNUNET_DHT_connect (ctx->daemon->cfg, 1); 2731 ctx->dht_handle = GNUNET_DHT_connect (ctx->daemon->cfg, 1);
2771 outstanding_malicious++; 2732 outstanding_malicious++;
2772 } 2733 }
2773 2734
2774 GNUNET_assert(ctx->dht_handle != NULL); 2735 GNUNET_assert (ctx->dht_handle != NULL);
2775 2736
2776#if VERBOSE > 1 2737#if VERBOSE > 1
2777 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Setting peer %s malicious type %d\n", 2738 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Setting peer %s malicious type %d\n",
2778 ctx->daemon->shortname, ctx->malicious_type); 2739 ctx->daemon->shortname, ctx->malicious_type);
2779#endif 2740#endif
2780 2741
2781 switch (ctx->malicious_type) 2742 switch (ctx->malicious_type)
2782 { 2743 {
2783 case GNUNET_MESSAGE_TYPE_DHT_MALICIOUS_GET: 2744 case GNUNET_MESSAGE_TYPE_DHT_MALICIOUS_GET:
2784 GNUNET_DHT_set_malicious_getter (ctx->dht_handle, malicious_get_frequency, &malicious_done_task, ctx); 2745 GNUNET_DHT_set_malicious_getter (ctx->dht_handle, malicious_get_frequency,
2785 break; 2746 &malicious_done_task, ctx);
2786 case GNUNET_MESSAGE_TYPE_DHT_MALICIOUS_PUT: 2747 break;
2787 GNUNET_DHT_set_malicious_putter (ctx->dht_handle, malicious_put_frequency, &malicious_done_task, ctx); 2748 case GNUNET_MESSAGE_TYPE_DHT_MALICIOUS_PUT:
2788 break; 2749 GNUNET_DHT_set_malicious_putter (ctx->dht_handle, malicious_put_frequency,
2789 case GNUNET_MESSAGE_TYPE_DHT_MALICIOUS_DROP: 2750 &malicious_done_task, ctx);
2790 GNUNET_DHT_set_malicious_dropper (ctx->dht_handle, &malicious_done_task, ctx); 2751 break;
2791 break; 2752 case GNUNET_MESSAGE_TYPE_DHT_MALICIOUS_DROP:
2792 default: 2753 GNUNET_DHT_set_malicious_dropper (ctx->dht_handle, &malicious_done_task,
2793 break; 2754 ctx);
2794 } 2755 break;
2795 2756 default:
2796 ctx->disconnect_task 2757 break;
2797 = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL,
2798 &malicious_disconnect_task, ctx);
2799 } 2758 }
2800 2759
2760 ctx->disconnect_task
2761 = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL,
2762 &malicious_disconnect_task, ctx);
2763}
2764
2801/** 2765/**
2802 * Choose the next peer from the peer group to set as malicious. 2766 * Choose the next peer from the peer group to set as malicious.
2803 * If we are doing a sybil attack, find the nearest peer to the 2767 * If we are doing a sybil attack, find the nearest peer to the
@@ -2809,57 +2773,70 @@ set_malicious(void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
2809 * chosen to be malicious 2773 * chosen to be malicious
2810 */ 2774 */
2811static uint32_t 2775static uint32_t
2812choose_next_malicious (struct GNUNET_TESTING_PeerGroup *pg, struct GNUNET_CONTAINER_BloomFilter *bloom) 2776choose_next_malicious (struct GNUNET_TESTING_PeerGroup *pg,
2813 { 2777 struct GNUNET_CONTAINER_BloomFilter *bloom)
2814 int i; 2778{
2815 int nearest; 2779 int i;
2816 int bits_match; 2780 int nearest;
2817 int curr_distance; 2781 int bits_match;
2818 int count; 2782 int curr_distance;
2819 struct GNUNET_TESTING_Daemon *temp_daemon; 2783 int count;
2820 GNUNET_HashCode uid_hash; 2784 struct GNUNET_TESTING_Daemon *temp_daemon;
2821 2785 GNUNET_HashCode uid_hash;
2822 curr_distance = 0;
2823 nearest = 0;
2824 GNUNET_assert (bloom != NULL);
2825 2786
2826 if (GNUNET_YES == malicious_sybil) 2787 curr_distance = 0;
2827 { 2788 nearest = 0;
2828 for (i = 0; i < num_peers; i++) 2789 GNUNET_assert (bloom != NULL);
2829 { 2790
2830 temp_daemon = GNUNET_TESTING_daemon_get(pg, i); 2791 if (GNUNET_YES == malicious_sybil)
2831 hash_from_uid(i, &uid_hash); 2792 {
2832 /* Check if this peer matches the bloomfilter */ 2793 for (i = 0; i < num_peers; i++)
2833 if ((GNUNET_NO == GNUNET_TESTING_daemon_running(temp_daemon)) || (GNUNET_YES == GNUNET_CONTAINER_bloomfilter_test (bloom, &uid_hash))) 2794 {
2834 continue; 2795 temp_daemon = GNUNET_TESTING_daemon_get (pg, i);
2835 2796 hash_from_uid (i, &uid_hash);
2836 bits_match = GNUNET_CRYPTO_hash_matching_bits (&temp_daemon->id.hashPubKey, &sybil_target); 2797 /* Check if this peer matches the bloomfilter */
2837 if (bits_match >= curr_distance) 2798 if ((GNUNET_NO == GNUNET_TESTING_daemon_running (temp_daemon)) ||
2838 { 2799 (GNUNET_YES == GNUNET_CONTAINER_bloomfilter_test (bloom, &uid_hash)))
2839 GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Found nearer peer %s to %s, old matching bits %d, new %d\n", GNUNET_i2s(&temp_daemon->id), GNUNET_h2s(&sybil_target), curr_distance, bits_match); 2800 continue;
2840 nearest = i; 2801
2841 curr_distance = bits_match; 2802 bits_match =
2842 } 2803 GNUNET_CRYPTO_hash_matching_bits (&temp_daemon->id.hashPubKey,
2843 } 2804 &sybil_target);
2844 } 2805 if (bits_match >= curr_distance)
2845 else
2846 { 2806 {
2847 nearest = GNUNET_CRYPTO_random_u32(GNUNET_CRYPTO_QUALITY_WEAK, num_peers); 2807 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
2848 hash_from_uid(nearest, &uid_hash); 2808 "Found nearer peer %s to %s, old matching bits %d, new %d\n",
2849 count = 0; 2809 GNUNET_i2s (&temp_daemon->id), GNUNET_h2s (&sybil_target),
2850 while ((GNUNET_YES == GNUNET_CONTAINER_bloomfilter_test (bloom, &uid_hash)) && (count < num_peers)) 2810 curr_distance, bits_match);
2851 { 2811 nearest = i;
2852 GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Peer %d already in bloom (tried %d times)\n", nearest, count); 2812 curr_distance = bits_match;
2853 nearest = GNUNET_CRYPTO_random_u32(GNUNET_CRYPTO_QUALITY_WEAK, num_peers);
2854 hash_from_uid(nearest, &uid_hash);
2855 count++;
2856 }
2857 if (count == num_peers)
2858 GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Tried %d times to find a peer, selecting %d at random!!\n", count, nearest);
2859 } 2813 }
2860 2814 }
2861 return nearest;
2862 } 2815 }
2816 else
2817 {
2818 nearest = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, num_peers);
2819 hash_from_uid (nearest, &uid_hash);
2820 count = 0;
2821 while ((GNUNET_YES == GNUNET_CONTAINER_bloomfilter_test (bloom, &uid_hash))
2822 && (count < num_peers))
2823 {
2824 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
2825 "Peer %d already in bloom (tried %d times)\n", nearest,
2826 count);
2827 nearest =
2828 GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, num_peers);
2829 hash_from_uid (nearest, &uid_hash);
2830 count++;
2831 }
2832 if (count == num_peers)
2833 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
2834 "Tried %d times to find a peer, selecting %d at random!!\n",
2835 count, nearest);
2836 }
2837
2838 return nearest;
2839}
2863 2840
2864/** 2841/**
2865 * Select randomly from set of known peers, 2842 * Select randomly from set of known peers,
@@ -2867,62 +2844,62 @@ choose_next_malicious (struct GNUNET_TESTING_PeerGroup *pg, struct GNUNET_CONTAI
2867 * proper malicious types. 2844 * proper malicious types.
2868 */ 2845 */
2869static void 2846static void
2870setup_malicious_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 2847setup_malicious_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
2871 { 2848{
2872 struct MaliciousContext *ctx; 2849 struct MaliciousContext *ctx;
2873 int i; 2850 int i;
2874 uint32_t temp_daemon; 2851 uint32_t temp_daemon;
2875 GNUNET_HashCode uid_hash; 2852 GNUNET_HashCode uid_hash;
2876 2853
2877 for (i = 0; i < malicious_getters; i++) 2854 for (i = 0; i < malicious_getters; i++)
2878 { 2855 {
2879 ctx = GNUNET_malloc(sizeof(struct MaliciousContext)); 2856 ctx = GNUNET_malloc (sizeof (struct MaliciousContext));
2880 temp_daemon = choose_next_malicious(pg, malicious_bloom); 2857 temp_daemon = choose_next_malicious (pg, malicious_bloom);
2881 ctx->daemon = GNUNET_TESTING_daemon_get(pg, temp_daemon); 2858 ctx->daemon = GNUNET_TESTING_daemon_get (pg, temp_daemon);
2882 hash_from_uid(temp_daemon, &uid_hash); 2859 hash_from_uid (temp_daemon, &uid_hash);
2883 GNUNET_CONTAINER_bloomfilter_add(malicious_bloom, &uid_hash); 2860 GNUNET_CONTAINER_bloomfilter_add (malicious_bloom, &uid_hash);
2884 ctx->malicious_type = GNUNET_MESSAGE_TYPE_DHT_MALICIOUS_GET; 2861 ctx->malicious_type = GNUNET_MESSAGE_TYPE_DHT_MALICIOUS_GET;
2885 GNUNET_SCHEDULER_add_now (&set_malicious, ctx); 2862 GNUNET_SCHEDULER_add_now (&set_malicious, ctx);
2886 2863
2887 } 2864 }
2888 2865
2889 for (i = 0; i < malicious_putters; i++) 2866 for (i = 0; i < malicious_putters; i++)
2890 { 2867 {
2891 ctx = GNUNET_malloc(sizeof(struct MaliciousContext)); 2868 ctx = GNUNET_malloc (sizeof (struct MaliciousContext));
2892 temp_daemon = choose_next_malicious(pg, malicious_bloom); 2869 temp_daemon = choose_next_malicious (pg, malicious_bloom);
2893 ctx->daemon = GNUNET_TESTING_daemon_get(pg, temp_daemon); 2870 ctx->daemon = GNUNET_TESTING_daemon_get (pg, temp_daemon);
2894 hash_from_uid(temp_daemon, &uid_hash); 2871 hash_from_uid (temp_daemon, &uid_hash);
2895 GNUNET_CONTAINER_bloomfilter_add(malicious_bloom, &uid_hash); 2872 GNUNET_CONTAINER_bloomfilter_add (malicious_bloom, &uid_hash);
2896 ctx->malicious_type = GNUNET_MESSAGE_TYPE_DHT_MALICIOUS_PUT; 2873 ctx->malicious_type = GNUNET_MESSAGE_TYPE_DHT_MALICIOUS_PUT;
2897 GNUNET_SCHEDULER_add_now (&set_malicious, ctx); 2874 GNUNET_SCHEDULER_add_now (&set_malicious, ctx);
2898 2875
2899 } 2876 }
2900 2877
2901 for (i = 0; i < malicious_droppers; i++) 2878 for (i = 0; i < malicious_droppers; i++)
2902 { 2879 {
2903 ctx = GNUNET_malloc(sizeof(struct MaliciousContext)); 2880 ctx = GNUNET_malloc (sizeof (struct MaliciousContext));
2904 temp_daemon = choose_next_malicious(pg, malicious_bloom); 2881 temp_daemon = choose_next_malicious (pg, malicious_bloom);
2905 ctx->daemon = GNUNET_TESTING_daemon_get(pg, temp_daemon); 2882 ctx->daemon = GNUNET_TESTING_daemon_get (pg, temp_daemon);
2906 hash_from_uid(temp_daemon, &uid_hash); 2883 hash_from_uid (temp_daemon, &uid_hash);
2907 GNUNET_CONTAINER_bloomfilter_add(malicious_bloom, &uid_hash); 2884 GNUNET_CONTAINER_bloomfilter_add (malicious_bloom, &uid_hash);
2908 ctx->malicious_type = GNUNET_MESSAGE_TYPE_DHT_MALICIOUS_DROP; 2885 ctx->malicious_type = GNUNET_MESSAGE_TYPE_DHT_MALICIOUS_DROP;
2909 GNUNET_SCHEDULER_add_now (&set_malicious, ctx); 2886 GNUNET_SCHEDULER_add_now (&set_malicious, ctx);
2910 }
2911 } 2887 }
2888}
2912#endif 2889#endif
2913 2890
2914#if ONLY_TESTING 2891#if ONLY_TESTING
2915/* Forward declaration */ 2892/* Forward declaration */
2916static void 2893static void
2917topology_callback (void *cls, 2894topology_callback (void *cls,
2918 const struct GNUNET_PeerIdentity *first, 2895 const struct GNUNET_PeerIdentity *first,
2919 const struct GNUNET_PeerIdentity *second, 2896 const struct GNUNET_PeerIdentity *second,
2920 uint32_t distance, 2897 uint32_t distance,
2921 const struct GNUNET_CONFIGURATION_Handle *first_cfg, 2898 const struct GNUNET_CONFIGURATION_Handle *first_cfg,
2922 const struct GNUNET_CONFIGURATION_Handle *second_cfg, 2899 const struct GNUNET_CONFIGURATION_Handle *second_cfg,
2923 struct GNUNET_TESTING_Daemon *first_daemon, 2900 struct GNUNET_TESTING_Daemon *first_daemon,
2924 struct GNUNET_TESTING_Daemon *second_daemon, 2901 struct GNUNET_TESTING_Daemon *second_daemon,
2925 const char *emsg); 2902 const char *emsg);
2926 2903
2927/** 2904/**
2928 * Retry connecting two specific peers until they connect, 2905 * Retry connecting two specific peers until they connect,
@@ -2931,19 +2908,24 @@ topology_callback (void *cls,
2931 * debug the reason they are having issues. 2908 * debug the reason they are having issues.
2932 */ 2909 */
2933static void 2910static void
2934repeat_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc) 2911repeat_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
2935 { 2912{
2936
2937 GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "Repeating connect attempt between %s and %s.\n", repeat_connect_peer1->shortname, repeat_connect_peer2->shortname);
2938 GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "Peer 1 configuration `%s'\n", repeat_connect_peer1->cfgfile);
2939 GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "Peer 2 configuration `%s'\n", repeat_connect_peer2->cfgfile);
2940 2913
2941 repeat_connect_task = GNUNET_SCHEDULER_NO_TASK; 2914 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
2942 GNUNET_TESTING_daemons_connect(repeat_connect_peer1, 2915 "Repeating connect attempt between %s and %s.\n",
2943 repeat_connect_peer2, 2916 repeat_connect_peer1->shortname, repeat_connect_peer2->shortname);
2944 GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 60), 2917 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Peer 1 configuration `%s'\n",
2945 2, &topology_callback, NULL); 2918 repeat_connect_peer1->cfgfile);
2946 } 2919 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Peer 2 configuration `%s'\n",
2920 repeat_connect_peer2->cfgfile);
2921
2922 repeat_connect_task = GNUNET_SCHEDULER_NO_TASK;
2923 GNUNET_TESTING_daemons_connect (repeat_connect_peer1,
2924 repeat_connect_peer2,
2925 GNUNET_TIME_relative_multiply
2926 (GNUNET_TIME_UNIT_SECONDS, 60), 2,
2927 &topology_callback, NULL);
2928}
2947#endif 2929#endif
2948 2930
2949/** 2931/**
@@ -2956,12 +2938,13 @@ repeat_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext * tc)
2956 * failure (peers failed to connect). 2938 * failure (peers failed to connect).
2957 */ 2939 */
2958static void 2940static void
2959topology_callback(void *cls, const struct GNUNET_PeerIdentity *first, 2941topology_callback (void *cls, const struct GNUNET_PeerIdentity *first,
2960 const struct GNUNET_PeerIdentity *second, uint32_t distance, 2942 const struct GNUNET_PeerIdentity *second, uint32_t distance,
2961 const struct GNUNET_CONFIGURATION_Handle *first_cfg, 2943 const struct GNUNET_CONFIGURATION_Handle *first_cfg,
2962 const struct GNUNET_CONFIGURATION_Handle *second_cfg, 2944 const struct GNUNET_CONFIGURATION_Handle *second_cfg,
2963 struct GNUNET_TESTING_Daemon *first_daemon, 2945 struct GNUNET_TESTING_Daemon *first_daemon,
2964 struct GNUNET_TESTING_Daemon *second_daemon, const char *emsg) 2946 struct GNUNET_TESTING_Daemon *second_daemon,
2947 const char *emsg)
2965{ 2948{
2966 struct TopologyIteratorContext *topo_ctx; 2949 struct TopologyIteratorContext *topo_ctx;
2967 uint64_t duration; 2950 uint64_t duration;
@@ -2978,314 +2961,318 @@ topology_callback(void *cls, const struct GNUNET_PeerIdentity *first,
2978 2961
2979#if ONLY_TESTING 2962#if ONLY_TESTING
2980 if (repeat_connect_mode == GNUNET_YES) 2963 if (repeat_connect_mode == GNUNET_YES)
2964 {
2965 if ((first_daemon == repeat_connect_peer1) &&
2966 (second_daemon == repeat_connect_peer2))
2981 { 2967 {
2982 if ((first_daemon == repeat_connect_peer1) && 2968 if (emsg != NULL) /* Peers failed to connect again! */
2983 (second_daemon == repeat_connect_peer2)) 2969 {
2984 { 2970 GNUNET_assert (repeat_connect_task == GNUNET_SCHEDULER_NO_TASK);
2985 if (emsg != NULL) /* Peers failed to connect again! */ 2971 repeat_connect_task =
2986 { 2972 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
2987 GNUNET_assert(repeat_connect_task == GNUNET_SCHEDULER_NO_TASK); 2973 (GNUNET_TIME_UNIT_SECONDS, 60),
2988 repeat_connect_task = GNUNET_SCHEDULER_add_delayed(GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 60), &repeat_connect, NULL); 2974 &repeat_connect, NULL);
2989 return; 2975 return;
2990 } 2976 }
2991 else /* Repeat peers actually connected! */ 2977 else /* Repeat peers actually connected! */
2992 { 2978 {
2993 if (repeat_connect_task != GNUNET_SCHEDULER_NO_TASK) 2979 if (repeat_connect_task != GNUNET_SCHEDULER_NO_TASK)
2994 GNUNET_SCHEDULER_cancel(repeat_connect_task); 2980 GNUNET_SCHEDULER_cancel (repeat_connect_task);
2995 repeat_connect_peer1 = NULL; 2981 repeat_connect_peer1 = NULL;
2996 repeat_connect_peer2 = NULL; 2982 repeat_connect_peer2 = NULL;
2997 repeat_connect_mode = GNUNET_NO; 2983 repeat_connect_mode = GNUNET_NO;
2998 GNUNET_TESTING_resume_connections(pg); 2984 GNUNET_TESTING_resume_connections (pg);
2999 GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "Resuming normal connection mode, debug connection was successful!\n"); 2985 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3000 } 2986 "Resuming normal connection mode, debug connection was successful!\n");
3001 } 2987 }
3002 } 2988 }
2989 }
3003#endif 2990#endif
3004 2991
3005 if (GNUNET_TIME_absolute_get_difference (connect_last_time, 2992 if (GNUNET_TIME_absolute_get_difference (connect_last_time,
3006 GNUNET_TIME_absolute_get ()).rel_value 2993 GNUNET_TIME_absolute_get
3007 > GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 2994 ()).rel_value >
3008 CONN_UPDATE_DURATION).rel_value) 2995 GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS,
2996 CONN_UPDATE_DURATION).rel_value)
2997 {
2998 /* Get number of new connections */
2999 new_connections = total_connections - previous_connections;
3000
3001 /* Get number of new FAILED connections */
3002 new_failed_connections = failed_connections - previous_failed_connections;
3003
3004 /* Get duration in seconds */
3005 duration
3006 = GNUNET_TIME_absolute_get_difference (connect_last_time,
3007 GNUNET_TIME_absolute_get
3008 ()).rel_value / 1000;
3009 total_duration =
3010 GNUNET_TIME_absolute_get_difference (connect_start_time,
3011 GNUNET_TIME_absolute_get
3012 ()).rel_value / 1000;
3013
3014 failed_conns_per_sec_recent = (double) new_failed_connections
3015 / (double) duration;
3016 failed_conns_per_sec_total = (double) failed_connections
3017 / (double) total_duration;
3018 conns_per_sec_recent = (double) new_connections / (double) duration;
3019 conns_per_sec_total = (double) total_connections / (double) total_duration;
3020 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3021 "Recent: %.2f/s, Total: %.2f/s, Recent failed: %.2f/s, total failed %.2f/s\n",
3022 conns_per_sec_recent, conns_per_sec_total,
3023 failed_conns_per_sec_recent, failed_conns_per_sec_total);
3024 connect_last_time = GNUNET_TIME_absolute_get ();
3025 previous_connections = total_connections;
3026 previous_failed_connections = failed_connections;
3027 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3028 "have %llu total_connections, %llu failed\n",
3029 total_connections, failed_connections);
3030#if ONLY_TESTING
3031 /* These conditions likely mean we've entered the death spiral of doom */
3032 if ((total_connections > 20000) &&
3033 (conns_per_sec_recent < 5.0) &&
3034 (conns_per_sec_total > 10.0) &&
3035 (emsg != NULL) && (repeat_connect_mode == GNUNET_NO))
3009 { 3036 {
3010 /* Get number of new connections */
3011 new_connections = total_connections - previous_connections;
3012
3013 /* Get number of new FAILED connections */
3014 new_failed_connections = failed_connections - previous_failed_connections;
3015
3016 /* Get duration in seconds */
3017 duration
3018 = GNUNET_TIME_absolute_get_difference (connect_last_time,
3019 GNUNET_TIME_absolute_get ()).rel_value
3020 / 1000;
3021 total_duration
3022 = GNUNET_TIME_absolute_get_difference (connect_start_time,
3023 GNUNET_TIME_absolute_get ()).rel_value
3024 / 1000;
3025
3026 failed_conns_per_sec_recent = (double) new_failed_connections
3027 / (double) duration;
3028 failed_conns_per_sec_total = (double) failed_connections
3029 / (double) total_duration;
3030 conns_per_sec_recent = (double) new_connections / (double) duration;
3031 conns_per_sec_total = (double) total_connections
3032 / (double) total_duration;
3033 GNUNET_log (
3034 GNUNET_ERROR_TYPE_WARNING,
3035 "Recent: %.2f/s, Total: %.2f/s, Recent failed: %.2f/s, total failed %.2f/s\n",
3036 conns_per_sec_recent, conns_per_sec_total,
3037 failed_conns_per_sec_recent, failed_conns_per_sec_total);
3038 connect_last_time = GNUNET_TIME_absolute_get ();
3039 previous_connections = total_connections;
3040 previous_failed_connections = failed_connections;
3041 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 3037 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3042 "have %llu total_connections, %llu failed\n", 3038 "Entering repeat connection attempt mode!\n");
3043 total_connections, failed_connections); 3039 repeat_connect_peer1 = first_daemon;
3044#if ONLY_TESTING 3040 repeat_connect_peer2 = second_daemon;
3045 /* These conditions likely mean we've entered the death spiral of doom */ 3041 repeat_connect_mode = GNUNET_YES;
3046 if ((total_connections > 20000) && 3042 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3047 (conns_per_sec_recent < 5.0) && 3043 "Stopping NEW connections from being scheduled!\n");
3048 (conns_per_sec_total > 10.0) && 3044 GNUNET_TESTING_stop_connections (pg);
3049 (emsg != NULL) && 3045 repeat_connect_task =
3050 (repeat_connect_mode == GNUNET_NO)) 3046 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
3051 { 3047 (GNUNET_TIME_UNIT_SECONDS, 60),
3052 GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "Entering repeat connection attempt mode!\n"); 3048 &repeat_connect, NULL);
3053 repeat_connect_peer1 = first_daemon;
3054 repeat_connect_peer2 = second_daemon;
3055 repeat_connect_mode = GNUNET_YES;
3056 GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "Stopping NEW connections from being scheduled!\n");
3057 GNUNET_TESTING_stop_connections(pg);
3058 repeat_connect_task = GNUNET_SCHEDULER_add_delayed(GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 60), &repeat_connect, NULL);
3059 }
3060#endif
3061 } 3049 }
3050#endif
3051 }
3062 3052
3063 if (emsg == NULL) 3053 if (emsg == NULL)
3064 { 3054 {
3065 total_connections++; 3055 total_connections++;
3066#if VERBOSE > 1 3056#if VERBOSE > 1
3067 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "connected peer %s to peer %s, distance %u\n", 3057 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
3068 first_daemon->shortname, 3058 "connected peer %s to peer %s, distance %u\n",
3069 second_daemon->shortname, 3059 first_daemon->shortname, second_daemon->shortname, distance);
3070 distance);
3071#endif 3060#endif
3072 } 3061 }
3073 else 3062 else
3074 { 3063 {
3075 failed_connections++; 3064 failed_connections++;
3076#if VERBOSE 3065#if VERBOSE
3077 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Failed to connect peer %s to peer %s with error :\n%s\n", 3066 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3078 first_daemon->shortname, 3067 "Failed to connect peer %s to peer %s with error :\n%s\n",
3079 second_daemon->shortname, emsg); 3068 first_daemon->shortname, second_daemon->shortname, emsg);
3080 3069
3081 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failed to connect peer %s to peer %s with error :\n%s\n", 3070 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
3082 first_daemon->shortname, 3071 "Failed to connect peer %s to peer %s with error :\n%s\n",
3083 second_daemon->shortname, emsg); 3072 first_daemon->shortname, second_daemon->shortname, emsg);
3084#endif 3073#endif
3085 } 3074 }
3086 3075
3087#if ONLY_TESTING 3076#if ONLY_TESTING
3088 if ((repeat_connect_mode == GNUNET_YES) ) 3077 if ((repeat_connect_mode == GNUNET_YES))
3089 return; 3078 return;
3090#endif 3079#endif
3091 3080
3092 GNUNET_assert(peer_connect_meter != NULL); 3081 GNUNET_assert (peer_connect_meter != NULL);
3093 if (GNUNET_YES == update_meter (peer_connect_meter)) 3082 if (GNUNET_YES == update_meter (peer_connect_meter))
3094 { 3083 {
3095#if VERBOSE 3084#if VERBOSE
3096 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 3085 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
3097 "Created %d total connections, which is our target number! Starting next phase of testing.\n", 3086 "Created %d total connections, which is our target number! Starting next phase of testing.\n",
3098 total_connections); 3087 total_connections);
3099#endif 3088#endif
3100 if (failed_connections > 0) 3089 if (failed_connections > 0)
3101 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 3090 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3102 "While connecting, had %u failed connections.\n", 3091 "While connecting, had %u failed connections.\n",
3103 failed_connections); 3092 failed_connections);
3104 if (dhtlog_handle != NULL) 3093 if (dhtlog_handle != NULL)
3105 { 3094 {
3106 dhtlog_handle->update_connections (total_connections); 3095 dhtlog_handle->update_connections (total_connections);
3107 dhtlog_handle->insert_topology (expected_connections); 3096 dhtlog_handle->insert_topology (expected_connections);
3108 } 3097 }
3109 3098
3110 total_duration 3099 total_duration
3111 = GNUNET_TIME_absolute_get_difference (connect_start_time, 3100 = GNUNET_TIME_absolute_get_difference (connect_start_time,
3112 GNUNET_TIME_absolute_get ()).rel_value 3101 GNUNET_TIME_absolute_get
3113 / 1000; 3102 ()).rel_value / 1000;
3114 failed_conns_per_sec_total = (long double) failed_connections 3103 failed_conns_per_sec_total =
3115 / total_duration; 3104 (long double) failed_connections / total_duration;
3116 conns_per_sec_total = (long double) total_connections / total_duration; 3105 conns_per_sec_total = (long double) total_connections / total_duration;
3106 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3107 "Overall connection info --- Total: %u, Total Failed %u/s\n",
3108 total_connections, failed_connections);
3109 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3110 "Overall connection info --- Total: %.2f/s, Total Failed %.2f/s\n",
3111 conns_per_sec_total, failed_conns_per_sec_total);
3112
3113 GNUNET_asprintf (&temp_conn_string, "DHT Profiler Connection/s",
3114 trial_to_run);
3115 GNUNET_asprintf (&temp_conn_failed_string,
3116 "DHT Profiler Connection/s failed", trial_to_run);
3117 GNUNET_asprintf (&revision_str, "%llu", revision);
3118
3119 if (GNUNET_YES == insert_gauger_data)
3120 GAUGER_ID ("DHT_TESTING", temp_conn_string,
3121 (long double) conns_per_sec_total, "conns/s", revision_str);
3122 if (GNUNET_YES == insert_gauger_data)
3123 GAUGER_ID ("DHT_TESTING", temp_conn_failed_string,
3124 (long double) failed_conns_per_sec_total, "failed_conns",
3125 revision_str);
3126
3127 GNUNET_free (temp_conn_string);
3128 GNUNET_free (temp_conn_failed_string);
3129 GNUNET_asprintf (&temp_conn_string, "DHT Profiler Total Connections",
3130 trial_to_run);
3131 GNUNET_asprintf (&temp_conn_failed_string,
3132 "DHT Profiler Total Connections failed", trial_to_run);
3133 if (GNUNET_YES == insert_gauger_data)
3134 GAUGER_ID ("DHT_TESTING", temp_conn_string, (double) total_connections,
3135 "conns", revision_str);
3136 if (GNUNET_YES == insert_gauger_data)
3137 GAUGER_ID ("DHT_TESTING", temp_conn_failed_string,
3138 (double) failed_connections, "failed conns", revision_str);
3139 GNUNET_free (temp_conn_string);
3140 GNUNET_free (temp_conn_failed_string);
3141 GNUNET_free (revision_str);
3142
3143 GNUNET_SCHEDULER_cancel (die_task);
3144
3145 if ((GNUNET_YES == dhtlog_minimal) && (NULL != dhtlog_handle))
3146 {
3147 topo_ctx = GNUNET_malloc (sizeof (struct TopologyIteratorContext));
3117 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 3148 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3118 "Overall connection info --- Total: %u, Total Failed %u/s\n", 3149 "Setting continue gets and puts as topo_cont\n");
3119 total_connections, failed_connections); 3150 topo_ctx->cont = &continue_puts_and_gets;
3120 GNUNET_log ( 3151 topo_ctx->peers_seen = GNUNET_CONTAINER_multihashmap_create (num_peers);
3121 GNUNET_ERROR_TYPE_WARNING, 3152 GNUNET_SCHEDULER_add_now (&capture_current_topology, topo_ctx);
3122 "Overall connection info --- Total: %.2f/s, Total Failed %.2f/s\n",
3123 conns_per_sec_total, failed_conns_per_sec_total);
3124
3125 GNUNET_asprintf (&temp_conn_string, "DHT Profiler Connection/s",
3126 trial_to_run);
3127 GNUNET_asprintf (&temp_conn_failed_string,
3128 "DHT Profiler Connection/s failed", trial_to_run);
3129 GNUNET_asprintf (&revision_str, "%llu", revision);
3130
3131 if (GNUNET_YES == insert_gauger_data)
3132 GAUGER_ID("DHT_TESTING", temp_conn_string, (long double)conns_per_sec_total, "conns/s", revision_str);
3133 if (GNUNET_YES == insert_gauger_data)
3134 GAUGER_ID("DHT_TESTING", temp_conn_failed_string, (long double)failed_conns_per_sec_total, "failed_conns", revision_str);
3135
3136 GNUNET_free(temp_conn_string);
3137 GNUNET_free(temp_conn_failed_string);
3138 GNUNET_asprintf (&temp_conn_string, "DHT Profiler Total Connections",
3139 trial_to_run);
3140 GNUNET_asprintf (&temp_conn_failed_string,
3141 "DHT Profiler Total Connections failed", trial_to_run);
3142 if (GNUNET_YES == insert_gauger_data)
3143 GAUGER_ID("DHT_TESTING", temp_conn_string, (double)total_connections, "conns", revision_str);
3144 if (GNUNET_YES == insert_gauger_data)
3145 GAUGER_ID("DHT_TESTING", temp_conn_failed_string, (double)failed_connections, "failed conns", revision_str);
3146 GNUNET_free(temp_conn_string);
3147 GNUNET_free(temp_conn_failed_string);
3148 GNUNET_free(revision_str);
3149
3150 GNUNET_SCHEDULER_cancel (die_task);
3151
3152 if ((GNUNET_YES == dhtlog_minimal) && (NULL != dhtlog_handle))
3153 {
3154 topo_ctx = GNUNET_malloc(sizeof(struct TopologyIteratorContext));
3155 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3156 "Setting continue gets and puts as topo_cont\n");
3157 topo_ctx->cont = &continue_puts_and_gets;
3158 topo_ctx->peers_seen
3159 = GNUNET_CONTAINER_multihashmap_create (num_peers);
3160 GNUNET_SCHEDULER_add_now (&capture_current_topology, topo_ctx);
3161 }
3162 else
3163 {
3164 GNUNET_log (
3165 GNUNET_ERROR_TYPE_WARNING,
3166 "For some reason, NOT scheduling final topology capture (settle_time %d, dhtlog_handle %s)!\n",
3167 settle_time, dhtlog_handle);
3168 GNUNET_SCHEDULER_add_now (&continue_puts_and_gets, NULL);
3169 }
3170 } 3153 }
3171 else if (total_connections + failed_connections == expected_connections) 3154 else
3172 { 3155 {
3173 GNUNET_SCHEDULER_cancel (die_task); 3156 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3174 die_task 3157 "For some reason, NOT scheduling final topology capture (settle_time %d, dhtlog_handle %s)!\n",
3175 = GNUNET_SCHEDULER_add_now (&end_badly, 3158 settle_time, dhtlog_handle);
3176 "from topology_callback (too many failed connections)"); 3159 GNUNET_SCHEDULER_add_now (&continue_puts_and_gets, NULL);
3177 } 3160 }
3161 }
3162 else if (total_connections + failed_connections == expected_connections)
3163 {
3164 GNUNET_SCHEDULER_cancel (die_task);
3165 die_task
3166 = GNUNET_SCHEDULER_add_now (&end_badly,
3167 "from topology_callback (too many failed connections)");
3168 }
3178} 3169}
3179 3170
3180static void 3171static void
3181peers_started_callback(void *cls, const struct GNUNET_PeerIdentity *id, 3172peers_started_callback (void *cls, const struct GNUNET_PeerIdentity *id,
3182 const struct GNUNET_CONFIGURATION_Handle *cfg, 3173 const struct GNUNET_CONFIGURATION_Handle *cfg,
3183 struct GNUNET_TESTING_Daemon *d, const char *emsg) 3174 struct GNUNET_TESTING_Daemon *d, const char *emsg)
3184{ 3175{
3185 char *revision_str; 3176 char *revision_str;
3177
3186 if (emsg != NULL) 3178 if (emsg != NULL)
3187 { 3179 {
3188 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 3180 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
3189 "Failed to start daemon with error: `%s'\n", emsg); 3181 "Failed to start daemon with error: `%s'\n", emsg);
3190 return; 3182 return;
3191 } 3183 }
3192 GNUNET_assert (id != NULL); 3184 GNUNET_assert (id != NULL);
3193 3185
3194#if VERBOSE > 1 3186#if VERBOSE > 1
3195 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Started daemon %llu out of %llu\n", 3187 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Started daemon %llu out of %llu\n",
3196 (num_peers - peers_left) + 1, num_peers); 3188 (num_peers - peers_left) + 1, num_peers);
3197#endif 3189#endif
3198 3190
3199 peers_left--; 3191 peers_left--;
3200 3192
3201 if (GNUNET_YES == update_meter (peer_start_meter)) 3193 if (GNUNET_YES == update_meter (peer_start_meter))
3202 { 3194 {
3203#if VERBOSE 3195#if VERBOSE
3204 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 3196 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
3205 "All %d daemons started, now connecting peers!\n", 3197 "All %d daemons started, now connecting peers!\n", num_peers);
3206 num_peers);
3207#endif 3198#endif
3208 GNUNET_SCHEDULER_cancel (die_task); 3199 GNUNET_SCHEDULER_cancel (die_task);
3209 3200
3210 GNUNET_asprintf (&revision_str, "%llu", revision); 3201 GNUNET_asprintf (&revision_str, "%llu", revision);
3211 if (GNUNET_YES == insert_gauger_data) 3202 if (GNUNET_YES == insert_gauger_data)
3212 GAUGER_ID("DHT_TESTING", 3203 GAUGER_ID ("DHT_TESTING",
3213 "peer_startup_time", 3204 "peer_startup_time",
3214 GNUNET_TIME_absolute_get_duration(peer_start_time).rel_value / (double)num_peers, 3205 GNUNET_TIME_absolute_get_duration (peer_start_time).rel_value /
3215 "ms/peer", revision_str); 3206 (double) num_peers, "ms/peer", revision_str);
3216 GNUNET_free(revision_str); 3207 GNUNET_free (revision_str);
3217 3208
3218 expected_connections = UINT_MAX; 3209 expected_connections = UINT_MAX;
3219 if ((pg != NULL) && (peers_left == 0)) 3210 if ((pg != NULL) && (peers_left == 0))
3220 { 3211 {
3221 connect_start_time = GNUNET_TIME_absolute_get (); 3212 connect_start_time = GNUNET_TIME_absolute_get ();
3222 expected_connections 3213 expected_connections
3223 = GNUNET_TESTING_connect_topology ( 3214 = GNUNET_TESTING_connect_topology (pg,
3224 pg, 3215 connect_topology,
3225 connect_topology, 3216 connect_topology_option,
3226 connect_topology_option, 3217 connect_topology_option_modifier,
3227 connect_topology_option_modifier, 3218 connect_timeout,
3228 connect_timeout, 3219 connect_attempts, NULL, NULL);
3229 connect_attempts, NULL, NULL); 3220
3230 3221 peer_connect_meter = create_meter (expected_connections,
3231 peer_connect_meter = create_meter (expected_connections, 3222 "Peer connection ", GNUNET_YES);
3232 "Peer connection ", GNUNET_YES); 3223 fprintf (stderr, "Have %d expected connections\n", expected_connections);
3233 fprintf (stderr, "Have %d expected connections\n", 3224 }
3234 expected_connections);
3235 }
3236
3237 if (expected_connections == 0)
3238 {
3239 die_task
3240 = GNUNET_SCHEDULER_add_now (&end_badly,
3241 "from connect topology (bad return)");
3242 }
3243 3225
3226 if (expected_connections == 0)
3227 {
3244 die_task 3228 die_task
3245 = GNUNET_SCHEDULER_add_delayed ( 3229 = GNUNET_SCHEDULER_add_now (&end_badly,
3246 GNUNET_TIME_relative_multiply ( 3230 "from connect topology (bad return)");
3247 GNUNET_TIME_UNIT_SECONDS,
3248 DEFAULT_CONNECT_TIMEOUT
3249 * expected_connections),
3250 &end_badly,
3251 "from connect topology (timeout)");
3252
3253 ok = 0;
3254 } 3231 }
3232
3233 die_task
3234 =
3235 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
3236 (GNUNET_TIME_UNIT_SECONDS,
3237 DEFAULT_CONNECT_TIMEOUT *
3238 expected_connections), &end_badly,
3239 "from connect topology (timeout)");
3240
3241 ok = 0;
3242 }
3255} 3243}
3256 3244
3257static void 3245static void
3258create_topology() 3246create_topology ()
3259{ 3247{
3260 unsigned int create_expected_connections; 3248 unsigned int create_expected_connections;
3261 peers_left = num_peers; /* Reset counter */ 3249
3250 peers_left = num_peers; /* Reset counter */
3262 create_expected_connections 3251 create_expected_connections
3263 = GNUNET_TESTING_create_topology (pg, topology, blacklist_topology, 3252 = GNUNET_TESTING_create_topology (pg, topology, blacklist_topology,
3264 blacklist_transports); 3253 blacklist_transports);
3265 if (create_expected_connections > 0) 3254 if (create_expected_connections > 0)
3266 { 3255 {
3267 GNUNET_log ( 3256 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3268 GNUNET_ERROR_TYPE_WARNING, 3257 "Topology set up, have %u expected connections, now starting peers!\n",
3269 "Topology set up, have %u expected connections, now starting peers!\n", 3258 create_expected_connections);
3270 create_expected_connections); 3259 GNUNET_TESTING_daemons_continue_startup (pg);
3271 GNUNET_TESTING_daemons_continue_startup (pg); 3260 peer_start_time = GNUNET_TIME_absolute_get ();
3272 peer_start_time = GNUNET_TIME_absolute_get (); 3261 }
3273 }
3274 else 3262 else
3275 { 3263 {
3276 GNUNET_SCHEDULER_cancel (die_task); 3264 GNUNET_SCHEDULER_cancel (die_task);
3277 die_task = GNUNET_SCHEDULER_add_now (&end_badly, 3265 die_task = GNUNET_SCHEDULER_add_now (&end_badly,
3278 "from create topology (bad return)"); 3266 "from create topology (bad return)");
3279 } 3267 }
3280 GNUNET_free_non_null(blacklist_transports); 3268 GNUNET_free_non_null (blacklist_transports);
3281 GNUNET_SCHEDULER_cancel (die_task); 3269 GNUNET_SCHEDULER_cancel (die_task);
3282 die_task 3270 die_task
3283 = GNUNET_SCHEDULER_add_delayed ( 3271 =
3284 GNUNET_TIME_relative_multiply ( 3272 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
3285 seconds_per_peer_start, 3273 (seconds_per_peer_start, num_peers),
3286 num_peers), 3274 &end_badly,
3287 &end_badly, 3275 "from continue startup (timeout)");
3288 "from continue startup (timeout)");
3289} 3276}
3290 3277
3291/** 3278/**
@@ -3297,64 +3284,66 @@ create_topology()
3297 * @param emsg non-null on failure 3284 * @param emsg non-null on failure
3298 */ 3285 */
3299static void 3286static void
3300hostkey_callback(void *cls, const struct GNUNET_PeerIdentity *id, 3287hostkey_callback (void *cls, const struct GNUNET_PeerIdentity *id,
3301 struct GNUNET_TESTING_Daemon *d, const char *emsg) 3288 struct GNUNET_TESTING_Daemon *d, const char *emsg)
3302{ 3289{
3303 char * revision_str; 3290 char *revision_str;
3291
3304 if (emsg != NULL) 3292 if (emsg != NULL)
3305 { 3293 {
3306 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 3294 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3307 "Hostkey callback received error: %s\n", emsg); 3295 "Hostkey callback received error: %s\n", emsg);
3308 } 3296 }
3309 3297
3310#if VERBOSE > 1 3298#if VERBOSE > 1
3311 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 3299 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
3312 "Hostkey (%d/%d) created for peer `%s'\n", 3300 "Hostkey (%d/%d) created for peer `%s'\n",
3313 num_peers - peers_left, num_peers, GNUNET_i2s(id)); 3301 num_peers - peers_left, num_peers, GNUNET_i2s (id));
3314#endif 3302#endif
3315 3303
3316 peers_left--; 3304 peers_left--;
3317 if (GNUNET_YES == update_meter (hostkey_meter)) 3305 if (GNUNET_YES == update_meter (hostkey_meter))
3318 { 3306 {
3319 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 3307 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3320 "All %d hostkeys created, now creating topology!\n", 3308 "All %d hostkeys created, now creating topology!\n", num_peers);
3321 num_peers);
3322 3309
3323 GNUNET_asprintf (&revision_str, "%llu", revision); 3310 GNUNET_asprintf (&revision_str, "%llu", revision);
3324 if (GNUNET_YES == insert_gauger_data) 3311 if (GNUNET_YES == insert_gauger_data)
3325 { 3312 {
3326 if (GNUNET_YES == GNUNET_CONFIGURATION_have_value (config, "TESTING", 3313 if (GNUNET_YES == GNUNET_CONFIGURATION_have_value (config, "TESTING",
3327 "HOSTKEYSFILE")) 3314 "HOSTKEYSFILE"))
3328 { 3315 {
3329 GAUGER_ID("DHT_TESTING", 3316 GAUGER_ID ("DHT_TESTING",
3330 "HOSTKEY_GENERATION", 3317 "HOSTKEY_GENERATION",
3331 GNUNET_TIME_absolute_get_duration(hostkey_start_time).rel_value / (double)num_peers, 3318 GNUNET_TIME_absolute_get_duration
3332 "ms/hostkey", revision_str); 3319 (hostkey_start_time).rel_value / (double) num_peers,
3333 } 3320 "ms/hostkey", revision_str);
3334 else 3321 }
3335 { 3322 else
3336 GAUGER_ID("DHT_TESTING", 3323 {
3337 "HOSTKEY_GENERATION_REAL", 3324 GAUGER_ID ("DHT_TESTING",
3338 GNUNET_TIME_absolute_get_duration(hostkey_start_time).rel_value / (double)num_peers, 3325 "HOSTKEY_GENERATION_REAL",
3339 "ms/hostkey", revision_str); 3326 GNUNET_TIME_absolute_get_duration
3340 } 3327 (hostkey_start_time).rel_value / (double) num_peers,
3341 } 3328 "ms/hostkey", revision_str);
3329 }
3330 }
3342 3331
3343 GNUNET_free(revision_str); 3332 GNUNET_free (revision_str);
3344 3333
3345 GNUNET_SCHEDULER_cancel (die_task); 3334 GNUNET_SCHEDULER_cancel (die_task);
3346 /* Set up task in case topology creation doesn't finish 3335 /* Set up task in case topology creation doesn't finish
3347 * within a reasonable amount of time */ 3336 * within a reasonable amount of time */
3348 die_task = GNUNET_SCHEDULER_add_delayed (DEFAULT_TOPOLOGY_TIMEOUT, 3337 die_task = GNUNET_SCHEDULER_add_delayed (DEFAULT_TOPOLOGY_TIMEOUT,
3349 &end_badly, 3338 &end_badly,
3350 "from create_topology"); 3339 "from create_topology");
3351 GNUNET_SCHEDULER_add_now (&create_topology, NULL); 3340 GNUNET_SCHEDULER_add_now (&create_topology, NULL);
3352 ok = 0; 3341 ok = 0;
3353 } 3342 }
3354} 3343}
3355 3344
3356static void 3345static void
3357run (void *cls, char * const *args, const char *cfgfile, 3346run (void *cls, char *const *args, const char *cfgfile,
3358 const struct GNUNET_CONFIGURATION_Handle *cfg) 3347 const struct GNUNET_CONFIGURATION_Handle *cfg)
3359{ 3348{
3360 struct stat frstat; 3349 struct stat frstat;
@@ -3388,27 +3377,26 @@ run (void *cls, char * const *args, const char *cfgfile,
3388 3377
3389 config = cfg; 3378 config = cfg;
3390 rounds_finished = 0; 3379 rounds_finished = 0;
3391 memset (&trial_info, 0, sizeof(struct GNUNET_DHTLOG_TrialInfo)); 3380 memset (&trial_info, 0, sizeof (struct GNUNET_DHTLOG_TrialInfo));
3392 /* Get path from configuration file */ 3381 /* Get path from configuration file */
3393 if (GNUNET_YES != GNUNET_CONFIGURATION_get_value_string (cfg, "paths", 3382 if (GNUNET_YES != GNUNET_CONFIGURATION_get_value_string (cfg, "paths",
3394 "servicehome", 3383 "servicehome",
3395 &test_directory)) 3384 &test_directory))
3396 { 3385 {
3397 ok = 404; 3386 ok = 404;
3398 return; 3387 return;
3399 } 3388 }
3400 3389
3401 /* Get number of peers to start from configuration */ 3390 /* Get number of peers to start from configuration */
3402 if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_number (cfg, "testing", 3391 if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_number (cfg, "testing",
3403 "num_peers", 3392 "num_peers",
3404 &num_peers)) 3393 &num_peers))
3405 { 3394 {
3406 GNUNET_log ( 3395 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3407 GNUNET_ERROR_TYPE_WARNING, 3396 "Number of peers must be specified in section %s option %s\n",
3408 "Number of peers must be specified in section %s option %s\n", 3397 "TESTING", "NUM_PEERS");
3409 "TESTING", "NUM_PEERS"); 3398 }
3410 } 3399 GNUNET_assert (num_peers > 0 && num_peers < ULONG_MAX);
3411 GNUNET_assert(num_peers > 0 && num_peers < ULONG_MAX);
3412 3400
3413 if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_number (cfg, "testing", 3401 if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_number (cfg, "testing",
3414 "connect_timeout", 3402 "connect_timeout",
@@ -3416,39 +3404,39 @@ run (void *cls, char * const *args, const char *cfgfile,
3416 connect_timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 3404 connect_timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS,
3417 temp_config_number); 3405 temp_config_number);
3418 else 3406 else
3419 { 3407 {
3420 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", 3408 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n",
3421 "testing", "connect_timeout"); 3409 "testing", "connect_timeout");
3422 return; 3410 return;
3423 } 3411 }
3424 3412
3425 if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (cfg, "testing", 3413 if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (cfg, "testing",
3426 "connect_attempts", 3414 "connect_attempts",
3427 &connect_attempts)) 3415 &connect_attempts))
3428 { 3416 {
3429 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", 3417 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n",
3430 "testing", "connect_attempts"); 3418 "testing", "connect_attempts");
3431 return; 3419 return;
3432 } 3420 }
3433 3421
3434 if (GNUNET_OK 3422 if (GNUNET_OK
3435 != GNUNET_CONFIGURATION_get_value_number (cfg, "testing", 3423 != GNUNET_CONFIGURATION_get_value_number (cfg, "testing",
3436 "max_outstanding_connections", 3424 "max_outstanding_connections",
3437 &max_outstanding_connections)) 3425 &max_outstanding_connections))
3438 { 3426 {
3439 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", 3427 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n",
3440 "testing", "max_outstanding_connections"); 3428 "testing", "max_outstanding_connections");
3441 return; 3429 return;
3442 } 3430 }
3443 3431
3444 if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (cfg, "testing", 3432 if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (cfg, "testing",
3445 "max_concurrent_ssh", 3433 "max_concurrent_ssh",
3446 &max_concurrent_ssh)) 3434 &max_concurrent_ssh))
3447 { 3435 {
3448 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", 3436 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n",
3449 "testing", "max_concurrent_ssh"); 3437 "testing", "max_concurrent_ssh");
3450 return; 3438 return;
3451 } 3439 }
3452 3440
3453 /** 3441 /**
3454 * Get DHT specific testing options. 3442 * Get DHT specific testing options.
@@ -3461,21 +3449,21 @@ run (void *cls, char * const *args, const char *cfgfile,
3461 || (GNUNET_YES 3449 || (GNUNET_YES
3462 == GNUNET_CONFIGURATION_get_value_yesno (cfg, "dht_testing", 3450 == GNUNET_CONFIGURATION_get_value_yesno (cfg, "dht_testing",
3463 "mysql_logging_minimal"))) 3451 "mysql_logging_minimal")))
3464 { 3452 {
3465 if (GNUNET_YES 3453 if (GNUNET_YES
3466 == GNUNET_CONFIGURATION_get_value_yesno (cfg, "dht_testing", 3454 == GNUNET_CONFIGURATION_get_value_yesno (cfg, "dht_testing",
3467 "mysql_logging_minimal")) 3455 "mysql_logging_minimal"))
3468 dhtlog_minimal = GNUNET_YES; 3456 dhtlog_minimal = GNUNET_YES;
3469 3457
3470 dhtlog_handle = GNUNET_DHTLOG_connect (cfg); 3458 dhtlog_handle = GNUNET_DHTLOG_connect (cfg);
3471 if (dhtlog_handle == NULL) 3459 if (dhtlog_handle == NULL)
3472 { 3460 {
3473 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 3461 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3474 "Could not connect to mysql server for logging, will NOT log dht operations!"); 3462 "Could not connect to mysql server for logging, will NOT log dht operations!");
3475 ok = 3306; 3463 ok = 3306;
3476 return; 3464 return;
3477 }
3478 } 3465 }
3466 }
3479 3467
3480 stop_closest = GNUNET_CONFIGURATION_get_value_yesno (cfg, "dht", 3468 stop_closest = GNUNET_CONFIGURATION_get_value_yesno (cfg, "dht",
3481 "stop_on_closest"); 3469 "stop_on_closest");
@@ -3501,107 +3489,106 @@ run (void *cls, char * const *args, const char *cfgfile,
3501 if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string (cfg, "dht_testing", 3489 if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string (cfg, "dht_testing",
3502 "churn_file", 3490 "churn_file",
3503 &churn_filename)) 3491 &churn_filename))
3492 {
3493 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Reading churn data from %s\n",
3494 churn_filename);
3495 if (GNUNET_OK != GNUNET_DISK_file_test (churn_filename))
3496 {
3497 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Error reading churn file!\n");
3498 GNUNET_free_non_null (trialmessage);
3499 GNUNET_free (churn_filename);
3500 return;
3501 }
3502 if ((0 != STAT (churn_filename, &frstat)) || (frstat.st_size == 0))
3504 { 3503 {
3505 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Reading churn data from %s\n", 3504 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
3505 "Could not open file specified for churn data, ending test!");
3506 ok = 1119;
3507 GNUNET_free_non_null (trialmessage);
3508 GNUNET_free (churn_filename);
3509 return;
3510 }
3511
3512 churn_data = GNUNET_malloc_large (frstat.st_size);
3513 GNUNET_assert (churn_data != NULL);
3514 if (frstat.st_size != GNUNET_DISK_fn_read (churn_filename, churn_data,
3515 frstat.st_size))
3516 {
3517 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
3518 "Could not read file %s specified for churn, ending test!",
3506 churn_filename); 3519 churn_filename);
3507 if (GNUNET_OK != GNUNET_DISK_file_test (churn_filename)) 3520 GNUNET_free (churn_filename);
3508 { 3521 GNUNET_free (churn_data);
3509 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Error reading churn file!\n"); 3522 GNUNET_free_non_null (trialmessage);
3510 GNUNET_free_non_null(trialmessage); 3523 return;
3511 GNUNET_free(churn_filename); 3524 }
3512 return; 3525
3513 } 3526 GNUNET_free_non_null (churn_filename);
3514 if ((0 != STAT (churn_filename, &frstat)) || (frstat.st_size == 0))
3515 {
3516 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
3517 "Could not open file specified for churn data, ending test!");
3518 ok = 1119;
3519 GNUNET_free_non_null(trialmessage);
3520 GNUNET_free(churn_filename);
3521 return;
3522 }
3523 3527
3524 churn_data = GNUNET_malloc_large (frstat.st_size); 3528 buf = churn_data;
3525 GNUNET_assert(churn_data != NULL); 3529 count = 0;
3526 if (frstat.st_size != GNUNET_DISK_fn_read (churn_filename, churn_data, 3530 /* Read the first line */
3527 frstat.st_size)) 3531 while (count < frstat.st_size)
3532 {
3533 count++;
3534 if (((churn_data[count] == '\n')) && (buf != &churn_data[count]))
3535 {
3536 churn_data[count] = '\0';
3537 if (1 != sscanf (buf, "%u", &churn_rounds))
3528 { 3538 {
3529 GNUNET_log ( 3539 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3530 GNUNET_ERROR_TYPE_ERROR, 3540 "Failed to read number of rounds from churn file, ending test!\n");
3531 "Could not read file %s specified for churn, ending test!", 3541 ret = 4200;
3532 churn_filename); 3542 GNUNET_free_non_null (trialmessage);
3533 GNUNET_free (churn_filename); 3543 GNUNET_free_non_null (churn_data);
3534 GNUNET_free (churn_data);
3535 GNUNET_free_non_null(trialmessage);
3536 return; 3544 return;
3537 } 3545 }
3546 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3547 "Read %u rounds from churn file\n", churn_rounds);
3548 buf = &churn_data[count + 1];
3549 churn_array = GNUNET_malloc (sizeof (unsigned int) * churn_rounds);
3550 break; /* Done with this part */
3551 }
3552 }
3538 3553
3539 GNUNET_free_non_null(churn_filename); 3554 if (GNUNET_OK
3555 != GNUNET_CONFIGURATION_get_value_number (cfg, "dht_testing",
3556 "churns_per_round",
3557 &churns_per_round))
3558 {
3559 churns_per_round = (unsigned long long) churn_rounds;
3560 }
3540 3561
3541 buf = churn_data; 3562 line_number = 0;
3542 count = 0; 3563 while ((count < frstat.st_size) && (line_number < churn_rounds))
3543 /* Read the first line */ 3564 {
3544 while (count < frstat.st_size) 3565 count++;
3545 { 3566 if (((churn_data[count] == '\n')) && (buf != &churn_data[count]))
3546 count++; 3567 {
3547 if (((churn_data[count] == '\n')) && (buf != &churn_data[count])) 3568 churn_data[count] = '\0';
3548 {
3549 churn_data[count] = '\0';
3550 if (1 != sscanf (buf, "%u", &churn_rounds))
3551 {
3552 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3553 "Failed to read number of rounds from churn file, ending test!\n");
3554 ret = 4200;
3555 GNUNET_free_non_null(trialmessage);
3556 GNUNET_free_non_null(churn_data);
3557 return;
3558 }
3559 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3560 "Read %u rounds from churn file\n", churn_rounds);
3561 buf = &churn_data[count + 1];
3562 churn_array = GNUNET_malloc(sizeof(unsigned int) * churn_rounds);
3563 break; /* Done with this part */
3564 }
3565 }
3566 3569
3567 if (GNUNET_OK 3570 ret = sscanf (buf, "%u", &churn_array[line_number]);
3568 != GNUNET_CONFIGURATION_get_value_number (cfg, "dht_testing", 3571 if (1 == ret)
3569 "churns_per_round",
3570 &churns_per_round))
3571 { 3572 {
3572 churns_per_round = (unsigned long long) churn_rounds; 3573 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3574 "Read %u peers in round %u\n",
3575 churn_array[line_number], line_number);
3576 line_number++;
3573 } 3577 }
3574 3578 else
3575 line_number = 0;
3576 while ((count < frstat.st_size) && (line_number < churn_rounds))
3577 { 3579 {
3578 count++; 3580 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3579 if (((churn_data[count] == '\n')) && (buf != &churn_data[count])) 3581 "Error reading line `%s' in hostfile\n", buf);
3580 { 3582 buf = &churn_data[count + 1];
3581 churn_data[count] = '\0'; 3583 continue;
3582
3583 ret = sscanf (buf, "%u", &churn_array[line_number]);
3584 if (1 == ret)
3585 {
3586 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3587 "Read %u peers in round %u\n",
3588 churn_array[line_number], line_number);
3589 line_number++;
3590 }
3591 else
3592 {
3593 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3594 "Error reading line `%s' in hostfile\n", buf);
3595 buf = &churn_data[count + 1];
3596 continue;
3597 }
3598 buf = &churn_data[count + 1];
3599 }
3600 else if (churn_data[count] == '\n') /* Blank line */
3601 buf = &churn_data[count + 1];
3602 } 3584 }
3585 buf = &churn_data[count + 1];
3586 }
3587 else if (churn_data[count] == '\n') /* Blank line */
3588 buf = &churn_data[count + 1];
3603 } 3589 }
3604 GNUNET_free_non_null(churn_data); 3590 }
3591 GNUNET_free_non_null (churn_data);
3605 3592
3606 /* Check for a hostfile containing user@host:port triples */ 3593 /* Check for a hostfile containing user@host:port triples */
3607 if (GNUNET_OK 3594 if (GNUNET_OK
@@ -3613,74 +3600,70 @@ run (void *cls, char * const *args, const char *cfgfile,
3613 temphost = NULL; 3600 temphost = NULL;
3614 data = NULL; 3601 data = NULL;
3615 if (hostfile != NULL) 3602 if (hostfile != NULL)
3603 {
3604 if (GNUNET_OK != GNUNET_DISK_file_test (hostfile))
3605 GNUNET_DISK_fn_write (hostfile, NULL, 0, GNUNET_DISK_PERM_USER_READ
3606 | GNUNET_DISK_PERM_USER_WRITE);
3607 if ((0 != STAT (hostfile, &frstat)) || (frstat.st_size == 0))
3616 { 3608 {
3617 if (GNUNET_OK != GNUNET_DISK_file_test (hostfile)) 3609 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
3618 GNUNET_DISK_fn_write (hostfile, NULL, 0, GNUNET_DISK_PERM_USER_READ 3610 "Could not open file specified for host list, ending test!");
3619 | GNUNET_DISK_PERM_USER_WRITE); 3611 ok = 1119;
3620 if ((0 != STAT (hostfile, &frstat)) || (frstat.st_size == 0)) 3612 GNUNET_free_non_null (trialmessage);
3621 { 3613 GNUNET_free (hostfile);
3622 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, 3614 return;
3623 "Could not open file specified for host list, ending test!"); 3615 }
3624 ok = 1119;
3625 GNUNET_free_non_null(trialmessage);
3626 GNUNET_free(hostfile);
3627 return;
3628 }
3629 3616
3630 data = GNUNET_malloc_large (frstat.st_size); 3617 data = GNUNET_malloc_large (frstat.st_size);
3631 GNUNET_assert(data != NULL); 3618 GNUNET_assert (data != NULL);
3632 if (frstat.st_size 3619 if (frstat.st_size != GNUNET_DISK_fn_read (hostfile, data, frstat.st_size))
3633 != GNUNET_DISK_fn_read (hostfile, data, frstat.st_size)) 3620 {
3634 { 3621 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
3635 GNUNET_log ( 3622 "Could not read file %s specified for host list, ending test!",
3636 GNUNET_ERROR_TYPE_ERROR, 3623 hostfile);
3637 "Could not read file %s specified for host list, ending test!", 3624 GNUNET_free (hostfile);
3638 hostfile); 3625 GNUNET_free (data);
3639 GNUNET_free (hostfile); 3626 GNUNET_free_non_null (trialmessage);
3640 GNUNET_free (data); 3627 return;
3641 GNUNET_free_non_null(trialmessage); 3628 }
3642 return;
3643 }
3644 3629
3645 GNUNET_free_non_null(hostfile); 3630 GNUNET_free_non_null (hostfile);
3646 3631
3647 buf = data; 3632 buf = data;
3648 count = 0; 3633 count = 0;
3649 while (count < frstat.st_size - 1) 3634 while (count < frstat.st_size - 1)
3635 {
3636 count++;
3637 if (((data[count] == '\n')) && (buf != &data[count]))
3638 {
3639 data[count] = '\0';
3640 temphost = GNUNET_malloc (sizeof (struct GNUNET_TESTING_Host));
3641 ret = sscanf (buf, "%a[a-zA-Z0-9_]@%a[a-zA-Z0-9.]:%hd",
3642 &temphost->username, &temphost->hostname,
3643 &temphost->port);
3644 if (3 == ret)
3650 { 3645 {
3651 count++; 3646 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
3652 if (((data[count] == '\n')) && (buf != &data[count])) 3647 "Successfully read host %s, port %d and user %s from file\n",
3653 { 3648 temphost->hostname, temphost->port, temphost->username);
3654 data[count] = '\0';
3655 temphost = GNUNET_malloc(sizeof(struct GNUNET_TESTING_Host));
3656 ret = sscanf (buf, "%a[a-zA-Z0-9_]@%a[a-zA-Z0-9.]:%hd",
3657 &temphost->username, &temphost->hostname,
3658 &temphost->port);
3659 if (3 == ret)
3660 {
3661 GNUNET_log (
3662 GNUNET_ERROR_TYPE_DEBUG,
3663 "Successfully read host %s, port %d and user %s from file\n",
3664 temphost->hostname, temphost->port,
3665 temphost->username);
3666 }
3667 else
3668 {
3669 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3670 "Error reading line `%s' in hostfile\n", buf);
3671 GNUNET_free(temphost);
3672 buf = &data[count + 1];
3673 continue;
3674 }
3675 temphost->next = hosts;
3676 hosts = temphost;
3677 buf = &data[count + 1];
3678 }
3679 else if ((data[count] == '\n') || (data[count] == '\0'))
3680 buf = &data[count + 1];
3681 } 3649 }
3650 else
3651 {
3652 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3653 "Error reading line `%s' in hostfile\n", buf);
3654 GNUNET_free (temphost);
3655 buf = &data[count + 1];
3656 continue;
3657 }
3658 temphost->next = hosts;
3659 hosts = temphost;
3660 buf = &data[count + 1];
3661 }
3662 else if ((data[count] == '\n') || (data[count] == '\0'))
3663 buf = &data[count + 1];
3682 } 3664 }
3683 GNUNET_free_non_null(data); 3665 }
3666 GNUNET_free_non_null (data);
3684 if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (cfg, "dht_testing", 3667 if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (cfg, "dht_testing",
3685 "malicious_getters", 3668 "malicious_getters",
3686 &malicious_getters)) 3669 &malicious_getters))
@@ -3814,7 +3797,7 @@ run (void *cls, char * const *args, const char *cfgfile,
3814 == GNUNET_CONFIGURATION_get_value_number (cfg, "dht_testing", 3797 == GNUNET_CONFIGURATION_get_value_number (cfg, "dht_testing",
3815 "target_completions", 3798 "target_completions",
3816 &target_completions)) 3799 &target_completions))
3817 target_completions = 0; /* Not required, on stack */ 3800 target_completions = 0; /* Not required, on stack */
3818 3801
3819 if (GNUNET_YES == GNUNET_CONFIGURATION_get_value_yesno (cfg, "DHT_TESTING", 3802 if (GNUNET_YES == GNUNET_CONFIGURATION_get_value_yesno (cfg, "DHT_TESTING",
3820 "GET_FROM_SAME")) 3803 "GET_FROM_SAME"))
@@ -3839,12 +3822,12 @@ run (void *cls, char * const *args, const char *cfgfile,
3839 3822
3840 if (GNUNET_YES == GNUNET_CONFIGURATION_get_value_yesno (cfg, "DHT_TESTING", 3823 if (GNUNET_YES == GNUNET_CONFIGURATION_get_value_yesno (cfg, "DHT_TESTING",
3841 "MALICIOUS_SYBIL")) 3824 "MALICIOUS_SYBIL"))
3842 { 3825 {
3843 /* Set up the malicious target at random for this round */ 3826 /* Set up the malicious target at random for this round */
3844 GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, 3827 GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK,
3845 &sybil_target); 3828 &sybil_target);
3846 malicious_sybil = GNUNET_YES; 3829 malicious_sybil = GNUNET_YES;
3847 } 3830 }
3848 3831
3849 /* Create the bloomfilter for choosing which peers to set malicious */ 3832 /* Create the bloomfilter for choosing which peers to set malicious */
3850 3833
@@ -3916,9 +3899,9 @@ run (void *cls, char * const *args, const char *cfgfile,
3916 total_rounds = 1; 3899 total_rounds = 1;
3917 3900
3918 if ((GNUNET_SYSERR 3901 if ((GNUNET_SYSERR
3919 == GNUNET_CONFIGURATION_get_value_number (cfg, "dht_testing", 3902 == GNUNET_CONFIGURATION_get_value_number (cfg, "dht_testing",
3920 "target_total_connections", 3903 "target_total_connections",
3921 &target_total_connections)) 3904 &target_total_connections))
3922 || (target_total_connections == 0)) 3905 || (target_total_connections == 0))
3923 target_total_connections = connection_estimate (num_peers, 3906 target_total_connections = connection_estimate (num_peers,
3924 DEFAULT_BUCKET_SIZE); 3907 DEFAULT_BUCKET_SIZE);
@@ -3928,82 +3911,79 @@ run (void *cls, char * const *args, const char *cfgfile,
3928 "topology", 3911 "topology",
3929 &topology_str)) 3912 &topology_str))
3930 && (GNUNET_NO == GNUNET_TESTING_topology_get (&topology, topology_str))) 3913 && (GNUNET_NO == GNUNET_TESTING_topology_get (&topology, topology_str)))
3931 { 3914 {
3932 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 3915 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3933 "Invalid topology `%s' given for section %s option %s\n", 3916 "Invalid topology `%s' given for section %s option %s\n",
3934 topology_str, "TESTING", "TOPOLOGY"); 3917 topology_str, "TESTING", "TOPOLOGY");
3935 topology = GNUNET_TESTING_TOPOLOGY_CLIQUE; /* Defaults to NONE, so set better default here */ 3918 topology = GNUNET_TESTING_TOPOLOGY_CLIQUE; /* Defaults to NONE, so set better default here */
3936 } 3919 }
3937 3920
3938 if (GNUNET_OK 3921 if (GNUNET_OK
3939 != GNUNET_CONFIGURATION_get_value_string (cfg, "testing", "percentage", 3922 != GNUNET_CONFIGURATION_get_value_string (cfg, "testing", "percentage",
3940 &topology_percentage_str)) 3923 &topology_percentage_str))
3941 topology_percentage = 0.5; 3924 topology_percentage = 0.5;
3942 else 3925 else
3943 { 3926 {
3944 topology_percentage = atof (topology_percentage_str); 3927 topology_percentage = atof (topology_percentage_str);
3945 GNUNET_free(topology_percentage_str); 3928 GNUNET_free (topology_percentage_str);
3946 } 3929 }
3947 3930
3948 if (GNUNET_OK 3931 if (GNUNET_OK
3949 != GNUNET_CONFIGURATION_get_value_string (cfg, "testing", "probability", 3932 != GNUNET_CONFIGURATION_get_value_string (cfg, "testing", "probability",
3950 &topology_probability_str)) 3933 &topology_probability_str))
3951 topology_probability = 0.5; 3934 topology_probability = 0.5;
3952 else 3935 else
3953 { 3936 {
3954 topology_probability = atof (topology_probability_str); 3937 topology_probability = atof (topology_probability_str);
3955 GNUNET_free(topology_probability_str); 3938 GNUNET_free (topology_probability_str);
3956 } 3939 }
3957 3940
3958 if ((GNUNET_YES 3941 if ((GNUNET_YES
3959 == GNUNET_CONFIGURATION_get_value_string (cfg, "testing", 3942 == GNUNET_CONFIGURATION_get_value_string (cfg, "testing",
3960 "connect_topology", 3943 "connect_topology",
3961 &connect_topology_str)) 3944 &connect_topology_str))
3962 && (GNUNET_NO == GNUNET_TESTING_topology_get (&connect_topology, 3945 && (GNUNET_NO == GNUNET_TESTING_topology_get (&connect_topology,
3963 connect_topology_str))) 3946 connect_topology_str)))
3964 { 3947 {
3965 GNUNET_log ( 3948 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3966 GNUNET_ERROR_TYPE_WARNING, 3949 "Invalid connect topology `%s' given for section %s option %s\n",
3967 "Invalid connect topology `%s' given for section %s option %s\n", 3950 connect_topology_str, "TESTING", "CONNECT_TOPOLOGY");
3968 connect_topology_str, "TESTING", "CONNECT_TOPOLOGY"); 3951 }
3969 } 3952 GNUNET_free_non_null (connect_topology_str);
3970 GNUNET_free_non_null(connect_topology_str);
3971 3953
3972 if ((GNUNET_YES 3954 if ((GNUNET_YES
3973 == GNUNET_CONFIGURATION_get_value_string (cfg, "testing", 3955 == GNUNET_CONFIGURATION_get_value_string (cfg, "testing",
3974 "connect_topology_option", 3956 "connect_topology_option",
3975 &connect_topology_option_str)) 3957 &connect_topology_option_str))
3976 && (GNUNET_NO 3958 && (GNUNET_NO
3977 == GNUNET_TESTING_topology_option_get (&connect_topology_option, 3959 == GNUNET_TESTING_topology_option_get (&connect_topology_option,
3978 connect_topology_option_str))) 3960 connect_topology_option_str)))
3979 { 3961 {
3980 GNUNET_log ( 3962 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3981 GNUNET_ERROR_TYPE_WARNING, 3963 "Invalid connect topology option `%s' given for section %s option %s\n",
3982 "Invalid connect topology option `%s' given for section %s option %s\n", 3964 connect_topology_option_str, "TESTING",
3983 connect_topology_option_str, "TESTING", 3965 "CONNECT_TOPOLOGY_OPTION");
3984 "CONNECT_TOPOLOGY_OPTION"); 3966 connect_topology_option = GNUNET_TESTING_TOPOLOGY_OPTION_ALL; /* Defaults to NONE, set to ALL */
3985 connect_topology_option = GNUNET_TESTING_TOPOLOGY_OPTION_ALL; /* Defaults to NONE, set to ALL */ 3967 }
3986 } 3968 GNUNET_free_non_null (connect_topology_option_str);
3987 GNUNET_free_non_null(connect_topology_option_str);
3988 3969
3989 if (GNUNET_YES 3970 if (GNUNET_YES
3990 == GNUNET_CONFIGURATION_get_value_string ( 3971 == GNUNET_CONFIGURATION_get_value_string (cfg,
3991 cfg,
3992 "testing", 3972 "testing",
3993 "connect_topology_option_modifier", 3973 "connect_topology_option_modifier",
3994 &connect_topology_option_modifier_string)) 3974 &connect_topology_option_modifier_string))
3975 {
3976 if (sscanf (connect_topology_option_modifier_string, "%lf",
3977 &connect_topology_option_modifier) != 1)
3995 { 3978 {
3996 if (sscanf (connect_topology_option_modifier_string, "%lf", 3979 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3997 &connect_topology_option_modifier) != 1) 3980 _
3998 { 3981 ("Invalid value `%s' for option `%s' in section `%s': expected float\n"),
3999 GNUNET_log ( 3982 connect_topology_option_modifier_string,
4000 GNUNET_ERROR_TYPE_WARNING, 3983 "connect_topology_option_modifier", "TESTING");
4001 _("Invalid value `%s' for option `%s' in section `%s': expected float\n"),
4002 connect_topology_option_modifier_string,
4003 "connect_topology_option_modifier", "TESTING");
4004 }
4005 GNUNET_free (connect_topology_option_modifier_string);
4006 } 3984 }
3985 GNUNET_free (connect_topology_option_modifier_string);
3986 }
4007 3987
4008 if (GNUNET_YES 3988 if (GNUNET_YES
4009 != GNUNET_CONFIGURATION_get_value_string (cfg, "testing", 3989 != GNUNET_CONFIGURATION_get_value_string (cfg, "testing",
@@ -4012,30 +3992,29 @@ run (void *cls, char * const *args, const char *cfgfile,
4012 blacklist_transports = NULL; 3992 blacklist_transports = NULL;
4013 3993
4014 if ((GNUNET_YES 3994 if ((GNUNET_YES
4015 == GNUNET_CONFIGURATION_get_value_string (cfg, "testing", 3995 == GNUNET_CONFIGURATION_get_value_string (cfg, "testing",
4016 "blacklist_topology", 3996 "blacklist_topology",
4017 &blacklist_topology_str)) 3997 &blacklist_topology_str))
4018 && (GNUNET_NO == GNUNET_TESTING_topology_get (&blacklist_topology, 3998 && (GNUNET_NO == GNUNET_TESTING_topology_get (&blacklist_topology,
4019 blacklist_topology_str))) 3999 blacklist_topology_str)))
4020 { 4000 {
4021 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 4001 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
4022 "Invalid topology `%s' given for section %s option %s\n", 4002 "Invalid topology `%s' given for section %s option %s\n",
4023 topology_str, "TESTING", "BLACKLIST_TOPOLOGY"); 4003 topology_str, "TESTING", "BLACKLIST_TOPOLOGY");
4024 } 4004 }
4025 GNUNET_free_non_null(topology_str); 4005 GNUNET_free_non_null (topology_str);
4026 GNUNET_free_non_null(blacklist_topology_str); 4006 GNUNET_free_non_null (blacklist_topology_str);
4027 4007
4028 /* Set peers_left so we know when all peers started */ 4008 /* Set peers_left so we know when all peers started */
4029 peers_left = num_peers; 4009 peers_left = num_peers;
4030 4010
4031 /* Set up a task to end testing if peer start fails */ 4011 /* Set up a task to end testing if peer start fails */
4032 die_task 4012 die_task
4033 = GNUNET_SCHEDULER_add_delayed ( 4013 =
4034 GNUNET_TIME_relative_multiply ( 4014 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
4035 seconds_per_peer_start, 4015 (seconds_per_peer_start, num_peers),
4036 num_peers), 4016 &end_badly,
4037 &end_badly, 4017 "didn't generate all hostkeys within allowed startup time!");
4038 "didn't generate all hostkeys within allowed startup time!");
4039 4018
4040 if (dhtlog_handle == NULL) 4019 if (dhtlog_handle == NULL)
4041 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "dhtlog_handle is NULL!"); 4020 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "dhtlog_handle is NULL!");
@@ -4072,7 +4051,7 @@ run (void *cls, char * const *args, const char *cfgfile,
4072 if (dhtlog_handle != NULL) 4051 if (dhtlog_handle != NULL)
4073 dhtlog_handle->insert_trial (&trial_info); 4052 dhtlog_handle->insert_trial (&trial_info);
4074 4053
4075 GNUNET_free_non_null(trialmessage); 4054 GNUNET_free_non_null (trialmessage);
4076 4055
4077 hostkey_meter = create_meter (peers_left, "Hostkeys created ", GNUNET_YES); 4056 hostkey_meter = create_meter (peers_left, "Hostkeys created ", GNUNET_YES);
4078 peer_start_meter = create_meter (peers_left, "Peers started ", GNUNET_YES); 4057 peer_start_meter = create_meter (peers_left, "Peers started ", GNUNET_YES);
@@ -4080,36 +4059,34 @@ run (void *cls, char * const *args, const char *cfgfile,
4080 put_meter = create_meter (num_puts, "Puts completed ", GNUNET_YES); 4059 put_meter = create_meter (num_puts, "Puts completed ", GNUNET_YES);
4081 get_meter = create_meter (num_gets, "Gets completed ", GNUNET_YES); 4060 get_meter = create_meter (num_gets, "Gets completed ", GNUNET_YES);
4082 hostkey_start_time = GNUNET_TIME_absolute_get (); 4061 hostkey_start_time = GNUNET_TIME_absolute_get ();
4083 pg 4062 pg = GNUNET_TESTING_daemons_start (cfg,
4084 = GNUNET_TESTING_daemons_start ( 4063 peers_left,
4085 cfg, 4064 max_outstanding_connections,
4086 peers_left, 4065 max_concurrent_ssh,
4087 max_outstanding_connections, 4066 GNUNET_TIME_relative_multiply
4088 max_concurrent_ssh, 4067 (seconds_per_peer_start, num_peers),
4089 GNUNET_TIME_relative_multiply ( 4068 &hostkey_callback, NULL,
4090 seconds_per_peer_start, 4069 &peers_started_callback, NULL,
4091 num_peers), 4070 &topology_callback, NULL, hosts);
4092 &hostkey_callback, NULL,
4093 &peers_started_callback, NULL,
4094 &topology_callback, NULL, hosts);
4095 temphost = hosts; 4071 temphost = hosts;
4096 while (temphost != NULL) 4072 while (temphost != NULL)
4097 { 4073 {
4098 tempnext = temphost->next; 4074 tempnext = temphost->next;
4099 GNUNET_free (temphost->username); 4075 GNUNET_free (temphost->username);
4100 GNUNET_free (temphost->hostname); 4076 GNUNET_free (temphost->hostname);
4101 GNUNET_free (temphost); 4077 GNUNET_free (temphost);
4102 temphost = tempnext; 4078 temphost = tempnext;
4103 } 4079 }
4104} 4080}
4105 4081
4106int 4082int
4107main(int argc, char *argv[]) 4083main (int argc, char *argv[])
4108{ 4084{
4109 int ret; 4085 int ret;
4110 struct GNUNET_GETOPT_CommandLineOption options[] = 4086
4111 { 4087 struct GNUNET_GETOPT_CommandLineOption options[] = {
4112 GNUNET_GETOPT_OPTION_END }; 4088 GNUNET_GETOPT_OPTION_END
4089 };
4113 4090
4114 ret = GNUNET_PROGRAM_run (argc, argv, "gnunet-dht-driver", "nohelp", options, 4091 ret = GNUNET_PROGRAM_run (argc, argv, "gnunet-dht-driver", "nohelp", options,
4115 &run, &ok); 4092 &run, &ok);
@@ -4118,20 +4095,20 @@ main(int argc, char *argv[])
4118 GNUNET_CONTAINER_bloomfilter_free (malicious_bloom); 4095 GNUNET_CONTAINER_bloomfilter_free (malicious_bloom);
4119 4096
4120 if (ret != GNUNET_OK) 4097 if (ret != GNUNET_OK)
4121 { 4098 {
4122 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 4099 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
4123 "`gnunet-dht-driver': Failed with error code %d\n", ret); 4100 "`gnunet-dht-driver': Failed with error code %d\n", ret);
4124 } 4101 }
4125 4102
4126 /** 4103 /**
4127 * Need to remove base directory, subdirectories taken care 4104 * Need to remove base directory, subdirectories taken care
4128 * of by the testing framework. 4105 * of by the testing framework.
4129 */ 4106 */
4130 if (GNUNET_DISK_directory_remove (test_directory) != GNUNET_OK) 4107 if (GNUNET_DISK_directory_remove (test_directory) != GNUNET_OK)
4131 { 4108 {
4132 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 4109 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
4133 "Failed to remove testing directory %s\n", test_directory); 4110 "Failed to remove testing directory %s\n", test_directory);
4134 } 4111 }
4135 return ret; 4112 return ret;
4136} 4113}
4137 4114